/* * This program is free software; you can redistribute it and/or modify it under the * terms of the GNU Lesser General Public License, version 2.1 as published by the Free Software * Foundation. * * You should have received a copy of the GNU Lesser General Public License along with this * program; if not, you can obtain a copy at http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html * or from the Free Software Foundation, Inc., * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. * * This program 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 Lesser General Public License for more details. * * Copyright (c) 2009 Pentaho Corporation. All rights reserved. */ package org.pentaho.reporting.ui.datasources.jdbc.ui; import java.awt.BorderLayout; import java.awt.Component; import java.awt.FlowLayout; import java.awt.Window; import java.awt.event.ActionEvent; import java.beans.PropertyChangeEvent; import java.beans.PropertyChangeListener; import java.net.URL; import java.util.Locale; import javax.swing.AbstractAction; import javax.swing.Action; import javax.swing.Box; import javax.swing.DefaultComboBoxModel; import javax.swing.DefaultListCellRenderer; import javax.swing.ImageIcon; import javax.swing.JButton; import javax.swing.JLabel; import javax.swing.JList; import javax.swing.JPanel; import javax.swing.JScrollPane; import javax.swing.ListSelectionModel; import javax.swing.event.ListSelectionEvent; import javax.swing.event.ListSelectionListener; import org.pentaho.reporting.engine.classic.core.designtime.DesignTimeContext; import org.pentaho.reporting.libraries.base.util.ObjectUtilities; import org.pentaho.reporting.libraries.base.util.ResourceBundleSupport; import org.pentaho.reporting.libraries.base.util.StringUtils; import org.pentaho.reporting.libraries.designtime.swing.BorderlessButton; import org.pentaho.reporting.libraries.designtime.swing.LibSwingUtil; import org.pentaho.reporting.ui.datasources.jdbc.JdbcDataSourceModule; import org.pentaho.reporting.ui.datasources.jdbc.connection.JdbcConnectionDefinition; import org.pentaho.ui.xul.XulException; public abstract class ConnectionPanel extends JPanel { private class DataSourceDefinitionListSelectionListener implements ListSelectionListener { private JList dataSourceList; private DataSourceDefinitionListSelectionListener(final JList dataSourceList) { this.dataSourceList = dataSourceList; } public void valueChanged(final ListSelectionEvent e) { getDialogModel().getConnections().setSelectedItem(dataSourceList.getSelectedValue()); } } private static class DataSourceDefinitionListCellRenderer extends DefaultListCellRenderer { public Component getListCellRendererComponent(final JList list, final Object value, final int index, final boolean isSelected, final boolean cellHasFocus) { final JLabel listCellRendererComponent = (JLabel) super.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus); if (value != null) { final String jndiName = ((JdbcConnectionDefinition) value).getName(); if (!"".equals(jndiName)) { listCellRendererComponent.setText(jndiName); } else { listCellRendererComponent.setText(" "); } } return listCellRendererComponent; } } private static class SelectionConnectionUpdateHandler implements PropertyChangeListener { private JList dataSourceList; private SelectionConnectionUpdateHandler(final JList dataSourceList) { this.dataSourceList = dataSourceList; } public void propertyChange(final PropertyChangeEvent aEvent) { final DataSourceDialogModel theDialogModel = (DataSourceDialogModel) aEvent.getSource(); final DefaultComboBoxModel theConnections = theDialogModel.getConnections(); final Object theConnection = theConnections.getSelectedItem(); if (theConnection != null) { dataSourceList.setSelectedValue(theConnection, true); } else { dataSourceList.clearSelection(); } } } private class EditDataSourceAction extends AbstractAction implements PropertyChangeListener { private JList dataSourceList; private EditDataSourceAction(final JList dataSourceList) { this.dataSourceList = dataSourceList; final URL location = ConnectionPanel.class.getResource("/org/pentaho/reporting/ui/datasources/jdbc/resources/Edit.png"); if (location != null) { putValue(Action.SMALL_ICON, new ImageIcon(location)); } else { putValue(Action.NAME, bundleSupport.getString("ConnectionPanel.Edit.Name")); } putValue(Action.SHORT_DESCRIPTION, bundleSupport.getString("ConnectionPanel.Edit.Description")); setEnabled(getDialogModel().isConnectionSelected()); } public void propertyChange(final PropertyChangeEvent evt) { setEnabled(getDialogModel().isConnectionSelected()); } public void actionPerformed(final ActionEvent e) { final JdbcConnectionDefinition existingConnection = (JdbcConnectionDefinition) dataSourceList.getSelectedValue(); final DesignTimeContext designTimeContext = getDesignTimeContext(); try { final Window parentWindow = LibSwingUtil.getWindowAncestor(ConnectionPanel.this); final XulDatabaseDialog connectionDialog = new XulDatabaseDialog(parentWindow, designTimeContext); final JdbcConnectionDefinition connectionDefinition = connectionDialog.open(existingConnection); // See if the edit completed... if (connectionDefinition != null) { // If the name changed, delete it before the update is performed if (existingConnection.getName().equals(connectionDefinition.getName()) == false) { getDialogModel().getConnectionDefinitionManager().removeSource(existingConnection.getName()); } final DataSourceDialogModel dialogModel = getDialogModel(); // Add / update the JNDI source getDialogModel().getConnectionDefinitionManager().updateSourceList(connectionDefinition); dialogModel.editConnection(existingConnection, connectionDefinition); dataSourceList.setSelectedValue(connectionDefinition, true); } } catch (XulException e1) { designTimeContext.error(e1); } } } private class RemoveDataSourceAction extends AbstractAction implements PropertyChangeListener { private JList dataSourceList; /** * Defines an <code>Action</code> object with a default description string and default icon. * * @param dataSourceList the list containing the datasources */ private RemoveDataSourceAction(final JList dataSourceList) { this.dataSourceList = dataSourceList; setEnabled(getDialogModel().isConnectionSelected()); final URL resource = ConnectionPanel.class.getResource("/org/pentaho/reporting/ui/datasources/jdbc/resources/Remove.png"); if (resource != null) { putValue(Action.SMALL_ICON, new ImageIcon(resource)); } else { putValue(Action.NAME, bundleSupport.getString("ConnectionPanel.Remove.Name")); } putValue(Action.SHORT_DESCRIPTION, bundleSupport.getString("ConnectionPanel.Remove.Description")); } public void propertyChange(final PropertyChangeEvent evt) { setEnabled(getDialogModel().isConnectionSelected()); } public void actionPerformed(final ActionEvent e) { final JdbcConnectionDefinition source = (JdbcConnectionDefinition) dataSourceList.getSelectedValue(); if (source != null) { getDialogModel().getConnectionDefinitionManager().removeSource(source.getName()); getDialogModel().removeConnection(source); } } } private class AddDataSourceAction extends AbstractAction { private JList dataSourceList; private AddDataSourceAction(final JList dataSourceList) { this.dataSourceList = dataSourceList; final URL location = ConnectionPanel.class.getResource( "/org/pentaho/reporting/ui/datasources/jdbc/resources/Add.png"); if (location != null) { putValue(Action.SMALL_ICON, new ImageIcon(location)); } else { putValue(Action.NAME, bundleSupport.getString("ConnectionPanel.Add.Name")); } putValue(Action.SHORT_DESCRIPTION, bundleSupport.getString("ConnectionPanel.Add.Description")); } public void actionPerformed(final ActionEvent e) { final DesignTimeContext designTimeContext = getDesignTimeContext(); try { final Window parentWindow = LibSwingUtil.getWindowAncestor(ConnectionPanel.this); final XulDatabaseDialog connectionDialog = new XulDatabaseDialog(parentWindow, designTimeContext); final JdbcConnectionDefinition connectionDefinition = connectionDialog.open(null); if (connectionDefinition != null && !StringUtils.isEmpty(connectionDefinition.getName())) { // A new JNDI source was created if (getDialogModel().getConnectionDefinitionManager().updateSourceList(connectionDefinition) == false) { getDialogModel().addConnection(connectionDefinition); dataSourceList.setSelectedValue(connectionDefinition, true); } } } catch (XulException e1) { designTimeContext.error(e1); } } } private DataSourceDialogModel dialogModel; private DesignTimeContext designTimeContext; private ResourceBundleSupport bundleSupport; private boolean securityConfigurationAvailable; public ConnectionPanel(final DataSourceDialogModel aDialogModel, final DesignTimeContext designTimeContext) { this.securityConfigurationAvailable = true; this.dialogModel = aDialogModel; this.designTimeContext = designTimeContext; this.bundleSupport = new ResourceBundleSupport(Locale.getDefault(), JdbcDataSourceModule.MESSAGES, ObjectUtilities.getClassLoader(JdbcDataSourceModule.class)); } protected void initPanel() { setLayout(new BorderLayout()); final JList dataSourceList = new JList(dialogModel.getConnections()); dataSourceList.setCellRenderer(new DataSourceDefinitionListCellRenderer()); dataSourceList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION); dataSourceList.addListSelectionListener(new DataSourceDefinitionListSelectionListener(dataSourceList)); dataSourceList.setVisibleRowCount(10); final SelectionConnectionUpdateHandler theSelectedConnectionAction = new SelectionConnectionUpdateHandler( dataSourceList); dialogModel.addPropertyChangeListener(theSelectedConnectionAction); final EditDataSourceAction editDataSourceAction = new EditDataSourceAction(dataSourceList); dialogModel.addPropertyChangeListener(editDataSourceAction); final RemoveDataSourceAction removeDataSourceAction = new RemoveDataSourceAction(dataSourceList); dialogModel.addPropertyChangeListener(removeDataSourceAction); final JPanel connectionButtonPanel = new JPanel(); connectionButtonPanel.setLayout(new FlowLayout(FlowLayout.RIGHT)); if (isSecurityConfigurationAvailable()) { connectionButtonPanel.add(new JButton(createEditSecurityAction())); connectionButtonPanel.add(Box.createHorizontalStrut(40)); } connectionButtonPanel.add(new BorderlessButton(editDataSourceAction)); connectionButtonPanel.add(new BorderlessButton(new AddDataSourceAction(dataSourceList))); connectionButtonPanel.add(new BorderlessButton(removeDataSourceAction)); final JPanel connectionButtonPanelWrapper = new JPanel(new BorderLayout()); connectionButtonPanelWrapper.add(new JLabel(bundleSupport.getString("ConnectionPanel.Connections")), BorderLayout.CENTER); connectionButtonPanelWrapper.add(connectionButtonPanel, BorderLayout.EAST); add(BorderLayout.NORTH, connectionButtonPanelWrapper); add(BorderLayout.CENTER, new JScrollPane(dataSourceList)); } protected abstract Action createEditSecurityAction(); public boolean isSecurityConfigurationAvailable() { return securityConfigurationAvailable; } public void setSecurityConfigurationAvailable(final boolean securityConfigurationAvailable) { this.securityConfigurationAvailable = securityConfigurationAvailable; } public DataSourceDialogModel getDialogModel() { return dialogModel; } public DesignTimeContext getDesignTimeContext() { return designTimeContext; } protected ResourceBundleSupport getBundleSupport() { return bundleSupport; } }