1 package org.apache.maven.plugin.jira;
2
3 /*
4 * Licensed to the Apache Software Foundation (ASF) under one
5 * or more contributor license agreements. See the NOTICE file
6 * distributed with this work for additional information
7 * regarding copyright ownership. The ASF licenses this file
8 * to you under the Apache License, Version 2.0 (the
9 * "License"); you may not use this file except in compliance
10 * with the License. You may obtain a copy of the License at
11 *
12 * http://www.apache.org/licenses/LICENSE-2.0
13 *
14 * Unless required by applicable law or agreed to in writing,
15 * software distributed under the License is distributed on an
16 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17 * KIND, either express or implied. See the License for the
18 * specific language governing permissions and limitations
19 * under the License.
20 */
21
22 import org.apache.maven.plugin.MojoExecutionException;
23 import org.apache.maven.plugin.issues.Issue;
24 import org.apache.maven.plugin.issues.IssueUtils;
25 import org.apache.maven.plugin.logging.Log;
26 import org.apache.maven.project.MavenProject;
27 import org.apache.maven.settings.Proxy;
28 import org.apache.maven.settings.Settings;
29 import org.apache.maven.wagon.proxy.ProxyInfo;
30
31 import java.io.File;
32 import java.net.MalformedURLException;
33 import java.net.URL;
34 import java.util.List;
35
36 /**
37 * Abstract API, more or less, to retrieving issue information from JIRA. Intended to have subclasses for the old (RSS)
38 * and new (REST) ways of doing things.
39 *
40 * @author mfranken@xebia.com
41 * @author jruiz@exist.com
42 * @version $Id: AbstractJiraDownloader.java 1685894 2015-06-16 19:29:09Z khmarbaise $
43 */
44 public abstract class AbstractJiraDownloader
45 {
46 protected static final String UTF_8 = "UTF-8";
47
48 /** Log for debug output. */
49 protected Log log;
50
51 /** Output file for xml document. */
52 protected File output;
53
54 /** The maximum number of entries to show. */
55 protected int nbEntriesMax;
56
57 /** The filter to apply to query to JIRA. */
58 protected String filter;
59
60 /** Ids of fix versions to show, as comma separated string. */
61 protected String fixVersionIds;
62
63 /** Ids of status to show, as comma separated string. */
64 protected String statusIds;
65
66 /** Ids of resolution to show, as comma separated string. */
67 protected String resolutionIds;
68
69 /** Ids of priority to show, as comma separated string. */
70 protected String priorityIds;
71
72 /** The component to show. */
73 protected String component;
74
75 /** Ids of types to show, as comma separated string. */
76 protected String typeIds;
77
78 /** Column names to sort by, as comma separated string. */
79 protected String sortColumnNames;
80
81 /** The username to log into JIRA. */
82 protected String jiraUser;
83
84 /** The password to log into JIRA. */
85 protected String jiraPassword;
86
87 /** The username to log into webserver. */
88 protected String webUser;
89
90 /** The password to log into webserver. */
91 protected String webPassword;
92
93 /** The maven project. */
94 protected MavenProject project;
95
96 /** The maven settings. */
97 protected Settings settings;
98
99 /**
100 * Use JQL, JIRA query language, instead of URL parameter based queries. Note that this is down here to make it
101 * easier for the mojo to deal with both new and old flavors.
102 */
103 protected boolean useJql;
104
105 /** Filter the JIRA query based on the current version */
106 protected boolean onlyCurrentVersion;
107
108 /** The versionPrefix to apply to the POM version */
109 protected String versionPrefix;
110
111 /** The pattern used to parse dates from the JIRA xml file. */
112 protected String jiraDatePattern;
113
114 protected String proxyHost;
115
116 protected int proxyPort;
117
118 protected String proxyUser;
119
120 protected String proxyPass;
121
122 protected int connectionTimeout;
123
124 protected int receiveTimout;
125
126 /**
127 * Execute the query on the JIRA server.
128 *
129 * @throws Exception on error
130 */
131 public abstract void doExecute()
132 throws Exception;
133
134 /**
135 * Check to see if we think that JIRA authentication is needed.
136 *
137 * @return <code>true</code> if jiraUser and jiraPassword are set, otherwise <code>false</code>
138 */
139 protected boolean isJiraAuthenticationConfigured()
140 {
141 return ( jiraUser != null ) && ( jiraUser.length() > 0 ) && ( jiraPassword != null );
142 }
143
144 protected void getProxyInfo( String jiraUrl )
145 {
146 // see whether there is any proxy defined in maven
147 Proxy proxy = null;
148
149 if ( project == null )
150 {
151 getLog().error( "No project set. No proxy info available." );
152
153 return;
154 }
155
156 if ( settings != null )
157 {
158 proxy = settings.getActiveProxy();
159 }
160
161 if ( proxy != null )
162 {
163
164 ProxyInfo proxyInfo = new ProxyInfo();
165 proxyInfo.setNonProxyHosts( proxy.getNonProxyHosts() );
166
167 // Get the host out of the JIRA URL
168 URL url = null;
169 try
170 {
171 url = new URL( jiraUrl );
172 }
173 catch ( MalformedURLException e )
174 {
175 getLog().error( "Invalid JIRA URL: " + jiraUrl + ". " + e.getMessage() );
176 }
177 String jiraHost = null;
178 if ( url != null )
179 {
180 jiraHost = url.getHost();
181 }
182
183 // Validation of proxy method copied from org.apache.maven.wagon.proxy.ProxyUtils.
184 // @todo Can use original when maven-changes-plugin requires a more recent version of Maven
185
186 // if ( ProxyUtils.validateNonProxyHosts( proxyInfo, jiraHost ) )
187 if ( JiraHelper.validateNonProxyHosts( proxyInfo, jiraHost ) )
188 {
189 return;
190 }
191
192 proxyHost = settings.getActiveProxy().getHost();
193 proxyPort = settings.getActiveProxy().getPort();
194 proxyUser = settings.getActiveProxy().getUsername();
195 proxyPass = settings.getActiveProxy().getPassword();
196 }
197 }
198
199 /**
200 * Override this method if you need to get issues for a specific Fix For.
201 *
202 * @return A Fix For id or <code>null</code> if you don't have that need
203 */
204 protected String getFixFor()
205 {
206 if ( onlyCurrentVersion && useJql )
207 {
208 // Let JIRA do the filtering of the current version instead of the JIRA mojo.
209 // This way JIRA returns less issues and we do not run into the "nbEntriesMax" limit that easily.
210
211 String version = ( versionPrefix == null ? "" : versionPrefix ) + project.getVersion();
212
213 // Remove "-SNAPSHOT" from the end of the version, if it's there
214 if ( version.endsWith( IssueUtils.SNAPSHOT_SUFFIX ) )
215 {
216 return version.substring( 0, version.length() - IssueUtils.SNAPSHOT_SUFFIX.length() );
217 }
218 else
219 {
220 return version;
221 }
222 }
223 else
224 {
225 return null;
226 }
227 }
228
229 public abstract List<Issue> getIssueList()
230 throws MojoExecutionException;
231
232 public void setJiraDatePattern( String jiraDatePattern )
233 {
234 this.jiraDatePattern = jiraDatePattern;
235 }
236
237 /**
238 * Set the output file for the log.
239 *
240 * @param thisOutput the output file
241 */
242 public void setOutput( File thisOutput )
243 {
244 this.output = thisOutput;
245 }
246
247 public File getOutput()
248 {
249 return this.output;
250 }
251
252 /**
253 * Sets the project.
254 *
255 * @param thisProject The project to set
256 */
257 public void setMavenProject( Object thisProject )
258 {
259 this.project = (MavenProject) thisProject;
260 }
261
262 /**
263 * Sets the maximum number of Issues to show.
264 *
265 * @param nbEntries The maximum number of Issues
266 */
267 public void setNbEntries( final int nbEntries )
268 {
269 nbEntriesMax = nbEntries;
270 }
271
272 /**
273 * Sets the statusIds.
274 *
275 * @param thisStatusIds The id(s) of the status to show, as comma separated string
276 */
277 public void setStatusIds( String thisStatusIds )
278 {
279 statusIds = thisStatusIds;
280 }
281
282 /**
283 * Sets the priorityIds.
284 *
285 * @param thisPriorityIds The id(s) of the priority to show, as comma separated string
286 */
287 public void setPriorityIds( String thisPriorityIds )
288 {
289 priorityIds = thisPriorityIds;
290 }
291
292 /**
293 * Sets the resolutionIds.
294 *
295 * @param thisResolutionIds The id(s) of the resolution to show, as comma separated string
296 */
297 public void setResolutionIds( String thisResolutionIds )
298 {
299 resolutionIds = thisResolutionIds;
300 }
301
302 /**
303 * Sets the sort column names.
304 *
305 * @param thisSortColumnNames The column names to sort by
306 */
307 public void setSortColumnNames( String thisSortColumnNames )
308 {
309 sortColumnNames = thisSortColumnNames;
310 }
311
312 /**
313 * Sets the password for authentication against the webserver.
314 *
315 * @param thisWebPassword The password of the webserver
316 */
317 public void setWebPassword( String thisWebPassword )
318 {
319 this.webPassword = thisWebPassword;
320 }
321
322 /**
323 * Sets the username for authentication against the webserver.
324 *
325 * @param thisWebUser The username of the webserver
326 */
327 public void setWebUser( String thisWebUser )
328 {
329 this.webUser = thisWebUser;
330 }
331
332 /**
333 * Sets the password to log into a secured JIRA.
334 *
335 * @param thisJiraPassword The password for JIRA
336 */
337 public void setJiraPassword( final String thisJiraPassword )
338 {
339 this.jiraPassword = thisJiraPassword;
340 }
341
342 /**
343 * Sets the username to log into a secured JIRA.
344 *
345 * @param thisJiraUser The username for JIRA
346 */
347 public void setJiraUser( String thisJiraUser )
348 {
349 this.jiraUser = thisJiraUser;
350 }
351
352 /**
353 * Sets the filter to apply to query to JIRA.
354 *
355 * @param thisFilter The filter to query JIRA
356 */
357 public void setFilter( String thisFilter )
358 {
359 this.filter = thisFilter;
360 }
361
362 /**
363 * Sets the component(s) to apply to query JIRA.
364 *
365 * @param theseComponents The id(s) of components to show, as comma separated string
366 */
367 public void setComponent( String theseComponents )
368 {
369 this.component = theseComponents;
370 }
371
372 /**
373 * Sets the fix version id(s) to apply to query JIRA.
374 *
375 * @param theseFixVersionIds The id(s) of fix versions to show, as comma separated string
376 */
377 public void setFixVersionIds( String theseFixVersionIds )
378 {
379 this.fixVersionIds = theseFixVersionIds;
380 }
381
382 /**
383 * Sets the typeIds.
384 *
385 * @param theseTypeIds The id(s) of the types to show, as comma separated string
386 */
387 public void setTypeIds( String theseTypeIds )
388 {
389 typeIds = theseTypeIds;
390 }
391
392 public void setLog( Log log )
393 {
394 this.log = log;
395 }
396
397 protected Log getLog()
398 {
399 return log;
400 }
401
402 public void setSettings( Settings settings )
403 {
404 this.settings = settings;
405 }
406
407 public boolean isUseJql()
408 {
409 return useJql;
410 }
411
412 public void setUseJql( boolean useJql )
413 {
414 this.useJql = useJql;
415 }
416
417 public boolean isOnlyCurrentVersion()
418 {
419 return onlyCurrentVersion;
420 }
421
422 public void setOnlyCurrentVersion( boolean onlyCurrentVersion )
423 {
424 this.onlyCurrentVersion = onlyCurrentVersion;
425 }
426
427 public String getVersionPrefix()
428 {
429 return versionPrefix;
430 }
431
432 public void setVersionPrefix( String versionPrefix )
433 {
434 this.versionPrefix = versionPrefix;
435 }
436
437 public void setConnectionTimeout( int connectionTimeout )
438 {
439 this.connectionTimeout = connectionTimeout;
440 }
441
442 public void setReceiveTimout( int receiveTimout )
443 {
444 this.receiveTimout = receiveTimout;
445 }
446 }