source: DASISH/t5.6/backend/annotator-backend/trunk/annotator-backend/src/main/java/eu/dasish/annotation/backend/dao/impl/DBIntegrityServiceImlp.java @ 4207

Last change on this file since 4207 was 4207, checked in by olhsha, 10 years ago

adding trasnactional, refactoring and fixing bugs in updated annotations, removing try-catch from resource methods (The Greek's advice)

File size: 22.2 KB
Line 
1/*
2 * Copyright (C) 2013 DASISH
3 *
4 * This program is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU General Public License
6 * as published by the Free Software Foundation; either version 2
7 * of the License, or (at your option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
17 */
18package eu.dasish.annotation.backend.dao.impl;
19
20import eu.dasish.annotation.backend.Helpers;
21import eu.dasish.annotation.backend.dao.AnnotationDao;
22import eu.dasish.annotation.backend.dao.CachedRepresentationDao;
23import eu.dasish.annotation.backend.dao.DBIntegrityService;
24import eu.dasish.annotation.backend.dao.TargetDao;
25import eu.dasish.annotation.backend.dao.UserDao;
26import eu.dasish.annotation.backend.rest.AnnotationResource;
27import eu.dasish.annotation.schema.Annotation;
28import eu.dasish.annotation.schema.AnnotationBody;
29import eu.dasish.annotation.schema.AnnotationInfo;
30import eu.dasish.annotation.schema.AnnotationInfoList;
31import eu.dasish.annotation.schema.CachedRepresentationFragment;
32import eu.dasish.annotation.schema.CachedRepresentationFragmentList;
33import eu.dasish.annotation.schema.CachedRepresentationInfo;
34import eu.dasish.annotation.schema.TargetInfoList;
35import eu.dasish.annotation.schema.Permission;
36import eu.dasish.annotation.schema.UserWithPermissionList;
37import eu.dasish.annotation.schema.ReferenceList;
38import eu.dasish.annotation.schema.Target;
39import eu.dasish.annotation.schema.TargetInfo;
40import eu.dasish.annotation.schema.User;
41import eu.dasish.annotation.schema.UserWithPermission;
42import java.io.IOException;
43import java.io.InputStream;
44import java.lang.Number;
45import java.sql.SQLException;
46import java.sql.Timestamp;
47import java.util.ArrayList;
48import java.util.HashMap;
49import java.util.List;
50import java.util.Map;
51import java.util.UUID;
52import javax.xml.parsers.ParserConfigurationException;
53import org.springframework.beans.factory.annotation.Autowired;
54import org.slf4j.Logger;
55import org.slf4j.LoggerFactory;
56import org.springframework.transaction.annotation.Transactional;
57
58/**
59 *
60 * @author olhsha
61 */
62public class DBIntegrityServiceImlp implements DBIntegrityService {
63
64    @Autowired
65    UserDao userDao;
66    @Autowired
67    CachedRepresentationDao cachedRepresentationDao;
68    @Autowired
69    TargetDao targetDao;
70    @Autowired
71    AnnotationDao annotationDao;
72    private static final Logger logger = LoggerFactory.getLogger(AnnotationResource.class);
73    //////////////////////////////////
74
75    @Override
76    public void setServiceURI(String serviceURI) {
77        userDao.setServiceURI(serviceURI + "users/");
78        cachedRepresentationDao.setServiceURI(serviceURI + "cached/");
79        targetDao.setServiceURI(serviceURI + "targets/");
80        annotationDao.setServiceURI(serviceURI + "annotations/");
81        //notebookDao.setServiceURI(serviceURI+"notebooks/");
82    }
83
84    ///////////// GETTERS //////////////////////////
85    @Override
86    public Number getAnnotationInternalIdentifier(UUID externalID) {
87        return annotationDao.getInternalID(externalID);
88    }
89
90    @Override
91    public Number getAnnotationInternalIdentifierFromURI(String uri) {
92        return annotationDao.getInternalIDFromURI(uri);
93    }
94
95    @Override
96    public UUID getAnnotationExternalIdentifier(Number annotationID) {
97        return annotationDao.getExternalID(annotationID);
98    }
99
100   
101    @Override
102    public Number getTargetInternalIdentifier(UUID externalID) {
103        return targetDao.getInternalID(externalID);
104    }
105
106    @Override
107    public UUID getTargetExternalIdentifier(Number targetID) {
108        return targetDao.getExternalID(targetID);
109    }
110
111    @Override
112    public String getTargetURI(Number targetID) {
113        return targetDao.getURIFromInternalID(targetID);
114    }
115
116    @Override
117    public String getUserURI(Number userID) {
118        return userDao.getURIFromInternalID(userID);
119    }
120
121    @Override
122    public Number getUserInternalIdentifier(UUID externalID) {
123        return userDao.getInternalID(externalID);
124    }
125
126    @Override
127    public UUID getUserExternalIdentifier(Number userID) {
128        return userDao.getExternalID(userID);
129    }
130
131    @Override
132    public Number getCachedRepresentationInternalIdentifier(UUID externalID) {
133        return cachedRepresentationDao.getInternalID(externalID);
134    }
135
136    @Override
137    public UUID getCachedRepresentationExternalIdentifier(Number cachedID) {
138        return cachedRepresentationDao.getExternalID(cachedID);
139    }
140
141   
142    @Override
143    public Annotation getAnnotation(Number annotationID) {
144        if (annotationID != null) {
145            Map<Annotation, Number> annotationOwner = annotationDao.getAnnotationWithoutTargetsAndPermissions(annotationID);
146
147            Annotation[] annotations = new Annotation[1];
148            annotationOwner.keySet().toArray(annotations);
149            Annotation result = annotations[0];
150            result.setOwnerRef(userDao.getURIFromInternalID(annotationOwner.get(result)));
151
152            List<Number> targetIDs = annotationDao.retrieveTargetIDs(annotationID);
153            TargetInfoList sis = new TargetInfoList();
154            for (Number targetID : targetIDs) {
155                TargetInfo targetInfo = getTargetInfoFromTarget(targetDao.getTarget(targetID));
156                sis.getTargetInfo().add(targetInfo);
157            }
158            result.setTargets(sis);
159
160            result.setPermissions(getPermissionsForAnnotation(annotationID));
161            return result;
162        } else {
163            return null;
164        }
165    }
166
167    ///////////////////////////////////////////////////
168    // TODO UNIT tests
169    @Override
170    public UserWithPermissionList getPermissionsForAnnotation(Number annotationID) {
171        if (annotationID != null) {
172            List<Map<Number, String>> principalsPermissions = annotationDao.getPermissions(annotationID);
173            UserWithPermissionList result = new UserWithPermissionList();
174            List<UserWithPermission> list = result.getUserWithPermission();
175            for (Map<Number, String> principalPermission : principalsPermissions) {
176
177                Number[] principal = new Number[1];
178                principalPermission.keySet().toArray(principal);
179
180                UserWithPermission userWithPermission = new UserWithPermission();
181                userWithPermission.setRef(userDao.getURIFromInternalID(principal[0]));
182                userWithPermission.setPermission(Permission.fromValue(principalPermission.get(principal[0])));
183
184                list.add(userWithPermission);
185            }
186            return result;
187        } else {
188            return null;
189        }
190
191    }
192
193    ////////////////////////////////////////////////////////////////////////
194    @Override
195    public List<Number> getFilteredAnnotationIDs(String link, String text, Number inloggedUserID, String[] accessModes, String namespace, UUID owner, Timestamp after, Timestamp before) {
196
197        if (accessModes == null) {
198            return null;
199        }
200
201        List<Number> annotationIDs = annotationDao.getAnnotationIDsForUserWithPermission(inloggedUserID, accessModes);
202
203        if (link != null) {
204            List<Number> targetIDs = targetDao.getTargetsReferringTo(link);
205            List<Number> annotationIDsForTargets = annotationDao.retrieveAnnotationList(targetIDs);
206            annotationIDs.retainAll(annotationIDsForTargets);
207        }
208
209        return annotationDao.getFilteredAnnotationIDs(annotationIDs, text, namespace, userDao.getInternalID(owner), after, before);
210    }
211
212    @Override
213    public ReferenceList getAnnotationTargets(Number annotationID) {
214        ReferenceList result = new ReferenceList();
215        List<Number> targetIDs = annotationDao.retrieveTargetIDs(annotationID);
216        for (Number targetID : targetIDs) {
217            result.getRef().add(targetDao.getURIFromInternalID(targetID));
218        }
219        return result;
220    }
221
222    @Override
223    public List<String> getTargetsWithNoCachedRepresentation(Number annotationID) {
224        if (annotationID == null) {
225            return null;
226        }
227        List<String> result = new ArrayList<String>();
228        List<Number> targetIDs = annotationDao.retrieveTargetIDs(annotationID);
229        for (Number targetID : targetIDs) {
230            List<Number> versions = targetDao.getCachedRepresentations(targetID);
231            if (versions == null) {
232                result.add(targetDao.getURIFromInternalID(targetID));
233            } else {
234                if (versions.isEmpty()) {
235                    result.add(targetDao.getURIFromInternalID(targetID));
236                }
237
238            }
239        }
240        return result;
241    }
242
243    @Override
244    public List<String> getUsersWithNoInfo(Number annotationID) {
245        if (annotationID == null) {
246            return null;
247        }
248        List<String> result = new ArrayList<String>();
249        List<Map<Number, String>> usersWithPermissions = annotationDao.getPermissions(annotationID);
250        for (Map<Number, String> userWithPermission : usersWithPermissions) {
251            Number[] userID = new Number[1];
252            userWithPermission.keySet().toArray(userID);
253            User user = userDao.getUser(userID[0]);
254
255            if (user.getDisplayName() == null || user.getDisplayName().trim().isEmpty() || user.getEMail() == null || user.getEMail().trim().isEmpty()) {
256                result.add(userDao.getURIFromInternalID(userID[0]));
257
258            }
259        }
260        return result;
261    }
262
263    @Override
264    public AnnotationInfoList getFilteredAnnotationInfos(String word, String text, Number inloggedUserID, String[] accessModes, String namespace, UUID owner, Timestamp after, Timestamp before) {
265        List<Number> annotationIDs = getFilteredAnnotationIDs(word, text, inloggedUserID, accessModes, namespace, owner, after, before);
266        if (annotationIDs != null) {
267            AnnotationInfoList result = new AnnotationInfoList();
268            for (Number annotationID : annotationIDs) {
269                Map<AnnotationInfo, Number> annotationInfoOwnerId = annotationDao.getAnnotationInfoWithoutTargets(annotationID);
270                ReferenceList targets = getAnnotationTargets(annotationID);
271                AnnotationInfo[] annotationInfos = new AnnotationInfo[1];
272                annotationInfoOwnerId.keySet().toArray(annotationInfos);
273                AnnotationInfo annotationInfo = annotationInfos[0];
274                annotationInfo.setTargets(targets);
275                annotationInfo.setOwnerRef(userDao.getURIFromInternalID(annotationInfoOwnerId.get(annotationInfo)));
276                result.getAnnotationInfo().add(annotationInfo);
277            }
278
279            return result;
280        } else {
281            return null;
282        }
283
284    }
285
286    // TODO unit test
287    @Override
288    public Target getTarget(Number internalID) {
289        Target result = targetDao.getTarget(internalID);
290        result.setSiblingTargets(getTargetsForTheSameLinkAs(internalID));
291        Map<Number, String> cachedIDsFragments = targetDao.getCachedRepresentationFragmentPairs(internalID);
292        CachedRepresentationFragmentList cachedRepresentationFragmentList = new CachedRepresentationFragmentList();
293        for (Number key : cachedIDsFragments.keySet()) {
294            CachedRepresentationFragment cachedRepresentationFragment = new CachedRepresentationFragment();
295            cachedRepresentationFragment.setRef(cachedRepresentationDao.getURIFromInternalID(key));
296            cachedRepresentationFragment.setFragmentString(cachedIDsFragments.get(key));
297            cachedRepresentationFragmentList.getCached().add(cachedRepresentationFragment);
298        }
299        result.setCachedRepresentatinons(cachedRepresentationFragmentList);
300        return result;
301    }
302
303    // TODO unit test
304    @Override
305    public CachedRepresentationInfo getCachedRepresentationInfo(Number internalID) {
306        return cachedRepresentationDao.getCachedRepresentationInfo(internalID);
307    }
308
309    //TODO unit test
310    @Override
311    public InputStream getCachedRepresentationBlob(Number cachedID) {
312        return cachedRepresentationDao.getCachedRepresentationBlob(cachedID);
313    }
314
315    @Override
316    public ReferenceList getTargetsForTheSameLinkAs(Number targetID) {
317        List<Number> targetIDs = targetDao.getTargetsForLink(targetDao.getLink(targetID));
318        ReferenceList referenceList = new ReferenceList();
319        for (Number siblingID : targetIDs) {
320            referenceList.getRef().add(targetDao.externalIDtoURI(targetDao.getExternalID(siblingID).toString()));
321        }
322        return referenceList;
323    }
324
325    @Override
326    public User getUser(Number userID) {
327        return userDao.getUser(userID);
328    }
329
330    @Override
331    public User getUserByInfo(String eMail) {
332        return userDao.getUserByInfo(eMail);
333    }
334
335    @Override
336    public String getUserRemoteID(Number internalID) {
337        return userDao.getRemoteID(internalID);
338    }
339
340    @Override
341    public Permission getPermission(Number annotationID, Number userID) {
342        return annotationDao.getPermission(annotationID, userID);
343    }
344
345    @Override
346    public Number getUserInternalIDFromRemoteID(String remoteID) {
347        return userDao.getUserInternalIDFromRemoteID(remoteID);
348    }
349
350    ///// UPDATERS /////////////////
351    @Override
352    public int updateAnnotationPrincipalPermission(Number annotationID, Number userID, Permission permission) {
353        return annotationDao.updateAnnotationPrincipalPermission(annotationID, userID, permission);
354    }
355
356    @Override
357    public int updatePermissions(Number annotationID, UserWithPermissionList permissionList) {
358
359        List<UserWithPermission> usersWithPermissions = permissionList.getUserWithPermission();
360        int result = 0;
361        for (UserWithPermission userWithPermission : usersWithPermissions) {
362            Number userID = userDao.getInternalID(UUID.fromString(userDao.stringURItoExternalID(userWithPermission.getRef())));
363            Permission permission = userWithPermission.getPermission();
364            Permission currentPermission = annotationDao.getPermission(annotationID, userID);
365            if (currentPermission != null) {
366                if (!permission.value().equals(currentPermission.value())) {
367                    result = result + annotationDao.updateAnnotationPrincipalPermission(annotationID, userID, permission);
368                }
369            } else {
370                result = result + annotationDao.addAnnotationPrincipalPermission(annotationID, userID, permission);
371            }
372        }
373
374        return result;
375    }
376
377    // TODO: optimize (not chnaged targets should not be deleted)
378    // TODO: unit test
379    @Override
380    public int updateUsersAnnotation(Number userID, Annotation annotation) {
381        int updatedAnnotations = annotationDao.updateAnnotation(annotation, userID);
382        Number annotationID = annotationDao.getInternalIDFromURI(annotation.getURI());
383        int deletedTargets = annotationDao.deleteAllAnnotationTarget(annotationID);
384        int deletedPrinsipalsPermissions = annotationDao.deleteAnnotationPrincipalPermissions(annotationID);
385        int addedTargets = addTargets(annotation, annotationID);
386        int addedPrincipalsPermissions = addPrincipalsPermissions(annotation, annotationID);
387        return updatedAnnotations;
388    }
389   
390     
391    // TODO: unit test
392    @Override
393    public int updateAnnotationBody(Number internalID, AnnotationBody annotationBody) {
394        String[] body = annotationDao.retrieveBodyComponents(annotationBody);
395        return annotationDao.updateAnnotationBody(internalID, body[0], body[1], annotationBody.getXmlBody()!=null);
396    }
397   
398   
399   
400    /////////////// ADDERS  /////////////////////////////////
401    @Override
402    public Number[] addCachedForTarget(Number targetID, String fragmentDescriptor, CachedRepresentationInfo cachedInfo, InputStream cachedBlob) {
403        Number[] result = new Number[2];
404        result[1] = cachedRepresentationDao.getInternalIDFromURI(cachedInfo.getURI());
405        if (result[1] == null) {
406            result[1] = cachedRepresentationDao.addCachedRepresentation(cachedInfo, cachedBlob);
407        }
408        result[0] = targetDao.addTargetCachedRepresentation(targetID, result[1], fragmentDescriptor);
409        return result;
410
411    }
412
413    // TODo: mapping uri to external ID
414    @Override
415    public Map<String, String> addTargetsForAnnotation(Number annotationID, List<TargetInfo> targets) {
416        Map<String, String> result = new HashMap<String, String>();
417        Number targetIDRunner;
418        for (TargetInfo targetInfo : targets) {
419            targetIDRunner = targetDao.getInternalIDFromURI(targetInfo.getRef());
420            if (targetIDRunner != null) {
421                int affectedRows = annotationDao.addAnnotationTarget(annotationID, targetIDRunner);
422            } else {
423                Target newTarget = createFreshTarget(targetInfo);
424                Number targetID = targetDao.addTarget(newTarget);
425                String targetTemporaryID = targetDao.stringURItoExternalID(targetInfo.getRef());
426                result.put(targetTemporaryID, targetDao.getExternalID(targetID).toString());
427                int affectedRows = annotationDao.addAnnotationTarget(annotationID, targetID);
428            }
429        }
430        return result;
431    }
432
433    @Override
434    public Number addUsersAnnotation(Number userID, Annotation annotation) {
435        Number annotationID = annotationDao.addAnnotation(annotation, userID);
436        int affectedAnnotRows = addTargets(annotation, annotationID);
437        int affectedPermissions = annotationDao.addAnnotationPrincipalPermission(annotationID, userID, Permission.OWNER);
438        return annotationID;
439    }
440
441    @Override
442    public Number updateUser(User user) {
443        return userDao.updateUser(user);
444    }
445
446    @Override
447    public Number addUser(User user, String remoteID) {
448        if (userDao.userExists(user)) {
449            return null;
450        } else {
451            return userDao.addUser(user, remoteID);
452        }
453    }
454
455    @Override
456    public int addAnnotationPrincipalPermission(Number annotationID, Number userID, Permission permission) {
457        return annotationDao.addAnnotationPrincipalPermission(annotationID, userID, permission);
458    }
459
460    ////////////// DELETERS //////////////////
461    @Override
462    public int deleteUser(Number userID) {
463        return userDao.deleteUser(userID);
464    }
465
466    @Override
467    public int[] deleteCachedRepresentationOfTarget(Number versionID, Number cachedID) {
468        int[] result = new int[2];
469        result[0] = targetDao.deleteTargetCachedRepresentation(versionID, cachedID);
470        if (result[0] > 0) {
471            result[1] = cachedRepresentationDao.deleteCachedRepresentation(cachedID);
472        } else {
473            result[1] = 0;
474
475        }
476        return result;
477    }
478
479    @Override
480    public int[] deleteAllCachedRepresentationsOfTarget(Number TargetID) {
481        int[] result = new int[2];
482        result[0] = 0;
483        result[1] = 0;
484        List<Number> cachedIDs = targetDao.getCachedRepresentations(TargetID);
485        for (Number cachedID : cachedIDs) {
486            int[] currentResult = deleteCachedRepresentationOfTarget(TargetID, cachedID);
487            result[0] = result[0] + currentResult[0];
488            result[1] = result[1] + currentResult[1];
489        }
490        return result;
491    }
492
493    @Override
494    public int[] deleteAnnotation(Number annotationID) {
495        int[] result = new int[4];
496        result[1] = annotationDao.deleteAnnotationPrincipalPermissions(annotationID);
497        List<Number> targetIDs = annotationDao.retrieveTargetIDs(annotationID);
498        result[2] = annotationDao.deleteAllAnnotationTarget(annotationID);
499        result[0] = annotationDao.deleteAnnotation(annotationID);
500        result[3] = 0;
501        if (targetIDs != null) {
502            for (Number targetID : targetIDs) {
503                deleteAllCachedRepresentationsOfTarget(targetID);
504                result[3] = result[3] + targetDao.deleteTarget(targetID);
505
506            }
507        }
508        return result;
509    }
510
511    ////////////// HELPERS ////////////////////
512    private Target createFreshTarget(TargetInfo targetInfo) {
513        Target target = new Target();
514        target.setLink(targetInfo.getLink());
515        target.setVersion(targetInfo.getVersion());
516        return target;
517    }
518
519    private int addTargets(Annotation annotation, Number annotationID) {
520        List<TargetInfo> targets = annotation.getTargets().getTargetInfo();
521        Map<String, String> targetIdPairs = addTargetsForAnnotation(annotationID, targets);
522        AnnotationBody annotationBody = annotation.getBody();
523        String bodyText;
524        String newBodyText;
525        String mimeType;
526        if (annotationBody.getXmlBody() != null) {
527            bodyText = Helpers.elementToString(annotation.getBody().getXmlBody().getAny());
528            mimeType = annotationBody.getXmlBody().getMimeType();
529        } else {
530            if (annotation.getBody().getTextBody() != null) {
531                bodyText = annotation.getBody().getTextBody().getValue();
532                mimeType = annotationBody.getTextBody().getMimeType();
533            } else {
534                logger.error("The client has sent ill-formed annotation body.");
535                return -1;
536            }
537        }
538        newBodyText = Helpers.replace(bodyText, targetIdPairs);
539        return annotationDao.updateAnnotationBody(annotationID, newBodyText, mimeType, annotationBody.getXmlBody() != null);
540    }
541
542    private int addPrincipalsPermissions(Annotation annotation, Number annotationID) {
543        List<UserWithPermission> permissions = annotation.getPermissions().getUserWithPermission();
544        int addedPermissions = 0;
545        for (UserWithPermission permission : permissions) {
546            addedPermissions = addedPermissions + annotationDao.addAnnotationPrincipalPermission(annotationID, userDao.getInternalIDFromURI(permission.getRef()), permission.getPermission());
547
548        }
549        return addedPermissions;
550    }
551   
552     private TargetInfo getTargetInfoFromTarget(Target target) {
553        TargetInfo targetInfo = new TargetInfo();
554        targetInfo.setRef(target.getURI());
555        targetInfo.setLink(target.getLink());
556        targetInfo.setVersion(target.getVersion());
557        return targetInfo;
558    }
559}
Note: See TracBrowser for help on using the repository browser.