001: /*
002: * Copyright (C) 2003 Robert MacGrogan
003: *
004: * This library is free software; you can redistribute it and/or
005: * modify it under the terms of the GNU Lesser General Public
006: * License as published by the Free Software Foundation; either
007: * version 2.1 of the License, or (at your option) any later version.
008: *
009: * This library is distributed in the hope that it will be useful,
010: * but WITHOUT ANY WARRANTY; without even the implied warranty of
011: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
012: * Lesser General Public License for more details.
013: *
014: * You should have received a copy of the GNU Lesser General Public
015: * License along with this library; if not, write to the Free Software
016: * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
017: *
018: *
019: * $Archive: SourceJammer$
020: * $FileName: LabelMaker.java$
021: * $FileID: 4808$
022: *
023: * Last change:
024: * $AuthorName: Rob MacGrogan$
025: * $Date: 9/17/03 6:19 PM$
026: * $Comment: Debug. Building change list was failing with a null pointer.$
027: */
028: package org.sourcejammer.project.controller;
029:
030: import java.io.File;
031: import java.io.FileOutputStream;
032: import java.io.IOException;
033: import java.io.PrintStream;
034: import java.util.Date;
035: import java.util.Enumeration;
036:
037: import org.sourcejammer.project.NodeDoesNotExistException;
038: import org.sourcejammer.project.model.FileAccessException;
039: import org.sourcejammer.project.model.NodeLibrary;
040: import org.sourcejammer.project.view.FileProperties;
041: import org.sourcejammer.project.view.NodeInfo;
042: import org.sourcejammer.server.make.EndOfSourceException;
043: import org.sourcejammer.server.security.CheckInException;
044: import org.sourcejammer.server.security.CheckOutException;
045: import org.sourcejammer.server.security.SecurityException;
046: import org.sourcejammer.server.source.InvalidSourceException;
047: import org.sourcejammer.server.source.TextFileException;
048: import org.sourcejammer.util.AppConfig;
049: import org.sourcejammer.util.ConfigurationException;
050: import org.sourcejammer.util.TempDirectoryManager;
051:
052: /**
053: * Title: $FileName: LabelMaker.java$
054: * @version $VerNum: 4$
055: * @author $AuthorName: Rob MacGrogan$<br><br>
056: *
057: * $Description: Used to construct label objects and files.$<br>
058: * $KeyWordsOff: $<br>
059: */
060: public class LabelMaker {
061:
062: private Label label = null;
063: private NodeLibrary library = null;
064: private long parentProjectID = -1;
065: private String labelName = null;
066: private String description = null;
067: private Date createDate = null;
068: private long existingLabelID = -1;
069: private Archive archive = null;
070: private File tempLabelFile = null;
071: private String userName = null;
072: private boolean buildChangeList = false;
073:
074: public LabelMaker() {
075: }
076:
077: public void makeLabel() throws LabelBuildException,
078: FileAccessException, SecurityException {
079: doesExistingLabelExist();
080: java.io.File labelTempFile = null;
081: //Make Label object.
082: Label oLabel = new Label();
083: oLabel.setNodeName(labelName);
084: oLabel.setDescription(description);
085: oLabel.setCreatedDate(createDate);
086: oLabel.setRootProjectUniqueID(parentProjectID);
087: label = oLabel;
088: buildLabel(parentProjectID, "", existingLabelID);
089: manageNew();
090: manageRebuild();
091: }
092:
093: private void manageNew() throws FileAccessException,
094: LabelBuildException, SecurityException {
095: if (existingLabelID < 0) {
096: try {
097: //New label.
098: tempLabelFile = TempDirectoryManager.getNewTempFile();
099: label.saveXML(tempLabelFile);
100: try {
101: FileProperties fileProps = new FileProperties();
102: fileProps.setDescription(description);
103: fileProps.setFileType(AppConfig.FileTypes.LABEL);
104: fileProps
105: .setHistoryStorageType(AppConfig.FileHistoryStorageTypes.DIFF);
106: fileProps.setLimitHistorySize(false);
107:
108: //Add label as file to parent project.
109: archive.addFile(parentProjectID, labelName,
110: tempLabelFile, fileProps, userName,
111: description);
112: } finally {
113: //remove temp file.
114: tempLabelFile.delete();
115: }
116: } catch (IOException ex) {
117: throw new FileAccessException(ex.getMessage(), ex);
118: } catch (FileAlreadyExistsException ex) {
119: throw new FileAccessException(ex.getMessage(), ex);
120: } catch (TextFileException ex) {
121: throw new FileAccessException(ex.getMessage(), ex);
122: } catch (ProjectDoesNotExistException ex) {
123: throw new FileAccessException(ex.getMessage(), ex);
124: }
125: }
126: }
127:
128: private void doesExistingLabelExist() throws SecurityException,
129: FileAccessException, LabelBuildException {
130: if (existingLabelID > -1) {
131: //Get label file node.
132: try {
133: FileNode ndLabel = library.getFileNode(existingLabelID);
134: try {
135: //Is it a label?
136: if (ndLabel.getFileType() != AppConfig.FileTypes.LABEL) {
137: throw new NodeDoesNotExistException(
138: "There is no label with the specified id: "
139: + existingLabelID + ".");
140: }
141: labelName = ndLabel.getNodeName();
142: } finally {
143: library.releaseNode(ndLabel);
144: }
145: } catch (FileDoesNotExistException ex) {
146: throw new LabelBuildException(ex.getMessage(), ex);
147: } catch (NodeDoesNotExistException ex) {
148: throw new LabelBuildException(ex.getMessage(), ex);
149: }
150: }
151: }
152:
153: private void manageRebuild() throws LabelBuildException,
154: SecurityException, FileAccessException {
155: if (existingLabelID > -1) {
156: try {
157: manageChangeList();
158: tempLabelFile = TempDirectoryManager.getNewTempFile();
159: label.saveXML(tempLabelFile);
160:
161: //Check out to user.
162: archive.checkOutFile(existingLabelID, userName,
163: "server");
164: try {
165: archive.addNewVersion(existingLabelID,
166: tempLabelFile, description, userName);
167: } finally {
168: //Check in new label to supercede old label.
169: archive.checkInFile(existingLabelID);
170: }
171: } catch (IOException ex) {
172: throw new FileAccessException(ex.getMessage(), ex);
173: } catch (ProjectDoesNotExistException ex) {
174: throw new LabelBuildException(ex.getMessage(), ex);
175: } catch (FileDoesNotExistException ex) {
176: throw new LabelBuildException(ex.getMessage(), ex);
177: } catch (TextFileException ex) {
178: throw new LabelBuildException(ex.getMessage(), ex);
179: } catch (InvalidSourceException ex) {
180: throw new LabelBuildException(ex.getMessage(), ex);
181: } catch (EndOfSourceException ex) {
182: throw new LabelBuildException(ex.getMessage(), ex);
183: } catch (WrongFileTypeException ex) {
184: throw new LabelBuildException(ex.getMessage(), ex);
185: } finally {
186: tempLabelFile.delete();
187: }
188: }
189: }
190:
191: private void manageChangeList() throws SecurityException,
192: LabelBuildException, FileAccessException {
193:
194: if (buildChangeList) {
195: System.out.println("** gotta build change list");
196: File changeListFile = buildChangeListFile();
197: try {
198: //Now we need to check in the change list file and added it to the label.
199: String changeListName = labelName + "-changes.txt";
200: System.out.println("** change list name: "
201: + changeListName);
202:
203: //Does file exist in label's parent project?
204: ProjectNode parent = library
205: .getProjectNode(parentProjectID);
206: boolean fileExists = false;
207: long changeListID = -1;
208: try {
209: ProjectChild child = parent
210: .getChildNode(changeListName);
211: System.out.println("** change list already exists");
212: fileExists = true;
213: changeListID = child.getUniqueID();
214: } catch (NodeDoesNotExistException ex) {
215: //just means change list file does not exist.
216: System.out.println("** change does not exist");
217: }
218:
219: long changeListVersionID = -1;
220: if (fileExists) {
221: //Check out to user.
222: archive.checkOutFile(changeListID, userName,
223: "server");
224: System.out.println("** checked out change list");
225: try {
226: changeListVersionID = archive
227: .addNewVersion(changeListID,
228: changeListFile,
229: "Auto-generated change list.",
230: userName);
231: System.out.println("** added new version");
232: } finally {
233: //Check in new label to supercede old label.
234: archive.checkInFile(changeListID);
235: System.out.println("** checked in change list");
236: }
237: } else {
238: System.out.println("** adding change list");
239: //Add it.
240: FileProperties fileProps = new FileProperties();
241: fileProps
242: .setDescription("Auto-generated change list.");
243: fileProps.setFileType(AppConfig.FileTypes.TEXT);
244: fileProps
245: .setHistoryStorageType(AppConfig.FileHistoryStorageTypes.DIFF);
246: fileProps.setLimitHistorySize(false);
247: long[] l = archive.addFile(parentProjectID,
248: changeListName, changeListFile, fileProps,
249: userName, description);
250: System.out.println("** added it");
251: changeListID = l[0];
252: changeListVersionID = l[1];
253: }
254: changeListFile.delete();
255: System.out.println("** deleted generated temp file");
256:
257: //Look up version number
258: FileNode ndChangeList = library
259: .getFileNode(changeListID);
260: int changeListVerNumber = ndChangeList.childCount();
261:
262: //Add change list to label.
263: label.addVersion(changeListVerNumber,
264: changeListVersionID, changeListID, "/"
265: + changeListName);
266: System.out.println("** added change list to label");
267: } catch (CheckInException ex) {
268: throw new LabelBuildException(ex.getMessage(), ex);
269: } catch (ProjectDoesNotExistException ex) {
270: throw new LabelBuildException(ex.getMessage(), ex);
271: } catch (FileDoesNotExistException ex) {
272: throw new LabelBuildException(ex.getMessage(), ex);
273: } catch (EndOfSourceException ex) {
274: throw new LabelBuildException(ex.getMessage(), ex);
275: } catch (TextFileException ex) {
276: throw new LabelBuildException(ex.getMessage(), ex);
277: } catch (InvalidSourceException ex) {
278: throw new LabelBuildException(ex.getMessage(), ex);
279: } catch (WrongFileTypeException ex) {
280: throw new LabelBuildException(ex.getMessage(), ex);
281: } catch (FileAlreadyExistsException ex) {
282: throw new LabelBuildException(ex.getMessage(), ex);
283: }
284: }
285: }
286:
287: private File buildChangeListFile() throws FileAccessException,
288: LabelBuildException, SecurityException {
289: long prevID = -1;
290: int prevVerNum = -1;
291:
292: System.out.println("** building change list file");
293: File changeListFile = null;
294: try {
295: //Get previous label and info.
296: FileNode ndLabelFile = library.getFileNode(existingLabelID);
297: System.out.println("** got prev label node");
298: try {
299: NodeInfo prev = ndLabelFile.getLatestVersionNode();
300: prevVerNum = ndLabelFile.childCount();
301: prevID = prev.getUniqueID();
302: } finally {
303: library.releaseNode(ndLabelFile);
304: }
305:
306: Label prevLabel = archive.getLabelContentList(
307: existingLabelID, prevVerNum);
308: System.out.println("** got prev label");
309:
310: long tempFileID = -1;
311: //Get new temp file.
312: tempFileID = TempDirectoryManager.getNextID();
313: changeListFile = TempDirectoryManager
314: .getNewTempFile(tempFileID);
315:
316: FileOutputStream stmOut = new FileOutputStream(
317: changeListFile);
318: try {
319: PrintStream stm = new PrintStream(stmOut);
320: try {
321: //Build change list.
322: ChangeListMaker maker = new ChangeListMaker(library);
323: maker.setNewLabel(label, description);
324: maker.setOldLabel(prevLabel, prevID);
325: maker.setTarget(stm);
326: maker.setEolType(AppConfig.getInstance()
327: .getDefaultEOLType());
328: System.out
329: .println("** about to generate change list");
330: maker.generateList();
331: System.out.println("** generated change list");
332: } finally {
333: stm.flush();
334: stm.close();
335: }
336: } finally {
337: stmOut.close();
338: }
339: } catch (FileDoesNotExistException ex) {
340: System.out.println("!! NO FILE");
341: throw new LabelBuildException(ex.getMessage(), ex);
342: } catch (ProjectDoesNotExistException ex) {
343: System.out.println("!! NO PROJECT");
344: throw new LabelBuildException(ex.getMessage(), ex);
345: } catch (NoSuchVersionException ex) {
346: System.out.println("!! NO VERSION");
347: throw new LabelBuildException(ex.getMessage(), ex);
348: } catch (WrongFileTypeException ex) {
349: System.out.println("!! WRONG FILE TYPE");
350: throw new LabelBuildException(ex.getMessage(), ex);
351: } catch (InvalidSourceException ex) {
352: System.out.println("!! INVALID SOURCE");
353: throw new LabelBuildException(ex.getMessage(), ex);
354: } catch (EndOfSourceException ex) {
355: System.out.println("!! END OF SOURCE");
356: throw new LabelBuildException(ex.getMessage(), ex);
357: } catch (TextFileException ex) {
358: System.out.println("!! TEXT FILE EXCEPTION");
359: throw new LabelBuildException(ex.getMessage(), ex);
360: } catch (IOException ex) {
361: System.out.println("!! IO EXCEPTION");
362: throw new FileAccessException(ex.getMessage(), ex);
363: } catch (NodeDoesNotExistException ex) {
364: System.out.println("!! NO NODE");
365: throw new FileAccessException(ex.getMessage(), ex);
366: }
367: System.out.println("** returning change list file.");
368: return changeListFile;
369: }
370:
371: /**
372: * This method recursively calls itself until it has put all of the latest
373: * versions of all the file nodes in parent (and in all ProjectNode children
374: * of parent) into label.
375: */
376: private void buildLabel(long parentProjectID, String baseSJPath,
377: long skipFile) throws LabelBuildException,
378: SecurityException, FileAccessException {
379: try {
380: System.out.println("** buildLabel(" + baseSJPath + ")");
381: ProjectNode ndParent = library
382: .getProjectNode(parentProjectID);
383: try {
384: Enumeration children = ndParent.getChildrenInfo();
385: while (children.hasMoreElements()) {
386: ProjectChild child = (ProjectChild) children
387: .nextElement();
388:
389: String childName = null;
390: try {
391: childName = library.getProjectChildName(child);
392: } catch (NodeDoesNotExistException ex) {
393: if (child.getNodeType() == AppConfig.NodeTypes.PROJECT) {
394: throw new ProjectDoesNotExistException(
395: "Project does not exist.", ex);
396: } else {
397: throw new FileDoesNotExistException(
398: "File does not exist.", ex);
399: }
400: }
401:
402: if (child.getNodeType() == AppConfig.NodeTypes.PROJECT) {
403: System.out.println("** project: " + childName);
404: String sChildSJPath = baseSJPath
405: + AppConfig.getInstance()
406: .getSourceJammerSwitch()
407: + childName;
408: //Recursive call.
409: buildLabel(child.getUniqueID(), sChildSJPath,
410: skipFile);
411: } else if (child.getNodeType() == AppConfig.NodeTypes.FILE) {
412: FileNode ndFile = library.getFileNode(child
413: .getUniqueID());
414: try {
415: if (ndFile.getUniqueID() != skipFile) {
416: NodeInfo ndVer = ndFile
417: .getLatestVersionNode();
418: int iVerNum = Integer.parseInt(ndVer
419: .getNodeName());
420: String sFullPath = baseSJPath
421: + AppConfig
422: .getInstance()
423: .getSourceJammerSwitch()
424: + ndFile.getNodeName();
425: label.addVersion(iVerNum, ndVer
426: .getUniqueID(), ndFile
427: .getUniqueID(), sFullPath);
428: }
429: } finally {
430: library.releaseNode(ndFile);
431: }
432: } else {
433: throw new ConfigurationException(
434: "Unexpected node type found in project: "
435: + ndParent.toString() + ".");
436: }
437: }//end while more children
438: } finally {
439: library.releaseNode(ndParent);
440: }
441: } catch (ProjectDoesNotExistException ex) {
442: throw new LabelBuildException(ex.getMessage(), ex);
443: } catch (FileDoesNotExistException ex) {
444: throw new LabelBuildException(ex.getMessage(), ex);
445: } catch (NoSuchVersionException ex) {
446: throw new LabelBuildException(ex.getMessage(), ex);
447: }
448: }
449:
450: /**
451: * Returns the label.
452: * @return Label
453: */
454: public Label getLabel() {
455: return label;
456: }
457:
458: /**
459: * Sets the library.
460: * @param library The library to set
461: */
462: public void setLibrary(NodeLibrary library) {
463: this .library = library;
464: }
465:
466: /**
467: * Sets the parentProjectID.
468: * @param parentProjectID The parentProjectID to set
469: */
470: public void setParentProjectID(long parentProjectID) {
471: this .parentProjectID = parentProjectID;
472: }
473:
474: /**
475: * Sets the createDate.
476: * @param createDate The createDate to set
477: */
478: public void setCreateDate(Date createDate) {
479: this .createDate = createDate;
480: }
481:
482: /**
483: * Sets the description.
484: * @param description The description to set
485: */
486: public void setDescription(String description) {
487: this .description = description;
488: }
489:
490: /**
491: * Sets the existingLabelID.
492: * @param existingLabelID The existingLabelID to set
493: */
494: public void setExistingLabelID(long existingLabelID) {
495: this .existingLabelID = existingLabelID;
496: }
497:
498: /**
499: * Sets the labelName.
500: * @param labelName The labelName to set
501: */
502: public void setLabelName(String labelName) {
503: this .labelName = labelName;
504: }
505:
506: /**
507: * Sets the archive.
508: * @param archive The archive to set
509: */
510: public void setArchive(Archive archive) {
511: this .archive = archive;
512: }
513:
514: /**
515: * Sets the userName.
516: * @param userName The userName to set
517: */
518: public void setUserName(String userName) {
519: this .userName = userName;
520: }
521:
522: /**
523: * Sets the buildChangeList.
524: * @param buildChangeList The buildChangeList to set
525: */
526: public void setBuildChangeList(boolean buildChangeList) {
527: this.buildChangeList = buildChangeList;
528: }
529:
530: }
|