版本声明:本篇基线为AVEVA E3D Design 3.1(文档版本线存在 1.1 / 2.1 / 3.1,教程统一以 3.1 为准);前代产品AVEVA PDMS 自 2024 年 4 月 1 日起不再销售、不再提供支持。文中 Reporting 能力清单与 Export to Excel 的出处为官方帮助站 Common Functionality Guide(DCFUG),前代版本(1.1)的对应页面同样可达;本篇存在一处必须如实交代的资料空白:官方未提供 Dabacon 的 ODBC/SQL 直连规范。代码示例凡按官方 API 签名构造者,均标注需在本地 E3D Design 环境验证。
一句话结论
报表这件事在 E3D 里有两条路——应用层的 Reporting(含 Batch Reports 与 Export to Excel)与开发层的 .NET 数据库接口;而想用 SQL/ODBC 直连数据库取数是走错了方向,因为 DABACON 是自有面向对象数据库,官方没有提供这类直连规范。
〇、认知问题(读完本篇你应该能回答)
- 官方 Reporting 的能力清单具体包含哪些功能?
- Attributes 窗口的Export to Excel解决的是什么问题?
- 碰撞(Clashes)结果怎么导出?
- 批量报表(Batch Reports)与应用内报表是什么关系?
- DABACON 是什么?为什么不能按关系数据库去理解它?官方有没有提供 ODBC/SQL 直连规范?
- MTO 类报表的字段应该怎么设计?
一、机制解析
1.1 官方 Reporting 的能力清单
官方帮助(Common Functionality Guide)中,Reporting 之下含以下能力(均为官方章节名,可直接作为功能清单引用):
| 能力 | 作用 |
|---|---|
| Simple Reports | 简单报表,开箱即用的一类固定报表 |
| Export | 导出报表结果 |
| Create / Run / Modify / Delete | 报表作业的完整生命周期管理 |
| Dump Attributes | 把属性整批转储出来 |
| Batch Reports | 批量报表——批量化能力的官方落点 |
| DB Listing | 数据库清单类输出 |
| Surface Treatment Report | 表面处理相关报表(专业报表类型) |
| Export to Excel | 导出到 Excel |
| Print Preview | 打印预览 |
| Get All Changes | 取全部变更 |
| Model Changes | 模型变更 |
这张表里有两件事最值得注意:
第一,批量能力是官方内建的(Batch Reports)。这与第 13 篇出图的情况不同——出图侧官方公开文档中未找到批量化 PML API 章节,而报表侧有明确的 Batch Reports。所以报表批处理的第一选择是用官方 Batch Reports,而不是自己从零写调度器。
第二,变更追踪是官方内建的(Model Changes / Get All Changes)。这两个能力解决的是"这批数据从上一版到现在改了什么"。在交付场景里,"变更清单"往往比"全量清单"更值钱——它直接对应"需要复核的范围"。
1.2 属性级导出:Attributes 窗口的 Export to Excel
官方帮助中明确有Attributes 窗口的 “Export to Excel”(出处为 DCFUG 的属性窗口章节)。
它解决的是最日常的取数需求:把当前对象的属性批量拉成表格。工程价值在于:
- 不用写任何代码就能得到一份结构化的属性表;
- 适合作为一次性核对与抽样检查的手段——比如核对"某个 ZONE 下所有支吊架的关键属性是否齐全";
- 适合作为二次开发的"正确答案":你写的导出脚本跑出来的结果,应该能和 Attributes 窗口人工导出的结果对上。
注意区分两件事:Attributes 窗口的 Export to Excel 是应用层的人工能力;程序化导出 Excel 则是开发层的事。这两件事经常被混为一谈,导致有人以为"官方既然能手导 Excel,那一定有导出 Excel 的 API"。
1.3 碰撞结果导出:Print Preview 与 Save to Excel
碰撞(Clashes)结果的导出官方给的是右键菜单路径:Print Preview或Save to Excel(导出为.xls)。
这里值得记住的细节是格式是.xls。在交付环节这意味着两件事:
- 行数限制:
.xls是旧格式,行数有上限,大项目的碰撞结果可能超出,需要考虑拆分或改用其他格式再转换; - 与其他导出能力的一致性:官方在导出这件事上大量采用 Excel 兼容格式,说明"Excel 是交付侧的通用交换格式"这一判断成立——报表与导出的目标格式优先考虑 Excel 系。
1.4 Batch Reports:批量化在哪里
Batch Reports 是官方批量化报表能力的落点。它的定位是"把报表作业成批地跑",与第 13 篇出图的处境形成对照:
| 出图 | 报表 | |
|---|---|---|
| 官方批量化能力 | 公开文档中未找到批量 PML API 章节 | 有 Batch Reports |
| 定制代码该做什么 | 补批处理外壳、做导出核验 | 组织报表作业清单、做结果核验与分发 |
由此得出一个很实用的分工结论:报表批处理先试官方 Batch Reports,只有官方能力覆盖不到的部分(例如结果要进企业系统、要按自定义规则二次加工)才写定制代码。
1.5 DABACON 的定位与那条空白
DABACON = DAtaBAse CONstructor,是 Plant & Marine 的数据库管理系统,用于构建、导航与查询数据库结构;E3D Design 沿用同一 DABACON 引擎(来源性质:DABACON 全称与定位见于第三方行业资料)。
关键事实:DABACON 是自有面向对象数据库,不是 Oracle/SQL Server 这类关系库。
由此引出本篇必须如实交代的空白:
官方未提供 Dabacon 的 ODBC / SQL 直连规范。
这条空白的工程含义非常大:
- "用 SQL 直连数据库取数"这条路,在官方资料里没有依据。你在网上看到的任何"连接字符串 + SQL 查询"方案,都不属于官方路径。
- 官方的取数路径是:开发层用
Aveva.Core.Database.dll(旧代是Pdms.Database.dll)这类 .NET 接口;应用层用Reporting(含 Batch Reports、Export to Excel)。 - 反向说明了一件事:DABACON 的自有对象模型正是
DbElement/DbElementType这套接口存在的理由——如果它是关系库,就不需要这层面向对象的通用元素句柄了。
这就是那个"反直觉点":想直连数据库取数的人容易走错方向,官方取数路径是 .NET 接口与 Reporting,不是 SQL。
1.6 MTO 报表的字段设计
MTO(Material Take-Off,材料表)是工厂设计交付里最典型的一类报表。它的字段设计建议按"四段式"组织:
| 段 | 字段类型 | 说明 |
|---|---|---|
| 定位段 | 项目、区域、装置、管线号 | 让每一行都能被回溯到模型位置 |
| 身份段 | 元件类型、规格等级、材质、口径 | MTO 的核心维度 |
| 数量段 | 数量、单位、长度/面积/体积 | 必须带单位,且单位口径全表统一 |
| 状态段 | 数据版本、提取时间、数据源标识 | 让报表具备"可追溯"属性 |
三条设计纪律:
- 定位段一个字段都不能省。少了管线号,一行材料就没法核对回模型。
- 数量段的单位口径必须全表统一,并且在表头或元数据里声明清楚。单位口径不统一是 MTO 最经典的翻车方式(第 11 篇"不要手工拼单位"说的是同一件事)。
- 状态段必须有。没有"数据版本 + 提取时间"的 MTO,在会议上无法回答"这版数据是什么时候的"。
二、完整代码与逐行剖析
本节代码来源性质:按官方 API 与机制构造,需在本地 E3D Design 环境验证。
2.1 报表作业配置表
批量报表的第一件事是把作业外置(与第 13 篇出图的清单驱动同一思路):
| 字段 | 说明 | 示例形态 |
|---|---|---|
ReportId | 报表作业编号 | RPT-MTO-001 |
ReportType | 报表类型 | MTO / 变更清单 / 属性转储 |
Scope | 数据范围(区域/管线/筛选条件) | 与作业范围字段同构 |
Template | 使用的报表模板名 | 由报表系统管理 |
Format | 输出格式 | Excel 兼容格式优先 |
OutPath | 输出路径(可由ReportId推导) | …\RPT\RPT-MTO-001.xls |
Status | 执行状态 | 待跑 / 成功 / 失败 / 待重跑 |
设计要点与出图清单完全一致:ReportId唯一、OutPath可由ReportId推导,这样"重跑"是幂等的。
2.2 变更清单报表模板(对应 Model Changes / Get All Changes)
变更清单是交付期最有价值的报表,建议固定六列:
| 列 | 含义 | 来源 |
|---|---|---|
| 变更对象全名 | 可回溯到模型位置 | 全名/路径类属性 |
| 对象类型 | BRAN / 支吊架 / 设备等 | 类型属性 |
| 变更类型 | 新增 / 修改 / 删除 | 变更记录 |
| 变更前值 | 旧值 | 变更记录 |
| 变更后值 | 新值 | 变更记录 |
| 变更时间/批次 | 可追溯的批次标识 | 变更记录 |
列设计的关键:"变更前值—变更后值"必须成对出现。只有"变更后值"的清单无法复核——这一点与第 08 篇批量改写要求"变更前后对照"是同一个道理。
2.3 用 .NET 接口程序化取数并落 CSV/Excel 兼容格式
当官方 Reporting 覆盖不到(例如结果要进企业系统、要按自定义规则二次加工)时,走 .NET 接口:
// 14-01-export-mto.cs// 代码来源性质:按官方 NCUG 4.05 记载的 DbElement 机制构造,// 需在本地 E3D Design 环境验证。// 说明:取值方法名与属性实例成员名以本机 Aveva.Core.Database.dll// 的 IntelliSense 与 NCUG 4.05 章节为准;// 导出格式用 CSV(Excel 可直接打开),避免依赖第三方 Excel 组件。usingSystem;usingSystem.Collections.Generic;usingSystem.IO;usingSystem.Text;usingAveva.Core.Database;// DbElement 等核心类// 批量筛选使用 Filters/Iterators,相关类型位于 Aveva.Core.Database.Filters.dll// (具体构造方法名请按本机 IntelliSense 与 NCUG 4.05 的 Filters/Iterators 章节补全)namespaceMyCompany.E3DReport{publicstaticclassMtoExport{/// <summary>/// 把一批元素导出为 MTO 雏形 CSV。/// 关键点:/// 1) 每个元素都要判空(GetElement 取不到返回 null,不抛异常);/// 2) 数量列必须带单位口径声明(写在表头或元数据里);/// 3) 状态段必须有(数据版本 + 提取时间)。/// </summary>publicstaticvoidExport(IList<DbElement>elements,stringoutPath,stringdataVersion){// UTF8 带 BOM:Excel 打开中文不乱码using(StreamWriterw=newStreamWriter(outPath,false,newUTF8Encoding(true))){// 定位段 + 身份段 + 数量段 + 状态段w.WriteLine("Area,Pipeline,ItemType,Spec,Size,Quantity,Unit,DataVersion,ExtractTime");stringextractTime=DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss");foreach(DbElementeinelements){// 判空:批量集合里可能混入取元素失败留下的 nullif(e==null){continue;}// 以下取值方法名以本机为准(按官方 API 签名构造)stringtype=e.GetString(DbAttributeInstance.TYPE);// 身份段:元件类型stringname=e.GetString(DbAttributeInstance.NAME);// 定位段:名称stringfull=e.GetString(DbAttributeInstance.FLNN);// 定位段:全名// 数量段:这里只演示组织方式;// 真实数量必须来自本机的数值属性并经单位格式化对象输出,// 不要手工拼单位(见 DbUnits / DbDoubleUnits / DbDimension / DbFormat)doubleqty=1.0;// 定位段的区域/管线应从上级元素推导,而不是从全名里截字符串w.WriteLine(Escape("(从上级推导)")+","+// AreaEscape("(从上级推导)")+","+// PipelineEscape(type)+","+// ItemTypeEscape("(从规格属性取)")+","+// SpecEscape("(从口径属性取)")+","+// Sizeqty.ToString("0.###")+","+// QuantityEscape("EA")+","+// Unit:全表统一口径Escape(dataVersion)+","+// 状态段:数据版本Escape(extractTime));// 状态段:提取时间// 全名不建议直接进数量表,但可用于核对;如需保留可另加一列_=name+full;}}}/// <summary>CSV 转义:含逗号/引号/换行时用双引号包裹。</summary>privatestaticstringEscape(stringv){if(string.IsNullOrEmpty(v)){return"";}if(v.IndexOf(',')>=0||v.IndexOf('"')>=0||v.IndexOf('\n')>=0){return"\""+v.Replace("\"","\"\"")+"\"";}returnv;}}}2.4 逐行剖析
using Aveva.Core.Database;:DbElement在这里;批量筛选的 Filters/Iterators 在Aveva.Core.Database.Filters.dll(对应命名空间以本机为准)。if (e == null) { continue; }:再次强调判空。DbElement.GetElement()取不到时返回null而不是抛异常,批量集合里混入null是常态。e.GetString(DbAttributeInstance.TYPE)等:取值方法名与属性实例成员名以本机为准。这是本篇唯一需要你亲自核对签名的地方。double qty = 1.0;上方的注释是刻意留的纪律声明:真实数量必须来自数值属性并经过单位格式化对象输出。手工拼单位是 MTO 的经典事故(模型用毫米、报表写成英寸),官方为此专门提供了DbUnits/DbDoubleUnits/DbDimension/DbFormat这一组类。- 用
"(从上级推导)"这类占位字符串,是刻意的诚实标注:区域/管线的推导依赖本机的层级结构,不在示例里假装写死。 Escape(...):CSV 转义不是可选项。元素名称里出现逗号或引号并不罕见,不转义会让整张表的列错位。new UTF8Encoding(true):带 BOM 的 UTF-8,这是让 Excel 正确识别中文的关键一行。
2.5 用官方能力做"正确答案"
程序化导出做完之后,必须用官方能力做一次交叉验证:
- 在 Attributes 窗口对同一批对象用Export to Excel导出一份;
- 与你脚本导出的结果逐字段比对;
- 差异逐条归因(属性名取错?单位口径不同?筛选范围不一致?)。
这一步的价值在于:它把"我觉得对"变成了"两种独立路径给出同一个答案"。第 08 篇的巡检、第 13 篇的出图核验,走的都是同一个方法论。
三、常见报错与排查
3.1 想连数据库却找不到连接方式
- 现象:试图用 ODBC/SQL 连接 DABACON,翻遍官方文档也找不到规范。
- 原因:官方未提供 Dabacon 的 ODBC/SQL 直连规范;DABACON 是自有面向对象数据库,不是关系库。
- 排查:改用官方路径——开发层用
Aveva.Core.Database.dll这类 .NET 接口;应用层用 Reporting(含 Batch Reports 与 Export to Excel)。不要相信网上任何"连接字符串 + SQL"的方案,它们在官方资料里没有依据。
3.2 导出的中文在 Excel 里乱码
- 现象:CSV 用 Excel 打开,中文变成乱码。
- 原因:文件编码与 Excel 的默认解析不一致。
- 排查:写入时使用带 BOM 的 UTF-8(
new UTF8Encoding(true));或者导出为.xls兼容格式(官方多处导出能力都用 Excel 兼容格式,是交付侧的通用交换格式)。
3.3 报表列错位
- 现象:某几行开始列与列对不上。
- 原因:字段值里含逗号或引号,未做转义。
- 排查:所有文本字段一律经过转义函数(见 2.3 的
Escape);不要只在"看起来可能有问题"的字段上转义。
3.4 数量单位口径不统一
- 现象:同一个 MTO 里,长度列混着毫米和米;或重量列的单位来源不明。
- 原因:绕过单位格式化机制、手工拼单位符号。
- 排查:改用
DbUnits/DbDoubleUnits/DbDimension/DbFormat这一组类做"数值 → 字符串"的转换;在表头声明全表单位口径。
3.5 变更清单无法复核
- 现象:项目要求提供变更清单,但你导出的只有"当前值"。
- 原因:报表设计时只设计了"结果状态",没设计"变更前后对照"。
- 排查:改用官方的Model Changes / Get All Changes能力取变更记录;导出模板固定为"变更前值 + 变更后值"成对出现(见 2.2)。
3.6 大项目碰撞结果导出不完整
- 现象:碰撞结果导出到
.xls后发现条数明显少于界面上看到的总数。 - 原因:
.xls是旧格式,行数有上限。 - 排查:按区域/批次拆分导出,或先导出再转为其他格式;导出后必须做条数核对(界面总数 vs 文件行数),这属于第 13 篇"导出后核验"的同一套习惯。
四、动手练习
用官方能力导出一次属性表
选中一批对象,用 Attributes 窗口的Export to Excel导出,检查字段是否齐全、中文是否正常。
判定标准:文件能被 Excel 正常打开;字段与界面展示的属性一致;记录下导出的字段数。做一次双路径交叉验证
对同一批对象,用官方 Export to Excel 与 2.3 的脚本各导一份,逐字段比对。
判定标准:能列出所有差异字段并给出归因(属性名取错/单位口径不同/范围不一致);差异归零或每条差异都有明确解释。设计一份 MTO 报表模板
按 1.6 的四段式设计字段,至少包含 9 列,并写清单位口径声明的位置。
判定标准:定位段字段完整(能回溯到模型位置);数量段单位全表统一;状态段包含数据版本与提取时间。做一份变更清单模板
按 2.2 的六列设计,并用 Model Changes / Get All Changes 取一次数据填进去。
判定标准:每一条变更都有"变更前值—变更后值"成对字段;空值有统一约定(例如用固定符号表示"新增时变更前值为空")。
五、小结与下一篇预告
本篇的结论可以压成两句话:
第一句(能力清单):官方 Reporting 覆盖了 Simple Reports、Export、Create/Run/Modify/Delete、Dump Attributes、Batch Reports、DB Listing、Surface Treatment Report、Export to Excel、Print Preview、Get All Changes、Model Changes;属性级导出有 Attributes 窗口的 Export to Excel;碰撞结果可 Print Preview 或 Save to Excel(.xls)。
第二句(边界):DABACON 是自有面向对象数据库,官方未提供 ODBC/SQL 直连规范——取数的正道是 .NET 接口(Aveva.Core.Database.dll)与应用层 Reporting。
下一篇15 元件库与规格驱动:从"用数据"转向"定义数据"。讲 SCHEMATIC 与 CATALOGUE 两类数据库、Catalogue Explorer、SECT → SCOM → SPCO三层目录结构的真实语义,以及规格驱动设计中那条最重要的性质——违反规格的元件在数据库层被禁止放置,这意味着二次开发绕不过它。
FAQ
Q1:官方 Reporting 的能力清单具体包含哪些功能?
官方帮助(Common Functionality Guide)的 Reporting 之下包含:Simple Reports(简单报表)、Export(导出)、Create / Run / Modify / Delete(报表作业的完整生命周期管理)、Dump Attributes(属性整批转储)、Batch Reports(批量报表)、DB Listing、Surface Treatment Report、Export to Excel、Print Preview、Get All Changes、Model Changes。其中两点最值得注意:批量能力是官方内建的(Batch Reports),所以报表批处理的第一选择是官方能力而不是自建调度器;变更追踪也是官方内建的(Model Changes / Get All Changes),在交付场景里"变更清单"往往比"全量清单"更有价值。
Q2:Attributes 窗口的Export to Excel解决的是什么问题?
它解决最日常的取数需求:把当前对象的属性批量拉成表格,不需要写任何代码。它的三个用途是:作为一次性核对与抽样检查的手段(例如检查某区域内支吊架的关键属性是否齐全);作为二次开发导出脚本的"正确答案"(你写的脚本结果应当能与它对上);作为交付前的快速自检。需要区分的是:这是应用层的人工能力,与"程序化导出 Excel 的开发能力"不是一回事——不能因为界面上能手导 Excel,就推断存在对应的导出 API。
Q3:碰撞(Clashes)结果怎么导出?
官方给出的路径是碰撞网格右键菜单,选择Print Preview或Save to Excel。要注意导出的文件格式是.xls(旧格式),在交付环节有两个后果:一是行数有上限,大项目的碰撞结果可能超出,需要考虑按区域/批次拆分或先导出再转换格式;二是导出后必须做条数核对(界面总数与文件行数比对),不能默认导出完整。这也侧面说明 Excel 兼容格式是交付侧的通用交换格式。
Q4:批量报表(Batch Reports)与应用内报表是什么关系?Batch Reports是官方批量化报表能力的落点,作用是把报表作业成批地跑;应用内报表则是单次、交互式的报表运行与查看。两者的关系是同一套报表能力在"批量"与"交互"两种使用方式上的分工。工程上的结论是:报表批处理先试官方 Batch Reports,只有官方能力覆盖不到的部分(例如结果要进企业系统、要按自定义规则二次加工)才写定制代码——这与出图侧"官方公开文档中未找到批量化 PML API 章节、需要自建批处理外壳"的处境正好相反。
Q5:DABACON 是什么?为什么不能按关系数据库去理解它?官方有没有提供 ODBC/SQL 直连规范?
DABACON 全称DAtaBAse CONstructor,是 Plant & Marine 的数据库管理系统,用于构建、导航与查询数据库结构,E3D Design 沿用同一 DABACON 引擎。它是自有面向对象数据库,而不是 Oracle/SQL Server 这类关系库——这正是DbElement/DbElementType这套面向对象的通用元素接口存在的理由:如果它是关系库,就不需要这一层。官方未提供 Dabacon 的 ODBC / SQL 直连规范,所以"用连接字符串 + SQL 取数"这条路在官方资料里没有依据;官方取数路径是开发层用Aveva.Core.Database.dll这类 .NET 接口,应用层用 Reporting(含 Batch Reports 与 Export to Excel)。
Q6:MTO 类报表的字段应该怎么设计?
建议按四段式设计:定位段(项目、区域、装置、管线号)、身份段(元件类型、规格等级、材质、口径)、数量段(数量、单位、长度/面积/体积)、状态段(数据版本、提取时间、数据源标识)。三条纪律:定位段一个字段都不能省,否则某一行材料无法核对回模型;数量段的单位口径必须全表统一并在表头或元数据中声明(单位口径不统一是 MTO 最经典的翻车方式,正确做法是用单位格式化对象转换而不是手工拼单位);状态段必须有,否则无法回答"这版数据是什么时候的"。