3

How can I render a component that has been compiled using svelte.compile() manually? I'm compiling a component like this:

<script type="module">
    import * as svelte from 'svelte/compiler';

    var { js: Awesome } = svelte.compile(svelteComponentCode, {
        generate: 'dom', //can use 'ssr' too
        hydratable: true,
        filename: 'Helloworld.svelte'
    });
</script>

I have access to Awesome.code which is the JS compiled from the svelte component and want to use it to render the component to the DOM.

TheUnKnown
  • 681
  • 5
  • 29

1 Answers1

3

I know this is an old question now, but I think you need to use the same technique that you'll find in the Svelte REPL where you need to create a Blob with the code, and then load and mount that.

const { code } = svelte.compile(inputCode).js;

const blob = new Blob([code], { type: 'text/javascript' });
const url = URL.createObjectURL(blob);

import(url).then(({ default: Component }) => {
  new Component({
    target: document.body, // or whatever your target is
  });
});

The compile is usually done in a webworker to get it off the main UI thread.

There is a nice video on building a barebones REPL that can be used as a nice way to learn about "in browser" svelte compiling; this uses the browser version of rollup as well. That's because your svelte component will probably be importing other code.

https://www.youtube.com/watch?v=S3j1fLzC8_E

There's another really relevant answer here that is far more fleshed out and explains more about linking of imports during the build of a component, although it's more about node build step than an in browser build experience. Regardless, it's likely it can be of some use.

Just remember that the browser doesn't have access to your file system, so imports will need to be loaded from a server when building/bundling an app in the browser.

plumpNation
  • 142
  • 1
  • 12
  • Hi there! Thanks for your answer! I've tried to use Blob in an endpoint file so it runs on the server-side but I keep getting this error: `__vite_ssr_import_1__.Blob is not a constructor` – TheUnKnown Feb 25 '22 at 14:35
  • I think this question is relevant maybe https://stackoverflow.com/questions/14653349/node-js-cant-create-blobs – plumpNation Feb 26 '22 at 15:58
  • The thing is that you probably don't want to render the blob on the server, just compile the javascript. Then send that to the front end and use the Blob constructor there. – plumpNation Feb 26 '22 at 15:59
  • The way I want to use this compiled component is so that the one who requests for it don't have to do anything as far as compiling goes. Which is why I can't put any logic on the client side. Just to give you an overview of the flow that I'm trying to make it work is: Svelte project 1: compiles components based on request and sends it as response Svelte project 2: Gets data and renders it in the DOM. – TheUnKnown Mar 08 '22 at 16:00
  • As far as the browser app is concerned, it's just loading javascript from a server. So you have the options available to you that the browser offers, for instance script tags, eval, import(...) etc. – plumpNation Mar 09 '22 at 22:14
  • Right, but with your suggested approach, I'll have to get to client side to be able to use Blob, I want to compile the component and send it as a response while being on the server side so the requester can render it on their end on the client side. – TheUnKnown Mar 11 '22 at 01:37
  • 1
    The Blob does not compile the component. The output of the compile process on the server is js. The Blob is just one way to parse that on the frontend. A script tag is another. If I've misunderstood your needs I'm sorry, and I'm very curious about the technique you find in the end to suit your needs. I hope you update with an answer when you find one that suits your needs :) – plumpNation Mar 12 '22 at 10:25