@grafana/openapi-to-k6 0.2.4 → 0.2.6

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.
Files changed (68) hide show
  1. package/.github/workflows/tests.yaml +1 -0
  2. package/README.md +7 -5
  3. package/dist/cli.js +27 -12
  4. package/dist/errors.js +10 -0
  5. package/dist/generator/index.js +50 -3
  6. package/dist/helper.js +32 -0
  7. package/examples/basic_schema/single/simpleAPI.ts +1 -1
  8. package/examples/basic_schema/split/simpleAPI.schemas.ts +1 -1
  9. package/examples/basic_schema/split/simpleAPI.ts +1 -1
  10. package/examples/basic_schema/tags/default.ts +1 -1
  11. package/examples/basic_schema/tags/simpleAPI.schemas.ts +1 -1
  12. package/examples/form_data_schema/single/formDataAPI.ts +1 -1
  13. package/examples/form_data_schema/split/formDataAPI.schemas.ts +1 -1
  14. package/examples/form_data_schema/split/formDataAPI.ts +1 -1
  15. package/examples/form_data_schema/tags/default.ts +1 -1
  16. package/examples/form_data_schema/tags/formDataAPI.schemas.ts +1 -1
  17. package/examples/form_url_encoded_data_schema/single/formURLEncodedAPI.ts +1 -1
  18. package/examples/form_url_encoded_data_schema/split/formURLEncodedAPI.schemas.ts +1 -1
  19. package/examples/form_url_encoded_data_schema/split/formURLEncodedAPI.ts +1 -1
  20. package/examples/form_url_encoded_data_schema/tags/default.ts +1 -1
  21. package/examples/form_url_encoded_data_schema/tags/formURLEncodedAPI.schemas.ts +1 -1
  22. package/examples/form_url_encoded_data_with_query_params_schema/single/formURLEncodedAPIWithQueryParameters.ts +1 -1
  23. package/examples/form_url_encoded_data_with_query_params_schema/split/formURLEncodedAPIWithQueryParameters.schemas.ts +1 -1
  24. package/examples/form_url_encoded_data_with_query_params_schema/split/formURLEncodedAPIWithQueryParameters.ts +1 -1
  25. package/examples/form_url_encoded_data_with_query_params_schema/tags/default.ts +1 -1
  26. package/examples/form_url_encoded_data_with_query_params_schema/tags/formURLEncodedAPIWithQueryParameters.schemas.ts +1 -1
  27. package/examples/get_request_with_path_parameters_schema/single/simpleAPI.ts +1 -1
  28. package/examples/get_request_with_path_parameters_schema/split/simpleAPI.schemas.ts +1 -1
  29. package/examples/get_request_with_path_parameters_schema/split/simpleAPI.ts +1 -1
  30. package/examples/get_request_with_path_parameters_schema/tags/default.ts +1 -1
  31. package/examples/get_request_with_path_parameters_schema/tags/simpleAPI.schemas.ts +1 -1
  32. package/examples/headers_schema/single/headerDemoAPI.ts +1 -1
  33. package/examples/headers_schema/split/headerDemoAPI.schemas.ts +1 -1
  34. package/examples/headers_schema/split/headerDemoAPI.ts +1 -1
  35. package/examples/headers_schema/tags/default.ts +1 -1
  36. package/examples/headers_schema/tags/headerDemoAPI.schemas.ts +1 -1
  37. package/examples/no_title_schema/single/k6Client.ts +1 -1
  38. package/examples/no_title_schema/split/k6Client.schemas.ts +1 -1
  39. package/examples/no_title_schema/split/k6Client.ts +1 -1
  40. package/examples/no_title_schema/tags/default.ts +1 -1
  41. package/examples/no_title_schema/tags/k6Client.schemas.ts +1 -1
  42. package/examples/post_request_with_query_params/single/exampleAPI.ts +1 -1
  43. package/examples/post_request_with_query_params/split/exampleAPI.schemas.ts +1 -1
  44. package/examples/post_request_with_query_params/split/exampleAPI.ts +1 -1
  45. package/examples/post_request_with_query_params/tags/default.ts +1 -1
  46. package/examples/post_request_with_query_params/tags/exampleAPI.schemas.ts +1 -1
  47. package/examples/query_params_schema/single/exampleAPI.ts +1 -1
  48. package/examples/query_params_schema/split/exampleAPI.schemas.ts +1 -1
  49. package/examples/query_params_schema/split/exampleAPI.ts +1 -1
  50. package/examples/query_params_schema/tags/default.ts +1 -1
  51. package/examples/query_params_schema/tags/exampleAPI.schemas.ts +1 -1
  52. package/examples/simple_post_request_schema/single/exampleAPI.ts +1 -1
  53. package/examples/simple_post_request_schema/split/exampleAPI.schemas.ts +1 -1
  54. package/examples/simple_post_request_schema/split/exampleAPI.ts +1 -1
  55. package/examples/simple_post_request_schema/tags/default.ts +1 -1
  56. package/examples/simple_post_request_schema/tags/exampleAPI.schemas.ts +1 -1
  57. package/package.json +3 -2
  58. package/src/cli.ts +32 -14
  59. package/src/errors.ts +6 -0
  60. package/src/generator/index.ts +67 -2
  61. package/src/helper.ts +40 -0
  62. package/src/type.d.ts +1 -0
  63. package/tests/e2e/schema.json +1 -0
  64. package/tests/e2e/single-tag-filter/k6Script.ts +50 -0
  65. package/tests/e2e/tags/k6Script.ts +3 -3
  66. package/tests/functional-tests/fixtures/tags_filtering.json +141 -0
  67. package/tests/functional-tests/generator.test.ts +159 -3
  68. package/tests/helper.test.ts +59 -0
@@ -12,6 +12,7 @@ import {
12
12
  it,
13
13
  } from 'vitest'
14
14
  import { Mode } from '../../src/constants'
15
+ import { NoFilesGeneratedError } from '../../src/errors'
15
16
  import generator from '../../src/generator'
16
17
 
17
18
  const writeFile = promisify(fs.writeFile)
@@ -19,7 +20,7 @@ const readFile = promisify(fs.readFile)
19
20
  const mkdtemp = promisify(fs.mkdtemp)
20
21
  const rmdir = promisify(fs.rmdir)
21
22
 
22
- const fixturesDir = path.join(__dirname, 'fixtures', 'schemas')
23
+ const fixturesDir = path.join(__dirname, 'fixtures')
23
24
 
24
25
  const loadFixture = (filename: string) => {
25
26
  const filePath = path.join(fixturesDir, filename)
@@ -44,7 +45,7 @@ function replaceSpacesAndNewLineToSingleSpace(input: string): string {
44
45
 
45
46
  describe('generator', () => {
46
47
  let tempDir: string, schemaDirectory: string
47
- const allFixtures = fs.readdirSync(fixturesDir)
48
+ const allFixtures = fs.readdirSync(path.join(fixturesDir, 'schemas'))
48
49
 
49
50
  beforeAll(async () => {
50
51
  tempDir = await mkdtemp(path.join(os.tmpdir(), 'sdk-generator-'))
@@ -57,7 +58,7 @@ describe('generator', () => {
57
58
  for (const fixtureName of allFixtures) {
58
59
  describe(`test ${fixtureName} OpenAPI schema`, () => {
59
60
  let openApiPath: string, generatedSchemaPath: string
60
- const fixture = loadFixture(fixtureName)
61
+ const fixture = loadFixture(path.join('schemas', fixtureName))
61
62
 
62
63
  beforeEach(async () => {
63
64
  schemaDirectory = await mkdtemp(
@@ -160,4 +161,159 @@ describe('generator', () => {
160
161
  })
161
162
  })
162
163
  }
164
+
165
+ describe('validate tags filtering', () => {
166
+ let tempDir: string, openApiPath: string
167
+ const tagsFilteringSchema = loadFixture('tags_filtering.json')
168
+
169
+ beforeAll(async () => {
170
+ tempDir = await mkdtemp(path.join(os.tmpdir(), 'tags-filtering-test-'))
171
+ openApiPath = path.join(tempDir, 'openapi-schema.json')
172
+ await writeFile(openApiPath, JSON.stringify(tagsFilteringSchema))
173
+ })
174
+
175
+ afterAll(async () => {
176
+ await rmdir(tempDir, { recursive: true })
177
+ })
178
+
179
+ const generateAndTest = async (
180
+ mode: Mode,
181
+ tags: string[],
182
+ expectedFiles: string[],
183
+ expectedContents: string[],
184
+ unexpectedContents: string[]
185
+ ) => {
186
+ const generatedSchemaPath = path.join(
187
+ tempDir,
188
+ `generated-schema-${mode}-${tags.join('-')}`
189
+ )
190
+ await generator({
191
+ openApiPath,
192
+ outputDir: generatedSchemaPath,
193
+ tags,
194
+ mode,
195
+ })
196
+
197
+ const generatedFiles = fs.readdirSync(generatedSchemaPath)
198
+ expect(generatedFiles).to.have.members(expectedFiles)
199
+
200
+ for (const file of expectedFiles) {
201
+ if (file.includes('.schemas.ts')) {
202
+ // Skip schemas file
203
+ continue
204
+ }
205
+ const generatedFilePath = path.join(generatedSchemaPath, file)
206
+ const generatedContent = await readFile(generatedFilePath, 'utf-8')
207
+
208
+ for (const content of expectedContents) {
209
+ expect(generatedContent).to.contain(content)
210
+ }
211
+
212
+ for (const content of unexpectedContents) {
213
+ expect(generatedContent).not.to.contain(content)
214
+ }
215
+ }
216
+ }
217
+
218
+ it('should generate only endpoints with specified tags in single mode', async () => {
219
+ await generateAndTest(
220
+ Mode.SINGLE,
221
+ ['users'],
222
+ ['sampleAPI.ts'],
223
+ ['/users'],
224
+ ['/user-profiles', '/pets', '/auth']
225
+ )
226
+
227
+ await generateAndTest(
228
+ Mode.SINGLE,
229
+ ['users', 'userProfiles'],
230
+ ['sampleAPI.ts'],
231
+ ['/users', '/user-profiles'],
232
+ ['/pets', '/auth']
233
+ )
234
+
235
+ // Invalid tag should not generate any endpoints
236
+ await generateAndTest(
237
+ Mode.SINGLE,
238
+ ['invalid-tag'],
239
+ ['sampleAPI.ts'],
240
+ [],
241
+ ['/users', '/user-profiles', '/pets', '/auth']
242
+ )
243
+
244
+ // Empty tags should generate all endpoints
245
+ await generateAndTest(
246
+ Mode.SINGLE,
247
+ [],
248
+ ['sampleAPI.ts'],
249
+ ['/users', '/user-profiles', '/pets', '/auth'],
250
+ []
251
+ )
252
+ })
253
+
254
+ it('should generate only endpoints with specified tags in split mode', async () => {
255
+ await generateAndTest(
256
+ Mode.SPLIT,
257
+ ['users'],
258
+ ['sampleAPI.ts', 'sampleAPI.schemas.ts'],
259
+ ['/users'],
260
+ ['/user-profiles', '/pets', '/auth']
261
+ )
262
+
263
+ // Test empty tags
264
+ await generateAndTest(
265
+ Mode.SPLIT,
266
+ [],
267
+ ['sampleAPI.ts', 'sampleAPI.schemas.ts'],
268
+ ['/users', '/user-profiles', '/pets', '/auth'],
269
+ []
270
+ )
271
+
272
+ // Invalid tag should not generate any endpoints
273
+ // In the single mode it will create the client file which will have only the schemas
274
+ await expect(
275
+ generateAndTest(
276
+ Mode.SPLIT,
277
+ ['invalid-tag'],
278
+ [],
279
+ [],
280
+ ['/users', '/user-profiles', '/pets', '/auth']
281
+ )
282
+ ).rejects.toThrow(NoFilesGeneratedError)
283
+
284
+ // Empty tags should generate all endpoints
285
+ await generateAndTest(
286
+ Mode.SPLIT,
287
+ [],
288
+ ['sampleAPI.ts', 'sampleAPI.schemas.ts'],
289
+ ['/users', '/user-profiles', '/pets', '/auth'],
290
+ []
291
+ )
292
+ })
293
+
294
+ it('should generate only endpoints with specified tags in tags mode', async () => {
295
+ await generateAndTest(
296
+ Mode.TAGS,
297
+ ['users'],
298
+ ['users.ts', 'sampleAPI.schemas.ts'],
299
+ ['/users'],
300
+ ['/user-profiles', '/pets', '/auth']
301
+ )
302
+
303
+ // Empty tags should generate all endpoints
304
+ await generateAndTest(
305
+ Mode.TAGS,
306
+ [],
307
+ [
308
+ 'users.ts',
309
+ 'sampleAPI.schemas.ts',
310
+ 'auth.ts',
311
+ 'pets.ts',
312
+ 'user-profiles.ts',
313
+ ],
314
+ [], // Skipping test for content
315
+ []
316
+ )
317
+ })
318
+ })
163
319
  })
@@ -157,3 +157,62 @@ describe('getDirectoryForPath', () => {
157
157
  expect(directory).toEqual(expectedDirectory)
158
158
  })
159
159
  })
160
+
161
+ describe('hasOnlyComments', () => {
162
+ it('should return true if the file has only comments', () => {
163
+ const expectedResultsAndData = [
164
+ {
165
+ fileContent: '// This is a comment',
166
+ expectedResult: true,
167
+ },
168
+ {
169
+ fileContent: '/* This is a comment */',
170
+ expectedResult: true,
171
+ },
172
+ {
173
+ fileContent: '// This is a comment\nconst x = 1',
174
+ expectedResult: false,
175
+ },
176
+ {
177
+ fileContent: '/* This is a comment */\nconst x = 1',
178
+ expectedResult: false,
179
+ },
180
+ {
181
+ fileContent: 'const x = 1',
182
+ expectedResult: false,
183
+ },
184
+ {
185
+ fileContent: '',
186
+ expectedResult: true,
187
+ },
188
+ {
189
+ fileContent: '// This is a comment\n// This is another comment',
190
+ expectedResult: true,
191
+ },
192
+ {
193
+ fileContent: '/* This is a comment */\n/* This is another comment */',
194
+ expectedResult: true,
195
+ },
196
+ {
197
+ fileContent: '// This is a comment\n/* This is another comment */',
198
+ expectedResult: true,
199
+ },
200
+ {
201
+ fileContent: `/**
202
+ * This is a comment
203
+ */
204
+ `,
205
+ expectedResult: true,
206
+ },
207
+ ]
208
+ for (const { fileContent, expectedResult } of expectedResultsAndData) {
209
+ const result = helper.hasOnlyComments(fileContent)
210
+ try {
211
+ expect(result).toBe(expectedResult)
212
+ } catch (error) {
213
+ console.log(`Expected ${expectedResult} for content:\n${fileContent}`)
214
+ throw error
215
+ }
216
+ }
217
+ })
218
+ })