Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Declare subpath exports for bundled plugins, Eleventy-maintained data, .d.ts typings, etc. #3460

Open
noelforte opened this issue Sep 27, 2024 · 3 comments

Comments

@noelforte
Copy link
Contributor

noelforte commented Sep 27, 2024

Upfront note: I'd be willing to submit a PR to help out with this.

Is your feature request related to a problem? Please describe.

Commit c505822 inadvertantly introduced some breaking changes to subpath exports when Eleventy is consumed as a dependency. By adding the exports key to package.json with only 1 conditional import (import/requre keys), any attempt to import a subpath throws a ERR_PACKAGE_PATH_NOT_EXPORTED error. (source)

Describe the solution you'd like

This is more specific to @11ty/eleventy/src/Engines/Util/ContextAugmenter.js (#3355 (comment)) but is applicable to any exports in Eleventy that could be consumed by outside packages, including (but not limited to):

  • Plugins bundled with Eleventy
  • .d.ts declaration files (#3097, #3296)
  • Eleventy-maintained global data and methods like augmentKeys

Syntax I'm thinking of could be something like:

"exports": {
  ".": {
    "import": "./src/Eleventy.js",
    "require": "./src/EleventyCommonJs.cjs",
  },
  "./user-config": {
    "types": "./types/UserConfig.d.ts"
  },
  "./plugins/*": "./src/Plugins/*",
}

The above declarations can be consumed as so:

import type UserConfig from '@11ty/eleventy/user-config';
import Eleventy from '@11ty/eleventy';
import HtmlBasePlugin from '@11ty/eleventy/plugins/HtmlBasePlugin.js';
// ...

Or via an aggregator:

"exports": {
  "./internal-plugins": "./src/Plugins/index.js",
}
import {
  HtmlBasePlugin,
  RenderPlugin,
  InputPathToUrlPlugin,
} from '@11ty/eleventy/internal-plugins';

Describe alternatives you've considered

It is possible to import something from a package with an "exports" key directly via node_modules, for instance this doesn't throw an error:

import { augmentKeys } from 'node_modules/@11ty/eleventy/src/Engines/Util/ContextAugmenter.js';

...however I'm cautious to use that pattern because it's 1) not terribly erganomic, and 2) I'm not sure if there's any resolution errors that could stem from that syntax. In my case specifically, augmentKeys is a 2-element array so my solve is copy-pasting the array into my code to achieve the same result.

Additional context

Subpath exports are supported by Node 18 which is the required minimum for 3.0.

Additionally, when an exports field is present the main field is ignored by Node v12.7.0 and later, so to alleviate any confusion in Node's entry-point resolution, it might be worth removing the "main" key from Eleventy's package.json entirely. (source)

@noelforte noelforte changed the title Declare subpath exports for bundled plugins, Eleventy-maintained data, etc. Declare subpath exports for bundled plugins, Eleventy-maintained data, .d.ts typings, etc. Oct 29, 2024
@Ryuno-Ki
Copy link
Contributor

Related to #3097

@noelforte
Copy link
Contributor Author

Related to #3097

@Ryuno-Ki yep, I mentioned that issue in my original post. I opened a new issue since while .d.ts files can be referenced through subpath imports, the implementation of subpath imports isn't directly dependent on typings. I'm ok closing in favor of the other issue, but there's my explanation 😄

@Ryuno-Ki
Copy link
Contributor

Ryuno-Ki commented Nov 3, 2024

Ah, missed the nuance.

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

No branches or pull requests

2 participants