ПредыдущийУпомянул, что я действительно не узнаю лидера веб-пакета, которого я назначил, поэтому я должен...
используется здесьпрограммист маленький серыйКартинка, вторглась и удалила.(пс: не знаю, оригинальная ли ссылка)
неудобные вопросы на собеседовании
В: Какие решения модульности js вы знаете?
Ответ: Модульность js обычно включает Commonjs AMD (CMD), ESModule и т. д. Синхронная загрузка, используемая Commonjs, обычно используется для узла, а AMD (CMD) обычно используется во внешнем интерфейсе из-за асинхронной загрузки. добиться модуляризации интерфейсной и серверной части. Унификация .
В: Так почему же синхронный Commonjs используется в узле, а асинхронный AMD — во внешнем интерфейсе?
Ответ: Приложение Node запускается на сервере, и программа может напрямую читать файлы каждого модуля через файловую систему, что отличается быстрым откликом и не будет блокировать работу программы за счет синхронизации. запускается в браузере, и каждый модуль Все js-файлы должны быть загружены через HTTP-запросы.Влияет на такие факторы, как сеть, при синхронизации браузер будет выглядеть «притворной смертью»---то есть он застрянет.Это повлияет на пользовательский опыт. Вся встреча была полностью покрыта. нет ^_^.
В: Вы слышали о webpack и знаете, как webpack реализует модульность?
Ответ: вебпакСмотри сюда, Модульность веб-пакета на самом деле заключается в перекодировании модульного кода ES6 в форму Commonjs (эй, немного паники, но вопросы интервью так запоминаются), чтобы быть совместимым с браузерами.Противоречие, это начало двигаться немного, Но сдерживаюсь, надеясь выпутаться...
В: Хорошо, поскольку вы сказали, что синхронный способ Commonjs неприменим к внешнему интерфейсу, почему форма Commonjs, перекодированная веб-пакетом, сможет работать во внешнем интерфейсе в будущем?
Ответ: эммммм
Интервьюер: Что бы еще прийти сюда первое интервью сегодня, право, вы сначала идете обратно на такие уведомления ...
я: хмммм
Что именно делает вебпак
Выполнял команду webpack снова и снова, и снова и снова изучал сгенерированный bundle.js. А? Все модули js упакованы в один bundle.js, а загрузки подмодулей вообще нет, так что мне все равно про синхронизацию или асинхронность.js файлы напрямую считываются в память за один шаг, что удобнее, чем nodejs, нуждающийся в чтении файлов...
Итак, как webpack объединяет так много файлов в один файл bundle.js?Подумайте об этом внимательно, или давайте учиться из книги со всеми, иначе я чувствую, что эта серия статей станет учебником по обмену пакетами emoji!2019-01-25-16-16-47
Далее я поделюсь обработкой webpack в Commonjs и es6 Module.Если есть вопросы по этим двум методам,погуглите.На самом деле так называемая модуляризация это не что иное,как добавление двух ключей к куску кода. Общайтесь с другими кодами, звоните друг другу, получайте возможность импортировать другие модули через require и реализуйте функцию экспорта методов в другие модули через export.
модульная обработка commonjs
Сначала добавьтеnpm script
Измените package.json, как показано ниже:
После добавлениякод, можно отбросить./node_modules/.bin/webpack
Эта команда есть сейчас, нужно только ее запаковатьnpm run build
Вот и все.
построить код проекта,кодовый адрес, где содержимое index.js:
const foo = require('./foo');
console.log(foo);
console.log('我是高级前端工程师~');
Содержимое foo.js:
module.exports = {
name: 'quanquan',
job: 'fe',
};
Чисто чистый код Commonjs, выполнитьnpm run build
После этого давайте посмотрим на упакованный bundle.js (ps: добавлены некоторые комментарии)
(function(modules) {
// 缓存模块对象
var installedModules = {};
// 模拟 commonjs 实现的 require
function __webpack_require__(moduleId) {
// require 模块时先判断是否已经缓存, 已经缓存的模块直接返回
if(installedModules[moduleId]) {
return installedModules[moduleId].exports;
}
// (模拟)创建一个模块, 并把新模块的引用保存到缓存中
var module = installedModules[moduleId] = {
// 模块 id
i: moduleId,
// 模块是否已加载
l: false,
// 模块主体内容, 会被重写
exports: {}
};
// 执行以下模块的包装函数, 并把模块内部的 this 志向模块主体
modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
// 将模块标记为已加载
module.l = true;
// 返回模块主体内容
return module.exports;
}
// 向外暴露所有的模块
__webpack_require__.m = modules;
// 向外暴露已缓存的模块
__webpack_require__.c = installedModules;
// 下边两个方法暂时还没有用到
// define getter function for harmony exports
__webpack_require__.d = function(exports, name, getter) {
if(!__webpack_require__.o(exports, name)) {
Object.defineProperty(exports, name, {
configurable: false,
enumerable: true,
get: getter
});
}
};
// getDefaultExport function for compatibility with non-harmony modules
__webpack_require__.n = function(module) {
var getter = module && module.__esModule ?
function getDefault() { return module['default']; } :
function getModuleExports() { return module; };
__webpack_require__.d(getter, 'a', getter);
return getter;
};
// Object.prototype.hasOwnProperty.call 这个就没啥好解释的啦
// js 权威指南上有说
__webpack_require__.o = function(object, property) {
return Object.prototype.hasOwnProperty.call(object, property);
};
// __webpack_public_path__
// 这个暂时还没有用到
__webpack_require__.p = "";
// Load entry module and return exports
// 准备工作做完了, require 一下入口模块, 让项目跑起来
return __webpack_require__(__webpack_require__.s = 0);
})
/******** 华丽的分割线 上边时 webpack 初始化代码, 下边是我们写的模块代码 ***************/
([
/* 模块 0 对应 index.js */
/***/ (function(module, exports, __webpack_require__) {
const foo = __webpack_require__(1);
console.log(foo);
console.log('我是高级前端工程师~');
/***/ }),
/* 模块 1 对应 foo.js */
/***/ (function(module, exports) {
module.exports = {
name: 'quanquan',
job: 'fe',
};
/***/ })
]);
Получается, что webpack оборачивает написанный нами код одной за другой функцией-оберткой, а затем вызывает функцию-обертку при выполнении __webpack_require__, код внутри функции-обертки переписывает атрибут exports модуля параметра в параметре, и получает нам тело код написанного модуля.
так что мы видимindex.js
Обернутый код:
function(module, exports, __webpack_require__) {
const foo = __webpack_require__(1);
console.log(foo);
console.log('我是高级前端工程师~');
}
foo.js
Обернутый код:
function(module, exports) {
module.exports = {
name: 'quanquan',
job: 'fe',
};
}
Поскольку index.js имеетrequire('./foo')
Поэтому __webpack_require__ используется для импорта модуля foo в параметры функции упаковки, сгенерированные index.js. От начала до конца предыдущая книга больше не кажется непонятной и сложной для понимания. Конечно, эта часть контента требует небольшой мозговой штурм .Я также надеюсь, что каждый будет оставлять свои мысли и вопросы в области комментариев, и мы будем обсуждать вместе.
Модульная обработка модуля es6
Измените код нашего проекта на модульный код es6, сначала изменитеindex.js
:
import foo from './foo';
console.log(foo);
console.log('我是高级前端工程师~');
Вторая модификацияfoo.js
export default {
name: 'quanquan',
job: 'fe',
};
Наконец, выполнение командной строкиnpm run build
Упакуйте его После упаковкиbundle.js
Содержание выглядит следующим образом (оптимизировано):
(function(modules) {
var installedModules = {};
function __webpack_require__(moduleId) {
if(installedModules[moduleId]) {
return installedModules[moduleId].exports;
}
var module = installedModules[moduleId] = {
i: moduleId,
l: false,
exports: {}
};
modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
module.l = true;
return module.exports;
}
__webpack_require__.m = modules;
__webpack_require__.c = installedModules;
__webpack_require__.d = function(exports, name, getter) {
if(!__webpack_require__.o(exports, name)) {
Object.defineProperty(exports, name, {
configurable: false,
enumerable: true,
get: getter
});
}
};
__webpack_require__.n = function(module) {
var getter = module && module.__esModule ?
function getDefault() { return module['default']; } :
function getModuleExports() { return module; };
__webpack_require__.d(getter, 'a', getter);
return getter;
};
__webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };
__webpack_require__.p = "";
return __webpack_require__(__webpack_require__.s = 0);
})([
function(module, __webpack_exports__, __webpack_require__) {
"use strict";
Object.defineProperty(__webpack_exports__, "__esModule", { value: true });
var __WEBPACK_IMPORTED_MODULE_0__foo__ = __webpack_require__(1);
console.log(__WEBPACK_IMPORTED_MODULE_0__foo__["a"]);
console.log('我是高级前端工程师~');
},
function(module, __webpack_exports__, __webpack_require__) {
"use strict";
__webpack_exports__["a"] = ({
name: 'quanquan',
job: 'fe',
});
}
]);
Результатом упаковки по-прежнему является код небес, к счастью, он аналогичен методу модуляризации commonjs.Код инициализации веб-пакета такой же.
index.js
Сгенерированный код пакета:
function(module, __webpack_exports__, __webpack_require__) {
"use strict";
Object.defineProperty(__webpack_exports__, "__esModule", { value: true });
var __WEBPACK_IMPORTED_MODULE_0__foo__ = __webpack_require__(1);
console.log(__WEBPACK_IMPORTED_MODULE_0__foo__["a"]);
console.log('我是高级前端工程师~');
}
foo.js
Сгенерированный код пакета:
function(module, __webpack_exports__, __webpack_require__) {
"use strict";
__webpack_exports__["a"] = ({
name: 'quanquan',
job: 'fe',
});
}
Отличие от commonjs найти несложно:
- Во-первых, перед параметрами функции-оболочки
module.exports
стал__webpack_exports__
- Во-вторых, если используется синтаксис импорта модуля es6 (import), дайте
__webpack_exports__
Добавлены свойства__esModule
- Остальное похоже на commonjs
Мы обнаружили, что то, что полезно в commonjs__webpack_require__.n
Этот метод до сих пор не используется, это пустой метод?Тогда вы можете подать заявку на веб-пакет, и проекты с открытым исходным кодом, в которых вы участвовали, больше не будут пустыми.
Не будет ли слишком легко сесть на автобус такого международного проекта с открытым исходным кодом?
Модуль es6 CommonJs смешанное использование
Исправлятьfoo.js
Содержание следующее:
module.exports = {
name: 'quanquan',
job: 'fe',
};
Результат упаковки:
/******/ (function(modules) { // webpackBootstrap
/******/ // The module cache
/******/ var installedModules = {};
/******/
/******/ // The require function
/******/ function __webpack_require__(moduleId) {
/******/
/******/ // Check if module is in cache
/******/ if(installedModules[moduleId]) {
/******/ return installedModules[moduleId].exports;
/******/ }
/******/ // Create a new module (and put it into the cache)
/******/ var module = installedModules[moduleId] = {
/******/ i: moduleId,
/******/ l: false,
/******/ exports: {}
/******/ };
/******/
/******/ // Execute the module function
/******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
/******/
/******/ // Flag the module as loaded
/******/ module.l = true;
/******/
/******/ // Return the exports of the module
/******/ return module.exports;
/******/ }
/******/
/******/
/******/ // expose the modules object (__webpack_modules__)
/******/ __webpack_require__.m = modules;
/******/
/******/ // expose the module cache
/******/ __webpack_require__.c = installedModules;
/******/
/******/ // define getter function for harmony exports
/******/ __webpack_require__.d = function(exports, name, getter) {
/******/ if(!__webpack_require__.o(exports, name)) {
/******/ Object.defineProperty(exports, name, {
/******/ configurable: false,
/******/ enumerable: true,
/******/ get: getter
/******/ });
/******/ }
/******/ };
/******/
/******/ // getDefaultExport function for compatibility with non-harmony modules
/******/ __webpack_require__.n = function(module) {
/******/ var getter = module && module.__esModule ?
/******/ function getDefault() { return module['default']; } :
/******/ function getModuleExports() { return module; };
/******/ __webpack_require__.d(getter, 'a', getter);
/******/ return getter;
/******/ };
/******/
/******/ // Object.prototype.hasOwnProperty.call
/******/ __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); };
/******/
/******/ // __webpack_public_path__
/******/ __webpack_require__.p = "";
/******/
/******/ // Load entry module and return exports
/******/ return __webpack_require__(__webpack_require__.s = 0);
/******/ })
/************************************************************************/
/******/ ([
/* 0 */
/***/ (function(module, __webpack_exports__, __webpack_require__) {
"use strict";
Object.defineProperty(__webpack_exports__, "__esModule", { value: true });
/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0__foo__ = __webpack_require__(1);
// 这里用到了 __webpack_require__.n
/* harmony import */ var __WEBPACK_IMPORTED_MODULE_0__foo___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0__foo__);
console.log(__WEBPACK_IMPORTED_MODULE_0__foo___default.a);
console.log('我是高级前端工程师~');
/* harmony default export */ __webpack_exports__["default"] = ({});
/***/ }),
/* 1 */
/***/ (function(module, exports) {
module.exports = {
name: 'quanquan',
job: 'fe',
};
/***/ })
/******/ ]);
index.js
Нет никаких изменений, то есть, когда синтаксис экспорта модуля экспорта — commonjs, а синтаксис импорта импортированного модуля — es6, будет использоваться модуль импорта.__webpack_require__.n
Сюда.
Превью следующего эпизода: Здесь анализируется результат упаковки чистого js-файла. Webpack умно упаковывает все модули в файл bundle.js для достижения синхронной загрузки модулей, что действительно умно. Однако, если ваш проект очень большой, Сотни тысяч js-модулей, как мы можем использовать webpack для разделения кода в это время? Давайте обсудим вместе на следующем шаге.