Skip to content

Commit 17f99cc

Browse files
Peter Bengtssonpull[bot]
Peter Bengtsson
authored andcommitted
Port context.js to TypeScript (#50978)
1 parent 9b109a6 commit 17f99cc

File tree

21 files changed

+473
-138
lines changed

21 files changed

+473
-138
lines changed

.github/workflows/link-check-daily.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ jobs:
5252
uses: actions/cache@13aacd865c20de90d75de3b17ebe84f7a17d57d2 # v4.0.0
5353
with:
5454
path: external-link-checker-db.json
55-
key: external-link-checker-${{ hashFiles('src/links/scripts/rendered-content-link-checker.js') }}
55+
key: external-link-checker-${{ hashFiles('src/links/scripts/rendered-content-link-checker.ts') }}
5656

5757
- name: Insight into external link checker DB json file (before)
5858
run: |
@@ -87,7 +87,7 @@ jobs:
8787
EXTERNAL_SERVER_ERRORS_AS_WARNINGS: true
8888
FAIL_ON_FLAW: false
8989
timeout-minutes: 30
90-
run: node src/links/scripts/rendered-content-link-checker.js
90+
run: npm run rendered-content-link-checker
9191

9292
- name: Insight into external link checker DB json file (after)
9393
run: |

.github/workflows/link-check-on-pr.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -50,4 +50,4 @@ jobs:
5050
# been loaded.
5151
ENABLED_LANGUAGES: en
5252
FAIL_ON_FLAW: true
53-
run: node src/links/scripts/rendered-content-link-checker.js
53+
run: npm run rendered-content-link-checker

package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,8 @@
5656
"prevent-pushes-to-main": "node src/workflows/prevent-pushes-to-main.js",
5757
"release-banner": "node src/ghes-releases/scripts/release-banner.js",
5858
"remove-version-markup": "node src/ghes-releases/scripts/remove-version-markup.js",
59-
"rendered-content-link-checker-cli": "node src/links/scripts/rendered-content-link-checker-cli.js",
59+
"rendered-content-link-checker": "tsx src/links/scripts/rendered-content-link-checker.ts",
60+
"rendered-content-link-checker-cli": "tsx src/links/scripts/rendered-content-link-checker-cli.ts",
6061
"rest-dev": "node src/rest/scripts/update-files.js",
6162
"show-action-deps": "echo 'Action Dependencies:' && rg '^[\\s|-]*(uses:.*)$' .github -I -N --no-heading -r '$1$2' | sort | uniq | cut -c 7-",
6263
"start": "cross-env NODE_ENV=development ENABLED_LANGUAGES=en nodemon src/frame/server.ts",

src/content-linter/tests/category-pages.ts

Lines changed: 5 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import path from 'path'
22
import fs from 'fs'
33

4+
import type { Response } from 'express'
45
import walk from 'walk-sync'
56
import { zip, difference } from 'lodash-es'
67
import GithubSlugger from 'github-slugger'
@@ -10,10 +11,10 @@ import { beforeAll, describe, expect, test } from 'vitest'
1011
import matter from '@/frame/lib/read-frontmatter.js'
1112
import { renderContent } from '@/content-render/index.js'
1213
import getApplicableVersions from '@/versions/lib/get-applicable-versions.js'
13-
import contextualize from '@/frame/middleware/context/context.js'
14+
import contextualize from '@/frame/middleware/context/context'
1415
import shortVersions from '@/versions/middleware/short-versions.js'
1516
import { ROOT } from '@/frame/lib/constants.js'
16-
import type { Context, FrontmatterVersions } from '@/types'
17+
import type { Context, ExtendedRequest, FrontmatterVersions } from '@/types'
1718

1819
const slugger = new GithubSlugger()
1920

@@ -29,12 +30,6 @@ type Frontmatter = {
2930
hidden?: boolean
3031
}
3132

32-
type MockedRequest = {
33-
language: string
34-
pagePath: string
35-
context: Context
36-
}
37-
3833
function getFrontmatterData(markdown: string): Frontmatter {
3934
const parsed = matter(markdown)
4035
if (!parsed.data) throw new Error('No frontmatter')
@@ -139,13 +134,13 @@ describe.skip('category pages', () => {
139134
const next = () => {}
140135
const res = {}
141136
const context: Context = {}
142-
const req: MockedRequest = {
137+
const req = {
143138
language: 'en',
144139
pagePath: '/en',
145140
context,
146141
}
147142

148-
await contextualize(req, res, next)
143+
await contextualize(req as ExtendedRequest, res as Response, next)
149144
await shortVersions(req, res, next)
150145

151146
// Save the index title for later testing

src/content-render/scripts/all-documents/lib.ts

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
1-
import type { Page } from '@/types'
2-
import contextualize from '@/frame/middleware/context/context.js'
1+
import type { Response } from 'express'
2+
3+
import type { ExtendedRequest, Page } from '@/types'
4+
import contextualize from '@/frame/middleware/context/context'
35
import features from '@/versions/middleware/features.js'
46
import shortVersions from '@/versions/middleware/short-versions.js'
57

@@ -63,7 +65,7 @@ export async function allDocuments(options: Options): Promise<AllDocument[]> {
6365
context,
6466
}
6567

66-
await contextualize(req, res, next)
68+
await contextualize(req as ExtendedRequest, res as Response, next)
6769
await shortVersions(req, res, next)
6870
req.context.page = page
6971
await features(req, res, next)

src/dev-toc/generate.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ import { program } from 'commander'
77
import fpt from '#src/versions/lib/non-enterprise-default-version.js'
88
import { allVersionKeys } from '#src/versions/lib/all-versions.js'
99
import { liquid } from '#src/content-render/index.js'
10-
import contextualize from '#src/frame/middleware/context/context.js'
10+
import contextualize from '#src/frame/middleware/context/context'
1111

1212
const layoutFilename = path.posix.join(process.cwd(), 'src/dev-toc/layout.html')
1313
const layout = fs.readFileSync(layoutFilename, 'utf8')

src/frame/middleware/context/context.js renamed to src/frame/middleware/context/context.ts

Lines changed: 25 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,22 @@
1-
import languages from '#src/languages/lib/languages.js'
2-
import enterpriseServerReleases from '#src/versions/lib/enterprise-server-releases.js'
3-
import { allVersions } from '#src/versions/lib/all-versions.js'
4-
import { productMap } from '#src/products/lib/all-products.js'
1+
import type { NextFunction, Response } from 'express'
2+
3+
import type { ExtendedRequest, Context } from '@/types'
4+
5+
import languages from '@/languages/lib/languages.js'
6+
import enterpriseServerReleases from '@/versions/lib/enterprise-server-releases.js'
7+
import { allVersions } from '@/versions/lib/all-versions.js'
8+
import { productMap } from '@/products/lib/all-products.js'
59
import {
610
getVersionStringFromPath,
711
getProductStringFromPath,
812
getCategoryStringFromPath,
913
getPathWithoutLanguage,
1014
getPathWithoutVersion,
11-
} from '#src/frame/lib/path-utils.js'
12-
import productNames from '#src/products/lib/product-names.js'
13-
import warmServer from '#src/frame/lib/warm-server.js'
14-
import nonEnterpriseDefaultVersion from '#src/versions/lib/non-enterprise-default-version.js'
15-
import { getDataByLanguage, getUIDataMerged } from '#src/data-directory/lib/get-data.js'
15+
} from '@/frame/lib/path-utils.js'
16+
import productNames from '@/products/lib/product-names.js'
17+
import warmServer from '@/frame/lib/warm-server.js'
18+
import nonEnterpriseDefaultVersion from '@/versions/lib/non-enterprise-default-version.js'
19+
import { getDataByLanguage, getUIDataMerged } from '@/data-directory/lib/get-data.js'
1620

1721
// This doesn't change just because the request changes, so compute it once.
1822
const enterpriseServerVersions = Object.keys(allVersions).filter((version) =>
@@ -21,18 +25,24 @@ const enterpriseServerVersions = Object.keys(allVersions).filter((version) =>
2125

2226
// Supply all route handlers with a baseline `req.context` object
2327
// Note that additional middleware in middleware/index.js adds to this context object
24-
export default async function contextualize(req, res, next) {
28+
export default async function contextualize(
29+
req: ExtendedRequest,
30+
res: Response,
31+
next: NextFunction,
32+
) {
2533
// Ensure that we load some data only once on first request
26-
const { redirects, siteTree, pages: pageMap } = await warmServer()
34+
const { redirects, siteTree, pages: pageMap } = await warmServer([])
2735

28-
req.context = {}
36+
const context: Context = {}
37+
req.context = context
2938
req.context.process = { env: {} }
3039

3140
// define each context property explicitly for code-search friendliness
3241
// e.g. searches for "req.context.page" will include results from this file
3342
req.context.currentLanguage = req.language
3443
req.context.userLanguage = req.userLanguage
35-
req.context.currentVersion = getVersionStringFromPath(req.pagePath)
44+
req.context.currentVersion = getVersionStringFromPath(req.pagePath) as string
45+
3646
req.context.currentVersionObj = allVersions[req.context.currentVersion]
3747
req.context.currentProduct = getProductStringFromPath(req.pagePath)
3848
req.context.currentCategory = getCategoryStringFromPath(req.pagePath)
@@ -79,8 +89,8 @@ export default async function contextualize(req, res, next) {
7989
if (!page) {
8090
throw new Error("The 'page' has not been put into the context yet.")
8191
}
82-
const enPath = context.currentPath.replace(`/${page.languageCode}`, '/en')
83-
const enPage = context.pages[enPath]
92+
const enPath = context.currentPath!.replace(`/${page.languageCode}`, '/en')
93+
const enPage = context.pages![enPath]
8494
if (!enPage) {
8595
throw new Error(`Unable to find equivalent English page by the path '${enPath}'`)
8696
}

src/frame/middleware/index.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ import handleErrors from '@/observability/middleware/handle-errors'
1919
import handleNextDataPath from './handle-next-data-path'
2020
import detectLanguage from '@/languages/middleware/detect-language'
2121
import reloadTree from './reload-tree'
22-
import context from './context/context.js'
22+
import context from './context/context'
2323
import shortVersions from '@/versions/middleware/short-versions.js'
2424
import languageCodeRedirects from '@/redirects/middleware/language-code-redirects.js'
2525
import handleRedirects from '@/redirects/middleware/handle-redirects.js'

src/links/lib/README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ If the action finds any broken links, it opens an internal issue for the Docs Co
2020
<pre>
2121
curl -Lso /dev/null -w "%{http_code}\n" <em>URL</em>
2222
</pre>
23-
A `200` response is success.
23+
A `200` response is success.
2424

2525
- You can see a comprehensive list of HTTP response codes [here](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status).
2626
- For external links that now `404` or have otherwise gone missing entirely, you may be able to use the [Wayback Machine](https://web.archive.org) to see the page before it went offline.
@@ -39,4 +39,4 @@ Before you decide whether to exclude a link from the daily link checker, you sho
3939
- Has it has been flagged as a broken link for more than a week, but the URL works when a real user opens it in their browser?
4040
- Has the URL been available for more than 3 months? You can check using the [Wayback Machine](https://web.archive.org).
4141

42-
If you are confident that the URL for the article should work for real users, then you can open a pull request to add it to the `src/links/lib/excluded-links.js` file.
42+
If you are confident that the URL for the article should work for real users, then you can open a pull request to add it to the `src/links/lib/excluded-links.ts` file.

src/links/lib/excluded-links.js renamed to src/links/lib/excluded-links.ts

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,9 @@
88

99
/* eslint-disable prefer-regex-literals */
1010

11-
export default [
11+
type ExcludedLink = string | RegExp
12+
13+
const excludedLinks: ExcludedLink[] = [
1214
// Skip GitHub search links.
1315
// E.g. https://github.com/search?foo=bar
1416
regex('https://github.com/search?'),
@@ -79,6 +81,8 @@ export default [
7981
'https://packages.ubuntu.com/search?keywords=netcat&searchon=names',
8082
]
8183

84+
export default excludedLinks
85+
8286
// Return a regular expression from a URL string that matches the URL
8387
// as a base. It's basically shorthand for "URL.startsWith(BASE_URL)"
8488
// but as a RegExp object.
@@ -88,6 +92,6 @@ export default [
8892
// true
8993
// > regex('https://github.com').test('otherhttps://github.com/page')
9094
// false
91-
function regex(url) {
95+
function regex(url: string) {
9296
return new RegExp('^' + url.replace(/[.*+?^${}()|[\]\\]/g, '\\$&'))
9397
}

src/links/lib/validate-docs-urls.ts

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,15 @@
1+
import type { Response } from 'express'
12
import cheerio from 'cheerio'
23

34
import warmServer from '@/frame/lib/warm-server.js'
45
import { liquid } from '@/content-render/index.js'
56
import shortVersions from '@/versions/middleware/short-versions.js'
6-
import contextualize from '@/frame/middleware/context/context.js'
7+
import contextualize from '@/frame/middleware/context/context'
78
import features from '@/versions/middleware/features.js'
89
import findPage from '@/frame/middleware/find-page.js'
910
import { createMinimalProcessor } from '@/content-render/unified/processor.js'
1011
import getRedirect from '@/redirects/lib/get-redirect.js'
11-
import type { Page } from '@/types'
12+
import type { ExtendedRequest, Page } from '@/types'
1213

1314
export type DocsUrls = {
1415
[identifier: string]: string
@@ -116,7 +117,7 @@ async function renderInnerHTML(page: Page, permalink: Permalink) {
116117
// Here it just exists for the sake of TypeScript.
117118
context: {},
118119
}
119-
await contextualize(req, res, next)
120+
await contextualize(req as ExtendedRequest, res as Response, next)
120121
await shortVersions(req, res, next)
121122
await findPage(req, res, next)
122123
await features(req, res, next)

src/links/scripts/action-injections.js renamed to src/links/scripts/action-injections.ts

Lines changed: 16 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -7,21 +7,29 @@ import fs from 'fs'
77
import path from 'path'
88
import chalk from 'chalk'
99

10-
import github from '#src/workflows/github.js'
10+
import github from '@/workflows/github.js'
1111

12+
export type CoreInject = {
13+
info: (message: string) => void
14+
debug: (message: string) => void
15+
warning: (message: string) => void
16+
error: (message: string) => void
17+
setOutput: (name: string, value: any) => void
18+
setFailed: (message: string) => void
19+
}
1220
// Directs core logging to console
13-
export function getCoreInject(debug) {
21+
export function getCoreInject(debug: boolean): CoreInject {
1422
return {
1523
info: console.log,
16-
debug: (message) => (debug ? console.warn(chalk.blue(message)) : {}),
17-
warning: (message) => console.warn(chalk.yellow(message)),
24+
debug: (message: string) => (debug ? console.warn(chalk.blue(message)) : {}),
25+
warning: (message: string) => console.warn(chalk.yellow(message)),
1826
error: console.error,
19-
setOutput: (name, value) => {
27+
setOutput: (name: string, value: any) => {
2028
if (debug) {
2129
console.log(`Output "${name}" set to: "${value}"`)
2230
}
2331
},
24-
setFailed: (message) => {
32+
setFailed: (message: string) => {
2533
if (debug) {
2634
console.log('setFailed called.')
2735
}
@@ -36,8 +44,8 @@ const logsPath = path.join(cwd, '..', '..', 'logs')
3644
if (!fs.existsSync(logsPath)) {
3745
fs.mkdirSync(logsPath)
3846
}
39-
export function getUploadArtifactInject(debug) {
40-
return (name, contents) => {
47+
export function getUploadArtifactInject(debug: boolean) {
48+
return (name: string, contents: string) => {
4149
const logFilename = path.join(logsPath, `${new Date().toISOString().substr(0, 16)}-${name}`)
4250
if (debug) {
4351
fs.writeFileSync(logFilename, contents)

src/links/scripts/rendered-content-link-checker-cli.js renamed to src/links/scripts/rendered-content-link-checker-cli.ts

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -10,10 +10,10 @@
1010
import fs from 'fs'
1111
import path from 'path'
1212
import { program, Option, InvalidArgumentError } from 'commander'
13-
import renderedContentLinkChecker from '#src/links/scripts/rendered-content-link-checker.js'
14-
import { getCoreInject, getUploadArtifactInject } from '#src/links/scripts/action-injections.js'
15-
import { allVersions } from '#src/versions/lib/all-versions.js'
16-
import github from '#src/workflows/github.js'
13+
import renderedContentLinkChecker from './rendered-content-link-checker'
14+
import { getCoreInject, getUploadArtifactInject } from '@/links/scripts/action-injections.js'
15+
import { allVersions } from '@/versions/lib/all-versions.js'
16+
import github from '@/workflows/github.js'
1717

1818
const STATIC_PREFIXES = {
1919
assets: path.resolve('assets'),
@@ -115,7 +115,7 @@ program
115115
return resolvedPath
116116
},
117117
)
118-
.arguments('[files...]', 'Specific files to check')
118+
.arguments('[files...]')
119119
.parse(process.argv)
120120

121121
const opts = program.opts()

0 commit comments

Comments
 (0)