@@ -51,11 +51,13 @@ public abstract class AbstractGpgMojo extends AbstractMojo {
5151 private String agentSocketLocations ;
5252
5353 /**
54- * BC Signer only: The path of the exported key in TSK format, and probably passphrase protected. If relative,
55- * the file is resolved against Maven local repository root.
54+ * BC Signer only: The path of the exported key in
55+ * <a href="https://openpgp.dev/book/private_keys.html#transferable-secret-key-format">TSK format</a>,
56+ * and may be passphrase protected. If relative, the file is resolved against user home directory.
5657 * <p>
57- * <em>Note: it is not recommended to have sensitive files on disk or SCM repository, this mode is more to be used
58- * in local environment (workstations) or for testing purposes.</em>
58+ * <em>Note: it is not recommended to have sensitive files checked into SCM repository. Key file should reside on
59+ * developer workstation, outside of SCM tracked repository. For CI-like use cases you should set the
60+ * key material as env variable instead.</em>
5961 *
6062 * @since 3.2.0
6163 */
@@ -71,9 +73,11 @@ public abstract class AbstractGpgMojo extends AbstractMojo {
7173 private String keyFingerprint ;
7274
7375 /**
74- * BC Signer only: The env variable name where the GnuPG key is set. The default value is {@code MAVEN_GPG_KEY}.
76+ * BC Signer only: The env variable name where the GnuPG key is set.
7577 * To use BC Signer you must provide GnuPG key, as it does not use GnuPG home directory to extract/find the
76- * key (while it does use GnuPG Agent to ask for password in interactive mode).
78+ * key (while it does use GnuPG Agent to ask for password in interactive mode). The key should be in
79+ * <a href="https://openpgp.dev/book/private_keys.html#transferable-secret-key-format">TSK format</a> and may
80+ * be passphrase protected.
7781 *
7882 * @since 3.2.0
7983 */
@@ -82,16 +86,16 @@ public abstract class AbstractGpgMojo extends AbstractMojo {
8286
8387 /**
8488 * BC Signer only: The env variable name where the GnuPG key fingerprint is set, if the provided keyring contains
85- * multiple keys. The default value is {@code MAVEN_GPG_KEY_FINGERPRINT}.
89+ * multiple keys.
8690 *
8791 * @since 3.2.0
8892 */
8993 @ Parameter (property = "gpg.keyFingerprintEnvName" , defaultValue = DEFAULT_ENV_MAVEN_GPG_FINGERPRINT )
9094 private String keyFingerprintEnvName ;
9195
9296 /**
93- * The env variable name where the GnuPG passphrase is set. The default value is {@code MAVEN_GPG_PASSPHRASE}.
94- * This is the recommended way to pass passphrase for signing in batch mode execution of Maven.
97+ * The env variable name where the GnuPG passphrase is set. This is the recommended way to pass passphrase
98+ * for signing in batch mode execution of Maven.
9599 *
96100 * @since 3.2.0
97101 */
@@ -109,23 +113,25 @@ public abstract class AbstractGpgMojo extends AbstractMojo {
109113
110114 /**
111115 * The passphrase to use when signing. If not given, look up the value under Maven
112- * settings using server id at 'passphraseServerKey' configuration. <em>Do not use this parameter, if set, the
113- * plugin will fail . Passphrase should be provided only via gpg-agent (interactive) or via env variable
114- * (non-interactive) .</em>
116+ * settings using server id at 'passphraseServerKey' configuration. <em>Do not use this parameter, it leaks
117+ * sensitive data . Passphrase should be provided only via gpg-agent or via env variable.
118+ * If parameter {@link #bestPractices} set to {@code true}, plugin fails when this parameter is configured .</em>
115119 *
116- * @deprecated Do not use this configuration, plugin will fail if set.
120+ * @deprecated Do not use this configuration, it may leak sensitive information. Rely on gpg-agent or env
121+ * variables instead.
117122 **/
118123 @ Deprecated
119124 @ Parameter (property = "gpg.passphrase" )
120125 private String passphrase ;
121126
122127 /**
123- * Server id to lookup the passphrase under Maven settings. <em>Do not use this parameter, if set, the
124- * plugin will fail . Passphrase should be provided only via gpg-agent (interactive) or via env variable
125- * (non-interactive) .</em>
128+ * Server id to lookup the passphrase under Maven settings. <em>Do not use this parameter, it leaks
129+ * sensitive data . Passphrase should be provided only via gpg-agent or via env variable.
130+ * If parameter {@link #bestPractices} set to {@code true}, plugin fails when this parameter is configured .</em>
126131 *
127132 * @since 1.6
128- * @deprecated Do not use this configuration, plugin will fail if set.
133+ * @deprecated Do not use this configuration, it may leak sensitive information. Rely on gpg-agent or env
134+ * variables instead.
129135 **/
130136 @ Deprecated
131137 @ Parameter (property = "gpg.passphraseServerId" )
@@ -138,23 +144,22 @@ public abstract class AbstractGpgMojo extends AbstractMojo {
138144 private String keyname ;
139145
140146 /**
141- * GPG Signer only: Passes <code>--use-agent</code> or <code>--no-use-agent</code> to gpg. If using an agent, the
142- * passphrase is optional as the agent will provide it. For gpg2, specify true as --no-use-agent was removed in
143- * gpg2 and doesn't ask for a passphrase anymore. Deprecated, and better to rely on session "interactive" setting
144- * (if interactive, agent will be used, otherwise not).
145- *
146- * @deprecated
147+ * All signers: whether gpg-agent is allowed to be used or not. If enabled, passphrase is optional, as agent may
148+ * provide it. Have to be noted, that in "batch" mode, gpg-agent will be prevented to pop up pinentry
149+ * dialogue, hence best is to "prime" the agent caches beforehand.
150+ * <p>
151+ * GPG Signer: Passes <code>--use-agent</code> or <code>--no-use-agent</code> option to gpg if it is version 2.1
152+ * or older. Otherwise, will use an agent. In non-interactive mode gpg options are appended with
153+ * <code>--pinentry-mode error</code>, preventing gpg agent to pop up pinentry dialogue. Agent will be able to
154+ * hand over only cached passwords.
155+ * <p>
156+ * BC Signer: Allows signer to communicate with gpg agent. In non-interactive mode it uses
157+ * <code>--no-ask</code> option with the <code>GET_PASSPHRASE</code> function. Agent will be able to hand over
158+ * only cached passwords.
147159 */
148- @ Deprecated
149160 @ Parameter (property = "gpg.useagent" , defaultValue = "true" )
150161 private boolean useAgent ;
151162
152- /**
153- * Detect is session interactive or not.
154- */
155- @ Parameter (defaultValue = "${settings.interactiveMode}" , readonly = true )
156- private boolean interactive ;
157-
158163 /**
159164 * GPG Signer only: The path to the GnuPG executable to use for artifact signing. Defaults to either "gpg" or
160165 * "gpg.exe" depending on the operating system.
@@ -182,7 +187,7 @@ public abstract class AbstractGpgMojo extends AbstractMojo {
182187 * ‘private-keys-v1.d’ directory below the GnuPG home directory.
183188 *
184189 * @since 1.2
185- * @deprecated
190+ * @deprecated Obsolete option since GnuPG 2.1 version.
186191 */
187192 @ Deprecated
188193 @ Parameter (property = "gpg.secretKeyring" )
@@ -198,7 +203,7 @@ public abstract class AbstractGpgMojo extends AbstractMojo {
198203 * ‘pubring.kbx’ file below the GnuPG home directory.
199204 *
200205 * @since 1.2
201- * @deprecated
206+ * @deprecated Obsolete option since GnuPG 2.1 version.
202207 */
203208 @ Deprecated
204209 @ Parameter (property = "gpg.publicKeyring" )
@@ -224,7 +229,7 @@ public abstract class AbstractGpgMojo extends AbstractMojo {
224229 private boolean skip ;
225230
226231 /**
227- * Sets the arguments to be passed to gpg. Example:
232+ * GPG Signer only: Sets the arguments to be passed to gpg. Example:
228233 *
229234 * <pre>
230235 * <gpgArguments>
@@ -256,32 +261,32 @@ public abstract class AbstractGpgMojo extends AbstractMojo {
256261 // === Deprecated stuff
257262
258263 /**
259- * Switch to lax plugin enforcement of "best practices". If set to {@code false}, plugin will retain all the
260- * backward compatibility regarding getting secrets (but will warn). By default, plugin enforces "best practices"
261- * and in such cases plugin fails.
264+ * Switch to improve plugin enforcement of "best practices". If set to {@code false}, plugin retains all the
265+ * backward compatibility regarding getting secrets (but will warn). If set to {@code true}, plugin will fail
266+ * if any "bad practices" regarding sensitive data handling are detected. By default, plugin remains backward
267+ * compatible (this flag is {@code false}). Somewhere in the future, when this parameter enabling transitioning
268+ * from older plugin versions is removed, the logic using this flag will be modified like it is set to {@code true}.
269+ * It is warmly advised to configure this parameter to {@code true} and migrate project and user environment
270+ * regarding how sensitive information is stored.
262271 *
263272 * @since 3.2.0
264- * @deprecated
265273 */
266- @ Deprecated
267- @ Parameter (property = "gpg.bestPractices" , defaultValue = "true" )
274+ @ Parameter (property = "gpg.bestPractices" , defaultValue = "false" )
268275 private boolean bestPractices ;
269276
270277 /**
271278 * Current user system settings for use in Maven.
272279 *
273280 * @since 1.6
274- * @deprecated
275281 */
276- @ Deprecated
277282 @ Parameter (defaultValue = "${settings}" , readonly = true , required = true )
278283 private Settings settings ;
279284
280285 /**
281286 * Maven Security Dispatcher.
282287 *
283288 * @since 1.6
284- * @deprecated
289+ * @deprecated Provides quasi-encryption, should be avoided.
285290 */
286291 @ Deprecated
287292 @ Component
@@ -310,7 +315,7 @@ private void logBestPracticeWarning(String source) {
310315 getLog ().warn ("W A R N I N G" );
311316 getLog ().warn ("" );
312317 getLog ().warn ("Do not store passphrase in any file (disk or SCM repository)," );
313- getLog ().warn ("instead rely on GnuPG agent in interactive sessions, or provide passphrase in " );
318+ getLog ().warn ("instead rely on GnuPG agent or provide passphrase in " );
314319 getLog ().warn (passphraseEnvName + " environment variable for batch mode." );
315320 getLog ().warn ("" );
316321 getLog ().warn ("Sensitive content loaded from " + source );
@@ -334,7 +339,7 @@ protected AbstractGpgSigner newSigner(MavenProject mavenProject) throws MojoFail
334339 }
335340
336341 signer .setLog (getLog ());
337- signer .setInteractive (interactive );
342+ signer .setInteractive (settings . isInteractiveMode () );
338343 signer .setKeyName (keyname );
339344 signer .setUseAgent (useAgent );
340345 signer .setHomeDirectory (homedir );
@@ -371,13 +376,6 @@ protected AbstractGpgSigner newSigner(MavenProject mavenProject) throws MojoFail
371376 }
372377 }
373378 }
374-
375- // gpg signer: always failed if no passphrase and no agent and not interactive: retain this behavior
376- // bc signer: it is optimistic, will fail during prepare() only IF key is passphrase protected
377- if (GpgSigner .NAME .equals (this .signer ) && null == passphrase && !useAgent && !interactive ) {
378- throw new MojoFailureException ("Cannot obtain passphrase in batch mode" );
379- }
380-
381379 signer .prepare ();
382380
383381 return signer ;
@@ -419,7 +417,7 @@ public String getPassphrase(MavenProject project) {
419417 pass = prj2 .getProperties ().getProperty (GPG_PASSPHRASE );
420418 }
421419 }
422- if (project != null ) {
420+ if (project != null && pass != null ) {
423421 findReactorProject (project ).getProperties ().setProperty (GPG_PASSPHRASE , pass );
424422 }
425423 return pass ;
0 commit comments