Showing preview only (788K chars total). Download the full file or copy to clipboard to get everything.
Repository: callstack/linaria
Branch: master
Commit: 8bb4e92c481b
Files: 282
Total size: 720.8 KB
Directory structure:
gitextract_xouc4tvv/
├── .all-contributorsrc
├── .changeset/
│ ├── README.md
│ └── config.json
├── .codecov.yml
├── .editorconfig
├── .eslintignore
├── .eslintrc.js
├── .git-blame-ignore-revs
├── .github/
│ ├── ISSUE_TEMPLATE/
│ │ ├── bug_report.md
│ │ ├── config.yml
│ │ ├── enhancement_request.md
│ │ └── feature_request.md
│ ├── PULL_REQUEST_TEMPLATE.md
│ ├── labels.json
│ └── workflows/
│ ├── check.yml
│ ├── main.yml
│ ├── release.yml
│ └── site-deploy.yml
├── .gitignore
├── .npmrc
├── .prettierrc
├── .syncpackrc.js
├── .vscode/
│ └── settings.json
├── CODE_OF_CONDUCT.md
├── CONTRIBUTING.md
├── LICENSE
├── README.md
├── babel.config.js
├── commitlint.config.js
├── docs/
│ ├── API.md
│ ├── ATOMIC_CSS.md
│ ├── BASICS.md
│ ├── BENEFITS.md
│ ├── BUNDLERS_INTEGRATION.md
│ ├── CLI.md
│ ├── CONFIGURATION.md
│ ├── CRITICAL_CSS.md
│ ├── DYNAMIC_STYLES.md
│ ├── FEATURE_FLAGS.md
│ ├── HOW_IT_WORKS.md
│ ├── LINTING.md
│ ├── MIGRATION_GUIDE.md
│ └── THEMING.md
├── examples/
│ ├── astro-solid/
│ │ ├── astro.config.js
│ │ ├── package.json
│ │ ├── pages/
│ │ │ ├── csr.tsx
│ │ │ ├── csr_child.tsx
│ │ │ ├── external.ts
│ │ │ └── index.astro
│ │ └── tsconfig.json
│ ├── esbuild/
│ │ ├── .gitignore
│ │ ├── app.js
│ │ ├── build.js
│ │ └── package.json
│ ├── rollup/
│ │ ├── .gitignore
│ │ ├── app.js
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ └── rollup.config.mjs
│ ├── vite/
│ │ ├── .linariarc.mjs
│ │ ├── app.js
│ │ ├── index.html
│ │ ├── package.json
│ │ └── vite.config.js
│ ├── vpssr-linaria-solid/
│ │ ├── package.json
│ │ ├── pages/
│ │ │ ├── html-js/
│ │ │ │ ├── _default.page.client.js
│ │ │ │ └── index.page.server.tsx
│ │ │ ├── html-only/
│ │ │ │ └── index.page.server.tsx
│ │ │ ├── index.page.server.tsx
│ │ │ ├── spa/
│ │ │ │ └── index.page.client.tsx
│ │ │ └── ssr/
│ │ │ ├── Counter.tsx
│ │ │ └── index.page.tsx
│ │ ├── renderer/
│ │ │ ├── _default.page.client.tsx
│ │ │ └── _default.page.server.tsx
│ │ ├── server.js
│ │ ├── tsconfig.json
│ │ └── vite.config.js
│ └── webpack5/
│ ├── app.js
│ ├── babel.config.js
│ ├── package.json
│ └── webpack.config.js
├── greenkeeper.json
├── jest.config.js
├── link-wyw.sh
├── package.json
├── packages/
│ ├── atomic/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── processors/
│ │ │ ├── css.js
│ │ │ └── styled.js
│ │ ├── src/
│ │ │ ├── CSSProperties.ts
│ │ │ ├── css.ts
│ │ │ ├── index.ts
│ │ │ └── processors/
│ │ │ ├── css.ts
│ │ │ ├── helpers/
│ │ │ │ ├── atomize.ts
│ │ │ │ └── propertyPriority.ts
│ │ │ └── styled.ts
│ │ └── tsconfig.json
│ ├── core/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── __dtslint__/
│ │ │ ├── core.ts
│ │ │ ├── index.d.ts
│ │ │ ├── tsconfig.eslint.json
│ │ │ └── tsconfig.json
│ │ ├── __tests__/
│ │ │ ├── cx.test.ts
│ │ │ └── detect-core-js.test.ts
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── processors/
│ │ │ └── css.js
│ │ ├── src/
│ │ │ ├── CSSProperties.ts
│ │ │ ├── css.ts
│ │ │ ├── cx.ts
│ │ │ ├── index.ts
│ │ │ └── processors/
│ │ │ └── css.ts
│ │ └── tsconfig.json
│ ├── interop/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── __tests__/
│ │ │ ├── __snapshots__/
│ │ │ │ └── index.test.ts.snap
│ │ │ └── index.test.ts
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── src/
│ │ │ └── index.ts
│ │ └── tsconfig.json
│ ├── linaria/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── babel/
│ │ │ └── package.json
│ │ ├── babel.config.js
│ │ ├── evaluators/
│ │ │ └── package.json
│ │ ├── loader/
│ │ │ └── package.json
│ │ ├── package.json
│ │ ├── react/
│ │ │ └── package.json
│ │ ├── rollup/
│ │ │ └── package.json
│ │ ├── server/
│ │ │ └── package.json
│ │ ├── src/
│ │ │ ├── core.ts
│ │ │ ├── react.ts
│ │ │ └── server.ts
│ │ ├── stylelint-config/
│ │ │ └── package.json
│ │ └── tsconfig.json
│ ├── postcss-linaria/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── __tests__/
│ │ │ ├── __utils__/
│ │ │ │ └── index.ts
│ │ │ ├── locationCorrection.test.ts
│ │ │ ├── parse.test.ts
│ │ │ ├── stringify.test.ts
│ │ │ ├── stylelint.test.ts
│ │ │ └── utils.test.ts
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── src/
│ │ │ ├── index.ts
│ │ │ ├── locationCorrection.ts
│ │ │ ├── parse.ts
│ │ │ ├── stringify.ts
│ │ │ └── util.ts
│ │ └── tsconfig.json
│ ├── react/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── __dtslint-react17__/
│ │ │ ├── index.d.ts
│ │ │ ├── react17.tsx
│ │ │ ├── stubs/
│ │ │ │ ├── jsx-runtime.d.ts
│ │ │ │ └── react17.d.ts
│ │ │ ├── tsconfig.eslint.json
│ │ │ └── tsconfig.json
│ │ ├── __dtslint__/
│ │ │ ├── index.d.ts
│ │ │ ├── styled.ts
│ │ │ ├── tsconfig.eslint.json
│ │ │ └── tsconfig.json
│ │ ├── __tests__/
│ │ │ ├── __snapshots__/
│ │ │ │ └── styled.test.tsx.snap
│ │ │ ├── detect-core-js.test.ts
│ │ │ └── styled.test.tsx
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── processors/
│ │ │ └── styled.js
│ │ ├── src/
│ │ │ ├── index.ts
│ │ │ ├── processors/
│ │ │ │ └── styled.ts
│ │ │ ├── react-html-attributes.d.ts
│ │ │ └── styled.ts
│ │ └── tsconfig.json
│ ├── server/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── __tests__/
│ │ │ ├── __snapshots__/
│ │ │ │ └── collect.test.ts.snap
│ │ │ └── collect.test.ts
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── src/
│ │ │ ├── collect.ts
│ │ │ └── index.ts
│ │ └── tsconfig.json
│ ├── stylelint/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── src/
│ │ │ ├── index.ts
│ │ │ └── preprocessor.ts
│ │ └── tsconfig.json
│ ├── stylelint-config-standard-linaria/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── src/
│ │ │ └── index.js
│ │ └── tsconfig.json
│ └── testkit/
│ ├── CHANGELOG.md
│ ├── jest.config.js
│ ├── package.json
│ ├── src/
│ │ ├── __fixtures__/
│ │ │ ├── assignToExport.js
│ │ │ ├── bar.js
│ │ │ ├── circular-imports/
│ │ │ │ ├── bar.js
│ │ │ │ ├── constants.js
│ │ │ │ ├── foo.js
│ │ │ │ └── index.js
│ │ │ ├── complex-component.js
│ │ │ ├── components-library.js
│ │ │ ├── computedKeys.js
│ │ │ ├── enums.ts
│ │ │ ├── escape-character.js
│ │ │ ├── foo-nonstatic.js
│ │ │ ├── foo.js
│ │ │ ├── linaria-ui-library/
│ │ │ │ ├── components/
│ │ │ │ │ └── index.js
│ │ │ │ ├── hocs.js
│ │ │ │ ├── non-linaria-components.js
│ │ │ │ ├── package.json
│ │ │ │ └── types.ts
│ │ │ ├── loop/
│ │ │ │ ├── a.js
│ │ │ │ ├── ab.js
│ │ │ │ ├── b.js
│ │ │ │ ├── ba.js
│ │ │ │ └── index.js
│ │ │ ├── module-reexport.js
│ │ │ ├── non-linaria-ui-library/
│ │ │ │ ├── index.js
│ │ │ │ └── package.json
│ │ │ ├── objectExport.js
│ │ │ ├── re-exports/
│ │ │ │ ├── constants.js
│ │ │ │ ├── empty.js
│ │ │ │ ├── foo.js
│ │ │ │ └── index.js
│ │ │ ├── reexports.js
│ │ │ ├── runNearFramePaint.js
│ │ │ ├── sample-data.json
│ │ │ ├── sample-script.cjs
│ │ │ ├── sample-script.js
│ │ │ ├── sample-typescript.tsx
│ │ │ ├── self-import.js
│ │ │ ├── sequenceExport.js
│ │ │ ├── slugify.js
│ │ │ ├── ts-compiled-re-exports/
│ │ │ │ ├── constants.js
│ │ │ │ └── index.js
│ │ │ ├── ts-data.ts
│ │ │ └── with-babelrc/
│ │ │ ├── .babelrc.js
│ │ │ └── index.js
│ │ ├── __snapshots__/
│ │ │ ├── babel.test.ts.snap
│ │ │ └── transform.test.ts.snap
│ │ ├── __utils__/
│ │ │ └── linaria-snapshot-serializer.ts
│ │ ├── babel.test.ts
│ │ └── transform.test.ts
│ └── tsconfig.json
├── pnpm-workspace.yaml
├── react/
│ └── package.json
├── tsconfig.eslint.json
├── tsconfig.json
├── tsconfig.prod.json
├── tslint.json
├── turbo.json
└── website/
├── .eslintrc
├── CHANGELOG.md
├── babel.config.js
├── index.html
├── linaria.config.js
├── package.json
├── serve.config.js
├── src/
│ ├── .eslintrc
│ ├── api/
│ │ ├── index.js
│ │ └── react/
│ │ └── index.js
│ ├── components/
│ │ ├── App.jsx
│ │ ├── Container.js
│ │ ├── Example.js
│ │ ├── Header.jsx
│ │ └── Hero.jsx
│ ├── index.jsx
│ ├── server.jsx
│ └── styles/
│ ├── constants.js
│ └── utils.js
├── stylelint.config.js
└── webpack.config.js
================================================
FILE CONTENTS
================================================
================================================
FILE: .all-contributorsrc
================================================
{
"projectName": "linaria",
"projectOwner": "callstack",
"files": [
"README.md"
],
"imageSize": 100,
"commit": false,
"contributors": [
{
"login": "zamotany",
"name": "Paweł Trysła",
"avatar_url": "https://avatars2.githubusercontent.com/u/17573635?v=4",
"profile": "https://twitter.com/_zamotany",
"contributions": [
"code",
"doc",
"ideas"
]
},
{
"login": "satya164",
"name": "Satyajit Sahoo",
"avatar_url": "https://avatars2.githubusercontent.com/u/1174278?v=4",
"profile": "https://medium.com/@satya164",
"contributions": [
"code",
"doc",
"ideas"
]
},
{
"login": "thymikee",
"name": "Michał Pierzchała",
"avatar_url": "https://avatars2.githubusercontent.com/u/5106466?v=4",
"profile": "https://github.com/thymikee",
"contributions": [
"code",
"doc",
"ideas"
]
},
{
"login": "AgtLucas",
"name": "Lucas",
"avatar_url": "https://avatars1.githubusercontent.com/u/1909761?v=4",
"profile": "https://lcs.sh",
"contributions": [
"doc"
]
},
{
"login": "pronevich",
"name": "Alexey Pronevich",
"avatar_url": "https://avatars0.githubusercontent.com/u/680439?v=4",
"profile": "https://github.com/pronevich",
"contributions": [
"doc"
]
},
{
"login": "wojteg1337",
"name": "Wojtek Szafraniec",
"avatar_url": "https://avatars3.githubusercontent.com/u/18573330?v=4",
"profile": "https://github.com/wojteg1337",
"contributions": [
"code"
]
},
{
"login": "Anber",
"name": "Anton Evzhakov",
"avatar_url": "https://avatars3.githubusercontent.com/u/148258?v=4",
"profile": "http://twitter.com/anber_dev",
"contributions": [
"code",
"ideas",
"doc"
]
},
{
"login": "Tushkiz",
"name": "Tushar Sonawane",
"avatar_url": "https://avatars1.githubusercontent.com/u/1854763?v=4",
"profile": "https://twitter.com/tushkiz",
"contributions": [
"doc",
"example"
]
},
{
"login": "ferrannp",
"name": "Ferran Negre",
"avatar_url": "https://avatars2.githubusercontent.com/u/774577?v=4",
"profile": "http://twitter.com/ferrannp",
"contributions": [
"doc"
]
},
{
"login": "jukben",
"name": "Jakub Beneš",
"avatar_url": "https://avatars3.githubusercontent.com/u/8135252?v=4",
"profile": "https://jukben.cz",
"contributions": [
"code",
"doc"
]
},
{
"login": "oBusk",
"name": "Oscar Busk",
"avatar_url": "https://avatars2.githubusercontent.com/u/13413409?v=4",
"profile": "https://github.com/oBusk",
"contributions": [
"bug",
"code"
]
},
{
"login": "Trancever",
"name": "Dawid",
"avatar_url": "https://avatars3.githubusercontent.com/u/18584155?v=4",
"profile": "https://github.com/Trancever",
"contributions": [
"code",
"doc"
]
},
{
"login": "Esemesek",
"name": "Kacper Wiszczuk",
"avatar_url": "https://avatars2.githubusercontent.com/u/9092510?v=4",
"profile": "https://twitter.com/esemesek",
"contributions": [
"code",
"doc"
]
},
{
"login": "que-etc",
"name": "Denis Rul",
"avatar_url": "https://avatars3.githubusercontent.com/u/2401842?v=4",
"profile": "https://github.com/que-etc",
"contributions": [
"code"
]
},
{
"login": "johanholmerin",
"name": "Johan Holmerin",
"avatar_url": "https://avatars0.githubusercontent.com/u/7433263?v=4",
"profile": "https://github.com/johanholmerin",
"contributions": [
"code",
"doc"
]
},
{
"login": "pgilad",
"name": "Gilad Peleg",
"avatar_url": "https://avatars0.githubusercontent.com/u/4533329?v=4",
"profile": "https://www.giladpeleg.com/",
"contributions": [
"doc"
]
},
{
"login": "giuseppeg",
"name": "Giuseppe",
"avatar_url": "https://avatars3.githubusercontent.com/u/711311?v=4",
"profile": "http://giuseppe.pizza",
"contributions": [
"code"
]
},
{
"login": "silvenon",
"name": "Matija Marohnić",
"avatar_url": "https://avatars2.githubusercontent.com/u/471278?v=4",
"profile": "https://silvenon.com",
"contributions": [
"code",
"doc"
]
},
{
"login": "Schubidu",
"name": "Stefan Schult",
"avatar_url": "https://avatars2.githubusercontent.com/u/120432?v=4",
"profile": "http://schultstefan.de",
"contributions": [
"code"
]
},
{
"login": "wardpeet",
"name": "Ward Peeters",
"avatar_url": "https://avatars3.githubusercontent.com/u/1120926?v=4",
"profile": "http://www.coding-tech.be",
"contributions": [
"code"
]
},
{
"login": "radoslaw-medryk",
"name": "radoslaw-medryk",
"avatar_url": "https://avatars0.githubusercontent.com/u/43260833?v=4",
"profile": "https://github.com/radoslaw-medryk",
"contributions": [
"code"
]
},
{
"login": "dr2009",
"name": "杨兴洲",
"avatar_url": "https://avatars1.githubusercontent.com/u/8262650?v=4",
"profile": "http://dr2009.com",
"contributions": [
"code"
]
},
{
"login": "hinok",
"name": "Dawid Karabin",
"avatar_url": "https://avatars2.githubusercontent.com/u/1313605?v=4",
"profile": "https://github.com/hinok",
"contributions": [
"doc"
]
},
{
"login": "chrisabrams",
"name": "Chris Abrams",
"avatar_url": "https://avatars1.githubusercontent.com/u/527740?s=460&v=4",
"profile": "https://github.com/chrisabrams",
"contributions": [
"code",
"doc",
"ideas"
]
},
{
"login": "Jayphen",
"name": "Jayphen",
"avatar_url": "https://avatars0.githubusercontent.com/u/329184?v=4",
"profile": "http://hyperlab.se",
"contributions": [
"code"
]
},
{
"login": "bolasblack",
"name": "c4605",
"avatar_url": "https://avatars0.githubusercontent.com/u/382011?v=4",
"profile": "https://github.com/bolasblack",
"contributions": [
"code"
]
},
{
"login": "koba04",
"name": "Toru Kobayashi",
"avatar_url": "https://avatars2.githubusercontent.com/u/250407?v=4",
"profile": "https://koba04.com/",
"contributions": [
"code"
]
},
{
"login": "jayu",
"name": "Jakub Mazurek",
"avatar_url": "https://avatars.githubusercontent.com/u/11561585?v=4",
"profile": "https://github.com/jayu",
"contributions": [
"code"
]
},
{
"login": "jpnelson",
"name": "Joshua Nelson",
"avatar_url": "https://avatars.githubusercontent.com/u/1518604?v=4",
"profile": "http://subsecond.dev/",
"contributions": [
"code",
"ideas",
"doc"
]
},
{
"login": "TMaszko",
"name": "Tomasz Krzyżowski",
"avatar_url": "https://avatars.githubusercontent.com/u/16257732?v=4",
"profile": "https://twitter.com/TMaszko",
"contributions": [
"code"
]
},
{
"login": "dfrkp",
"name": "Martin Schulze",
"avatar_url": "https://avatars.githubusercontent.com/u/1476435?v=4",
"profile": "https://www.slash-m.com/",
"contributions": [
"code"
]
},
{
"login": "wmzy",
"name": "wmzy",
"avatar_url": "https://avatars.githubusercontent.com/u/5526525?v=4",
"profile": "https://github.com/wmzy",
"contributions": [
"code"
]
},
{
"login": "cometkim",
"name": "Hyeseong Kim",
"avatar_url": "https://avatars.githubusercontent.com/u/9696352?v=4",
"profile": "https://blog.cometkim.kr/",
"contributions": [
"code"
]
},
{
"login": "Hotell",
"name": "Martin Hochel",
"avatar_url": "https://avatars.githubusercontent.com/u/1223799?v=4",
"profile": "https://github.com/Hotell",
"contributions": [
"code"
]
},
{
"login": "Daniel15",
"name": "Daniel Lo Nigro",
"avatar_url": "https://avatars.githubusercontent.com/u/91933?v=4",
"profile": "https://d.sb/",
"contributions": [
"code"
]
},
{
"login": "0xflotus",
"name": "0xflotus",
"avatar_url": "https://avatars.githubusercontent.com/u/26602940?v=4",
"profile": "https://github.com/0xflotus",
"contributions": [
"code"
]
},
{
"login": "afzalsayed96",
"name": "Afzal Sayed",
"avatar_url": "https://avatars.githubusercontent.com/u/14029371?v=4",
"profile": "https://github.com/afzalsayed96",
"contributions": [
"code"
]
},
{
"login": "aiji42",
"name": "AijiUejima",
"avatar_url": "https://avatars.githubusercontent.com/u/6711766?v=4",
"profile": "https://github.com/aiji42",
"contributions": [
"code"
]
},
{
"login": "le0pard",
"name": "Oleksii Vasyliev",
"avatar_url": "https://avatars.githubusercontent.com/u/98444?v=4",
"profile": "https://leopard.in.ua/",
"contributions": [
"code"
]
},
{
"login": "alicanerdogan",
"name": "Alican Erdoğan",
"avatar_url": "https://avatars.githubusercontent.com/u/1814803?v=4",
"profile": "https://github.com/alicanerdogan",
"contributions": [
"code"
]
},
{
"login": "amankkg",
"name": "Aman Kubanychbek",
"avatar_url": "https://avatars.githubusercontent.com/u/3933028?v=4",
"profile": "https://amank.me/",
"contributions": [
"code"
]
},
{
"login": "kinetifex",
"name": "Andrew Gerard",
"avatar_url": "https://avatars.githubusercontent.com/u/82775?v=4",
"profile": "http://kinetifex.com/",
"contributions": [
"code"
]
},
{
"login": "frolovdev",
"name": "Andrey Frolov",
"avatar_url": "https://avatars.githubusercontent.com/u/30667180?v=4",
"profile": "https://www.linkedin.com/in/andrey-frolov-3b8579155/",
"contributions": [
"code"
]
},
{
"login": "soluml",
"name": "Benjamin Solum",
"avatar_url": "https://avatars.githubusercontent.com/u/589571?v=4",
"profile": "https://github.com/soluml",
"contributions": [
"code"
]
},
{
"login": "billykwok",
"name": "Billy Kwok",
"avatar_url": "https://avatars.githubusercontent.com/u/8078716?v=4",
"profile": "https://billykwok.me/",
"contributions": [
"code"
]
},
{
"login": "chrstntdd",
"name": "Christian Todd",
"avatar_url": "https://avatars.githubusercontent.com/u/17863654?v=4",
"profile": "https://github.com/chrstntdd",
"contributions": [
"code"
]
},
{
"login": "dpeek",
"name": "David Peek",
"avatar_url": "https://avatars.githubusercontent.com/u/128329?v=4",
"profile": "https://estii.com/",
"contributions": [
"code"
]
},
{
"login": "dskiba",
"name": "Denis Skiba",
"avatar_url": "https://avatars.githubusercontent.com/u/28356785?v=4",
"profile": "https://github.com/dskiba",
"contributions": [
"code"
]
},
{
"login": "geakstr",
"name": "Dima Kharitonov",
"avatar_url": "https://avatars.githubusercontent.com/u/1496368?v=4",
"profile": "https://github.com/geakstr",
"contributions": [
"code"
]
},
{
"login": "GabbeV",
"name": "Gabriel Valfridsson",
"avatar_url": "https://avatars.githubusercontent.com/u/13839236?v=4",
"profile": "https://github.com/GabbeV",
"contributions": [
"code"
]
},
{
"login": "GitaiQAQ",
"name": "Gitai",
"avatar_url": "https://avatars.githubusercontent.com/u/5354788?v=4",
"profile": "http://t.cn/EvDFUFF",
"contributions": [
"code"
]
},
{
"login": "hampuskraft",
"name": "Hampus Kraft",
"avatar_url": "https://avatars.githubusercontent.com/u/24176136?v=4",
"profile": "https://hampuskraft.com/",
"contributions": [
"code"
]
},
{
"login": "isumix",
"name": "Igor Sukharev",
"avatar_url": "https://avatars.githubusercontent.com/u/16747416?v=4",
"profile": "https://github.com/isumix",
"contributions": [
"code"
]
},
{
"login": "eltociear",
"name": "Ikko Ashimine",
"avatar_url": "https://avatars.githubusercontent.com/u/22633385?v=4",
"profile": "https://bandism.net/",
"contributions": [
"code"
]
},
{
"login": "ImanMh",
"name": "Iman Mohamadi",
"avatar_url": "https://avatars.githubusercontent.com/u/4482199?v=4",
"profile": "http://jsdecorator.com/",
"contributions": [
"code"
]
},
{
"login": "codecorsair",
"name": "JB <codecorsair>",
"avatar_url": "https://avatars.githubusercontent.com/u/9878445?v=4",
"profile": "https://github.com/codecorsair",
"contributions": [
"code"
]
},
{
"login": "Jack-Works",
"name": "Jack Works",
"avatar_url": "https://avatars.githubusercontent.com/u/5390719?v=4",
"profile": "https://jack-works.github.io/",
"contributions": [
"code"
]
},
{
"login": "jamesgeorge007",
"name": "James George",
"avatar_url": "https://avatars.githubusercontent.com/u/25279263?v=4",
"profile": "https://ghuser.io/jamesgeorge007",
"contributions": [
"code"
]
},
{
"login": "jedmao",
"name": "Jed Mao",
"avatar_url": "https://avatars.githubusercontent.com/u/1058243?v=4",
"profile": "https://appleid.apple.com/",
"contributions": [
"code"
]
},
{
"login": "lencioni",
"name": "Joe Lencioni",
"avatar_url": "https://avatars.githubusercontent.com/u/195534?v=4",
"profile": "https://github.com/lencioni",
"contributions": [
"code"
]
},
{
"login": "joeycozza",
"name": "Joey Cozza",
"avatar_url": "https://avatars.githubusercontent.com/u/3885959?v=4",
"profile": "https://github.com/joeycozza",
"contributions": [
"code"
]
},
{
"login": "juanferreras",
"name": "Juan Ferreras",
"avatar_url": "https://avatars.githubusercontent.com/u/8507996?v=4",
"profile": "https://github.com/juanferreras",
"contributions": [
"code"
]
},
{
"login": "kazuma1989",
"name": "Kazuma Ebina",
"avatar_url": "https://avatars.githubusercontent.com/u/15844862?v=4",
"profile": "https://www.linkedin.com/in/kazuma1989/",
"contributions": [
"code"
]
},
{
"login": "webpro",
"name": "Lars Kappert",
"avatar_url": "https://avatars.githubusercontent.com/u/456426?v=4",
"profile": "https://webpro.nl/",
"contributions": [
"code"
]
},
{
"login": "lmammino",
"name": "Luciano Mammino",
"avatar_url": "https://avatars.githubusercontent.com/u/205629?v=4",
"profile": "https://loige.co/",
"contributions": [
"code"
]
},
{
"login": "madhavarshney",
"name": "Madhav Varshney",
"avatar_url": "https://avatars.githubusercontent.com/u/40002855?v=4",
"profile": "https://github.com/madhavarshney",
"contributions": [
"code"
]
},
{
"login": "malash",
"name": "Malash",
"avatar_url": "https://avatars.githubusercontent.com/u/1812118?v=4",
"profile": "https://malash.me/",
"contributions": [
"code"
]
},
{
"login": "Swaagie",
"name": "Martijn Swaagman",
"avatar_url": "https://avatars.githubusercontent.com/u/670951?v=4",
"profile": "https://github.com/Swaagie",
"contributions": [
"code"
]
},
{
"login": "moitias",
"name": "Matias Lahti",
"avatar_url": "https://avatars.githubusercontent.com/u/1009280?v=4",
"profile": "https://github.com/moitias",
"contributions": [
"code"
]
},
{
"login": "majames",
"name": "Michael James",
"avatar_url": "https://avatars.githubusercontent.com/u/7553458?v=4",
"profile": "https://github.com/majames",
"contributions": [
"code"
]
},
{
"login": "kryops",
"name": "Michael Strobel",
"avatar_url": "https://avatars.githubusercontent.com/u/1042594?v=4",
"profile": "https://github.com/kryops",
"contributions": [
"code"
]
},
{
"login": "michalchudziak",
"name": "Michał Chudziak",
"avatar_url": "https://avatars.githubusercontent.com/u/7837457?v=4",
"profile": "https://twitter.com/michalchudziak",
"contributions": [
"code"
]
},
{
"login": "mkanyar",
"name": "Mike ",
"avatar_url": "https://avatars.githubusercontent.com/u/33469024?v=4",
"profile": "https://github.com/mkanyar",
"contributions": [
"code"
]
},
{
"login": "mikestopcontinues",
"name": "Mike Stop Continues",
"avatar_url": "https://avatars.githubusercontent.com/u/150434?v=4",
"profile": "https://www.mikestopcontinues.com/",
"contributions": [
"code"
]
},
{
"login": "Mokshit06",
"name": "Mokshit Jain",
"avatar_url": "https://avatars.githubusercontent.com/u/50412128?v=4",
"profile": "https://github.com/Mokshit06",
"contributions": [
"code"
]
},
{
"login": "layershifter",
"name": "Oleksandr Fediashov",
"avatar_url": "https://avatars.githubusercontent.com/u/14183168?v=4",
"profile": "https://www.linkedin.com/in/layershifter/",
"contributions": [
"code"
]
},
{
"login": "paddyobrien",
"name": "Paddy O'Brien",
"avatar_url": "https://avatars.githubusercontent.com/u/846372?v=4",
"profile": "https://github.com/paddyobrien",
"contributions": [
"code"
]
},
{
"login": "SogoCZE",
"name": "Patrik Smělý",
"avatar_url": "https://avatars.githubusercontent.com/u/8431593?v=4",
"profile": "https://sogocze.cz/",
"contributions": [
"code"
]
},
{
"login": "Nedgeva",
"name": "Pavel Udaloff",
"avatar_url": "https://avatars.githubusercontent.com/u/19298874?v=4",
"profile": "https://github.com/Nedgeva",
"contributions": [
"code"
]
},
{
"login": "pbitkowski",
"name": "Przemysław Bitkowski",
"avatar_url": "https://avatars.githubusercontent.com/u/22204594?v=4",
"profile": "https://github.com/pbitkowski",
"contributions": [
"code"
]
},
{
"login": "ri7nz",
"name": "RiN",
"avatar_url": "https://avatars.githubusercontent.com/u/16365952?v=4",
"profile": "https://rin.rocks/",
"contributions": [
"code"
]
},
{
"login": "pustomytnyk",
"name": "Roman Sokhan",
"avatar_url": "https://avatars.githubusercontent.com/u/9644824?v=4",
"profile": "https://github.com/pustomytnyk",
"contributions": [
"code"
]
},
{
"login": "SeokminHong",
"name": "Seokmin Hong (Ray)",
"avatar_url": "https://avatars.githubusercontent.com/u/11614766?v=4",
"profile": "https://github.com/SeokminHong",
"contributions": [
"code"
]
},
{
"login": "lebedev",
"name": "Serge K Lebedev",
"avatar_url": "https://avatars.githubusercontent.com/u/5000549?v=4",
"profile": "https://github.com/lebedev",
"contributions": [
"code"
]
},
{
"login": "funsis",
"name": "Sergey Korovin",
"avatar_url": "https://avatars.githubusercontent.com/u/28862758?v=4",
"profile": "https://github.com/funsis",
"contributions": [
"code"
]
},
{
"login": "shreyas44",
"name": "Shreyas Sreenivas",
"avatar_url": "https://avatars.githubusercontent.com/u/46835608?v=4",
"profile": "https://github.com/shreyas44",
"contributions": [
"code"
]
},
{
"login": "skywickenden",
"name": "Sky Wickenden",
"avatar_url": "https://avatars.githubusercontent.com/u/4930551?v=4",
"profile": "https://github.com/skywickenden",
"contributions": [
"code"
]
},
{
"login": "s-panferov",
"name": "Stanislav Panferov",
"avatar_url": "https://avatars.githubusercontent.com/u/198327?v=4",
"profile": "https://www.linkedin.com/in/stanislavpanferov",
"contributions": [
"code"
]
},
{
"login": "jsbalrog",
"name": "Ted Jenkins",
"avatar_url": "https://avatars.githubusercontent.com/u/2457489?v=4",
"profile": "https://github.com/jsbalrog",
"contributions": [
"code"
]
},
{
"login": "trongthanh",
"name": "Thanh Tran",
"avatar_url": "https://avatars.githubusercontent.com/u/234226?v=4",
"profile": "https://int3ractive.com/",
"contributions": [
"code"
]
},
{
"login": "tamorim",
"name": "Thor Amorim",
"avatar_url": "https://avatars.githubusercontent.com/u/5040487?v=4",
"profile": "https://github.com/tamorim",
"contributions": [
"code"
]
},
{
"login": "tobenna",
"name": "tobenna",
"avatar_url": "https://avatars.githubusercontent.com/u/12450941?v=4",
"profile": "https://github.com/tobenna",
"contributions": [
"code"
]
},
{
"login": "wereHamster",
"name": "Tomas Carnecky",
"avatar_url": "https://avatars.githubusercontent.com/u/34538?v=4",
"profile": "https://caurea.org/",
"contributions": [
"code"
]
},
{
"login": "Tsubasa1218",
"name": "Tsubasa1218",
"avatar_url": "https://avatars.githubusercontent.com/u/20498480?v=4",
"profile": "https://github.com/Tsubasa1218",
"contributions": [
"code"
]
},
{
"login": "turadg",
"name": "Turadg Aleahmad",
"avatar_url": "https://avatars.githubusercontent.com/u/21505?v=4",
"profile": "http://turadg.aleahmad.net/",
"contributions": [
"code"
]
},
{
"login": "buzinas",
"name": "Vitor Buzinaro",
"avatar_url": "https://avatars.githubusercontent.com/u/7298695?v=4",
"profile": "https://github.com/buzinas",
"contributions": [
"code"
]
},
{
"login": "Mistereo",
"name": "Mistereo",
"avatar_url": "https://avatars.githubusercontent.com/u/1505518?v=4",
"profile": "https://github.com/Mistereo",
"contributions": [
"code"
]
},
{
"login": "5angel",
"name": "Vladislav Kozulya",
"avatar_url": "https://avatars.githubusercontent.com/u/351676?v=4",
"profile": "https://ru.linkedin.com/in/govnokoder",
"contributions": [
"code"
]
},
{
"login": "yuheiy",
"name": "Yuhei Yasuda",
"avatar_url": "https://avatars.githubusercontent.com/u/11547305?v=4",
"profile": "https://yuheiy.com/",
"contributions": [
"code"
]
},
{
"login": "dkamyshov",
"name": "Danil Kamyshov",
"avatar_url": "https://avatars.githubusercontent.com/u/26835323?v=4",
"profile": "https://github.com/dkamyshov",
"contributions": [
"code"
]
},
{
"login": "dword-design",
"name": "Sebastian Landwehr",
"avatar_url": "https://avatars.githubusercontent.com/u/13484795?v=4",
"profile": "https://sebastianlandwehr.com/",
"contributions": [
"code"
]
},
{
"login": "everdimension",
"name": "everdimension",
"avatar_url": "https://avatars.githubusercontent.com/u/5347023?v=4",
"profile": "https://github.com/everdimension",
"contributions": [
"code"
]
},
{
"login": "ptol",
"name": "ptol",
"avatar_url": "https://avatars.githubusercontent.com/u/17497724?v=4",
"profile": "https://github.com/ptol",
"contributions": [
"code"
]
},
{
"login": "roottool",
"name": "roottool",
"avatar_url": "https://avatars.githubusercontent.com/u/11808736?v=4",
"profile": "https://roottool.vercel.app/",
"contributions": [
"code"
]
},
{
"login": "ryamaguchi0220",
"name": "ryamaguchi0220",
"avatar_url": "https://avatars.githubusercontent.com/u/14275842?v=4",
"profile": "https://github.com/ryamaguchi0220",
"contributions": [
"code"
]
},
{
"login": "simka",
"name": "simka",
"avatar_url": "https://avatars.githubusercontent.com/u/16965735?v=4",
"profile": "https://www.simka.dev/",
"contributions": [
"code"
]
},
{
"login": "SoYoung210",
"name": "soso",
"avatar_url": "https://avatars.githubusercontent.com/u/18658235?v=4",
"profile": "https://so-so.dev/",
"contributions": [
"code"
]
},
{
"login": "ChALkeR",
"name": "Nikita Skovoroda",
"avatar_url": "https://avatars.githubusercontent.com/u/291301?v=4",
"profile": "https://twitter.com/skovorodan",
"contributions": [
"code"
]
},
{
"login": "huang-xiao-jian",
"name": "黄小健",
"avatar_url": "https://avatars.githubusercontent.com/u/4002210?v=4",
"profile": "https://github.com/huang-xiao-jian",
"contributions": [
"code"
]
},
{
"login": "iMoses",
"name": "iMoses",
"avatar_url": "https://avatars.githubusercontent.com/u/1083065?v=4",
"profile": "https://github.com/iMoses",
"contributions": [
"code"
]
},
{
"login": "jneander",
"name": "Jeremy Neander",
"avatar_url": "https://avatars.githubusercontent.com/u/880186?v=4",
"profile": "http://jneander.com",
"contributions": [
"code"
]
},
{
"login": "andparsons",
"name": "Andy Parsons",
"avatar_url": "https://avatars.githubusercontent.com/u/1213447?v=4",
"profile": "https://evensix.com",
"contributions": [
"code"
]
},
{
"login": "Platane",
"name": "Platane",
"avatar_url": "https://avatars.githubusercontent.com/u/1659820?v=4",
"profile": "http://platane.github.io",
"contributions": [
"doc"
]
},
{
"login": "kutnickclose",
"name": "Tim Kutnick",
"avatar_url": "https://avatars.githubusercontent.com/u/6117662?v=4",
"profile": "https://github.com/kutnickclose",
"contributions": [
"doc"
]
},
{
"login": "aspirisen",
"name": "Dmitrii Pikulin",
"avatar_url": "https://avatars.githubusercontent.com/u/3620639?v=4",
"profile": "https://github.com/aspirisen",
"contributions": [
"code"
]
}
],
"repoType": "github",
"contributorsPerLine": 7,
"commitConvention": "none"
}
================================================
FILE: .changeset/README.md
================================================
# Changesets
Hello and welcome! This folder has been automatically generated by `@changesets/cli`, a build tool that works
with multi-package repos, or single-package repos to help you version and publish your code. You can
find the full documentation for it [in our repository](https://github.com/changesets/changesets)
We have a quick list of common questions to get you started engaging with this project in
[our documentation](https://github.com/changesets/changesets/blob/main/docs/common-questions.md)
================================================
FILE: .changeset/config.json
================================================
{
"$schema": "https://unpkg.com/@changesets/config@2.0.0/schema.json",
"changelog": "@changesets/cli/changelog",
"commit": false,
"fixed": [],
"linked": [],
"access": "restricted",
"baseBranch": "master",
"updateInternalDependencies": "patch",
"ignore": []
}
================================================
FILE: .codecov.yml
================================================
coverage:
precision: 2
round: down
range: 70...100
status:
project: true
patch: true
changes: false
comment: false
================================================
FILE: .editorconfig
================================================
# EditorConfig helps developers define and maintain consistent
# coding styles between different editors and IDEs
# editorconfig.org
root = true
[*]
# change these settings to your own preference
indent_style = space
indent_size = 2
# we recommend you to keep these unchanged
end_of_line = lf
charset = utf-8
trim_trailing_whitespace = true
insert_final_newline = true
[*.md]
trim_trailing_whitespace = false
================================================
FILE: .eslintignore
================================================
__fixtures__/
coverage/
lib/
esm/
packages/*/bin/
packages/*/types/
dist/
build/
node_modules/
vendor/
examples/
================================================
FILE: .eslintrc.js
================================================
const noRestrictedSyntax =
// eslint-disable-next-line import/no-extraneous-dependencies
require('eslint-config-airbnb-base/rules/style').rules[
'no-restricted-syntax'
].filter(
(rule) => typeof rule === 'string' || rule.selector !== 'ForOfStatement'
);
// Workaround for https://github.com/import-js/eslint-plugin-import/issues/1810
const noUnresolved = ['error', { ignore: ['@linaria/*'] }];
const memberOrder = [
'warn',
{
default: {
memberTypes: [
// Index signature
'signature',
'call-signature',
// Fields
'public-static-field',
'protected-static-field',
'private-static-field',
'#private-static-field',
'public-decorated-field',
'protected-decorated-field',
'private-decorated-field',
'public-instance-field',
'protected-instance-field',
'private-instance-field',
'#private-instance-field',
'public-abstract-field',
'protected-abstract-field',
'public-field',
'protected-field',
'private-field',
'#private-field',
'static-field',
'instance-field',
'abstract-field',
'decorated-field',
'field',
// Static initialization
'static-initialization',
// Constructors
'public-constructor',
'protected-constructor',
'private-constructor',
'constructor',
// Getters & Setters
['public-static-get', 'public-static-set'],
['protected-static-get', 'protected-static-set'],
['private-static-get', 'private-static-set'],
['#private-static-get', '#private-static-set'],
['public-decorated-get', 'public-decorated-set'],
['protected-decorated-get', 'protected-decorated-set'],
['private-decorated-get', 'private-decorated-set'],
['public-instance-get', 'public-instance-set'],
['protected-instance-get', 'protected-instance-set'],
['private-instance-get', 'private-instance-set'],
['#private-instance-get', '#private-instance-set'],
['public-abstract-get', 'public-abstract-set'],
['protected-abstract-get', 'protected-abstract-set'],
['public-get', 'public-set'],
['protected-get', 'protected-set'],
['private-get', 'private-set'],
['#private-get', '#private-set'],
['static-get', 'static-set'],
['instance-get', 'instance-set'],
['abstract-get', 'abstract-set'],
['decorated-get', 'decorated-set'],
['get', 'set'],
// Methods
'public-static-method',
'protected-static-method',
'private-static-method',
'#private-static-method',
'public-decorated-method',
'protected-decorated-method',
'private-decorated-method',
'public-instance-method',
'protected-instance-method',
'private-instance-method',
'#private-instance-method',
'public-abstract-method',
'protected-abstract-method',
'public-method',
'protected-method',
'private-method',
'#private-method',
'static-method',
'instance-method',
'abstract-method',
'decorated-method',
'method',
],
order: 'alphabetically',
},
},
];
const importOrder = [
'warn',
{
'newlines-between': 'always',
alphabetize: {
order: 'asc',
},
groups: ['builtin', 'external', 'internal', 'parent', 'sibling', 'index'],
pathGroups: [
{
pattern: '@linaria/**',
group: 'internal',
position: 'before',
},
],
pathGroupsExcludedImportTypes: [],
},
];
module.exports = {
plugins: ['prettier', 'import'],
rules: {
'import/no-extraneous-dependencies': [
'error',
{
devDependencies: [
'**/*.test.{js,ts,jsx,tsx}',
'src/{babel,server}/**/*.{js,ts,jsx,tsx}',
],
},
],
'import/no-unresolved': noUnresolved,
'max-len': [
'error',
150,
2,
{
ignoreComments: true,
ignoreStrings: true,
ignoreTemplateLiterals: true,
ignoreUrls: true,
},
],
'prettier/prettier': 'error',
},
globals: {
JSX: 'readonly',
},
settings: {
'import/resolver': {
node: {
extensions: ['.js', '.jsx', '.ts', '.tsx'],
},
},
},
overrides: [
{
files: ['*.ts', '*.tsx'],
extends: [
'airbnb-base',
'airbnb-typescript/base',
'plugin:@typescript-eslint/recommended',
'prettier',
'plugin:prettier/recommended',
'plugin:import/recommended',
'plugin:import/typescript',
],
parserOptions: {
project: './tsconfig.eslint.json',
},
rules: {
'import/extensions': 0,
'import/no-unresolved': noUnresolved,
'import/order': importOrder,
'import/prefer-default-export': 0,
'no-plusplus': ['error', { allowForLoopAfterthoughts: true }],
'@typescript-eslint/consistent-type-imports': [
'error',
{ prefer: 'type-imports' },
],
'@typescript-eslint/member-ordering': memberOrder,
// TODO
'@typescript-eslint/ban-ts-comment': 0,
'@typescript-eslint/comma-dangle': 0,
'@typescript-eslint/no-non-null-assertion': 0,
'@typescript-eslint/no-var-requires': 0,
'global-require': 0,
'import/no-dynamic-require': 0,
'no-underscore-dangle': 0,
'no-restricted-syntax': noRestrictedSyntax,
},
},
{
files: ['**/processors/**/*.ts'],
rules: {},
},
{
files: ['*.js', '*.jsx'],
extends: [
'airbnb-base',
'plugin:prettier/recommended',
'plugin:import/recommended',
],
parser: '@babel/eslint-parser',
parserOptions: {
requireConfigFile: false,
},
rules: {
'import/no-unresolved': noUnresolved,
},
},
{
files: [
'packages/testkit/**/*.test.ts',
'**/__tests__/**/*.test.ts',
'**/__tests__/**/*.test.tsx',
'**/__utils__/**/*.ts',
],
rules: {
'@typescript-eslint/naming-convention': [
'error',
{
selector: 'variable',
format: ['camelCase', 'PascalCase', 'UPPER_CASE'],
},
{
selector: 'function',
leadingUnderscore: 'allow',
format: ['camelCase', 'PascalCase'],
},
{
selector: 'typeLike',
format: ['PascalCase'],
},
],
'@typescript-eslint/no-explicit-any': 0,
'@typescript-eslint/no-non-null-assertion': 0,
'@typescript-eslint/no-var-requires': 0,
'global-require': 0,
'no-template-curly-in-string': 0,
},
},
{
files: ['**/__dtslint__/**/*.ts'],
rules: {
'@typescript-eslint/ban-types': 0,
'@typescript-eslint/no-explicit-any': 0,
'@typescript-eslint/no-non-null-assertion': 0,
'@typescript-eslint/no-unused-expressions': 0,
},
},
{
files: ['website/**/*.jsx'],
extends: [
'airbnb',
'plugin:prettier/recommended',
'plugin:import/recommended',
],
parser: '@babel/eslint-parser',
settings: {
react: {
version: 'detect',
},
},
parserOptions: {
requireConfigFile: false,
babelOptions: {
presets: ['@babel/preset-react'],
},
},
rules: {
'import/no-unresolved': noUnresolved,
'global-require': 0,
},
},
],
};
================================================
FILE: .git-blame-ignore-revs
================================================
================================================
FILE: .github/ISSUE_TEMPLATE/bug_report.md
================================================
---
name: '🐛 Report a bug'
about: 'Report a reproducible bug or reproducible regression.'
labels: 'bug report 🦗, needs: triage 🏷, needs: complete repro 🖥️'
---
## Environment
<!--
All necessary environmental info that will help triage this
-->
<!--
Especially include:
-->
- Linaria version:
- Bundler (+ version):
- Node.js version:
- OS:
## Description
<!--
Describe your issue in detail.
Include screenshots if needed.
If this is a regression, let us know.
-->
## Reproducible Demo
<!--
Let us know how to reproduce the issue.
Include a code sample or share a project that reproduces the issue.
Please include you tooling setup eg. webpack config for webpack
Please follow the guidelines for providing a minimal example: https://stackoverflow.com/help/mcve.
-->
================================================
FILE: .github/ISSUE_TEMPLATE/config.yml
================================================
blank_issues_enabled: false
contact_links:
- name: 🤔 Questions and Help
url: https://discord.gg/fAbHe67
about: Reach the community on discord if you need help or have a question.
================================================
FILE: .github/ISSUE_TEMPLATE/enhancement_request.md
================================================
---
name: '💬 Enhancement proposal'
about: Suggest an possible improvement of existing features.
labels: 'enhancement: proposal 💬'
---
## Describe the enhancement
<!-- Describe what you would like to improve -->
## Motivation
<!-- Describe what problem the improvement solves -->
## Possible implementations
<!-- Describe how the improvement could be implemented -->
## Related Issues
<!-- Link related issues here -->
================================================
FILE: .github/ISSUE_TEMPLATE/feature_request.md
================================================
---
name: '💬 Feature proposal'
about: Suggest introduction of a new feature.
labels: 'feature: proposal 💬'
---
## Describe the feature
<!-- Describe what you would like to introduce -->
## Motivation
<!-- Describe what problem the feature solves -->
## Possible implementations
<!-- Describe how the feature could be implemented -->
## Related Issues
<!-- Link related issues here -->
================================================
FILE: .github/PULL_REQUEST_TEMPLATE.md
================================================
<!--
Thanks for submitting a pull request!
Please provide enough information so that others can review your pull request.
Motivation and Test plan are mandatory.
-->
## Motivation
<!--
If pull request address existing issues, link the issues, thats all.
If issue for this soled problem does not exist,
please share your motivation and describe the problem.
We may ask you to open issue to discuss the problem first.
-->
## Summary
<!--
Explain how your implementation works and your thoughts behind the solution.
It will help maintainers to review your PR.
You can skip it if PR is trivial.
-->
## Test plan
<!--
Demonstrate the code is solid.
Example: The exact commands you ran and their output.
Write down steps on how maintainers can test your PR.
-->
================================================
FILE: .github/labels.json
================================================
{
"labels": {
"babel-plugin": {
"name": "babel-plugin",
"description": "",
"colour": "006b75"
},
"bug-report": {
"name": "bug report 🦗",
"description": "Issue is probably a bug, but it needs to be checked",
"colour": "f8c4c4"
},
"bug": {
"name": "bug 🐛",
"description": "Issue is a confirmed bug",
"colour": "ee0701"
},
"bundler-parcel": {
"name": "bundler: parcel 🎁",
"description": "Issue is related to parcel bundler",
"colour": "e5e5e5"
},
"bundler-rollup": {
"name": "bundler: rollup 🗞️",
"description": "Issue is related to rollup bundler",
"colour": "e5e5e5"
},
"bundler-webpack": {
"name": "bundler: webpack 📦",
"description": "Issue is related to webpack bundler",
"colour": "e5e5e5"
},
"cat-documentation": {
"name": "cat: documentation 📖",
"description": "Work focused on writing documentation",
"colour": "f9acca"
},
"cat-extend-support": {
"name": "cat: extend support 🤝",
"description": "Support for a new bundler/platform",
"colour": "f9acca"
},
"cat-extend-syntax": {
"name": "cat: extend syntax ✍",
"description": "Support for a new syntax",
"colour": "f9acca"
},
"cat-improve-publishing": {
"name": "cat: improve publishing 🚢",
"description": "Issues about improvement of publishing libs with Linaria",
"colour": "f9acca"
},
"cat-modules-aliasing": {
"name": "cat: modules aliasing 🔗",
"description": "Issue related to modules aliasing",
"colour": "f9acca"
},
"cat-monorepo": {
"name": "cat: monorepo 🔱",
"description": "Issues related to usage of linaria in monorepo",
"colour": "f9acca"
},
"cat-performance": {
"name": "cat: performance 🚀",
"description": "Issue is related to performance",
"colour": "f9acca"
},
"cat-testing": {
"name": "cat: testing 🛡",
"description": "Issue related to testing components",
"colour": "f9acca"
},
"cat-typings": {
"name": "cat: typings 👮",
"description": "Typescript types related issues",
"colour": "f9acca"
},
"core-team": {
"name": "core team 🧬",
"description": "Issues reserved for the core team",
"colour": "fef2c0"
},
"duplicate": {
"name": "duplicate",
"description": "Issue is a duplicate of another issue",
"colour": "cccccc"
},
"enhancement-approved": {
"name": "enhancement: approved ✅",
"description": "Improvement of the current behaviour that has been approved",
"colour": "1d76db"
},
"enhancement-proposal": {
"name": "enhancement: proposal 💬",
"description": "Improvement of current behaviour that needs to be discussed",
"colour": "1d76db"
},
"enhancement-rejected": {
"name": "enhancement: rejected ❌",
"description": "Improvement of the current behaviour that has been rejected",
"colour": "1d76db"
},
"feature-approved": {
"name": "feature: approved ✅",
"description": "New feature that has been approved",
"colour": "1d3082"
},
"feature-proposal": {
"name": "feature: proposal 💬",
"description": "New feature proposal that needs to be discussed",
"colour": "1d3082"
},
"feature-rejected": {
"name": "feature: rejected ❌",
"description": "New feature that has been rejected",
"colour": "1d3082"
},
"good-first-issue": {
"name": "good first issue 😊",
"description": "It is a good issue for new comers",
"colour": "5319e7"
},
"greenkeeper": {
"name": "greenkeeper",
"description": "",
"colour": "00c775"
},
"hacktoberfest": {
"name": "hacktoberfest 🍺",
"description": "https://hacktoberfest.digitalocean.com/",
"colour": "FF8C00"
},
"needs-complete-repro": {
"name": "needs: complete repro 🖥️",
"description": "Issue need to have complete repro provided",
"colour": "b2ffbb"
},
"needs-help": {
"name": "needs: help 🆘",
"description": "Help is needed",
"colour": "b2ffbb"
},
"needs-investigation": {
"name": "needs: investigation 🔎",
"description": "Issue has to be investigated for reason or solution",
"colour": "b2ffbb"
},
"needs-more-info": {
"name": "needs: more info ℹ",
"description": "Not enough information was provided to work on issue",
"colour": "b2ffbb"
},
"needs-response": {
"name": "needs: response 📩",
"description": "Response from author/commenters is requested",
"colour": "b2ffbb"
},
"needs-to-be-grouped": {
"name": "needs: to be grouped",
"description": "Issue needs to be grouped with other similar issues",
"colour": "b2ffbb"
},
"needs-triage": {
"name": "needs: triage 🏷",
"description": "Issue needs to be checked and prioritized",
"colour": "b2ffbb"
},
"platform-electron": {
"name": "platform: electron 🛠️",
"description": "Issue related to electron platform",
"colour": "00e5e5"
},
"platform-next.js": {
"name": "platform: next.js 🛠️",
"description": "Issue related to next.js",
"colour": "00e5e5"
},
"platform-react": {
"name": "platform: react 🛠️",
"description": "Issue related to react",
"colour": "00e5e5"
},
"platform-ssr": {
"name": "platform: ssr 🛠️",
"description": "Issue related to SSR",
"colour": "00e5e5"
},
"platform-vanilla": {
"name": "platform: vanilla 🛠️",
"description": "Issue related to vanilla css tags",
"colour": "00e5e5"
},
"platform-svelte": {
"name": "platform: svelte 🛠️",
"description": "Issue related to svelte",
"colour": "00e5e5"
},
"priority-critical": {
"name": "priority: critical ☢️",
"description": "Issue is a critical bug that affects most of the users",
"colour": "000000"
},
"priority-high": {
"name": "priority: high ⚠️",
"description": "Issue is important and should be prioritized among others",
"colour": "e093f7"
},
"priority-low": {
"name": "priority: low 📉",
"description": "Something nice to have",
"colour": "ebebeb"
},
"priority-medium": {
"name": "priority: medium 💻",
"description": "Issue is important but not the most important",
"colour": "ffb732"
},
"question": {
"name": "question ❔",
"description": "Question related to the library",
"colour": "f9acca"
},
"status-has-PR": {
"name": "status: has PR 😍",
"description": "Issue has opened PR",
"colour": "feffa5"
},
"status-in-progress": {
"name": "status: in progress 🚧",
"description": "Someone is working on the issue",
"colour": "feffa5"
},
"status-merged": {
"name": "status: merged 🎉",
"description": "Solution was merged",
"colour": "feffa5"
},
"status-up-for-grabs": {
"name": "status: up for grabs 🙏",
"description": "research is done and issue is ready to be grabbed",
"colour": "feffa5"
},
"status-wontfix": {
"name": "status: wontfix ⚰",
"description": "Issue will not be fixed",
"colour": "feffa5"
},
"workaround-exist": {
"name": "workaround exist",
"description": "Workaround for the issue exist",
"colour": "70f488"
},
"skip-labeling": {
"name": "skip autolabeling",
"description": "Use it to disable auto laberer bot for an issue/pr",
"colour": "D9BBF9"
}
},
"issue": {
"bundler-rollup": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/rollup/i"
},
{
"type": "descriptionMatches",
"pattern": "/rollup/i"
}
]
},
"bundler-webpack": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/webpack/i"
},
{
"type": "descriptionMatches",
"pattern": "/webpack/i"
}
]
},
"bundler-parcel": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/parcel/i"
},
{
"type": "descriptionMatches",
"pattern": "/parcel/i"
}
]
},
"platform-svelte": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/svelte/i"
},
{
"type": "descriptionMatches",
"pattern": "/svelte/i"
}
]
},
"platform-next.js": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/next(\\.){0,1}js/i"
},
{
"type": "descriptionMatches",
"pattern": "/next(\\.){0,1}js/i"
}
]
},
"platform-ssr": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/(ssr)|(server)/i"
},
{
"type": "descriptionMatches",
"pattern": "/(ssr)|(server)/i"
}
]
},
"platform-electron": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/electron/i"
},
{
"type": "descriptionMatches",
"pattern": "/electron/i"
}
]
},
"cat-performance": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/(slow)|(build[\\s\\S]*time)|(time[\\s\\S]*build)(performance)/i"
},
{
"type": "descriptionMatches",
"pattern": "/(slow)|(build[\\s\\S]*time)|(time[\\s\\S]*build)(performance)/i"
}
]
},
"cat-testing": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/(test)|(jest)/i"
}
]
},
"cat-monorepo": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/(monorepo)|(workspace)|(lerna)/i"
},
{
"type": "descriptionMatches",
"pattern": "/(monorepo)|(workspace)|(lerna)/i"
}
]
},
"cat-modules-aliasing": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/(alias)|(namemapper)/i"
},
{
"type": "descriptionMatches",
"pattern": "/(alias)|(namemapper)/i"
}
]
},
"cat-typings": {
"requires": 1,
"conditions": [
{
"type": "titleMatches",
"pattern": "/typescript/i"
},
{
"type": "titleMatches",
"pattern": "/TS/"
}
]
}
},
"issue_fallback": {
"fallbackActivationValue": 2,
"labels": [
"needs-triage"
]
},
"pr": {},
"skip_labeling": "skip-labeling"
}
================================================
FILE: .github/workflows/check.yml
================================================
name: Node.js CI
on:
push:
branches: [ master ]
pull_request:
branches: [ master ]
jobs:
build:
runs-on: ${{ matrix.os }}
env:
TURBO_TOKEN: ${{ secrets.TURBO_TOKEN }}
TURBO_TEAM: ${{ secrets.TURBO_TEAM }}
strategy:
fail-fast: false
matrix:
os: [ubuntu-latest]
node-version: [20.x, 22.x]
include:
- os: windows-latest
node-version: 20.x
steps:
- uses: actions/checkout@v4
- uses: pnpm/action-setup@v3
with:
version: 9
run_install: false
- name: Get pnpm store directory
id: pnpm-cache
shell: bash
run: |
echo "STORE_PATH=$(pnpm store path)" >> $GITHUB_OUTPUT
- name: Setup pnpm cache
uses: actions/cache@v4
with:
path: ${{ steps.pnpm-cache.outputs.STORE_PATH }}
key: ${{ runner.os }}-pnpm-store-${{ hashFiles('./pnpm-lock.yaml') }}
restore-keys: |
${{ runner.os }}-pnpm-store-
- name: Use Node.js ${{ matrix.node-version }}
uses: actions/setup-node@v4
with:
node-version: ${{ matrix.node-version }}
- name: Install and prepare
run: pnpm install --frozen-lockfile --strict-peer-dependencies
- name: ESLint
if: matrix.os == 'ubuntu-latest' && matrix.node-version == '20.x'
run: pnpm lint
- name: TSLint
if: matrix.os == 'ubuntu-latest' && matrix.node-version == '20.x'
run: pnpm turbo run test:dts
- name: Tests
run: pnpm turbo run test
================================================
FILE: .github/workflows/main.yml
================================================
name: labeler
on:
issues:
types: [opened, edited, reopened]
pull_request:
types: [opened, edited, reopened, ready_for_review, synchronize]
jobs:
labeler:
runs-on: ubuntu-latest
name: label issues and pull requests
steps:
- name: check-out-repository
uses: actions/checkout@v4
- name: labeler
uses: jayu/super-labeler-action@develop
env:
ACTIONS_STEP_DEBUG: ${{ secrets.ACTIONS_STEP_DEBUG }}
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
================================================
FILE: .github/workflows/release.yml
================================================
name: Release
on:
push:
branches:
- master
concurrency: ${{ github.workflow }}-${{ github.ref }}
permissions:
contents: write
pull-requests: write
id-token: write
jobs:
release:
name: Release
runs-on: ubuntu-latest
env:
TURBO_TOKEN: ${{ secrets.TURBO_TOKEN }}
TURBO_TEAM: ${{ secrets.TURBO_TEAM }}
steps:
- name: Checkout Repo
uses: actions/checkout@v4
- uses: pnpm/action-setup@v3
with:
version: 9
run_install: false
- name: Get pnpm store directory
id: pnpm-cache
shell: bash
run: |
echo "STORE_PATH=$(pnpm store path)" >> $GITHUB_OUTPUT
- name: Setup pnpm cache
uses: actions/cache@v4
with:
path: ${{ steps.pnpm-cache.outputs.STORE_PATH }}
key: ${{ runner.os }}-pnpm-store-${{ hashFiles('./pnpm-lock.yaml') }}
restore-keys: |
${{ runner.os }}-pnpm-store-
- name: Setup Node.js 20.x
uses: actions/setup-node@v4
with:
node-version: 20.x
registry-url: 'https://registry.npmjs.org'
- name: Upgrade npm for trusted publishing (OIDC)
run: npm i -g npm@11.5.1
- name: Install and prepare
run: pnpm install --frozen-lockfile --strict-peer-dependencies
- name: Create Release Pull Request or Publish to npm
id: changesets
uses: changesets/action@v1
with:
publish: pnpm run release
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
================================================
FILE: .github/workflows/site-deploy.yml
================================================
name: Build and Deploy
on:
push:
branches:
- master
jobs:
build-and-deploy:
runs-on: ubuntu-latest
env:
TURBO_TOKEN: ${{ secrets.TURBO_TOKEN }}
TURBO_TEAM: ${{ secrets.TURBO_TEAM }}
steps:
- uses: actions/checkout@v4
- uses: pnpm/action-setup@v3
with:
version: 9
run_install: false
- name: Get pnpm store directory
id: pnpm-cache
shell: bash
run: |
echo "STORE_PATH=$(pnpm store path)" >> $GITHUB_OUTPUT
- name: Setup pnpm cache
uses: actions/cache@v4
with:
path: ${{ steps.pnpm-cache.outputs.STORE_PATH }}
key: ${{ runner.os }}-pnpm-store-${{ hashFiles('./pnpm-lock.yaml') }}
restore-keys: |
${{ runner.os }}-pnpm-store-
- name: Use Node.js 20.x
uses: actions/setup-node@v4
with:
node-version: 20.x
- name: Install and prepare
run: pnpm install --frozen-lockfile --strict-peer-dependencies
- name: Deploy 🚀
uses: JamesIves/github-pages-deploy-action@3.7.1
with:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
BRANCH: gh-pages
FOLDER: website
CLEAN: true
================================================
FILE: .gitignore
================================================
### OS Junk ###
.DS_Store
*~
.history
### Node ###
# Logs
logs
*.log
npm-debug.log*
yarn-debug.log*
yarn-error.log*
# Runtime data
pids
*.pid
*.seed
*.pid.lock
# Directory for instrumented libs generated by jscoverage/JSCover
lib-cov
# Coverage directory used by tools like istanbul
coverage
# nyc test coverage
.nyc_output
# Grunt intermediate storage (http://gruntjs.com/creating-plugins#storing-task-files)
.grunt
# Bower dependency directory (https://bower.io/)
bower_components
# node-waf configuration
.lock-wscript
# Compiled binary addons (http://nodejs.org/api/addons.html)
build/Release
# Dependency directories
node_modules/
jspm_packages/
# Optional npm cache directory
.npm
# Turborepo cache directory
.turbo
# Optional eslint cache
.eslintcache
# Optional REPL history
.node_repl_history
# Output of 'npm pack'
*.tgz
# Yarn Integrity file
.yarn-integrity
# dotenv environment variables file
.env
# generated files
lib/
esm/
types/
dist/
build/
tsconfig.tsbuildinfo
.linaria-cache
.wyw-cache
# debug
*.debug.ts
**/linaria-debug
**/wyw-debug
================================================
FILE: .npmrc
================================================
lockfile = true
================================================
FILE: .prettierrc
================================================
{
"endOfLine": "auto",
"trailingComma": "es5",
"singleQuote": true
}
================================================
FILE: .syncpackrc.js
================================================
module.exports = {
dependencyTypes: ['dev', 'overrides', 'pnpmOverrides', 'prod', 'resolutions'],
filter: '.',
indent: ' ',
semverGroups: [],
semverRange: '',
sortAz: [
'contributors',
'dependencies',
'devDependencies',
'keywords',
'peerDependencies',
'resolutions',
'scripts',
],
// https://github.com/keithamus/sort-package-json/blob/master/defaultRules.md
sortFirst: [
'$schema',
'name',
'displayName',
'version',
'private',
'description',
'categories',
'keywords',
'homepage',
'bugs',
'repository',
'funding',
'license',
'qna',
'author',
'maintainers',
'contributors',
'publisher',
'sideEffects',
'type',
'imports',
'exports',
'main',
'svelte',
'umd:main',
'jsdelivr',
'unpkg',
'module',
'source',
'jsnext:main',
'browser',
'react-native',
'types',
'typesVersions',
'typings',
'style',
'example',
'examplestyle',
'assets',
'bin',
'man',
'directories',
'files',
'workspaces',
'binary',
'wyw-in-js',
'scripts',
'betterScripts',
'contributes',
'activationEvents',
'husky',
'simple-git-hooks',
'pre-commit',
'commitlint',
'lint-staged',
'config',
'nodemonConfig',
'browserify',
'babel',
'browserslist',
'xo',
'prettier',
'eslintConfig',
'eslintIgnore',
'npmpackagejsonlint',
'release',
'remarkConfig',
'stylelint',
'ava',
'jest',
'mocha',
'nyc',
'tap',
'resolutions',
'dependencies',
'devDependencies',
'dependenciesMeta',
'peerDependencies',
'peerDependenciesMeta',
'optionalDependencies',
'bundledDependencies',
'bundleDependencies',
'extensionPack',
'extensionDependencies',
'flat',
'packageManager',
'engines',
'engineStrict',
'volta',
'languageName',
'os',
'cpu',
'preferGlobal',
'publishConfig',
'icon',
'badges',
'galleryBanner',
'preview',
'markdown',
'tsup',
],
source: [],
versionGroups: [
{
dependencies: [
'@types/enhanced-resolve',
'css-loader',
'enhanced-resolve',
'mini-css-extract-plugin',
'webpack',
],
packages: ['@linaria/webpack4-loader', 'webpack4-example'],
},
],
workspace: true,
};
================================================
FILE: .vscode/settings.json
================================================
{
"typescript.tsdk": "website/node_modules/typescript/lib"
}
================================================
FILE: CODE_OF_CONDUCT.md
================================================
# Contributor Covenant Code of Conduct
## Our Pledge
In the interest of fostering an open and welcoming environment, we as
contributors and maintainers pledge to making participation in our project and
our community a harassment-free experience for everyone, regardless of age, body
size, disability, ethnicity, gender identity and expression, level of experience,
nationality, personal appearance, race, religion, or sexual identity and
orientation.
## Our Standards
Examples of behavior that contributes to creating a positive environment
include:
* Using welcoming and inclusive language
* Being respectful of differing viewpoints and experiences
* Gracefully accepting constructive criticism
* Focusing on what is best for the community
* Showing empathy towards other community members
Examples of unacceptable behavior by participants include:
* The use of sexualized language or imagery and unwelcome sexual attention or
advances
* Trolling, insulting/derogatory comments, and personal or political attacks
* Public or private harassment
* Publishing others' private information, such as a physical or electronic
address, without explicit permission
* Other conduct which could reasonably be considered inappropriate in a
professional setting
## Our Responsibilities
Project maintainers are responsible for clarifying the standards of acceptable
behavior and are expected to take appropriate and fair corrective action in
response to any instances of unacceptable behavior.
Project maintainers have the right and responsibility to remove, edit, or
reject comments, commits, code, wiki edits, issues, and other contributions
that are not aligned to this Code of Conduct, or to ban temporarily or
permanently any contributor for other behaviors that they deem inappropriate,
threatening, offensive, or harmful.
## Scope
This Code of Conduct applies both within project spaces and in public spaces
when an individual is representing the project or its community. Examples of
representing a project or community include using an official project e-mail
address, posting via an official social media account, or acting as an appointed
representative at an online or offline event. Representation of a project may be
further defined and clarified by project maintainers.
## Enforcement
Instances of abusive, harassing, or otherwise unacceptable behavior may be
reported by contacting the project team at [oss@callstack.io](mailto:oss@callstack.io). All
complaints will be reviewed and investigated and will result in a response that
is deemed necessary and appropriate to the circumstances. The project team is
obligated to maintain confidentiality with regard to the reporter of an incident.
Further details of specific enforcement policies may be posted separately.
Project maintainers who do not follow or enforce the Code of Conduct in good
faith may face temporary or permanent repercussions as determined by other
members of the project's leadership.
## Attribution
This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4,
available at https://www.contributor-covenant.org/version/1/4/code-of-conduct/
[homepage]: https://www.contributor-covenant.org
================================================
FILE: CONTRIBUTING.md
================================================
# Contributing to Linaria
## [Code of Conduct](/CODE_OF_CONDUCT.md)
We want this community to be friendly and respectful to each other. Please read [the full text](/CODE_OF_CONDUCT.md) so that you can understand what actions will and will not be tolerated.
## Our Development Process
The core team works directly on GitHub and all work is public.
### Development workflow
> **Working on your first pull request?** You can learn how from this *free* series: [How to Contribute to an Open Source Project on GitHub](https://egghead.io/series/how-to-contribute-to-an-open-source-project-on-github).
1. Fork the repo and create your branch from `master` (a guide on [how to fork a repository](https://help.github.com/articles/fork-a-repo/)).
1. Linaria uses [Pnpm](https://pnpm.io) for running development scripts. If you haven't already done so, please [install Pnpm](https://pnpm.io/installation).
1. Run `pnpm bootstrap` to setup the development environment.
1. When working on the code, you can use the watch mode to watch and compiles changed files:
```sh
pnpm watch
```
1. If you've added code that should be tested, add tests.
1. You can test the changes you are making in our website located under the `website/` folder in the repo.
1. If you've changed APIs, remember to update the documentation under `docs/`.
### Working on the website
If you are making changes to the website, test the website folder and run the server to check if your changes are being displayed accurately. To run the development server with live reloading, run:
```sh
pnpm website start
```
### Commit message convention
We follow the [conventional commits specification](https://www.conventionalcommits.org/en) for our commit messages:
* `fix`: bug fixes, e.g. fix wrong classname generated by babel plugin.
* `feat`: new features, e.g. add support for a config file.
* `refactor`: code refactor, e.g. split the babel plugin into multiple visitors.
* `docs`: changes into documentation, e.g. add usage example for styled tag.
* `test`: adding or updating tests, eg unit, snapshot testing.
* `chore`: tooling changes, e.g. change the eslint config.
* `BREAKING CHANGE`: for changes that break existing usage, e.g. change the API or behaviour.
Our pre-commit hooks verify that your commit message matches this format when committing. If you are working on some in progress commits and don't care about the pre-commit hook, pass the `--no-verify` (`-n`) flag to git when committing (e.g. `git commit -n -m "wip"`).
### Linting and tests
We use `eslint` with `prettier` for linting and formatting the code, and `jest` for testing. Our pre-commit hooks verify that the linter and tests pass when commiting. You can also run the following commands manually:
* `pnpm typecheck`: run tests for typescript definitions.
* `pnpm lint`: lint files with eslint and prettier.
* `pnpm test`: run unit tests with jest.
### Sending a pull request
When you're sending a pull request:
* Prefer small pull requests focused on one change.
* Verify that `eslint` and all tests are passing.
* Run `pnpm changeset` to generate a changeset.
* Preview the documentation to make sure it looks good.
* Follow the pull request template when opening a pull request.
## How to try a development build of Linaria in a project
To link `linaria` on the command line to local copy in a development build:
```sh
cd /path/to/your/linaria_clone/
yarn
yarn link
cd /path/to/test_project/
yarn link linaria
```
To unlink it:
```sh
yarn unlink linaria
```
### Debugging and deep dive into babel plugin
To understand what is actually going in under the hood of Linaria we recommend to first read the top-level [How it works](/docs/HOW_IT_WORKS.md).
Then you can run Linaria in debug mode for a specific file from you project and see step-by-step logs informing what is happening.
```sh
DEBUG=linaria* LINARIA_LOG=debug npx babel -d dist PATH_TO_COMPONENT
```
> In example we use `npx` to run babel, but you can also put this script into package.json with removed `npx` to run it.
You will see how the babel part of Linaria work, result JS file will be stored in `dist` directory. You will not see the resulting CSS file, because this is the role of next layer - bundlers (CSS content is stored in babel metadata to be consumed by bundler).
### Publishing a release
We use [release-it](https://github.com/webpro/release-it) to automate our release. If you have publish access to the NPM package, run the following from the master branch to publish a new release:
```sh
yarn release
```
NOTE: You must have a `GITHUB_TOKEN` environment variable available. You can create a GitHub access token with the "repo" access [here](https://github.com/settings/tokens).
## Reporting New Issues
The best way to get your bug fixed is to provide a reduced test case. Please provide a public repository with a runnable example.
## How to Get in Touch
* Callstack Open Source Discord - [#linaria](https://discord.gg/zwR2Cdh).
## Code Conventions
We use Prettier with ESLint integration for linting and formatting. To fix any auto-fixable lint or matting errors, run:
```sh
pnpm lint -- --fix
```
## License
By contributing to Linaria, you agree that your contributions will be licensed under its MIT license.
================================================
FILE: LICENSE
================================================
MIT License
Copyright (c) 2017 Callstack
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
================================================
FILE: README.md
================================================
<a href="https://www.callstack.com/open-source" align="center">
<img alt="Linaria" src="https://github.com/user-attachments/assets/746f7b2a-8136-47a7-b79b-e790c1974e40">
</a>
<p align="center">
Zero-runtime CSS in JS library.
</p>
---
[![Build Status][build-badge]][build]
[![Code Coverage][coverage-badge]][coverage]
[![Version][version-badge]][package]
[![MIT License][license-badge]][license]
[![All Contributors][all-contributors-badge]](#contributors)
[![PRs Welcome][prs-welcome-badge]][prs-welcome]
[![Chat][chat-badge]][chat]
[![Code of Conduct][coc-badge]][coc]
[![Greenkeeper][greenkeeper-badge]][greenkeeper]
[![Sponsored by Callstack][callstack-badge]][callstack]
[![tweet][tweet-badge]][tweet]
## Features
- Write CSS in JS, but with **zero runtime**, CSS is extracted to CSS files during build
- Familiar **CSS syntax** with Sass like nesting
- Use **dynamic prop based styles** with the React bindings, uses CSS variables behind the scenes
- Easily find where the style was defined with **CSS sourcemaps**
- **Lint your CSS** in JS with [stylelint](https://github.com/stylelint/stylelint)
- Use **JavaScript for logic**, no CSS preprocessor needed
- Optionally use any **CSS preprocessor** such as Sass or PostCSS
- Supports **atomic styles** with `@linaria/atomic`
**[Why use Linaria](/docs/BENEFITS.md)**
**[Learn how Airbnb improved both developer experience and web performance with Linaria](https://medium.com/airbnb-engineering/airbnbs-trip-to-linaria-dc169230bd12)**
## Installation
```sh
npm install @linaria/core @linaria/react @wyw-in-js/babel-preset
```
or
```sh
yarn add @linaria/core @linaria/react @wyw-in-js/babel-preset
```
## Setup
Linaria is now built on top of [wyw-in-js.dev](https://wyw-in-js.dev/). It supports various bundlers to extract the CSS at build time. To configure your bundler, check the following guides on the wyw-in-js.dev site:
- [webpack](https://wyw-in-js.dev/bundlers/webpack)
- [esbuild](https://wyw-in-js.dev/bundlers/esbuild)
- [Rollup](https://wyw-in-js.dev/bundlers/rollup)
- [Vite](https://wyw-in-js.dev/bundlers/vite)
- [Svelte](https://wyw-in-js.dev/bundlers/svelte)
See [Configuration](https://wyw-in-js.dev/configuration) to customize how Linaria processes your files.
## Stability
Linaria relies on WyW (`@wyw-in-js/*`) to evaluate your modules at build time and extract CSS. If you hit issues like slow builds, invalidation storms, or unexpected code being executed during the build, it’s usually related to the WyW evaluation model and how your modules are structured.
Linaria 7 requires Node.js `>=20` (WyW 1.x enforces this via `engines`).
See https://wyw-in-js.dev/stability for practical guidance and common pitfalls.
## Syntax
Linaria can be used with any framework, with additional helpers for React. The basic syntax looks like this:
```js
import { css } from '@linaria/core';
import { modularScale, hiDPI } from 'polished';
import fonts from './fonts';
// Write your styles in `css` tag
const header = css`
text-transform: uppercase;
font-family: ${fonts.heading};
font-size: ${modularScale(2)};
${hiDPI(1.5)} {
font-size: ${modularScale(2.5)};
}
`;
// Then use it as a class name
<h1 className={header}>Hello world</h1>;
```
You can use imported variables and functions for logic inside the CSS code. They will be evaluated at build time.
If you're using [React](https://reactjs.org/), you can use the `styled` helper, which makes it easy to write React components with dynamic styles with a styled-component like syntax:
```js
import { styled } from '@linaria/react';
import { families, sizes } from './fonts';
// Write your styles in `styled` tag
const Title = styled.h1`
font-family: ${families.serif};
`;
const Container = styled.div`
font-size: ${sizes.medium}px;
color: ${props => props.color};
border: 1px solid red;
&:hover {
border-color: blue;
}
${Title} {
margin-bottom: 24px;
}
`;
// Then use the resulting component
<Container color="#333">
<Title>Hello world</Title>
</Container>;
```
Dynamic styles will be applied using CSS custom properties (aka CSS variables) and don't require any runtime.
See [Basics](/docs/BASICS.md) for a detailed information about the syntax.
## Demo
[](https://codesandbox.io/s/linaria-react-vite-ts-qyj5xd)
## Documentation
- [Basics](/docs/BASICS.md)
- [API and usage](/docs/API.md)
- [Client APIs](/docs/API.md#client-apis)
- [Server APIs](/docs/API.md#server-apis)
- [Configuration](/docs/CONFIGURATION.md)
- [Dynamic styles with `css` tag](/docs/DYNAMIC_STYLES.md)
- [Theming](/docs/THEMING.md)
- [Critical CSS extraction](/docs/CRITICAL_CSS.md)
- [Bundlers integration](/docs/BUNDLERS_INTEGRATION.md)
- [webpack](/docs/BUNDLERS_INTEGRATION.md#webpack)
- [Rollup](/docs/BUNDLERS_INTEGRATION.md#rollup)
- [CLI](/docs/CLI.md)
- [Linting](/docs/LINTING.md)
- [How it works](/docs/HOW_IT_WORKS.md)
- [Example](/website)
## Contributing
We appreciate any support in library development!
Take a look on [Contributing](CONTRIBUTING.md) docs to check how you can run Linaria in development mode.
## Trade-offs
- No IE11 support when using dynamic styles in components with `styled`, since it uses CSS custom properties
- Dynamic styles are not supported with `css` tag. See [Dynamic styles with `css` tag](/docs/DYNAMIC_STYLES.md) for alternative approaches.
- Modules used in the CSS rules cannot have side-effects.
For example:
```js
import { css } from '@linaria/core';
import colors from './colors';
const title = css`
color: ${colors.text};
`;
```
Here, there should be no side-effects in the `colors.js` file, or any file it imports. We recommend to move helpers and shared configuration to files without any side-effects.
## Interoperability with other CSS-in-JS libraries
Linaria can work together with other CSS-in-JS libraries out-of-the-box. However, if you want to use styled components from Linaria as selectors in `styled-components`/`emotion`, you need to use [@linaria/interop](/packages/interop/README.md)
## Editor Plugins
### VSCode
- Syntax Highlighting - [language-babel](https://marketplace.visualstudio.com/items?itemName=mgmcdermott.vscode-language-babel)
- Autocompletion - [vscode-styled-components](https://marketplace.visualstudio.com/items?itemName=styled-components.vscode-styled-components)
- Linting - [stylelint](https://marketplace.visualstudio.com/items?itemName=stylelint.vscode-stylelint)
### Atom
- Syntax Highlighting and Autocompletion - [language-babel](https://atom.io/packages/language-babel)
### Webstorm
- Syntax Highlighting & Autocompletion - [webstorm-styled-components](https://github.com/styled-components/webstorm-styled-components)
### Sublime Text
- Syntax Highlighting & Autocompletion - [Naomi](https://packagecontrol.io/packages/Naomi), [JSCustom](https://packagecontrol.io/packages/JSCustom) (refer to document on how to turn on Styled Component syntax)
- Linting - [SublimeLinter-stylelint](https://packagecontrol.io/packages/SublimeLinter-stylelint), [LSP Stylelint](https://packagecontrol.io/packages/LSP-stylelint)
## Recommended Libraries
- [gatsby-plugin-linaria](https://github.com/cometkim/gatsby-plugin-linaria) – Gatsby plugin that sets up Babel and webpack configuration for Linaria.
- [polished.js](https://polished.js.org/) - A lightweight toolset for writing styles in JavaScript.
- [craco-linaria](https://github.com/jedmao/craco-linaria) - A [Craco](https://www.npmjs.com/package/@craco/craco) plugin that allows you to use Linaria [without ejecting](https://create-react-app.dev/docs/alternatives-to-ejecting) from a [CRA](https://create-react-app.dev/).
## Inspiration
- [glam](https://github.com/threepointone/glam)
- [styled-components](https://github.com/styled-components/styled-components)
- [css-literal-loader](https://github.com/4Catalyzer/css-literal-loader)
## Acknowledgements
This project wouldn't have been possible without the following libraries or the people behind them.
- [babel](https://babeljs.io/)
- [stylis.js](https://github.com/thysultan/stylis.js)
Special thanks to [@kentcdodds](https://github.com/kentcdodds) for his babel plugin and [@threepointone](https://github.com/threepointone) for his suggestions and encouragement.
## Made with ❤️ at Callstack
Linaria is an open source project and will always remain free to use. If you think it's cool, please star it 🌟. [Callstack](https://callstack.com) is a group of React and React Native geeks, contact us at [hello@callstack.com](mailto:hello@callstack.com) if you need any help with these or just want to say hi!
Like the project? ⚛️ [Join the team](https://callstack.com/careers/?utm_campaign=Senior_RN&utm_source=github&utm_medium=readme) who does amazing stuff for clients and drives React Native Open Source! 🔥
## Sponsors
<p>
<a href="https://www.callstack.com"><img alt="{callstack}" src="website/assets/callstack-logo.svg" width="250"></a>
</p>
<p>
<a href="https://www.servers.com"><img alt="Servers.com" src="website/assets/serverscom-logo-black.svg" width="250"></a>
</p>
## Contributors
Thanks goes to these wonderful people ([emoji key](https://github.com/kentcdodds/all-contributors#emoji-key)):
<!-- ALL-CONTRIBUTORS-LIST:START - Do not remove or modify this section -->
<!-- prettier-ignore-start -->
<!-- markdownlint-disable -->
<table>
<tbody>
<tr>
<td align="center"><a href="https://twitter.com/_zamotany"><img src="https://avatars2.githubusercontent.com/u/17573635?v=4?s=100" width="100px;" alt="Paweł Trysła"/><br /><sub><b>Paweł Trysła</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=zamotany" title="Code">💻</a> <a href="https://github.com/callstack/linaria/commits?author=zamotany" title="Documentation">📖</a> <a href="#ideas-zamotany" title="Ideas, Planning, & Feedback">🤔</a></td>
<td align="center"><a href="https://medium.com/@satya164"><img src="https://avatars2.githubusercontent.com/u/1174278?v=4?s=100" width="100px;" alt="Satyajit Sahoo"/><br /><sub><b>Satyajit Sahoo</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=satya164" title="Code">💻</a> <a href="https://github.com/callstack/linaria/commits?author=satya164" title="Documentation">📖</a> <a href="#ideas-satya164" title="Ideas, Planning, & Feedback">🤔</a></td>
<td align="center"><a href="https://github.com/thymikee"><img src="https://avatars2.githubusercontent.com/u/5106466?v=4?s=100" width="100px;" alt="Michał Pierzchała"/><br /><sub><b>Michał Pierzchała</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=thymikee" title="Code">💻</a> <a href="https://github.com/callstack/linaria/commits?author=thymikee" title="Documentation">📖</a> <a href="#ideas-thymikee" title="Ideas, Planning, & Feedback">🤔</a></td>
<td align="center"><a href="https://lcs.sh"><img src="https://avatars1.githubusercontent.com/u/1909761?v=4?s=100" width="100px;" alt="Lucas"/><br /><sub><b>Lucas</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=AgtLucas" title="Documentation">📖</a></td>
<td align="center"><a href="https://github.com/pronevich"><img src="https://avatars0.githubusercontent.com/u/680439?v=4?s=100" width="100px;" alt="Alexey Pronevich"/><br /><sub><b>Alexey Pronevich</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=pronevich" title="Documentation">📖</a></td>
<td align="center"><a href="https://github.com/wojteg1337"><img src="https://avatars3.githubusercontent.com/u/18573330?v=4?s=100" width="100px;" alt="Wojtek Szafraniec"/><br /><sub><b>Wojtek Szafraniec</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=wojteg1337" title="Code">💻</a></td>
<td align="center"><a href="http://twitter.com/anber_dev"><img src="https://avatars3.githubusercontent.com/u/148258?v=4?s=100" width="100px;" alt="Anton Evzhakov"/><br /><sub><b>Anton Evzhakov</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Anber" title="Code">💻</a> <a href="#ideas-Anber" title="Ideas, Planning, & Feedback">🤔</a> <a href="https://github.com/callstack/linaria/commits?author=Anber" title="Documentation">📖</a></td>
</tr>
<tr>
<td align="center"><a href="https://twitter.com/tushkiz"><img src="https://avatars1.githubusercontent.com/u/1854763?v=4?s=100" width="100px;" alt="Tushar Sonawane"/><br /><sub><b>Tushar Sonawane</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Tushkiz" title="Documentation">📖</a> <a href="#example-Tushkiz" title="Examples">💡</a></td>
<td align="center"><a href="http://twitter.com/ferrannp"><img src="https://avatars2.githubusercontent.com/u/774577?v=4?s=100" width="100px;" alt="Ferran Negre"/><br /><sub><b>Ferran Negre</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=ferrannp" title="Documentation">📖</a></td>
<td align="center"><a href="https://jukben.cz"><img src="https://avatars3.githubusercontent.com/u/8135252?v=4?s=100" width="100px;" alt="Jakub Beneš"/><br /><sub><b>Jakub Beneš</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=jukben" title="Code">💻</a> <a href="https://github.com/callstack/linaria/commits?author=jukben" title="Documentation">📖</a></td>
<td align="center"><a href="https://github.com/oBusk"><img src="https://avatars2.githubusercontent.com/u/13413409?v=4?s=100" width="100px;" alt="Oscar Busk"/><br /><sub><b>Oscar Busk</b></sub></a><br /><a href="https://github.com/callstack/linaria/issues?q=author%3AoBusk" title="Bug reports">🐛</a> <a href="https://github.com/callstack/linaria/commits?author=oBusk" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/Trancever"><img src="https://avatars3.githubusercontent.com/u/18584155?v=4?s=100" width="100px;" alt="Dawid"/><br /><sub><b>Dawid</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Trancever" title="Code">💻</a> <a href="https://github.com/callstack/linaria/commits?author=Trancever" title="Documentation">📖</a></td>
<td align="center"><a href="https://twitter.com/esemesek"><img src="https://avatars2.githubusercontent.com/u/9092510?v=4?s=100" width="100px;" alt="Kacper Wiszczuk"/><br /><sub><b>Kacper Wiszczuk</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Esemesek" title="Code">💻</a> <a href="https://github.com/callstack/linaria/commits?author=Esemesek" title="Documentation">📖</a></td>
<td align="center"><a href="https://github.com/que-etc"><img src="https://avatars3.githubusercontent.com/u/2401842?v=4?s=100" width="100px;" alt="Denis Rul"/><br /><sub><b>Denis Rul</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=que-etc" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://github.com/johanholmerin"><img src="https://avatars0.githubusercontent.com/u/7433263?v=4?s=100" width="100px;" alt="Johan Holmerin"/><br /><sub><b>Johan Holmerin</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=johanholmerin" title="Code">💻</a> <a href="https://github.com/callstack/linaria/commits?author=johanholmerin" title="Documentation">📖</a></td>
<td align="center"><a href="https://www.giladpeleg.com/"><img src="https://avatars0.githubusercontent.com/u/4533329?v=4?s=100" width="100px;" alt="Gilad Peleg"/><br /><sub><b>Gilad Peleg</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=pgilad" title="Documentation">📖</a></td>
<td align="center"><a href="http://giuseppe.pizza"><img src="https://avatars3.githubusercontent.com/u/711311?v=4?s=100" width="100px;" alt="Giuseppe"/><br /><sub><b>Giuseppe</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=giuseppeg" title="Code">💻</a></td>
<td align="center"><a href="https://silvenon.com"><img src="https://avatars2.githubusercontent.com/u/471278?v=4?s=100" width="100px;" alt="Matija Marohnić"/><br /><sub><b>Matija Marohnić</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=silvenon" title="Code">💻</a> <a href="https://github.com/callstack/linaria/commits?author=silvenon" title="Documentation">📖</a></td>
<td align="center"><a href="http://schultstefan.de"><img src="https://avatars2.githubusercontent.com/u/120432?v=4?s=100" width="100px;" alt="Stefan Schult"/><br /><sub><b>Stefan Schult</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Schubidu" title="Code">💻</a></td>
<td align="center"><a href="http://www.coding-tech.be"><img src="https://avatars3.githubusercontent.com/u/1120926?v=4?s=100" width="100px;" alt="Ward Peeters"/><br /><sub><b>Ward Peeters</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=wardpeet" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/radoslaw-medryk"><img src="https://avatars0.githubusercontent.com/u/43260833?v=4?s=100" width="100px;" alt="radoslaw-medryk"/><br /><sub><b>radoslaw-medryk</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=radoslaw-medryk" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="http://dr2009.com"><img src="https://avatars1.githubusercontent.com/u/8262650?v=4?s=100" width="100px;" alt="杨兴洲"/><br /><sub><b>杨兴洲</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=dr2009" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/hinok"><img src="https://avatars2.githubusercontent.com/u/1313605?v=4?s=100" width="100px;" alt="Dawid Karabin"/><br /><sub><b>Dawid Karabin</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=hinok" title="Documentation">📖</a></td>
<td align="center"><a href="https://github.com/chrisabrams"><img src="https://avatars1.githubusercontent.com/u/527740?s=460&v=4?s=100" width="100px;" alt="Chris Abrams"/><br /><sub><b>Chris Abrams</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=chrisabrams" title="Code">💻</a> <a href="https://github.com/callstack/linaria/commits?author=chrisabrams" title="Documentation">📖</a> <a href="#ideas-chrisabrams" title="Ideas, Planning, & Feedback">🤔</a></td>
<td align="center"><a href="http://hyperlab.se"><img src="https://avatars0.githubusercontent.com/u/329184?v=4?s=100" width="100px;" alt="Jayphen"/><br /><sub><b>Jayphen</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Jayphen" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/bolasblack"><img src="https://avatars0.githubusercontent.com/u/382011?v=4?s=100" width="100px;" alt="c4605"/><br /><sub><b>c4605</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=bolasblack" title="Code">💻</a></td>
<td align="center"><a href="https://koba04.com/"><img src="https://avatars2.githubusercontent.com/u/250407?v=4?s=100" width="100px;" alt="Toru Kobayashi"/><br /><sub><b>Toru Kobayashi</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=koba04" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/jayu"><img src="https://avatars.githubusercontent.com/u/11561585?v=4?s=100" width="100px;" alt="Jakub Mazurek"/><br /><sub><b>Jakub Mazurek</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=jayu" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="http://subsecond.dev/"><img src="https://avatars.githubusercontent.com/u/1518604?v=4?s=100" width="100px;" alt="Joshua Nelson"/><br /><sub><b>Joshua Nelson</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=jpnelson" title="Code">💻</a> <a href="#ideas-jpnelson" title="Ideas, Planning, & Feedback">🤔</a> <a href="https://github.com/callstack/linaria/commits?author=jpnelson" title="Documentation">📖</a></td>
<td align="center"><a href="https://twitter.com/TMaszko"><img src="https://avatars.githubusercontent.com/u/16257732?v=4?s=100" width="100px;" alt="Tomasz Krzyżowski"/><br /><sub><b>Tomasz Krzyżowski</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=TMaszko" title="Code">💻</a></td>
<td align="center"><a href="https://www.slash-m.com/"><img src="https://avatars.githubusercontent.com/u/1476435?v=4?s=100" width="100px;" alt="Martin Schulze"/><br /><sub><b>Martin Schulze</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=dfrkp" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/wmzy"><img src="https://avatars.githubusercontent.com/u/5526525?v=4?s=100" width="100px;" alt="wmzy"/><br /><sub><b>wmzy</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=wmzy" title="Code">💻</a></td>
<td align="center"><a href="https://blog.cometkim.kr/"><img src="https://avatars.githubusercontent.com/u/9696352?v=4?s=100" width="100px;" alt="Hyeseong Kim"/><br /><sub><b>Hyeseong Kim</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=cometkim" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/Hotell"><img src="https://avatars.githubusercontent.com/u/1223799?v=4?s=100" width="100px;" alt="Martin Hochel"/><br /><sub><b>Martin Hochel</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Hotell" title="Code">💻</a></td>
<td align="center"><a href="https://d.sb/"><img src="https://avatars.githubusercontent.com/u/91933?v=4?s=100" width="100px;" alt="Daniel Lo Nigro"/><br /><sub><b>Daniel Lo Nigro</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Daniel15" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://github.com/0xflotus"><img src="https://avatars.githubusercontent.com/u/26602940?v=4?s=100" width="100px;" alt="0xflotus"/><br /><sub><b>0xflotus</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=0xflotus" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/afzalsayed96"><img src="https://avatars.githubusercontent.com/u/14029371?v=4?s=100" width="100px;" alt="Afzal Sayed"/><br /><sub><b>Afzal Sayed</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=afzalsayed96" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/aiji42"><img src="https://avatars.githubusercontent.com/u/6711766?v=4?s=100" width="100px;" alt="AijiUejima"/><br /><sub><b>AijiUejima</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=aiji42" title="Code">💻</a></td>
<td align="center"><a href="https://leopard.in.ua/"><img src="https://avatars.githubusercontent.com/u/98444?v=4?s=100" width="100px;" alt="Oleksii Vasyliev"/><br /><sub><b>Oleksii Vasyliev</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=le0pard" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/alicanerdogan"><img src="https://avatars.githubusercontent.com/u/1814803?v=4?s=100" width="100px;" alt="Alican Erdoğan"/><br /><sub><b>Alican Erdoğan</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=alicanerdogan" title="Code">💻</a></td>
<td align="center"><a href="https://amank.me/"><img src="https://avatars.githubusercontent.com/u/3933028?v=4?s=100" width="100px;" alt="Aman Kubanychbek"/><br /><sub><b>Aman Kubanychbek</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=amankkg" title="Code">💻</a></td>
<td align="center"><a href="http://kinetifex.com/"><img src="https://avatars.githubusercontent.com/u/82775?v=4?s=100" width="100px;" alt="Andrew Gerard"/><br /><sub><b>Andrew Gerard</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=kinetifex" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://www.linkedin.com/in/andrey-frolov-3b8579155/"><img src="https://avatars.githubusercontent.com/u/30667180?v=4?s=100" width="100px;" alt="Andrey Frolov"/><br /><sub><b>Andrey Frolov</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=frolovdev" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/soluml"><img src="https://avatars.githubusercontent.com/u/589571?v=4?s=100" width="100px;" alt="Benjamin Solum"/><br /><sub><b>Benjamin Solum</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=soluml" title="Code">💻</a></td>
<td align="center"><a href="https://billykwok.me/"><img src="https://avatars.githubusercontent.com/u/8078716?v=4?s=100" width="100px;" alt="Billy Kwok"/><br /><sub><b>Billy Kwok</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=billykwok" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/chrstntdd"><img src="https://avatars.githubusercontent.com/u/17863654?v=4?s=100" width="100px;" alt="Christian Todd"/><br /><sub><b>Christian Todd</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=chrstntdd" title="Code">💻</a></td>
<td align="center"><a href="https://estii.com/"><img src="https://avatars.githubusercontent.com/u/128329?v=4?s=100" width="100px;" alt="David Peek"/><br /><sub><b>David Peek</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=dpeek" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/dskiba"><img src="https://avatars.githubusercontent.com/u/28356785?v=4?s=100" width="100px;" alt="Denis Skiba"/><br /><sub><b>Denis Skiba</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=dskiba" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/geakstr"><img src="https://avatars.githubusercontent.com/u/1496368?v=4?s=100" width="100px;" alt="Dima Kharitonov"/><br /><sub><b>Dima Kharitonov</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=geakstr" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://github.com/GabbeV"><img src="https://avatars.githubusercontent.com/u/13839236?v=4?s=100" width="100px;" alt="Gabriel Valfridsson"/><br /><sub><b>Gabriel Valfridsson</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=GabbeV" title="Code">💻</a></td>
<td align="center"><a href="http://t.cn/EvDFUFF"><img src="https://avatars.githubusercontent.com/u/5354788?v=4?s=100" width="100px;" alt="Gitai"/><br /><sub><b>Gitai</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=GitaiQAQ" title="Code">💻</a></td>
<td align="center"><a href="https://hampuskraft.com/"><img src="https://avatars.githubusercontent.com/u/24176136?v=4?s=100" width="100px;" alt="Hampus Kraft"/><br /><sub><b>Hampus Kraft</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=hampuskraft" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/isumix"><img src="https://avatars.githubusercontent.com/u/16747416?v=4?s=100" width="100px;" alt="Igor Sukharev"/><br /><sub><b>Igor Sukharev</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=isumix" title="Code">💻</a></td>
<td align="center"><a href="https://bandism.net/"><img src="https://avatars.githubusercontent.com/u/22633385?v=4?s=100" width="100px;" alt="Ikko Ashimine"/><br /><sub><b>Ikko Ashimine</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=eltociear" title="Code">💻</a></td>
<td align="center"><a href="http://jsdecorator.com/"><img src="https://avatars.githubusercontent.com/u/4482199?v=4?s=100" width="100px;" alt="Iman Mohamadi"/><br /><sub><b>Iman Mohamadi</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=ImanMh" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/codecorsair"><img src="https://avatars.githubusercontent.com/u/9878445?v=4?s=100" width="100px;" alt="JB <codecorsair>"/><br /><sub><b>JB <codecorsair></b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=codecorsair" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://jack-works.github.io/"><img src="https://avatars.githubusercontent.com/u/5390719?v=4?s=100" width="100px;" alt="Jack Works"/><br /><sub><b>Jack Works</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Jack-Works" title="Code">💻</a></td>
<td align="center"><a href="https://ghuser.io/jamesgeorge007"><img src="https://avatars.githubusercontent.com/u/25279263?v=4?s=100" width="100px;" alt="James George"/><br /><sub><b>James George</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=jamesgeorge007" title="Code">💻</a></td>
<td align="center"><a href="https://appleid.apple.com/"><img src="https://avatars.githubusercontent.com/u/1058243?v=4?s=100" width="100px;" alt="Jed Mao"/><br /><sub><b>Jed Mao</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=jedmao" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/lencioni"><img src="https://avatars.githubusercontent.com/u/195534?v=4?s=100" width="100px;" alt="Joe Lencioni"/><br /><sub><b>Joe Lencioni</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=lencioni" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/joeycozza"><img src="https://avatars.githubusercontent.com/u/3885959?v=4?s=100" width="100px;" alt="Joey Cozza"/><br /><sub><b>Joey Cozza</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=joeycozza" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/juanferreras"><img src="https://avatars.githubusercontent.com/u/8507996?v=4?s=100" width="100px;" alt="Juan Ferreras"/><br /><sub><b>Juan Ferreras</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=juanferreras" title="Code">💻</a></td>
<td align="center"><a href="https://www.linkedin.com/in/kazuma1989/"><img src="https://avatars.githubusercontent.com/u/15844862?v=4?s=100" width="100px;" alt="Kazuma Ebina"/><br /><sub><b>Kazuma Ebina</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=kazuma1989" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://webpro.nl/"><img src="https://avatars.githubusercontent.com/u/456426?v=4?s=100" width="100px;" alt="Lars Kappert"/><br /><sub><b>Lars Kappert</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=webpro" title="Code">💻</a></td>
<td align="center"><a href="https://loige.co/"><img src="https://avatars.githubusercontent.com/u/205629?v=4?s=100" width="100px;" alt="Luciano Mammino"/><br /><sub><b>Luciano Mammino</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=lmammino" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/madhavarshney"><img src="https://avatars.githubusercontent.com/u/40002855?v=4?s=100" width="100px;" alt="Madhav Varshney"/><br /><sub><b>Madhav Varshney</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=madhavarshney" title="Code">💻</a></td>
<td align="center"><a href="https://malash.me/"><img src="https://avatars.githubusercontent.com/u/1812118?v=4?s=100" width="100px;" alt="Malash"/><br /><sub><b>Malash</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=malash" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/Swaagie"><img src="https://avatars.githubusercontent.com/u/670951?v=4?s=100" width="100px;" alt="Martijn Swaagman"/><br /><sub><b>Martijn Swaagman</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Swaagie" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/moitias"><img src="https://avatars.githubusercontent.com/u/1009280?v=4?s=100" width="100px;" alt="Matias Lahti"/><br /><sub><b>Matias Lahti</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=moitias" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/majames"><img src="https://avatars.githubusercontent.com/u/7553458?v=4?s=100" width="100px;" alt="Michael James"/><br /><sub><b>Michael James</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=majames" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://github.com/kryops"><img src="https://avatars.githubusercontent.com/u/1042594?v=4?s=100" width="100px;" alt="Michael Strobel"/><br /><sub><b>Michael Strobel</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=kryops" title="Code">💻</a></td>
<td align="center"><a href="https://twitter.com/michalchudziak"><img src="https://avatars.githubusercontent.com/u/7837457?v=4?s=100" width="100px;" alt="Michał Chudziak"/><br /><sub><b>Michał Chudziak</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=michalchudziak" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/mkanyar"><img src="https://avatars.githubusercontent.com/u/33469024?v=4?s=100" width="100px;" alt="Mike "/><br /><sub><b>Mike </b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=mkanyar" title="Code">💻</a></td>
<td align="center"><a href="https://www.mikestopcontinues.com/"><img src="https://avatars.githubusercontent.com/u/150434?v=4?s=100" width="100px;" alt="Mike Stop Continues"/><br /><sub><b>Mike Stop Continues</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=mikestopcontinues" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/Mokshit06"><img src="https://avatars.githubusercontent.com/u/50412128?v=4?s=100" width="100px;" alt="Mokshit Jain"/><br /><sub><b>Mokshit Jain</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Mokshit06" title="Code">💻</a></td>
<td align="center"><a href="https://www.linkedin.com/in/layershifter/"><img src="https://avatars.githubusercontent.com/u/14183168?v=4?s=100" width="100px;" alt="Oleksandr Fediashov"/><br /><sub><b>Oleksandr Fediashov</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=layershifter" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/paddyobrien"><img src="https://avatars.githubusercontent.com/u/846372?v=4?s=100" width="100px;" alt="Paddy O'Brien"/><br /><sub><b>Paddy O'Brien</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=paddyobrien" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://sogocze.cz/"><img src="https://avatars.githubusercontent.com/u/8431593?v=4?s=100" width="100px;" alt="Patrik Smělý"/><br /><sub><b>Patrik Smělý</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=SogoCZE" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/Nedgeva"><img src="https://avatars.githubusercontent.com/u/19298874?v=4?s=100" width="100px;" alt="Pavel Udaloff"/><br /><sub><b>Pavel Udaloff</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Nedgeva" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/pbitkowski"><img src="https://avatars.githubusercontent.com/u/22204594?v=4?s=100" width="100px;" alt="Przemysław Bitkowski"/><br /><sub><b>Przemysław Bitkowski</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=pbitkowski" title="Code">💻</a></td>
<td align="center"><a href="https://rin.rocks/"><img src="https://avatars.githubusercontent.com/u/16365952?v=4?s=100" width="100px;" alt="RiN"/><br /><sub><b>RiN</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=ri7nz" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/pustomytnyk"><img src="https://avatars.githubusercontent.com/u/9644824?v=4?s=100" width="100px;" alt="Roman Sokhan"/><br /><sub><b>Roman Sokhan</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=pustomytnyk" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/SeokminHong"><img src="https://avatars.githubusercontent.com/u/11614766?v=4?s=100" width="100px;" alt="Seokmin Hong (Ray)"/><br /><sub><b>Seokmin Hong (Ray)</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=SeokminHong" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/lebedev"><img src="https://avatars.githubusercontent.com/u/5000549?v=4?s=100" width="100px;" alt="Serge K Lebedev"/><br /><sub><b>Serge K Lebedev</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=lebedev" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://github.com/funsis"><img src="https://avatars.githubusercontent.com/u/28862758?v=4?s=100" width="100px;" alt="Sergey Korovin"/><br /><sub><b>Sergey Korovin</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=funsis" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/shreyas44"><img src="https://avatars.githubusercontent.com/u/46835608?v=4?s=100" width="100px;" alt="Shreyas Sreenivas"/><br /><sub><b>Shreyas Sreenivas</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=shreyas44" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/skywickenden"><img src="https://avatars.githubusercontent.com/u/4930551?v=4?s=100" width="100px;" alt="Sky Wickenden"/><br /><sub><b>Sky Wickenden</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=skywickenden" title="Code">💻</a></td>
<td align="center"><a href="https://www.linkedin.com/in/stanislavpanferov"><img src="https://avatars.githubusercontent.com/u/198327?v=4?s=100" width="100px;" alt="Stanislav Panferov"/><br /><sub><b>Stanislav Panferov</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=s-panferov" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/jsbalrog"><img src="https://avatars.githubusercontent.com/u/2457489?v=4?s=100" width="100px;" alt="Ted Jenkins"/><br /><sub><b>Ted Jenkins</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=jsbalrog" title="Code">💻</a></td>
<td align="center"><a href="https://int3ractive.com/"><img src="https://avatars.githubusercontent.com/u/234226?v=4?s=100" width="100px;" alt="Thanh Tran"/><br /><sub><b>Thanh Tran</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=trongthanh" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/tamorim"><img src="https://avatars.githubusercontent.com/u/5040487?v=4?s=100" width="100px;" alt="Thor Amorim"/><br /><sub><b>Thor Amorim</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=tamorim" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://github.com/tobenna"><img src="https://avatars.githubusercontent.com/u/12450941?v=4?s=100" width="100px;" alt="tobenna"/><br /><sub><b>tobenna</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=tobenna" title="Code">💻</a></td>
<td align="center"><a href="https://caurea.org/"><img src="https://avatars.githubusercontent.com/u/34538?v=4?s=100" width="100px;" alt="Tomas Carnecky"/><br /><sub><b>Tomas Carnecky</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=wereHamster" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/Tsubasa1218"><img src="https://avatars.githubusercontent.com/u/20498480?v=4?s=100" width="100px;" alt="Tsubasa1218"/><br /><sub><b>Tsubasa1218</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Tsubasa1218" title="Code">💻</a></td>
<td align="center"><a href="http://turadg.aleahmad.net/"><img src="https://avatars.githubusercontent.com/u/21505?v=4?s=100" width="100px;" alt="Turadg Aleahmad"/><br /><sub><b>Turadg Aleahmad</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=turadg" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/buzinas"><img src="https://avatars.githubusercontent.com/u/7298695?v=4?s=100" width="100px;" alt="Vitor Buzinaro"/><br /><sub><b>Vitor Buzinaro</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=buzinas" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/Mistereo"><img src="https://avatars.githubusercontent.com/u/1505518?v=4?s=100" width="100px;" alt="Mistereo"/><br /><sub><b>Mistereo</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Mistereo" title="Code">💻</a></td>
<td align="center"><a href="https://ru.linkedin.com/in/govnokoder"><img src="https://avatars.githubusercontent.com/u/351676?v=4?s=100" width="100px;" alt="Vladislav Kozulya"/><br /><sub><b>Vladislav Kozulya</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=5angel" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://yuheiy.com/"><img src="https://avatars.githubusercontent.com/u/11547305?v=4?s=100" width="100px;" alt="Yuhei Yasuda"/><br /><sub><b>Yuhei Yasuda</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=yuheiy" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/dkamyshov"><img src="https://avatars.githubusercontent.com/u/26835323?v=4?s=100" width="100px;" alt="Danil Kamyshov"/><br /><sub><b>Danil Kamyshov</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=dkamyshov" title="Code">💻</a></td>
<td align="center"><a href="https://sebastianlandwehr.com/"><img src="https://avatars.githubusercontent.com/u/13484795?v=4?s=100" width="100px;" alt="Sebastian Landwehr"/><br /><sub><b>Sebastian Landwehr</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=dword-design" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/everdimension"><img src="https://avatars.githubusercontent.com/u/5347023?v=4?s=100" width="100px;" alt="everdimension"/><br /><sub><b>everdimension</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=everdimension" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/ptol"><img src="https://avatars.githubusercontent.com/u/17497724?v=4?s=100" width="100px;" alt="ptol"/><br /><sub><b>ptol</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=ptol" title="Code">💻</a></td>
<td align="center"><a href="https://roottool.vercel.app/"><img src="https://avatars.githubusercontent.com/u/11808736?v=4?s=100" width="100px;" alt="roottool"/><br /><sub><b>roottool</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=roottool" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/ryamaguchi0220"><img src="https://avatars.githubusercontent.com/u/14275842?v=4?s=100" width="100px;" alt="ryamaguchi0220"/><br /><sub><b>ryamaguchi0220</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=ryamaguchi0220" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="https://www.simka.dev/"><img src="https://avatars.githubusercontent.com/u/16965735?v=4?s=100" width="100px;" alt="simka"/><br /><sub><b>simka</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=simka" title="Code">💻</a></td>
<td align="center"><a href="https://so-so.dev/"><img src="https://avatars.githubusercontent.com/u/18658235?v=4?s=100" width="100px;" alt="soso"/><br /><sub><b>soso</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=SoYoung210" title="Code">💻</a></td>
<td align="center"><a href="https://twitter.com/skovorodan"><img src="https://avatars.githubusercontent.com/u/291301?v=4?s=100" width="100px;" alt="Nikita Skovoroda"/><br /><sub><b>Nikita Skovoroda</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=ChALkeR" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/huang-xiao-jian"><img src="https://avatars.githubusercontent.com/u/4002210?v=4?s=100" width="100px;" alt="黄小健"/><br /><sub><b>黄小健</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=huang-xiao-jian" title="Code">💻</a></td>
<td align="center"><a href="https://github.com/iMoses"><img src="https://avatars.githubusercontent.com/u/1083065?v=4?s=100" width="100px;" alt="iMoses"/><br /><sub><b>iMoses</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=iMoses" title="Code">💻</a></td>
<td align="center"><a href="http://jneander.com"><img src="https://avatars.githubusercontent.com/u/880186?v=4?s=100" width="100px;" alt="Jeremy Neander"/><br /><sub><b>Jeremy Neander</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=jneander" title="Code">💻</a></td>
<td align="center"><a href="https://evensix.com"><img src="https://avatars.githubusercontent.com/u/1213447?v=4?s=100" width="100px;" alt="Andy Parsons"/><br /><sub><b>Andy Parsons</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=andparsons" title="Code">💻</a></td>
</tr>
<tr>
<td align="center"><a href="http://platane.github.io"><img src="https://avatars.githubusercontent.com/u/1659820?v=4?s=100" width="100px;" alt="Platane"/><br /><sub><b>Platane</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=Platane" title="Documentation">📖</a></td>
<td align="center"><a href="https://github.com/kutnickclose"><img src="https://avatars.githubusercontent.com/u/6117662?v=4?s=100" width="100px;" alt="Tim Kutnick"/><br /><sub><b>Tim Kutnick</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=kutnickclose" title="Documentation">📖</a></td>
<td align="center"><a href="https://github.com/aspirisen"><img src="https://avatars.githubusercontent.com/u/3620639?v=4?s=100" width="100px;" alt="Dmitrii Pikulin"/><br /><sub><b>Dmitrii Pikulin</b></sub></a><br /><a href="https://github.com/callstack/linaria/commits?author=aspirisen" title="Code">💻</a></td>
</tr>
</tbody>
</table>
<!-- markdownlint-restore -->
<!-- prettier-ignore-end -->
<!-- ALL-CONTRIBUTORS-LIST:END -->
This project follows the [all-contributors](https://github.com/kentcdodds/all-contributors) specification. Contributions of any kind welcome!
<!-- badges -->
[build-badge]: https://img.shields.io/circleci/project/github/callstack/linaria/master.svg?style=flat-square
[build]: https://circleci.com/gh/callstack/linaria
[coverage-badge]: https://img.shields.io/codecov/c/github/callstack/linaria.svg?style=flat-square
[coverage]: https://codecov.io/github/callstack/linaria
[version-badge]: https://img.shields.io/npm/v/linaria.svg?style=flat-square
[package]: https://www.npmjs.com/package/linaria
[license-badge]: https://img.shields.io/npm/l/linaria.svg?style=flat-square
[license]: https://opensource.org/licenses/MIT
[prs-welcome-badge]: https://img.shields.io/badge/PRs-welcome-brightgreen.svg?style=flat-square
[prs-welcome]: https://github.com/callstack/linaria/blob/master/CONTRIBUTING.md
[coc-badge]: https://img.shields.io/badge/code%20of-conduct-ff69b4.svg?style=flat-square
[coc]: https://github.com/callstack/linaria/blob/master/CODE_OF_CONDUCT.md
[all-contributors-badge]: https://img.shields.io/badge/all_contributors-23-orange.svg?style=flat-square
[chat-badge]: https://img.shields.io/discord/426714625279524876.svg?style=flat-square&colorB=758ED3
[chat]: https://discord.gg/zwR2Cdh
[tweet-badge]: https://img.shields.io/badge/tweet-%23linaria-blue.svg?style=flat-square&colorB=1DA1F2&logo=data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABgAAAAUCAYAAACXtf2DAAAAAXNSR0IArs4c6QAAAaRJREFUOBGtlM8rBGEYx3cWtRHJRaKcuMtBSitxkCQ3LtzkP9iUUu5ODspRHLhRLtq0FxeicEBC2cOivcge%2FMgan3fNM8bbzL4zm6c%2BPT%2Fe7%2FO8887svrFYBWbbtgWzsAt3sAcpqJFxxF1QV8oJFqFPFst5dLWQAT87oTgPB7DtziFRT1EA4yZolsFkhwjGYFRO8Op0KD8HVe7unoB6PRTBZG8IctAmG1xrHcfkQ2B55sfI%2ByGMXSBqV71xZ8CWdxBxN6ThFuECDEAL%2Bc9HIzDYumVZ966GZnX0SzCZvEqTbkaGywkyFE6hKAsBPhFQ18uPUqh2ggJ%2BUor%2F4M%2F%2FzOC8g6YzR1i%2F8g4vvSI%2ByD7FFNjexQrjHd8%2BnjABI3AU4Wl16TuF1qANGll81jsi5qu%2Bw6XIsCn4ijhU5FmCJpkV6BGNw410hfSf6JKBQ%2FUFxHGYBnWnmOwDwYQ%2BwzdHqO75HtiAMJfaC7ph32FSRJCENUhDHsLaJkL%2FX4wMF4%2BwA5bgAcrZE4sr0Cu9Jq9fxyrvBHWbNkMD5CEHWTjjT2m6r5D92jfmbbKJEWuMMAAAAABJRU5ErkJggg%3D%3D
[tweet]: https://twitter.com/intent/tweet?text=Check%20out%20linaria!%20https://github.com/callstack/linaria%20%F0%9F%91%8D
[greenkeeper-badge]: https://badges.greenkeeper.io/callstack/linaria.svg
[greenkeeper]: https://greenkeeper.io/
[callstack-badge]: https://callstack.com/images/callstack-badge.svg
[callstack]: https://callstack.com/open-source/?utm_source=github.com&utm_medium=referral&utm_campaign=linaria&utm_term=readme
================================================
FILE: babel.config.js
================================================
/*
* The following environments are supported:
*
* (unspecified): Produces ES module output, no language features
* (except non-standard ones) are transpiled.
* "legacy": Produces CommonJS output, uses @babel/preset-env to target
* Node.js 12 and specific browsers.
* "test": Used by Jest, produces CommonJS output, targetting
* the same version as legacy.
*/
/*
* Configuration for the legacy build
*/
const commonJSTargets = {
browsers: '> 0.25% and supports array-includes',
// browsers: 'chrome > 90',
node: '12',
};
module.exports = {
presets: ['@babel/preset-typescript'],
plugins: ['@babel/plugin-proposal-explicit-resource-management'],
env: {
legacy: {
presets: [
[
'@babel/preset-env',
{
targets: {
node: commonJSTargets.node,
},
},
],
],
},
test: {
presets: [
[
'@babel/preset-env',
{
targets: {
node: commonJSTargets.node,
},
},
],
'@babel/preset-typescript',
],
},
},
overrides: [
{
/**
* only react and core packages are targeted to be run in the browser
*/
test: /[\\/]packages[\\/](?:atomic|core|react)[\\/](?!src[\\/]processors[\\/])/,
presets: ['@babel/preset-react'],
env: {
legacy: {
presets: [
[
'@babel/preset-env',
{
targets: commonJSTargets.browsers,
loose: true,
// our styled component should not need to use any polyfill. We do not include core-js in dependencies. However, we leave this to detect if future changes would not introduce any need for polyfill
useBuiltIns: 'usage',
// Even core-js doesn't remember IE11
exclude: ['es.array.includes', 'web.dom-collections.iterator'],
corejs: 3,
// this is used to test if we do not introduced core-js polyfill
debug: process.env.DEBUG_CORE_JS === 'true',
},
],
],
},
},
},
{
/**
* we have to transpile JSX in tests
*/
test: /[\\/](__tests__|__fixtures__|packages[\\/]teskit[\\/]src)[\\/]/,
presets: ['@babel/preset-react'],
},
],
};
================================================
FILE: commitlint.config.js
================================================
module.exports = {
extends: ['@commitlint/config-conventional'],
};
================================================
FILE: docs/API.md
================================================
# API
Linaria exposes a core `css` method alongside with small, but just enough amount of helpers. Inside `@linaria/core` module you can find following methods:
## Client APIs
### `css`
String tag for tagged template literals consisting CSS code. The tagged template literal is evaluated to a unique class name by the Babel plugin:
```js
import { css } from '@linaria/core';
const flower = css`
display: inline;
color: violet;
`;
// flower === flower__9o5awv –> with babel plugin
```
All rules inside the template literal are scoped to the class name, including media queries and animations. For example, we can declare CSS animation like so:
```js
import { css } from '@linaria/core';
const box = css`
animation: rotate 1s linear infinite;
@keyframes rotate {
{
from: 0deg;
}
{
to: 360deg;
}
}
`;
```
### `cx(...classNames: Array<string | false | void | null | 0>) => string`
Takes a list of class names and returns a concatenated string with the class names. Falsy values are ignored.
```js
import { css, cx } from '@linaria/core';
const cat = css`
font-weight: bold;
`;
const yarn = css`
color: violet;
`;
const fun = css`
display: flex;
`;
function App({ isPlaying }) {
return <Playground className={cx(cat, yarn, isPlaying && fun)} />;
}
```
Unlike the [`classnames`](https://www.npmjs.com/package/classnames) library, this doesn't handle objects. If you want or need the features of the `classnames` library, you can use it instead.
### `styled`
Helper to build React components. It allows you to write your components in a similar syntax as [`styled-components`](https://www.styled-components.com/):
The syntax is similar to the `css` tag. Additionally, you can use function interpolations that receive the component's props:
```js
import { styled } from '@linaria/react';
import colors from './colors.json';
const Container = styled.div`
background-color: ${colors.background};
color: ${(props) => props.color};
width: ${100 / 3}%;
border: 1px solid red;
&:hover {
border-color: blue;
}
`;
```
All rules inside the template literal are scoped to the component, similar to the `css` tag.
Dynamic function interpolations are replaced with CSS custom properties. A dynamic function interpolation will receive the `props` of the component as it's arguments and the returned result will be used as the value for the variable. When using this, a tiny helper is imported so that we don't duplicate the code for creating the component in all files.
You can also interpolate a component to refer to it:
```js
const Title = styled.h1`
font-size: 36px;
`;
const Article = styled.article`
font-size: 16px;
/* this will evaluate to the selector that refers to `Title` */
${Title} {
margin-bottom: 24px;
}
`;
```
If you want to swap out the tag that's rendered, you can use the `as` prop:
```js
// Here `Button` is defined as a `button` tag
const Button = styled.button`
background-color: rebeccapurple;
`;
// You can switch it to use an `a` tag with the `as` prop
<Button as="a" href="/get-started">
Click me
</Button>;
```
You can also decorate another styled component with `styled`:
```js
const Button = styled.button`
background-color: rebeccapurple;
`;
// The background-color in FancyButton will take precedence
const FancyButton = styled(Button)`
background-color: black;
`;
```
### Atomic `css`
In addition to `css` from `@linaria/core`, the `@linaria/atomic` package exports its own `css` template literal which produces _atomic_ styles. See [the atomic css documentation](./ATOMIC_CSS.md) on this for more information.
## Server APIs (`@linaria/server`)
### `collect(html: string, css: string) => string`
Takes HTML and CSS strings and returns the critical CSS used in the page by analyzing the class names. It can be used to determine critical CSS for server side rendering.
```js
import { collect } from '@linaria/server';
const css = fs.readFileSync('./dist/styles.css', 'utf8');
const html = ReactDOMServer.renderToString(<App />);
const { critical, other } = collect(html, css);
// critical – returns critical CSS for given html
// other – returns the rest of styles
```
This will only detect critical CSS based on class names, so if you have any other type of selectors, they'll get added to the critical CSS.
Also note that extracting critical CSS this way will change the order of class names. It's not a problem if you're primarily using Linaria for styling. However if you're using a third party framework which imports its own CSS, then it's not recommended to use this helper on the extracted CSS.
================================================
FILE: docs/ATOMIC_CSS.md
================================================
# Atomic CSS
## What is Atomic CSS?
Atomic CSS is an approach to styling that reduces payload sizes for style delivery, and allows style composition and reuse easily. This document describes the concept of Atomic CSS, its advantage and use cases.
Atomic CSS is a way of writing CSS such that each CSS rule has exactly one declaration (an "atom"). For example,
```css
/** A normal class */
.myClass {
background: red;
width: 100%;
height: 100%;
}
/** Can be written atomically as: */
.a {
background: red;
}
.b {
width: 100%;
}
.c {
height: 100%;
}
```
## Usage in Linaria
Atomic styles can be enabled in the linaria config by providing an `atomizer` function (see [configuration](./CONFIGURATION.md) for details).
Once enabled, it is possible to write atomic styles by importing the `css` template literal from `@linaria/atomic`:
```tsx
import { cx } from '@linaria/core';
import { css } from '@linaria/atomic';
const atomicCss = css`
background: red;
width: 100%;
height: 100%;
border: 1px solid black;
`;
const blueBackground = css`
background: blue;
border: 1px solid black;
`;
// In React:
<div className={cx(atomicCss, blueBackground)} />;
// In vanilla JS:
const div = document.createElement('div');
div.setAttribute('class', cx(atomicCss, blueBackground));
document.body.appendChild(div);
```
Which at build time, is transformed into:
```ts
import { cx } from '@linaria/core';
import { css } from '@linaria/atomic';
const atomicCss =
'atm_background_abcd atm_width_efgh atm_height_ijkl atm_border_mnop';
const blueBackground = 'atm_background_qrst atm_border_mnop';
// In React:
<div className={cx(atomicCss, blueBackground)} />; // <div class="atm_width_efgh atm_height_ijkl atm_border_mnop" atm_background_qrst />
// In vanilla JS:
const div = document.createElement('div');
div.setAttribute('class', cx(atomicCss, blueBackground)); // same as React example
document.body.appendChild(div);
```
(Note: in the example above, the slugs in the atoms are lengthened for readability)
The format of these atoms is `atm_${propertySlug}_${valueSlug}` which lets us deduplicate based on the `propertySlug` part of the atom.
As you can see in the above example, `atm_border_mnop` can be removed as it duplicated, and we see two atoms with the `background` property slug, and can remove one of them.
### at-rules, pseudo classes and keyframes
Linaria's atomic css also supports creating (nested) at-rules, pseudo classes and keyframes:
```ts
import { css } from '@linaria/atomic';
// Note: animation name namespacing does not happen automatically with @linaria/atomic. Keyframe animations are pulled out to the top level and not atomized.
export const animation = css`
@keyframes my-animation {
from {
opacity: 0;
}
to {
opacity: 1;
}
}
animation: my-animation 1s infinite;
`;
export const pseudoClass = css`
&:hover {
color: pink;
}
`;
export const mediaQuery = css`
@media (max-width: 400px) {
background: orange;
}
`;
```
These can also be combined for further nesting.
### Property priorities
Using atomic CSS, longhand properties such as `padding-top` have a _higher_ priority than their shorthand equivalents like `padding`. For example:
```ts
import { css } from '@linaria/atomic';
const noPadding = css`
padding: 0;
`;
const paddingTop = css`
padding-top: 5px:
`;
// In react:
<div className={cx(noPadding, paddingTop)}>...</div>;
```
The result will be that the div has `padding-top: 5px;`, as that is higher priority than `padding: 0`.
The way linaria achieves this is through property priorities. See [this blog post](https://weser.io/blog/the-shorthand-longhand-problem-in-atomic-css) for more details on the concept, and the problems it solves. The method used in linaria is to increase the specificity of the rules: see `@linaria/atomic`'s `propertyPriority` function for a list of longhand and shorthand properties supported by this. The basic rules are:
- Longhand properties have higher priority than shorthand properties
- Declarations in @media rules (and any @-rule, such as @supports) have higher priority than those outside of them
## Use cases
### Reducing number of rules
One advantage of writing styles in this way is that we can reuse CSS more effectively. In many cases, declarations are repeated in CSS, and atomic CSS allows heavy reuse of these classes. For example if we have the classes,
```html
<style>
.redButton {
background: red;
width: 100px;
}
.blueButton {
background: blue;
width: 100px;
}
</style>
<button class="redButton" />
<button class="blueButton" />
```
We've repeated the declaration `width: 100px` twice. This repetition can become heavy as the amount of rules increases. Atomically, this can be written as:
```html
<style>
.a {
background: red;
}
.b {
background: blue;
}
.c {
width: 100px;
}
</style>
<button class="a c" />
<button class="b c" />
```
### Application order precedence vs. Definition order precedence
Another advantage is that rule precedence can be managed upon _application_ to an element rather than in the declaration. Consider a React component that passes a class name through a prop:
```ts
// BaseComponent.js
import { cx, css } from '@linaria/core';
const myClass = css`
background: red;
`;
export default function BaseComponent({ overrideClass }) {
return <div className={cx(myClass, overrideClass)} />;
}
// OverrideComponent.js
import { cx, css } from '@linaria/core';
import BaseComponent from './BaseComponent';
const overrides = css`
background: blue;
`;
function OverrideComponent({ overrideClass }) {
return <BaseComponent overrideClass={overrideClass} />;
}
```
The expectation would be that `background: blue` should be the result for `OverrideComponent`, but the result depends on the ordering of the compiled output in the DOM:
```ts
// dist/BaseComponent.js
import { cx, css } from '@linaria/core';
const myClass = 'myClass';
export default function BaseComponent({ overrideClass }) {
return <div className={cx(myClass, overrideClass)} />;
}
// dist/BaseComponent.css
.myClass {
background: red;
}
// dist/OverrideComponent.js
import { cx, css } from '@linaria/core';
import BaseComponent from './BaseComponent';
const overrides = 'overrides';
function OverrideComponent({ overrideClass }) {
return <BaseComponent overrideClass={overrideClass} />;
}
// dist/BaseComponent.css
.overrides {
background: blue;
}
```
Since `.overrides` and `.myClass` have the same specificity, the ultimate result of which component has precedence depends on their ordering in the DOM. This may be stable, but for async components, it may produce race conditions in styling.
With atomic styles, the precedence can be managed upon application – `cx` has the ability to look at the classes it is provided with, and filter duplicates. This means that there should never be rules with the same precedence applied to the same element.
Note that this example uses React, but is not a unique problem to react – it applies to any files that deliver bundles split between different files, where the ordering (and ultimate winner in specificity) may be nondeterministic at runtime.
### Limitations
- `@linaria/atomic` does not support targeting child selectors in css
- Shorthand properties like background are discouraged, as conflicts may still occur between properties like `border` and `border-top`
- Usage of `cx` is required to correctly deduplicate atoms, to ensure the application order precedence is guaranteed.
## See also
- [style9](https://github.com/johanholmerin/style9) using atomic styles
- Introduction of stylex: [conference talk video](https://www.youtube.com/watch?v=9JZHodNR184&t=229s)
================================================
FILE: docs/BASICS.md
================================================
# Basics
## Basic syntax
Linaria uses the [tagged template literal syntax](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Template_literals#Tagged_templates) for defining styles. This is a new syntax introduced in the recent versions of JavaScript.
A template literal is a string wrapped between backticks (`` ` ``) instead of quotes. You can use multi-line strings and string interpolation with them.
```js
const message = `
This is a template literal.
This is an interpolation: ${answer}.
`;
```
A tagged template literal is a tag attached to a template literal:
```js
const message = someTag`This is a tagged template literal`;
```
Tags are normal JavaScript function that receive the template literal and its interpolations, and can perform operations before returning a value.
Linaria exposes 2 tags for styling, `css` and `styled`. They both support the same set of features, except prop based styles, which is only supported by the `styled` tag.
These tags let you write styles in CSS syntax inside the template literals.
### The `css` tag
The `css` tag allows you to create simple class names:
```js
import { css } from '@linaria/core';
// Create a class name
const title = css`
font-size: 24px;
font-weight: bold;
`;
function Heading() {
// Pass it to a component
return <h1 className={title}>This is a title</h1>;
}
```
Here the value of the `title` variable will be a unique class name which you can pass in the `className` prop. This code is equivalent to the following CSS and JavaScript.
CSS:
```css
.title {
font-size: 24px;
font-weight: bold;
}
```
JavaScript:
```js
function Heading() {
return <h1 className="title">This is a title</h1>;
}
```
### The `styled` tag
The `styled` tag allows you to create a React component with some styles already applied.
You write `styled` followed by the name of the HTML tag you want to use, e.g. `styled.div`, `styled.a`, `styled.button`, `styled.h3` etc.
```js
import { styled } from '@linaria/react';
// Create a styled component
const Title = styled.h1`
font-size: 24px;
font-weight: bold;
`;
function Heading() {
// Use the styled component
return <Title>This is a title</Title>;
}
```
This reduces quite a bit of boilerplate code you had to write when you manually created the class name and applied it to a tag. This code is equivalent to the following CSS and JavaScript.
CSS:
```css
.title {
font-size: 24px;
font-weight: bold;
}
```
JavaScript:
```js
function Title(props) {
return <h1 {...props} className="title" />;
}
function Heading() {
return <Title>This is a title</Title>;
}
```
Apart from the reduced boilerplate code, this also makes it easier to do prop based styling which you'll cover later in the guide.
### Nesting, pseudo-elements and pseudo-selectors
You can nest selectors, pseudo-elements and pseudo-selectors similar to Sass, thanks to [stylis](https://github.com/thysultan/stylis.js).
For example, to change the color of a button on hover, you'll write something like this:
```js
const Button = styled.button`
color: black;
&:hover {
color: blue;
}
`;
```
The value of `&` refers to the class name. This code is equivalent to the following CSS:
```css
.button {
color: black;
}
.button:hover {
color: blue;
}
```
You can nest pseudo-elements as well as other selectors:
```js
const Thing = styled.div`
color: black;
&::after {
/* .thing::after */
content: '🌟';
}
h3 {
/* .thing h3 */
color: tomato;
}
.code {
/* .thing .code */
color: #555;
}
& + & {
/* .thing + .thing */
background: yellow;
}
&.bordered {
/* .thing.bordered */
border: 1px solid black;
}
.parent & {
/* .parent .thing */
color: blue;
}
`;
```
You can also nest media queries:
```js
const Thing = styled.div`
color: black;
@media (min-width: 200px) {
color: blue;
}
`;
```
This is equivalent to the following CSS:
```css
.thing {
color: black;
}
@media (min-width: 200px) {
.thing {
color: blue;
}
}
```
### Keyframe animations
You can write keyframe declarations right inside the template literal:
```js
const Box = styled.div`
height: 200px;
width: 200px;
background-color: tomato;
animation: spin 2s linear infinite;
@keyframes spin {
from {
transform: rotate(0deg);
}
to {
transform: rotate(360deg);
}
}
`;
```
Here `spin` will be replaced with a unique string to scope the animation to the class name.
## Interpolations
Like normal template literals, you can interpolate other expressions inside a template literal tagged with `css` or `styled`.
If you try to interpolate an invalid value, you'll get an error at build-time.
### Basic interpolations
You can interpolate variables declared in the same file as well as imported variables:
```js
const fontSize = 16;
const Title = styled.h1`
font-size: ${fontSize}px;
`;
```
Here, the `fontSize` variable will be evaluated at build time and inserted into the generated CSS.
You can also call functions while interpolating:
```js
const Button = styled.button`
background-color: ${colors.primary};
&:hover {
background-color: ${darken(0.2, colors.primary)};
}
`;
```
### Object interpolations
You can also interpolate object styles. It's converted to a CSS string before inserting to the stylesheet:
```js
const cover = {
position: 'absolute',
top: 0,
right: 0,
bottom: 0,
left: 0,
opacity: 1,
minHeight: 360,
'@media (min-width: 200px)': {
minHeight: 480,
},
};
const Title = styled.h1`
font-size: 24px;
${cover};
`;
```
This is equivalent to the following CSS:
```js
const Title = styled.h1`
font-size: 24px;
position: absolute;
top: 0;
right: 0;
bottom: 0;
left: 0;
opacity: 1;
min-height: 360px;
@media (min-width: 200px): {
min-height: 480px;
}
`;
```
The interpolated object can have nested selectors, media queries, pseudo-selectors and pseudo-elements. Numeric values which require a unit (e.g. `minHeight` in the above example) will be appended with `px` unless specified.
### Prop based styles
When writing React components using the `styled` syntax, you can write styles based on the component's props. These values will use [CSS variables](https://developer.mozilla.org/en-US/docs/Web/CSS/Using_CSS_variables) under the hood and can change dynamically in runtime.
For dynamic prop based styles, pass a function to the interpolation:
```js
const Title = styled.h1`
color: ${props => (props.primary ? 'tomato' : 'black')};
`;
```
The function will be called with the component's props as an argument when it is rendered. Here, the color of the title will be automatically updated whenever the value of the `primary` prop changes.
### Referring to another component or class name
You can interpolate a styled component or a class name to refer to it. For example:
```js
const title = css`
font-size: 24px;
color: black;
`;
const Paragraph = styled.p`
font-size: 16px;
color: #555;
`;
const Article = styled.article`
/* when referring to class names, prepend a dot (.) */
.${title} {
font-size: 36px;
}
/* when referring to a component, interpolate it as a selector */
${Paragraph} {
font-size: 14px;
margin: 16px;
}
`;
```
## Overriding styles
If you want to override few styles on a styled component you defined earlier, you can do so by wrapping it in the `styled(..)` tag:
```js
const Button = styled.button`
font-size: 14px;
background-color: tomato;
padding: 8px;
box-shadow: 0 0.5px 0.3px rgba(0, 0, 0, 0.1);
`;
const LargeButton = styled(Button)`
font-size: 18px;
padding: 16px;
`;
```
Here, when you use `LargeButton`, it'll have all the same styles as `Button` except the `font-size` and `padding` which we overrode.
## Styling custom components
You can use the `styled(..)` tag to style any component as long as they accept a `className` and a `style` prop:
```js
function CoolComponent({ className, style, ...rest }) {
return (
<div className={className} style={style}>
{...}
</div>
);
}
const StyledCoolComponent = styled(CoolComponent)`
background-color: tomato;
`;
```
The `style` prop is necessary to apply CSS variables. If you're using a component library that doesn't support passing a `style` prop, you can wrap it in a `div` (or any other tag that makes sense) to apply it:
```js
import { Card } from 'some-library';
function CustomCard({ className, style, ...rest }) {
return (
<div style={style}>
<Card className={className} {...rest} />
</div>
);
}
const StyledCustomCard = styled(CustomCard)`
margin: 16px;
height: ${props => props.height}px;
`;
```
If you want to use linaria classname, which is generated for component, you can get it as last item from `className` prop:
```js
function CoolComponent({ className, style, variant, ...rest }) {
const allClasses = className.split(' ');
const linariaClassName = allClasses[allClasses.length - 1];
const classes = cx(
className,
variant === 'primary' && `${linariaClassName}--primary`
);
return (
<div className={classes} style={style}>
{...}
</div>
);
}
const StyledCoolComponent = styled(CoolComponent)`
background-color: tomato;
&--primary {
background-color: yellow;
}
`;
```
## Adding global styles
Normally, the styles are scoped to specific components. But sometimes you may need to write some global styles, for example, to normalize browser inconsistencies, define a font-family etc.
You can do the following to generate unscoped global styles:
```js
export const globals = css`
:global() {
html {
box-sizing: border-box;
}
*,
*:before,
*:after {
box-sizing: inherit;
}
@font-face {
font-family: 'MaterialIcons';
src: url(../assets/fonts/MaterialIcons.ttf) format('truetype');
}
}
`;
```
It's not possible to use dynamic prop based styles inside global styles.
================================================
FILE: docs/BENEFITS.md
================================================
# Why use Linaria
## Advantages over regular CSS
### 1. Selectors are scoped
Unlike regular CSS, Linaria will generate scoped class names so that there's no collision between multiple styles in a large application. It's automatic, unlike conventions such as BEM.
For example, consider the following:
```js
const title = css`
font-size: 18px;
`;
```
The resulting CSS will look something like:
```css
.k4yi6fg {
font-size: 18px;
}
```
Here the generated class name is unique and based on the hash of the file path.
### 2. Styles are in same file as the component
With regular CSS, you'll need to create a separate file to write the CSS. This can be annoying when working with components because you'll need to do constant switching between the JS and CSS files while you're tweaking the styles. With Linaria, you can have the styles in the same file as rest of the JS.
You can also keep the styles in a separate JS file if you want, of course.
### 3. Refactor with confidence
You don't have to worry about breaking an unrelated component when changing and removing styles. Since Linaria's styles are like regular JavaScript variables, it's easy to track their usage and refactor.
### 4. No pre-processor needed
Linaria supports JavaScript expressions, which enables you to generate style rules inside a declaration programmatically with JavaScript. You can share constants and helper functions between your CSS and JavaScript freely.
For example, here we are using a `lighten` helper from a third-party library:
```js
import { lighten } from 'polished';
const PRIMARY_COLOR = '#de2d68';
const button = css`
background-color: ${PRIMARY_COLOR};
&:hover {
background-color: ${lighten(0.2, PRIMARY_COLOR)};
}
`;
```
### 5. Automatic unused styles removal
Linaria automatically drops unused styles in a file unless it is exported. Linters like [ESLint](https://eslint.org/) can also warn you about when you have unused styles since they are just normal JS variables.
### 6. Automatic vendor prefixing
Linaria will automatically vendor prefix your CSS, so you don't have to worry about supporting older browsers. You write modern CSS, and Linaria takes care of the rest.
You can still use tools like [PostCSS](https://postcss.org/) to further optimize the CSS.
### 7. Declarative dynamic styling with React
When using the `styled` helper, Linaria will generate dynamic CSS variables which automatically update when props change. When writing regular CSS, you'll have to manage it manually.
For example, here the `height` and `width` will automatically update based on the `size` prop of `Box`:
```js
const Box = styled.div`
background-color: orange;
height: ${props => props.size}px;
width: ${props => props.size}px;
`;
<Box size={48}>
```
## Advantages over CSS preprocessors
### 1. No new syntax to learn
Linaria's syntax is just like regular CSS, plus ability to nest selectors for convenience. There's no new syntax for variables, mixins or functions. It's just JavaScript.
### 2. Same advantages as regular CSS
Linaria has all the same advantages mentioned in "Advantages over regular CSS" even when you are using a CSS pre-processor.
## Advantages over inline styles
### 1. Full power of CSS
Unlike inline styles, you have the full power of CSS with Linaria, such as:
- Media queries
- Animation keyframes
- Hover, focus states etc.
- Pseudo-selectors
### 2. Performance
Class names perform much faster than inline styles.
## Advantages over other CSS-in-JS solutions
### 1. CSS is downloaded and parsed separately from JS
Since the styles are extracted to separate CSS files, the CSS and JavaScript can be downloaded and parsed by the browser in parallel and can improve the load time.
### 2. No extra parsing needed for CSS
Many CSS-in-JS libraries parse the CSS string using a custom parser on the client. This increases the bundle size (albeit slightly) due to the inclusion of the parser. In addition, the CSS cannot be parsed until the JavaScript code is parsed and executed, which can be noticable, especially on low-end devices and bigger JS bundles.
Linaria is unique in the sense that it doesn't need a runtime to work. Styles are parsed, evaluated and generated at build time and no extra parsing is needed on the client.
### 3. No style duplication on SSR
For component based CSS in JS libraries, rendering same component with different props can lead to duplicating the same set of styles multiple times. It doesn't matter on client side, but may increase the size of the rendered CSS when doing SSR. It may not matter in most cases, but in cases where you are rendering a large list of elements with tiny differences in styles, it can quickly add up.
In addition, when you do SSR, the rendered CSS is downloaded in addition to the CSS you wrote in JS files, further increasing the size.
Linaria produces only one rule set per declaration, and the differences are taken care of using CSS variables, so there's no duplication, which is great for reducing bundle size.
### 4. Catch errors early due to build-time evaluation
When you interpolate invalid values in Linaria (for example NaN in styles), you'll get a build time error. So you don't accidentally ship bugs into production and realize it later.
Linaria's stylelint processor is also more robust and can lint styles much better, like you're writing vanilla CSS files.
### 5. Familiar CSS syntax
Unlike some CSS in JS libraries, Linaria lets you write normal CSS syntax, which means you can copy paste styles from the browser's dev tools (or StackOverflow), and avoid unnecessary noise in the styles.
You can also use a pre-processor such as Sass if you prefer.
### 6. Works without JavaScript
If your website needs to work without JavaScript, or you generate the HTML in advance at build time, Linaria is a great fit for styling such websites.
================================================
FILE: docs/BUNDLERS_INTEGRATION.md
================================================
# Bundlers Integration
## Jump To
- [webpack](#webpack)
- [esbuild](#esbuild)
- [Rollup](#Rollup)
- [Vite](#Vite)
- [Svelte](#Svelte)
## Pre-requisites
If you use Babel in your project, make sure to have a [config file for Babel](https://babeljs.io/docs/en/config-files) in your project root with the plugins and presets you use. Otherwise Linaria won't be able to parse the code.
## Bundlers
Please note, that `@babel/core` is a peer dependency of all loaders. Do not forget to add it to `devDependencies` list in your project.
### webpack
To use Linaria with webpack, in your webpack config, add `@wyw-in-js/webpack-loader` under `module.rules`:
```js
{
test: /\.js$/,
use: [
{ loader: 'babel-loader' },
{
loader: '@wyw-in-js/webpack-loader',
options: {
sourceMap: process.env.NODE_ENV !== 'production',
},
}
],
}
```
Make sure that `@wyw-in-js/webpack-loader` is included after `babel-loader`.
In order to have your styles extracted, you'll also need to use **css-loader** and **MiniCssExtractPlugin**. First, install them:
```sh
yarn add --dev css-loader mini-css-extract-plugin
```
Import `mini-css-extract-plugin` at the top of your webpack config:
```js
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
```
Now add the following snippet in under `module.rules`:
```js
{
test: /\.css$/,
use: [
{
loader: MiniCssExtractPlugin.loader,
},
{
loader: 'css-loader',
options: {
sourceMap: process.env.NODE_ENV !== 'production',
},
},
],
},
```
Then add the following under `plugins`:
```js
new MiniCssExtractPlugin({
filename: 'styles.css',
});
```
This will extract the CSS from all files into a single `styles.css`. Then you can link to this file in your HTML file manually or use something like [`HTMLWebpackPlugin`](https://github.com/jantimon/html-webpack-plugin).
It will also hot reload your styles when in a development environment.
For production usage, you should include a hash in the filename:
```js
new MiniCssExtractPlugin({
filename: 'styles-[contenthash].css',
});
```
Using a hash like this allows for a far future `Expires` header to be used, to improve cache efficiency. To link to the correct filename, you can either use [`HTMLWebpackPlugin`](https://github.com/jantimon/html-webpack-plugin) for a static HTML file, or [`assets-webpack-plugin`](https://yarn.pm/assets-webpack-plugin) to save the filename to a JSON file which you can then read in your server-side code.
Linaria integrates with your CSS pipeline, so you can always perform additional operations on the CSS, for example, using [postcss](https://postcss.org/) plugins such as [clean-css](https://github.com/jakubpawlowicz/clean-css) to further minify your CSS.
#### Full example
Here is an example webpack config with Linaria:
```js
const webpack = require('webpack');
const path = require('path');
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
const dev = process.env.NODE_ENV !== 'production';
module.exports = {
mode: dev ? 'development' : 'production',
devtool: 'source-map',
entry: {
app: './src/index',
},
output: {
path: path.resolve(__dirname, 'dist'),
publicPath: '/dist/',
filename: '[name].bundle.js',
},
optimization: {
noEmitOnErrors: true,
},
plugins: [
new webpack.DefinePlugin({
'process.env': { NODE_ENV: JSON.stringify(process.env.NODE_ENV) },
}),
new MiniCssExtractPlugin({ filename: 'styles.css' }),
],
module: {
rules: [
{
test: /\.js$/,
exclude: /node_modules/,
use: [
{ loader: 'babel-loader' },
{
loader: '@wyw-in-js/webpack-loader',
options: { sourceMap: dev },
},
],
},
{
test: /\.css$/,
use: [
{
loader: MiniCssExtractPlugin.loader,
},
{
loader: 'css-loader',
options: { sourceMap: dev },
},
],
},
{
test: /\.(jpg|png|gif|woff|woff2|eot|ttf|svg)$/,
use: [{ loader: 'file-loader' }],
},
],
},
devServer: {
contentBase: [path.join(__dirname, 'public')],
historyApiFallback: true,
},
};
```
You can copy this file to your project if you are starting from scratch.
To install the dependencies used in the example config, run:
```sh
yarn add --dev webpack webpack-cli webpack-dev-server mini-css-extract-plugin css-loader file-loader babel-loader @wyw-in-js/webpack-loader
```
You can now run the dev server by running `webpack-dev-server` and build the files by running `webpack`.
#### Options
The loader accepts the following options:
- `sourceMap: boolean` (default: `false`):
Setting this option to `true` will include source maps for the generated CSS so that you can see where source of the class name in devtools. We recommend to enable this only in development mode because the sourcemap is inlined into the CSS files.
- `cacheProvider: undefined | string | ICache` (default: `undefined`):
By default Linaria use a memory cache to store temporary CSS files. But if you are using this loader with [thread-loader](https://www.npmjs.com/package/thread-loader) you should use some consistent cache to prevent [some unexpected issues](https://github.com/callstack/linaria/issues/881). This options support a `ICache` instance or a path to NodeJS module which export a `ICache` instance as `module.exports`
> ```
> interface ICache {
> get: (key: string) => Promise<string>;
> set: (key: string, value: string) => Promise<void>;
> getDependencies?: (key: string) => Promise<string[]>;
> setDependencies?: (key: string, value: string[]) => Promise<void>;
> }
> ```
When running webpack with `--watch`, `getDependencies` and `setDependencies` will be used to carry dependencies of the Linaria JavaScript source to the generated css output, ensuring both are rebuilt when dependencies change. When these methods are not present on the cache instance, dependencies for the css output will be ignored and may get out of sync with the JavaScript output. Linaria's default memory cache does not have this issue.
- `extension: string` (default: `'.linaria.css'`):
An extension of the intermediate CSS files.
- `preprocessor: 'none' | 'stylis' | Function` (default: `'stylis'`)
You can override the pre-processor if you want to override how the loader processes the CSS.
- `'none'`: This will disable pre-processing entirely and the CSS will be left as you wrote it.
You might want to do it if you want to use non-standard syntax such as Sass or custom [postcss](https://postcss.org/) syntax. Features such as nesting will no longer work with this option. You need to specify a loader such as [`sass-loader`](https://github.com/webpack-contrib/sass-loader) for `.linaria.css` files which handles the syntax you wrote.
- `'stylis'`: This is the default pre-processor using [stylis.js](https://github.com/thysultan/stylis.js).
This option also applies a custom `stylis` plugin to correct the relative paths inside `url(...)` expressions so that `css-loader` can resolve them properly.
- `Function`: You can pass a custom function which receives the `selector` and `cssText` strings. It should return the resulting CSS code.
A very basic implementation may look like this: `` (selector, cssText) => `${selector} { ${cssText} }`; ``.
Changing the `preprocessor` doesn't affect the following operations:
- The class names are always generated by the library and the pre-processor cannot change it.
- Dynamic interpolations are always replaced with CSS variables.
- Interpolations for JS objects always generate syntax used by default.
Note that if you use a custom syntax, you also need to specify the `syntax` in your `stylelint.config.js` to properly lint the CSS.
In addition to the above options, the loader also accepts all the options supported in the [configuration file](/docs/CONFIGURATION.md).
You can pass options to the loader like so:
```js
{
loader: '@wyw-in-js/webpack-loader',
options: {
sourceMap: false,
},
}
```
### esbuild
To use Linaria with esbuild, you don't need to install any external package since esbuild handles CSS by itself:
```sh
yarn add --dev @wyw-in-js/esbuild
```
Then add it to your esbuild config:
```js
import linaria from '@wyw-in-js/esbuild';
import esbuild from 'esbuild';
const prod = process.env.NODE_ENV === 'production';
esbuild
.build({
entryPoints: ['src/index.ts'],
outdir: 'dist',
bundle: true,
minify: prod,
plugins: [
linaria({
sourceMap: prod,
}),
],
})
.catch(() => process.exit(1));
```
### Rollup
To use Linaria with Rollup, you need to use it together with a plugin which handles CSS files, such as `rollup-plugin-css-only`:
```sh
yarn add --dev rollup-plugin-css-only @wyw-in-js/rollup
```
Then add them to your `rollup.config.js`:
```js
import linaria from '@wyw-in-js/rollup';
import css from 'rollup-plugin-css-only';
export default {
plugins: [
linaria({
sourceMap: process.env.NODE_ENV !== 'production',
}),
css({
output: 'styles.css',
}),
],
};
```
If you are using [@rollup/plugin-babel](https://github.com/rollup/plugins/tree/master/packages/babel) as well, ensure the linaria plugin is declared earlier in the `plugins` array than your babel plugin.
```js
import linaria from '@wyw-in-js/rollup';
import css from 'rollup-plugin-css-only';
import babel from '@rollup/plugin-babel';
export default {
plugins: [
linaria({
sourceMap: process.env.NODE_ENV !== 'production',
}),
css({
output: 'styles.css',
}),
babel({}),
/* rest of your plugins */
],
};
```
### Vite
~~Since Vite supports Rollup plugin~~ Since Vite provides more features and flexibility, Linaria has a separate plugin for it `@wyw-in-js/vite`. Vite handles CSS by itself, you don't need a css plugin.
```sh
yarn add --dev @wyw-in-js/vite
```
Then add them to your `vite.config.js`:
```js
import { defineConfig } from 'vite';
import linaria from '@wyw-in-js/vite';
export default defineConfig(() => ({
// ...
plugins: [linaria()],
}));
```
If you are using language features that requires a babel transform (such as typescript), ensure the proper babel presets or plugins are passed to linaria.
```js
import { defineConfig } from 'vite';
import linaria from '@wyw-in-js/vite';
// example to support typescript syntax:
export default defineConfig(() => ({
// ...
plugins: [
linaria({
include: ['**/*.{ts,tsx}'],
babelOptions: {
presets: ['@babel/preset-typescript', '@babel/preset-react'],
},
}),
],
}));
```
### Svelte
#### Contents
- [Svelte with Rollup](#Rollup-1)
- [Svelte with Webpack](#Webpack-1)
#### Rollup
Take a look: [d964432](https://github.com/madhavarshney/svelte-linaria-sample/commit/d96443218694c0c8d80edf7c40a8fbf7c1f6997f)
Install `rollup-plugin-css-only` and update `rollup.config.js`
```js
import svelte from 'rollup-plugin-svelte';
import css from 'rollup-plugin-css-only'; // for CSS bundling
import linaria from '@wyw-in-js/rollup';
const dev = process.env.NODE_ENV !== 'production';
export default {
...
plugins: [
svelte({
dev,
// allow `plugin-css-only` to bundle with CSS generated by linaria
emitCss: true,
}),
linaria({
sourceMap: dev,
}),
css({
output: '<OUT_FOLDER>/bundle.css',
}),
],
};
```
**IMPORTANT**: `rollup-plugin-css-only` generates incorrect sourcemaps (see [thgh/rollup-plugin-css-only#10](https://github.com/thgh/rollup-plugin-css-only/issues/10)). Use an alternative CSS plugin such as [`rollup-plugin-postcss`](https://github.com/egoist/rollup-plugin-postcss) instead in the same way as above.
#### Webpack
Take a look: [5ffd69d](https://github.com/madhavarshney/svelte-linaria-sample/commit/5ffd69dc9f9584e3eec4127e798d7a4c1552ec19)
Update `webpack.config.js` with the following:
```js
const prod = process.env.NODE_ENV === 'production';
const linariaLoader = {
loader: '@wyw-in-js/webpack-loader',
options: {
sourceMap: !prod,
},
};
module.exports = {
...
module: {
rules: [
{
test: /\.m?js$/,
exclude: /node_modules/,
use: [linariaLoader],
},
{
test: /\.svelte$/,
use: [
linariaLoader,
{
loader: 'svelte-loader',
options: {
dev: !prod,
emitCss: true,
hotReload: true,
},
},
],
},
...(CSS rules)
],
},
};
```
================================================
FILE: docs/CLI.md
================================================
# CLI
Linaria CLI (`@linaria/cli`) allows you to extract CSS from your source files using a command line.
### Usage
```bash
yarn linaria [options] <file1> [<fileN>...]
```
Option `-o, --out-dir <dir>` __is always required__.
You can also use glob for specifying files to process:
```bash
yarn linaria -o styles src/component/**/*.js
# or multiple globs
yarn linaria -o styles src/component/**/*.js src/screens/**/*.js
```
CLI supports adding a require statement for generated CSS file automatically:
```bash
yarn linaria -o out-dir --source-root src --insert-css-requires dist src/**/*.js
```
where `source-root` is directory with source JS files and `insert-css-requires` has directory with transpiled/compiled JS files.
### Options
* `-o, --out-dir <dir>` (__required__) - Output directory for the extracted CSS files
* `-s, --source-maps` - Generate source maps for the CSS files
* `-r, --source-root <dir>` - Directory containing the source JS files
* `-i, --insert-css-requires <dir>` - Directory containing JS files to insert require statements for the CSS files (__works only if `-r, --source-root` is provided__)
* `-c, --config-file <filepath>` - Path to the configuration file. If a relative path is given, it'll be resolved relative to the current working directory.
* `-x, --ignore "<pattern>"` - Pattern of files to ignore. Be sure to wrap with quotes.
* `-m, --modules <type>` - Specifies a type of used imports.
* `-t, --transform <boolean>` - Replace template tags with evaluated values.
================================================
FILE: docs/CONFIGURATION.md
================================================
# Configuration
Linaria uses [WyW-in-JS](https://wyw-in-js.dev) under the hood and can be customized using a JavaScript, JSON or YAML file. This can be in form of:
- `wyw-in-js.config.js` JS file exporting the object (recommended).
- `wyw-in-js` property in a `package.json` file.
- `.wyw-in-jsrc` file with JSON or YAML syntax.
- `.wyw-in-jsrc.json`, `.wyw-in-jsrc.yaml`, `.wyw-in-jsrc.yml`, or `.wyw-in-jsrc.js` file.
Example `wyw-in-js.config.js`:
```js
module.exports = {
evaluate: true,
displayName: false,
};
```
## Options
- `evaluate: boolean` (default: `true`):
Enabling this will evaluate dynamic expressions in the CSS. You need to enable this if you want to use imported variables in the CSS or interpolate other components. Enabling this also ensures that your styled components wrapping other styled components will have the correct specificity and override styles properly.
- `displayName: boolean` (default: `false`):
Enabling this will add a display name to generated class names, e.g. `.Title_abcdef` instead of `.abcdef'. It is disabled by default to generate smaller CSS files.
- `variableNameConfig: "var" | "dashes" | "raw"` (default: `var`):
Configures how the variable will be formatted in final CSS.
### Possible values
#### `var`
Use full css variable structure. This is default behavior.
```js
import { styled } from "@linaria/react";
export const MyComponent = styled.div`
color: ${(props) => props.color};
`;
```
In CSS you will see full variable declaration
```css
.MyComponent_m1cus5as {
color: var(--m1cus5as-0);
}
```
#### `dashes`
Removes `var()` around the variable name. It is useful when you want to control the variable on your own. For example you can set default value for CSS variable.
```js
import { styled } from "@linaria/react";
export const Theme = styled.div`
--font-color: red;
`;
export const MyComponent = styled.div`
// Returning empty string is mandatory
// Otherwise you will have "undefined" in css variable value
color: var(${(props) => props.color ?? ""}, var(--font-color));
`;
function App() {
return (
<Theme>
<MyComponent>Text with red color</MyComponent>
<MyComponent color="blue">Text with blue color</MyComponent>
</Theme>
);
}
```
In CSS you will see generated variable name and your default value.
```css
.Theme_t1cus5as {
--font-color: red;
}
.MyComponent_mc195ga {
color: var(--mc195ga-0, var(--font-color));
}
```
#### `raw`
Use only variable name without dashes and `var()` wrapper.
```js
import { styled } from "@linaria/react";
export const MyComponent = styled.div`
color: ${(props) => props.color};
`;
```
In CSS you will see just the variable name. This is not valid value for css property.
```css
.MyComponent_mc195ga {
color: mc195ga-0;
}
```
You will have to make it valid:
```js
export const MyComponent = styled.div`
color: var(--${(props) => props.color});
`;
```
- `classNameSlug: string | ((hash: string, title: string, args: ClassNameSlugVars) => string)` (default: `default`):
Using this will provide an interface to customize the output of the CSS class name. Example:
classNameSlug: '[title]',
Would generate a class name such as `.header` instead of the default `.header_absdjfsdf` which includes a hash.
You may also use a function to define the slug. The function will be evaluated at build time and must return a string:
classNameSlug: (hash, title) => `${hash}__${7 * 6}__${title}`,
Would generate the class name `.absdjfsdf__42__header`.
Last argument `args` is an object that contains following properties: `title`, `hash`, `dir`, `ext`, `file`, `name`. These properties
are useful when you want to generate your own hash:
```js
const sha1 = require("sha1");
module.exports = {
classNameSlug: (hash, title, args) => sha1(`${args.name}-${title}`)
};
```
**note** invalid characters will be replaced with an underscore (`_`).
### Variables
- `hash`: The hash of the content.
- `title`: The name of the class.
- `variableNameSlug: string | ((context: IVariableContext) => string)` (default: `default`):
Using this will provide an interface to customize the output of the CSS variable name. Example:
variableNameSlug: '[componentName]-[valueSlug]-[index]',
Would generate a variable name such as `--Title-absdjfsdf-0` instead of the `@react/styled`'s default `--absdjfsdf-0`.
You may also use a function to define the slug. The function will be evaluated at build time and must return a string:
variableNameSlug: (context) => `${context.valueSlug}__${context.componentName}__${context.precedingCss.match(/([\w-]+)\s*:\s*$/)[1]}`,
Would generate the variable name `--absdjfsdf__Title__flex-direction`.
**note** invalid characters will be replaced with an underscore (`_`).
### Variables
- `componentName` - the displayName of the component.
- `componentSlug` - the component slug.
- `index` - the index of the css variable in the current component.
- `precedingCss` - the preceding part of the css for the variable, i.e. `flex: 1; flex-direction: `.
- `preprocessor` - the preprocessor used to process the tag (e.g. 'StyledProcessor' or 'AtomicStyledProcessor').
- `source` - the string source of the css property value.
- `unit` - the unit.
- `valueSlug` - the value slug.
- `overrideContext: (context: Partial<vm.Context>, filename: string) => Partial<vm.Context>`
A custom function to override the context used to evaluate modules. This can be used to add custom globals or override the default ones.
```js
module.exports = {
overrideContext: (context, filename) => ({
...context,
HighLevelAPI: () => "I'm a high level API",
}),
};
```
- `rules: EvalRule[]`
The set of rules that defines how the matched files will be transformed during the evaluation.
`EvalRule` is an object with two fields:
- `test` is a regular expression or a function `(path: string) => boolean`;
- `action` is an `Evaluator` function, `"ignore"` or a name of the module that exports `Evaluator` function as a default export.
If `test` is omitted, the rule is applicable for all the files.
The last matched rule is used for transformation. If the last matched action for a file is `"ignore"` the file will be evaluated as is, so that file must not contain any js code that cannot be executed in nodejs environment (it's usually true for any lib in `node_modules`).
If you need to compile certain modules under `/node_modules/` (which can be the case in monorepo projects), it's recommended to do it on a module by module basis for faster transforms, e.g. `ignore: /node_modules[\/\\](?!some-module|other-module)/`. Example is using Regular Expressions negative lookahead.
The Information about `Evaluator`, its default setting and custom implementations can be founded it [evaluators section of How it works docs](./HOW_IT_WORKS.md#evaluators)
The default setup is:
```js
[
{
action: require.resolve('@linaria/shaker'),
},
{
test: /[\\/]node_modules[\\/]/,
action: 'ignore',
},
{
test: (filename, code) => {
if (!/[\\/]node_modules[\\/]/.test(filename)) {
return false;
}
return /(?:^|\*\/|;|})\s*(?:export|import)\s/m.test(code);
},
action: require.resolve('@linaria/shaker'),
}
];
```
- `tagResolver: (source, tag) => string`
A custom function to use when resolving template tags.
By default, linaria APIs like `css` and `styled` **must** be imported directly from the package – this is because babel needs to be able to recognize the API's to do static style extraction. `tagResolver` allows `css` and `styled` APIs to be imported from other files too.
`tagResolver` takes the path for the source module (eg. `@linaria/core`) and the name of imported tag (eg. `css`), and returns the full path to the related processor. If `tagResolver` returns `null`, the default tag processor will be used.
For example, we can use this to map `@linaria/core` , `@linaria/react` or `@linaria/atomic` where we re-export the module.
```js
{
tagResolver: (source, tag) => {
const pathToLocalFile = join(__dirname, './my-local-folder/linaria.js');
if (source === pathToLocalFile) {
if (tag === 'css') {
return require.resolve('@linaria/core/processors/css');
}
if (tag === 'styled') {
return require.resolve('@linaria/react/processors/styled');
}
}
return null;
};
}
```
We can then re-export and use linaria API's from `./my-local-folder`:
```js
// my-file.js
import { css, styled } from './my-local-folder/linaria';
export const MyComponent = styled.div`
color: red;
`;
export default css`
border: 1px solid black;
`;
```
```js
// ./my-local-folder/core.js
export * from '@linaria/core';
```
- `babelOptions: Object`
If you need to specify custom babel configuration, you can pass them here. These babel options will be used by Linaria when parsing and evaluating modules.
- `features: Record<string, FeatureFlag>`
A map of feature flags to enable/disable. See [Feature Flags](./FEATURE_FLAGS.md##feature-flags) for more information.
## `@linaria/babel-preset`
The preset pre-processes and evaluates the CSS. The bundler plugins use this preset under the hood. You also might want to use this preset if you import the components outside of the files handled by your bundler, such as on your server or in unit tests.
To use this preset, add `@linaria/babel-preset` to your Babel configuration at the end of the presets list:
`.babelrc`:
```diff
{
"presets": [
"@babel/preset-env",
"@babel/preset-react",
+ "@linaria"
]
}
```
The babel preset can accept the same options supported by the configuration file, however it's recommended to use the configuration file directly.
## Preact
If you wish you use Preact, we recommend you to use the `preact-cli` and start from there. The following configuration assumes you are using the default template provided by preact-cli. Start by creating your project using;
```
npx preact-cli create default my-project
```
On top of the default template, you will need to install `@babel/preset-react`. This is because Linaria works with JSX syntax. Otherwise, preact will throw an error saying that `@linaria/webpack-loader` can't parse JSX. Don't forget to install all required `@linaria`-packages!.
After that, your `package.json` should look like the following:
```diff
"devDependencies": {
+ "@babel/preset-react": "^7.8.3",
"enzyme": "^3.10.0",
"enzyme-adapter-preact-pure": "^2.0.0",
"eslint": "^6.0.1",
"eslint-config-preact": "^1.1.0",
"identity-obj-proxy": "^3.0.0",
"jest": "^24.9.0",
"jest-preset-preact": "^1.0.0",
"per-env": "^1.0.2",
"preact-cli": "^3.0.0-rc.6",
"preact-render-spy": "^1.2.1",
"sirv-cli": "^0.4.5"
},
"dependencies": {
+ "@linaria/babel-preset": "^3.0.0",
+ "@linaria/core": "^3.0.0",
+ "@linaria/react": "^3.0.0",
+ "@linaria/webpack-loader": "^3.0.0",
"preact": "^10.3.2",
"preact-render-to-string": "^5.1.4",
"preact-router": "^3.2.1"
},
```
> If you wish to work with TypeScript, you will also need to install `@babel/preset-typescript`
Now in your `preact.config.js`, we will modify the babel rule to use the necessary loaders and presets. Add the following:
```js
export default (config) => {
const { options, ...babelLoaderRule } = config.module.rules[0]; // Get the babel rule and options
options.presets.push('@babel/preset-react', '@linaria'); // Push the necessary presets
config.module.rules[0] = {
...babelLoaderRule,
loader: undefined, // Disable the predefined babel-loader on the rule
use: [
{
loader: 'babel-loader',
options,
},
{
loader: '@linaria/webpack-loader',
options: {
babelOptions: options, // Pass the current babel options to linaria's babel instance
},
},
],
};
};
```
> If you wish to work with TypeScript, add the `@babel/preset-typescript` preset before `@babel/preset-react`.
After all of that, you should be able to run `npm build`, and it should have no errors.
To test that everthing is working, go to a file, for example `components/Header/index.js`, and create a class name.
```js
import { h } from 'preact';
import { Link } from 'preact-router/match';
import style from './style.css';
import { css } from '@linaria/core';
const className = css`
color: red;
font-weight: 800;
`;
const Header = () => (
<header class={style.header}>
<h1>Preact App</h1>
<nav>
<Link activeClassName={style.active} href="/">
Home
</Link>
<Link activeClassName={style.active} href="/profile">
Me
</Link>
<Link activeClassName={style.active} href="/profile/john">
John
</Link>
</nav>
<button class={className}>Hello</button> //here I use it
</header>
);
export default Header;
```
> You can also use the `styled` variant, importing from `@linaria/react`.
If you run `npm run dev`, you should be able to see a button next to the nav title, with red bold text.
You can take a look at this example [here](../examples/Preact)
## Gatsby
If you wish you use Gatsby, we recommend you to use the `gatsby-cli` and start from there. The following configuration assumes you are using the default template provided by gatsby-cli. Start by creating your project using:
```
npx gatsby new my-project
```
Now, you have two options. You can use `gatsby-plugin-linaria` or create a custom config.
### gatsby-plugin-linaria
This is an easier and more straightforward way of integrating Linaria with Gatsby. Check [plugin docs](https://github.com/cometkim/gatsby-plugin-linaria) for instructions.
You can also take a look at the example [here](../examples/gatsby/plugin)
### Custom config
This is a bit more advanced way of integrating Linaria into your Gatsby project.
First, you will need to install `@linaria/babel-preset` and `babel-preset-gatsby`. Then, create `babel.config.js` in the root of your project with the following contents:
```js
module.exports = {
presets: [
'babel-preset-gatsby',
[
'@linaria',
{
evaluate: true,
displayName: process.env.NODE_ENV !== 'production',
},
],
],
};
```
You can read more about configuring Babel in Gatsby projects in [their docs](https://www.gatsbyjs.org/docs/babel/).
Besides that, you will need to alter Gatsby's Webpack config to modify the Babel loader. This can be done in `gatsby-node.js` file. Consider the following snippet:
```js
exports.onCreateWebpackConfig = ({ actions, loaders, getConfig, stage }) => {
const config = getConfig();
config.module.rules = [
...config.module.rules.filter(
(rule) => String(rule.test) !== String(/\.js?$/)
),
{
...loaders.js(),
test: /\.js?$/,
loader: '@linaria/webpack-loader',
options: {
sourceMap: stage.includes('develop'),
displayName: stage.includes('develop'),
babelOptions: {
presets: ['babel-preset-gatsby'],
},
},
exclude: /node_modules/,
},
];
actions.replaceWebpackConfig(config);
};
```
If you want to know more about extending Webpack config in Gatsby projects, check out [relevant Gatsby docs](https://www.gatsbyjs.org/docs/add-custom-webpack-config/).
With that done, you should be all set! You can take a look at the minimal example using the above configuration [here](../examples/gatsby/custom-config).
================================================
FILE: docs/CRITICAL_CSS.md
================================================
# Critical CSS extraction
Since Linaria extracts the CSS statically at build time, you don't need to setup a server rendering. Usually, critical CSS extraction will be automatic if you are code splitting your code and using something like [mini-css-extract-plugin](https://github.com/webpack-contrib/mini-css-extract-plugin) for webpack to generate your CSS files.
If you're not code splitting, or the initial CSS chunk is not representative of initially rendered content, you might want to extract critical CSS using the `collect` helper we provide to ship the minimal amount of CSS used in the page to the browser. To be able to use the `collect` helper, you need to provide the initial HTML, which usually means that you need to have SSR setup for your web app.
The `collect` method takes some HTML and CSS and gives you the critical CSS:
```js
import { collect } from '@linaria/server';
const { critical, other } = collect(html, css);
```
For example, in an express app with React, you could do something like the following:
```js
import fs from 'fs';
import express from 'express';
import crypto from 'crypto';
import React from 'react';
import ReactDOMServer from 'react-dom/server';
import { collect } from '@linaria/server';
import App from './App';
const cache = {};
const css = fs.readFileSync('./dist/styles.css', 'utf8');
const app = express();
app.get('/', (req, res) => {
const html = ReactDOMServer.renderToString(<App />);
const { critical, other } = collect(html, css);
const slug = crypto.createHash('md5').update(other).digest('hex');
cache[slug] = other;
res.end(`
<html lang="en">
<head>
<title>App</title>
<style type="text/css">${critical}</style>
</head>
<body>
<div id="root">
${html}
</div>
<link rel="css" href="/styles/${slug}" />
</body>
</html>
`);
});
app.get('/styles/:slug', (req, res) => {
res.type('text/css');
res.end(cache[req.params.slug])
});
app.listen(3242);
```
By placing the non-critical CSS at the end of `body`, you can make sure that page rendering is not blocked until the CSS is loaded. You can also load the non-critical CSS lazily with JavaScript once the page has loaded for a more efficient strategy. However, it's highly recommended that you take advantage of code splitting in webpack which gives you automatic CSS chunks in addition to critical CSS.
================================================
FILE: docs/DYNAMIC_STYLES.md
================================================
# Dynamic styles with `css` tag
Sometimes we have some styles based on component's props or state, or dynamic in some way. If you use the `styled` helper with React, this is automatically handled using CSS custom properties. But we cannot do the same for `css` tags since they aren't linked to any component, and so we don't have access to state and props. However, there are some approaches to tackle this, each with their own limitations.
## Inline styles
Inline styles are the most straightforward way to use dynamic styles. Pass a `style` object with the dynamic styles, and you're done.
```js
import React from 'react';
export function Pager({ index, children }) {
return (
<div style={{ transform: `translateX(${index * 100}%)` }}>
{children}
</div>
);
}
```
However, it's not possible to use inline styles with pseudo-selectors or media queries.
## CSS custom properties
[CSS custom properties](https://developer.mozilla.org/en-US/docs/Web/CSS/--*) can be used to expose dynamic properties to the CSS.
```js
import React from 'react';
import { css } from '@linaria/core';
const box = css`
height: var(--box-size);
width: var(--box-size);
`;
export function Box({ size }) {
return (
<div
className={box}
style={{ '--box-size': size }}
/>
);
}
```
The [browser support for CSS custom properties](http://caniuse.com/#feat=css-variables) is limited, and it's not polyfilled. Therefore it's not a viable approach if you need to support older browsers. Worth noting that custom properties cascade, so if you don't override the value for the current element, and a custom property with the same name exists for a parent element, it'll be used instead.
## Data attributes
In cases where you know the values ahead of time, you can use [data attributes](https://developer.mozilla.org/en-US/docs/Learn/HTML/Howto/Use_data_attributes) to dynamically switch the styles that are applied.
```js
import React from 'react';
import { css } from '@linaria/core';
const box = css`
&[data-valid] {
color: yellow;
}
&[data-valid="invalid"] {
color: red;
}
&[data-valid="valid"] {
color: green;
}
`
export function Box({ color, valid }) {
return (
<div
className={box}
data-valid={valid ? 'valid' : 'invalid'}
/>
);
}
```
## `currentColor`
For color values, browsers support a `currentColor` property which points to the text color of the element. It is well supported in all browsers.
```js
import React from 'react';
import { css } from '@linaria/core';
const box = css`
background-color: currentColor;
`;
const content = css`
color: white;
`;
export function Box({ color }) {
return (
<div
className={box}
style={{ color }}
>
<span className={content}>
¯\_(ツ)_/¯
</span>
</div>
);
}
```
You cannot use this approach if the dynamic value is not a color, or the element contains some text which needs to be styled with a different color. If the element has children, you will need to reset the `color` property for the text.
================================================
FILE: docs/FEATURE_FLAGS.md
================================================
# Feature Flags
Feature flags are used to enable or disable specific features provided. The `features` option in the configuration allows you to control the availability of these features.
## Syntax for Specifying Flags
- `true`: Enables the feature for all files.
- `false`: Disables the feature for all files.
- `"glob"`: Enables the feature only for files that match the specified glob pattern.
- `["glob1", "glob2"]`: Enables the feature for files matching any of the specified glob patterns.
- `["glob1", "!glob2"]`: Enables the feature for files matching `glob1` but excludes files that match `glob2`.
# `dangerousCodeRemover` Feature
The `dangerousCodeRemover` is a flag that is enabled by default. It is designed to enhance the static evaluation of values that are interpolated in styles and to optimize the processing of styled-wrapped components during the build stage. This optimization is crucial for maintaining a stable and fast build process. It is important to note that the `dangerousCodeRemover` does not impact the runtime code; it solely focuses on the code used during the build.
## How It Works
During the build process, Linaria statically analyzes the CSS-in-JS codebase and evaluates the styles and values that are being interpolated. The `dangerousCodeRemover` steps in at this stage to remove potentially unsafe code, which includes code that might interact with browser-specific APIs, make HTTP requests, or perform other runtime-specific operations. By removing such code, the evaluation becomes more reliable, predictable, and efficient.
## Benefits
Enabling the `dangerousCodeRemover` feature provides several benefits:
1. **Stability**: The removal of potentially unsafe code ensures that the build process remains stable. It minimizes the chances of encountering build-time errors caused by unsupported browser APIs or non-static operations.
2. **Performance**: Removing unnecessary code results in faster build times. The build tool can efficiently process and evaluate the styles and components without unnecessary overhead, leading to quicker development cycles.
## Fine-Tuning the Removal
While the `dangerousCodeRemover` is highly effective at optimizing the build process, there may be cases where it becomes overly aggressive and removes code that is actually required for your specific use case. In such situations, you have the flexibility to fine-tune the behavior of the remover.
By leveraging the `features` option in the configuration, you can selectively disable the `dangerousCodeRemover` for specific files. This allows you to preserve valuable code that may not be safely evaluated during the build process.
### Example
Suppose you have a file named `specialComponent.js` that contains code that should not be deleted. By adding the following entry to your `features` configuration:
```js
{
features: {
dangerousCodeRemover: ["**/*", "!**/specialComponent.js"],
},
}
```
You are instructing Linaria to exclude the `specialComponent.js` file from the removal process. As a result, any code within this file that would have been removed by the `dangerousCodeRemover` will be retained in the build output.
# `globalCache` Feature
The `globalCache` is enabled by default. Linaria uses two levels of caching to improve the performance of the build process. The first level is used to cache transformation and evaluation results for each `transform` call, usually a single call of Webpack's loader or Vite's transform hook. The second level is used to cache the results of the entire build process. The `globalCache` feature controls the second level of caching. Turning off this feature will result in a slower build process but decreased memory usage.
# `happyDOM` Feature
The `happyDOM` is enabled by default. This feature enables usage of https://github.com/capricorn86/happy-dom to emulate a browser environment during the build process. Typically, the `dangerousCodeRemover` feature should remove all browser-related code. However, some libraries may still contain browser-specific code that cannot be statically evaluated. In such cases, the `happyDOM` feature can be used to emulate a browser environment during the build process. This allows Linaria to evaluate the code without encountering errors caused by missing browser APIs.
# `softErrors` Feature
The `softErrors` is disabled by default. It is designed to provide a more lenient evaluation of styles and values that are interpolated in styles. This flag is useful for debugging and prevents the build from failing even if some files cannot be processed with Linaria.
# 'useBabelConfigs' Feature
The `useBabelConfigs` feature is enabled by default. If it is enabled, Linaria will try to resolve the `.babelrc` file for each processed file. Otherwise, it will use the default Babel configuration from `babelOptions` in the configuration.
Please note that the default value of `useBabelConfigs` will be changed to `false` in the next major release.
================================================
FILE: docs/HOW_IT_WORKS.md
================================================
# How it works
Linaria consists of 2 parts:
1. Babel plugin
2. Bundler integration
## Babel plugin
The Babel plugin will look for `css` and `styled` tags in your code, extract the CSS out and return it in the file's metadata. It will also generate unique class names based on the hash of the filename.
> To get a deep dive into Linaria babel plugin internals, check [debugging section of Contributing docs](../CONTRIBUTING.md#debugging-and-deep-dive-into-babel-plugin)
When using the `styled` tag, dynamic interpolations will be replaced with CSS custom properties. References to constants in the scope will also be inlined. If the same expression is used multiple times, the plugin will create a single CSS custom property for those.
The interpolations used for the CSS custom properties are left in the file, and are passed to the helper which creates the React components. Function interpolations receive the component's props and their return value will be used as the value for the CSS custom property. For other expressions, their result is used as is. If the resulting values aren't strings, they'll be converted to a string before setting the property. Inline styles are used to set the custom properties.
For example, the plugin will transpile this:
```js
import { styled } from '@linaria/react';
import { families, sizes } from './fonts';
const background = 'yellow';
const Title = styled.h1`
font-family: ${families.serif};
`;
const Container = styled.div`
font-size: ${sizes.medium}px;
background-color: ${background};
color: ${props => props.color};
width: ${100 / 3}%;
border: 1px solid red;
&:hover {
border-color: blue;
}
`;
```
To this:
```js
import { styled } from '@linaria/react';
import { families, sizes } from './fonts';
const background = 'yellow';
const Title = styled('h1')({
name: 'Title',
class: 'Title_t1ugh8t',
vars: {
't1ugh8t9-0': [families.serif],
},
});
const Container = styled('div')({
name: 'Container',
class: 'Container_c1ugh8t',
vars: {
'c1ugh8t9-0': [sizes.medium, 'px'],
'c1ugh8t9-2': [props => props.color],
},
});
```
The extracted CSS will look something like this:
```css
.Title_t1ugh8t9 {
font-family: var(--t1ugh8t-0);
}
.Container_c1ugh8t9 {
font-size: var(--c1ugh8t-0);
background-color: yellow;
color: var(--c1ugh8t-2);
width: 33.333333333333336%;
border: 1px solid red;
}
.Container_c1ugh8t9:hover {
border-color: blue;
}
```
If we encounter a valid unit directly after the interpolation, it'll be passed to the helper so that the correct unit is used when setting the property. This allows you to write this:
```js
const Title = styled.h1`
font-size: ${large}px;
`;
```
Instead of having to write this:
```js
const Title = styled.h1`
font-size: ${large + 'px'};
`;
```
It's necessary since if we just replaced the interpolation as is, it wouldn't be a valid syntax:
```css
.Title_t1ugh8t9 {
font-size: var(--t1ugh8t9-0-0)px; /* you can't have 'px' after the `var(..)` */
}
```
If we encounter a JS object when inlining, the JS object is assumed to be a style rule and converted to a CSS string before inlining it. For example, if you write this:
```js
const absoluteFill = {
position: 'absolute',
top: 0,
right: 0,
bottom: 0,
left: 0,
};
const Container = styled.h1`
background-color: papayawhip;
${Box} {
${absoluteFill}
}
`;
```
It is equivalent to writing this:
```js
const Container = styled.h1`
background-color: papayawhip;
${Box} {
position: absolute;
top: 0;
right: 0;
bottom: 0;
left: 0;
}
`;
```
We support this usage because it allows you to use a library such as [polished.js](https://polished.js.org) which outputs object based styles along with Linaria.
If you've configured the plugin to evaluate expressions with `evaluate: true` (default), any dynamic expressions we encounter will be evaluated during the build-time in a sandbox, and the result will be included in the CSS. Since these expressions are evaluated at build time in Node, you cannot use any browser specific APIs or any API which is only available in runtime. Access to Node native modules such as `fs` is also not allowed inside the sandbox to prevent malicious scripts. In addition, to achieve consistent build output, you should also avoid doing any side effects in these expres
gitextract_xouc4tvv/
├── .all-contributorsrc
├── .changeset/
│ ├── README.md
│ └── config.json
├── .codecov.yml
├── .editorconfig
├── .eslintignore
├── .eslintrc.js
├── .git-blame-ignore-revs
├── .github/
│ ├── ISSUE_TEMPLATE/
│ │ ├── bug_report.md
│ │ ├── config.yml
│ │ ├── enhancement_request.md
│ │ └── feature_request.md
│ ├── PULL_REQUEST_TEMPLATE.md
│ ├── labels.json
│ └── workflows/
│ ├── check.yml
│ ├── main.yml
│ ├── release.yml
│ └── site-deploy.yml
├── .gitignore
├── .npmrc
├── .prettierrc
├── .syncpackrc.js
├── .vscode/
│ └── settings.json
├── CODE_OF_CONDUCT.md
├── CONTRIBUTING.md
├── LICENSE
├── README.md
├── babel.config.js
├── commitlint.config.js
├── docs/
│ ├── API.md
│ ├── ATOMIC_CSS.md
│ ├── BASICS.md
│ ├── BENEFITS.md
│ ├── BUNDLERS_INTEGRATION.md
│ ├── CLI.md
│ ├── CONFIGURATION.md
│ ├── CRITICAL_CSS.md
│ ├── DYNAMIC_STYLES.md
│ ├── FEATURE_FLAGS.md
│ ├── HOW_IT_WORKS.md
│ ├── LINTING.md
│ ├── MIGRATION_GUIDE.md
│ └── THEMING.md
├── examples/
│ ├── astro-solid/
│ │ ├── astro.config.js
│ │ ├── package.json
│ │ ├── pages/
│ │ │ ├── csr.tsx
│ │ │ ├── csr_child.tsx
│ │ │ ├── external.ts
│ │ │ └── index.astro
│ │ └── tsconfig.json
│ ├── esbuild/
│ │ ├── .gitignore
│ │ ├── app.js
│ │ ├── build.js
│ │ └── package.json
│ ├── rollup/
│ │ ├── .gitignore
│ │ ├── app.js
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ └── rollup.config.mjs
│ ├── vite/
│ │ ├── .linariarc.mjs
│ │ ├── app.js
│ │ ├── index.html
│ │ ├── package.json
│ │ └── vite.config.js
│ ├── vpssr-linaria-solid/
│ │ ├── package.json
│ │ ├── pages/
│ │ │ ├── html-js/
│ │ │ │ ├── _default.page.client.js
│ │ │ │ └── index.page.server.tsx
│ │ │ ├── html-only/
│ │ │ │ └── index.page.server.tsx
│ │ │ ├── index.page.server.tsx
│ │ │ ├── spa/
│ │ │ │ └── index.page.client.tsx
│ │ │ └── ssr/
│ │ │ ├── Counter.tsx
│ │ │ └── index.page.tsx
│ │ ├── renderer/
│ │ │ ├── _default.page.client.tsx
│ │ │ └── _default.page.server.tsx
│ │ ├── server.js
│ │ ├── tsconfig.json
│ │ └── vite.config.js
│ └── webpack5/
│ ├── app.js
│ ├── babel.config.js
│ ├── package.json
│ └── webpack.config.js
├── greenkeeper.json
├── jest.config.js
├── link-wyw.sh
├── package.json
├── packages/
│ ├── atomic/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── processors/
│ │ │ ├── css.js
│ │ │ └── styled.js
│ │ ├── src/
│ │ │ ├── CSSProperties.ts
│ │ │ ├── css.ts
│ │ │ ├── index.ts
│ │ │ └── processors/
│ │ │ ├── css.ts
│ │ │ ├── helpers/
│ │ │ │ ├── atomize.ts
│ │ │ │ └── propertyPriority.ts
│ │ │ └── styled.ts
│ │ └── tsconfig.json
│ ├── core/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── __dtslint__/
│ │ │ ├── core.ts
│ │ │ ├── index.d.ts
│ │ │ ├── tsconfig.eslint.json
│ │ │ └── tsconfig.json
│ │ ├── __tests__/
│ │ │ ├── cx.test.ts
│ │ │ └── detect-core-js.test.ts
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── processors/
│ │ │ └── css.js
│ │ ├── src/
│ │ │ ├── CSSProperties.ts
│ │ │ ├── css.ts
│ │ │ ├── cx.ts
│ │ │ ├── index.ts
│ │ │ └── processors/
│ │ │ └── css.ts
│ │ └── tsconfig.json
│ ├── interop/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── __tests__/
│ │ │ ├── __snapshots__/
│ │ │ │ └── index.test.ts.snap
│ │ │ └── index.test.ts
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── src/
│ │ │ └── index.ts
│ │ └── tsconfig.json
│ ├── linaria/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── babel/
│ │ │ └── package.json
│ │ ├── babel.config.js
│ │ ├── evaluators/
│ │ │ └── package.json
│ │ ├── loader/
│ │ │ └── package.json
│ │ ├── package.json
│ │ ├── react/
│ │ │ └── package.json
│ │ ├── rollup/
│ │ │ └── package.json
│ │ ├── server/
│ │ │ └── package.json
│ │ ├── src/
│ │ │ ├── core.ts
│ │ │ ├── react.ts
│ │ │ └── server.ts
│ │ ├── stylelint-config/
│ │ │ └── package.json
│ │ └── tsconfig.json
│ ├── postcss-linaria/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── __tests__/
│ │ │ ├── __utils__/
│ │ │ │ └── index.ts
│ │ │ ├── locationCorrection.test.ts
│ │ │ ├── parse.test.ts
│ │ │ ├── stringify.test.ts
│ │ │ ├── stylelint.test.ts
│ │ │ └── utils.test.ts
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── src/
│ │ │ ├── index.ts
│ │ │ ├── locationCorrection.ts
│ │ │ ├── parse.ts
│ │ │ ├── stringify.ts
│ │ │ └── util.ts
│ │ └── tsconfig.json
│ ├── react/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── __dtslint-react17__/
│ │ │ ├── index.d.ts
│ │ │ ├── react17.tsx
│ │ │ ├── stubs/
│ │ │ │ ├── jsx-runtime.d.ts
│ │ │ │ └── react17.d.ts
│ │ │ ├── tsconfig.eslint.json
│ │ │ └── tsconfig.json
│ │ ├── __dtslint__/
│ │ │ ├── index.d.ts
│ │ │ ├── styled.ts
│ │ │ ├── tsconfig.eslint.json
│ │ │ └── tsconfig.json
│ │ ├── __tests__/
│ │ │ ├── __snapshots__/
│ │ │ │ └── styled.test.tsx.snap
│ │ │ ├── detect-core-js.test.ts
│ │ │ └── styled.test.tsx
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── processors/
│ │ │ └── styled.js
│ │ ├── src/
│ │ │ ├── index.ts
│ │ │ ├── processors/
│ │ │ │ └── styled.ts
│ │ │ ├── react-html-attributes.d.ts
│ │ │ └── styled.ts
│ │ └── tsconfig.json
│ ├── server/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── __tests__/
│ │ │ ├── __snapshots__/
│ │ │ │ └── collect.test.ts.snap
│ │ │ └── collect.test.ts
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── src/
│ │ │ ├── collect.ts
│ │ │ └── index.ts
│ │ └── tsconfig.json
│ ├── stylelint/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── src/
│ │ │ ├── index.ts
│ │ │ └── preprocessor.ts
│ │ └── tsconfig.json
│ ├── stylelint-config-standard-linaria/
│ │ ├── CHANGELOG.md
│ │ ├── README.md
│ │ ├── babel.config.js
│ │ ├── package.json
│ │ ├── src/
│ │ │ └── index.js
│ │ └── tsconfig.json
│ └── testkit/
│ ├── CHANGELOG.md
│ ├── jest.config.js
│ ├── package.json
│ ├── src/
│ │ ├── __fixtures__/
│ │ │ ├── assignToExport.js
│ │ │ ├── bar.js
│ │ │ ├── circular-imports/
│ │ │ │ ├── bar.js
│ │ │ │ ├── constants.js
│ │ │ │ ├── foo.js
│ │ │ │ └── index.js
│ │ │ ├── complex-component.js
│ │ │ ├── components-library.js
│ │ │ ├── computedKeys.js
│ │ │ ├── enums.ts
│ │ │ ├── escape-character.js
│ │ │ ├── foo-nonstatic.js
│ │ │ ├── foo.js
│ │ │ ├── linaria-ui-library/
│ │ │ │ ├── components/
│ │ │ │ │ └── index.js
│ │ │ │ ├── hocs.js
│ │ │ │ ├── non-linaria-components.js
│ │ │ │ ├── package.json
│ │ │ │ └── types.ts
│ │ │ ├── loop/
│ │ │ │ ├── a.js
│ │ │ │ ├── ab.js
│ │ │ │ ├── b.js
│ │ │ │ ├── ba.js
│ │ │ │ └── index.js
│ │ │ ├── module-reexport.js
│ │ │ ├── non-linaria-ui-library/
│ │ │ │ ├── index.js
│ │ │ │ └── package.json
│ │ │ ├── objectExport.js
│ │ │ ├── re-exports/
│ │ │ │ ├── constants.js
│ │ │ │ ├── empty.js
│ │ │ │ ├── foo.js
│ │ │ │ └── index.js
│ │ │ ├── reexports.js
│ │ │ ├── runNearFramePaint.js
│ │ │ ├── sample-data.json
│ │ │ ├── sample-script.cjs
│ │ │ ├── sample-script.js
│ │ │ ├── sample-typescript.tsx
│ │ │ ├── self-import.js
│ │ │ ├── sequenceExport.js
│ │ │ ├── slugify.js
│ │ │ ├── ts-compiled-re-exports/
│ │ │ │ ├── constants.js
│ │ │ │ └── index.js
│ │ │ ├── ts-data.ts
│ │ │ └── with-babelrc/
│ │ │ ├── .babelrc.js
│ │ │ └── index.js
│ │ ├── __snapshots__/
│ │ │ ├── babel.test.ts.snap
│ │ │ └── transform.test.ts.snap
│ │ ├── __utils__/
│ │ │ └── linaria-snapshot-serializer.ts
│ │ ├── babel.test.ts
│ │ └── transform.test.ts
│ └── tsconfig.json
├── pnpm-workspace.yaml
├── react/
│ └── package.json
├── tsconfig.eslint.json
├── tsconfig.json
├── tsconfig.prod.json
├── tslint.json
├── turbo.json
└── website/
├── .eslintrc
├── CHANGELOG.md
├── babel.config.js
├── index.html
├── linaria.config.js
├── package.json
├── serve.config.js
├── src/
│ ├── .eslintrc
│ ├── api/
│ │ ├── index.js
│ │ └── react/
│ │ └── index.js
│ ├── components/
│ │ ├── App.jsx
│ │ ├── Container.js
│ │ ├── Example.js
│ │ ├── Header.jsx
│ │ └── Hero.jsx
│ ├── index.jsx
│ ├── server.jsx
│ └── styles/
│ ├── constants.js
│ └── utils.js
├── stylelint.config.js
└── webpack.config.js
SYMBOL INDEX (137 symbols across 44 files)
FILE: examples/astro-solid/pages/csr.tsx
constant GLOBAL_VARS (line 6) | const GLOBAL_VARS = {
function CSRComponent (line 10) | function CSRComponent() {
FILE: examples/astro-solid/pages/csr_child.tsx
function CSRChild (line 4) | function CSRChild() {
FILE: examples/vpssr-linaria-solid/pages/html-js/_default.page.client.js
function handleCounter (line 6) | function handleCounter() {
FILE: examples/vpssr-linaria-solid/pages/html-js/index.page.server.tsx
function Page (line 3) | function Page() {
FILE: examples/vpssr-linaria-solid/pages/html-only/index.page.server.tsx
function Page (line 3) | function Page() {
FILE: examples/vpssr-linaria-solid/pages/index.page.server.tsx
function Page (line 1) | function Page() {
FILE: examples/vpssr-linaria-solid/pages/spa/index.page.client.tsx
function Page (line 4) | function Page() {
FILE: examples/vpssr-linaria-solid/pages/ssr/Counter.tsx
function Counter (line 3) | function Counter() {
FILE: examples/vpssr-linaria-solid/pages/ssr/index.page.tsx
function Page (line 4) | function Page() {
FILE: examples/vpssr-linaria-solid/renderer/_default.page.client.tsx
function render (line 3) | async function render(pageContext: PageContextBuiltInClient) {
FILE: examples/vpssr-linaria-solid/renderer/_default.page.server.tsx
function render (line 5) | function render(pageContext: PageContextBuiltInClient) {
FILE: examples/vpssr-linaria-solid/server.js
function main (line 10) | async function main () {
FILE: packages/atomic/src/CSSProperties.ts
type CSSProperties (line 1) | type CSSProperties = {
FILE: packages/atomic/src/css.ts
type CSS (line 5) | type CSS = (
FILE: packages/atomic/src/processors/css.ts
class AtomicCssProcessor (line 11) | class AtomicCssProcessor extends CssProcessor {
method classes (line 14) | private get classes(): string {
method doRuntimeReplacement (line 22) | public override doRuntimeReplacement(): void {
method extractRules (line 26) | public override extractRules(
FILE: packages/atomic/src/processors/helpers/atomize.ts
function hashProperty (line 17) | function hashProperty(property: string) {
function atomize (line 39) | function atomize(cssText: string, hasPriority = false) {
FILE: packages/atomic/src/processors/helpers/propertyPriority.ts
function getPropertyPriority (line 199) | function getPropertyPriority(property: string) {
FILE: packages/atomic/src/processors/styled.ts
class AtomicStyledProcessor (line 12) | class AtomicStyledProcessor extends StyledProcessor {
method classes (line 15) | private get classes(): string {
method extractRules (line 25) | public override extractRules(
method getProps (line 60) | protected override getProps(): IProps {
method getVariableId (line 67) | protected override getVariableId(
FILE: packages/core/src/CSSProperties.ts
type CSSProperties (line 1) | type CSSProperties = {
FILE: packages/core/src/css.ts
type WYWEvalMeta (line 4) | type WYWEvalMeta = { __wyw_meta: unknown };
type CSS (line 6) | type CSS = (
FILE: packages/core/src/cx.ts
type LinariaClassName (line 1) | type LinariaClassName = string & { __linariaClassName: true };
type ClassName (line 3) | type ClassName<T = string> = T | false | void | null | 0 | '';
type ICX (line 5) | interface ICX {
FILE: packages/core/src/processors/css.ts
class CssProcessor (line 5) | class CssProcessor extends TaggedTemplateProcessor {
method asSelector (line 6) | public override get asSelector(): string {
method value (line 10) | public override get value(): StringLiteral {
method addInterpolation (line 15) | public override addInterpolation(
method doEvaltimeReplacement (line 25) | public override doEvaltimeReplacement(): void {
method doRuntimeReplacement (line 29) | public override doRuntimeReplacement(): void {
method extractRules (line 33) | public override extractRules(
FILE: packages/interop/src/index.ts
type Core (line 11) | type Core = typeof core;
method TaggedTemplateExpression (line 44) | TaggedTemplateExpression(path: NodePath<TaggedTemplateExpression>) {
FILE: packages/postcss-linaria/__tests__/__utils__/index.ts
function createTestAst (line 5) | function createTestAst(source: string): {
function getSourceForNodeByLoc (line 14) | function getSourceForNodeByLoc(source: string, node: Node): string {
function getSourceForNodeByRange (line 47) | function getSourceForNodeByRange(source: string, node: Node): string {
FILE: packages/postcss-linaria/src/locationCorrection.ts
function computeCorrectedString (line 103) | function computeCorrectedString(
function computeCorrectedRawValue (line 147) | function computeCorrectedRawValue<T extends AnyNode>(
function computeBeforeAfter (line 172) | function computeBeforeAfter(
function locationCorrectionWalker (line 262) | function locationCorrectionWalker(
FILE: packages/postcss-linaria/src/stringify.ts
class LinariaStringifier (line 60) | class LinariaStringifier extends Stringifier {
method constructor (line 62) | public constructor(builder: Builder) {
method atrule (line 86) | public override atrule(node: AtRule, semicolon?: boolean) {
method comment (line 99) | public override comment(node: Comment): void {
method decl (line 120) | public override decl(node: Declaration, semicolon: boolean): void {
method document (line 144) | public override document(node: Document): void {
method raw (line 153) | public override raw(
method rawValue (line 171) | public override rawValue(node: AnyNode, prop: string): string {
method root (line 181) | public override root(node: Root): void {
method rule (line 196) | public override rule(node: Rule): void {
FILE: packages/react/__dtslint-react17__/stubs/react17.d.ts
type ElementType (line 5) | type ElementType = unknown;
type CSSProperties (line 7) | interface CSSProperties {
type FunctionComponent (line 11) | interface FunctionComponent<P = Record<string, unknown>> {
type IntrinsicElements (line 23) | interface IntrinsicElements {
FILE: packages/react/__dtslint__/styled.ts
function isExtends (line 10) | function isExtends<C, T>(arg1?: C, arg2?: T): C extends T ? 'extends' : ...
type GridProps (line 159) | type GridProps = { container?: false } | { container: true; spacing: num...
type BaseProps (line 173) | interface BaseProps {
type ComponentProps (line 178) | interface ComponentProps extends BaseProps {
FILE: packages/react/src/processors/styled.ts
type WrappedNode (line 39) | type WrappedNode =
type IProps (line 43) | interface IProps {
class StyledProcessor (line 60) | class StyledProcessor extends TaggedTemplateProcessor {
method constructor (line 67) | constructor(params: Params, ...args: TailProcessorParams) {
method asSelector (line 177) | public override get asSelector(): string {
method value (line 181) | public override get value(): ObjectExpression {
method tagExpression (line 211) | protected get tagExpression(): CallExpression {
method tagExpressionArgument (line 216) | protected get tagExpressionArgument(): Expression {
method addInterpolation (line 229) | public override addInterpolation(
method doEvaltimeReplacement (line 247) | public override doEvaltimeReplacement(): void {
method doRuntimeReplacement (line 251) | public override doRuntimeReplacement(): void {
method extractRules (line 262) | public override extractRules(
method toString (line 293) | public override toString(): string {
method getCustomVariableId (line 307) | protected getCustomVariableId(
method getProps (line 323) | protected getProps(): IProps {
method getTagComponentProps (line 348) | protected getTagComponentProps(props: IProps): ObjectExpression {
method getVariableContext (line 385) | protected getVariableContext(
method getVariableId (line 409) | protected getVariableId(
FILE: packages/react/src/react-html-attributes.d.ts
type IElements (line 2) | interface IElements {
type IAttributes (line 7) | interface IAttributes {
FILE: packages/react/src/styled.ts
type WYWEvalMeta (line 15) | type WYWEvalMeta = { __wyw_meta: unknown };
type NoInfer (line 17) | type NoInfer<A> = [A][A extends any ? 0 : never];
type Component (line 19) | type Component<TProps> =
type Has (line 23) | type Has<T, TObj> = [T] extends [TObj] ? T : T & TObj;
type Options (line 25) | type Options = {
function filterProps (line 58) | function filterProps<T extends Record<string, unknown>, TKeys extends ke...
type IProps (line 104) | interface IProps {
type IntrinsicElements (line 113) | interface IntrinsicElements {}
type GlobalJSXIntrinsicElements (line 119) | type GlobalJSXIntrinsicElements = JSX.IntrinsicElements;
type IntrinsicElements (line 124) | interface IntrinsicElements extends GlobalJSXIntrinsicElements {}
type IntrinsicElements (line 128) | type IntrinsicElements = React.JSX.IntrinsicElements;
function styled (line 156) | function styled(tag: any): any {
type StyledComponent (line 259) | type StyledComponent<T> = WYWEvalMeta &
type StaticPlaceholder (line 264) | type StaticPlaceholder = string | number | CSSProperties | WYWEvalMeta;
type HtmlStyledTag (line 266) | type HtmlStyledTag<TName extends keyof IntrinsicElements> = <
type ComponentStyledTagWithoutInterpolation (line 280) | type ComponentStyledTagWithoutInterpolation<TOrigCmp> = (
type ComponentStyledTagWithInterpolation (line 289) | type ComponentStyledTagWithInterpolation<TTrgProps, TOrigCmp> = <OwnProp...
type StyledJSXIntrinsics (line 299) | type StyledJSXIntrinsics = {
type Styled (line 303) | type Styled = typeof styled & StyledJSXIntrinsics;
method get (line 307) | get(o, prop: keyof IntrinsicElements) {
FILE: packages/server/src/collect.ts
type CollectResult (line 4) | type CollectResult = {
type ClassnameModifiers (line 9) | interface ClassnameModifiers {
function escapeRegex (line 18) | function escapeRegex(string: string) {
function collect (line 53) | function collect(
FILE: packages/stylelint/src/preprocessor.ts
type Errors (line 7) | type Errors = {
type Cache (line 23) | type Cache = {
type Warning (line 27) | type Warning = {
type LintResult (line 35) | type LintResult = {
type IPosition (line 40) | interface IPosition {
type ISourceOffset (line 45) | interface ISourceOffset {
function preprocessor (line 51) | function preprocessor() {
FILE: packages/testkit/src/__fixtures__/enums.ts
type Colors (line 1) | enum Colors {
FILE: packages/testkit/src/__fixtures__/linaria-ui-library/types.ts
type ComponentType (line 1) | type ComponentType = 'class' | 'function' | 'arrow';
FILE: packages/testkit/src/__fixtures__/runNearFramePaint.js
function runNearFramePaint (line 11) | function runNearFramePaint(callback) {
FILE: packages/testkit/src/__fixtures__/slugify.js
function UInt32 (line 10) | function UInt32(str, pos) {
function UInt16 (line 19) | function UInt16(str, pos) {
function Umul32 (line 23) | function Umul32(n, m) {
function doHash (line 31) | function doHash(str, seed = 0) {
function slugify (line 77) | function slugify(code) {
FILE: packages/testkit/src/__fixtures__/ts-data.ts
type TestEnum (line 1) | enum TestEnum {
FILE: packages/testkit/src/__utils__/linaria-snapshot-serializer.ts
type Serializer (line 4) | type Serializer<T> = {
FILE: packages/testkit/src/babel.test.ts
type PartialOptions (line 34) | type PartialOptions = Partial<Omit<PluginOptions, 'features'>> & {
type Options (line 38) | type Options = [
function transform (line 121) | async function transform(
function transformFile (line 170) | async function transformFile(filename: string, opts: Options) {
function hasNotBeenProcessed (line 191) | function hasNotBeenProcessed(filename: string) {
FILE: packages/testkit/src/transform.test.ts
type TransformUrlArgs (line 26) | type TransformUrlArgs = Parameters<typeof transformUrl>;
FILE: website/src/components/App.jsx
function Index (line 13) | function Index() {
FILE: website/src/components/Header.jsx
function Header (line 9) | function Header() {
FILE: website/src/components/Hero.jsx
function Hero (line 9) | function Hero() {
Condensed preview — 282 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (794K chars).
[
{
"path": ".all-contributorsrc",
"chars": 28250,
"preview": "{\n \"projectName\": \"linaria\",\n \"projectOwner\": \"callstack\",\n \"files\": [\n \"README.md\"\n ],\n \"imageSize\": 100,\n \"co"
},
{
"path": ".changeset/README.md",
"chars": 510,
"preview": "# Changesets\n\nHello and welcome! This folder has been automatically generated by `@changesets/cli`, a build tool that wo"
},
{
"path": ".changeset/config.json",
"chars": 277,
"preview": "{\n \"$schema\": \"https://unpkg.com/@changesets/config@2.0.0/schema.json\",\n \"changelog\": \"@changesets/cli/changelog\",\n \""
},
{
"path": ".codecov.yml",
"chars": 137,
"preview": "coverage:\n precision: 2\n round: down\n range: 70...100\n\n status:\n project: true\n patch: true\n changes: false"
},
{
"path": ".editorconfig",
"chars": 415,
"preview": "# EditorConfig helps developers define and maintain consistent\n# coding styles between different editors and IDEs\n# edit"
},
{
"path": ".eslintignore",
"chars": 113,
"preview": "__fixtures__/\ncoverage/\nlib/\nesm/\npackages/*/bin/\npackages/*/types/\ndist/\nbuild/\nnode_modules/\nvendor/\nexamples/\n"
},
{
"path": ".eslintrc.js",
"chars": 7790,
"preview": "const noRestrictedSyntax =\n // eslint-disable-next-line import/no-extraneous-dependencies\n require('eslint-config-airb"
},
{
"path": ".git-blame-ignore-revs",
"chars": 0,
"preview": ""
},
{
"path": ".github/ISSUE_TEMPLATE/bug_report.md",
"chars": 782,
"preview": "---\nname: '🐛 Report a bug'\nabout: 'Report a reproducible bug or reproducible regression.'\nlabels: 'bug report 🦗, needs: "
},
{
"path": ".github/ISSUE_TEMPLATE/config.yml",
"chars": 189,
"preview": "blank_issues_enabled: false\ncontact_links:\n - name: 🤔 Questions and Help\n url: https://discord.gg/fAbHe67\n about:"
},
{
"path": ".github/ISSUE_TEMPLATE/enhancement_request.md",
"chars": 426,
"preview": "---\nname: '💬 Enhancement proposal'\nabout: Suggest an possible improvement of existing features.\nlabels: 'enhancement: pr"
},
{
"path": ".github/ISSUE_TEMPLATE/feature_request.md",
"chars": 393,
"preview": "---\nname: '💬 Feature proposal'\nabout: Suggest introduction of a new feature.\nlabels: 'feature: proposal 💬'\n---\n\n## Descr"
},
{
"path": ".github/PULL_REQUEST_TEMPLATE.md",
"chars": 763,
"preview": "<!--\nThanks for submitting a pull request!\nPlease provide enough information so that others can review your pull request"
},
{
"path": ".github/labels.json",
"chars": 11278,
"preview": "{\n \"labels\": {\n \"babel-plugin\": {\n \"name\": \"babel-plugin\",\n \"description\": \"\",\n \"colour\": \"006b75\"\n "
},
{
"path": ".github/workflows/check.yml",
"chars": 1593,
"preview": "name: Node.js CI\n\non:\n push:\n branches: [ master ]\n pull_request:\n branches: [ master ]\n\njobs:\n build:\n\n run"
},
{
"path": ".github/workflows/main.yml",
"chars": 531,
"preview": "name: labeler\non:\n issues:\n types: [opened, edited, reopened]\n pull_request:\n types: [opened, edited, reopened, "
},
{
"path": ".github/workflows/release.yml",
"chars": 1563,
"preview": "name: Release\n\non:\n push:\n branches:\n - master\n\nconcurrency: ${{ github.workflow }}-${{ github.ref }}\n\npermissi"
},
{
"path": ".github/workflows/site-deploy.yml",
"chars": 1248,
"preview": "name: Build and Deploy\non:\n push:\n branches:\n - master\njobs:\n build-and-deploy:\n runs-on: ubuntu-latest\n\n "
},
{
"path": ".gitignore",
"chars": 1074,
"preview": "### OS Junk ###\n.DS_Store\n*~\n.history\n\n### Node ###\n# Logs\nlogs\n*.log\nnpm-debug.log*\nyarn-debug.log*\nyarn-error.log*\n\n# "
},
{
"path": ".npmrc",
"chars": 16,
"preview": "lockfile = true\n"
},
{
"path": ".prettierrc",
"chars": 75,
"preview": "{\n \"endOfLine\": \"auto\",\n \"trailingComma\": \"es5\",\n \"singleQuote\": true\n}\n"
},
{
"path": ".syncpackrc.js",
"chars": 2432,
"preview": "module.exports = {\n dependencyTypes: ['dev', 'overrides', 'pnpmOverrides', 'prod', 'resolutions'],\n filter: '.',\n ind"
},
{
"path": ".vscode/settings.json",
"chars": 63,
"preview": "{\n \"typescript.tsdk\": \"website/node_modules/typescript/lib\"\n}\n"
},
{
"path": "CODE_OF_CONDUCT.md",
"chars": 3213,
"preview": "# Contributor Covenant Code of Conduct\n\n## Our Pledge\n\nIn the interest of fostering an open and welcoming environment, w"
},
{
"path": "CONTRIBUTING.md",
"chars": 5288,
"preview": "# Contributing to Linaria\n\n## [Code of Conduct](/CODE_OF_CONDUCT.md)\n\nWe want this community to be friendly and respectf"
},
{
"path": "LICENSE",
"chars": 1066,
"preview": "MIT License\n\nCopyright (c) 2017 Callstack\n\nPermission is hereby granted, free of charge, to any person obtaining a copy\n"
},
{
"path": "README.md",
"chars": 49615,
"preview": "<a href=\"https://www.callstack.com/open-source\" align=\"center\">\n <img alt=\"Linaria\" src=\"https://github.com/user-attach"
},
{
"path": "babel.config.js",
"chars": 2400,
"preview": "/*\n * The following environments are supported:\n *\n * (unspecified): Produces ES module output, no language features\n * "
},
{
"path": "commitlint.config.js",
"chars": 70,
"preview": "module.exports = {\n extends: ['@commitlint/config-conventional'],\n};\n"
},
{
"path": "docs/API.md",
"chars": 4648,
"preview": "# API\n\nLinaria exposes a core `css` method alongside with small, but just enough amount of helpers. Inside `@linaria/cor"
},
{
"path": "docs/ATOMIC_CSS.md",
"chars": 7778,
"preview": "# Atomic CSS\n\n## What is Atomic CSS?\n\nAtomic CSS is an approach to styling that reduces payload sizes for style delivery"
},
{
"path": "docs/BASICS.md",
"chars": 10022,
"preview": "# Basics\n\n## Basic syntax\n\nLinaria uses the [tagged template literal syntax](https://developer.mozilla.org/en-US/docs/We"
},
{
"path": "docs/BENEFITS.md",
"chars": 5892,
"preview": "# Why use Linaria\n\n## Advantages over regular CSS\n\n### 1. Selectors are scoped\n\nUnlike regular CSS, Linaria will generat"
},
{
"path": "docs/BUNDLERS_INTEGRATION.md",
"chars": 12743,
"preview": "# Bundlers Integration\n\n## Jump To\n\n- [webpack](#webpack)\n- [esbuild](#esbuild)\n- [Rollup](#Rollup)\n- [Vite](#Vite)\n- [S"
},
{
"path": "docs/CLI.md",
"chars": 1517,
"preview": "# CLI\n\nLinaria CLI (`@linaria/cli`) allows you to extract CSS from your source files using a command line.\n\n### Usage\n\n`"
},
{
"path": "docs/CONFIGURATION.md",
"chars": 15889,
"preview": "# Configuration\n\nLinaria uses [WyW-in-JS](https://wyw-in-js.dev) under the hood and can be customized using a JavaScript"
},
{
"path": "docs/CRITICAL_CSS.md",
"chars": 2420,
"preview": "# Critical CSS extraction\n\nSince Linaria extracts the CSS statically at build time, you don't need to setup a server ren"
},
{
"path": "docs/DYNAMIC_STYLES.md",
"chars": 3080,
"preview": "# Dynamic styles with `css` tag\n\nSometimes we have some styles based on component's props or state, or dynamic in some w"
},
{
"path": "docs/FEATURE_FLAGS.md",
"chars": 4995,
"preview": "# Feature Flags\n\nFeature flags are used to enable or disable specific features provided. The `features` option in the co"
},
{
"path": "docs/HOW_IT_WORKS.md",
"chars": 7024,
"preview": "# How it works\n\nLinaria consists of 2 parts:\n\n1. Babel plugin\n2. Bundler integration\n\n## Babel plugin\n\nThe Babel plugin "
},
{
"path": "docs/LINTING.md",
"chars": 3444,
"preview": "# Linting\n\nThere are separate installations based on whether you use stylelint v13 or stylelint v14\n\n## Stylelint 13\n\nFo"
},
{
"path": "docs/MIGRATION_GUIDE.md",
"chars": 4469,
"preview": "# Migration Guide\n\n# 7.x from 6.x\n\n## For Users\n\nLinaria 7 updates the WyW toolchain (`@wyw-in-js/*`) to `^1.0.0` (stabl"
},
{
"path": "docs/THEMING.md",
"chars": 2952,
"preview": "# Theming\n\nThere are several approaches you can use for theming. Depending on the browser support and requirements, you "
},
{
"path": "examples/astro-solid/astro.config.js",
"chars": 680,
"preview": "import { defineConfig } from 'astro/config';\nimport astro_solid from '@astrojs/solid-js';\nimport vite_wyw from '@wyw-in-"
},
{
"path": "examples/astro-solid/package.json",
"chars": 499,
"preview": "{\n \"name\": \"astro-solid-example\",\n \"version\": \"0.0.1\",\n \"license\": \"MIT\",\n \"main\": \"index.js\",\n \"type\": \"module\",\n "
},
{
"path": "examples/astro-solid/pages/csr.tsx",
"chars": 1175,
"preview": "import { css } from '@linaria/core';\nimport { CSRChild, cssVariableFromModule } from './csr_child';\nimport { astroTextCo"
},
{
"path": "examples/astro-solid/pages/csr_child.tsx",
"chars": 359,
"preview": "import { css } from '@linaria/core';\nimport { astroTextColor } from './external';\n\nexport function CSRChild() {\n return"
},
{
"path": "examples/astro-solid/pages/external.ts",
"chars": 40,
"preview": "export const astroTextColor = 'orange';\n"
},
{
"path": "examples/astro-solid/pages/index.astro",
"chars": 257,
"preview": "---\nimport CSRComponent from './csr';\n---\n\n<head>\n <meta charset=\"utf-8\" />\n <meta name=\"viewport\" content=\"width=devi"
},
{
"path": "examples/astro-solid/tsconfig.json",
"chars": 219,
"preview": "{\n \"compilerOptions\": {\n \"baseUrl\": \".\",\n \"module\": \"ESNext\",\n \"target\": \"ESNext\",\n \"jsx\": \"preserve\",\n "
},
{
"path": "examples/esbuild/.gitignore",
"chars": 7,
"preview": "/build\n"
},
{
"path": "examples/esbuild/app.js",
"chars": 26,
"preview": "import 'linaria-website';\n"
},
{
"path": "examples/esbuild/build.js",
"chars": 401,
"preview": "const wyw = require('@wyw-in-js/esbuild').default;\n\nconst prod = process.env.NODE_ENV === 'production';\n\nrequire('esbuil"
},
{
"path": "examples/esbuild/package.json",
"chars": 324,
"preview": "{\n \"private\": true,\n \"name\": \"esbuild-example\",\n \"version\": \"0.0.0\",\n \"license\": \"MIT\",\n \"dependencies\": {\n \"lin"
},
{
"path": "examples/rollup/.gitignore",
"chars": 7,
"preview": "/build\n"
},
{
"path": "examples/rollup/app.js",
"chars": 26,
"preview": "import 'linaria-website';\n"
},
{
"path": "examples/rollup/babel.config.js",
"chars": 58,
"preview": "module.exports = {\n presets: ['@babel/preset-react'],\n};\n"
},
{
"path": "examples/rollup/package.json",
"chars": 587,
"preview": "{\n \"private\": true,\n \"name\": \"rollup-example\",\n \"version\": \"0.0.0\",\n \"license\": \"MIT\",\n \"dependencies\": {\n \"lina"
},
{
"path": "examples/rollup/rollup.config.mjs",
"chars": 742,
"preview": "import wyw from '@wyw-in-js/rollup';\nimport { babel } from '@rollup/plugin-babel';\nimport commonjs from '@rollup/plugin-"
},
{
"path": "examples/vite/.linariarc.mjs",
"chars": 526,
"preview": "module.exports = {\n rules: [\n {\n action: require.resolve('@linaria/shaker'),\n },\n {\n "
},
{
"path": "examples/vite/app.js",
"chars": 26,
"preview": "import 'linaria-website';\n"
},
{
"path": "examples/vite/index.html",
"chars": 305,
"preview": "<!doctype html>\n<html lang=\"en\">\n\n<head>\n <meta charset=\"utf-8\" />\n <meta name=\"viewport\" content=\"width=device-width,"
},
{
"path": "examples/vite/package.json",
"chars": 437,
"preview": "{\n \"private\": true,\n \"name\": \"vite-example\",\n \"version\": \"0.0.0\",\n \"license\": \"MIT\",\n \"main\": \"index.js\",\n \"type\":"
},
{
"path": "examples/vite/vite.config.js",
"chars": 582,
"preview": "import wyw from '@wyw-in-js/vite';\nimport { nodeResolve } from '@rollup/plugin-node-resolve';\nimport react from '@vitejs"
},
{
"path": "examples/vpssr-linaria-solid/package.json",
"chars": 593,
"preview": "{\n \"name\": \"vpssr-linaria-solid-example\",\n \"version\": \"1.0.0\",\n \"private\": true,\n \"scripts\": {\n \"dev\": \"node ./se"
},
{
"path": "examples/vpssr-linaria-solid/pages/html-js/_default.page.client.js",
"chars": 504,
"preview": "// We could also define `handleCounter()` in `index.page.client.js` instead of `_default.page.client.js`.\n// We define `"
},
{
"path": "examples/vpssr-linaria-solid/pages/html-js/index.page.server.tsx",
"chars": 473,
"preview": "import { css } from '@linaria/core'\n\nexport function Page() {\n\treturn (\n\t\t<>\n\t\t\t<h1>HTML + JS</h1>\n\t\t\t<p>This page is re"
},
{
"path": "examples/vpssr-linaria-solid/pages/html-only/index.page.server.tsx",
"chars": 677,
"preview": "import { css } from '@linaria/core'\n\nexport function Page() {\n\treturn (\n\t\t<>\n\t\t\t<h1>HTML-only</h1>\n\t\t\t<p>\n\t\t\t\tThe React "
},
{
"path": "examples/vpssr-linaria-solid/pages/index.page.server.tsx",
"chars": 503,
"preview": "export function Page() {\n\treturn (\n\t\t<>\n\t\t\t<h1>Render Modes</h1>\n\t\t\t<ul>\n\t\t\t\t<li>\n\t\t\t\t\t<a href=\"/html-only\">HTML only</a"
},
{
"path": "examples/vpssr-linaria-solid/pages/spa/index.page.client.tsx",
"chars": 397,
"preview": "import { Counter } from '../ssr/Counter'\nimport { css } from '@linaria/core'\n\nexport function Page() {\n\treturn (\n\t\t<>\n\t\t"
},
{
"path": "examples/vpssr-linaria-solid/pages/ssr/Counter.tsx",
"chars": 238,
"preview": "import { createSignal } from 'solid-js'\n\nexport function Counter() {\n\tconst [count, setCount] = createSignal(0)\n\treturn "
},
{
"path": "examples/vpssr-linaria-solid/pages/ssr/index.page.tsx",
"chars": 405,
"preview": "import { Counter } from './Counter'\nimport { css } from '@linaria/core'\n\nexport function Page() {\n\treturn (\n\t\t<>\n\t\t\t<h1>"
},
{
"path": "examples/vpssr-linaria-solid/renderer/_default.page.client.tsx",
"chars": 509,
"preview": "import { render as solidRender, hydrate as solidHydrate } from 'solid-js/web'\nimport type { PageContextBuiltInClient } f"
},
{
"path": "examples/vpssr-linaria-solid/renderer/_default.page.server.tsx",
"chars": 1011,
"preview": "import { generateHydrationScript, renderToStream } from 'solid-js/web'\nimport { escapeInject, stampPipe, dangerouslySkip"
},
{
"path": "examples/vpssr-linaria-solid/server.js",
"chars": 1243,
"preview": "const express = require(\"express\");\nconst compression = require(\"compression\");\nconst { renderPage } = require(\"vite-plu"
},
{
"path": "examples/vpssr-linaria-solid/tsconfig.json",
"chars": 439,
"preview": "{\n \"compilerOptions\": {\n \"baseUrl\": \".\",\n \"target\": \"ESNext\",\n \"module\": \"ESNext\",\n \"jsx\": \"p"
},
{
"path": "examples/vpssr-linaria-solid/vite.config.js",
"chars": 946,
"preview": "import vite_ssr from 'vite-plugin-ssr/plugin';\nimport vite_wyw from '@wyw-in-js/vite';\nimport vite_solid from 'vite-plug"
},
{
"path": "examples/webpack5/app.js",
"chars": 26,
"preview": "import 'linaria-website';\n"
},
{
"path": "examples/webpack5/babel.config.js",
"chars": 58,
"preview": "module.exports = {\n presets: ['@babel/preset-react'],\n};\n"
},
{
"path": "examples/webpack5/package.json",
"chars": 678,
"preview": "{\n \"private\": true,\n \"name\": \"webpack5-example\",\n \"version\": \"0.0.0\",\n \"license\": \"MIT\",\n \"main\": \"index.js\",\n \"de"
},
{
"path": "examples/webpack5/webpack.config.js",
"chars": 1496,
"preview": "const path = require('path');\nconst webpack = require('webpack');\nconst MiniCssExtractPlugin = require('mini-css-extract"
},
{
"path": "greenkeeper.json",
"chars": 128,
"preview": "{\n \"groups\": {\n \"default\": {\n \"packages\": [\n \"package.json\",\n \"website/package.json\"\n ]\n "
},
{
"path": "jest.config.js",
"chars": 187,
"preview": "module.exports = {\n testEnvironment: 'node',\n collectCoverageFrom: ['src/*.ts'],\n transformIgnorePatterns: ['node_mod"
},
{
"path": "link-wyw.sh",
"chars": 854,
"preview": "#!/bin/bash\n\n# Find package.json files in the current folder (excluding node_modules)\npackage_json_files=$(find . -name "
},
{
"path": "package.json",
"chars": 3007,
"preview": "{\n \"name\": \"umbrella\",\n \"version\": \"3.0.0-beta.19\",\n \"private\": true,\n \"homepage\": \"https://github.com/callstack/lin"
},
{
"path": "packages/atomic/CHANGELOG.md",
"chars": 15713,
"preview": "# Change Log\n\n## 7.0.1\n\n### Patch Changes\n\n- Updated dependencies [b3331e45]\n - @linaria/react@7.0.1\n\n## 7.0.0\n\n### Maj"
},
{
"path": "packages/atomic/README.md",
"chars": 1060,
"preview": "<p align=\"center\">\n <img alt=\"Linaria\" src=\"https://raw.githubusercontent.com/callstack/linaria/HEAD/website/assets/lin"
},
{
"path": "packages/atomic/babel.config.js",
"chars": 72,
"preview": "const config = require('../../babel.config');\n\nmodule.exports = config;\n"
},
{
"path": "packages/atomic/package.json",
"chars": 2158,
"preview": "{\n \"name\": \"@linaria/atomic\",\n \"version\": \"7.0.1\",\n \"description\": \"Blazing fast zero-runtime CSS in JS library\",\n \""
},
{
"path": "packages/atomic/processors/css.js",
"chars": 128,
"preview": "Object.defineProperty(exports, '__esModule', {\n value: true,\n});\n\nexports.default = require('../dist/processors/css').d"
},
{
"path": "packages/atomic/processors/styled.js",
"chars": 131,
"preview": "Object.defineProperty(exports, '__esModule', {\n value: true,\n});\n\nexports.default = require('../dist/processors/styled'"
},
{
"path": "packages/atomic/src/CSSProperties.ts",
"chars": 83,
"preview": "export type CSSProperties = {\n [key: string]: string | number | CSSProperties;\n};\n"
},
{
"path": "packages/atomic/src/css.ts",
"chars": 586,
"preview": "import type { LinariaClassName } from '@linaria/core';\n\nimport type { CSSProperties } from './CSSProperties';\n\ntype CSS "
},
{
"path": "packages/atomic/src/index.ts",
"chars": 172,
"preview": "export { default as css } from './css';\nexport { styled } from '@linaria/react';\nexport { cx } from '@linaria/core';\n\nex"
},
{
"path": "packages/atomic/src/processors/css.ts",
"chars": 1583,
"preview": "import type { SourceLocation } from '@babel/types';\nimport type { Rules, ValueCache } from '@wyw-in-js/processor-utils';"
},
{
"path": "packages/atomic/src/processors/helpers/atomize.ts",
"chars": 3671,
"preview": "import { slugify } from '@wyw-in-js/shared';\nimport { all as knownProperties } from 'known-css-properties';\nimport type "
},
{
"path": "packages/atomic/src/processors/helpers/propertyPriority.ts",
"chars": 5327,
"preview": "const shorthandProperties = {\n // The `all` property resets everything, and should effectively have priority zero.\n //"
},
{
"path": "packages/atomic/src/processors/styled.ts",
"chars": 2271,
"preview": "import type { SourceLocation } from '@babel/types';\nimport type { Rules, ValueCache } from '@wyw-in-js/processor-utils';"
},
{
"path": "packages/atomic/tsconfig.json",
"chars": 194,
"preview": "{\n \"extends\": \"../../tsconfig.json\",\n \"compilerOptions\": {\n \"paths\": {},\n \"rootDir\": \"src/\",\n \"types\": [\"node"
},
{
"path": "packages/core/CHANGELOG.md",
"chars": 13773,
"preview": "# Change Log\n\n## 7.0.0\n\n### Major Changes\n\n- ab11ebb7: BREAKING: bump `@wyw-in-js/*` dependencies to `^1.0.0` (stable).\n"
},
{
"path": "packages/core/README.md",
"chars": 1060,
"preview": "<p align=\"center\">\n <img alt=\"Linaria\" src=\"https://raw.githubusercontent.com/callstack/linaria/HEAD/website/assets/lin"
},
{
"path": "packages/core/__dtslint__/core.ts",
"chars": 311,
"preview": "/* eslint-disable @typescript-eslint/no-unused-vars */\nimport { css, cx } from '../src';\n\n// $ExpectType LinariaClassNam"
},
{
"path": "packages/core/__dtslint__/index.d.ts",
"chars": 86,
"preview": "// dtslint wants to see index.d.ts. Well, here it is.\ndeclare const linaria: unknown;\n"
},
{
"path": "packages/core/__dtslint__/tsconfig.eslint.json",
"chars": 35,
"preview": "{\n \"extends\": \"./tsconfig.json\"\n}\n"
},
{
"path": "packages/core/__dtslint__/tsconfig.json",
"chars": 289,
"preview": "{\n \"compilerOptions\": {\n \"module\": \"commonjs\",\n \"lib\": [\"es6\"],\n \"target\": \"ES2015\",\n \"esModuleInterop\": tr"
},
{
"path": "packages/core/__tests__/cx.test.ts",
"chars": 568,
"preview": "import cx from '../src/cx';\n\nit('should filter falsy values', () => {\n expect(cx('1', 'test', false, '2', 0, '', null, "
},
{
"path": "packages/core/__tests__/detect-core-js.test.ts",
"chars": 1063,
"preview": "import cp from 'child_process';\n\nconst waitForProcess = async (process: cp.ChildProcess) => {\n return new Promise((reso"
},
{
"path": "packages/core/babel.config.js",
"chars": 72,
"preview": "const config = require('../../babel.config');\n\nmodule.exports = config;\n"
},
{
"path": "packages/core/package.json",
"chars": 2202,
"preview": "{\n \"name\": \"@linaria/core\",\n \"version\": \"7.0.0\",\n \"description\": \"Blazing fast zero-runtime CSS in JS library\",\n \"ke"
},
{
"path": "packages/core/processors/css.js",
"chars": 128,
"preview": "Object.defineProperty(exports, '__esModule', {\n value: true,\n});\n\nexports.default = require('../dist/processors/css').d"
},
{
"path": "packages/core/src/CSSProperties.ts",
"chars": 83,
"preview": "export type CSSProperties = {\n [key: string]: string | number | CSSProperties;\n};\n"
},
{
"path": "packages/core/src/css.ts",
"chars": 681,
"preview": "import type { CSSProperties } from './CSSProperties';\nimport type { LinariaClassName } from './cx';\n\ntype WYWEvalMeta = "
},
{
"path": "packages/core/src/cx.ts",
"chars": 1969,
"preview": "export type LinariaClassName = string & { __linariaClassName: true };\n\nexport type ClassName<T = string> = T | false | v"
},
{
"path": "packages/core/src/index.ts",
"chars": 178,
"preview": "export { default as css } from './css';\nexport { default as cx } from './cx';\nexport type { CSSProperties } from './CSSP"
},
{
"path": "packages/core/src/processors/css.ts",
"chars": 1323,
"preview": "import type { SourceLocation, StringLiteral } from '@babel/types';\nimport type { Rules, ValueCache } from '@wyw-in-js/pr"
},
{
"path": "packages/core/tsconfig.json",
"chars": 149,
"preview": "{\n \"extends\": \"../../tsconfig.json\",\n \"compilerOptions\": {\n \"paths\": {},\n \"rootDir\": \"src/\",\n \"types\": [\"node"
},
{
"path": "packages/interop/CHANGELOG.md",
"chars": 6162,
"preview": "# Change Log\n\n## 7.0.0\n\n### Major Changes\n\n- ab11ebb7: BREAKING: bump `@wyw-in-js/*` dependencies to `^1.0.0` (stable).\n"
},
{
"path": "packages/interop/README.md",
"chars": 890,
"preview": "<p align=\"center\">\n <img alt=\"Linaria\" src=\"https://raw.githubusercontent.com/callstack/linaria/HEAD/website/assets/lin"
},
{
"path": "packages/interop/__tests__/__snapshots__/index.test.ts.snap",
"chars": 4100,
"preview": "// Jest Snapshot v1, https://goo.gl/fbAQLP\n\nexports[`styled-components css 1`] = `\n\"\"use strict\";\n\nObject.defineProperty"
},
{
"path": "packages/interop/__tests__/index.test.ts",
"chars": 2382,
"preview": "const babel = require('@babel/core');\nconst dedent = require('dedent');\n\nconst plugin = require('../src');\n\nconst getCod"
},
{
"path": "packages/interop/babel.config.js",
"chars": 72,
"preview": "const config = require('../../babel.config');\n\nmodule.exports = config;\n"
},
{
"path": "packages/interop/package.json",
"chars": 1386,
"preview": "{\n \"name\": \"@linaria/babel-plugin-interop\",\n \"version\": \"7.0.0\",\n \"homepage\": \"https://github.com/callstack/linaria/t"
},
{
"path": "packages/interop/src/index.ts",
"chars": 2416,
"preview": "import type core from '@babel/core';\nimport type { NodePath } from '@babel/traverse';\nimport type {\n Expression,\n Iden"
},
{
"path": "packages/interop/tsconfig.json",
"chars": 116,
"preview": "{\n \"extends\": \"../../tsconfig.json\",\n \"compilerOptions\": { \"paths\": {}, \"rootDir\": \"src/\" },\n \"references\": []\n}\n"
},
{
"path": "packages/linaria/CHANGELOG.md",
"chars": 20729,
"preview": "# Change Log\n\n## 7.0.1\n\n### Patch Changes\n\n- Updated dependencies [b3331e45]\n - @linaria/react@7.0.1\n\n## 7.0.0\n\n### Maj"
},
{
"path": "packages/linaria/README.md",
"chars": 1060,
"preview": "<p align=\"center\">\n <img alt=\"Linaria\" src=\"https://raw.githubusercontent.com/callstack/linaria/HEAD/website/assets/lin"
},
{
"path": "packages/linaria/babel/package.json",
"chars": 97,
"preview": "{\n \"main\": \"../lib/babel.js\",\n \"module\": \"../esm/babel.js\",\n \"types\": \"../types/babel.d.ts\"\n}\n"
},
{
"path": "packages/linaria/babel.config.js",
"chars": 72,
"preview": "const config = require('../../babel.config');\n\nmodule.exports = config;\n"
},
{
"path": "packages/linaria/evaluators/package.json",
"chars": 112,
"preview": "{\n \"main\": \"../lib/evaluators.js\",\n \"module\": \"../esm/evaluators.js\",\n \"types\": \"../types/evaluators.d.ts\"\n}\n"
},
{
"path": "packages/linaria/loader/package.json",
"chars": 127,
"preview": "{\n \"main\": \"../lib/webpack4-loader.js\",\n \"module\": \"../esm/webpack4-loader.js\",\n \"types\": \"../types/webpack4-loader.d"
},
{
"path": "packages/linaria/package.json",
"chars": 1616,
"preview": "{\n \"name\": \"linaria\",\n \"version\": \"7.0.1\",\n \"description\": \"Blazing fast zero-runtime CSS in JS library\",\n \"keywords"
},
{
"path": "packages/linaria/react/package.json",
"chars": 97,
"preview": "{\n \"main\": \"../lib/react.js\",\n \"module\": \"../esm/react.js\",\n \"types\": \"../types/react.d.ts\"\n}\n"
},
{
"path": "packages/linaria/rollup/package.json",
"chars": 100,
"preview": "{\n \"main\": \"../lib/rollup.js\",\n \"module\": \"../esm/rollup.js\",\n \"types\": \"../types/rollup.d.ts\"\n}\n"
},
{
"path": "packages/linaria/server/package.json",
"chars": 100,
"preview": "{\n \"main\": \"../lib/server.js\",\n \"module\": \"../esm/server.js\",\n \"types\": \"../types/server.d.ts\"\n}\n"
},
{
"path": "packages/linaria/src/core.ts",
"chars": 31,
"preview": "export * from '@linaria/core';\n"
},
{
"path": "packages/linaria/src/react.ts",
"chars": 32,
"preview": "export * from '@linaria/react';\n"
},
{
"path": "packages/linaria/src/server.ts",
"chars": 33,
"preview": "export * from '@linaria/server';\n"
},
{
"path": "packages/linaria/stylelint-config/package.json",
"chars": 109,
"preview": "{\n \"main\": \"../lib/stylelint.js\",\n \"module\": \"../esm/stylelint.js\",\n \"types\": \"../types/stylelint.d.ts\"\n}\n"
},
{
"path": "packages/linaria/tsconfig.json",
"chars": 202,
"preview": "{\n \"extends\": \"../../tsconfig.json\",\n \"compilerOptions\": { \"paths\": {}, \"rootDir\": \"src/\" },\n \"references\": [\n { \""
},
{
"path": "packages/postcss-linaria/CHANGELOG.md",
"chars": 4574,
"preview": "# Change Log\n\n## 7.0.0\n\n### Major Changes\n\n- ab11ebb7: BREAKING: bump `@wyw-in-js/*` dependencies to `^1.0.0` (stable).\n"
},
{
"path": "packages/postcss-linaria/README.md",
"chars": 764,
"preview": "<p align=\"center\">\n <img alt=\"Linaria\" src=\"https://raw.githubusercontent.com/callstack/linaria/HEAD/website/assets/lin"
},
{
"path": "packages/postcss-linaria/__tests__/__utils__/index.ts",
"chars": 2562,
"preview": "import type { Document, Node } from 'postcss';\n\nimport { parse } from '../../src/parse';\n\nexport function createTestAst("
},
{
"path": "packages/postcss-linaria/__tests__/locationCorrection.test.ts",
"chars": 9273,
"preview": "import type { Root, Rule, Declaration, Comment } from 'postcss';\n\nimport {\n createTestAst,\n getSourceForNodeByRange,\n "
},
{
"path": "packages/postcss-linaria/__tests__/parse.test.ts",
"chars": 12165,
"preview": "import type { Root, Rule, Declaration } from 'postcss';\n\nimport { placeholderText } from '../src/util';\n\nimport { create"
},
{
"path": "packages/postcss-linaria/__tests__/stringify.test.ts",
"chars": 9218,
"preview": "import type { Root, Rule, Declaration } from 'postcss';\n\nimport syntax from '../src/index';\nimport { placeholderText } f"
},
{
"path": "packages/postcss-linaria/__tests__/stylelint.test.ts",
"chars": 3268,
"preview": "import { resolve } from 'path';\n\nimport stylelint, { type Config } from 'stylelint';\n\n// importing from the package woul"
},
{
"path": "packages/postcss-linaria/__tests__/utils.test.ts",
"chars": 2065,
"preview": "import { createPlaceholder, placeholderText } from '../src/util';\n\ndescribe('createPlaceholder', () => {\n it('should cr"
},
{
"path": "packages/postcss-linaria/babel.config.js",
"chars": 72,
"preview": "const config = require('../../babel.config');\n\nmodule.exports = config;\n"
},
{
"path": "packages/postcss-linaria/package.json",
"chars": 1699,
"preview": "{\n \"name\": \"@linaria/postcss-linaria\",\n \"version\": \"7.0.0\",\n \"description\": \"Blazing fast zero-runtime CSS in JS libr"
},
{
"path": "packages/postcss-linaria/src/index.ts",
"chars": 141,
"preview": "import { parse } from './parse';\nimport { stringify } from './stringify';\n\nexport { parse, stringify };\nexport default {"
},
{
"path": "packages/postcss-linaria/src/locationCorrection.ts",
"chars": 7862,
"preview": "/* eslint-disable no-param-reassign */\nimport type { TaggedTemplateExpression } from '@babel/types';\nimport type { Root,"
},
{
"path": "packages/postcss-linaria/src/parse.ts",
"chars": 6844,
"preview": "import { parse as babelParse } from '@babel/parser';\nimport type { NodePath } from '@babel/traverse';\nimport traverse fr"
},
{
"path": "packages/postcss-linaria/src/stringify.ts",
"chars": 6333,
"preview": "import type {\n Stringifier as StringifierFn,\n Comment,\n Root,\n Document,\n AnyNode,\n Builder,\n Declaration,\n Rule"
},
{
"path": "packages/postcss-linaria/src/util.ts",
"chars": 2737,
"preview": "const getLine = (sourceAsString: string, indexAfterExpression: number) => {\n const begginningOfLineIndex =\n sourceAs"
},
{
"path": "packages/postcss-linaria/tsconfig.json",
"chars": 116,
"preview": "{\n \"extends\": \"../../tsconfig.json\",\n \"compilerOptions\": { \"paths\": {}, \"rootDir\": \"src/\" },\n \"references\": []\n}\n"
},
{
"path": "packages/react/CHANGELOG.md",
"chars": 18718,
"preview": "# Change Log\n\n## 7.0.1\n\n### Patch Changes\n\n- b3331e45: Fix `styled.<tag>` typings in environments where only the React J"
},
{
"path": "packages/react/README.md",
"chars": 1060,
"preview": "<p align=\"center\">\n <img alt=\"Linaria\" src=\"https://raw.githubusercontent.com/callstack/linaria/HEAD/website/assets/lin"
},
{
"path": "packages/react/__dtslint-react17__/index.d.ts",
"chars": 55,
"preview": "// dtslint expects an `index.d.ts` in the test folder.\n"
},
{
"path": "packages/react/__dtslint-react17__/react17.tsx",
"chars": 186,
"preview": "import { styled } from '..';\n\nconst Button = styled.button``;\n\n// Should not require `children` for intrinsic elements o"
},
{
"path": "packages/react/__dtslint-react17__/stubs/jsx-runtime.d.ts",
"chars": 440,
"preview": "declare module 'react/jsx-runtime' {\n const Fragment: unknown;\n function jsx(type: unknown, props: unknown, key?: unkn"
},
{
"path": "packages/react/__dtslint-react17__/stubs/react17.d.ts",
"chars": 576,
"preview": "// Minimal React 17-like type surface for dtslint.\n// It intentionally does NOT export a module-level `JSX` namespace.\n\n"
},
{
"path": "packages/react/__dtslint-react17__/tsconfig.eslint.json",
"chars": 35,
"preview": "{\n \"extends\": \"./tsconfig.json\"\n}\n"
},
{
"path": "packages/react/__dtslint-react17__/tsconfig.json",
"chars": 551,
"preview": "{\n \"compilerOptions\": {\n \"module\": \"commonjs\",\n \"lib\": [\"es6\"],\n \"target\": \"ES2015\",\n \"jsx\": \"react-jsx\",\n "
},
{
"path": "packages/react/__dtslint__/index.d.ts",
"chars": 86,
"preview": "// dtslint wants to see index.d.ts. Well, here it is.\ndeclare const linaria: unknown;\n"
},
{
"path": "packages/react/__dtslint__/styled.ts",
"chars": 4762,
"preview": "/* tslint:disable:no-unnecessary-generics */\n// eslint-disable-next-line import/no-extraneous-dependencies\nimport * as R"
},
{
"path": "packages/react/__dtslint__/tsconfig.eslint.json",
"chars": 35,
"preview": "{\n \"extends\": \"./tsconfig.json\"\n}\n"
},
{
"path": "packages/react/__dtslint__/tsconfig.json",
"chars": 375,
"preview": "{\n \"compilerOptions\": {\n \"module\": \"commonjs\",\n \"lib\": [\"es6\"],\n \"target\": \"ES2015\",\n \"esModuleInterop\": tr"
},
{
"path": "packages/react/__tests__/__snapshots__/styled.test.tsx.snap",
"chars": 2810,
"preview": "// Jest Snapshot v1, https://goo.gl/fbAQLP\n\nexports[`applies CSS variables in style prop 1`] = `\n<div\n className=\"mocke"
},
{
"path": "packages/react/__tests__/detect-core-js.test.ts",
"chars": 1067,
"preview": "import cp from 'child_process';\n\nconst waitForProcess = async (process) => {\n return new Promise((resolve) => {\n let"
},
{
"path": "packages/react/__tests__/styled.test.tsx",
"chars": 7628,
"preview": "import React from 'react';\n\nimport { omit } from '../src/styled';\n\nconst renderer = require('react-test-renderer');\n\ncon"
},
{
"path": "packages/react/babel.config.js",
"chars": 72,
"preview": "const config = require('../../babel.config');\n\nmodule.exports = config;\n"
},
{
"path": "packages/react/package.json",
"chars": 2586,
"preview": "{\n \"name\": \"@linaria/react\",\n \"version\": \"7.0.1\",\n \"description\": \"Blazing fast zero-runtime CSS in JS library\",\n \"k"
},
{
"path": "packages/react/processors/styled.js",
"chars": 131,
"preview": "Object.defineProperty(exports, '__esModule', {\n value: true,\n});\n\nexports.default = require('../dist/processors/styled'"
},
{
"path": "packages/react/src/index.ts",
"chars": 254,
"preview": "export { default as styled } from './styled';\nexport type {\n HtmlStyledTag,\n StyledComponent,\n StyledJSXIntrinsics,\n "
},
{
"path": "packages/react/src/processors/styled.ts",
"chars": 11681,
"preview": "import { readFileSync } from 'fs';\nimport { dirname, join, posix } from 'path';\n\nimport type {\n CallExpression,\n Expre"
},
{
"path": "packages/react/src/react-html-attributes.d.ts",
"chars": 253,
"preview": "declare module 'react-html-attributes' {\n interface IElements {\n html: string[];\n svg: string[];\n }\n\n interface"
},
{
"path": "packages/react/src/styled.ts",
"chars": 9645,
"preview": "/* eslint-disable @typescript-eslint/no-explicit-any */\n/**\n * This file contains a runtime version of `styled` componen"
},
{
"path": "packages/react/tsconfig.json",
"chars": 205,
"preview": "{\n \"extends\": \"../../tsconfig.json\",\n \"compilerOptions\": {\n \"paths\": {},\n \"rootDir\": \"src/\",\n \"types\": [\n "
},
{
"path": "packages/server/CHANGELOG.md",
"chars": 7498,
"preview": "# Change Log\n\n## 7.0.0\n\n### Major Changes\n\n- ab11ebb7: BREAKING: bump `@wyw-in-js/*` dependencies to `^1.0.0` (stable).\n"
},
{
"path": "packages/server/README.md",
"chars": 1060,
"preview": "<p align=\"center\">\n <img alt=\"Linaria\" src=\"https://raw.githubusercontent.com/callstack/linaria/HEAD/website/assets/lin"
},
{
"path": "packages/server/__tests__/__snapshots__/collect.test.ts.snap",
"chars": 3519,
"preview": "// Jest Snapshot v1, https://goo.gl/fbAQLP\n\nexports[`classname in @rule critical 1`] = `\n\"@supports (object-fit: cover) "
},
{
"path": "packages/server/__tests__/collect.test.ts",
"chars": 7039,
"preview": "import dedent from 'dedent';\nimport prettier from 'prettier';\n\nimport collect from '../src/collect';\n\nconst prettyPrint "
},
{
"path": "packages/server/babel.config.js",
"chars": 72,
"preview": "const config = require('../../babel.config');\n\nmodule.exports = config;\n"
},
{
"path": "packages/server/package.json",
"chars": 1327,
"preview": "{\n \"name\": \"@linaria/server\",\n \"version\": \"7.0.0\",\n \"description\": \"Blazing fast zero-runtime CSS in JS library\",\n \""
},
{
"path": "packages/server/src/collect.ts",
"chars": 4596,
"preview": "import type { AtRule, ChildNode } from 'postcss';\nimport postcss from 'postcss';\n\ntype CollectResult = {\n critical: str"
},
{
"path": "packages/server/src/index.ts",
"chars": 48,
"preview": "export { default as collect } from './collect';\n"
},
{
"path": "packages/server/tsconfig.json",
"chars": 106,
"preview": "{\n \"extends\": \"../../tsconfig.json\",\n \"compilerOptions\": {\n \"paths\": {},\n \"rootDir\": \"src/\"\n }\n}\n"
},
{
"path": "packages/stylelint/CHANGELOG.md",
"chars": 13442,
"preview": "# Change Log\n\n## 7.0.0\n\n### Major Changes\n\n- ab11ebb7: BREAKING: bump `@wyw-in-js/*` dependencies to `^1.0.0` (stable).\n"
},
{
"path": "packages/stylelint/README.md",
"chars": 473,
"preview": "<p align=\"center\">\n <img alt=\"Linaria\" src=\"https://raw.githubusercontent.com/callstack/linaria/HEAD/website/assets/lin"
},
{
"path": "packages/stylelint/babel.config.js",
"chars": 72,
"preview": "const config = require('../../babel.config');\n\nmodule.exports = config;\n"
},
{
"path": "packages/stylelint/package.json",
"chars": 1358,
"preview": "{\n \"name\": \"@linaria/stylelint\",\n \"version\": \"7.0.0\",\n \"description\": \"Blazing fast zero-runtime CSS in JS library\",\n"
},
{
"path": "packages/stylelint/src/index.ts",
"chars": 273,
"preview": "export default {\n processors: [require.resolve('./preprocessor')],\n syntax: 'scss',\n rules: {\n 'property-no-vendor"
},
{
"path": "packages/stylelint/src/preprocessor.ts",
"chars": 6377,
"preview": "import { stripVTControlCharacters as stripAnsi } from 'node:util';\n\nimport type { Replacements } from '@wyw-in-js/shared"
},
{
"path": "packages/stylelint/tsconfig.json",
"chars": 135,
"preview": "{\n \"extends\": \"../../tsconfig.json\",\n \"compilerOptions\": { \"paths\": {}, \"rootDir\": \"src/\", \"types\": [\"node\"] },\n \"ref"
},
{
"path": "packages/stylelint-config-standard-linaria/CHANGELOG.md",
"chars": 5123,
"preview": "# Change Log\n\n## 7.0.0\n\n### Major Changes\n\n- ab11ebb7: BREAKING: bump `@wyw-in-js/*` dependencies to `^1.0.0` (stable).\n"
},
{
"path": "packages/stylelint-config-standard-linaria/README.md",
"chars": 764,
"preview": "<p align=\"center\">\n <img alt=\"Linaria\" src=\"https://raw.githubusercontent.com/callstack/linaria/HEAD/website/assets/lin"
},
{
"path": "packages/stylelint-config-standard-linaria/babel.config.js",
"chars": 72,
"preview": "const config = require('../../babel.config');\n\nmodule.exports = config;\n"
},
{
"path": "packages/stylelint-config-standard-linaria/package.json",
"chars": 1425,
"preview": "{\n \"name\": \"@linaria/stylelint-config-standard-linaria\",\n \"version\": \"7.0.0\",\n \"description\": \"Blazing fast zero-runt"
},
{
"path": "packages/stylelint-config-standard-linaria/src/index.js",
"chars": 729,
"preview": "module.exports = {\n extends: ['stylelint-config-standard'],\n // eslint-disable-next-line global-require\n customSyntax"
},
{
"path": "packages/stylelint-config-standard-linaria/tsconfig.json",
"chars": 116,
"preview": "{\n \"extends\": \"../../tsconfig.json\",\n \"compilerOptions\": { \"paths\": {}, \"rootDir\": \"src/\" },\n \"references\": []\n}\n"
}
]
// ... and 82 more files (download for full content)
About this extraction
This page contains the full source code of the callstack/linaria GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 282 files (720.8 KB), approximately 213.8k tokens, and a symbol index with 137 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.
Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.