I have a project using a function class.
the webpack config part of the output is something like below:
...
output: {
library: 'FirstPoint',
...
FirstPoint is first point to access main class, and main class at index.js (entry point) is something like:
import { onInit } from './intilize'
import { showSomeThing } './somthing'
export function MyClass(props) {
onInit()
}
MyClass.prototype.showFoo = showSomeThing
the full example for this:
let myClass1 = new FirstPoint.MyClass()
let myClass2 = new FirstPoint.MyClass()
myClass1 .showFoo() //not show myClass1 detail, use last instance detail (myClass2)
after the run, all thing is done. just after creating another instance the showFoo method that using a function outside main class keep last value from the last instance.
I want to make instance for all new object that defines from MyClass class, Or, in other words, is there a way that I can import all the imported modules into the first level, ie, the main class, and instead of the output (production version) of an array of modules, there is only one modulus, and within that other modules, like the function?
One method for doing this, is using encapsulation, and the other way use a Param class!
Related
I am migrating code that used to not use native JS modules.
// File: form.js
// `lc` is a global object I attach each file's functions to.
let lc = window.lc || {}
lc.form = {};
lc.form.add = function() {
// add a form
}
And then would be called as lc.form.add(), which is nice because the word add has context.
However now that I am changing the code to use JS modules:
// File: form.mjs
export function add() {
// add a form
}
And then would be called as add(), which has no context. Now I understand I could do:
import {add as formAdd} from '/form.mjs'
But thats like a step backwards to start smurf naming all imported things.
Is there a way to import the module like in Python, and then call functions of the modules. E.g. use dot etc notation to access it's function, something like this:
import '/form.mjs' as form
form.add()
You're looking for a namespace import:
import * as form from '/form.mjs';
form.add();
I am confused, or I can say, I have no clue how the exporting actually works.
I have a React app, and I have some protected Routes. On login, I create a Client object instance and pass it to child components through Context, and then consume it.
Recently I saw an approach where the example code exported an object instance from a file directly and just imported it in files they wanted to consume it.
/** My approach **/
export default Example
/** The Object Instance approach **/
export default new Example()
What is the lifecycle of the object instance? Are there any disadvantages with the second approach, because it seems way easier?
If you export the class, with
export default Example
then consumers of the module will be able to instantiate their own instances, and each instance will be able to have its own data. For example
// 1.js
import TheClass from './TheClass';
const tc1 = new TheClass();
tc1.foo = 'foo';
// 2.js
import TheClass from './TheClass';
const tc2 = new TheClass();
tc2.foo = 'bar';
Both modules can continue to use tc1 and tc2 completely independently, since they're separate instances.
But if the original module exports an instance rather than a class, then all consumers of the module are forced to use the same instance:
// 1.js
import theInstance from '...';
theInstance.foo = 'foo';
// 2.js
import theInstance from '...';
// might not be a good idea to do theInstance.foo = 'bar' here
// because that will affect 1.js as well
// and will affect any other modules that imported the instance
In short - exporting the class is more reusable than exporting the instance. Sometimes potential reusability is something a script-writer will consider important, and sometimes it isn't. (And sometimes, even if you don't consider it useful initially, you may encounter a situation later that forces you to reconsider.)
And sometimes you want to make sure that there's only one instance ever in a script, in which case
export default new Example()
is a way to accomplish it.
I am trying to understand the behavior of exporting class object instead of class name. Please help me make understand. Example
class Util {
method() {
return "method";
}
}
module.exports = new Util();
and then importing it like
import Util from 'Util';
I want to understand, how many times the object will be created?
Once, in the normal case. Modules are loaded and cached, and if they're imported by multiple other modules, those modules all see the same instance of the module doing the exporting.
When using CJS modules, the cache is require.cache and you can clear a module from the cache by deleting the property for it from the require.cache object, meaning that it will get loaded fresh the next time it's require'd. (I don't think it's possible to do that with ESM modules.)
Note: You're mixing CJS (module.exports =...) and ESM (import). I suggest you pick one and use it consistently, not least because you can't use require to import an ESM module.
Exporting the class will let you create new instances using new on any other modules that require/import it.
import MyModule from 'module';
// when exporting class:
const mdl = new MyModule();
console.log(mdl.constructor === MyModule); // => true
console.log(mdl.myValue); // => 'test'
console.log(MyModule.myValue); // => undefined
Exporting the instance will only export a single object that has this class as prototype. Module caching/resolution will ensure the same object is returned and the value is not re-calculated when re-importing from different modules.
import MyModule from 'module';
// when exporting instance
const mdl = new MyModule(); // TypeError: MyModule is not a constructor
console.log(MyModule.myValue); // => 'test'
First of all, the class syntax is just sugar on top of constructor functions.
If you export the Util "class", what you are exposing is that constructor function to be used with the new Util() syntax. Right?
In the other hand, if you export new Util(), instead of exporting the constructor function or the "class", you are exposing essentially an object constructed based on that constructor function's prototype object (or that "class") as it's prototype.
In javascript is it not possible to import a class without having to refrence the page. This seems ugly to me.
I have a class called "DashboardPage" It is located within a file name called "DashboardPage.js".
In order for me to import the class, I have to export the class in the file and then import it in another file. Like so
module.exports.DashboardPage = DashboardPage;//Export
var DashboardPage = require("DashboardPage");//Import
Now when I want to create a new DashboardPage. I have to go:
//Here is the problem. Why do I have to call the file name then the object.
var page = new DashboardPage.DashboardPage();
Am I doing something silly here? This seems silly. I come from a C# background and I may be going at this the wrong way.
This doesn't really have to do anything with class in JavaScript but with the CommonJS module system.
require simply returns the value that is assigned to module.exports. So you can also export a value by directly assigning to module.exports:
module.exports = DashboardPage;
Then when you do
var DashboardPage = require("DashboardPage");
DashboardPage is already your class and you create a new instance by calling new DashboardPage().
I have recently discovered Meteor and I am struggling with using ES6 classes and imports in a new Meteor project. What I want to do is to have a complex structure of classes, which methods get called from Meteor events/methods/helpers. I've added Babel.js to the project by writing a command $ meteor add grigio:babel and it works properly.
Example of what I am trying to achieve:
in server/models/article.js:
class Article {
static all() {
//returns all articles from db
}
}
in server/methods/articles.js:
Meteor.methods({
allArticles: {
Article.all();
}
})
Having just that raises ReferenceError: Article is not defined in a methods file, which is adequate. So I have got three options: write all classes in one file, append all classes to a global object or use a good module system like Browserify. Obviously, third option is better.
But how do I use that? Babel converts export, import into Browserify by default and Meteor raises a require is not defined error on page refresh. After googling the problem I didn't find a clear solution on how to add Browserify to Meteor. Should I add a npm packages support to Meteor, add a npm package of browserify and add it manually to Meteor on every page where I import/export anything? Or should I use a completely different approach? How is this task usually handled in Meteor? Thank you!
I was reading about this earlier and found this issue on github that may help.
Essentially just assign the class to a variable that is exposed to both the client and server (lib/both/etc depends on your file structure). Like so:
Article = class Article {...}
Seems to be the best solution at the moment.
The way I do this is to collect objects together into various namespaces, for example:
// Global
Collections = {};
class Article {
static all() {
//returns all articles from db
}
}
_.extend(Collections, { Article });
Then to avoid having to use Collections.Article everywhere I can use the following in the file I need to access Article in:
// Make `Article` available
let { Article } = Collections;
I am using Meteor 1.4.1.1 and the error remains, when reproducing your approach. However, there are some new ways to use es6 classes now:
1. Export your class as a constant (e.g. for use as a singleton object):
class MyModuleInternalClassName {
//... class internals
}
export const PublicClassName = new MyModuleInternalClassName();
You can import this one via
import {PublicClassName} from 'path/to/PublicClassFileName.js';
2. Export your class directly as the module's default
export default class PublicClassName {
//... class internals
}
and then import it (as with the above one) as the following
import {PublicClassName} from from 'path/to/PublicClassFileName.js';
let myInstance = new PublicClassName();
+++++++++++++++++++++++++++++++++
Regarding the question of OP and the error, you can try something like this:
Article.js
class InternalArticle {
constructor(){
//setup class
}
all() {
//returns all articles from db
}
register(article){
//add article to db
}
}
export const Article = new InternalArticle();
Import and use the Singleton
import {Article} from 'path/to/Article.js';
//either register some article
Article.register(someArticle);
//or get all your articles
const allArticles = Article.all();