master
md 100 lines 3.32 KB
Rendered Raw
1 # Auditing `metadata.yaml` links to Learn
2
3 Use this when a generated integration page contains links to
4 `learn.netdata.cloud` and one of them drifts from the current Learn route.
5
6 ## Why this matters
7
8 `metadata.yaml` is rendered into integration pages on Learn, the website, and
9 the in-app integrations catalog (`../SKILL.md:37`). A broken Learn URL in
10 metadata therefore becomes a user-visible broken link on multiple surfaces.
11
12 Learn routes are not derived from source filenames. They are derived from
13 `docs/.map/map.yaml` labels and hierarchy, while source-relative `/docs/... .md`
14 links can be rewritten by Learn ingest (`../../learn-site-structure/mapping.md:219`).
15 For example, `docs/network-flows/visualization/summary-sankey.md` is published
16 as `/docs/network-flows/visualization/sankey-and-table` because the map label is
17 `Sankey and Table` (`docs/.map/map.yaml:515`).
18
19 ## Audit command
20
21 Extract unique absolute Learn URLs from all metadata files and check their
22 published response:
23
24 ```bash
25 rg -No "https://learn\\.netdata\\.cloud/docs[^)\\]\\s,\"']+" --glob 'metadata.yaml' . \
26 | sed 's/^.*https:/https:/' \
27 | sort -u \
28 | while read -r url; do
29 printf '%s\t' "$url"
30 curl -sL -o /dev/null -w '%{http_code}\t%{url_effective}\n' "$url"
31 done
32 ```
33
34 For URLs with fragments, also confirm the target anchor exists in the rendered
35 HTML:
36
37 ```bash
38 curl -A 'Mozilla/5.0' -sL 'https://learn.netdata.cloud/docs/netdata-agent/configuration' \
39 | rg 'id="locate-your-config-directory"'
40 ```
41
42 Validate source-relative metadata links locally:
43
44 ```bash
45 python3 - <<'PY'
46 import pathlib, re, sys
47
48 root = pathlib.Path('.')
49 pat = re.compile(r'\[[^\]]+\]\(([^)]+)\)')
50 problems = []
51
52 for path in sorted(root.rglob('metadata.yaml')):
53 text = path.read_text(errors='replace')
54 for match in pat.finditer(text):
55 target = match.group(1).strip()
56 if target.startswith('/docs/'):
57 file = root / target.split('#', 1)[0].lstrip('/')
58 elif target.startswith('../') or target.startswith('./'):
59 file = (path.parent / target.split('#', 1)[0]).resolve()
60 else:
61 continue
62
63 if not file.is_file():
64 line = text.count('\n', 0, match.start()) + 1
65 problems.append((str(path), line, target))
66
67 if problems:
68 for path, line, target in problems:
69 print(f'{path}:{line}: missing linked source file: {target}')
70 sys.exit(1)
71
72 print('OK: all metadata.yaml /docs and relative markdown links resolve to source files')
73 PY
74 ```
75
76 ## Repair rule
77
78 - If the link is Markdown text and points to a Netdata source doc, prefer the
79 source-relative `/docs/... .md` form when the consuming surface supports Learn
80 ingest rewriting.
81 - If the same metadata is consumed by non-Learn surfaces that do not rewrite
82 source-relative links, keep an absolute `https://learn.netdata.cloud/docs/...`
83 URL, but derive the slug from `docs/.map/map.yaml` labels and verify it with
84 `curl`.
85 - Do not infer slugs from filenames. Check the map label first, then validate
86 the published URL.
87
88 ## How I figured this out
89
90 Files read:
91
92 - `../SKILL.md`
93 - `../../learn-site-structure/mapping.md`
94 - `docs/.map/map.yaml`
95
96 Commands run:
97
98 - `rg -No 'https://learn\.netdata\.cloud/docs...' --glob 'metadata.yaml' .`
99 - `curl -sL -o /dev/null -w '%{http_code}\t%{url_effective}\n' <url>`
100 - local source-relative metadata link validation script above.