View Javadoc

1   /*
2    * Copyright (c) 2009 QOS.ch All rights reserved.
3    * 
4    * Permission is hereby granted, free of charge, to any person obtaining a copy
5    * of this software and associated documentation files (the "Software"), to deal
6    * in the Software without restriction, including without limitation the rights
7    * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8    * copies of the Software, and to permit persons to whom the Software is
9    * furnished to do so, subject to the following conditions:
10   * 
11   * The above copyright notice and this permission notice shall be included in
12   * all copies or substantial portions of the Software.
13   * 
14   * THE SOFTWARE IS PROVIDED "AS  IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15   * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16   * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17   * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18   * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19   * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20   * SOFTWARE.
21   */
22  package ch.qos.cal10n.plugins;
23  
24  import java.io.File;
25  import java.lang.reflect.Constructor;
26  import java.net.MalformedURLException;
27  import java.net.URL;
28  import java.text.MessageFormat;
29  import java.util.ArrayList;
30  import java.util.List;
31  import java.util.Locale;
32  import java.util.Set;
33  
34  import org.apache.maven.artifact.Artifact;
35  import org.apache.maven.artifact.repository.ArtifactRepository;
36  import org.apache.maven.plugin.AbstractMojo;
37  import org.apache.maven.plugin.MojoExecutionException;
38  import org.apache.maven.plugin.MojoFailureException;
39  
40  import ch.qos.cal10n.Cal10nConstants;
41  import ch.qos.cal10n.verifier.IMessageKeyVerifier;
42  
43  /**
44   * Verifies resources bundles in various locales against an enumType
45   * 
46   * @goal verify
47   * @phase verify
48   * @requiresProject true
49   */
50  public class VerifyMojo extends AbstractMojo {
51  
52    /**
53     * @parameter
54     * @required
55     */
56    private String[] enumTypes;
57  
58    /**
59     * The directory for compiled classes.
60     * 
61     * @parameter expression="${project.build.outputDirectory}"
62     * @required
63     * @readonly
64     */
65    private File outputDirectory;
66  
67    // direct dependencies of this project
68    /**
69     * 
70     * @parameter expression="${project.artifacts}"
71     * @required
72     * @readonly
73     */
74    private Set<Artifact> projectArtifacts;
75  
76    /**
77     * @parameter expression="${localRepository}"
78     * @required
79     * @readonly
80     * @since 1.0
81     */
82    private ArtifactRepository localRepository;
83  
84    public void execute() throws MojoExecutionException, MojoFailureException {
85  
86      if (enumTypes == null) {
87        throw new MojoFailureException(Cal10nConstants.MISSING_ENUM_TYPES_MSG);
88      }
89      for (String enumTypeAsStr : enumTypes) {
90        IMessageKeyVerifier imcv = getMessageKeyVerifierInstance(enumTypeAsStr);
91        getLog()
92            .info(
93                "Checking all resource bundles for enum type [" + enumTypeAsStr
94                    + "]");
95        checkAllLocales(imcv);
96      }
97    }
98  
99    public void checkAllLocales(IMessageKeyVerifier mcv)
100       throws MojoFailureException, MojoExecutionException {
101 
102     String enumClassAsStr = mcv.getEnumTypeAsStr();
103 
104     String[] localeNameArray = mcv.getLocaleNames();
105 
106     if (localeNameArray == null || localeNameArray.length == 0) {
107       String errMsg = MessageFormat.format(
108           Cal10nConstants.MISSING_LD_ANNOTATION_MESSAGE, enumClassAsStr);
109       getLog().error(errMsg);
110       throw new MojoFailureException(errMsg);
111     }
112 
113     boolean failure = false;
114     for (String localeName : localeNameArray) {
115       Locale locale = new Locale(localeName);
116       List<String> errorList = mcv.typeIsolatedVerify(locale);
117       if (errorList.size() == 0) {
118         String resouceBundleName = mcv.getBaseName();
119         getLog().info(
120             "SUCCESSFUL verification for resource bundle [" + resouceBundleName
121                 + "] for locale [" + locale + "]");
122       } else {
123         failure = true;
124         getLog().error(
125             "FAILURE during verification of resource bundle for locale ["
126                 + locale + "] enum class [" + enumClassAsStr + "]");
127         for (String s : errorList) {
128           getLog().error(s);
129         }
130       }
131     }
132     if (failure) {
133       throw new MojoFailureException("FAIL Verification of [" + enumClassAsStr
134           + "] keys.");
135     }
136   }
137 
138   IMessageKeyVerifier getMessageKeyVerifierInstance(String enumClassAsStr)
139       throws MojoExecutionException {
140     String errMsg = "Failed to instantiate MessageKeyVerifier class";
141     try {
142       ThisFirstClassLoader thisFirstClassLoader = (ThisFirstClassLoader) buildClassLoader();
143       Class<?> mkvClass = Class.forName(
144           Cal10nConstants.MessageKeyVerifier_FQCN, true, thisFirstClassLoader);
145       Constructor<?> mkvCons = mkvClass.getConstructor(String.class);
146       IMessageKeyVerifier imcv = (IMessageKeyVerifier) mkvCons
147           .newInstance(enumClassAsStr);
148       return imcv;
149     } catch (ClassNotFoundException e) {
150       throw new MojoExecutionException(errMsg, e);
151     } catch (NoClassDefFoundError e) {
152       throw new MojoExecutionException(errMsg, e);
153     } catch (Exception e) {
154       throw new MojoExecutionException(errMsg, e);
155     }
156   }
157 
158   ClassLoader buildClassLoader() {
159     ArrayList<URL> classpathURLList = new ArrayList<URL>();
160     classpathURLList.add(toURL(outputDirectory));
161     classpathURLList.addAll(getDirectDependencies());
162     ClassLoader parentCL = this.getClass().getClassLoader();
163     URL[] classpathURLArray = classpathURLList.toArray(new URL[] {});
164     return new ThisFirstClassLoader(classpathURLArray, parentCL);
165   }
166 
167   List<URL> getDirectDependencies() {
168     ArrayList<URL> urlList = new ArrayList<URL>();
169     for (Artifact a : projectArtifacts) {
170       String pathOfArtifact = localRepository.getBasedir() + "/"
171           + localRepository.pathOf(a);
172       File artifactAsFile = new File(pathOfArtifact);
173       if (!artifactAsFile.exists()) {
174         getLog()
175             .error("Artifact [" + artifactAsFile + "] could not be located");
176       }
177       try {
178         URL url = artifactAsFile.toURI().toURL();
179         urlList.add(url);
180       } catch (MalformedURLException e) {
181         getLog().info("Failed to build URL", e);
182       }
183     }
184     return urlList;
185   }
186 
187   URL toURL(File file) {
188     try {
189       return file.toURI().toURL();
190     } catch (MalformedURLException e) {
191       // this should never happen
192       getLog().error("Failed to convert file [" + file + "] to a URL", e);
193       return null;
194     }
195   }
196 
197 }