2f2bea125db775cf09b136489ee7433334141ee3
[redakcja.git] / apps / api / handlers.py
1 from piston.handler import BaseHandler, AnonymousBaseHandler
2 from piston.utils import rc, validate
3
4 import settings
5 import librarian
6 import api.forms as forms
7 from datetime import date
8
9 from django.core.urlresolvers import reverse
10 from wlrepo import MercurialLibrary, CabinetNotFound
11
12 from librarian import dcparser
13
14 #
15 # Document List Handlers
16 #
17 class BasicLibraryHandler(AnonymousBaseHandler):
18     allowed_methods = ('GET',)
19
20     def read(self, request):
21         """Return the list of documents."""
22         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
23         cab = lib.main_cabinet
24
25         document_list = [{
26             'url': reverse('document_view', args=[docid]),
27             'name': docid } for docid in cab.documents() ]
28
29         return {
30             'cabinet': cab.name,
31             'latest_rev': cab.shelf(),
32             'documents' : document_list }
33
34 class LibraryHandler(BaseHandler):
35     allowed_methods = ('GET', 'POST')
36     anonymous = BasicLibraryHandler
37
38     def read(self, request):
39         """Return the list of documents."""
40         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
41         cab = lib.main_cabinet
42
43         document_list = [{
44             'url': reverse('document_view', args=[docid]),
45             'name': docid } for docid in cab.documents() ]
46
47         return {
48             'cabinet': cab.name,
49             'latest_rev': cab.shelf(),
50             'documents' : document_list }
51
52     def create(self, request):
53         """Create a new document."""
54         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
55         cab = lib.main_cabinet
56
57         form = forms.DocumentUploadForm(request.POST, request.FILES)
58         if not form.is_valid():
59             return rc.BAD_REQUEST
60
61         f = request.FILES['ocr']
62         data = f.read().decode('utf-8')
63
64         if form.cleaned_data['generate_dc']:
65             data = librarian.wrap_text(data, unicode(date.today()))
66
67         doc = cab.create(form.cleaned_data['bookname'], initial_data=data)
68         
69         return {
70             'url': reverse('document_view', args=[doc.name]),
71             'name': doc.name,
72             'size': doc.size,
73             'revision': doc.shelf() }
74
75 #
76 # Document Handlers
77 #
78 class BasicDocumentHandler(AnonymousBaseHandler):
79     allowed_methods = ('GET',)
80
81     def read(self, request, docid):
82         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
83
84         opts = forms.DocumentGetForm(request.GET)
85         if not opts.is_valid():
86             return rc.BAD_REQUEST
87
88         document = lib.main_cabinet.retrieve(docid)        
89
90         result = {
91             'name': document.name,
92             'size': document.size,
93             'text_url': reverse('doctext_view', args=[docid]),
94             #'dc_url': reverse('docdc_view', docid=document.name),
95             #'parts_url': reverse('docparts_view', docid=document.name),
96             'latest_rev': document.shelf(),          
97         }
98
99         if request.GET.get('with_part', 'no') == 'yes':
100             result['parts'] = document.parts()
101
102         return result   
103
104 #
105 # Document Meta Data
106 #
107 class DocumentHandler(BaseHandler):
108     allowed_methods = ('GET', 'PUT')
109     anonymous = BasicDocumentHandler
110     
111     def read(self, request, docid):
112         """Read document's meta data"""        
113         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
114
115         opts = forms.DocumentGetForm(request.GET)
116         if not opts.is_valid():
117             return rc.BAD_REQUEST
118               
119         document = lib.cabinet(docid, request.user.username, \
120                 create=opts.cleaned_data['autocabinet'] ).retrieve()
121
122         if not document:
123             return rc.NOT_HERE
124                 
125         shared = lib.main_cabinet.retrieve(docid)
126
127         result = {
128             'name': document.name,
129             'size': document.size,
130             'text_url': reverse('doctext_view', args=[docid]),
131             'dc_url': reverse('docdc_view', args=[docid]),
132             'parts_url': reverse('docparts_view', args=[docid]),
133             'latest_rev': document.shelf(),
134             'latest_shared_rev': shared.shelf(),
135             #'shared': lib.isparentof(document, shared),
136             #'up_to_date': lib.isparentof(shared, document),
137         }
138
139         if request.GET.get('with_part', 'no') == 'yes':
140             result['parts'] = document.parts()
141
142         return result        
143
144 #
145 # Document Text View
146 #
147 class DocumentTextHandler(BaseHandler):
148     allowed_methods = ('GET', 'PUT')
149
150     def read(self, request, docid):
151         """Read document as raw text"""
152         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
153         try:            
154             return lib.document(docid, request.user.username).read()
155         except CabinetNotFound:
156             return rc.NOT_HERE
157
158     def update(self, request, docid):
159         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
160         try:
161             data = request.PUT['contents']
162             lib.document(docid, request.user.username).write(data)
163             return rc.ALL_OK
164         except (CabinetNotFound, KeyError):
165             return rc.NOT_HERE
166
167
168 #
169 # Dublin Core handlers
170 #
171 # @requires librarian
172 #
173 class DocumentDublinCoreHandler(BaseHandler):
174     allowed_methods = ('GET', 'PUT')
175
176     def read(self, request, docid):
177         """Read document as raw text"""
178         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
179         try:
180             doc = lib.document(docid, request.user.username)
181
182             # TODO: RAL:document should support file-like ops
183             bookinfo = dcparser.BookInfo.from_string(doc.read())
184             return bookinfo.serialize()
185         except CabinetNotFound:
186             return rc.NOT_HERE
187
188     def update(self, request, docid):
189         lib = MercurialLibrary(path=settings.REPOSITORY_PATH)
190         try:
191             data = request.PUT['contents']
192             lib.document(docid, request.user.username).write(data)
193             return rc.ALL_OK
194         except (CabinetNotFound, KeyError):
195             return rc.NOT_HERE
196