emulsify-ds / emulsify-design-system
The official Drupal theme for Emulsify, with Storybook and a Vite-based build workflow for generated child themes
Package info
github.com/emulsify-ds/emulsify-drupal
Language:Twig
Type:drupal-theme
pkg:composer/emulsify-ds/emulsify-design-system
Requires
- drupal/core: ^11.3 || ^12
- drupal/emulsify_tools: ^2.2
Requires (Dev)
None
Suggests
None
Provides
None
Conflicts
None
Replaces
None
- dev-main
- 7.2.2
- 7.2.1
- 7.2.0
- 7.1.1
- 7.1.0
- 7.0.0
- 6.2.0
- 6.1.1
- 6.1.0
- 6.0.1
- 6.0.0
- 5.4.1
- 5.4.0
- 5.3.2
- 5.3.1
- 5.3.0
- 5.2.0
- 5.1.0
- 5.0.2
- 5.0.1
- 5.0.0
- 4.9.1
- 4.9.0
- 4.8.1
- 4.8.0
- 4.7.0
- 4.6.0
- 4.5.0
- 4.4.0
- 4.3.3
- 4.3.2
- 4.3.1
- 4.3.0
- 4.2.2
- 4.2.1
- 4.2.0
- 4.1.1
- 4.1.0
- 4.0.0
- 3.0.2
- 3.0.1
- 3.0.0
- 2.x-dev
- 2.2.0
- 2.1.0
- 2.0.2
- 2.0.1
- 2.0.0
- 1.0.0
- v1.0.0-beta.4
- v1.0.0-beta.3
- v1.0.0-beta.2
- v1.0.0-beta.1
- v1.0.0-alpha.7
- v1.0.0-alpha.6
- v1.0.0-alpha.5
- v1.0.0-alpha.4
- dev-release-7.3
- dev-codex/test-generated-audit-wrappers
- dev-customizable-preview-config
- dev-emulsify-tools-stable-version
- dev-master
- dev-82-remove-lint-scripts
- dev-semver
- dev-bug/disable-minify-for-development
- dev-cli
- dev-feat/global-data
This package is auto-updated.
Last update: 2026-09-10 15:17:46 UTC
README
Emulsify Drupal
Emulsify is an open-source toolset for creating and implementing design systems on your website
Storybook, Emulsify Core 4, and a Vite-based build workflow for Drupal 11.3+
Emulsify Drupal is the official Drupal parent theme for Emulsify. It provides Storybook integration, Emulsify Core 4 tooling, and a Vite-based build workflow for Drupal 11.3+ with Drupal 12 forward compatibility. Your selected component library supplies the components. Until Drupal 12 beta or stable recommended-project releases are available, Drupal core development branch coverage is experimental.
The current 7.x series no longer depends on stable9; Emulsify now ships its own complete template layer instead of inheriting one from a Drupal parent theme.
Documentation
Use this README and UPGRADE.md for the current 7.x installation and upgrade workflow. The Emulsify documentation site also contains guides for older release lines; check the guide's version before following its commands.
Quick Links
- Installation
- Usage
- Upgrade guide
- Twig component includes
- Sister-project parity contract
- Template override map
- Favicon generation lifecycle
- Optional design-token integration
- Release readiness checklist
Demo
License
Emulsify Drupal is licensed under GPL-2.0-or-later, matching Drupal.org Composer metadata guidance for hosted Drupal projects.
How To
Install or upgrade the parent theme
Run these commands from an existing Composer-managed Drupal site's project root,
using that site's PHP/Composer environment. Examples assume a web document
root and Drush 13+ on your path; use your project's wrapper (for example,
ddev composer and ddev drush) when applicable.
The recommended distribution is drupal/emulsify from Drupal.org. Configure
Drupal.org in the site's root composer.json if it is not already configured,
then install the parent theme and its required companion module:
composer config repositories.drupal composer https://packages.drupal.org/8 composer require 'drupal/emulsify:^7.2' 'drupal/emulsify_tools:^2.2' --with-all-dependencies drush en emulsify_tools -y
The parallel Packagist package
is named emulsify-ds/emulsify-drupal. Existing sites using that package should
keep that name when updating:
composer update emulsify-ds/emulsify-drupal drupal/emulsify_tools --with-all-dependencies
Both package names distribute the parent theme and Whisk starter. Choose one
package name per site. The Packagist route also needs the Drupal.org repository
in the site's root Composer configuration to resolve drupal/emulsify_tools;
Composer does not load repository declarations from dependencies.
For an existing Drupal.org installation, update within your site's declared ranges and read the applicable upgrade notes:
composer update drupal/emulsify drupal/emulsify_tools --with-all-dependencies drush updb -y drush cr -y
The theme inherits its PHP floor from Drupal: PHP 8.3 for Drupal 11 and PHP 8.5
for Drupal 12. The declared core compatibility is ^11.3 || ^12; consult
Drupal's PHP requirements
for the supported PHP versions of your installed core release.
Identify your installed release
Composer's installed package version is authoritative for the parent theme. Run the command matching your site's package name:
composer show drupal/emulsify
composer show emulsify-ds/emulsify-drupal
The versions and source reference in that output identify what is installed;
the matching composer.lock entry records what a subsequent composer install
will reproduce. A development branch is identified by its source commit rather
than by claiming the latest stable release. Published release history lives in
GitHub Releases, with
consumer actions in UPGRADE.md. The
next-release draft contains unreleased changes.
The root package.json version is owned by @semantic-release/npm. That plugin
writes the calculated version during release preparation, with npmPublish: false;
the workflow does not commit that generated metadata back to Git.
Consequently, the checked-in npm version is tooling metadata, not an installed
Emulsify Drupal release identifier. Do not bump it manually. The release guard
checks this ownership policy and the unchanged metadata baseline from the latest
tag. The generated child theme's npm version belongs to that child project;
generatedFromVersion records its starter lineage, not the currently installed
parent theme version.
Generate a child theme
Emulsify Tools 2.2 or newer is required by the Emulsify Drupal parent theme.
The drush emulsify and drush emulsify_tools:bake commands are implemented by
Emulsify Tools, which must be installed and enabled. Its Drush helper delegates
to Drupal Starterkit so both generation commands
produce the same child theme. Generate a child theme with:
drush emulsify my_theme
The helper module also exposes the fully qualified command name:
drush emulsify_tools:bake my_theme
The whisk directory is the Whisk starter source used by both generation methods. Do not enable whisk directly; generated child themes keep emulsify as their runtime parent theme.
You can also generate the same child theme with Drupal core's standard
Starterkit command from the root of your Drupal site. On Drupal 11.4 and newer,
use the Composer-installed dr executable:
vendor/bin/dr generate-theme my_theme --starterkit whisk --path themes/custom
For Drupal 11.3, which does not provide that executable, use the earlier entrypoint:
php web/core/scripts/drupal generate-theme my_theme --starterkit whisk --path themes/custom
These generation methods should be treated as equivalent:
- They generate the theme into
web/themes/custom/my_theme. - They use the Whisk starter source.
- They keep
emulsifyas the runtime parent theme for the generated child theme. - They preserve
project.emulsify.jsonso Emulsify Core can identify the generated Drupal project structure. - They retain
generatedFromandgeneratedFromVersionmetadata so support tooling can identify the Emulsify Drupal source and version used to create the child theme.
After generation:
- Enable the theme:
drush theme:enable my_theme -y drush config:set system.theme default my_theme -y drush cr -y
- Install the generated child theme's frontend dependencies:
cd web/themes/custom/my_theme
npm install
- Select and install the project's component library. Whisk does not provide a project source tree or build entrypoints. Its generated Drupal library file contains only commented CSS and JavaScript examples. Follow the component library's setup instructions; once it provides build inputs, update those examples and start the local tooling:
npm run develop
Generated child themes include the Vite and Storybook tooling from Emulsify Core 4. The selected component library owns the source structure and asset integration those tools consume.
Write Twig component includes
For new project Twig, prefer Drupal Single Directory Component names:
{% include "my_theme:list" with {
items: items,
} only %}
The Twig function form is also supported:
{{ include("my_theme:list", {
items: items,
}, with_context = false) }}
Replace my_theme with the generated child theme machine name. Legacy namespace
includes such as {% include "@components/button/button.twig" %} are still
valid for existing projects and migrations, but they are not the recommended
default for new project components. See
docs/twig-component-includes.md for the
component include guidance.
Verify your generated child theme
Run the install and test commands from the generated child theme directory, not
from whisk:
cd web/themes/custom/my_theme node --version npm install npm run test npm run inspect:components
The component inspector discovers the project component inventory and reports component metadata, dependencies, configuration issues, and orphaned files. It does not require components to exist, so a newly generated component-neutral theme returns a valid empty report. Use JSON output for automation or view the command help:
npm run inspect:components -- --json npm run inspect:components -- --help
After the selected component library supplies project sources, also run its asset-dependent checks:
npm run build npm run storybook-build
Whisk advertises Node.js >=24, while Emulsify Core 4.3.1 and 4.4.0 require
>=24.13.0; the effective frontend floor for those versions is therefore
24.13.0. Root release tooling separately requires 24.15 or newer. Both
.nvmrc files select the Node 24 line without pinning its minor version. These
declared requirements differ; a Node 24.0 installation does not satisfy Emulsify
Core. Check the resolved Core package's engines when updating dependencies.
Use npm install for the first local install, or npm ci when the generated
child theme already has a committed package-lock.json.
These checks verify the expected local workflow:
- Compare
node --versionwith the effective Node.js floor above. npm installinstalls Emulsify Core 4 and the generated child theme tooling.npm run testverifies the generated Jest setup. It passes when no project tests exist yet.npm run inspect:componentsreports the component inventory and related project health information.- After component-library installation,
npm run buildcompiles its Drupal-facing assets with the Vite build workflow. npm run storybook-buildverifies the component library's static Storybook build.
Optional browser-based accessibility check:
npm run a11y
npm run a11y builds Storybook and runs the Emulsify Core accessibility check.
Run it after component-library installation in local or CI environments that
can use the required browser-based tooling.
Manage generated favicon packages
The generated favicon workflow is built around one portable SVG source stored in theme settings.
Emulsify Drupal owns the theme-facing parts of that workflow: the theme settings form, config defaults and schema, admin previews, frontend head tags, generated asset references in <theme>.settings, and sanitized SVG storage for config portability.
- Configure the package in the theme settings form for
emulsifyor a generated child theme. - Save the theme settings form to generate or update the package during normal admin changes.
- Review package and portable-source diagnostics in the theme settings UI.
Emulsify Tools owns deployment-oriented Drush operations for those same settings. After configuration import or deploy, use the Emulsify Tools favicon commands to generate, inspect, or reset environment-local package files before public traffic reaches the environment. See the Emulsify Tools README for the full command documentation.
Runtime page requests never generate favicon files. If the configured package is missing, Emulsify skips favicon head tags until the theme settings form or the Emulsify Tools generate command creates the package.
Generated favicon packages require the PHP gd extension and the Imagick extension for SVG rasterization. If either extension is unavailable, the uploaded SVG can still be stored in configuration, but PNG and ICO package generation will fail until those extensions are installed.
The theme settings UI surfaces the current portable-source and package status. Portable SVG copies larger than 256 KB are flagged because very large config payloads are awkward to review and deploy.
See docs/favicon-generation.md for generated files, package location, generator limits, and deployment expectations.
Contributing
Code of Conduct
The project maintainers have adopted a Code of Conduct that we expect project participants to adhere to. Please read the full text so that you can understand what actions will and will not be tolerated.
Contribution Guide
Please also follow the issue template and pull request templates provided. See below for the correct places to post issues:
Committing Changes
To facilitate automatic semantic release versioning, we utilize the Conventional Changelog standard through Commitizen. Follow these steps when committing your work to ensure semantic release can version correctly.
- Stage your changes, ensuring they encompass exactly what you wish to change, no more.
- Create a Conventional Commit message, either manually or with your preferred commit helper.
- Your commit message will be used to create the changelog for the next version that includes that commit.
Release Readiness
Run the release guard before merging packaging, Whisk starter, favicon settings, or release metadata changes, and before preparing a 7.x release:
npm run release:check
Use Node.js 24.15 or newer for local release tooling.
Release automation publishes from main with non-prefixed SemVer tags.
Use npm run release:check -- --skip-smoke when you only want the static metadata, README, duplicate-script, and schema checks. The static checks verify that favicon settings stay aligned across FaviconSettings::DEFAULTS, config/install/emulsify.settings.yml, and config/schema/emulsify.schema.yml.
Author
Emulsify® is a product of Four Kitchens — We make BIG websites.
Contributors
This project follows the all-contributors specification. Contributions of any kind welcome!
