暂无图片
暂无图片
暂无图片
暂无图片
暂无图片

5分钟带你了解MatrixDB 4.2新特性 — UPSERT

yMatrix 2021-09-04
1496

1

前言

MatrixDB 4.2版本发布后,MatrixGate推出了一个新特性—UPSERT。

本文将详细介绍UPSERT语义及MatrixGate新特性的使用方法。

什么是UPSERT?

UPSERT 就是 UPDATE 和 INSERT 的结合。

实现一条SQL内自动插入或者更新:如果记录不存在则插入,如果记录存在则更新。

这是应用开发中最常见的场景之一,通过UPSERT语法可以大幅简化开发代码的复杂度,提升效率。

在众多场景下,都免不了使用UPSERT功能,比如:
  • 设备数据不是一次性发送全部,而是分批次发送,需要按设备号和时间戳为主键进行合并

  • 设备数据可能会重复发送,对于重复数据要做更新而不是重复插入

而UPSERT语义则直接实现了该逻辑。下面演示一下UPSERT的用法。

2

UPSERT的使用方法

准备数据表

SQL

    DROP TABLE IF EXISTS upsert_demo;

    CREATE TABLE upsert_demo (
    ts timestamp
    , tagid int
    , c1 int
    , c2 float4
    , UNIQUE(ts, tagid)
    ) DISTRIBUTED BY (tagid);

    注意

    为了数据库能够使用UPSERT功能,记得要在表的“设备id+时间戳”上创建UNIQUE约束。

    使用UPSERT语义接入数据

    SQL方式

    先来演示下,如何通过直接执行SQL语句的方式进行UPSERT,对于使用libpq或JDBC等来连接数据库的用户,可以直接参考如下SQL语法来操作。
    假设设备指标c1和c2分两个批次发送,则使用SQL来进行数据填充。

    SQL

      INSERT INTO upsert_demo VALUES ('2020-11-11', 1, 10, NULL)
      ON CONFLICT (ts, tagid)
      DO UPDATE SET
      c1 = coalesce(EXCLUDED.c1, upsert_demo.c1),
      c2 = coalesce(EXCLUDED.c2, upsert_demo.c2);

      INSERT INTO upsert_demo VALUES ('2020-11-11', 1, NULL, 20.1)
      ON CONFLICT (ts, tagid)
      DO UPDATE SET
      c1 = coalesce(EXCLUDED.c1, upsert_demo.c1),
      c2 = coalesce(EXCLUDED.c2, upsert_demo.c2);
      如上两条SQL语句里都包含了唯一索引列:ts和tagid,并且值相同。SQL1只包含了c1列,c2列为空;SQL2只包含了c2列,c1列为空。
      ON CONFLICT子句指定了唯一索引包含的列,用来判断数据行是INSERT还是UPDATE。
      c1=coalesce(EXCLUDED.c1,upsert_demo.c1)的含义是取EXCLUDED.c1和upsert_demo.c1中,第一个不为NULL的值。
      EXCLUDED.c1是原行的值,upsert_demo.c1是新插入的值。即如果原数据行存在,且列值不为空则使用原值;否则使用新插入的值。

      通过这种方式,实现了相同设备、相同时间的指标数据合并。

      SQL

        test=# select * from upsert_demo ;
        ts | tagid | c1 | c2
        ---------------------+-------+----+------
        2020-11-11 00:00:00 | 1 | 10 | 20.1
        (1 row)

        查询upsert_demo可以看到,c1和c2的数据是期望的结果。

        通过如上演示可以看到,使用UPSERT语义,可以通过单条SQL实现根据数据是否存在来选择是插入还是更新,大大简化了开发人员的工作。

        MatrixGate方式

        相比使用SQL方式来接入,MatrixGate作为MatrixDB高性能数据接入工具,在4.2版本中也加入了对UPSERT语义的支持,所以在生产环境中,更加推荐用户选择使用MatrixGate方式接入,性能可以提升百倍。

        下面演示如何使用MatrixGate的UPSERT语义:

        1. 准备数据文件
        文件1: tmp/upsert_demo1.dat

        Plain Text

          ts|tagid|c1|c2
          2020-11-11|1|10|
          文件1: tmp/upsert_demo2.dat

          Plain Text

            ts|tagid|c1|c2
            2020-11-11|1||20.1
            2020-11-11|2||100.5
            2020-11-11|2|200|

            2. 执行Gate

            目标数据库假设为 test,端口为 5432
            重点在--upsert-key参数
            载入第一个文件(为了验证结果,载入前已将表中原数据清空)

            Bash

              tail -n +2 tmp/upsert_demo1.dat | mxgated --source stdin \
              --db-database test \
              --db-master-host localhost \
              --db-master-port 5432 \
              --db-user mxadmin \
              --time-format raw \
              --delimiter "|" \
              --target upsert_demo \
              --upsert-key ts \
              --upsert-key tagid

              结果

              Plain Text

                test=# select * from upsert_demo ;
                ts | tagid | c1 | c2
                ---------------------+-------+----+----
                2020-11-11 00:00:00 | 1 | 10 |
                (1 row)

                载入第二个文件

                Bash

                  tail -n +2 tmp/upsert_demo2.dat | mxgated --source stdin \
                  --db-database test \
                  --db-master-host localhost \
                  --db-master-port 5432 \
                  --db-user mxadmin \
                  --time-format raw \
                  --delimiter "|" \
                  --target upsert_demo \
                  --upsert-key ts \
                  --upsert-key tagid

                  结果

                  Plain Text

                    test=# select * from upsert_demo;
                    ts | tagid | c1 | c2
                    ---------------------+-------+-----+-------
                    2020-11-11 00:00:00 | 1 | 10 | 20.1
                    2020-11-11 00:00:00 | 2 | 200 | 100.5
                    (2 rows)
                    从结果可以看到,ts和tagid相同的行数据,进行了合并。

                    3. Q&A

                    3

                    总结

                    通过如上演示可以看到,UPSERT语义对于时序数据指标分批发送的场景非常有用,会大大的减少开发人员的负担,而在MatrixDB4.2版本中MatrixGate高性能数据接入工具也支持了该特性,欢迎大家下载使用。

                    官网下载地址:

                    https://ymatrix.cn/download

                    推 荐 阅 读

                    yMatrix官方社群诚挚地期待您的加入!
                    yMatrix官方技术社群现已正式对外开放,我们诚挚地期待您的加入。在这里,您不仅可以了解到最前沿的创新技术,掌握最In的科技资讯,获取最专业的技术解答,还能够有机会与大咖面对面的互动和交流;您还在等什么?
                    扫码添加小M助手

                    入群方式超简单,扫描下方二维码
                    小M助手为好友即可入群
                    扫码添加


                    转发,点赞,在看,安排一下?

                    文章转载自 yMatrix,如果涉嫌侵权,请发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

                    评论