检查列表中是否存在具有密钥的节点 [英] Check if a node with a key exists in a list

查看:100
本文介绍了检查列表中是否存在具有密钥的节点的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

问题



我需要在现有的firebase数据结构中进行特殊检查,并想知道是否有可能(或任何解决方法)。 >

所以现在的结构是:

$ p $ {
groups:{
group1:{name:Group one}
group2:{name:Group two}
},
成员:{
group1:{
some @ email,com:true,
another @ email,com:true
},
group2:{some @ email,com:true}
}
}

我需要并且可以轻松做到:


  1. 获取特定组中的所有用户

  2. 将用户添加到任何特定组从任何特定的组中删除用户

但是我不知道如何进行检查:有些电子邮件是任何组的成员。



组和成员的数量可以相当大,所以我不想加载所有我我不是最佳解决方案

我能找到的唯一方法是添加一个更多的对象用户并在那里保留可用的组。像这样:

  {
users:{
some @ email,com:{
groups:{
group1:true,
group2:true
}
}
}
}

在这种情况下,我可以在没有任何问题的情况下执行检查,但会添加一个请求来添加/删除操作(向成员添加电子邮件并添加groupID用户;删除成员的电子邮件,并从用户删除组ID)。

感谢您的帮助。

解决方案



例如,给定这个结构



<$ p $ 会员
Group_0
ben @ thing,com:value
jerry @ thing,com:@value
frank @ thing,com :@value
Group_1
elmo @ thing,com:value
linda @ thing,com:value

  FQuery * q1 = [ref queryOrderedByCh ILD:@ 毛毛@事情,COM]; 
FQuery * q2 = [q1 queryEqualToValue:@value];

[q2 observeEventType:FEventTypeChildAdded withBlock:^(FDataSnapshot * snapshot){
NSLog(@%@,snapshot.value);
}];

和查询返回

  Group_1 
elmo @ thing,com:value
linda @ thing,com:value


 使用未指定的索引。考虑添加.indexOn:.... etc 

下面是一个可能的解决方案:使用节点结构像这样

  emails_node 
random_node_name_0
email:jerry@thing.com
group :group_0
random_node_name_1
email:linda@thing.com
组:group_1
random_node_name_2
电子邮件:elmo@thing.com
group:group_1

和一组规则

 rules:{
.read:true,
.write:true,
emails_node :{
.indexOn:email
}
}



random_node_name_x是由childByAutoId(ObjC)创建的一个Firebase引用。

然后查询变为

  FQuery * q1 = [ref queryOrderedByChild:@email]; 
FQuery * q2 = [q1 queryEqualToValue:@elmo@thing.com];

结果是

  email =elmo@thing.com; 
group = group1;

这里的优点有两个:

1)查询返回的电子邮件和组,所以你不仅可以检查重复,但也告诉我们它在哪里(如果需要的话)



2)实际可以使用电子邮件的值,而不是解析/更改电子邮件。 (点)到,

The problem

I need to have a special check in existed firebase data structure and want to know if it is possible (or any work around).

So current structure is:

{
   groups: {
      group1: { name: "Group one" }
      group2: { name: "Group two" }
   },
   members: {
      group1: { 
         "some@email,com": true,
         "another@email,com": true
      },
      group2: { "some@email,com": true }
   }
}

What I need and can do easily:

  1. Get all users in a specific group
  2. Add a user to any specific group
  3. Remove a user from any specific group

But I have no idea how to make a check: if a user with some email is a member of any group.

Number of groups and members can be quite big so i do not want to load all members objects and check manually.

My not optimal solution

The only way I could find is to add one more object users and keep available groups there. Like so:

{
    users: {
       "some@email,com": {
           groups: {
              group1: true,
              group2: true
           }
        }
    }
}

In this case I can do the check without any problems, but will add one more request to add/remove actions (add email to members and add groupID to user; remove email from members and remove groupID from user).

Thanks for any help.

解决方案

It can be done

For example, given this structure

Members
  Group_0
    ben@thing,com: "value"
    jerry@thing,com: @"value"
    frank@thing,com: @"value"
  Group_1
    elmo@thing,com: "value"
    linda@thing,com: "value"

We construct a query as follows (ObjC)

FQuery *q1 = [ref queryOrderedByChild:@"elmo@thing,com"];
FQuery *q2 = [q1 queryEqualToValue:@"value"];

[q2 observeEventType:FEventTypeChildAdded withBlock:^(FDataSnapshot *snapshot) {
    NSLog(@"%@", snapshot.value);
}];

and the query returns

  Group_1
    elmo@thing,com: "value"
    linda@thing,com: "value"

(updated info)

The downside of the above is the key you are looking up is dynamic (the email) and there won't be a rule in place for indexing on that key - so Firebase will complain that

Using an unspecified index. Consider adding ".indexOn":....etc

Here's a possible solution: Use a node structure like this

emails_node
   random_node_name_0
      email: "jerry@thing.com"
      group: "group_0"
   random_node_name_1
      email: "linda@thing.com"
      group: "group_1"
   random_node_name_2
      email: "elmo@thing.com"
      group: "group_1"

and a set of rules

  "rules": {
    ".read": true,
    ".write": true,
    "emails_node": {
      ".indexOn": "email"
    }
  }

the random_node_name_x is a Firebase reference created by childByAutoId (ObjC)

the query then becomes

FQuery *q1 = [ref queryOrderedByChild:@"email"];
FQuery *q2 = [q1 queryEqualToValue:@"elmo@thing.com"];

the result is

email = "elmo@thing.com";
group = group1;

The advantages here are two fold:

1) The query returns both the email and group so you can not only check for duplicates but also tells us which group it's in (if needed)

2) The actual email value can be used instead of parsing/changing the email from . (dot) to ,

这篇关于检查列表中是否存在具有密钥的节点的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆