1 7 package fr.jayasoft.ivy.parser; 8 9 import java.io.IOException ; 10 import java.net.URL ; 11 import java.text.ParseException ; 12 import java.util.ArrayList ; 13 import java.util.Date ; 14 import java.util.HashSet ; 15 import java.util.List ; 16 import java.util.Set ; 17 18 import org.xml.sax.SAXException ; 19 import org.xml.sax.SAXParseException ; 20 import org.xml.sax.helpers.DefaultHandler ; 21 22 import fr.jayasoft.ivy.Configuration; 23 import fr.jayasoft.ivy.DefaultDependencyDescriptor; 24 import fr.jayasoft.ivy.DefaultModuleDescriptor; 25 import fr.jayasoft.ivy.DependencyDescriptor; 26 import fr.jayasoft.ivy.Ivy; 27 import fr.jayasoft.ivy.ModuleDescriptor; 28 import fr.jayasoft.ivy.ModuleRevisionId; 29 import fr.jayasoft.ivy.repository.Resource; 30 import fr.jayasoft.ivy.repository.url.URLResource; 31 import fr.jayasoft.ivy.util.Message; 32 33 public abstract class AbstractModuleDescriptorParser implements ModuleDescriptorParser { 34 public ModuleDescriptor parseDescriptor(Ivy ivy, URL descriptorURL, boolean validate) throws ParseException , IOException { 35 return parseDescriptor(ivy, descriptorURL, new URLResource(descriptorURL), validate); 36 } 37 38 protected abstract static class AbstractParser extends DefaultHandler { 39 private static final String DEFAULT_CONF_MAPPING = "*->*"; 40 private String _defaultConf; private String _defaultConfMapping; private DefaultDependencyDescriptor _defaultConfMappingDescriptor; 45 private Resource _res; 46 private List _errors = new ArrayList (); 47 protected DefaultModuleDescriptor _md; 48 private ModuleDescriptorParser _parser; 49 50 protected AbstractParser(ModuleDescriptorParser parser) { 51 _parser = parser; 52 } 53 54 public ModuleDescriptorParser getModuleDescriptorParser() { 55 return _parser; 56 } 57 58 protected void checkErrors() throws ParseException { 59 if (!_errors.isEmpty()) { 60 throw new ParseException (_errors.toString(), 0); 61 } 62 } 63 64 protected void setResource(Resource res) { 65 _res = res; _md = new DefaultModuleDescriptor(_parser, res); 67 _md.setLastModified(getLastModified()); 68 } 69 70 protected Resource getResource() { 71 return _res; 72 } 73 74 protected String getDefaultConfMapping() { 75 return _defaultConfMapping; 76 } 77 78 protected void setDefaultConfMapping(String defaultConf) { 79 _defaultConfMapping = defaultConf; 80 } 81 82 83 protected void parseDepsConfs(String confs, DefaultDependencyDescriptor dd) { 84 parseDepsConfs(confs, dd, _defaultConfMapping != null); 85 } 86 protected void parseDepsConfs(String confs, DefaultDependencyDescriptor dd, boolean useDefaultMappingToGuessRightOperande) { 87 parseDepsConfs(confs, dd, useDefaultMappingToGuessRightOperande, true); 88 } 89 protected void parseDepsConfs(String confs, DefaultDependencyDescriptor dd, boolean useDefaultMappingToGuessRightOperande, boolean evaluateConditions) { 90 if (confs == null) { 91 return; 92 } 93 94 String [] conf = confs.split(";"); 95 parseDepsConfs(conf, dd, useDefaultMappingToGuessRightOperande, evaluateConditions); 96 } 97 protected void parseDepsConfs(String [] conf, DefaultDependencyDescriptor dd, boolean useDefaultMappingToGuessRightOperande) { 98 parseDepsConfs(conf, dd, useDefaultMappingToGuessRightOperande, true); 99 } 100 protected void parseDepsConfs(String [] conf, DefaultDependencyDescriptor dd, boolean useDefaultMappingToGuessRightOperande, boolean evaluateConditions) { 101 replaceConfigurationWildcards(_md); 102 for (int i = 0; i < conf.length; i++) { 103 String [] ops = conf[i].split("->"); 104 if (ops.length == 1) { 105 String [] modConfs = ops[0].split(","); 106 if (!useDefaultMappingToGuessRightOperande) { 107 for (int j = 0; j < modConfs.length; j++) { 108 dd.addDependencyConfiguration(modConfs[j].trim(), modConfs[j].trim()); 109 } 110 } else { 111 for (int j = 0; j < modConfs.length; j++) { 112 String [] depConfs = getDefaultConfMappingDescriptor().getDependencyConfigurations(modConfs[j]); 113 if (depConfs.length > 0) { 114 for (int k = 0; k < depConfs.length; k++) { 115 String mappedDependency = evaluateConditions ? evaluateCondition(depConfs[k].trim(), dd): depConfs[k].trim(); 116 if (mappedDependency != null) { 117 dd.addDependencyConfiguration(modConfs[j].trim(), mappedDependency); 118 } 119 } 120 } else { 121 dd.addDependencyConfiguration(modConfs[j].trim(), modConfs[j].trim()); 123 } 124 } 125 } 126 } else if (ops.length == 2) { 127 String [] modConfs = ops[0].split(","); 128 String [] depConfs = ops[1].split(","); 129 for (int j = 0; j < modConfs.length; j++) { 130 for (int k = 0; k < depConfs.length; k++) { 131 String mappedDependency = evaluateConditions ? evaluateCondition(depConfs[k].trim(), dd): depConfs[k].trim(); 132 if (mappedDependency != null) { 133 dd.addDependencyConfiguration(modConfs[j].trim(), mappedDependency); 134 } 135 } 136 } 137 } else { 138 addError("invalid conf "+conf[i]+" for "+dd.getDependencyRevisionId()); 139 } 140 } 141 142 if (_md.isMappingOverride()) { 143 addExtendingConfigurations(conf, dd, useDefaultMappingToGuessRightOperande); 144 } 145 } 146 156 private String evaluateCondition(String conf, DefaultDependencyDescriptor dd) { 157 if (conf.charAt(0) != '[') { 158 return conf; 159 } 160 161 int endConditionIndex = conf.indexOf(']'); 162 if (endConditionIndex == -1) { 163 addError("invalid conf " + conf + " for " + dd.getDependencyRevisionId()); 164 return null; 165 } 166 167 String condition = conf.substring(1, endConditionIndex); 168 169 int notEqualIndex = condition.indexOf("!="); 170 if (notEqualIndex == -1) { 171 int equalIndex = condition.indexOf('='); 172 if (equalIndex == -1) { 173 addError("invalid conf " + conf + " for " + dd.getDependencyRevisionId()); 174 return null; 175 } 176 177 String leftOp = condition.substring(0, equalIndex).trim(); 178 String rightOp = condition.substring(equalIndex + 1).trim(); 179 180 if (leftOp.equals("org") || leftOp.equals("organization")) { 182 leftOp = "organisation"; 183 } 184 185 String attrValue = dd.getAttribute(leftOp); 186 if (!rightOp.equals(attrValue)) { 187 return null; 188 } 189 } else { 190 String leftOp = condition.substring(0, notEqualIndex).trim(); 191 String rightOp = condition.substring(notEqualIndex + 2).trim(); 192 193 if (leftOp.equals("org") || leftOp.equals("organization")) { 195 leftOp = "organisation"; 196 } 197 198 String attrValue = dd.getAttribute(leftOp); 199 if (rightOp.equals(attrValue)) { 200 return null; 201 } 202 } 203 204 return conf.substring(endConditionIndex + 1); 205 } 206 207 private void addExtendingConfigurations(String [] confs, DefaultDependencyDescriptor dd, boolean useDefaultMappingToGuessRightOperande) { 208 for (int i = 0; i < confs.length; i++) { 209 addExtendingConfigurations(confs[i], dd, useDefaultMappingToGuessRightOperande); 210 } 211 } 212 private void addExtendingConfigurations(String conf, DefaultDependencyDescriptor dd, boolean useDefaultMappingToGuessRightOperande) { 213 Set configsToAdd = new HashSet (); 214 Configuration[] configs = _md.getConfigurations(); 215 for (int i = 0; i < configs.length; i++) { 216 String [] ext = configs[i].getExtends(); 217 for (int j = 0; j < ext.length; j++) { 218 if (conf.equals(ext[j])) { 219 String configName = configs[i].getName(); 220 configsToAdd.add(configName); 222 addExtendingConfigurations(configName, dd, useDefaultMappingToGuessRightOperande); 224 } 226 } 227 } 228 229 String [] confs = (String []) configsToAdd.toArray(new String [configsToAdd.size()]); 230 parseDepsConfs(confs, dd, useDefaultMappingToGuessRightOperande); 231 } 232 233 protected DependencyDescriptor getDefaultConfMappingDescriptor() { 234 if (_defaultConfMappingDescriptor == null) { 235 _defaultConfMappingDescriptor = new DefaultDependencyDescriptor(ModuleRevisionId.newInstance("", "", ""), false); 236 parseDepsConfs(_defaultConfMapping, _defaultConfMappingDescriptor, false, false); 237 } 238 return _defaultConfMappingDescriptor; 239 } 240 241 protected void addError(String msg) { 242 if (_res != null) { 243 _errors.add(msg+" in "+_res+"\n"); 244 } else { 245 _errors.add(msg+"\n"); 246 } 247 } 248 public void warning(SAXParseException ex) { 249 Message.warn("xml parsing: " + 250 getLocationString(ex)+": "+ 251 ex.getMessage()); 252 } 253 254 public void error(SAXParseException ex) { 255 addError("xml parsing: " + 256 getLocationString(ex)+": "+ 257 ex.getMessage()); 258 } 259 260 public void fatalError(SAXParseException ex) throws SAXException { 261 addError("[Fatal Error] "+ 262 getLocationString(ex)+": "+ 263 ex.getMessage()); 264 } 265 266 267 private String getLocationString(SAXParseException ex) { 268 StringBuffer str = new StringBuffer (); 269 270 String systemId = ex.getSystemId(); 271 if (systemId != null) { 272 int index = systemId.lastIndexOf('/'); 273 if (index != -1) 274 systemId = systemId.substring(index + 1); 275 str.append(systemId); 276 } else if (getResource() != null) { 277 str.append(getResource().toString()); 278 } 279 str.append(':'); 280 str.append(ex.getLineNumber()); 281 str.append(':'); 282 str.append(ex.getColumnNumber()); 283 284 return str.toString(); 285 286 } 288 protected String getDefaultConf() { 289 return _defaultConfMapping != null ? _defaultConfMapping : (_defaultConf != null ? _defaultConf : DEFAULT_CONF_MAPPING); 290 } 291 protected void setDefaultConf(String defaultConf) { 292 _defaultConf = defaultConf; 293 } 294 public ModuleDescriptor getModuleDescriptor() throws ParseException { 295 checkErrors(); 296 return _md; 297 } 298 protected Date getDefaultPubDate() { 299 return new Date (_md.getLastModified()); 300 } 301 protected long getLastModified() { 302 long last = getResource().getLastModified(); 303 if (last > 0) { 304 return last; 305 } else { 306 Message.debug("impossible to get date for "+getResource()+": using 'now'"); 307 return System.currentTimeMillis(); 308 } 309 } 310 311 private void replaceConfigurationWildcards(ModuleDescriptor md) { 312 Configuration[] configs = md.getConfigurations(); 313 for (int i = 0; i < configs.length; i++) { 314 configs[i].replaceWildcards(md); 315 } 316 } 317 318 } 319 } 320 | Popular Tags |