Webpack.config jak po prostu skopiować plik index.html do folderu dist

189

Próbuję zautomatyzować przechodzenie do / dist. Mam następujące config.js:

module.exports = {
  context: __dirname + "/lib",
  entry: {
    main: [
      "./baa.ts"
    ]
  },
  output: {
    path: __dirname + "/dist",
    filename: "foo.js"
  },
  devtool: "source-map",
  module: {
    loaders: [
      {
        test: /\.ts$/,
        loader: 'awesome-typescript-loader'
      },
      { test: /\.css$/, loader: "style-loader!css-loader" }
    ]
  },
  resolve: {
    // you can now require('file') instead of require('file.js')
    extensions: ['', '.js', '.json']
  }
}

Chcę również dołączyć main.html z katalogu, który znajduje się obok / lib, do folderu / dist podczas uruchamiania pakietu. W jaki sposób mogę to zrobić?

AKTUALIZACJA 1 2017_____________

Moim ulubionym sposobem na zrobienie tego teraz jest użycie html-webpack-pluginz plikiem szablonu. Dzięki również przyjętej odpowiedzi! Zaletą tego sposobu jest to, że do pliku indeksu zostanie dodany także dołączony link js!

SuperUberDuper
źródło

Odpowiedzi:

162

opcja 1

W swoim index.jspliku (czyli wejście WebPack) dodaj wymagają do swojej index.htmlpoprzez file-ładowarki wtyczki, np:

require('file-loader?name=[name].[ext]!../index.html');

Po zbudowaniu projektu za pomocą pakietu Webpack index.htmlbędzie w folderze wyjściowym.

Opcja 2

Użyj wtyczki html-webpack, aby w ogóle nie mieć pliku index.html. Wystarczy, że webpack wygeneruje plik dla Ciebie.

Witalij B.
źródło
2
czy mogę jakoś go załadować, pisząc coś w samym pliku konfiguracyjnym?
codeVerine
Wypróbowałem pierwszy sposób i skopiowałem pliki. Ale kopiowany przeze mnie CSS przestał działać poprawnie. (Potrzebowałem go zewnętrznego do webpacka, ponieważ Handsontable nie może współpracować z webpakiem.)
Vaccano
@Vaccano dla CSS nie powinieneś używać tej metody. Użyj modułu ładującego styl i modułu ładującego css, patrz tutaj: stackoverflow.com/questions/34039826/...
VitalyB
4
W webpack v2 najwyraźniej nie można pominąć -loaderprzyrostka. np.require('file-loader?name=[name].[ext]!../index.html');
przemyśl
1
@codeVerine Tak, używając dodając coś { test: /index\.html/, loader: 'file-loader', query: { name: '[name].[ext]' }do swojej loaderstablicy w pliku konfiguracyjnym webpack, tylko nie mogłem uzyskać serwera webpack-dev-server, który mógłby go obsłużyć, co prowadziło, co zabawne, do żądania 404 /(root nie istnieje !).
Brian McCutchon
67

Dodam opcję do odpowiedzi VitalyB:

Opcja 3

Via npm. Jeśli uruchamiasz swoje polecenia za pomocą npm, możesz dodać tę konfigurację do pliku package.json (sprawdź tam również plik webpack.config.js). W celu opracowania uruchomienia npm startnie trzeba w tym przypadku kopiować pliku index.html, ponieważ serwer WWW zostanie uruchomiony z katalogu plików źródłowych, a plik bundle.js będzie dostępny z tego samego miejsca (plik bundle.js będzie żył tylko w pamięci, ale będzie dostępny tak, jakby był umieszczony razem z plikiem index.html). Do uruchomienia produkcyjnego npm run buildfolder dist będzie zawierać plik bundle.js, a plik index.html zostanie skopiowany za pomocą starego, dobrego polecenia cp, jak widać poniżej:

"scripts": {
    "test": "NODE_ENV=test karma start",
    "start": "node node_modules/.bin/webpack-dev-server --content-base app",
    "build": "NODE_ENV=production node node_modules/.bin/webpack && cp app/index.html dist/index.html"
  }

Aktualizacja: Opcja 4

Istnieje wtyczka copy-webpack , jak opisano w odpowiedzi Stackoverflow

Ale generalnie, z wyjątkiem samego „pierwszego” pliku (takiego jak index.html) i większych zasobów (takich jak duże obrazy lub wideo), dołącz css, html, obrazy itd. Bezpośrednio do Twojej aplikacji za pośrednictwem, requirea webpack je dla ciebie uwzględni (cóż, po prawidłowej konfiguracji z modułami ładującymi i prawdopodobnie wtyczkami).

EricC
źródło
11
Wariant 3 powinien być wariantem 1
Gil Epshtain
2
Wypróbowałem opcję 3, ale ponowne ładowanie index.html nie działało. Czy nie edytujesz często pliku index.html? Poważne pytanie.
kamień
3
Użyj ncp zamiast cp, jeśli chcesz obsługiwać środowiska programistyczne dla różnych systemów operacyjnych
Vivek Maharajh,
33

Możesz użyć CopyWebpackPlugin . Działa tak:

module.exports = {
  plugins: [
    new CopyWebpackPlugin([{
      from: './*.html'
    }])
  ]
}
hobbeshunter
źródło
Teraz, gdy Webpack zastąpił Gulpa i Grunta nie tylko łączeniem pakietów, ale także wieloma innymi zadaniami związanymi z kompilacją, to rozwiązanie widziałem w większości projektów. Skrypty w package.jsonsą używane tylko do prostych rzeczy, takich jak uruchomienie testera lub serwera deweloperskiego.
Robert Jack Will
15

Powiedziałbym, że odpowiedź brzmi: nie możesz. (a przynajmniej: nie powinieneś). Nie to powinien robić Webpack. Webpack jest pakietem i nie należy go używać do innych zadań (w tym przypadku: kopiowanie plików statycznych to inne zadanie). Do takich zadań powinieneś używać narzędzia takiego jak Grunt lub Gulp. Bardzo często integruje się Webpack jako zadanie Grunt lub Gulp . Oba mają inne zadania przydatne do kopiowania plików, takich jak opisany, na przykład chrobot-contrib-copy lub gulp-copy .

W przypadku innych zasobów (nie index.html) możesz po prostu połączyć je z pakietem Webpack (właśnie do tego służy pakiet Webpack). Na przykład var image = require('assets/my_image.png');. Ale zakładam, że twoje index.htmlpotrzeby nie powinny być częścią pakietu, a zatem nie jest to zadanie dla osoby pakującej.

Brodie Garnet
źródło
59
Właśnie poszedłem na webpack, więc nie musiałbym używać chrząkania ani przełykania. Czy jest jakaś inna alternatywa? Jeśli muszę użyć łyka, dlaczego powinienem zawracać sobie głowę pakietem internetowym?
SuperUberDuper
4
Pytanie jest do góry nogami. Dlaczego warto korzystać z webpacka, jeśli można używać chrząkania lub przełykania? Są to bardzo dobre systemy zadań / kompilacji. Webpack (lub Browserify lub r.js) to narzędzia, których można używać do łączenia wielu plików JS (i innych zasobów) w jeden duży (lub wiele) pakietów javascript. Powinieneś użyć właściwego narzędzia do pracy. I znowu bardzo często uruchamia się webpack, browserrify lub inne programy pakujące od chrząkania lub przełykania.
Brodie Garnet
1
Webpack może to zrobić na wiele sposobów. Można użyć file-loaderktóre w zasadzie tylko kopiuje plik / obraz do katalogu wyjściowego i daje url gdy tego wymaga: var url = require('myFile');. Jak powiedziałem, pakiet może zawierać jeden lub wiele plików.
Brodie Garnet
1
Mogę użyć brocolli jako procesu kompilacji nadrzędnej
SuperUberDuper
1
To dla mnie odpowiednia odpowiedź. W dużych / złożonych projektach ważna jest wydajność kompilacji pakietu. Różne wtyczki do kopiowania plików zwiększają niepotrzebny koszt pakietu internetowego, pozwalając skupić się na pakietowaniu JS.
Evi Song,
14

Możesz dodać indeks bezpośrednio do konfiguracji wpisu i załadować go za pomocą modułu ładującego pliki

module.exports = {

  entry: [
    __dirname + "/index.html",
    .. other js files here
  ],

  module: {
    rules: [
      {
        test: /\.html/, 
        loader: 'file-loader?name=[name].[ext]', 
      },
      .. other loaders
    ]
  }

}
Jake Coxon
źródło
5

Aby skopiować już istniejący index.htmlplik do distkatalogu, możesz po prostu użyć HtmlWebpackPlugin , określając źródło index.htmljako szablon .

const HtmlWebpackPlugin = require('html-webpack-plugin');

module.exports = {
  // ...
  plugins: [    
    new HtmlWebpackPlugin({
      template: './path/to/index.html',
    })
  ],
  // ...
};

Utworzony dist/index.htmlplik będzie w zasadzie taki sam, jak plik źródłowy, z tą różnicą, że zasoby pakietowe, takie jak pliki .js, są wstrzykiwane za pomocą <script>znaczników przez pakiet WWW. Można skonfigurować minimalizację i dodatkowe opcje, które są udokumentowane na github .

Tobi Obeck
źródło
3

Działa to dobrze w systemie Windows:

  1. npm install --save-dev copyfiles
  2. W package.jsonMam zadanie kopiowania:"copy": "copyfiles -u 1 ./app/index.html ./deploy"

To przenosi mój index.html z folderu aplikacji do folderu wdrażania.

Patrick Desjardins
źródło
Rozumiem, że działa, korzystając z odpowiedzi tam: stackoverflow.com/questions/38858718/…
IsraGab
3

Aby rozszerzyć odpowiedź @ hobbeshunter, jeśli chcesz wziąć tylko index.html, możesz także użyć CopyPlugin. Główną motywacją do korzystania z tej metody w porównaniu z innymi pakietami jest koszmar, aby dodawać wiele pakietów dla każdego typu i konfigurować je itd. najprostszym sposobem jest użycie CopyPlugin do wszystkiego:

npm install copy-webpack-plugin --save-dev

Następnie

const CopyPlugin = require('copy-webpack-plugin');

module.exports = {
  plugins: [
    new CopyPlugin([
      { from: 'static', to: 'static' },
      { from: 'index.html', to: 'index.html', toType: 'file'},
    ]),
  ],
};

Jak widać, skopiuj cały folder statyczny wraz z całą zawartością do folderu dist. Nie wymaga css, pliku ani żadnych innych wtyczek.

Chociaż ta metoda nie pasuje do wszystkiego, wykona zadanie w prosty i szybki sposób.

Remy
źródło
-1

Znalazłem też to łatwe i tyle ogólne, aby umieścić mój index.html plik w dist/ katalogu i dodać <script src='main.js'></script>do index.htmlobejmować moje spakowane pliki WebPACK. main.jswydaje się być domyślną nazwą wyjściową naszego pakietu, jeśli nie podano go w pliku conf pakietu web . Myślę, że to nie jest dobre i długoterminowe rozwiązanie, ale mam nadzieję, że pomoże zrozumieć, jak działa webpack .

Qback
źródło