转自:http://www.8000hz.com/archives/5.html
第三章:Processing Call Detail Records(处理CDR)
在本章节中将会涵盖
使用CSV CDRS
使用 XML CDRS
将CDR插入到一个后端数据库
使用WEB SERVER 处理CDR
使用event socket 处理CDR
Introduction 介绍
CDR是所有电话系统账单处理的重要组成。它们也是可以用于排错的重要资源。Freeswitch提供多种方法来生成CDR.最普通的方法是创建基于文本的,逗号分割的CSV文件。CSV文件中每一行都描述一通电话(或更准确地说是一个call leg).当然也有其他的方法去处理CDR,最值得一提的就是使用mod_xml_cdr去存储更多更详细的通话信息,也可以使用event_socket去处理CDR信息。
Using CSV CDRs 使用CSV的CDR
存储CSV格式的CDR是非常简单的。下面的方法就是描述使用CSR文件存储通话记录的必要步骤。
准备Getting ready
mod_cdr_csv模块默认已经编译和加载。CDR文件存储在目录$FS_INSTALL/log/cdr-csv/。确定配置是否启用,打开文件 conf/autoload_configs/cdr_csv.conf.xml。下面就是设置中可用的参数。
<settings>
<!– ‘cdr-csv’ will always be appended to log-base –>
<!–<param name=”log-base” value=”/var/log”/>–>
<param name=”default-template” value=”example”/>
<!– This is like the info app but after the call is hung up –>
<!–<param name=”debug” value=”true”/>–>
<param name=”rotate-on-hup” value=”true”/>
<!– may be a b or ab –>
<param name=”legs” value=”a”/>
<!– Only log in Master.csv –>
<!– <param name=”master-file-only” value=”true”/> –>
</settings>
在下面的章节中,我们将会讲解这些参数.
How to do it… 如何看到CDR
最简单的方式去看新CDR是在linux下使用cat或在windows环境下使用type. 另外,如果你在Linux/Unix环境你可以使用tail程序去看文件的结尾。(Windows没有提供tail程序,但是也有另一个免费和开源的方案)
Linux/Unix环境下的步骤:
1. 进入目录/usr/local/freeswitch/log/cdr-csv/
2. 执行tail -f Master.csv去显示新的CDR条目。
3. 打一个测试电话,也许用一个电话打另一个电话。
4. 挂断测试电话和注意新的CDR已经添加到了Master.csv.
5. 使用Ctrl+c去退出tail命令
这里是一个示例的CDR, 1001拨打1007.
“Michael Collins”,”1001″,”1007″,”default”,”2011-03-02 12:09:25″,”2011-
03-02 12:09:26″,”2011-03-02 12:09:29″,”4″,”3″,”NORMAL_
CLEARING”,”f896639c-4508-11e0-a4cb-fb7d5a93c62e”,”f89d504e-4508-11e0-
a4cc-fb7d5a93c62e”,”1001″,”G722″,”G722″
How it works…如何工作
通过查看该文件我们可以获取到写入硬盘中的新的CDR. 但在生产环境中并不是特别的有用, 我们做这个是帮助我们去学习CDR和它们包含的信息。而且,这也是在你使用FS的路上一个简单的排除错误的工具。
There’s more… 不止这些
当使用CSV CDR时还有些东西是需要我们关注的。下面的小节就是帮助你充分的使用它们。
File names and locations 文件名和位置
如果你列出目录log/cdr-csv,你可能会看到除了Master.csv文件外的其他文件。例如,你使用1001打了1007,你会看到一个名叫1001.csv的文件(记住,这个文件名是由用户的directory 配置中的accountcode属性决定).默认,每一个 directory user 都拥有他自己的.csv文件,此文件中只包含他自己的通话记录。这纯粹是一个方便的功能,可以通过设置conf/autoload_configs/cdr_csv.conf.xml 文件中的这个参数来禁用它:
<param name=”master-file-only” value=”true”/>
You may see other fles with date/time stamps in their names like this:
你可能还看到一些包含 日期/时间戳 的文件像这样:
Master.csv.2011-02-24-16-51-06
这些文件是当日志滚动请求发生时创建的。这个行为也可以通过调协下面的参数来改变:
<param name=”rotate-on-hup” value=”false”/>
最后,你可以通过使用base-log参数指定产生cdr-csv文件夹的基础目录。例如,设置<param name=”log-base” value=”/var/log”/>将会强制生成CSV CDR文件到/var/log/cdr-csv文件夹。
当修改了cdr_csv.conf.xml文件中有参数,请确保保存且在fs_cli控制台中执行reload mod_cdr_csv 命令去使修改生效。
Other options 其他选项
在cdr_csv.conf.xml文件的设置部分还有几个其他选项。第一个就是debug。设置debug为true将会把每一个通话结束时都执行一次 information dump(像diaplan中的info application)。
注意不仅产生到fs_cli还有FreeSWITCH的日志文件,请注意磁盘空间。
来说另一个名叫legs有参数. 它决定哪个leg或哪些leg将产生CDR。默认只有A leg(主叫)产生一条CDR。 你可以把这个参数设置成“b”来只记录B leg(被叫)或你可以设置它为”ab”,这样你以收到每个leg的CDR.处理A和B leg稍后会在本章中讨论。
CDR CSV templates CDR CSV 模块
Default-template 参数决定在创建CDR记录时使用哪种模板。注意cdr_csv.conf.xml文件中的<templates>片断。<template>片断中有一些你可以使用和编辑的模板。你也可以你自己的模板。默认我们使用的是example模板。随便更改和编辑default-template 参数去使用不同的模板。Asterisk模块将会产生可供astersik PBX使用的CDR格式。Sql 模板将会产生一种特别有用的格式,我们将会在方法 插入CDR到后端数据库 中讨论。
模板还有另外有一个功能,允许自定义行为。当一个channel中的accountcode变量被设置成了一个模板的名字,那么通话的CDR将会使用名为accountcode模板格式。你可以通过设置一个 directory user 的account code 来测试这个功能:
1. 打开conf/directory/default/1007.xml和设置:
<variable name=”accountcode” value=”sql”/>
2. 保存文件退出。在fs_cli中执行命令reloadxml。
3. 使用1007拨打另一个电话,接听,然后挂断。
4. 现在在你的cdr-csv目录中将会有一个名叫sql.csv的文件。
这个小技巧可以用来定制CDR数据存储的方式。例如,你可能想记录指定终端的一些指定channle变量到CDR文件中,然后,你可能并不希望每一通通话都存储这些信息。使用accountcode和一个CDR CSV 模板允许你按需要来定制行为。
See also 参见
请参阅本章后面――插入CDR到后端的数据库
Using XML CDRs 使用XML CDR
XML CDR 拥有在传统的CSV 平面格式无法简单描述的大量信息。在这个小方法中,我们将会开启mod_xml_cdr 和 讨论它的一些配置选项。
Getting ready 准备
默认的配置中,mod_xml_cdr 已经被编译了但没有启用。使用下面步骤来开启它:
1. 打开 conf/autoload_configs/modules.conf.xml
2. 取消下面一行的注释
<!– <load module=”mod_xml_cdr”/> –>
3.保存文件退出
现在当Freeswitch启动时mod_xml_cdr 将会自动加载。不过,如果Freeswitch已经在运行中了,我们就需要手动来加载它。只需要简单地在fs_cli 中输入命令 load mod_xml_cdr 就能完成加载了。XML CDR 文件将会保存在$FS_INSTALL/log/xml-cdr 文件夹中。
XML CDR有很多的选项,打开文件conf/autoload_configs/xml_cdr.conf.xml 来查看它们。在本节稍后我们将会讨论一部分参数。
How to do it…
查看最新的XML CDR的方式最简单的方法是在Linux/Unix 环境下使用cat,在windows环境下使用type这类的工具(注意,windows 的 Povershell有一个cat的别名)。或者你可以使用像less 这样的翻页工具去查看整个文件。Windows 和 Linux/Unix都支持管道输出到more来达到相同的效果。
下面是你可以在Linux/Unix环境下使用的步骤:
1. 进入目录 /usr/local/freeswitch/log/xml-cdr/
2. 使用ls命令列出目录内容
3. 拨打一个测试电话,也许从一个电话到另一个。
4. 挂断电话,注册类似这样a_uuid.xml 命名的新XML CDR.
5. 输入 less a_uuid.xml 和 按回车键 来查看XML CDR 文件中的内容。
How it works…
通过监视 log/xml-cdr 目录,我们可以获取写入到硬盘的新CDR。在生产环境是就不那么实用了,做这个可以帮助我们了解XML CDR和它们包含的信息。更进一步说,它是一个将来你能用到的简单排错工具。
什么是UUID?
处理CDR,尤其是XML CDR, 会有很多的UUID出现在你面前. UUID的全意是 Universally Unique Identifier (全球唯一标识符号)。它是一个使用连字符(-)分成5部分的32个16进制数字。一个示例UUID 678a195f-8431-4d77-8f10-550f7435f18e。每一个call leg 都会收到一个UUID用来不同于其他的call leg 。
There’s more…
Mod_xml_cdr 模块可以做很多事情,最重要的就是POST 新的XML CDR 信息到一个只是存储CDR到数据库或执行其他计费功能的WEB服务器。
File names and locations
在文件 conf/autoload_configs/xml_cdr.conf.xml文件中的<setting> section 中有两个参数用来影响文件名和文件存储位置。第一个参数就是 prefix-a-leg. 当设置为true的时候, A leg 的XML CDR 的文件名都会有一个”a_”前缀。这样就可以很轻松的区分A leg和B leg 的CDR。另一个参数就是 log-dir, 当设置为一个绝对路径的时候它会改变 /xml-cdr 的保存位置。例如:<param name=”log-dir” value=”/var/log”/>
这样设置会让所有的XML CDR 写到目录 /var/log/xml-cdr 目录中(你也可以把log-dir 设置成相对路径,但很少有人用)
NOTE:当改变了xml_cdr.conf.xml文件中的参数时,请确定保存和通过fs_cli执行命令reload mod_xml_cdr 来使之生效。
Logging the B leg
默认情况下, mod_xml_cdr 只记录A leg (主叫)。如果你希望记录B leg(被叫),那么设置这个参数:
<param name=”log-b-leg” value=”true”/>
这样B leg的 XML CDR 也会被记录。注意 B leg 的CDR 永远命名为uuid.xml,UUID就是通话的真实UUID。没有一个像A leg那样的选项用来配置成以”b_”前缀来命名文件。
See also
在本章的后面,请参阅使用WEB SERVER 处理CDR。
Inserting CDRs into a backend database(插入CDR到后端的数据库)
常常插入CDR信息到一个数据库如MYSQL,POSTGRESQL或其他的数据库是有必要的。FreeSWITCH不支持将CDR直接写入到数据库(不直接写入到数据库这个决定是一个engineering,并不是技术限制)。这个方法讨论一个简单的方法,写一个SQL语句的CSV文件和使用这些CSV文件去更新后台的数据库。
Getting ready
当然,你需要一个数据库去保存你的文件。任何的数据都可以,只要是能使用SQL 语句。为您的CDR创建一个数据库,并允许任何必要的访问权限。这完全由你的数据库类型决定-参阅你的数据库文档来做。
你还需要准备一个存储CDR的表。下面的创建表的语法是适用与PGSQL数据库和cdr_csv.conf.xml配置文件中的SQL模板:
CREATE TABLE cdr (
caller_id_name character varying(30),
caller_id_number character varying(30),
destination_number character varying(30),
context character varying(20),
start_stamp timestamp without time zone,
answer_stamp timestamp without time zone,
end_stamp timestamp without time zone,
duration integer,
billsec integer,
hangup_cause character varying(50),
uuid uuid,
bleg_uuid uuid,
accountcode character varying(10),
read_codec character varying(20),
write_codec character varying(20)
);
适用与MYSQL的生成表语句是:
CREATE TABLE cdr (
caller_id_name varchar(30) DEFAULT NULL,
caller_id_number varchar(30) DEFAULT NULL,
destination_number varchar(30) DEFAULT NULL,
context varchar(20) DEFAULT NULL,
start_stamp datetime DEFAULT NULL,
answer_stamp datetime DEFAULT NULL,
end_stamp datetime DEFAULT NULL,
duration int(11) DEFAULT NULL,
billsec int(11) DEFAULT NULL,
hangup_cause varchar(50) DEFAULT NULL,
uuid varchar(100) DEFAULT NULL,
bleg_uuid varchar(100) DEFAULT NULL,
accountcode varchar(10) DEFAULT NULL,
domain_name varchar(100) DEFAULT NULL
);
在本方法中的所有示例都使用数据库CDR和表CDR。最后一件事就是设置SQL模板为默认的CDR模板。请按照以下步骤操作:
1. 打开文件 conf/autoload_configs/cdr_csv.conf.xml.
2. 改变default-template 参数到<param name=”default-template” value=”sql”/>.
3. 保存文件和退出。在控制台fs_cli中执行命令reload mod_cdr_csv
4. 在fs_cli 中执行 fsctl send_sighup 去rotate(滚动)日志文件。
现在你可以创建和处理CDR了。
How to do it…
按照以下步骤去将一条通话记录插入到你的数据库表中:
1. 从一个电话拨打另一个电话进行测试呼叫,接听,等待一会,然后挂断(Master.csv文件中至少有一条记录)
2 在fs_cli 中执行命令 fsctl send_sighup
3. 列出目录 log/cdr-csv/文件夹中的内容,注意一个 rotated(滚动) Master.csv 文件,例如 Master.csv.2011-03-02-16-25-21.
4. 这个滚动的日志文件就是用来插入通话记录到你的数据库, 根据数据库的不同你需要不同的命令去插入记录. 例如,PGSQL使用下面的命令:
cat Master.csv.2011-03-02-16-44-29 | tr \” \’ | psql -U postgres cdr
5. 使用一个简单的SQL语句 SELECT * FROM cdr 去检查记录是否已经插入到了CDR表中.删除rotated(滚动)日志文件.
How it works…
mod_cdr_csr 的模板sql会把CDR使用SQL语句的格式来保存. 示例记录看起来像这样:
INSERT INTO cdr VALUES (“Michael Collins”,”1001″,”1007″,”defa
ult”,”2011-03-02 17:02:21″,”2011-03-02 17:02:23″,”2011-03-02
17:02:25″,”4″,”2″,”NORMAL_CLEARING”,”e4cfe0b2-4531-11e0-b634-
d7bcff4e7b8a”,”e4d6b072-4531-11e0-b635-d7bcff4e7b8a”, “1001”);
这些SQL语句可以输入到一个基于命令行的数据库客户端. 为了兼容PGSQL使用tr命令转换双引号到单引号.
你的实际生产环境中可能会有不同的需求就像在PGSQL中要使用单引号而非双引号.使用Unix 命令 tr 是处理这类问题的一种方法. 你也可以改变模板文件来使用单引号而非双引号.
最后, 当确定CDR已经成功的插入到了数据库中,我们删除滚动日志. 我们也可以把它们归档到另一个盘符中做个备份.
There’s more…
大多数的系统管理员应该会意识到这里的命令是很容易编写成脚本的.事实上,这也是FreeSWITCH的开发者没有创建一个直接写入到数据库的本地模块原因之一. 直接写到CDR到硬盘然后使用cron 任务计划(或类似的)去执行剩下的所有任务. 把它们分解成离散的任务, 而不是抽象它们在freeswitch的模块中, 可以更轻松的使用现成的方法去创建健壮的,可扩展的解决方案.
事实上, 你可以将存储CDR的数据库装在另一台独立的服务器上, 使用最基本的命令像 fs_cli去滚动日志和SCP或FTP将 通话记录文件下载到本地数据库服务器. 一个智能化的脚本可以在发出问题时通知系统管理员.而且,只要FreeSWITCH 服务器上有磁盘空间, 就算CDR服务器和CDR服务器之间的连接断开也不会有任何的通话记录丢失. CDR将会继续写到FS的硬盘上, 当它们之间的连接重新建立时可以继续收集和处理CDR.
See also
Refer to the Getting familiar with the “fs_cli” interface recipe in Chapter 4
请参考第四章中的小秘方 – 熟悉fs_cli 接口