Skip to content

Conversation

@webpro
Copy link

@webpro webpro commented Jan 7, 2026

Initial checklist

  • I read the support docs
  • I read the contributing guide
  • I agree to follow the code of conduct
  • I searched issues and discussions and couldn’t find anything or linked relevant results below
  • I made sure the docs are up to date
  • I included tests (or that’s not needed)

Description of changes

Part of

Has already been quite useful in two projects:

@github-actions github-actions bot added the 👋 phase/new Post is being triaged automatically label Jan 7, 2026
@github-actions

This comment has been minimized.

Signed-off-by: Lars Kappert <[email protected]>
@codecov
Copy link

codecov bot commented Jan 7, 2026

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 100.00%. Comparing base (f1f9321) to head (654a107).

Additional details and impacted files
@@            Coverage Diff            @@
##              main     #1474   +/-   ##
=========================================
  Coverage   100.00%   100.00%           
=========================================
  Files            6         6           
  Lines          138       138           
=========================================
  Hits           138       138           

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@github-actions github-actions bot added 🤞 phase/open Post is being triaged manually and removed 👋 phase/new Post is being triaged automatically labels Jan 7, 2026
— turn bolds, italics, and code into UTF 8 special characters
* 🟢 [`remark-validate-links`](https://github.com/remarkjs/remark-validate-links)
— check links to headings and files
* 🟢 [`remark-validate-relative-links`](https://github.com/webpro/remark-validate-relative-links)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not sure I understand this plugin from the readme, it looks like it does the same thing as https://github.com/remarkjs/remark-validate-links ?

ALso this doesn't appear to have types? Or be published to npm? Or have a CI/CD job testing it. All are things we look for in something to recommend to the community

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good points!

So, I started out by using remark-validate-links. But wanted to include/validate only relative links. With "skipPathPatterns": ["^/"] I noticed it resolves everything to absolute paths so the result is that all links are excluded (there isn't really a way around this, right?). Also was looking for something simpler without the "did you mean.." output (auto-completion in the editor is enough for me). So it's very similar indeed but the difference is that it validates only relative links. No frills.

The plugin is published at https://www.npmjs.com/package/remark-validate-relative-links. There's some basic types, the plugin does not take options (yet?).

I'll add some tests right away.

@remcohaszing
Copy link
Member

I have some tips.

  • You can type check JSDoc types with tsc and publish type definitions. I strongly recommend doing so. This also means that dependencies of those emitted types should go in package.json

  • @types/vfile is outdated. You should depend on vfile instead.

  • The following jsdoc:

    /**
     * @typedef {import('mdast').Root} Root
     */

    is equivalent to the following TypeScript:

    export type Root = import('mdast').Root

    This defines a new type named Root. This type is equivalent to (but not the same as) the Root type exported by mdast. This Root type is then exported.

    Most of the times you should do this:

    /**
     * @import { Root } from 'mdast'
     */

    This is equivalent to:

    import type { Root } from 'mdast'

    This only imports the Root type from mdast locally.

    If you intend to re-export a type, you can write the following in TypeScript:

    export type { Root } from 'mdast'

    Unfortunately there’s not jsdoc equivalent.

  • Relative links don’t have to start with a dot. The following are practically equivalent:

    [example](example.md)
    [example](./example.md)

    I think relative paths can’t start with a protocol, slash, or hashtag.

  • You can use mdast-util-to-string to get the text content of an mdast node.

  • I believe there are some smarter slugger implementation available. Notably they may deal with slugs of duplicate headings.

@webpro
Copy link
Author

webpro commented Jan 9, 2026

Thanks a bunch for the tips, much appreciated. Applied most of it and released v1.

@wooorm
Copy link
Member

wooorm commented Jan 9, 2026

I think relative paths can’t start with a protocol, slash, or hashtag.

// is relative to the current protocol, also ? starts query parameters.
But then ? and # are relative to the current path. And /asd is relative to the repo. And the // is relative to the protocol. So “relative” is a very vague term.
Not the exact same but maybe useful are https://github.com/micromark/micromark/blob/774a70c6bae6dd94486d3385dbd9a0f14550b709/packages/micromark-util-sanitize-uri/dev/index.js#L27 and https://github.com/micromark/micromark/blob/774a70c6bae6dd94486d3385dbd9a0f14550b709/test/io/misc/dangerous-protocols.js

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

🤞 phase/open Post is being triaged manually

Development

Successfully merging this pull request may close these issues.

4 participants