Skip to content

Commit cc2132c

Browse files
authored
Support toc generation in the api-documenter (#4931)
* make toc generation part of the api-documenter * add instruction for generating toc * generate toc only for classes and interfaces * add jssdk flag * update description of the command * change parameter name to --host-path
1 parent 2a5039e commit cc2132c

File tree

7 files changed

+201
-137
lines changed

7 files changed

+201
-137
lines changed

package.json

+1-2
Original file line numberDiff line numberDiff line change
@@ -54,8 +54,7 @@
5454
"docgen:exp": "ts-node-script scripts/exp/docgen.ts",
5555
"postinstall": "yarn --cwd repo-scripts/changelog-generator build",
5656
"sa": "ts-node-script repo-scripts/size-analysis/cli.ts",
57-
"api-documenter-devsite": "ts-node-script repo-scripts/api-documenter/src/start.ts",
58-
"toc-devsite": "ts-node-script scripts/exp/generate-devsite-toc.ts -i temp"
57+
"api-documenter-devsite": "ts-node-script repo-scripts/api-documenter/src/start.ts"
5958
},
6059
"repository": {
6160
"type": "git",

repo-scripts/api-documenter/README.md

+11
Original file line numberDiff line numberDiff line change
@@ -3,3 +3,14 @@
33
It is a fork of [API Documenter](https://github.com/microsoft/rushstack/tree/master/apps/api-documenter)
44
It reads the *.api.json data files produced by [API Extractor](https://api-extractor.com/),
55
and then generates files in [Markdown](https://en.wikipedia.org/wiki/Markdown) format suitable for displaying in Firebase Devsite.
6+
7+
## Generate toc for Firebase devsite
8+
`api-documenter-fire toc -i temp -p "/docs/reference/js/v9"`
9+
10+
`-i` and `-p` (`--host-path`) are required parameters.
11+
Use `-i` to specify the folder that contains api.json files.
12+
Use `-p` to specify the g3 path that contains the reference docs.
13+
14+
By default, the command will create `toc.yaml` in folder `/toc`. To change the output folder, use the flag `-o`.
15+
16+
To generate toc for the Firebase JS SDK, also set the flag `-j` to create the top level `firebase` toc item.

repo-scripts/api-documenter/package.json

+3-1
Original file line numberDiff line numberDiff line change
@@ -27,9 +27,11 @@
2727
"@rushstack/ts-command-line": "4.7.8",
2828
"colors": "~1.2.1",
2929
"resolve": "~1.17.0",
30-
"tslib": "^2.1.0"
30+
"tslib": "^2.1.0",
31+
"js-yaml": "4.0.0"
3132
},
3233
"devDependencies": {
34+
"@types/js-yaml": "4.0.0",
3335
"@types/resolve": "1.17.1",
3436
"mocha-chai-jest-snapshot": "1.1.1"
3537
}

repo-scripts/api-documenter/src/cli/ApiDocumenterCommandLine.ts

+2
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020

2121
import { CommandLineParser } from '@rushstack/ts-command-line';
2222
import { MarkdownAction } from './MarkdownAction';
23+
import { TocAction } from './TocAction';
2324

2425
export class ApiDocumenterCommandLine extends CommandLineParser {
2526
public constructor() {
@@ -39,5 +40,6 @@ export class ApiDocumenterCommandLine extends CommandLineParser {
3940

4041
private _populateActions(): void {
4142
this.addAction(new MarkdownAction(this));
43+
this.addAction(new TocAction(this));
4244
}
4345
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,77 @@
1+
/**
2+
* @license
3+
* Copyright 2021 Google LLC
4+
*
5+
* Licensed under the Apache License, Version 2.0 (the "License");
6+
* you may not use this file except in compliance with the License.
7+
* You may obtain a copy of the License at
8+
*
9+
* http://www.apache.org/licenses/LICENSE-2.0
10+
*
11+
* Unless required by applicable law or agreed to in writing, software
12+
* distributed under the License is distributed on an "AS IS" BASIS,
13+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14+
* See the License for the specific language governing permissions and
15+
* limitations under the License.
16+
*/
17+
18+
import {
19+
CommandLineFlagParameter,
20+
CommandLineStringParameter
21+
} from '@rushstack/ts-command-line';
22+
import { ApiDocumenterCommandLine } from './ApiDocumenterCommandLine';
23+
import { BaseAction } from './BaseAction';
24+
import { generateToc } from '../toc';
25+
26+
export class TocAction extends BaseAction {
27+
private _g3PathParameter!: CommandLineStringParameter;
28+
private _jsSDKParameter!: CommandLineFlagParameter;
29+
public constructor(parser: ApiDocumenterCommandLine) {
30+
super({
31+
actionName: 'toc',
32+
summary: 'Generate TOC(table of content) for Firebase devsite.',
33+
documentation: 'Generate TOC(table of content) for Firebase devsite.'
34+
});
35+
}
36+
37+
protected onDefineParameters(): void {
38+
super.onDefineParameters();
39+
40+
this._g3PathParameter = this.defineStringParameter({
41+
parameterLongName: '--host-path',
42+
parameterShortName: '-p',
43+
argumentName: 'HOSTPATH',
44+
description: `Specifies the path where the reference docs resides (e.g. g3).
45+
Used to generate paths in the toc`
46+
});
47+
48+
this._jsSDKParameter = this.defineFlagParameter({
49+
parameterLongName: '--js-sdk',
50+
parameterShortName: '-j',
51+
description:
52+
`Generating toc for the Firebase JS SDK.` +
53+
`It will create an artificial top level toc item "firebase".`
54+
});
55+
}
56+
57+
protected async onExecute(): Promise<void> {
58+
// override
59+
const { apiModel, outputFolder, addFileNameSuffix } = this.buildApiModel();
60+
const g3Path: string | undefined = this._g3PathParameter.value;
61+
const jsSdk: boolean = this._jsSDKParameter.value;
62+
63+
if (!g3Path) {
64+
throw new Error(
65+
'--g3-path is a required to generate toc, but it is not provided'
66+
);
67+
}
68+
69+
generateToc({
70+
apiModel,
71+
outputFolder,
72+
addFileNameSuffix,
73+
g3Path,
74+
jsSdk
75+
});
76+
}
77+
}
+107
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,107 @@
1+
/**
2+
* @license
3+
* Copyright 2021 Google LLC
4+
*
5+
* Licensed under the Apache License, Version 2.0 (the "License");
6+
* you may not use this file except in compliance with the License.
7+
* You may obtain a copy of the License at
8+
*
9+
* http://www.apache.org/licenses/LICENSE-2.0
10+
*
11+
* Unless required by applicable law or agreed to in writing, software
12+
* distributed under the License is distributed on an "AS IS" BASIS,
13+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14+
* See the License for the specific language governing permissions and
15+
* limitations under the License.
16+
*/
17+
18+
import yaml from 'js-yaml';
19+
import { ApiItem, ApiItemKind, ApiModel } from 'api-extractor-model-me';
20+
import { getFilenameForApiItem } from './documenters/MarkdownDocumenterHelpers';
21+
import { ModuleSource } from '@microsoft/tsdoc/lib-commonjs/beta/DeclarationReference';
22+
import { writeFileSync } from 'fs';
23+
import { resolve } from 'path';
24+
25+
export interface ITocGenerationOptions {
26+
apiModel: ApiModel;
27+
g3Path: string;
28+
outputFolder: string;
29+
addFileNameSuffix: boolean;
30+
jsSdk: boolean;
31+
}
32+
33+
interface ITocItem {
34+
title: string;
35+
path: string;
36+
section?: ITocItem[];
37+
}
38+
39+
export function generateToc({
40+
apiModel,
41+
g3Path,
42+
outputFolder,
43+
addFileNameSuffix,
44+
jsSdk
45+
}: ITocGenerationOptions) {
46+
const toc = [];
47+
48+
if (jsSdk) {
49+
const firebaseToc: ITocItem = {
50+
title: 'firebase',
51+
path: `${g3Path}/index`,
52+
section: []
53+
};
54+
toc.push(firebaseToc);
55+
}
56+
57+
generateTocRecursively(apiModel, g3Path, addFileNameSuffix, toc);
58+
59+
writeFileSync(
60+
resolve(outputFolder, 'toc.yaml'),
61+
yaml.dump(
62+
{ toc },
63+
{
64+
quotingType: '"'
65+
}
66+
)
67+
);
68+
}
69+
70+
function generateTocRecursively(
71+
apiItem: ApiItem,
72+
g3Path: string,
73+
addFileNameSuffix: boolean,
74+
toc: ITocItem[]
75+
) {
76+
if (apiItem.kind === ApiItemKind.EntryPoint) {
77+
// Entry point
78+
const entryPointName = (apiItem.canonicalReference
79+
.source! as ModuleSource).escapedPath.replace('@firebase/', '');
80+
const entryPointToc: ITocItem = {
81+
title: entryPointName,
82+
path: `${g3Path}/${getFilenameForApiItem(apiItem, addFileNameSuffix)}`,
83+
section: []
84+
};
85+
86+
for (const member of apiItem.members) {
87+
// only classes and interfaces have dedicated pages
88+
if (
89+
member.kind === ApiItemKind.Class ||
90+
member.kind === ApiItemKind.Interface
91+
) {
92+
const fileName = getFilenameForApiItem(member, addFileNameSuffix);
93+
entryPointToc.section!.push({
94+
title: member.displayName,
95+
path: `${g3Path}/${fileName}`
96+
});
97+
}
98+
}
99+
100+
toc.push(entryPointToc);
101+
} else {
102+
// travel the api tree to find the next entry point
103+
for (const member of apiItem.members) {
104+
generateTocRecursively(member, g3Path, addFileNameSuffix, toc);
105+
}
106+
}
107+
}

scripts/exp/generate-devsite-toc.ts

-134
This file was deleted.

0 commit comments

Comments
 (0)