~michael.nelson/ubuntu-webcatalog/1267731-import-sca-apps-error

« back to all changes in this revision

Viewing changes to src/webcatalog/static/yui/3.10.3/build/autocomplete-sources/autocomplete-sources-debug.js

  • Committer: Tarmac
  • Author(s): Stephen Stewart
  • Date: 2013-06-26 09:19:32 UTC
  • mfrom: (184.1.4 ubuntu-global-nav)
  • Revision ID: tarmac-20130626091932-8urtuli368k8p7ds
[r=beuno,jonas-drange] add ubuntu global nav to apps.ubuntu.com

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
YUI 3.10.3 (build 2fb5187)
 
3
Copyright 2013 Yahoo! Inc. All rights reserved.
 
4
Licensed under the BSD License.
 
5
http://yuilibrary.com/license/
 
6
*/
 
7
 
 
8
YUI.add('autocomplete-sources', function (Y, NAME) {
 
9
 
 
10
/**
 
11
Mixes support for JSONP and YQL result sources into AutoCompleteBase.
 
12
 
 
13
@module autocomplete
 
14
@submodule autocomplete-sources
 
15
**/
 
16
 
 
17
var ACBase = Y.AutoCompleteBase,
 
18
    Lang   = Y.Lang,
 
19
 
 
20
    _SOURCE_SUCCESS = '_sourceSuccess',
 
21
 
 
22
    MAX_RESULTS         = 'maxResults',
 
23
    REQUEST_TEMPLATE    = 'requestTemplate',
 
24
    RESULT_LIST_LOCATOR = 'resultListLocator';
 
25
 
 
26
// Add prototype properties and methods to AutoCompleteBase.
 
27
Y.mix(ACBase.prototype, {
 
28
    /**
 
29
    Regular expression used to determine whether a String source is a YQL query.
 
30
 
 
31
    @property _YQL_SOURCE_REGEX
 
32
    @type RegExp
 
33
    @protected
 
34
    @for AutoCompleteBase
 
35
    **/
 
36
    _YQL_SOURCE_REGEX: /^(?:select|set|use)\s+/i,
 
37
 
 
38
    /**
 
39
    Runs before AutoCompleteBase's `_createObjectSource()` method and augments
 
40
    it to support additional object-based source types.
 
41
 
 
42
    @method _beforeCreateObjectSource
 
43
    @param {String} source
 
44
    @protected
 
45
    @for AutoCompleteBase
 
46
    **/
 
47
    _beforeCreateObjectSource: function (source) {
 
48
        // If the object is a <select> node, use the options as the result
 
49
        // source.
 
50
        if (source instanceof Y.Node &&
 
51
                source.get('nodeName').toLowerCase() === 'select') {
 
52
 
 
53
            return this._createSelectSource(source);
 
54
        }
 
55
 
 
56
        // If the object is a JSONPRequest instance, try to use it as a JSONP
 
57
        // source.
 
58
        if (Y.JSONPRequest && source instanceof Y.JSONPRequest) {
 
59
            return this._createJSONPSource(source);
 
60
        }
 
61
 
 
62
        // Fall back to a basic object source.
 
63
        return this._createObjectSource(source);
 
64
    },
 
65
 
 
66
    /**
 
67
    Creates a DataSource-like object that uses `Y.io` as a source. See the
 
68
    `source` attribute for more details.
 
69
 
 
70
    @method _createIOSource
 
71
    @param {String} source URL.
 
72
    @return {Object} DataSource-like object.
 
73
    @protected
 
74
    @for AutoCompleteBase
 
75
    **/
 
76
    _createIOSource: function (source) {
 
77
        var ioSource = {type: 'io'},
 
78
            that     = this,
 
79
            ioRequest, lastRequest, loading;
 
80
 
 
81
        // Private internal _sendRequest method that will be assigned to
 
82
        // ioSource.sendRequest once io-base and json-parse are available.
 
83
        function _sendRequest(request) {
 
84
            var cacheKey = request.request;
 
85
 
 
86
            // Return immediately on a cached response.
 
87
            if (that._cache && cacheKey in that._cache) {
 
88
                that[_SOURCE_SUCCESS](that._cache[cacheKey], request);
 
89
                return;
 
90
            }
 
91
 
 
92
            // Cancel any outstanding requests.
 
93
            if (ioRequest && ioRequest.isInProgress()) {
 
94
                ioRequest.abort();
 
95
            }
 
96
 
 
97
            ioRequest = Y.io(that._getXHRUrl(source, request), {
 
98
                on: {
 
99
                    success: function (tid, response) {
 
100
                        var data;
 
101
 
 
102
                        try {
 
103
                            data = Y.JSON.parse(response.responseText);
 
104
                        } catch (ex) {
 
105
                            Y.error('JSON parse error', ex);
 
106
                        }
 
107
 
 
108
                        if (data) {
 
109
                            that._cache && (that._cache[cacheKey] = data);
 
110
                            that[_SOURCE_SUCCESS](data, request);
 
111
                        }
 
112
                    }
 
113
                }
 
114
            });
 
115
        }
 
116
 
 
117
        ioSource.sendRequest = function (request) {
 
118
            // Keep track of the most recent request in case there are multiple
 
119
            // requests while we're waiting for the IO module to load. Only the
 
120
            // most recent request will be sent.
 
121
            lastRequest = request;
 
122
 
 
123
            if (loading) { return; }
 
124
 
 
125
            loading = true;
 
126
 
 
127
            // Lazy-load the io-base and json-parse modules if necessary,
 
128
            // then overwrite the sendRequest method to bypass this check in
 
129
            // the future.
 
130
            Y.use('io-base', 'json-parse', function () {
 
131
                ioSource.sendRequest = _sendRequest;
 
132
                _sendRequest(lastRequest);
 
133
            });
 
134
        };
 
135
 
 
136
        return ioSource;
 
137
    },
 
138
 
 
139
    /**
 
140
    Creates a DataSource-like object that uses the specified JSONPRequest
 
141
    instance as a source. See the `source` attribute for more details.
 
142
 
 
143
    @method _createJSONPSource
 
144
    @param {JSONPRequest|String} source URL string or JSONPRequest instance.
 
145
    @return {Object} DataSource-like object.
 
146
    @protected
 
147
    @for AutoCompleteBase
 
148
    **/
 
149
    _createJSONPSource: function (source) {
 
150
        var jsonpSource = {type: 'jsonp'},
 
151
            that        = this,
 
152
            lastRequest, loading;
 
153
 
 
154
        function _sendRequest(request) {
 
155
            var cacheKey = request.request,
 
156
                query    = request.query;
 
157
 
 
158
            if (that._cache && cacheKey in that._cache) {
 
159
                that[_SOURCE_SUCCESS](that._cache[cacheKey], request);
 
160
                return;
 
161
            }
 
162
 
 
163
            // Hack alert: JSONPRequest currently doesn't support
 
164
            // per-request callbacks, so we're reaching into the protected
 
165
            // _config object to make it happen.
 
166
            //
 
167
            // This limitation is mentioned in the following JSONP
 
168
            // enhancement ticket:
 
169
            //
 
170
            // http://yuilibrary.com/projects/yui3/ticket/2529371
 
171
            source._config.on.success = function (data) {
 
172
                that._cache && (that._cache[cacheKey] = data);
 
173
                that[_SOURCE_SUCCESS](data, request);
 
174
            };
 
175
 
 
176
            source.send(query);
 
177
        }
 
178
 
 
179
        jsonpSource.sendRequest = function (request) {
 
180
            // Keep track of the most recent request in case there are multiple
 
181
            // requests while we're waiting for the JSONP module to load. Only
 
182
            // the most recent request will be sent.
 
183
            lastRequest = request;
 
184
 
 
185
            if (loading) { return; }
 
186
 
 
187
            loading = true;
 
188
 
 
189
            // Lazy-load the JSONP module if necessary, then overwrite the
 
190
            // sendRequest method to bypass this check in the future.
 
191
            Y.use('jsonp', function () {
 
192
                // Turn the source into a JSONPRequest instance if it isn't
 
193
                // one already.
 
194
                if (!(source instanceof Y.JSONPRequest)) {
 
195
                    source = new Y.JSONPRequest(source, {
 
196
                        format: Y.bind(that._jsonpFormatter, that)
 
197
                    });
 
198
                }
 
199
 
 
200
                jsonpSource.sendRequest = _sendRequest;
 
201
                _sendRequest(lastRequest);
 
202
            });
 
203
        };
 
204
 
 
205
        return jsonpSource;
 
206
    },
 
207
 
 
208
    /**
 
209
    Creates a DataSource-like object that uses the specified `<select>` node as
 
210
    a source.
 
211
 
 
212
    @method _createSelectSource
 
213
    @param {Node} source YUI Node instance wrapping a `<select>` node.
 
214
    @return {Object} DataSource-like object.
 
215
    @protected
 
216
    @for AutoCompleteBase
 
217
    **/
 
218
    _createSelectSource: function (source) {
 
219
        var that = this;
 
220
 
 
221
        return {
 
222
            type: 'select',
 
223
            sendRequest: function (request) {
 
224
                var options = [];
 
225
 
 
226
                source.get('options').each(function (option) {
 
227
                    options.push({
 
228
                        html    : option.get('innerHTML'),
 
229
                        index   : option.get('index'),
 
230
                        node    : option,
 
231
                        selected: option.get('selected'),
 
232
                        text    : option.get('text'),
 
233
                        value   : option.get('value')
 
234
                    });
 
235
                });
 
236
 
 
237
                that[_SOURCE_SUCCESS](options, request);
 
238
            }
 
239
        };
 
240
    },
 
241
 
 
242
    /**
 
243
    Creates a DataSource-like object that calls the specified  URL or executes
 
244
    the specified YQL query for results. If the string starts with "select ",
 
245
    "use ", or "set " (case-insensitive), it's assumed to be a YQL query;
 
246
    otherwise, it's assumed to be a URL (which may be absolute or relative).
 
247
    URLs containing a "{callback}" placeholder are assumed to be JSONP URLs; all
 
248
    others will use XHR. See the `source` attribute for more details.
 
249
 
 
250
    @method _createStringSource
 
251
    @param {String} source URL or YQL query.
 
252
    @return {Object} DataSource-like object.
 
253
    @protected
 
254
    @for AutoCompleteBase
 
255
    **/
 
256
    _createStringSource: function (source) {
 
257
        if (this._YQL_SOURCE_REGEX.test(source)) {
 
258
            // Looks like a YQL query.
 
259
            return this._createYQLSource(source);
 
260
        } else if (source.indexOf('{callback}') !== -1) {
 
261
            // Contains a {callback} param and isn't a YQL query, so it must be
 
262
            // JSONP.
 
263
            return this._createJSONPSource(source);
 
264
        } else {
 
265
            // Not a YQL query or JSONP, so we'll assume it's an XHR URL.
 
266
            return this._createIOSource(source);
 
267
        }
 
268
    },
 
269
 
 
270
    /**
 
271
    Creates a DataSource-like object that uses the specified YQL query string to
 
272
    create a YQL-based source. See the `source` attribute for details. If no
 
273
    `resultListLocator` is defined, this method will set a best-guess locator
 
274
    that might work for many typical YQL queries.
 
275
 
 
276
    @method _createYQLSource
 
277
    @param {String} source YQL query.
 
278
    @return {Object} DataSource-like object.
 
279
    @protected
 
280
    @for AutoCompleteBase
 
281
    **/
 
282
    _createYQLSource: function (source) {
 
283
        var that      = this,
 
284
            yqlSource = {type: 'yql'},
 
285
            lastRequest, loading, yqlRequest;
 
286
 
 
287
        if (!that.get(RESULT_LIST_LOCATOR)) {
 
288
            that.set(RESULT_LIST_LOCATOR, that._defaultYQLLocator);
 
289
        }
 
290
 
 
291
        function _sendRequest(request) {
 
292
            var query      = request.query,
 
293
                env        = that.get('yqlEnv'),
 
294
                maxResults = that.get(MAX_RESULTS),
 
295
                callback, opts, yqlQuery;
 
296
 
 
297
            yqlQuery = Lang.sub(source, {
 
298
                maxResults: maxResults > 0 ? maxResults : 1000,
 
299
                request   : request.request,
 
300
                query     : query
 
301
            });
 
302
 
 
303
            if (that._cache && yqlQuery in that._cache) {
 
304
                that[_SOURCE_SUCCESS](that._cache[yqlQuery], request);
 
305
                return;
 
306
            }
 
307
 
 
308
            callback = function (data) {
 
309
                that._cache && (that._cache[yqlQuery] = data);
 
310
                that[_SOURCE_SUCCESS](data, request);
 
311
            };
 
312
 
 
313
            opts = {proto: that.get('yqlProtocol')};
 
314
 
 
315
            // Only create a new YQLRequest instance if this is the
 
316
            // first request. For subsequent requests, we'll reuse the
 
317
            // original instance.
 
318
            if (yqlRequest) {
 
319
                yqlRequest._callback   = callback;
 
320
                yqlRequest._opts       = opts;
 
321
                yqlRequest._params.q   = yqlQuery;
 
322
 
 
323
                if (env) {
 
324
                    yqlRequest._params.env = env;
 
325
                }
 
326
            } else {
 
327
                yqlRequest = new Y.YQLRequest(yqlQuery, {
 
328
                    on: {success: callback},
 
329
                    allowCache: false // temp workaround until JSONP has per-URL callback proxies
 
330
                }, env ? {env: env} : null, opts);
 
331
            }
 
332
 
 
333
            yqlRequest.send();
 
334
        }
 
335
 
 
336
        yqlSource.sendRequest = function (request) {
 
337
            // Keep track of the most recent request in case there are multiple
 
338
            // requests while we're waiting for the YQL module to load. Only the
 
339
            // most recent request will be sent.
 
340
            lastRequest = request;
 
341
 
 
342
            if (!loading) {
 
343
                // Lazy-load the YQL module if necessary, then overwrite the
 
344
                // sendRequest method to bypass this check in the future.
 
345
                loading = true;
 
346
 
 
347
                Y.use('yql', function () {
 
348
                    yqlSource.sendRequest = _sendRequest;
 
349
                    _sendRequest(lastRequest);
 
350
                });
 
351
            }
 
352
        };
 
353
 
 
354
        return yqlSource;
 
355
    },
 
356
 
 
357
    /**
 
358
    Default resultListLocator used when a string-based YQL source is set and the
 
359
    implementer hasn't already specified one.
 
360
 
 
361
    @method _defaultYQLLocator
 
362
    @param {Object} response YQL response object.
 
363
    @return {Array}
 
364
    @protected
 
365
    @for AutoCompleteBase
 
366
    **/
 
367
    _defaultYQLLocator: function (response) {
 
368
        var results = response && response.query && response.query.results,
 
369
            values;
 
370
 
 
371
        if (results && Lang.isObject(results)) {
 
372
            // If there's only a single value on YQL's results object, that
 
373
            // value almost certainly contains the array of results we want. If
 
374
            // there are 0 or 2+ values, then the values themselves are most
 
375
            // likely the results we want.
 
376
            values  = Y.Object.values(results) || [];
 
377
            results = values.length === 1 ? values[0] : values;
 
378
 
 
379
            if (!Lang.isArray(results)) {
 
380
                results = [results];
 
381
            }
 
382
        } else {
 
383
            results = [];
 
384
        }
 
385
 
 
386
        return results;
 
387
    },
 
388
 
 
389
    /**
 
390
    Returns a formatted XHR URL based on the specified base _url_, _query_, and
 
391
    the current _requestTemplate_ if any.
 
392
 
 
393
    @method _getXHRUrl
 
394
    @param {String} url Base URL.
 
395
    @param {Object} request Request object containing `query` and `request`
 
396
      properties.
 
397
    @return {String} Formatted URL.
 
398
    @protected
 
399
    @for AutoCompleteBase
 
400
    **/
 
401
    _getXHRUrl: function (url, request) {
 
402
        var maxResults = this.get(MAX_RESULTS);
 
403
 
 
404
        if (request.query !== request.request) {
 
405
            // Append the request template to the URL.
 
406
            url += request.request;
 
407
        }
 
408
 
 
409
        return Lang.sub(url, {
 
410
            maxResults: maxResults > 0 ? maxResults : 1000,
 
411
            query     : encodeURIComponent(request.query)
 
412
        });
 
413
    },
 
414
 
 
415
    /**
 
416
    URL formatter passed to `JSONPRequest` instances.
 
417
 
 
418
    @method _jsonpFormatter
 
419
    @param {String} url
 
420
    @param {String} proxy
 
421
    @param {String} query
 
422
    @return {String} Formatted URL
 
423
    @protected
 
424
    @for AutoCompleteBase
 
425
    **/
 
426
    _jsonpFormatter: function (url, proxy, query) {
 
427
        var maxResults      = this.get(MAX_RESULTS),
 
428
            requestTemplate = this.get(REQUEST_TEMPLATE);
 
429
 
 
430
        if (requestTemplate) {
 
431
            url += requestTemplate(query);
 
432
        }
 
433
 
 
434
        return Lang.sub(url, {
 
435
            callback  : proxy,
 
436
            maxResults: maxResults > 0 ? maxResults : 1000,
 
437
            query     : encodeURIComponent(query)
 
438
        });
 
439
    }
 
440
});
 
441
 
 
442
// Add attributes to AutoCompleteBase.
 
443
Y.mix(ACBase.ATTRS, {
 
444
    /**
 
445
    YQL environment file URL to load when the `source` is set to a YQL query.
 
446
    Set this to `null` to use the default Open Data Tables environment file
 
447
    (http://datatables.org/alltables.env).
 
448
 
 
449
    @attribute yqlEnv
 
450
    @type String
 
451
    @default null
 
452
    @for AutoCompleteBase
 
453
    **/
 
454
    yqlEnv: {
 
455
        value: null
 
456
    },
 
457
 
 
458
    /**
 
459
    URL protocol to use when the `source` is set to a YQL query.
 
460
 
 
461
    @attribute yqlProtocol
 
462
    @type String
 
463
    @default 'http'
 
464
    @for AutoCompleteBase
 
465
    **/
 
466
    yqlProtocol: {
 
467
        value: 'http'
 
468
    }
 
469
});
 
470
 
 
471
// Tell AutoCompleteBase about the new source types it can now support.
 
472
Y.mix(ACBase.SOURCE_TYPES, {
 
473
    io    : '_createIOSource',
 
474
    jsonp : '_createJSONPSource',
 
475
    object: '_beforeCreateObjectSource', // Run our version before the base version.
 
476
    select: '_createSelectSource',
 
477
    string: '_createStringSource',
 
478
    yql   : '_createYQLSource'
 
479
}, true);
 
480
 
 
481
 
 
482
}, '3.10.3', {"optional": ["io-base", "json-parse", "jsonp", "yql"], "requires": ["autocomplete-base"]});