/* *****************************************************************************
* JFire - it's hot - Free ERP System - http://jfire.org *
* Copyright (C) 2004-2005 NightLabs - http://NightLabs.org *
* *
* This library is free software; you can redistribute it and/or *
* modify it under the terms of the GNU Lesser General Public *
* License as published by the Free Software Foundation; either *
* version 2.1 of the License, or (at your option) any later version. *
* *
* This library 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. *
* *
* You should have received a copy of the GNU Lesser General Public *
* License along with this library; if not, write to the *
* Free Software Foundation, Inc., *
* 51 Franklin St, Fifth Floor, *
* Boston, MA 02110-1301 USA *
* *
* Or get it online : *
* http://www.gnu.org/copyleft/lesser.html *
* *
* *
******************************************************************************/
package org.nightlabs.jfire.reporting.admin.ui.oda.jfs.client.ui;
import java.util.Iterator;
import org.apache.log4j.Logger;
import org.eclipse.datatools.connectivity.oda.IConnection;
import org.eclipse.datatools.connectivity.oda.IDriver;
import org.eclipse.datatools.connectivity.oda.IParameterMetaData;
import org.eclipse.datatools.connectivity.oda.IQuery;
import org.eclipse.datatools.connectivity.oda.IResultSetMetaData;
import org.eclipse.datatools.connectivity.oda.OdaException;
import org.eclipse.datatools.connectivity.oda.design.DataElementAttributes;
import org.eclipse.datatools.connectivity.oda.design.DataSetDesign;
import org.eclipse.datatools.connectivity.oda.design.DataSetParameters;
import org.eclipse.datatools.connectivity.oda.design.DesignFactory;
import org.eclipse.datatools.connectivity.oda.design.InputElementAttributes;
import org.eclipse.datatools.connectivity.oda.design.InputParameterAttributes;
import org.eclipse.datatools.connectivity.oda.design.ParameterDefinition;
import org.eclipse.datatools.connectivity.oda.design.ResultSetColumns;
import org.eclipse.datatools.connectivity.oda.design.ResultSetDefinition;
import org.eclipse.datatools.connectivity.oda.design.ui.designsession.DesignSessionUtil;
import org.eclipse.datatools.connectivity.oda.design.ui.wizards.DataSetWizardPage;
import org.eclipse.datatools.connectivity.oda.design.util.DesignUtil;
import org.eclipse.datatools.connectivity.oda.jfire.JFireOdaException;
import org.eclipse.emf.common.util.EList;
import org.eclipse.jface.resource.ImageDescriptor;
import org.eclipse.swt.SWT;
import org.eclipse.swt.custom.SashForm;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Group;
import org.nightlabs.base.ui.composite.XComposite;
import org.nightlabs.base.ui.composite.XComposite.LayoutMode;
import org.nightlabs.jfire.reporting.admin.ui.oda.jfs.client.ui.property.IJFSQueryPropertySetEditor;
import org.nightlabs.jfire.reporting.admin.ui.oda.jfs.client.ui.property.IJFSQueryPropertySetEditorFactory;
import org.nightlabs.jfire.reporting.admin.ui.oda.jfs.client.ui.property.JFSQueryPropertySetEditorRegistry;
import org.nightlabs.jfire.reporting.admin.ui.resource.Messages;
import org.nightlabs.jfire.reporting.oda.client.jfs.ClientJFSDriver;
import org.nightlabs.jfire.reporting.oda.jfs.JFSParameterUtil;
import org.nightlabs.jfire.reporting.oda.jfs.JFSQueryPropertySet;
import org.nightlabs.jfire.reporting.oda.jfs.JFSQueryUtil;
import org.nightlabs.jfire.reporting.oda.wrapper.DriverWrapper;
/**
* DataSet WizardPage that lets the user pick a JFireScript that
* should be executed for the DataSet and also lets the user
* configure the {@link JFSQueryPropertySet} for the data-set script.
*
* @author Alexander Bieber <alex [AT] nightlabs [DOT] de>
*/
public class JFSQueryPropertySetWizardPage extends DataSetWizardPage {
/**
* Logger used by this class.
*/
private static final Logger logger = Logger.getLogger(JFSQueryPropertySetWizardPage.class);
private SashForm wrapper;
private SelectedScriptComposite selectedScriptComposite;
private Group propertyGroup;
private IJFSQueryPropertySetEditorFactory propertySetEditorFactory;
private IJFSQueryPropertySetEditor propertySetEditor;
/**
* Create a new {@link JFSQueryPropertySetWizardPage}.
*
* @param name The page name.
*/
public JFSQueryPropertySetWizardPage(String name) {
super(name);
}
/**
* Create a new {@link JFSQueryPropertySetWizardPage}.
*
* @param name The page name.
* @param title The page title.
* @param icon The page icon.
*/
public JFSQueryPropertySetWizardPage(String name, String title,
ImageDescriptor icon) {
super(name, title, icon);
}
private JFSQueryPropertySet queryPropertySet = null;
/* (non-Javadoc)
* @see org.eclipse.datatools.connectivity.oda.design.ui.wizards.DataSetWizardPage#createPageCustomControl(org.eclipse.swt.widgets.Composite)
*/
@Override
public void createPageCustomControl(Composite parent) {
// wrapper = new XComposite(parent, SWT.NONE, LayoutMode.TIGHT_WRAPPER);
wrapper = new SashForm(parent, SWT.VERTICAL);
selectedScriptComposite = new SelectedScriptComposite(wrapper, SWT.NONE);
propertyGroup = new Group(wrapper, SWT.NONE);
GridLayout gl = new GridLayout();
XComposite.configureLayout(LayoutMode.TIGHT_WRAPPER, gl);
propertyGroup.setLayout(gl);
propertyGroup.setText(Messages.getString("org.nightlabs.jfire.reporting.admin.ui.oda.jfs.client.ui.JFSQueryPropertySetWizardPage.propertyGroup.text")); //$NON-NLS-1$
wrapper.setWeights(new int[] {3, 2});
setControl(wrapper);
setMessage(Messages.getString("org.nightlabs.jfire.reporting.admin.ui.oda.jfs.client.ui.JFSQueryPropertySetWizardPage.message")); //$NON-NLS-1$
refresh(null);
}
/*
* (non-Javadoc)
* @see org.eclipse.datatools.connectivity.oda.design.ui.wizards.DataSetWizardPage#refresh(org.eclipse.datatools.connectivity.oda.design.DataSetDesign)
*/
@Override
protected void refresh(DataSetDesign design) {
super.refresh(design);
if (design != null && design.getQueryText() != null) {
try {
queryPropertySet = JFSQueryUtil.createPropertySetFromQueryString(design.getQueryText());
if (queryPropertySet == null)
queryPropertySet = new JFSQueryPropertySet();
} catch (Exception e) {
logger.error("Have query text, but can not create JFSQueryProperySet out of it!", e); //$NON-NLS-1$
queryPropertySet = new JFSQueryPropertySet();
}
logDesignParameters("refresh: ", design); //$NON-NLS-1$
}
if (queryPropertySet == null) {
queryPropertySet = new JFSQueryPropertySet();
}
if (queryPropertySet.getScriptRegistryItemID() != null) {
if (selectedScriptComposite != null && !selectedScriptComposite.isDisposed()) {
selectedScriptComposite.setScriptRegistryItemID(queryPropertySet.getScriptRegistryItemID());
}
IJFSQueryPropertySetEditorFactory newFactory = JFSQueryPropertySetEditorRegistry.sharedInstance()
.getJFSQueryPropertySetFactory(queryPropertySet.getScriptRegistryItemID());
if (newFactory == null) {
throw new IllegalStateException(JFSQueryPropertySetEditorRegistry.class.getName() + " returned null on getJFSQueryPropertySetFactory()"); //$NON-NLS-1$
}
if (newFactory != null && newFactory != propertySetEditorFactory) {
if (
propertySetEditor != null &&
propertySetEditor.getControl() != null &&
!propertySetEditor.getControl().isDisposed()
) {
propertySetEditor.getControl().dispose();
}
propertySetEditorFactory = newFactory;
propertySetEditor = propertySetEditorFactory.createJFSQueryPropertySetEditor();
if (propertySetEditor == null) {
throw new IllegalStateException(propertySetEditorFactory.getClass().getName() + " returned no editor on createJFSQueryPropertySetEditor()", new NullPointerException("propertySetEditor")); //$NON-NLS-1$ //$NON-NLS-2$
}
propertySetEditor.createControl(propertyGroup);
}
if (propertySetEditor != null) {
propertySetEditor.setJFSQueryPropertySet(queryPropertySet);
}
} // if (queryPropertySet.getScriptRegistryItemID() != null)
}
/*
* (non-Javadoc)
* @see org.eclipse.datatools.connectivity.oda.design.ui.wizards.DataSetWizardPage#collectDataSetDesign(org.eclipse.datatools.connectivity.oda.design.DataSetDesign)
*/
@Override
protected DataSetDesign collectDataSetDesign(DataSetDesign design) {
if (queryPropertySet != null) {
if (selectedScriptComposite != null && !selectedScriptComposite.isDisposed()) {
queryPropertySet.setScriptRegistryItemID(selectedScriptComposite.getScriptRegistryItemID());
}
if (propertySetEditor != null) {
queryPropertySet.setProperties(propertySetEditor.getProperties());
}
String queryText = JFSQueryUtil.createQueryStringFromPropertySet(queryPropertySet);
design.setQueryText(queryText);
// obtain query's current runtime metadata, and maps it to the dataSetDesign
org.eclipse.datatools.connectivity.oda.IConnection customConn = null;
try
{
// instantiate your custom ODA runtime driver class
/* Note: You may need to manually update your ODA runtime extension's
* plug-in manifest to export its package for visibility here.
*/
IDriver customDriver = new DriverWrapper(new ClientJFSDriver());
// obtain and open a live connection
customConn = customDriver.getConnection( null );
java.util.Properties connProps =
DesignUtil.convertDataSourceProperties(
getInitializationDesign().getDataSourceDesign() );
customConn.open( connProps );
// update the data set design with the
// query's current runtime metadata
updateDesign( design, customConn, queryText );
}
catch( OdaException e )
{
// not able to get current metadata, reset previous derived metadata
design.setResultSets( null );
design.setParameters( null );
e.printStackTrace();
}
finally
{
closeConnection( customConn );
}
}
logDesignParameters("collect: ", design); //$NON-NLS-1$
return design;
}
/**
* Updates the given dataSetDesign with the queryText and its derived metadata
* obtained from the ODA runtime connection.
*/
private void updateDesign(DataSetDesign dataSetDesign, IConnection conn, String queryText)
throws OdaException
{
IQuery query = conn.newQuery( null );
query.prepare( queryText );
// TODO a runtime driver might require a query to first execute before
// its metadata is available
// query.setMaxRows( 1 );
// query.executeQuery();
try {
IResultSetMetaData md = query.getMetaData();
updateResultSetDesign( md, dataSetDesign );
} catch( OdaException e ) {
// no result set definition available, reset previous derived metadata
dataSetDesign.setResultSets( null );
e.printStackTrace();
}
// proceed to get parameter design definition
try {
IParameterMetaData paramMd = query.getParameterMetaData();
updateParameterDesign( paramMd, dataSetDesign );
} catch( OdaException ex ) {
// no parameter definition available, reset previous derived metadata
dataSetDesign.setParameters( null );
ex.printStackTrace();
}
}
/**
* Updates the specified data set design's result set definition based on the
* specified runtime metadata.
* @param md runtime result set metadata instance
* @param dataSetDesign data set design instance to update
* @throws JFireOdaException
*/
private void updateResultSetDesign( IResultSetMetaData md,
DataSetDesign dataSetDesign )
throws OdaException
{
ResultSetColumns columns = DesignSessionUtil.toResultSetColumnsDesign( md );
ResultSetDefinition resultSetDefn = DesignFactory.eINSTANCE
.createResultSetDefinition();
// resultSetDefn.setName( value ); // result set name
resultSetDefn.setResultSetColumns( columns );
// no exception in conversion; go ahead and assign to specified dataSetDesign
dataSetDesign.setPrimaryResultSet( resultSetDefn );
dataSetDesign.getResultSets().setDerivedMetaData( true );
}
/**
* Updates the specified data set design's parameter definition based on the
* specified runtime metadata.
* @param paramMd The runtime parameter metadata instance.
* @param dataSetDesign The data set design instance to update.
* @throws JFireOdaException
*/
private void updateParameterDesign( IParameterMetaData paramMd,
DataSetDesign dataSetDesign )
throws OdaException
{
DataSetParameters paramDesign =
DesignSessionUtil.toDataSetParametersDesign( paramMd,
DesignSessionUtil.toParameterModeDesign( IParameterMetaData.parameterModeIn ) );
if (paramDesign == null)
return;
// no exception in conversion; go ahead and assign to specified dataSetDesign
paramDesign.setDerivedMetaData( true );
// TODO WORKAROUND
// hard-coded parameter's default because bindings will be ignored if no default value set :-(
for (int i = 0; i < paramDesign.getParameterDefinitions().size(); i++) {
ParameterDefinition paramDef = (ParameterDefinition) paramDesign.getParameterDefinitions().get(i);
if( paramDef != null )
paramDef.setDefaultScalarValue(JFSParameterUtil.DUMMY_DEFAULT_PARAMETER_VALUE);
}
dataSetDesign.setParameters( paramDesign );
}
/**
* Attempts to close given ODA connection.
*/
private void closeConnection( IConnection conn )
{
try
{
if( conn != null && conn.isOpen() )
conn.close();
}
catch ( OdaException e )
{
// ignore
e.printStackTrace();
}
}
private void logDesignParameters(String prefix, DataSetDesign design) {
if (design.getParameters() == null)
return;
EList paramDefns = design.getParameters().getParameterDefinitions();
for (Iterator iter = paramDefns.iterator(); iter.hasNext();) {
ParameterDefinition definition = (ParameterDefinition) iter.next();
logger.info(prefix + "Found parameter with InOutMode: " + definition.getInOutMode().toString()); //$NON-NLS-1$
DataElementAttributes dataElementAttributes = definition.getAttributes();
InputParameterAttributes attrs = definition.getInputAttributes();
if (attrs == null)
return;
InputElementAttributes elementAttributes = attrs.getElementAttributes();
logger.info(prefix + "Parameter name: " + dataElementAttributes.getName()); //$NON-NLS-1$
logger.info(prefix + "Parameter allowsNull: " + dataElementAttributes.allowsNull()); //$NON-NLS-1$
logger.info(prefix + "Parameter defaultValue: " + elementAttributes.getDefaultScalarValue()); //$NON-NLS-1$
}
}
}