Typescript ReferenceError: nie zdefiniowano eksportu


105

Próbując wdrożyć moduł zgodnie z oficjalnym podręcznikiem , otrzymuję następujący komunikat o błędzie:

Uncaught ReferenceError: nie zdefiniowano eksportu

w app.js: 2

Ale nigdzie w moim kodzie nie używam tego imienia exports.

Jak mogę to naprawić?


Pliki

app.ts

let a = 2;
let b:number = 3;

import Person = require ('./mods/module-1');

moduł-1.t

 export class Person {
  constructor(){
    console.log('Person Class');
  }
}
export default Person;

tsconfig.json

{
   "compilerOptions": {
        "module": "commonjs",
        "target": "es5",
        "noImplicitAny": false,
        "sourceMap": true,
        "outDir": "scripts/"
    },
    "exclude": [
        "node_modules"
    ]
}

Skopiuj i wklej tekst błędu do pytania zamiast używać zrzutów ekranu.
Igor

Na pewno nie typ exportsz S na końcu zamiast export? To wyjaśniałoby komunikat o błędzie, ponieważ w przypadku s jest błędne.
Igor

piszę eksport, a nie eksport
George C.

jakikolwiek przykład z repozytorium, który będzie działał 10000%
George C.

Gdzie to się dzieje? Na stronie internetowej? Na serwerze node.js? Będziesz potrzebował modułu ładującego moduł w środowisku wykonawczym, w którym ostatecznie uruchomi się javascript. Z flag kompilatora, których używasz, commonjs. Nie jestem zbyt zaznajomiony z commonjs, ale będziesz musiał skonfigurować commonjs, zanim moduły Typescript będą działać, lub będziesz musiał zmienić na inny moduł ładujący (taki jak require.js) i ustawić go.
Mike Wodarczyk

Odpowiedzi:


41

EDYTOWAĆ:

Ta odpowiedź może nie działać, w zależności od tego, czy nie jesteś es5już celem , postaram się uzupełnić odpowiedź.

Oryginalna odpowiedź

Jeśli CommonJS nie jest zainstalowany ( co definiujeexports ), musisz usunąć ten wiersz z tsconfig.json:

 "module": "commonjs",

Zgodnie z komentarzami, to samo może nie działać z późniejszymi wersjami tsc. W takim przypadku można zainstalować moduł ładujący, taki jak CommonJS, SystemJS lub RequireJS, a następnie to określić.

Uwaga:

Spójrz na wygenerowany main.jsplik tsc. Znajdziesz to na samej górze:

Object.defineProperty(exports, "__esModule", { value: true });

Jest to źródło komunikatu o błędzie i po usunięciu "module": "commonjs",zniknie.


3
Tak, ponownie skompilowałem mój plik .ts i błąd nadal występuje po skomentowaniu "module": "commonJs",:(
Acidic9,

2
Jeśli po zainstalowaniu CommonJS ten błąd zniknie, to jak właściwie można zainstalować CommonJS? Spędziłem większą część godziny na Google i nie mogę znaleźć żadnych instrukcji, jak to zrobić. Może ktoś proszę wyjaśnić?
Sturm

1
@Sturm Moja odpowiedź może być myląca. CommonJS to tylko specyfikacja. Możesz znaleźć (niekoniecznie wyczerpującą) listę implementacji tutaj: en.wikipedia.org/wiki/CommonJS
iFreilicht

1
Mam moduł: amd, a nie moduł: commonjs, i mam tę linię w moim transpilowanym pliku .js.
pabrams

2
Jeśli masz cel jako ES3 lub ES5 w swoim tsconfig.json, to Typscript automatycznie ustawi twój moduł na CommonJS, jeśli nie jest zdefiniowany. Usunięcie modułu nie wystarczy, zamiast tego musisz ustawić coś innego - patrz typescriptlang.org/docs/handbook/compiler-options.html
Jake,

52

Kilka innych rozwiązań tego problemu

  • Dodaj następujący wiersz przed innymi odwołaniami do JavaScript. To miły mały hack.
   <script>var exports = {};</script>
  • Ten problem występuje w najnowszej wersji języka TypeScript. Ten błąd można wyeliminować, odwołując się do maszynopisu w wersji 2.1.6

3
@ChuckLeButt Mam nadzieję, że to pomaga stackoverflow.com/questions/19059580/…
Venkatesh Muniyandi

3
Nienawidzę tego, że to działa! I na pewno działa. Czy nie ma sposobu na przeniesienie TypeScript do czegoś, czego oczekuje Node? Czy to w ogóle Node narzeka? A może to przeglądarka? Nie mogę znieść, że nie rozumiem, na czym właściwie polega problem.
skillit zimberg

9

npm install @babel/plugin-transform-modules-commonjs

i dodanie do .babelrc wtyczek rozwiązało moje pytanie.



7

moje rozwiązanie jest podsumowaniem wszystkiego powyżej z małymi sztuczkami, które dodałem, w zasadzie dodałem to do mojego kodu HTML

<script>var exports = {"__esModule": true};</script>
<script src="js/file.js"></script>

pozwala to nawet na użycie importzamiast, requirejeśli używasz elektronu lub czegoś podobnego, i działa dobrze z maszynopisem 3.5.1, target: es3 -> esnext.


3
pewien postęp, błąd właśnie się zmienił naapp.js:3 Uncaught ReferenceError: require is not defined
Muhammed Moussa

Dzieje się tak, jeśli podczas tworzenia okna nodeIntegration ma wartość false, błąd występuje, ponieważ zaktualizowałeś swój electronJS lub śledzisz przestarzałe źródło. nodeIntegration była domyślnie true, teraz jest false, więc musisz włączyć ją ręcznie, jeśli chcesz uzyskać dostęp do nodeJS w procesie renderowania. Zobacz [Electron require () is not defined] [1] [1]: stackoverflow.com/questions/44391448/…
Hocine Abdellatif

Nie używam elektronu, zresztą rozwiązałem w moim przypadku dodając paczkę do paczki i usunąłem inne trudne sposoby
Muhammed Moussa

5

Miałem ten sam problem i rozwiązałem go dodając bibliotekę " es5 " do tsconfig.json w następujący sposób:

{
    "compilerOptions": {
        "target": "es5", //defines what sort of code ts generates, es5 because it's what most browsers currently UNDERSTANDS.
        "module": "commonjs",
        "moduleResolution": "node",
        "sourceMap": true,
        "emitDecoratorMetadata": true, //for angular to be able to use metadata we specify in our components.
        "experimentalDecorators": true, //angular needs decorators like @Component, @Injectable, etc.
        "removeComments": false,
        "noImplicitAny": false,
        "lib": [
            "es2016",
            "dom",
            "es5"
        ]
    }
}

5

Dla osób, które nadal mają ten problem, jeśli docelowy kompilator jest ustawiony na ES6, musisz powiedzieć babelowi, aby pominął transformację modułu. Aby to zrobić, dodaj to do swojego .babelrcpliku

{
  "presets": [ ["env", {"modules": false} ]]
}

1
Dzięki! Próbowałem pracować ze starszą bazą kodu, która zrzuca wszystko do globalnego, a skrypty są zawarte w przeglądarce z <script>tagiem. Miałem nadzieję, że użyję modułu razem ze starszym kodem i wygląda na to, że nie jest to możliwe. To przynajmniej pozwala mi używać ES6 i zajmę się później eksportem.
przytulić

2
robiąc to otrzymałem następujący błąd: Używając usuniętej opcji Babel 5: .modules - Użyj odpowiedniej wtyczki transformacji modułu w pluginsopcji. Sprawdź babeljs.io/docs/plugins/#modules
chharvey

5

Można to naprawić, ustawiając moduleopcję kompilatora na es6:

{
  "compilerOptions": {     
    "module": "es6",
    "target": "es5",    
  }
}

3

Miałem też ten sam błąd. W moim przypadku było tak, ponieważ mieliśmy staromodną instrukcję importu w naszym projekcie TypeScript AngularJS w następujący sposób:

import { IAttributes, IScope } from "angular";

który został skompilowany do JavaScript w następujący sposób:

"use strict";
Object.defineProperty(exports, "__esModule", { value: true });

Było to potrzebne w dawnych czasach, ponieważ używaliśmy wtedy IAttributeskodu, a TypeScript nie wiedziałby, co z tym zrobić w inny sposób. Ale po usunięciu instrukcji importu i konwersji IAttributesdo ng.IAttributestych dwóch wierszy JavaScript zniknął - podobnie jak komunikat o błędzie.


1
Jak to zadziała w przypadku typu maszynopisu? Muszę go zaimportować, więc Typescript go kompiluje.
BluE,

Co masz na myśli przez „typ maszynopisu”? Jeśli jest to typ całkowity znany przez TypeScript - taki jak liczba lub ciąg - możesz go od razu użyć. Jeśli definiować własne typy w module, sprawdź to: typescriptlang.org/docs/handbook/modules.html
mATX

Miałem na myśli definicje typów zewnętrznej biblioteki, takie jak @ types / jquery z npmjs.com/package/@types/jquery . Aby zmienna $ była użyteczna z mojego kodu Typescript, umieściłem to w moim kodzie: import * as $ from "jquery";
BluE,

Celuję w es5, czy potrzebuję innej biblioteki, takiej jak requirejs, aby to działało?
BluE,

1

Po prostu dodaj libraryTarget: 'umd', tak

const webpackConfig = {
  output: {
    libraryTarget: 'umd' // Fix: "Uncaught ReferenceError: exports is not defined".
  }
};

module.exports = webpackConfig; // Export all custom Webpack configs.

1

dla mnie, usunięcie "esModuleInterop": truez tsconfig.json załatwiło sprawę.


0

W przypadku niektórych projektów ASP.NET importi exportmoże nie być w ogóle używany w skryptach Typescripts.

Błąd pytania pojawił się, gdy próbowałem to zrobić i dopiero później odkryłem, że muszę tylko dodać wygenerowany skrypt JS do widoku w następujący sposób:

<script src="~/scripts/js/[GENERATED_FILE].Index.js" asp-append-version="true"></script>

0

Wypróbuj to, co @iFreilicht zasugerował powyżej. Jeśli to nie zadziałało po zainstalowaniu pakietu webpacka i wszystkiego innego, być może właśnie skopiowałeś konfigurację pakietu internetowego z innego miejsca online i skonfigurowałeś tam, że chcesz, aby dane wyjściowe przez pomyłkę obsługiwały CommonJS. Upewnij się, że tak nie jest w przypadku webpack.config.js:

module.exports = {
  mode: process.env.NODE_ENV || "development",
  entry: { 
    index: "./src/js/index.ts"
  },
  ...
  ...
  output: {
    libraryTarget: 'commonjs',         <==== DELETE THIS LINE
    path: path.join(__dirname, 'build'),
    filename: "[name].bundle.js"
  }
};

0

Miałem ten sam problem i naprawiłem go, zmieniając kolejność ładowania pakietów JS.

Sprawdź kolejność wywoływania potrzebnych pakietów i załaduj je w odpowiedniej kolejności.

W moim konkretnym przypadku (nie używając modułu Bundler) I potrzebne do obciążenia Redux, a następnie Redux Thunk, po czym React Redux. Ładowanie React Reduxwcześniej Redux Thunkdałoby mi exports is not defined.


0

Uwaga: to może nie mieć zastosowania do odpowiedzi OP, ale otrzymywałem ten błąd i tak go rozwiązałem.

Tak więc problem, z którym się zmagałem, polegał na tym, że otrzymywałem ten błąd podczas pobierania biblioteki „js” z określonej sieci CDN.

Jedyną złą rzeczą, jaką robiłem, było importowanie z katalogu CDN w następujący cjssposób: https://cdn.jsdelivr.net/npm/@popperjs/core@2.4.0/dist/cjs/popper.min.js

Zwróć uwagę na dist/cjsczęść? Tam był problem.

Wróciłem do CDN (jsdelivr) w moim przypadku i przeszedłem, aby znaleźć umdfolder. I udało mi się znaleźć innego zestawu popper.min.js, który był poprawny plik do importu: https://cdn.jsdelivr.net/npm/@popperjs/core@2.4.0/dist/umd/popper.min.js.


0
  {
    "compileOnSave": false,
    "compilerOptions": {
      "baseUrl": "./",
      "outDir": "./dist",
      "sourceMap": true,
      "declaration": false,
      "module": "esnext",
      "moduleResolution": "node",
      "emitDecoratorMetadata": true,
      "experimentalDecorators": true,
      "target": "es5",
      "typeRoots": ["node_modules/@types"],
      "lib": ["es2018", "dom"]
    }
  }

5
Witamy w StackOverflow. Dodaj kontekst do odpowiedzi lub wyjaśnienia, aby użytkownik mógł zrozumieć, co zostało zrobione. Samo wysłanie JSON może nie być tak pomocne ...
Bruno Monteiro

0

Miałem ten sam problem, ale moja konfiguracja wymagała innego rozwiązania.

Używam create-react-app-rewiredpakietu z config-overrides.jsplikiem. Wcześniej korzystałem z addBabelPresetsimportu (w override()metodzie) z customize-crai postanowiłem wyodrębnić te presety do oddzielnego pliku. Przypadkowo rozwiązało to mój problem.

Dodałem useBabelRc()do override()metody w config-overrides.jsi utworzyłem babel.config.jsplik z następującymi elementami:

module.exports = {
    presets: [
        '@babel/preset-react',
        '@babel/preset-env'
    ],
}
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.