แสดง jQuery กับวัตถุ Window จริงด้วย Webpack


111

ฉันต้องการแสดงวัตถุ jQuery กับวัตถุหน้าต่างส่วนกลางที่สามารถเข้าถึงได้ภายในคอนโซลนักพัฒนาในเบราว์เซอร์ ตอนนี้ในการกำหนดค่า webpack ของฉันฉันมีบรรทัดต่อไปนี้:

plugins: [
                new webpack.ProvidePlugin({
                    $: 'jquery',
                    jQuery: 'jquery'
                })
            ]

บรรทัดเหล่านี้จะเพิ่มนิยาม jQuery ให้กับแต่ละไฟล์ในโมดูล webpack ของฉัน แต่เมื่อฉันสร้างโครงการและพยายามเข้าถึง jQuery ในคอนโซลนักพัฒนาซอฟต์แวร์เช่นนี้:

window.$;
window.jQuery;

มันบอกว่าคุณสมบัติเหล่านี้ไม่ได้กำหนด ...

มีวิธีแก้ไขปัญหานี้หรือไม่?


1
ฉันสามารถตั้งค่าได้this: 'window'หรือไม่? เนื่องจากห้องสมุดหลายแห่งถือว่าthisตัวแปรเป็นวัตถุ Window
Abhinav Singi

คำตอบ:


129

คุณจำเป็นต้องใช้เปิดเผย-loader

npm install expose-loader --save-dev

คุณสามารถทำได้เมื่อต้องการ:

require("expose?$!jquery");

หรือคุณสามารถทำได้ใน config ของคุณ:

loaders: [
    { test: require.resolve('jquery'), loader: 'expose?jQuery!expose?$' }
]

UPDATE : ใน webpack 2 คุณต้องใช้expose-loaderแทนexpose :

module: {
    rules: [{
        test: require.resolve('jquery'),
        use: [{
            loader: 'expose-loader',
            options: '$'
        }]
    }]
}

11
ProvidePluginควรใช้เป็นหลักในสถานการณ์ที่ห้องสมุดของบุคคลที่สามพึ่งพาการปรากฏตัวของตัวแปรโลก
Johannes Ewald

ฉันตั้งสมมติฐานที่ไม่ถูกต้องว่าคำถามคือการใช้ปลั๊กอินให้เพื่อวัตถุประสงค์ 'ขี้เกียจ' ซึ่งฉันเห็นออนไลน์มากมาย แต่คุณถูกต้อง :)
Matt Derrick

8
นี่คือสิ่งที่ฉันกำลังมองหาและเพียงแค่เพิ่มเพิ่มเติมสำหรับรถตักคุณสามารถทำได้ในบรรทัดเดียวเช่นกัน:{test: /jquery\.js$/, loader: 'expose?jQuery!expose?$'}
Fernando

8
คุณไม่สามารถเพิ่มสคริปต์แรกได้$ = require('jquery'); window.jQuery = $; window.$ = $;หรือไม่? (ไม่จำเป็นexpose-loader)
herman

1
ตามหน้า GitHub expose-loaderไวยากรณ์ของ webpack 2 เป็นดังนี้: module: { rules: [{ test: require.resolve('jquery'), use: [{ loader: 'expose-loader', options: 'jQuery' },{ loader: 'expose-loader', options: '$' }] }] }. นี่เป็นวิธีเดียวที่ฉันจะได้รับ jQuery และใช้ไวยากรณ์module.rulesใหม่
Gavin Sutherland

84

GivePlugin จะแทนที่สัญลักษณ์ในแหล่งอื่นผ่านการนำเข้าตามลำดับ แต่ไม่แสดงสัญลักษณ์บนเนมสเปซส่วนกลาง ตัวอย่างคลาสสิกคือปลั๊กอิน jQuery ส่วนใหญ่คาดว่าjQueryจะได้รับการกำหนดขึ้นทั่วโลก ด้วยProvidePluginคุณจะตรวจสอบให้แน่ใจว่า jQuery เป็นการพึ่งพา (เช่นโหลดมาก่อน) และการเกิดขึ้นjQueryในโค้ดของพวกเขาจะถูกแทนที่ด้วย webpack ดิบที่เทียบเท่ากับrequire('jquery').

หากคุณมีสคริปต์ภายนอกที่อาศัยสัญลักษณ์ที่จะอยู่ในเนมสเปซส่วนกลาง (เช่นสมมติว่า JS โฮสต์ภายนอก Javascript เรียกใน Selenium หรือเพียงแค่เข้าถึงสัญลักษณ์ในคอนโซลของเบราว์เซอร์) คุณต้องการใช้expose-loaderแทน

ในระยะสั้น: GivePlugin จัดการการอ้างอิงเวลาสร้างกับสัญลักษณ์ส่วนกลางในขณะที่expose-loaderจัดการการอ้างอิงรันไทม์เป็นสัญลักษณ์ส่วนกลาง


2
ขอบคุณสำหรับคำอธิบาย
Foton

ตัวอย่างของ GivePlugin พร้อมด้วย webpack จากเอกสารอย่างเป็นทางการ: webpack.js.org/plugins/provide-plugin/#usage-jquery
James Gentes

33

ดูเหมือนว่าwindowวัตถุจะถูกเปิดเผยในโมดูลทั้งหมด

ทำไมไม่เพียงแค่นำเข้า / ต้องการJQueryและใส่:

window.$ = window.JQuery = JQuery;

คุณจะต้องตรวจสอบให้แน่ใจว่าสิ่งนี้เกิดขึ้นก่อนที่จะต้อง / นำเข้าโมดูลใด ๆ ที่ใช้ประโยชน์window.JQueryไม่ว่าจะเป็นในโมดูลที่ต้องการหรือในโมดูลที่ใช้


ทางออกที่ง่ายที่สุดโดยไม่ต้องเพิ่มการพึ่งพาใหม่ ขอบคุณ!
fatihpense

ที่จะไม่ทำงานในขณะที่โมดูลซ้อนอื่น ๆ ที่ใช้ตัวแปรเพียงแค่ 'ไม่ได้กำหนด'
aboutqx

4
ใช้งานได้ดีเมื่อใช้requireในขณะที่ไม่ได้ใช้งานimport
aboutqx

@aboutqx ไม่แน่ใจว่าคุณหมายถึงอะไร คำตอบของฉันสันนิษฐานว่า JQuery ได้ถูกนำเข้า / จำเป็นและกำหนดให้กับตัวแปรที่ชื่อJQueryแล้ว
mhess

2
@mhess เมื่อคุณใช้importคุณอาจได้รับข้อผิดพลาดเนื่องจากimportถูกจัดเรียงไปที่ด้านบนของไฟล์และrequireอยู่ในตำแหน่งที่วางไว้ ดังนั้นคำสั่งรันจะเปลี่ยนimportเมื่อไม่ได้ตั้งค่า varaivble ของหน้าต่างเท่านั้น
aboutqx

16

สิ่งนี้ใช้ได้ผลสำหรับฉันเสมอ รวมถึงwebpack 3 window.$ = window.jQuery = require("jquery");


2
ทางออกที่ดีที่สุด! 2018
waza123

6

ข้างต้นไม่ได้ผลสำหรับฉัน (และฉันไม่ชอบไวยากรณ์ expose-loader) แทน,

ฉันเพิ่มไปที่ webpack.config.js:

var webpack = require('webpack');
module.exports = {
   plugins: [
       new webpack.ProvidePlugin({
           $: 'jquery',
       })     
   ]
}

กว่าโมดูลทั้งหมดจะเข้าถึงผ่าน jQuery ถึง $

คุณสามารถแสดงให้เห็นในหน้าต่างโดยเพิ่มสิ่งต่อไปนี้ในโมดูลใด ๆ ของคุณที่มาพร้อมกับ webpack:

window.$ = window.jQuery = $

1
สิ่งนี้ใช้ได้ผลสำหรับฉันโดยใช้ webpack-stream เบื้องหลัง
klewis

1

อัปเดตสำหรับ Webpack v2.0

ติดตั้งexpose-loaderตามที่ Matt Derrick อธิบายไว้:

npm install expose-loader --save-dev

จากนั้นใส่ข้อมูลโค้ดต่อไปนี้ในwebpack.config.js:

module.exports = {
    entry: {
        // ...
    },
    output: {
        // ...
    },
    module: {
        loaders: [
                { test: require.resolve("jquery"), loader: "expose-loader?$!expose-loader?jQuery" }
        ]
    }
};

(จากเอกสารexpose-loader )


ตอนนี้ฉันไม่สามารถทำให้สิ่งนี้ทำงานใน Webpack เวอร์ชันใดก็ได้อีกต่อไป ไม่แน่ใจว่ามีอะไรเปลี่ยนแปลงไปบ้าง แต่วิธีเดียวที่ฉันจะได้รับ jQuery หรือ $ ให้เป็นที่รู้จักคือทำwindow.jQuery = require('jquery');
trpt4him

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.