FR+Django实现报表导入DBF数据

DBF格式文件是一种类似于excel的行列式存储且支持sql查询的数据文件,其广泛的应用于事业单位中的数据交换
目前FR不支持DBF格式文件导入,本文介绍使用Django辅助,使得用FR能够导入DBF(甚至任意文件格式)(询问了FR客服,导入DBF功能正在开发,现在是2022年4月份)

基本思路

1.FR填报报表里,插入文件上传插件,让用户上传DBF文件到服务器文件夹
2.上传时,触发JS访问Django接口,Django将DBF文件转换为EXCEL文件
3.设置文件数据集,数据源为2中的EXCEL文件,填报报表页面展示该文件数据集
4.将3中页面展示的数据写入数据库

实现步骤

1.搭建Django服务接口

win10搭建Django教程 view.py如下,使用dbfread库读取DBF文件,使用openpyxl库写入excel文件;xlsx文件的行数上限为1048576行,而DBF文件是由机器内存大小决定(只要内存够大,理论上就没有上限),所以dbf转excel时,要注意下数据量。

#coding = utf-8
# Create your views here.
from django.shortcuts import render
import dbfread, openpyxl
import time
from django.http import HttpResponse
from . import models
def upTransform(request,):
    """接收帆软js传来的get请求,get请求携带一个参数表示需转excel的dbf文件名,依据此参数进行转换"""
    time.sleep(3) #怕FR上传DBF过大,要点时间,这里等3s
    fileName = request.GET.get('fileName')
    table = dbfread.DBF('D:\\FineReport_11.0\\webapps\\webroot\\WEB-INF\\reportlets\\dbf\\'+fileName,encoding='GBK',char_decode_errors='ignore') #读取dbf
    wb = openpyxl.Workbook() #生成excel对象
    wb.create_sheet(index=0, title="sheet1")
    ws = wb.active
    for i in range(len(table.field_names)):
        ws.cell(1, i+1, table.field_names[i]) #写excel表头行
    row = 1
    for line in table:
        row += 1
        col = 0
        for k in line:
            col += 1
            ws.cell(row, col, line[k])        #写excel数据
    wb.save('D:\\FineReport_11.0\\webapps\\webroot\\WEB-INF\\reportlets\\dbf\\'+fileName[:len(fileName)-4]+'.xlsx')
    return HttpResponse("ok")

2.填报报表制作

A2为文件上传插件,注意文件上传插件使用时,只是将操作系统中的文件调入浏览器页面中,要上传还需提交报表(A4提交按钮会负责提交动作,即_g().writeReport();)

python3 dbf模块说明 python操作dbf文件_js


提交设置为上传至服务器,磁盘路径即保存文件路径,该路径即view.py中读dbf的路径;为了区分不同用户上传的dbf,文件名需要唯一(我用的是$fine_username+该cpt文件名+dbf文件名)

python3 dbf模块说明 python操作dbf文件_文件名_02


提交按钮,点击触发js,js作用是提交文件和访问一次Django接口(告诉Django要转换文件了并带上要转换的文件名)

python3 dbf模块说明 python操作dbf文件_文件名_03

//提交文件
_g().writeReport();
//获取dbf文件名,a控件单元格的值是INDEXOFARRAY(filename(A2),1)
var Widget = contentPane.getWidgetByName("a");
var fileName = Widget.getValue();
//带文件名访问Django接口,接口处理逻辑就是view.py;访问成功后跳转xsgl_dbfview.cpt报表,并带上转换后的文件名
FR.ajax({ url: "http://localhost:8080/dbf/upTransform/",type:"GET", data: "fileName="+fine_username+"任务添加学生"+fileName, complete: function(data,textStatus){ window.location =  encodeURI(encodeURI("${servletURL}?viewlet=xxw/xxadmin/xsgl_dbfview.cpt&op=write&fileName="+fine_username+"任务添加学生"+fileName.replace("dbf","xlsx"))); } });

3.xsgl_dbfview.cpt读取转换后的EXCEL

新建文件数据集,读取转换后的文件,读取时文件名用js跳转带的fileName参数的值

python3 dbf模块说明 python操作dbf文件_python3 dbf模块说明_04

4.预览并提交文件数据集数据

把文件数据集数据拖到页面上,就能正常提交入库了

总结

FR是纯java编写的,可以通过插件直接调自己写的java程序,但综合来看还是通过http接口来调用python程序方便。
但前者才是更标准更正规的,甚至有些api只能java调用,比如最近碰到的kettle的任务调度api,只支持java调用,刚好也是个学习java的契机
下一个任务!FR报表实现web调度kettle任务!