VueeJS is open source reactive javascript framework library that helps us to create powerful client side web application. VueJS with its templating functionality can help us define HTML template, in which data is bound with models. HTML template elements change their status, style, values etc automatically with respect to changes in data model.
In addition to VueJS, there are many open source libraries that are provided and work well with VueJS.
/**
* Symbol is primitive data type that helps in meta programming
* Symbol is memory location to store data, but symbol is immutable and unique
* Hence data is better encapsulated in the form of symbol
*/
//to demonstrate uniqueness of Symbol
const s1 = Symbol("Hi");
const s2 = Symbol("Hi");
const string1 = "Hi";
const string2 = "Hi";
console.log("string1==string2",(string1==string2));
console.log("s1==s2",(s1==s2));
//Symbol.for - if symbol already present in registry, use same else create new one.
const userName = Symbol.for('userName') // creates a new Symbol in registry
const user_Name = Symbol.for('userName') // reuses already created Symbol
console.log(userName == user_Name)
const studentName = Symbol("studentName") // creates symbol but not in registry
const student_Name = Symbol.for("studentName")// creates a new Symbol in registry
console.log(studentName == student_Name)
//Symbol.keyFor - to return symbol from registry
const user_Name2 = Symbol.for('userName');
console.log("user_Name from registry ::" + Symbol.keyFor(user_Name2));
const userName2 = Symbol('userName');
console.log("userName from registry ::" + Symbol.keyFor(userName2));
const COLOR = Symbol()
const MODEL = Symbol()
const MFG = Symbol()
class CAR {
constructor(color ,make,model){
this[COLOR] = color;
this[MFG] = make;
this[MODEL] = model;
}
}
var civic = new CAR("Red","Honda","2020");
console.log("car info civic ", civic[COLOR],civic[MODEL],civic[MFG]);
/**
* Proxy APIs are used to define proxy/custom behaviors for original ones.
* It is another form of meta programming based on
* target : it can be targetted function or class or array to make proxy for
* handler : it is an object which properties are handler methods
* traps : Methods those provides property access
*/
//defining targets
class Employee{
constructor(firstName, lastName, role="Software Developer"){
this.firstName = firstName;
this.lastName = lastName;
this.role = role;
}
get info(){
return `Name : ${this.lastName} ${this.firstName} \n role : ${this.role}`;
}
}
function calculateRectangleArea(length, width){
return "rectangle area is : " + (length*width);
}
//Defining handler which contains properties as methods
const handler = {
apply : function(target,thisArgs,argsList){
if(argsList.length==2){
return Reflect.apply(target,thisArgs,argsList);
} else {
throw new Error("Illegal number of arguments :: " + argsList.legth);
}
},
construct : function(target,argsList){
if(argsList.length>=2){
return Reflect.construct(target,argsList);
} else {
throw new Error("Illegal number of arguments for construct:: " + argsList.legth);
}
},
get : function(target,property){
return "lastName is : " + Reflect.get(target,property).toLowerCase();
},
set : function(target,property,value){
value = value.toUpperCase();
return Reflect.set(target,property,value);
},
has : function(target,property){
console.log(`is property ${property} present : `, Reflect.has(target,property));
}
}
//Proxy.Apply demo - To call method through Proxy Apply
const proxyRectangle = new Proxy(calculateRectangleArea,handler);
console.log("Rectangle area : "+ proxyRectangle(15,20));
//console.log("Rectangle area : "+ proxyRectangle(15));
//Proxy.construct - to construct Object from Proxy
const employeeProxy = new Proxy(Employee,handler);
const employeeDisha = new employeeProxy("Disha","Sharma","Software Tester");
console.log("Disha Role ::"+employeeDisha.role);
//Proxy.get - to get value of object property through proxy
const employeeNeha = new Employee("Neha","Sharma","Developer");
const nehaProxy = new Proxy(employeeNeha,handler);
console.log("nehaproxy get last name : "+nehaProxy.lastName);
//Proxy.has- to check if object has property
Reflect.has(nehaProxy,"firstName");
/**
* Reflect APIs are set of APIs that allow us to inspect, modify classes,objects,properties, methods at runtime
*
*/
//Demo of Reflect.Apply
//Reflect.apply(target, thisArgument, argumentsList)
//target method/function to call
//object to be treated as This value for call.
//argumentsList is array of arguments
function calculateRectangleArea(length, width){
return "rectangle area is : " + (length*width)+ " "+this.unit;
}
var areaUnit = {unit : "m2"};
var argsList = [25,30];
const result = Reflect.apply(calculateRectangleArea,areaUnit,argsList);
console.log(result);
//Demo of Reflect.construct
//Reflect.construct(target,argumentList[,newTarget])
class Employee{
constructor(firstName, lastName, role="Software Developer"){
this.firstName = firstName;
this.lastName = lastName;
this.role = role;
}
get info(){
return `Name : ${this.lastName} ${this.firstName} \n role : ${this.role}`;
}
}
class Person{
get info(){
return `Mr/Ms. ${this.firstName} ${this.lastName}`;
}
}
var args = ["Disha", "Khera"];
var employeeDisha = Reflect.construct(Employee, args,Person);//employeeDisha is constructed from Employee constructor, but later class type of employeeDisha changed to Person
var employeeNeha = Reflect.construct(Employee,["Neha","Singh"],Person);
console.log(`details of Disha : ${employeeDisha.info}`);
console.log(`Disha is a person ? : ${employeeDisha instanceof Person}`);
console.log(`Disha is a Employee ? : ${employeeDisha instanceof Employee}`);
//Demo of Reflect.get
//Reflect.get(target,propertyKey[,receiver]) to set value to target object property
//target : target object on which to get the property
//propertyKey : name of property to get
//Receiver : to get property from receiver class
console.log(`details of Disha :: ${employeeDisha.info}`);
console.log("details of Disha as employee:: ",Reflect.get(employeeDisha,"firstName",Employee));
console.log("details of Disha as a person employee:: ",Reflect.get(employeeDisha,"firstName",Person));
//Demo of Reflect.set
//Reflect.set(targetObject,propertyKey, value[,receiver])
//targetObject : object or object type to get property value
//propertyKey : name of property key to set
//value : value to set
//receiver : optional argument to target if a setter is encountered
Reflect.set(employeeDisha,"lastName","Kaur")
console.log(`After setting lastName : ${employeeDisha.info}`);
Reflect.set(Employee,"lastName","Jat",employeeNeha);
console.log(`After setting lastName : ${employeeDisha.info}`);
console.log(`After setting lastName : ${employeeNeha.info}`);
//Demo of Reflect.has
//Reflect.has(target, propertyKey) to check if target object has property key
console.log(`employee Disha has firstName : `, Reflect.has(employeeDisha,"firstName"));
console.log(`employee Neha has firstName : `, Reflect.has(employeeNeha,"firstName"));
console.log(`employee Disha has info : `, Reflect.has(employeeNeha,"info"));
console.log(`employee Neha has info : `, Reflect.has(employeeNeha,"info"));
/**
* Runtime Error handling can be done by throw, try..catch..finally
*
*/
//Following type of javascript error objects are already
//EvalError - results from eval() function
//RangeError - results when value is outside valid range
//ReferenceError - results when dereferencing when invalid reference
//SyntaxError - results when syntax error in parsing code
//TypeError - results when variable is of invalid type
//URIError - results when encodeURI(), decodeURI() are passed invalid parameters
//throw syntax
//throw new Error([message])
//throw([message])
//try catch finally demo
var num1=2;
var num2=0;
try{
//code that may throw runtime error
if(num2==0){
throw new SyntaxError("Divide by zero not allowed");//this error will throw error because num2 is ZERO.
}
var result = num1/num2;
console.log("result is ::"+result);//this statement is not executed if previous statement is ERROR.
}catch(e){
//catch block will contain code to handle situation in case of error situation
console.log("Error :",e);
}finally{
//finally will contain block of code which to be executed in any case error or not.
console.log("Code execution is complete");
}
//create custom Error type
function CustomError(message){
this.name ="customError";
this.message = message || "this is custom error";
}
//try catch finally demo
var num1=2;
var num2=0;
try{
//code that may throw runtime error
if(num2==0){
throw new CustomError();//this error will throw error because num2 is ZERO.
}
var result = num1/num2;
console.log("result is ::"+result);//this statement is not executed if previous statement is ERROR.
}catch(e){
//catch block will contain code to handle situation in case of error situation
console.log("Error :",e);
}finally{
//finally will contain block of code which to be executed in any case error or not.
console.log("Code execution is complete");
}
/**
* Promise is an object that executes resolve function if promise is successful
* else executes reject function
*
Syntax
let p = new Promise(function(resolve,reject){
let workDone = true; // some time consuming work
if(workDone){
//invoke resolve function passed
resolve(SUCCESSVALUE)
}
else{
reject(ERRORVALUE)
}
})
p.then(SUCCESSHANDLER).catch(ERRORHANDLER)
*Promise can also be used to execute asynchronous callbacks
*/
function isPositiveMultiplication(num1,num2){
let p = new Promise(function(resolve,reject){
if(num1>0 && num2>0)
resolve(num1*num2);
else
reject("multiplication is negative ");
});
return p;
}
function printMultiplication(result){
console.log("multiplication result is :: "+result);
}
function printMultiplicationError(error){
console.log("multiplication error is :: " + error);
}
isPositiveMultiplication(10,20).then(printMultiplication).catch(printMultiplicationError);
isPositiveMultiplication(-10,20).then(printMultiplication).catch(printMultiplicationError);
isPositiveMultiplication(10,-20).then(printMultiplication).catch(printMultiplicationError);
//Promise.all - this function is used to return values of all promises. Resolve is called if all promises are successful, if any of promise fails Error method is called
Promise.all([isPositiveMultiplication(10,20),isPositiveMultiplication(30,40),isPositiveMultiplication(50,60),isPositiveMultiplication(50,-60)])
.then(function(resolveValue){
/*console.log(resolveValue[0])
console.log(resolveValue[1])
console.log(resolveValue[2])
*/console.log('all multiply operations done & positive')
})
.catch(function(err){
console.log('Error :: ',err)
})
Promise.all([isPositiveMultiplication(10,20),isPositiveMultiplication(30,40),isPositiveMultiplication(50,60),isPositiveMultiplication(50,60)])
.then(function(resolveValue){
console.log(resolveValue[0])
console.log(resolveValue[1])
console.log(resolveValue[2])
console.log(resolveValue[3])
console.log('all add operations done & positive')
})
.catch(function(err){
console.log('Error :: ',err)
})
//race method returns result of promise that is settled first
Promise.race([isPositiveMultiplication(10,20),isPositiveMultiplication(30,40)])
.then(function(resolveValue){
console.log('one of them is done::'+resolveValue)
console.log(resolveValue)
}).catch(function(err){
console.log("Error",err)
})
/**
* To demonstrate Classes in ES6
*/
//define the class
class Employee{
constructor(firstName, lastName){//this is constructor for class
this.firstName = firstName;
this.lastName = lastName;
}
printName(){//this is method for class
console.log("My Name is :: " + this.firstName+" "+this.lastName);
}
}
//creating object of the class
var employeeJohn = new Employee("John","Kesar");
//print object on console
console.log("employeeJohn ::" + employeeJohn);
console.log(employeeJohn);
//accessing object function
employeeJohn.printName();
//accessing object property
console.log("employeeJohn.firstName :: " + employeeJohn.firstName);
//creating unnamed class
var employeeVar = class{
constructor(firstName,lastName, idNo){//this is constructor for class
this.firstName=firstName;
this.lastName=lastName;
this.idNo=idNo;
}
printPersonId(){
console.log("Person Id :: " + this.idNo);
}
printPersonInfo(){
console.log("Person Id :: "+this.idNo+", Name :: "+this.firstName+" "+this.lastName);
}
}
//creating object of unnamed class
var employeeMohan = new employeeVar("Mohan","Kore","777");
employeeMohan.printPersonInfo();
//assigning another unnamed class to same variable
employeeVar = class{
constructor(firstName,lastName, idNo,role="Software Engineer"){//this is constructor for class
this.firstName=firstName;
this.lastName=lastName;
this.idNo=idNo;
this.role=role;
}
printPersonId(){
console.log("Person Id :: " + this.idNo);
}
printPersonInfo(){
console.log("Person Id :: "+this.idNo+", Name :: "+this.firstName+" "+this.lastName+", role ::"+this.role);
}
}
//creating objects of unnamed classes using same variable employeeVar
var employeeKiran = new employeeVar("Kiran","Kaur","111");
employeeKiran.printPersonInfo();
var employeeNupur = new employeeVar("Nupur","Kaur","222","Lead Developer");
employeeNupur.printPersonInfo();
console.log(employeeNupur);
//getter methods
//{get prop() { ... } }
//{get [expression]() { ... } }
employeeVar = class{
constructor(firstName,lastName, idNo,role="Software Engineer"){//this is constructor for class
this.firstName=firstName;
this.lastName=lastName;
this.idNo=idNo;
this.role=role;
}
get fullName(){//demo for get [expression](), fullName is not property of object
return this.firstName+" " + this.lastName;
}
}
var employeeMihir = new employeeVar("Mihir","Kumar","333","DBA");
console.log("employeeMihir.fullName :: " + employeeMihir.fullName);
console.log("employeeMihir.firstName :: " + employeeMihir.firstName);
console.log("employeeMihir.lastName :: " + employeeMihir.lastName);
//static method
employeeVar = class{
constructor(firstName,lastName, idNo,role="Software Engineer"){//this is constructor for class
this.firstName=firstName;
this.lastName=lastName;
this.idNo=idNo;
this.role=role;
}
static sayHello()
{
return "hey there, hello";
}
}
var employeeMonty = new employeeVar("Monty","pollard","555","Manager");
//static methods are called by class name. calling by object name gives error
console.log("employeeMonty says :: " +employeeVar.sayHello());
//instanceof operator returns if object is of class?
console.log("class of Monty is employeeVar ? " + (employeeMonty instanceof employeeVar));
//class inheritance it can be single level or multilevel
class Shape {
constructor(color){
this.color=color;
}
printShape(){
return this.color;
}
}
class Rectangle extends Shape{
constructor(length, width, color){
super(color);
this.length=length;
this.width=width;
}
printArea(){
return this.length*this.width;
}
printShape(){//method overriding
return "Rectangle having area :: " + this.printArea()+", with color :: "+super.printShape();
}
}
var rectangleRed = new Rectangle(10,20,"red");
console.log("rectangleRed :: "+rectangleRed.printShape());
console.log("rectangleRed instanceof Shape ? " + (rectangleRed instanceof Shape));
console.log("rectangleRed instanceof Rectangle ? " + (rectangleRed instanceof Rectangle));
/**
* Demonstration of Map and Set
*
*/
//intialize Map
var employee = new Map();
//initialize Map by passing array of key value pairs
var employee2 = new Map([
["name","Raj kher"],
["designation","Lead Engineer"],
["city","Mumbai"]
]);
//set function demo
employee.set("name","San Jose");
employee.set(1, "home : Delhi");
employee.set(2, "home : Tokyo");
employee.set(3,"home : New York").set(4,"home : Dubai").set(5,"home : Vienna");
//has key demo
console.log("employee has name key ? " + employee.has("name"));
console.log("employee has isMarried key ? " + employee.has("isMarried"));
console.log("employee has home '2' ? "+employee.has('2'));
console.log("employee has home 2 ? "+employee.has(2));
//get value from Map
console.log("employee Name :: "+employee.get("name"));
console.log("employee 5 home :: "+employee.get(5));
console.log("employee2 name :: "+employee2.get("name"));
console.log("employee2 designation :: "+employee2.get("designation"));
//get function demo
//clear function to remove all key-value pairs from map
employee2.clear();
console.log("employee2 has name ? " + employee2.has("name"));
console.log("employee2 has city ? " + employee2.has("city"));
console.log("employee2 has designation ? " + employee2.has("designation"));
//delete function to remove key and associated value. It returns true if deleted.
employee2 = new Map([
["name","Raj kher"],
["designation","Lead Engineer"],
["city","Mumbai"]
]);
console.log("deleting designation :: "+employee2.delete("designation"));
console.log("deleting designation again :: "+employee2.delete("designation"));
console.log("designation exists? :: "+employee2.delete("designation"));
//entries() function to return iterator function with array of [key,value]
var itr1 = employee2.entries();
console.log("itr1 ::"+itr1.next().value);
console.log("itr1 ::"+itr1.next().value);
console.log("itr1 ::"+itr1.next().value);
//forEach(callback[,thisArg]) - execute function for each item
function print(key, value){
console.log("key ::" + key +", value ::"+value);
}
employee2.forEach(print);
//keys() - returns iterator object to refer to keys of Map
var keyItr1 = employee2.keys();
console.log("keyItr1 ::"+keyItr1.next().value);
console.log("keyItr1 ::"+keyItr1.next().value);
//values() - returns iterator object to refer to values of Map
var valueItr1 = employee.values();
console.log("valueItr1 ::"+valueItr1.next().value);
console.log("valueItr1 ::"+valueItr1.next().value);
//for .. in loop over map
for(let item of employee2)
console.log("key ::"+item);
//weakMap is a Map having key as object. Those objects can be garbage collected
var weakMap3 = new WeakMap();
var object = {};
weakMap3.set(object, "Hello World");
console.log("weakMap3.get ::"+weakMap3.get(object));
//Set is data structure which does not allow duplicates
//Set can allow primitive and non-primitive types
//Set elements can be iterated in order of their insertion
//Set constructor
var fruitSet = new Set("Mango","Banana","Chikkoo","Orange");
//Size property returns the size of set
console.log("fruitSet.size :: " + fruitSet.size);
//add() to add a value to set,duplicates are not added
fruitSet.add("Apple");
fruitSet.add("Pineapple");
fruitSet.add("Mango");
console.log("fruitSet.size ::"+fruitSet.size);
//clear() to return all values from set
fruitSet.clear();
console.log("cleared size ::"+fruitSet.size);
//delete(value) to remove value from set
fruitSet = new Set();
fruitSet.add("Apple");
fruitSet.add("Pineapple");
fruitSet.add("Mango");
fruitSet.add("Banana");
fruitSet.delete("Mango");
console.log("deleted Mango fruitSet size :: " + fruitSet.size);
//entries() to return iterator that contains array of values
fruitSet = new Set();
fruitSet.add("Apple");
fruitSet.add("Pineapple");
fruitSet.add("Mango");
fruitSet.add("Banana");
var fruitSetItr1 = fruitSet.entries();
console.log("fruitSet itr :: " + fruitSetItr1.next().value);
console.log("fruitSet itr :: " + fruitSetItr1.next().value);
console.log("fruitSet itr :: " + fruitSetItr1.next().value);
console.log("fruitSet itr :: " + fruitSetItr1.next().value);
//forEach(callback[,thisArg]) - to execute callback function on each value of set
function printSetItem(value){
console.log("set.value ::" + value);
}
fruitSet = new Set();
fruitSet.add("Apple");
fruitSet.add("Pineapple");
fruitSet.add("Mango");
fruitSet.forEach(printSetItem);
//has(value) returns true if value present
console.log("fruitSet has value 'Apple' ::"+fruitSet.has("Apple"));
//values() - returns iterator that contains array of values in insertion order
var fruitSetItr2 = fruitSet.values();
console.log("fruitSet itr :: " + fruitSetItr2.next().value);
console.log("fruitSet itr :: " + fruitSetItr2.next().value);
console.log("fruitSet itr :: " + fruitSetItr2.next().value);
//WeakSet - is a set which contains only objects as values
var fruitWeakSet = new WeakSet();
fruitWeakSet.add({name:"Mango"});
fruitWeakSet.add({name:"Apple"});
fruitWeakSet.add({name:"Pineapple"});
fruitWeakSet.add({name:"Banana"});
fruitWeakSet.add({name:"Kiwi"});
Output
employee has name key ? true
employee has isMarried key ? false
employee has home '2' ? false
employee has home 2 ? true
employee Name :: San Jose
employee 5 home :: home : Vienna
employee2 name :: Raj kher
employee2 designation :: Lead Engineer
employee2 has name ? false
employee2 has city ? false
employee2 has designation ? false
deleting designation :: true
deleting designation again :: false
designation exists? :: false
itr1 ::name,Raj kher
itr1 ::city,Mumbai
itr1 ::undefined
key ::Raj kher, value ::name
key ::Mumbai, value ::city
keyItr1 ::name
keyItr1 ::city
valueItr1 ::San Jose
valueItr1 ::home : Delhi
key ::name,Raj kher
key ::city,Mumbai
weakMap3.get ::Hello World
fruitSet.size :: 5
fruitSet.size ::8
cleared size ::0
deleted Mango fruitSet size :: 3
fruitSet itr :: Apple,Apple
fruitSet itr :: Pineapple,Pineapple
fruitSet itr :: Mango,Mango
fruitSet itr :: Banana,Banana
set.value ::Apple
set.value ::Pineapple
set.value ::Mango
fruitSet has value 'Apple' ::true
fruitSet itr :: Apple
fruitSet itr :: Pineapple
fruitSet itr :: Mango
/**
* To demonstrate Iterators and Genearators
*
*/
//Some Object like Array, String, Map, Set are by default iterable
//while other custom types like class are not iterable. So we can define custom iterable for them
//Demo of existing iterable objects.we can use For Of or For In loop to iterate over them
var fruits = ["Mango","Banana","Apple","Kivi"];
for(let name of fruits){
console.log("fruit name : " + name);
}
//Iteration of Array using Symbol.Iterator. Since Iterators are in build for array we dont need to define it
//the next() method returns the object with properties "value" and "done".
//"value" denotes actual value and done returns TRUE when all objects finished with iterations.
let cities = ["Mumbai","Singapore","Tokyo","London", "New York","Beijing"];
let iterCities = cities[Symbol.iterator]();
let city;
do{
city = iterCities.next();
console.log("City Name :: " + city.value +", done :: " + city.done);
}while(!city.done);
//define custom Iterator for custom class
class EmployeeList {
constructor(arrayOfEmployee){
this.employees = [].concat(arrayOfEmployee);
}
[Symbol.iterator](){
let index=0;
let employeeList = this.employees;
return{
next:function(){
let emp = employeeList[index];
index++;
if(index<employeeList.length){
return {
value : emp,
done :false
}
} else {
return {
value : undefined,
done : true
}
}
}
}
}
}
let employee1 = {firstName :"James", lastName:"Kore",getInfo : function(){return "first Name : " + this.firstName+" last Name : "+this.lastName;}};
let employee2 = {firstName : "Tejas", lastName:"Goyal",getInfo : function(){return "first Name : " + this.firstName+" last Name : "+this.lastName;}};
let employee3 = {firstName : "Wu", lastName : "Xi",getInfo : function(){return "first Name : " + this.firstName+" last Name : "+this.lastName;}};
var arrayOfEmployee = [employee1, employee2, employee3];
let listOfEmployee = new EmployeeList(arrayOfEmployee);
let employeeItr = listOfEmployee[Symbol.iterator]();
let currentEmployee;
do{
currentEmployee = employeeItr.next();
console.log("currentEmployee ::" + currentEmployee +", done :" + currentEmployee.done+" employee.firstName ::" + currentEmployee.firstName+" employee.lastName ::" + currentEmployee.lastName);
}while(!currentEmployee.done);
//Generators
function * getName(){
console.log("Step 1")
yield "Robert"
console.log("Step 2")
yield "Robin"
console.log("Step 3")
yield "Rocky"
console.log("End of function")
}
//return an iterator object
let nameIter = getName()
//invoke statements until first yield
console.log(nameIter.next())
//resume execution after the last yield until second yield expression
console.log(nameIter.next())
//resume execution after last yield until third yield expression
console.log(nameIter.next())
console.log(nameIter.next())