View Javadoc

1   package net.sf.jpkgmk.prototype;
2   
3   
4   import java.io.File;
5   import java.io.FileNotFoundException;
6   
7   import net.sf.jpkgmk.AbstractLineProvider;
8   import net.sf.jpkgmk.ParseException;
9   import net.sf.jpkgmk.util.VariableResolver;
10  
11  import org.apache.commons.logging.Log;
12  import org.apache.commons.logging.LogFactory;
13  
14  /**
15   * The prototype entry command
16   * 
17   * @author gommma (gommma AT users.sourceforge.net)
18   * @author Last changed by: $Author: gommma $
19   * @version $Revision: 2 $ $Date: 2008-08-20 21:14:19 +0200 (Mi, 20 Aug 2008) $
20   * @since 1.0
21   */
22  public abstract class PrototypeEntryCommand extends AbstractLineProvider implements PrototypeEntry 
23  {
24  	private PrototypeEntryType type = PrototypeEntryType.COMMAND;
25  	private CommandType commandType;
26  	/**
27  	 * Defines whether or not the "!" symbol is separated with a whitespace from the rest of the line.
28  	 * Is needed to create the line as it was originally when parsing an existing prototype file.
29  	 */
30  	private boolean hasWhitespaceSeparator = true;
31  
32  	private Log log = LogFactory.getLog(PrototypeEntryCommand.class);
33  	
34  	
35  	/**
36  	 * @param commandType
37  	 */
38  	public PrototypeEntryCommand(CommandType commandType)
39  	{
40  		if(commandType == null) {
41  			throw new NullPointerException("The parameter 'commandType' must not be null");
42  		}
43  		this.commandType = commandType;
44  	}
45  
46  	/**
47  	 * @return
48  	 */
49  	public boolean isHasWhitespaceSeparator() {
50  		return hasWhitespaceSeparator;
51  	}
52  
53  	/**
54  	 * @param hasWhitespaceSeparator If the "!" is separated by a whitespace from the rest of the line or not.
55  	 */
56  	public void setHasWhitespaceSeparator(boolean hasWhitespaceSeparator) {
57  		this.hasWhitespaceSeparator = hasWhitespaceSeparator;
58  	}
59  
60  	/**
61  	 * @return Returns the part of the line that is specific for the implementation of the command. This includes everything
62  	 * after the '! cmdType' string
63  	 */
64  	protected abstract String getCommandLinePart();
65  	
66  	
67  	/**
68  	 * @see net.sf.jpkgmk.LineProvider#getLine()
69  	 */
70  	public String getLine() {
71  		log.debug("<Entering> getLine()");
72  			
73  		StringBuffer sb = new StringBuffer();
74  		sb.append(this.type.getKey());
75  		if(this.hasWhitespaceSeparator) {
76  			sb.append(" ");
77  		}
78  		
79  		if(this.commandType.getIdName() != null) {
80  			// Add command type and blank
81  			sb.append(this.commandType.getIdName());
82  			// Append separator
83  			sb.append(" ");
84  		}
85  		
86  		String commandLinePart = getCommandLinePart();
87  		sb.append(commandLinePart);
88  		
89  		return sb.toString();
90  	}
91  
92  	public PrototypeEntryType getType() {
93  		return this.type;
94  	}
95  
96  
97      @Override
98  	public String toString() {
99  		StringBuffer sb = new StringBuffer();
100 		sb.append(this.getClass().getName()).append("[");
101 		sb.append("type=").append(this.type);
102 		sb.append(",commandType=").append(this.commandType);
103 		sb.append(",hasWhitespaceSeparater=").append(this.hasWhitespaceSeparator);
104 		sb.append("]");
105 		return sb.toString();
106 	}
107 	
108 	
109 	
110 	/**
111 	 * Class for parsing a prototype 'command' line
112 	 * 
113 	 */
114 	public static class PrototypeEntryCommandParser implements PrototypeEntryParser
115 	{
116 
117 		public PrototypeEntry parse(String line, PrototypeEntryCommandDefault entryCommandDefault) 
118 		{
119 			if (line == null) {
120 				throw new NullPointerException(
121 						"The parameter 'line' must not be null");
122 			}
123 			
124 			String[] items = PrototypeParser.getLineItems(line);
125 			// After the exclamation mark the whitespace is not required, e.g. "!PROJDIR=/usr/proj" is a valid command
126 			if(items.length <= 0) {
127 				throw new ParseException("Invalid line: " + line);
128 			}
129 			
130 			String firstItem = items[0];
131 			
132 			boolean hasWhitespaceSeparator;
133 			// Build the parameters of the command excluding the prefixed "!"
134 			String[] commandParams = null;
135 			if(firstItem.equals(PrototypeEntryType.COMMAND.getKey())) {
136 				commandParams = new String[items.length-1];
137 				System.arraycopy(items, 1, commandParams, 0, commandParams.length);
138 				hasWhitespaceSeparator=true;
139 			}
140 			// No whitespace between the exclamation mark and the command key
141 			else if(firstItem.startsWith(PrototypeEntryType.COMMAND.getKey())) {
142 				// We have to cut of the starting exclamation mark in front of the first string
143 				commandParams = new String[items.length];
144 				commandParams[0] = firstItem.substring(1);
145 				System.arraycopy(items, 1, commandParams, 1, commandParams.length-1);
146 				hasWhitespaceSeparator=false;
147 			}
148 			else {
149 				throw new IllegalArgumentException("The line '" + line + "' must start with the character '" + PrototypeEntryType.COMMAND.getKey() + "'");
150 			}
151 			
152 			PrototypeEntryCommand entryCommand = this.parse(commandParams);
153 			// To ensure that the "getLine()" method returns the same format of the line as the original has
154 			entryCommand.setHasWhitespaceSeparator(hasWhitespaceSeparator);
155 			return entryCommand;
156 		}
157 
158 		
159 		/**
160 		 * @param commandParams
161 		 * @return
162 		 */
163 		private PrototypeEntryCommand parse(String[] commandParams) 
164 		{
165 			if(commandParams.length <= 0) {
166 				throw new ParseException("The given command parameter array must not be empty!");
167 			}
168 			
169 			// First get the type of command
170 			CommandType commandType = CommandType.findTypeByName(commandParams[0]);
171 			PrototypeEntryCommand entry = commandType.getParser().parse(commandParams);
172 			return entry;
173 		}
174 		
175 	}
176 
177 	/**
178 	 * Resolves the file for the given path and expands potential variables within the string path. If the file
179 	 * cannot be found, a {@link FileNotFoundException} is thrown.
180 	 * @param filePath
181 	 * @param variableResolver
182 	 * @return
183 	 * @throws FileNotFoundException
184 	 */
185 	protected File resolveFile(String filePath, VariableResolver variableResolver) throws FileNotFoundException {
186 		String expandedPath = variableResolver.expand(filePath);
187 		File file = new File(expandedPath);
188 		if(!file.exists()) {
189 			throw new FileNotFoundException("The file " + file.getAbsolutePath() + " does not exist.");
190 		}
191 		return file;
192 	}
193 	
194 	
195 }