source: AnnotationManagerN4J/src/main/java/de/mpiwg/itgroup/annotations/restlet/AnnotatorAnnotations.java @ 61:b8ef15c8c4a5

Last change on this file since 61:b8ef15c8c4a5 was 61:b8ef15c8c4a5, checked in by casties, 11 years ago

implemented new shape format for image annotations.
minor cleanups.

File size: 9.5 KB
Line 
1/**
2 * Implements the "annotations" uri of the Annotator API. see
3 * <https://github.com/okfn/annotator/wiki/Storage>
4 */
5package de.mpiwg.itgroup.annotations.restlet;
6
7import java.io.IOException;
8import java.util.ArrayList;
9import java.util.List;
10
11import org.json.JSONArray;
12import org.json.JSONException;
13import org.json.JSONObject;
14import org.restlet.data.Form;
15import org.restlet.data.Parameter;
16import org.restlet.data.Status;
17import org.restlet.ext.json.JsonRepresentation;
18import org.restlet.representation.Representation;
19import org.restlet.resource.Delete;
20import org.restlet.resource.Get;
21import org.restlet.resource.Post;
22import org.restlet.resource.Put;
23
24import de.mpiwg.itgroup.annotations.Annotation;
25import de.mpiwg.itgroup.annotations.Person;
26import de.mpiwg.itgroup.annotations.neo4j.AnnotationStore;
27import de.mpiwg.itgroup.annotations.restlet.utils.JSONObjectComparator;
28
29/**
30 * Implements the "annotations" uri of the Annotator API. see
31 * <https://github.com/okfn/annotator/wiki/Storage>
32 *
33 * @author dwinter, casties
34 *
35 */
36public class AnnotatorAnnotations extends AnnotatorResourceImpl {
37
38    protected String getAllowedMethodsForHeader() {
39        return "OPTIONS,GET,POST,PUT,DELETE";
40    }
41
42    /**
43     * GET with JSON content-type.
44     *
45     * @param entity
46     * @return
47     */
48    @Get("json")
49    public Representation doGetJSON(Representation entity) {
50        logger.debug("AnnotatorAnnotations doGetJSON!");
51        setCorsHeaders();
52        // id from URI /annotations/{id}
53        String jsonId = (String) getRequest().getAttributes().get("id");
54        String id = decodeJsonId(jsonId);
55        logger.debug("annotation-id=" + id);
56
57        // do authentication
58        Person authUser = Person.createPersonWithId(this.checkAuthToken(entity));
59        logger.debug("request authenticated=" + authUser);
60
61        if (id == null) {
62            return getAllAnnotations(authUser);
63        }
64
65        AnnotationStore store = getAnnotationStore();
66        Annotation annot = store.getAnnotationById(id);
67        if (annot != null) {
68            if (!annot.isActionAllowed("read", authUser, store)) {
69                setStatus(Status.CLIENT_ERROR_FORBIDDEN, "Not Authorized!");
70                return null;
71            }
72            JSONObject result = createAnnotatorJson(annot, (authUser == null));
73            logger.debug("sending:");
74            logger.debug(result);
75            return new JsonRepresentation(result);
76        } else {
77            // not found
78            setStatus(Status.CLIENT_ERROR_NOT_FOUND);
79            return null;
80        }
81    }
82
83    private Representation getAllAnnotations(Person authUser) {
84
85        Form form = getRequest().getResourceRef().getQueryAsForm();
86        String sortBy = null;
87        for (Parameter parameter : form) {
88            if (parameter.getName().equals("sortBy")) {
89                sortBy = parameter.getValue();
90            }
91        }
92
93        AnnotationStore store = getAnnotationStore();
94        ArrayList<JSONObject> results = new ArrayList<JSONObject>();
95
96        List<Annotation> annotations = store.getAnnotations(null, null);
97        for (Annotation annotation : annotations) {
98            // check permission
99            if (!annotation.isActionAllowed("read", authUser, store)) continue;
100
101            JSONObject jo = createAnnotatorJson(annotation, false);
102            results.add(jo);
103        }
104
105        if (sortBy != null) {
106            JSONObjectComparator.sortAnnotations(results, sortBy);
107        }
108
109        JSONArray resultsJa = new JSONArray();
110        for (JSONObject result : results) {
111            resultsJa.put(result);
112        }
113
114        // assemble result object
115        JSONObject result = new JSONObject();
116        try {
117            result.put("rows", resultsJa);
118            result.put("total", resultsJa.length());
119        } catch (JSONException e) {
120            setStatus(Status.SERVER_ERROR_INTERNAL, "JSON Error");
121            return null;
122        }
123        logger.debug("sending:");
124        logger.debug(result);
125        return new JsonRepresentation(result);
126    }
127
128    /**
129     * POST with JSON content-type. Creates a new Annotation.
130     *
131     * @return
132     */
133    @Post("json")
134    public Representation doPostJson(Representation entity) {
135        logger.debug("AnnotatorAnnotations doPostJSON!");
136        // set headers
137        setCorsHeaders();
138
139        // do authentication TODO: who's allowed to create?
140        Person authUser = Person.createPersonWithId(this.checkAuthToken(entity));
141        logger.debug("request authenticated=" + authUser);
142        if (authUser == null) {
143            setStatus(Status.CLIENT_ERROR_FORBIDDEN, "Not Authorized!");
144            return null;
145        }
146
147        Annotation annot = null;
148        try {
149            JsonRepresentation jrep = new JsonRepresentation(entity);
150            JSONObject jo = jrep.getJsonObject();
151            if (jo == null) {
152                setStatus(Status.SERVER_ERROR_INTERNAL);
153                return null;
154            }
155            // make sure id is not set for POST
156            jo.remove("id");
157            // get Annotation object from posted JSON
158            annot = createAnnotation(jo, entity);
159        } catch (IOException e1) {
160            setStatus(Status.SERVER_ERROR_INTERNAL);
161            return null;
162        } catch (JSONException e) {
163            setStatus(Status.CLIENT_ERROR_BAD_REQUEST);
164            return null;
165        }
166        if (annot == null) {
167            setStatus(Status.CLIENT_ERROR_BAD_REQUEST);
168            return null;
169        }
170        Annotation storedAnnot;
171        // store Annotation
172        storedAnnot = getAnnotationStore().storeAnnotation(annot);
173        /*
174         * according to https://github.com/okfn/annotator/wiki/Storage we should
175         * return 303: see other. For now we return the annotation.
176         */
177        JSONObject jo = createAnnotatorJson(storedAnnot, (authUser == null));
178        JsonRepresentation retRep = new JsonRepresentation(jo);
179        return retRep;
180    }
181
182    /**
183     * PUT with JSON content-type. Modifies an Annotation.
184     *
185     * @param entity
186     * @return
187     */
188    @Put("json")
189    public Representation doPutJSON(Representation entity) {
190        logger.debug("AnnotatorAnnotations doPutJSON!");
191        setCorsHeaders();
192        // id from URI /annotations/{id}
193        String jsonId = (String) getRequest().getAttributes().get("id");
194        String id = decodeJsonId(jsonId);
195        logger.debug("annotation-id=" + id);
196
197        // do authentication
198        Person authUser = Person.createPersonWithId(this.checkAuthToken(entity));
199        logger.debug("request authenticated=" + authUser);
200
201        Annotation annot = null;
202        AnnotationStore store = getAnnotationStore();
203        try {
204            JsonRepresentation jrep = new JsonRepresentation(entity);
205            JSONObject jo = jrep.getJsonObject();
206            if (jo == null) {
207                setStatus(Status.CLIENT_ERROR_BAD_REQUEST);
208                return null;
209            }
210            // get stored Annotation
211            Annotation storedAnnot = store.getAnnotationById(id);
212            if (storedAnnot == null) {
213                setStatus(Status.CLIENT_ERROR_NOT_FOUND);
214                return null;
215            }
216            if (!storedAnnot.isActionAllowed("update", authUser, store)) {
217                setStatus(Status.CLIENT_ERROR_FORBIDDEN);
218                return null;
219            }
220            // update from posted JSON
221            annot = updateAnnotation(storedAnnot, jo, entity);
222            // store Annotation
223            storedAnnot = store.storeAnnotation(annot);
224            /*
225             * according to https://github.com/okfn/annotator/wiki/Storage we
226             * should return 303: see other. but the client doesn't like it
227             * setStatus(Status.REDIRECTION_SEE_OTHER); // go to same URL as
228             * this one Reference thisUrl = this.getReference();
229             * this.getResponse().setLocationRef(thisUrl);
230             */
231            // return new annotation
232            jo = createAnnotatorJson(storedAnnot, (authUser == null));
233            JsonRepresentation retRep = new JsonRepresentation(jo);
234            return retRep;
235        } catch (JSONException e) {
236            e.printStackTrace();
237            setStatus(Status.CLIENT_ERROR_BAD_REQUEST);
238        } catch (IOException e) {
239            e.printStackTrace();
240            setStatus(Status.SERVER_ERROR_INTERNAL, "Other Error");
241        }
242        return null;
243    }
244
245    /**
246     * DELETE with JSON content-type. Deletes an Annotation.
247     *
248     * @param entity
249     * @return
250     */
251    @Delete("json")
252    public Representation doDeleteJSON(Representation entity) {
253        logger.debug("AnnotatorAnnotations doDeleteJSON!");
254        setCorsHeaders();
255        // id from URI /annotations/{id}
256        String jsonId = (String) getRequest().getAttributes().get("id");
257        String id = decodeJsonId(jsonId);
258        logger.debug("annotation-id=" + id);
259
260        // do authentication
261        Person authUser = Person.createPersonWithId(this.checkAuthToken(entity));
262        logger.debug("request authenticated=" + authUser);
263        AnnotationStore store = getAnnotationStore();
264        Annotation annot = store.getAnnotationById(id);
265        if (annot != null) {
266            if (!annot.isActionAllowed("delete", authUser, store)) {
267                setStatus(Status.CLIENT_ERROR_FORBIDDEN, "Not Authorized!");
268                return null;
269            }
270        }
271
272        // delete annotation
273        store.deleteAnnotationById(id);
274        setStatus(Status.SUCCESS_NO_CONTENT);
275        return null;
276    }
277
278}
Note: See TracBrowser for help on using the repository browser.