Uncaught TypeError: (valeur intermédiaire) (…) n'est pas une fonction


129

Tout fonctionne bien lorsque j'ai écrit la logique js dans une fermeture sous la forme d'un seul fichier js, comme:

(function(win){
   //main logic here
   win.expose1 = ....
   win.expose2 = ....
})(window)

mais quand j'essaye d'insérer une fonction alternative de journalisation avant cette fermeture dans le même fichier js,

 window.Glog = function(msg){
     console.log(msg)
 }
 // this was added before the main closure.

 (function(win){
   //the former closure that contains the main javascript logic;
 })(window)

il se plaint qu'il y a une TypeError:

Uncaught TypeError: (intermediate value)(...) is not a function

Qu'ai-je fait de mal?

Réponses:


276

L'erreur est le résultat du point-virgule manquant sur la troisième ligne:

window.Glog = function(msg) {
  console.log(msg);
}; // <--- Add this semicolon

(function(win) {
  // ...
})(window);

La spécification ECMAScript a des règles spécifiques pour l'insertion automatique de points-virgules , mais dans ce cas, un point-virgule n'est pas automatiquement inséré car l'expression entre parenthèses qui commence sur la ligne suivante peut être interprétée comme une liste d'arguments pour un appel de fonction.

Cela signifie que sans ce point-virgule, la window.Glogfonction anonyme était appelée avec une fonction comme msgparamètre, suivie de (window)laquelle tentait par la suite d'appeler ce qui était retourné.

Voici comment le code était interprété:

window.Glog = function(msg) {
  console.log(msg);
}(function(win) {
  // ...
})(window);

4
@armnotstrong Josh était plus rapide, et la réponse est la même :)
mrlew

1
Merci Monsieur! Mon linter a enlevé le point-virgule automatiquement et tout s'est cassé :)
Jonas Lomholdt

1
impressionnant!!! Merci beaucoup!! J'ai presque perdu tous mes cheveux sur celui-ci ...
TMS

1
Ceci, mon ami, c'est de l'or!
LihO

1
c'est fou et je suis très reconnaissant pour ce post. J'étais en train de définir l'état après une ifdéclaration dans une useEffect()fonction React lorsque je continuais à recevoir cette erreur "... n'est pas une fonction".
Rahul Nath

7

Pour simplifier les règles de point-virgule

Chaque ligne qui commence par un (, [, `, ou tout opérateur (/, +, - sont les seuls valides), doit commencer par un point - virgule.

func()
;[0].concat(myarr).forEach(func)
;(myarr).forEach(func)
;`hello`.forEach(func)
;/hello/.exec(str)
;+0
;-0

Cela empêche un

func()[0].concat(myarr).forEach(func)(myarr).forEach(func)`hello`.forEach(func)/hello/.forEach(func)+0-0

monstruosité.

Remarque additionnelle

Pour mentionner ce qui va se passer: les parenthèses seront indexées, les parenthèses seront traitées comme des paramètres de fonction. Le backtick se transformerait en un modèle étiqueté , et l'expression régulière ou les entiers explicitement signés se transformeraient en opérateurs. Bien sûr, vous pouvez simplement ajouter un point-virgule à la fin de chaque ligne. Il est bon de garder à l'esprit que lorsque vous effectuez rapidement un prototypage et que vous supprimez vos points-virgules.

De plus, l'ajout de points-virgules à la fin de chaque ligne ne vous aidera pas avec ce qui suit, alors gardez à l'esprit des déclarations telles que

return // Will automatically insert semicolon, and return undefined.
    (1+2);
i // Adds a semicolon
   ++ // But, if you really intended i++ here, your codebase needs help.

Le cas ci-dessus arrivera à retourner / continuer / break / ++ / -. Tout linter l'attrapera avec une erreur de code mort ou de syntaxe ++ / - (++ / - ne se produira jamais de manière réaliste).

Enfin, si vous souhaitez que la concaténation de fichiers fonctionne, assurez-vous que chaque fichier se termine par un point-virgule. Si vous utilisez un programme bundler (recommandé), il devrait le faire automatiquement.


5

Cas d'erreur:

var userListQuery = {
    userId: {
        $in: result
    },
    "isCameraAdded": true
}

( cameraInfo.findtext != "" ) ? searchQuery : userListQuery;

Production:

TypeError: (intermediate value)(intermediate value) is not a function

Correction: il vous manque un point-virgule (;) pour séparer les expressions

userListQuery = {
    userId: {
        $in: result
    },
    "isCameraAdded": true
}; // Without a semi colon, the error is produced

( cameraInfo.findtext != "" ) ? searchQuery : userListQuery;

3

Pour moi, c'était beaucoup plus simple, mais il m'a fallu un certain temps pour le comprendre. Nous avions essentiellement dans notre .jslib

some_array.forEach(item => {
    do_stuff(item);
});

Il s'avère que Unity (emscripten?) N'aime tout simplement pas cette syntaxe. Nous l'avons remplacé par une bonne vieille boucle for et il a cessé de se plaindre tout de suite. Je déteste vraiment qu'il ne montre pas la ligne dont il se plaint, mais de toute façon, trompez-moi deux fois, honte à moi.


Je suppose que votre problème était quelque chose à voir avec ça
Brandito

C'est un cas différent de celui sur lequel porte la question.
CherryDT

@CherryDT ce n'est pas le cas, car l'erreur que j'obtenais était exactement la même.
tfrascaroli le

Non, cette question concerne les erreurs que vous obtenez en appelant accidentellement quelque chose en tant que fonction en raison de l'absence de point-virgule entre l'instruction et un (sur la ligne suivante. Je ne vois rien de tout cela dans votre cas. La question ne consiste pas seulement en son titre!
CherryDT

1

J'ai rencontré ce problème lorsque j'ai créé une nouvelle classe ES2015 où le nom de la propriété était égal au nom de la méthode.

par exemple:

class Test{
  constructor () {
    this.test = 'test'
  }

  test (test) {
    this.test = test
  }
}

let t = new Test()
t.test('new Test')

Veuillez noter que cette implémentation était dans NodeJS 6.10.

Pour contourner le problème (si vous ne souhaitez pas utiliser le nom de méthode ennuyeux 'setTest'), vous pouvez utiliser un préfixe pour vos propriétés 'privées' (comme _test).

Ouvrez vos outils de développement dans jsfiddle .


C'est un cas différent de celui sur lequel porte la question.
CherryDT

0
  **Error Case:**

var handler = function(parameters) {
  console.log(parameters);
}

(function() {     //IIFE
 // some code
})();

Sortie: TypeError: (valeur intermédiaire) (valeur intermédiaire) n'est pas une fonction * Comment réparer IT -> car il vous manque un point-virgule (;) pour séparer les expressions;

 **Fixed**


var handler = function(parameters) {
  console.log(parameters);
}; // <--- Add this semicolon(if you miss that semi colan .. 
   //error will occurs )

(function() {     //IIFE
 // some code
})();

pourquoi cette erreur vient? Raison: règles spécifiques pour l'insertion automatique de points-virgules qui reçoivent les normes ES6


0

Lorsque je crée une classe racine, dont j'ai défini les méthodes à l'aide des fonctions fléchées. Lors de l'héritage et de l'écrasement de la fonction d'origine, j'ai remarqué le même problème.

class C {
  x = () => 1; 
 };
 
class CC extends C {
  x = (foo) =>  super.x() + foo;
};

let add = new CC;
console.log(add.x(4));

ceci est résolu en définissant la méthode de la classe parent sans fonctions fléchées

class C {
  x() { 
    return 1; 
  }; 
 };
 
class CC extends C {
  x = foo =>  super.x() + foo;
};

let add = new CC;
console.log(add.x(4));
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.