JavaScript:我如何创buildJSONP?
我有两个域,example1.com和example2.com
从example1.com,我想调用我在example2.com上的JSON API。 知道这是不允许的,我想到了 – 这正是JSON P创build的原因。
问题是,我如何修改我的JSON API使其具有JSONP的能力?
基本上,我如何创buildcallbackapi?
UPDATE
我的服务器端语言是PHP
很简单。 只需在GET中接受一个名为callback
的参数即可。
然后将callbackJavaScript函数包装在数据中。
PHP中的示例:
<?php $data = '{}'; // json string if(array_key_exists('callback', $_GET)){ header('Content-Type: text/javascript; charset=utf8'); header('Access-Control-Allow-Origin: http://www.example.com/'); header('Access-Control-Max-Age: 3628800'); header('Access-Control-Allow-Methods: GET, POST, PUT, DELETE'); $callback = $_GET['callback']; echo $callback.'('.$data.');'; }else{ // normal JSON string header('Content-Type: application/json; charset=utf8'); echo $data; }
它的思想是简单地返回一个JavaScript文件,该文件用JSON对象调用callback函数作为JavaScriptcallback函数的第一个参数。
您可以使用内置的json_encode()
函数从PHP中的数组和对象创buildJSONstring(上述示例中的$data
)。
要使用JSONP服务,您可以使用<script>
标签:
<script> function receiver(data){ console.log(data); } </script> <script src="data-service.php?callback=receiver"></script>
你需要一个服务器端的语言,callback参数只是一个GET参数,你读的参数,你包装的JSON响应到函数调用,你打印它像这个callback(jsonResponse);
。
因为您没有提及任何服务器端语言,所以我给你留下了一个使用Python的极简主义例子:
import os import cgi form = cgi.FieldStorage() callback = form.getvalue('callback','') address = cgi.escape(os.environ["REMOTE_ADDR"]) json = '{"ip": "'+address+'", "address":"'+address+'"}' #Allow cross domain XHR print 'Access-Control-Allow-Origin: *' print 'Access-Control-Allow-Methods: GET' if callback != '': print 'Content-Type: application/javascript' result = callback+'('+json+');' else: print 'Content-Type: application/json' result = json print '' print result
这是用于检索由Zach制作的客户端IP地址的小型JSONP服务的代码,它位于Google App Engine上 。
毛里斯已经给了你一个工作的例子。 我只会补充说,你应该检查一个callback
参数是否存在和非空,如果没有,返回的JSON数据是没有括号。 所以基本上你的api将会是JSON,并提供了作为JSON-P的callback
。
要使用JSON-P webservice,除非使用YUI或jQuery之类的框架,否则可以简单地创build一个脚本节点,并将其src
属性设置为指向web服务。 请记住从dom中删除节点,然后再重复一次,因为此dynamic脚本节点只能单独使用。
我知道我迟到了,并且在其中一个答案中有关于代码安全性的评论。 这里有一个很好的文章:
http://www.geekality.net/2010/06/27/php-how-to-easily-provide-json-and-jsonp/
这里是你应该运行的代码:
<?php header('content-type: application/json; charset=utf-8'); function is_valid_callback($subject) { $identifier_syntax = '/^[$_\p{L}][$_\p{L}\p{Mn}\p{Mc}\p{Nd}\p{Pc}\x{200C}\x{200D}]*+$/u'; $reserved_words = array('break', 'do', 'instanceof', 'typeof', 'case', 'else', 'new', 'var', 'catch', 'finally', 'return', 'void', 'continue', 'for', 'switch', 'while', 'debugger', 'function', 'this', 'with', 'default', 'if', 'throw', 'delete', 'in', 'try', 'class', 'enum', 'extends', 'super', 'const', 'export', 'import', 'implements', 'let', 'private', 'public', 'yield', 'interface', 'package', 'protected', 'static', 'null', 'true', 'false'); return preg_match($identifier_syntax, $subject) && ! in_array(mb_strtolower($subject, 'UTF-8'), $reserved_words); } $data = array(1, 2, 3, 4, 5, 6, 7, 8, 9); $json = json_encode($data); # JSON if no callback if( ! isset($_GET['callback'])) exit($json); # JSONP if valid callback if(is_valid_callback($_GET['callback'])) exit("{$_GET['callback']}($json)"); # Otherwise, bad request header('status: 400 Bad Request', true, 400);
// Adds script tag to head of the page function addScriptToHead(source, code, type) { var script = document.createElement('script'); if (type === 'js') { script.setAttribute('type', 'text/javascript'); } if (source !== '') { script.setAttribute('src', source); } if (code !== '') { if (document.all && !window.opera) { script.text = code; } else { script.innerHTML = code; } } document.getElementsByTagName('head')[0].appendChild(script); } // Callback function function addScriptToHead(any_param) { // do whatever needs to be done } //call example addScriptToHead('http://url_to_receiver_script/index.php¶m=anything', '', 'js');
///callback脚本应该返回callback函数的名字,即如果你在浏览器中input
HTTP://url_to_receiver_script/index.php¶m=anything
它应该只返回一个文本(现有处理函数的名称):addScriptToHead(any_param)
像任何浏览器中的时钟一样工作。
容易与jQuery,这是客户端:
$.ajax({ dataType: 'jsonp', data: "somedata="+somevalue, //this is very important since it's the callback we will and that allow cross domain jsonp: 'jsonp_callback', url: 'http://example2.com', //function we trigger on success success: ParseJson //error handling not working with jsonP //error: handleError }); function ParseJson(data) { for (var key in data) { if (data.hasOwnProperty(key)) { alert(key + " -> " + data[key]); } } }
并确保你从服务器端得到正确的JSON;
不要忘记返回jsonp_callback参数,否则将无法正常工作!
这就是真的。
这里的例子http://www.insideria.com/2009/03/what-in-the-heck-is-jsonp-and.html基本上;
<script src=".../example2...?output=json;callback=loadit"></script> <script> alert( "I got this from example2 " + loadit); </script>
您可以使用简单的JSON for PHP来伪造它! 它简化了一切!
<?php include('../includes/json.php'); $json = new json('callback', 'myCallback'); $object = new stdClass(); $object->FirstName = 'John'; $object->LastName = 'Doe'; $array = array(1,'2', 'Pieter', true); $jsonOnly = '{"Hello" : "darling"}'; // Add objects to send $json->add('status', '200'); $json->add("worked"); $json->add("things", false); $json->add('friend', $object); $json->add("arrays", $array); $json->add("json", $jsonOnly, false); /* Expected result : myCallback({ "status": "200", "worked": true, "things": false, "friend": { "FirstName": "John", "LastName": "Doe" }, "arrays": [ 1, "2", "Pieter", true ], "json": { "Hello": "darling" } }); */ $json->send(); ?>