I'm trying to set up Yesod, while running Fay for the frontend of my site. It's mostly working as I'd expect, as in any Fay I write runs. The problem is I'm getting an Uncaught ReferenceError in the generated JS.
Here is a short version of the JS in question:
(function(){
var Data = {};Data.Data = {};var Fay = {}; ... lots of code ... Home.main = new Fay$$$(function(){return Fay$$_(Home.alert)(Fay$$list("test"));});
;
Fay$$_(Home.main);
})();
Fay$$_(Home.main); /* Uncaught ReferenceError: Home is not defined */
And the Fay code that generates it:
module Home where
import Prelude
import Fay.FFI
import Language.Fay.Yesod
import SharedTypes
alert :: String -> Fay ()
alert = ffi "window.alert(%1)"
main :: Fay ()
main = alert "test"
I suspect that the extra call is being added by the yesod-fay package, but I'm not sure how to avoid this happening. https://github.com/fpco/yesod-fay/blob/master/Yesod/Fay.hs#L124 is the function I think might be involved.
Related
My app.bundle.js created by webpack is effing up:
/* harmony import */ var firebase_app__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(10);
/* harmony import */ var firebase_firestore__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(16);
var firebaseConfig = {
//config options for database
}; // Initialize Firebase
var defaultProject = firebase_app__WEBPACK_IMPORTED_MODULE_0__.default.initializeApp(firebaseConfig);
var defaultFirestore = defaultProject.firestore();
console.log("Firebase globals: ", firebase_app__WEBPACK_IMPORTED_MODULE_0__.default);
function userFunction(pdb) {
console.log("Firebase globals inside function: ", firebase_app__WEBPACK_IMPORTED_MODULE_0__.default);
}
As you can see firebase_app_WEBPACK_IMPORTED_MODULE_0__ is defined at the top yet when loading webpage error ReferenceError: firebase_app__WEBPACK_IMPORTED_MODULE_0__ is not defined pops up out of nowhere.
Update:
I actually found the mistake, basically I'm using Autodesk's Forge Viewer Library which at some point calls my function userFunction, userFunction needs firebase to process a list in one pass, sadly this function is executed in a webworker (async) which means I can't easily reference a variable outside the function's scope.
You will have to add an import for each Firebase SDK you want to use.
import firebase from 'firebase/app'
import 'firebase/storage'
import 'firebase/analytics'
import ....
If you already have done so, you also need them to be in correct order in a react project
The correct order:
import './initializedFirebase'
import App from './App'
If you import App.jsx before initializeFirebase.js, then firebase.storage() is used before it gets initialized.
Also consider upgrading your version of Firebase which solves many issues.
I have a TypeScript file config.ts that will be run with node:
import myDependency = require('my-dependency');
export = {
doSomething = () => {
...
}
}
In other TypeScript file, I can import this file with full type safety:
import config = require('./config');
config.doSomething();
config.doSomethingElse(); // compiler error, this method doesn't exist
Now I want to unit test this script. In order to mock out the dependencies that this script require()s I'm using proxyquire, which lets me provide the values that my script will get when it makes calls to require(). Here's what my test might look like:
import proxyquire = require('proxyquire');
const config = proxyquire('./config', {
'my-dependency': {} // this mocked object will be provided when config.ts asks for `my-dependency`
});
expect(config.doSomething()).to.do.something();
This works fine, except that my config variable is of type any because I'm using proxyquire() in place of require(). TypeScript must give the require() function special treatment to allow it to perform module resolution. Is there a way to tell the TypeScript compiler that proxyquire() should also do module resolution, similar to require()?
I could rewrite config.ts as a class or make it use an interface. Then I would be able to explicitly type the variables in my tests by importing the class/interface definition. But allowing proxyquire() to implicitly type things for me would be far be the easier solution.
There is a workaround - you can get the type of config.ts module by importing actual module and using typeof in a type cast:
import proxyquire = require('proxyquire');
import configType = require('./config');
const config = <typeof configType> proxyquire('./config', {
'my-dependency': {} // this mocked object will be provided when config.ts asks for `my-dependency`
});
config.doSomething();
// config.noSuchMethod(); // does not compile
This is not ideal because you have to import the same module in your test twice - the real one just to get at the type of it and "proxiquired" one to actually use in your tests, and you have to be careful not to mix up the two. But it's pretty simple compared to the task of implementing another variant of module resolution for typescript. Also, when configType is used in this way - for typing only - its import will not even appear in generated javacsript code.
EDIT : This was answered pretty quickly by someone pointing to something obvious in the rewire documentation. Note that I wrapped my modules in IIFEs because I was trying to get node to stop complaining about block scoped declarations outside of strict mode. Instead of using IIFEs (with strict mode), the easier way is just to use the --use-strict flag on your node command:
node --use-strict app.js
that way you can use ES6 in your code as normal and they will still be accessible by rewire. Hooray!
I am trying to test my node ES6 application. More specifically, I am trying to test a function in a module that isn't exported from a module. Currently, I cannot even get that function to be defined in my test. I am trying to use rewire to test this.
I'm not sure if this might a problem with strict mode or using ES6, but I cannot seem to find any hints to solutions online :(
Any help would be appreciated!
Here is my module:
//myModule.js
(function(){
'use strict';
let myFunction = () => {
return 'hello';
};
})();
And here is my test:
//myModule.spec.js
(function(){
'use strict';
let rewire = require('rewire');
let myModule = rewire('./myModule.js');
describe('app', () => {
it('should do something', () => {
let func = myModule.__get__('myFunction');
expect(func).toBeDefined();
});
});
})();
And this is the output I get from running jasmine-node on the directory:
Failures:
1) app should do something
Message:
ReferenceError: myFunction is not defined
Stacktrace:
ReferenceError: myFunction is not defined
Those IIFE's you're wrapping your code with are causing the problem. It's even mentioned in the fine manual:
Variables inside functions can not be changed by rewire
I'm new to TypeScript and I'm facing a problem while trying to load lodash.
Here is my code :
///<reference path="../../typings/lodash/lodash.d.ts"/>
///<reference path="../interfaces/IScheduler.ts"/>
import _ = require('lodash');
module MyModule {
export class LeastUsedScheduler implements IScheduler {
/// CODE HERE
}
}
I tried replacing the import line by :
import * as _ from lodash;
In the two cases I get :
"error| Cannot find name 'IScheduler'."
When I remove the import directive it compiles perfectly but _ is undefined at runtime.
I also tried to put the import inside the module without success.
I'm sorry It must be a very dumb question but I can't figure it out.
Thank you
EDIT :
I understood the problem. Referencing the typing for lodash created the variable _ in the scope. That's why it compiles fine without the import line. The problem is referencing the typing does not really import lodash. That's why it fails at runtime.
When I import lodash the compilation fails because lodash is already in the scope.
Thank you for your support.
I'm not 100% about the issue but can you try the following and let me know how it goes?
///<reference path="../../typings/lodash/lodash.d.ts"/>
///<reference path="../interfaces/IScheduler.ts"/>
import _ = require("lodash");
export class LeastUsedScheduler implements IScheduler {
doSomething(){
_.each([],function name(parameter) {
// ...
});
}
}
When compiled it looks like:
var _ = require("lodash");
var LeastUsedScheduler = (function () {
function LeastUsedScheduler() {
}
LeastUsedScheduler.prototype.doSomething = function () {
_.each([], function name(parameter) {
throw new Error("Not implemented yet");
});
};
return LeastUsedScheduler;
})();
exports.LeastUsedScheduler = LeastUsedScheduler;
If you import the module import _ = require("lodash"); but you don't use it, TypeScript will remove the import (I added the doSoemthing method for that reason).
Update: Why it didn't work?
The problem was that the module keyword is used to declare an internal module. At the same time the code was loading an external module. You should avoid mixing internal and external modules. You can learn more about the difference between internal and external modules at http://www.codebelt.com/typescript/typescript-internal-and-external-modules/.
Also, if you use internal modules avoid using the module keyword as it is deprecated and you should use the namespace keyword instead.
I'm having another issue with node.js, this time I cannot get my javascript code to recognize that a coffeescript module's class has functions.
In my main file, main.js I have the following code:
require('./node_modules/coffee-script/lib/coffee-script/coffee-script');
var Utils = require('./test');
console.log(typeof Utils);
console.log(Utils);
console.log(typeof Utils.myFunction);
And in my module, test.coffe, I have the following code:
class MyModule
myFunction : () ->
console.log("debugging hello world!")
module.exports = MyModule
Here is the output when I run node main.js :
function
[Function: MyModule]
undefined
My question is, why is my main file loading the correct module, but why is it unable to access the function? What am I doing wrong, whether it be with the coffeescript syntax, or with how I am requiring my module? Let me know if I should clarify my question.
Thanks,
Vineet
myFunction is an instance method, so it won't be accessible directly from the class.
If you want it as a class (or static) method, prefix the name with # to refer to the class:
class MyModule
#myFunction : () ->
# ...
You can also export an Object if the intention is for all methods to be static:
module.exports =
myFunction: () ->
# ...
Otherwise, you'll need to create an instance, either in main:
var utils = new Utils();
console.log(typeof utils.myFunction);
Or, as the export object:
module.exports = new Utils