1
0
mirror of https://github.com/sasjs/adapter.git synced 2026-01-20 10:30:06 +00:00

Compare commits

..

1 Commits

Author SHA1 Message Date
snyk-bot
28e0e3a147 fix: upgrade axios from 0.26.0 to 0.26.1
Snyk has created this PR to upgrade axios from 0.26.0 to 0.26.1.

See this package in npm:
https://www.npmjs.com/package/axios

See this project in Snyk:
https://app.snyk.io/org/allanbowe/project/2cf085e5-c256-4a84-bf6a-227076754853?utm_source=github&utm_medium=referral&page=upgrade-pr
2022-03-30 20:49:57 +00:00
14 changed files with 121 additions and 142 deletions

28
package-lock.json generated
View File

@@ -8,8 +8,8 @@
"hasInstallScript": true, "hasInstallScript": true,
"license": "ISC", "license": "ISC",
"dependencies": { "dependencies": {
"@sasjs/utils": "2.42.0", "@sasjs/utils": "2.40.0",
"axios": "0.26.0", "axios": "^0.26.1",
"axios-cookiejar-support": "1.0.1", "axios-cookiejar-support": "1.0.1",
"form-data": "4.0.0", "form-data": "4.0.0",
"https": "1.0.0", "https": "1.0.0",
@@ -1142,9 +1142,9 @@
} }
}, },
"node_modules/@sasjs/utils": { "node_modules/@sasjs/utils": {
"version": "2.42.0", "version": "2.40.0",
"resolved": "https://registry.npmjs.org/@sasjs/utils/-/utils-2.42.0.tgz", "resolved": "https://registry.npmjs.org/@sasjs/utils/-/utils-2.40.0.tgz",
"integrity": "sha512-Y69l89PYNF/h9xvVH72om/39xA+cY80bhiVLzp/fJb3BlvzCf4RNswBBanUOv2I5JNa7gPpJuE7mEiXOlhD3eg==", "integrity": "sha512-U0y/eqRlvfkMHmKDlr1xmeN+Rask7TnJPuRpOz71P8QpGYTw1M9AyZvzRSk503p4KCJb8ysdcqXyGVLfhuoM+A==",
"hasInstallScript": true, "hasInstallScript": true,
"dependencies": { "dependencies": {
"@types/fs-extra": "9.0.13", "@types/fs-extra": "9.0.13",
@@ -2189,9 +2189,9 @@
} }
}, },
"node_modules/axios": { "node_modules/axios": {
"version": "0.26.0", "version": "0.26.1",
"resolved": "https://registry.npmjs.org/axios/-/axios-0.26.0.tgz", "resolved": "https://registry.npmjs.org/axios/-/axios-0.26.1.tgz",
"integrity": "sha512-lKoGLMYtHvFrPVt3r+RBMp9nh34N0M8zEfCWqdWZx6phynIEhQqAdydpyBAAG211zlhX9Rgu08cOamy6XjE5Og==", "integrity": "sha512-fPwcX4EvnSHuInCMItEhAGnaSEXRBjtzh9fOtsE6E1G6p7vl7edEeZe11QHf18+6+9gR5PbKV/sGKNaD8YaMeA==",
"dependencies": { "dependencies": {
"follow-redirects": "^1.14.8" "follow-redirects": "^1.14.8"
} }
@@ -13870,9 +13870,9 @@
} }
}, },
"@sasjs/utils": { "@sasjs/utils": {
"version": "2.42.0", "version": "2.40.0",
"resolved": "https://registry.npmjs.org/@sasjs/utils/-/utils-2.42.0.tgz", "resolved": "https://registry.npmjs.org/@sasjs/utils/-/utils-2.40.0.tgz",
"integrity": "sha512-Y69l89PYNF/h9xvVH72om/39xA+cY80bhiVLzp/fJb3BlvzCf4RNswBBanUOv2I5JNa7gPpJuE7mEiXOlhD3eg==", "integrity": "sha512-U0y/eqRlvfkMHmKDlr1xmeN+Rask7TnJPuRpOz71P8QpGYTw1M9AyZvzRSk503p4KCJb8ysdcqXyGVLfhuoM+A==",
"requires": { "requires": {
"@types/fs-extra": "9.0.13", "@types/fs-extra": "9.0.13",
"@types/prompts": "2.0.13", "@types/prompts": "2.0.13",
@@ -14787,9 +14787,9 @@
"dev": true "dev": true
}, },
"axios": { "axios": {
"version": "0.26.0", "version": "0.26.1",
"resolved": "https://registry.npmjs.org/axios/-/axios-0.26.0.tgz", "resolved": "https://registry.npmjs.org/axios/-/axios-0.26.1.tgz",
"integrity": "sha512-lKoGLMYtHvFrPVt3r+RBMp9nh34N0M8zEfCWqdWZx6phynIEhQqAdydpyBAAG211zlhX9Rgu08cOamy6XjE5Og==", "integrity": "sha512-fPwcX4EvnSHuInCMItEhAGnaSEXRBjtzh9fOtsE6E1G6p7vl7edEeZe11QHf18+6+9gR5PbKV/sGKNaD8YaMeA==",
"requires": { "requires": {
"follow-redirects": "^1.14.8" "follow-redirects": "^1.14.8"
} }

View File

@@ -72,8 +72,8 @@
}, },
"main": "index.js", "main": "index.js",
"dependencies": { "dependencies": {
"@sasjs/utils": "2.42.0", "@sasjs/utils": "2.40.0",
"axios": "0.26.0", "axios": "0.26.1",
"axios-cookiejar-support": "1.0.1", "axios-cookiejar-support": "1.0.1",
"form-data": "4.0.0", "form-data": "4.0.0",
"https": "1.0.0", "https": "1.0.0",

View File

@@ -84,15 +84,6 @@ parmcards4;
%webout(CLOSE) %webout(CLOSE)
;;;; ;;;;
%mm_createwebservice(path=/Public/app/common,name=sendArr) %mm_createwebservice(path=/Public/app/common,name=sendArr)
parmcards4;
data work.macvars;
set sashelp.vmacro;
run;
%webout(OPEN)
%webout(OBJ,macvars)
%webout(CLOSE)
;;;;
%mm_createwebservice(path=/Public/app/common,name=sendMacVars)
parmcards4; parmcards4;
let he who hath understanding, reckon the number of the beast let he who hath understanding, reckon the number of the beast
;;;; ;;;;
@@ -127,6 +118,7 @@ parmcards4;
%webout(CLOSE) %webout(CLOSE)
;;;; ;;;;
%mp_createwebservice(path=/Public/app/common,name=sendObj) %mp_createwebservice(path=/Public/app/common,name=sendObj)
filename ft15f001 temp;
parmcards4; parmcards4;
%webout(FETCH) %webout(FETCH)
%webout(OPEN) %webout(OPEN)
@@ -140,15 +132,7 @@ parmcards4;
%webout(CLOSE) %webout(CLOSE)
;;;; ;;;;
%mp_createwebservice(path=/Public/app/common,name=sendArr) %mp_createwebservice(path=/Public/app/common,name=sendArr)
parmcards4; filename ft15f001 temp;
data work.macvars;
set sashelp.vmacro;
run;
%webout(OPEN)
%webout(OBJ,macvars)
%webout(CLOSE)
;;;;
%mp_createwebservice(path=/Public/app/common,name=sendMacVars)
parmcards4; parmcards4;
If you can keep your head when all about you If you can keep your head when all about you
Are losing theirs and blaming it on you, Are losing theirs and blaming it on you,

View File

@@ -2388,11 +2388,11 @@
"node_modules/@sasjs/adapter": { "node_modules/@sasjs/adapter": {
"version": "5.0.0", "version": "5.0.0",
"resolved": "file:../build/sasjs-adapter-5.0.0.tgz", "resolved": "file:../build/sasjs-adapter-5.0.0.tgz",
"integrity": "sha512-5qtEs9yFuZ4v2UrFGNHeCIr/yZTp7D9He+e+N333qW9mdLJJ8fzRifuur/rFE6bNPqC2bdCjicYkO/yrHR4LQw==", "integrity": "sha512-lbDWueAEnfNlu4OGrc9hBEzT0aoLfAy7eLd2nLHArrF6zukcSGBNhUgOqxIhlz4WeBdf1gt3nk1G7p5X1mrWYQ==",
"hasInstallScript": true, "hasInstallScript": true,
"license": "ISC", "license": "ISC",
"dependencies": { "dependencies": {
"@sasjs/utils": "2.40.1", "@sasjs/utils": "2.36.1",
"axios": "0.26.0", "axios": "0.26.0",
"axios-cookiejar-support": "1.0.1", "axios-cookiejar-support": "1.0.1",
"form-data": "4.0.0", "form-data": "4.0.0",
@@ -2422,9 +2422,9 @@
} }
}, },
"node_modules/@sasjs/utils": { "node_modules/@sasjs/utils": {
"version": "2.40.1", "version": "2.36.1",
"resolved": "https://registry.npmjs.org/@sasjs/utils/-/utils-2.40.1.tgz", "resolved": "https://registry.npmjs.org/@sasjs/utils/-/utils-2.36.1.tgz",
"integrity": "sha512-wWYElDH71bSZTdZ5V38743vAnw2EPDhzH7+1s7zxINHpaQWK/qrDldI0vgVFLeGpxVU0D7WPZ/ltG6MoE2obeg==", "integrity": "sha512-JkGUpLOODsvkeU+S25jb9k2WnvzyD2w6cEk7YyQ/byuqKL8xawH91PPWegrVcJlDY8WmqKE4CPcA3d1mM3B3LA==",
"hasInstallScript": true, "hasInstallScript": true,
"dependencies": { "dependencies": {
"@types/fs-extra": "9.0.13", "@types/fs-extra": "9.0.13",
@@ -20998,9 +20998,9 @@
}, },
"@sasjs/adapter": { "@sasjs/adapter": {
"version": "file:../build/sasjs-adapter-5.0.0.tgz", "version": "file:../build/sasjs-adapter-5.0.0.tgz",
"integrity": "sha512-5qtEs9yFuZ4v2UrFGNHeCIr/yZTp7D9He+e+N333qW9mdLJJ8fzRifuur/rFE6bNPqC2bdCjicYkO/yrHR4LQw==", "integrity": "sha512-lbDWueAEnfNlu4OGrc9hBEzT0aoLfAy7eLd2nLHArrF6zukcSGBNhUgOqxIhlz4WeBdf1gt3nk1G7p5X1mrWYQ==",
"requires": { "requires": {
"@sasjs/utils": "2.40.1", "@sasjs/utils": "2.36.1",
"axios": "0.26.0", "axios": "0.26.0",
"axios-cookiejar-support": "1.0.1", "axios-cookiejar-support": "1.0.1",
"form-data": "4.0.0", "form-data": "4.0.0",
@@ -21022,9 +21022,9 @@
} }
}, },
"@sasjs/utils": { "@sasjs/utils": {
"version": "2.40.1", "version": "2.36.1",
"resolved": "https://registry.npmjs.org/@sasjs/utils/-/utils-2.40.1.tgz", "resolved": "https://registry.npmjs.org/@sasjs/utils/-/utils-2.36.1.tgz",
"integrity": "sha512-wWYElDH71bSZTdZ5V38743vAnw2EPDhzH7+1s7zxINHpaQWK/qrDldI0vgVFLeGpxVU0D7WPZ/ltG6MoE2obeg==", "integrity": "sha512-JkGUpLOODsvkeU+S25jb9k2WnvzyD2w6cEk7YyQ/byuqKL8xawH91PPWegrVcJlDY8WmqKE4CPcA3d1mM3B3LA==",
"requires": { "requires": {
"@types/fs-extra": "9.0.13", "@types/fs-extra": "9.0.13",
"@types/prompts": "2.0.13", "@types/prompts": "2.0.13",

View File

@@ -6,7 +6,6 @@ import { specialCaseTests } from './testSuites/SpecialCases'
import { sasjsRequestTests } from './testSuites/SasjsRequests' import { sasjsRequestTests } from './testSuites/SasjsRequests'
import '@sasjs/test-framework/dist/index.css' import '@sasjs/test-framework/dist/index.css'
import { computeTests } from './testSuites/Compute' import { computeTests } from './testSuites/Compute'
import { fileUploadTests } from './testSuites/FileUpload'
const App = (): ReactElement<{}> => { const App = (): ReactElement<{}> => {
const { adapter, config } = useContext(AppContext) const { adapter, config } = useContext(AppContext)
@@ -19,8 +18,7 @@ const App = (): ReactElement<{}> => {
sendArrTests(adapter), sendArrTests(adapter),
sendObjTests(adapter), sendObjTests(adapter),
specialCaseTests(adapter), specialCaseTests(adapter),
sasjsRequestTests(adapter), sasjsRequestTests(adapter)
fileUploadTests(adapter)
] ]
if (adapter.getSasjsConfig().serverType === 'SASVIYA') { if (adapter.getSasjsConfig().serverType === 'SASVIYA') {

View File

@@ -1,35 +0,0 @@
import SASjs from '@sasjs/adapter'
import { TestSuite } from '@sasjs/test-framework'
export const fileUploadTests = (adapter: SASjs): TestSuite => ({
name: 'File Upload Tests',
tests: [
{
title: 'Upload File',
description: 'Should upload the file to VIYA',
test: async () => {
let blob: any = new Blob(['test'], { type: 'text/html' })
blob['lastModifiedDate'] = ''
blob['name'] = 'macvars_testfile'
let file = blob
const filesToUpload = [
{
file: file,
fileName: file.name
}
]
return adapter.uploadFile('common/sendMacVars', filesToUpload, null)
},
assertion: (response: any) =>
(response.macvars as any[]).findIndex(
(el: any) => el.NAME === '_WEBIN_FILE_COUNT' && el.VALUE === '1'
) > -1 &&
(response.macvars as any[]).findIndex(
(el: any) =>
el.NAME === '_WEBIN_FILENAME' && el.VALUE === 'macvars_testfile'
) > -1
}
]
})

View File

@@ -218,7 +218,6 @@ export const sendObjTests = (adapter: SASjs): TestSuite => ({
const invalidData: any = { const invalidData: any = {
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx: [{ col1: 42 }] xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx: [{ col1: 42 }]
} }
return adapter.request('common/sendObj', invalidData).catch((e) => e) return adapter.request('common/sendObj', invalidData).catch((e) => e)
}, },
assertion: (error: any) => assertion: (error: any) =>

View File

@@ -5,7 +5,8 @@ import {
EditContextInput, EditContextInput,
PollOptions, PollOptions,
LoginMechanism, LoginMechanism,
ExecutionQuery ExecutionQuery,
FileTree
} from './types' } from './types'
import { SASViyaApiClient } from './SASViyaApiClient' import { SASViyaApiClient } from './SASViyaApiClient'
import { SAS9ApiClient } from './SAS9ApiClient' import { SAS9ApiClient } from './SAS9ApiClient'
@@ -17,7 +18,7 @@ import {
AuthConfig, AuthConfig,
ExtraResponseAttributes, ExtraResponseAttributes,
SasAuthResponse, SasAuthResponse,
ServicePackSASjs StreamConfig
} from '@sasjs/utils/types' } from '@sasjs/utils/types'
import { RequestClient } from './request/RequestClient' import { RequestClient } from './request/RequestClient'
import { SasjsRequestClient } from './request/SasjsRequestClient' import { SasjsRequestClient } from './request/SasjsRequestClient'
@@ -888,21 +889,27 @@ export default class SASjs {
/** /**
* Creates the folders and services at the given location `appLoc` on the given server `serverUrl`. * Creates the folders and services at the given location `appLoc` on the given server `serverUrl`.
* @param dataJson - the JSON specifying the folders and files to be created, can also includes * @param members - the JSON specifying the folders and services to be created.
* appLoc, streamServiceName, streamWebFolder, streamLogo * @param appLoc - the base folder in which to create the new folders and
* @param appLoc - (optional) the base folder in which to create the new folders and * services. If not provided, is taken from SASjsConfig.
* services. If not provided, is taken from SASjsConfig. Precedence will be of appLoc present in dataJson. * @param streamConfig - optional configuration object of StreamConfig for deploying streaming app.
* @param authConfig - (optional) a valid client, secret, refresh and access tokens that are authorised to execute compute jobs. * @param authConfig - a valid client, secret, refresh and access tokens that are authorised to execute compute jobs.
*/ */
public async deployToSASjs( public async deployToSASjs(
dataJson: ServicePackSASjs, members: FileTree,
appLoc?: string, appLoc?: string,
streamConfig?: StreamConfig,
authConfig?: AuthConfig authConfig?: AuthConfig
) { ) {
if (!appLoc) { if (!appLoc) {
appLoc = this.sasjsConfig.appLoc appLoc = this.sasjsConfig.appLoc
} }
return await this.sasJSApiClient?.deploy(dataJson, appLoc, authConfig) return await this.sasJSApiClient?.deploy(
members,
appLoc,
streamConfig,
authConfig
)
} }
public async executeJobSASjs(query: ExecutionQuery) { public async executeJobSASjs(query: ExecutionQuery) {
@@ -1095,8 +1102,13 @@ export default class SASjs {
} }
if (this.sasjsConfig.serverType === ServerType.Sasjs) { if (this.sasjsConfig.serverType === ServerType.Sasjs) {
if (!this.sasJSApiClient) { if (this.sasJSApiClient) {
this.sasJSApiClient = new SASjsApiClient(this.requestClient) this.sasJSApiClient.setConfig(this.sasjsConfig.serverUrl)
} else {
this.sasJSApiClient = new SASjsApiClient(
this.sasjsConfig.serverUrl,
this.requestClient
)
} }
} }

View File

@@ -1,5 +1,5 @@
import { AuthConfig, ServerType, ServicePackSASjs } from '@sasjs/utils/types' import { AuthConfig, ServerType, StreamConfig } from '@sasjs/utils/types'
import { ExecutionQuery } from './types' import { FileTree, ExecutionQuery } from './types'
import { RequestClient } from './request/RequestClient' import { RequestClient } from './request/RequestClient'
import { getAccessTokenForSasjs } from './auth/getAccessTokenForSasjs' import { getAccessTokenForSasjs } from './auth/getAccessTokenForSasjs'
import { refreshTokensForSasjs } from './auth/refreshTokensForSasjs' import { refreshTokensForSasjs } from './auth/refreshTokensForSasjs'
@@ -8,11 +8,19 @@ import { parseWeboutResponse } from './utils'
import { getTokens } from './auth/getTokens' import { getTokens } from './auth/getTokens'
export class SASjsApiClient { export class SASjsApiClient {
constructor(private requestClient: RequestClient) {} constructor(
private serverUrl: string,
private requestClient: RequestClient
) {}
public setConfig(serverUrl: string) {
if (serverUrl) this.serverUrl = serverUrl
}
public async deploy( public async deploy(
dataJson: ServicePackSASjs, members: FileTree,
appLoc: string, appLoc: string,
streamConfig?: StreamConfig,
authConfig?: AuthConfig authConfig?: AuthConfig
) { ) {
let access_token = (authConfig || {}).access_token let access_token = (authConfig || {}).access_token
@@ -23,9 +31,6 @@ export class SASjsApiClient {
ServerType.Sasjs ServerType.Sasjs
)) ))
} }
dataJson.appLoc = dataJson.appLoc || appLoc
const { result } = await this.requestClient.post<{ const { result } = await this.requestClient.post<{
status: string status: string
message: string message: string
@@ -33,7 +38,13 @@ export class SASjsApiClient {
example?: {} example?: {}
}>( }>(
'SASjsApi/drive/deploy', 'SASjsApi/drive/deploy',
dataJson, {
fileTree: members,
appLoc: appLoc,
streamServiceName: streamConfig?.streamServiceName,
streamWebFolder: streamConfig?.streamWebFolder,
streamLogo: streamConfig?.streamLogo
},
access_token, access_token,
undefined, undefined,
{}, {},

View File

@@ -99,20 +99,7 @@ export class FileUploader extends BaseJobExecutor {
? parseWeboutResponse(res.result, uploadUrl) ? parseWeboutResponse(res.result, uploadUrl)
: res.result : res.result
break break
case ServerType.Sasjs:
if (typeof res.result._webout === 'object') {
jsonResponse = res.result._webout
} else {
const webout = parseWeboutResponse(
res.result._webout,
uploadUrl
)
jsonResponse = getValidJson(webout)
} }
break
}
} else if (this.serverType === ServerType.Sasjs) {
jsonResponse = getValidJson(res.result._webout)
} else { } else {
jsonResponse = jsonResponse =
typeof res.result === 'string' typeof res.result === 'string'

View File

@@ -131,26 +131,6 @@ export class RequestClient implements HttpClient {
} else { } else {
sasWork = response.log sasWork = response.log
} }
} else if (response?.result?.log) {
//In this scenario we know we got the response from SASJS server
//Log is array of `{ line: '' }` so we need to convert it back to text
//To be able to parse it with current functions.
let log: string = ''
if (typeof log !== 'string') {
log = response.result.log
.map((logLine: any) => logLine.line)
.join('\n')
}
sourceCode = parseSourceCode(log)
generatedCode = parseGeneratedCode(log)
if (response?.result?._webout) {
sasWork = response.result._webout.WORK
} else {
sasWork = log
}
} else if (response?.result) { } else if (response?.result) {
sourceCode = parseSourceCode(response.result) sourceCode = parseSourceCode(response.result)
generatedCode = parseGeneratedCode(response.result) generatedCode = parseGeneratedCode(response.result)

47
src/types/FileTree.ts Normal file
View File

@@ -0,0 +1,47 @@
export interface FileTree {
members: [FolderMember, ServiceMember]
}
export enum MemberType {
folder = 'folder',
service = 'service'
}
export interface FolderMember {
name: string
type: MemberType.folder
members: [FolderMember, ServiceMember]
}
export interface ServiceMember {
name: string
type: MemberType.service
code: string
}
export const isFileTree = (arg: any): arg is FileTree =>
arg &&
arg.members &&
Array.isArray(arg.members) &&
arg.members.filter(
(member: FolderMember | ServiceMember) =>
!isFolderMember(member) && !isServiceMember(member)
).length === 0
const isFolderMember = (arg: any): arg is FolderMember =>
arg &&
typeof arg.name === 'string' &&
arg.type === MemberType.folder &&
arg.members &&
Array.isArray(arg.members) &&
arg.members.filter(
(member: FolderMember | ServiceMember) =>
!isFolderMember(member) && !isServiceMember(member)
).length === 0
const isServiceMember = (arg: any): arg is ServiceMember =>
arg &&
typeof arg.name === 'string' &&
arg.type === MemberType.service &&
arg.code &&
typeof arg.code === 'string'

View File

@@ -12,4 +12,5 @@ export * from './Session'
export * from './UploadFile' export * from './UploadFile'
export * from './PollOptions' export * from './PollOptions'
export * from './WriteStream' export * from './WriteStream'
export * from './FileTree'
export * from './ExecuteScript' export * from './ExecuteScript'

View File

@@ -16,15 +16,10 @@ export const parseSasViyaDebugResponse = async (
requestClient: RequestClient, requestClient: RequestClient,
serverUrl: string serverUrl: string
) => { ) => {
// On viya 3.5, iframe is like <iframe style="width: 99%; height: 500px" src="..."></iframe>
// On viya 4, iframe is like <iframe style="width: 99%; height: 500px; background-color:Canvas;" src=...></iframe>
const iframeStart = response.split( const iframeStart = response.split(
/<iframe style="width: 99%; height: 500px" src="|<iframe style="width: 99%; height: 500px; background-color:Canvas;" src=/ '<iframe style="width: 99%; height: 500px" src="'
)[1] )[1]
const jsonUrl = iframeStart const jsonUrl = iframeStart ? iframeStart.split('"></iframe>')[0] : null
? iframeStart.split(/"><\/iframe>|><\/iframe>/)[0]
: null
if (!jsonUrl) { if (!jsonUrl) {
throw new Error('Unable to find webout file URL.') throw new Error('Unable to find webout file URL.')
} }