/*
* Copyright (C) 2002 Erik Swenson - erik@oreports.com
*
* This program 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 of the License, or (at your option)
* any later version.
*
* 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 General Public License for
* more details.
*
* You should have reserved a copy of the GNU General Public License along with
* this program; if not, write to the Free Software Foundation, Inc., 59 Temple
* Place - Suite 330, Boston, MA 02111-1307, USA.
*
*/
package org.efs.openreports.providers.impl;
import java.math.BigDecimal;
import java.sql.*;
import java.util.*;
import org.apache.log4j.Logger;
import org.efs.openreports.objects.*;
import org.efs.openreports.providers.*;
import org.efs.openreports.util.*;
import org.hibernate.Criteria;
import org.hibernate.HibernateException;
import org.hibernate.Session;
import org.hibernate.criterion.Restrictions;
public class ParameterProviderImpl implements ParameterProvider
{
protected static Logger log =
Logger.getLogger(ParameterProviderImpl.class.getName());
private DataSourceProvider dataSourceProvider;
private DateProvider dateProvider;
private HibernateProvider hibernateProvider;
public ParameterProviderImpl(DataSourceProvider dataSourceProvider, DateProvider dateProvider, HibernateProvider hibernateProvider) throws ProviderException
{
this.dataSourceProvider = dataSourceProvider;
this.dateProvider = dateProvider;
this.hibernateProvider = hibernateProvider;
log.info("Created");
}
public ReportParameterValue[] getParamValues(
ReportParameter reportParameter,
Map<String,Object> parameters)
throws ProviderException
{
if (reportParameter.getType().equals(ReportParameter.QUERY_PARAM))
{
return getParamValuesFromDataSource(reportParameter, parameters);
}
else if (reportParameter.getType().equals(ReportParameter.LIST_PARAM))
{
return parseListValues(reportParameter);
}
else if (reportParameter.getType().equals(ReportParameter.BOOLEAN_PARAM))
{
// default to Yes/No
if (reportParameter.getData() == null || reportParameter.getData().indexOf("|") == -1)
{
reportParameter.setData("true:Yes|false:No");
}
return parseListValues(reportParameter);
}
throw new ProviderException(
reportParameter.getName()
+ ": param-type "
+ reportParameter.getType()
+ " not supported!");
}
protected ReportParameterValue[] parseListValues(ReportParameter reportParameter)
throws ProviderException
{
StringTokenizer st =
new StringTokenizer(reportParameter.getData(), "|");
ReportParameterValue[] values =
new ReportParameterValue[st.countTokens()];
int index = 0;
while (st.hasMoreTokens())
{
String token = st.nextToken();
String id = token;
String description = token;
StringTokenizer paramValue = new StringTokenizer(token,":");
if (paramValue.countTokens() == 2)
{
id = paramValue.nextToken();
description = paramValue.nextToken();
}
try
{
if (reportParameter.getClassName().equals("java.lang.Integer"))
{
values[index] =
new ReportParameterValue(Integer.valueOf(id), description);
}
else if (
reportParameter.getClassName().equals("java.lang.Double"))
{
values[index] =
new ReportParameterValue(Double.valueOf(id), description);
}
else if (
reportParameter.getClassName().equals("java.lang.Long"))
{
values[index] =
new ReportParameterValue(Long.valueOf(id), description);
}
else if (
reportParameter.getClassName().equals(
"java.math.BigDecimal"))
{
values[index] =
new ReportParameterValue(new BigDecimal(id), description);
}
else
{
values[index] = new ReportParameterValue(id, description);
}
}
catch (Exception e)
{
throw new ProviderException(
reportParameter.getData()
+ " contains invalid "
+ reportParameter.getClassName());
}
index++;
}
return values;
}
protected ReportParameterValue[] getParamValuesFromDataSource(
ReportParameter param,
Map<String,Object> parameters)
throws ProviderException
{
Connection conn = null;
PreparedStatement pStmt = null;
ResultSet rs = null;
try
{
ReportDataSource dataSource = param.getDataSource();
conn = dataSourceProvider.getConnection(dataSource.getId());
if (parameters == null || parameters.isEmpty())
{
pStmt = conn.prepareStatement(param.getData());
}
else
{}
rs = pStmt.executeQuery();
ResultSetMetaData rsMetaData = rs.getMetaData();
boolean multipleColumns = false;
if (rsMetaData.getColumnCount() > 1)
multipleColumns = true;
ArrayList<ReportParameterValue> v = new ArrayList<ReportParameterValue>();
while (rs.next())
{
ReportParameterValue value = new ReportParameterValue();
if (param.getClassName().equals("java.lang.String"))
{
value.setId(rs.getString(1));
}
else if (param.getClassName().equals("java.lang.Double"))
{
value.setId(new Double(rs.getDouble(1)));
}
else if (param.getClassName().equals("java.lang.Integer"))
{
value.setId(new Integer(rs.getInt(1)));
}
else if (param.getClassName().equals("java.lang.Long"))
{
value.setId(new Long(rs.getLong(1)));
}
else if (param.getClassName().equals("java.math.BigDecimal"))
{
value.setId(rs.getBigDecimal(1));
}
else if (param.getClassName().equals("java.util.Date"))
{
value.setId(rs.getDate(1));
}
else if (param.getClassName().equals("java.sql.Date"))
{
value.setId(rs.getDate(1));
}
else if (param.getClassName().equals("java.sql.Timestamp"))
{
value.setId(rs.getTimestamp(1));
}
if (multipleColumns)
{
value.setDescription(rs.getString(2));
}
v.add(value);
}
rs.close();
ReportParameterValue[] values = new ReportParameterValue[v.size()];
v.toArray(values);
return values;
}
catch (Exception e)
{
throw new ProviderException(
"Error retreiving param values from database: "
+ e.getMessage());
}
finally
{
try
{
if (pStmt != null)
pStmt.close();
if (conn != null)
conn.close();
}
catch (Exception c)
{
log.error("Error closing");
}
}
}
protected void validateParameter(ReportParameter parameter, String value)
throws ProviderException
{
try
{
if (parameter.getClassName().equals("java.lang.Double"))
{
new Double(value);
}
else if (parameter.getClassName().equals("java.lang.Integer"))
{
new Integer(value);
}
else if (parameter.getClassName().equals("java.lang.Long"))
{
new Long(value);
}
else if (parameter.getClassName().equals("java.math.BigDecimal"))
{
new BigDecimal(value);
}
else if (
parameter.getClassName().equals("java.util.Date")
|| parameter.getClassName().equals("java.sql.Date")
|| parameter.getClassName().equals("java.sql.Timestamp"))
{
try
{
dateProvider.parseDate(value);
}
catch (Exception e)
{
throw new ProviderException(e.getMessage());
}
}
}
catch (Exception e)
{
throw new ProviderException(
parameter.getDescription() + " Invalid: " + e.getMessage());
}
}
protected Object parseParameter(ReportParameter parameter, String value)
throws ProviderException
{
try
{
if (parameter.getClassName().equals("java.lang.String"))
{
return value;
}
else if (parameter.getClassName().equals("java.lang.Double"))
{
return new Double(value);
}
else if (parameter.getClassName().equals("java.lang.Integer"))
{
return new Integer(value);
}
else if (parameter.getClassName().equals("java.lang.Long"))
{
return new Long(value);
}
else if (parameter.getClassName().equals("java.math.BigDecimal"))
{
return new BigDecimal(value);
}
else if (parameter.getClassName().equals("java.util.Date"))
{
return dateProvider.parseDate(value);
}
else if (parameter.getClassName().equals("java.sql.Date"))
{
return dateProvider.parseDate(value);
}
else if (parameter.getClassName().equals("java.sql.Timestamp"))
{
long time = dateProvider.parseDate(value).getTime();
return new Timestamp(time);
}
else if (parameter.getClassName().equals("java.lang.Boolean"))
{
return new Boolean(value);
}
}
catch (Exception e)
{
throw new ProviderException(
parameter.getName() + " Invalid: " + e.getMessage());
}
throw new ProviderException(
parameter.getName() + " currently unsupported!");
}
public List<ReportParameter> getReportParameters(Report report, String type)
throws ProviderException
{
List<ReportParameter> parameters = new ArrayList<ReportParameter>();
List<ReportParameterMap> allParameters = report.getParameters();
if (allParameters != null)
{
Iterator<ReportParameterMap> iterator = allParameters.iterator();
while (iterator.hasNext())
{
ReportParameterMap rpMap = iterator.next();
if (rpMap.getReportParameter().getType().equals(type))
{
parameters.add(rpMap.getReportParameter());
}
}
}
return parameters;
}
public void loadReportParameterValues(
List<ReportParameterMap> reportParameters,
Map<String,Object> parameters)
throws ProviderException
{
for (int i = 0; i < reportParameters.size(); i++)
{
ReportParameterMap rpMap = reportParameters.get(i);
ReportParameter rp = rpMap.getReportParameter();
try
{
if (rp.getType().equals(ReportParameter.LIST_PARAM)
|| rp.getType().equals(ReportParameter.QUERY_PARAM)
|| rp.getType().equals(ReportParameter.BOOLEAN_PARAM))
{
if (rp.getValues() == null) // only load once...
{
log.debug("loading parameter values: " + rp.getName());
rp.setValues(getParamValues(rp, parameters));
}
}
}
catch (Exception e)
{
log.error("Error loading parameter values: " + rp.getName());
throw new ProviderException(
"loadReportParameterValues: " + e.getMessage());
}
}
}
public Map<String,Object> getReportParametersMap(List<ReportParameterMap> reportParameters, Map<String,Object> origParameters) throws ProviderException
{
Map<String,Object> map = new HashMap<String,Object>();
// if multiple selections, use origParameters; otherwise, use
// parameters
Map<String,Object> parameters = new SingleValueMap(origParameters);
Iterator<ReportParameterMap> iterator = reportParameters.iterator();
while (iterator.hasNext())
{
ReportParameterMap rpMap = iterator.next();
ReportParameter reportParameter = rpMap.getReportParameter();
// if we are expecting multiple selections, convert the array of
// parameters
// into a comma-delimited string so that it can be used in the SQL
// where
// clause. Otherwise, just expect a simple String
if (reportParameter.isMultipleSelect())
{
Object[] values =
(String[]) origParameters.get(reportParameter.getName());
// load up the StringBuffer with the multiple selections.
String s = buildMultipleSelectString(reportParameter, values);
// save the parameter into the Map
if (rpMap.isRequired() || s.length() > 0)
{
map.put(reportParameter.getName(), s);
log.debug(
reportParameter.getName()
+ " => "
+ map.get(reportParameter.getName()));
}
}
else
{
String value =
(String) parameters.get(reportParameter.getName());
if (value != null)
{
try
{
Object object = parseParameter(reportParameter, value);
if (rpMap.isRequired() || value.length() > 0)
{
map.put(reportParameter.getName(), object);
}
}
catch (Exception e)
{
log.warn(
"Error setting parameter: "
+ reportParameter.getName()
+ " : "
+ e.getMessage());
}
}
}
}
// always pass drilldown chart parameter to reports if it exists
String value = (String) parameters.get(ReportChart.DRILLDOWN_PARAMETER);
if (value != null) map.put(ReportChart.DRILLDOWN_PARAMETER, parameters
.get(ReportChart.DRILLDOWN_PARAMETER));
//
return map;
}
private String buildMultipleSelectString(
ReportParameter reportParameter,
Object[] values)
{
StringBuffer sb = new StringBuffer();
if (values == null || values.length < 1 || values[0].equals("")) return "";
for (int j = 0; j < values.length; j++)
{
String value = "";
if (values[j] instanceof ReportParameterValue)
{
value = ((ReportParameterValue) values[j]).getId().toString();
}
else
{
value = (String) values[j];
}
if (j > 0)
{
sb.append(',');
}
if (reportParameter.getClassName().equals("java.lang.String"))
{
sb.append("'" + value + "'");
}
else
{
sb.append(value);
}
}
return sb.toString();
}
public boolean validateParameters(List<ReportParameterMap> reportParameters, Map<String,Object> parameters)
throws ProviderException
{
parameters = new SingleValueMap(parameters);
if (reportParameters != null && reportParameters.size() > 0)
{
Iterator<ReportParameterMap> iterator = reportParameters.iterator();
while (iterator.hasNext())
{
ReportParameterMap rpMap = iterator.next();
ReportParameter param = rpMap.getReportParameter();
if (!parameters.containsKey(param.getName())
&& rpMap.isRequired())
{
throw new ProviderException(LocalStrings.ERROR_PARAMETER_REQUIRED);
}
if (param.getType().equals(ReportParameter.TEXT_PARAM)
|| param.getType().equals(ReportParameter.DATE_PARAM))
{
String value = (String) parameters.get(param.getName());
if (value != null && value.length() > 0)
{
try
{
validateParameter(param, value);
}
catch (Exception e)
{
throw new ProviderException(e.getMessage());
}
}
else if (rpMap.isRequired())
{
throw new ProviderException(LocalStrings.ERROR_PARAMETER_REQUIRED);
}
}
}
}
return true;
}
public List<ReportParameter> getAvailableParameters(Report report) throws ProviderException
{
List<ReportParameter> parameters = getReportParameters();
Iterator<ReportParameter> iterator = parameters.iterator();
while (iterator.hasNext())
{
ReportParameter rp = iterator.next();
Iterator<ReportParameterMap> reportIterator = report.getParameters().iterator();
while (reportIterator.hasNext())
{
ReportParameterMap rpMap = reportIterator.next();
if (rp.getId().equals(rpMap.getReportParameter().getId()))
{
parameters.remove(rp);
iterator = parameters.iterator();
}
}
}
return parameters;
}
public ReportParameter getReportParameter(Integer id)
throws ProviderException
{
return (ReportParameter) hibernateProvider.load(ReportParameter.class, id);
}
public ReportParameter getReportParameter(String name) throws ProviderException
{
Session session = null;
try
{
session = hibernateProvider.openSession();
Criteria criteria = session.createCriteria(ReportParameter.class);
criteria.add(Restrictions.eq("name", name));
return (ReportParameter) criteria.uniqueResult();
}
catch (HibernateException he)
{
throw new ProviderException(he);
}
finally
{
hibernateProvider.closeSession(session);
}
}
@SuppressWarnings("unchecked")
public List<ReportParameter> getReportParameters() throws ProviderException
{
String fromClause =
"from org.efs.openreports.objects.ReportParameter reportParameter order by reportParameter.name ";
return (List<ReportParameter>) hibernateProvider.query(fromClause);
}
public ReportParameter insertReportParameter(ReportParameter reportParameter)
throws ProviderException
{
return (ReportParameter) hibernateProvider.save(reportParameter);
}
public void updateReportParameter(ReportParameter reportParameter)
throws ProviderException
{
hibernateProvider.update(reportParameter);
}
public void deleteReportParameter(ReportParameter reportParameter)
throws ProviderException
{
try
{
hibernateProvider.delete(reportParameter);
}
catch (ConstraintException ce)
{
throw new ProviderException(LocalStrings.ERROR_PARAMETER_DELETION);
}
}
public void setDataSourceProvider(DataSourceProvider dataSourceProvider)
{
this.dataSourceProvider = dataSourceProvider;
}
public void setDateProvider(DateProvider dateProvider)
{
this.dateProvider = dateProvider;
}
}