You are viewing a plain text version of this content. The canonical link for it is here.
Posted to scm@geronimo.apache.org by am...@apache.org on 2005/11/12 18:52:03 UTC

svn commit: r332802 - in /geronimo/trunk/modules: assembly/ deploy-tool/ deploy-tool/src/java/org/apache/geronimo/deployment/cli/ util/ util/src/java/org/apache/geronimo/util/ util/src/test/ util/src/test/org/ util/src/test/org/apache/ util/src/test/or...

Author: ammulder
Date: Sat Nov 12 09:51:49 2005
New Revision: 332802

URL: http://svn.apache.org/viewcvs?rev=332802&view=rev
Log:
Lets you save your login information for the deploy tool (GERONIMO-766)
Use: java -jar bin/deployer.jar login

Added:
    geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/CommandLogin.java   (with props)
    geronimo/trunk/modules/util/src/java/org/apache/geronimo/util/SimpleEncryption.java   (with props)
    geronimo/trunk/modules/util/src/test/
    geronimo/trunk/modules/util/src/test/org/
    geronimo/trunk/modules/util/src/test/org/apache/
    geronimo/trunk/modules/util/src/test/org/apache/geronimo/
    geronimo/trunk/modules/util/src/test/org/apache/geronimo/util/
    geronimo/trunk/modules/util/src/test/org/apache/geronimo/util/SimpleEncryptionTest.java   (with props)
Modified:
    geronimo/trunk/modules/assembly/project.xml
    geronimo/trunk/modules/deploy-tool/project.xml
    geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/DeployTool.java
    geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/ServerConnection.java
    geronimo/trunk/modules/util/   (props changed)

Modified: geronimo/trunk/modules/assembly/project.xml
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/assembly/project.xml?rev=332802&r1=332801&r2=332802&view=diff
==============================================================================
--- geronimo/trunk/modules/assembly/project.xml (original)
+++ geronimo/trunk/modules/assembly/project.xml Sat Nov 12 09:51:49 2005
@@ -470,6 +470,8 @@
             <artifactId>geronimo-util</artifactId>
             <version>${pom.currentVersion}</version>
             <properties>
+                <lib>true</lib>
+                <deploy>true</deploy>
                 <repository>true</repository>
             </properties>
         </dependency>

Modified: geronimo/trunk/modules/deploy-tool/project.xml
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/deploy-tool/project.xml?rev=332802&r1=332801&r2=332802&view=diff
==============================================================================
--- geronimo/trunk/modules/deploy-tool/project.xml (original)
+++ geronimo/trunk/modules/deploy-tool/project.xml Sat Nov 12 09:51:49 2005
@@ -81,6 +81,12 @@
 
         <dependency>
             <groupId>geronimo</groupId>
+            <artifactId>geronimo-util</artifactId>
+            <version>${pom.currentVersion}</version>
+        </dependency>
+
+        <dependency>
+            <groupId>geronimo</groupId>
             <artifactId>geronimo-system</artifactId>
             <version>${pom.currentVersion}</version>
         </dependency>

Added: geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/CommandLogin.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/CommandLogin.java?rev=332802&view=auto
==============================================================================
--- geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/CommandLogin.java (added)
+++ geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/CommandLogin.java Sat Nov 12 09:51:49 2005
@@ -0,0 +1,95 @@
+/**
+ *
+ * Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+
+package org.apache.geronimo.deployment.cli;
+
+import org.apache.geronimo.common.DeploymentException;
+import org.apache.geronimo.util.SimpleEncryption;
+
+import java.io.PrintWriter;
+import java.io.File;
+import java.io.InputStream;
+import java.io.FileInputStream;
+import java.io.BufferedInputStream;
+import java.io.OutputStream;
+import java.io.BufferedOutputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Properties;
+import javax.enterprise.deploy.spi.TargetModuleID;
+import javax.enterprise.deploy.spi.DeploymentManager;
+import javax.enterprise.deploy.spi.Target;
+import javax.enterprise.deploy.spi.exceptions.TargetException;
+import javax.enterprise.deploy.spi.status.ProgressObject;
+
+/**
+ * The CLI deployer logic to start.
+ *
+ * @version $Rev: 53762 $ $Date: 2004-10-04 18:54:53 -0400 (Mon, 04 Oct 2004) $
+ */
+public class CommandLogin extends AbstractCommand {
+    public CommandLogin() {
+        super("login", "1. Common Commands", "",
+                "Saves the username and password for this connection to the "+
+                "file .geronimo-deployer in the current user's home directory.  " +
+                "Future connections to the same server will try to use this "+
+                "saved authentication information instead of prompting where " +
+                "possible.  This information is saved separately per connection " +
+                "URL, so you can specify --url on the command line to save a" +
+                "login to a different server.\n" +
+                "WARNING: while the login information is not saved in " +
+                "clear text, it is not secure either.  If you want to " +
+                "save the authentication securely, you should change the " +
+                ".geronimo-deployer file so that nobody else can read or " +
+                "write it.");
+    }
+
+    public CommandLogin(String command, String group, String helpArgumentList, String helpText) {
+        super(command, group, helpArgumentList, helpText);
+    }
+
+    public void execute(PrintWriter out, ServerConnection connection, String[] args) throws DeploymentException {
+        if(!connection.isOnline()) {
+            throw new DeploymentException("This command cannot be run unless connecting to a running server.  Specify --url if server is not running on the default port on localhost.");
+        }
+        try {
+            File authFile = new File(System.getProperty("user.home"), ".geronimo-deployer");
+            if(!authFile.exists()) {
+                if(!authFile.createNewFile()) {
+                    throw new DeploymentException("Unable to create "+authFile.getAbsolutePath()+" to hold saved logins");
+                }
+            }
+            if(!authFile.canRead() || !authFile.canWrite()) {
+                throw new DeploymentException("Saved login file "+authFile.getAbsolutePath()+" is not readable or not writable");
+            }
+            Properties props = new Properties();
+            InputStream in = new BufferedInputStream(new FileInputStream(authFile));
+            props.load(in);
+            in.close();
+            props.setProperty("login."+connection.getServerURI(), "{Standard}"+SimpleEncryption.encrypt(connection.getAuthentication()));
+            OutputStream save = new BufferedOutputStream(new FileOutputStream(authFile));
+            props.store(save, "Saved authentication information to connect to Geronimo servers");
+            save.flush();
+            save.close();
+            System.out.println(DeployUtils.reformat("Saved login for: "+connection.getServerURI(), 4, 72));
+        } catch (IOException e) {
+            throw new DeploymentException("Unable to save authentication to login file", e);
+        }
+    }
+}

Propchange: geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/CommandLogin.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/DeployTool.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/DeployTool.java?rev=332802&r1=332801&r2=332802&view=diff
==============================================================================
--- geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/DeployTool.java (original)
+++ geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/DeployTool.java Sat Nov 12 09:51:49 2005
@@ -61,6 +61,7 @@
     }
 
     static {
+        registerCommand(new CommandLogin());
         registerCommand(new CommandDeploy());
         registerCommand(new CommandDistribute());
         registerCommand(new CommandListModules());

Modified: geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/ServerConnection.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/ServerConnection.java?rev=332802&r1=332801&r2=332802&view=diff
==============================================================================
--- geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/ServerConnection.java (original)
+++ geronimo/trunk/modules/deploy-tool/src/java/org/apache/geronimo/deployment/cli/ServerConnection.java Sat Nov 12 09:51:49 2005
@@ -21,6 +21,7 @@
 import java.util.LinkedHashMap;
 import java.util.List;
 import java.util.Map;
+import java.util.Properties;
 import java.util.jar.JarFile;
 import javax.enterprise.deploy.shared.factories.DeploymentFactoryManager;
 import javax.enterprise.deploy.spi.DeploymentManager;
@@ -34,6 +35,7 @@
 import org.apache.geronimo.deployment.plugin.jmx.JMXDeploymentManager;
 import org.apache.geronimo.system.main.CommandLine;
 import org.apache.geronimo.system.main.CommandLineManifest;
+import org.apache.geronimo.util.SimpleEncryption;
 
 /**
  * Supports two types of connections to the server.  One, via JSR-88, is valid
@@ -106,6 +108,7 @@
     private KernelWrapper kernel;
     private PrintWriter out;
     private BufferedReader in;
+    private SavedAuthentication auth;
 
     public ServerConnection(String[] args, boolean forceLocal, PrintWriter out, BufferedReader in) throws DeploymentException {
         String uri = null, driver = null, user = null, password = null;
@@ -213,30 +216,70 @@
         }
     }
 
-    private void tryToConnect(String uri, JMXDeploymentManager.CommandContext commandContext, String driver, String user, String password, boolean authPrompt) throws DeploymentException {
+    Serializable getAuthentication() {
+        return auth;
+    }
+
+    String getServerURI() {
+        return auth.uri;
+    }
+
+    private void tryToConnect(String argURI, JMXDeploymentManager.CommandContext commandContext, String driver, String user, String password, boolean authPrompt) throws DeploymentException {
         DeploymentFactoryManager mgr = DeploymentFactoryManager.getInstance();
         if(driver != null) {
             loadDriver(driver, mgr);
         } else {
             mgr.registerDeploymentFactory(new DeploymentFactoryImpl());
         }
+        String useURI = argURI == null ? DEFAULT_URI : argURI;
 
-        if(authPrompt && uri != null && !uri.equals(DEFAULT_URI) && user == null && password == null) {
+        if(authPrompt && user == null && password == null) {
+            File authFile = new File(System.getProperty("user.home"), ".geronimo-deployer");
+            if(authFile.exists() && authFile.canRead()) {
+                try {
+                    Properties props = new Properties();
+                    InputStream in = new BufferedInputStream(new FileInputStream(authFile));
+                    props.load(in);
+                    in.close();
+                    String encryped = props.getProperty("login."+useURI);
+                    if(encryped != null) {
+                        if(encryped.startsWith("{Standard}")) {
+                            SavedAuthentication auth = (SavedAuthentication) SimpleEncryption.decrypt(encryped.substring(10));
+                            if(auth.uri.equals(useURI)) {
+                                user = auth.user;
+                                password = new String(auth.password);
+                            }
+                        } else if(encryped.startsWith("{Plain}")) {
+                            int pos = encryped.indexOf("/");
+                            user = encryped.substring(7, pos);
+                            password = encryped.substring(pos+1);
+                        } else {
+                            System.out.println(DeployUtils.reformat("Unknown encryption used in saved login file", 4, 72));
+                        }
+                    }
+                } catch (IOException e) {
+                    System.out.println(DeployUtils.reformat("Unable to read authentication from saved login file: "+e.getMessage(), 4, 72));
+                }
+            }
+        }
+
+        if(authPrompt && !useURI.equals(DEFAULT_URI) && user == null && password == null) {
             // Non-standard URI, but no authentication information
-            doAuthPromptAndRetry(uri, commandContext, user, password);
+            doAuthPromptAndRetry(useURI, commandContext, user, password);
             return;
         } else { // Standard URI with no auth, Non-standard URI with auth, or else this is the 2nd try already
             try {
-                manager = mgr.getDeploymentManager(uri == null ? DEFAULT_URI : uri, user, password);
+                manager = mgr.getDeploymentManager(useURI, user, password);
+                auth = new SavedAuthentication(useURI, user, password.toCharArray());
             } catch(AuthenticationFailedException e) { // server's there, you just can't talk to it
-                if(authPrompt && (user == null || password == null)) {
-                    doAuthPromptAndRetry(uri, commandContext, user, password);
+                if(authPrompt) {
+                    doAuthPromptAndRetry(useURI, commandContext, user, password);
                     return;
                 } else {
                     throw new DeploymentException("Login Failed");
                 }
             } catch(DeploymentManagerCreationException e) {
-                throw new DeploymentException("Unable to connect to server at "+(uri == null ? DEFAULT_URI : uri)+" -- "+e.getMessage());
+                throw new DeploymentException("Unable to connect to server at "+useURI+" -- "+e.getMessage());
             }
         }
 
@@ -405,6 +448,18 @@
             } catch (InterruptedException e) {
             }
             return password;
+        }
+    }
+
+    private final static class SavedAuthentication implements Serializable {
+        private String uri;
+        private String user;
+        private char[] password;
+
+        public SavedAuthentication(String uri, String user, char[] password) {
+            this.uri = uri;
+            this.user = user;
+            this.password = password;
         }
     }
 }

Propchange: geronimo/trunk/modules/util/
------------------------------------------------------------------------------
--- svn:ignore (original)
+++ svn:ignore Sat Nov 12 09:51:49 2005
@@ -1 +1,2 @@
 target
+*.iml

Added: geronimo/trunk/modules/util/src/java/org/apache/geronimo/util/SimpleEncryption.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/util/src/java/org/apache/geronimo/util/SimpleEncryption.java?rev=332802&view=auto
==============================================================================
--- geronimo/trunk/modules/util/src/java/org/apache/geronimo/util/SimpleEncryption.java (added)
+++ geronimo/trunk/modules/util/src/java/org/apache/geronimo/util/SimpleEncryption.java Sat Nov 12 09:51:49 2005
@@ -0,0 +1,88 @@
+/**
+ *
+ * Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.apache.geronimo.util;
+
+import java.io.ByteArrayOutputStream;
+import java.io.ObjectOutputStream;
+import java.io.Serializable;
+import java.io.ObjectInputStream;
+import java.io.ByteArrayInputStream;
+import javax.crypto.spec.SecretKeySpec;
+import javax.crypto.Cipher;
+import javax.crypto.SealedObject;
+import org.apache.geronimo.util.encoders.Base64;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+/**
+ * This class protects some value BY ENCRYPTING WITH A KNOWN KEY.  That is
+ * to say, it's only safe against anyone who can't read the source code.
+ * So the main idea is to protect against casual observers.
+ *
+ * If someone has a better idea for how to implement encryption with a
+ * non-obvious key that the user isn't likely to change during the normal
+ * course of working with the server, I'd be happy to hear it.  (But I
+ * assume the SSL keystore is likely to be changed, which would result
+ * in losing all the "encrypted" data.
+ *
+ * @version $Rev: 46019 $ $Date: 2004-09-14 05:56:06 -0400 (Tue, 14 Sep 2004) $
+ */
+public class SimpleEncryption {
+    private final static Log log = LogFactory.getLog(SimpleEncryption.class);
+    private final static SecretKeySpec SECRET_KEY = new SecretKeySpec(new byte[]{(byte)-45,(byte)-15,(byte)100,(byte)-34,(byte)70,(byte)83,(byte)75,(byte)-100,(byte)-75,(byte)61,(byte)26,(byte)114,(byte)-20,(byte)-58,(byte)114,(byte)77}, "AES");
+
+
+    /**
+     * Gets a String which contains the Base64-encoded form of the source,
+     * encrypted with the known key.
+     */
+    public static String encrypt(Serializable source) {
+        try {
+            Cipher c = Cipher.getInstance("AES");
+            c.init(Cipher.ENCRYPT_MODE, SECRET_KEY);
+            SealedObject so = new SealedObject(source, c);
+            ByteArrayOutputStream store = new ByteArrayOutputStream();
+            ObjectOutputStream out = new ObjectOutputStream(store);
+            out.writeObject(so);
+            out.close();
+            byte[] data = store.toByteArray();
+            byte[] textData = Base64.encode(data);
+            return new String(textData, "US-ASCII");
+        } catch (Exception e) {
+            log.error("Unable to encrypt", e);
+            return null;
+        }
+    }
+
+    /**
+     * Given a String which is the Base64-encoded encrypted data, retrieve
+     * the original Object.
+     */
+    public static Object decrypt(String source) {
+        try {
+            byte[] data = Base64.decode(source);
+            Cipher c = Cipher.getInstance("AES");
+            c.init(Cipher.DECRYPT_MODE, SECRET_KEY);
+            ObjectInputStream in = new ObjectInputStream(new ByteArrayInputStream(data));
+            SealedObject so = (SealedObject) in.readObject();
+            return so.getObject(c);
+        } catch (Exception e) {
+            log.error("Unable to decrypt", e);
+            return null;
+        }
+    }
+}

Propchange: geronimo/trunk/modules/util/src/java/org/apache/geronimo/util/SimpleEncryption.java
------------------------------------------------------------------------------
    svn:eol-style = native

Added: geronimo/trunk/modules/util/src/test/org/apache/geronimo/util/SimpleEncryptionTest.java
URL: http://svn.apache.org/viewcvs/geronimo/trunk/modules/util/src/test/org/apache/geronimo/util/SimpleEncryptionTest.java?rev=332802&view=auto
==============================================================================
--- geronimo/trunk/modules/util/src/test/org/apache/geronimo/util/SimpleEncryptionTest.java (added)
+++ geronimo/trunk/modules/util/src/test/org/apache/geronimo/util/SimpleEncryptionTest.java Sat Nov 12 09:51:49 2005
@@ -0,0 +1,33 @@
+/**
+ *
+ * Copyright 2003-2004 The Apache Software Foundation
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ */
+package org.apache.geronimo.util;
+
+import junit.framework.TestCase;
+
+/**
+ * @version $Rev: 46019 $ $Date: 2004-09-14 05:56:06 -0400 (Tue, 14 Sep 2004) $
+ */
+public class SimpleEncryptionTest extends TestCase {
+    public void testSimpleEncryption() {
+        Object[] source = new Object[]{"This is a test", new Integer(14)};
+        String text = SimpleEncryption.encrypt(source);
+        Object[] result = (Object[]) SimpleEncryption.decrypt(text);
+        assertEquals(2, result.length);
+        assertEquals("This is a test", result[0]);
+        assertEquals(new Integer(14), result[1]);
+    }
+}

Propchange: geronimo/trunk/modules/util/src/test/org/apache/geronimo/util/SimpleEncryptionTest.java
------------------------------------------------------------------------------
    svn:eol-style = native