-
Notifications
You must be signed in to change notification settings - Fork 2
/
maps_client.go
130 lines (104 loc) · 3.33 KB
/
maps_client.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
package main
////////////////////////////////////////////////////////////////////////////////
// Copyright (c) 2017-2018, Gianluca Fiore
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
////////////////////////////////////////////////////////////////////////////////
// Query the Google Maps API for results matching a specific category of places around Krakow.
// This was a base for a full web app that never saw the light
import (
"flag"
"log"
"fmt"
"os"
"time"
"bytes"
"encoding/csv"
"googlemaps.github.io/maps"
"golang.org/x/net/context"
)
const (
version float64 = 0.1
)
var api_key string
var search_name string
func init() {
flag.StringVar(&api_key, "apikey", " ", "the api key for Google Maps")
flag.StringVar(&api_key, "a", " ", "the api key for Google Maps")
flag.StringVar(&search_name, "search", " ", "search query for Maps")
flag.StringVar(&search_name, "s", " ", "search query for Maps")
flag.Parse()
}
func JsonToCsv(s string, r ...maps.PlacesSearchResponse) {
// creatte a buffer to concatenate the result's filename to
var buffer bytes.Buffer
buffer.WriteString(s)
buffer.WriteString("-results.csv")
// Create an output csv file
f, err := os.Create(buffer.String())
if err != nil {
log.Fatal(err)
}
defer f.Close()
// Create a csv writer
w := csv.NewWriter(f)
// if multiple responses given, iterate on them all
for _, params := range r {
for _, obj := range params.Results {
var record []string
latitude := fmt.Sprintf("%.4f", obj.Geometry.Location.Lat)
longitude := fmt.Sprintf("%.4f", obj.Geometry.Location.Lng)
record = append(record, obj.Name, obj.FormattedAddress, latitude, longitude)
w.Write(record)
}
w.Flush()
}
}
func main() {
Krakow := &maps.LatLng{50.06, 19.94}
c, err := maps.NewClient(maps.WithAPIKey(api_key))
if err != nil {
log.Fatal("error! %s", err)
}
var txtresp, txtresp2, txtresp3 maps.PlacesSearchResponse
txtr := &maps.TextSearchRequest{
Query: search_name,
Location: Krakow,
Radius: 20000,
Language: "english"}
txtresp, err = c.TextSearch(context.Background(), txtr)
if err != nil {
log.Fatal("error while doing a Text Search on Maps: %s", err)
}
// Check if there are more than 20 results by checking the NextPageToken
// existence. Up to 3 pages for up to 60 results.
// Long break between the next request as otherwise Maps API reply with
// "INVALID REQUEST" as there needs to be given time to the NextPageToken to
// be generated
//
// Yes it is ugly. Yes it works.
//
if len(txtresp.NextPageToken) > 0 {
time.Sleep(10000 * time.Millisecond)
txtr2 := &maps.TextSearchRequest{
PageToken: txtresp.NextPageToken}
txtresp2, err = c.TextSearch(context.Background(), txtr2)
if err != nil {
log.Fatal("error while doing a Text Search2 on Maps: %s", err)
}
if len(txtresp2.NextPageToken) > 0 {
time.Sleep(10000 * time.Millisecond)
txtr3 := &maps.TextSearchRequest{
PageToken: txtresp2.NextPageToken}
txtresp3, err = c.TextSearch(context.Background(), txtr3)
if err != nil {
log.Fatal("error while doing a Text Search3 on Maps: %s", err)
}
}
}
JsonToCsv(search_name, txtresp, txtresp2, txtresp3)
}