`
lzqustc
  • 浏览: 211028 次
  • 性别: Icon_minigender_1
  • 来自: 厦门
社区版块
存档分类
最新评论

Perl之Spreadsheet::WriteExcel

阅读更多

一般导出excel功能是出现在后台管理系统中,运营人员为了便于统计,经常需要将大量数据导出。

本文主要描述如何将mongodb查询出来的数据写入excel表格。

 

一、安装相关模块:

1、MongoDB  -> 操作数据库

接口文档https://metacpan.org/pod/distribution/MongoDB/lib/MongoDB/Tutorial.pod

 

2、Spreadsheet::WriteExcel  -> 操作excel

接口文档https://metacpan.org/pod/Spreadsheet::WriteExcel

 

3、Try::Tiny  -> try-catch功能

4、Safe::Isa  -> try-catch功能

 

安装方法:

sudo perl -MCPAN -e 'install MongoDB'

sudo perl -MCPAN -e 'install Spreadsheet::WriteExcel'

 

或者 

perl -MCPAN -e shell

cpan[1]> install MongoDB

 

或者

下载源码包MongoDB-v1.4.5.tar.gz

解压tar xvf MongoDB-v1.4.5.tar.gz, 

cd MongoDB-v1.4.5/

perl Makefile.PL

make

make install

 

二、本文方案

web前端将运营者的输入条件POST给服务端的CGI脚本,CGI脚本解析请求后,根据规则查表,写入excel,同时将excel文件放到可下载的目录,完成后返回下载链接给web前端。

 

三、代码片段

对于一个后台管理系统,可能会在很多地方需要用到导出excel功能,而且运营者通常需要加入查询/过滤条件,同时只要求返回特定的字段。所以,本文尽量写个通用的版本,以供参考。

#excel.pl  - CGI脚本

use warnings;

use utf8;

binmode(STDIN, ':encoding(utf8)');

binmode(STDOUT, ':encoding(utf8)');

binmode(STDERR, ':encoding(utf8)');

==》 以上解决中文问题(要求数据库表里的内容也是utf8格式)

 

use CGI;

use JSON;    #解析web前端的post请求

use Encode;  #查询条件可能带中文,需要utf8编码

use MongoDB;

use Try::Tiny;

use Safe::Isa;

use Spreadsheet::WriteExcel;

use Time::HiRes qw(gettimeofday usleep);

use Data::Dumper;

 

my $OUTPUT = '{"file_path":"", "status":"failed"}';  #返回给web前端的结果

my $DOWNLOAD_ROOT = "/tmp/download"; #excel文件所在目录

my $DB_NAME = "TEST";

my $DB_OPTIONS = {

username => "db",

        password => "123"

};

my $DB_HOSTS = "mongodb://localhost";  # 默认mongodb装在本机,端口号27017, 也可以是ip加端口号"mongodb://116.5.100.152:27000", 具体参考MongoDB的接口文档

 

$ROW_COLUM_SET = { #表格设置

abc_list => { #对应后台的某个功能

collection => "abc", #对应表名称

search => { #查询条件

title => {db_key => "title", regex => "true"}, #db_key对应数据库字段, format是否正则匹配方式

day => {db_key => "start_time", regex => "false"},

default_query => {tag=> "myself"}  #默认的查询条件

},

row_colum => { #表头设置

"ID" => {db_key => "_id", format => "string"}, #db_key对应数据库字段, format字段数据类型

"标题" => {db_key => "title", format => "string"},

"图片" => {db_key => "image_fid", format => "string"},

"链接" => {db_key => "url", format => "string"},

"时间" => {db_key => "start_time", format => "time"}

}

},

 

xyz_list => { #对应后台的某个功能

collection => "xyz", #对应表名称

search => { #查询条件

person_account => {db_key => "person_account", regex => "true"}, 

status => {db_key => "exchge_status", regex => "false"}

},

row_colum => {

"记录ID" => {db_key => "_id", format => "string"}

"日期" => {db_key => "et", format => "time"},

"用户号码" => {db_key => "person_account", format => "string"}

"状态" => {db_key => "status", format => "string"}

},

special_func => \&xyz_list #需要调用特定函数处理(函数指针方式

}

 

};

 

###CGI处理POST请求####

# web前端post过来的数据: {"methond":"abc_list", "search_condition":{"title":"历史"}}

if ($cgi->param("POSTDATA")) {

my $post_data = $cgi->param("POSTDATA");

my $input_json = $json->decode($post_data);

my $methond = $input_json->{methond};

if (length($methond) ) {

if (!$ROW_COLUM_SET->{$methond}) {

write_log("input.log", "Not implement: $methond");

print_result($OUTPUT);

}

#连接数据库

my $client;

my $db;

try {

$client = MongoDB->connect($DB_HOSTS, $DB_OPTIONS);

} catch {

if ( $_->$_isa("MongoDB::AuthError" ) ) {

write_log("db.log", "MongoDB::AuthError");

} elsif ( $_->$_isa("MongoDB::ConnectionError" ) ) {

write_log("db.log", "MongoDB::ConnectionError");

}

print_result($OUTPUT);

};

 

try {

$db = $client->get_database($DB_NAME );

} catch {

if ( $_->$_isa("MongoDB::DatabaseError" ) ) {

write_log("db.log", "MongoDB::DatabaseError");

}

print_result($OUTPUT);

};

 

#获取数据

my $collection = $ROW_COLUM_SET->{$methond}->{collection};

my $search = $ROW_COLUM_SET->{$methond}->{search};

 

write_log("db.log", "Set Query hash of $collection");

my $queryHash;

foreach my $cod (keys %{$search}) {

if ($cod eq "default_query") { #默认查询条件赋值

foreach my $k (keys %{ $search->{$cod} }) {

$queryHash->{$k} = $search->{$cod}->{$k};

}

} elsif (length($input_json->{search_condition}->{$cod})) { #前端输入的查询条件

#处理中文

my $value = Encode::decode("utf-8", $input_json->{search_condition}->{$cod}); 

my $db_key = $search->{$cod}->{db_key};

$queryHash->{$db_key} = $value;

if ($search->{$cod}->{db_key} eq "true") { #需要正则匹配

$queryHash->{$db_key} = {'$regex'=> $value};

}

}

}

my @result = ();  #数据放入数组中

               #是否需要调用特定函数来查询, 利用了函数指针

my $func_ref = $ROW_COLUM_SET->{$methond}->{special_func};

if ((ref($func_ref) eq "CODE") && defined(&{$func_ref}) ) {

@result = &{$func_ref}($db, $queryHash); #调用特定函数查询

} else {

my $mocl = $db->get_collection($collection)->find($queryHash);

@result = $mocl->all();

}

 

#填充表格

               my $FILE_ID = time().int(rand(10000)).".xls";  #生成一个随机名字

my $xls_name = "$DOWNLOAD_ROOT/$FILE_ID";

 

my $workbook = Spreadsheet::WriteExcel->new($xls_name);

$worksheet = $workbook->add_worksheet();

 

write_log("db.log", "---Start write---\n");

#写标题

my $row_colum = $ROW_COLUM_SET->{$methond}->{row_colum};

my $colum_id = 0;

foreach my $k (keys %{ $row_colum }) {

$worksheet->write(0, $colum_id, $k); #写入第一行

$colum_id++; #列递增

}

 

write_log("db.log", "Finish wirte title\n");

#写内容

my $row_id = 1; #从第二行开始

foreach my $obj (@result) {

next if(!$obj);

$colum_id = 0;

foreach my $k (keys %{ $row_colum }) {

my $db_key = $row_colum->{$k}->{db_key};

my $content = $obj->{$db_key};

if (length($content) == 0) {

$content = "NULL";

} elsif ($row_colum->{$k}->{format} eq  "time") { #数据类型处理

$content = formateTime($content);

} elsif ($row_colum->{$k}->{format} eq  "float") {#数据类型处理

$content = formateFloat($content);

}

$worksheet->write($row_id, $colum_id, $content);

$colum_id++;

}

$row_id++;

}

 

$workbook->close();

my $file_path = "http://xxx/$FILE_ID";

$OUTPUT = '{"file_path":"'.$file_path.'", "status":"success"}'; #输出结果

print_result($OUTPUT);

}

}

 

exit;

 

#########################相关子函数#####################

sub print_result {

my $output = $_[0];

print "Access-Control-Allow-Origin: *\r\n";

print "Content-Type: application/json\r\n\r\n";

print $output;

exit;

}

 

sub formateTime { 

my $time1 = $_[0] + 0;

my ($sec,$min,$hour,$day,$month,$year,$wday,$yday,$isdst) = localtime($time1);

$year = $year + 1900;

$month = $month + 1;

return "$year/$month/$day $hour:$min:$sec";

}

 

sub formateFloat { 

my $float = $_[0];

 

$float = sprintf("%.2f", $float);

return $float;

}

 

sub xyz_list {

my ($db, $query_hash) = @_;

 

my @result_list = ();

....

return @result_list;

}

分享到:
评论

相关推荐

    Spreadsheet-WriteExcel-2.15.tar.rar

    标题中的"Spreadsheet-WriteExcel-2.15.tar.rar"是一个软件库的打包文件,主要用于Perl语言,目的是为了能够创建和写入Excel文件。这个版本是2.15,通常意味着它包含了该库的最新功能和修复。".tar"和".rar"都是压缩...

    Spreadsheet-WriteExcel-2.40 .tar.gz

    Spreadsheet::WriteEXcel安装包 下载 Spreadsheet-WriteExcel-2.40.tar.gz并解压在DBI-1.13中 和安装cpan一样,在目录中执行以下操作: perl Makefile.PL make make test make install make clean

    perl Spreadsheet

    除了这两个主要模块,还有一些其他的Perl模块扩展了Spreadsheet的功能,如Spreadsheet::ParseXLSX用于处理.xlsx格式,Spreadsheet::WriteExcel::Utilities提供了一些辅助功能,比如将数组转换成Excel格式。...

    Spreadsheet-ParseExcel-0.65.tar.gz

    Spreadsheet-ParseExcel,Perl的Excel插件,可用于读写Excel文件,在Linux下对...可以用Spreadsheet::ParseExcel先解析excel,再用Spreadsheet::WriteExcel写入。 或者直接使用Spreadsheet::ParseExcel::SaveParser。

    Perl SpreadSheet_Excel

    Perl SpreadSheet_Excel 是一个基于Perl编程语言的库,用于解析和操作Microsoft Excel电子表格文件。这个库的核心组件是 `...通过 `Spreadsheet::WriteExcel` 这样的配套模块,还可以实现Excel文件的写入功能。

    perl Excel操作

    除了这两个核心模块,还有其他一些扩展模块,如Spreadsheet::WriteExcel::Simple用于简化写入过程,或者Spreadsheet::XLSX::Reader::Simple用于简化读取过程。这些模块可以帮助开发者更高效地处理Excel文件。 在...

    Perl读写excel

    这些库主要是Spreadsheet::WriteExcel和Spreadsheet::ParseExcel,它们为Perl开发者提供了方便的API,使得在不依赖Microsoft Office的情况下,也能处理Excel数据。 1. **Spreadsheet::WriteExcel**: 这个模块允许...

    perl 模块(spreadsheet、XML::Simple、DBB::mysql等模块)

    在Perl中,你可以使用Spreadsheet::ParseXLSX或Spreadsheet::WriteExcel等子模块来处理Microsoft Excel格式的文件。例如,你可以读取一个现有的Excel文件,修改其中的数据,然后重新保存。这对于数据分析、报告生成...

    用Perl操作Excel2007 (xlsx) with Excel-Writer-XLSXL

    对于需要与Microsoft Office 2007及以上版本兼容的.xlsx格式文件交互的任务,Perl社区提供了多个库,其中“Excel::Writer::XLSX”是处理.xlsx文件的首选工具之一。 #### 核心知识点详解: ##### Excel::Writer::...

    perl解析excel文件

    Perl提供了多种库来处理这种任务,其中最常用的是Spreadsheet::ParseXLSX和Spreadsheet::WriteExcel。 1. **Spreadsheet::ParseXLSX**:这是Perl中用于读取Excel 2007及以上版本(.xlsx文件)的库。它不依赖...

    perl-site的压缩包

    2. Spreadsheet::WriteExcel:这是一个用于创建老版 Excel 文件(.xls)的模块。如果你需要生成新的 Excel 文件或向现有文件写入数据,这个模块将派上用场。它可以创建工作表、格式化单元格、添加公式等。 在实际...

    Spreadsheet-ParseExcel-0.59.tar.gz

    描述中提到的"for linux perl, can read and write for excel file, very easy to use it"意味着这个模块在Linux操作系统下运行,并且具备读写Excel文件的能力。Perl是一种跨平台的脚本语言,因此Spreadsheet::...

    perl操作office

    例如,`Office::ParseXLS`模块用于解析Excel文件,而`Spreadsheet::WriteExcel`模块则可以用来创建新的Excel文件或者写入数据到已有的Excel文件中。对于Word文档,`Win32::OLE`模块允许通过COM接口与Word应用程序...

    perl操作Excel示例

    `Spreadsheet::WriteExcel`是一个用于创建Microsoft Excel (XLS)工作簿的Perl模块。它可以创建纯Excel 95/97/2000/2003文件,不需要安装任何其他软件或库。该模块支持多种功能,包括但不限于: - 创建新的Excel文件...

    Perl中使用Win32_OLE模块读写Excel的方法1

    5. **广泛支持**:Perl社区庞大,有大量的模块和资源可供使用,包括处理Excel的其他模块如Spreadsheet::WriteExcel、Spreadsheet::ParseExcel等,为开发者提供了丰富的选择。 **使用Win32::OLE模块操作Excel的基本...

    TCOM学习资料

    set workbook [::Spreadsheet::WriteExcel::new "example.xls"] ``` 然后,向工作簿中添加工作表: ```tcl set worksheet [$workbook addWorksheet "Sheet1"] ``` 接着,写入数据到工作表中: ```tcl $worksheet ...

    QTxlsx库和需要的perl安装文件

    在Perl编程语言中,虽然有多种处理Excel文件的模块,如Spreadsheet::WriteExcel,但对于已经习惯使用Qt库的开发者来说,QTxlsx可能是一个更自然的选择,特别是当他们的项目已经依赖于Qt库时。 Perl是一种功能强大的...

    excel_Perl_源码

    例如,`Text::CSV`模块用于读取和写入CSV文件,而`Spreadsheet::WriteExcel`或`Excel::Writer::XLSX`模块则用于创建Excel文件。以下是一个基本的流程概述: 1. **数据提取**: - 使用`Text::CSV`打开和解析数据...

    writeexcel:ruby gem用于写入跨平台Excel二进制文件

    该库是从Perl的Spreadsheet :: WriteExcel模块转换而来的。 / 原始说明如下: The Spreadsheet::WriteExcel module can be used to create a cross- platform Excel binary file. Multiple worksheets can be ...

    Perl在电信网管的简单应用.pptx

    Perl的`Spreadsheet`模块如`Spreadsheet::WriteExcel`或`Spreadsheet::ParseExcel`可以帮助将数据转化为符合标准格式的报表,例如将数据导出为MIS系统所需的格式。这样可以避免手动操作,减少错误并提高效率。 3. *...

Global site tag (gtag.js) - Google Analytics