自定义函数实现润乾报表call函数功能
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
自定义函数实现报表call函数功能
关键字:自定义增强函数call 存储过程
使用前注意
由于增强函数是授权控制的功能点,所以这种在简单版本下实现增强函数的功能请慎用。本文介绍的方式适用于客户开发时使用的全功能临时授权,而正式购买的版本中无增强函数,销售要求在现有版本上实现增强函数的功能。
使用时可根据实际情况适当采用。
问题背景
某客户购买的报表开发版(无增强套件),而他们在开发报表阶段使用的是全功能临时授权,报表中使用了大量的call query seq等增强函数,正式上线时发现报表不可用,提示使用了增强函数。
客户处已无预算增购增强套件,销售要求在现有版本上实现报表call函数等功能。
问题分析
报表call函数的作用是调用存储过程,并将输出参数返回给报表。可以通过自定义函数,在程序里调用存储过程,并将输出参数作为自定义函数的返回值返回给报表。
所以在自定义函数中要实现如下几块功能:
1、解析自定义函数中的传递的报表表达式参数,如:A1;
2、根据相应参数调用存储过程并接收存储过程输出参数;
3、将输出参数值返回
具体实现
自定义函数名:callProcedure,参数:存储过程名,输入参数
1、接收参数,并解析
// 取得第一个参数,默认为表达式,需要把该表达式算出来,结果才是函数的参数值Expression param1 = (Expression) this.paramList.get(0);
Expression param2 = (Expression) this.paramList.get(1);
// 算出参数值
Object result1 = Variant2.getValue(param1.calculate(ctx, isInput),false, isInput);
Object result2 = Variant2.getValue(param2.calculate(ctx, isInput),false, isInput);
2、调用存储过程
//获取ctx中保存的连接工厂连接
conn = ctx.getConnectionFactory("mysqlProc").getConnection();
//调用存储过程
cstmt = conn.prepareCall("{call "+procName+"(?,?)}");
cstmt.setString(1, inParam);//设置第一个输入参数值
cstmt.registerOutParameter(2, Types.VARCHAR);//将 OUT 参数注册为 JDBC 类型 sqlType
cstmt.execute();
outParam = cstmt.getString(2);//接收输出参数的值
3、将输出参数值返回给报表
return outParam;//函数返回值
源程序:
1、mysql存储过程
create procedure nameProc(
in id varchar(10),
out name varchar(50)
)
begin
set name =CONCAT(id,'aaa');
end
2、自定义函数CallProcedure.java
package customFunction;
import java.sql.CallableStatement;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.sql.Types;
import com.runqian.base4.resources.EngineMessage;
import com.runqian.base4.resources.MessageManager;
import com.runqian.base4.util.ReportError;
import com.runqian.report4.model.expression.Expression;
import com.runqian.report4.model.expression.Function;
import com.runqian.report4.model.expression.Variant2;
import ermodel.Context;
public class CallProcedure extends Function{
public Object calculate(Context ctx, boolean isInput) { /**
*计算报表参数
*/
//判断参数个数
if (this.paramList.size() < 1) {
MessageManager mm = EngineMessage.get();
throw new ReportError("encrypt:"
+ mm.getMessage("function.missingParam"));
}
// 取得第一个参数,默认为表达式,需要把该表达式算出来,结果才是函数的参数值
Expression param1 = (Expression) this.paramList.get(0);
Expression param2 = (Expression) this.paramList.get(1);
if (param1 == null) {// 判断参数是否为空
MessageManager mm = EngineMessage.get();
throw new ReportError("encrypt:"+
mm.getMessage("function.invalidParam"));
}
if (param2 == null) {// 判断参数是否为空
MessageManager mm = EngineMessage.get();
throw new ReportError("encrypt:"+
mm.getMessage("function.invalidParam"));
}
// 算出参数值
Object result1 = Variant2.getValue(param1.calculate(ctx, isInput),false, isInput);
Object result2 = Variant2.getValue(param2.calculate(ctx, isInput),false, isInput);
// 判断第一个参数值是否为空
if (result1 == null) {
return null;
}
if (result2 == null) {
return null;
}
String procName = result1.toString();//存储过程名
String inParam = result2.toString();//输入参数
Connection conn = null;