View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  package org.apache.maven.shared.release.transform.jdom2;
20  
21  import java.util.ArrayList;
22  import java.util.Collections;
23  import java.util.List;
24  import java.util.Properties;
25  
26  import org.apache.maven.model.Build;
27  import org.apache.maven.model.Dependency;
28  import org.apache.maven.model.DependencyManagement;
29  import org.apache.maven.model.Model;
30  import org.apache.maven.model.Parent;
31  import org.apache.maven.model.Profile;
32  import org.apache.maven.model.Reporting;
33  import org.apache.maven.model.Scm;
34  import org.apache.maven.shared.release.config.ReleaseDescriptor;
35  import org.apache.maven.shared.release.util.CiFriendlyVersion;
36  import org.jdom2.Document;
37  import org.jdom2.Element;
38  import org.jdom2.Text;
39  
40  /**
41   * JDOM2 implementation of poms PROJECT element
42   *
43   * @author Robert Scholte
44   * @since 3.0
45   */
46  public class JDomModel extends Model {
47      private final Element project;
48  
49      private final JDomModelBase modelBase;
50  
51      /**
52       * The ReleaseDescriptor after a commit performed
53       *
54       */
55      private final ReleaseDescriptor releaseDescriptor;
56  
57      /**
58       * <p>Constructor for JDomModel.</p>
59       *
60       * @param document a {@link org.jdom2.Document} object
61       */
62      public JDomModel(Document document, ReleaseDescriptor releaseDescriptor) {
63          this(document.getRootElement(), releaseDescriptor);
64      }
65  
66      /**
67       * <p>Constructor for JDomModel.</p>
68       *
69       * @param project a {@link org.jdom2.Element} object
70       */
71      public JDomModel(Element project, ReleaseDescriptor releaseDescriptor) {
72          this.project = project;
73          this.releaseDescriptor = releaseDescriptor;
74          this.modelBase = new JDomModelBase(project);
75      }
76  
77      @Override
78      public Build getBuild() {
79          return modelBase.getBuild();
80      }
81  
82      @Override
83      public List<Dependency> getDependencies() {
84          return modelBase.getDependencies();
85      }
86  
87      @Override
88      public DependencyManagement getDependencyManagement() {
89          return modelBase.getDependencyManagement();
90      }
91  
92      @Override
93      public Parent getParent() {
94          Element elm = getParentElement();
95          if (elm == null) {
96              return null;
97          } else {
98              // this way scm setters change DOM tree immediately
99              return new JDomParent(elm);
100         }
101     }
102 
103     private Element getParentElement() {
104         return project.getChild("parent", project.getNamespace());
105     }
106 
107     @Override
108     public List<Profile> getProfiles() {
109         Element profilesElm = project.getChild("profiles", project.getNamespace());
110         if (profilesElm == null) {
111             return Collections.emptyList();
112         } else {
113             List<Element> profileElms = profilesElm.getChildren("profile", project.getNamespace());
114 
115             List<Profile> profiles = new ArrayList<>(profileElms.size());
116 
117             for (Element profileElm : profileElms) {
118                 profiles.add(new JDomProfile(profileElm));
119             }
120 
121             return profiles;
122         }
123     }
124 
125     @Override
126     public Properties getProperties() {
127         Element properties = project.getChild("properties", project.getNamespace());
128 
129         if (properties == null) {
130             return null;
131         } else {
132             return new JDomProperties(properties);
133         }
134     }
135 
136     @Override
137     public Reporting getReporting() {
138         Element reporting = project.getChild("reporting", project.getNamespace());
139 
140         if (reporting == null) {
141             return null;
142         } else {
143             return new JDomReporting(reporting);
144         }
145     }
146 
147     @Override
148     public void setScm(Scm scm) {
149         if (scm == null) {
150             JDomUtils.rewriteElement("scm", null, project, project.getNamespace());
151         } else {
152             Element scmRoot = new Element("scm");
153             scmRoot.addContent("\n  ");
154 
155             // Write current values to JDOM2 tree
156             Scm jdomScm = new JDomScm(scmRoot);
157             jdomScm.setConnection(scm.getConnection());
158             jdomScm.setDeveloperConnection(scm.getDeveloperConnection());
159             jdomScm.setTag(scm.getTag());
160             jdomScm.setUrl(scm.getUrl());
161 
162             project.addContent("\n  ").addContent(scmRoot).addContent("\n");
163         }
164     }
165 
166     @Override
167     public Scm getScm() {
168         Element elm = project.getChild("scm", project.getNamespace());
169         if (elm == null) {
170             return null;
171         } else {
172             // this way scm setters change DOM tree immediately
173             return new JDomScm(elm);
174         }
175     }
176 
177     @Override
178     public void setVersion(String version) {
179         Element versionElement = project.getChild("version", project.getNamespace());
180 
181         String parentVersion;
182         Element parent = getParentElement();
183         if (parent != null) {
184             parentVersion = parent.getChildTextTrim("version", project.getNamespace());
185         } else {
186             parentVersion = null;
187         }
188 
189         if (versionElement == null) {
190             // never add version when parent references CI friendly property
191             if (!(parentVersion != null && CiFriendlyVersion.isCiFriendlyVersion(parentVersion))
192                     && !version.equals(parentVersion)) {
193                 // we will add this after artifactId, since it was missing but different from the inherited version
194                 Element artifactIdElement = project.getChild("artifactId", project.getNamespace());
195                 int index = project.indexOf(artifactIdElement);
196 
197                 versionElement = new Element("version", project.getNamespace());
198                 versionElement.setText(version);
199                 project.addContent(index + 1, new Text("\n  "));
200                 project.addContent(index + 2, versionElement);
201             }
202         } else {
203             if (CiFriendlyVersion.isCiFriendlyVersion(versionElement.getTextNormalize())) {
204                 // try to rewrite property if CI friendly expression is used
205                 CiFriendlyVersion.rewriteCiFriendlyProperties(version, getProperties(), releaseDescriptor);
206             } else {
207                 JDomUtils.rewriteValue(versionElement, version);
208             }
209         }
210     }
211 }