Guide for contributors.
PHP language is required to develop this package. In order to support other frontend developers which do not have installed PHP locally, there is a Docker image available to develop this package.
To start this project simply run make start
and then add project certificates to your machine by make cert
.
In a moment the app will be setup and ready on https://localhost:4443
.
Please consult Makefile
for available commands and options to setup and run this project.
In order to maintain the uniformity of writing and functioning of components in HTML-like syntax, it is necessary to accept the following rules in the implementation.
This is an example of a typical file structure of a component:
├── src
└── Resources
└── components
└── <ComponentName>
├── stories - Component stories
├── <ComponentName>.stories.twig - Template rendered in demo app
├── <ComponentName>.twig — Twig component
└── README.md — documentation of the component
- Name of components must be camelCase with first letter small.
- New components must contain a property class so that they can be extended according to the instructions
{% set _class = (props.class is defined) ? ' ' ~ props.class : '' -%}
- Components must have block content when is not self-closing. This block is in HTML-like syntax used to define children.
- Components must contain attribute props. This is so that it resembles the React components as much as possible.
- All internal twig variables should start by underscore (this represents private variables).
{% set _privateAttr = (props.attr is defined) ? pros.attr : '' %}
🚨 Do not use default(true)
filter for setting default value of the prop to true
.
This will lead to unexpected behavior.
The false
value is never passed and is treated as empty/null, so the prop will be true
every time.
Do not use:
{%- set _ariaHidden = props.ariaHidden | default(true) -%}
Instead use:
{%- set _ariaHidden = props.ariaHidden ?? true -%}
See default filter does not work issue and Twig default filter documentation for more information
🚨 All props that uses raw filter must be prefixed with UNSAFE_
.
These props are unescaped.
For example we used this prefix for props that can accept HTML string.
<Checkbox UNSAFE_helperText="<strong>Help!</strong>" />
{# This represent main component class and prepend class prefix #}
{% set _className = _spiritClassPrefix ~ 'MainComponentClass' %}
{# This represent extendable component #}
{% set _class = (props.class is defined) ? ' ' ~ props.class : '' -%}
<span class="{{ _className }}{{ _class }}">
{# This represent children #}
{%- block content %}{% endblock %}
</span>
{% embed "@spirit/button.twig" with { props: {
attr: 'value'
}} %}
{% block content %}
Some children content
{% endblock %}
{% endembed %}
Components testing is done by snapshots tests. It is required to create snapshot test for each component. Please create a new component fixture file in tests/components-fixtures/
folder and name it according to the component name.
Run composer phpunit:update
or make phpunit-update
to create or update snapshots from fixtures.
% cd <your-local-path>/spirit-design-system/packages/web-twig
% yarn test:unit
for unit tests
The component testing is done only via snapshot testing. When adding new functionality or removing an old one, please, check twice the output of the snapshot test.
Every component has its own suite of snapshot tests in the following directory architecture:
├── src
└── Resources
└── components
└── <ComponentName>
└── __tests__ - Component tests
├── <ComponentName>SnapshotTest.php - Test class that extends tests/AbstractComponentSnapshotTest.php
├── __fixtures__ — Directory with prescriptions
└── __snapshots__ — Directory with snapshots
Snapshots are generated based on prescription by the command above.
Note: Every component MUST contain the test that extends tests/AbstractComponentSnapshotTest.php
which contains the current logic of the test itself.
It is balanced between the DRY principle and how the PHPUnit works.
TODO: Automate release process.
As we are now using only dev-main
version of this package, until we have stable release process, we are not able to release new version with release script and tag it.
./newVersion.sh <version>
!
Packagist requires a single repository for a single package to be present to publish the package. In order to publish this package we are using READ-ONLY repository https://github.com/lmc-eu/spirit-web-twig-bundle where we are publishing the subtree of this monorepo.
Please use these commands to update the READ-ONLY repository.
Add remote repository only once:
git remote add web-twig-readonly [email protected]:lmc-eu/spirit-web-twig-bundle.git
Force push current changes to remote using subtree:
git push web-twig-readonly `git subtree split --prefix packages/web-twig main`:main --force
Or
- use
make publish pkg=web-twig
in repository root to publish changes to remote.