Project

General

Profile

Download (19.1 KB) Statistics
| Branch: | Tag: | Revision:
1
/**
2
* Copyright (C) 2007 EDIT
3
* European Distributed Institute of Taxonomy
4
* http://www.e-taxonomy.eu
5
*
6
* The contents of this file are subject to the Mozilla Public License Version 1.1
7
* See LICENSE.TXT at the top of this package for the full license terms.
8
*/
9

    
10
package eu.etaxonomy.cdm.persistence.dao.hibernate.term;
11

    
12
import java.util.ArrayList;
13
import java.util.Collection;
14
import java.util.Collections;
15
import java.util.HashSet;
16
import java.util.List;
17
import java.util.Map;
18
import java.util.Set;
19
import java.util.UUID;
20

    
21
import org.hibernate.Criteria;
22
import org.hibernate.Query;
23
import org.hibernate.Session;
24
import org.hibernate.criterion.Restrictions;
25
import org.hibernate.envers.query.AuditEntity;
26
import org.hibernate.envers.query.AuditQuery;
27
import org.springframework.stereotype.Repository;
28

    
29
import eu.etaxonomy.cdm.model.common.CdmClass;
30
import eu.etaxonomy.cdm.model.term.DefinedTermBase;
31
import eu.etaxonomy.cdm.model.term.OrderedTermVocabulary;
32
import eu.etaxonomy.cdm.model.term.TermType;
33
import eu.etaxonomy.cdm.model.term.TermVocabulary;
34
import eu.etaxonomy.cdm.model.view.AuditEvent;
35
import eu.etaxonomy.cdm.persistence.dao.hibernate.common.IdentifiableDaoBase;
36
import eu.etaxonomy.cdm.persistence.dao.term.ITermVocabularyDao;
37
import eu.etaxonomy.cdm.persistence.dto.FeatureDto;
38
import eu.etaxonomy.cdm.persistence.dto.TermCollectionDto;
39
import eu.etaxonomy.cdm.persistence.dto.TermDto;
40
import eu.etaxonomy.cdm.persistence.dto.TermVocabularyDto;
41
import eu.etaxonomy.cdm.persistence.dto.UuidAndTitleCache;
42
import eu.etaxonomy.cdm.persistence.query.OrderHint;
43

    
44
/**
45
 * @author a.mueller
46
 *
47
 */
48
@Repository
49
public class TermVocabularyDaoImpl extends IdentifiableDaoBase<TermVocabulary> implements
50
		ITermVocabularyDao {
51

    
52
	/**
53
	 * @param type
54
	 */
55
	public TermVocabularyDaoImpl() {
56
		super(TermVocabulary.class);
57
		indexedClasses = new Class[2];
58
		indexedClasses[0] = TermVocabulary.class;
59
		indexedClasses[1] = OrderedTermVocabulary.class;
60
	}
61

    
62
	@Override
63
    public long countTerms(TermVocabulary termVocabulary) {
64
		AuditEvent auditEvent = getAuditEventFromContext();
65
		if(auditEvent.equals(AuditEvent.CURRENT_VIEW)) {
66
		    Query query = getSession().createQuery("select count(term) from DefinedTermBase term where term.vocabulary = :vocabulary");
67
		    query.setParameter("vocabulary", termVocabulary);
68

    
69
		    return (Long)query.uniqueResult();
70
		} else {
71
			AuditQuery query = makeAuditQuery(null, auditEvent);
72
			query.addProjection(AuditEntity.id().count());
73
			query.add(AuditEntity.relatedId("vocabulary").eq(termVocabulary.getId()));
74
			return (Long)query.getSingleResult();
75
		}
76
	}
77

    
78
	@Override
79
    public <T extends DefinedTermBase> List<T> getTerms(TermVocabulary<T> vocabulary,Integer pageSize, Integer pageNumber, List<OrderHint> orderHints,List<String> propertyPaths) {
80
		AuditEvent auditEvent = getAuditEventFromContext();
81
		if(auditEvent.equals(AuditEvent.CURRENT_VIEW)) {
82
			Criteria criteria = getCriteria(DefinedTermBase.class);
83
			criteria.createCriteria("vocabulary").add(Restrictions.idEq(vocabulary.getId()));
84

    
85
			addPageSizeAndNumber(criteria, pageSize, pageNumber);
86
		    this.addOrder(criteria, orderHints);
87

    
88
		    @SuppressWarnings("unchecked")
89
            List<T> result = criteria.list();
90
		    defaultBeanInitializer.initializeAll(result, propertyPaths);
91
		    return result;
92
		} else {
93
			AuditQuery query = makeAuditQuery(null, auditEvent);
94
			query.add(AuditEntity.relatedId("vocabulary").eq(vocabulary.getId()));
95

    
96
			addPageSizeAndNumber(query, pageSize, pageNumber);
97

    
98
			@SuppressWarnings("unchecked")
99
            List<T> result = query.getResultList();
100
		    defaultBeanInitializer.initializeAll(result, propertyPaths);
101
			return result;
102
		}
103
	}
104

    
105
    @Override
106
    public <T extends DefinedTermBase> TermVocabulary<T> findByUri(String termSourceUri, Class<T> clazz) {
107
		AuditEvent auditEvent = getAuditEventFromContext();
108
		if(auditEvent.equals(AuditEvent.CURRENT_VIEW)) {
109
		    //TODO use clazz
110
    		Query query = getSession().createQuery("select vocabulary from TermVocabulary vocabulary where vocabulary.termSourceUri= :termSourceUri");
111
	    	query.setParameter("termSourceUri", termSourceUri);
112

    
113
	    	@SuppressWarnings("unchecked")
114
	    	TermVocabulary<T> result = (TermVocabulary<T>)query.uniqueResult();
115
	    	return result;
116
		} else {
117
			@SuppressWarnings("unchecked")
118
            AuditQuery query = makeAuditQuery(clazz, auditEvent);
119
			query.add(AuditEntity.property("termSourceUri").eq(termSourceUri));
120

    
121
			@SuppressWarnings("unchecked")
122
            TermVocabulary<T> result = (TermVocabulary<T>)query.getSingleResult();
123
			return result;
124
		}
125
	}
126

    
127

    
128
	@Override
129
    public <T extends DefinedTermBase> List<T> getTerms(TermVocabulary<T> termVocabulary, Integer pageSize,	Integer pageNumber) {
130
		return getTerms(termVocabulary, pageSize, pageNumber, null, null);
131
	}
132

    
133

    
134
    @Override
135
    public <T extends DefinedTermBase> List<TermVocabulary<T>> findByTermType(TermType termType, List<String> propertyPaths) {
136

    
137
        Criteria criteria = getSession().createCriteria(type);
138
        criteria.add(Restrictions.eq("termType", termType));
139
        criteria.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY);
140
        //this.addOrder(criteria, orderHints);
141

    
142
        @SuppressWarnings("unchecked")
143
        List<TermVocabulary<T>> result = criteria.list();
144
        defaultBeanInitializer.initializeAll(result, propertyPaths);
145
        return result;
146
    }
147

    
148
	@Override
149
    public List<TermVocabulary> listByTermType(TermType termType, boolean includeSubTypes, Integer limit, Integer start,List<OrderHint> orderHints, List<String> propertyPaths) {
150
        checkNotInPriorView("TermVocabularyDao.listByTermType(TermType termType, Integer limit, Integer start, List<OrderHint> orderHints, List<String> propertyPaths)");
151

    
152
        Set<TermType> allTermTypes = new HashSet<TermType>();
153
        allTermTypes.add(termType);
154
        if (includeSubTypes){
155
            allTermTypes.addAll(termType.getGeneralizationOf(true));
156
        }
157

    
158
        Criteria criteria = getSession().createCriteria(type);
159
        criteria.add(Restrictions.in("termType", allTermTypes));
160

    
161
        if(limit != null) {
162
            criteria.setMaxResults(limit);
163
            if(start != null) {
164
                criteria.setFirstResult(start);
165
            }
166
        }
167

    
168
        this.addOrder(criteria, orderHints);
169

    
170
        @SuppressWarnings("unchecked")
171
        List<TermVocabulary> result = criteria.list();
172
        defaultBeanInitializer.initializeAll(result, propertyPaths);
173
        return result;
174
    }
175

    
176
	@Override
177
	public void missingTermUuids(
178
			Map<UUID, Set<UUID>> uuidsRequested,
179
			Map<UUID, Set<UUID>> uuidMissingTermsRepsonse,
180
			Map<UUID, TermVocabulary<?>> vocabularyResponse){
181

    
182
		Set<UUID> missingTermCandidateUuids = new HashSet<>();
183

    
184
		for (Set<UUID> uuidsPerVocSet : uuidsRequested.values()){
185
			missingTermCandidateUuids.addAll(uuidsPerVocSet);
186
		}
187

    
188
 		//search persisted subset of required (usually all)
189
		String hql = " SELECT terms.uuid " +
190
				" FROM TermVocabulary voc join voc.terms terms  " +
191
				" WHERE terms.uuid IN (:uuids) " +
192
				" ORDER BY voc.uuid ";
193
		Query query = getSession().createQuery(hql);
194

    
195
		int splitSize = 2000;
196
		List<Collection<UUID>> missingTermCandidates = splitCollection(missingTermCandidateUuids, splitSize);
197
		List<UUID> persistedUuids = new ArrayList<>();
198

    
199
		for (Collection<UUID> uuids : missingTermCandidates){
200
		    query.setParameterList("uuids", uuids);
201
		    @SuppressWarnings("unchecked")
202
            List<UUID> list = query.list();
203
		    persistedUuids.addAll(list);
204
		}
205

    
206

    
207
 		//fully load and initialize vocabularies if required
208
		if (vocabularyResponse != null){
209
			String hql2 = " SELECT DISTINCT voc " +
210
					" FROM TermVocabulary voc " +
211
						" LEFT JOIN FETCH voc.terms terms " +
212
						" LEFT JOIN FETCH terms.representations representations " +
213
						" LEFT JOIN FETCH voc.representations vocReps " +
214
					" WHERE terms.uuid IN (:termUuids) OR  (  voc.uuid IN (:vocUuids)  ) " +  //was: AND voc.terms is empty, but did not load originally empty vocabularies with user defined terms added
215
//					" WHERE  voc.uuid IN (:vocUuids) AND voc.terms is empty  " +
216
					" ORDER BY voc.uuid ";
217
			query = getSession().createQuery(hql2);
218
			query.setParameterList("termUuids", missingTermCandidateUuids);
219
			query.setParameterList("vocUuids", uuidsRequested.keySet());
220

    
221
			for (Collection<UUID> uuids : missingTermCandidates){
222
			    query.setParameterList("termUuids", uuids);
223
			    @SuppressWarnings("unchecked")
224
	            List<TermVocabulary<?>> o = query.list();
225
	            for (TermVocabulary<?> voc : o){
226
	                vocabularyResponse.put(voc.getUuid(), voc);
227
	            }
228
	        }
229
		}
230

    
231
		//compute missing terms
232
		if (missingTermCandidateUuids.size() == persistedUuids.size()){
233
			missingTermCandidateUuids.clear();
234
		}else{
235
			missingTermCandidateUuids.removeAll(persistedUuids);
236
			//add missing terms to response
237
			for (UUID vocUUID : uuidsRequested.keySet()){
238
				for (UUID termUuid : uuidsRequested.get(vocUUID)){
239
					if (missingTermCandidateUuids.contains(termUuid)){
240
						Set<UUID> r = uuidMissingTermsRepsonse.get(vocUUID);
241
						if (r == null){
242
							r = new HashSet<>();
243
							uuidMissingTermsRepsonse.put(vocUUID, r);
244
						}
245
						r.add(termUuid);
246
					}
247
				}
248
			}
249
		}
250

    
251
		return;
252
	}
253

    
254
	@Override
255
	public Collection<TermDto> getTerms(List<UUID> vocabularyUuids) {
256
	    String queryString = TermDto.getTermDtoSelect()
257
	            + "where v.uuid in :vocabularyUuids "
258
	            + "order by a.titleCache";
259
	    Query query =  getSession().createQuery(queryString);
260
	    query.setParameterList("vocabularyUuids", vocabularyUuids);
261

    
262
	    @SuppressWarnings("unchecked")
263
	    List<Object[]> result = query.list();
264

    
265
	    List<TermDto> list = TermDto.termDtoListFrom(result);
266
	    return list;
267
	}
268

    
269
	@Override
270
	public Collection<TermDto> getTerms(UUID vocabularyUuid) {
271
	    String queryString = TermDto.getTermDtoSelect()
272
	            + "where v.uuid = :vocabularyUuid "
273
	            + "order by a.titleCache";
274
	    Query query =  getSession().createQuery(queryString);
275
	    query.setParameter("vocabularyUuid", vocabularyUuid);
276

    
277
	    @SuppressWarnings("unchecked")
278
	    List<Object[]> result = query.list();
279

    
280
	    List<TermDto> list = TermDto.termDtoListFrom(result);
281
	    return list;
282
	}
283

    
284
	@Override
285
    public Collection<TermDto> getNamedAreaTerms(List<UUID> vocabularyUuids) {
286
        String queryString = TermDto.getTermDtoSelectNamedArea()
287
                + "where v.uuid in :vocabularyUuids "
288
                + "order by a.titleCache";
289
        Query query =  getSession().createQuery(queryString);
290
        query.setParameterList("vocabularyUuids", vocabularyUuids);
291

    
292
        @SuppressWarnings("unchecked")
293
        List<Object[]> result = query.list();
294

    
295
        List<TermDto> list = TermDto.termDtoListFrom(result);
296
        return list;
297
    }
298

    
299
    @Override
300
    public Collection<TermDto> getTopLevelTerms(UUID vocabularyUuid) {
301
        String queryString = TermDto.getTermDtoSelect()
302
                + "where v.uuid = :vocabularyUuid "
303
                + "and a.partOf is null "
304
                + "and a.kindOf is null";
305
        Query query =  getSession().createQuery(queryString);
306
        query.setParameter("vocabularyUuid", vocabularyUuid);
307

    
308
        @SuppressWarnings("unchecked")
309
        List<Object[]> result = query.list();
310

    
311
        List<TermDto> list = TermDto.termDtoListFrom(result);
312
        return list;
313
    }
314

    
315
    @Override
316
    public Collection<TermDto> getTopLevelTerms(UUID vocabularyUuid, TermType type) {
317
        String queryString;
318
        if (type.equals(TermType.NamedArea)){
319
            queryString = TermDto.getTermDtoSelectNamedArea();
320
        }else if (type.equals(TermType.Feature) || type.isKindOf(TermType.Feature)){
321
            queryString = FeatureDto.getTermDtoSelect();
322
        }else{
323
            queryString = TermDto.getTermDtoSelect();
324
        }
325
        queryString = queryString
326
                + "where v.uuid = :vocabularyUuid "
327
                + "and a.partOf is null "
328
                + "and a.kindOf is null";
329
        Query query =  getSession().createQuery(queryString);
330
        query.setParameter("vocabularyUuid", vocabularyUuid);
331

    
332
        @SuppressWarnings("unchecked")
333
        List<Object[]> result = query.list();
334
        List<TermDto> list = null;
335
        if (type.equals(TermType.Feature)|| type.isKindOf(TermType.Feature)){
336
            list = FeatureDto.termDtoListFrom(result);
337
        }else{
338
            list = TermDto.termDtoListFrom(result);
339
        }
340
        return list;
341
    }
342

    
343
    @Override
344
    public List<TermVocabularyDto> findVocabularyDtoByTermTypes(Set<TermType> termTypes) {
345
        return findVocabularyDtoByTermTypes(termTypes, true);
346
    }
347

    
348
    @Override
349
    public List<TermVocabularyDto> findVocabularyDtoByTermTypes(Set<TermType> termTypes, boolean includeSubtypes) {
350
        return findVocabularyDtoByTermTypes(termTypes, null, includeSubtypes);
351
    }
352

    
353

    
354
    @Override
355
    public List<TermVocabularyDto> findVocabularyDtoByAvailableFor(Set<CdmClass> availableForSet) {
356

    
357
        String queryVocWithFittingTerms = "SELECT DISTINCT(v.uuid) FROM DefinedTermBase term JOIN term.vocabulary as v WHERE " ;
358
        for (CdmClass availableFor: availableForSet){
359
            queryVocWithFittingTerms += " term.availableFor like '%"+availableFor.getKey()+"%' AND term.termType = :feature";
360

    
361
        }
362

    
363
//        Query query1 =  getSession().createQuery(queryVocWithFittingTerms);
364
//        List<Object[]> result1 = query1.list();
365

    
366
        String queryString = TermCollectionDto.getTermCollectionDtoSelect()
367
                + " WHERE a.uuid in "
368
                + " (" + queryVocWithFittingTerms + ")";
369

    
370

    
371

    
372

    
373
        Query query =  getSession().createQuery(queryString);
374
        query.setParameter("feature", TermType.Feature);
375

    
376
        @SuppressWarnings("unchecked")
377
        List<Object[]> result = query.list();
378

    
379
//        Map<UUID, TermVocabularyDto> dtoMap = new HashMap<>(result.size());
380
        List<TermVocabularyDto>  dtos = TermVocabularyDto.termVocabularyDtoListFrom(result);
381

    
382
        return dtos;
383
    }
384

    
385

    
386
    @Override
387
    public List<TermVocabularyDto> findVocabularyDtoByTermTypes(Set<TermType> termTypes, String pattern, boolean includeSubtypes) {
388
        Set<TermType> termTypeWithSubType = new HashSet<>();
389
        if (! (termTypes.isEmpty() || (termTypes.size() == 1 && termTypes.iterator().next() == null))){
390
            termTypeWithSubType = new HashSet<>(termTypes);
391
        }
392

    
393
        if(includeSubtypes){
394
            if (!termTypes.isEmpty()){
395
                for (TermType termType : termTypes) {
396
                    if (termType != null){
397
                        termTypeWithSubType.addAll(termType.getGeneralizationOf(true));
398
                    }
399
                }
400
            }
401
        }
402
        String queryString = TermVocabularyDto.getTermCollectionDtoSelect();
403

    
404
        if (!termTypeWithSubType.isEmpty()){
405
            queryString += " where a.termType in (:termTypes) ";
406
            if (pattern != null){
407
                queryString += " AND a.titleCache like :pattern";
408
            }
409
        }else{
410
            if (pattern != null){
411
                queryString += " WHERE a.titleCache like :pattern";
412
            }
413
        }
414

    
415
        Query query =  getSession().createQuery(queryString);
416
        if (!termTypeWithSubType.isEmpty()){
417
            query.setParameterList("termTypes", termTypeWithSubType);
418
        }
419
        if (pattern != null){
420
            pattern = pattern.replace("*", "%");
421
            pattern = "%"+pattern+"%";
422
            query.setParameter("pattern", pattern);
423
        }
424
        @SuppressWarnings("unchecked")
425
        List<Object[]> result = query.list();
426
        List<TermVocabularyDto> dtos = TermVocabularyDto.termVocabularyDtoListFrom(result);
427
        return dtos;
428

    
429
//        Map<UUID, TermVocabularyDto> dtoMap = new HashMap<>(result.size());
430
//        for (Object[] elements : result) {
431
//            UUID uuid = (UUID)elements[0];
432
//            TermType termType = (TermType)elements[1];
433
//            if(dtoMap.containsKey(uuid)){
434
//                dtoMap.get(uuid).addRepresentation((Representation)elements[2]);
435
//            } else {
436
//                Set<Representation> representations = new HashSet<>();
437
//                if(elements[2] instanceof Representation) {
438
//                    representations = new HashSet<Representation>();
439
//                    representations.add((Representation)elements[2]);
440
//                } else {
441
//                    representations = (Set<Representation>)elements[2];
442
//                }
443
//                dtoMap.put(uuid, new TermVocabularyDto(uuid, representations, termType, (String)elements[3]));
444
//            }
445
//        }
446
//        return new ArrayList<>(dtoMap.values());
447
    }
448

    
449
    @Override
450
    public List<TermVocabularyDto> findVocabularyDtoByTermType(TermType termType) {
451
        return findVocabularyDtoByTermTypes(Collections.singleton(termType));
452
    }
453

    
454
    @Override
455
    public <S extends TermVocabulary> List<UuidAndTitleCache<S>> getUuidAndTitleCache(Class<S> clazz, TermType termType,
456
            Integer limit, String pattern) {
457
        if(termType==null){
458
            return getUuidAndTitleCache(clazz, limit, pattern);
459
        }
460
        Session session = getSession();
461
        Query query = null;
462
        if (pattern != null){
463
            query = session.createQuery(
464
                      " SELECT uuid, id, titleCache "
465
                    + " FROM " + clazz.getSimpleName()
466
                    + " WHERE titleCache LIKE :pattern "
467
                    + " AND termType = :termType");
468
            pattern = pattern.replace("*", "%");
469
            pattern = pattern.replace("?", "_");
470
            pattern = pattern + "%";
471
            query.setParameter("pattern", pattern);
472
        } else {
473
            query = session.createQuery(
474
                      " SELECT uuid, id, titleCache "
475
                    + " FROM  " + clazz.getSimpleName()
476
                    + " WHERE termType = :termType");
477
        }
478
        query.setParameter("termType", termType);
479
        if (limit != null){
480
           query.setMaxResults(limit);
481
        }
482
        return getUuidAndTitleCache(query);
483
    }
484

    
485
    @Override
486
    public TermVocabularyDto findVocabularyDtoByUuid(UUID vocUuid) {
487
        if (vocUuid == null ){
488
            return null;
489
        }
490

    
491
        String queryString = TermCollectionDto.getTermCollectionDtoSelect()
492
                + " where a.uuid like :uuid ";
493
//                + "order by a.titleCache";
494
        Query query =  getSession().createQuery(queryString);
495
        query.setParameter("uuid", vocUuid);
496

    
497
        @SuppressWarnings("unchecked")
498
        List<Object[]> result = query.list();
499
        if (result.size() == 1){
500
            return TermVocabularyDto.termVocabularyDtoListFrom(result).get(0);
501
        }
502
        return null;
503
    }
504

    
505
    @Override
506
    public List<TermVocabularyDto> findVocabularyDtoByUuids(List<UUID> vocUuids) {
507

    
508
        if (vocUuids == null || vocUuids.isEmpty()){
509
            return null;
510
        }
511
        List<TermVocabularyDto> list = new ArrayList<>();
512

    
513

    
514
        String queryString = TermCollectionDto.getTermCollectionDtoSelect()
515
                + "where a.uuid in :uuidList ";
516
//                + "order by a.titleCache";
517
        Query query =  getSession().createQuery(queryString);
518
        query.setParameterList("uuidList", vocUuids);
519

    
520
        @SuppressWarnings("unchecked")
521
        List<Object[]> result = query.list();
522

    
523
        list = TermVocabularyDto.termVocabularyDtoListFrom(result);
524
        return list;
525

    
526
    }
527

    
528

    
529

    
530
}
(6-6/6)