dataschema-xml.js revision 3a38d5b7ad9ebee258ce6cb2ebe712f058ea27c5
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav GlassYUI.add('dataschema-xml', function(Y) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass/**
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * The DataSchema utility provides a common configurable interface for widgets to
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * apply a given schema to a variety of data.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass *
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @module dataschema
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass */
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glassvar LANG = Y.Lang,
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass/**
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * XML subclass for the YUI DataSchema utility.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @class DataSchema.XML
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @extends DataSchema.Base
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @static
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass */
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav GlassSchemaXML = {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass /////////////////////////////////////////////////////////////////////////////
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass //
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass // DataSchema.XML static methods
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass //
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass /////////////////////////////////////////////////////////////////////////////
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass /**
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * Returns string name.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass *
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @method toString
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @return {String} String representation for this object.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass */
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass toString: function() {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass return "DataSchema.XML";
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass },
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass /**
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * Applies a given schema to given XML data.
479b9ac417be02467aadae8cd650d29050001f0bSatyen Desai *
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @method apply
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @param schema {Object} Schema to apply.
479b9ac417be02467aadae8cd650d29050001f0bSatyen Desai * @param data {XMLDoc} XML document.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @return {Object} Schema-parsed data.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @static
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass */
479b9ac417be02467aadae8cd650d29050001f0bSatyen Desai apply: function(schema, data) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass var xmldoc = data,
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass data_out = {results:[],meta:{}};
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass if(LANG.isObject(xmldoc) && schema) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass // Parse results data
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass data_out = SchemaXML._parseResults(schema, xmldoc, data_out);
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass // Parse meta data
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass data_out = SchemaXML._parseMeta(schema.metaFields, xmldoc, data_out);
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass else {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass data_out.error = new Error(this.toString() + " Schema parse failure");
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass return data_out;
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass },
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass /**
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * Get an XPath-specified value for a given field from an XML node or document.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass *
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @method _getLocationValue
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @param field {String | Object} Field definition.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @param context {Object} XML node or document to search within.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @return {Object} Data value or null.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @static
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @protected
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass */
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass _getLocationValue: function(field, context) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass var locator = field.locator || field.key || field,
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass xmldoc = context.ownerDocument || context,
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass result, res, value = null;
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass try {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass // Standards mode
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass if(!LANG.isUndefined(xmldoc.evaluate)) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass result = xmldoc.evaluate(locator, context, xmldoc.createNSResolver(!context.ownerDocument ? context.documentElement : context.ownerDocument.documentElement), 0, null);
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass while(res = result.iterateNext()) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass value = res.textContent;
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass // IE mode
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass else {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass xmldoc.setProperty("SelectionLanguage", "XPath");
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass result = context.selectNodes(locator)[0];
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass value = result.value || result.text || null;
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass return Y.DataSchema.Base.parse(value, field);
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass catch(e) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass },
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass /**
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * Parses results data according to schema
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass *
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @method _parseMeta
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @param xmldoc_in {Object} XML document parse.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @param data_out {Object} In-progress schema-parsed data to update.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @return {Object} Schema-parsed data.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @static
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @protected
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass */
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass _parseMeta: function(metaFields, xmldoc_in, data_out) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass if(LANG.isObject(metaFields)) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass var key,
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass xmldoc = xmldoc_in.ownerDocument || xmldoc_in;
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass for(key in metaFields) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass if (metaFields.hasOwnProperty(key)) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass data_out.meta[key] = SchemaXML._getLocationValue(metaFields[key], xmldoc);
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass return data_out;
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass },
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass /**
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * Schema-parsed list of results from full data
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass *
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @method _parseResults
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @param schema {Object} Schema to parse against.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @param xmldoc_in {Object} XML document parse.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @param data_out {Object} In-progress schema-parsed data to update.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @return {Object} Schema-parsed data.
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @static
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass * @protected
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass */
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass _parseResults: function(schema, xmldoc_in, data_out) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass if(schema.resultsLocator && LANG.isArray(schema.resultsFields)) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass var nodeList = xmldoc_in.getElementsByTagName(schema.resultsLocator),
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass fields = schema.resultsFields,
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass results = [],
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass node, field, result, i, j;
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass if(nodeList.length) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass // Loop through each result node
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass for(i=nodeList.length-1; i>= 0; i--) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass result = {};
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass node = nodeList[i];
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass // Find each field value
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass for(j=fields.length-1; j>= 0; j--) {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass field = fields[j];
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass result[field.key || field] = SchemaXML._getLocationValue(field, node);
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass results[i] = result;
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
d5daadf7c87a641483741ee68c26b343acb5717cJenny Donnelly
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass data_out.results = results;
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass else {
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass data_out.error = new Error(this.toString() + " Result nodes retrieval failure");
609b3fdb3368975ebd66bf9ef6a074e3ca726524Jenny Donnelly }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass return data_out;
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass }
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass};
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav GlassY.DataSchema.XML = Y.mix(SchemaXML, Y.DataSchema.Base);
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass}, '@VERSION@' ,{requires:['dataschema-base']});
76ca635d61eb3f9fb7c9d788a44fa8b1690aa138Dav Glass