Skip to content

Improve package format publishing and release verification #51

Description

@rockwellll

Problem

The package advertises multiple consumption paths, but the current published shape is fragile:

  • package.json advertises ESM through module: "lib/index.js" and exports["."].import: "./lib/index.js".
  • The emitted ESM files use extensionless or directory-style internal imports such as ./hellotext, ./core, ./api, and ./models, which do not resolve under Node ESM.
  • The emitted CJS files live beside .js siblings and also use extensionless internal require() calls, so Node can resolve the wrong sibling in some paths.
  • The UMD bundle is useful for script tag/CDN usage, but it is currently named generically as dist/hellotext.js, which can be confused with package ESM/CJS entries.

Reproduction checks

From this repo, the ESM path currently fails:

node --input-type=module -e "import('./lib/index.js')"

Observed failure:

ERR_MODULE_NOT_FOUND: Cannot find module './lib/hellotext' imported from './lib/index.js'

The advertised vanilla path is also affected:

node --input-type=module -e "import('./lib/vanilla.js')"
node -e "require('./lib/vanilla.cjs')"

Proposed improvements

  1. Fix the actual ESM build by emitting extensionful internal imports, for example ./hellotext.js, ./core/index.js, ./api/index.js, and so on.

  2. Fix the CJS build by making internal require() calls resolve .cjs siblings explicitly, or by moving CJS output into a separate folder where extensionless resolution cannot pick ESM-looking .js files.

  3. Separate module formats cleanly. Prefer a structure such as dist/esm/*.js and dist/cjs/*.cjs, or use .mjs for ESM and .cjs for CommonJS.

  4. Add packed-package smoke tests in CI. Run npm pack, install the generated tarball into a temporary project, then verify:

    • import '@hellotext/hellotext'
    • require('@hellotext/hellotext')
    • import '@hellotext/hellotext/vanilla'
    • require('@hellotext/hellotext/vanilla')
    • import '@hellotext/hellotext/styles/index.css' in a bundler fixture
    • loading the UMD script path
  5. Clarify browser vs Node entrypoints. The root entry starts Stimulus and writes to window, while @hellotext/hellotext/vanilla is documented as the non-browser path. Make that contract explicit in docs, exports, and tests.

  6. Clean up the exports map. Keep root, ./vanilla, ./styles/index.css, and ./package.json, but make every condition precise: types, import, require, and possibly browser.

  7. Reconsider the vague default export condition pointing at ./dist/hellotext.js. If the UMD bundle is a fallback only for specific consumers, document that intent or replace it with clearer conditions.

  8. Align engines and Babel targets. package.json requires Node >=20, while the CJS Babel env targets Node 14. Pick the real support floor and compile accordingly.

  9. Modernize the ESM output. The ESM build targets esmodules: true, but still applies transforms such as class transforms. The ESM output can likely be smaller, cleaner, and more tree-shakable.

  10. Reduce package payload intentionally. npm pack --dry-run currently includes src, lib, and dist. Decide whether shipping src is intentional; if not, remove it from the files list.

  11. Ship source maps for lib and dist/hellotext.js so downstream debugging works without relying on raw source being present in the package.

  12. Make CSS side effects explicit. Keep CSS marked as side-effectful and ensure the docs and sideEffects field agree with the separate CSS import contract.

  13. Improve type packaging. Add per-entry declaration coverage or declaration tests for @hellotext/hellotext, @hellotext/hellotext/vanilla, and @hellotext/hellotext/styles/index.css.

  14. Make release packaging harder to stale. Use prepack or a release script that cleans, builds, packs, installs the tarball, smoke-tests it, and only then publishes.

  15. Name CDN artifacts intentionally. Consider names like hellotext.umd.js and hellotext.umd.min.js so script-tag artifacts are clearly distinct from package module entrypoints.

Acceptance criteria

  • The packed tarball works for both ESM import and CommonJS require from a fresh temporary consumer project.
  • @hellotext/hellotext/vanilla works in Node without touching browser globals.
  • Bundler users can import the package and CSS using the documented paths.
  • CDN/script-tag users still have a stable UMD artifact.
  • CI verifies the packed package before release.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions