2013-06-04 2 views
1

Я использую внешнюю библиотеку, состоящую из «основного» и множественного «расширений». Каждое расширение зависит от ядра. Подумайте о jQuery или Rx.RequireJS: модуль связывания с плагинами

Что мне нужно сделать, так это объединить ядро ​​вместе с некоторыми расширениями и обеспечить его как отдельный модуль. На поверхности, кажется, что-то вроде этого должно работать:

// lib.js 
define(
    "lib", 
    ["./Lib/lib", "./Lib/ext1", "./Lib/ext2"], 
    function(lib) { return lib; } 
); 

Проблема, однако, заключается в том, что расширение ожидают «ядро» будет доступен модулем ИД «Lib». Другими слова, «ext1» определяются следующим образом:

// Lib/ext1.js 
define(["lib"], function(lib) { lib.ext.someFunc = ... }); 

можно обнаружить проблему здесь: потому что название «Lib» относится к моему модулю «в комплекте», а не только «ядро», это не но доступный в то время, когда ext1 загружается, поэтому вся цепь становится круговой и разваливается.

Конечно, я мог бы сопоставить ядро ​​с «Lib», а затем дать мой в комплекте модуль другое имя:

// main.js 
require.config({ paths: { lib: "Lib/lib" } }); 

// lib.js 
define(
    "bundled-lib", 
    ["./Lib/lib", "./Lib/ext1", "./Lib/ext2"], 
    function(lib) { return lib; } 
); 

Но такой подход крайне нежелательно по нескольким причинам:

  1. Просто неудобно использовать другое имя. Нет хорошего имени здравого смысла, которое я мог бы использовать вместо этого, «lib» - это почти единственный вариант, и все остальное будет выглядеть уродливым.

  2. Но что еще более важно, это может привести к затруднительным ошибкам. В дороге, когда я забыл все об этом маленьком хаке, я могу просто следовать своему здравому смыслу и импортировать «lib» вместо «bundled-lib», а затем мои расширения не будут загружены. Или иногда они будут. Если какой-либо другой модуль, который правильно импортирует «bundled-lib», просто загружается перед новым модулем «lib» -импорт, тогда он будет работать. В противном случае это не произойдет. Это означает, что мое приложение будет либо сбой, либо не зависит от того, были ли определенные функции использованы или не использовались.

Таким образом, нижняя линия, Я хотел бы связать ядро ​​с расширениями, вызовите пакет «Lib», но почему-то есть расширения для импортировать только ядро, а не изменяя сами расширений.

Любые идеи кто-нибудь?

ответ

0

Так что всего через несколько часов после запроса вопроса я нашел ответ самостоятельно.

Ответ - map config Требований.
В принципе, как оказалось, я могу определить отображение имен модулей, как это видно каждому модулю индивидуально.

В частности, моя проблема, как это описано в вопросе, будет решена в следующей конфигурации:

require.config({ 
    map: { 
     'ext1': { 'lib': 'Lib/lib' } 
     'ext2': { 'lib': 'Lib/lib' } 
    } 
}); 

Это сделает как ext1 и ext2 модуль см «Lib/Lib» как «Lib» , не влияя на все остальные модули.

1

Звучит очень похоже на плагины jQuery и jQuery. Похоже, что у вас есть понимание последствий, поэтому вам просто нужно принять решение о том, какой метод является предпочтительным.

Я бы не пошел с модулем, который возвращает «lib», который уже имеет эти расширения. Если вы чувствуете, что вам нужна только одна зависимость, в которой вы ссылаетесь на расширенную библиотеку lib, просто перейдите к подходу «bundled-lib».

придерживаться лучших практик и не запутать себя в будущем, я считаю, что было бы лучше не объединять, но и для тех модулей, где вы полагаетесь на расширениях, включают зависимость к вашей основной Lib и тех расширений:

define(['lib', 'ext1'], function(lib){ 
    // module definition... 
    }); 

Таким образом, ОЧЕНЬ ясно, каковы зависимости для этого модуля. Я уверен, что вы об этом подумали, и я просто надеюсь, что это поможет вам принять решение.

+0

Что произойдет, если я забуду включить зависимость «ext» в некотором модуле когда-нибудь по дороге? Код иногда работает, а иногда и не работает - в зависимости от сценария использования, и его будет очень сложно поймать. Я бы очень хотел защититься от этого. –

+0

Как вы можете забыть включить зависимость в модуль? Он должен работать, когда вы его разрабатываете. Другой зависимый код будет загружать собственные зависимости. –

+0

Я могу забыть включить его, потому что на самом деле он не упоминается нигде в моем коде. Рассмотрим это: 'require (['jQuery', 'jQueryUI'], function ($, jqui) {...})'. Хотя я могу использовать расширения, предоставляемые jQueryUI, я никогда не ссылаюсь на сам аргумент 'jqui'. Поэтому, если я забуду включить его, мой код будет по-прежнему действителен, браузер не будет жаловаться, и не будут такие инструменты, как JSLint или TypeScript. И когда я загружаю его в браузер для тестирования, скорее всего, он будет работать нормально, потому что в каком-то другом модуле, вероятно, уже загружен jQueryUI. –

Смежные вопросы