Mix tasks for installing and invoking sass.
If you are going to build assets in production, then you add
dart_sass
as a dependency on all environments but only start it
in dev:
def deps do
[
{:dart_sass, "~> 0.7", runtime: Mix.env() == :dev}
]
end
However, if your assets are precompiled during development, then it only needs to be a dev dependency:
def deps do
[
{:dart_sass, "~> 0.7", only: :dev}
]
end
Once installed, change your config/config.exs
to pick your
dart_sass version of choice:
config :dart_sass, version: "1.77.8"
Now you can install dart-sass by running:
$ mix sass.install
And invoke sass with:
$ mix sass default assets/css/app.scss priv/static/assets/app.css
If you need additional load paths you may specify them:
$ mix sass default assets/css/app.scss --load-path=assets/node_modules/bulma priv/static/assets/app.css
The executable may be kept at _build/sass-TARGET
. However in most cases
running dart-sass requires two files: the portable Dart VM is kept at
_build/dart-TARGET
and the Sass snapshot is kept at _build/sass.snapshot-TARGET
.
Where TARGET
is your system target architecture.
The first argument to dart_sass
is the execution profile.
You can define multiple execution profiles with the current
directory, the OS environment, and default arguments to the
sass
task:
config :dart_sass,
version: "1.77.8",
default: [
args: ~w(css/app.scss ../priv/static/assets/app.css),
cd: Path.expand("../assets", __DIR__)
]
When mix sass default
is invoked, the task arguments will be appended
to the ones configured above.
To add dart_sass
to an application using Phoenix, you need only four steps.
Note that installation requires that Phoenix watchers can accept MFArgs
tuples – so you must have Phoenix > v1.5.9.
First add it as a dependency in your mix.exs
:
def deps do
[
{:phoenix, "~> 1.7.14"},
{:dart_sass, "~> 0.7", runtime: Mix.env() == :dev}
]
end
Now let's configure dart_sass
to use assets/css/app.scss
as the input file and
compile CSS to the output location priv/static/assets/app.css
:
config :dart_sass,
version: "1.77.8",
default: [
args: ~w(css/app.scss ../priv/static/assets/app.css),
cd: Path.expand("../assets", __DIR__)
]
Note: if you are using esbuild (the default from Phoenix v1.6), make sure you remove the
import "../css/app.css"
line at the top of assets/js/app.js soesbuild
stops generating css files.
Note: make sure the "assets" directory from priv/static is listed in the :only option for Plug.Static in your endpoint file at, for instance
lib/my_app_web/endpoint.ex
.
For development, we want to enable watch mode. So find the watchers
configuration in your config/dev.exs
and add:
sass: {
DartSass,
:install_and_run,
[:default, ~w(--embed-source-map --source-map-urls=absolute --watch)]
}
Note we are embedding source maps with absolute URLs and enabling the file system watcher.
Finally, back in your mix.exs
, make sure you have an assets.deploy
alias for deployments, which will also use the --style=compressed
option:
"assets.deploy": [
"esbuild default --minify",
"sass default --no-source-map --style=compressed",
"phx.digest"
]
Note: Using glibc on Alpine Linux is not recommended. Proceed at your own risk.
Dart-native executables rely on glibc to be present. Because Alpine Linux uses musl instead, you have to add the package alpine-pkg-glibc to your installation. Follow the installation guide in the README.
For example, add the following to your Dockerfile before you
run mix sass
:
ENV GLIBC_VERSION=2.34-r0
RUN wget -q -O /etc/apk/keys/sgerrand.rsa.pub https://alpine-pkgs.sgerrand.com/sgerrand.rsa.pub && \
wget -q -O /tmp/glibc.apk https://github.com/sgerrand/alpine-pkg-glibc/releases/download/${GLIBC_VERSION}/glibc-${GLIBC_VERSION}.apk && \
apk add /tmp/glibc.apk && \
rm -rf /tmp/glibc.apk
In case you get the error ../../runtime/bin/eventhandler_linux.cc: 412: error: Failed to start event handler thread 1
, it means that your Docker installation or the used Docker-in-Docker image, is using a version below Docker 20.10.6. This error is related to an updated version of the musl library. It can be resolved by using the alpine-pkg-glibc with the version 2.33 instead of 2.34.
Notes: The Alpine package gcompat vs libc6-compat will not work.
In order to ensure graceful termination of the sass
process
when stdin closes, when the--watch
option is given then the
sass process will be invoked by a bash script that will
handle the cleanup.
This package is based on the excellent esbuild by Wojtek Mach and José Valim.
Copyright (c) 2021 CargoSense, Inc.
dart_sass source code is licensed under the MIT License.