Promise.all 和 Firebase DataSnapshot.forEach [英] Promise.all with Firebase DataSnapshot.forEach

查看:25
本文介绍了Promise.all 和 Firebase DataSnapshot.forEach的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有几个 HTML 选择(下拉列表),它们是从名为状态"的 Firebase 节点填充的(见下图).选择一个城市后,下面的函数会触发并检索在该城市发生的所有会议.有一个单独的会议"节点,每个会议都有各种键/值对,例如街道、时间等.

I have a couple of HTML select's (dropdowns) that are populated from a Firebase node called "states" (see image below). Upon choosing a city, the below function fires and should retrieve all meetings occurring in that City. There is a separate "meetings" node and each meeting has various key/value pairs such as street, time, etc.

我(认为我)想使用 Promise.all,因为我想在 DataSnapshot.forEach 中执行 Firebase 读取(每个会议 ID 上的 .once).下面不起作用.

I (think that I) want to use Promise.all because I want to do a Firebase read (a .once on each meetingID) inside the DataSnapshot.forEach. Below does not work.

function loadMeetings(city,state){
    //$('#meetingsTable').empty();
    var reads = [];
    ref.child('states').child(state).child(city).once('value').then(function(snapshot) {
        snapshot.forEach(function(childSnapshot) {
            var id = childSnapshot.key();
            var dfd = ref.child('meetings').child(id).once('value').then(function(snap) {
                // The Promise was fulfilled.
            }, function(error) {
                // The Promise was rejected.
                console.error(error);
            });
            reads.push( dfd );
        });       
    }, function(error) {
        // The Promise was rejected.
        console.error(error);
    });

    Promise.all(reads).then(function(values) { 
      console.log(values); // [snap, snap, snap] 
    });
}

{
  "geofire" : {
    "25dbab9c-8e4e-45ce-a69b-8641b6579560" : {
      ".priority" : "9q5cc9ye4w",
      "g" : "9q5cc9ye4w",
      "l" : [ 34.0677809, -118.4016105 ]
    },
    "3d2c7948-16e5-466c-b0d8-0a9e24ed7529" : {
      ".priority" : "7zzzzzzzzz",
      "g" : "7zzzzzzzzz",
      "l" : [ 0, 0 ]
    },
    "3fc846d4-7e55-4134-a0f5-9393aaf02269" : {
      ".priority" : "dhyy1zhnu1",
      "g" : "dhyy1zhnu1",
      "l" : [ 27.8130538, -80.42524100000003 ]
    },
    "5952bd9f-8438-44b0-addb-a5b806dab5da" : {
      ".priority" : "9vw1zzv421",
      "g" : "9vw1zzv421",
      "l" : [ 31.288082, -92.46505450000001 ]
    },
    "7001c8a7-c4f0-44ba-a4fc-2dba32097cc6" : {
      ".priority" : "9vqe68qs06",
      "g" : "9vqe68qs06",
      "l" : [ 30.1046126, -91.99056969999998 ]
    },
    "ecb350d6-6664-4f95-9c1c-2fd1d2f11a40" : {
      ".priority" : "9vrk9tstc9",
      "g" : "9vrk9tstc9",
      "l" : [ 30.353474, -90.98251599999998 ]
    }
  },
  "markup" : {
    "addMeeting" : "<form class="outline"><div class="row"><h1 class="blue topTitle col-xs-10 col-xs-offset-1 col-md-4 col-md-offset-4">New Meeting</h1></div><br><div class="form-group row"><div class="col-xs-10 col-xs-offset-1 col-md-3 col-md-offset-2"> <input type="text" class="form-control" id="meetingName" placeholder="Meeting Name"> </div><div class="col-xs-10 col-xs-offset-1 col-md-4 col-md-pull-1"> <input type="text" class="form-control" id="meetingStreet" placeholder="Street" required> </div></div><div class="form-group row"><div class="col-xs-10 col-xs-offset-1 col-md-3 col-md-offset-2"> <input type="text" class="form-control" id="meetingCity" placeholder="City" required> </div><div class="col-xs-10 col-xs-offset-1 col-md-2 col-md-pull-1"> <select class="form-control c-select" id="meetingState" required><option>Alabama </option><option>Alaska</option><option>Arizona</option><option>Arkansas</option><option>California</option><option>Colorado</option><option>Connecticut</option><option>Delaware</option><option>Florida</option><option>Georgia</option><option>Hawaii</option><option>Idaho</option><option>Illinois</option><option>Indiana</option><option>Iowa</option><option>Kansas</option><option>Kentucky</option><option>Louisiana</option><option>Maine</option><option>Maryland</option><option>Massachusetts</option><option>Michigan</option><option>Minnesota</option><option>Mississippi</option><option>Missouri</option><option>Montana</option><option>Nebraska</option><option>Nevada</option><option>New Hampshire</option><option>New Jersey</option><option>New Mexico</option><option>New York</option><option>North Carolina</option><option>North Dakota</option><option>Ohio</option><option>Oklahoma</option><option>Oregon</option><option>Pennsylvania</option><option>Rhode Island</option><option>South Carolina</option><option>South Dakota</option><option>Tennessee</option><option>Texas</option><option>Utah</option><option>Vermont</option><option>Virginia</option><option>Washington</option><option>West Virginia</option><option>Wisconsin</option><option>Wyoming</option></select></div><div class="col-xs-10 col-xs-offset-1 col-md-2 col-md-pull-2"> <input type="text" class="form-control" id="meetingZip" placeholder="ZIP" required> </div></div><div class="form-group row"><div class="col-xs-5 col-xs-offset-1 col-md-2 col-md-offset-2"> <input type="text" class="form-control" id="latitude" placeholder="latitude" disabled> </div><div class="col-xs-5 col-md-2 pull-left"> <input type="text" class="form-control" id="longitude" placeholder="longitude" disabled> </div></div><div class="form-group row"><div class="col-xs-10 col-xs-offset-1 col-md-2 col-md-offset-2"><select class="form-control c-select" id="weekday"><option>Sunday</option><option>Monday</option><option>Tuesday</option><option>Wednesday</option><option>Thursday</option><option>Friday</option><option>Saturday</option></select></div><div class="col-xs-10 col-xs-offset-1 col-md-3 col-md-pull-1"><div class="form-inline"><div class="form-group"><select class="form-control c-select" id="hour"><option>1</option><option>2</option><option>3</option><option>4</option><option>5</option><option>6</option><option>7</option><option>8</option><option>9</option><option>10</option><option>11</option><option>12</option></select><select class="form-control c-select" id="minute"><option>:00</option><option>:15</option><option>:30</option><option>:45</option></select><select class="form-control c-select" id="timeframe"><option>AM</option><option>PM</option></select></div></div></div></div><div class="form-group row"><div class="col-xs-10 col-xs-offset-1 col-md-4 col-md-offset-2"> <label class="radio-inline c-input c-radio"> <input type="radio" name="meetingType" id="openMeeting"> <span class="c-indicator"></span> Open Meeting </label> <label class="radio-inline c-input c-radio"> <input type="radio" name="meetingType" id="closedMeeting" checked> <span class="c-indicator"></span> Closed Meeting </label> </div></div><div class="form-group row"><div class="col-xs-5 col-xs-offset-1 col-md-2 col-md-offset-2"> <label class="c-input c-checkbox"> <input type="checkbox" id="mensOnly"> <span class="c-indicator"></span> Mens Only </label><br><label class="c-input c-checkbox"> <input type="checkbox" id="womensOnly"> <span class="c-indicator"></span> Womens Only </label><br><label class="c-input c-checkbox"> <input type="checkbox" id="childcare"> <span class="c-indicator"></span> Childcare </label> </div><div class="col-xs-5 col-xs-offset-1 col-md-2 col-md-pull-1"> <label class="c-input c-checkbox"> <input type="checkbox" id="meditation"> <span class="c-indicator"></span> Meditation </label><br><label class="c-input c-checkbox"> <input type="checkbox" id="speaker"> <span class="c-indicator"></span> Speaker </label><br><label class="c-input c-checkbox"> <input type="checkbox" id="step"> <span class="c-indicator"></span> Step </label> </div></div><div class="form-group row"><div class="col-xs-5 col-xs-offset-1 col-md-2 col-md-offset-2"> <label class="c-input c-checkbox"> <input type="checkbox" id="spanish"> <span class="c-indicator"></span> Español </label><br><label class="c-input c-checkbox"> <input type="checkbox" id="bigBook"> <span class="c-indicator"></span> Big Book </label><br><label class="c-input c-checkbox"> <input type="checkbox" id="discussion"> <span class="c-indicator"></span> Discussion </label> </div><div class="col-xs-5 col-xs-offset-1 col-md-2 col-md-pull-1"> <label class="c-input c-checkbox"> <input type="checkbox" id="tradition"> <span class="c-indicator"></span> Tradition </label><br><label class="c-input c-checkbox"> <input type="checkbox" id="beginner"> <span class="c-indicator"></span> Beginner </label> </div></div><div class="form-group row"><div class="col-xs-5 col-xs-offset-8 col-md-2 col-md-offset-8"> <input class="btn btn-primary" type="submit" id="submit"></input> </div></div></form>",
    "admin" : "<ul id="tabs" class="nav nav-tabs"> <li class="nav-item"> <a data-toggle="tab" class="nav-link active" href="#adminWelcome" role="tab">Welcome</a> </li><li class="nav-item dropdown"> <a class="nav-link dropdown-toggle" data-toggle="dropdown" href="#" role="button" aria-haspopup="true" aria-expanded="false">Meetings</a> <div class="dropdown-menu"> <a data-toggle="tab" class="dropdown-item" href="#addMeeting">Add</a> <a data-toggle="tab" class="dropdown-item" href="#manageMeeting">Manage</a> </div></li><li class="nav-item dropdown"> <a class="nav-link dropdown-toggle" data-toggle="dropdown" href="#" role="button" aria-haspopup="true" aria-expanded="false">Users</a> <div class="dropdown-menu"> <a data-toggle="tab" class="dropdown-item" href="#addUser">Add</a> <a data-toggle="tab" class="dropdown-item" href="#manageUser">Manage</a> </div></li></ul> <div class="tab-content"> <div id="adminWelcome" class="tab-pane fade in active" role="tabpanel"> <h3 class="topTitle">Welcome.</h3><div class="loader"><img src="images/loading.gif"><p class="blue">Running Scripts...</p></div><script>adminInit();</script> </div><div id="addMeeting" class="tab-pane fade" role="tabpanel"><div class="loader"><img src="images/loading.gif"><p class="blue">Running Scripts...</p></div></div><div id="manageMeeting" class="tab-pane fade" role="tabpanel"><div class="loader"><img src="images/loading.gif"><p class="blue">Running Scripts...</p></div></div><div id="addUser" class="tab-pane fade" role="tabpanel"><div class="loader"><img src="images/loading.gif"><p class="blue">Running Scripts...</p></div></div><div id="manageUser" class="tab-pane fade" role="tabpanel"><div class="loader"><img src="images/loading.gif"><p class="blue">Running Scripts...</p></div></div></div>",
    "adminWelcome" : "<p>This is the admin welcome pane</p>",
    "login" : "<div class="row topMargin myLogin col-xs-10 col-xs-offset-1 col-md-6 col-md-offset-3"><br><h1 class="">Log In</h1><br><div class="btn-group-vertical" role="group"><button class="btn btn-secondary myButton" id="facebook"><img src="images/facebook.png" class="middle" alt="Facebook logo" height="24"> Facebook</button><button class="btn btn-secondary myButton" id="google"><img src="images/google.png" class="middle" alt="Google logo" height="24"> Google</button><button class="btn btn-secondary myButton" id="twitter"><img src="images/twitter.png" class="middle" alt="Twitter logo" height="24"> Twitter</button></div><br><br><br></div>",
    "manageMeeting" : "<form class="form-inline outline"><div class="form-group"><label for="ddState">Filter&nbsp; </label><select class="form-control" id="ddState" disabled></select></div><div class="form-group"><label for="ddState">&nbsp;&nbsp;&nbsp; </label><select class="form-control state" id="ddCity" disabled></select></div></form>"
  },
  "meetings" : {
    "25dbab9c-8e4e-45ce-a69b-8641b6579560" : {
      "author" : "Ron Royston",
      "beginner" : true,
      "bigBook" : true,
      "childcare" : false,
      "city" : "los angeles",
      "day" : "sunday",
      "discussion" : false,
      "hour" : "4",
      "key" : "25dbab9c-8e4e-45ce-a69b-8641b6579560",
      "latitude" : 34.0677809,
      "layer" : "",
      "longitude" : -118.4016105,
      "meditation" : false,
      "meetingOpen" : false,
      "min" : ":00",
      "name" : "highrise",
      "onlyMen" : false,
      "onlyWomen" : true,
      "spanish" : true,
      "speaker" : false,
      "state" : "california",
      "step" : false,
      "street" : "111 rodeo",
      "timeframe" : "pm",
      "timestamp" : 1457470568863,
      "tradition" : true,
      "type" : "",
      "user" : "facebook:196986260658947",
      "zip" : "90210"
    },
    "3d2c7948-16e5-466c-b0d8-0a9e24ed7529" : {
      "author" : "Ron Royston",
      "beginner" : false,
      "bigBook" : false,
      "childcare" : false,
      "city" : "baton rouge",
      "day" : "sunday",
      "discussion" : false,
      "hour" : "1",
      "key" : "3d2c7948-16e5-466c-b0d8-0a9e24ed7529",
      "latitude" : 0,
      "layer" : "",
      "longitude" : 0,
      "meditation" : false,
      "meetingOpen" : false,
      "min" : ":00",
      "name" : "asdf",
      "onlyMen" : false,
      "onlyWomen" : false,
      "spanish" : false,
      "speaker" : false,
      "state" : "louisiana",
      "step" : false,
      "street" : "234 kjhkj",
      "timeframe" : "am",
      "timestamp" : 1457470215505,
      "tradition" : false,
      "type" : "",
      "user" : "facebook:196986260658947",
      "zip" : "70817"
    },
    "3fc846d4-7e55-4134-a0f5-9393aaf02269" : {
      "author" : "Ron Royston",
      "beginner" : false,
      "bigBook" : true,
      "childcare" : true,
      "city" : "miami",
      "day" : "sunday",
      "discussion" : true,
      "hour" : "1",
      "key" : "3fc846d4-7e55-4134-a0f5-9393aaf02269",
      "latitude" : 27.8130538,
      "layer" : "",
      "longitude" : -80.42524100000003,
      "meditation" : false,
      "meetingOpen" : false,
      "min" : ":00",
      "name" : "beach",
      "onlyMen" : false,
      "onlyWomen" : false,
      "spanish" : true,
      "speaker" : false,
      "state" : "florida",
      "step" : false,
      "street" : "120 a1a",
      "timeframe" : "am",
      "timestamp" : 1457470499310,
      "tradition" : false,
      "type" : "",
      "user" : "facebook:196986260658947",
      "zip" : "33101"
    },
    "5952bd9f-8438-44b0-addb-a5b806dab5da" : {
      "author" : "Ron Royston",
      "beginner" : true,
      "bigBook" : false,
      "childcare" : false,
      "city" : "alexandria",
      "day" : "sunday",
      "discussion" : false,
      "hour" : "1",
      "key" : "5952bd9f-8438-44b0-addb-a5b806dab5da",
      "latitude" : 31.288082,
      "layer" : "",
      "longitude" : -92.46505450000001,
      "meditation" : false,
      "meetingOpen" : false,
      "min" : ":00",
      "name" : "howdy",
      "onlyMen" : false,
      "onlyWomen" : false,
      "spanish" : false,
      "speaker" : false,
      "state" : "louisiana",
      "step" : false,
      "street" : "5676 city park",
      "timeframe" : "am",
      "timestamp" : 1457470284850,
      "tradition" : true,
      "type" : "",
      "user" : "facebook:196986260658947",
      "zip" : "71301"
    },
    "7001c8a7-c4f0-44ba-a4fc-2dba32097cc6" : {
      "author" : "Ron Royston",
      "beginner" : false,
      "bigBook" : false,
      "childcare" : false,
      "city" : "lafayette",
      "day" : "sunday",
      "discussion" : false,
      "hour" : "1",
      "key" : "7001c8a7-c4f0-44ba-a4fc-2dba32097cc6",
      "latitude" : 30.1046126,
      "layer" : "",
      "longitude" : -91.99056969999998,
      "meditation" : false,
      "meetingOpen" : false,
      "min" : ":00",
      "name" : "test3",
      "onlyMen" : false,
      "onlyWomen" : false,
      "spanish" : false,
      "speaker" : false,
      "state" : "louisiana",
      "step" : false,
      "street" : "234 kjhkj",
      "timeframe" : "am",
      "timestamp" : 1457470252872,
      "tradition" : false,
      "type" : "",
      "user" : "facebook:196986260658947",
      "zip" : "70500"
    },
    "ecb350d6-6664-4f95-9c1c-2fd1d2f11a40" : {
      "author" : "Ron Royston",
      "beginner" : false,
      "bigBook" : false,
      "childcare" : false,
      "city" : "baton rouge",
      "day" : "sunday",
      "discussion" : false,
      "hour" : "5",
      "key" : "ecb350d6-6664-4f95-9c1c-2fd1d2f11a40",
      "latitude" : 30.353474,
      "layer" : "",
      "longitude" : -90.98251599999998,
      "meditation" : true,
      "meetingOpen" : false,
      "min" : ":00",
      "name" : "test1",
      "onlyMen" : false,
      "onlyWomen" : false,
      "spanish" : false,
      "speaker" : true,
      "state" : "louisiana",
      "step" : false,
      "street" : "18432 lake iris",
      "timeframe" : "pm",
      "timestamp" : 1457470192281,
      "tradition" : false,
      "type" : "",
      "user" : "facebook:196986260658947",
      "zip" : "70817"
    }
  },
  "states" : {
    "california " : {
      "los angeles" : {
        "25dbab9c-8e4e-45ce-a69b-8641b6579560" : true
      }
    },
    "florida " : {
      "miami" : {
        "3fc846d4-7e55-4134-a0f5-9393aaf02269" : true
      }
    },
    "louisiana " : {
      "alexandria" : {
        "5952bd9f-8438-44b0-addb-a5b806dab5da" : true
      },
      "baton rouge" : {
        "3d2c7948-16e5-466c-b0d8-0a9e24ed7529" : true,
        "ecb350d6-6664-4f95-9c1c-2fd1d2f11a40" : true
      },
      "lafayette" : {
        "7001c8a7-c4f0-44ba-a4fc-2dba32097cc6" : true
      }
    }
  }
}

推荐答案

你必须在用 promise 填充数组后执行 Promise.all,即在 then 回调:

You have to execute the Promise.all after you filled the array with promises, i.e. inside the then callback:

function loadMeetings(city,state) {
    //$('#meetingsTable').empty();
    return ref.child('states').child(state).child(city).once('value').then(function(snapshot) {
        var reads = [];
//      ^^^^^^^^^^^^^^
        snapshot.forEach(function(childSnapshot) {
            var id = childSnapshot.key;
            var promise = ref.child('meetings').child(id).once('value').then(function(snap) {
                // The Promise was fulfilled.
            }, function(error) {
                // The Promise was rejected.
                console.error(error);
            });
            reads.push(promise);
        });
        return Promise.all(reads);
//      ^^^^^^^^^^^^^^^^^
    }, function(error) {
        // The Promise was rejected.
        console.error(error);
    }).then(function(values) { 
        console.log(values); // [snap, snap, snap] 
    });
}

这篇关于Promise.all 和 Firebase DataSnapshot.forEach的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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