Begin converting Extended to FiveDay & adding advanced request opts

This commit is contained in:
Andrew Scott 2022-09-01 02:09:45 -04:00
parent bcbe199848
commit 8f7897d41b
Signed by: a
GPG key ID: 3EB62D0BBB8DB381
3 changed files with 50 additions and 16 deletions

View file

@ -15,8 +15,8 @@ import (
func (s *Server) Current(ctx context.Context, in *pb.RequestCurrent) (*pb.SendCurrent, error) {
log.Println("'Current' function called...")
url := "https://pro.openweathermap.org/data/2.5/weather?"
lat, lon := getLocation(in.City, s.ApiKey)
url := "https://api.openweathermap.org/data/2.5/weather?"
lat, lon, err := getLocation(in.Location.String(), s.ApiKey)
units := "&units=imperial"
token := "&appid=" + s.ApiKey

View file

@ -10,20 +10,49 @@ import (
pb "codeberg.org/andcscott/OpenWeatherMap-gRPC-API/proto"
)
func (s *Server) createFiveDayUrl(in *pb.RequestFiveDay) (string, error) {
var lat, lon float32
var units string
var err error
url := "https://api.openweathermap.org/data/2.5/forecast?"
switch in.Units {
case pb.Units_UNITS_IMPERIAL:
units = "imperial"
case pb.Units_UNITS_METRIC:
units = "metric"
default:
units = "standard"
}
if in.LocationType == pb.LocationType_LOCATION_TYPE_COORDS {
lat = in.Location.GetCoords().Latitude
lon = in.Location.GetCoords().Longitude
} else {
lat, lon, err = getLocation(in.Location.String(), s.ApiKey)
if err != nil {
return "", fmt.Errorf("Error: %v\n", err)
}
}
url = url + fmt.Sprintf("lat=%f", lat) + fmt.Sprintf("&lon=%f", lon) + units
return url, err
}
// Receives a gRPC request for an extended forecast
// Returns a SendExtended message with the forecast in JSON
func (s *Server) Extended(ctx context.Context, in *pb.RequestExtended) (*pb.SendExtended, error) {
func (s *Server) FiveDay(ctx context.Context, in *pb.RequestFiveDay) (*pb.SendFiveDay, error) {
log.Println("'Extended' function called...")
url := "https://pro.openweathermap.org/data/2.5/forecast/daily?"
lat, lon := getLocation(in.City, s.ApiKey)
days := "&cnt=" + fmt.Sprint(in.Days)
units := "&units=imperial"
url, err := s.createFiveDayUrl(in)
if err != nil {
return nil, err
}
token := "&appid=" + s.ApiKey
url = url + fmt.Sprintf("lat=%f", lat) + fmt.Sprintf("&lon=%f", lon) + units + days + token
res, err := http.Get(url)
res, err := http.Get(url + token)
if err != nil {
log.Printf("Error fetching extended weather: %v\n", err)
}
@ -34,7 +63,7 @@ func (s *Server) Extended(ctx context.Context, in *pb.RequestExtended) (*pb.Send
log.Printf("Error reading extending weather: %v\n", err)
}
return &pb.SendExtended{
return &pb.SendFiveDay{
Payload: string(body),
}, nil
}

View file

@ -3,6 +3,7 @@ package main
import (
"context"
"encoding/json"
"fmt"
"io/ioutil"
"log"
"net/http"
@ -20,7 +21,10 @@ type Coordinates struct {
func (s *Server) Location(ctx context.Context, in *pb.RequestLocation) (*pb.SendLocation, error) {
log.Println("'Location' function called...")
lat, lon := getLocation(in.City, s.ApiKey)
lat, lon, err := getLocation(in.Location.String(), s.ApiKey)
if err != nil {
return nil, fmt.Errorf("Error: %v\n", err)
}
return &pb.SendLocation{
Latitude: lat,
@ -31,12 +35,12 @@ func (s *Server) Location(ctx context.Context, in *pb.RequestLocation) (*pb.Send
// Used internally to fetch precise locations
// Receives the city name and the server's API key
// Returns the latitude and longitude for the given location
func getLocation(city string, key string) (float32, float32) {
func getLocation(location string, key string) (float32, float32, error) {
url := "http://api.openweathermap.org/geo/1.0/direct?q="
token := "&appid=" + key
url = url + city + token
url = url + location + token
res, err := http.Get(url)
if err != nil {
@ -52,7 +56,8 @@ func getLocation(city string, key string) (float32, float32) {
coords := []Coordinates{}
err = json.Unmarshal(body, &coords)
if err != nil {
log.Printf("Error decoding JSON: %v\n", err)
log.Printf("Error decoding geolocation JSON: %v\n", err)
}
return coords[0].Latitude, coords[0].Longitude
return coords[0].Latitude, coords[0].Longitude, err
}