Syntax: SCSS vs. Sass
|
This section documents Sass/SCSS as implemented by Dart Sass, the current official and actively maintained compiler — it is not tied to any specific book, build tool, or CSS framework (Bootstrap, Bulma, etc.). Unlike the other reference sections on this site, no single reference book underpins it: the content was generated with the assistance of AI from general knowledge of Dart Sass, and should be verified against the current official documentation at sass-lang.com before relying on it in production. Sass continues to evolve, so behaviour described here may lag the compiler you are actually running. This section’s bibliography lists the reference material consulted while preparing these pages. |
Sass is a CSS preprocessor: a language that adds variables, nesting, mixins, functions, and a module system on top of CSS, then compiles down to the plain CSS a browser actually understands (see Compilation). What makes it slightly unusual among preprocessors is that it offers two different syntaxes for the same language. Both are handled by the same compiler, expose exactly the same features, and produce exactly the same CSS — they differ only in punctuation.
The two syntaxes
| SCSS | Indented Sass | |
|---|---|---|
File extension |
|
|
Blocks |
Curly braces |
Indentation |
Statement terminator |
Semicolon |
Newline |
Relationship to CSS |
A strict superset — any valid CSS file is a valid SCSS file |
Not CSS-compatible — plain CSS must be converted first |
Typical use |
The default choice, and by far the most common in practice |
Niche; favoured by those who prefer terse, whitespace-driven syntax |
SCSS: the default
SCSS ("Sassy CSS") is the syntax you should reach for unless you have a specific reason not to. Because it is a
superset of CSS, you can rename an existing .css file to .scss and it will compile unchanged, then adopt
Sass features incrementally. Every example elsewhere in this section uses SCSS.
@use "sass:color";
$primary: #3f51b5;
$radius: 4px;
@mixin button-base {
border: 0;
border-radius: $radius;
cursor: pointer;
}
.card {
padding: 1rem;
border-radius: $radius;
.card__title {
margin: 0;
color: $primary;
}
.card__button {
@include button-base;
background: $primary;
color: white;
&:hover {
background: color.adjust($primary, $lightness: -10%);
}
}
}
The indented syntax
The indented syntax — the original one, and the reason the language is called "Sass" — drops braces and semicolons entirely, deriving block structure from indentation the way Python or YAML does. Here is the exact same stylesheet:
@use "sass:color"
$primary: #3f51b5
$radius: 4px
@mixin button-base
border: 0
border-radius: $radius
cursor: pointer
.card
padding: 1rem
border-radius: $radius
.card__title
margin: 0
color: $primary
.card__button
@include button-base
background: $primary
color: white
&:hover
background: color.adjust($primary, $lightness: -10%)
Both files compile to identical CSS:
.card {
padding: 1rem;
border-radius: 4px;
}
.card .card__title {
margin: 0;
color: #3f51b5;
}
.card .card__button {
border: 0;
border-radius: 4px;
cursor: pointer;
background: #3f51b5;
color: white;
}
.card .card__button:hover {
background: rgb(19.5419479267%, 25.1253616201%, 56.1443265831%);
}
That hover value looks odd printed as a percentage rgb() rather than a hex code, but it’s the same colour
(#32408f) — current Dart Sass’s colour engine represents the output of a colour function like color.adjust()
in this form rather than re-serializing it back to hex.
The indented syntax is consistent about its terseness: multi-line expressions must be escaped or kept on one line, and a few constructs (such as inline comments) are written differently. Indentation must also be consistent within a file — mixing tabs and spaces is an error.
Which one to choose
Prefer SCSS. It is the default in essentially every toolchain, it is what published Sass libraries and framework source (Bootstrap, Bulma) are written in, it is what almost all documentation and answers online use, and its CSS-superset property means there is no translation step when copying a snippet out of a browser’s developer tools or a CSS reference. The indented syntax remains fully supported and is not deprecated — it is simply a stylistic preference, and choosing it costs you nothing in features but some convenience.
The two syntaxes can coexist in one project: a .scss file may @use a .sass partial and vice versa, since
the distinction is purely at the parsing stage. Dart Sass also ships a sass-convert-style migration path
through the community sass-migrator tool for translating between them wholesale.
Comments
Comment syntax is one place worth calling out, because Sass adds a form CSS doesn’t have:
/* A standard CSS comment. This is preserved in the compiled output
(except in compressed mode). */
// A Sass single-line comment. This is stripped from the output entirely.
/*! A loud comment. Preserved even in compressed output -- useful for licence banners. */
Silent // comments are the right default for notes meant for whoever is reading the Sass source, since they
add nothing to the bytes shipped to the browser.