diff --git a/README.md b/README.md index 81c7afd..75fa8e9 100644 --- a/README.md +++ b/README.md @@ -58,6 +58,7 @@ API * [valueOf()](#valueof) * [toJSON()](#tojson) * [isBemCell(cell)](#isbemcellcell) +* [create(object)](#createobject) ### constructor(obj) @@ -191,6 +192,40 @@ BemCell.isBemCell(cell); // true BemCell.isBemCell({}); // false ``` +### #create(object) + +Creates BemCell instance by the any object representation. + +Helper for sugar-free simplicity. + +Parameter | Type | Description +-------------|----------|-------------------------- +`object` | `object` | Representation of entity name. + +Passed Object can have fields for BemEntityName and cell itself: + +Object field | Type | Description +-------------|----------|------------------------------ +`block` | `string` | The block name of entity. +`elem` | `string` | The element name of entity. +`mod` | `string`, `object` | The modifier of entity.

If specified value is `string` then it will be equivalent to `{ name: string, val: true }`. +`val` | `string` | The modifier value of entity. Used if `mod` is a string. +`mod.name` | `string` | The modifier name of entity. +`mod.val` | `*` | The modifier value of entity. +`modName` | `string` | The modifier name of entity. Used if `mod.name` wasn't specified. +`modVal` | `*` | The modifier value of entity. Used if neither `mod.val` nor `val` were not specified. +`tech` | `string` | Technology of cell. +`layer` | `string` | Layer of cell. + +```js +const BemCell = require('@bem/cell'); + +BemCell.create({ block: 'my-button', mod: 'theme', val: 'red', tech: 'css', layer: 'common' }); +BemCell.create({ block: 'my-button', modName: 'theme', modVal: 'red', tech: 'css', layer: 'common' }); +BemCell.create({ entity: { block: 'my-button', modName: 'theme', modVal: 'red' }, tech: 'css' }); // valueOf() format +// BemCell { entity: { block: 'my-button', mod: { name: 'theme', val: 'red' } }, tech: 'css', layer: 'common' } +``` + Debuggability ------------- diff --git a/index.js b/index.js index c42badb..17ac663 100644 --- a/index.js +++ b/index.js @@ -211,4 +211,42 @@ module.exports = class BemCell { static isBemCell(cell) { return cell && this.name === cell.constructor.name; } + + /** + * Creates BemCell instance by the any object representation. + * + * @param {object} obj — representation of cell. + * @param {string} obj.block — the block name of entity. + * @param {string} [obj.elem] — the element name of entity. + * @param {object|string} [obj.mod] — the modifier of entity. + * @param {string} obj.mod.name — the modifier name of entity. + * @param {string} [obj.mod.val] — the modifier value of entity. + * @param {string} [obj.modName] — the modifier name of entity. + * @param {string} [obj.modVal] — the modifier value of entity. + * @param {string} [obj.tech] — technology of cell. + * @param {string} [obj.layer] — layer of cell. + * + * @returns {BemCell} An object representing cell. + * @example + * const BemCell = require('@bem/cell'); + * + * BemCell.create({ block: 'my-button', mod: 'theme', val: 'red', tech: 'css' }); + * BemCell.create({ block: 'my-button', modName: 'theme', modVal: 'red', tech: 'css' }); + * BemCell.create({ entity: { block: 'my-button', modName: 'theme', modVal: 'red' }, tech: 'css' }); + * // BemCell { block: 'my-button', mod: { name: 'theme', val: 'red' }, tech: 'css' } + */ + static create(obj) { + if (BemCell.isBemCell(obj)) { + return obj; + } + + const data = {}; + + data.entity = BemEntityName.create(obj.entity || obj); + + obj.tech && (data.tech = obj.tech); + obj.layer && (data.layer = obj.layer); + + return new BemCell(data); + } }; diff --git a/package.json b/package.json index af237ab..0831ae7 100644 --- a/package.json +++ b/package.json @@ -3,7 +3,7 @@ "version": "0.2.1", "description": "Representation of identifier of a part of BEM entity.", "license": "MPL-2.0", - "repository": "bem-sdk/cell", + "repository": "bem-sdk/bem-cell", "author": "Andrew Abramov (github.com/blond)", "keywords": [ "bem", @@ -24,7 +24,7 @@ "node": ">= 4.0" }, "dependencies": { - "@bem/entity-name": "1.1.0" + "@bem/entity-name": "1.2.0" }, "devDependencies": { "ava": "^0.17.0", diff --git a/test/create.test.js b/test/create.test.js new file mode 100644 index 0000000..4987968 --- /dev/null +++ b/test/create.test.js @@ -0,0 +1,63 @@ +const test = require('ava'); + +const BemEntityName = require('@bem/entity-name'); + +const BemCell = require('../index'); + +test('should return object as is if it`s a BemCell', t => { + const cell = new BemCell({ entity: new BemEntityName({ block: 'b' }) }); + + t.is(BemCell.create(cell), cell); +}); + +test('should create BemCell for block from obj', t => { + const cell = BemCell.create({ block: 'b' }); + + t.pass(cell instanceof BemCell, 'Should be an instance of BemCell'); + t.is(cell.entity.block, 'b', 'Should create entity with BemEntityName.create'); +}); + +test('should create cell for elem from obj', t => { + const cell = BemCell.create({ block: 'b', elem: 'e' }); + + t.deepEqual(cell.entity.valueOf(), { block: 'b', elem: 'e' }); +}); + +test('should create cell with tech', t => { + const cell = BemCell.create({ block: 'block', tech: 'css' }); + + t.is(cell.tech, 'css'); +}); + +test('should create cell with layer', t => { + const cell = BemCell.create({ block: 'block', layer: 'desktop' }); + + t.is(cell.layer, 'desktop'); +}); + +test('should create cell with layer', t => { + const cell = BemCell.create({ block: 'block', tech: 'css', layer: 'desktop' }); + + t.is(cell.tech, 'css'); + t.is(cell.layer, 'desktop'); +}); + +test('should create BemCell for block from obj', t => { + const cell = BemCell.create({ block: 'b', elem: 'e', mod: 'm', val: 'v', tech: 't', layer: 'l' }); + + t.deepEqual(cell.valueOf(), { + entity: { block: 'b', elem: 'e', mod: { name: 'm', val: 'v' } }, + tech: 't', + layer: 'l' + }); +}); + +test('should create BemCell for entity with tech and layer from obj', t => { + const cell = BemCell.create({ entity: { block: 'b', mod: 'm', val: 'v' }, tech: 't', layer: 'l' }); + + t.deepEqual(cell.valueOf(), { + entity: { block: 'b', mod: { name: 'm', val: 'v' } }, + tech: 't', + layer: 'l' + }); +});