View Javadoc
1   /**
2    * Copyright (c) 2012-2022, jcabi.com
3    * All rights reserved.
4    *
5    * Redistribution and use in source and binary forms, with or without
6    * modification, are permitted provided that the following conditions
7    * are met: 1) Redistributions of source code must retain the above
8    * copyright notice, this list of conditions and the following
9    * disclaimer. 2) Redistributions in binary form must reproduce the above
10   * copyright notice, this list of conditions and the following
11   * disclaimer in the documentation and/or other materials provided
12   * with the distribution. 3) Neither the name of the jcabi.com nor
13   * the names of its contributors may be used to endorse or promote
14   * products derived from this software without specific prior written
15   * permission.
16   *
17   * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18   * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT
19   * NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
20   * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
21   * THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
22   * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
23   * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
24   * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
25   * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
26   * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
27   * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
28   * OF THE POSSIBILITY OF SUCH DAMAGE.
29   */
30  package com.jcabi.ssl.maven.plugin;
31  
32  import com.jcabi.aspects.Immutable;
33  import com.jcabi.aspects.Loggable;
34  import com.jcabi.log.Logger;
35  import java.io.File;
36  import java.io.IOException;
37  import java.util.Properties;
38  import javax.validation.constraints.NotNull;
39  import lombok.EqualsAndHashCode;
40  import lombok.ToString;
41  import org.apache.commons.io.FileUtils;
42  
43  /**
44   * Abstraction of {@code java.home/lib/security/cacerts} file.
45   *
46   * @author Yegor Bugayenko (yegor256@gmail.com)
47   * @version $Id: 9ca22d732718d9bd350beae2582a4f1d8ba759ac $
48   * @since 0.5
49   */
50  @Immutable
51  @ToString
52  @EqualsAndHashCode(of = "store")
53  final class Cacerts {
54  
55      /**
56       * Constant {@code javax.net.ssl.trustStore}.
57       */
58      public static final String TRUST = "javax.net.ssl.trustStore";
59  
60      /**
61       * Constant {@code javax.net.ssl.trustStorePassword}.
62       */
63      public static final String TRUST_PWD = "javax.net.ssl.trustStorePassword";
64  
65      /**
66       * Standard password of {@code cacerts} file.
67       */
68      public static final String STD_PWD = "changeit";
69  
70      /**
71       * New location of the trust store.
72       */
73      private final transient String store;
74  
75      /**
76       * Public ctor.
77       * @param file New location
78       * @throws IOException If fails
79       */
80      public Cacerts(@NotNull final File file) throws IOException {
81          this.store = file.getAbsolutePath();
82          final File prev = new File(
83              String.format(
84                  "%s/lib/security/cacerts",
85                  System.getProperty("java.home")
86              )
87          );
88          FileUtils.copyFile(prev, file);
89          Logger.info(
90              this,
91              "Existing cacerts '%s' copied to '%s' (%s)",
92              prev,
93              this.store,
94              FileUtils.byteCountToDisplaySize(this.store.length())
95          );
96      }
97  
98      /**
99       * Import existing keystore content into this trust store.
100      * @throws IOException If fails
101      */
102     public void imprt() throws IOException {
103         final File keystore = new File(System.getProperty(Keystore.KEY));
104         final String pwd = System.getProperty(Keystore.KEY_PWD);
105         new Keytool(new File(this.store), Cacerts.STD_PWD).imprt(keystore, pwd);
106         System.setProperty(Cacerts.TRUST, this.store);
107         System.setProperty(Cacerts.TRUST_PWD, Cacerts.STD_PWD);
108         Logger.info(
109             this,
110             "keyStore '%s' imported into trustStore '%s'",
111             keystore,
112             this.store
113         );
114     }
115 
116     /**
117      * Populate given properties with this truststore's path and password.
118      *
119      * @param props The properties
120      */
121     @Loggable(Loggable.DEBUG)
122     public void populate(final Properties props) {
123         final String[] names = new String[] {Cacerts.TRUST, Cacerts.TRUST_PWD};
124         for (final String name : names) {
125             final String value = System.getProperty(name);
126             if (value == null) {
127                 continue;
128             }
129             props.put(name, value);
130             Logger.info(
131                 this,
132                 "Maven property ${%s} set to '%s'",
133                 name,
134                 value
135             );
136         }
137     }
138 }