2024/03/26

つないでみよう:#10)Google マップ - Place API で一番近隣の場所を取得

いよいよ、Place API を使用したサンプルプログラムを作成します。今回は座標とキーワードをもとに一番近隣の場所を取得します。


メインルーチン

新しいエージェントを作成、メインルーチンを記述します。検索地点を準備して、一番近隣の場所名を取得する関数 xGetNearestPlaceName をコールして結果を表示します。関数の最後の引数で検索キーワードを指定しています。

Option Declare
Private xns As NotesSession

Sub Initialize
   Dim dLat As Double '緯度
   Dim dLng As Double '経度
   Dim sName As String

   Set xns = New NotesSession
   
   '検索地点の準備
   dLat = 34.683742526906634
   dLng = 135.49698067096077
   
   '検索の実行と表示
   sName = xGetNearestPlaceName(dLat, dLng, "鳥貴族")
   MsgBox sName, 64
End Sub


一番近隣の場所の取得

Place API の Nearby Search を使用して、一番近隣の場所の取得する関数がこちらです。

URL を準備して、GET の HTTP リクエストを実行し、レスポンスを NotesJSONNavigator オブジェクトで取得させています。

検索結果は、まず Results エレメントを取得、そこから 1 件目(一番近隣の場所)のエレメントを取得しています。

Function xGetNearestPlaceName(ByVal vdLat As Double, vdLng As Double, ByVal vsKeyword As String) As String
   Dim sURL As String
   Dim sPram As String
   Dim http As NotesHTTPRequest
   Dim jnav As NotesJSONNavigator
   Dim jeResults As NotesJSONElement
   Dim jePlace As NotesJSONElement

   'URL の準備
   sURL = "https://maps.googleapis.com/maps/api/place/nearbysearch/json"
   sPram = xGetPram(vdLat, vdLng, vsKeyword)
   sURL = sURL & "?" & sPram

   'API に接続しレスポンスを JSON で取得
   Set http = xns.CreateHttpRequest()
   http.PreferJSONNavigator = True
   Set jnav = http.Get(sURL)

   '一番近隣の地点情報を取得
   Set jeResults = jnav.GetElementByName("results")
   Set jePlace = xGetPlace_Nth(jeResults, 1)

   '地点情報から名称の取得
   xGetNearestPlaceName = xGetPlaceName(jePlace)
End Function


レスポンスの JSON は以下のようなイメージでした。コードと比較してもらうとわかりやすいかと思います。


パラメータ文字列の作成

xGetPram 関数は URL に付加するパラメータを生成する関数です。引数で指定した検索条件のほかに、API キーや言語設定、ソートの設定を追加して返しています。

なお、検索キーワードには2バイト文字が入ることを前提に @URLEncode 関数を使用して変換しています。

Function xGetPram(ByVal vdLat As Double, ByVal vdLng As Double, ByVal vsKeyword As String) As String
   Dim s As String
   Dim v As Variant

   s = "key=xxxxxxxxxxx"   ' ← ここに API Key をセット
   s = s & "&" & "location=" & CStr(vdLat) & "," & CStr(vdLng)
   'キーワードは設定がある場合のみ 
   If vsKeyword <> "" Then
      '全角文字に対応するためエンコード
      v = Evaluate(|@URLEncode("UTF-8"; "| & vsKeyword & |")|)
      s = s & "&" & "keyword=" & v(0)

   End If
   s = s & "&" & "language=ja"
   s = s & "&" & "rankby=distance"

   xGetPram = s
End Function


n 件目の取得

xGetPlace_Nth 関数は Results エレメントの中らから引数で指定した地点情報を返します。

今回のサンプルでは1件目しか使用しませんが汎用的に使えるよう要素数の確認などエラーチェックを行っています。

Function xGetPlace_Nth(vjeResults As NotesJSONElement, ByVal viIndex As Integer) As NotesJSONElement
   Dim ja As NotesJSONArray

   If vjeResults Is Nothing Then Exit Function
   If viIndex < 1 Then Exit Function
   If vjeResults.Type = Jsonelem_type_array Then
      Set ja = vjeResults.Value
      If ja.Size < viIndex Then Exit Function

      Set xGetPlace_Nth = ja.GetNthElement(viIndex)
   End If
End Function


地点名の取得

最後は、地点情報から場所の名称である name エレメントの値を取得する関数です。処理自体は簡単なのですが、こちらもエラー処理を追加してあります。

Function xGetPlaceName(vjePlace As NotesJSONElement) As String
   Dim je As NotesJSONElement
   Dim jobj As NotesJSONObject

   On Error GoTo Err_Proc

   Set jobj = vjePlace.Value
   Set je = jobj.GetElementByName("name")
   xGetPlaceName = CStr(je.Value)

Exit_Proc:
   Exit Function

Err_Proc:
   Resume Exit_Proc
End Function


前回 連載:つないでみよう 次回


0 件のコメント:

コメントを投稿