View Javadoc

1   /**
2    *
3    */
4   package org.kuali.student.lum.program.service.impl;
5   
6   import static org.apache.commons.collections.CollectionUtils.isEmpty;
7   import static org.apache.commons.lang.StringUtils.isEmpty;
8   
9   import java.util.HashMap;
10  import java.util.List;
11  import java.util.Map;
12  
13  import org.apache.log4j.Logger;
14  import org.kuali.student.common.assembly.BOAssembler;
15  import org.kuali.student.common.assembly.BaseDTOAssemblyNode;
16  import org.kuali.student.common.assembly.BaseDTOAssemblyNode.NodeOperation;
17  import org.kuali.student.common.assembly.data.AssemblyException;
18  import org.kuali.student.common.dto.DtoConstants;
19  import org.kuali.student.common.exceptions.DoesNotExistException;
20  import org.kuali.student.common.exceptions.InvalidParameterException;
21  import org.kuali.student.common.exceptions.MissingParameterException;
22  import org.kuali.student.common.exceptions.OperationFailedException;
23  import org.kuali.student.common.util.UUIDHelper;
24  import org.kuali.student.core.statement.dto.RefStatementRelationInfo;
25  import org.kuali.student.core.statement.dto.StatementTreeViewInfo;
26  import org.kuali.student.core.statement.service.StatementService;
27  import org.kuali.student.core.statement.service.assembler.StatementTreeViewAssembler;
28  import org.kuali.student.lum.course.service.assembler.LoAssembler;
29  import org.kuali.student.lum.lo.service.LearningObjectiveService;
30  import org.kuali.student.lum.lu.dto.CluCluRelationInfo;
31  import org.kuali.student.lum.lu.dto.CluIdentifierInfo;
32  import org.kuali.student.lum.lu.dto.CluInfo;
33  import org.kuali.student.lum.lu.service.LuService;
34  import org.kuali.student.lum.program.dto.ProgramRequirementInfo;
35  import org.kuali.student.lum.program.service.assembler.ProgramAssemblerConstants;
36  import org.kuali.student.lum.program.service.assembler.ProgramAssemblerUtils;
37  import org.kuali.student.lum.service.assembler.CluAssemblerUtils;
38  
39  
40  /**
41   * @author glindholm
42   *
43   */
44  public class ProgramRequirementAssembler implements BOAssembler<ProgramRequirementInfo, CluInfo> {
45      final static Logger LOG = Logger.getLogger(ProgramRequirementAssembler.class);
46  
47  	private StatementService statementService;
48  	private StatementTreeViewAssembler statementTreeViewAssembler;
49  	private LearningObjectiveService loService;
50  	private LuService luService;
51  	private LoAssembler loAssembler;
52  	private CluAssemblerUtils cluAssemblerUtils;
53      private ProgramAssemblerUtils programAssemblerUtils;
54  
55  
56  	@Override
57  	public ProgramRequirementInfo assemble(CluInfo clu,
58  			ProgramRequirementInfo progReqInfo, boolean shallowBuild)
59  			throws AssemblyException {
60  		ProgramRequirementInfo progReq = (progReqInfo != null ? progReqInfo : new ProgramRequirementInfo());
61  
62  		if (clu.getOfficialIdentifier() != null) {
63  			progReq.setShortTitle(clu.getOfficialIdentifier().getShortName());
64  			progReq.setLongTitle(clu.getOfficialIdentifier().getLongName());
65  		}
66  		progReq.setDescr(clu.getDescr());
67  
68  		//assembling minCredits & maxCredits
69  		assembleCredits(clu, progReq);
70  
71  		if (progReq.getStatement() == null) {
72  			try {
73  				List<RefStatementRelationInfo> relations = statementService.getRefStatementRelationsByRef(ProgramAssemblerConstants.PROGRAM_REQUIREMENT, clu.getId());
74  
75  
76  				StatementTreeViewInfo statementTree = new StatementTreeViewInfo();
77  				if (relations != null) {
78  					statementTreeViewAssembler.assemble(statementService.getStatementTreeView(relations.get(0).getStatementId()), statementTree, shallowBuild);
79  				}
80  				progReq.setStatement(statementTree);
81  			} catch (AssemblyException e) {
82  				throw e;
83  			} catch (Exception e) {
84  				throw new AssemblyException(e);
85  			}
86  		}
87  
88  		if (isEmpty(progReq.getLearningObjectives())) {
89  			progReq.setLearningObjectives(cluAssemblerUtils.assembleLos(clu.getId(), shallowBuild));
90  		}
91  
92  		progReq.setMetaInfo(clu.getMetaInfo());
93  		progReq.setType(clu.getType());
94  		progReq.setAttributes(clu.getAttributes());
95  		progReq.setId(clu.getId());
96  
97  		return progReq;
98  	}
99  
100 	@Override
101 	public BaseDTOAssemblyNode<ProgramRequirementInfo, CluInfo> disassemble(
102 			ProgramRequirementInfo progReq, NodeOperation operation)
103 			throws AssemblyException {
104 
105 		if (progReq == null) {
106 			// FIXME Unsure now if this is an exception or just return null or
107 			// empty assemblyNode
108 		    LOG.error("ProgramRequirementInfo to disassemble is null!");
109 			throw new AssemblyException("ProgramRequirementInfo can not be null");
110 		}
111 
112 		BaseDTOAssemblyNode<ProgramRequirementInfo, CluInfo> result = new BaseDTOAssemblyNode<ProgramRequirementInfo, CluInfo>(null);
113 
114 		// Create the Statement Tree
115         StatementTreeViewInfo statement = progReq.getStatement();
116         statement.setId(UUIDHelper.genStringUUID(statement.getId()));
117         BaseDTOAssemblyNode<StatementTreeViewInfo, StatementTreeViewInfo> statementTree;
118 		try {
119 			statementTree = statementTreeViewAssembler.disassemble(statement, operation);
120 		} catch (AssemblyException e) {
121 			throw e;
122 		} catch (Exception e) {
123 			throw new AssemblyException(e);
124 		}
125         result.getChildNodes().add(statementTree);
126 
127 		CluInfo clu;
128 		try {
129 			clu = (NodeOperation.UPDATE == operation) ?  luService.getClu(progReq.getId()) : new CluInfo();
130         } catch (Exception e) {
131 			throw new AssemblyException("Error getting existing learning unit during program requirement update", e);
132         }
133 
134         if (operation.equals(NodeOperation.DELETE)) {
135             try {
136 				final List<CluCluRelationInfo> relations = luService.getCluCluRelationsByClu(progReq.getId());
137 	            final BaseDTOAssemblyNode<ProgramRequirementInfo, CluCluRelationInfo> cluRelation = new BaseDTOAssemblyNode<ProgramRequirementInfo, CluCluRelationInfo>(null);
138 	            if (relations.size() > 1) {
139 	            	throw new AssemblyException("Unable to dissamble ProgramRequirement, more than one CluCluRelation found");
140 	            } else if (relations.size() == 1) {
141 	            	cluRelation.setNodeData(relations.get(0));
142 	            	cluRelation.setOperation(operation);
143 	            	result.getChildNodes().add(cluRelation);
144 	            }
145 			} catch (Exception e) {
146 				throw new AssemblyException(e);
147 			}
148         }
149 
150         BaseDTOAssemblyNode<ProgramRequirementInfo, CluInfo> cluResult = new BaseDTOAssemblyNode<ProgramRequirementInfo, CluInfo>(this);
151 
152         cluResult.setNodeData(clu);
153         cluResult.setBusinessDTORef(progReq);
154         cluResult.setOperation(operation);
155         result.getChildNodes().add(cluResult);
156 
157         programAssemblerUtils.disassembleBasics(clu, progReq);
158 
159 		//disassembling minCredits & maxCredits
160         disassembleCredits(clu, progReq);
161 
162         progReq.setId(clu.getId());
163         CluIdentifierInfo official = null != clu.getOfficialIdentifier() ? clu.getOfficialIdentifier() : new CluIdentifierInfo();
164         official.setLongName(progReq.getLongTitle());
165         official.setShortName(progReq.getShortTitle());
166         official.setState(!isEmpty(clu.getState()) ? clu.getState() : DtoConstants.STATE_ACTIVE);
167         // gotta be this type
168         official.setType(ProgramAssemblerConstants.OFFICIAL);
169         clu.setOfficialIdentifier(official);
170 
171         clu.setDescr(progReq.getDescr());
172         clu.setState(!isEmpty(clu.getState()) ? clu.getState() : DtoConstants.STATE_ACTIVE);
173         if (progReq.getLearningObjectives() != null) {
174             disassembleLearningObjectives(progReq, operation, result);
175         }
176 
177         RefStatementRelationInfo relation;
178         if (operation == NodeOperation.CREATE) {
179             relation = new RefStatementRelationInfo();
180             relation.setId(UUIDHelper.genStringUUID(null));
181         } else {
182         	try {
183         		relation = statementService.getRefStatementRelationsByRef(ProgramAssemblerConstants.PROGRAM_REQUIREMENT, clu.getId()).get(0);
184 			} catch (Exception e) {
185 				throw new AssemblyException("Unable to find RefStatementRelation", e);
186 			}
187         }
188         //relation.setType("clu.prerequisites"); // FIXME Derive from statement and rule types
189         relation.setType(ProgramAssemblerConstants.PROGRAM_REFERENCE_TYPE);
190         relation.setRefObjectId(clu.getId());
191         relation.setRefObjectTypeKey(ProgramAssemblerConstants.PROGRAM_REQUIREMENT);
192         relation.setStatementId(statement.getId());
193         relation.setState(DtoConstants.STATE_ACTIVE);
194 
195         BaseDTOAssemblyNode<ProgramRequirementInfo, RefStatementRelationInfo> relationNode = new BaseDTOAssemblyNode<ProgramRequirementInfo, RefStatementRelationInfo>(null);
196         relationNode.setNodeData(relation);
197         relationNode.setOperation(operation);
198 
199         result.getChildNodes().add(relationNode);
200         result.setBusinessDTORef(progReq);
201         result.setOperation(operation);
202 		return result;
203 	}
204 
205 	private void disassembleLearningObjectives(ProgramRequirementInfo progReq,
206 			NodeOperation operation,
207 			BaseDTOAssemblyNode<ProgramRequirementInfo, CluInfo> result) throws AssemblyException {
208         try {
209             List<BaseDTOAssemblyNode<?, ?>> loResults = cluAssemblerUtils.disassembleLos(progReq.getId(), progReq.getState(),  progReq.getLearningObjectives(), operation);
210             if (loResults != null) {
211                 result.getChildNodes().addAll(loResults);
212             }
213         } catch (DoesNotExistException e) {
214         } catch (Exception e) {
215             throw new AssemblyException("Error while disassembling los", e);
216         }
217 	}
218 
219 	private void disassembleCredits(CluInfo clu, ProgramRequirementInfo progReq){
220 		Map<String,String> attributes = null != clu.getAttributes() ? clu.getAttributes() : new HashMap<String,String>();
221 
222 		if(progReq.getMinCredits() != null){
223 			attributes.put(ProgramAssemblerConstants.MIN_CREDITS, Integer.toString(progReq.getMinCredits()));
224 		}else{
225 			attributes.put(ProgramAssemblerConstants.MIN_CREDITS, null);
226 		}
227 		if(progReq.getMaxCredits() != null) {
228 			attributes.put(ProgramAssemblerConstants.MAX_CREDITS, Integer.toString(progReq.getMaxCredits()));
229 		}else{
230 			attributes.put(ProgramAssemblerConstants.MAX_CREDITS, null);
231 		}
232 			
233 		clu.setAttributes(attributes);
234 	}
235 
236 	private void assembleCredits(CluInfo clu, ProgramRequirementInfo progReq){
237 		Map<String,String> attributes = clu.getAttributes();
238 		if(attributes != null){
239 			String minCredits = attributes.get(ProgramAssemblerConstants.MIN_CREDITS);
240 			String maxCredits = attributes.get(ProgramAssemblerConstants.MAX_CREDITS);
241 			progReq.setMinCredits(isEmpty(minCredits)?null:Integer.parseInt(minCredits));
242 			progReq.setMaxCredits(isEmpty(maxCredits)?null:Integer.parseInt(maxCredits));
243 		}
244 	}
245 
246 	public StatementTreeViewAssembler getStatementTreeViewAssembler() {
247 		return statementTreeViewAssembler;
248 	}
249 
250 	public void setStatementTreeViewAssembler(
251 			StatementTreeViewAssembler statementTreeViewAssembler) {
252 		this.statementTreeViewAssembler = statementTreeViewAssembler;
253 	}
254 
255 	public StatementService getStatementService() {
256 		return statementService;
257 	}
258 
259 	public void setStatementService(StatementService statementService) {
260 		this.statementService = statementService;
261 	}
262 
263 	public LearningObjectiveService getLoService() {
264 		return loService;
265 	}
266 
267 	public void setLoService(LearningObjectiveService loService) {
268 		this.loService = loService;
269 	}
270 
271 	public LuService getLuService() {
272 		return luService;
273 	}
274 
275 	public void setLuService(LuService luService) {
276 		this.luService = luService;
277 	}
278 
279 	public LoAssembler getLoAssembler() {
280 		return loAssembler;
281 	}
282 
283 	public void setLoAssembler(LoAssembler loAssembler) {
284 		this.loAssembler = loAssembler;
285 	}
286 
287 	public CluAssemblerUtils getCluAssemblerUtils() {
288 		return cluAssemblerUtils;
289 	}
290 
291 	public void setCluAssemblerUtils(CluAssemblerUtils cluAssemblerUtils) {
292 		this.cluAssemblerUtils = cluAssemblerUtils;
293 	}
294 
295 	public ProgramAssemblerUtils getProgramAssemblerUtils() {
296 		return programAssemblerUtils;
297 	}
298 
299 	public void setProgramAssemblerUtils(ProgramAssemblerUtils programAssemblerUtils) {
300 		this.programAssemblerUtils = programAssemblerUtils;
301 	}
302 }