1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.kuali.rice.krms.impl.repository;
17
18 import org.apache.commons.lang.StringUtils;
19 import org.kuali.rice.core.api.mo.common.Versioned;
20 import org.kuali.rice.krad.data.DataObjectService;
21 import org.kuali.rice.krad.data.jpa.PortableSequenceGenerator;
22 import org.kuali.rice.krad.service.KRADServiceLocator;
23 import org.kuali.rice.krms.api.repository.LogicalOperator;
24 import org.kuali.rice.krms.api.repository.proposition.PropositionDefinition;
25 import org.kuali.rice.krms.api.repository.proposition.PropositionDefinitionContract;
26 import org.kuali.rice.krms.api.repository.proposition.PropositionParameter;
27 import org.kuali.rice.krms.api.repository.proposition.PropositionParameterType;
28 import org.kuali.rice.krms.api.repository.proposition.PropositionType;
29 import org.kuali.rice.krms.impl.ui.CustomOperatorUiTranslator;
30 import org.kuali.rice.krms.impl.ui.TermParameter;
31 import org.kuali.rice.krms.impl.util.KrmsImplConstants;
32 import org.kuali.rice.krms.impl.util.KrmsServiceLocatorInternal;
33
34 import javax.persistence.CascadeType;
35 import javax.persistence.Column;
36 import javax.persistence.Entity;
37 import javax.persistence.GeneratedValue;
38 import javax.persistence.Id;
39 import javax.persistence.JoinColumn;
40 import javax.persistence.JoinTable;
41 import javax.persistence.ManyToMany;
42 import javax.persistence.OneToMany;
43 import javax.persistence.OrderBy;
44 import javax.persistence.Table;
45 import javax.persistence.Transient;
46 import javax.persistence.Version;
47 import java.io.IOException;
48 import java.io.ObjectOutputStream;
49 import java.io.Serializable;
50 import java.util.ArrayList;
51 import java.util.Arrays;
52 import java.util.HashMap;
53 import java.util.List;
54 import java.util.Map;
55 import java.util.UUID;
56
57 @Entity
58 @Table(name = "KRMS_PROP_T")
59 public class PropositionBo implements PropositionDefinitionContract, Versioned, Serializable {
60
61 private static final long serialVersionUID = 1l;
62
63 private static final String PROP_SEQ_NAME = "KRMS_PROP_S";
64 static final RepositoryBoIncrementer propositionIdIncrementer = new RepositoryBoIncrementer(PROP_SEQ_NAME);
65 static final RepositoryBoIncrementer propositionParameterIdIncrementer = new RepositoryBoIncrementer("KRMS_PROP_PARM_S");
66
67 @PortableSequenceGenerator(name = PROP_SEQ_NAME)
68 @GeneratedValue(generator = PROP_SEQ_NAME)
69 @Id
70 @Column(name = "PROP_ID")
71 private String id;
72
73 @Column(name = "DESC_TXT")
74 private String description;
75
76 @Column(name = "RULE_ID")
77 private String ruleId;
78
79 @Column(name = "TYP_ID")
80 private String typeId;
81
82 @Column(name = "DSCRM_TYP_CD")
83 private String propositionTypeCode;
84
85 @OneToMany(orphanRemoval = true, cascade = CascadeType.ALL, mappedBy = "proposition")
86 @OrderBy("sequenceNumber")
87 private List<PropositionParameterBo> parameters = new ArrayList<PropositionParameterBo>();
88
89 @Column(name = "CMPND_OP_CD")
90 private String compoundOpCode;
91
92 @Column(name = "CMPND_SEQ_NO")
93 private Integer compoundSequenceNumber;
94
95 @Column(name = "VER_NBR")
96 @Version
97 private Long versionNumber;
98
99 @ManyToMany(targetEntity = PropositionBo.class, cascade = { CascadeType.REFRESH, CascadeType.REMOVE, CascadeType.PERSIST })
100 @JoinTable(name = "KRMS_CMPND_PROP_PROPS_T", joinColumns = { @JoinColumn(name = "CMPND_PROP_ID", referencedColumnName = "PROP_ID") }, inverseJoinColumns = { @JoinColumn(name = "PROP_ID", referencedColumnName = "PROP_ID") })
101 @OrderBy("compoundSequenceNumber")
102 private List<PropositionBo> compoundComponents;
103
104 @Transient
105 private String parameterDisplayString;
106
107 @Transient
108 private boolean editMode = false;
109
110 @Transient
111 private String categoryId;
112
113 @Transient
114 private String termSpecId;
115
116 @Transient
117 private boolean showCustomValue;
118
119 @Transient
120 private String termParameter;
121
122 @Transient
123 private List<TermParameter> termParameterList = new ArrayList<TermParameter>();
124
125 @Transient
126 private String newTermDescription = "new term " + UUID.randomUUID().toString();
127
128 @Transient
129 private Map<String, String> termParameters = new HashMap<String, String>();
130
131 private void setupParameterDisplayString() {
132 if (PropositionType.SIMPLE.getCode().equalsIgnoreCase(getPropositionTypeCode())) {
133
134
135 List<PropositionParameterBo> parameters = getParameters();
136
137 if (parameters != null && parameters.size() == 3) {
138 StringBuilder sb = new StringBuilder();
139 String valueDisplay = getParamValue(parameters.get(1));
140 sb.append(getParamValue(parameters.get(0))).append(" ").append(getParamValue(parameters.get(2)));
141
142 if (valueDisplay != null) {
143
144 sb.append(" ").append(valueDisplay);
145 }
146
147 setParameterDisplayString(sb.toString());
148 } else {
149
150 }
151 }
152 }
153
154
155
156
157
158
159
160 private String getParamValue(PropositionParameterBo param) {
161 CustomOperatorUiTranslator customOperatorUiTranslator =
162 KrmsServiceLocatorInternal.getCustomOperatorUiTranslator();
163
164 if (PropositionParameterType.TERM.getCode().equalsIgnoreCase(param.getParameterType())) {
165 String termName = "";
166 String termId = param.getValue();
167
168 if (termId != null && termId.length() > 0) {
169 if (termId.startsWith(KrmsImplConstants.PARAMETERIZED_TERM_PREFIX)) {
170 if (!StringUtils.isBlank(newTermDescription)) {
171 termName = newTermDescription;
172 } else {
173 TermSpecificationBo termSpec = getDataObjectService().find(TermSpecificationBo.class,
174 termId.substring(1 + termId.indexOf(":")));
175 termName = termSpec.getName() + "(...)";
176 }
177 } else {
178 TermBo term = getDataObjectService().find(TermBo.class, termId);
179 termName = term.getSpecification().getName();
180 }
181 }
182
183 return termName;
184
185 } else if (PropositionParameterType.FUNCTION.getCode().equalsIgnoreCase(param.getParameterType()) ||
186 PropositionParameterType.OPERATOR.getCode().equalsIgnoreCase(param.getParameterType())) {
187 if (customOperatorUiTranslator.isCustomOperatorFormValue(param.getValue())) {
188 String functionName = customOperatorUiTranslator.getCustomOperatorName(param.getValue());
189 if (!StringUtils.isEmpty(functionName)) {
190 return functionName;
191 }
192 }
193 }
194
195 return param.getValue();
196 }
197
198
199
200
201 public String getParameterDisplayString() {
202 setupParameterDisplayString();
203
204 return this.parameterDisplayString;
205 }
206
207
208
209
210 public void setParameterDisplayString(String parameterDisplayString) {
211 this.parameterDisplayString = parameterDisplayString;
212 }
213
214 public boolean getEditMode() {
215 return this.editMode;
216 }
217
218 public void setEditMode(boolean editMode) {
219 this.editMode = editMode;
220 }
221
222 public String getCategoryId() {
223 return this.categoryId;
224 }
225
226 public void setCategoryId(String categoryId) {
227 this.categoryId = categoryId;
228 }
229
230
231
232
233
234
235
236 public void setTypeId(String typeId) {
237 if (StringUtils.isBlank(typeId)) {
238 this.typeId = null;
239 } else {
240 this.typeId = typeId;
241 }
242 }
243
244 public Long getVersionNumber() {
245 return versionNumber;
246 }
247
248 public void setVersionNumber(Long versionNumber) {
249 this.versionNumber = versionNumber;
250 }
251
252 public Map<String, String> getTermParameters() {
253 return termParameters;
254 }
255
256 public void setTermParameters(Map<String, String> termParameters) {
257 this.termParameters = termParameters;
258 }
259
260 public DataObjectService getDataObjectService() {
261 return KRADServiceLocator.getDataObjectService();
262 }
263
264
265
266
267
268
269
270 public static PropositionDefinition to(PropositionBo bo) {
271 if (bo == null) {
272 return null;
273 }
274
275 return PropositionDefinition.Builder.create(bo).build();
276 }
277
278
279
280
281
282
283
284 public static PropositionBo from(PropositionDefinition im) {
285 if (im == null) {
286 return null;
287 }
288
289 PropositionBo bo = new PropositionBo();
290 bo.id = im.getId();
291 bo.description = im.getDescription();
292
293
294
295 setRuleIdRecursive(im.getRuleId(), bo);
296
297 bo.typeId = im.getTypeId();
298 bo.propositionTypeCode = im.getPropositionTypeCode();
299 bo.parameters = new ArrayList<PropositionParameterBo>();
300
301 for (PropositionParameter parm : im.getParameters()) {
302 PropositionParameterBo parmBo = PropositionParameterBo.from(parm);
303 bo.parameters.add(parmBo);
304 parmBo.setProposition(bo);
305 }
306
307 bo.compoundOpCode = im.getCompoundOpCode();
308 bo.compoundSequenceNumber = im.getCompoundSequenceNumber();
309 bo.compoundComponents = new ArrayList<PropositionBo>();
310
311 if (im.getCompoundComponents() != null) for (PropositionDefinition prop : im.getCompoundComponents()) {
312 bo.compoundComponents.add(PropositionBo.from(prop));
313 }
314
315 bo.setVersionNumber(im.getVersionNumber());
316
317 return bo;
318 }
319
320 private static void setRuleIdRecursive(String ruleId, PropositionBo prop) {
321 prop.ruleId = ruleId;
322
323 if (prop.compoundComponents != null) {
324 for (PropositionBo child : prop.compoundComponents) {
325 if (child != null) {
326 setRuleIdRecursive(ruleId, child);
327 }
328 }
329 }
330 }
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346 public static PropositionBo createSimplePropositionBoStub(PropositionBo sibling, String pType) {
347
348 PropositionBo prop = null;
349 if (PropositionType.SIMPLE.getCode().equalsIgnoreCase(pType)) {
350 prop = new PropositionBo();
351 prop.setId(propositionIdIncrementer.getNewId());
352 prop.setPropositionTypeCode(pType);
353 prop.setEditMode(true);
354
355 if (sibling != null) {
356 prop.setRuleId(sibling.getRuleId());
357 }
358
359
360 PropositionParameterBo pTerm = new PropositionParameterBo();
361 pTerm.setId(propositionParameterIdIncrementer.getNewId());
362 pTerm.setParameterType("T");
363 pTerm.setProposition(prop);
364 pTerm.setSequenceNumber(new Integer("0"));
365 pTerm.setVersionNumber(new Long(1));
366 pTerm.setValue("");
367
368
369 PropositionParameterBo pOp = new PropositionParameterBo();
370 pOp.setId(propositionParameterIdIncrementer.getNewId());
371 pOp.setParameterType("O");
372 pOp.setProposition(prop);
373 pOp.setSequenceNumber(new Integer("2"));
374 pOp.setVersionNumber(new Long(1));
375
376
377 PropositionParameterBo pConst = new PropositionParameterBo();
378 pConst.setId(propositionParameterIdIncrementer.getNewId());
379 pConst.setParameterType("C");
380 pConst.setProposition(prop);
381 pConst.setSequenceNumber(new Integer("1"));
382 pConst.setVersionNumber(new Long(1));
383 pConst.setValue("");
384 List<PropositionParameterBo> paramList = Arrays.asList(pTerm, pConst, pOp);
385
386 prop.setParameters(paramList);
387 }
388
389 return prop;
390 }
391
392 public static PropositionBo createCompoundPropositionBoStub(PropositionBo existing, boolean addNewChild) {
393
394 PropositionBo prop = new PropositionBo();
395 prop.setId(propositionIdIncrementer.getNewId());
396 prop.setPropositionTypeCode(PropositionType.COMPOUND.getCode());
397 prop.setCompoundOpCode(LogicalOperator.AND.getCode());
398
399
400 prop.setDescription("");
401 prop.setEditMode(true);
402
403 if (existing != null) {
404 prop.setRuleId(existing.getRuleId());
405 }
406
407 List<PropositionBo> components = new ArrayList<PropositionBo>(2);
408 components.add(existing);
409
410 if (addNewChild) {
411 PropositionBo newProp = createSimplePropositionBoStub(existing, PropositionType.SIMPLE.getCode());
412 components.add(newProp);
413 prop.setEditMode(false);
414 }
415
416 prop.setCompoundComponents(components);
417
418 return prop;
419 }
420
421 public static PropositionBo createCompoundPropositionBoStub2(PropositionBo existing) {
422
423 PropositionBo prop = new PropositionBo();
424 prop.setId(propositionIdIncrementer.getNewId());
425 prop.setPropositionTypeCode(PropositionType.COMPOUND.getCode());
426 prop.setRuleId(existing.getRuleId());
427 prop.setCompoundOpCode(LogicalOperator.AND.getCode());
428
429 prop.setDescription("");
430 prop.setEditMode(true);
431 List<PropositionBo> components = new ArrayList<PropositionBo>();
432 ((ArrayList<PropositionBo>) components).add(existing);
433 prop.setCompoundComponents(components);
434
435 return prop;
436 }
437
438 public static PropositionBo copyProposition(PropositionBo existing) {
439
440 PropositionBo newProp = new PropositionBo();
441 newProp.setId(propositionIdIncrementer.getNewId());
442 newProp.setDescription(existing.getDescription());
443 newProp.setPropositionTypeCode(existing.getPropositionTypeCode());
444 newProp.setTypeId(existing.getTypeId());
445 newProp.setCompoundOpCode(existing.getCompoundOpCode());
446 newProp.setCompoundSequenceNumber(existing.getCompoundSequenceNumber());
447
448
449 List<PropositionParameterBo> newParms = new ArrayList<PropositionParameterBo>();
450
451 for (PropositionParameterBo parm : existing.getParameters()) {
452 PropositionParameterBo p = new PropositionParameterBo();
453 p.setId(propositionParameterIdIncrementer.getNewId());
454 p.setParameterType(parm.getParameterType());
455 p.setProposition(newProp);
456 p.setSequenceNumber(parm.getSequenceNumber());
457 p.setValue(parm.getValue());
458 ((ArrayList<PropositionParameterBo>) newParms).add(p);
459 }
460
461 newProp.setParameters(newParms);
462
463
464 List<PropositionBo> newCompoundComponents = new ArrayList<PropositionBo>();
465 for (PropositionBo component : existing.getCompoundComponents()) {
466 PropositionBo newComponent = copyProposition(component);
467 ((ArrayList<PropositionBo>) newCompoundComponents).add(component);
468 }
469
470 newProp.setCompoundComponents(newCompoundComponents);
471
472 return newProp;
473 }
474
475
476
477
478
479
480
481 private void writeObject(ObjectOutputStream stream) throws IOException, ClassNotFoundException {
482 parameters.size();
483 stream.defaultWriteObject();
484 }
485
486 public String getTermSpecId() {
487 return termSpecId;
488 }
489
490 public void setTermSpecId(String componentId) {
491 this.termSpecId = componentId;
492 }
493
494 public boolean isShowCustomValue() {
495 return showCustomValue;
496 }
497
498 public void setShowCustomValue(boolean showCustomValue) {
499 this.showCustomValue = showCustomValue;
500 }
501
502 public String getTermParameter() {
503 return termParameter;
504 }
505
506 public void setTermParameter(String termParameter) {
507 this.termParameter = termParameter;
508 }
509
510 public List<TermParameter> getTermParameterList() {
511 return termParameterList;
512 }
513
514 public void setTermParameterList(List<TermParameter> termParameterList) {
515 this.termParameterList = termParameterList;
516 }
517
518 public String getId() {
519 return id;
520 }
521
522 public void setId(String id) {
523 this.id = id;
524 }
525
526 public String getDescription() {
527 return description;
528 }
529
530 public void setDescription(String description) {
531 this.description = description;
532 }
533
534 public String getRuleId() {
535 return ruleId;
536 }
537
538 public void setRuleId(String ruleId) {
539 this.ruleId = ruleId;
540 }
541
542 public String getTypeId() {
543 return typeId;
544 }
545
546 public String getPropositionTypeCode() {
547 return propositionTypeCode;
548 }
549
550 public void setPropositionTypeCode(String propositionTypeCode) {
551 this.propositionTypeCode = propositionTypeCode;
552 }
553
554 public List<PropositionParameterBo> getParameters() {
555 return parameters;
556 }
557
558 public void setParameters(List<PropositionParameterBo> parameters) {
559 this.parameters = parameters;
560 }
561
562 public String getCompoundOpCode() {
563 return compoundOpCode;
564 }
565
566 public void setCompoundOpCode(String compoundOpCode) {
567 this.compoundOpCode = compoundOpCode;
568 }
569
570 public Integer getCompoundSequenceNumber() {
571 return compoundSequenceNumber;
572 }
573
574 public void setCompoundSequenceNumber(Integer compoundSequenceNumber) {
575 this.compoundSequenceNumber = compoundSequenceNumber;
576 }
577
578 public List<PropositionBo> getCompoundComponents() {
579 return compoundComponents;
580 }
581
582 public void setCompoundComponents(List<PropositionBo> compoundComponents) {
583 this.compoundComponents = compoundComponents;
584 }
585
586 public boolean getShowCustomValue() {
587 return showCustomValue;
588 }
589
590 public String getNewTermDescription() {
591 return newTermDescription;
592 }
593
594 public void setNewTermDescription(String newTermDescription) {
595 this.newTermDescription = newTermDescription;
596 }
597 }