@scalar/api-client 0.2.0 → 0.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/SimpleTable/SimpleCell.vue.d.ts.map +1 -1
- package/dist/components/SimpleTable/SimpleHeader.vue.d.ts.map +1 -1
- package/dist/components/SimpleTable/SimpleRow.vue.d.ts.map +1 -1
- package/dist/components/SimpleTable/SimpleTable.vue.d.ts.map +1 -1
- package/dist/fixtures/index.d.ts +1 -1
- package/dist/fixtures/index.d.ts.map +1 -1
- package/dist/index.js +37 -26
- package/package.json +6 -6
- package/src/components/ApiClient/AddressBar.vue +462 -0
- package/src/components/ApiClient/ApiClient.vue +266 -0
- package/src/components/ApiClient/Request/Request.vue +271 -0
- package/src/components/ApiClient/Request/RequestAuth.vue +221 -0
- package/src/components/ApiClient/Request/RequestBody.vue +39 -0
- package/src/components/ApiClient/Request/RequestHeaders.vue +24 -0
- package/src/components/ApiClient/Request/RequestQuery.vue +25 -0
- package/src/components/ApiClient/Request/RequestVariables.vue +25 -0
- package/src/components/ApiClient/Request/index.ts +1 -0
- package/src/components/ApiClient/RequestHistory.vue +114 -0
- package/src/components/ApiClient/RequestHistoryItem.vue +59 -0
- package/src/components/ApiClient/Response/Copilot.vue.bak +385 -0
- package/src/components/ApiClient/Response/Response.vue +120 -0
- package/src/components/ApiClient/Response/ResponseBody.vue +23 -0
- package/src/components/ApiClient/Response/ResponseHeaders.vue +52 -0
- package/src/components/ApiClient/Response/ResponseMetaInformation.vue +58 -0
- package/src/components/ApiClient/Response/index.ts +1 -0
- package/src/components/ApiClient/index.ts +1 -0
- package/src/components/CodeMirror/CodeMirror.vue +232 -0
- package/src/components/CodeMirror/extensions/variables.ts +41 -0
- package/src/components/CodeMirror/index.ts +1 -0
- package/src/components/CollapsibleSection/CollapsibleSection.vue +149 -0
- package/src/components/CollapsibleSection/index.ts +1 -0
- package/src/components/FlowModal.vue +133 -0
- package/src/components/Grid/Grid.vue +511 -0
- package/src/components/Grid/SimpleGrid.vue +33 -0
- package/src/components/Grid/index.ts +2 -0
- package/src/components/HelpfulLink.vue +19 -0
- package/src/components/SimpleTable/SimpleCell.vue +47 -0
- package/src/components/SimpleTable/SimpleHeader.vue +17 -0
- package/src/components/SimpleTable/SimpleRow.vue +14 -0
- package/src/components/SimpleTable/SimpleTable.vue +13 -0
- package/src/components/SimpleTable/index.ts +4 -0
- package/src/fixtures/httpHeaders.ts +530 -0
- package/src/fixtures/httpStatusCodes.ts +259 -0
- package/src/fixtures/index.ts +6 -0
- package/src/helpers/createPlaceholderRequest.ts +16 -0
- package/src/helpers/generateParameters.ts +19 -0
- package/src/helpers/generateRequest.ts +26 -0
- package/src/helpers/index.ts +5 -0
- package/src/helpers/mapFromArray.ts +16 -0
- package/src/helpers/sendRequest.ts +94 -0
- package/src/hooks/index.ts +2 -0
- package/src/hooks/useCopilot.ts +64 -0
- package/src/hooks/useOperation.test.ts +7 -0
- package/src/hooks/useOperation.ts +43 -0
- package/src/index.ts +9 -0
- package/src/stores/apiClientRequestStore.ts +103 -0
- package/src/stores/apiClientStore.ts +57 -0
- package/src/stores/index.ts +5 -0
- package/src/types.ts +181 -0
|
@@ -0,0 +1,259 @@
|
|
|
1
|
+
export type HttpStatusCode = {
|
|
2
|
+
name: string
|
|
3
|
+
url: string
|
|
4
|
+
}
|
|
5
|
+
|
|
6
|
+
export type HttpStatusCodes = Record<string, HttpStatusCode>
|
|
7
|
+
|
|
8
|
+
export const httpStatusCodes: HttpStatusCodes = {
|
|
9
|
+
100: {
|
|
10
|
+
name: 'Continue',
|
|
11
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/100',
|
|
12
|
+
},
|
|
13
|
+
101: {
|
|
14
|
+
name: 'Switching Protocols',
|
|
15
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/101',
|
|
16
|
+
},
|
|
17
|
+
102: {
|
|
18
|
+
name: 'Processing',
|
|
19
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/102',
|
|
20
|
+
},
|
|
21
|
+
103: {
|
|
22
|
+
name: 'Early Hints',
|
|
23
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/103',
|
|
24
|
+
},
|
|
25
|
+
200: {
|
|
26
|
+
name: 'OK',
|
|
27
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/200',
|
|
28
|
+
},
|
|
29
|
+
201: {
|
|
30
|
+
name: 'Created',
|
|
31
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/201',
|
|
32
|
+
},
|
|
33
|
+
202: {
|
|
34
|
+
name: 'Accepted',
|
|
35
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/202',
|
|
36
|
+
},
|
|
37
|
+
203: {
|
|
38
|
+
name: 'Non-Authoritative Information',
|
|
39
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/203',
|
|
40
|
+
},
|
|
41
|
+
204: {
|
|
42
|
+
name: 'No Content',
|
|
43
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/204',
|
|
44
|
+
},
|
|
45
|
+
205: {
|
|
46
|
+
name: 'Reset Content',
|
|
47
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/205',
|
|
48
|
+
},
|
|
49
|
+
206: {
|
|
50
|
+
name: 'Partial Content',
|
|
51
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/206',
|
|
52
|
+
},
|
|
53
|
+
207: {
|
|
54
|
+
name: 'Multi-Status',
|
|
55
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/207',
|
|
56
|
+
},
|
|
57
|
+
208: {
|
|
58
|
+
name: 'Already Reported',
|
|
59
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/208',
|
|
60
|
+
},
|
|
61
|
+
226: {
|
|
62
|
+
name: 'IM Used',
|
|
63
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/226',
|
|
64
|
+
},
|
|
65
|
+
300: {
|
|
66
|
+
name: 'Multiple Choices',
|
|
67
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/300',
|
|
68
|
+
},
|
|
69
|
+
301: {
|
|
70
|
+
name: 'Moved Permanently',
|
|
71
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/301',
|
|
72
|
+
},
|
|
73
|
+
302: {
|
|
74
|
+
name: 'Found',
|
|
75
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/302',
|
|
76
|
+
},
|
|
77
|
+
303: {
|
|
78
|
+
name: 'See Other',
|
|
79
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/303',
|
|
80
|
+
},
|
|
81
|
+
304: {
|
|
82
|
+
name: 'Not Modified',
|
|
83
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/304',
|
|
84
|
+
},
|
|
85
|
+
305: {
|
|
86
|
+
name: 'Use Proxy',
|
|
87
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/305',
|
|
88
|
+
},
|
|
89
|
+
306: {
|
|
90
|
+
name: '(Unused)',
|
|
91
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/306',
|
|
92
|
+
},
|
|
93
|
+
307: {
|
|
94
|
+
name: 'Temporary Redirect',
|
|
95
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/307',
|
|
96
|
+
},
|
|
97
|
+
308: {
|
|
98
|
+
name: 'Permanent Redirect',
|
|
99
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/308',
|
|
100
|
+
},
|
|
101
|
+
400: {
|
|
102
|
+
name: 'Bad Request',
|
|
103
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/400',
|
|
104
|
+
},
|
|
105
|
+
401: {
|
|
106
|
+
name: 'Unauthorized',
|
|
107
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/401',
|
|
108
|
+
},
|
|
109
|
+
402: {
|
|
110
|
+
name: 'Payment Required',
|
|
111
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/402',
|
|
112
|
+
},
|
|
113
|
+
403: {
|
|
114
|
+
name: 'Forbidden',
|
|
115
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/403',
|
|
116
|
+
},
|
|
117
|
+
404: {
|
|
118
|
+
name: 'Not Found',
|
|
119
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/404',
|
|
120
|
+
},
|
|
121
|
+
405: {
|
|
122
|
+
name: 'Method Not Allowed',
|
|
123
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/405',
|
|
124
|
+
},
|
|
125
|
+
406: {
|
|
126
|
+
name: 'Not Acceptable',
|
|
127
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/406',
|
|
128
|
+
},
|
|
129
|
+
407: {
|
|
130
|
+
name: 'Proxy Authentication Required',
|
|
131
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/407',
|
|
132
|
+
},
|
|
133
|
+
408: {
|
|
134
|
+
name: 'Request Timeout',
|
|
135
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/408',
|
|
136
|
+
},
|
|
137
|
+
409: {
|
|
138
|
+
name: 'Conflict',
|
|
139
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/409',
|
|
140
|
+
},
|
|
141
|
+
410: {
|
|
142
|
+
name: 'Gone',
|
|
143
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/410',
|
|
144
|
+
},
|
|
145
|
+
411: {
|
|
146
|
+
name: 'Length Required',
|
|
147
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/411',
|
|
148
|
+
},
|
|
149
|
+
412: {
|
|
150
|
+
name: 'Precondition Failed',
|
|
151
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/412',
|
|
152
|
+
},
|
|
153
|
+
413: {
|
|
154
|
+
name: 'Content Too Large',
|
|
155
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/413',
|
|
156
|
+
},
|
|
157
|
+
414: {
|
|
158
|
+
name: 'URI Too Long',
|
|
159
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/414',
|
|
160
|
+
},
|
|
161
|
+
415: {
|
|
162
|
+
name: 'Unsupported Media Type',
|
|
163
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/415',
|
|
164
|
+
},
|
|
165
|
+
416: {
|
|
166
|
+
name: 'Range Not Satisfiable',
|
|
167
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/416',
|
|
168
|
+
},
|
|
169
|
+
417: {
|
|
170
|
+
name: 'Expectation Failed',
|
|
171
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/417',
|
|
172
|
+
},
|
|
173
|
+
421: {
|
|
174
|
+
name: 'Misdirected Request',
|
|
175
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/421',
|
|
176
|
+
},
|
|
177
|
+
422: {
|
|
178
|
+
name: 'Unprocessable Content',
|
|
179
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/422',
|
|
180
|
+
},
|
|
181
|
+
423: {
|
|
182
|
+
name: 'Locked',
|
|
183
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/423',
|
|
184
|
+
},
|
|
185
|
+
424: {
|
|
186
|
+
name: 'Failed Dependency',
|
|
187
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/424',
|
|
188
|
+
},
|
|
189
|
+
425: {
|
|
190
|
+
name: 'Too Early',
|
|
191
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/425',
|
|
192
|
+
},
|
|
193
|
+
426: {
|
|
194
|
+
name: 'Upgrade Required',
|
|
195
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/426',
|
|
196
|
+
},
|
|
197
|
+
428: {
|
|
198
|
+
name: 'Precondition Required',
|
|
199
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/428',
|
|
200
|
+
},
|
|
201
|
+
429: {
|
|
202
|
+
name: 'Too Many Requests',
|
|
203
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/429',
|
|
204
|
+
},
|
|
205
|
+
431: {
|
|
206
|
+
name: 'Request Header Fields Too Large',
|
|
207
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/431',
|
|
208
|
+
},
|
|
209
|
+
451: {
|
|
210
|
+
name: 'Unavailable For Legal Reasons',
|
|
211
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/451',
|
|
212
|
+
},
|
|
213
|
+
500: {
|
|
214
|
+
name: 'Internal Server Error',
|
|
215
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/500',
|
|
216
|
+
},
|
|
217
|
+
501: {
|
|
218
|
+
name: 'Not Implemented',
|
|
219
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/501',
|
|
220
|
+
},
|
|
221
|
+
502: {
|
|
222
|
+
name: 'Bad Gateway',
|
|
223
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/502',
|
|
224
|
+
},
|
|
225
|
+
503: {
|
|
226
|
+
name: 'Service Unavailable',
|
|
227
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/503',
|
|
228
|
+
},
|
|
229
|
+
504: {
|
|
230
|
+
name: 'Gateway Timeout',
|
|
231
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/504',
|
|
232
|
+
},
|
|
233
|
+
505: {
|
|
234
|
+
name: 'HTTP Version Not Supported',
|
|
235
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/505',
|
|
236
|
+
},
|
|
237
|
+
506: {
|
|
238
|
+
name: 'Variant Also Negotiates',
|
|
239
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/506',
|
|
240
|
+
},
|
|
241
|
+
507: {
|
|
242
|
+
name: 'Insufficient Storage',
|
|
243
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/507',
|
|
244
|
+
},
|
|
245
|
+
508: {
|
|
246
|
+
name: 'Loop Detected',
|
|
247
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/508',
|
|
248
|
+
},
|
|
249
|
+
510: {
|
|
250
|
+
name: 'Not Extended',
|
|
251
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/510',
|
|
252
|
+
},
|
|
253
|
+
511: {
|
|
254
|
+
name: 'Network Authentication Required',
|
|
255
|
+
url: 'https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/511',
|
|
256
|
+
},
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
export default httpStatusCodes
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import type { ClientRequestConfig } from '../types'
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Generate a new placeholder request
|
|
5
|
+
*/
|
|
6
|
+
export const createPlaceholderRequest = (): ClientRequestConfig => ({
|
|
7
|
+
name: '',
|
|
8
|
+
url: '',
|
|
9
|
+
type: 'GET',
|
|
10
|
+
path: '',
|
|
11
|
+
parameters: [],
|
|
12
|
+
headers: [],
|
|
13
|
+
query: [],
|
|
14
|
+
body: '',
|
|
15
|
+
formData: [],
|
|
16
|
+
})
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import type { BaseParameter, Parameters } from '../types'
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Generate parameters for the request from the parameters in the swagger file
|
|
5
|
+
*/
|
|
6
|
+
export function generateParameters(parameters: Parameters[]) {
|
|
7
|
+
const params: BaseParameter[] = []
|
|
8
|
+
parameters.forEach((parameter: Parameters) => {
|
|
9
|
+
const param: BaseParameter = {
|
|
10
|
+
name: parameter.name,
|
|
11
|
+
value: '',
|
|
12
|
+
customClass: parameter.required ? 'required-parameter' : '',
|
|
13
|
+
}
|
|
14
|
+
param.value = ''
|
|
15
|
+
params.push(param)
|
|
16
|
+
})
|
|
17
|
+
|
|
18
|
+
return params
|
|
19
|
+
}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { type ParamMap } from '../hooks/useOperation'
|
|
2
|
+
import type { ClientRequestConfig, Operation, Server } from '../types'
|
|
3
|
+
import { generateParameters } from './generateParameters'
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* Generate parameters for the request
|
|
7
|
+
*/
|
|
8
|
+
export function generateRequest(
|
|
9
|
+
operation: Operation,
|
|
10
|
+
parameterMap: ParamMap,
|
|
11
|
+
server: Server,
|
|
12
|
+
): ClientRequestConfig {
|
|
13
|
+
const item = {
|
|
14
|
+
id: operation.operationId,
|
|
15
|
+
name: operation.name,
|
|
16
|
+
type: operation.httpVerb,
|
|
17
|
+
path: operation.path,
|
|
18
|
+
parameters: generateParameters(parameterMap.path),
|
|
19
|
+
query: generateParameters(parameterMap.query),
|
|
20
|
+
headers: generateParameters(parameterMap.header),
|
|
21
|
+
url: server.url,
|
|
22
|
+
body: '',
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
return item
|
|
26
|
+
}
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
export { createPlaceholderRequest } from './createPlaceholderRequest'
|
|
2
|
+
export { generateRequest } from './generateRequest'
|
|
3
|
+
export { generateParameters } from './generateParameters'
|
|
4
|
+
export { mapFromArray } from './mapFromArray'
|
|
5
|
+
export { sendRequest } from './sendRequest'
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A utility function to convert an array of objects to an object of objects.
|
|
3
|
+
*/
|
|
4
|
+
export function mapFromArray<
|
|
5
|
+
T extends Record<string, unknown>,
|
|
6
|
+
K extends keyof T & string,
|
|
7
|
+
V extends keyof T & string,
|
|
8
|
+
>(arr: T[], key: K, valueKey: V) {
|
|
9
|
+
const obj: Record<string, T[V]> = {}
|
|
10
|
+
|
|
11
|
+
arr.forEach((entry) => {
|
|
12
|
+
obj[entry[key] as string] = entry[valueKey]
|
|
13
|
+
})
|
|
14
|
+
|
|
15
|
+
return obj
|
|
16
|
+
}
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
import axios from 'axios'
|
|
2
|
+
import { nanoid } from 'nanoid'
|
|
3
|
+
import nunjucks from 'nunjucks'
|
|
4
|
+
|
|
5
|
+
import type {
|
|
6
|
+
ClientRequestConfig,
|
|
7
|
+
ClientResponse,
|
|
8
|
+
RequestResult,
|
|
9
|
+
} from '../types'
|
|
10
|
+
import { mapFromArray } from './mapFromArray'
|
|
11
|
+
|
|
12
|
+
const templateEngine = nunjucks.configure({
|
|
13
|
+
tags: {
|
|
14
|
+
variableStart: '{',
|
|
15
|
+
variableEnd: '}',
|
|
16
|
+
},
|
|
17
|
+
})
|
|
18
|
+
|
|
19
|
+
const defaultHeaders = {
|
|
20
|
+
'User-Agent': 'Scalar API Client',
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
/**
|
|
24
|
+
* Send a request via the proxy
|
|
25
|
+
*/
|
|
26
|
+
export async function sendRequest(
|
|
27
|
+
request: ClientRequestConfig,
|
|
28
|
+
proxyUrl: string,
|
|
29
|
+
): Promise<RequestResult | null> {
|
|
30
|
+
// Format complete URL
|
|
31
|
+
const method = request.type.toUpperCase()
|
|
32
|
+
const fullUrl = `${request.url}${request.path}`
|
|
33
|
+
const headers: Record<string, string | number> = {
|
|
34
|
+
...defaultHeaders,
|
|
35
|
+
...mapFromArray(request.headers, 'name', 'value'),
|
|
36
|
+
}
|
|
37
|
+
/** TODO: Make dynamic */
|
|
38
|
+
const auth = {
|
|
39
|
+
type: 'none',
|
|
40
|
+
}
|
|
41
|
+
const variables = mapFromArray(request.parameters, 'name', 'value')
|
|
42
|
+
const renderedURL = templateEngine.renderString(fullUrl, variables)
|
|
43
|
+
/** TODO: Make dynamic */
|
|
44
|
+
const proxy = true
|
|
45
|
+
|
|
46
|
+
const startTime = Date.now()
|
|
47
|
+
|
|
48
|
+
const requestOptions = {
|
|
49
|
+
method,
|
|
50
|
+
url: renderedURL,
|
|
51
|
+
auth,
|
|
52
|
+
headers,
|
|
53
|
+
data: request.body,
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
const config = proxy
|
|
57
|
+
? {
|
|
58
|
+
method: 'POST',
|
|
59
|
+
url: proxyUrl,
|
|
60
|
+
data: requestOptions,
|
|
61
|
+
}
|
|
62
|
+
: {
|
|
63
|
+
method: requestOptions.method,
|
|
64
|
+
url: requestOptions.url,
|
|
65
|
+
headers: requestOptions.headers,
|
|
66
|
+
data: requestOptions.data,
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
console.info(`${requestOptions.method} ${requestOptions.url}`)
|
|
70
|
+
|
|
71
|
+
const response: (ClientResponse & { error: false }) | { error: true } =
|
|
72
|
+
// @ts-ignore
|
|
73
|
+
await axios(config)
|
|
74
|
+
.then((res) => ({
|
|
75
|
+
...res.data,
|
|
76
|
+
error: false,
|
|
77
|
+
}))
|
|
78
|
+
.catch((err) => ({
|
|
79
|
+
error: true,
|
|
80
|
+
...err?.response,
|
|
81
|
+
}))
|
|
82
|
+
|
|
83
|
+
return !response.error
|
|
84
|
+
? {
|
|
85
|
+
sentTime: Date.now(),
|
|
86
|
+
request,
|
|
87
|
+
response: {
|
|
88
|
+
...response,
|
|
89
|
+
duration: Date.now() - startTime,
|
|
90
|
+
},
|
|
91
|
+
responseId: nanoid(),
|
|
92
|
+
}
|
|
93
|
+
: null
|
|
94
|
+
}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import { useWebSocket } from '@vueuse/core'
|
|
2
|
+
import { reactive, readonly } from 'vue'
|
|
3
|
+
|
|
4
|
+
export enum CopilotLoadingStates {
|
|
5
|
+
Inactive = 'Inactive',
|
|
6
|
+
Fix = 'Fix',
|
|
7
|
+
Loading = 'Loading',
|
|
8
|
+
Working = 'Working',
|
|
9
|
+
Success = 'Success',
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
export type RequestData = {
|
|
13
|
+
id: string
|
|
14
|
+
request: string
|
|
15
|
+
}
|
|
16
|
+
export type RecommendationHandler = (recommendation: string) => void
|
|
17
|
+
|
|
18
|
+
const recommendationHandler: Set<RecommendationHandler> = new Set([])
|
|
19
|
+
|
|
20
|
+
function onMessage(_ws: WebSocket, event: MessageEvent) {
|
|
21
|
+
const jsonData = JSON.parse(event.data)
|
|
22
|
+
const recommendation = jsonData['response']
|
|
23
|
+
recommendationHandler.forEach((handler) => handler(recommendation))
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
const { send } = useWebSocket(import.meta.env.VITE_COPILOT_WS_URL, {
|
|
27
|
+
onMessage,
|
|
28
|
+
autoReconnect: true,
|
|
29
|
+
})
|
|
30
|
+
|
|
31
|
+
function sendCopilot(requestData: RequestData) {
|
|
32
|
+
setLoadingState(CopilotLoadingStates.Loading)
|
|
33
|
+
const jsonString = JSON.stringify(requestData)
|
|
34
|
+
send(jsonString)
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
const serverHandler = () => ({
|
|
38
|
+
uuid: '',
|
|
39
|
+
curlRequest:
|
|
40
|
+
"curl -X 'GET' 'https://petstore.swagger.io/v2/pet/findByStatus?status=SOld' -H 'accept: application/json'",
|
|
41
|
+
})
|
|
42
|
+
|
|
43
|
+
const serverHandlerState = reactive(serverHandler())
|
|
44
|
+
|
|
45
|
+
const state = reactive({
|
|
46
|
+
loadingState: CopilotLoadingStates.Inactive,
|
|
47
|
+
})
|
|
48
|
+
|
|
49
|
+
function setLoadingState(loadingState: CopilotLoadingStates) {
|
|
50
|
+
state.loadingState = loadingState
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
/**
|
|
54
|
+
* This hook is used to send requests to the copilot server and receive recommendations.
|
|
55
|
+
*/
|
|
56
|
+
export const useCopilot = () => ({
|
|
57
|
+
sendCopilot,
|
|
58
|
+
state: readonly(state),
|
|
59
|
+
onRecommendation: (handler: RecommendationHandler) => {
|
|
60
|
+
recommendationHandler.add(handler)
|
|
61
|
+
},
|
|
62
|
+
serverHandlerState,
|
|
63
|
+
setLoadingState,
|
|
64
|
+
})
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import { computed } from 'vue'
|
|
2
|
+
|
|
3
|
+
import type { Operation, Parameters } from '../types'
|
|
4
|
+
|
|
5
|
+
export type ParamMap = {
|
|
6
|
+
path: Parameters[]
|
|
7
|
+
query: Parameters[]
|
|
8
|
+
header: Parameters[]
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
export type OperationProps = {
|
|
12
|
+
operation: Operation
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* This hook is used to generate the parameters for the request from the parameters in the swagger file
|
|
17
|
+
*/
|
|
18
|
+
export function useOperation(props: OperationProps) {
|
|
19
|
+
const parameterMap = computed(() => {
|
|
20
|
+
const { parameters } = props.operation.information
|
|
21
|
+
const map: ParamMap = {
|
|
22
|
+
path: [],
|
|
23
|
+
query: [],
|
|
24
|
+
header: [],
|
|
25
|
+
}
|
|
26
|
+
if (parameters) {
|
|
27
|
+
parameters.forEach((parameter: Parameters) => {
|
|
28
|
+
if (parameter.in === 'path') {
|
|
29
|
+
map.path.push(parameter)
|
|
30
|
+
} else if (parameter.in === 'query') {
|
|
31
|
+
map.query.push(parameter)
|
|
32
|
+
} else if (parameter.in === 'header') {
|
|
33
|
+
map.header.push(parameter)
|
|
34
|
+
}
|
|
35
|
+
})
|
|
36
|
+
}
|
|
37
|
+
return map
|
|
38
|
+
})
|
|
39
|
+
|
|
40
|
+
return {
|
|
41
|
+
parameterMap,
|
|
42
|
+
}
|
|
43
|
+
}
|
package/src/index.ts
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
export { ApiClient } from './components/ApiClient'
|
|
2
|
+
export { CodeMirror } from './components/CodeMirror'
|
|
3
|
+
|
|
4
|
+
export * from './helpers'
|
|
5
|
+
export * from './hooks'
|
|
6
|
+
export * from './stores/apiClientStore'
|
|
7
|
+
export * from './stores/apiClientRequestStore'
|
|
8
|
+
export * from './types'
|
|
9
|
+
export * from './fixtures'
|
|
@@ -0,0 +1,103 @@
|
|
|
1
|
+
import { computed, reactive, ref } from 'vue'
|
|
2
|
+
|
|
3
|
+
import { createPlaceholderRequest } from '../helpers/createPlaceholderRequest'
|
|
4
|
+
import type { AuthState, ClientRequestConfig, RequestResult } from '../types'
|
|
5
|
+
|
|
6
|
+
// Auth state template
|
|
7
|
+
export const createEmptyAuthState = (): AuthState => ({
|
|
8
|
+
type: 'none',
|
|
9
|
+
basic: {
|
|
10
|
+
userName: '',
|
|
11
|
+
password: '',
|
|
12
|
+
active: true,
|
|
13
|
+
},
|
|
14
|
+
oauthTwo: {
|
|
15
|
+
generatedToken: '',
|
|
16
|
+
discoveryURL: '',
|
|
17
|
+
authURL: '',
|
|
18
|
+
accessTokenURL: '',
|
|
19
|
+
clientID: '',
|
|
20
|
+
clientSecret: '',
|
|
21
|
+
scope: '',
|
|
22
|
+
active: true,
|
|
23
|
+
},
|
|
24
|
+
bearer: {
|
|
25
|
+
token: '',
|
|
26
|
+
active: true,
|
|
27
|
+
},
|
|
28
|
+
digest: {
|
|
29
|
+
userName: '',
|
|
30
|
+
password: '',
|
|
31
|
+
active: true,
|
|
32
|
+
},
|
|
33
|
+
})
|
|
34
|
+
|
|
35
|
+
/**
|
|
36
|
+
* Request state
|
|
37
|
+
*/
|
|
38
|
+
type RequestHistoryOrder = string[]
|
|
39
|
+
type RequestHistoryEntry = RequestResult
|
|
40
|
+
|
|
41
|
+
// Request Authorization State
|
|
42
|
+
const authState = reactive(createEmptyAuthState())
|
|
43
|
+
|
|
44
|
+
// Log of all requests made
|
|
45
|
+
const requestHistory: Record<string, RequestHistoryEntry> = reactive({})
|
|
46
|
+
|
|
47
|
+
// Request list order
|
|
48
|
+
const requestHistoryOrder = ref<RequestHistoryOrder>([])
|
|
49
|
+
|
|
50
|
+
// Id of the currently viewed request
|
|
51
|
+
const activeRequestId = ref('')
|
|
52
|
+
|
|
53
|
+
// Active request object
|
|
54
|
+
const activeRequest = reactive(createPlaceholderRequest())
|
|
55
|
+
|
|
56
|
+
/**
|
|
57
|
+
* Mutators
|
|
58
|
+
*/
|
|
59
|
+
|
|
60
|
+
// Add a new request to the history log and make it active
|
|
61
|
+
const addRequestToHistory = (value: RequestHistoryEntry) => {
|
|
62
|
+
requestHistory[value.responseId] = value
|
|
63
|
+
activeRequestId.value = value.responseId
|
|
64
|
+
requestHistoryOrder.value.unshift(value.responseId)
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
// Set a response by key to currently active
|
|
68
|
+
const setActiveResponse = (historyID: string) => {
|
|
69
|
+
activeRequestId.value = historyID
|
|
70
|
+
const { request }: { request: ClientRequestConfig } =
|
|
71
|
+
requestHistory[historyID]
|
|
72
|
+
Object.assign(activeRequest, request)
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
// Get the currently active response
|
|
76
|
+
const activeResponse = computed(() =>
|
|
77
|
+
activeRequestId.value ? requestHistory[activeRequestId.value].response : null,
|
|
78
|
+
)
|
|
79
|
+
|
|
80
|
+
// Set the active request object
|
|
81
|
+
const setActiveRequest = (request: ClientRequestConfig) => {
|
|
82
|
+
Object.assign(activeRequest, request)
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
/**
|
|
86
|
+
* View state
|
|
87
|
+
*/
|
|
88
|
+
|
|
89
|
+
// Whether the request is in read mode or edit mode
|
|
90
|
+
const readOnly = ref(true)
|
|
91
|
+
|
|
92
|
+
export const useApiClientRequestStore = () => ({
|
|
93
|
+
authState,
|
|
94
|
+
readOnly,
|
|
95
|
+
activeRequest,
|
|
96
|
+
activeResponse,
|
|
97
|
+
requestHistory,
|
|
98
|
+
requestHistoryOrder,
|
|
99
|
+
activeRequestId,
|
|
100
|
+
setActiveResponse,
|
|
101
|
+
addRequestToHistory,
|
|
102
|
+
setActiveRequest,
|
|
103
|
+
})
|