【问题标题】:MYSQL duplicate key syntax using multiple primary keysMYSQL 使用多个主键的重复键语法
【发布时间】:2015-07-11 04:55:24
【问题描述】:

大家好,这是我的第一篇文章,请见谅。

我已经在 SO 中搜索了这些问题,虽然它们接近答案,但我所看到的并不正确。

环境信息:

  • MySQL 服务器版本:5.1.69-community-log MySQL 社区服务器 (GPL)
  • 内核版本:CentOS 5.10 版(最终版)

我正在做一个项目来跟踪包更新中的文件版本。此数据当前以下列格式存储在文本文件中。

文件名版本

示例(不,这些不是我们的文件,只是我想到的随机东西)

资源管理器 1.1.2.254 勺子 1.0.0.8

我正在使用 awk 脚本创建 mysql 脚本以插入下表:

创建表`TBL_Versions`( `File` varchar(50) NOT NULL, `Version` varchar(10) NOT NULL 唯一键, `LastUpdate` 时间戳 NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, 主键(`文件`,`版本`) );

目前我正在使用以下插入格式:

INSERT INTO TBL_Versions (File,Version,LastUpdate) values("explorer", "1.1.2.254", CURRENT_TIMESTAMP) ON DUPLICATE KEY UPDATE Version=VALUES(Version);

INSERT INTO TBL_Versions (File,Version,LastUpdate) values("spoon", "1.0.0.8", CURRENT_TIMESTAMP) ON DUPLICATE KEY UPDATE Version=VALUES(Version);

这会在我的表格中留下以下数据:

+----------+------------+----------+ |文件 |版本 |最后更新 | +----------+------------+----------+ |探险家 | 1.1.2.254 | 2014-03-04 08:40:08 | |勺子| 高分辨率照片| CLIPARTO 1.0.0.8 | 2014-03-04 08:40:23 | +----------+------------+----------+

稍后版本文件可能会更新,说勺子的版本是 1.0.0.10,但资源管理器的版本不会改变。所以在文件中它看起来像这样:

资源管理器 1.1.2.254 勺子 1.0.0.10

有没有办法让 awk 脚本编写插入以允许它改变勺子而不是资源管理器?如果需要或其他任何可能需要的东西,我愿意更换桌子。您更有经验的头脑可能已经看到了我遇到的问题,但我会列出我需要解决的问题。

1. 我希望 explorer 的线路保持不变。 2. 我希望勺子的 Version 和 LastUpdate 改变。

提前感谢社区中的每个人的帮助。非常感谢。

【问题讨论】:

  • 您的密钥是文件、版本。因此,在 DUPLICATE 上,您的文件和版本与您要插入的完全一样。那么更新版本应该没有意义吧?
  • 您的密钥是文件和版本的组合......或者只有在文件和版本的组合重复时,重复密钥才有效......只有一个不会成功。跨度>

标签: mysql sql-server awk


【解决方案1】:

使用您当前的表架构,文件和版本的组合唯一标识一条记录...如果只有文件是主键并且您从版本中删除唯一键属性,您可以尝试替换为 TBL ..插入到 TBl 中。

mysql> REPLACE INTO TBL_Versions (File,Version,LastUpdate) values("explorer", "1 .1.2.256", CURRENT_TIMESTAMP);

这可以是一个更简单的查询 .. 前提是 ..PRIMARY KEY 约束仅在 File 列上..

【讨论】:

  • 为什么?为什么要替换而不是插入?有什么区别?如果使用它会发生什么?
  • REPLACE 的工作方式与 INSERT 完全相同,只是如果表中的旧行与 PRIMARY KEY 或 UNIQUE 索引的新行具有相同的值,则在新行被删除之前旧行被删除插入。
  • 如果有对刚刚被删除的 pk 的 FK 约束?
  • 如果文件的版本在表格中不断变化......我不确定它是否适合成为 FK。
【解决方案2】:

这就是我最终要做的。

更改为表架构

CREATE TABLE `TBL_Versions` (
    `File` varchar(50) NOT NULL,
    `Version` varchar(10) NOT NULL,
    `LastUpdate` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
    PRIMARY KEY (`File`)
);

然后我编写了一个 bash 脚本来按照描述从文件中读取数据

从版本文件创建更新文件。

awk '{ printf "INSERT INTO TBL_Versions (File,Version,LastUpdate) values(\"%s\", \"%s\", CURRENT_TIMESTAMP) ON DUPLICATE KEY UPDATE Version=VALUES(Version);\n", $1, $2 }' $VerFile | sed -e"s~\"~\'~g" > /tmp/versions.$$

然后我将 /tmp/versions.$$ 文件通过管道传输到 mysql。

cat /tmp/versions.$$ | while read Update
do
mysql -u$USER -p$PASS DATABASE -Nse "$Update"
done

所有这些都在一个更大的 shell 脚本中。已经运行了一段时间并且工作顺利。它被称为每晚的 cron 作业。

【讨论】:

    猜你喜欢
    • 2016-07-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-11-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-08-18
    相关资源
    最近更新 更多