热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

Firebase数据库-反向索引中的安全性考虑因素-FirebaseDatabase-securityconsiderationinaninverseindex

IntheFirebaseguides,oneoftherecommendationsistomaintainaninverseindextokeeptrackof

In the Firebase guides, one of the recommendations is to maintain an inverse index to keep track of user actions. Here's a snippet of what I'm referring to:

在Firebase指南中,建议之一是维护反向索引以跟踪用户操作。这是我所指的内容片段:

// An index to track Ada's memberships
{
  "users": {
    "alovelace": {
      "name": "Ada Lovelace",
      // Index Ada's groups in her profile
      "groups": {
         // the value here doesn't matter, just that the key exists
         "techpioneers": true,
         "womentechmakers": true
      }
    },
    ...
  },
  "groups": {
    "techpioneers": {
     "name": "Historical Tech Pioneers",
     "members": {
        "alovelace": true,
        "ghopper": true,
        "eclarke": true
      }
    },
    ...
  }
}

Each user keeps track of his/her groups in an inverse index - meaning in this case, that the keys hold the real value, and the value doesn't matter.

每个用户在反向索引中跟踪他/她的组 - 在这种情况下,密钥保持实际值,并且值无关紧要。


Update

I wasn't sure how to update the index technically but I got it after a little research: the setValue can take all manor of variables, not just key-value pairs. That means that updating an index is pretty simple: just get a reference to groups/$group_id/members/$member_id and set its value to true.

我不确定如何在技术上更新索引但我在经过一些研究后得到了它:setValue可以采用所有变量,而不仅仅是键值对。这意味着更新索引非常简单:只需获取groups / $ group_id / members / $ member_id的引用并将其值设置为true。

Now my question is different:

现在我的问题不同了:

Lets say all groups are private. Meaning users can join a group by invitation only - a current group member must add another user to the member list. So if I'm ghopper and I want to add alovelace as a member, I need to update her index which is part of her user object - which means I have to know her user ID somehow and have write access to her groups field - and that seems like a security risk.

让我们说所有团体都是私人的。意味着用户只能通过邀请加入组 - 当前组成员必须将另一个用户添加到成员列表中。因此,如果我是ghopper并且我想添加alovelace作为成员,我需要更新她的索引,这是她的用户对象的一部分 - 这意味着我必须以某种方式知道她的用户ID并且具有对她的组字段的写入权限 - 以及这似乎是一种安全风险。

Any thoughts on how to manage this while keeping access as restricted as possible? Perhaps another DB object that maps a user known identifier, like an email to a group list?

有关如何管理这一点的任何想法,同时尽可能限制访问?也许另一个DB对象将用户已知的标识符(如电子邮件)映射到组列表?

1 个解决方案

#1


1  

Solution 1 - Client-side

解决方案1 ​​ - 客户端

One solution would be to have a separate user invitation object so that ghopper can add alovelace to the private group and have that show up alovelace's invitations instead of automatically adding her to the group. alovelace would then need to approve the addition and update her group membership. This way, only the user retains access to their user record. This is quite similar to adding friends on facebook, or requesting connections on linkedin.

一个解决方案是拥有一个单独的用户邀请对象,以便ghopper可以将alovelace添加到私人组并让其显示alovelace的邀请,而不是自动将她添加到组中。然后,alovelace需要批准添加并更新她的组成员资格。这样,只有用户才能保留对其用户记录的访问权限。这非常类似于在Facebook上添加朋友或在linkedin上请求连接。

For illustration, the schema could look something like this

为了说明,模式可能看起来像这样

// An index to track Ada's memberships
{
  "users": {
    "alovelace": {
      "name": "Ada Lovelace",
      // Index Ada's groups in her profile
      "groups": {
         // the value here doesn't matter, just that the key exists
         // Only Ada can write here
         "techpioneers": true,
         "womentechmakers": true
      }
    },
    ...
  },
  "invitations": {
    "alovelace": {
      "name": "Ada Lovelace",
      "groups": {
         // the value here doesn't matter, just that the key exists
         // Anyone can write here
         "ghoppersfanclub": true, // Ada might accept this and move it to groups
         "explicitcontentgroup": true, // Ada might reject this and delete this entry
      }
    },
    ...
  },
  "groups": {
    "techpioneers": {
     "name": "Historical Tech Pioneers",
     "members": {
        "alovelace": true,
        "ghopper": true,
        "eclarke": true
      }
    },
    ...
  }
}

Solution 2 - Server-side

解决方案2 - 服务器端

Although Firebase is meant to enable building apps without server code, there are instances where you should get the server in the mix. In my opinon, security and the execution of trusted actions like one user making changes to another user's record (if we're not using a separate object like 'invitations' above) should be handled by your trusted server using the admin API. When ghopper adds alovelace as a member, one possible event sequence would be:

虽然Firebase旨在支持在没有服务器代码的情况下构建应用程序,但有些情况下您应该将服务器混合在一起。在我看来,安全性和可信操作的执行,例如一个用户对另一个用户的记录进行更改(如果我们没有使用上面的“邀请”之类的单独对象)应由您的可信服务器使用admin API处理。当ghopper添加alovelace作为成员时,一个可能的事件序列将是:

  • Check that ghopper belongs to the group and can add another user (client-side)
  • 检查ghopper是否属于该组,并可以添加另一个用户(客户端)

  • Send a request to your server with payload that includes group name/id, user sending the request and email of the user being added

    向您的服务器发送请求,其中包含有效负载,包括组名/ ID,发送请求的用户以及正在添加的用户的电子邮件

  • Server then looks up alovelace's user id using the provided email and update the user record.

    然后,服务器使用提供的电子邮件查找alovelace的用户ID并更新用户记录。

    admin.auth().getUserByEmail(alovelace_email)
      .then(function(userRecord) {
        // Add group to alovelace's groups.
        // Trigger a client-side notification using child_changed
        // Allow alovelace to approve or decline addition to group
      })
      .catch(function(error) {
        console.log("Error fetching user data:", error);
      });
    

The above example uses email as a public/shareable unique identifier, but there's also a similar getUserByPhoneNumber(phoneNumber) method.

上面的示例使用电子邮件作为公共/可共享的唯一标识符,但也有类似的getUserByPhoneNumber(phoneNumber)方法。


推荐阅读
  • 解决.net项目中未注册“microsoft.ACE.oledb.12.0”提供程序的方法
    在开发.net项目中,通过microsoft.ACE.oledb读取excel文件信息时,报错“未在本地计算机上注册“microsoft.ACE.oledb.12.0”提供程序”。本文提供了解决这个问题的方法,包括错误描述和代码示例。通过注册提供程序和修改连接字符串,可以成功读取excel文件信息。 ... [详细]
  • 本文介绍了闭包的定义和运转机制,重点解释了闭包如何能够接触外部函数的作用域中的变量。通过词法作用域的查找规则,闭包可以访问外部函数的作用域。同时还提到了闭包的作用和影响。 ... [详细]
  • 在Android开发中,使用Picasso库可以实现对网络图片的等比例缩放。本文介绍了使用Picasso库进行图片缩放的方法,并提供了具体的代码实现。通过获取图片的宽高,计算目标宽度和高度,并创建新图实现等比例缩放。 ... [详细]
  • Nginx使用(server参数配置)
    本文介绍了Nginx的使用,重点讲解了server参数配置,包括端口号、主机名、根目录等内容。同时,还介绍了Nginx的反向代理功能。 ... [详细]
  • IhaveconfiguredanactionforaremotenotificationwhenitarrivestomyiOsapp.Iwanttwodiff ... [详细]
  • Linux重启网络命令实例及关机和重启示例教程
    本文介绍了Linux系统中重启网络命令的实例,以及使用不同方式关机和重启系统的示例教程。包括使用图形界面和控制台访问系统的方法,以及使用shutdown命令进行系统关机和重启的句法和用法。 ... [详细]
  • 目录实现效果:实现环境实现方法一:基本思路主要代码JavaScript代码总结方法二主要代码总结方法三基本思路主要代码JavaScriptHTML总结实 ... [详细]
  • android listview OnItemClickListener失效原因
    最近在做listview时发现OnItemClickListener失效的问题,经过查找发现是因为button的原因。不仅listitem中存在button会影响OnItemClickListener事件的失效,还会导致单击后listview每个item的背景改变,使得item中的所有有关焦点的事件都失效。本文给出了一个范例来说明这种情况,并提供了解决方法。 ... [详细]
  • 本文介绍了九度OnlineJudge中的1002题目“Grading”的解决方法。该题目要求设计一个公平的评分过程,将每个考题分配给3个独立的专家,如果他们的评分不一致,则需要请一位裁判做出最终决定。文章详细描述了评分规则,并给出了解决该问题的程序。 ... [详细]
  • 本文介绍了Oracle数据库中tnsnames.ora文件的作用和配置方法。tnsnames.ora文件在数据库启动过程中会被读取,用于解析LOCAL_LISTENER,并且与侦听无关。文章还提供了配置LOCAL_LISTENER和1522端口的示例,并展示了listener.ora文件的内容。 ... [详细]
  • 本文讨论了一个关于cuowu类的问题,作者在使用cuowu类时遇到了错误提示和使用AdjustmentListener的问题。文章提供了16个解决方案,并给出了两个可能导致错误的原因。 ... [详细]
  • Windows7 64位系统安装PLSQL Developer的步骤和注意事项
    本文介绍了在Windows7 64位系统上安装PLSQL Developer的步骤和注意事项。首先下载并安装PLSQL Developer,注意不要安装在默认目录下。然后下载Windows 32位的oracle instant client,并解压到指定路径。最后,按照自己的喜好对解压后的文件进行命名和压缩。 ... [详细]
  • iOS Swift中如何实现自动登录?
    本文介绍了在iOS Swift中如何实现自动登录的方法,包括使用故事板、SWRevealViewController等技术,以及解决用户注销后重新登录自动跳转到主页的问题。 ... [详细]
  • MySQL语句大全:创建、授权、查询、修改等【MySQL】的使用方法详解
    本文详细介绍了MySQL语句的使用方法,包括创建用户、授权、查询、修改等操作。通过连接MySQL数据库,可以使用命令创建用户,并指定该用户在哪个主机上可以登录。同时,还可以设置用户的登录密码。通过本文,您可以全面了解MySQL语句的使用方法。 ... [详细]
  • 本文讨论了微软的STL容器类是否线程安全。根据MSDN的回答,STL容器类包括vector、deque、list、queue、stack、priority_queue、valarray、map、hash_map、multimap、hash_multimap、set、hash_set、multiset、hash_multiset、basic_string和bitset。对于单个对象来说,多个线程同时读取是安全的。但如果一个线程正在写入一个对象,那么所有的读写操作都需要进行同步。 ... [详细]
author-avatar
浪漫的白狼族
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有