You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@stanbol.apache.org by sz...@apache.org on 2013/04/12 14:40:45 UTC
svn commit: r1467253 [7/8] - in /stanbol/trunk/demos/webvie: ./ src/license/
src/main/java/org/apache/stanbol/commons/web/vie/fragment/
src/main/resources/META-INF/resources/static/enhancervie/
src/main/resources/META-INF/resources/static/enhancervie/l...
Added: stanbol/trunk/demos/webvie/src/main/resources/META-INF/resources/static/enhancervie/lib/vie/vie-2.1.0.debug.js
URL: http://svn.apache.org/viewvc/stanbol/trunk/demos/webvie/src/main/resources/META-INF/resources/static/enhancervie/lib/vie/vie-2.1.0.debug.js?rev=1467253&view=auto
==============================================================================
--- stanbol/trunk/demos/webvie/src/main/resources/META-INF/resources/static/enhancervie/lib/vie/vie-2.1.0.debug.js (added)
+++ stanbol/trunk/demos/webvie/src/main/resources/META-INF/resources/static/enhancervie/lib/vie/vie-2.1.0.debug.js Fri Apr 12 12:40:44 2013
@@ -0,0 +1,6992 @@
+/*
+
+Copyright (c) 2011 Henri Bergius, IKS Consortium
+Copyright (c) 2011 Sebastian Germesin, IKS Consortium
+
+Permission is hereby granted, free of charge, to any person
+obtaining a copy of this software and associated documentation
+files (the "Software"), to deal in the Software without
+restriction, including without limitation the rights to use,
+copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the
+Software is furnished to do so, subject to the following
+conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
+HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+OTHER DEALINGS IN THE SOFTWARE.
+*/
+
+(function(){
+// VIE - Vienna IKS Editables
+// (c) 2011 Henri Bergius, IKS Consortium
+// (c) 2011 Sebastian Germesin, IKS Consortium
+// (c) 2011 Szaby Grünwald, IKS Consortium
+// VIE may be freely distributed under the MIT license.
+// For all details and documentation:
+// http://viejs.org/
+
+/*global console:false exports:false require:false */
+
+var root = this,
+ jQuery = root.jQuery,
+ Backbone = root.Backbone,
+ _ = root._;
+
+
+// ## VIE constructor
+//
+// The VIE constructor is the way to initialize VIE for your
+// application. The instance of VIE handles all management of
+// semantic interaction, including keeping track of entities,
+// changes to them, the possible RDFa views on the page where
+// the entities are displayed, and connections to external
+// services like Stanbol and DBPedia.
+//
+// To get a VIE instance, simply run:
+//
+// var vie = new VIE();
+//
+// You can also pass configurations to the VIE instance through
+// the constructor. For example, to set a different default
+// namespace to be used for names that don't have a namespace
+// specified, do:
+//
+// var vie = new VIE({
+// baseNamespace: 'http://example.net'
+// });
+//
+// ### Differences with VIE 1.x
+//
+// VIE 1.x used singletons for managing entities and views loaded
+// from a page. This has been changed with VIE 2.x, and now all
+// data managed by VIE is tied to the instance of VIE being used.
+//
+// This means that VIE needs to be instantiated before using. So,
+// when previously you could get entities from page with:
+//
+// VIE.RDFaEntities.getInstances();
+//
+// Now you need to instantiate VIE first. This example uses the
+// Classic API compatibility layer instead of the `load` method:
+//
+// var vie = new VIE();
+// vie.RDFaEntities.getInstances();
+//
+// Currently the Classic API is enabled by default, but it is
+// recommended to ensure it is enabled before using it. So:
+//
+// var vie = new VIE({classic: true});
+// vie.RDFaEntities.getInstances();
+var VIE = root.VIE = function(config) {
+ this.config = (config) ? config : {};
+ this.services = {};
+ this.jQuery = jQuery;
+ this.entities = new this.Collection([], {
+ vie: this
+ });
+
+ this.Entity.prototype.entities = this.entities;
+ this.Entity.prototype.entityCollection = this.Collection;
+ this.Entity.prototype.vie = this;
+
+ this.Namespaces.prototype.vie = this;
+// ### Namespaces in VIE
+// VIE supports different ontologies and an easy use of them.
+// Namespace prefixes reduce the amount of code you have to
+// write. In VIE, it does not matter if you access an entitie's
+// property with
+// `entity.get('<http://dbpedia.org/property/capitalOf>')` or
+// `entity.get('dbprop:capitalOf')` or even
+// `entity.get('capitalOf')` once the corresponding namespace
+// is registered as *baseNamespace*.
+// By default `"http://viejs.org/ns/"`is set as base namespace.
+// For more information about how to set, get and list all
+// registered namespaces, refer to the
+// <a href="Namespace.html">Namespaces documentation</a>.
+ this.namespaces = new this.Namespaces(
+ (this.config.baseNamespace) ? this.config.baseNamespace : "http://viejs.org/ns/",
+
+// By default, VIE is shipped with common namespace prefixes:
+
+// + owl : "http://www.w3.org/2002/07/owl#"
+// + rdfs : "http://www.w3.org/2000/01/rdf-schema#"
+// + rdf : "http://www.w3.org/1999/02/22-rdf-syntax-ns#"
+// + schema : 'http://schema.org/'
+// + foaf : 'http://xmlns.com/foaf/0.1/'
+// + geo : 'http://www.w3.org/2003/01/geo/wgs84_pos#'
+// + dbpedia: "http://dbpedia.org/ontology/"
+// + dbprop : "http://dbpedia.org/property/"
+// + skos : "http://www.w3.org/2004/02/skos/core#"
+// + xsd : "http://www.w3.org/2001/XMLSchema#"
+// + sioc : "http://rdfs.org/sioc/ns#"
+// + dcterms: "http://purl.org/dc/terms/"
+ {
+ owl : "http://www.w3.org/2002/07/owl#",
+ rdfs : "http://www.w3.org/2000/01/rdf-schema#",
+ rdf : "http://www.w3.org/1999/02/22-rdf-syntax-ns#",
+ schema : 'http://schema.org/',
+ foaf : 'http://xmlns.com/foaf/0.1/',
+ geo : 'http://www.w3.org/2003/01/geo/wgs84_pos#',
+ dbpedia: "http://dbpedia.org/ontology/",
+ dbprop : "http://dbpedia.org/property/",
+ skos : "http://www.w3.org/2004/02/skos/core#",
+ xsd : "http://www.w3.org/2001/XMLSchema#",
+ sioc : "http://rdfs.org/sioc/ns#",
+ dcterms: "http://purl.org/dc/terms/"
+ }
+ );
+
+
+ this.Type.prototype.vie = this;
+ this.Types.prototype.vie = this;
+ this.Attribute.prototype.vie = this;
+ this.Attributes.prototype.vie = this;
+// ### Type hierarchy in VIE
+// VIE takes care about type hierarchy of entities
+// (aka. *schema* or *ontology*).
+// Once a type hierarchy is known to VIE, we can leverage
+// this information, to easily ask, whether an entity
+// is of type, e.g., *foaf:Person* or *schema:Place*.
+// For more information about how to generate such a type
+// hierarchy, refer to the
+// <a href="Type.html">Types documentation</a>.
+ this.types = new this.Types();
+// By default, there is a parent type in VIE, called
+// *owl:Thing*. All types automatically inherit from this
+// type and all registered entities, are of this type.
+ this.types.add("owl:Thing");
+
+// As described above, the Classic API of VIE 1.x is loaded
+// by default. As this might change in the future, it is
+// recommended to ensure it is enabled before using it. So:
+//
+// var vie = new VIE({classic: true});
+// vie.RDFaEntities.getInstances();
+ if (this.config.classic === true) {
+ /* Load Classic API as well */
+ this.RDFa = new this.ClassicRDFa(this);
+ this.RDFaEntities = new this.ClassicRDFaEntities(this);
+ this.EntityManager = new this.ClassicEntityManager(this);
+
+ this.cleanup = function() {
+ this.entities.reset();
+ };
+ }
+};
+
+// ### use(service, name)
+// This method registers services within VIE.
+// **Parameters**:
+// *{string|object}* **service** The service to be registered.
+// *{string}* **name** An optional name to register the service with. If this
+// is not set, the default name that comes with the service is taken.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{VIE}* : The current VIE instance.
+// **Example usage**:
+//
+// var vie = new VIE();
+// var conf1 = {...};
+// var conf2 = {...};
+// vie.use(new vie.StanbolService());
+// vie.use(new vie.StanbolService(conf1), "stanbol_1");
+// vie.use(new vie.StanbolService(conf2), "stanbol_2");
+// // <-- this means that there are now 3 services registered!
+VIE.prototype.use = function(service, name) {
+ if (!name && !service.name) {
+ throw new Error("Please provide a name for the service!");
+ }
+ service.vie = this;
+ service.name = (name)? name : service.name;
+ if (service.init) {
+ service.init();
+ }
+ this.services[service.name] = service;
+
+ return this;
+};
+
+// ### service(name)
+// This method returns the service object that is
+// registered under the given name.
+// **Parameters**:
+// *{string}* **name** ...
+// **Throws**:
+// *{Error}* if no service could be found.
+// **Returns**:
+// *{object}* : The service to be queried.
+// **Example usage**:
+//
+// var vie = new VIE();
+// vie.use(new vie.StanbolService(), "stanbol");
+// var service = vie.service("stanbol");
+VIE.prototype.service = function(name) {
+ if (!this.hasService(name)) {
+ throw "Undefined service " + name;
+ }
+ return this.services[name];
+};
+
+// ### hasService(name)
+// This method returns a boolean telling whether VIE has a particular
+// service loaded.
+// **Parameters**:
+// *{string}* **name**
+// **Returns**:
+// *{boolean}* whether service is available
+VIE.prototype.hasService = function(name) {
+ if (!this.services[name]) {
+ return false;
+ }
+ return true;
+};
+
+// ### getServicesArray()
+// This method returns an array of all registered services.
+// **Parameters**:
+// *nothing*
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{array}* : An array of service instances.
+// **Example usage**:
+//
+// var vie = new VIE();
+// vie.use(new vie.StanbolService(), "stanbol");
+// var services = vie.getServicesArray();
+// services.length; // <-- 1
+VIE.prototype.getServicesArray = function() {
+ return _.map(this.services, function (v) {return v;});
+};
+
+// ### load(options)
+// This method instantiates a new VIE.Loadable in order to
+// perform queries on the services.
+// **Parameters**:
+// *{object}* **options** Options to be set.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{VIE.Loadable}* : A new instance of VIE.Loadable.
+// **Example usage**:
+//
+// var vie = new VIE();
+// vie.use(new vie.StanbolService(), "stanbol");
+// var loader = vie.load({...});
+VIE.prototype.load = function(options) {
+ if (!options) { options = {}; }
+ options.vie = this;
+ return new this.Loadable(options);
+};
+
+// ### save(options)
+// This method instantiates a new VIE.Savable in order to
+// perform queries on the services.
+// **Parameters**:
+// *{object}* **options** Options to be set.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{VIE.Savable}* : A new instance of VIE.Savable.
+// **Example usage**:
+//
+// var vie = new VIE();
+// vie.use(new vie.StanbolService(), "stanbol");
+// var saver = vie.save({...});
+VIE.prototype.save = function(options) {
+ if (!options) { options = {}; }
+ options.vie = this;
+ return new this.Savable(options);
+};
+
+// ### remove(options)
+// This method instantiates a new VIE.Removable in order to
+// perform queries on the services.
+// **Parameters**:
+// *{object}* **options** Options to be set.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{VIE.Removable}* : A new instance of VIE.Removable.
+// **Example usage**:
+//
+// var vie = new VIE();
+// vie.use(new vie.StanbolService(), "stanbol");
+// var remover = vie.remove({...});
+VIE.prototype.remove = function(options) {
+ if (!options) { options = {}; }
+ options.vie = this;
+ return new this.Removable(options);
+};
+
+// ### analyze(options)
+// This method instantiates a new VIE.Analyzable in order to
+// perform queries on the services.
+// **Parameters**:
+// *{object}* **options** Options to be set.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{VIE.Analyzable}* : A new instance of VIE.Analyzable.
+// **Example usage**:
+//
+// var vie = new VIE();
+// vie.use(new vie.StanbolService(), "stanbol");
+// var analyzer = vie.analyze({...});
+VIE.prototype.analyze = function(options) {
+ if (!options) { options = {}; }
+ options.vie = this;
+ return new this.Analyzable(options);
+};
+
+// ### find(options)
+// This method instantiates a new VIE.Findable in order to
+// perform queries on the services.
+// **Parameters**:
+// *{object}* **options** Options to be set.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{VIE.Findable}* : A new instance of VIE.Findable.
+// **Example usage**:
+//
+// var vie = new VIE();
+// vie.use(new vie.StanbolService(), "stanbol");
+// var finder = vie.find({...});
+VIE.prototype.find = function(options) {
+ if (!options) { options = {}; }
+ options.vie = this;
+ return new this.Findable(options);
+};
+
+// ### loadSchema(url, options)
+// VIE only knows the *owl:Thing* type by default.
+// You can use this method to import another
+// schema (ontology) from an external resource.
+// (Currently, this supports only the JSON format!!)
+// As this method works asynchronously, you might want
+// to register `success` and `error` callbacks via the
+// options.
+// **Parameters**:
+// *{string}* **url** The url, pointing to the schema to import.
+// *{object}* **options** Options to be set.
+// (Set ```success``` and ```error``` as callbacks.).
+// **Throws**:
+// *{Error}* if the url is not set.
+// **Returns**:
+// *{VIE}* : The VIE instance itself.
+// **Example usage**:
+//
+// var vie = new VIE();
+// vie.loadSchema("http://schema.rdfs.org/all.json",
+// {
+// baseNS : "http://schema.org/",
+// success : function () {console.log("success");},
+// error : function (msg) {console.warn(msg);}
+// });
+VIE.prototype.loadSchema = function(url, options) {
+ options = (!options)? {} : options;
+
+ if (!url) {
+ throw new Error("Please provide a proper URL");
+ }
+ else {
+ var vie = this;
+ jQuery.getJSON(url)
+ .success(function(data) {
+ try {
+ VIE.Util.loadSchemaOrg(vie, data, options.baseNS);
+ if (options.success) {
+ options.success.call(vie);
+ }
+ } catch (e) {
+ options.error.call(vie, e);
+ return;
+ }
+ })
+ .error(function(data, textStatus, jqXHR) {
+ if (options.error) {
+ console.warn(data, textStatus, jqXHR);
+ options.error.call(vie, "Could not load schema from URL (" + url + ")");
+ }
+ });
+ }
+
+ return this;
+};
+
+// ### getTypedEntityClass(type)
+// This method generates a special type of `Entity` based on the given type.
+// **Parameters**:
+// *{string}* **type** The type.
+// **Throws**:
+// *{Error}* if the type is unknown to VIE.
+// **Returns**:
+// *{VIE.Entity}* : A subclass of `VIE.Entity`.
+// **Example usage**:
+//
+// var vie = new VIE();
+// vie.types.add("Person");
+// var PersonClass = vie.getTypedEntityClass("Person");
+// var Person = new PersonClass({"name", "Sebastian"});
+VIE.prototype.getTypedEntityClass = function (type) {
+ var typeType = this.types.get(type);
+ if (!typeType) {
+ throw new Error("Unknown type " + type);
+ }
+ var TypedEntityClass = function (attrs, opts) {
+ if (!attrs) {
+ attrs = {};
+ }
+ attrs["@type"] = type;
+ this.set(attrs, opts);
+ };
+ TypedEntityClass.prototype = new this.Entity();
+ TypedEntityClass.prototype.schema = function () {
+ return VIE.Util.getFormSchemaForType(typeType);
+ };
+ return TypedEntityClass;
+};
+
+// ## Running VIE on Node.js
+//
+// When VIE is running under Node.js we can use the CommonJS
+// require interface to load our dependencies automatically.
+//
+// This means Node.js users don't need to care about dependencies
+// and can just run VIE with:
+//
+// var VIE = require('vie');
+//
+// In browser environments the dependencies have to be included
+// before including VIE itself.
+if (typeof exports === 'object') {
+ exports.VIE = VIE;
+
+ if (!jQuery) {
+ jQuery = require('jquery');
+ }
+ if (!Backbone) {
+ Backbone = require('backbone');
+ Backbone.setDomLibrary(jQuery);
+ }
+ if (!_) {
+ _ = require('underscore')._;
+ }
+}
+// VIE - Vienna IKS Editables
+// (c) 2011 Henri Bergius, IKS Consortium
+// (c) 2011 Sebastian Germesin, IKS Consortium
+// (c) 2011 Szaby Grünwald, IKS Consortium
+// VIE may be freely distributed under the MIT license.
+// For all details and documentation:
+// http://viejs.org/
+
+// ## VIE.Able
+// VIE implements asynchronius service methods through
+// [jQuery.Deferred](http://api.jquery.com/category/deferred-object/) objects.
+// Loadable, Analysable, Savable, etc. are part of the VIE service API and
+// are implemented with the generic VIE.Able class.
+// Example:
+//
+// VIE.prototype.Loadable = function (options) {
+// this.init(options,"load");
+// };
+// VIE.prototype.Loadable.prototype = new VIE.prototype.Able();
+//
+// This defines
+//
+// someVIEService.load(options)
+// .using(...)
+// .execute()
+// .success(...)
+// .fail(...)
+// which will run the asynchronius `load` function of the service with the created Loadable
+// object.
+
+// ### VIE.Able()
+// This is the constructor of a VIE.Able. This should not be called
+// globally but using the inherited classes below.
+// **Parameters**:
+// *nothing*
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{VIE.Able}* : A **new** VIE.Able object.
+// Example:
+//
+// VIE.prototype.Loadable = function (options) {
+// this.init(options,"load");
+// };
+// VIE.prototype.Loadable.prototype = new VIE.prototype.Able();
+VIE.prototype.Able = function(){
+
+// ### init(options, methodName)
+// Internal method, called during initialization.
+// **Parameters**:
+// *{object}* **options** the *able* options coming from the API call
+// *{string}* **methodName** the service method called on `.execute`.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{VIE.Able}* : The current instance.
+// **Example usage**:
+//
+// VIE.prototype.Loadable = function (options) {
+// this.init(options,"load");
+// };
+// VIE.prototype.Loadable.prototype = new VIE.prototype.Able();
+ this.init = function(options, methodName) {
+ this.options = options;
+ this.services = options.from || options.using || options.to || [];
+ this.vie = options.vie;
+
+ this.methodName = methodName;
+
+ // Instantiate the deferred object
+ this.deferred = jQuery.Deferred();
+
+// In order to get more information and documentation about the passed-through
+// deferred methods and their synonyms, please see the documentation of
+// the [jQuery.Deferred object](http://api.jquery.com/category/deferred-object/)
+ /* Public deferred-methods */
+ this.resolve = this.deferred.resolve;
+ this.resolveWith = this.deferred.resolveWith;
+ this.reject = this.deferred.reject;
+ this.rejectWith = this.deferred.rejectWith;
+ this.success = this.done = this.deferred.done;
+ this.fail = this.deferred.fail;
+ this.then = this.deferred.then;
+ this.always = this.deferred.always;
+ this.from = this.using;
+ this.to = this.using;
+
+ return this;
+ };
+
+
+// ### using(services)
+// This method registers services with the current able instance.
+// **Parameters**:
+// *{string|array}* **services** An id of a service or an array of strings.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{VIE.Able}* : The current instance.
+// **Example usage**:
+//
+// var loadable = vie.load({id: "http://example.com/entity/1234"});
+// able.using("myService");
+ this.using = function(services) {
+ var self = this;
+ services = (_.isArray(services))? services : [ services ];
+ _.each (services, function (s) {
+ var obj = (typeof s === "string")? self.vie.service(s) : s;
+ self.services.push(obj);
+ });
+ return this;
+ };
+
+// ### execute()
+// This method runs the actual method on all registered services.
+// **Parameters**:
+// *nothing*
+// **Throws**:
+// *nothing* ...
+// **Returns**:
+// *{VIE.Able}* : The current instance.
+// **Example usage**:
+//
+// var able = new vie.Able().init();
+// able.using("stanbol")
+// .done(function () {alert("finished");})
+// .execute();
+ this.execute = function() {
+ /* call service[methodName] */
+ var able = this;
+ _(this.services).each(function(service){
+ service[able.methodName](able);
+ });
+ return this;
+ };
+};
+
+// ## VIE.Loadable
+// A ```VIE.Loadable``` is a wrapper around the deferred object
+// to **load** semantic data from a semantic web service.
+VIE.prototype.Loadable = function (options) {
+ this.init(options,"load");
+};
+VIE.prototype.Loadable.prototype = new VIE.prototype.Able();
+
+// ## VIE.Savable
+// A ```VIE.Savable``` is a wrapper around the deferred object
+// to **save** entities by a VIE service. The RDFaService would write the data
+// in the HTML as RDFa, the StanbolService stores the data in its Entityhub, etc.
+VIE.prototype.Savable = function(options){
+ this.init(options, "save");
+};
+VIE.prototype.Savable.prototype = new VIE.prototype.Able();
+
+// ## VIE.Removable
+// A ```VIE.Removable``` is a wrapper around the deferred object
+// to **remove** semantic data from a semantic web service.
+VIE.prototype.Removable = function(options){
+ this.init(options, "remove");
+};
+VIE.prototype.Removable.prototype = new VIE.prototype.Able();
+
+// ## VIE.Analyzable
+// A ```VIE.Analyzable``` is a wrapper around the deferred object
+// to **analyze** data and extract semantic information with the
+// help of a semantic web service.
+VIE.prototype.Analyzable = function (options) {
+ this.init(options, "analyze");
+};
+VIE.prototype.Analyzable.prototype = new VIE.prototype.Able();
+
+// ## VIE.Findable
+// A ```VIE.Findable``` is a wrapper around the deferred object
+// to **find** semantic data on a semantic storage.
+VIE.prototype.Findable = function (options) {
+ this.init(options, "find");
+};
+VIE.prototype.Findable.prototype = new VIE.prototype.Able();
+
+// VIE - Vienna IKS Editables
+// (c) 2011 Henri Bergius, IKS Consortium
+// (c) 2011 Sebastian Germesin, IKS Consortium
+// (c) 2011 Szaby Grünwald, IKS Consortium
+// VIE may be freely distributed under the MIT license.
+// For all details and documentation:
+// http://viejs.org/
+
+// ## VIE Utils
+//
+// The here-listed methods are utility methods for the day-to-day
+// VIE.js usage. All methods are within the static namespace ```VIE.Util```.
+VIE.Util = {
+
+// ### VIE.Util.toCurie(uri, safe, namespaces)
+// This method converts a given
+// URI into a CURIE (or SCURIE), based on the given ```VIE.Namespaces``` object.
+// If the given uri is already a URI, it is left untouched and directly returned.
+// If no prefix could be found, an ```Error``` is thrown.
+// **Parameters**:
+// *{string}* **uri** The URI to be transformed.
+// *{boolean}* **safe** A flag whether to generate CURIEs or SCURIEs.
+// *{VIE.Namespaces}* **namespaces** The namespaces to be used for the prefixes.
+// **Throws**:
+// *{Error}* If no prefix could be found in the passed namespaces.
+// **Returns**:
+// *{string}* The CURIE or SCURIE.
+// **Example usage**:
+//
+// var ns = new myVIE.Namespaces(
+// "http://viejs.org/ns/",
+// { "dbp": "http://dbpedia.org/ontology/" }
+// );
+// var uri = "<http://dbpedia.org/ontology/Person>";
+// VIE.Util.toCurie(uri, false, ns); // --> dbp:Person
+// VIE.Util.toCurie(uri, true, ns); // --> [dbp:Person]
+ toCurie : function (uri, safe, namespaces) {
+ if (VIE.Util.isCurie(uri, namespaces)) {
+ return uri;
+ }
+ var delim = ":";
+ for (var k in namespaces.toObj()) {
+ if (uri.indexOf(namespaces.get(k)) === 1) {
+ var pattern = new RegExp("^" + "<?" + namespaces.get(k));
+ if (k === '') {
+ delim = '';
+ }
+ return ((safe)? "[" : "") +
+ uri.replace(pattern, k + delim).replace(/>$/, '') +
+ ((safe)? "]" : "");
+ }
+ }
+ throw new Error("No prefix found for URI '" + uri + "'!");
+ },
+
+// ### VIE.Util.isCurie(curie, namespaces)
+// This method checks, whether
+// the given string is a CURIE and returns ```true``` if so and ```false```otherwise.
+// **Parameters**:
+// *{string}* **curie** The CURIE (or SCURIE) to be checked.
+// *{VIE.Namespaces}* **namespaces** The namespaces to be used for the prefixes.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{boolean}* ```true``` if the given curie is a CURIE or SCURIE and ```false``` otherwise.
+// **Example usage**:
+//
+// var ns = new myVIE.Namespaces(
+// "http://viejs.org/ns/",
+// { "dbp": "http://dbpedia.org/ontology/" }
+// );
+// var uri = "<http://dbpedia.org/ontology/Person>";
+// var curie = "dbp:Person";
+// var scurie = "[dbp:Person]";
+// var text = "This is some text.";
+// VIE.Util.isCurie(uri, ns); // --> false
+// VIE.Util.isCurie(curie, ns); // --> true
+// VIE.Util.isCurie(scurie, ns); // --> true
+// VIE.Util.isCurie(text, ns); // --> false
+ isCurie : function (curie, namespaces) {
+ if (VIE.Util.isUri(curie)) {
+ return false;
+ } else {
+ try {
+ VIE.Util.toUri(curie, namespaces);
+ return true;
+ } catch (e) {
+ return false;
+ }
+ }
+ },
+
+// ### VIE.Util.toUri(curie, namespaces)
+// This method converts a
+// given CURIE (or save CURIE) into a URI, based on the given ```VIE.Namespaces``` object.
+// **Parameters**:
+// *{string}* **curie** The CURIE to be transformed.
+// *{VIE.Namespaces}* **namespaces** The namespaces object
+// **Throws**:
+// *{Error}* If no URI could be assembled.
+// **Returns**:
+// *{string}* : A string, representing the URI.
+// **Example usage**:
+//
+// var ns = new myVIE.Namespaces(
+// "http://viejs.org/ns/",
+// { "dbp": "http://dbpedia.org/ontology/" }
+// );
+// var curie = "dbp:Person";
+// var scurie = "[dbp:Person]";
+// VIE.Util.toUri(curie, ns);
+// --> <http://dbpedia.org/ontology/Person>
+// VIE.Util.toUri(scurie, ns);
+// --> <http://dbpedia.org/ontology/Person>
+ toUri : function (curie, namespaces) {
+ if (VIE.Util.isUri(curie)) {
+ return curie;
+ }
+ var delim = ":";
+ for (var prefix in namespaces.toObj()) {
+ if (prefix !== "" && (curie.indexOf(prefix + ":") === 0 || curie.indexOf("[" + prefix + ":") === 0)) {
+ var pattern = new RegExp("^" + "\\[{0,1}" + prefix + delim);
+ return "<" + curie.replace(pattern, namespaces.get(prefix)).replace(/\]{0,1}$/, '') + ">";
+ }
+ }
+ /* check for the default namespace */
+ if (curie.indexOf(delim) === -1) {
+ return "<" + namespaces.base() + curie + ">";
+ }
+ throw new Error("No prefix found for CURIE '" + curie + "'!");
+ },
+
+// ### VIE.Util.isUri(something)
+// This method checks, whether the given string is a URI.
+// **Parameters**:
+// *{string}* **something** : The string to be checked.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{boolean}* : ```true``` if the string is a URI, ```false``` otherwise.
+// **Example usage**:
+//
+// var uri = "<http://dbpedia.org/ontology/Person>";
+// var curie = "dbp:Person";
+// VIE.Util.isUri(uri); // --> true
+// VIE.Util.isUri(curie); // --> false
+ isUri : function (something) {
+ return (typeof something === "string" && something.search(/^<.+>$/) === 0);
+ },
+
+// ### VIE.Util.mapAttributeNS(attr, ns)
+// This method maps an attribute of an entity into namespaces if they have CURIEs.
+// **Parameters**:
+// *{string}* **attr** : The attribute to be transformed.
+// *{VIE.Namespaces}* **ns** : The namespaces.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{string}* : The transformed attribute's name.
+// **Example usage**:
+//
+// var attr = "name";
+// var ns = myVIE.namespaces;
+// VIE.Util.mapAttributeNS(attr, ns); // '<' + ns.base() + attr + '>';
+ mapAttributeNS : function (attr, ns) {
+ var a = attr;
+ if (ns.isUri (attr) || attr.indexOf('@') === 0) {
+ //ignore
+ } else if (ns.isCurie(attr)) {
+ a = ns.uri(attr);
+ } else if (!ns.isUri(attr)) {
+ if (attr.indexOf(":") === -1) {
+ a = '<' + ns.base() + attr + '>';
+ } else {
+ a = '<' + attr + '>';
+ }
+ }
+ return a;
+ },
+
+// ### VIE.Util.rdf2Entities(service, results)
+// This method converts *rdf/json* data from an external service
+// into VIE.Entities.
+// **Parameters**:
+// *{object}* **service** The service that retrieved the data.
+// *{object}* **results** The data to be transformed.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{[VIE.Entity]}* : An array, containing VIE.Entity instances which have been transformed from the given data.
+ rdf2Entities: function (service, results) {
+ if (typeof jQuery.rdf !== 'function') {
+ /* fallback if no rdfQuery has been loaded */
+ return VIE.Util._rdf2EntitiesNoRdfQuery(service, results);
+ }
+ try {
+ var rdf = (results instanceof jQuery.rdf)?
+ results.base(service.vie.namespaces.base()) :
+ jQuery.rdf().base(service.vie.namespaces.base()).load(results, {});
+
+ /* if the service contains rules to apply special transformation, they are executed here.*/
+ if (service.rules) {
+ var rules = jQuery.rdf.ruleset();
+ for (var prefix in service.vie.namespaces.toObj()) {
+ if (prefix !== "") {
+ rules.prefix(prefix, service.vie.namespaces.get(prefix));
+ }
+ }
+ for (var i = 0; i < service.rules.length; i++)if(service.rules.hasOwnProperty(i)) {
+ var rule = service.rules[i];
+ rules.add(rule.left, rule.right);
+ }
+ rdf = rdf.reason(rules, 10); /* execute the rules only 10 times to avoid looping */
+ }
+ var entities = {};
+ rdf.where('?subject ?property ?object').each(function() {
+ var subject = this.subject.toString();
+ if (!entities[subject]) {
+ entities[subject] = {
+ '@subject': subject,
+ '@context': service.vie.namespaces.toObj(true),
+ '@type': []
+ };
+ }
+ var propertyUri = this.property.toString();
+ var propertyCurie;
+
+ try {
+ propertyCurie = service.vie.namespaces.curie(propertyUri);
+ //jQuery.createCurie(propertyUri, {namespaces: service.vie.namespaces.toObj(true)});
+ } catch (e) {
+ propertyCurie = propertyUri;
+ // console.warn(propertyUri + " doesn't have a namespace definition in '", service.vie.namespaces.toObj());
+ }
+ entities[subject][propertyCurie] = entities[subject][propertyCurie] || [];
+
+ function getValue(rdfQueryLiteral){
+ if(typeof rdfQueryLiteral.value === "string"){
+ if (rdfQueryLiteral.lang){
+ var literal = {
+ toString: function(){
+ return this["@value"];
+ },
+ "@value": rdfQueryLiteral.value.replace(/^"|"$/g, ''),
+ "@language": rdfQueryLiteral.lang
+ };
+ return literal;
+ }
+ else
+ return rdfQueryLiteral.value;
+ return rdfQueryLiteral.value.toString();
+ } else if (rdfQueryLiteral.type === "uri"){
+ return rdfQueryLiteral.toString();
+ } else {
+ return rdfQueryLiteral.value;
+ }
+ }
+ entities[subject][propertyCurie].push(getValue(this.object));
+ });
+
+ _(entities).each(function(ent){
+ ent["@type"] = ent["@type"].concat(ent["rdf:type"]);
+ delete ent["rdf:type"];
+ _(ent).each(function(value, property){
+ if(value.length === 1){
+ ent[property] = value[0];
+ }
+ });
+ });
+
+ var vieEntities = [];
+ jQuery.each(entities, function() {
+ var entityInstance = new service.vie.Entity(this);
+ entityInstance = service.vie.entities.addOrUpdate(entityInstance);
+ vieEntities.push(entityInstance);
+ });
+ return vieEntities;
+ } catch (e) {
+ console.warn("Something went wrong while parsing the returned results!", e);
+ return [];
+ }
+ },
+
+ /*
+ VIE.Util.getPreferredLangForPreferredProperty(entity, preferredFields, preferredLanguages)
+ looks for specific ranking fields and languages. It calculates all possibilities and gives them
+ a score. It returns the value with the best score.
+ */
+ getPreferredLangForPreferredProperty: function(entity, preferredFields, preferredLanguages) {
+ var l, labelArr, lang, p, property, resArr, valueArr, _len, _len2,
+ _this = this;
+ resArr = [];
+ /* Try to find a label in the preferred language
+ */
+ _.each(preferredLanguages, function (lang) {
+ _.each(preferredFields, function (property) {
+ labelArr = null;
+ /* property can be a string e.g. "skos:prefLabel"
+ */
+ if (typeof property === "string" && entity.get(property)) {
+ labelArr = _.flatten([entity.get(property)]);
+ _(labelArr).each(function(label) {
+ /*
+ The score is a natural number with 0 for the
+ best candidate with the first preferred language
+ and first preferred property
+ */
+ var labelLang, score, value;
+ score = p;
+ labelLang = label["@language"];
+ /*
+ legacy code for compatibility with uotdated stanbol,
+ to be removed after may 2012
+ */
+ if (typeof label === "string" && (label.indexOf("@") === label.length - 3 || label.indexOf("@") === label.length - 5)) {
+ labelLang = label.replace(/(^\"*|\"*@)..(..)?$/g, "");
+ }
+ /* end of legacy code
+ */
+ if (labelLang) {
+ if (labelLang === lang) {
+ score += l;
+ } else {
+ score += 20;
+ }
+ } else {
+ score += 10;
+ }
+ value = label.toString();
+ /* legacy code for compatibility with uotdated stanbol, to be removed after may 2012
+ */
+ value = value.replace(/(^\"*|\"*@..$)/g, "");
+ /* end of legacy code
+ */
+ return resArr.push({
+ score: score,
+ value: value
+ });
+ });
+ /*
+ property can be an object like
+ {
+ property: "skos:broader",
+ makeLabel: function(propertyValueArr) { return "..."; }
+ }
+ */
+ } else if (typeof property === "object" && entity.get(property.property)) {
+ valueArr = _.flatten([entity.get(property.property)]);
+ valueArr = _(valueArr).map(function(termUri) {
+ if (termUri.isEntity) {
+ return termUri.getSubject();
+ } else {
+ return termUri;
+ }
+ });
+ resArr.push({
+ score: p,
+ value: property.makeLabel(valueArr)
+ });
+ }
+ });
+ });
+ /*
+ take the result with the best score
+ */
+ resArr = _(resArr).sortBy(function(a) {
+ return a.score;
+ });
+ if(resArr.length) {
+ return resArr[0].value;
+ } else {
+ return "n/a";
+ }
+ },
+
+
+// ### VIE.Util._rdf2EntitiesNoRdfQuery(service, results)
+// This is a **private** method which should
+// only be accessed through ```VIE.Util._rdf2Entities()``` and is a helper method in case there is no
+// rdfQuery loaded (*not recommended*).
+// **Parameters**:
+// *{object}* **service** The service that retrieved the data.
+// *{object}* **results** The data to be transformed.
+// **Throws**:
+// *nothing*
+// **Returns**:
+// *{[VIE.Entity]}* : An array, containing VIE.Entity instances which have been transformed from the given data.
+ _rdf2EntitiesNoRdfQuery: function (service, results) {
+ var jsonLD = [];
+ _.forEach(results, function(value, key) {
+ var entity = {};
+ entity['@subject'] = '<' + key + '>';
+ _.forEach(value, function(triples, predicate) {
+ predicate = '<' + predicate + '>';
+ _.forEach(triples, function(triple) {
+ if (triple.type === 'uri') {
+ triple.value = '<' + triple.value + '>';
+ }
+
+ if (entity[predicate] && !_.isArray(entity[predicate])) {
+ entity[predicate] = [entity[predicate]];
+ }
+
+ if (_.isArray(entity[predicate])) {
+ entity[predicate].push(triple.value);
+ return;
+ }
+ entity[predicate] = triple.value;
+ });
+ });
+ jsonLD.push(entity);
+ });
+ return jsonLD;
+ },
+
+// ### VIE.Util.loadSchemaOrg(vie, SchemaOrg, baseNS)
+// This method is a wrapper around
+// the <a href="http://schema.org/">schema.org</a> ontology. It adds all the
+// given types and properties as ```VIE.Type``` instances to the given VIE instance.
+// If the paramenter **baseNS** is set, the method automatically sets the namespace
+// to the provided one. If it is not set, it will keep the base namespace of VIE untouched.
+// **Parameters**:
+// *{VIE}* **vie** The instance of ```VIE```.
+// *{object}* **SchemaOrg** The data imported from schema.org.
+// *{string|undefined}* **baseNS** If set, this will become the new baseNamespace within the given ```VIE``` instance.
+// **Throws**:
+// *{Error}* If the parameter was not given.
+// **Returns**:
+// *nothing*
+ loadSchemaOrg : function (vie, SchemaOrg, baseNS) {
+
+ if (!SchemaOrg) {
+ throw new Error("Please load the schema.json file.");
+ }
+ vie.types.remove("<http://schema.org/Thing>");
+
+ var baseNSBefore = (baseNS)? baseNS : vie.namespaces.base();
+ vie.namespaces.base(baseNS);
+
+ var datatypeMapping = {
+ 'DataType': 'xsd:anyType',
+ 'Boolean' : 'xsd:boolean',
+ 'Date' : 'xsd:date',
+ 'DateTime': 'xsd:dateTime',
+ 'Time' : 'xsd:time',
+ 'Float' : 'xsd:float',
+ 'Integer' : 'xsd:integer',
+ 'Number' : 'xsd:anySimpleType',
+ 'Text' : 'xsd:string',
+ 'URL' : 'xsd:anyURI'
+ };
+
+ var dataTypeHelper = function (ancestors, id) {
+ var type = vie.types.add(id, [{'id' : 'value', 'range' : datatypeMapping[id]}]);
+
+ for (var i = 0; i < ancestors.length; i++) {
+ var supertype = (vie.types.get(ancestors[i]))? vie.types.get(ancestors[i]) :
+ dataTypeHelper.call(vie, SchemaOrg.datatypes[ancestors[i]].supertypes, ancestors[i]);
+ type.inherit(supertype);
+ }
+ return type;
+ };
+
+ for (var dt in SchemaOrg.datatypes) {
+ if (!vie.types.get(dt)) {
+ var ancestors = SchemaOrg.datatypes[dt].supertypes;
+ dataTypeHelper.call(vie, ancestors, dt);
+ }
+ }
+
+ var metadataHelper = function (definition) {
+ var metadata = {};
+
+ if (definition.label) {
+ metadata.label = definition.label;
+ }
+
+ if (definition.url) {
+ metadata.url = definition.url;
+ }
+
+ if (definition.comment) {
+ metadata.comment = definition.comment;
+ }
+
+ if (definition.metadata) {
+ metadata = _.extend(metadata, definition.metadata);
+ }
+ return metadata;
+ };
+
+ var typeProps = function (id) {
+ var props = [];
+ _.each(SchemaOrg.types[id].specific_properties, function (pId) {
+ var property = SchemaOrg.properties[pId];
+ props.push({
+ 'id' : property.id,
+ 'range' : property.ranges,
+ 'min' : property.min,
+ 'max' : property.max,
+ 'metadata': metadataHelper(property)
+ });
+ });
+ return props;
+ };
+
+ var typeHelper = function (ancestors, id, props, metadata) {
+ var type = vie.types.add(id, props, metadata);
+
+ for (var i = 0; i < ancestors.length; i++) {
+ var supertype = (vie.types.get(ancestors[i]))? vie.types.get(ancestors[i]) :
+ typeHelper.call(vie, SchemaOrg.types[ancestors[i]].supertypes, ancestors[i], typeProps.call(vie, ancestors[i]), metadataHelper(SchemaOrg.types[ancestors[i]]));
+ type.inherit(supertype);
+ }
+ if (id === "Thing" && !type.isof("owl:Thing")) {
+ type.inherit("owl:Thing");
+ }
+ return type;
+ };
+
+ _.each(SchemaOrg.types, function (typeDef) {
+ if (vie.types.get(typeDef.id)) {
+ return;
+ }
+ var ancestors = typeDef.supertypes;
+ var metadata = metadataHelper(typeDef);
+ typeHelper.call(vie, ancestors, typeDef.id, typeProps.call(vie, typeDef.id), metadata);
+ });
+
+ /* set the namespace to either the old value or the provided baseNS value */
+ vie.namespaces.base(baseNSBefore);
+ },
+
+// ### VIE.Util.getEntityTypeUnion(entity)
+// This generates a entity-specific VIE type that is a subtype of all the
+// types of the entity. This makes it easier to deal with attribute definitions
+// specific to an entity because they're merged to a single list. This custom
+// type is transient, meaning that it won't be automatilly added to the entity
+// or the VIE type registry.
+ getEntityTypeUnion : function(entity) {
+ var vie = entity.vie;
+ return new vie.Type('Union').inherit(entity.get('@type'));
+ },
+
+// ### VIE.Util.getFormSchemaForType(type)
+// This creates a [Backbone Forms](https://github.com/powmedia/backbone-forms)
+// -compatible form schema for any VIE Type.
+ getFormSchemaForType : function(type, allowNested) {
+ var schema = {};
+
+ // Generate a schema
+ _.each(type.attributes.toArray(), function (attribute) {
+ var key = VIE.Util.toCurie(attribute.id, false, attribute.vie.namespaces);
+ schema[key] = VIE.Util.getFormSchemaForAttribute(attribute);
+ });
+
+ // Clean up unknown attribute types
+ _.each(schema, function (field, id) {
+ if (!field.type) {
+ delete schema[id];
+ }
+
+ if (field.type === 'URL') {
+ field.type = 'Text';
+ field.dataType = 'url';
+ }
+
+ if (field.type === 'List' && !field.listType) {
+ delete schema[id];
+ }
+
+ if (!allowNested) {
+ if (field.type === 'NestedModel' || field.listType === 'NestedModel') {
+ delete schema[id];
+ }
+ }
+ });
+
+ return schema;
+ },
+
+/// ### VIE.Util.getFormSchemaForAttribute(attribute)
+ getFormSchemaForAttribute : function(attribute) {
+ var primaryType = attribute.range[0];
+ var schema = {};
+
+ var getWidgetForType = function (type) {
+ switch (type) {
+ case 'xsd:anySimpleType':
+ case 'xsd:float':
+ case 'xsd:integer':
+ return 'Number';
+ case 'xsd:string':
+ return 'Text';
+ case 'xsd:date':
+ return 'Date';
+ case 'xsd:dateTime':
+ return 'DateTime';
+ case 'xsd:boolean':
+ return 'Checkbox';
+ case 'xsd:anyURI':
+ return 'URL';
+ default:
+ var typeType = attribute.vie.types.get(type);
+ if (!typeType) {
+ return null;
+ }
+ if (typeType.attributes.get('value')) {
+ // Convert to proper xsd type
+ return getWidgetForType(typeType.attributes.get('value').range[0]);
+ }
+ return 'NestedModel';
+ }
+ };
+
+ // TODO: Generate a nicer label
+ schema.title = VIE.Util.toCurie(attribute.id, false, attribute.vie.namespaces);
+
+ // TODO: Handle attributes linking to other VIE entities
+
+ if (attribute.min > 0) {
+ schema.validators = ['required'];
+ }
+
+ if (attribute.max > 1) {
+ schema.type = 'List';
+ schema.listType = getWidgetForType(primaryType);
+ if (schema.listType === 'NestedModel') {
+ schema.nestedModelType = primaryType;
+ }
+ return schema;
+ }
+
+ schema.type = getWidgetForType(primaryType);
+ if (schema.type === 'NestedModel') {
+ schema.nestedModelType = primaryType;
+ }
+ return schema;
+ },
+
+// ### VIE.Util.getFormSchema(entity)
+// This creates a [Backbone Forms](https://github.com/powmedia/backbone-forms)
+// -compatible form schema for any VIE Entity. The form schema creation
+// utilizes type information attached to the entity.
+// **Parameters**:
+// *{```Entity```}* **entity** An instance of VIE ```Entity```.
+// **Throws**:
+// *nothing*..
+// **Returns**:
+// *{object}* a JavaScript object representation of the form schema
+ getFormSchema : function(entity) {
+ if (!entity || !entity.isEntity) {
+ return {};
+ }
+
+ var unionType = VIE.Util.getEntityTypeUnion(entity);
+ var schema = VIE.Util.getFormSchemaForType(unionType, true);
+
+ // Handle nested models
+ _.each(schema, function (property, id) {
+ if (property.type !== 'NestedModel' && property.listType !== 'NestedModel') {
+ return;
+ }
+ schema[id].model = entity.vie.getTypedEntityClass(property.nestedModelType);
+ });
+
+ return schema;
+ },
+
+// ### VIE.Util.xsdDateTime(date)
+// This transforms a ```Date``` instance into an xsd:DateTime format.
+// **Parameters**:
+// *{```Date```}* **date** An instance of a javascript ```Date```.
+// **Throws**:
+// *nothing*..
+// **Returns**:
+// *{string}* A string representation of the dateTime in the xsd:dateTime format.
+ xsdDateTime : function(date) {
+ function pad(n) {
+ var s = n.toString();
+ return s.length < 2 ? '0'+s : s;
+ }
+
+ var yyyy = date.getFullYear();
+ var mm1 = pad(date.getMonth()+1);
+ var dd = pad(date.getDate());
+ var hh = pad(date.getHours());
+ var mm2 = pad(date.getMinutes());
+ var ss = pad(date.getSeconds());
+
+ return yyyy +'-' +mm1 +'-' +dd +'T' +hh +':' +mm2 +':' +ss;
+ },
+
+// ### VIE.Util.extractLanguageString(entity, attrs, langs)
+// This method extracts a literal string from an entity, searching through the given attributes and languages.
+// **Parameters**:
+// *{```VIE.Entity```}* **entity** An instance of a VIE.Entity.
+// *{```array|string```}* **attrs** Either a string or an array of possible attributes.
+// *{```array|string```}* **langs** Either a string or an array of possible languages.
+// **Throws**:
+// *nothing*..
+// **Returns**:
+// *{string|undefined}* The string that was found at the attribute with the wanted language, undefined if nothing could be found.
+// **Example usage**:
+//
+// var attrs = ["name", "rdfs:label"];
+// var langs = ["en", "de"];
+// VIE.Util.extractLanguageString(someEntity, attrs, langs); // "Barack Obama";
+ extractLanguageString : function(entity, attrs, langs) {
+ var p, attr, name, i, n;
+ if (entity && typeof entity !== "string") {
+ attrs = (_.isArray(attrs))? attrs : [ attrs ];
+ langs = (_.isArray(langs))? langs : [ langs ];
+ for (p = 0; p < attrs.length; p++) {
+ for (var l = 0; l < langs.length; l++) {
+ var lang = langs[l];
+ attr = attrs[p];
+ if (entity.has(attr)) {
+ name = entity.get(attr);
+ name = (_.isArray(name))? name : [ name ];
+ for (i = 0; i < name.length; i++) {
+ n = name[i];
+ if (n.isEntity) {
+ n = VIE.Util.extractLanguageString(n, attrs, lang);
+ } else if (typeof n === "string") {
+ n = n;
+ } else {
+ n = "";
+ }
+ if (n && n.indexOf('@' + lang) > -1) {
+ return n.replace(/"/g, "").replace(/@[a-z]+/, '').trim();
+ }
+ }
+ }
+ }
+ }
+ /* let's do this again in case we haven't found a name but are dealing with
+ broken data where no language is given */
+ for (p = 0; p < attrs.length; p++) {
+ attr = attrs[p];
+ if (entity.has(attr)) {
+ name = entity.get(attr);
+ name = (_.isArray(name))? name : [ name ];
+ for (i = 0; i < name.length; i++) {
+ n = name[i];
+ if (n.isEntity) {
+ n = VIE.Util.extractLanguageString(n, attrs, []);
+ }
+ if (n && (typeof n === "string") && n.indexOf('@') === -1) {
+ return n.replace(/"/g, "").replace(/@[a-z]+/, '').trim();
+ }
+ }
+ }
+ }
+ }
+ return undefined;
+ },
+
+// ### VIE.Util.transformationRules(service)
+// This returns a default set of rdfQuery rules that transform semantic data into the
+// VIE entity types.
+// **Parameters**:
+// *{object}* **service** An instance of a vie.service.
+// **Throws**:
+// *nothing*..
+// **Returns**:
+// *{array}* An array of rules with 'left' and 'right' side.
+ transformationRules : function (service) {
+ var res = [
+ // rule(s) to transform a dbpedia:Person into a VIE:Person
+ {
+ 'left' : [
+ '?subject a dbpedia:Person',
+ '?subject rdfs:label ?label'
+ ],
+ 'right': function(ns){
+ return function(){
+ return [
+ jQuery.rdf.triple(this.subject.toString(),
+ 'a',
+ '<' + ns.base() + 'Person>', {
+ namespaces: ns.toObj()
+ }),
+ jQuery.rdf.triple(this.subject.toString(),
+ '<' + ns.base() + 'name>',
+ this.label, {
+ namespaces: ns.toObj()
+ })
+ ];
+ };
+ }(service.vie.namespaces)
+ },
+ // rule(s) to transform a foaf:Person into a VIE:Person
+ {
+ 'left' : [
+ '?subject a foaf:Person',
+ '?subject rdfs:label ?label'
+ ],
+ 'right': function(ns){
+ return function(){
+ return [
+ jQuery.rdf.triple(this.subject.toString(),
+ 'a',
+ '<' + ns.base() + 'Person>', {
+ namespaces: ns.toObj()
+ }),
+ jQuery.rdf.triple(this.subject.toString(),
+ '<' + ns.base() + 'name>',
+ this.label, {
+ namespaces: ns.toObj()
+ })
+ ];
+ };
+ }(service.vie.namespaces)
+ },
+ // rule(s) to transform a dbpedia:Place into a VIE:Place
+ {
+ 'left' : [
+ '?subject a dbpedia:Place',
+ '?subject rdfs:label ?label'
+ ],
+ 'right': function(ns) {
+ return function() {
+ return [
+ jQuery.rdf.triple(this.subject.toString(),
+ 'a',
+ '<' + ns.base() + 'Place>', {
+ namespaces: ns.toObj()
+ }),
+ jQuery.rdf.triple(this.subject.toString(),
+ '<' + ns.base() + 'name>',
+ this.label.toString(), {
+ namespaces: ns.toObj()
+ })
+ ];
+ };
+ }(service.vie.namespaces)
+ },
+ // rule(s) to transform a dbpedia:City into a VIE:City
+ {
+ 'left' : [
+ '?subject a dbpedia:City',
+ '?subject rdfs:label ?label',
+ '?subject dbpedia:abstract ?abs',
+ '?subject dbpedia:country ?country'
+ ],
+ 'right': function(ns) {
+ return function() {
+ return [
+ jQuery.rdf.triple(this.subject.toString(),
+ 'a',
+ '<' + ns.base() + 'City>', {
+ namespaces: ns.toObj()
+ }),
+ jQuery.rdf.triple(this.subject.toString(),
+ '<' + ns.base() + 'name>',
+ this.label.toString(), {
+ namespaces: ns.toObj()
+ }),
+ jQuery.rdf.triple(this.subject.toString(),
+ '<' + ns.base() + 'description>',
+ this.abs.toString(), {
+ namespaces: ns.toObj()
+ }),
+ jQuery.rdf.triple(this.subject.toString(),
+ '<' + ns.base() + 'containedIn>',
+ this.country.toString(), {
+ namespaces: ns.toObj()
+ })
+ ];
+ };
+ }(service.vie.namespaces)
+ }
+ ];
+ return res;
+ },
+
+ getAdditionalRules : function (service) {
+
+ var mapping = {
+ Work : "CreativeWork",
+ Film : "Movie",
+ TelevisionEpisode : "TVEpisode",
+ TelevisionShow : "TVSeries", // not listed as equivalent class on dbpedia.org
+ Website : "WebPage",
+ Painting : "Painting",
+ Sculpture : "Sculpture",
+
+ Event : "Event",
+ SportsEvent : "SportsEvent",
+ MusicFestival : "Festival",
+ FilmFestival : "Festival",
+
+ Place : "Place",
+ Continent : "Continent",
+ Country : "Country",
+ City : "City",
+ Airport : "Airport",
+ Station : "TrainStation", // not listed as equivalent class on dbpedia.org
+ Hospital : "GovernmentBuilding",
+ Mountain : "Mountain",
+ BodyOfWater : "BodyOfWater",
+
+ Company : "Organization",
+ Person : "Person"
+ };
+
+ var additionalRules = [];
+ _.each(mapping, function (map, key) {
+ var tripple = {
+ 'left' : [ '?subject a dbpedia:' + key, '?subject rdfs:label ?label' ],
+ 'right' : function(ns) {
+ return function() {
+ return [ jQuery.rdf.triple(this.subject.toString(), 'a', '<' + ns.base() + map + '>', {
+ namespaces : ns.toObj()
+ }), jQuery.rdf.triple(this.subject.toString(), '<' + ns.base() + 'name>', this.label.toString(), {
+ namespaces : ns.toObj()
+ }) ];
+ };
+ }(service.vie.namespaces)
+ };
+ additionalRules.push(tripple);
+ });
+ return additionalRules;
+ }
+};
+// VIE - Vienna IKS Editables
+// (c) 2011 Henri Bergius, IKS Consortium
+// (c) 2011 Sebastian Germesin, IKS Consortium
+// (c) 2011 Szaby Grünwald, IKS Consortium
+// VIE may be freely distributed under the MIT license.
+// For all details and documentation:
+// http://viejs.org/
+
+// ## VIE Entities
+//
+// In VIE there are two low-level model types for storing data.
+// **Collections** and **Entities**. Considering `var v = new VIE();` a VIE instance,
+// `v.entities` is a Collection with `VIE Entity` objects in it.
+// VIE internally uses JSON-LD to store entities.
+//
+// Each Entity has a few special attributes starting with an `@`. VIE has an API
+// for correctly using these attributes, so in order to stay compatible with later
+// versions of the library, possibly using a later version of JSON-LD, use the API
+// to interact with your entities.
+//
+// * `@subject` stands for the identifier of the entity. Use `e.getSubject()`
+// * `@type` stores the explicit entity types. VIE internally handles Type hierarchy,
+// which basically enables to define subtypes and supertypes. Every entity has
+// the type 'owl:Thing'. Read more about Types in <a href="Type.html">VIE.Type</a>.
+// * `@context` stores namespace definitions used in the entity. Read more about
+// Namespaces in <a href="Namespace.html">VIE Namespaces</a>.
+VIE.prototype.Entity = function(attrs, opts) {
+
+ attrs = (attrs)? attrs : {};
+ opts = (opts)? opts : {};
+
+ var self = this;
+
+ if (attrs['@type'] !== undefined) {
+ attrs['@type'] = (_.isArray(attrs['@type']))? attrs['@type'] : [ attrs['@type'] ];
+ attrs['@type'] = _.map(attrs['@type'], function(val){
+ if (!self.vie.types.get(val)) {
+ //if there is no such type -> add it and let it inherit from "owl:Thing"
+ self.vie.types.add(val).inherit("owl:Thing");
+ }
+ return self.vie.types.get(val).id;
+ });
+ attrs['@type'] = (attrs['@type'].length === 1)? attrs['@type'][0] : attrs['@type'];
+ } else {
+ // provide "owl:Thing" as the default type if none was given
+ attrs['@type'] = self.vie.types.get("owl:Thing").id;
+ }
+
+ //the following provides full seamless namespace support
+ //for attributes. It should not matter, if you
+ //query for `model.get('name')` or `model.get('foaf:name')`
+ //or even `model.get('http://xmlns.com/foaf/0.1/name');`
+ //However, if we just overwrite `set()` and `get()`, this
+ //raises a lot of side effects, so we need to expand
+ //the attributes before we create the model.
+ _.each (attrs, function (value, key) {
+ var newKey = VIE.Util.mapAttributeNS(key, this.namespaces);
+ if (key !== newKey) {
+ delete attrs[key];
+ attrs[newKey] = value;
+ }
+ }, self.vie);
+
+ var Model = Backbone.Model.extend({
+ idAttribute: '@subject',
+
+ initialize: function(attributes, options) {
+ if (attributes['@subject']) {
+ this.id = this['@subject'] = this.toReference(attributes['@subject']);
+ } else {
+ this.id = this['@subject'] = attributes['@subject'] = this.cid.replace('c', '_:bnode');
+ }
+ return this;
+ },
+
+ schema: function() {
+ return VIE.Util.getFormSchema(this);
+ },
+
+ // ### Getter, Has, Setter
+ // #### `.get(attr)`
+ // To be able to communicate to a VIE Entity you can use a simple get(property)
+ // command as in `entity.get('rdfs:label')` which will give you one or more literals.
+ // If the property points to a collection, its entities can be browsed further.
+ get: function (attr) {
+ attr = VIE.Util.mapAttributeNS(attr, self.vie.namespaces);
+ var value = Backbone.Model.prototype.get.call(this, attr);
+ value = (_.isArray(value))? value : [ value ];
+
+ value = _.map(value, function(v) {
+ if (v !== undefined && attr === '@type' && self.vie.types.get(v)) {
+ return self.vie.types.get(v);
+ } else if (v !== undefined && self.vie.entities.get(v)) {
+ return self.vie.entities.get(v);
+ } else {
+ return v;
+ }
+ }, this);
+ if(value.length === 0) {
+ return undefined;
+ }
+ // if there is only one element, just return that one
+ value = (value.length === 1)? value[0] : value;
+ return value;
+ },
+
+ // #### `.has(attr)`
+ // Sometimes you'd like to determine if a specific attribute is set
+ // in an entity. For this reason you can call for example `person.has('friend')`
+ // to determine if a person entity has friends.
+ has: function(attr) {
+ attr = VIE.Util.mapAttributeNS(attr, self.vie.namespaces);
+ return Backbone.Model.prototype.has.call(this, attr);
+ },
+
+ hasRelations: function() {
+ var found = false;
+ _.each(this.attributes, function (value) {
+ if (value && value.isCollection) {
+ found = true;
+ }
+ });
+ return found;
+ },
+
+ // #### `.set(attrName, value, opts)`,
+ // The `options` parameter always refers to a `Backbone.Model.set` `options` object.
+ //
+ // **`.set(attributes, options)`** is the most universal way of calling the
+ // `.set` method. In this case the `attributes` object is a map of all
+ // attributes to be changed.
+ set : function(attrs, options, opts) {
+ if (!attrs) {
+ return this;
+ }
+
+ if (attrs['@subject']) {
+ attrs['@subject'] = this.toReference(attrs['@subject']);
+ }
+
+ // Use **`.set(attrName, value, options)`** for setting or changing exactly one
+ // entity attribute.
+ if (typeof attrs === "string") {
+ var obj = {};
+ obj[attrs] = options;
+ return this.set(obj, opts);
+ }
+ // **`.set(entity)`**: In case you'd pass a VIE entity,
+ // the passed entities attributes are being set for the entity.
+ if (attrs.attributes) {
+ attrs = attrs.attributes;
+ }
+ var self = this;
+ var coll;
+ // resolve shortened URIs like rdfs:label..
+ _.each (attrs, function (value, key) {
+ var newKey = VIE.Util.mapAttributeNS(key, self.vie.namespaces);
+ if (key !== newKey) {
+ delete attrs[key];
+ attrs[newKey] = value;
+ }
+ }, this);
+ // Finally iterate through the *attributes* to be set and prepare
+ // them for the Backbone.Model.set method.
+ _.each (attrs, function (value, key) {
+ if (!value) { return; }
+ if (key.indexOf('@') === -1) {
+ if (value.isCollection) {
+ // ignore
+ value.each(function (child) {
+ self.vie.entities.addOrUpdate(child);
+ });
+ } else if (value.isEntity) {
+ self.vie.entities.addOrUpdate(value);
+ coll = new self.vie.Collection(value, {
+ vie: self.vie,
+ predicate: key
+ });
+ attrs[key] = coll;
+ } else if (_.isArray(value)) {
+ if (this.attributes[key] && this.attributes[key].isCollection) {
+ var newEntities = this.attributes[key].addOrUpdate(value);
+ attrs[key] = this.attributes[key];
+ attrs[key].reset(newEntities);
+ }
+ } else if (value["@value"]) {
+ // The value is a literal object, ignore
+ } else if (_.isObject(value) && !_.isDate(value)) {
+ // The value is another VIE Entity
+ var child = new self.vie.Entity(value, options);
+ // which is being stored in `v.entities`
+ self.vie.entities.addOrUpdate(child);
+ // and set as VIE Collection attribute on the original entity
+ coll = new self.vie.Collection(value, {
+ vie: self.vie,
+ predicate: key
+ });
+ attrs[key] = coll;
+ } else {
+ // ignore
+ }
+ }
+ }, this);
+ var ret = Backbone.Model.prototype.set.call(this, attrs, options);
+ if (options && options.ignoreChanges) {
+ // TODO: This will need to be changed to reflect now change tracking mechanisms
+ // in Backbone.js 1.0.0
+ this.changed = {};
+ this._previousAttributes = _.clone(this.attributes);
+ }
+ return ret;
+ },
+
+ // **`.unset(attr, opts)` ** removes an attribute from the entity.
+ unset: function (attr, opts) {
+ attr = VIE.Util.mapAttributeNS(attr, self.vie.namespaces);
+ return Backbone.Model.prototype.unset.call(this, attr, opts);
+ },
+
+ // Validation based on type rules.
+ //
+ // There are two ways to skip validation for entity operations:
+ //
+ // * `options.silent = true`
+ // * `options.validate = false`
+ validate: function (attrs, opts) {
+ if (opts && opts.validate === false) {
+ return;
+ }
+ var types = this.get('@type');
+ if (_.isArray(types)) {
+ var results = [];
+ _.each(types, function (type) {
+ var res = this.validateByType(type, attrs, opts);
+ if (res) {
+ results.push(res);
+ }
+ }, this);
+ if (_.isEmpty(results)) {
+ return;
+ }
+ return _.flatten(results);
+ }
+
+ return this.validateByType(types, attrs, opts);
+ },
+
+ validateByType: function (type, attrs, opts) {
+ var messages = {
+ max: '<%= property %> cannot contain more than <%= num %> items',
+ min: '<%= property %> must contain at least <%= num %> items',
+ required: '<%= property %> is required'
+ };
+
+ if (!type.attributes) {
+ return;
+ }
+
+ var toError = function (definition, constraint, messageValues) {
+ return {
+ property: definition.id,
+ constraint: constraint,
+ message: _.template(messages[constraint], _.extend({
+ property: definition.id
+ }, messageValues))
+ };
+ };
+
+ var checkMin = function (definition, attrs) {
+ if (!attrs[definition.id] || _.isEmpty(attrs[definition.id])) {
+ return toError(definition, 'required', {});
+ }
+ };
+
+ // Check the number of items in attr against max
+ var checkMax = function (definition, attrs) {
+ if (!attrs[definition.id]) {
+ return;
+ }
+
+ if (!attrs[definition.id].isCollection && !_.isArray(attrs[definition.id])) {
+ return;
+ }
+
+ if (attrs[definition.id].length > definition.max) {
+ return toError(definition, 'max', {
+ num: definition.max
+ });
+ }
+ };
+
+ var results = [];
+ _.each(type.attributes.list(), function (definition) {
+ var res;
+ if (definition.max && definition.max != -1) {
+ res = checkMax(definition, attrs);
+ if (res) {
+ results.push(res);
+ }
+ }
+
+ if (definition.min && definition.min > 0) {
+ res = checkMin(definition, attrs);
+ if (res) {
+ results.push(res);
+ }
+ }
+ });
+
+ if (_.isEmpty(results)) {
+ return;
+ }
+ return results;
+ },
+
+ isNew: function() {
+ if (this.getSubjectUri().substr(0, 7) === '_:bnode') {
+ return true;
+ }
+ return false;
+ },
+
+ hasChanged: function(attr) {
+ if (this.markedChanged) {
+ return true;
+ }
+
+ return Backbone.Model.prototype.hasChanged.call(this, attr);
+ },
+
+ // Force hasChanged to return true
+ forceChanged: function(changed) {
+ this.markedChanged = changed ? true : false;
+ },
+
+ // **`getSubject()`** is the getter for the entity identifier.
+ getSubject: function(){
+ if (typeof this.id === "undefined") {
+ this.id = this.attributes[this.idAttribute];
+ }
+ if (typeof this.id === 'string') {
+ if (this.id.substr(0, 7) === 'http://' || this.id.substr(0, 4) === 'urn:') {
+ return this.toReference(this.id);
+ }
+ return this.id;
+ }
+ return this.cid.replace('c', '_:bnode');
+ },
+
+ // TODO describe
+ getSubjectUri: function(){
+ return this.fromReference(this.getSubject());
+ },
+
+ isReference: function(uri){
+ var matcher = new RegExp("^\\<([^\\>]*)\\>$");
+ if (matcher.exec(uri)) {
+ return true;
+ }
+ return false;
+ },
+
+ toReference: function(uri){
+ if (_.isArray(uri)) {
+ var self = this;
+ return _.map(uri, function(part) {
+ return self.toReference(part);
+ });
+ }
+ var ns = this.vie.namespaces;
+ var ret = uri;
+ if (uri.substring(0, 2) === "_:") {
+ ret = uri;
+ }
+ else if (ns.isCurie(uri)) {
+ ret = ns.uri(uri);
+ if (ret === "<" + ns.base() + uri + ">") {
+ /* no base namespace extension with IDs */
+ ret = '<' + uri + '>';
+ }
+ } else if (!ns.isUri(uri)) {
+ ret = '<' + uri + '>';
+ }
+ return ret;
+ },
+
+ fromReference: function(uri){
+ var ns = this.vie.namespaces;
+ if (!ns.isUri(uri)) {
+ return uri;
+ }
+ return uri.substring(1, uri.length - 1);
+ },
+
+ as: function(encoding){
+ if (encoding === "JSON") {
+ return this.toJSON();
+ }
+ if (encoding === "JSONLD") {
+ return this.toJSONLD();
+ }
+ throw new Error("Unknown encoding " + encoding);
+ },
+
+ toJSONLD: function(){
+ var instanceLD = {};
+ var instance = this;
+ _.each(instance.attributes, function(value, name){
+ var entityValue = value; //instance.get(name);
+
+ if (value instanceof instance.vie.Collection) {
+ entityValue = value.map(function(instance) {
+ return instance.getSubject();
+ });
+ }
+
+ // TODO: Handle collections separately
+ instanceLD[name] = entityValue;
+ });
+
+ instanceLD['@subject'] = instance.getSubject();
+
+ return instanceLD;
+ },
+
+ // **`.setOrAdd(arg1, arg2)`** similar to `.set(..)`, `.setOrAdd(..)` can
+ // be used for setting one or more attributes of an entity, but in
+ // this case it's a collection of values, not just one. That means, if the
+ // entity already has the attribute set, make the value to a VIE Collection
+ // and use the collection as value. The collection can contain entities
+ // or literals, but not both at the same time.
+ setOrAdd: function (arg1, arg2, option) {
+ var entity = this;
+ if (typeof arg1 === "string" && arg2) {
+ // calling entity.setOrAdd("rdfs:type", "example:Musician")
+ entity._setOrAddOne(arg1, arg2, option);
+ }
+ else
+ if (typeof arg1 === "object") {
+ // calling entity.setOrAdd({"rdfs:type": "example:Musician", ...})
+ _(arg1).each(function(val, key){
+ entity._setOrAddOne(key, val, arg2);
+ });
+ }
+ return this;
+ },
+
+
+ /* attr is always of type string */
+ /* value can be of type: string,int,double,object,VIE.Entity,VIE.Collection */
+ /* val can be of type: undefined,string,int,double,array,VIE.Collection */
+
+ /* depending on the type of value and the type of val, different actions need to be made */
+ _setOrAddOne: function (attr, value, options) {
+ if (!attr || !value)
+ return;
+ options = (options)? options : {};
+ var v;
+
+ attr = VIE.Util.mapAttributeNS(attr, self.vie.namespaces);
+
+ if (_.isArray(value)) {
+ for (v = 0; v < value.length; v++) {
+ this._setOrAddOne(attr, value[v], options);
+ }
+ return;
+ }
+
+ if (attr === "@type" && value instanceof self.vie.Type) {
+ value = value.id;
+ }
+
+ var obj = {};
+ var existing = Backbone.Model.prototype.get.call(this, attr);
+
+ if (!existing) {
+ obj[attr] = value;
+ this.set(obj, options);
+ } else if (existing.isCollection) {
+ if (value.isCollection) {
+ value.each(function (model) {
+ existing.add(model);
+ });
+ } else if (value.isEntity) {
+ existing.add(value);
+ } else if (typeof value === "object") {
+ value = new this.vie.Entity(value);
+ existing.add(value);
+ } else {
+ throw new Error("you cannot add a literal to a collection of entities!");
+ }
+ this.trigger('change:' + attr, this, value, {});
+ this.change({});
+ } else if (_.isArray(existing)) {
+ if (value.isCollection) {
+ for (v = 0; v < value.size(); v++) {
+ this._setOrAddOne(attr, value.at(v).getSubject(), options);
+ }
+ } else if (value.isEntity) {
+ this._setOrAddOne(attr, value.getSubject(), options);
+ } else if (typeof value === "object") {
+ value = new this.vie.Entity(value);
+ this._setOrAddOne(attr, value, options);
+ } else {
+ /* yes, we (have to) allow multiple equal values */
+ existing.push(value);
+ obj[attr] = existing;
+ this.set(obj);
+ }
+ } else {
+ var arr = [ existing ];
+ arr.push(value);
+ obj[attr] = arr;
+ return this.set(obj, options);
+ }
+ },
+
+ // **`.hasType(type)`** determines if the entity has the explicit `type` set.
+ hasType: function(type){
+ type = self.vie.types.get(type);
+ return this.hasPropertyValue("@type", type);
+ },
+
+ // TODO describe
+ hasPropertyValue: function(property, value) {
+ var t = this.get(property);
+ if (!(value instanceof Object)) {
+ value = self.vie.entities.get(value);
+ }
+ if (t instanceof Array) {
+ return t.indexOf(value) !== -1;
+ }
+ else {
+ return t === value;
+ }
+ },
+
+ // **`.isof(type)`** determines if the entity is of `type` by explicit or implicit
+ // declaration. E.g. if Employee is a subtype of Person and e Entity has
+ // explicitly set type Employee, e.isof(Person) will evaluate to true.
+ isof: function (type) {
+ var types = this.get('@type');
+
+ if (types === undefined) {
+ return false;
+ }
+ types = (_.isArray(types))? types : [ types ];
+
+ type = (self.vie.types.get(type))? self.vie.types.get(type) : new self.vie.Type(type);
+ for (var t = 0; t < types.length; t++) {
+ if (self.vie.types.get(types[t])) {
+ if (self.vie.types.get(types[t]).isof(type)) {
+ return true;
+ }
+ } else {
+ var typeTmp = new self.vie.Type(types[t]);
+ if (typeTmp.id === type.id) {
+ return true;
+ }
+ }
+ }
+ return false;
+ },
+ // TODO describe
+ addTo : function (collection, update) {
+ var self = this;
+ if (collection instanceof self.vie.Collection) {
+ if (update) {
+ collection.addOrUpdate(self);
+ } else {
+ collection.add(self);
+ }
+ return this;
+ }
+ throw new Error("Please provide a proper collection of type VIE.Collection as argument!");
+ },
+
+ isEntity: true,
+
+ vie: self.vie
+ });
+
+ return new Model(attrs, opts);
+};
+// VIE - Vienna IKS Editables
+// (c) 2011 Henri Bergius, IKS Consortium
+// (c) 2011 Sebastian Germesin, IKS Consortium
+// (c) 2011 Szaby Grünwald, IKS Consortium
+// VIE may be freely distributed under the MIT license.
+// For all details and documentation:
+// http://viejs.org/
+VIE.prototype.Collection = Backbone.Collection.extend({
+ model: VIE.prototype.Entity,
+
+ initialize: function (models, options) {
+ if (!options || !options.vie) {
+ throw new Error('Each collection needs a VIE reference');
+ }
+ this.vie = options.vie;
+ this.predicate = options.predicate;
+ },
+
+ canAdd: function (type) {
+ return true;
+ },
+
+ get: function(id) {
+ if (id === null) {
+ return null;
+ }
+
+ id = (id.getSubject)? id.getSubject() : id;
+ if (typeof id === "string" && id.indexOf("_:") === 0) {
+ if (id.indexOf("bnode") === 2) {
+ //bnode!
+ id = id.replace("_:bnode", 'c');
+ return this._byCid[id];
+ } else {
+ return this._byId["<" + id + ">"];
+ }
+ } else {
+ id = this.toReference(id);
+ return this._byId[id];
+ }
+ },
+
+ addOrUpdate: function(model, options) {
+ options = options || {};
+
+ var collection = this;
+ var existing;
+ if (_.isArray(model)) {
+ var entities = [];
+ _.each(model, function(item) {
+ entities.push(collection.addOrUpdate(item, options));
+ });
+ return entities;
+ }
+
+ if (model === undefined) {
+ throw new Error("No model given");
+ }
+
+ if (_.isString(model)) {
+ model = {
+ '@subject': model,
+ id: model
+ };
+ }
+
+ if (!model.isEntity) {
+ model = new this.model(model);
+ }
+
+ if (model.id && this.get(model.id)) {
+ existing = this.get(model.id);
+ }
+ if (this.getByCid(model.cid)) {
+ existing = this.getByCid(model.cid);
+ }
+ if (existing) {
+ var newAttribs = {};
+ _.each(model.attributes, function(value, attribute) {
+ if (!existing.has(attribute)) {
+ newAttribs[attribute] = value;
+ return true;
+ }
+
+ if (attribute === '@subject') {
+ if (model.isNew() && !existing.isNew()) {
+ // Save order issue, skip
+ return true;
+ }
+ }
+
+ if (existing.get(attribute) === value) {
+ return true;
+ }
+ //merge existing attribute values with new ones!
+ //not just overwrite 'em!!
+ var oldVals = existing.attributes[attribute];
+ var newVals = value;
+ if (oldVals instanceof collection.vie.Collection) {
+ // TODO: Merge collections
+ return true;
+ }
+ if (options.overrideAttributes) {
+ newAttribs[attribute] = value;
+ return true;
+ }
+ if (attribute === '@context') {
+ newAttribs[attribute] = jQuery.extend(true, {}, oldVals, newVals);
+ } else {
+ oldVals = (jQuery.isArray(oldVals))? oldVals : [ oldVals ];
+ newVals = (jQuery.isArray(newVals))? newVals : [ newVals ];
+ newAttribs[attribute] = _.uniq(oldVals.concat(newVals));
+ newAttribs[attribute] = (newAttribs[attribute].length === 1)? newAttribs[attribute][0] : newAttribs[attribute];
+ }
+ });
+
+ if (!_.isEmpty(newAttribs)) {
+ existing.set(newAttribs, options.updateOptions);
+ }
+ return existing;
+ }
+ this.add(model, options.addOptions);
+ return model;
+ },
+
+ isReference: function(uri){
+ var matcher = new RegExp("^\\<([^\\>]*)\\>$");
+ if (matcher.exec(uri)) {
+ return true;
+ }
+ return false;
+ },
+
+ toReference: function(uri){
+ if (this.isReference(uri)) {
+ return uri;
+ }
+ return '<' + uri + '>';
+ },
+
+ fromReference: function(uri){
+ if (!this.isReference(uri)) {
+ return uri;
+ }
+ return uri.substring(1, uri.length - 1);
+ },
+
+ isCollection: true
+});
+// VIE - Vienna IKS Editables
+// (c) 2011 Henri Bergius, IKS Consortium
+// (c) 2011 Sebastian Germesin, IKS Consortium
+// (c) 2011 Szaby Grünwald, IKS Consortium
+// VIE may be freely distributed under the MIT license.
+// For all details and documentation:
+// http://viejs.org/
+//
+
+// ## VIE.Types
+// Within VIE, we provide special capabilities of handling types of entites. This helps
+// for example to query easily for certain entities (e.g., you only need to query for *Person*s
+// and not for all subtypes).
+if (VIE.prototype.Type) {
+ throw new Error("ERROR: VIE.Type is already defined. Please check your installation!");
+}
+if (VIE.prototype.Types) {
+ throw new Error("ERROR: VIE.Types is already defined. Please check your installation!");
+}
+
+// ### VIE.Type(id, attrs, metadata)
+// This is the constructor of a VIE.Type.
+// **Parameters**:
+// *{string}* **id** The id of the type.
+// *{string|array|VIE.Attribute}* **attrs** A string, proper ```VIE.Attribute``` or an array of these which
+// *{object}* **metadata** Possible metadata about the type
+// are the possible attributes of the type
+// **Throws**:
+// *{Error}* if one of the given paramenters is missing.
+// **Returns**:
+// *{VIE.Type}* : A **new** VIE.Type object.
+// **Example usage**:
+//
+// var person = new vie.Type("Person", ["name", "knows"]);
+VIE.prototype.Type = function (id, attrs, metadata) {
+ if (id === undefined || typeof id !== 'string') {
+ throw "The type constructor needs an 'id' of type string! E.g., 'Person'";
+ }
+
+// ### id
+// This field stores the id of the type's instance.
+// **Parameters**:
+// nothing
+// **Throws**:
+// nothing
+// **Returns**:
+// *{string}* : The id of the type as a URI.
+// **Example usage**:
+//
+// console.log(person.id);
+// // --> "<http://viejs.org/ns/Person>"
+ this.id = this.vie.namespaces.isUri(id) ? id : this.vie.namespaces.uri(id);
+
+ /* checks whether such a type is already defined. */
+ if (this.vie.types.get(this.id)) {
+ throw new Error("The type " + this.id + " is already defined!");
+ }
+
+// ### supertypes
+// This field stores all parent types of the type's instance. This
+// is set if the current type inherits from another type.
+// **Parameters**:
+// nothing
+// **Throws**:
+// nothing
+// **Returns**:
+// *{VIE.Types}* : The supertypes (parents) of the type.
+// **Example usage**:
+//
+// console.log(person.supertypes);
+ this.supertypes = new this.vie.Types();
+
+// ### subtypes
+// This field stores all children types of the type's instance. This
[... 4595 lines stripped ...]