是否有相当于$ scope。$ apply?

时间:2017-02-17 01:54:07

标签: javascript angularjs firebase ionic-framework firebase-realtime-database

我在Javascript中遇到错误,因为我的$ digest周期显然都在同时运行。

我收到错误:Error: [$rootScope:inprog] $digest already in progress

我想知道我是否可以使用某些东西来阻止这些循环,或者我可能没有正确定义我的功能?

这是我的控制器的代码,你可以看到有两个不同的$ scope函数,第二个似乎是问题:

.controller('accountController',['$scope', '$firebaseArray', 'CONFIG', '$document', '$state', function($scope, $firebaseArray, CONFIG, $document, $state) {
  // Create a reference to the file we want to download
  var userId = firebase.auth().currentUser.uid;
  console.log(userId);
  var database = firebase.database().ref('/accounts/' + userId);
  var storageRef = firebase.storage();
  var pathReference = storageRef.ref('/' + userId + 'profilepic.jpg');
  // Get the download URL
  pathReference.getDownloadURL().then(function(url) {
  // Insert url into an <img> tag to "download"
    $scope.$apply(function() {
      $scope.imageUrl = url;
      database.on('value', function(snapshot) {
  var displayProfilePic = snapshot.val().photoURL;
  $scope.displayProfilePic = displayProfilePic;



  });

            });



  });
  var database = firebase.database().ref('/accounts/' + userId);
    database.on('value', function(snapshot) {
       var displayName = snapshot.val().name;
        var description = snapshot.val().description;
      var displayHobbies = snapshot.val().hobbies;
      var displayFacebook = snapshot.val().facebook;
      var displayTwitter = snapshot.val().twitter;
      var displayInstagram = snapshot.val().instagram;
      var displayYoutube = snapshot.val().youtube;
      var displaySnapchat = snapshot.val().snapchat;
      var displayLinkedin = snapshot.val().linkedin;
      var displayProfilePic = snapshot.val().photoURL;

         $scope.$apply(function() {
                        $scope.displayName = displayName;
                        $scope.description = description;
            $scope.displayHobbies = displayHobbies;
            $scope.displayFacebook = displayFacebook;
            $scope.displayTwitter = displayTwitter;
            $scope.displayInstagram = displayInstagram;
            $scope.displayYoutube = displayYoutube;
            $scope.displaySnapchat = displaySnapchat;
            $scope.displayLinkedin = displayLinkedin;
            $scope.displayProfilePic = displayProfilePic;

            // Hide Social buttons if no value in Database :
            if (displayFacebook === "") {
              document.getElementById('iconFacebook').style.color = '#EFF1F5';
              var anchor = document.getElementById("linkFacebook");  // Get the <a> element with id="myAnchor"
              var att = document.createAttribute("href");        // Create a "href" attribute
              att.value = "#";            // Set the value of the href attribute
              anchor.setAttributeNode(att);
            } else {
              document.getElementById('iconFacebook').style.color = '#80d5f2';
              var anchor = document.getElementById("linkFacebook");  // Get the <a> element with id="myAnchor"
              var att = document.createAttribute("href");        // Create a "href" attribute
              att.value = "http://www.facebook.com/" + displayFacebook;            // Set the value of the href attribute
              anchor.setAttributeNode(att);                      // Add the href attribute to <a>
              };
              if (displayTwitter === "") {
                document.getElementById('iconTwitter').style.color = '#EFF1F5';
                var anchor = document.getElementById("linkTwitter");  // Get the <a> element with id="myAnchor"
                var att = document.createAttribute("href");        // Create a "href" attribute
                att.value = "#";            // Set the value of the href attribute
                anchor.setAttributeNode(att);
              } else {
                document.getElementById('iconTwitter').style.color = '#80d5f2';
                var anchor = document.getElementById("linkTwitter");  // Get the <a> element with id="myAnchor"
                var att = document.createAttribute("href");        // Create a "href" attribute
                att.value = "http://www.twitter.com/" + displayTwitter;            // Set the value of the href attribute
                anchor.setAttributeNode(att);
                };
                if (displayInstagram === "") {
                  document.getElementById('iconInstagram').style.color = '#EFF1F5';
                  var anchor = document.getElementById("linkInstagram");  // Get the <a> element with id="myAnchor"
                  var att = document.createAttribute("href");        // Create a "href" attribute
                  att.value = "#";            // Set the value of the href attribute
                  anchor.setAttributeNode(att);
                } else {
                  document.getElementById('iconInstagram').style.color = '#80d5f2';
                  var anchor = document.getElementById("linkInstagram");  // Get the <a> element with id="myAnchor"
                  var att = document.createAttribute("href");        // Create a "href" attribute
                  att.value = "http://www.instagram.com/" + displayInstagram;            // Set the value of the href attribute
                  anchor.setAttributeNode(att);
                  };
                  if (displayYoutube === "") {
                    document.getElementById('iconYoutube').style.color = '#EFF1F5';
                    var anchor = document.getElementById("linkYoutube");  // Get the <a> element with id="myAnchor"
                    var att = document.createAttribute("href");        // Create a "href" attribute
                    att.value = "#";            // Set the value of the href attribute
                    anchor.setAttributeNode(att);
                  } else {
                    document.getElementById('iconYoutube').style.color = '#80d5f2';
                    var anchor = document.getElementById("linkYoutube");  // Get the <a> element with id="myAnchor"
                    var att = document.createAttribute("href");        // Create a "href" attribute
                    att.value = "http://www.youtube.com/" + displayYoutube;            // Set the value of the href attribute
                    anchor.setAttributeNode(att);
                    };
                    if (displaySnapchat === "") {
                      document.getElementById('iconSnapchat').style.color = '#EFF1F5';
                      var anchor = document.getElementById("linkSnapchat");  // Get the <a> element with id="myAnchor"
                      var att = document.createAttribute("href");        // Create a "href" attribute
                      att.value = "#";            // Set the value of the href attribute
                      anchor.setAttributeNode(att);
                    } else {
                      document.getElementById('iconSnapchat').style.color = '#80d5f2';
                      var anchor = document.getElementById("linkSnapchat");  // Get the <a> element with id="myAnchor"
                      var att = document.createAttribute("href");        // Create a "href" attribute
                      att.value = "http://www.snapchat.com/" + displaySnapchat;            // Set the value of the href attribute
                      anchor.setAttributeNode(att);
                      };
                      if (displayLinkedin === "") {
                        document.getElementById('iconLinkedin').style.color = '#EFF1F5';
                        var anchor = document.getElementById("linkLinkedin");  // Get the <a> element with id="myAnchor"
                        var att = document.createAttribute("href");        // Create a "href" attribute
                        att.value = "#";            // Set the value of the href attribute
                        anchor.setAttributeNode(att);
                      } else {
                        document.getElementById('iconLinkedin').style.color = '#80d5f2';
                        var anchor = document.getElementById("linkLinkedin");  // Get the <a> element with id="myAnchor"
                        var att = document.createAttribute("href");        // Create a "href" attribute
                        att.value = "http://www.linkedin.com/" + displayLinkedin;            // Set the value of the href attribute
                        anchor.setAttributeNode(att);
                        };

                });

    });

}])

感谢您的建议!

编辑:我使用带有标签的应用,我认为这些标签不会停止每次屏幕转换之间的循环?也许?

2 个答案:

答案 0 :(得分:2)

您始终可以将$scope.$apply替换为$scope.$evalAsync$timeout。下面解释了每个人的作用:

$scope.$evalAsync - 在当前摘要周期内执行回调,或者创建一个没有运行摘要的新回调。

$timeout - 等待当前摘要(如果有)完成,然后在新摘要中运行回调。

希望这会有所帮助。

汤姆

答案 1 :(得分:0)

  

错误:$ rootScope:inprog

     

行动已在进行中

     

<强>描述

     

在任何时间点,只能进行一次$digest$apply操作。这是为了防止很难检测到进入您的应用程序的错误。此错误的堆栈跟踪允许您跟踪当前正在执行的$apply$digest调用的来源,这会导致错误。

     

摘要阶段

     

AngularJS会跟踪我们处理的处理阶段,相关的处理是$apply$digest当其中一个正在进行中时,尝试重新输入$digest$apply通常是需要修复的编程错误的迹象。因此,当发生这种情况时,AngularJS会抛出此错误。

代码显然需要修复。

  

诊断此错误

     

当您收到此错误时,诊断问题的原因可能相当令人生畏。最好的做法是调查错误中的堆栈跟踪。您需要查找已调用$apply$digest的位置,并找到发生此情况的上下文。

     

应该有两个电话:

     
      
  • 第一个电话是好$apply / $digest,通常会被调用堆栈顶部附近的某个事件触发。

  •   
  • 第二个电话是错误的$apply / $digest,这是要调查的电话。

  •   
     

一旦你确定了这个电话,你就可以在堆栈中找到问题所在。

     

如果在您的应用程序代码中进行了第二次调用,那么您应该查看为什么在$apply / $digest内调用此代码。这可能是一个简单的疏忽,也可能适合前面描述的同步/异步方案。

     

如果第二次调用是在AngularJS指令内进行的,那么很可能它与前面描述的第二个编程事件触发器场景相匹配。在这种情况下,您可能需要进一步查看树,以便首先触发事件。

有关详细信息,请参阅AngularJS inprog Error Reference -- Diagnosing This Error