I have a basic migration class that looks like this:
"use strict";
var Schema = require('../database/schema');
var sequence = require('when/sequence');
var _ = require('lodash');
class Migrate {
constructor(knex) {
this.knex = knex;
}
createTable(tableName) {
...
}
createTables() {
...
}
run() {
return this.createTables();
}
}
module.exports = (knex) => {
return new Migrate(knex)
}
and I can use it like so:
require('./app/commands/' + process.argv[2] + '.js')(knex)
.run()
.then((...))
However, I want to inherit from an abstract class called "Command", so I add the following lines to my "Migrate" class.
"use strict";
var Command = require('./command');
class Migrate extends Command {
...
}
The problem is, I don't know how I can convert my Command class to a module. Right now it is like this:
"use strict";
module.exports = class Command {
sayHello() {
console.log("hello");
}
}
but it doesn't work. (e.g this becomes undefined on Migrate class' constructor method so I cannot put Knex to the instance)
Is there any proper way to use abstract classes with module pattern?
Thank you.
Related
How can I avoid the creation of global functions when compiling typescript into javascript.
Benefit: obfuscator won't have to provide a public API
Foo.ts:
class Foo {}
Foo.js:
var Foo = (function () {
function Foo() {
}
return Foo;
}());
Foo.obfuscated.js (using npm jsobfuscator):
var _0xcd14=[];var _0x12e2=[];var Foo=(function(){function Foo(){}return Foo}())
Foo is still visible. I understand why (public API). Solution would be:
Foo.isolated.js:
(function() { /* code from Foo.js */ })();
Foo.isolated.obfuscated.js (what I want):
var _0xe1f1=[];var _0xa6a8=[];(function(){var _0x64f8x2=(function(){function _0x64f8x2(){}return _0x64f8x2}())})()
Is there a typescript setup for tsconfig.js / compiler options like isolation: true or something?
Wrapping the class inside a function scope should do the trick.
(function(){
class Foo {}
})
There isn't built in support in the form of an option as far as I am aware. Let me know if doing the above does not achieve your aim - in which case some more details about exactly what the goal is will help us understand what you're going for here.
nested (private) class ?
module MyModule {
export class MyPublicClass {
private myPrivateClass: PrivateClass;
constructor() {
this.myPrivateClass = new PrivateClass;
}
public test() {
this.myPrivateClass.test();
}
}
class PrivateClass {
public test() {
console.log('it works');
}
}
}
I encountered a problem, if use methodology: one file - one class in typescript project, as in the example below.
File Greeter.ts
module App {
export class Greeter {
constructor(public greeting: string) { }
public greet() {
return "<h1>" + this.greeting + "</h1>";
}
};
}
File Program.ts
module App {
export class Program {
private _greeter = new Greeter("Hello, world!");
public main() {
document.body.innerHTML = this._greeter.greet();
}
};
}
Result file
var App;
(function (App) {
var Greeter = (function () {
// class code
} ());
App.Greeter = Greeter;
})(App || (App = {}));
var App;
(function (App) {
var Program = (function () {
// class code
} ());
App.Program = Program;
})(App || (App = {}));
// point of entry
var program = new App.Program();
program.main();
As can be seen duplication declaration App. I would like exclude any repetition like this:
var App;
(function (App) {
var Greeter = (function () {
// class code
} ());
App.Greeter = Greeter;
var Program = (function () {
// class code
} ());
App.Program = Program;
})(App || (App = {}));
// point of entry
var program = new App.Program();
program.main();
Otherwise, when a large amount of classes, it turns out a lot of excess code in the output file.
Maybe I'm wrong somewhere?
----Update----
The project is building by gulp-concat and gulp-typescript, maybe exist package allowing avoid this?
example on github
Otherwise, when a large amount of classes, it turns out a lot of excess code in the output file.
Maybe I'm wrong somewhere?
No. This is by design. Basically typescript allows each section to run in isolation.
Warning
Please try and migration to modules . More https://basarat.gitbooks.io/typescript/content/docs/tips/outFile.html
This is a follow-up question to In Node.js, how do I "include" functions from my other files?
I would like to include an external js file that contains common functions for a node.js app.
From one of the answers in In Node.js, how do I "include" functions from my other files?, this can be done by
// tools.js
// ========
module.exports = {
foo: function () {
// whatever
},
bar: function () {
// whatever
}
};
var zemba = function () {
}
It is inconvenient to export each and every function. Is it possible to have a one-liner that exports all functions? Something that looks like this;
module.exports = 'all functions';
It is so much more convenient this way. It is also less buggy in case one forgets to export certain functions later.
If not a one-liner, are there simpler alternatives that make coding more convenient? I just want to include an external js file made up of common functions conveniently. Something like include <stdio.h> in C/C++.
You can write all your function declarations first and then export them in an object:
function bar() {
//bar
}
function foo() {
//foo
}
module.exports = {
foo, bar
};
There's no magical one-liner though, you need to explicitly export the functions you want to be public.
I have done something like the following:
var Exported = {
someFunction: function() { },
anotherFunction: function() { },
}
module.exports = Exported;
I require it in another file and I can access those functions
var Export = require('path/to/Exported');
Export.someFunction();
This is essentially just an object with functions in it, and then you export the object.
A really old question but I just had to solve the same issue myself.
the solution I used was to define a Class inside the module to contain all my functions and simply export an instance of the class.
classes.js looks like this:
class TestClass
{
Function1() {
return "Function1";
}
Function2() {
return "Function2";
}
}
module.exports = new TestClass();
app.js looks like this:
const TestClass = require("./classes");
console.log( TestClass.Function1);
just keep adding more functions to the class and they will be exported :)
It is worth noting that in ES6, you can now export functions like this:
export function foo(){}
export function bar(){}
function zemba(){}
Simply write export before the functions you want to export. More information here.
If you use ES6 you can do something like that:
function bar() {
//bar
}
function foo() {
//foo
}
export default { bar, foo };
const fs = require("fs")
var ExportAll = {
deleteFile : function deleteFile(image,folder="uploads"){
let imagePath = `public/${folder}/${image}`
if (fs.existsSync(imagePath)){
fs.unlinkSync(imagePath)
}
},
checkFile : function checkFile(image,folder="uploads"){
let imagePath = `public/${folder}/${image}`
if (fs.existsSync(imagePath)){
return true
}
else{
return false
}
},
rand : function(min=1,max=10)
{
return Math.floor((Math.random() * max) + min)
}
}
module.exports = ExportAll
Import everything from a type module file that has functions that are exported.
Found here:
https://javascript.info/import-export
myfile.js
export function myFunction()
{
// ................
}
export function myFunction2()
{
// ................
}
myfile2.js - import everything that is exported in the file
import * as myFunctions from './myfile.js';
// Usage
myFunctions.myFunction();
myFunctions.myFunction2();
I defined a class in a module:
"use strict";
var AspectTypeModule = function() {};
module.exports = AspectTypeModule;
var AspectType = class AspectType {
// ...
};
module.export.AspectType = AspectType;
But I get the following error message:
TypeError: Cannot set property 'AspectType' of undefined
at Object.<anonymous> (...\AspectType.js:30:26)
at Module._compile (module.js:434:26)
....
How should I export this class and use it in another module? I have seen other SO questions, but I get other error messages when I try to implement their solutions.
// person.js
'use strict';
module.exports = class Person {
constructor(firstName, lastName) {
this.firstName = firstName;
this.lastName = lastName;
}
display() {
console.log(this.firstName + " " + this.lastName);
}
}
// index.js
'use strict';
var Person = require('./person.js');
var someone = new Person("First name", "Last name");
someone.display();
If you are using ES6 in Node 4, you cannot use ES6 module syntax without a transpiler, but CommonJS modules (Node's standard modules) work the same.
module.export.AspectType
should be
module.exports.AspectType
hence the error message "Cannot set property 'AspectType' of undefined" because module.export === undefined.
Also, for
var AspectType = class AspectType {
// ...
};
can you just write
class AspectType {
// ...
}
and get essentially the same behavior.
With ECMAScript 2015 you can export and import multiple classes like this
class Person
{
constructor()
{
this.type = "Person";
}
}
class Animal{
constructor()
{
this.type = "Animal";
}
}
module.exports = {
Person,
Animal
};
then where you use them:
const { Animal, Person } = require("classes");
const animal = new Animal();
const person = new Person();
In case of name collisions, or you prefer other names you can rename them like this:
const { Animal : OtherAnimal, Person : OtherPerson} = require("./classes");
const animal = new OtherAnimal();
const person = new OtherPerson();
Use
// aspect-type.js
class AspectType {
}
export default AspectType;
Then to import it
// some-other-file.js
import AspectType from './aspect-type';
Read http://babeljs.io/docs/learn-es2015/#modules for more details
I simply write it this way
in the AspectType file:
class AspectType {
//blah blah
}
module.exports = AspectType;
and import it like this:
const AspectType = require('./AspectType');
var aspectType = new AspectType();
class expression can be used for simplicity.
// Foo.js
'use strict';
// export default class Foo {}
module.exports = class Foo {}
-
// main.js
'use strict';
const Foo = require('./Foo.js');
let Bar = new class extends Foo {
constructor() {
super();
this.name = 'bar';
}
}
console.log(Bar.name);
Several of the other answers come close, but honestly, I think you're better off going with the cleanest, simplest syntax. The OP requested a means of exporting a class in ES6 / ES2015. I don't think you can get much cleaner than this:
'use strict';
export default class ClassName {
constructor () {
}
}
I had the same problem.
What i found was i called my recieving object the same name as the class name. example:
const AspectType = new AspectType();
this screwed things up that way...
hope this helps
Sometimes I need to declare multiple classes in one file, or I want to export base classes and keep their names exported because of my JetBrains editor understands that better. I just use
global.MyClass = class MyClass { ... };
And somewhere else:
require('baseclasses.js');
class MySubclass extends MyClass() { ... }
How can I inherit from a constructor function in javascript?
e.g. I have a base class written in native js
var MyModule;
(function (MyModule) {
var MyBase = (function () {
function MyBase(container, $MyElement) {
this._container = container;
this._$MyElement = $MyElement;
}
MyBase.prototype.toString = function () {
return this._previewType;
};
MyBase.prototype.method1 = function(){
};
MyBase.prototype.method2 = function () {
return this._isPreviewAffected;
};
return MyBase;
})();
MyModule.MyBase = MyBase;
})(MyModule || (MyModule = {}));
How do I inherit it in typescript. I tried following code. I get the error "Incorrect reference: referenced file: "my-base.js" cannot be resolved"
/// <reference path="my-base.js" />
module MyModule {
export class MyConcrete extends MyBase {
}
}
You need to declare the signature equivalent of your javascript code in typescript. This is to let TypeScript know what your JavaScript means if it was written in TypeScript:
declare module MyModule{
export class MyBase{
constructor(container, $MyElement);
toString();
method1():void;
method2():bool;
}
}
module MyModule {
export class MyConcrete extends MyBase {
}
}
Additionally /// <reference path="file" /> is for Typescript files only. For Javascript files you can use some script management (e.g. <script> tags, requireJS etc) to ensure MyBase is available before MyConcrete.