changeset 1042:40414c3e4f02

Introduce preferences for Eclipse plugin. Reviewed-by: neugens Review-thread: http://icedtea.classpath.org/pipermail/thermostat/2013-March/006109.html
author Severin Gehwolf <sgehwolf@redhat.com>
date Tue, 19 Mar 2013 17:33:08 +0100
parents 2359df39aa5a
children 1e5d9c28e9ed
files Makefile eclipse/com.redhat.thermostat.client.feature/build.properties eclipse/com.redhat.thermostat.client.feature/linux_x86-64/.empty eclipse/com.redhat.thermostat.client.feature/linux_x86/.empty eclipse/com.redhat.thermostat.eclipse/META-INF/MANIFEST.MF eclipse/com.redhat.thermostat.eclipse/plugin.xml eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/ThermostatConstants.java eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/Activator.java eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/jobs/ConnectDbJob.java eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/preferences/MainPreferencePage.java eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/views/HostsVmsTreeViewPart.java keyring/src/main/resources/META-INF/p2.inf
diffstat 12 files changed, 286 insertions(+), 13 deletions(-) [+]
line wrap: on
line diff
--- a/Makefile	Wed Mar 20 15:37:33 2013 -0400
+++ b/Makefile	Tue Mar 19 17:33:08 2013 +0100
@@ -13,6 +13,7 @@
 REPO_FLAG       = -Dmaven.repo.local=$(REPO_LOC)
 GOAL            = package
 POM             = pom.xml
+ARCH            = $(shell uname -m)
 
 ifeq ($(SKIP_TESTS),true)
 	MAVEN_SKIP_TEST = -Dmaven.test.skip=true
@@ -33,6 +34,13 @@
 core-install: create-repo-dir
 	$(MAVEN) -f $(POM) $(MAVEN_FLAGS) $(REPO_FLAG) $(MAVEN_SKIP_TEST) clean install
 
+copy-core-natives: core-install
+	if [ "_$(ARCH)" = "_x86_64" ]; then \
+        	cp keyring/target/libGnomeKeyringWrapper.so eclipse/com.redhat.thermostat.client.feature/linux_x86-64; \
+	else \
+		cp keyring/target/libGnomeKeyringWrapper.so eclipse/com.redhat.thermostat.client.feature/linux_x86; \
+	fi
+
 eclipse-test: eclipse eclipse-test-p2
 ifeq ($(USE_VNC),true)
 	$(VNC) $(VNC_DISPLAY) $(VNC_FLAGS)
@@ -43,13 +51,13 @@
 	$(VNC) -kill $(VNC_DISPLAY)
 endif
 
-eclipse-test-deps: core-install
+eclipse-test-deps: copy-core-natives
 	$(MAVEN) -f eclipse/test-deps-bundle-wrapping/pom.xml $(MAVEN_FLAGS) $(REPO_FLAG) $(MAVEN_SKIP_TEST) clean install
 
 eclipse-test-p2: eclipse-test-deps
 	$(MAVEN) -f eclipse/test-deps-p2-repository/pom.xml $(MAVEN_FLAGS) $(REPO_FLAG) $(MAVEN_SKIP_TEST) clean $(GOAL)
 
-jfreechart-deps: core-install
+jfreechart-deps: copy-core-natives
 	$(MAVEN) -f eclipse/jfreechart-bundle-wrapping/pom.xml $(MAVEN_FLAGS) $(REPO_FLAG) $(MAVEN_SKIP_TEST) clean install
 
 jfreechart-p2: jfreechart-deps
@@ -71,4 +79,4 @@
 	echo "Using private Maven repository: $(REPO_LOC)"
 
 # We only have phony targets
-.PHONY:	all core core-install eclipse-test eclipse-test-p2 eclipse-test-deps jfreechart-deps jfreechart-p2 eclipse create-repo-dir clean-repo echo-repo
+.PHONY:	all core core-install copy-core-natives eclipse-test eclipse-test-p2 eclipse-test-deps jfreechart-deps jfreechart-p2 eclipse create-repo-dir clean-repo echo-repo
--- a/eclipse/com.redhat.thermostat.client.feature/build.properties	Wed Mar 20 15:37:33 2013 -0400
+++ b/eclipse/com.redhat.thermostat.client.feature/build.properties	Tue Mar 19 17:33:08 2013 +0100
@@ -1,2 +1,4 @@
 bin.includes = feature.xml
 forceContextQualifier = SNAPSHOT
+root.linux.gtk.x86=linux_x86
+root.linux.gtk.x86_64=linux_x86-64
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/eclipse/com.redhat.thermostat.client.feature/linux_x86-64/.empty	Tue Mar 19 17:33:08 2013 +0100
@@ -0,0 +1,1 @@
+File in order to trick hg into tracking the parent folder.
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/eclipse/com.redhat.thermostat.client.feature/linux_x86/.empty	Tue Mar 19 17:33:08 2013 +0100
@@ -0,0 +1,1 @@
+File in order to trick hg into tracking the parent folder.
--- a/eclipse/com.redhat.thermostat.eclipse/META-INF/MANIFEST.MF	Wed Mar 20 15:37:33 2013 -0400
+++ b/eclipse/com.redhat.thermostat.eclipse/META-INF/MANIFEST.MF	Tue Mar 19 17:33:08 2013 +0100
@@ -8,7 +8,8 @@
 Bundle-RequiredExecutionEnvironment: JavaSE-1.7
 Bundle-ActivationPolicy: lazy
 Require-Bundle: org.eclipse.core.runtime,
- org.eclipse.ui
+ org.eclipse.ui,
+ org.eclipse.ui.workbench
 Import-Package: com.redhat.thermostat.client.core,
  com.redhat.thermostat.client.core.controllers,
  com.redhat.thermostat.client.core.views,
@@ -22,7 +23,10 @@
  com.redhat.thermostat.storage.config,
  com.redhat.thermostat.storage.core,
  com.redhat.thermostat.storage.model,
- com.redhat.thermostat.storage.dao
+ com.redhat.thermostat.storage.dao,
+ com.redhat.thermostat.utils.keyring,
+ com.redhat.thermostat.common.config,
+ org.eclipse.equinox.security.storage
 Export-Package: com.redhat.thermostat.eclipse,
  com.redhat.thermostat.eclipse.internal;x-friends:="com.redhat.thermostat.eclipse.test,com.redhat.thermostat.eclipse.test.ui",
  com.redhat.thermostat.eclipse.internal.controllers;x-friends:="com.redhat.thermostat.eclipse.test,com.redhat.thermostat.eclipse.test.ui",
--- a/eclipse/com.redhat.thermostat.eclipse/plugin.xml	Wed Mar 20 15:37:33 2013 -0400
+++ b/eclipse/com.redhat.thermostat.eclipse/plugin.xml	Tue Mar 19 17:33:08 2013 +0100
@@ -67,5 +67,12 @@
             name="Thermostat">
       </perspective>
    </extension>
+   <extension
+         point="org.eclipse.ui.preferencePages">
+         <page
+            class="com.redhat.thermostat.eclipse.internal.preferences.MainPreferencePage"
+            id="com.redhat.thermostat.eclipse.preferences"
+            name="Thermostat Client"/>
+   </extension>
 </plugin>
 
--- a/eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/ThermostatConstants.java	Wed Mar 20 15:37:33 2013 -0400
+++ b/eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/ThermostatConstants.java	Tue Mar 19 17:33:08 2013 +0100
@@ -48,6 +48,10 @@
     public static final String VIEW_ID_VM_GC = "com.redhat.thermostat.eclipse.chart.vmGcView";
     
     public static final String TEST_TAG = "com.redhat.thermostat.eclipse.test.swtTag";
-
+    
+    public static final String CONNECTION_URL_PREF_NAME = "com.redhat.thermostat.eclipse.prefs.connectionURL";
+    public static final String USERNAME_PREF_NAME = "com.redhat.thermostat.eclipse.prefs.username";
+    public static final String PASSWORD_PREF_NAME = "com.redhat.thermostat.eclipse.prefs.password";
+    public static final String SAVE_ENTITLEMENTS_PREF_NAME = "com.redhat.thermostat.eclipse.prefs.saveEntitlements";
 }
 
--- a/eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/Activator.java	Wed Mar 20 15:37:33 2013 -0400
+++ b/eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/Activator.java	Tue Mar 19 17:33:08 2013 +0100
@@ -44,6 +44,7 @@
 import org.eclipse.ui.plugin.AbstractUIPlugin;
 import org.osgi.framework.BundleContext;
 import org.osgi.framework.ServiceReference;
+import org.osgi.util.tracker.ServiceTracker;
 
 import com.redhat.thermostat.common.utils.OSGIUtils;
 import com.redhat.thermostat.eclipse.LoggerFacility;
@@ -51,6 +52,7 @@
 import com.redhat.thermostat.host.overview.client.core.HostOverviewViewProvider;
 import com.redhat.thermostat.storage.core.ConnectionException;
 import com.redhat.thermostat.storage.core.DbService;
+import com.redhat.thermostat.utils.keyring.Keyring;
 
 /**
  * The activator class controls the plug-in life cycle
@@ -62,6 +64,10 @@
 
     // The shared instance
     private static Activator plugin;
+    
+    private Keyring keyring;
+    @SuppressWarnings({ "rawtypes" })
+    private ServiceTracker keyringTracker;
 
     /**
      * The constructor
@@ -76,6 +82,7 @@
      * org.eclipse.ui.plugin.AbstractUIPlugin#start(org.osgi.framework.BundleContext
      * )
      */
+    @SuppressWarnings({ "rawtypes", "unchecked" })
     public void start(BundleContext context) throws Exception {
         super.start(context);
         plugin = this;
@@ -83,6 +90,24 @@
         // Register ViewProvider
         context.registerService(HostOverviewViewProvider.class,
                 new SWTHostOverviewViewProvider(), null);
+        
+        keyringTracker = new ServiceTracker(context, Keyring.class, null) {
+            @Override
+            public Object addingService(ServiceReference reference) {
+                Keyring keyring = (Keyring) context.getService(reference);
+                Activator.this.keyring = keyring;
+                return keyring;
+            }
+
+            @Override
+            public void removedService(ServiceReference reference, Object service) {
+                Activator.this.keyring = null;
+                context.ungetService(reference);
+            }
+            
+        };
+        // Track for Keyring service.
+        keyringTracker.open();
     }
 
     /*
@@ -107,6 +132,7 @@
             }
         }
         plugin = null;
+        keyringTracker.close();
         super.stop(context);
     }
 
@@ -164,6 +190,10 @@
                 DbService.class);
         return dbService != null;
     }
+    
+    public Keyring getKeyring() {
+        return keyring;
+    }
 
 }
 
--- a/eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/jobs/ConnectDbJob.java	Wed Mar 20 15:37:33 2013 -0400
+++ b/eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/jobs/ConnectDbJob.java	Tue Mar 19 17:33:08 2013 +0100
@@ -41,7 +41,6 @@
 import org.eclipse.core.runtime.Status;
 import org.eclipse.core.runtime.jobs.Job;
 
-import com.redhat.thermostat.common.utils.OSGIUtils;
 import com.redhat.thermostat.eclipse.LoggerFacility;
 import com.redhat.thermostat.eclipse.internal.Activator;
 import com.redhat.thermostat.eclipse.internal.ConnectionConfiguration;
@@ -81,8 +80,6 @@
         DbService dbService = dbServiceFactory.createDbService(configuration.getUsername(),
                 configuration.getPassword(), configuration.getDBConnectionString());
         dbService.connect();
-        // register service in order to indicate that we are connected
-        OSGIUtils.getInstance().registerService(DbService.class, dbService);
     }
 
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/preferences/MainPreferencePage.java	Tue Mar 19 17:33:08 2013 +0100
@@ -0,0 +1,209 @@
+/*
+ * Copyright 2012, 2013 Red Hat, Inc.
+ *
+ * This file is part of Thermostat.
+ *
+ * Thermostat is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published
+ * by the Free Software Foundation; either version 2, or (at your
+ * option) any later version.
+ *
+ * Thermostat is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with Thermostat; see the file COPYING.  If not see
+ * <http://www.gnu.org/licenses/>.
+ *
+ * Linking this code with other modules is making a combined work
+ * based on this code.  Thus, the terms and conditions of the GNU
+ * General Public License cover the whole combination.
+ *
+ * As a special exception, the copyright holders of this code give
+ * you permission to link this code with independent modules to
+ * produce an executable, regardless of the license terms of these
+ * independent modules, and to copy and distribute the resulting
+ * executable under terms of your choice, provided that you also
+ * meet, for each linked independent module, the terms and conditions
+ * of the license of that module.  An independent module is a module
+ * which is not derived from or based on this code.  If you modify
+ * this code, you may extend this exception to your version of the
+ * library, but you are not obligated to do so.  If you do not wish
+ * to do so, delete this exception statement from your version.
+ */
+
+package com.redhat.thermostat.eclipse.internal.preferences;
+
+import java.util.prefs.BackingStoreException;
+
+import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.preferences.DefaultScope;
+import org.eclipse.core.runtime.preferences.IEclipsePreferences;
+import org.eclipse.jface.layout.GridDataFactory;
+import org.eclipse.jface.preference.BooleanFieldEditor;
+import org.eclipse.jface.preference.FieldEditor;
+import org.eclipse.jface.preference.FieldEditorPreferencePage;
+import org.eclipse.jface.preference.StringFieldEditor;
+import org.eclipse.jface.util.PropertyChangeEvent;
+import org.eclipse.swt.SWT;
+import org.eclipse.swt.layout.GridLayout;
+import org.eclipse.swt.widgets.Composite;
+import org.eclipse.swt.widgets.Group;
+import org.eclipse.ui.IWorkbench;
+import org.eclipse.ui.IWorkbenchPreferencePage;
+
+import com.redhat.thermostat.common.config.ClientPreferences;
+import com.redhat.thermostat.eclipse.LoggerFacility;
+import com.redhat.thermostat.eclipse.ThermostatConstants;
+import com.redhat.thermostat.eclipse.internal.Activator;
+
+/**
+ * Main preferences page for the Thermostat Eclipse client.
+ *
+ */
+public class MainPreferencePage extends FieldEditorPreferencePage implements
+        IWorkbenchPreferencePage {
+    
+    private static final int GROUP_SPAN = 2;
+    private static final String HTTP_PREFIX = "http";
+    private static final String MONGODB_PREFIX = "mongodb";
+    
+    private StringFieldEditor connectionUrlEditor;
+    private StringFieldEditor usernameEditor;
+    private StringFieldEditor passwordEditor;
+    private BooleanFieldEditor saveEntitlementsEditor;
+    private ClientPreferences clientPrefs;
+    
+    /**
+     * Default no-arg constructor.
+     */
+    public MainPreferencePage() {
+        super(GRID);
+        // TODO: Externalize string.
+        setDescription("Thermostat Client Preferences");
+        setPreferenceStore(Activator.getDefault().getPreferenceStore());
+    }
+    
+    /**
+     * Validate fields for sane values.
+     */
+    @Override
+    public void checkState() {
+        super.checkState();
+        // connection URL has to be http(s) or mongodb
+        if (connectionUrlEditor.getStringValue() != null
+                && !(connectionUrlEditor.getStringValue().startsWith(HTTP_PREFIX)
+                        || connectionUrlEditor.getStringValue().startsWith(MONGODB_PREFIX))) {
+            setErrorMessage("Connection URL must start with either 'http' or 'mongodb'");
+            setValid(false);
+        } else {
+            // erase error message and mark things valid
+            setErrorMessage(null);
+            setValid(true);
+        }
+    }
+    
+    @Override
+    public boolean performOk() {
+        clientPrefs.setConnectionUrl(connectionUrlEditor.getStringValue());
+        clientPrefs.setSaveEntitlements(saveEntitlementsEditor.getBooleanValue());
+        if (saveEntitlementsEditor.getBooleanValue()) {
+            clientPrefs.setCredentials(usernameEditor.getStringValue(), passwordEditor.getStringValue());
+            try {
+                clientPrefs.flush();
+            } catch (BackingStoreException e) {
+                LoggerFacility.getInstance().log(IStatus.ERROR, "Failed to save preferences", e);
+            }
+        }
+        return true;
+    }
+    
+    /*
+     * (non-Javadoc)
+     * @see org.eclipse.ui.IWorkbenchPreferencePage#init(org.eclipse.ui.IWorkbench)
+     */
+    @Override
+    public void init(IWorkbench arg0) {
+        // nothing
+    }
+    
+    /*
+     * (non-Javadoc)
+     * @see org.eclipse.jface.util.IPropertyChangeListener#propertyChange(org.eclipse.jface.util.PropertyChangeEvent)
+     */
+    @Override
+    public void propertyChange(PropertyChangeEvent event) {
+        /*
+         * Validate input on change events.
+         */
+        if (event.getProperty().equals(FieldEditor.VALUE)) {
+            checkState();
+        }
+    }
+
+    @Override
+    protected void createFieldEditors() {
+        Composite composite = getFieldEditorParent();
+        
+        // General prefs
+        Group generalGroup = new Group(composite, SWT.SHADOW_ETCHED_IN);
+        generalGroup.setText("General");
+
+        GridDataFactory.fillDefaults().grab(true, false).span(GROUP_SPAN, 1)
+                .applyTo(generalGroup);
+        connectionUrlEditor = new StringFieldEditor(
+                ThermostatConstants.CONNECTION_URL_PREF_NAME,
+                "Connection URL",
+                generalGroup);
+        usernameEditor = new StringFieldEditor(
+                ThermostatConstants.USERNAME_PREF_NAME,
+                "Username",
+                generalGroup);
+        passwordEditor = new StringFieldEditor(ThermostatConstants.PASSWORD_PREF_NAME,
+                "Password", generalGroup);
+        passwordEditor.getTextControl(generalGroup).setEchoChar('*');
+        saveEntitlementsEditor = new BooleanFieldEditor(
+                ThermostatConstants.SAVE_ENTITLEMENTS_PREF_NAME,
+                "Save Entitlements", generalGroup);
+        // register change listener
+        connectionUrlEditor.setPropertyChangeListener(this);
+        addField(connectionUrlEditor);
+        addField(usernameEditor);
+        addField(passwordEditor);
+        addField(saveEntitlementsEditor);
+        updateMargins(generalGroup);
+        this.clientPrefs = new ClientPreferences(Activator.getDefault().getKeyring());
+        synchronizeValues();
+    }
+    
+    private void updateMargins(Group group) {
+        // make sure there is some room between the group border
+        // and the controls in the group
+        GridLayout layout = (GridLayout) group.getLayout();
+        layout.marginWidth = 5;
+        layout.marginHeight = 5;
+    }
+    
+    private void synchronizeValues() {
+        IEclipsePreferences node = DefaultScope.INSTANCE.getNode(Activator.PLUGIN_ID);
+        if (clientPrefs.getSaveEntitlements()) { 
+            node.put(ThermostatConstants.USERNAME_PREF_NAME, clientPrefs.getUserName());
+            node.put(ThermostatConstants.PASSWORD_PREF_NAME, clientPrefs.getPassword());
+            passwordEditor.setStringValue(clientPrefs.getPassword());
+            usernameEditor.setStringValue(clientPrefs.getUserName());
+        } else {
+            try {
+                node.clear();
+            } catch (org.osgi.service.prefs.BackingStoreException e) {
+                LoggerFacility.getInstance().log(IStatus.ERROR, "Failed to clear preferences", e);
+            }
+        }
+        node.put(ThermostatConstants.CONNECTION_URL_PREF_NAME,
+                clientPrefs.getConnectionUrl());
+        connectionUrlEditor.setStringValue(clientPrefs.getConnectionUrl());
+        node.putBoolean(ThermostatConstants.SAVE_ENTITLEMENTS_PREF_NAME, clientPrefs.getSaveEntitlements());
+    }
+
+}
--- a/eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/views/HostsVmsTreeViewPart.java	Wed Mar 20 15:37:33 2013 -0400
+++ b/eclipse/com.redhat.thermostat.eclipse/src/com/redhat/thermostat/eclipse/internal/views/HostsVmsTreeViewPart.java	Tue Mar 19 17:33:08 2013 +0100
@@ -51,6 +51,7 @@
 import org.eclipse.ui.part.PageBook;
 import org.eclipse.ui.part.ViewPart;
 
+import com.redhat.thermostat.common.config.ClientPreferences;
 import com.redhat.thermostat.common.utils.OSGIUtils;
 import com.redhat.thermostat.eclipse.internal.Activator;
 import com.redhat.thermostat.eclipse.internal.ConnectionConfiguration;
@@ -81,10 +82,10 @@
     private PageBook pageBook;
 
     public HostsVmsTreeViewPart() {
-        // FIXME: Get these values from preferences
-        // This circumvents webservice (uses mongo directly). If you want to use webstorage use something like:
-        // ConnectionConfiguration configuration = new ConnectionConfiguration("", "", "http://127.0.0.1:8082");
-        ConnectionConfiguration configuration = new ConnectionConfiguration("", "", "mongodb://127.0.0.1:27518");
+        ClientPreferences clientPrefs = new ClientPreferences(Activator.getDefault().getKeyring());
+        ConnectionConfiguration configuration = new ConnectionConfiguration(
+                clientPrefs.getUserName(), clientPrefs.getPassword(),
+                clientPrefs.getConnectionUrl());
         Job connectJob = new ConnectDbJob(
                 "Connecting to Thermostat storage...", configuration);
         connectJob.setSystem(true);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/keyring/src/main/resources/META-INF/p2.inf	Tue Mar 19 17:33:08 2013 +0100
@@ -0,0 +1,9 @@
+# Instructs Eclipse update manager to auto-start this bundle, and also adds
+# -Djava.library.path=path/to/eclipse-home where native libs are to be found
+instructions.configure = \
+org.eclipse.equinox.p2.touchpoint.eclipse.setStartLevel(startLevel: 4); \
+org.eclipse.equinox.p2.touchpoint.eclipse.markStarted(started: true); \
+org.eclipse.equinox.p2.touchpoint.eclipse.addJvmArg(jvmArg: -Djava.library.path=${installFolder});
+instructions.unconfigure = \
+org.eclipse.equinox.p2.touchpoint.eclipse.setStartLevel(startLevel: -1); \
+org.eclipse.equinox.p2.touchpoint.eclipse.markStarted(started: false);