
简介一份面向工业自动化与组态软件学习者的PDF技术笔记解决通过VBS脚本将Access数据库指定记录写入WinCC变量的实操问题也可作为相关考试或技能鉴定的参考资料。文档完整覆盖Access数据库及数据表建立、ODBC数据源配置、ADODB对象连接、SQL查询提取字段以及将结果写入WinCC内部变量的全过程并给出可复用的VBS脚本片段。压缩包共1个文件类型为PDF大小仅18KB篇幅精简、便于快速查阅。目前已有342人学习适合使用WinCC进行数据采集与监控的初学者、工程师以及备考自动化组态类科目的考生阅读参考。文中以完整实例演示VBS脚本调用ADODB对象、执行SQL查询并写入U16Tag1变量涵盖从建库建表、配置DSN到代码调试的关键细节可帮助读者避开常见连接问题和数据写入坑点。1. 一个Access文件怎么变成WinCC画面上会跳动的数值看到“Access数据库数据写入WinCC变量”这个标题第一反应是这不就是上位机组态里最不起眼、却又最绕不开的那条数据链路吗。很多工厂的质检、称重、能耗记录都落在Access文件里MES不愿意开放接口给SCADA现场工程师只能在WinCC这边想办法周期性把数据库里新增的记录读出来写进内部变量再让画面、报警、报表去用。方案看着简单真正跑起来才知道驱动版本、连接串、脚本语法、文件锁哪一环都够折腾一阵。这套东西适合单站WinCC、数据量在每分钟几条到几百条、不想上大型中间件的场景一个VBS脚本就能长期稳定跑这也是很多老工程师最后都走回同一条路的原因。2. WinCC读Access的四种路线我为什么锁定VBS加ADO标题里三个关键词——Access数据库、WinCC、变量——串起来其实是一条数据链路数据源在Access文件里中间要有数据库驱动脚本负责查询最终把结果塞进WinCC内存里的Tag。很多人一上来就问“WinCC能不能直接连Access”能但不是画面控件直接绑数据库而是通过脚本中转。先把这个链路想清楚后面踩坑才有方向。2.1 数据从Access到WinCC变量要经过哪几步Access是文件型数据库整个库就是单个.mdb或.accdb文件结构、数据、索引都在这一个文件里。WinCC本身不认这个文件中间必须靠微软的OLEDB/ODBC驱动去读。WinCC里的入口是全局脚本也就是C脚本或VBS脚本脚本里创建数据库连接对象、执行SQL、拿到记录集再调用HMIRuntime.Tags对象的Write方法把值写进变量。这里的“变量”要分清两种。WinCC有外部变量和内部变量外部变量通过通信驱动连PLC或S7内部变量只是上位机内存里的数据点。数据库来的数据正确做法是先写内部变量画面、报表、归档都读这个内部变量如果PLC也要用再通过中间变量或网关转发不要让脚本去直接怼外部变量的通信通道。刷新机制也得说清楚。WinCC全局脚本不会自己循环跑它要挂在触发器上周期触发器、变量触发器、事件触发器都行。数据库读数据这条链路没有“数据变了”的通知信号通常就用周期触发比如每10秒跑一次。没有触发器脚本写得再对也是摆设。2.2 四条技术路线的对比与取舍从业者方案里Access数据进WinCC变量常见有四条路各有各的适用位置。我把它们放在一起对比新手可以少走弯路熟手也能看看有没有漏掉更省事的选项。路线技术载体优点缺点适合场景VBS脚本 ADOWinCC全局脚本VBS创建ADODB.Connection代码量小调试直观WinCC原生支持解释执行性能一般不适合毫秒级高频访问单站、低频、字段少是最常见做法C脚本 ODBCWinCC C脚本调SQLConnect、SQLExecDirect执行效率高可控性强API繁琐句柄和类型转换容易翻车熟悉C、访问密度高、需要精细控制DataMonitor / OLE DB抽取通过WinCC DataMonitor或报表组件定时取数适合做报表和归档不占系统脚本实时性差配置复杂不适合写变量做日报、趋势分析而非实时刷新数据库同步工具到SQL Server再走OPC UA中间件把Access同步到SQL ServerWinCC用OPC UA连接稳定、支持多站和大数据量链路长延迟高要额外维护同步工具数据量大、有多台上位机、需要历史查询第一和第二条路线的差别本质是VBS和C脚本的差别。WinCC的C脚本里用ODBC要自己管连接句柄、结果集、内存释放一个指针没处理好就出事。VBS加ADO把大部分细节封装在ADODB对象里代码短出了问题打开脚本编辑器逐行看就行。现场调试经常是半夜电话打过来能快速定位问题比性能重要得多。所以我的选择很明确数据量在每分钟几百条以内一套单站WinCC无脑用VBS加ADO。拿C脚本去读Access属于给自己加戏数据库同步工具加OPC UA这种路线适合多站或大数据量单站场景投入产出不划算。2.3 运行环境怎么准备先解决驱动再谈脚本VBS脚本要能连上Access系统里必须装对应的OLEDB Provider。xp和Server 2003那批老机器上常见的“Microsoft.Jet.OLEDB.4.0”只能读.mdb老格式新格式.accdb和Office 2010以上版本要用“Microsoft.ACE.OLEDB.12.0”。新建项目建议直接统一用ACE驱动省得设备升级后脚本一堆兼容问题。驱动有32位和64位之分WinCC装的是32位还是64位驱动就得配套。这个问题非常阴系统是64位不代表WinCC是64位。装错了驱动脚本一跑就报“未找到提供程序”。另外ACE引擎安装包和Office会打架机器上装了Office 64位就装不进ACE 32位现场里这个问题出现过很多次有专门的开关可以绕过但更稳的做法是在工程师站上不装办公Office只装Access Runtime或直接用绿色版驱动文件。环境准备好之后先用一个最小的脚本验证连接串别急着往WinCC里搬 最小连接测试验证OLEDB Provider和路径是否可用 Dim conn Set conn CreateObject(ADODB.Connection) conn.Open ProviderMicrosoft.ACE.OLEDB.12.0; _ Data SourceD:\Data\quality.mdb; MsgBox 连接成功 conn.Close Set conn Nothing连接串里两个参数最关键Provider指定用什么驱动Data Source指向Access文件的全路径。把这两行单独跑通后面所有报错都跟脚本逻辑无关直接排查环境和路径就行。如果手边有装了Access的办公电脑用Excel的数据选项卡连一下这个库也能验证驱动和数据完整性这个方法在现场很土但很管用。3. 最小可运行脚本从Access表到WinCC变量的落地步骤环境、驱动、连接串都验证过了下面就是完整的落地过程。我以一个质检表为例Access库文件名叫quality.mdb表名叫qa_result有三个字段——measure_val实测值、record_time记录时间、line_id产线号。需求是把最新一条记录的measure_val和record_time写进WinCC变量让画面显示当前质检值。3.1 先建好目标变量内部变量与外部变量的分工在WinCC Explorer里打开“变量管理”在“内部变量”下新建两个变量。数据库数据只跟内部变量发生关系不要图省事直接建外部变量去连PLC通道那是两套体系。Access字段数据类型WinCC内部变量名WinCC变量类型measure_val双精度浮点QA_Value浮点数32位record_time日期/时间QA_Time文本变量line_id文本QA_Line文本变量变量命名我习惯统一加项目前缀比如QA_代表质检系统这样画面上绑定时扫一眼就知道来自哪里。QA_Time用文本变量而不是日期时间变量是血泪教训换来的不同版本WinCC对日期时间变量的写入格式兼容性有差异写成字符串“2025-04-01 10:23:45”在画面上显示、归档、导出都省事文本变量还能直接进报表不用再做格式转换。三个变量建好后在画面上放一个IO域或文本对象连接QA_Value这就是最终展示效果。如果画面还要显示这条数据是什么时候来的再放一个文本显示控件绑QA_Time。3.2 WinCC全局脚本从Access读取最新记录并写入变量打开WinCC的全局脚本编辑器新建一个VBS动作把下面的脚本贴进去。这段脚本是完整可运行的包含了连接、查询、写入、释放四个环节 从Access读取最新质检记录并写入WinCC内部变量 适用WinCC V7/V8 全局脚本周期触发 Option Explicit Dim conn, rs, sql, connStr Dim measureValue, recordTimeStr 1. 组装连接字符串 Provider注意跟Access文件格式匹配 .accdb / Office 2010 - Microsoft.ACE.OLEDB.12.0 .mdb 老格式 - Microsoft.Jet.OLEDB.4.0 connStr ProviderMicrosoft.ACE.OLEDB.12.0; _ Data SourceD:\Data\quality.mdb; _ Persist Security InfoFalse; 2. 打开连接并执行查询 Set conn CreateObject(ADODB.Connection) conn.ConnectionString connStr conn.Open 取时间戳最大的一条记录也就是最新一次质检结果 sql SELECT TOP 1 measure_val, record_time, line_id _ FROM qa_result ORDER BY record_time DESC; Set rs conn.Execute(sql) 3. 判断是否有数据有就写入WinCC变量 If Not rs.EOF Then measureValue rs.Fields(measure_val).Value recordTimeStr CStr(rs.Fields(record_time).Value) Write方法是WinCC脚本写变量的标准方式 HMIRuntime.Tags(QA_Value).Write measureValue HMIRuntime.Tags(QA_Time).Write recordTimeStr Else 没有数据时写一个约定的异常值方便画面判断 HMIRuntime.Tags(QA_Value).Write -9999 End If 4. 释放对象避免文件锁累积 rs.Close Set rs Nothing conn.Close Set conn Nothing代码里需要注意几个地方。连接串我分两行用“”拼接这是VBS的续行写法注意每行末尾的续行符“_”前面必须有空格很多“脚本语句未结束”的报错就出在这里后面避坑章节专门说。查询用SELECT TOP 1加ORDER BY record_time DESC取的是时间最新的记录如果你的表没有时间字段只有自增ID也可以ORDER BY ID DESC效果一样。写入用的是HMIRuntime.Tags(变量名).Write这是WinCC VBS脚本里写变量的标准接口。有人图省事直接写HMIRuntime.Tags(QA_Value) measureValue这种写法在部分版本里能跑但Write方法的语义更明确且支持变量类型检查建议统一用它。连接用完必须关闭并置空这步偷懒的后果很直接——Access文件被锁住下次脚本再跑就超时。我在现场见过Access的.ldb锁文件越积越多最后整个库打不开只能重启工程师站就是从这儿开始的。3.3 把脚本挂到周期触发器并验证一次写入脚本写好之后在全局脚本编辑器里给这个VBS动作分配触发器。做法是选中动作右键打开“触发器/行动计划”新建一个触发器类型选“周期”周期设成10秒。这里要区分触发器的命名WinCC里“1 s”是一秒“1 m”是一分钟粗心选错会变成一分钟才刷新一次。触发器关联好之后把WinCC运行系统启动起来全局脚本的“运行”按钮也要确认是启动状态。脚本不会因为画面运行了就自动跑全局脚本是一个独立运行时组件。验证方法很关键。在Access里手动插入一条新记录比如measure_val填52.6record_time填当前时间然后回到WinCC画面看QA_Value这个IO域。正常情况下10秒内画面会跳到52.6。如果没变先别急着改代码打开全局脚本的监视窗口看有没有报错或者把MsgBox临时加在Write之前强制看脚本执行到哪一步。还有一个容易被忽略的点脚本第一次跑成功、后续没反应多半是Access文件被其他程序占用了。下面避坑章节专门展开这类问题。4. 落地避坑清单Access写WinCC变量的常见故障与排查这个方向看着简单真正落地时全是细节。以下按“现象、原因、解决”三条写都是我跑现场时实打实遇到过的照着排查能省不少时间。4.1 报错“未找到提供程序”或连接闪断先查驱动位数现象脚本一执行就报错提示“未找到提供程序”或“Provider cannot be found”错误号0x800A0E7A。原因90%是ACE/Jet驱动没装或者装的驱动位数和WinCC进程位数不一致。很多工程师站系统是Windows 10 64位但WinCC本身装的是32位版本这时候装了64位的AccessDatabaseEngine一样连不上。剩下10%是Access文件被Office 64位组件干扰安装ACE时直接提示已有更高版本拒绝安装。解决先看WinCC的安装目录里bin文件夹是x86还是x64判断WinCC位数。再到命令行用reg query检查Provider注册表项确认有没有Microsoft.ACE.OLEDB.12.0。没有就下载对应位数的AccessDatabaseEngine安装包注意区分X64和X86。装的时候如果Office占着坑用安装包的被动模式开关绕过或者干脆在工程师站上卸载办公版Office改用Access Runtime这个问题就永久消失了。4.2 脚本语句未结束WinCC脚本编辑器的语法陷阱现象保存VBS动作时提示“脚本语句未结束”或编译红叉尤其刚写完If和SQL拼接的长语句时几乎必现。原因VBScript对续行的要求非常严格上一行结尾必须是“”才能换行而且“”前面要有空格。同时WinCC脚本编辑器对中英文字符混排敏感全角引号、全角分号混进去看着一样编译器不认。另外VBS的单行If写法“If a 1 Then b 2”在WinCC里容易和后续语句纠缠报出莫名其妙的“语句未结束”。解决小段逻辑用单行If没问题但只要If体内超过一条语句就必须写成多行If…Then…End If。续行符统一写成“空格下划线”行尾不要留多余空格。写完用脚本编辑器自带的编译检查跑一遍再把代码全文复制到记事本里做一次全角转半角这招能消灭绝大多数语法怪问题。养成这个习惯后“语句未结束”基本绝迹。4.3 变量写进去了画面纹丝不动检查绑定和刷新周期现象脚本执行成功监视窗口没报错Access里也确实插了新记录但画面上那个IO域就是不跳。原因最常见的是画面控件根本没绑QA_Value这个变量绑了别的同名变量其次是控件绑定的更新周期太长比如设了“仅在鼠标操作时更新”或60秒脚本每10秒写一次刷新周期比写入还长画面自然看着没反应。还有一种是画面绑了变量但控件被设置成了“输出”而不是“输入输出”IO域只读不更新显示。解决先在画面编辑器里双击IO域确认“连接”选项卡里选的是QA_Value不是QA_Line或别的变量。然后把更新周期改成“2秒”或“1秒”或者干脆选“画面周期”。运行状态下打开WinCC的变量监控工具输入QA_Value看数值是否在变化——如果变量监控里在跳而画面不动就是控件属性问题如果变量监控里也没变就得回头查脚本和触发器的运行状态。这个方法能把问题范围缩到最小。4.4 读一次就停摆Access文件锁与连接未释放现象脚本第一次能读到数据之后再也不更新。Active Connections一直在但数据库就是打不开。原因Access是文件型数据库多个进程同时打开同一个文件时会有锁机制。最常见的是脚本每次执行都创建了新连接但没释放连接对象攒着不销毁Access文件被锁。另外如果工程师站上有人用Access或Excel手动打开了这个库文件文件也会被独占脚本只能读第一次。解决脚本末尾必须执行rs.Close、Set rs Nothing、conn.Close、Set conn Nothing四句一个都不能少。开发期调试时频繁中断脚本进程残留的连接不会自动清可以在任务管理器里看有没有残留的“dllhost”或“Access”进程有就结束掉。Access库文件放置位置也注意别放桌面、别放同步盘、别放共享网络盘——共享盘最容易出锁问题WinCC脚本所在的机器本地访问最稳。4.5 中文路径、共享盘与运行时授权几件说不清的玄学现象脚本在开发站跑得好好的拷到现场工控机上就报错有时候是连接失败有时候干脆脚本不运行。报错内容五花八门跟脚本逻辑无关。原因一类是路径问题Access库放在中文目录、带空格的目录、或者桌面/OneDrive同步目录里OLEDB驱动解析路径时翻车。另一类是运行时授权问题WinCC开发系统能跑不代表运行系统能跑全局脚本的运行授权缺失的话脚本一个都不会执行连报错都没有像个黑匣子。WinCC 8.1这类较新版本对授权控制更严格脚本功能被拆得很细。解决Path统一硬编码成不含中文的绝对路径比如D:\SCADA_DATA\quality.mdb并在模块配置里设好工作目录。工程机和开发机保持同一版本的WinCC和ACE驱动。授权问题去WinCC的授权管理器里确认“全局脚本”和“VBS脚本”相关选项是否激活WinCC 8.1还要额外看运行系统模块是否授权完整。这种问题没有捷径只能按路径、驱动、授权、触发器四层顺序一个一个排除排查顺序对了半天内能找到问题。5. 时间戳增量读取与持续验证让脚本长期稳定跑基础脚本能跑通了接下来就是让它跑得省、跑得稳。Access文件读起来轻但也架不住每次全表扫描。如果表里积累了十万条记录“SELECT *”每次都要从头读时间长了脚本执行时间会逼近触发器周期系统越来越卡。我的做法是用时间戳做增量读取只取上次之后的新数据。 增量读取只取上次处理时间之后的新记录 Dim lastTime, sql lastTime从WinCC变量里取脚本每次写完后更新它 lastTime HMIRuntime.Tags(QA_LastTime).Read Access日期条件要用#号包起来字符串条件用单引号 sql SELECT measure_val, record_time, line_id _ FROM qa_result _ WHERE record_time # lastTime # _ ORDER BY record_time; Set rs conn.Execute(sql) Do While Not rs.EOF HMIRuntime.Tags(QA_Value).Write rs.Fields(measure_val).Value lastTime rs.Fields(record_time).Value rs.MoveNext Loop 处理完更新水位 HMIRuntime.Tags(QA_LastTime).Write CStr(lastTime)这段代码的思路是维护一个“水位变量”QA_LastTime每次脚本执行时只读比水位新的记录处理完再把水位推进到最新时间。增量读取还有额外好处即使脚本某次运行失败水位还停在失败之前下次启动能把缺口数据补回来相当于有了后悔药。Access的日期条件必须用#号包围字符串条件用单引号这个语法区别经常被来自SQL Server习惯的人写错。验证脚本是不是一直在健康运行我习惯在画面角落放一个“最后刷新时间”文本绑定QA_Time变量这样值班人员一眼就能看出来数据链路是否活着。如果这个时间超过五分钟没变基本可以判定脚本停了或数据库被锁不用等到生产報告开始报错才发现问题。更彻底一点把脚本异常写进WinCC的报警列表数据库连不上时直接触发一条报警这个做法对无人值守的现场很实用。回过头看这条链路Access文件、OLEDB驱动、VBS脚本、WinCC变量每一步都不复杂但每一步都有各自的雷。我的习惯是每套系统都留一个最小的连接测试脚本环境一变先跑它确认驱动和路径没问题再去翻业务脚本这个习惯帮我少熬了好几个夜班。把基础环境稳住、增量逻辑用上、验证手段放明处这套Access到WinCC的数据通路就能一直稳定跑下去希望帮到你。本文还有配套的精品资源点击获取