Skip to content

Method: checkName(Collection)

1: package de.fhdw.wtf.generator.database.generation;
2:
3: import java.util.ArrayList;
4: import java.util.Collection;
5: import java.util.Iterator;
6: import java.util.List;
7:
8: import de.fhdw.wtf.generator.database.exception.GenerationException;
9: import de.fhdw.wtf.generator.database.exception.NotSameAttributeException;
10: import de.fhdw.wtf.persistence.exception.NoSubtypeException;
11: import de.fhdw.wtf.persistence.exception.NotAbstractException;
12: import de.fhdw.wtf.persistence.exception.PersistenceException;
13: import de.fhdw.wtf.persistence.facade.ClassFacade;
14: import de.fhdw.wtf.persistence.facade.ObjectFacade;
15: import de.fhdw.wtf.persistence.meta.Type;
16: import de.fhdw.wtf.persistence.meta.UnidirectionalAssociation;
17: import de.fhdw.wtf.persistence.meta.UserType;
18:
19: public class RefactoringsGenerator {
20:         
21:         private final ClassFacade classFacade;
22:         private final ObjectFacade objectFacade;
23:         
24:         public RefactoringsGenerator(final ClassFacade classFacade, final ObjectFacade objectFacade) {
25:                 this.classFacade = classFacade;
26:                 this.objectFacade = objectFacade;
27:                 
28:         }
29:         
30:         /**
31:          * Moves the given association to all subtypes of its current owner.
32:          *
33:          * @param association
34:          * the association that should be moved.
35:          * @param subtypes
36:          * the sub types
37:          * @throws PersistenceException
38:          * A persistence Exception is thrown if any Error contacting the database occurs.
39:          * @throws NoSubtypeException
40:          * Without subtypes push down is not possible.
41:          * @throws NotSameAttributeException
42:          * if given types are no subtyps of owner
43:          * @throws NotAbstractException
44:          * thrown when the owner of asso is abstract
45:          */
46:         public void pushDown(final UnidirectionalAssociation association, final Collection<UserType> subtypes)
47:                         throws PersistenceException, NoSubtypeException, NotAbstractException, NotSameAttributeException {
48:                 this.checkAreSubTypesOf(subtypes, association.getOwner());
49:                 if (!association.getOwner().isAbs()) {
50:                         throw new NotAbstractException();
51:                 }
52:                 final Collection<Long> newAssociations = this.createUnidirectionalAssociationsForAllSubtypes(subtypes, association);
53:                 this.classFacade.updateLinksToNewAssociation(association.getId(), newAssociations);
54:                 this.classFacade.deleteAssociation(association.getId());
55:         }
56:         
57:         /**
58:          * checks if superType is a super type of the collection subtypes. When not a Exception is thrown.
59:          *
60:          * @param subtypes
61:          * the collection of subtypes
62:          * @param superType
63:          * the super type
64:          * @throws NotSameAttributeException
65:          * thrown when a subtype is not a subtype of superType
66:          * @throws PersistenceException
67:          * A persistence Exception is thrown if any Error contacting the database occurs.
68:          */
69:         private void checkAreSubTypesOf(final Collection<UserType> subtypes, final UserType superType)
70:                         throws NotSameAttributeException, PersistenceException {
71:                 final Iterator<UserType> i = subtypes.iterator();
72:                 while (i.hasNext()) {
73:                         final UserType current = i.next();
74:                         this.checkIsSuperTypeOf(current, superType);
75:                 }
76:                 
77:         }
78:         
79:         /**
80:          * creates unidirectional associations for all subtypes.
81:          *
82:          * @param subtypes
83:          * the collection of subtypes.
84:          * @param template
85:          * a unidirectional Association used as a template for the new associations
86:          * @return a collection of the ids of the created associations
87:          * @throws PersistenceException
88:          * A persistence Exception is thrown if any Error contacting the database occurs.
89:          */
90:         private Collection<Long> createUnidirectionalAssociationsForAllSubtypes(final Collection<UserType> subtypes,
91:                         final UnidirectionalAssociation template) throws PersistenceException {
92:                 if (subtypes.isEmpty()) {
93:                         throw new NoSubtypeException();
94:                 }
95:                 final Collection<Long> result = new ArrayList<>();
96:                 final Iterator<UserType> i = subtypes.iterator();
97:                 while (i.hasNext()) {
98:                         final UserType current = i.next();
99:                         final UnidirectionalAssociation create =
100:                                         this.classFacade.createUnidirectionalAssociation(
101:                                                         template.getName(),
102:                                                         template.isEssential(),
103:                                                         template.isUnique(),
104:                                                         current,
105:                                                         template.getTarget());
106:                         result.add(create.getId());
107:                 }
108:                 return result;
109:         }
110:         
111:         /**
112:          * Replaces current association target with a more general target type.
113:          *
114:          * @param asso
115:          * the association to expand.
116:          * @param newType
117:          * the type to expand the association.
118:          * @throws PersistenceException
119:          * A persistence Exception is thrown if any Error contacting the database occurs.
120:          * @throws NotSameAttributeException
121:          * throws when newType is not a super type of the old target.
122:          */
123:         public void expandUnidirectionalAssociationTarget(final UnidirectionalAssociation asso, final UserType newType)
124:                         throws PersistenceException, NotSameAttributeException {
125:                 this.checkIsSuperTypeOf(asso.getTarget(), newType);
126:                 final UnidirectionalAssociation newAsso =
127:                                 this.classFacade.createUnidirectionalAssociation(
128:                                                 asso.getName(),
129:                                                 asso.isEssential(),
130:                                                 asso.isUnique(),
131:                                                 asso.getOwner(),
132:                                                 newType);
133:                 final Collection<Long> newAssociations = new ArrayList<>();
134:                 newAssociations.add(newAsso.getId());
135:                 this.classFacade.updateLinksToNewAssociation(asso.getId(), newAssociations);
136:                 this.classFacade.deleteAssociation(asso.getId());
137:         }
138:         
139:         /**
140:          * Moves the given associations to the supertype of its current owner. All Associations must have different owners.
141:          * All Associations must have same essential, unique flag, target and name. All owners must be subtypes of
142:          * 'supertype'.
143:          *
144:          * @param asso
145:          * the association that should be moved
146:          * @param supertype
147:          * the super type
148:          * @throws PersistenceException
149:          * A persistence Exception is thrown if any Error contacting the database occurs.
150:          * @throws GenerationException
151:          * if a prerequisite is violated
152:          * @throws NoSubtypeException
153:          * Without subtypes push down is not possible.
154:          * @throws NotSameAttributeException
155:          * thrown when the owner of the assocation is not a subtype of supertype
156:          */
157:         public void pullUp(final Collection<UnidirectionalAssociation> asso, final UserType supertype)
158:                         throws PersistenceException, NotSameAttributeException, GenerationException {
159:                 if (asso.isEmpty()) {
160:                         throw new GenerationException("You must specify associations!") {
161:                                 private static final long serialVersionUID = 1L;
162:                         };
163:                 }
164:                 this.checkIsSuperTypeOfOwners(asso, supertype);
165:                 final boolean essential = this.checkEssential(asso);
166:                 final boolean unique = this.checkUnique(asso);
167:                 final Type target = this.checkSameTarget(asso);
168:                 final String name = this.checkName(asso);
169:                 
170:                 final UnidirectionalAssociation newAsso =
171:                                 this.classFacade.createUnidirectionalAssociation(name, essential, unique, supertype, target);
172:                 final Collection<Long> newAssociation = new ArrayList<>();
173:                 newAssociation.add(newAsso.getId());
174:                 final Iterator<UnidirectionalAssociation> i = asso.iterator();
175:                 while (i.hasNext()) {
176:                         final UnidirectionalAssociation current = i.next();
177:                         this.classFacade.updateLinksToNewAssociation(current.getId(), newAssociation);
178:                         this.classFacade.deleteAssociation(current.getId());
179:                 }
180:         }
181:         
182:         /**
183:          * check if all the associations of the collection asso are sub types of super type. Throws Exception when not.
184:          *
185:          * @param asso
186:          * collection of the association which should checked.
187:          * @param supertype
188:          * the super type to check
189:          * @throws NotSameAttributeException
190:          * throws when min. 1 association is not a subtype of supertype
191:          * @throws PersistenceException
192:          * A persistence Exception is thrown if any Error contacting the database occurs.
193:          */
194:         private void checkIsSuperTypeOfOwners(final Collection<UnidirectionalAssociation> asso, final UserType supertype)
195:                         throws NotSameAttributeException, PersistenceException {
196:                 final Iterator<UnidirectionalAssociation> i = asso.iterator();
197:                 while (i.hasNext()) {
198:                         final UnidirectionalAssociation current = i.next();
199:                         this.checkIsSuperTypeOf(current.getOwner(), supertype);
200:                 }
201:         }
202:         
203:         /**
204:          * Check if subtype is a sub type of supertype. Throws NotSameAttributeException when not.
205:          *
206:          * @param subtype
207:          * the sub type to check.
208:          * @param superType
209:          * the super type to check.
210:          * @throws NotSameAttributeException
211:          * thrown when subtype is not a sub type of super type
212:          * @throws PersistenceException
213:          * A persistence Exception is thrown if any Error contacting the database occurs.
214:          */
215:         private void checkIsSuperTypeOf(final Type subtype, final UserType superType) throws NotSameAttributeException,
216:                         PersistenceException {
217:                 if (!this.classFacade.isSuperClassTo(superType, subtype)) {
218:                         throw new NotSameAttributeException("supertype");
219:                 }
220:         }
221:         
222:         /**
223:          * checks if all the associations of the collection asso have the same target. Throws NotSameAttributeException when
224:          * not.
225:          *
226:          * @param asso
227:          * the collection of the associations to check.
228:          * @return the target of all associations
229:          * @throws NotSameAttributeException
230:          * thrown when min. 1 association has a other target.
231:          */
232:         private Type checkSameTarget(final Collection<UnidirectionalAssociation> asso) throws NotSameAttributeException {
233:                 final Iterator<UnidirectionalAssociation> i = asso.iterator();
234:                 final Type result = i.next().getTarget();
235:                 while (i.hasNext()) {
236:                         final UnidirectionalAssociation current = i.next();
237:                         if (!current.getTarget().equals(result)) {
238:                                 throw new NotSameAttributeException("target");
239:                         }
240:                 }
241:                 return result;
242:         }
243:         
244:         /**
245:          * checks if all the associations of the collection asso have the same owner. Throws NotSameAttributeException when
246:          * not.
247:          *
248:          * @param asso
249:          * the collection of the associations to check.
250:          * @return the owner of all associations
251:          * @throws NotSameAttributeException
252:          * thrown when min. 1 association has a other owner.
253:          */
254:         private UserType checkSameOwner(final Collection<UnidirectionalAssociation> asso) throws NotSameAttributeException {
255:                 final Iterator<UnidirectionalAssociation> i = asso.iterator();
256:                 final UserType result = i.next().getOwner();
257:                 while (i.hasNext()) {
258:                         final UnidirectionalAssociation current = i.next();
259:                         if (!current.getOwner().equals(result)) {
260:                                 throw new NotSameAttributeException("owner");
261:                         }
262:                 }
263:                 return result;
264:         }
265:         
266:         /**
267:          * checks if all the associations of the collection asso have unique flag. Throws NotSameAttributeException when
268:          * not.
269:          *
270:          * @param asso
271:          * the collection of the associations to check.
272:          * @return the Unique-Flag of all associations
273:          * @throws NotSameAttributeException
274:          * thrown when min. 1 association has a other unique flag.
275:          */
276:         private boolean checkUnique(final Collection<UnidirectionalAssociation> asso) throws NotSameAttributeException {
277:                 final Iterator<UnidirectionalAssociation> i = asso.iterator();
278:                 final boolean result = i.next().isUnique();
279:                 while (i.hasNext()) {
280:                         final UnidirectionalAssociation current = i.next();
281:                         if (!current.isUnique() == result) {
282:                                 throw new NotSameAttributeException("unique");
283:                         }
284:                 }
285:                 return result;
286:         }
287:         
288:         /**
289:          * checks if all the associations of the collection asso have essential flag. Throws NotSameAttributeException when
290:          * not.
291:          *
292:          * @param asso
293:          * the collection of the associations to check.
294:          * @return the Essential-Flag of all associations
295:          * @throws NotSameAttributeException
296:          * thrown when min. 1 association has a other essential flag.
297:          */
298:         private Boolean checkEssential(final Collection<UnidirectionalAssociation> asso) throws NotSameAttributeException {
299:                 final Iterator<UnidirectionalAssociation> i = asso.iterator();
300:                 final boolean result = i.next().isEssential();
301:                 while (i.hasNext()) {
302:                         final UnidirectionalAssociation current = i.next();
303:                         if (!current.isEssential() == result) {
304:                                 throw new NotSameAttributeException("essential");
305:                         }
306:                 }
307:                 return result;
308:         }
309:         
310:         /**
311:          * checks if all the associations of the collection asso the same name. Throws NotSameAttributeException when not.
312:          *
313:          * @param asso
314:          * the collection of the associations to check.
315:          * @return the name of all associations
316:          * @throws NotSameAttributeException
317:          * thrown when min. 1 association has a other name.
318:          */
319:         private String checkName(final Collection<UnidirectionalAssociation> asso) throws NotSameAttributeException {
320:                 final Iterator<UnidirectionalAssociation> i = asso.iterator();
321:                 final String result = i.next().getName();
322:•                while (i.hasNext()) {
323:                         final UnidirectionalAssociation current = i.next();
324:•                        if (!current.getName().equals(result)) {
325:                                 throw new NotSameAttributeException("Name");
326:                         }
327:                 }
328:                 return result;
329:         }
330:         
331:         /**
332:          * Removes this abstract user type while keeping all data.
333:          *
334:          * @param ownedAssociations
335:          * the owned associations
336:          * @param type
337:          * to be removed
338:          * @param subtypes
339:          * a collection of subtypes
340:          * @throws PersistenceException
341:          * A persistence Exception is thrown if any Error contacting the database occurs.
342:          * @throws NotSameAttributeException
343:          * wrong subtypes list
344:          */
345:         public void deleteUserType(final UserType type,
346:                         final Collection<UnidirectionalAssociation> ownedAssociations,
347:                         final Collection<UserType> subtypes) throws PersistenceException, NotSameAttributeException {
348:                 if (!type.isAbs()) {
349:                         throw new NotAbstractException();
350:                 }
351:                 
352:                 final Iterator<UnidirectionalAssociation> i = ownedAssociations.iterator();
353:                 while (i.hasNext()) {
354:                         final UnidirectionalAssociation current = i.next();
355:                         this.pushDown(current, subtypes);
356:                 }
357:                 this.classFacade.deleteUserType(type.getId());
358:         }
359:         
360:         /**
361:          * Inserts a new abstract class between an existing specialisation relation (lowerType, upperType).
362:          *
363:          * @param lowerType
364:          * the type under the specialisation
365:          * @param upperType
366:          * the type over the specialisation
367:          * @param name
368:          * the name of the new user type
369:          * @return the created user type
370:          * @throws PersistenceException
371:          * A persistence Exception is thrown if any Error contacting the database occurs.
372:          * @throws NotSameAttributeException
373:          * thrown when upperType is not a super type of lowerType
374:          * @return
375:          */
376:         public UserType insertUserTypeBetween(final UserType lowerType, final UserType upperType, final String name)
377:                         throws NotSameAttributeException, PersistenceException {
378:                 this.checkIsSuperTypeOf(lowerType, upperType);
379:                 final UserType newType = this.classFacade.createUserType(name, true, false);
380:                 this.classFacade.createSpecializationBetween(newType, lowerType);
381:                 this.classFacade.createSpecializationBetween(upperType, newType);
382:                 this.classFacade.finalizeSpecialization();
383:                 return newType;
384:         }
385:         
386:         /**
387:          * Creates a new type including all old associations and adds a new association from the old owner to the new type.
388:          *
389:          * @param assoOld
390:          * associations to be moved - same owner!
391:          * @param typeName
392:          * name for new type
393:          * @throws NotSameAttributeException
394:          * thrown then not all associations have the same owner
395:          * @throws PersistenceException
396:          * A persistence Exception is thrown if any Error contacting the database occurs.
397:          */
398:         public void extractClassFromUnidirectionalAssociations(final List<UnidirectionalAssociation> assoOld,
399:                         final String typeName) throws NotSameAttributeException, PersistenceException {
400:                 final UserType from = this.checkSameOwner(assoOld);
401:                 final UserType newType = this.classFacade.createUserType(typeName, false, false);
402:                 final UnidirectionalAssociation newAsso =
403:                                 this.classFacade.createUnidirectionalAssociation("my" + typeName, true, true, from, newType);
404:                 final List<UnidirectionalAssociation> newAssos =
405:                                 this.createUnidirectionalAssociationCopiesWithNewOwner(assoOld, newType);
406:                 
407:                 this.classFacade.moveLinksAndCreateObjects(this.getIds(assoOld), newAsso, newType, this.getIds(newAssos));
408:                 
409:                 this.deleteUnidirectionalAssociations(assoOld);
410:         }
411:         
412:         /**
413:          * get a list of all associations of the collection assoOld.
414:          *
415:          * @param assoOld
416:          * the collection of associations.
417:          * @return a list of all given associations.
418:          */
419:         private List<Long> getIds(final List<UnidirectionalAssociation> assoOld) {
420:                 final List<Long> result = new ArrayList<>();
421:                 final Iterator<UnidirectionalAssociation> i = assoOld.iterator();
422:                 while (i.hasNext()) {
423:                         final UnidirectionalAssociation current = i.next();
424:                         result.add(current.getId());
425:                 }
426:                 return result;
427:         }
428:         
429:         /**
430:          * delete all associations of the collection assoOld.
431:          *
432:          * @param assoOld
433:          * the collection of associations should be deleted.
434:          * @throws PersistenceException
435:          * A persistence Exception is thrown if any Error contacting the database occurs.
436:          */
437:         private void deleteUnidirectionalAssociations(final Collection<UnidirectionalAssociation> assoOld)
438:                         throws PersistenceException {
439:                 final Iterator<UnidirectionalAssociation> i = assoOld.iterator();
440:                 while (i.hasNext()) {
441:                         final UnidirectionalAssociation current = i.next();
442:                         this.classFacade.deleteAssociation(current.getId());
443:                 }
444:         }
445:         
446:         /**
447:          * creates new associations between the targets of the associations of the collection assoOld and the owner newType.
448:          *
449:          * @param assoOld
450:          * a collection of associations.
451:          * @param newType
452:          * the owner for the new associations.
453:          * @return the list of the created associations.
454:          * @throws PersistenceException
455:          * A persistence Exception is thrown if any Error contacting the database occurs.
456:          */
457:         private List<UnidirectionalAssociation> createUnidirectionalAssociationCopiesWithNewOwner(final Collection<UnidirectionalAssociation> assoOld,
458:                         final UserType newType) throws PersistenceException {
459:                 final List<UnidirectionalAssociation> result = new ArrayList<>();
460:                 final Iterator<UnidirectionalAssociation> i = assoOld.iterator();
461:                 while (i.hasNext()) {
462:                         final UnidirectionalAssociation current = i.next();
463:                         final UnidirectionalAssociation copy =
464:                                         this.classFacade.createUnidirectionalAssociation(
465:                                                         current.getName(),
466:                                                         current.isEssential(),
467:                                                         current.isUnique(),
468:                                                         newType,
469:                                                         current.getTarget());
470:                         result.add(copy);
471:                 }
472:                 return result;
473:         }
474:         
475:         public ClassFacade getClassFacade() {
476:                 return this.classFacade;
477:         }
478:         
479:         public ObjectFacade getObjectFacade() {
480:                 return this.objectFacade;
481:         }
482:         
483: }