Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,2 +1,3 @@
node_modules
*.swp
*.sh
13 changes: 7 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,18 +8,19 @@ $ npm install libbeacon

## Example
```js
var beacon = new Libbeacon();
beacon.login('username', 'password', function(err, success) {
beacon.get('Jobs/1', {}, function(error, data) {
console.log(data);
}
const libbeacon = require('libbeacon')(client_id, client_secret, 'preview');
libbeacon.login('username', 'password').then((api) => {
api.get('Messages/')
}, (error) => {
// fail
});
*/
```

## Tests
```bash
$ npm install
$ BEACON_USERNAME='user' BEACON_PASSWORD='pass' npm test
$ IDENTITY_CLIENT_ID='' IDENTITY_CLIENT_SECRET='' BEACON_USERNAME='user' BEACON_PASSWORD='pass' npm test
```

## License
Expand Down
43 changes: 43 additions & 0 deletions lib/auth.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
const oauth2 = require('simple-oauth2');
const c = require('./constants');
const debug = require('debug')('libbeacon:auth');

module.exports = function(
client_id, client_secret, environment='prod',
) {
const credentials = {
client: {
id: client_id,
secret: client_secret,
},
auth: {
tokenHost: c.environments[environment].identity_url,
tokenPath: '/core/connect/token',
authorizePath: '/core/connect/authorize',
},
};

const api = oauth2.create(credentials);

return {
getToken: (username, password) => {
return new Promise((resolve, reject) => {
const tokenConfig = {
username: username,
password: password,
scope: c.environments[environment].oauth_scope,
};

api.ownerPassword.getToken(tokenConfig)
.then((result) => {
debug('Successful auth: ', result);
resolve(api.accessToken.create(result));
})
.catch((error) => {
debug('Auth fail: ', error);
reject(Error('Access token error: ' + error.message));
});
});
},
};
};
112 changes: 112 additions & 0 deletions lib/client.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
const c = require('./constants');
const Request = require('request');
const _ = require('underscore');
const debug = require('debug')('libbeacon:client');


class Client {
constructor(token, environment) {
debug('Initialize Client with token: ', token);
this._token = token;
this.environment = environment;
const userAgent = "libbeacon/" + c.version + " (github.com/SESMembers/libbeacon)";
this._request = Request.defaults({
rejectUnauthorized: false,
timeout: 30000,
headers: {
"User-Agent": userAgent,
"Authorization": this.authHeader,
},
});
}

get authHeader() {
return 'Bearer ' +this._token.token.access_token;
}

get path() {
return c.environments[this.environment].api_url + 'Api/v1/'
}

get(path, opts) {
return new Promise((resolve, reject) => {
debug('Get request for ' + path);
var options = _.defaults(_.clone(opts) || {}, {
headers: {}, // make sure headers is an empty obj if not passed
});
options.url = this.path + path;

debug('Making request with args: ', options);
var req = this._request(options, function(error, response, body) {
if(error) {
debug('Error in HTTP request: ' + response);
reject(error);
}
if(response.statusCode === 403 || response.statusCode === 401) {
reject(new Error("unauthorized"));
}
if(response.statusCode != 200) {
debug('Non-200 HTTP status code: ' + response.statusCode);
reject(new Error('Non-200 HTTP status code: ' + response.statusCode));
}
try {
var data = JSON.parse(body);
} catch(e) {
debug(options.url);
debug('Could not parse response: ' + body);
resolve(e)
}
resolve(null, data)
});
});
}

getPagedResults(path, opts) {
return new Promise((resolve, reject) => {
var dataresult = []
this.getPagedResultsPage(path, opts, 1, function(err,finished,data) {
dataresult = dataresult.concat(data);
err && reject(err)
finished && data && resolve(dataresult)
});
});
}

getPagedResultsPage(path, opts, page, cb) {
// cb(error, finished, data)
var self = this;
var options = _.defaults(_.clone(opts) || {}, {
qs: {}, // make sure qs is an empty obj if not passed
});
var totalItemsKey = 'TotalItems';
if(options.totalItemsKey) {
totalItemsKey = options.totalItemsKey;
delete options.totalItemsKey;
}
options.qs['PageIndex'] = page;
this.get(path, options, function(error, data) {
if(error) {
cb && cb(error);
return;
}
var bad = false;
bad = 'CurrentPage' in data ? bad : true;
bad = 'PageSize' in data ? bad : true;
bad = totalItemsKey in data ? bad : true;
bad = 'Results' in data ? bad : true;
if(bad) {
cb && cb('Received data that does not contain page information');
return;
}
if(data[totalItemsKey] > data['CurrentPage'] * data['PageSize']) {
cb && cb(null, false, data['Results']);
self.getPagedResultsPage(path, opts, page+1, cb);
}
else {
cb && cb(null, true, data['Results']);
}
});
}
}

module.exports = Client;
19 changes: 19 additions & 0 deletions lib/constants.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
const package = require('../package.json');

module.exports = {
version: package.version,
environments: {
prod: {
api_url: 'https://apibeacon.ses.nsw.gov.au/',
beacon_url: 'https://beacon.ses.nsw.gov.au/',
identity_url: 'https://identity.ses.nsw.gov.au/',
oauth_scope: 'beaconApi profile',
},
preview: {
api_url: 'https://apipreviewbeacon.ses.nsw.gov.au/',
beacon_url: 'https://previewbeacon.ses.nsw.gov.au/',
identity_url: 'https://identitypreview.ses.nsw.gov.au/',
oauth_scope: 'beaconApi profile',
},
}
}
Loading