从JavaScript返回JSON到Python
我正在写一个简单的App Engine应用。
我有一个简单的页面,用户可以在谷歌地图上移动一个标记。每次用户放下标记时,我想把经纬度返回给我的Python应用。
function initialize() {
... // Init map
var marker = new GMarker(center, {draggable: true});
GEvent.addListener(marker, "dragend", function() {
// I want to return the marker.x/y to my app when this function is called ..
});
}
根据我(确实有限的)知识,我应该:
1). 在上面的监听器回调中返回一个包含我需要数据的JSON结构。
2). 在我的webapp.RequestHandler处理类中,尝试在post方法中获取这个JSON结构。
我非常希望能在不重新加载页面的情况下将这个JSON数据传回应用(因为到目前为止,我使用各种post/form.submit方法时,页面都会重新加载)。
有没有人能给我一些伪代码或示例,告诉我怎么实现我想要的功能?
谢谢。
2 个回答
为了防止页面重新加载,我们可以在网页上使用AJAX来处理这个问题。
如果你用jquery的话,可以这样做:
$("#testform").submit(function() {
// post the form values via AJAX...
var postdata = {lat: $("#lat").val(), long: $("#long").val()} ;
$.post('/submit', postdata, function(data) {
// and set the location with the result
$("#location").html(data['location']) ;
});
return false ;
});
假设你有一个这样的网页:
<p>Enter lat and long:</p>
<form id="testform" action="#" method="post">
<p>
<label for="lat">Lat:</label>
<input type="text" id="lat" /> <br />
<label for="long">Long:</label>
<input type="text" id="long" /> <br />
<input type="submit" value="Get Location" />
</p>
</form>
<p>The location is:</p><p id="location">(enter lat and long above)</p>
然后让Python代码返回一个包含位置的JSON字典。
最后,我建议你设置一个优雅的备用方案:如果用户禁用了JavaScript,就正常提交到比如说 /getlocation
并重新加载页面;然后让JavaScript覆盖这个操作,提交到一个特殊的URL,这个URL会返回JSON数据,比如 /getlocationajax
。
如果你不想让页面自动更新,那你需要用到 XMLHttpRequest。在这个例子中,我使用了客户端的 function Request(function_name, opt_argv)
和服务器端的 RPCHandler
,这些来自于这个 Google App Engine 的例子。我还没有测试过这个,但大概会是这样的:
客户端的 Javascript
function initialize() {
... // Init map
var marker = new GMarker(center, {draggable: true});
GEvent.addListener(marker, "dragend", function(position) {
Request('update_marker_position', [ unique_identifier, position.lat(), position.lng() ] );
});
}
服务器端的 Python
# Create database model for LatLng position
class LatLng(db.Model):
lat = db.IntegerProperty()
lng = db.IntegerProperty()
...
class RPCMethods:
""" Defines the methods that can be RPCed.
NOTE: Do not allow remote callers access to private/protected "_*" methods.
"""
def update_marker_position(self, *args):
# args[0] - unique identifier, say GAE db key
# args[1] - lat
# args[2] - lng
# Note: need to do some checking that lat and lng are valid
# Retrieve key and update position
position = LatLng.get(db.Key(args[0])
if position:
position.lat = args[1]
position.lng = args[2]
else:
position = LatLng(
lat= args[1],
lng= args[2]
)
position.put()
payload = {
'lat': args[1],
'lng': args[2],
}
return payload
你需要在页面加载时创建数据库条目,并在客户端保存数据库的键。你也可以使用其他唯一的标识符。在这个例子中,我假设你把它存储为一个全局变量 'unique_identifier'。
另外,你还需要添加一个回调函数来处理返回的数据(里面有 'lat' 和 'lng' 这两个值)。根据这个例子,我认为你只需要把你的回调函数作为 opt_argv 数组中的第一个参数传给 Request。希望这能帮到你。