Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

@okta/okta-sdk-nodejs

Package Overview
Dependencies
Maintainers
1
Versions
39
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@okta/okta-sdk-nodejs - npm Package Compare versions

Comparing version 3.2.0 to 3.3.1

4

CHANGELOG.md
# Okta Node SDK Changelog
## 3.3.1
- [#138](https://github.com/okta/okta-sdk-nodejs/pull/138) Add strategy to handle access token refresh
## 3.2.0

@@ -4,0 +8,0 @@

6

package.json
{
"name": "@okta/okta-sdk-nodejs",
"version": "3.2.0",
"version": "3.3.1",
"description": "Okta API wrapper for Node.js",

@@ -62,5 +62,5 @@ "engines": {

"okta": {
"commitSha": "cd47a5dbd75cf52671f9f25c82d7c54a32c48468",
"fullVersion": "3.2.0-20200302224712-cd47a5d"
"commitSha": "161205e72a67d63a2c0ed27f3120cc0107a0b698",
"fullVersion": "3.3.1-g161205e"
}
}

@@ -39,4 +39,28 @@ # okta-sdk-nodejs

### OAuth 2.0 Authentication
Okta allows you to interact with Okta APIs using scoped OAuth 2.0 access tokens. Each access token enables the bearer to perform specific actions on specific Okta endpoints, with that ability controlled by which scopes the access token contains.
This SDK supports this feature only for service-to-service applications. Please read [this guide](https://developer.okta.com/docs/guides/implement-oauth-for-okta/overview/) to learn more about how to register a new service application using a private and public key pair.
When using this approach you won't need an API Token because the SDK will request an access token for you. In order to use OAuth 2.0, construct a client instance by passing the following parameters:
```js
const client = new okta.Client({
orgUrl: 'https://{yourOktaDomain}/',
client: {
authorizationMode: 'PrivateKey',
clientId: '{oauth application ID}',
scopes: ['okta.users.manage'],
privateKey: '{JWK}' // <-- see notes below
}
});
```
The `privateKey` can be passed in the following ways:
- As a JSON encoded string of a JWK object
- A string in PEM format
- As a JSON object, in JWK format
## Table of Contents

@@ -61,2 +85,3 @@

* [Get Logs](#get-logs)
* [Call other API Endpoints](#call-other-api-endpoints)
* [Collection](#collection)

@@ -363,2 +388,33 @@ * [each](#each)

### Call other API Endpoints
Not every API endpoint is represented by a method in this library. You can call any Okta management API endpoint using this generic syntax:
```javascript
const okta = require('@okta/okta-sdk-nodejs');
// Assumes configuration is loaded via yaml or environment variables
const client = new okta.Client();
// https://developer.okta.com/docs/reference/api/apps/#preview-saml-metadata-for-application
const applicationId = '{your custom SAML app id}';
const url = `${client.baseUrl}/api/v1/apps/${applicationId}/sso/saml/metadata`;
const request = {
method: 'get',
headers: {
'Accept': 'application/xml',
'Content-Type': 'application/json',
}
};
client.http.http(url, request)
.then(res => res.text())
.then(text => {
console.log(text);
})
.catch(err => {
console.error(err);
});
```
## Collection

@@ -365,0 +421,0 @@

@@ -47,3 +47,3 @@ /*!

if (!parsedConfig.client.token) {
if (!parsedConfig.client.token && parsedConfig.client.authorizationMode !== 'PrivateKey') {
errors.push('Okta API token not provided');

@@ -50,0 +50,0 @@ }

@@ -26,4 +26,5 @@ /*!

* @param {Object} Ctor Class of each item in the collection
* @param {Request} [request] Fetch API request object
*/
constructor(client, uri, factory) {
constructor(client, uri, factory, request) {
this.nextUri = uri;

@@ -33,2 +34,3 @@ this.client = client;

this.currentItems = [];
this.request = request;
}

@@ -69,3 +71,3 @@

getNextPage() {
return this.client.http.http(this.nextUri, null, {isCollection: true})
return this.client.http.http(this.nextUri, this.request, {isCollection: true})
.then(res => {

@@ -72,0 +74,0 @@ const link = res.headers.get('link');

@@ -24,2 +24,22 @@ /*!

class Http {
static errorFilter(response) {
if (response.status >= 200 && response.status < 300) {
return Promise.resolve(response);
} else {
return response.text()
.then(body => {
let err;
// If the response is JSON, assume it's an Okta API error. Otherwise, assume it's some other HTTP error
try {
err = new OktaApiError(response.url, response.status, JSON.parse(body), response.headers);
} catch (e) {
err = new HttpError(response.url, response.status, body, response.headers);
}
throw err;
});
}
}
constructor(httpConfig) {

@@ -40,17 +60,4 @@ this.defaultHeaders = {};

let getToken;
if (this.accessToken) {
getToken = Promise.resolve(this.accessToken);
} else {
getToken = this.oauth.getAccessToken()
.then(this.errorFilter)
.then(res => res.json())
return this.oauth.getAccessToken()
.then(accessToken => {
this.accessToken = accessToken;
return accessToken;
});
}
return getToken
.then(accessToken => {
request.headers.Authorization = `Bearer ${accessToken.access_token}`;

@@ -60,22 +67,2 @@ });

errorFilter(response) {
if (response.status >= 200 && response.status < 300) {
return response;
} else {
return response.text()
.then(body => {
let err;
// If the response is JSON, assume it's an Okta API error. Otherwise, assume it's some other HTTP error
try {
err = new OktaApiError(response.url, response.status, JSON.parse(body), response.headers);
} catch (e) {
err = new HttpError(response.url, response.status, body, response.headers);
}
throw err;
});
}
}
http(uri, request, context) {

@@ -87,25 +74,41 @@ request = request || {};

request.method = request.method || 'get';
if (!this.cacheMiddleware) {
return this.prepareRequest(request)
let retriedOnAuthError = false;
const execute = () => {
const promise = this.prepareRequest(request)
.then(() => this.requestExecutor.fetch(request))
.then(this.errorFilter);
}
const ctx = {
uri, // TODO: remove unused property. req.url should be the key.
isCollection: context.isCollection,
resources: context.resources,
req: request,
cacheStore: this.cacheStore
};
return this.cacheMiddleware(ctx, () => {
if (ctx.res) {
return;
.then(Http.errorFilter)
.catch(error => {
// Clear cached token then retry request one more time
if (this.oauth && error && error.status === 401 && !retriedOnAuthError) {
retriedOnAuthError = true;
this.oauth.clearCachedAccessToken();
return execute();
}
throw error;
});
if (!this.cacheMiddleware) {
return promise;
}
return this.prepareRequest(request)
.then(() => this.requestExecutor.fetch(request))
.then(this.errorFilter)
.then(res => ctx.res = res);
})
.then(() => ctx.res);
const ctx = {
uri, // TODO: remove unused property. req.url should be the key.
isCollection: context.isCollection,
resources: context.resources,
req: request,
cacheStore: this.cacheStore
};
return this.cacheMiddleware(ctx, () => {
if (ctx.res) {
return;
}
return promise.then(res => ctx.res = res);
})
.then(() => ctx.res);
};
return execute();
}

@@ -112,0 +115,0 @@

@@ -35,3 +35,3 @@ const nJwt = require('njwt');

function makeJwt(client) {
function makeJwt(client, endpoint) {
const now = Math.floor(new Date().getTime() / 1000); // seconds since epoch

@@ -41,3 +41,3 @@ const plus5Minutes = new Date((now + (5 * 60)) * 1000); // Date object

const claims = {
aud: `${client.baseUrl}/oauth2/v1/token`,
aud: `${client.baseUrl}${endpoint}`,
};

@@ -44,0 +44,0 @@ return getPemAndJwk(client.privateKey)

const { makeJwt } = require('./jwt');
const Http = require('./http');

@@ -24,7 +25,12 @@ function formatParams(obj) {

this.client = client;
this.jwt = null;
this.accessToken = null;
}
getAccessToken() {
return this.getJwt()
if (this.accessToken) {
return Promise.resolve(this.accessToken);
}
const endpoint = '/oauth2/v1/token';
return this.getJwt(endpoint)
.then(jwt => {

@@ -38,3 +44,3 @@ const params = formatParams({

return this.client.requestExecutor.fetch({
url: `${this.client.baseUrl}/oauth2/v1/token`,
url: `${this.client.baseUrl}${endpoint}`,
method: 'POST',

@@ -47,17 +53,21 @@ body: params,

});
})
.then(Http.errorFilter)
.then(res => res.json())
.then(accessToken => {
this.accessToken = accessToken;
return this.accessToken;
});
}
getJwt() {
if (!this.jwt) {
return makeJwt(this.client)
.then(jwt => {
this.jwt = jwt.compact();
return this.jwt;
});
}
return Promise.resolve(this.jwt);
clearCachedAccessToken() {
this.accessToken = null;
}
getJwt(endpoint) {
return makeJwt(this.client, endpoint)
.then(jwt => jwt.compact());
}
}
module.exports = OAuth;
SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc