41

I have somewhere in my code following construction:

var getMenu = function () {
    return window.fetch("portal/content/json/menu.json").then(function (data) {
        return data.json();
    });
};

I tried in my webpack.config.js this:

module: {
    loaders: [
        ...
        {
            test: /\.json$/,
            exclude: /node_modules/,
            use: [
                'file-loader?name=[name].[ext]&outputPath=portal/content/json'
            ]
        },
        ...
   ]
}

Project structure:

dist
  content
     json
        menu.json <- this is missing

src
  content
     json
       menu.json <- source file

Question:

How can webpack copy src/content/json/menu.json to dist/content/json/menu.json ?

2 Answers 2

52

You're using fetch to request a JSON file and that will only happen at runtime. Furthermore, webpack only processes anything that is imported. You expected it to handle an argument to a function, but if webpack did that, every argument to a function would be considered a module and that breaks any other use for that function.

If you want your loaders to kick in, you can import the file.

import './portal/content/json/menu.json';

You can also import the JSON and use it directly instead of fetching it a runtime. Webpack 2 uses json-loader by default for all .json files. You should remove the .json rule and you would import the JSON as follows.

import menu from './portal/content/json/menu.json';

menu is the same JavaScript object that you would get from your getMenu function.

Sign up to request clarification or add additional context in comments.

3 Comments

I use the latter option you gave but I get Cannot find module 'givenPath'.
What if you don't use fetch? Is it possible to do what's OP is asking?
14

if you'd like your json to be loaded in runtime/deferred you can use awesome webpack's dynamic imports feature:

import(
    /* webpackChunkName: "json_menu" */
    './portal/content/json/menu.json'
);

it will return a Promise which resolves to the module object, with "default" field containing your data. So you might want something like this (with es6 it looks really nice):

import(
    /* webpackChunkName: "json_menu" */
    './portal/content/json/menu.json'
).then(({default: jsonMenu}) => {
    // do whatever you like with your "jsonMenu" variable
    console.log('my menu: ', jsonMenu);
});

Notice that dynamic imports require a babel plugin syntax-dynamic-import, install it with npm:

npm i babel-plugin-syntax-dynamic-import -D

2 Comments

This is a nice alternative to fetch, but still doesn't tell me how to get webpack to write the json file to the dist folder.
@Luminous it will be there automatically, whatever you imported anywhere is turned into chunks (see webpackChunkName: "json_menu") during the compilation. Final file name and path will be determined by the webpack config - if you're not satisfied with generated names - you can utilize the code splitting name callback to fine tune it

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.