+ The JSONP Utility is a specialized API for communicating with web
+ services that provide JSON responses wrapped in a callback
+ function. A typical JSONP request URL might look like
+ "http://example.com/service.php?callback=handleData" and
+ receive a text response in the form of
+ handleData({"records":[....]});.
+
+ The nature of YUI 3's sandbox model complicates JSONP transactions
+ because JSONP relies on a global access point to process the
+ response, but YUI 3 implementation code is typically wrapped in a
+ use(...) callback and is therefore not globally
+ accessible. The JSONP module provides a proxy system for
+ channeling JSONP responses back into your YUI instance sandbox.
+
+ Security Note: JSONP is an inherently unsecure + communication method, since it involves the transfer of unvalidated + JavaScript. It is by convention alone that the format is + associated with JSON, but in reality, the response can include any + arbitrary JavaScript, potentially opening your page to attack. + Be cautious about which services you communicate with via + JSONP. For safe JSON communication, use the JSON module in + conjunction with the IO module wherever + possible. +
+Getting Started
+ ++To include the source files for JSONP and its dependencies, first load +the YUI seed file if you haven't already loaded it. +
+ +<script src="http://yui.yahooapis.com/3.10.3/build/yui/yui-min.js"></script>+ + +
+Next, create a new YUI instance for your application and populate it with the
+modules you need by specifying them as arguments to the YUI().use() method.
+YUI will automatically load any dependencies required by the modules you
+specify.
+
<script>
+// Create a new YUI instance and populate it with the required modules.
+YUI().use('jsonp', 'jsonp-url', function (Y) {
+ // JSONP is available and ready for use. Add implementation
+ // code here.
+});
+</script>
+
+
+
+For more information on creating YUI instances and on the
+use() method, see the
+documentation for the YUI Global Object.
+
Using the JSONP Utility
+ +Instantiation and the Y.jsonp method
+
+
+ The JSONP utility provides the Y.jsonp(url, callback) method
+ for single transactions as well as a Y.JSONPRequest class to
+ manage reusable connections.
+
+ The first argument to either the Y.jsonp method or the
+ Y.JSONPRequest constructor is the URL of the JSONP service,
+ and the second is a callback function or configuration
+ object that contains a callback function. When the service responds
+ with the data, the callback will be executed with the response data as the
+ first parameter.
+
+ In place of the JSONP callback name in the URL, include the string + "{callback}". This placeholder will be used for a proxy function + that will route the data to your callback. +
+ + +// instead of service.php?callback=handleJSONP
+var url = "http://example.com/service.php?callback={callback}";
+
+function handleJSONP(response) {
+ // response is a JavaScript object. No parsing necessary
+ Y.one("#output").setHTML(response.outputHTML);
+}
+
+Y.jsonp(url, handleJSONP);
+
+// or
+var service = new Y.JSONPRequest(url, handleJSONP);
+service.send();
+
+
+Sending JSONP requests
+ +
+ Y.jsonp(url, callback) will dispatch the request immediately.
+ JSONPRequest instances will dispatch the request each time their
+ send() method is called.
+
// request sent immediately +Y.jsonp(url, handleJSONP); + +// No request sent +var service = new Y.JSONPRequest(url, handleJSONP); + +// ...until now +service.send(); + +// ...and now again +service.send();+ + +
+ Y.jsonp(url, callback) is a convenience wrapper to instantiate
+ a JSONPRequest instance and call its send() method.
+
+ This will generate a request to a URL like this one (note that the
+ {callback} placeholder has been replaced with a dynamically
+ generated callback name):
+
http://example.com/service.php?callback=YUI.Env.JSONP.yui_3_3_0_1_1294184187597423+ + +
+ The server will then be expected to respond with a JavaScript value wrapped + in a call to that function, like this: +
+ +YUI.Env.JSONP.yui_3_3_0_1_1294184187597423({"foo":"bar"});
+
+
+Configuring the connection
+ +
+ The second argument to either Y.jsonp or the
+ Y.JSONPRequest constructor can be a success callback function
+ or for more control, it can be a configuration object. The supported keys
+ of this object are:
+
| Property | +Description | +
|---|---|
| timeout | +
+ This value, defined as milliseconds, is a time threshold for
+ the transaction (e.g., { timeout: 2000 } ). When
+ this limit is reached, the transaction's
+ on.timeout callback will be executed if
+ supplied.
+ |
+
| context | +
+ Defines what will be "this" in the
+ callbacks. If undefined, the default will be the JSONPRequest
+ instance.
+ |
+
| args | ++ An array of additional arguments that will be passed to the + callbacks as second, third, and so on arguments. + | +
| on | +
+
+ Required. This object defines the
+ callbacks to be used for the transaction. At least an
+
|
+
| format | +
+ Preprocessor function to stitch together the supplied URL
+ (first argument), the proxy function name (internally
+ generated), and any additional arguments passed to
+ send(). See Customizing the
+ JSONP URL for more detail.
+ |
+
+ This is an example of a configuration object, with a set of properties + defined. +
+ +var url = "http://example.com/service.php?callback={callback}",
+ service = new Y.JSONPRequest(url, {
+ on: {
+ success: MyApp.handleJSONP,
+ timeout: MyApp.handleTimeout
+ },
+ context: MyApp
+ timeout: 3000, // 3 second timeout
+ args: [new Date(), 100] // e.g. handleJSONP(data, date, number)
+ });
+
+service.send();
+
+// or
+Y.jsonp(url, {
+ on: {
+ success: MyApp.handleJSONP,
+ timeout: MyApp.handleTimeout
+ },
+ context: MyApp
+ timeout: 3000, // 3 second timeout
+ args: [new Date(), 100] // e.g. handleJSONP(data, date, number)
+});
+
+
+Parsing the callback from the URL
+ +
+ An extension for the jsonp module is the
+ jsonp-url module which provides a few additional features.
+
-
+
-
+ If you have a global function or a function available from the YUI
+ instance (e.g.
Y.MyApp.handleJSONP), you can include the + name in the URL and omit the second parameter entirely. +
+ - + The URL passed as the first parameter need not include the + "{callback}" string. If it is not found, it will look for + "callback=", then fall back to adding the query parameter + onto the URL. + +
Y.MyApp.handleJSONP = function (data) {
+ Y.one("#output").setHTML(data.outputHTML);
+};
+
+Y.jsonp("http://example.com/service.php?callback=Y.MyApp.handleJSONP");
+
+// or
+Y.jsonp("http://example.com/service.php", {
+ context: Y.MyApp,
+ on: {
+ success: Y.MyApp.handleJSONP,
+ failure: Y.MyApp.handleFailure
+ }
+});
+
+
+Customizing the JSONP URL
+ +
+ The default URL formatter simply replaces the "{callback}"
+ placehold with the name of the generated proxy function. If you want to
+ customize the URL generation process, you can provide a format
+ function in the configuration. The function will receive the configured
+ URL (with "{callback}" placeholder), the string name of the proxy
+ function, and any additional arguments that were passed to
+ send().
+
// Our custom formatter will expect a URL with an additional placeholder for
+// username that must be supplied in send("bill");
+// e.g. http://example.com/bill/json?fn=YUI.Env.JSONP._12345
+function prepareJSONPUrl(url, proxy, username) {
+ return Y.Lang.sub(url, {
+ callback: proxy,
+ name: username || "user"
+ });
+}
+
+var url = "http://example.com/{name}/json?fn={callback}";
+
+var service = new Y.JSONPRequest(url, {
+ format: prepareJSONPUrl,
+ on: {
+ success: handleJSONP
+ }
+ });
+
+service.send("apipkin");
+service.send("tivac");
+service.send("razass");
+
+
+Known Issues
+ +-
+
- + Unlike the XMLHttpRequest calls generated by the IO utility, JSONP + requests can't be aborted, since they rely on dynamic script insertion + (which provides less low-level control than XHR). Keep this in mind + when deciding which method to use. + + +
- + Since most browsers don't enforce execution order for dynamically + inserted scripts, JSONP callbacks may not be called in the same order + that the requests were sent. On the other hand, some browsers + do enforce execution order, so in these browsers a slow + request may block the execution of subsequent JSONP callbacks. + +
-
+ In WinJS (Windows 8 application mode), JSONP is not supported
+ due to the security measures enforced in that environment. Making
+ a JSONP request requires a remote script tag which is prohibited.
+ An alternative is to use the YQL module to query a YQL table that
+ can return the data that you need. The YQL module is supported in
+ this environment because it uses native
XMLHttpRequestto fetch it's data. +
+
