diff -r 322d0feea350 -r 89ef5ed3c48b src/cm/media/js/lib/yui/yui_3.10.3/build/dataschema-json/dataschema-json-debug.js --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/cm/media/js/lib/yui/yui_3.10.3/build/dataschema-json/dataschema-json-debug.js Tue Jul 16 14:29:46 2013 +0200 @@ -0,0 +1,450 @@ +/* +YUI 3.10.3 (build 2fb5187) +Copyright 2013 Yahoo! Inc. All rights reserved. +Licensed under the BSD License. +http://yuilibrary.com/license/ +*/ + +YUI.add('dataschema-json', function (Y, NAME) { + +/** +Provides a DataSchema implementation which can be used to work with JSON data. + +@module dataschema +@submodule dataschema-json +**/ + +/** +Provides a DataSchema implementation which can be used to work with JSON data. + +See the `apply` method for usage. + +@class DataSchema.JSON +@extends DataSchema.Base +@static +**/ +var LANG = Y.Lang, + isFunction = LANG.isFunction, + isObject = LANG.isObject, + isArray = LANG.isArray, + // TODO: I don't think the calls to Base.* need to be done via Base since + // Base is mixed into SchemaJSON. Investigate for later. + Base = Y.DataSchema.Base, + + SchemaJSON; + +SchemaJSON = { + +///////////////////////////////////////////////////////////////////////////// +// +// DataSchema.JSON static methods +// +///////////////////////////////////////////////////////////////////////////// + /** + * Utility function converts JSON locator strings into walkable paths + * + * @method getPath + * @param locator {String} JSON value locator. + * @return {String[]} Walkable path to data value. + * @static + */ + getPath: function(locator) { + var path = null, + keys = [], + i = 0; + + if (locator) { + // Strip the ["string keys"] and [1] array indexes + // TODO: the first two steps can probably be reduced to one with + // /\[\s*(['"])?(.*?)\1\s*\]/g, but the array indices would be + // stored as strings. This is not likely an issue. + locator = locator. + replace(/\[\s*(['"])(.*?)\1\s*\]/g, + function (x,$1,$2) {keys[i]=$2;return '.@'+(i++);}). + replace(/\[(\d+)\]/g, + function (x,$1) {keys[i]=parseInt($1,10)|0;return '.@'+(i++);}). + replace(/^\./,''); // remove leading dot + + // Validate against problematic characters. + // commented out because the path isn't sent to eval, so it + // should be safe. I'm not sure what makes a locator invalid. + //if (!/[^\w\.\$@]/.test(locator)) { + path = locator.split('.'); + for (i=path.length-1; i >= 0; --i) { + if (path[i].charAt(0) === '@') { + path[i] = keys[parseInt(path[i].substr(1),10)]; + } + } + /*} + else { + Y.log("Invalid locator: " + locator, "error", "dataschema-json"); + } + */ + } + return path; + }, + + /** + * Utility function to walk a path and return the value located there. + * + * @method getLocationValue + * @param path {String[]} Locator path. + * @param data {String} Data to traverse. + * @return {Object} Data value at location. + * @static + */ + getLocationValue: function (path, data) { + var i = 0, + len = path.length; + for (;i(required) The path locator (String) + * `parser`: A function or the name of a function on `Y.Parsers` used + to convert the input value into a normalized type. Parser + functions are passed the value as input and are expected to + return a value. + + If no value parsing is needed, you can use path locators (strings) + instead of field identifiers (objects) -- see example below. + + If no processing of the result list array is needed, _schema.resultFields_ + can be omitted; the `response.results` will point directly to the array. + + If the result list contains arrays, `response.results` will contain an + array of objects with key:value pairs assuming the fields in + _schema.resultFields_ are ordered in accordance with the data array + values. + + If the result list contains objects, the identified _schema.resultFields_ + will be used to extract a value from those objects for the output result. + + To extract additional information from the JSON, include an array of + path locators in _schema.metaFields_. The collected values will be + stored in `response.meta`. + + + @example + // Process array of arrays + var schema = { + resultListLocator: 'produce.fruit', + resultFields: [ 'name', 'color' ] + }, + data = { + produce: { + fruit: [ + [ 'Banana', 'yellow' ], + [ 'Orange', 'orange' ], + [ 'Eggplant', 'purple' ] + ] + } + }; + + var response = Y.DataSchema.JSON.apply(schema, data); + + // response.results[0] is { name: "Banana", color: "yellow" } + + + // Process array of objects + some metadata + schema.metaFields = [ 'lastInventory' ]; + + data = { + produce: { + fruit: [ + { name: 'Banana', color: 'yellow', price: '1.96' }, + { name: 'Orange', color: 'orange', price: '2.04' }, + { name: 'Eggplant', color: 'purple', price: '4.31' } + ] + }, + lastInventory: '2011-07-19' + }; + + response = Y.DataSchema.JSON.apply(schema, data); + + // response.results[0] is { name: "Banana", color: "yellow" } + // response.meta.lastInventory is '2001-07-19' + + + // Use parsers + schema.resultFields = [ + { + key: 'name', + parser: function (val) { return val.toUpperCase(); } + }, + { + key: 'price', + parser: 'number' // Uses Y.Parsers.number + } + ]; + + response = Y.DataSchema.JSON.apply(schema, data); + + // Note price was converted from a numeric string to a number + // response.results[0] looks like { fruit: "BANANA", price: 1.96 } + + @method apply + @param {Object} [schema] Schema to apply. Supported configuration + properties are: + @param {String} [schema.resultListLocator] Path locator for the + location of the array of records to flatten into `response.results` + @param {Array} [schema.resultFields] Field identifiers to + locate/assign values in the response records. See above for + details. + @param {Array} [schema.metaFields] Path locators to extract extra + non-record related information from the data object. + @param {Object|Array|String} data JSON data or its string serialization. + @return {Object} An Object with properties `results` and `meta` + @static + **/ + apply: function(schema, data) { + var data_in = data, + data_out = { results: [], meta: {} }; + + // Convert incoming JSON strings + if (!isObject(data)) { + try { + data_in = Y.JSON.parse(data); + } + catch(e) { + data_out.error = e; + return data_out; + } + } + + if (isObject(data_in) && schema) { + // Parse results data + data_out = SchemaJSON._parseResults.call(this, schema, data_in, data_out); + + // Parse meta data + if (schema.metaFields !== undefined) { + data_out = SchemaJSON._parseMeta(schema.metaFields, data_in, data_out); + } + } + else { + Y.log("JSON data could not be schema-parsed: " + Y.dump(data) + " " + Y.dump(data), "error", "dataschema-json"); + data_out.error = new Error("JSON schema parse failure"); + } + + return data_out; + }, + + /** + * Schema-parsed list of results from full data + * + * @method _parseResults + * @param schema {Object} Schema to parse against. + * @param json_in {Object} JSON to parse. + * @param data_out {Object} In-progress parsed data to update. + * @return {Object} Parsed data object. + * @static + * @protected + */ + _parseResults: function(schema, json_in, data_out) { + var getPath = SchemaJSON.getPath, + getValue = SchemaJSON.getLocationValue, + path = getPath(schema.resultListLocator), + results = path ? + (getValue(path, json_in) || + // Fall back to treat resultListLocator as a simple key + json_in[schema.resultListLocator]) : + // Or if no resultListLocator is supplied, use the input + json_in; + + if (isArray(results)) { + // if no result fields are passed in, then just take + // the results array whole-hog Sometimes you're getting + // an array of strings, or want the whole object, so + // resultFields don't make sense. + if (isArray(schema.resultFields)) { + data_out = SchemaJSON._getFieldValues.call(this, schema.resultFields, results, data_out); + } else { + data_out.results = results; + } + } else if (schema.resultListLocator) { + data_out.results = []; + data_out.error = new Error("JSON results retrieval failure"); + Y.log("JSON data could not be parsed: " + Y.dump(json_in), "error", "dataschema-json"); + } + + return data_out; + }, + + /** + * Get field data values out of list of full results + * + * @method _getFieldValues + * @param fields {Array} Fields to find. + * @param array_in {Array} Results to parse. + * @param data_out {Object} In-progress parsed data to update. + * @return {Object} Parsed data object. + * @static + * @protected + */ + _getFieldValues: function(fields, array_in, data_out) { + var results = [], + len = fields.length, + i, j, + field, key, locator, path, parser, val, + simplePaths = [], complexPaths = [], fieldParsers = [], + result, record; + + // First collect hashes of simple paths, complex paths, and parsers + for (i=0; i=0; --i) { + record = {}; + result = array_in[i]; + if(result) { + // Cycle through complexLocators + for (j=complexPaths.length - 1; j>=0; --j) { + path = complexPaths[j]; + val = SchemaJSON.getLocationValue(path.path, result); + if (val === undefined) { + val = SchemaJSON.getLocationValue([path.locator], result); + // Fail over keys like "foo.bar" from nested parsing + // to single token parsing if a value is found in + // results["foo.bar"] + if (val !== undefined) { + simplePaths.push({ + key: path.key, + path: path.locator + }); + // Don't try to process the path as complex + // for further results + complexPaths.splice(i,1); + continue; + } + } + + record[path.key] = Base.parse.call(this, + (SchemaJSON.getLocationValue(path.path, result)), path); + } + + // Cycle through simpleLocators + for (j = simplePaths.length - 1; j >= 0; --j) { + path = simplePaths[j]; + // Bug 1777850: The result might be an array instead of object + record[path.key] = Base.parse.call(this, + ((result[path.path] === undefined) ? + result[j] : result[path.path]), path); + } + + // Cycle through fieldParsers + for (j=fieldParsers.length-1; j>=0; --j) { + key = fieldParsers[j].key; + record[key] = fieldParsers[j].parser.call(this, record[key]); + // Safety net + if (record[key] === undefined) { + record[key] = null; + } + } + results[i] = record; + } + } + data_out.results = results; + return data_out; + }, + + /** + * Parses results data according to schema + * + * @method _parseMeta + * @param metaFields {Object} Metafields definitions. + * @param json_in {Object} JSON to parse. + * @param data_out {Object} In-progress parsed data to update. + * @return {Object} Schema-parsed meta data. + * @static + * @protected + */ + _parseMeta: function(metaFields, json_in, data_out) { + if (isObject(metaFields)) { + var key, path; + for(key in metaFields) { + if (metaFields.hasOwnProperty(key)) { + path = SchemaJSON.getPath(metaFields[key]); + if (path && json_in) { + data_out.meta[key] = SchemaJSON.getLocationValue(path, json_in); + } + } + } + } + else { + data_out.error = new Error("JSON meta data retrieval failure"); + } + return data_out; + } +}; + +// TODO: Y.Object + mix() might be better here +Y.DataSchema.JSON = Y.mix(SchemaJSON, Base); + + +}, '3.10.3', {"requires": ["dataschema-base", "json"]});