svelte-preprocess-cssmodules
Advanced tools
Comparing version 2.0.0-rc.1 to 2.0.0-rc.2
# Svelte preprocess CSS Modules, changelog | ||
## 2.0.0-rc.2 (April 16, 2021) | ||
### Features | ||
- Add option `hashSeeder` to customize the source of the hashing method | ||
- Add option `allowedAttributes` to parse other attributes than `class` | ||
### Fixes | ||
- Replace `class` attribute on HTML elements and inline components | ||
- Fix external import on `native` & `mixed` mode when `<style>` already exists | ||
- Shorthand directive | ||
## 2.0.0-rc.1 (April 11, 2021) | ||
@@ -4,0 +14,0 @@ |
@@ -20,2 +20,4 @@ "use strict"; | ||
getLocalIdent: lib_1.getLocalIdent, | ||
hashSeeder: ['style', 'filepath', 'classname'], | ||
allowedAttributes: [], | ||
}; | ||
@@ -31,3 +33,4 @@ const markup = ({ content, filename }) => __awaiter(void 0, void 0, void 0, function* () { | ||
} | ||
let { mode } = pluginOptions; | ||
// eslint-disable-next-line prefer-const | ||
let { mode, hashSeeder } = pluginOptions; | ||
if (lib_1.hasModuleAttribute(ast)) { | ||
@@ -40,2 +43,7 @@ const moduleAttribute = ast.css.attributes.find((item) => item.name === 'module'); | ||
} | ||
hashSeeder.forEach((value) => { | ||
if (!['style', 'filepath', 'classname'].includes(value)) { | ||
throw new Error(`The hash seeder only accepts the keys 'style', 'filepath' and 'classname': '${value}' was passed.`); | ||
} | ||
}); | ||
let parsedContent; | ||
@@ -42,0 +50,0 @@ switch (mode) { |
@@ -13,3 +13,3 @@ "use strict"; | ||
* @param localName The local name/rules to replace | ||
* @param content The content to use base the hash on | ||
* @param content The content to base the hash on | ||
*/ | ||
@@ -52,13 +52,17 @@ // eslint-disable-next-line @typescript-eslint/no-explicit-any | ||
* @param resourcePath The file resourcePath | ||
* @param styles The style content | ||
* @param style The style content | ||
* @param className The cssModules className | ||
* @param localIdentName The localIdentName rule | ||
*/ | ||
function generateName(resourcePath, styles, className, localIdentName) { | ||
function generateName(resourcePath, style, className, pluginOptions) { | ||
const filePath = resourcePath; | ||
const localName = localIdentName.length | ||
? localIdentName.replace(/\[local\]/gi, () => className) | ||
const localName = pluginOptions.localIdentName.length | ||
? pluginOptions.localIdentName.replace(/\[local\]/gi, () => className) | ||
: className; | ||
const content = `${styles}-${filePath}-${className}`; | ||
let interpolatedName = interpolateName(resourcePath, localName, content).replace(/\./g, '-'); | ||
const hashSeeder = pluginOptions.hashSeeder | ||
.join('-') | ||
.replace(/style/gi, () => style) | ||
.replace(/filepath/gi, () => filePath) | ||
.replace(/classname/gi, () => className); | ||
let interpolatedName = interpolateName(resourcePath, localName, hashSeeder).replace(/\./g, '-'); | ||
// replace unwanted characters from [path] | ||
@@ -88,3 +92,3 @@ if (PATTERN_PATH_UNALLOWED.test(interpolatedName)) { | ||
function createCssModulesClassName(filename, markup, style, className, pluginOptions) { | ||
const interpolatedName = generateName(filename, style, className, pluginOptions.localIdentName); | ||
const interpolatedName = generateName(filename, style, className, pluginOptions); | ||
return pluginOptions.getLocalIdent({ | ||
@@ -91,0 +95,0 @@ context: path_1.default.dirname(filename), |
@@ -79,3 +79,3 @@ "use strict"; | ||
if (processor.style.ast) { | ||
processor.magicContent.appendLeft(processor.style.ast.content.start, content); | ||
processor.magicContent.prependLeft(processor.style.ast.content.start, content); | ||
} | ||
@@ -82,0 +82,0 @@ else { |
@@ -42,2 +42,3 @@ "use strict"; | ||
const directiveLength = 'class:'.length; | ||
const allowedAttributes = ['class', ...processor.options.allowedAttributes]; | ||
compiler_1.walk(processor.ast, { | ||
@@ -48,5 +49,5 @@ enter(node) { | ||
} | ||
if (node.type === 'Element' && node.attributes.length > 0) { | ||
if (['Element', 'InlineComponent'].includes(node.type) && node.attributes.length > 0) { | ||
node.attributes.forEach((item) => { | ||
if (item.type === 'Attribute') { | ||
if (item.type === 'Attribute' && allowedAttributes.includes(item.name)) { | ||
item.value.forEach((classItem) => { | ||
@@ -72,3 +73,8 @@ var _a; | ||
const end = start + item.name.length; | ||
processor.magicContent.overwrite(start, end, processor.cssModuleList[name]); | ||
if (item.expression.type === 'Identifier') { | ||
processor.magicContent.overwrite(start, end, `${processor.cssModuleList[name]}={${item.name}}`); | ||
} | ||
else { | ||
processor.magicContent.overwrite(start, end, processor.cssModuleList[name]); | ||
} | ||
} | ||
@@ -75,0 +81,0 @@ } |
@@ -7,2 +7,4 @@ import { GetLocalIdent } from '../lib'; | ||
getLocalIdent: GetLocalIdent; | ||
hashSeeder: Array<'style' | 'filepath' | 'classname'>; | ||
allowedAttributes: string[]; | ||
}; | ||
@@ -9,0 +11,0 @@ export interface PreprocessorOptions { |
{ | ||
"name": "svelte-preprocess-cssmodules", | ||
"version": "2.0.0-rc.1", | ||
"version": "2.0.0-rc.2", | ||
"description": "Svelte preprocessor to generate CSS Modules classname on Svelte components", | ||
@@ -5,0 +5,0 @@ "keywords": [ |
# Svelte preprocess CSS Modules | ||
Generate CSS Modules classname on Svelte components | ||
```bash | ||
@@ -7,10 +9,7 @@ npm install --save-dev svelte-preprocess-cssmodules@next | ||
Generate CSS Modules classname on Svelte components | ||
- [The module Attribute](#the-module-attribute) | ||
- [Global/Local mode](#global/local-mode) | ||
- [Usage](#usage) | ||
- [Modes](#modes) | ||
- [Target any classname format](#target-any-classname-format) | ||
- [Work with class directive](#work-with-class-directive) | ||
- [Import styles from an external stylesheet](#import-styles-from-an-external-stylesheet) | ||
- [Svelte scoped system on non class selectors](#svelte-scoped-system-on-non-class-selectors) | ||
- [Destructuring import](#destructuring-import) | ||
@@ -27,5 +26,5 @@ - [kebab-case situation](#kebab-case-situation) | ||
## The module attribute | ||
## Usage | ||
Add the attribute `module` to the `<style>` tag to enable cssModules to the component. | ||
Add `module` attribute to the `<style>` tag to enable cssModules in the component. | ||
@@ -52,6 +51,10 @@ ```html | ||
### Global/Local Mode | ||
### Modes | ||
The component will use the `native` mode by default (following the philosophy of cssModules). Other mode `mixed` (same as the preprocessor `v1` ) or `scoped` (generating a unique class while using the svelte scoped system) can also be used depending of your preferences. | ||
Preprocessor can operate in the following modes: | ||
- `native` (default) - scopes classes with cssModules, anything else is unscoped | ||
- `mixed` - scopes non-class selectors with svelte scoping in addition to `native` (same as preprocessor `v1`) | ||
- `scoped` - scopes classes with svelte scoping in addition to `mixed` | ||
The mode can be set globally from the preprocessor options or locally to override the global settings per component. | ||
@@ -161,2 +164,26 @@ | ||
Use of shorthand | ||
```html | ||
<script module> | ||
let bold = true; | ||
</script> | ||
<style> | ||
.bold { font-weight: bold; } | ||
</style> | ||
<p class:bold>My bold text</p> | ||
``` | ||
*After* | ||
```html | ||
<style> | ||
.bold-2jIMhI { font-weight: bold; } | ||
</style> | ||
<p class="bold-2jIMhI">My bold text</p> | ||
``` | ||
## Import styles from an external stylesheet | ||
@@ -209,3 +236,3 @@ | ||
<script> | ||
import { red, blue } from './style.css'; | ||
import { red, blue } from './style.module.css'; | ||
</script> | ||
@@ -291,3 +318,3 @@ | ||
<script> | ||
import './style.css' | ||
import './style.module.css' | ||
</script> | ||
@@ -313,8 +340,8 @@ | ||
Use the Svelte's builtin `class:` directive or javascript template to display a class dynamically. | ||
**Note**: the *shorthand directive* is **NOT working** with CSS Modules. | ||
Use the Svelte's builtin `class:` directive or javascript template to display a class dynamically. | ||
**Note**: the *shorthand directive* is **NOT working** with imported CSS Module identifiers. | ||
```html | ||
<script> | ||
import { success, error } from './styles/module.css'; | ||
import { success, error } from './style.module.css'; | ||
@@ -393,2 +420,23 @@ let isSuccess = true; | ||
### Svelte Preprocess | ||
```bash | ||
npm install --save-dev svelte-as-markup-preprocessor | ||
``` | ||
```js | ||
const asMarkupPreprocessor = require('svelte-as-markup-preprocessor'); | ||
... | ||
preprocess: [ | ||
asMarkupPreprocessor([ | ||
sveltePreprocess() | ||
]), | ||
cssModules() | ||
], | ||
... | ||
``` | ||
Explanation on why svelte-as-markup-preprocessor is needed: [read here](https://github.com/firefish5000/svelte-as-markup-preprocessor#motivation): | ||
### Options | ||
@@ -399,7 +447,8 @@ Pass an object of the following properties | ||
| ------------- | ------------- | ------------- | ------------- | | ||
| `mode` | `native\|mixed\|scoped` | `native` | The preprocess mode to use | ||
| `localIdentName` | `{String}` | `"[local]-[hash:base64:6]"` | A rule using any available token | | ||
| `includePaths` | `{Array}` | `[]` (Any) | An array of paths to be processed | | ||
| `getLocalIdent` | `Function` | `undefined` | Generate the classname by specifying a function instead of using the built-in interpolation | | ||
| `mode` | `native\|mixed\|scoped` | `native` | The preprocess mode to use | ||
| `hashSeeder` | `{Array}` | `['style', 'filepath', 'classname']` | An array of keys to base the hash on | | ||
| `allowedAttributes` | `{Array}` | `[]` | An array of attributes to parse along with `class` | | ||
@@ -457,3 +506,3 @@ **`localIdentName`** | ||
<!-- Button.svelte --> | ||
<button class="$style.red">Ok</button> | ||
<button class="red">Ok</button> | ||
@@ -480,2 +529,9 @@ <style> | ||
**`hashSeeder`** | ||
The list of available keys are: | ||
- `style` the content of the style tag (or the imported stylesheet) | ||
- `filepath` the path of the component | ||
- `classname` the local className | ||
## Code Example | ||
@@ -561,3 +617,3 @@ | ||
```css | ||
/** style.css */ | ||
/** style.module.css */ | ||
.modal { | ||
@@ -657,2 +713,2 @@ position: fixed; | ||
[MIT](https://opensource.org/licenses/MIT) | ||
[MIT](https://opensource.org/licenses/MIT) |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
61343
916
702
0