diff --git a/client/src/js/controllers/core.js b/client/src/js/controllers/core.js
index 1388d9e..12799aa 100644
--- a/client/src/js/controllers/core.js
+++ b/client/src/js/controllers/core.js
@@ -848,17 +848,44 @@ angular.module('histograph')
// }
});
- modalInstance.result.then(function(){
+ modalInstance.result.then(function (result) {
if(options && typeof options.discard == "function") {
- options.discard();
+ options.submit(options.annotator, result);
}
}, function(){
if(options && typeof options.discard == "function") {
- options.discard();
+ options.discard(options.annotator);
}
});
- }
+ };
+
+ /*
+ loadAnnotations
+ ---
+
+ Load notes attached to the target id
+ */
+ $scope.loadAnnotations = function(item, next) {
+ next([
+ {
+ "id": "39fc339cf058bd22176771b3e3187329", // unique id (added by backend)
+ "annotator_schema_version": "v1.0", // schema version: default v1.0
+ "created": "2011-05-24T18:52:08.036814", // created datetime in iso8601 format (added by backend)
+ "updated": "2011-05-26T12:17:05.012544", // updated datetime in iso8601 format (added by backend)
+ "text": "A note I wrote", // content of annotation
+ "quote": "the text that was annotated", // the annotated text (added by frontend)
+ "uri": "http://example.com",
+ "ranges": [{
+ end: "/blockquote[1]/p[1]",
+ endOffset: 222,
+ start: "/blockquote[1]/p[1]",
+ startOffset: 208,
+ }
+ ]
+ }
+ ]);
+ };
// $scope.contribute({id: 25723})
// $scope.inspect([26414])//27329]);
/*
@@ -1024,10 +1051,7 @@ angular.module('histograph')
$scope.q = options.query;
}
$scope.ok = function () {
- if(options && typeof options.discard == "function") {
- options.discard();
- }
- $uibModalInstance.close();
+
$log.log('ContributeModalCtrl -> ok()', 'saving...');
var entities = [].concat($scope.persons, $scope.locations, $scope.organizations)
for(var i in entities)
@@ -1037,14 +1061,16 @@ angular.module('histograph')
model: 'resource'
}, {}, function(res) {
$log.log('ContributeModalCtrl -> ok()', 'saved', res)
+ $uibModalInstance.close(res.result.item);
+
})
};
$scope.cancel = function () {
- if(options && typeof options.discard == "function") {
- options.discard();
- }
+ // if(options && typeof options.discard == "function") {
+ // options.discard();
+ // }
$uibModalInstance.dismiss('cancel');
};
diff --git a/client/src/js/directives/annotator.js b/client/src/js/directives/annotator.js
index 4389dad..5d72980 100644
--- a/client/src/js/directives/annotator.js
+++ b/client/src/js/directives/annotator.js
@@ -186,10 +186,12 @@ angular.module('histograph')
Annotator.Plugin.HelloWorld = function (element) {
return {
pluginInit: function () {
- var editor;
+ var editor,
+ annotator = this.annotator,
+ link;
this.annotator.subscribe("annotationCreated", function (annotation) {
- console.log("The annotation: %o has just been created!", annotation)
+ console.log("The annotation: %o has just been created!", annotation, link)
})
.subscribe("annotationUpdated", function (annotation) {
console.log("The annotation: %o has just been updated!", annotation)
@@ -201,12 +203,17 @@ angular.module('histograph')
})
.subscribe("annotationEditorShown", function (editor, annotation) {
editor = editor;
- console.log("The annotation: has just been annotationEditorShown!", arguments);
+ console.log("The annotation: has just been annotationEditorShown!", arguments, annotator);
scope.contribute(scope.item, "entity", {
query: annotation.quote,
- discard: function() {
- editor.hide()
+ annotator: annotator,
+ submit: function(annotator, result) {
+ link = result;
+ annotator.editor.submit();
+ },
+ discard: function(annotator) {
+ annotator.editor.hide();
}
});
scope.$apply();
@@ -220,24 +227,19 @@ angular.module('histograph')
}
var annotator = angular.element(element).annotator().data('annotator');
- annotator.addPlugin('Unsupported');
- annotator.addPlugin('HelloWorld');//' /*, any other options */);
- // element..annotator()bind('mouseup', function(e){
- // var selection;
-
- // if (window.getSelection) {
- // selection = window.getSelection();
- // } else if (document.selection) {
- // selection = document.selection.createRange();
- // }
- // if (selection.toString() !== '') {
- // var s = selection.toString();
- // $log.log('::annotator -> ',selection)
-
- // }
- // });
+ annotator.addPlugin('Unsupported');
+ annotator.addPlugin('HelloWorld');
+
+ // lazyload annotation for this specific goddamn element
+ // setTimeout(function(){
+ // attrs.target && scope.loadAnnotations({
+ // id: attrs.target
+ // }, function (annotations) {debugger
+ // annotator.loadAnnotations(annotations);
+ // });
+ // }, 20)
}
}
});
diff --git a/client/src/js/templates.js b/client/src/js/templates.js
index 29ec7e4..b18b9ae 100644
--- a/client/src/js/templates.js
+++ b/client/src/js/templates.js
@@ -30,7 +30,7 @@ $templateCache.put("templates/partials/neighbors.html","\n
\n {{user.username}} {{user.type}} {{user.last_modification_time*1000|date:\'longDate\'}}\n
\n \n {{relatedItem.props.ecmd|ecmd}} {{$index + 1}} out of {{totalItems}}
\n \n \n \n \n
\n \n \n no date found\n {{relatedItem.props|guessInterval}}\n — persons in the document:\n {{per.props.name||per.name}}\n \n
\n \n \n \n \n \n \n");
$templateCache.put("templates/partials/resource-toolbar.html","");
-$templateCache.put("templates/partials/resource.html","\n \n \n \n \n \n
\n
\n \n \n \n \n
\n \n
\n \n
\n
\n
\n \n
\n \n \n
\n
\n \n
\n
\n
\n \n \n \n
\n
\n
\n \n \n
\n
\n
1\" class=\"btn-group\" dropdown is-open=\"status.isopen\" tooltip=\"view a different version\">\n \n \n
\n
\n
\n
\n
\n \n
\n \n \n
\n
\n
\n \n \n \n \n \n
\n \n
\n\n \n
0\">\n \n \n
\n \n
");
+$templateCache.put("templates/partials/resource.html","\n \n \n \n \n \n
\n
\n \n \n \n \n
\n \n
\n \n
\n
\n
\n \n
\n \n \n
\n
\n \n
\n
\n
\n \n \n \n
\n
\n
\n \n \n
\n
\n
1\" class=\"btn-group\" dropdown is-open=\"status.isopen\" tooltip=\"view a different version\">\n \n \n
\n
\n
\n
\n
\n \n
\n \n \n
\n
\n
\n \n \n \n \n \n
\n \n
\n\n \n
0\">\n \n \n
\n \n
");
$templateCache.put("templates/partials/resources-masonry.html"," \r\n \r\n
\r\n There are no related resources.\r\n
\r\n
\r\n
0 && offset + limit < totalItems\'>\r\n \r\n
\r\n
");
$templateCache.put("templates/partials/resources.html"," \n
\n There are no related resources.\n
\n
\n
\n \n
\n
");
$templateCache.put("templates/partials/user-lite.html","\n");
diff --git a/client/src/templates/partials/resource.html b/client/src/templates/partials/resource.html
index 6126412..8876229 100644
--- a/client/src/templates/partials/resource.html
+++ b/client/src/templates/partials/resource.html
@@ -97,8 +97,10 @@
diff --git a/controllers/entity.js b/controllers/entity.js
index aae20e0..0011905 100644
--- a/controllers/entity.js
+++ b/controllers/entity.js
@@ -114,6 +114,9 @@ module.exports = function(io){
createRelatedResource: function(req, res) {
var form = validator.request(req);
+ // check if it contains a silly annotation....
+ if(!form.isValid)
+ return helpers.formError(form.errors, res);
Entity.createRelatedResource({
id: +form.params.entity_id
diff --git a/parser.js b/parser.js
index 8e852e1..6af7534 100644
--- a/parser.js
+++ b/parser.js
@@ -232,6 +232,9 @@ module.exports = {
return YAML.parse(yaml)
},
+ toYaml: function(item) {
+ return YAML.stringify(item, 2)
+ },
/*
get the chunks from a YAML content for the specific ids only,
then annotate them.
diff --git a/test/controllers.entity.js b/test/controllers.entity.js
index 00bfd63..f8633bc 100644
--- a/test/controllers.entity.js
+++ b/test/controllers.entity.js
@@ -213,7 +213,53 @@ describe('controller:entity related items', function() {
});
})
+ it('should create a manual connection with ANNOTATION!, with frequence = 1 resource B', function(done) {
+ var parser = require('../parser');
+ session
+ .post('/api/entity/' + __entity.id +'/related/resource/'+ __resourceB.id)
+ .send({
+ annotation: parser.toYaml([{
+ text: "A note I wrote", // content of annotation
+ quote: "the text that was annotated", // the annotated text (added by frontend)
+ ranges: [{
+ end: "/blockquote[1]/p[1]",
+ endOffset: 222,
+ start: "/blockquote[1]/p[1]",
+ startOffset: 208,
+ }
+ ]
+ }])
+ })
+ .expect('Content-Type', /json/)
+ .expect(200)
+ .end(function (err, res) {
+ should.exist(res.body.result.item.rel)
+ should.exist(res.body.result.item.related.action.props)
+ should.exist(res.body.result.item.rel.created_by)
+ should.not.exists(err);
+
+ // should remove the action
+ Action.remove(res.body.result.item.related.action, function(){
+ should.not.exist(err)
+ done();
+ });
+ });
+ });
+
+ it('should delete the manual connection', function(done) {
+ session
+ .delete('/api/entity/' + __entity.id +'/related/resource/'+ __resourceB.id)
+ .expect('Content-Type', /json/)
+ .expect(200)
+ .end(function (err, res) {
+ should.equal(res.body.result.item.id, __entity.id)
+ should.equal(res.body.result.item.related.resource.id, __resourceB.id)
+ // console.log('DELETE', res.body)
+ should.not.exists(err);
+ done();
+ });
+ })
});
describe('controller:entity related issues', function() {
diff --git a/test/parser.js b/test/parser.js
index 3b4fdf8..215e634 100644
--- a/test/parser.js
+++ b/test/parser.js
@@ -37,6 +37,24 @@ describe('parser:lucene', function() {
})
});
+describe('parser:annotation', function(){
+ it('should correctly parse a annotatrjs annotation', function (done) {
+ var q = parser.toYaml({
+ text: "A note I wrote", // content of annotation
+ quote: "the text that was annotated", // the annotated text (added by frontend)
+ ranges: [{
+ end: "/blockquote[1]/p[1]",
+ endOffset: 222,
+ start: "/blockquote[1]/p[1]",
+ startOffset: 208,
+ }
+ ]
+ });
+ var _q = parser.yaml(q);
+ should.equal(_q.ranges[0].endOffset, 222);
+ done();
+ })
+})
describe('parser:lucene real use case', function() {
it('understand "jacques delors" (@todo use case)', function (done) {
diff --git a/validator.js b/validator.js
index 3a0727a..1ec9826 100644
--- a/validator.js
+++ b/validator.js
@@ -21,6 +21,16 @@ validator.extend('includedIn', function (str, choices) {
return _.difference(str.split(','), choices).length === 0;
});
+validator.extend('isAnnotatorjs', function (str) {
+ var q = {};
+ try{
+ q = YAML.parse(str);
+ return true;
+ } catch(e) {
+ return false;
+ }
+})
+
/*
Verify that for each field in form, everything looks good.
@params form - req.body and/or req.params
@@ -142,6 +152,14 @@ module.exports = {
],
error: 'id not valid'
},
+ {
+ field: 'annotation',
+ check: 'isAnnotatorjs',
+ args: [
+ 0
+ ],
+ error: 'annotation not valid, should be annotatorjs compatible.'
+ },
{
field: 'center',
check: 'isInt',