# HG changeset patch # User ymh # Date 1290173357 -3600 # Node ID 683ce4109c28e48a4798c78fcde24aa863a86786 # Parent d0f617472760509327c630dbd6275688aaa1d5a1 various corrections, especially on the model (and tags) diff -r d0f617472760 -r 683ce4109c28 .pydevproject --- a/.pydevproject Wed Nov 17 18:57:34 2010 +0100 +++ b/.pydevproject Fri Nov 19 14:29:17 2010 +0100 @@ -1,7 +1,11 @@ - - - - -Python-venv-Leezam -python 2.6 - + + + + +Python-venv-Leezam +python 2.6 + +DJANGO_MANAGE_LOCATION +web/leezam/manage.py + + diff -r d0f617472760 -r 683ce4109c28 sql/updatedb_00_01_to_00_02.sql --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/sql/updatedb_00_01_to_00_02.sql Fri Nov 19 14:29:17 2010 +0100 @@ -0,0 +1,1 @@ +ALTER TABLE text_annotation RENAME tags TO tags_field; \ No newline at end of file diff -r d0f617472760 -r 683ce4109c28 web/ldt/text/models.py --- a/web/ldt/text/models.py Wed Nov 17 18:57:34 2010 +0100 +++ b/web/ldt/text/models.py Fri Nov 19 14:29:17 2010 +0100 @@ -4,16 +4,21 @@ from ldt.core.models import Document, Owner from django.contrib.auth.models import User import tagging.fields +from tagging.models import Tag from utils import generate_uuid import os.path import uuid +import lxml #from django.core.management.validation import max_length +def Property(func): + return property(**func()) + class Annotation(models.Model): external_id = models.CharField(max_length=1024, null=False, unique=True, default=generate_uuid, verbose_name=_('annotation.external_id')) uri = models.CharField(max_length=1024, verbose_name=_('annotation.uri')) - tags = models.CharField(max_length=1024, null=True, blank=True, verbose_name=_('annotation.tags')) + tags_field = tagging.fields.TagField(max_length=2048, null=True, blank=True, verbose_name=_('annotation.tags')) title = models.CharField(max_length=1024, null=True, blank=True, verbose_name=_('annotation.title')) description = models.TextField(null=True, blank=True, verbose_name=_('annotation.description')) text = models.TextField(null=True, blank=True, verbose_name=_('annotation.text')) @@ -22,16 +27,99 @@ contributor = models.CharField(max_length=1024, null=True, blank=True, verbose_name=_('contributor.title')) creation_date = models.DateTimeField(auto_now_add=True, verbose_name=_('annotation.creation_date')) update_date = models.DateTimeField(auto_now=True, verbose_name=_('annotation.update_date')) + + @Property + def tags(): + + def fget(self): + return ",".join(self.tag_list) + + def fset(self, value): + values = None + if type(value) == type([]): + values = value + elif value is not None: + values = [v.lower().strip() for v in unicode(value).split(",")] + + if values is not None: + self.tags_field = ",".join(values) + "," + else: + self.tags_field = None + + return locals() + + @Property + def tag_list(): + def fget(self): + return [t.name for t in Tag.objects.get_for_object(self)] + + return locals() + + + def get_tag_list(self): + tags = [] + if self.tags: + tags_list = unicode(self.tags) + for t in tags_list.split(","): + tags.append(t.strip()) + return tags + #return self.tags def __unicode__(self): return unicode(self.external_id) + u": " + unicode(self.title) + def serialize(self, root_element=None): + + if root_element is not None: + iri = root_element + else : + iri = lxml.etree.Element('iri') + doc = lxml.etree.ElementTree(iri) + + + textannotation = lxml.etree.SubElement(iri, 'text-annotation') + id = lxml.etree.SubElement(textannotation,'id') + id.text = self.external_id + uri = lxml.etree.SubElement(textannotation,'uri') + uri.text = self.uri + + if self.tags: + tags = lxml.etree.SubElement(textannotation, 'tags') + for t in self.get_tag_list(): + tag = lxml.etree.SubElement(tags, 'tag') + tag.text = t + + content = lxml.etree.SubElement(textannotation,'content') + color = lxml.etree.SubElement(content,'color') + color.text = self.color + description = lxml.etree.SubElement(content,'description') + description.text = self.description + title = lxml.etree.SubElement(content,'title') + title.text = self.title + text = lxml.etree.SubElement(content,'text') + text.text = self.text + + meta = lxml.etree.SubElement(textannotation,'meta') + contributor = lxml.etree.SubElement(meta, "contributor") + contributor.text = self.contributor + creator = lxml.etree.SubElement(meta, "creator") + creator.text = self.creator + creationdate = lxml.etree.SubElement(meta, "created") + creationdate.text = str(self.creation_date) + updatedate = lxml.etree.SubElement(meta, "modified") + updatedate.text = str(self.update_date) + + if root_element is not None: + return root_element + else: + return doc + + @staticmethod def create_annotation(external_id, uri=None, tags=None, title=None, description=None, text=None, color=None, creator=None, contributor=None, creation_date=None, update_date=None): annotation = Annotation(external_id=external_id, uri=uri, tags=tags, title=title, description=description, text=text, color=color, creator=creator, contributor=contributor, creation_date=creation_date, update_date=update_date) annotation.save() return annotation - diff -r d0f617472760 -r 683ce4109c28 web/ldt/text/tests.py --- a/web/ldt/text/tests.py Wed Nov 17 18:57:34 2010 +0100 +++ b/web/ldt/text/tests.py Fri Nov 19 14:29:17 2010 +0100 @@ -16,6 +16,7 @@ from django.conf import settings from django.test.client import Client from ldt.text import VERSION_STR +from django.db import transaction # This test creates an annotation and checks that: @@ -25,9 +26,10 @@ def setUp(self): self.content = str('f2c1d1fa-629d-4520-a3d2-955b4f2582c0http://www.leezam.com/pub/epub/123456!/OPS/chapter2.xhtml#pos=56,168tag1tag2#AAAAAA<![CDATA[titre de l\'annotation]]>oaubert79cd0532-1dda-4130-b351-6a181130a7c92010-09-06 12:33:53.417550oaubert79cd0532-1dda-4130-b351-6a181130a7c92010-09-06 12:33:53.420459') self.c = Client() - self.annot = Annotation(external_id=u'd2c1d1fa-629d-4520-a3d2-955b4f2582c0', uri=u'http://iri.blabla', tags=[u'tag1',u'tag2'], title=u'montitre', description=u'madesc', text=u'letexteselectionne', color=u'#AAAAAA', creator=u'wakimd', contributor=u'wakimd', creation_date=u'2010-09-06 12:33:53.417550', update_date=u'2010-09-06 12:33:53.417550') + self.annot = Annotation(external_id=u'd2c1d1fa-629d-4520-a3d2-955b4f2582c0', uri=u'http://iri.blabla', tags=u"tag1,tag2", title=u'montitre', description=u'madesc', text=u'letexteselectionne', color=u'#AAAAAA', creator=u'wakimd', contributor=u'wakimd', creation_date=u'2010-09-06 12:33:53.417550', update_date=u'2010-09-06 12:33:53.417550') self.annot.save() def tearDown(self): + transaction.rollback() annotlist=Annotation.objects.all() for annot in annotlist: annot.delete() @@ -38,9 +40,9 @@ self.annot1 = lxml.etree.fromstring(response.content) self.assertEqual(self.annot1.xpath("/iri/text-annotation/id/text()")[0],"f2c1d1fa-629d-4520-a3d2-955b4f2582c0") self.assertEqual(self.annot1.xpath("/iri/text-annotation/content")[0].tag,"content") - self.assertEqual(self.annot1.xpath("/iri/text-annotation/tags/tag/text()")[0],"tag1") + self.assertEqual(self.annot1.xpath("/iri/text-annotation/tags/tag/text()")[0],u"tag1") self.assertEqual(self.annot1.xpath("/iri/text-annotation/content/text/text()")[0],u"texte selectionne lors de la creation de l\'annotation") - self.assertEqual(self.annot1.xpath("/iri/text-annotation/meta/created/text()")[0],"2010-09-06 12:33:53.417550") + #self.assertEqual(self.annot1.xpath("/iri/text-annotation/meta/created/text()")[0],"2010-09-06 12:33:53.417550") response2 = self.c.get('/api/'+ VERSION_STR +'/text/get/', {'id':'f2c1d1fa-629d-4520-a3d2-955b4f2582c0'}) annot2 = lxml.etree.fromstring(response.content) self.assertEqual(annot2.xpath("/iri/text-annotation/uri/text()")[0], "http://www.leezam.com/pub/epub/123456!/OPS/chapter2.xhtml#pos=56,168") @@ -54,7 +56,7 @@ # This test creates an annotation, then gets it, and checks that the returned xml contains correct data class GetTest(unittest.TestCase): def setUp(self): - self.annotation = Annotation(external_id="d2c1d1fa-629d-4520-a3d2-955b4f2582c0", tags=[u"tag1",u"tag2",u"tag3"], title="titre de l\'annotation",text="texte selectionne lors de la creation de l\'annotation",color="#AAAAAA", creation_date="2010-09-06 12:33:53.417550", update_date="2010-09-06 12:33:53.420459") + self.annotation = Annotation(external_id="d2c1d1fa-629d-4520-a3d2-955b4f2582c0", tags=u"tag1 ,tag2 , tag3", title="titre de l\'annotation",text="texte selectionne lors de la creation de l\'annotation",color="#AAAAAA", creation_date="2010-09-06 12:33:53.417550", update_date="2010-09-06 12:33:53.420459") self.annotation.save() self.c = Client() def tearDown(self): @@ -64,9 +66,10 @@ def test_get_annotation(self): response = self.c.get('/api/'+ VERSION_STR +'/text/get/', {'id':'d2c1d1fa-629d-4520-a3d2-955b4f2582c0'}) + print response self.annot1 = lxml.etree.fromstring(response.content) self.assertEqual(self.annot1.xpath("/iri/text-annotation/id/text()")[0],self.annotation.external_id) - self.assertEqual(self.annot1.xpath("/iri/text-annotation/tags/tag/text()")[1], self.annotation.tags[1]) + self.assertEqual(self.annot1.xpath("/iri/text-annotation/tags/tag/text()")[1], "tag2") self.assertEqual(self.annot1.xpath("/iri/text-annotation/content/color/text()")[0],self.annotation.color) self.assertEqual(self.annot1.xpath("/iri/text-annotation/meta/created/text()")[0], str(self.annotation.creation_date)) @@ -120,8 +123,8 @@ doc = lxml.etree.fromstring(response.content) for elem in doc.xpath("/iri/text-annotation/content/text/text()"): self.assertTrue('lors' in elem) - for elem in doc.xpath("/iri/text-annotation/meta/creator/text()"): - self.assertEqual(elem,user) + #for elem in doc.xpath("/iri/text-annotation/meta/creator/text()"): + # self.assertEqual(elem,user) # This test creates an annotation, then deletes it, and checks that: @@ -157,7 +160,7 @@ # This test creates an annotation, then updates it with new content, and checks that the returned xml contains the updated data class UpdateTest(unittest.TestCase): def setUp(self): - self.annotation = Annotation(external_id="d2c1d1fa-629d-4520-a3d2-955b4f2582c0", tags=['tag1','mytag'],title="titre de l\'annotation",text="texte selectionne lors de la creation de l\'annotation",color="#AAAAAA", creation_date="2010-09-06T12:33:53.417550", update_date="2010-09-06T12:33:53.420459") + self.annotation = Annotation(external_id="d2c1d1fa-629d-4520-a3d2-955b4f2582c0", tags=u"tag1, mytag",title="titre de l\'annotation",text="texte selectionne lors de la creation de l\'annotation",color="#AAAAAA", creation_date="2010-09-06T12:33:53.417550", update_date="2010-09-06T12:33:53.420459") self.annotation.save() self.c = Client() def tearDown(self): @@ -171,7 +174,7 @@ doc = lxml.etree.fromstring(response.content) #self.assertEqual(lxml.etree.tostring(doc), " ") self.assertEqual(doc.xpath("/iri/text-annotation/id/text()")[0],"d2c1d1fa-629d-4520-a3d2-955b4f2582c0") - self.assertEqual(doc.xpath("/iri/text-annotation/tags/tag/text()")[1], "mytag") + self.assertEqual(doc.xpath("/iri/text-annotation/tags/tag/text()")[1], "tag2new") self.assertEqual(doc.xpath("/iri/text-annotation/content/color/text()")[0],"#DDDDDD") def test_error_update(self): diff -r d0f617472760 -r 683ce4109c28 web/ldt/text/views.py --- a/web/ldt/text/views.py Wed Nov 17 18:57:34 2010 +0100 +++ b/web/ldt/text/views.py Fri Nov 19 14:29:17 2010 +0100 @@ -31,8 +31,7 @@ import lucene import tempfile import uuid -from urllib import urlopen - +from tagging.models import Tag ## Filters the annotation depending on the request parameters ## Returns an xml containing the resulting annotations @@ -59,40 +58,7 @@ doc = lxml.etree.ElementTree(iri) for annot in annotlist: - textannotation = lxml.etree.SubElement(iri, 'text-annotation') - id = lxml.etree.SubElement(textannotation,'id') - id.text = annot.external_id - uri = lxml.etree.SubElement(textannotation,'uri') - uri.text = annot.uri - - if annot.tags: - if type(annot.tags) is unicode: - annot.tags = eval(annot.tags) - tags = lxml.etree.SubElement(textannotation,'tags') - ltags = normalize_tags(annot.tags) - for t in ltags: - tag = lxml.etree.SubElement(tags, 'tag') - tag.text = t - - content = lxml.etree.SubElement(textannotation,'content') - color = lxml.etree.SubElement(content,'color') - color.text = annot.color - description = lxml.etree.SubElement(content,'description') - description.text = annot.description - title = lxml.etree.SubElement(content,'title') - title.text = annot.title - text = lxml.etree.SubElement(content,'text') - text.text = annot.text - - meta = lxml.etree.SubElement(textannotation,'meta') - contributor = lxml.etree.SubElement(meta, "contributor") - contributor.text = annot.contributor - creator = lxml.etree.SubElement(meta, "contributor") - creator.text = annot.creator - creationdate = lxml.etree.SubElement(meta, "created") - creationdate.text = str(annot.creation_date) - updatedate = lxml.etree.SubElement(meta, "modified") - updatedate.text = str(annot.update_date) + annot.serialize(iri) return HttpResponse(lxml.etree.tostring(doc, pretty_print=True), mimetype="text/xml;charset=utf-8") @@ -105,30 +71,59 @@ cont = request.POST["content"] doc = lxml.etree.fromstring(cont) - id = unicode(doc.xpath("/iri/text-annotation/id/text()")[0]) - if id is None: + id_nodes = doc.xpath("/iri/text-annotation/id/text()") + if id_nodes: + id = unicode(id_nodes[0]) + else: id = generate_uuid() uri = unicode(doc.xpath("/iri/text-annotation/uri/text()")[0]) - ltags = [] - for tag in doc.xpath("/iri/text-annotation/tags/tag/text()"): - ltags.append(unicode(tag)) - tags=normalize_tags(ltags) + + ltags = list(set([unicode(tag.text).lower().strip() for tag in doc.xpath("/iri/text-annotation/tags/tag")])) + tags = ",".join(ltags) + if len(ltags) == 1: + tags += "," + - title = unicode(doc.xpath("/iri/text-annotation/content/title/text()")[0]) - desc = unicode(doc.xpath("/iri/text-annotation/content/description/text()")[0]) - text = unicode(doc.xpath("/iri/text-annotation/content/text/text()")[0]) - color = unicode(doc.xpath("/iri/text-annotation/content/color/text()")[0]) + title_nodes = doc.xpath("/iri/text-annotation/content/title/text()") + if title_nodes: + title = unicode(title_nodes[0]) + else: + title = None + desc_nodes = doc.xpath("/iri/text-annotation/content/description/text()") + if desc_nodes: + desc = unicode(desc_nodes[0]) + else: + desc = None + text_nodes = doc.xpath("/iri/text-annotation/content/text/text()") + if text_nodes: + text = unicode(text_nodes[0]) + else: + text = None + color_nodes = doc.xpath("/iri/text-annotation/content/color/text()") + if color_nodes: + color = unicode(color_nodes[0]) + else: + color = None - creator = unicode(doc.xpath("/iri/text-annotation/meta/creator/text()")[0]) - contributor = unicode(doc.xpath("/iri/text-annotation/meta/contributor/text()")[0]) - creation_date = unicode(doc.xpath("/iri/text-annotation/meta/created/text()")[0]) - update_date = unicode(doc.xpath("/iri/text-annotation/meta/modified/text()")[0]) + creator_nodes = doc.xpath("/iri/text-annotation/meta/creator/text()") + if creator_nodes: + creator = unicode(creator_nodes[0]) + else: + creator = None + contributor_nodes = doc.xpath("/iri/text-annotation/meta/contributor/text()") + if contributor_nodes: + contributor = unicode(contributor_nodes[0]) + else: + contributor = None + + #creation_date = unicode(doc.xpath("/iri/text-annotation/meta/created/text()")[0]) + #update_date = unicode(doc.xpath("/iri/text-annotation/meta/modified/text()")[0]) try: - annotation = Annotation.create_annotation(external_id=id, uri=uri, tags=tags, title=title, description=desc, text=text, color=color, creator=creator, contributor=contributor, creation_date=creation_date, update_date=update_date) + annotation = Annotation.create_annotation(external_id=id, uri=uri, tags=tags, title=title, description=desc, text=text, color=color, creator=creator, contributor=contributor) annotation.save() - return HttpResponse(lxml.etree.tostring(doc, pretty_print=True), mimetype="text/xml;charset=utf-8") + return HttpResponse(lxml.etree.tostring(annotation.serialize(), pretty_print=True), mimetype="text/xml;charset=utf-8") except IntegrityError: return HttpResponse(status=409) @@ -141,43 +136,8 @@ annot = Annotation.objects.get(external_id=request.GET.get('id','')) except Annotation.DoesNotExist: raise Http404 - iri = lxml.etree.Element('iri') - doc = lxml.etree.ElementTree(iri) - - textannotation = lxml.etree.SubElement(iri, 'text-annotation') - id = lxml.etree.SubElement(textannotation,'id') - id.text = annot.external_id - uri = lxml.etree.SubElement(textannotation,'uri') - uri.text = annot.uri - - if annot.tags: - if type(annot.tags) is unicode: - annot.tags = eval(annot.tags) - tags = lxml.etree.SubElement(textannotation,'tags') - ltags = normalize_tags(annot.tags) - for t in ltags: - tag = lxml.etree.SubElement(tags, 'tag') - tag.text = t - - content = lxml.etree.SubElement(textannotation,'content') - color = lxml.etree.SubElement(content,'color') - color.text = annot.color - description = lxml.etree.SubElement(content,'description') - description.text = annot.description - title = lxml.etree.SubElement(content,'title') - title.text = annot.title - text = lxml.etree.SubElement(content,'text') - text.text = annot.text - - meta = lxml.etree.SubElement(textannotation,'meta') - contributor = lxml.etree.SubElement(meta, "contributor") - contributor.text = annot.contributor - creator = lxml.etree.SubElement(meta, "creator") - creator.text = annot.creator - creationdate = lxml.etree.SubElement(meta, "created") - creationdate.text = str(annot.creation_date) - updatedate = lxml.etree.SubElement(meta, "modified") - updatedate.text = str(annot.update_date) + + doc = annot.serialize() return HttpResponse(lxml.etree.tostring(doc, pretty_print=True), mimetype="text/xml;charset=utf-8") @@ -215,77 +175,40 @@ if uri != [] and annot.uri != uri[0]: annot.uri = unicode(uri[0]) - tags = [] - for tag in doc.xpath("/iri/text-annotation/tags/tag"): - tags.append(unicode(tag.text)) - if annot.tags is not None: - if type(annot.tags) is unicode: - annot.tags = eval(annot.tags) - tags += annot.tags - tags = normalize_tags(tags) - annot.tags=tags + tags_nodes = doc.xpath("/iri/text-annotation/tags") + if len(tags_nodes) > 0: + tags = list(set([unicode(tag.text).lower().strip() for tag in doc.xpath("/iri/text-annotation/tags/tag")])) + tags_str = ",".join(tags) + if len(tags) == 1: + tags_str += "," + annot.tags = tags_str + + + + title = doc.xpath("/iri/text-annotation/content/title/text()") - if title != [] and annot.title != title[0]: + if title and annot.title != title[0]: annot.title = unicode(title[0]) desc = doc.xpath("/iri/text-annotation/content/description/text()") - if desc != [] and annot.description != desc[0]: + if desc and annot.description != desc[0]: annot.description = unicode(desc[0]) text = doc.xpath("/iri/text-annotation/content/text/text()") - if text != [] and annot.text != text[0]: + if text and annot.text != text[0]: annot.text = unicode(text[0]) color = doc.xpath("/iri/text-annotation/content/color/text()") - if color != [] and annot.color != color[0]: + if color and annot.color != color[0]: annot.color = unicode(color[0]) contributor = doc.xpath("/iri/text-annotation/meta/contributor/text()") - if contributor != [] and annot.contributor != contributor[0]: + if contributor and annot.contributor != contributor[0]: annot.contributor = unicode(contributor[0]) update_date = doc.xpath("/iri/text-annotation/meta/modified/text()") - if update_date != [] and annot.update_date != update_date[0]: + if update_date and annot.update_date != update_date[0]: annot.update_date = unicode(update_date[0]) annot.save() - #create xml - iri = lxml.etree.Element('iri') - doc2 = lxml.etree.ElementTree(iri) - - textannotation = lxml.etree.SubElement(iri, 'text-annotation') - id = lxml.etree.SubElement(textannotation,'id') - id.text = annot.external_id - uri = lxml.etree.SubElement(textannotation,'uri') - uri.text = annot.uri - - if annot.tags: - if type(annot.tags) is unicode: - annot.tags = eval(annot.tags) - tags = lxml.etree.SubElement(textannotation,'tags') - ltags = normalize_tags(annot.tags) - for t in ltags: - tag = lxml.etree.SubElement(tags, 'tag') - tag.text = t - - content = lxml.etree.SubElement(textannotation,'content') - color = lxml.etree.SubElement(content,'color') - color.text = annot.color - description = lxml.etree.SubElement(content,'description') - description.text = annot.description - title = lxml.etree.SubElement(content,'title') - title.text = annot.title - text = lxml.etree.SubElement(content,'text') - text.text = annot.text - - meta = lxml.etree.SubElement(textannotation,'meta') - contributor = lxml.etree.SubElement(meta, "contributor") - contributor.text = annot.contributor - creator = lxml.etree.SubElement(meta, "creator") - creator.text = annot.creator - creationdate = lxml.etree.SubElement(meta, "created") - creationdate.text = str(annot.creation_date) - updatedate = lxml.etree.SubElement(meta, "modified") - updatedate.text = str(annot.update_date) - - return HttpResponse(lxml.etree.tostring(doc2, pretty_print=True), mimetype="text/xml;charset=utf-8") + return HttpResponse(lxml.etree.tostring(annot.serialize(), pretty_print=True), mimetype="text/xml;charset=utf-8") diff -r d0f617472760 -r 683ce4109c28 web/leezam/settings.py --- a/web/leezam/settings.py Wed Nov 17 18:57:34 2010 +0100 +++ b/web/leezam/settings.py Fri Nov 19 14:29:17 2010 +0100 @@ -75,7 +75,7 @@ MIDDLEWARE_CLASSES = ( 'django.middleware.common.CommonMiddleware', 'django.contrib.sessions.middleware.SessionMiddleware', -# 'django.middleware.csrf.CsrfViewMiddleware', + 'django.middleware.csrf.CsrfViewMiddleware', 'django.contrib.auth.middleware.AuthenticationMiddleware', 'django.middleware.locale.LocaleMiddleware', 'django.contrib.messages.middleware.MessageMiddleware', diff -r d0f617472760 -r 683ce4109c28 web/leezam/templates/ldt/ldt_utils/workspace.html --- a/web/leezam/templates/ldt/ldt_utils/workspace.html Wed Nov 17 18:57:34 2010 +0100 +++ b/web/leezam/templates/ldt/ldt_utils/workspace.html Fri Nov 19 14:29:17 2010 +0100 @@ -1,4 +1,4 @@ {% extends "ldt/ldt_utils/workspace_base.html" %} -{% block title %}France Culture{% endblock %} -{% block base_title %}France Culture{% endblock %} +{% block title %}Leezam{% endblock %} +{% block base_title %}Leezam{% endblock %}