问题描述
我必须拨打http呼叫外部服务。通过发送地址,返回纬度和经度坐标。问题是,如果该地址是俄语或法语,则会出现类似以下错误:
URI must be ascii only "http://nominatim.openstreetmap.org/?format=json&addressdetails=1&q={Barrage de G\u00E9nissiat,Rue marcel Paul,Injoux,Franclens,Nantua,Ain,Auvergne-Rh\u00F4ne-Alpes,Francia metropolitana,74910,Francia}&format=json"
我的代码是:
url = "http://nominatim.openstreetmap.org/?format=json&addressdetails=1&q={"+ address_search +"}&format=json";
response = Faraday.get url
变量address_search是:
Barrage de Génissiat,Auvergne-Rhône-Alpes,Francia
法拉第只是发出HTTP请求的工具,这并不奇怪。我必须操纵URL。你有什么建议吗?
编辑:
print Rails.logger.info "body " + response.body
print Rails.logger.info response.status
print Rails.logger.info response.env.url
这是输出
body []
200
https://nominatim.openstreetmap.org/?addressdetails=1&format=json&q=Barrage+de+G%C3%A9nissiat%2C+Rue+marcel+Paul%2C+Injoux%2C+Franclens%2C+Nantua%2C+Ain%2C+Auvergne-Rh%C3%B4ne-Alpes%2C+Francia+metropolitana%2C+74910%2C+Francia
Rendering homes/index.html.erb within layouts/application
解决方法
查询应进行编码,您可以手动进行:
query = 'Barrage de Génissiat,Rue Marcel Paul,Injoux,Franclens,Nantua,Ain,Auvergne-Rhône-Alpes,Francia metropolitana,74910,Francia'
address_search = URI.escape(query)
url = "https://nominatim.openstreetmap.org/?format=json&addressdetails=1&q=#{address_search}&format=json"
response = Faraday.get(url)
或者将工作留给法拉第:
query = 'Barrage de Génissiat,Francia'
connection = Faraday.new('https://nominatim.openstreetmap.org')
response = connection.get do |request|
request.params = { format: 'json',addressdetails: 1,q: query }
end
以下是回复:
=> #<Faraday::Response:0x0000556afc452060
@env=
#<struct Faraday::Env
method=:get,body=
"[{\"place_id\":104161692,\"licence\":\"Data \xC2\xA9 OpenStreetMap contributors,ODbL 1.0. https://osm.org/copyright\",\"osm_type\":\"way\",\"osm_id\":80667335,\"boundingbox\":[\"46.0516289\",\"46.0531641\",\"5.8112371\",\"5.81
4139\"],\"lat\":\"46.0523765\",\"lon\":\"5.812744291298651\",\"display_name\":\"Barrage de G\xC3\xA9nissiat,Auvergne-Rh\xC3\xB4ne-Alpes,France m\xC3\xA9tropolitaine,France\",\"class\":\"tourism\",\"type\":\"attraction\",\"importance\":1.7983764706069638,\"icon\":\"https://nominatim.openstreetmap.org/images/mapicons/poi_point_of_interest.p.20.png\",\"address\":{\"tourism\":\"Barrage de G\xC3\xA9nissiat\
",\"road\":\"Rue Marcel Paul\",\"suburb\":\"Injoux\",\"village\":\"Franclens\",\"municipality\":\"Nantua\",\"county\":\"Ain\",\"state\":\"Auvergne-Rh\xC3\xB4ne-Alpes\",\"country\":\"France\",\"postcode\":\"74910\",\"country_code\":\
"fr\"}}]",url=
#<URI::HTTPS https://nominatim.openstreetmap.org/?addressdetails=1&format=json&q=Barrage+de+G%C3%A9nissiat%2C+Rue+Marcel+Paul%2C+Injoux%2C+Franclens%2C+Nantua%2C+Ain%2C+Auvergne-Rh%C3%B4ne-Alpes%2C+Francia+metropolitana%2C+74910%2C+Francia>,request=#<struct Faraday::RequestOptions params_encoder=nil,proxy=nil,bind=nil,timeout=nil,open_timeout=nil,write_timeout=nil,boundary=nil,oauth=nil,context=nil>,request_headers={"User-Agent"=>"Faraday v0.17.3"},ssl=
#<struct Faraday::SSLOptions
verify=true,ca_file=nil,ca_path=nil,verify_mode=nil,cert_store=nil,client_cert=nil,client_key=nil,certificate=nil,private_key=nil,verify_depth=nil,version=nil,min_version=nil,max_version=nil>,parallel_manager=nil,params=nil,response=#<Faraday::Response:0x0000556afc452060 ...>,response_headers=
{"server"=>"nginx","date"=>"Thu,15 Oct 2020 19:42:53 GMT","content-type"=>"application/json; charset=UTF-8","transfer-encoding"=>"chunked","connection"=>"close","access-control-allow-origin"=>"*","access-control-allow-methods"=>"OPTIONS,GET"},status=200,reason_phrase="OK">,@on_complete_callbacks=[]>
请确保您使用https
模式,否则,您将获得带有重定向的响应。
我使用以下代码:
query = "Barrage de Génissiat,Francia"
connection = Faraday.new('https://nominatim.openstreetmap.org')
response = connection.get do |request|
request.params = { format: 'json',q: query }
end
print Rails.logger.info response.body
然后我收到[]
。