2015-08-15 38 views
0

我想優化我的要求JS項目到單個文件。 我走過了多個教程,但沒有一個似乎能正常工作。要求JS - r.js優化 - 如何做到這一點?

我有以下文件結構:

scripts/ 
    build/ 
     r.js 
     build.js 
    common/ 
     misc.js 
     slider.js 
    library/ 
     jquery.min.js 
     jquery.colorbox.min.js 
     jquery.scrollTo.min.js 
     ... 
    mobile/ 
     app.js 
     catalogue.js 
     car-images.js 
     ... 
    web/ 
     app.js 
     catalogue.js 
     car-images.js 
     ... 
index.html 

我需要創建2個文件web.app.jsmobile.app.js。 經過多次嘗試後,我只管理了每個文件夾中的app.js,但沒有它的依賴關係。

結果應該是一個文件,包含commonlibraryweb/mobile目錄中的所有內容,這取決於app.js我嘗試編譯。

這裏是如何app.js樣子(webmobile是相似的):

requirejs.config({ 
    "paths": { 
     'jquery': [ 
      '//cdnjs.cloudflare.com/ajax/libs/jquery/2.1.3/jquery.min', 
      '../library/jquery.min' 
     ], 
     'colorbox': [ 
      '//cdnjs.cloudflare.com/ajax/libs/jquery.colorbox/1.4.33/jquery.colorbox-min', 
      '../library/jquery.colorbox-min' 
     ], 
     'colorbox-he': [ 
      '//cdnjs.cloudflare.com/ajax/libs/jquery.colorbox/1.4.33/i18n/jquery.colorbox-he.min', 
      '../library/jquery.colorbox-he.min' 
     ], 
     'scrollTo': [ 
      '//cdnjs.cloudflare.com/ajax/libs/jquery-scrollTo/2.1.1/jquery.scrollTo.min', 
      '../library/jquery.scrollTo.min' 
     ], 
     'misc': '../common/misc', 
     'slider': '../common/slider' 
    }, 
    "map": { 
     '*': { 
      'colorbox': 'colorbox-he' 
     }, 

     'colorbox-he': { 
      'colorbox': 'colorbox' 
     } 
    }, 
    "shim": { 
     'scrollTo': { 
      'deps': ['jquery'], 
      'exports': 'jQuery.fn.scrollTo' 
     }, 
     'colorbox': { 
      'deps': ['jquery'], 
      'exports': 'jQuery.fn.colorbox' 
     }, 
     'colorbox-he': ['colorbox'], 
     'misc': ['jquery', 'scrollTo'], 
     'car-images': ['jquery', 'colorbox'], 
    } 
}); 

if (typeof require_modules == 'object') { 
    require_modules.push('misc') 
} else { 
    var require_modules = ['misc'] 
} 

require(require_modules); 

這裏是所使用的配置:

({ 
    baseUrl: "../web", 
    name: "app", 
    out: "app-built.js" 
}) 

不知道如何對不對?由於多個文件和請求,加載時間相當長。

在此先感謝!

+0

你的問題應該包括你傳遞給'r.js'配置文件。 – Louis

+0

@Louis是的,你是對的。我更新了答案。他們非常簡單,所以我想也許沒有必要。 –

回答

0

的主要問題是,你問r.js處理此:

if (typeof require_modules == 'object') { 
    require_modules.push('misc') 
} else { 
    var require_modules = ['misc'] 
} 

require(require_modules); 

,它不能。該documentation是明確的:

優化器將僅結合了在傳遞給頂級requiredefine呼叫,或在簡化的CommonJS的包裝用require('name')字符串文字呼叫字符串文字的陣列指定模塊。如果指定像這樣

var mods = someCondition ? ['a', 'b'] : ['c', 'd']; 
require(mods); 

,但 'A' 和 'B' 將包括:所以,它不會發現,通過一個變量名加載的模塊

require(['a', 'b']); 

不幸的是,r.js只是忽略不包含字符串文字數組的require的調用。你不會有任何警告。

要解決這個問題,您可以爲每個要創建的包創建一個r.js構建配置,並對要包含的模塊進行硬編碼。更復雜的解決方案是使用類似esprima的代碼來分析代碼併爲每個包創建構建配置。或者你可以編寫一個腳本,它比esprima的能力差,但能夠從根據你所決定的約定書寫的文件中提取所需的模塊名稱。這在很大程度上取決於您的應用程序的結構。

配置中的其他問題...您必須在構建配置中使用mainConfigFile,或在運行時配置中使用重複值(如shim)到構建配置中。我會用mainConfigFile。如果您曾使用require不在頂級範圍內的呼叫,則還必須使用findNestedDependencies。您可能還需要removeCombined

+0

我有大約10種類型的頁面。每個頁面根據需要加載不同的模塊。例如,頁面正在使用一個滑塊,因此滑塊模塊將被添加到要加載的'require_modules'中。 @Louis因爲我知道在PHP級別上加載了哪些模塊,所以我應該使用類似的方式,稍後再將它組合到像我一樣的數組中。 那麼我如何優化它,但仍然使用動態包含? –

+0

「解決這個問題......」的段落會讓你得到你想要的東西。我不能更具體,因爲如何實現它高度依賴於你的應用程序的細節。 – Louis

0

正如路易斯提到你的主要問題是你的if聲明。

雖然有很多對你的選擇,我會用2個構建腳本在2個配置文件(您的應用程序文件),如指向編譯web.app.js接近這個腳本/網絡/ build.js

({ 
    mainConfigFile: 'app.js', 
    optimize: 'uglify2', 
    name: 'path/to/require.js', /* relative to where you run r.js */ 
    include: ['app'], 
    insertRequire: ['app'], 
    out: '../web.app.js', 
    wrap: true 
}) 

安裝r.js全球然後從腳本/網絡運行以下/

r.js -o build.js 

注:以上只編譯需要其它和它的依賴scrollTo & jQuery的