node-webodf
Version:
WebODF - JavaScript Document Engine http://webodf.org/
169 lines (152 loc) • 6.01 kB
JavaScript
/**
* Copyright (C) 2014 KO GmbH <copyright@kogmbh.com>
*
* @licstart
* This file is part of WebODF.
*
* WebODF is free software: you can redistribute it and/or modify it
* under the terms of the GNU Affero General Public License (GNU AGPL)
* as published by the Free Software Foundation, either version 3 of
* the License, or (at your option) any later version.
*
* WebODF is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with WebODF. If not, see <http://www.gnu.org/licenses/>.
* @licend
*
* @source: http://www.webodf.org/
* @source: https://github.com/kogmbh/WebODF/
*/
/*global gui, runtime, core, ops, odf*/
/**
* @constructor
* @implements {core.Destroyable}
* @param {!ops.Session} session
* @param {!string} inputMemberId
*/
gui.MetadataController = function MetadataController(session, inputMemberId) {
"use strict";
var odtDocument = session.getOdtDocument(),
eventNotifier = new core.EventNotifier([gui.MetadataController.signalMetadataChanged]),
/** @const @type {!Array.<!string>} */
readonlyProperties = [
"dc:creator",
"dc:date",
"meta:editing-cycles",
"meta:editing-duration",
"meta:document-statistic"
];
/**
* @param {!Object} changes
* @return {undefined}
*/
function onMetadataUpdated(changes) {
eventNotifier.emit(gui.MetadataController.signalMetadataChanged, changes);
}
/**
* @param {!string} property
* @return {!boolean}
*/
function isWriteableMetadata(property) {
var isWriteable = (readonlyProperties.indexOf(property) === -1);
if (! isWriteable) {
runtime.log("Setting " + property + " is restricted.");
}
return isWriteable;
}
/**
* Sets the metadata fields from the given properties map.
* Avoid setting certain fields since they are automatically set:
* dc:creator
* dc:date
* meta:editing-cycles
* If you do wish to externally set these fields, try getting
* the master session to inject operations into the timeline
* with the relevant properties.
*
* The following properties are never used and will be removed for semantic
* consistency from the document:
* meta:editing-duration
* meta:document-statistic
*
* Setting any of the above mentioned fields using this method will have no effect.
*
* @param {?Object.<!string, !string>} setProperties A flat object that is a string->string map of field name -> value.
* @param {?Array.<!string>|undefined=} removedProperties An array of metadata field names (prefixed).
* @return {undefined}
*/
this.setMetadata = function (setProperties, removedProperties) {
var /** @type {!Object.<!string,!string>} */
filteredSetProperties = {},
/** @type {!string} */
filteredRemovedProperties = "",
op;
if (setProperties) {
Object.keys(setProperties).filter(isWriteableMetadata).forEach(function (property) {
filteredSetProperties[property] = setProperties[property];
});
}
if (removedProperties) {
filteredRemovedProperties = removedProperties.filter(isWriteableMetadata).join(",");
}
if (filteredRemovedProperties.length > 0
|| Object.keys(filteredSetProperties).length > 0) {
op = new ops.OpUpdateMetadata();
op.init({
memberid: inputMemberId,
setProperties: filteredSetProperties,
removedProperties: filteredRemovedProperties.length > 0 ? { attributes: filteredRemovedProperties } : null
});
session.enqueue([op]);
}
};
/**
* Returns the value of the requested document metadata field
* @param {!string} property A namespace-prefixed field name, for example
* dc:creator
* @return {?string}
*/
this.getMetadata = function (property) {
var namespaceUri, parts;
runtime.assert(typeof property === "string", "Property must be a string");
parts = property.split(':');
runtime.assert(parts.length === 2, "Property must be a namespace-prefixed string");
namespaceUri = odf.Namespaces.lookupNamespaceURI(parts[0]);
// TODO: support other namespaces
runtime.assert(Boolean(namespaceUri), "Prefix must be for an ODF namespace.");
return odtDocument.getOdfCanvas().odfContainer().getMetadata(/**@type{!string}*/(namespaceUri), parts[1]);
};
/**
* @param {!string} eventid
* @param {!Function} cb
* @return {undefined}
*/
this.subscribe = function (eventid, cb) {
eventNotifier.subscribe(eventid, cb);
};
/**
* @param {!string} eventid
* @param {!Function} cb
* @return {undefined}
*/
this.unsubscribe = function (eventid, cb) {
eventNotifier.unsubscribe(eventid, cb);
};
/**
* @param {!function(!Error=):undefined} callback, passing an error object in case of error
* @return {undefined}
*/
this.destroy = function(callback) {
odtDocument.unsubscribe(ops.OdtDocument.signalMetadataUpdated, onMetadataUpdated);
callback();
};
function init() {
odtDocument.subscribe(ops.OdtDocument.signalMetadataUpdated, onMetadataUpdated);
}
init();
};
/**@const*/gui.MetadataController.signalMetadataChanged = "metadata/changed";