Replies: 11 comments 16 replies
-
That's a very neat feature I would like to see! |
Beta Was this translation helpful? Give feedback.
-
@bluwy we discussed this idea with the team and we think it is an interesting approach. As you already showcased in your plugin this can be implemented for the moment in userland without a commitment from core, so it is better to let people explore this path using your plugin. There is a chance that we may not end up adding new URL query suffixes in core, if build tools start to embrace the syntax from import assertions. So it is good to have more time before adding something like this in core. Regarding the API, you should go with the design that makes more sense for you. My personal opinion is to use the direct |
Beta Was this translation helpful? Give feedback.
-
If anyone's using Svelte or Vue, the custom typescript plugin from vite-plugin-iso-import to resolve intellisense for I have not a found a way to add support to load plugins for those extensions, but based on my recent findings, it may even be impossible unless we spawn a new If any Typescript experts are able to help out, that would be greatly appreciated! Otherwise, import assertions may be the way to go that could save us from the shambles. Or just manual module declarations. |
Beta Was this translation helpful? Give feedback.
-
One other use for environment-specific imports is for dev-only builds. e.g. having the import dependent on import.meta.env.DEV if (import.meta.env.DEV) {
import mod from 'some-dev-only-module';
// dev-only code
} |
Beta Was this translation helpful? Give feedback.
-
This would also help me with something I am trying to achieve. I have 2 api client implementations, one that is mocked out for development, and the other that actually fetches from the server for testing against the server and production. I would like to exclude the mock code from my final bundle, and I think this would allow me to do so by conditionally loading depending on an environment variable. |
Beta Was this translation helpful? Give feedback.
-
This works: // only enable solid-devtools during dev phase
if (import.meta.env.DEV) {
await import('solid-devtools');
} with vite config: optimizeDeps: {
esbuildOptions: {
target: 'esnext',
},
},
build: {
target: 'es2020',
}, |
Beta Was this translation helpful? Give feedback.
-
This is my version of @bluwy's vite-plugin-iso-import. It doesn't completely remove the import, but it is much simpler and it still works with static imports, which is needed for svelte: const serverRE = /(.*[?&])ssr(&.*|)$/
export default function devPlugin() {
return {
name: 'ssr-only-import',
enforce: 'pre',
async resolveId(id, importer, options) {
let m = serverRE.exec(id);
if(! m)
return null;
if(! options.ssr)
return {
id: 'data:text/javascript,export default null;',
external: true,
}
return this.resolve(
m[1] + m[2].substr(1),
importer,
{ skipSelf: true , ...options},
);
},
async load(id, options) {
if (id.startsWith('data:text/javascript,')) {
return id.substr(21);
}
},
}
} |
Beta Was this translation helpful? Give feedback.
-
Because Vite and TypeScript now supports
"imports": {
"#iso/*.ts": {
"types": "./src/*.client.ts",
"browser": "./src/*.client.ts",
"node": "./src/*.server.ts"
}
}
Stackblitz demo (It seems TS 5.0 doesn't work in stackblitz yet) Note that the types will refer |
Beta Was this translation helpful? Give feedback.
-
this is a very neat idea i hope it gets implemented |
Beta Was this translation helpful? Give feedback.
-
We should consider more than just conditional imports on the client and server. It will also have other conditions, so this should be a general function. For example, I am using Electron to develop an application, which is also compatible with the web version. I want the web version import It's easy for do this with CJS const foo = process.env.IS_ELECTRON ? require('./foo.electron.js') : require('./foo.browser.js') Proposaldefine the condition in {
...
condition: {
browser: true, // control by user
electron: false // control by user
}
} use condition with import foo from './foo?browser=./foo.browser.js&electron=./foo.electron.js' if condition not match, then import |
Beta Was this translation helpful? Give feedback.
-
Or we can do it more simply. Import two packages, but which package is empty will be determined based on the environment eg. import fooClient from './foo.client.js'
import fooServer from './foo.server.js'
const foo = import.meta.env.IS_CLIENT ? fooClient : fooServer If running on client, It will be transform to import fooClient from './foo.client.js'
const fooServer = {}
const foo = import.meta.env.IS_CLIENT ? fooClient : fooServer otherwise const fooClient = {}
import fooServer from './foo.server.js'
const foo = import.meta.env.IS_CLIENT ? fooClient : fooServer In this way it solves the problem of typescript very well |
Beta Was this translation helpful? Give feedback.
-
Summary
Allow tagging imports as environment-specific and only import them when the environment matches.
Basic example
Motivation
In most SSR frameworks, a route view is usually executed in the browser and node context. This causes browser-only modules and node-only modules to fail if they're executed in the opposite intended context. The current pattern is to use dynamic imports to load these modules conditionally, which generates some amount of boilerplate. For example:
Detailed design
Introduce new
?client
and?server
suffix. An experimental plugin is created and tested in a SvelteKit app.For example, in SSR mode,
?client
suffix will be stripped of the final bundled code as if the import never existed.?server
suffix, the import id will be stripped of the?server
suffix as if a normal import is written. e.g."./foo?server"
=>"./foo"
The opposite would be true for non-SSR mode.
Drawbacks
if (import.env.meta.SSR)
to avoid runtime unreferenced/undefined variables, which can sometimes be overlooked.?client
or?server
suffix loses intellisense (A custom typescript plugin can fix this)Alternative
?only=client
and?only=server
, which could future-proof the API if more environments are needed to be supported.?pure
to aggressively treeshake a bundle without accounting for side-effects, since side-effects are the issuewindow is not defined
errors pop up in the first place when importing browser-only module, for example.Beta Was this translation helpful? Give feedback.
All reactions