Reorgainzed menus, added search by zip and city

This commit is contained in:
Andrew Scott 2022-08-08 03:50:24 -04:00
parent 0143e501db
commit 740af88a2a
Signed by: a
GPG key ID: 3EB62D0BBB8DB381
6 changed files with 142 additions and 70 deletions

View file

@ -8,15 +8,13 @@ import (
"strings"
)
// Display advanced menu and get user input
func advancedMenu(app *Application) {
var option string
// Menu loop
for option != "0" {
fmt.Print("\nAdvanced Menu\n-------------\n\n")
fmt.Printf("1. Change units (Default: imperial; Current: %s)\n", app.Config.Units)
fmt.Println("2. Enter precise location")
fmt.Println("3. Get historical data")
@ -30,49 +28,63 @@ func advancedMenu(app *Application) {
}
option = strings.TrimSuffix(input, "\n")
// Check user input
if option == "1" {
current := app.Config.Units
if current == "imperial" {
app.Config.Units = "metric"
} else {
app.Config.Units = "imperial"
}
fmt.Printf("\nChanged units from %s to %s...\n\n", current, app.Config.Units)
} else if option == "2" {
// Loop to validate location entered
var validLoc bool
for !validLoc {
getPreciseLocation(app)
getCurrent(app)
if app.Forecast.Weather.Temp != -500.00 {
validLoc = true
} else {
fmt.Println("I couldn't get any information for that location.")
fmt.Println("Are you sure the coordinates are valid?")
}
}
printWeather(app)
app.Forecast.Weather.Temp = -500.00
} else if option == "3" {
var validLoc bool
for !validLoc {
getPreciseLocation(app)
getDate(app)
getHistoricalData(app.Client, app)
if app.HistoricalForecast.Temp != -500.00 {
validLoc = true
} else {
fmt.Println("I couldn't get any information for that location.")
fmt.Println("Are you sure the coordinates are valid?")
}
}
printHistorical(app)
app.Forecast.Weather.Temp = -500.00
if option != "0" {
doAdvanced(app, option)
}
}
}
// Perform the users selected option from the advanced menu
func doAdvanced(app *Application, option string) {
var isValid bool
if option == "1" {
current := app.Config.Units
if current == "imperial" {
app.Config.Units = "metric"
} else {
app.Config.Units = "imperial"
}
fmt.Printf("\nChanged units from %s to %s...\n\n", current, app.Config.Units)
} else if option == "2" {
for !isValid {
getPreciseLocation(app)
getCurrent(app)
isValid = validateCurrent(app)
}
printWeather(app)
app.Forecast.Weather.Temp = -500.00
} else if option == "3" {
for !isValid {
getPreciseLocation(app)
getDate(app)
getHistoricalData(app.Client, app)
isValid = validateHistorical(app)
}
printHistorical(app)
app.Forecast.Weather.Temp = -500.00
}
}
// Validates results of queries by location
func validateCurrent(app *Application) bool {
var isValid bool
if app.Forecast.Weather.Temp != -500.00 {
isValid = true
} else {
fmt.Println("I couldn't get any information for that location.")
fmt.Println("Please double check the location you entered.")
}
return isValid
}
// Validates results of queries for historical data
func validateHistorical(app *Application) bool {
var isValid bool
if app.HistoricalForecast.Temp != -500.00 {
isValid = true
} else {
fmt.Println("I couldn't get any information for that location.")
fmt.Println("Please double check the location you entered.")
}
return isValid
}

View file

@ -9,18 +9,6 @@ import (
pb "codeberg.org/andcscott/weather-cli/proto"
)
type HistoricalForecast struct {
Temp float32 `json:"temp"`
FeelsLike float32 `json:"feels_like"`
Pressure uint `json:"pressure"`
Humidity uint `json:"humidity"`
Speed float32 `json:"wind_speed"`
}
type HistoricalData struct {
HistoricalForecast []HistoricalForecast `json:"data"`
}
// Get a date from the user and save it to the config
func getDate(app *Application) {

View file

@ -36,11 +36,10 @@ func getLocation(app *Application) {
app.Config.Latitude, app.Config.Longitude = loc[0], loc[1]
}
// Prompt user for location
// Prompt user for coordinates
func getPreciseLocation(app *Application) {
fmt.Print("\nEnter latitude: ")
reader := bufio.NewReader(os.Stdin)
input, err := reader.ReadString('\n')
if err != nil {
@ -49,10 +48,27 @@ func getPreciseLocation(app *Application) {
app.Config.Latitude = strings.TrimSuffix(input, "\n")
fmt.Print("\nEnter longitude: ")
input, err = reader.ReadString('\n')
if err != nil {
log.Println(err)
}
app.Config.Longitude = strings.TrimSuffix(input, "\n")
}
// Prompt user for zip code
func getZip(app *Application) {
fmt.Print("\nEnter 5-digit zip code: ")
_, err := fmt.Scanf("%s", &app.Config.Location)
if err != nil {
log.Println(err)
}
}
// Prompt user for city
func getCity(app *Application) {
fmt.Print("\nEnter city: ")
_, err := fmt.Scanf("%s", &app.Config.Location)
if err != nil {
log.Println(err)
}
}

View file

@ -31,6 +31,18 @@ type Forecast struct {
Wind Wind `json:"wind"`
}
type HistoricalForecast struct {
Temp float32 `json:"temp"`
FeelsLike float32 `json:"feels_like"`
Pressure uint `json:"pressure"`
Humidity uint `json:"humidity"`
Speed float32 `json:"wind_speed"`
}
type HistoricalData struct {
HistoricalForecast []HistoricalForecast `json:"data"`
}
type Date struct {
Year int32
Month int32

View file

@ -21,12 +21,18 @@ func mainMenu(app *Application) {
fmt.Println(" - Added gRPC back end for historical data")
fmt.Println(" - Option to search historical data added to UI")
mainMenuLoop(app)
}
// Display main menu and get user input
func mainMenuLoop(app *Application) {
var option string
// Menu loop
for option != "0" {
fmt.Print("\nMain Menu\n---------\n\n")
fmt.Println("1. Today's forecast (use current location, default)")
fmt.Println("2. Advanced options (Change units, precise location, etc.)")
fmt.Println("1. Use current location (default)")
fmt.Println("2. Search by zip code")
fmt.Println("3. Search by city")
fmt.Println("4. Advanced options")
fmt.Print("0. Exit\n\n")
// Read user input
@ -37,18 +43,29 @@ func mainMenu(app *Application) {
}
option = strings.TrimSuffix(input, "\n")
// Check user input
if option == "1" || option == "" {
switch option {
case "":
getLocation(app)
getCurrent(app)
printWeather(app)
} else if option == "2" {
case "1":
getLocation(app)
getCurrent(app)
printWeather(app)
case "2":
getZip(app)
getCurrentByLoc(app)
printWeather(app)
case "3":
getCity(app)
getCurrentByLoc(app)
printWeather(app)
case "4":
advancedMenu(app)
} else if option == "0" {
case "0":
return
} else {
default:
fmt.Print("\nOops! An error occurred, please choose a valid option.\n\n")
}
}
}

View file

@ -2,6 +2,7 @@ package main
import (
"encoding/json"
"fmt"
"io/ioutil"
"log"
"net/http"
@ -16,6 +17,32 @@ func getCurrent(app *Application) {
key := "&appid=" + app.Config.ApiKey
url := "https://pro.openweathermap.org/data/2.5/weather?" + lat + lon + units + key
res, err := http.Get(url)
if err != nil {
log.Println(err)
}
defer res.Body.Close()
fmt.Println(res.Body)
body, err := ioutil.ReadAll(res.Body)
if err != nil {
log.Println(err)
}
err = json.Unmarshal(body, &app.Forecast)
if err != nil {
log.Println(err)
}
}
// Query forecast by zip code
func getCurrentByLoc(app *Application) {
zip := app.Config.Location
units := "&units=" + app.Config.Units
key := "&appid=" + app.Config.ApiKey
url := "https://pro.openweathermap.org/data/2.5/weather?q=" + zip + units + key
res, err := http.Get(url)
if err != nil {
log.Println(err)