o webpack não consegue encontrar o módulo se o arquivo for chamado jsx

107

Enquanto escrevo webpack.config.js assim

module.exports = {
  entry: './index.jsx',
  output: {
    filename: 'bundle.js'
  },
  module: {
    loaders: [{
      test: /\.jsx?$/,
      exclude: /node_modules/,
      loader: 'babel',
      query: {
        presets: ['es2015', 'react']
      }
    }]
  }
};

E index.jsxeu importo um reactmóduloApp

import React from 'react';
import { render } from 'react-dom';

import App from './containers/App';

let rootElement = document.getElementById('box')
render(
  <App />,
  rootElement
)

Se eu App.jsxnomeiei o módulo app em , então o webpack dirá index.jsxnão é possível encontrar o módulo App, mas se eu nomeei o módulo app nomeado em App.js, ele encontrará esse módulo e funcionará bem.

Então, estou confuso sobre isso. No meu webpack.config.js, escrevi test: /\.jsx?$/para verificar o arquivo, mas por que o named *.jsxnão pode ser encontrado?

insira a descrição da imagem aqui

qiuyuntao
fonte

Respostas:

214

Webpack não sabe resolver .jsxarquivos implicitamente. Você pode especificar uma extensão de arquivo em seu aplicativo ( import App from './containers/App.jsx';). Seu teste de carregador atual diz para usar o carregador babel quando você importar explicitamente um arquivo com a extensão jsx.

ou você pode incluir .jsxnas extensões que o webpack deve resolver sem declaração explícita:

module.exports = {
  entry: './index.jsx',
  output: {
    filename: 'bundle.js'
  },
  module: {
    loaders: [{
      test: /\.jsx?$/,
      exclude: /node_modules/,
      loader: 'babel',
      query: {
        presets: ['es2015', 'react']
      }
    }]
  },
  resolve: {
    extensions: ['', '.js', '.jsx'],
  }
};

Para Webpack 2, omita a extensão vazia.

resolve: {
  extensions: ['.js', '.jsx']
}
max
fonte
63
Para o webpack 4, descobri que precisava colocá-lo em um dos programas rulelistados em module...{ module: { rules: [ { test: /\.jsx?$/, resolve: { extensions: [".js", ".jsx"] }, include: ... } ] }
mr rogers
1
@mrrogers eu pesquisei em todos os lugares por isso! Eu tiro meu chapéu para você, senhor!
Frederik Petersen
1
muito obrigado! Eu estava procurando por isso por horas!
KevinH
1
@mrrogers Considere promover seu comentário como uma resposta :)
Alexander Varwijk
Obrigado @AlexanderVarwijk. Boa ideia. Eu mesmo voltei a esses comentários para lembrar o que tive que fazer :)
sr. Rogers
24

Adicionando à resposta acima,

A propriedade resolve é onde você deve adicionar todos os tipos de arquivo que está usando em seu aplicativo.

Suponha que você queira usar arquivos .jsx ou .es6 ; você pode incluí-los aqui e o webpack os resolverá:

resolve: {
  extensions: ["", ".js", ".jsx", ".es6"]
}

Se você adicionar as extensões na propriedade resolver , poderá removê-las da instrução de importação:

import Hello from './hello'; // Extensions removed
import World from './world';

Outros cenários, como se você deseja que o script de café seja detectado, você deve configurar sua propriedade de teste também como:

// webpack.config.js
module.exports = {
  entry: './main.js',
  output: {
    filename: 'bundle.js'       
  },
  module: {
    loaders: [
      { test: /\.coffee$/, loader: 'coffee-loader' },
      {
        test: /\.js$/,
        loader: 'babel-loader',
        query: {
          presets: ['es2015', 'react']
        }
      }
    ]
  },
  resolve: {
    // you can now require('file') instead of require('file.coffee')
    extensions: ['', '.js', '.json', '.coffee'] 
  }
};
Inácio André
fonte
7
No WebPack 3.4, você não pode usar resolve.extension com valor vazio. Isso causará uma exceção na compilação: "Objeto de configuração inválido. Webpack foi inicializado usando um objeto de configuração que não corresponde ao esquema da API. - configuration.resolve.extensions [0] não deve estar vazio."
Julio Spader
19

No interesse da legibilidade e da codificação copy-paste. Aqui está a resposta do webpack 4 do comentário do sr. Roger neste tópico.

module: {
  rules: [
    {
      test: /\.(js|jsx)$/,
      exclude: /node_modules/,
      resolve: {
        extensions: [".js", ".jsx"]
      },
      use: {
        loader: "babel-loader"
      }
    },
  ]
}
Richard Vanbergen
fonte
De 4.36.1 para ser mais preciso. Aqui está o documento webpack.js.org/configuration/module/#ruleresolve
Alexey Berezkin
10

Conforme mencionado nos comentários sobre a resposta de @max, para o webpack 4, descobri que precisava colocar isso em uma das regras que estavam listadas no módulo, assim:

{
  module: {
    rules: [ 
      {
        test: /\.jsx?$/, 
        resolve: {
          extensions: [".js", ".jsx"]
        },
        include: ...
      }
    ]
  }
}
Sr. Roger
fonte
1

Eu estava enfrentando um problema semelhante e consegui resolvê-lo usando a propriedade resolve .

const path = require('path');
module.exports = {
    entry: './src/app.jsx',
    output: {
        path: path.join(__dirname,'public'),
        filename:  'bundle.js'
    },
    module : {
        rules: [{
            loader: 'babel-loader',
            test: /\.jsx$/,
            exclude: /node_modules/
        }]
    },
    resolve: {
        extensions: ['.js', '.jsx']
    }
}

Como você pode ver, usei .jsx lá, que resolveu o seguinte erro

ERROR in ./src/app.jsx Module not found: Error: Can't resolve

Para referência: https://webpack.js.org/configuration/resolve/#resolve-extensions

apenas-seja-estranho
fonte
0

Verifique se bundle.js está sendo gerado sem erros (verifique o registro do executor de tarefas).

Eu estava recebendo 'não é possível localizar o módulo se o arquivo denominado jsx' devido ao erro de sintaxe em html na função de renderização do componente.

Rluks
fonte