Firebase:如何为键生成唯一的数字 ID?

Posted

技术标签:

【中文标题】Firebase:如何为键生成唯一的数字 ID?【英文标题】:Firebase: how to generate a unique numeric ID for key? 【发布时间】:2015-05-03 12:41:23 【问题描述】:

为了便于阅读,我需要数字 ID。如何在 Firebase 中获取它?

我想要键的数字 ID,例如“000000001”、“000000002”、“00000003”、“00000004”。

我需要它的原因是因为这些 ID 将成为在线和离线的永久对象 ID。我希望用户能够通过输入 URL “/objects/00000001” 轻松浏览该对象页面。

我在这里问,因为我想知道这是否可以在不使用.priority、子属性等的情况下完成。我猜set 方法可以以某种方式做到这一点。如果不可能,请告诉我不,我可以接受这个答案。

【问题讨论】:

请参阅***.com/help/how-to-ask。您是否尝试过任何尝试解决方案?您是否阅读过 Firebase 文档? 【参考方案1】:

我建议通读 Firebase 文档。具体而言,请参阅 Firebase javascript 网络指南的 Saving Data 部分。

来自指南:

获取 push() 生成的唯一 ID

调用push() 将返回对新数据路径的引用,您可以使用它来获取其ID 的值或为其设置数据。以下代码将产生与上述示例相同的数据,但现在我们可以访问生成的唯一推送 ID

// Generate a reference to a new location and add some data using push()
var newPostRef = postsRef.push(
 author: "gracehop",
 title: "Announcing COBOL, a New Programming Language"
);

// Get the unique ID generated by push() by accessing its key
var postID = newPostRef.key;

来源:https://firebase.google.com/docs/database/admin/save-data#section-ways-to-save

推送会生成一个新的数据路径,其key 是服务器时间戳。这些键看起来像 -JiGh_31GA20JabpZBfa,所以不是数字。 如果您想创建一个仅限数字的 ID,您可以将其作为对象的参数以避免覆盖生成的密钥。 键(新数据的路径)保证是唯一的,因此没有必要用数字键覆盖它们。 您可以改为将数字 ID 设置为对象的子对象。 然后您可以使用 Firebase Queries 按该 ID 子项查询对象。

来自指南:

在 JavaScript 中,调用push() 然后立即调用set() 的模式非常常见,我们让您只需将要设置的数据直接传递给push() 即可组合它们,如下所示。以下两个写入操作都会将相同的数据保存到 Firebase:

// These two methods are equivalent:
postsRef.push().set(
  author: "gracehop",
  title: "Announcing COBOL, a New Programming Language"
);
postsRef.push(
  author: "gracehop",
  title: "Announcing COBOL, a New Programming Language"
);

来源:https://firebase.google.com/docs/database/admin/save-data#getting-the-unique-key-generated-by-push

【讨论】:

看来newPostRef.key() 不再有效...newPostRef.key 确实返回了生成的密钥。看起来它直接与属性相关联,而不是从名为 key() 的函数返回。 刚碰到这个,不得不使用'.key'(不是方法,而是键),谢谢! 这有什么更新吗?我尝试了上述方法,但它们不起作用。该链接不再起作用。此外,当前从推送中获取 ID 的 firebase 指南也不起作用。我只得到 Uncaught SyntaxError: Unexpected identifier @Viet,此时我的回答已经过时了。我建议将我的答案与当前文档进行比较。 @SinanBolel 如果我想将该密钥用作子 ID 怎么办?获得参考后是否应该再次推送?【参考方案2】:

如上所述,您可以使用 Firebase 默认推送 ID。

如果你想要一些数字,你可以根据时间戳做一些事情以避免冲突

f.e.基于日期、小时、秒、毫秒和最后一些随机整数的东西

01612061353136799031

翻译为:

016-12-06 13:53:13:679 9031

这完全取决于您需要的精度(社会安全号码与日期末尾的一些随机字符相同)。就像在一天、一小时或一秒内预计会有多少交易一样。您可能希望降低精度以方便输入。

您还可以执行增加数字 id 的事务,成功后您将获得该用户的唯一连续数字。这些可以在客户端或服务器端完成。

(https://firebase.google.com/docs/database/android/read-and-write)

【讨论】:

这不是一种安全的方法,因为可以通过简单地循环遍历所有可能的值来进行冲突。 push方法产生的hash可能更好,虽然我不知道用的是什么算法。 @T9b 没有循环遍历所有可能的值,因为日期总是递增的。推送算法的作用几乎相同。 没错,就是这样做的。日期、时间和随机数是完全递增的,这正是它不安全的原因。正如我所说,你增加过去所有可能的数字日期和时间来打破它。 @T9b 秘密 ID 并不总是必须的,以 Facebook 为例,您可以简单地开始输入整数来获取用户资料(MZ 为 4)。但是你真的不能用这些数据做更多的事情。【参考方案3】:

正如the docs 所说,这可以通过使用set 而不是push 来实现。

正如文档所说,不建议这样做(因为可能会在“同一”时间被其他用户覆盖)。

但在某些情况下,控制提要的内容(包括键)会很有帮助。

以js中的webapp为例,193是你在别处生成的id,简单来说:

 firebase.initializeApp(firebaseConfig);
  var data=
      "name":"Prague"
  ;
  firebase.database().ref().child('areas').child("193").set(data);

这将覆盖标记为 193 的任何区域,如果该区域尚不存在,则创建一个。

【讨论】:

【参考方案4】:

https://firebase.google.com/docs/firestore/manage-data/transactions

使用事务并在数据库中保存一个可以加一的数字。这样你就可以得到一个漂亮的数字和简单的 id。

【讨论】:

【参考方案5】:

添加到@htafoya 答案。 代码 sn-p 将是

const getTimeEpoch = () => 
    return new Date().getTime().toString();                             

【讨论】:

以上是关于Firebase:如何为键生成唯一的数字 ID?的主要内容,如果未能解决你的问题,请参考以下文章

如何为 BigQuery 表中的记录生成唯一键值?

如何为数据库中的一列生成唯一的字符串?

如何为每位新访客创建唯一ID?

我应该如何为测试数据生成具有唯一 id3 数据的 mp3 文件?

如何为字段的每个唯一值生成随机记录?

如何解决 FIREBASE 唯一 ID 问题