【分享】BOTP转换对sql查询的支持
金蝶云社区-yangyang0283
yangyang0283
4人赞赏了该文章 2,909次浏览 未经作者许可,禁止转载编辑于2014年06月10日 13:46:38

原文档
---- Kscript支持宏函数
目的
改善Kscript脚本的易用性;
目标
允许通过短名称调用常用函数调用(目前只支持SQL函数);
提供简单易用的sql函数,简化数据库访问。
SQL函数语法
假定,sql是表示SQL语句的变量。
1.#sql_val 从数据库获取一个值(OBJECT);
java.lang.Object value = #sql_value(sql);

2.#sql_row 从数据库获取一行记录(MAP);
java.util.Map row = #sql_row(sql);
注:以SQL语句中的列名的小写形式作为Map的key,对应列的值作为与key关联的值。

3.#sql_col 从数据库表获取多行记录的某一列值(ARRAY);
java.lang.Object[] array = #sql_list(sql);

4.#sql_list 从数据库表获取结果集(由MAP组成的List);
java.util.ArrayList list = #sql_list(sql);
注:list中的每一个元素是一个java.util.Map对象,Map的内容以SQL语句中的列名的小写形式作为Map的key,对应列的值作为与
该key关联的值。

5.#sql_exec 执行修改/插入/删除SQL(返回影响的行数)。
int updated = #sql_exec(sql);

注意以上sql中,不能包含空格或其他字符,并且 必须使用小写形式(原文档上的注释,测试没发现空格的特殊影响)

需要#sql_val 几乎能实现目前所有业务函数!
1.函数举例:
a.弱类型关联函数
公式结果 = __BOTGetProperty(销售出库单.销售出库单分录.核心单据行ID,"entry.taxRate");
可以替换为:
公式结果 = #sql_val("select ftaxRate from **核心单据分录表名称 where fid ='"+销售出库单.销售出库单分录.核心单据行ID+"'");

2.利用sql的集合函数做一些之前没有实现的逻辑!在分录集合处理中能很好利用:
a.金额汇总 以汇总销售出库单分录单位实际成本为例:
公式结果 =#sql_val("select sum(funitactualcost) from t_im_saleissueentry where fparentid='"+销售出库单.ID+"'");
b.使用count()获取某种类型,或某字段值为指定值的分录的条数,在此不举例。

3.性能问题
如上对弱类型关联函数的修改,对于单字段的转换,能够减少查询的数据量(弱类型关联函数会取出整个分录或单据对象)。但是在转换过程中,每个脚本段可能被执行多次,造成不必要的查询重复消耗。对于公式函数,转换引擎有做函数级别的缓存。因此,若使用
sql宏函数代替BOTP原有内置的业务函数,强烈建议增加缓存处理。
处理方法:使用BOTP转换过程中的对象线程缓存BOTObjectCache:
具体公式平台脚本:
var result = com.kingdee.eas.base.botp.util.BOTObjectCache.getInstance(__bosContext).get("_BOTGetProperty"+销售出库单.销售出库单分录.核心单据行ID+"entry.taxRate"); //先从缓存取数
如果(result 不等于 null) {
公式结果 = result;

否则{
result = #sql_val("select ftaxRate from **核心单据分录表名称 where fid ='"+销售出库单.销售出库单分录.核心单据行ID+"'");
com.kingdee.eas.base.botp.util.BOTObjectCache.getInstance(__bosContext).put("_BOTGetProperty"+销售出库单.销售出库单分录.核心单据行ID+"entry.taxRate",result); //将查询结果存入缓存
公式结果 = result;


补充说明:
发现存在宏函数不生效的场景,如新增的“自定义公式”中的测试功能,可通过以下方式处理:
在参数中新增一个“__bosContext” 参数,不设置初始值再点测试即可。