Skip to content

Commit f043f7f

Browse files
feat: support document generation for workflows (#523)
* GH-240 upgrade packages to remove vulnerabilities * GH-240 move test fixtures to folders to separate action and workflow tests * GH-240 duplicate tests for workflows * GH-420 add run scripts to run action/workflow manually and run tests for action/workflow separately * WIP * GH-240 update CONTRIBUTING where command does not work and add additional helper scripts * GH-240 add option to have a top level header containing the name * GH-240 add header to readme and tests * Remove unused files * GH-240 fix error with enum * GH-240 ability to display workflow inputs and outputs * GH-240 add usage * GH-240 start adding workflow tests * GH-240 get a few more workflow tests working * Update action test files with main * GH-240 fix test for readme * GH-240 all fields readme test working * GH-240 sort out renaming of action > workflow of test files * GH-240 fix crlf test * GH-240 all tests fixed * GH-240 amend readme for workflow functionality * GH-240 add back in new lines at end of files * GH-240 tweak to readme to clarify description is only for actions * GH-240 Fix tests * GH-240 fix workflow syntax * GH-240 add source option and deprecate action option * GH-240 Make replace in readme backwards compatible with source/action * GH-240 add backwards compatibility test * Fix missed -a to -s in readme Co-authored-by: Niek Palm <[email protected]> * GH-420 rename ActionYml to YmlStructure, and actionFile to sourceFile --------- Co-authored-by: Niek Palm <[email protected]>
1 parent 7d4beb6 commit f043f7f

File tree

72 files changed

+1645
-494
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

72 files changed

+1645
-494
lines changed

.eslintrc.json

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,9 @@
5555
"@typescript-eslint/require-array-sort-compare": "error",
5656
"@typescript-eslint/restrict-plus-operands": "error",
5757
"@typescript-eslint/type-annotation-spacing": "error",
58-
"@typescript-eslint/unbound-method": "error"
58+
"@typescript-eslint/unbound-method": "error",
59+
"no-shadow": "off",
60+
"@typescript-eslint/no-shadow": "error"
5961
},
6062
"env": {
6163
"node": true,

CONTRIBUTING.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -80,15 +80,15 @@ Please provide tests for your contribution.
8080
To generate a new fixture for Markdown output run
8181

8282
```bash
83-
./lib/cli.js --no-banner -a __tests__/fixtures/<action>.yml | \
83+
./lib/cli.js --no-banner -s __tests__/fixtures/<action>.yml | \
8484
tail -r | tail -n +2 | tail -r > <action_md>.output
8585
```
8686

8787
For creating a README.md fixture, first create the readme input file for the test, and copy the same file to the an output file. Next run the following command to update the output which can be used to verify the test.
8888

8989

9090
```bash
91-
./lib/cli.js --no-banner -a __tests__/fixtures/<action>.yml -u __tests_/fixtures/<readme>.output
91+
./lib/cli.js --no-banner -s __tests__/fixtures/<action>.yml -u __tests_/fixtures/<readme>.output
9292
```
9393

9494
### Use a Consistent Coding Style

README.md

Lines changed: 30 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -6,26 +6,28 @@
66

77
# Action docs
88

9-
A CLI to generate and update documentation for GitHub actions, based on the action definition `.yml`. To update your README in a GitHub workflow you can use the [action-docs-action](https://github.com/npalm/action-docs-action).
9+
A CLI to generate and update documentation for GitHub actions or workflows, based on the definition `.yml`. To update your README in a GitHub workflow you can use the [action-docs-action](https://github.com/npalm/action-docs-action).
1010

1111
## TL;DR
1212

1313
### Add the following comment blocks to your README.md
1414

1515
```md
16-
<!-- action-docs-description action="action.yml" -->
16+
<!-- action-docs-header source="action.yml" -->
1717

18-
<!-- action-docs-inputs action="action.yml" -->
18+
<!-- action-docs-description source="action.yml" --> # applicable for actions only
1919

20-
<!-- action-docs-outputs action="action.yml" -->
20+
<!-- action-docs-inputs source="action.yml" -->
2121

22-
<!-- action-docs-runs action="action.yml" -->
22+
<!-- action-docs-outputs source="action.yml" -->
23+
24+
<!-- action-docs-runs source="action.yml" --> # applicable for actions only
2325
```
2426

2527
Optionally you can also add the following section to generate a usage guide, replacing \<project\> and \<version\> with the name and version of your project you would like to appear in your usage guide.
2628

2729
```md
28-
<!-- action-docs-usage action="action.yml" project="<project>" version="<version>" -->
30+
<!-- action-docs-usage source="action.yml" project="<project>" version="<version>" -->
2931
```
3032

3133
### Generate docs via CLI
@@ -55,39 +57,42 @@ The following options are available via the CLI
5557

5658
```
5759
Options:
58-
--help Show help [boolean]
59-
--version Show version number [boolean]
60-
-t, --toc-level TOC level used for markdown [number] [default: 2]
61-
-a, --action GitHub action file [string] [default: "action.yml"]
62-
--no-banner Print no banner
63-
-u, --update-readme Update readme file. [string]
64-
-l, --line-breaks Used line breaks in the generated docs.
65-
[string] [choices: "CR", "LF", "CRLF"] [default: "LF"]
66-
-n, --include-name-header Include a header with the action/workflow name.
60+
--version Show version number [boolean]
61+
-t, --toc-level TOC level used for markdown [number] [default: 2]
62+
-a, --action GitHub action file
63+
[deprecated: use "source" instead] [string] [default: "action.yml"]
64+
-s, --source GitHub source file [string] [default: "action.yml"]
65+
--no-banner Print no banner
66+
-u, --update-readme Update readme file. [string]
67+
-l, --line-breaks Used line breaks in the generated docs.
68+
[string] [choices: "CR", "LF", "CRLF"] [default: "LF"]
69+
-n, --include-name-header Include a header with the action/workflow name
70+
[boolean]
71+
--help Show help [boolean]
6772
```
6873

6974
### Update the README
7075

7176
Action-docs can update your README based on the `action.yml`. The following sections can be updated: description, inputs, outputs and runs. Add the following tags to your README and run `action-docs -u`.
7277

7378
```md
74-
<!-- action-docs-header action="action.yml" -->
79+
<!-- action-docs-header source="action.yml" -->
7580

76-
<!-- action-docs-description action="action.yml" -->
81+
<!-- action-docs-description source="action.yml" -->
7782

78-
<!-- action-docs-inputs action="action.yml" -->
83+
<!-- action-docs-inputs source="action.yml" -->
7984

80-
<!-- action-docs-outputs action="action.yml" -->
85+
<!-- action-docs-outputs source="action.yml" -->
8186

82-
<!-- action-docs-runs action="action.yml" -->
87+
<!-- action-docs-runs source="action.yml" -->
8388
```
8489

8590
For updating other Markdown files add the name of the file to the command `action-docs -u <file>`.
8691

8792
If you need to use `another/action.yml`:
8893

89-
1. write it in tags like `action="another/action.yml"`;
90-
1. specify in a command via the `-a` option like `action-docs -a another/action.yml`
94+
1. write it in tags like `source="another/action.yml"`;
95+
2. specify in a command via the `-s` option like `action-docs -s another/action.yml`
9196

9297
### Examples
9398

@@ -106,13 +111,13 @@ action-docs --update-readme
106111
#### Print action markdown for non default action file
107112

108113
```bash
109-
action-docs --action another/action.yaml
114+
action-docs --source another/action.yaml
110115
```
111116

112117
#### Update readme, custom action file and set TOC level 3, custom readme
113118

114119
```bash
115-
action-docs --action ./some-dir/action.yml --toc-level 3 --update-readme docs.md
120+
action-docs --source ./some-dir/action.yml --toc-level 3 --update-readme docs.md
116121
```
117122

118123
## API
@@ -121,7 +126,7 @@ action-docs --action ./some-dir/action.yml --toc-level 3 --update-readme docs.md
121126
import { generateActionMarkdownDocs } from 'action-docs'
122127

123128
await generateActionMarkdownDocs({
124-
actionFile: 'action.yml'
129+
sourceFile: 'action.yml'
125130
tocLevel: 2
126131
updateReadme: true
127132
readmeFile: 'README.md'

__tests__/action-docs.test.ts renamed to __tests__/action-docs-action.test.ts

Lines changed: 68 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,9 @@ import { generateActionMarkdownDocs, Options } from "../src";
22
import { readFileSync, writeFileSync, copyFileSync, unlink } from "fs";
33
import * as path from "path";
44

5-
const fixtureDir = path.join("__tests__", "fixtures");
5+
const fixtureDir = path.join("__tests__", "fixtures", "action");
66

7-
// By default an 'action.yml' is expected at the runtime location. Therefore we copy one during th test.
7+
// By default an 'action.yml' is expected at the runtime location. Therefore we copy one during the test.
88
beforeAll(() => {
99
copyFileSync(path.join(fixtureDir, "action.yml"), "action.yml");
1010
});
@@ -38,7 +38,7 @@ describe("Test output", () => {
3838

3939
test("A minimal action definition.", async () => {
4040
const markdown = await generateActionMarkdownDocs({
41-
actionFile: path.join(fixtureDir, "minimal_action.yml"),
41+
sourceFile: path.join(fixtureDir, "minimal_action.yml"),
4242
});
4343
const expected = <string>(
4444
readFileSync(path.join(fixtureDir, "minimal_action.output"), "utf-8")
@@ -49,7 +49,7 @@ describe("Test output", () => {
4949

5050
test("All fields action definition.", async () => {
5151
const markdown = await generateActionMarkdownDocs({
52-
actionFile: path.join(fixtureDir, "all_fields_action.yml"),
52+
sourceFile: path.join(fixtureDir, "all_fields_action.yml"),
5353
});
5454
const expected = <string>(
5555
readFileSync(path.join(fixtureDir, "all_fields_action.output"), "utf-8")
@@ -61,16 +61,35 @@ describe("Test output", () => {
6161

6262
describe("Test update readme ", () => {
6363
test("Empty readme (all fields)", async () => {
64-
await testReadme({
65-
actionFile: path.join(fixtureDir, "all_fields_action.yml"),
66-
originalReadme: path.join(fixtureDir, "all_fields_readme.input"),
67-
fixtureReadme: path.join(fixtureDir, "all_fields_readme.output"),
68-
});
64+
await testReadme(
65+
{
66+
sourceFile: path.join(fixtureDir, "all_fields_action.yml"),
67+
originalReadme: path.join(fixtureDir, "all_fields_readme.input"),
68+
fixtureReadme: path.join(fixtureDir, "all_fields_readme.output"),
69+
},
70+
{
71+
includeNameHeader: true,
72+
},
73+
);
74+
});
75+
test("Empty readme (all fields) with header", async () => {
76+
await testReadme(
77+
{
78+
sourceFile: path.join(fixtureDir, "all_fields_action.yml"),
79+
originalReadme: path.join(fixtureDir, "all_fields_readme.input"),
80+
fixtureReadme: path.join(fixtureDir, "all_fields_readme_header.output"),
81+
},
82+
{
83+
includeNameHeader: true,
84+
},
85+
false,
86+
true,
87+
);
6988
});
7089

7190
test("Filled readme (all fields)", async () => {
7291
await testReadme({
73-
actionFile: path.join(fixtureDir, "all_fields_action.yml"),
92+
sourceFile: path.join(fixtureDir, "all_fields_action.yml"),
7493
originalReadme: path.join(fixtureDir, "all_fields_readme_filled.input"),
7594
fixtureReadme: path.join(fixtureDir, "all_fields_readme_filled.output"),
7695
});
@@ -79,11 +98,13 @@ describe("Test update readme ", () => {
7998
test("Filled readme (all fields) with header", async () => {
8099
await testReadme(
81100
{
82-
actionFile: path.join(fixtureDir, "all_fields_action.yml"),
101+
sourceFile: path.join(fixtureDir, "all_fields_action.yml"),
83102
originalReadme: path.join(fixtureDir, "all_fields_readme.input"),
84103
fixtureReadme: path.join(fixtureDir, "all_fields_readme_header.output"),
85104
},
86-
{},
105+
{
106+
includeNameHeader: true,
107+
},
87108
false,
88109
true,
89110
);
@@ -92,7 +113,7 @@ describe("Test update readme ", () => {
92113
test("Readme (all fields) with CRLF line breaks", async () => {
93114
await testReadme(
94115
{
95-
actionFile: path.join(fixtureDir, "all_fields_action.yml.crlf"),
116+
sourceFile: path.join(fixtureDir, "all_fields_action.yml.crlf"),
96117
originalReadme: path.join(fixtureDir, "all_fields_readme.input.crlf"),
97118
fixtureReadme: path.join(fixtureDir, "all_fields_readme.output.crlf"),
98119
},
@@ -102,7 +123,7 @@ describe("Test update readme ", () => {
102123

103124
test("Readme (inputs) for action-docs-action", async () => {
104125
await testReadme({
105-
actionFile: path.join(fixtureDir, "action_docs_action_action.yml"),
126+
sourceFile: path.join(fixtureDir, "action_docs_action_action.yml"),
106127
originalReadme: path.join(fixtureDir, "action_docs_action_readme.input"),
107128
fixtureReadme: path.join(fixtureDir, "action_docs_action_readme.output"),
108129
});
@@ -111,7 +132,7 @@ describe("Test update readme ", () => {
111132
test("Readme for two action.yml-s", async () => {
112133
await testReadme(
113134
{
114-
actionFile: path.join(fixtureDir, "action_docs_action_action.yml"),
135+
sourceFile: path.join(fixtureDir, "action_docs_action_action.yml"),
115136
originalReadme: path.join(fixtureDir, "two_actions_readme.input"),
116137
fixtureReadme: path.join(fixtureDir, "two_actions_readme.output"),
117138
},
@@ -120,7 +141,7 @@ describe("Test update readme ", () => {
120141
);
121142

122143
await testReadme({
123-
actionFile: path.join(fixtureDir, "all_fields_action.yml"),
144+
sourceFile: path.join(fixtureDir, "all_fields_action.yml"),
124145
originalReadme: path.join(fixtureDir, "two_actions_readme.input"),
125146
fixtureReadme: path.join(fixtureDir, "two_actions_readme.output"),
126147
});
@@ -130,23 +151,38 @@ describe("Test update readme ", () => {
130151
describe("Test usage format", () => {
131152
test("Multi-line descriptions.", async () => {
132153
await testReadme({
133-
actionFile: path.join(fixtureDir, "action.yml"),
154+
sourceFile: path.join(fixtureDir, "action.yml"),
134155
originalReadme: path.join(fixtureDir, "action_usage_readme.input"),
135156
fixtureReadme: path.join(fixtureDir, "action_usage_readme.output"),
136157
});
137158
});
138159

139160
test("With and without defaults.", async () => {
140161
await testReadme({
141-
actionFile: path.join(fixtureDir, "all_fields_action.yml"),
162+
sourceFile: path.join(fixtureDir, "all_fields_action.yml"),
142163
originalReadme: path.join(fixtureDir, "all_fields_usage_readme.input"),
143164
fixtureReadme: path.join(fixtureDir, "all_fields_usage_readme.output"),
144165
});
145166
});
146167
});
147168

169+
describe("Backwards compatibility", () => {
170+
test("Deprecated action option still works correctly", async () => {
171+
await testReadme(
172+
{
173+
sourceFile: path.join(fixtureDir, "all_fields_action.yml"),
174+
originalReadme: path.join(fixtureDir, "action_deprecated.input"),
175+
fixtureReadme: path.join(fixtureDir, "action_deprecated.output"),
176+
},
177+
{
178+
includeNameHeader: true,
179+
},
180+
);
181+
});
182+
});
183+
148184
interface ReadmeTestFixtures {
149-
actionFile: string;
185+
sourceFile: string;
150186
originalReadme: string;
151187
fixtureReadme: string;
152188
}
@@ -160,18 +196,21 @@ async function testReadme(
160196
const expected = <string>readFileSync(files.fixtureReadme, "utf-8");
161197
const original = <string>readFileSync(files.originalReadme, "utf-8");
162198

163-
await generateActionMarkdownDocs({
164-
actionFile: files.actionFile,
165-
updateReadme: true,
166-
includeNameHeader: includeNameHeader,
167-
readmeFile: files.originalReadme,
168-
...overwriteOptions,
169-
});
199+
try {
200+
await generateActionMarkdownDocs({
201+
sourceFile: files.sourceFile,
202+
updateReadme: true,
203+
includeNameHeader: includeNameHeader,
204+
readmeFile: files.originalReadme,
205+
...overwriteOptions,
206+
});
170207

171-
const updated = <string>readFileSync(files.originalReadme, "utf-8");
208+
const updated = <string>readFileSync(files.originalReadme, "utf-8");
172209

173-
if (doExpect) {
210+
if (doExpect) {
211+
expect(updated).toEqual(expected);
212+
}
213+
} finally {
174214
writeFileSync(files.originalReadme, original);
175-
expect(updated).toEqual(expected);
176215
}
177216
}

0 commit comments

Comments
 (0)