Svonix
Svonix is a small library that allows you to easily create and use Svelte components in Phoenix.
Svonix is loosely based on the ideas behind Sveltex, but is written to support Phoenix > 1.6
, as well as dynamic loading of individual Svelte components to reduce filesizes.
Svonix works with ESBuild which is the default bundler for Phoenix.
Please note that while npm packages can be imported and work as you would expect, Svelte component libraries are currently not supported.
Installation
- Add
svonix
to your list of dependencies inmix.exs
:
def deps do
[
{:svonix, git: "https://github.com/nikokozak/svonix", tag: "v0.5.1"}
]
end
- Next, run
mix svonix.setup
from your Phoenix application's root folder.
Svonix will create an assets/js/svelte
folder, and will run npm install
after copying over the following files into your assets
folder:
-
package.json
(listing svelte's dependencies) -
build.js
(custom ESBuild build script)
- In your
config/dev.exs
file, add a watcher (you can replace the ESBuild watcher already there):
config :my_app, MyApp.Endpoint,
# other options
watchers: [
node: ["build.js", "--watch", cd: Path.expand("../assets", __DIR__)]
]
- Finally, in your
assets/js/app.js
file, add the following line at the top:
import 'svonix'
Usage
- Add new components to the
assets/js/svelte
folder. For example, we'll add atest.svelte
component:
<script>
export let name;
</script>
<h1>Hey {name}, Phoenix and Svelte setup is working!</h1>
- Next, add a Svonix tag where desired (the tag name must match the filename of the component), and pass in the arguments you like:
# lib/myapp_web/templates/page/index.html.heex
<%= Svonix.render "test", %{ name: "Nikolai" } %>
You should see the component rendered in the view.
Advanced Usage
Folder Structure
Svonix supports nesting components to accommodate whatever structure you might desire. In other words, you can structure your svelte files as follows:
assets/js/svelte/
ARootComponent.svelte
helpers/
AHelperComponent.svelte
AnotherComponent.svelte
evenMoreHelpers/
PrettyDeepNesting.svelte
In order to render a component that has been nested (say, for example, AnotherComponent.svelte
), simply pass in the path of the component (without an extension) into the render
function:
<%= Svonix.render "helpers/AnotherComponent" %>
Private Components
By default, any and all components you declare in your folder structure will generate individual js
files in your priv/static/assets/svelte_components
folder. This isn't really a problem given that these files are only loaded by the client on demand. Nonetheless, to avoid compiling a given file, simply prepend an _
(underscore) to its name. You can import the file from other components, but it will not be made available to render.
assets/js/svelte/
ThisWillRender.svelte
_ThisWillNot.svelte