64
Shashank Srivatsavaya Senior Developer Advocate [email protected] @ShashForce JavaScript for Lightning Components How-To and How-Not-To

Javascript for Lightning Components: How-To and How-Not-To

Embed Size (px)

Citation preview

Page 1: Javascript for Lightning Components: How-To and How-Not-To

Shashank SrivatsavayaSenior Developer Advocate

[email protected]@ShashForce

JavaScript for Lightning ComponentsHow-To and How-Not-To

Page 2: Javascript for Lightning Components: How-To and How-Not-To

Forward-Looking StatementsStatement under the Private Securities Litigation Reform Act of 1995:

This presentation may contain forward-looking statements that involve risks, uncertainties, and assumptions. If any such uncertainties materialize or if any of the assumptions proves incorrect, the results of salesforce.com, inc. could differ materially from the results expressed or implied by the forward-looking statements we make. All statements other than statements of historical fact could be deemed forward-looking, including any projections of product or service availability, subscriber growth, earnings, revenues, or other financial items and any statements regarding strategies or plans of management for future operations, statements of belief, any statements concerning new, planned, or upgraded services or technology developments and customer contracts or use of our services.

The risks and uncertainties referred to above include – but are not limited to – risks associated with developing and delivering new functionality for our service, new products and services, our new business model, our past operating losses, possible fluctuations in our operating results and rate of growth, interruptions or delays in our Web hosting, breach of our security measures, the outcome of any litigation, risks associated with completed and any possible mergers and acquisitions, the immature market in which we operate, our relatively limited operating history, our ability to expand, retain, and motivate our employees and manage our growth, new releases of our service and successful customer deployment, our limited history reselling non-salesforce.com products, and utilization and selling to larger enterprise customers. Further information on potential factors that could affect the financial results of salesforce.com, inc. is included in our annual report on Form 10-K for the most recent fiscal year and in our quarterly report on Form 10-Q for the most recent fiscal quarter. These documents and others containing important disclosures are available on the SEC Filings section of the Investor Information section of our Web site.

Any unreleased services or features referenced in this or other presentations, press releases or public statements are not currently available and may not be delivered on time or at all. Customers who purchase our services should make the purchase decisions based upon features that are currently available. Salesforce.com, inc. assumes no obligation and does not intend to update these forward-looking statements.

Page 3: Javascript for Lightning Components: How-To and How-Not-To

Where?Where do we use JavaScript in the Lightning Component framework?

Page 4: Javascript for Lightning Components: How-To and How-Not-To

Component Bundle

Resource NameComponent sample.cmp

Controller sampleController.js

Helper sampleHelper.js

Style sample.cssDocumentation sample.auradoc

Renderer sampleRenderer.js

Design Sample.designSVG sample.svg

This is how a ‘sample’ component bundle looks like

Page 5: Javascript for Lightning Components: How-To and How-Not-To

JavaScript in the component bundle JS goes into the controller, helper and renderer

Page 6: Javascript for Lightning Components: How-To and How-Not-To

Client-side controller methods to handle

events in the component

Controller

sampleController.js

JavaScript in the component bundle JS goes into the controller, helper and renderer

Page 7: Javascript for Lightning Components: How-To and How-Not-To

Client-side controller methods to handle

events in the component

JavaScript functions that can be called

from any JavaScript code in a

component’s bundle

Controller Helper

sampleController.js sampleHelper.js

JavaScript in the component bundle JS goes into the controller, helper and renderer

Page 8: Javascript for Lightning Components: How-To and How-Not-To

Client-side controller methods to handle

events in the component

JavaScript functions that can be called

from any JavaScript code in a

component’s bundle

Client-side renderer to override default

rendering for a component.

Controller Helper Renderer

sampleRenderer.jssampleController.js sampleHelper.js

JavaScript in the component bundle JS goes into the controller, helper and renderer

Page 9: Javascript for Lightning Components: How-To and How-Not-To

Controller Some thinks we do in the Controller

Page 10: Javascript for Lightning Components: How-To and How-Not-To

Controller

Accessing component attributes

Some thinks we do in the Controller

Page 11: Javascript for Lightning Components: How-To and How-Not-To

Controller

Accessing component attributes

Handling component actions

Some thinks we do in the Controller

Page 12: Javascript for Lightning Components: How-To and How-Not-To

Controller

Handling framework events

Accessing component attributes

Handling component actions

Some thinks we do in the Controller

Page 13: Javascript for Lightning Components: How-To and How-Not-To

Controller

Handling framework events

Accessing component attributes

Handling component actions

Some thinks we do in the Controller

<!-- sample.cmp --><aura:component> <aura:attribute name="text" type="String" default="Just a string"/> <ui:button label="Framework Button" press="{!c.handleClick}"/> <br/>{!v.text}</aura:component>

Page 14: Javascript for Lightning Components: How-To and How-Not-To

Controller

Handling framework events

Accessing component attributes

Handling component actions

Some thinks we do in the Controller

<!-- sample.cmp --><aura:component> <aura:attribute name="text" type="String" default="Just a string"/> <ui:button label="Framework Button" press="{!c.handleClick}"/> <br/>{!v.text}</aura:component>

/* sampleController.js */({ handleClick : function(component, event, helper) { var attributeValue = component.get("v.text"); console.log("current text: " + attributeValue);

var target = event.getSource(); component.set("v.text", target.get("v.label")); }})

Page 15: Javascript for Lightning Components: How-To and How-Not-To

Helper Move reusable utility functions into the helper

Page 16: Javascript for Lightning Components: How-To and How-Not-To

Helper Move reusable utility functions into the helper

/* sampleController.js */({ newItemEvent: function(component, event, helper) { helper.updateItem(component, event.getParam("item")); }})

Page 17: Javascript for Lightning Components: How-To and How-Not-To

Helper Move reusable utility functions into the helper

/* sampleController.js */({ newItemEvent: function(component, event, helper) { helper.updateItem(component, event.getParam("item")); }})

/* sampleHelper.js */({ updateItem : function(component, item, callback) { var action = component.get("c.saveItem"); action.setParams({"item" : item}); if (callback) { action.setCallback(this, callback); } $A.enqueueAction(action); }})

Page 18: Javascript for Lightning Components: How-To and How-Not-To

Renderer custom rendering for a component (if necessary)

Page 19: Javascript for Lightning Components: How-To and How-Not-To

Renderer

Lightning framework takes care of the rendering (creating and managing) of the DOM elements owned by a component.

custom rendering for a component (if necessary)

Page 20: Javascript for Lightning Components: How-To and How-Not-To

Renderer

Lightning framework takes care of the rendering (creating and managing) of the DOM elements owned by a component.

If you want to modify the default rendering behavior of the components and/or access the DOM elements, you can extend the existing functions from the rendering lifecycle of a component:

custom rendering for a component (if necessary)

Page 21: Javascript for Lightning Components: How-To and How-Not-To

Renderer

Lightning framework takes care of the rendering (creating and managing) of the DOM elements owned by a component.

If you want to modify the default rendering behavior of the components and/or access the DOM elements, you can extend the existing functions from the rendering lifecycle of a component:

• render()

custom rendering for a component (if necessary)

Page 22: Javascript for Lightning Components: How-To and How-Not-To

Renderer

Lightning framework takes care of the rendering (creating and managing) of the DOM elements owned by a component.

If you want to modify the default rendering behavior of the components and/or access the DOM elements, you can extend the existing functions from the rendering lifecycle of a component:

• render()• rerender()

custom rendering for a component (if necessary)

Page 23: Javascript for Lightning Components: How-To and How-Not-To

Renderer

Lightning framework takes care of the rendering (creating and managing) of the DOM elements owned by a component.

If you want to modify the default rendering behavior of the components and/or access the DOM elements, you can extend the existing functions from the rendering lifecycle of a component:

• render()• rerender()• afterRender()

custom rendering for a component (if necessary)

Page 24: Javascript for Lightning Components: How-To and How-Not-To

Renderer

Lightning framework takes care of the rendering (creating and managing) of the DOM elements owned by a component.

If you want to modify the default rendering behavior of the components and/or access the DOM elements, you can extend the existing functions from the rendering lifecycle of a component:

• render()• rerender()• afterRender()• unrender()

custom rendering for a component (if necessary)

Page 25: Javascript for Lightning Components: How-To and How-Not-To

Renderer

Lightning framework takes care of the rendering (creating and managing) of the DOM elements owned by a component.

If you want to modify the default rendering behavior of the components and/or access the DOM elements, you can extend the existing functions from the rendering lifecycle of a component:

• render()• rerender()• afterRender()• unrender()

custom rendering for a component (if necessary)/* sampleRenderer.js */({ render : function(component, helper) { var ret = this.superRender(); // do custom rendering here return ret; }, rerender : function(component, helper){ this.superRerender(); // do custom rerendering here }, afterRender: function (component, helper) { this.superAfterRender(); // interact with the DOM here }, unrender: function () { this.superUnrender(); // do custom unrendering here } })

Page 26: Javascript for Lightning Components: How-To and How-Not-To

How?Let’s explore further

Page 27: Javascript for Lightning Components: How-To and How-Not-To

Working with component attributes Getting and Setting component attributes

Page 28: Javascript for Lightning Components: How-To and How-Not-To

Working with component attributes

Use the framework’s Component methods or the “$A” utility functions API

Getting and Setting component attributes

Page 29: Javascript for Lightning Components: How-To and How-Not-To

Working with component attributes

Use the framework’s Component methods or the “$A” utility functions API

Getting and Setting component attributes

({ myFunc : function (component) { // get component attribute var label = component.get("v.label"); // set component attribute component.set("v.label”,"This is a label"); // check if attribute is undefined, null or empty var isEmpty = $A.util.isEmpty(component.get("v.label")); // get/set attribute of an inner component with “aura:id” var sumthin = component.find("cmpAuraId").get("v.value"); component.find("cmpAuraId").set("v.value”, “some value”); }})

Page 30: Javascript for Lightning Components: How-To and How-Not-To

Working with component attributes

Use the framework’s Component methods or the “$A” utility functions API

Don’t use standard JS methods

Getting and Setting component attributes

({ myFunc : function (component) { // get component attribute var label = component.get("v.label"); // set component attribute component.set("v.label”,"This is a label"); // check if attribute is undefined, null or empty var isEmpty = $A.util.isEmpty(component.get("v.label")); // get/set attribute of an inner component with “aura:id” var sumthin = component.find("cmpAuraId").get("v.value"); component.find("cmpAuraId").set("v.value”, “some value”); }})

Page 31: Javascript for Lightning Components: How-To and How-Not-To

Working with component attributes

Use the framework’s Component methods or the “$A” utility functions API

Don’t use standard JS methods

Getting and Setting component attributes

({ myFunc : function (component) { // get component attribute var label = component.get("v.label"); // set component attribute component.set("v.label”,"This is a label"); // check if attribute is undefined, null or empty var isEmpty = $A.util.isEmpty(component.get("v.label")); // get/set attribute of an inner component with “aura:id” var sumthin = component.find("cmpAuraId").get("v.value"); component.find("cmpAuraId").set("v.value”, “some value”); }})

Var x = document.getElementById(“htmlID”)

x.someAttribute = “Some Value”;

x.setAttribute('aria-label', 'Test');x.getAttribute('aria-label');

Page 32: Javascript for Lightning Components: How-To and How-Not-To

Handling Events The Lightning way

Page 33: Javascript for Lightning Components: How-To and How-Not-To

Handling Events

Browser events like onclick, as well as framework component events can be wired to controller actions.

The Lightning way

Page 34: Javascript for Lightning Components: How-To and How-Not-To

Handling Events

Browser events like onclick, as well as framework component events can be wired to controller actions.

The Lightning way

<aura:component>

<!-- standard html --> <input type="button" value=”HTML Button" onclick="{!c.handleClick}"/> <!-- framework component --> <ui:button label="Framework Button" press="{!c.handleClick}"/>

<!-- framework event --> <aura:handler name="init" value="{!this}” action="{!c.handleInit}"/>

</aura:component>

Page 35: Javascript for Lightning Components: How-To and How-Not-To

Handling Events

Browser events like onclick, as well as framework component events can be wired to controller actions.

Don’t include JS for browser events directly in the markup.

The Lightning way

<aura:component>

<!-- standard html --> <input type="button" value=”HTML Button" onclick="{!c.handleClick}"/> <!-- framework component --> <ui:button label="Framework Button" press="{!c.handleClick}"/>

<!-- framework event --> <aura:handler name="init" value="{!this}” action="{!c.handleInit}"/>

</aura:component>

Page 36: Javascript for Lightning Components: How-To and How-Not-To

Handling Events

Browser events like onclick, as well as framework component events can be wired to controller actions.

Don’t include JS for browser events directly in the markup.

The Lightning way

<aura:component>

<!-- don’t do this --> <input type="button" value=”Click Me" onclick="alert('this will not work')"/>

</aura:component>

<aura:component>

<!-- standard html --> <input type="button" value=”HTML Button" onclick="{!c.handleClick}"/> <!-- framework component --> <ui:button label="Framework Button" press="{!c.handleClick}"/>

<!-- framework event --> <aura:handler name="init" value="{!this}” action="{!c.handleInit}"/>

</aura:component>

Page 37: Javascript for Lightning Components: How-To and How-Not-To

Conditional display To show or not to show…

Page 38: Javascript for Lightning Components: How-To and How-Not-To

Conditional display

Toggle CSS styles using $A.util.toggleClass to conditionally display markup

To show or not to show…

Page 39: Javascript for Lightning Components: How-To and How-Not-To

Conditional display

Toggle CSS styles using $A.util.toggleClass to conditionally display markup

To show or not to show…

<!-- toggleCss.cmp --><aura:component> <ui:button label="Toggle" press="{!c.toggle}"/> <p aura:id="text">Now you see me</p></aura:component>

/* toggleCssController.js */({ toggle : function(component, event, helper) { var toggleText = component.find("text"); $A.util.toggleClass(toggleText, "toggle"); }})

/* toggleCss.css */.THIS.toggle { display: none;}

Page 40: Javascript for Lightning Components: How-To and How-Not-To

Conditional display

Toggle CSS styles using $A.util.toggleClass to conditionally display markup

aura:if can also be used, but CSS toggling is a more standard practice

To show or not to show…

<!-- toggleCss.cmp --><aura:component> <ui:button label="Toggle" press="{!c.toggle}"/> <p aura:id="text">Now you see me</p></aura:component>

/* toggleCssController.js */({ toggle : function(component, event, helper) { var toggleText = component.find("text"); $A.util.toggleClass(toggleText, "toggle"); }})

/* toggleCss.css */.THIS.toggle { display: none;}

Page 41: Javascript for Lightning Components: How-To and How-Not-To

Conditional display

Toggle CSS styles using $A.util.toggleClass to conditionally display markup

aura:if can also be used, but CSS toggling is a more standard practice

To show or not to show…

<!-- toggleCss.cmp --><aura:component> <ui:button label="Toggle" press="{!c.toggle}"/> <p aura:id="text">Now you see me</p></aura:component>

/* toggleCssController.js */({ toggle : function(component, event, helper) { var toggleText = component.find("text"); $A.util.toggleClass(toggleText, "toggle"); }})

/* toggleCss.css */.THIS.toggle { display: none;}

<aura:component>

<aura:attribute name="edit" type="Boolean” default="true"/>

<aura:if isTrue="{!v.edit}"> <ui:button label="Edit"/> <aura:set attribute="else"> You can’t edit this. </aura:set>

</aura:if>

</aura:component>

Page 42: Javascript for Lightning Components: How-To and How-Not-To

Dynamic Components

createComponent(String type, Object attributes, function callback)

Creating components based on events or conditionally

Page 43: Javascript for Lightning Components: How-To and How-Not-To

Dynamic Components

createComponent(String type, Object attributes, function callback)

Creating components based on events or conditionally

<!--c:createComponent--><aura:component> <aura:handler name="init" value="{!this}” action="{!c.doInit}"/>

<p>Dynamically created button</p> {!v.body}

</aura:component>

Page 44: Javascript for Lightning Components: How-To and How-Not-To

Dynamic Components

createComponent(String type, Object attributes, function callback)

Creating components based on events or conditionally

/*createComponentController.js*/({ doInit : function(cmp) {

$A.createComponent("ui:button",

{ "aura:id": "findableAuraId", "label": "Press Me", "press": cmp.getReference("c.handlePress") }, function(newButton){ if (cmp.isValid()) { var body = cmp.get("v.body"); body.push(newButton); cmp.set("v.body", body); } } ); }})

<!--c:createComponent--><aura:component> <aura:handler name="init" value="{!this}” action="{!c.doInit}"/>

<p>Dynamically created button</p> {!v.body}

</aura:component>

Page 45: Javascript for Lightning Components: How-To and How-Not-To

Renderer and the DOM Accessing, modifying, rendering DOM elements

Page 46: Javascript for Lightning Components: How-To and How-Not-To

Renderer and the DOM

The framework’s Renderer automatically manages DOM elements owned by a component.

Accessing, modifying, rendering DOM elements

Page 47: Javascript for Lightning Components: How-To and How-Not-To

Renderer and the DOM

The framework’s Renderer automatically manages DOM elements owned by a component.

If there is a need for custom rendering or DOM access, use the component's renderer.

Accessing, modifying, rendering DOM elements

Page 48: Javascript for Lightning Components: How-To and How-Not-To

Renderer and the DOM

The framework’s Renderer automatically manages DOM elements owned by a component.

If there is a need for custom rendering or DOM access, use the component's renderer.

Accessing, modifying, rendering DOM elements

/* sampleRenderer.js */({ render : function(component, helper){ var ret = this.superRender(); // do custom rendering here alert("I'm rendering"); return ret; }, })

Page 49: Javascript for Lightning Components: How-To and How-Not-To

Renderer and the DOM

The framework’s Renderer automatically manages DOM elements owned by a component.

If there is a need for custom rendering or DOM access, use the component's renderer.

Don’t fire events in a component’s renderer to avoid infinite rendering loops.

Accessing, modifying, rendering DOM elements

/* sampleRenderer.js */({ render : function(component, helper){ var ret = this.superRender(); // do custom rendering here alert("I'm rendering"); return ret; }, })

Page 50: Javascript for Lightning Components: How-To and How-Not-To

Renderer and the DOM

The framework’s Renderer automatically manages DOM elements owned by a component.

If there is a need for custom rendering or DOM access, use the component's renderer.

Don’t fire events in a component’s renderer to avoid infinite rendering loops.

Don’t set attributes in a component’s renderer to avoid new rendering cycles. Use the component’s controller instead.

Accessing, modifying, rendering DOM elements

/* sampleRenderer.js */({ render : function(component, helper){ var ret = this.superRender(); // do custom rendering here alert("I'm rendering"); return ret; }, })

Page 51: Javascript for Lightning Components: How-To and How-Not-To

Renderer and the DOM

The framework’s Renderer automatically manages DOM elements owned by a component.

If there is a need for custom rendering or DOM access, use the component's renderer.

Don’t fire events in a component’s renderer to avoid infinite rendering loops.

Don’t set attributes in a component’s renderer to avoid new rendering cycles. Use the component’s controller instead.

Only modify DOM elements that are part of the component to ensure component encapsulation

Accessing, modifying, rendering DOM elements

/* sampleRenderer.js */({ render : function(component, helper){ var ret = this.superRender(); // do custom rendering here alert("I'm rendering"); return ret; }, })

Page 52: Javascript for Lightning Components: How-To and How-Not-To

Locker Service Rules for writing of secure code

Page 53: Javascript for Lightning Components: How-To and How-Not-To

Locker Service

• A component can only traverse the DOM and access elements created by that component

Rules for writing of secure code

Page 54: Javascript for Lightning Components: How-To and How-Not-To

Locker Service

• A component can only traverse the DOM and access elements created by that component

• You can access published, supported JavaScript API framework methods only. Published at https://yourDomain.lightning.force.com/auradocs/reference.app

Rules for writing of secure code

Page 55: Javascript for Lightning Components: How-To and How-Not-To

Locker Service

• A component can only traverse the DOM and access elements created by that component

• You can access published, supported JavaScript API framework methods only. Published at https://yourDomain.lightning.force.com/auradocs/reference.app

• JavaScript ES5 strict mode is implicitly enabled

Rules for writing of secure code

Page 56: Javascript for Lightning Components: How-To and How-Not-To

Locker Service

• A component can only traverse the DOM and access elements created by that component

• You can access published, supported JavaScript API framework methods only. Published at https://yourDomain.lightning.force.com/auradocs/reference.app

• JavaScript ES5 strict mode is implicitly enabled

• Lightning CLI available for linting and Locker Service compatibility

Rules for writing of secure code

Page 57: Javascript for Lightning Components: How-To and How-Not-To

Server-side Controller Apex controller through “Action” utility to access data, metadata,

external API

Page 58: Javascript for Lightning Components: How-To and How-Not-To

Server-side Controller Apex controller through “Action” utility to access data, metadata,

external API<aura:component controller="MyObjController"/> <aura:attribute name="myObjects” type="namespace.MyObj__c[]"/> <aura:iteration items="{!v.myObjects}” var="obj"> {!obj.Name}, {!obj.myField__c} </aura:iteration><aura:component/>

Page 59: Javascript for Lightning Components: How-To and How-Not-To

Server-side Controller Apex controller through “Action” utility to access data, metadata,

external API<aura:component controller="MyObjController"/> <aura:attribute name="myObjects” type="namespace.MyObj__c[]"/> <aura:iteration items="{!v.myObjects}” var="obj"> {!obj.Name}, {!obj.myField__c} </aura:iteration><aura:component/>

getMyObjects: function(cmp){ var action = cmp.get("c.getMyObjects"); action.setCallback(this, function(response){ var state = response.getState(); if (state === "SUCCESS") { cmp.set("v.myObjects”, response.getReturnValue()); } }); $A.enqueueAction(action);}

Page 60: Javascript for Lightning Components: How-To and How-Not-To

Server-side Controller Apex controller through “Action” utility to access data, metadata,

external API<aura:component controller="MyObjController"/> <aura:attribute name="myObjects” type="namespace.MyObj__c[]"/> <aura:iteration items="{!v.myObjects}” var="obj"> {!obj.Name}, {!obj.myField__c} </aura:iteration><aura:component/>

getMyObjects: function(cmp){ var action = cmp.get("c.getMyObjects"); action.setCallback(this, function(response){ var state = response.getState(); if (state === "SUCCESS") { cmp.set("v.myObjects”, response.getReturnValue()); } }); $A.enqueueAction(action);}

public with sharing class MyObjController { @AuraEnabled public static List<MyObj__c> getMyObjects() { return [SELECT Id, Name, myField__c FROM MyObj__c];

}}

Page 61: Javascript for Lightning Components: How-To and How-Not-To

DemoLet’s try what we saw

Page 62: Javascript for Lightning Components: How-To and How-Not-To

Questions?

Page 63: Javascript for Lightning Components: How-To and How-Not-To

Thank Y u

Page 64: Javascript for Lightning Components: How-To and How-Not-To