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

Question: is there a way to drop specific exports? #3890

Open
fregante opened this issue Aug 21, 2024 · 3 comments
Open

Question: is there a way to drop specific exports? #3890

fregante opened this issue Aug 21, 2024 · 3 comments

Comments

@fregante
Copy link

I'm bundling a library that has about a hundred small exports, each followed by "inline test data" that should not be shipped to production.

I'm currently using --drop-labels=TEST and a helper function like TEST: addTest('name', [data]) but it feels a bit delicate because then I also have to make sure addTest is dropped, etc.

My full command is:

esbuild index.ts --bundle --external:github-reserved-names --format=esm --drop-labels=TEST

Ideally, this is what it'd write:

export const something = 23456;
export const something_TEST_DATA = [data]

And esbuild would provide a way to drop *_TEST_DATA exports. Unfortunately labels are not allowed before exports

Context: https://github.com/refined-github/github-url-detection/pull/196/files?file-filters%5B%5D=.json&file-filters%5B%5D=.ts&file-filters%5B%5D=.yml&show-viewed-files=true&show-deleted-files=false

@fregante
Copy link
Author

If tree-shaking works, I think it would be "as easy as" using a different entry-point like:

export {something, other, stuff} from './lib.js';

so that all unused test data is tree-shaken, but this becomes impractical and dangerous when there are a hundred exports and you forget to add new ones to this entry-point.

@hyrious
Copy link

hyrious commented Aug 21, 2024

I'm not sure why you're exporting a test-only data from the source code. Maybe it will be used in another script?

Anyway, I come up with 2 possible solutions:

  • The export names can always be scaned with es-module-lexer or something like that. Thus the second entry is generated automatically.

  • You can just don't export these data, for example, a JavaScript label can have a block follows:

    export const something = 23456
    TEST: {
    	const something_TEST_DATA = [data]
    	doSomeTestHere()
    }

    If the test data is going to be used in another block or module, it can be assigned to global scope:

    TEST: globalThis.something_TEST_DATA = [data]
    
    ...
    
    TEST: doSomeTestHere(something_TEST_DATA)

@fregante
Copy link
Author

I'm not sure why you're exporting a test-only data from the source code. Maybe it will be used in another script?

Yes, the test script uses import * as stuff and then the stuff array can be easily filtered by _TEST_DATA name.

I'm actually already using my "ideal" version in another project, but it works there because it's not a library (i.e. the other exports are imported by the production code, and the test exports are naturally tree-shaken)

Source with test code: https://github.com/refined-github/refined-github/blob/13510c32340b53fc0532e00f6b90a687bf1279bb/source/github-helpers/selectors.ts#L5-L10
Tests with filter: https://github.com/refined-github/refined-github/blob/13510c32340b53fc0532e00f6b90a687bf1279bb/source/github-helpers/selectors.test.ts#L60

  • a JavaScript label can have a block follows:

That's actually my current solution, as mentioned in my second paragraph. It works, but I'm looking for alternatives, ideally via exports since it works well in my other project.

  • The export names can always be scaned with es-module-lexer or something like that

I suppose that would require writing a esbuild plugin, which is less ideal than the current label-based solution.

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

No branches or pull requests

2 participants