Angularjs 如何使用Jasmine在Angular JS工厂中测试变量

Angularjs 如何使用Jasmine在Angular JS工厂中测试变量,angularjs,unit-testing,mocking,jasmine,bdd,Angularjs,Unit Testing,Mocking,Jasmine,Bdd,我想在这个实验中测试问题bucket .factory('QA', function(ShuffleArray, RandWords){ var answersBucket = RandWords.get(9); var questionsBucket = answersBucket; var questionToRemove, answers, question; var QA = { answers:

我想在这个实验中测试
问题bucket

.factory('QA', function(ShuffleArray, RandWords){
        var answersBucket = RandWords.get(9);
        var questionsBucket = answersBucket;
        var questionToRemove, answers, question;

        var QA = {
            answers: function(amount){
                if(typeof(amount) === 'undefined') amount = 3;

                answers = ShuffleArray.shuffle(answersBucket).slice(0,amount);
                return answers;
              },
            question: function(){
                questionToRemove = questionsBucket.indexOf(answers[Math.floor(Math.random() * 3)]);
                question = questionsBucket.splice(questionToRemove, 1)[0];
                return question;
              }
          };
        return QA;
      });
正如您可以看到的那样,
questionsBucket
是QA对象中没有返回的变量,我不希望它暴露于任何使用它的东西

在Ruby中,有很多方法可以获取这些数据或访问私有方法,但我不知道如何在Angular中实现

下面是我想用茉莉花写我的测试

  it('should remove a question from the questionsBucket',
  inject(function(QA){
    var answers = QA.answers(5);
    var question = Qa.question();

    //I can't access the questionBucket :(
    expect(QA.questionsBucket).toEqual(4);

  }));

如果您想在工厂中测试它,请返回它或返回一个函数以获取它

.factory('QA', function(ShuffleArray, RandWords){
    var answersBucket = RandWords.get(9);
    var questionsBucket = answersBucket;
    var questionToRemove, answers, question;

    var QA = {
        //return it-->
        questionsBucket: questionsBucket,
        //return a way to get it-->
        getQuestionsBucket: function(){
            return questionsBucket;
        },
        answers: function(amount){
            if(typeof(amount) === 'undefined') amount = 3;

            answers = ShuffleArray.shuffle(answersBucket).slice(0,amount);
            return answers;
          },
        question: function(){
            questionToRemove = questionsBucket.indexOf(answers[Math.floor(Math.random() * 3)]);
            question = questionsBucket.splice(questionToRemove, 1)[0];
            return question;
          }
      };
    return QA;
  });
另一种选择是使用服务,并将questionsBucket作为服务的成员返回:

.service('QA', function(ShuffleArray, RandWords){
    var answersBucket = RandWords.get(9);
    this.questionsBucket = answersBucket;
    var questionToRemove, answers, question;

    this.answers= function(amount){
        if(typeof(amount) === 'undefined') amount = 3;

        answers = ShuffleArray.shuffle(answersBucket).slice(0,amount);
        return answers;
    };
    this.question= function(){
        questionToRemove = questionsBucket.indexOf(answers[Math.floor(Math.random() * 3)]);
        question = questionsBucket.splice(questionToRemove, 1)[0];
        return question;
     };
  });
或者-您可以创建另一个服务/提供商/工厂,并将其注入QA服务/工厂:

app.service('Buckets', function(RandWords){
  this.answers = RandWords.get(9);
  this.questions = answersBucket;
});
app.service('QA', function(ShuffleArray, Buckets){
  this.answersBucket = Buckets.answers;
  this.questionsBucket = Buckets.questions;
  /*all the rest here - omitted for brevity*/
});

是的,我已经实现了第一种方法,但是我真的不希望questionBucket在普通代码中可以访问。我只是想知道是否有办法将它设置为私有变量,但他们让测试访问它?没有。如果没有闭包或手柄,你就做不到;但是,在您的情况下,将
问题bucket
答案bucket
移动到他们自己的服务/提供商/工厂中,并将其注入到您需要的任何地方,可能会带来好处。然后,您可以将该可注射性作为自己的东西进行分离和测试。