当前位置: 首页 > 知识库问答 >
问题:

后greSQL:即将用完整数列中的ID

公良安邦
2023-03-14

我们正在用爪哇在后交后SQL之上构建一个Web应用程序。它相当大且成功,至少应该能够再运行几年。

不幸的是,我们(嗯,我)在设计过程的早期阶段犯了一个严重的错误:所有数据库ID都是整数,从一个共享序列中分发。

Java的max int是2^31-1,所以大约20亿。PostgreSQL的整数类型也是如此。该系统目前每天消耗大约10k个id,而且随着新用户的增加,这个速度还在加快。

总有一天,id会用完并溢出。

我们正在寻找解决这种情况的方法。让我们立即解决显而易见的问题:切换到Java的long和Postgres的bigint是一个干净的解决方案,但它是大量的工作。我们需要尽可能推迟它。

到目前为止,我们有一些想法:

  • 不要对所有内容使用一个序列,为每个表指定自己的序列。
    • 优点:这给了我们长达N倍的时间,其中N是表的数量。
    • 缺点:我们喜欢每行都有一个唯一的ID。
    • 优点:我们一些最大的ID猪可以通过这种方式改变。
    • 缺点:工作量不大。
    • 优点:我们的一些最大的ID猪可以通过这种方式修复。
    • 缺点:我们失去了代码的简单性。
    • 优点:至少我们不会让情况变得更糟。
    • 缺点:与其余代码的接触面将很丑陋。

    在这些约束下,还有哪些方法会延迟ID耗尽?

共有2个答案

窦涵忍
2023-03-14

自从问了这个问题,我找到了一个很好的方法来解决一半的问题——数据库方面。所以,对于后代来说,这是做到这一点的方法。

>

  • 查找integerinteger[]类型的所有DB列。手动检查结果并删除类型的列,例如text[]

    SELECT *
    FROM information_schema.columns cls
    JOIN information_schema.tables tbl ON cls.table_name = tbl.table_name
    WHERE
      cls.table_schema = '<my schema>'
      AND cls.data_type = 'integer' OR cls.data_type = 'ARRAY'
      AND tbl.table_type = 'BASE TABLE';
    

    为每个列准备数据类型更改 DDL:

    ALTER TABLE <one of the tables found> 
    ALTER COLUMN <one of its integral columns> 
    TYPE bigint;
    

    这工作得很好,除了VIEW:他们不喜欢我改变他们的返回类型。我需要重新创建所有这些 - 序列将是

    1. 删除所有视图
    2. 更改列类型
    3. 重新创建所有视图

    如何仅导出/备份VIEWs?

  • 上官华池
    2023-03-14

    切换到多头远不是一个干净的解决方案。如果你增长得太大,只有一个明智的选择:uuid(是的,PostgreSQL附带了uuid数据类型)。

    在128位,它的大小为4个整数,但你不想在几年内完成整个应用程序,对吗?当你的规模变得太大,需要对数据进行分片时,UUIDs可以工作。那时你将不能拥有一个共享的序列,这就是UUIDs有意义的原因。

    作为奖励,您甚至可以在每一行保留您的独特属性。

    迁移并不难:在PostgreSQL中添加一个NULL列很便宜,因此您可以先添加一个列,然后分批进行在线迁移,一次更新几千条记录,这样就不会停机。

    然后,您可以使用这两个外键测试相同的代码。Java有类似于实验室或科学家的东西吗?

    会有很多工作要做吗?是的,但如果你有一个如此受欢迎的应用程序,这显然是一个好迹象。

    我还希望你已经吸取了教训,对所有的表使用相同的序列。老实说——我真的看不到这有什么附加值。如果你想知道一个对象适合哪里,你也可以用不同的方式命名主键(例如room_id、reservation_id等)。

     类似资料:
    • 问题内容: 我为此进行了高低搜寻,但似乎无法获得直接答案。 在Java中,可用的MessageDigest由您配置/安装的安全提供程序确定。但是,假设仅进行普通的JDK8安装(在我的情况下为1.8.0_11),可用的哈希算法列表是什么?从文档中的示例来看,很明显可以使用MD5,SHA1和SHA-256,但我似乎无法获得完整的权威列表。 该列表是否存在,或者我该如何找到适合我的特定安装的列表? 问题

    • 通过示例来学习 RxJS 操作符 RxJS 操作符的完整列表,每个操作符都有着清晰的解释、相关资源和可执行的示例。 更喜欢按操作符类型进行分类? 内容 (按字母顺序) audit auditTime buffer bufferCount bufferTime :star: bufferToggle bufferWhen catch / catchError :star: combineAll co

    • 我正在处理 PostgreSQL 客户记录。 我的任务是导出客户记录。 除了有联系信息的客户之外,我还有另一张桌子。 每行一个联系人项目(电话、值或电子邮件、值等)。 当我加入并关联数据时,我会为每个客户ID提取多个记录(如果每个客户有一个以上的通信类型,例如电话和电子邮件)。 我怎么能不为每种通信类型再做一行,而是将信息放入临时列(如电话列,传真列和电子邮件列)中 - 然后每个客户只有1行。 编

    • 如何强制spark中数据包的完全外部联接以使用Boradcast散列联接?下面是代码片段: 但是,当我使用“”作为联接类型时,spark出于某种未知原因决定使用。有人知道怎么解决这个问题吗?根据我在左外部联接中看到的性能,将有助于加快应用程序的速度。

    • 我想把我从stdin收到的一些浮点放在一个列表中。但使用以下程序只返回一个对象。我如何把我收到的彩车放在一个列表中? 输入如下所示:0.1 0.1 0.3 0.4 0.1 0.4 0.2 0.1 0.1 0.2 0.5 0.05 0.15 0.1 0.2 0.6 0.1 0.1 0.1 0.5 0.5 0.2 0.2 0.05 0.05

    • 我正在为IntelliJ创建一个自定义插件,我想把它放在我的个人存储库中。然后我看了一下如何创建一个存储库,基本上我只需要创建一个文件,它应该包含以下元素: 并将其放在存储库文件夹/服务器中。然后,当我打开IntelliJ IDEA并查看插件列表时,我可以看到我的插件列表(一旦我将我的存储库添加到列表中)。但是,我看到其他插件有更多的信息,例如描述、更改注释、类别等。。。 在这两个链接,插件列表和