如何用 RETURNING 子句返回批量插入后的所有自增 ID

发布时间 - 2026-01-31 00:00:00    点击率:
能,PostgreSQL原生支持INSERT...VALUES(...)RETURNING id按插入顺序返回所有自增ID,无需触发器或额外查询;但INSERT...SELECT需确保id由nextval()等生成,否则可能返回NULL。

PostgreSQL 批量 INSERT + RETURNING 能否一次拿到所有自增 ID

能,而且这是 PostgreSQL 原生支持的最可靠方式。只要用 INSERT ... VALUES (...), (...), (...) RETURNING id,数据库会按插入顺序逐行返回每条记录的 id(或其它字段),不需要触发器、临时表或额外查询。

RETURNING 必须跟在 VALUES 列表后,不能用于 INSERT ... SELECT 的模糊场景

常见误写是把 RETURNING 放在 INSERT INTO t SELECT ... 后面却没意识到:只要 SELECT 没有明确指定列别名,RETURNING 就无法引用目标表的自增列(比如 id)。此时要么改用 VALUES 批量插入,要么在 SELECT 中显式写出目标列并用 RETURNING id —— 但注意,这要求源 SELECT 确实生成了新 id(例如用 nextval())。

  • INSERT INTO users (name) VALUES ('a'), ('b'), ('c') RETURNING id; ✅ 安全有效
  • INSERT INTO users (name) SELECT name FROM temp_names RETURNING id; ⚠️ 仅当 users.idSERIAL 或由 DEFAULT nextval(...) 保证时才返回新值;否则可能返回 NULL 或旧值

批量插入时 RETURNING 返回结果的顺序与 VALUES 严格一致

PostgreSQL 不保证并发插入的全局顺序,但对单条 INSERT ... VALUES 语句,RETURNING 的行序永远匹配 VALUES 子句中元组的书写顺序。这意味着你可以安全地用数组下标对齐原始数据和返回的 id

INSERT INTO orders (product, amount) 
VALUES ('book', 29.99), ('pen', 3.5), ('notebook', 12.0)
RETURNING id, created_at;

返回三行,第一行对应 'book',第二行对应 'pen',依此类推。这个顺序不依赖索引、主键或任何外部因素。

用 RETURNING 配合 WITH 实现更复杂的批量关联插入

如果需要插入主表后,再用这些新 ID 插入子表(比如订单 + 订单项),可以用 WITHRETURNING 结果当作临时结果集复用:

WITH new_orders AS (
  INSERT INTO orders (customer_id, total)
  VALUES (123, 45.5), (123, 120.0)
  RETURNING id, total
)
INSERT INTO order_items (order_id, sku, qty)
SELECT id, 'SKU-001', 1 FROM new_orders
UNION ALL
SELECT id, 'SKU-002', 2 FROM new_orders;

这里关键点是:new_orders CTE 会完整保留两次插入产生的两个 id,后续 SELECT 可以多次引用它。但注意,UNION ALL 不改变行序,而每个 SELECT 分支内部仍保持原始 RETURNING 顺序。

容易被忽略的是:如果批量插入量极大(比如十万行),RETURNING 会把全部 ID 拉到客户端内存,此时应评估网络开销和应用层处理能力——不如分批提交,每批几千行。


# sql  # NULL  # select  # union  # 并发  # default  # postgresql  # 数据库  # 中元  # 的是  # 这是  # 子句  # 放在  # 你可以  # 不需要  # 依此类推  # 可以用  # 两次 


相关栏目: 【 网站优化151355 】 【 网络推广146373 】 【 网络技术251813 】 【 AI营销90571


相关推荐: 标准网站视频模板制作软件,现在有哪个网站的视频编辑素材最齐全的,背景音乐、音效等?  详解一款开源免费的.NET文档操作组件DocX(.NET组件介绍之一)  如何在阿里云通过域名搭建网站?  java获取注册ip实例  Laravel如何获取当前用户信息_Laravel Auth门面获取用户ID  如何在IIS中新建站点并配置端口与物理路径?  如何生成腾讯云建站专用兑换码?  如何用已有域名快速搭建网站?  Laravel的Blade指令怎么自定义_创建你自己的Laravel Blade Directives  如何彻底删除建站之星生成的Banner?  Win10如何卸载预装Edge扩展_Win10卸载Edge扩展教程【方法】  手机网站制作平台,手机靓号代理商怎么制作属于自己的手机靓号网站?  如何在万网ECS上快速搭建专属网站?  Laravel PHP版本要求一览_Laravel各版本环境要求对照  高防服务器租用如何选择配置与防御等级?  如何在万网开始建站?分步指南解析  Laravel如何使用Service Provider注册服务_Laravel服务提供者配置与加载  Laravel如何使用Collections进行数据处理?(实用方法示例)  Laravel如何实现多语言支持_Laravel本地化与国际化(i18n)配置教程  Laravel如何设置自定义的日志文件名_Laravel根据日期或用户ID生成动态日志【技巧】  Win11怎样安装网易有道词典_Win11安装词典教程【步骤】  千问怎样用提示词获取健康建议_千问健康类提示词注意事项【指南】  Laravel如何处理JSON字段的查询和更新_Laravel JSON列操作与查询技巧  详解Oracle修改字段类型方法总结  JavaScript中如何操作剪贴板_ClipboardAPI怎么用  学生网站制作软件,一个12岁的学生写小说,应该去什么样的网站?  怎么用AI帮你为初创公司进行市场定位分析?  Laravel如何使用Contracts(契约)进行编程_Laravel契约接口与依赖反转  php中::能调用final静态方法吗_final修饰静态方法调用规则【解答】  Laravel如何编写单元测试和功能测试?(PHPUnit示例)  JavaScript如何实现音频处理_Web Audio API如何工作?  Laravel的HTTP客户端怎么用_Laravel HTTP Client发起API请求教程  关于BootStrap modal 在IOS9中不能弹出的解决方法(IOS 9 bootstrap modal ios 9 noticework)  android nfc常用标签读取总结  深圳网站制作公司好吗,在深圳找工作哪个网站最好啊?  实例解析Array和String方法  Laravel怎么实现API接口鉴权_Laravel Sanctum令牌生成与请求验证【教程】  猎豹浏览器开发者工具怎么打开 猎豹浏览器F12调试工具使用【前端必备】  利用 Google AI 进行 YouTube 视频 SEO 描述优化  Laravel API资源类怎么用_Laravel API Resource数据转换  QQ浏览器网页版登录入口 个人中心在线进入  音乐网站服务器如何优化API响应速度?  Laravel如何自定义错误页面(404, 500)?(代码示例)  Laravel中的withCount方法怎么高效统计关联模型数量  如何在IIS中配置站点IP、端口及主机头?  再谈Python中的字符串与字符编码(推荐)  公司门户网站制作公司有哪些,怎样使用wordpress制作一个企业网站?  悟空浏览器如何设置小说背景色_悟空浏览器背景色设置【方法】  百度输入法ai面板怎么关 百度输入法ai面板隐藏技巧  微信小程序 配置文件详细介绍