最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Protractor: Using result of an api call - Stack Overflow

programmeradmin4浏览0评论

I created a small api to generate test data on the fly. Each call creates a fresh user and returns the created data.

To load the data I use the package request:

var flow = protractor.promise.controlFlow();
var result = flow.execute(function() {
    var defer = protractor.promise.defer();
    request('http://localhost/test/recipe/person', function (error, response, body) {
        if (!error && response.statusCode === 200) {
            defer.fulfill(JSON.parse(body));
        }
    });
    return defer.promise;
});

To make any use of the retrieved data I have to resolve the promise and proceed the test script inside a callback:

result.then(function(data) {
    element(by.model('username')).sendKeys(data.person.email);
    element(by.model('password')).sendKeys('test');
    $('button[type="submit"]').click();
});

I don't like this callback handling and the possible hell it will lead to. Besides that, Protractor is so good in hiding this messy callback handling thingy. So, the question is:

How to use the result of an async call?

At the end I would like to perform code like the following:

var flow = protractor.promise.controlFlow();
var result = flow.execute(function() {...});

element(by.model('username')).sendKeys(result.person.email);
//...

Any ideas?

I created a small api to generate test data on the fly. Each call creates a fresh user and returns the created data.

To load the data I use the package request:

var flow = protractor.promise.controlFlow();
var result = flow.execute(function() {
    var defer = protractor.promise.defer();
    request('http://localhost/test/recipe/person', function (error, response, body) {
        if (!error && response.statusCode === 200) {
            defer.fulfill(JSON.parse(body));
        }
    });
    return defer.promise;
});

To make any use of the retrieved data I have to resolve the promise and proceed the test script inside a callback:

result.then(function(data) {
    element(by.model('username')).sendKeys(data.person.email);
    element(by.model('password')).sendKeys('test');
    $('button[type="submit"]').click();
});

I don't like this callback handling and the possible hell it will lead to. Besides that, Protractor is so good in hiding this messy callback handling thingy. So, the question is:

How to use the result of an async call?

At the end I would like to perform code like the following:

var flow = protractor.promise.controlFlow();
var result = flow.execute(function() {...});

element(by.model('username')).sendKeys(result.person.email);
//...

Any ideas?

Share Improve this question asked May 16, 2014 at 23:24 scheffieldscheffield 6,7872 gold badges32 silver badges31 bronze badges 3
  • Closing as duplicate - short answer: You really can't in a good way, if you do it, it will slow your tests down a whole lot and they'll act unreliable in terms of performance. Long answer is in the duplicate question. If you feel that the duplicate I found does not cover your issue (I believe it really does) - let me know and I'll reopen this. – Benjamin Gruenbaum Commented May 16, 2014 at 23:32
  • @BenjaminGruenbaum: I don't think it's an exact duplicate. The different is the environment in which the ajax call is made. On the one side you have an event driven client in which blocking IO means a blocked UI. On the other side you have a test execution framework which key feature it is to execute subsequent async calls in one line as they where synchronous calls. – scheffield Commented May 17, 2014 at 7:49
  • Suit yourself, I think the core problem is exactly the same here, but I've reopened it – Benjamin Gruenbaum Commented May 17, 2014 at 11:26
Add a ment  | 

2 Answers 2

Reset to default 5

You can either make the http request synchronous - In most cases that's a bad thing to do.
Or, you can insert the callback into the execute function:

var flow = protractor.promise.controlFlow();
var result = flow.execute(function() {
    var defer = protractor.promise.defer();
    request('http://localhost/test/recipe/person', function (error, response, body) {
        if (!error && response.statusCode === 200) {
            defer.fulfill(JSON.parse(body));
        }
    });

    defer.promise.then(function(data) {
       element(by.model('username')).sendKeys(data.person.email);
       element(by.model('password')).sendKeys('test');
       $('button[type="submit"]').click();
    });

    return defer.promise;
});

but result will stay a promise.

It worked for me:

var request = require('request');

var options = {
  method: 'POST',
  url: 'http://testurl./endpoint/test/',
  headers: {'id': 'ABCD',
    'sessionid': 'dummyId',
    'Accept': 'application/json',
    'Accept-Language': 'en-us'
  },
  body: '{ "pay_load": [] }'
};

function callback(error, response, body) {
  if (!error && response.statusCode == 200) {
    var info = JSON.parse(body);
    console.log(body);
    console.log(info);
  }
}

request(options, callback);
发布评论

评论列表(0)

  1. 暂无评论