Войти с помощью github

В продолжение https://github.com/bem/bem-core/pull/622/files

@tadatuta: сборка бандла технологии инвалидируется по суффиксам, от которых она зависит.

@tadatuta: в данном случае есть «обычная» зависимость от js и browser.js — изменение блоков в этих технологиях инвалидирует сборку бандла. плюс по depsByTech есть зависимость от bemhtml. и изменение блоков в технологии bemhtml сейчас пересборку не вызывает, поэтому приходится передавать force явно.

@zxqfox: очень часто слова хак и depsByTech встречаются рядом.

@tadatuta: так и есть. полноценную реализацию, которую начали делать в рамках bem-tools@v1 так и не довели до конца :(

@veged: дело не столько в depsByTech сколько в сшивании двух технологий в один файл и инвалидации кешей

@zxqfox: Честно говоря, проблема здесь не в бэме или технологиях, а в его конкретной реализации/оптимизациях.

@zxqfox: Насколько я помню, там сейчас есть небезбажный монолит APW. Это он о протухшем кеше не знает?

@veged: APW это абстрактная очень штука, она сама по себе ни о чём таком не может ни знать ни не знать — но да, это уже оффтопик

Хочется понять, что надо сделать, чтобы этой проблемы не было.

На мой взгляд вариантов два:

  • Добить полноценную реализацию — для этого нужна её формализация
  • Перевести на enb и добить её там — для этого нужен адепт по enb, и опять же формализация

У кого-то еще есть желание что-то с этим сделать?

Если есть у кого, прошу ссылочку. Хочется видеть сборку простого проекта с bemtree

Наш постоянный фронтендер собрался в отпуск, а проект, кровь из носу, надо пилить. Необходимо разработать фронтенд для многошаговой регистрации с заполнением большого количества полей профиля. На вход будут предоставлен аккуратный psd-макет, консультации дизайнера и проджект-менеджера. На выходе мы ждем фронтенд, который будет сделан максимально приближенно к тому, что мы обычно делаем: БЭМ, LESS, jQuery, немного Knockout. Причем аккуратно, с любовью.

Столкнулся с этой ошибкой когда решил положить блоки и бандлы в папку src/ на проекте и настроить сборку так.

/
    .bem/
    src/
       desktop.blocks
       desktop.bundles

в make.js соответственно указал

getBundlesLevels: function() {
        return [
            'src/desktop.bundles'
        ];
    }

Сборка происходит нормально, но в такой схеме сервер падает на этом then

BEMTREE.apply(json)
        .then(function(bemjson) {
            res.send(BEMHTML.apply(bemjson));
        });

А если положить эти же папки, блоков и бандлов, в корень то все отрабатывает как надо.

Подскажике как поправить и настроить предложенную выше схему.

Весь кусок про сервер и шаблонизацию

    var bemtreeTemplate = FS.readFileSync( './src/desktop.bundles/index/_index.bemtree.js'),
        bemtmlTemplate = FS.readFileSync( './src/desktop.bundles/index/_index.bemhtml.js');


    var context = VM.createContext({
        Vow: vow,
        console: console,
        borschik: {
            link: function(i) {
                return i;
            }
        }
    });

    VM.runInContext(bemtreeTemplate, context);
    BEMTREE = context.BEMTREE;

    VM.runInContext(bemtmlTemplate, context);
    BEMHTML = context.BEMHTML;

    BEMTREE.apply(json)
        .then(function(bemjson) {
            res.send(BEMHTML.apply(bemjson));
        });

Где можно почитать?

Есть ли способ исключить блок из сборки? Например, есть блок A на уровне проекта и на уровне библиотеки. Хотелось бы, чтобы в сборку попала только реализация из проекта. Эксперименты с noDeps к желаемому результату не привели. Может быть, я не умею его готовить?

До сих пор не могу понять магию apply, applyNext, applyCtx хотя ни раз читал ман по ним

Вообще мне нужно изменить элемент на ссылку, если в параметрах есть url, я сделал так

block('nav').elem('item')
(
    match(this.ctx.url)
    (
        function()
        {
            this.ctx.block = 'link';

            delete this.ctx.elem;

            this.ctx.mix   = [
                {
                    block: this.block,
                    elem: 'item'
                }
            ];

            applyCtx(this.ctx);
        }
    )
);

Получаю бесконечную рекурсию - [RangeError: Maximum call stack size exceeded]

Сейчас я поставил такой костыль:

block('nav').elem('item')
(
    match(this.ctx.url && !this.ctx._prepared)
    (
        function()
        {
            this.ctx.block     = 'link';
            this.ctx._prepared = true;

            delete this.ctx.elem;

            this.ctx.mix   = [
                {
                    block: this.block,
                    elem: 'item'
                }
            ];

            applyCtx(this.ctx);
        }
    )
);

Как сделать правильно?

До сих пор не могу понять магию apply, applyNext, applyCtx хотя ни раз читал ман по ним

Вообще мне нужно изменить элемент на ссылку, если в параметрах есть url, я сделал так

block('nav').elem('item')
(
    match(this.ctx.url)
    (
        function()
        {
            this.ctx.block = 'link';

            delete this.ctx.elem;

            this.ctx.mix   = [
                {
                    block: this.block,
                    elem: 'item'
                }
            ];

            applyCtx(this.ctx);
        }
    )
);

Получаю бесконечную рекурсию - [RangeError: Maximum call stack size exceeded]

Сейчас я поставил такой костыль:

block('nav').elem('item')
(
    match(this.ctx.url && !this.ctx._prepared)
    (
        function()
        {
            this.ctx.block     = 'link';
            this.ctx._prepared = true;

            delete this.ctx.elem;

            this.ctx.mix   = [
                {
                    block: this.block,
                    elem: 'item'
                }
            ];

            applyCtx(this.ctx);
        }
    )
);

Как сделать правильно?

Покажите пожалуйста примеры такого использования

Входящие: Есть редктор, который сохраняет примерно такие данные

post.html = '<p>\r\n\t\tСтремление к совершенству – пожалуй, именно так можно описать развитие человечества. Вот взять, к примеру, женскую красоту. Чего только не сделают девушки, чтобы оказаться самой красивой. ... .</p>\r\n\t<!-- gallery(3) --><p>\r\n\tА вот раньше оверклокинг существовал исключительно ради выгоды. ... </p><p><!-- gallery(4) --></p>'

В этой строке есть вставки коментариев. Задача: В контексте bemtree хочу заменить комнтарии на html код блока галлереи с слайдером. Хоче сделать примерно следующее:

post.galleries.map(function(gallery, index) {
        var id = post.galleries_list[index].id,
            images = post.galleries[index].images,

            galleryBlock = {
                block : 'slider',
                slides : images
            }; //Здесь что-то нужно сделать что бы распарсить блок в строку

        post.html = post.html.replace('<!-- gallery(' + id +') -->', galleryBlock)
    })

Вопрос: Как в bemtree/bemhtml распарсить блок в html строку? Или предложите другие варианты решения проблемы?

Как к примеры вы разделяете блоки самого сайта и админки для сайта написанных на БЭМ, сейчас у меня это 2 разных проекта (основанных на project-stub, тоесть это 2 копии project-stub для публичной части и админки), думаю как их можно соеденить

Есть два блока которые должны ловить события третьего блока:

Блок который по какой-то причине не ловит события

BEM.DOM.decl('events', {

    onSetMod: {
        'js': function ()
        {
            this._invisible();

            BEM.DOM.blocks['chek-type-redaktor'].on('change_area', this._invisible, this); 

            BEM.DOM.blocks['chek-type-redaktor'].on('change_events', this._visible, this);
                }
    },

    _visible: function ()
    {
        this.setMod("hidden", "false");
    },

    _invisible: function ()
    {
        this.setMod("hidden", "true");
    }

}, {
    live: false
})

Блок который прекрасно ловит события

BEM.DOM.decl('area', {

    onSetMod:      {
        'js': function ()
        {
            BEM.DOM.blocks['chek-type-redaktor'].on('сhange_area', this._visible, this);

            BEM.DOM.blocks['chek-type-redaktor'].on('сhange_events', this._invisible, this); 
        }
    },

    _visible: function ()
    {
        this.setMod("hidden", "false");
    },

    _invisible: function ()
    {
        this.setMod("hidden", "true");
    }

}, {
    live: false
})

Блок который генерирует БЕМ события

BEM.DOM.decl('chek-type-redaktor', {
  onSetMod: {
    'js': {
      'inited': function ()
      {
                console.log("chek-type-redaktor active");
      }
    }
  },
    onChange_area: function ()
  {
    this.trigger('сhange_area');
  },
    onChange_events: function ()
  {
    this.trigger('сhange_events');
  }

}, {

  live: function ()
  {
    this.liveBindTo("change-area", 'click', function (e)
    {
      this.onChange_area(e);
    });
    this.liveBindTo("change-events", 'click', function (e)
    {
      this.onChange_events(e);
    });
    return false;
  }

});

Блоки в bemjson

{
          block: 'area',
          js: true          
},
{
          block: 'events',
          js: true
}

В чем причина того то блок events не ловит события блока chek-type-redaktor, а блок area прекрасно ловит?

5 years ago

singleton

Please kick me!

demo

/* global modules:false */
modules.define('singleton', ['inherit'], function (provide, inherit, Singleton) {

    /**
     * @abstract
     * @class Singleton
     */
    Singleton = inherit( /** @lends Singleton.prototype */ {

        /**
         * Must be implemented by subclass
         * @constructor
         * @private
         */
        __constructor: function () {}


    }, /** @lends Singleton */ {

        /**
         * Instance stores a reference to the Singleton
         * @private
         */
        _instances: [],

        /**
         * Get the Singleton instance if one exists or create one if it doesn't
         * @param c
         * @returns {*}
         */
        getInstance: function (c) {

            if (!this._instances[c]) {
                this._instances[c] = new c;
            }

            return this._instances[c];
        }
    });

    provide(Singleton);

});

/* global modules:false */
modules.define('my-singleton', ['inherit', 'singleton'], function (provide, inherit, Singleton, MySingleton) {

    /** @class MySingleton */
    MySingleton = inherit(Singleton, /** @lends MySingleton.prototype */ {

        /**
         * @constructor
         * @private
         */
        __constructor: function () {
            this._property = null;
        },

        setProperty: function (property) {
            this._property = property;
        },

        getProperty: function () {
            return this._property;
        }

    }, /** @lends MySingleton */ {

        getInstance: function () {
            return this.__base(this);
        }

    });

    provide(MySingleton);

});

modules.require(['my-singleton'], function (mySingleton) {
    var singleA = mySingleton.getInstance();
    var singleB = mySingleton.getInstance();
    alert(singleA === singleB)
});

Когда в первый раз заходишь на форум, еще не авторизован через GitHub. Начинаешь просматривать посты, проматываешь страницу вниз. При этом желтая кнопка авторизации уползает за пределы видимости. Если ты ее сразу не заметил и не авторизовался, ответить на пост невозможно. Там просто нет кнопки ответа, а то что это из-за отсуствия авторизации — не очевидно. Думаю, надо для неавторизованных делать кнопку "авторизоваться и ответить"

Привет! А есть/будет у форума RSS-лента? Есть вообще какой-нибудь roadmap?

Решил предложить в качестве идеи на подумать такой вариант - https://yadi.sk/i/HLM1KIHIYexBG Заголовок - над подписью, подпись меньше и убрать решетку с номером непонятно чего ;)

Ожидаемое поведение - открытие формы добавки поста с чекнутым bem-forum

Пока наш форум далек от идеала, но мы работаем над этим. И в этом процессе без вас не обойтись!

Поэтому, если вы заметили, что что-то не работает или работает не так, и как вам бы того хотелось, пишите про это пост прямо в форум с меткой bem-forum.

Предлагается написать блок для реализации сетки. Блок должен учитывать сетку из проектов Яндекса в новом дизайне, использующих bem-components. Я предлагаю взять для начала сетку реализованную мной тут. Это фактически порезанный порт сетки из Foundation. А затем следующей версией внедрить поддержку flexbox, чтобы можно было поддерживать старые браузеры. @tadatuta предлагал писать сразу, используя flexbox, а старые ie поддерживать отедльным css. Все заинтересованные лица приглашаются к обсуждению.

Предлагаю собрать случаи определения зависимостей, которые не удалось выразить в текущей схеме сборки, в текущих deps.js.

Обязанности bem-deps

  • инкрементальное накопление зависимостей в объектной модели
    • приём зависимостей в унифицированном формате
  • сериализация и десериализация накопленных зависимостей в унифицированный формат и из него (сохранение и чтение)
  • манипуляции с множествами зависимостей
    • объединение
    • пересечение
    • вычитание
  • вычисление упорядоченного множества БЭМ-сущностей из объектной модели дерева зависимостей по заданным критериям
  • инструменты для парсинга зависимостей из исходников

    Архитектура bem-deps

    Класс DepsContainer

Контейнер для инкрементального накопления зависимостей.

Методы инстанса:

  • add(deps) — добавляет информацию о зависимостях в контейнер; deps — чанк, описывающий зависимости в унифицированном формате
  • serialize() — сериализует информацию в унифицированный формат
  • forEach() — хелпер, позволяющий получить необходимое подмножество из объектной модели зависимостей

Статические методы:

  • deserialize() — фабрика, создаёт инстанс DepsContainer из сериализованного формата

    Формат для хранения зависимостей

TBD

Формат для накопления зависимостей

{
  deps: [
    {
      block: 'block-name', // имя блока
      elem: 'elem-name', // имя элемента
      mod: 'val' || true // имя и значение модификатора, `true` в качестве значения для булева модификатора
      priority: true // флаг приоритета зависимости
    }
  ],
  priority: [] // массив для указания приоритета зависимостей без их включения
}

Хелперы для парсинга зависимостей из исходников

Базовый класс DepsParser()

Абстрактный класс, задаёт интерфейс для парсеров зависимостей.

Класс DepsJsParser()

Парсер исходных файлов deps.js.

Класс DepsYmlParser()

Парсер исходных файлов deps.yaml.

Класс YmParser()

Парсер исходных js файлов, использующих модульную систему ym. Полезен при условии, что имена модулей однозначно соответствуют описываемых в них БЭМ-сущностям.

Утилиты

Утилиты возвращают новый инстанс DepsContainer с вычисленными зависимостями:

  • subtract(source, subtraction...)
  • merge(source...)
  • intersect(source...)
  • библиотека bem version https://github.com/bem/bem-version, статус разработки (активная или заморожена), как можно использовать? разработкой занимается @arikon, нужно уточнить у него.
  • bem-gen-doc и документация в project-stub. Заготовки для написания функциональной и jsdoc документации bem-gen-doc полностью потерял смысл существования, сейчас все возможности bem-gen-doc есть в bem-set + возможность собирать документацию по уровням.
  • bem-tools 1.0.0 в продакшене формулировка «bem-tools [любой версии] в продакшене» не имеет смысла, т.к. в продакшен попадает уже готовый код. если текущая альфа bem-tools@1.0.0 успешно собирает проект, то можно пользоваться.
  • bem.info куда постить ишью и pr исправлений на каждой странице внизу есть ссылка на соответствующий репозиторий
  • project-stub + http://yeoman.io/. Генерация вариантов проекта по bem project base, bem project express и тд давайте делать, @tadatuta готов обсуждать и всячески помогать.
  • и общий вопрос bem stack stable – стабильный набор инструментов, которые можно использовать для новых проектов. bem-bl@0.3 или bem-core + bem-tools@0.7.3

Analyze — пакет, который строит объектную структуру проекта. Первая цель — генерация UML-диаграмма классов и взаимодействий, которая бы не протухала.

Анализ структуры проекта и связей между ними.

Работает на провайдерах.

Подходит для BEViS-проектов, но сама структура не слишком завязана на BEViS, т.к. используются достаточно абстрактные сущности.

Но провайдер jsdoc работает на BT-шаблонах.

Есть провайдер для модульной системы, написанной dfilatov.

Есть дополнения.

CLI Единственная команда report — загружает конфиг .analyze.js (если есть), вынимает оттуда директории проекта, анализиует проект (все файлы с расширением js, но не test.js). Каждый файл обрабатывается отдельно.

Каждый провайдер возвращает данные, на основе которых формируется общий результат.

Пост-обработка — построение зависимостей (между классами).

Набор зависимостей — это отдельная сущность.

Обработка:

  1. Фильтры (из общей структуры остается какой-то необходимый сабсет) source target show — общая картина, все связи (source + target)
  2. Валидация (не связан со структурой, указывает на какие-то несоответствия, например, обязательное наличие return type) ErrorLog — в него пишут провайдеры и валидаторы Валидаторы имеют настройки в CLI.

На данном эта получаем Объектная модель (инстанс Project) и инстанс ErrorLog (включает указание на строку с ошибкой)

  1. Репортер

Настройка node.js-модуль экспортирует функцию, которая настраивается конфигуратором.

Планы на будущее Команда репорт не будет иметь предустановленных стратегий анализа (стратегии будут описываться отдельно). Будет возможность в js-файле описывать стратегии.

Хочется: builder (сделать настраиваемый, который бы можно было переопределять) стратегии (какой проект) вызывает процессоры про каждую сущность

file-analyzer -> js-file-analyzer

История разработки

BT-json -> MD + вставки ```BT-json, примеры и документация по js из jsdoc.

BEViS-doc-builder включает две технологии для генерации одно- и многостраничной (для Dash) документации.


Есть предложение, что нужно делать tool-chain из модулей с API, решающих конкретные задачи. И в этом контексте есть идея, что можно вынести из ENB ядро (task + node + target), для решения задачи сборки без привязки к предметной области.

У Марата нет уверенности, что устройство на node&target — это хорошо, т.к. понятие ноды излишне конкретное. Для сборщика общего назначения есть смысл оставить только target-ы (таски).


node - это папка (частный случай task) target - файлы либо папки, которые лежат в node task - как в Гранте, но без параметров (именованная задача, которая может использовать другие task).

Здесь собираем варианты API TechBuilder, выбираем наиболее подходящий.