|
|
|
|
@ -1,4 +1,4 @@ |
|
|
|
|
import { BackendSrv, getBackendSrv } from '../services/backend_srv'; |
|
|
|
|
import { BackendSrv, getBackendSrv, parseInitFromOptions, parseUrlFromOptions } from '../services/backend_srv'; |
|
|
|
|
import { Emitter } from '../utils/emitter'; |
|
|
|
|
import { ContextSrv, User } from '../services/context_srv'; |
|
|
|
|
import { Observable, of } from 'rxjs'; |
|
|
|
|
@ -47,11 +47,6 @@ const getTestContext = (overides?: object) => { |
|
|
|
|
const logoutMock = jest.fn(); |
|
|
|
|
const parseRequestOptionsMock = jest.fn().mockImplementation(options => options); |
|
|
|
|
const parseDataSourceRequestOptionsMock = jest.fn().mockImplementation(options => options); |
|
|
|
|
const parseUrlFromOptionsMock = jest.fn().mockImplementation(options => options.url); |
|
|
|
|
const parseInitFromOptionsMock = jest.fn().mockImplementation(options => ({ |
|
|
|
|
method: options.method, |
|
|
|
|
url: options.url, |
|
|
|
|
})); |
|
|
|
|
|
|
|
|
|
const backendSrv = new BackendSrv({ |
|
|
|
|
fromFetch: fromFetchMock, |
|
|
|
|
@ -62,19 +57,9 @@ const getTestContext = (overides?: object) => { |
|
|
|
|
|
|
|
|
|
backendSrv['parseRequestOptions'] = parseRequestOptionsMock; |
|
|
|
|
backendSrv['parseDataSourceRequestOptions'] = parseDataSourceRequestOptionsMock; |
|
|
|
|
backendSrv['parseUrlFromOptions'] = parseUrlFromOptionsMock; |
|
|
|
|
backendSrv['parseInitFromOptions'] = parseInitFromOptionsMock; |
|
|
|
|
|
|
|
|
|
const expectCallChain = (options: any) => { |
|
|
|
|
expect(parseUrlFromOptionsMock).toHaveBeenCalledTimes(1); |
|
|
|
|
expect(parseUrlFromOptionsMock).toHaveBeenCalledWith(options); |
|
|
|
|
expect(parseInitFromOptionsMock).toHaveBeenCalledTimes(1); |
|
|
|
|
expect(parseInitFromOptionsMock).toHaveBeenCalledWith(options); |
|
|
|
|
expect(fromFetchMock).toHaveBeenCalledTimes(1); |
|
|
|
|
expect(fromFetchMock).toHaveBeenCalledWith(options.url, { |
|
|
|
|
method: options.method, |
|
|
|
|
url: options.url, |
|
|
|
|
}); |
|
|
|
|
}; |
|
|
|
|
|
|
|
|
|
const expectRequestCallChain = (options: any) => { |
|
|
|
|
@ -98,8 +83,6 @@ const getTestContext = (overides?: object) => { |
|
|
|
|
logoutMock, |
|
|
|
|
parseRequestOptionsMock, |
|
|
|
|
parseDataSourceRequestOptionsMock, |
|
|
|
|
parseUrlFromOptionsMock, |
|
|
|
|
parseInitFromOptionsMock, |
|
|
|
|
expectRequestCallChain, |
|
|
|
|
expectDataSourceRequestCallChain, |
|
|
|
|
}; |
|
|
|
|
@ -150,45 +133,6 @@ describe('backendSrv', () => { |
|
|
|
|
); |
|
|
|
|
}); |
|
|
|
|
|
|
|
|
|
describe('parseUrlFromOptions', () => { |
|
|
|
|
it.each` |
|
|
|
|
params | url | expected |
|
|
|
|
${undefined} | ${'api/dashboard'} | ${'api/dashboard'} |
|
|
|
|
${{ key: 'value' }} | ${'api/dashboard'} | ${'api/dashboard?key=value'} |
|
|
|
|
${{ key: undefined }} | ${'api/dashboard'} | ${'api/dashboard'} |
|
|
|
|
${{ firstKey: 'first value', secondValue: 'second value' }} | ${'api/dashboard'} | ${'api/dashboard?firstKey=first%20value&secondValue=second%20value'} |
|
|
|
|
${{ firstKey: 'first value', secondValue: undefined }} | ${'api/dashboard'} | ${'api/dashboard?firstKey=first%20value'} |
|
|
|
|
${{ id: [1, 2, 3] }} | ${'api/dashboard'} | ${'api/dashboard?id=1&id=2&id=3'} |
|
|
|
|
${{ id: [] }} | ${'api/dashboard'} | ${'api/dashboard'} |
|
|
|
|
`(
|
|
|
|
|
"when called with params: '$params' and url: '$url' then result should be '$expected'", |
|
|
|
|
({ params, url, expected }) => { |
|
|
|
|
expect(getBackendSrv()['parseUrlFromOptions']({ params, url })).toEqual(expected); |
|
|
|
|
} |
|
|
|
|
); |
|
|
|
|
}); |
|
|
|
|
|
|
|
|
|
describe('parseInitFromOptions', () => { |
|
|
|
|
it.each` |
|
|
|
|
method | headers | data | expected |
|
|
|
|
${undefined} | ${undefined} | ${undefined} | ${{ method: undefined, headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*' }, body: undefined }} |
|
|
|
|
${'GET'} | ${undefined} | ${undefined} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*' }, body: undefined }} |
|
|
|
|
${'GET'} | ${{ Auth: 'Some Auth' }} | ${undefined} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: undefined }} |
|
|
|
|
${'GET'} | ${{ Auth: 'Some Auth' }} | ${{ data: { test: 'Some data' } }} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: '{"data":{"test":"Some data"}}' }} |
|
|
|
|
${'GET'} | ${{ Auth: 'Some Auth' }} | ${'some data'} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: 'some data' }} |
|
|
|
|
${'GET'} | ${{ Auth: 'Some Auth' }} | ${'{"data":{"test":"Some data"}}'} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: '{"data":{"test":"Some data"}}' }} |
|
|
|
|
${'POST'} | ${{ Auth: 'Some Auth', 'Content-Type': 'application/x-www-form-urlencoded' }} | ${undefined} | ${{ method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: undefined }} |
|
|
|
|
${'POST'} | ${{ Auth: 'Some Auth', 'Content-Type': 'application/x-www-form-urlencoded' }} | ${{ data: 'Some data' }} | ${{ method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: new URLSearchParams({ data: 'Some data' }) }} |
|
|
|
|
${'POST'} | ${{ Auth: 'Some Auth', 'Content-Type': 'application/x-www-form-urlencoded' }} | ${'some data'} | ${{ method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: 'some data' }} |
|
|
|
|
${'POST'} | ${{ Auth: 'Some Auth', 'Content-Type': 'application/x-www-form-urlencoded' }} | ${'{"data":{"test":"Some data"}}'} | ${{ method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: '{"data":{"test":"Some data"}}' }} |
|
|
|
|
`(
|
|
|
|
|
"when called with method: '$method', headers: '$headers' and data: '$data' then result should be '$expected'", |
|
|
|
|
({ method, headers, data, expected }) => { |
|
|
|
|
expect(getBackendSrv()['parseInitFromOptions']({ method, headers, data, url: '' })).toEqual(expected); |
|
|
|
|
} |
|
|
|
|
); |
|
|
|
|
}); |
|
|
|
|
|
|
|
|
|
describe('request', () => { |
|
|
|
|
describe('when making a successful call and conditions for showSuccessAlert are not favorable', () => { |
|
|
|
|
it('then it should return correct result and not emit anything', async () => { |
|
|
|
|
@ -354,7 +298,15 @@ describe('backendSrv', () => { |
|
|
|
|
statusText: 'Ok', |
|
|
|
|
type: 'basic', |
|
|
|
|
url, |
|
|
|
|
request: { url, method: 'GET' }, |
|
|
|
|
request: { |
|
|
|
|
url, |
|
|
|
|
method: 'GET', |
|
|
|
|
body: undefined, |
|
|
|
|
headers: { |
|
|
|
|
'Content-Type': 'application/json', |
|
|
|
|
Accept: 'application/json, text/plain, */*', |
|
|
|
|
}, |
|
|
|
|
}, |
|
|
|
|
}); |
|
|
|
|
expect(appEventsMock.emit).not.toHaveBeenCalled(); |
|
|
|
|
expectDataSourceRequestCallChain({ url, method: 'GET', silent: true }); |
|
|
|
|
@ -366,7 +318,7 @@ describe('backendSrv', () => { |
|
|
|
|
const url = 'http://localhost:3000/api/some-mock'; |
|
|
|
|
const { backendSrv, appEventsMock, expectDataSourceRequestCallChain } = getTestContext({ url }); |
|
|
|
|
const result = await backendSrv.datasourceRequest({ url, method: 'GET' }); |
|
|
|
|
expect(result).toEqual({ |
|
|
|
|
const expectedResult = { |
|
|
|
|
data: { test: 'hello world' }, |
|
|
|
|
headers: { |
|
|
|
|
'Content-Type': 'application/json', |
|
|
|
|
@ -377,22 +329,20 @@ describe('backendSrv', () => { |
|
|
|
|
statusText: 'Ok', |
|
|
|
|
type: 'basic', |
|
|
|
|
url, |
|
|
|
|
request: { url, method: 'GET' }, |
|
|
|
|
}); |
|
|
|
|
expect(appEventsMock.emit).toHaveBeenCalledTimes(1); |
|
|
|
|
expect(appEventsMock.emit).toHaveBeenCalledWith(CoreEvents.dsRequestResponse, { |
|
|
|
|
data: { test: 'hello world' }, |
|
|
|
|
headers: { |
|
|
|
|
'Content-Type': 'application/json', |
|
|
|
|
request: { |
|
|
|
|
url, |
|
|
|
|
method: 'GET', |
|
|
|
|
body: undefined as any, |
|
|
|
|
headers: { |
|
|
|
|
'Content-Type': 'application/json', |
|
|
|
|
Accept: 'application/json, text/plain, */*', |
|
|
|
|
}, |
|
|
|
|
}, |
|
|
|
|
ok: true, |
|
|
|
|
redirected: false, |
|
|
|
|
status: 200, |
|
|
|
|
statusText: 'Ok', |
|
|
|
|
type: 'basic', |
|
|
|
|
url, |
|
|
|
|
request: { url, method: 'GET' }, |
|
|
|
|
}); |
|
|
|
|
}; |
|
|
|
|
|
|
|
|
|
expect(result).toEqual(expectedResult); |
|
|
|
|
expect(appEventsMock.emit).toHaveBeenCalledTimes(1); |
|
|
|
|
expect(appEventsMock.emit).toHaveBeenCalledWith(CoreEvents.dsRequestResponse, expectedResult); |
|
|
|
|
expectDataSourceRequestCallChain({ url, method: 'GET' }); |
|
|
|
|
}); |
|
|
|
|
}); |
|
|
|
|
@ -451,7 +401,15 @@ describe('backendSrv', () => { |
|
|
|
|
statusText: 'Ok', |
|
|
|
|
type: 'basic', |
|
|
|
|
url, |
|
|
|
|
request: { url, method: 'GET' }, |
|
|
|
|
request: { |
|
|
|
|
url, |
|
|
|
|
method: 'GET', |
|
|
|
|
body: undefined, |
|
|
|
|
headers: { |
|
|
|
|
'Content-Type': 'application/json', |
|
|
|
|
Accept: 'application/json, text/plain, */*', |
|
|
|
|
}, |
|
|
|
|
}, |
|
|
|
|
}); |
|
|
|
|
|
|
|
|
|
const slowResponse = await slowRequest; |
|
|
|
|
@ -610,3 +568,43 @@ describe('backendSrv', () => { |
|
|
|
|
}); |
|
|
|
|
}); |
|
|
|
|
}); |
|
|
|
|
|
|
|
|
|
describe('parseUrlFromOptions', () => { |
|
|
|
|
it.each` |
|
|
|
|
params | url | expected |
|
|
|
|
${undefined} | ${'api/dashboard'} | ${'api/dashboard'} |
|
|
|
|
${{ key: 'value' }} | ${'api/dashboard'} | ${'api/dashboard?key=value'} |
|
|
|
|
${{ key: undefined }} | ${'api/dashboard'} | ${'api/dashboard'} |
|
|
|
|
${{ firstKey: 'first value', secondValue: 'second value' }} | ${'api/dashboard'} | ${'api/dashboard?firstKey=first%20value&secondValue=second%20value'} |
|
|
|
|
${{ firstKey: 'first value', secondValue: undefined }} | ${'api/dashboard'} | ${'api/dashboard?firstKey=first%20value'} |
|
|
|
|
${{ id: [1, 2, 3] }} | ${'api/dashboard'} | ${'api/dashboard?id=1&id=2&id=3'} |
|
|
|
|
${{ id: [] }} | ${'api/dashboard'} | ${'api/dashboard'} |
|
|
|
|
`(
|
|
|
|
|
"when called with params: '$params' and url: '$url' then result should be '$expected'", |
|
|
|
|
({ params, url, expected }) => { |
|
|
|
|
expect(parseUrlFromOptions({ params, url })).toEqual(expected); |
|
|
|
|
} |
|
|
|
|
); |
|
|
|
|
}); |
|
|
|
|
|
|
|
|
|
describe('parseInitFromOptions', () => { |
|
|
|
|
it.each` |
|
|
|
|
method | headers | data | expected |
|
|
|
|
${undefined} | ${undefined} | ${undefined} | ${{ method: undefined, headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*' }, body: undefined }} |
|
|
|
|
${'GET'} | ${undefined} | ${undefined} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*' }, body: undefined }} |
|
|
|
|
${'GET'} | ${undefined} | ${null} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*' }, body: null }} |
|
|
|
|
${'GET'} | ${{ Auth: 'Some Auth' }} | ${undefined} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: undefined }} |
|
|
|
|
${'GET'} | ${{ Auth: 'Some Auth' }} | ${{ data: { test: 'Some data' } }} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: '{"data":{"test":"Some data"}}' }} |
|
|
|
|
${'GET'} | ${{ Auth: 'Some Auth' }} | ${'some data'} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: 'some data' }} |
|
|
|
|
${'GET'} | ${{ Auth: 'Some Auth' }} | ${'{"data":{"test":"Some data"}}'} | ${{ method: 'GET', headers: { 'Content-Type': 'application/json', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: '{"data":{"test":"Some data"}}' }} |
|
|
|
|
${'POST'} | ${{ Auth: 'Some Auth', 'Content-Type': 'application/x-www-form-urlencoded' }} | ${undefined} | ${{ method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: undefined }} |
|
|
|
|
${'POST'} | ${{ Auth: 'Some Auth', 'Content-Type': 'application/x-www-form-urlencoded' }} | ${{ data: 'Some data' }} | ${{ method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: new URLSearchParams({ data: 'Some data' }) }} |
|
|
|
|
${'POST'} | ${{ Auth: 'Some Auth', 'Content-Type': 'application/x-www-form-urlencoded' }} | ${'some data'} | ${{ method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: 'some data' }} |
|
|
|
|
${'POST'} | ${{ Auth: 'Some Auth', 'Content-Type': 'application/x-www-form-urlencoded' }} | ${'{"data":{"test":"Some data"}}'} | ${{ method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded', Accept: 'application/json, text/plain, */*', Auth: 'Some Auth' }, body: '{"data":{"test":"Some data"}}' }} |
|
|
|
|
`(
|
|
|
|
|
"when called with method: '$method', headers: '$headers' and data: '$data' then result should be '$expected'", |
|
|
|
|
({ method, headers, data, expected }) => { |
|
|
|
|
expect(parseInitFromOptions({ method, headers, data, url: '' })).toEqual(expected); |
|
|
|
|
} |
|
|
|
|
); |
|
|
|
|
}); |
|
|
|
|
|