简介这份资源面向使用KettlePentaho Data Integration进行数据集成开发的工程师聚焦「循环获取结果集并传入转换」这一典型场景解决作业与转换之间变量传递、结果集逐行迭代处理的问题。包内共1个PDF文件约130KB以图文形式记录了完整实现思路适合具备一定Kettle基础、希望掌握作业与转换协同控制的中级开发者参考。内容围绕t1.ktr生成结果集、j1.kjb中通过JavaScript步骤调用previous_result.getRows()获取数据、借助parent_job.setVariable()将表名、数量、循环变量等写入作业变量再由var.ktr读取变量并输出到本地txt文件的完整链路展开同时给出循环控制变量的递增判断逻辑与文本文件输出配置。已有3111人学习可帮助读者理解Kettle变量作用域、结果集传递与循环调度的实现方式为处理批量表遍历、动态数据抽取等任务提供可复用的排错与设计思路。1. Kettle 结果集跨转换传递从 t1.ktr 到 var.ktr 的循环落地很多人第一次在 Kettle 里做「上一个转换的结果集喂给下一个转换」时都会卡在同一个地方明明 t1.ktr 里数据跑出来了var.ktr 里却拿不到日志里一片空白。这个资源给的方案核心就是用作业j1.kjb当调度层用 JavaScript 步骤把previous_result.getRows()拿到的结果集拆成作业变量再靠循环控制变量i逐行推进把id、name这类字段一行一行塞进 var.ktr。它解决的不是「怎么连数据库」这种基础问题而是「结果集怎么跨转换、按行、可控地传下去」。适合已经会写 Kettle 转换、但被作业与转换之间变量作用域卡住的 ETL 从业者也适合想把批量表名循环处理成 txt 输出的人。2. 结果集传递的底层逻辑为什么直接连两个转换不行2.1 转换与作业的变量作用域差异Kettle 里转换Transformation和作业Job是两套执行模型。转换内部步骤之间靠行集RowSet流式传数据速度快但生命周期只限本次转换。作业里的previous_result是作业级结果只有作业步骤Job Entry执行完才会挂上去。你如果直接把 t1.ktr 和 var.ktr 两个转换步骤串在作业里var.ktr 默认拿不到 t1.ktr 的行——因为转换步骤的结果默认不自动变成作业结果集得靠「复制上一步结果到结果集」这类选项或 JavaScript 步骤显式读取。常见做法是t1.ktr 末尾接一个「复制记录到结果」步骤作业里再让 JavaScript 步骤用previous_result.getRows()去取。这个资源里的 j1.kjb 正是这个套路取到之后不直接传行而是转成变量因为 var.ktr 是独立转换只能通过变量或参数接收外部输入。2.2 为什么用 ArrayList 存整个结果集代码里parent_job.setVariable(tables, prevRow)把整个 List 塞进一个变量。Kettle 变量本质是字符串但 JavaScript 步骤里 setVariable 传对象时作业内部会保留对象引用后续 JavaScript 步骤还能按 List 取。这样做的好处是一次取完循环时不用反复回查结果集代价是这个变量只在当前作业 JVM 内有效作业一结束就没了也不能跨作业引用。// j1.kjb 中第一个 JavaScript 步骤 var prevRow previous_result.getRows(); // 取上一个作业步骤的结果集 if (prevRow null || prevRow.size() 0) { false; // 结果集为空返回 false 让作业走失败分支 } else { parent_job.setVariable(tables, prevRow); // 整个 List 存进变量 parent_job.setVariable(size, prevRow.size()); // 总行数循环边界 parent_job.setVariable(i, 0); // 循环下标从 0 开始 parent_job.setVariable(id, prevRow.get(0).getString(id, )); parent_job.setVariable(name, prevRow.get(0).getString(name, )); true; }逻辑说明previous_result.getRows()返回的是 Row 对象的 List每个 Row 用getString(字段名, 默认值)取值。参数上size决定循环次数i是当前下标id/name是每次循环要传给 var.ktr 的当前行字段。注意原文里prevRow null (prevRow.size()0)是笔误应为且逻辑应为||否则空结果集判断会失效这是第一个要改的地方。2.3 循环推进的 JavaScript 校验步骤第二个 JavaScript 步骤负责「下一行」。它读size和i把i加一如果还没到末尾就更新id/name然后把新i写回变量。作业里这个步骤后面接一个「条件」判断i size成立就跳回 var.ktr 再跑一次不成立就结束。// j1.kjb 中循环用的 JavaScript 步骤 var prevRow previous_result.getRows(); // 这里仍可拿到结果集引用 var size new Number(parent_job.getVariable(size)); var i new Number(parent_job.getVariable(i)) 1; if (i size) { parent_job.setVariable(id, prevRow.get(i).getString(id, )); parent_job.setVariable(name, prevRow.get(i).getString(name, )); } parent_job.setVariable(i, i); // 无论是否越界都写回便于条件判断 true;参数说明new Number(...)是因为 getVariable 返回字符串不转数值比较会出错。i size是循环继续条件等于 size 时停止。这里有个边界当 i 刚好等于 size-1 时更新最后一行i 变成 size 后不再更新字段但变量 i 已写回条件步骤据此退出。如果你把条件写成i size会多跑一次并取到越界行直接报错。3. 从零搭一遍j1.kjb、t1.ktr、var.ktr 的配置步骤3.1 t1.ktr 产出结果集并复制到结果t1.ktr 里按你的业务做抽取比如「表输入」查一张元数据表字段至少包含id、name。末尾必须加「复制记录到结果」步骤把行集挂到作业结果上。没有这一步j1.kjb 里的previous_result.getRows()就是 null。配置要点用表格列一下步骤关键配置作用表输入SQL 查出 id、name产生结果集复制记录到结果默认即可把行挂到作业结果转换属性不要勾选「执行每一行」避免重复执行3.2 j1.kjb 的作业步骤顺序作业里按这个顺序排Start → 转换 t1.ktr → JavaScript初始化变量→ 转换 var.ktr → JavaScript推进 i→ 条件判断 → 回跳 var.ktr 或结束。条件步骤的「真」连回 var.ktr 前形成循环「假」连到成功结束。# 作业文件结构示意.kjb 本质是 XML这里只列步骤顺序 Start - Transformation: t1.ktr - JavaScript: init_vars - Transformation: var.ktr - JavaScript: next_row - Simple Evaluation: i size ? true - Transformation: var.ktr false - Success逻辑说明Kettle 作业的循环不是 for而是靠「条件 回跳」模拟。每次 var.ktr 执行时读的是当前id/name变量所以必须在 var.ktr 之前更新变量。把推进步骤放在 var.ktr 之后、条件之前保证下一轮用的是新值。3.3 var.ktr 读取变量并输出 txtvar.ktr 里用「获取变量」步骤把id、name读成字段再「文本文件输出」写盘。获取变量步骤要填变量名和字段名类型选 String。文本文件输出里指定路径、分隔符、是否追加。如果每轮都覆盖最后只剩一行要累积就勾选「追加」。// var.ktr 中若用 JavaScript 读变量可这样写 var id parent_job.getVariable(id, ); var name parent_job.getVariable(name, ); // 后续可做格式化再交给文本输出参数说明getVariable(id, )第二个参数是默认值防止变量未定义时报错。文本输出路径建议用变量拼比如/data/out_${id}.txt这样每行一个文件便于核对循环是否真的逐行执行。4. 避坑与排查结果集传递最常见的五个翻车点4.1 现象var.ktr 里变量全是空原因j1.kjb 里 JavaScript 步骤没勾选「兼容模式」或者变量名大小写不一致。Kettle 变量区分大小写ID和id是两个东西。解决统一小写JavaScript 步骤属性里勾选「兼容模式」并在日志里打印parent_job.getVariable(id)确认。4.2 现象循环只跑一次就结束原因条件步骤写成了i size或i size或者推进步骤没把 i 写回。解决条件用i size推进步骤末尾必须parent_job.setVariable(i, i)并在日志里输出每轮的 i 值。4.3 现象结果集为空但作业不报错原因原文的prevRow null (prevRow.size()0)逻辑写反空集时进了 else 分支。解决改成if (prevRow null || prevRow.size() 0) { false; }让空集走失败分支日志里能看到。4.4 现象txt 文件被覆盖只剩最后一行原因文本文件输出没勾「追加」每轮都重建文件。解决勾选追加或用${id}拼文件名每行独立文件。注意追加模式下表头只写一次否则每轮都插表头。4.5 现象字段取值报「字段不存在」原因t1.ktr 结果集里字段名和getString(id)不一致比如数据库返回的是ID大写。解决在 t1.ktr 里用「字段选择」统一改名为小写或在 JavaScript 里用实际字段名。Kettle 结果集字段名来自上游步骤输出不是数据库列名。5. 进阶把循环变量做成可复用模板与验证技巧把上面这套跑通之后我一般会把它固化成一个模板作业下次换业务只改 t1.ktr 的 SQL 和 var.ktr 的输出格式。具体做法是j1.kjb 里所有变量名统一加前缀比如loop_id、loop_name、loop_size、loop_i避免和业务变量撞名。var.ktr 里用「获取变量」步骤而不是 JavaScript减少脚本维护成本。输出路径用/data/${loop_id}_${loop_name}.txt跑完直接看文件名就知道循环有没有漏行。验证循环是否完整有个笨但有效的办法在 t1.ktr 里加一个「添加常量」步骤给每行打一个自增序号seqvar.ktr 输出时把seq也写进 txt。跑完检查 txt 里的 seq 是否连续、是否等于 size。如果中间断号说明某轮变量没更新或条件判断提前退出。另一个技巧是在推进步骤里把i和当前id写进日志用「写日志」步骤输出作业执行完看日志就能还原整个循环轨迹。// 带日志的推进步骤便于排查 var prevRow previous_result.getRows(); var size new Number(parent_job.getVariable(loop_size)); var i new Number(parent_job.getVariable(loop_i)) 1; if (i size) { parent_job.setVariable(loop_id, prevRow.get(i).getString(id, )); parent_job.setVariable(loop_name, prevRow.get(i).getString(name, )); } parent_job.setVariable(loop_i, i); // 输出到日志Kettle 日志级别设为 Detailed 可见 java.util.logging.Logger.getLogger(loop).info(i i , size size); true;参数上loop_size只在初始化时写一次循环中不要改loop_i每轮必须写回。如果你把结果集变量tables也传进 var.ktr注意它是个 List文本输出步骤不认得在 JavaScript 里转成字符串再用。最后提醒一句这套方案适合结果集行数在几百到几千级别上万行时逐行起转换开销很大常见做法是改成「表输入 字段流」一次跑完而不是循环。从那以后我每次做跨转换传参都强制先在日志里打一遍 size 和 i确认循环边界再往下接业务省得回头翻车。希望帮到你。本文还有配套的精品资源点击获取
企业数字化 ERP 产品动态
相关推荐
多智能体架构如何让AI代码审查从提示词走向产线 做 AI 代码审查这件事,几乎每个团队都走过同一条路:先拿大模型写个提示词,把 MR 的 diff 贴进去,让模型“看看有什么问题”,demo 效果惊艳得不行,觉得上线只是时间问题;可真把它挂到 CI 上&… · 2026/9/25 23:39:46
Codex CLI用户专属:My-Brain-Is-Full-Crew在Windows/WSL环境部署实战指南 Codex CLI用户专属:My-Brain-Is-Full-Crew在Windows/WSL环境部署实战指南 【免费下载链接】My-Brain-Is-Full-Crew Built by a PhD whose memory was failing, whose diet was a mess, and whose anxiety had its own agenda. Most second brain tools ignore the f… · 2026/9/25 23:39:34
Docker-Compose部署灯塔ARL资产侦察系统V2.6.2实战指南 简介:灯塔ARL资产侦察系统V2.6.2是一套面向安全团队与渗透测试人员的互联网资产侦察工具,用于快速发现与目标关联的域名、IP及服务资产,构建基础资产信息库,从而定位薄弱点与攻击面。资源以保姆级部署教程形式呈现,重点… · 2026/9/25 23:39:28
DeskcommCRM深度评测:全渠道客服与工单管理一体化实践 1. 客服系统不再只是"管工单":DeskcommCRM解决的真实业务痛点做了这么多年企业和客服系统相关项目,我有个特别深的感受:很多团队买 CRM 或者客服软件之前,并没有想清楚自己要解决的是"工具问题"还是"流程… · 2026/9/26 0:16:57
俄罗斯条形码申请找谁?跨境卖家避坑指南 直接说答案:俄罗斯条形码只能找GS1 Rus或其授权服务商,国内任何声称“官方直发”的代办都是忽悠。
做俄罗斯市场的卖家,无论是速卖通、亚马逊还是Ozon,商品上架时几乎都会卡在条形码这一关。我在这行摸爬滚打快八年,见… · 2026/9/26 0:16:38
Seedance2-Skill工作原理深度解析:Agent Skills如何驱动双语AI视频提示词工程 Seedance2-Skill工作原理深度解析:Agent Skills如何驱动双语AI视频提示词工程 【免费下载链接】seedance2-skill skill to create best prompts for generating videos with seedance2.0 项目地址: https://gitcode.com/gh_mirrors/se/seedance2-skill
Seeda… · 2026/9/26 0:15:54
交付攻坚第三战:复杂异构网络专线打通与跨网段 RPC 调试实录 交付攻坚第三战:复杂异构网络专线打通与跨网段 RPC 调试实录在为大型集团企业(如跨省设有数十个制造基地的重工集团、拥有复杂分支机构的金融银行)交付私有化 AI 智能中台时,系统架构师最常遭遇的物理噩梦莫过于“极度复杂的跨网段… · 2026/9/26 0:15:28
数据库课后习题答案别硬背:当测试用例集刷,效率翻倍 简介:万常选版《数据库原理与设计》课后习题答案资源,覆盖第2至6章及第9章,适合正在学习关系模型、数据库建模、关系数据理论与模式求精的本科生、自学者作为复习与自测材料。压缩包共7个文件,含3个doc参考答案、2个sql示例脚本、… · 2026/9/26 0:00:21
OpenClaw 替代品?Hermes Agent 踩坑实录:macOS 飞书接入 TaoToken 配置 /* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views … · 2026/9/26 0:00:40
向下兼容与向上兼容:接口设计中的兼容性策略与工程实践 一次版本升级事故,是很多团队绕不过去的坎。线上环境里,服务端明明已经上线了新版接口,老的移动端还在照着旧文档传参数。请求一到网关,校验直接拒绝,用户操作失败,客服群炸了锅,开发群里开始互… · 2026/9/26 0:00:46