Skip to content

Commit

Permalink
feat(scaffolder-backend-module-utils): add support to handle multiple…
Browse files Browse the repository at this point in the history
… documents in yaml file in merge
  • Loading branch information
Daniel Kopp authored and devtribe committed Dec 18, 2024
1 parent dbf15a8 commit dc75951
Show file tree
Hide file tree
Showing 6 changed files with 342 additions and 35 deletions.
5 changes: 5 additions & 0 deletions .changeset/mean-lions-rhyme.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@roadiehq/scaffolder-backend-module-utils': minor
---

add support to handle multiple documents in yaml file
Original file line number Diff line number Diff line change
Expand Up @@ -583,6 +583,7 @@ spec:

- mergeArrays: If `true` then where a value is an array the merge function will concatenate the provided array value with the target array.
- preserveYamlComments: If `true`, it will preserve standalone and inline comments in YAML files.
- useDocumentIncludingField: If multiple documents are present in the YAML file, it will merge the content into the document that includes the specified field.
- options: YAML stringify options to customize the output format.
- indent: (default: 2) - indentation width to use (in spaces).
- noArrayIndent: (default: false) - when true, will not add an indentation level to array elements.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -57,8 +57,8 @@
"jsonata": "^2.0.4",
"lodash": "^4.17.21",
"winston": "^3.2.1",
"yaml": "^2.3.4",
"yawn-yaml": "^2.2.0"
"yaml": "^2.6.1",
"yawn-yaml": "^2.3.0"
},
"devDependencies": {
"@backstage/cli": "^0.29.2",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -612,4 +612,157 @@ scripts: # Trailing comment
scripts: { lsltr: 'ls -ltr', lsltrh: 'ls -ltrh' },
});
});

it('should merge content into the correct YAML document', async () => {
mock({
'fake-tmp-dir': {
'fake-file.yaml': `
---
id: 1
name: Document 1
---
id: 2
scripts:
lsltr: ls -ltr
---
id: 3
name: Document 3
`,
},
});

await action.handler({
...mockContext,
workspacePath: 'fake-tmp-dir',
input: {
path: 'fake-file.yaml',
content: YAML.stringify({
scripts: {
lsltrh: 'ls -ltrh',
},
}),
useDocumentIncludingField: {
key: 'id',
value: '2',
},
},
});

expect(fs.existsSync('fake-tmp-dir/fake-file.yaml')).toBe(true);
const file = fs.readFileSync('fake-tmp-dir/fake-file.yaml', 'utf-8');
const documents = YAML.parseAllDocuments(file);
expect(documents[0].toJSON()).toEqual({
id: 1,
name: 'Document 1',
});
expect(documents[1].toJSON()).toEqual({
id: 2,
scripts: {
lsltr: 'ls -ltr',
lsltrh: 'ls -ltrh',
},
});
expect(documents[2].toJSON()).toEqual({
id: 3,
name: 'Document 3',
});
});

it('should merge content into the correct YAML document and preserve comments', async () => {
mock({
'fake-tmp-dir': {
'fake-file.yaml': `
---
id: 1
name: Document 1
# Comment for document 1
---
id: 2
scripts:
lsltr: ls -ltr # Inline comment
# Comment for document 2
---
id: 3
name: Document 3
# Comment for document 3
`,
},
});

await action.handler({
...mockContext,
workspacePath: 'fake-tmp-dir',
input: {
path: 'fake-file.yaml',
content: YAML.stringify({
scripts: {
lsltrh: 'ls -ltrh',
},
}),
useDocumentIncludingField: {
key: 'id',
value: '2',
},
preserveYamlComments: true,
},
});

expect(fs.existsSync('fake-tmp-dir/fake-file.yaml')).toBe(true);
const file = fs.readFileSync('fake-tmp-dir/fake-file.yaml', 'utf-8');
const documents = YAML.parseAllDocuments(file);
expect(documents[0].toJSON()).toEqual({
id: 1,
name: 'Document 1',
});
expect(file).toContain('# Inline comment');
expect(file).toContain('# Comment for document 2');
expect(documents[1].toJSON()).toEqual({
id: 2,
scripts: {
lsltr: 'ls -ltr',
lsltrh: 'ls -ltrh',
},
});
expect(file).toContain('# Comment for document 3');
expect(documents[2].toJSON()).toEqual({
id: 3,
name: 'Document 3',
});
});

it('should throw error when multiple yaml documents exist, but useDocumentIncludingField is missing', async () => {
mock({
'fake-tmp-dir': {
'fake-file.yaml': `
---
id: 1
name: Document 1
---
id: 2
scripts:
lsltr: ls -ltr
---
id: 3
name: Document 3
`,
},
});

await expect(
action.handler({
...mockContext,
workspacePath: 'fake-tmp-dir',
input: {
path: 'fake-file.yaml',
content: YAML.stringify({
scripts: {
lsltrh: 'ls -ltrh',
},
}),
},
}),
).rejects.toThrow(
'Multiple documents found in the input content. Please provide a key and value to use to find the document to merge into.',
);
});
});
Loading

0 comments on commit dc75951

Please sign in to comment.