Il s'agit d'une réponse extrêmement longue car cette question mérite une réponse extrêmement longue et détaillée, car la méthode des "meilleures pratiques" est plus compliquée qu'une simple réponse en quelques lignes.
Iv'e a maintenu nos bibliothèques internes pendant plus de 3,5 ans pendant cette période iv'e a opté pour deux façons, je pense que les bibliothèques devraient être regroupées, les compromis dépendent de la taille de votre bibliothèque et, personnellement, nous compilons les deux façons de satisfaire les deux sous-ensembles de les consommateurs.
Méthode 1: créez un fichier index.ts avec tout ce que vous souhaitez exposer exporté et rollup cible à ce fichier comme entrée. Regroupez votre bibliothèque entière dans un seul fichier index.js et un fichier index.css; Avec des dépendances externes héritées du projet consommateur pour éviter la duplication du code de bibliothèque. (l'essentiel inclus au bas de l'exemple de configuration)
- Avantages: Facile à consommer car les consommateurs du projet peuvent tout importer depuis le chemin d'accès de la bibliothèque relative à la racine
import { Foo, Bar } from "library"
- Inconvénients: Ce ne sera jamais secouable par les arbres; et avant que les gens ne disent cela, faites avec ESM et ce sera secouable. NextJS ne prend pas en charge ESM à ce stade actuel et pas plus que beaucoup de configurations de projet, c'est pourquoi c'est toujours une bonne idée de compiler cette build pour juste CJS. Si quelqu'un importe 1 de vos composants, il obtiendra tous les css et tous les javascript de tous vos composants.
Méthode 2: c'est pour les utilisateurs avancés: créez un nouveau fichier pour chaque exportation et utilisez rollup-plugin-multi-input avec l'option "preserveModules: true" selon la façon dont le système css que vous utilisez, vous devez également vous assurer que votre css n'est PAS fusionné en un seul fichier mais que chaque fichier css nécessite une instruction (". css") est laissé dans le fichier de sortie après le rollup et ce fichier css existe.
- Avantages: Lorsque les utilisateurs importent {Foo} à partir de "library / dist / foo", ils n'obtiendront que le code pour Foo, et le CSS pour Foo et rien de plus.
- Inconvénients: Cette configuration implique que le consommateur doit gérer les instructions node_modules require (". Css") dans sa configuration de construction avec NextJS, cela se fait avec le
next-transpile-modules
package npm.
- Avertissement: nous utilisons notre propre plugin babel que vous pouvez trouver ici: https://www.npmjs.com/package/babel-plugin-qubic pour permettre aux gens de le
import { Foo,Bar } from "library"
transformer en babel ...
import { Foo } from "library/dist/export/foo"
import { Bar } from "library/dist/export/bar"
Nous avons plusieurs configurations de cumul où nous utilisons en fait les deux méthodes; Ainsi, pour les consommateurs de bibliothèques qui ne se soucient pas de l'agitation des arbres, il suffit de faire "Foo from "library"
et d'importer le fichier CSS unique; et pour les consommateurs de bibliothèques qui se soucient de secouer les arbres et qui n'utilisent que des css critiques, ils peuvent simplement activer notre plugin babel.
Guide de synthèse des meilleures pratiques:
si vous utilisez tapuscrit ou non TOUJOURS construit avec "rollup-plugin-babel": "5.0.0-alpha.1"
Assurez-vous que votre .babelrc ressemble à ceci.
{
"presets": [
["@babel/preset-env", {
"targets": {"chrome": "58", "ie": "11"},
"useBuiltIns": false
}],
"@babel/preset-react",
"@babel/preset-typescript"
],
"plugins": [
["@babel/plugin-transform-runtime", {
"absoluteRuntime": false,
"corejs": false,
"helpers": true,
"regenerator": true,
"useESModules": false,
"version": "^7.8.3"
}],
"@babel/plugin-proposal-class-properties",
"@babel/plugin-transform-classes",
["@babel/plugin-proposal-optional-chaining", {
"loose": true
}]
]
}
Et avec le plugin babel en rollup qui ressemble à ceci ...
babel({
babelHelpers: "runtime",
extensions,
include: ["src/**/*"],
exclude: "node_modules/**",
babelrc: true
}),
Et votre package.json ressemblant à ATLEAST comme ceci:
"dependencies": {
"@babel/runtime": "^7.8.3",
"react": "^16.10.2",
"react-dom": "^16.10.2",
"regenerator-runtime": "^0.13.3"
},
"peerDependencies": {
"react": "^16.12.0",
"react-dom": "^16.12.0",
}
Et enfin, vos externes en résumé ressemblant à ATLEAST comme ceci.
const makeExternalPredicate = externalArr => {
if (externalArr.length === 0) return () => false;
return id => new RegExp(`^(${externalArr.join('|')})($|/)`).test(id);
};
//... rest of rollup config above external.
external: makeExternalPredicate(Object.keys(pkg.peerDependencies || {}).concat(Object.keys(pkg.dependencies || {}))),
// rest of rollup config below external.
Pourquoi?
- Cela regroupera votre merde pour hériter automatiquement de react / react-dom et de vos autres dépendances pairs / externes du projet consommateur, ce qui signifie qu'elles ne seront pas dupliquées dans votre bundle.
- Ce sera groupé à ES5
- Cela nécessitera automatiquement ("..") dans toutes les fonctions d'assistance babel pour objectSpread, les classes, etc. du projet consommateur qui effacera 15-25 Ko supplémentaires de la taille de votre bundle et signifiera que les fonctions d'assistance pour objectSpread ne seront pas dupliquées dans votre bibliothèque sortie + la sortie groupée des projets consommateurs.
- Les fonctions asynchrones continueront de fonctionner
- externals correspondra à tout ce qui commence par ce suffixe de dépendance des pairs, c'est-à-dire que babel-helpers correspondra à external pour babel-helpers / helpers / object-spread
Enfin, voici un aperçu d'un exemple de fichier de configuration de cumul de sortie de fichier index.js unique.
https://gist.github.com/ShanonJackson/deb65ebf5b2094b3eac6141b9c25a0e3
Où le src / export / index.ts cible ressemble à ceci ...
export { Button } from "../components/Button/Button";
export * from "../components/Button/Button.styles";
export { Checkbox } from "../components/Checkbox/Checkbox";
export * from "../components/Checkbox/Checkbox.styles";
export { DatePicker } from "../components/DateTimePicker/DatePicker/DatePicker";
export { TimePicker } from "../components/DateTimePicker/TimePicker/TimePicker";
export { DayPicker } from "../components/DayPicker/DayPicker";
// etc etc etc
Faites-moi savoir si vous rencontrez des problèmes avec babel, rollup ou si vous avez des questions sur le regroupement / bibliothèques.
imported
dans le code, diminuant ainsi la taille du bundle.