fix(medusa-plugin-brightpearl): automatic token refresh
This commit is contained in:
@@ -21,6 +21,8 @@
|
|||||||
"@babel/preset-env": "^7.7.5",
|
"@babel/preset-env": "^7.7.5",
|
||||||
"@babel/register": "^7.7.4",
|
"@babel/register": "^7.7.4",
|
||||||
"@babel/runtime": "^7.9.6",
|
"@babel/runtime": "^7.9.6",
|
||||||
|
"axios-mock-adapter": "^1.18.2",
|
||||||
|
"axios-mock-server": "^0.19.0",
|
||||||
"client-sessions": "^0.8.0",
|
"client-sessions": "^0.8.0",
|
||||||
"cross-env": "^7.0.2",
|
"cross-env": "^7.0.2",
|
||||||
"eslint": "^6.8.0",
|
"eslint": "^6.8.0",
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
import BrightpearlService from "../brightpearl"
|
import BrightpearlService from "../brightpearl"
|
||||||
import Brightpearl, { mockCreateOrder } from "../../utils/brightpearl"
|
import { mockCreateOrder } from "../../utils/brightpearl"
|
||||||
|
import MockAdapter from "axios-mock-adapter"
|
||||||
|
|
||||||
jest.mock("../../utils/brightpearl")
|
jest.mock("../../utils/brightpearl")
|
||||||
|
|
||||||
@@ -46,6 +47,43 @@ const RegionService = {
|
|||||||
}
|
}
|
||||||
|
|
||||||
describe("BrightpearlService", () => {
|
describe("BrightpearlService", () => {
|
||||||
|
describe("getClient", () => {
|
||||||
|
it("creates client", async () => {
|
||||||
|
const oauth = {
|
||||||
|
refreshToken: () => {
|
||||||
|
return Promise.resolve({
|
||||||
|
access_token: "good",
|
||||||
|
})
|
||||||
|
},
|
||||||
|
retrieveByName: () => {
|
||||||
|
return Promise.resolve({
|
||||||
|
data: {
|
||||||
|
access_token: "bad",
|
||||||
|
},
|
||||||
|
})
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
const bpService = new BrightpearlService({ oauthService: oauth }, {})
|
||||||
|
const client = await bpService.getClient()
|
||||||
|
|
||||||
|
const mockServer = new MockAdapter(client.client)
|
||||||
|
|
||||||
|
mockServer.onGet("/success").reply(() => {
|
||||||
|
return [200]
|
||||||
|
})
|
||||||
|
mockServer.onGet("/fail").reply((req) => {
|
||||||
|
if (req.headers.Authorization === "Bearer good") {
|
||||||
|
return [200]
|
||||||
|
}
|
||||||
|
return [401]
|
||||||
|
})
|
||||||
|
|
||||||
|
await client.test.fail()
|
||||||
|
await client.test.fail()
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
describe("createSalesOrder", () => {
|
describe("createSalesOrder", () => {
|
||||||
const order = {
|
const order = {
|
||||||
items: [
|
items: [
|
||||||
|
|||||||
@@ -26,10 +26,6 @@ class BrightpearlService extends BaseService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async getClient() {
|
async getClient() {
|
||||||
if (this.brightpearlClient_) {
|
|
||||||
return this.brightpearlClient_
|
|
||||||
}
|
|
||||||
|
|
||||||
const authData = await this.oauthService_.retrieveByName("brightpearl")
|
const authData = await this.oauthService_.retrieveByName("brightpearl")
|
||||||
const { data } = authData
|
const { data } = authData
|
||||||
|
|
||||||
@@ -60,7 +56,6 @@ class BrightpearlService extends BaseService {
|
|||||||
)
|
)
|
||||||
|
|
||||||
this.authData_ = data
|
this.authData_ = data
|
||||||
this.brightpearlClient_ = client
|
|
||||||
return client
|
return client
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,37 +1,89 @@
|
|||||||
|
import axios from "axios"
|
||||||
export const mockCreateOrder = jest
|
export const mockCreateOrder = jest
|
||||||
.fn()
|
.fn()
|
||||||
.mockReturnValue(Promise.resolve("1234"))
|
.mockReturnValue(Promise.resolve("1234"))
|
||||||
|
|
||||||
const mock = jest.fn().mockImplementation(() => {
|
const mock = jest.fn().mockImplementation(function (options, onRefresh) {
|
||||||
return {
|
this.token_ = options.access_token
|
||||||
warehouses: {
|
this.client = axios.create({
|
||||||
createReservation: jest.fn().mockReturnValue(Promise.resolve()),
|
baseURL: `https://mock.com`,
|
||||||
},
|
headers: {
|
||||||
payments: {
|
"brightpearl-app-ref": "medusa-dev",
|
||||||
create: jest.fn().mockReturnValue(Promise.resolve()),
|
"brightpearl-dev-ref": "sebrindom",
|
||||||
},
|
|
||||||
orders: {
|
|
||||||
create: mockCreateOrder,
|
|
||||||
retrieve: jest.fn().mockReturnValue(Promise.resolve()),
|
|
||||||
},
|
|
||||||
products: {
|
|
||||||
retrieveBySKU: jest.fn().mockReturnValue(
|
|
||||||
Promise.resolve({
|
|
||||||
productId: 1234,
|
|
||||||
})
|
|
||||||
),
|
|
||||||
},
|
|
||||||
customers: {
|
|
||||||
retrieveByEmail: jest.fn().mockReturnValue(
|
|
||||||
Promise.resolve([
|
|
||||||
{
|
|
||||||
primaryEmail: "test@example.com",
|
|
||||||
contactId: "12345",
|
|
||||||
},
|
|
||||||
])
|
|
||||||
),
|
|
||||||
},
|
},
|
||||||
|
})
|
||||||
|
|
||||||
|
this.updateAuth = (data) => {
|
||||||
|
this.token_ = data.access_token
|
||||||
}
|
}
|
||||||
|
|
||||||
|
this.client.interceptors.request.use((request) => {
|
||||||
|
const token = this.token_
|
||||||
|
|
||||||
|
if (token) {
|
||||||
|
request.headers["Authorization"] = `Bearer ${token}`
|
||||||
|
}
|
||||||
|
|
||||||
|
return request
|
||||||
|
})
|
||||||
|
|
||||||
|
this.client.interceptors.response.use(undefined, async (error) => {
|
||||||
|
const response = error.response
|
||||||
|
|
||||||
|
if (response) {
|
||||||
|
if (
|
||||||
|
response.status === 401 &&
|
||||||
|
error.config &&
|
||||||
|
!error.config.__isRetryRequest
|
||||||
|
) {
|
||||||
|
try {
|
||||||
|
await onRefresh(this)
|
||||||
|
} catch (authError) {
|
||||||
|
// refreshing has failed, but report the original error, i.e. 401
|
||||||
|
return Promise.reject(error)
|
||||||
|
}
|
||||||
|
|
||||||
|
// retry the original request
|
||||||
|
error.config.__isRetryRequest = true
|
||||||
|
return this.client(error.config)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return Promise.reject(error)
|
||||||
|
})
|
||||||
|
|
||||||
|
this.test = {
|
||||||
|
success: () => this.client.get("/success"),
|
||||||
|
fail: () => this.client.get("/fail"),
|
||||||
|
}
|
||||||
|
this.warehouses = {
|
||||||
|
createReservation: jest.fn().mockReturnValue(Promise.resolve()),
|
||||||
|
}
|
||||||
|
this.payments = {
|
||||||
|
create: jest.fn().mockReturnValue(Promise.resolve()),
|
||||||
|
}
|
||||||
|
this.orders = {
|
||||||
|
create: mockCreateOrder,
|
||||||
|
retrieve: jest.fn().mockReturnValue(Promise.resolve()),
|
||||||
|
}
|
||||||
|
this.products = {
|
||||||
|
retrieveBySKU: jest.fn().mockReturnValue(
|
||||||
|
Promise.resolve({
|
||||||
|
productId: 1234,
|
||||||
|
})
|
||||||
|
),
|
||||||
|
}
|
||||||
|
this.customers = {
|
||||||
|
retrieveByEmail: jest.fn().mockReturnValue(
|
||||||
|
Promise.resolve([
|
||||||
|
{
|
||||||
|
primaryEmail: "test@example.com",
|
||||||
|
contactId: "12345",
|
||||||
|
},
|
||||||
|
])
|
||||||
|
),
|
||||||
|
}
|
||||||
|
return this
|
||||||
})
|
})
|
||||||
|
|
||||||
export default mock
|
export default mock
|
||||||
|
|||||||
Reference in New Issue
Block a user