You need to sign in to do that
Don't have an account?
![satheesh p satheesh p](https://dfc-org-production.my.site.com/img/userprofile/default_profile_45_v2.png)
Unable to Submit New Expense in Lightning
I am new to salesforce and am using Lightning Components Developer Guide(winter 17) to learn saleforce lighning.in this i am creating Expense app.it retrive the data corretly but when submiting the new expense it shows the following Error Message
Something has gone wrong. Assertion Failed!: no client action by name {!v.createExpense} : false Failing descriptor: {ui$button$controller$press}. Please try again.
How can i resolve the problem.
I am using follwing Code.
ExpenseController.axpc
public with sharing class ExpenseController
{
@AuraEnabled
public static List<Expense__c> getExpenses()
{
// Perform isAccessible() check here
return [SELECT Id, Name, Amount__c, Client__c, Date__c, Reimbursed__c, CreatedDate FROM Expense__c];
}
@AuraEnabled
public static Expense__c saveExpense(Expense__c expense) {
// Perform isUpdateable() check here
upsert expense;
return expense;
}
}
FormController.js
({
doInit : function(component, event, helper)
{ //Update expense counters
helper.getExpenses(component);
},//Delimiter for future code
createExpense : function(component, event, helper) {
var amtField = component.find("amount");
var amt = amtField.get("v.value");
if (isNaN(amt)||amt==''){
amtField.set("v.errors", [{message:"Enter an expense amount."}]);
}
else {
amtField.set("v.errors", null);
var newExpense = component.get("v.newExpense");
helper.createExpense(component, newExpense);
}
},//Delimiter for future code
})
FormHelper.js
({
getExpenses: function(component)
{
var action = component.get("c.getExpenses");
action.setCallback(this, function(response)
{
var state = response.getState();
if (component.isValid() && state === "SUCCESS")
{
component.set("v.expenses", response.getReturnValue());
this.updateTotal(component);
}
}); $A.enqueueAction(action);
},
updateTotal : function(component)
{
var expenses = component.get("v.expenses");
var total = 0; for(var i=0; i<expenses.length; i++)
{
var e = expenses[i]; //If you’re using a namespace, use e.myNamespace__Amount__c instead
total += e.Amount__c;
}
//Update counters
component.set("v.total", total);
component.set("v.exp", expenses.length);
},
createExpense: function(component, expense) {
this.upsertExpense(component, expense, function(a) {
var expenses = component.get("v.expenses");
expenses.push(a.getReturnValue());
component.set("v.expenses", expenses);
this.updateTotal(component);
});
},
upsertExpense : function(component, expense, callback) {
var action = component.get("c.saveExpense");
action.setParams({
"expense": expense
});
if (callback) {
action.setCallback(this, callback);
}
$A.enqueueAction(action);
}
})
Something has gone wrong. Assertion Failed!: no client action by name {!v.createExpense} : false Failing descriptor: {ui$button$controller$press}. Please try again.
How can i resolve the problem.
I am using follwing Code.
ExpenseController.axpc
public with sharing class ExpenseController
{
@AuraEnabled
public static List<Expense__c> getExpenses()
{
// Perform isAccessible() check here
return [SELECT Id, Name, Amount__c, Client__c, Date__c, Reimbursed__c, CreatedDate FROM Expense__c];
}
@AuraEnabled
public static Expense__c saveExpense(Expense__c expense) {
// Perform isUpdateable() check here
upsert expense;
return expense;
}
}
FormController.js
({
doInit : function(component, event, helper)
{ //Update expense counters
helper.getExpenses(component);
},//Delimiter for future code
createExpense : function(component, event, helper) {
var amtField = component.find("amount");
var amt = amtField.get("v.value");
if (isNaN(amt)||amt==''){
amtField.set("v.errors", [{message:"Enter an expense amount."}]);
}
else {
amtField.set("v.errors", null);
var newExpense = component.get("v.newExpense");
helper.createExpense(component, newExpense);
}
},//Delimiter for future code
})
FormHelper.js
({
getExpenses: function(component)
{
var action = component.get("c.getExpenses");
action.setCallback(this, function(response)
{
var state = response.getState();
if (component.isValid() && state === "SUCCESS")
{
component.set("v.expenses", response.getReturnValue());
this.updateTotal(component);
}
}); $A.enqueueAction(action);
},
updateTotal : function(component)
{
var expenses = component.get("v.expenses");
var total = 0; for(var i=0; i<expenses.length; i++)
{
var e = expenses[i]; //If you’re using a namespace, use e.myNamespace__Amount__c instead
total += e.Amount__c;
}
//Update counters
component.set("v.total", total);
component.set("v.exp", expenses.length);
},
createExpense: function(component, expense) {
this.upsertExpense(component, expense, function(a) {
var expenses = component.get("v.expenses");
expenses.push(a.getReturnValue());
component.set("v.expenses", expenses);
this.updateTotal(component);
});
},
upsertExpense : function(component, expense, callback) {
var action = component.get("c.saveExpense");
action.setParams({
"expense": expense
});
if (callback) {
action.setCallback(this, callback);
}
$A.enqueueAction(action);
}
})
and
{!c.createExpense} reffer to clinetSide contrller where you create createExpenses method.
i hop it helps you
Thanks
All Answers
Thanks for your response.below i give my Componet Code
<aura:component implements="force:appHostable" controller="ExpenseController">
<aura:handler name="init" value="{!this}" action="{!c.doInit}" />
<ltng:require styles="/resource/SLDS213/assets/styles/salesforce-lightning-design-system.min.css"/>
<aura:attribute name="expenses" type="Expense__c[]"/>
<aura:attribute name="newExpense" type="Expense__c"
default="{ 'sobjectType': 'Expense__c', 'Name':'',
'Amount__c': 0, 'Client__c': '',
'Date__c': '', 'Reimbursed__c': false }"/>
<!-- If you registered a namespace, replace the previous aura:attribute tags with the following -->
<!-- <aura:attribute name="expenses" type="myNamespace.Expense__c[]"/>
<aura:attribute name="newExpense" type="myNamespace__Expense__c"
default="{ 'sobjectType': 'myNamespace__Expense__c', 'Name': '',
'myNamespace__Amount__c': 0, 'myNamespace__Client__c': '',
'myNamespace__Date__c': '', 'myNamespace__Reimbursed__c': false }"/> -->
<!-- Attributes for Expense Counters -->
<aura:attribute name="total" type="Double" default="0.00" />
<aura:attribute name="exp" type="Double" default="0" />
<!-- Input Form using components -->
<div class="container">
<form class="slds-form--stacked">
<div class="slds-form-element slds-is-required">
<div class="slds-form-element__control">
<!-- If you registered a namespace, the attributes include your namespace. For example, value="{!v.newExpense.myNamespace__Amount__c}" -->
<ui:inputText aura:id="expname" label="Expense Name"
class="slds-input" labelClass="slds-form-element__label"
value="{!v.newExpense.Name}" required="true"/>
</div>
</div>
<div class="slds-form-element slds-is-required">
<div class="slds-form-element__control">
<ui:inputNumber aura:id="amount" label="Amount"
class="slds-input" labelClass="slds-form-element__label"
value="{!v.newExpense.Amount__c}"
placeholder="20.80" required="true"/>
</div>
</div>
<div class="slds-form-element">
<div class="slds-form-element__control">
<ui:inputText aura:id="client" label="Client"
class="slds-input" labelClass="slds-form-element__label"
value="{!v.newExpense.Client__c}" placeholder="ABC Co."/>
</div>
</div>
<div class="slds-form-element">
<div class="slds-form-element__control">
<ui:inputDateTime aura:id="expdate" label="Expense Date"
class="slds-input" labelClass="slds-form-element__label"
value="{!v.newExpense.Date__c}" displayDatePicker="true"/>
</div>
</div>
<div class="slds-form-element">
<ui:inputCheckbox aura:id="reimbursed"
label="Reimbursed?"
class="slds-checkbox"
labelClass="slds-form-element__label"
value="{!v.newExpense.Reimbursed__c}"/>
<ui:button label="Submit" class="slds-button slds-button--neutral"
labelClass="label"
press="{!v.createExpense}"/>
</div>
</form>
</div><!-- ./container-->
<!-- Expense Counters -->
<div class="container slds-p-top--medium">
<div class="row">
<div class="slds-tile ">
<!-- Make the counter red if total amount is more than 100 -->
<div class="{!v.total >= 100 ? 'slds-notify slds-notify--toast slds-theme--error slds-theme--alert-texture' : 'slds-notify slds-notify--toast slds-theme--alert-texture'}">
<p class="slds-tile__title slds-truncate">Total Expenses</p>
$<ui:outputNumber class="slds-truncate" value="{!v.total}" format=".00"/>
</div>
</div>
<div class="slds-tile ">
<div class="slds-notify slds-notify--toast slds-theme--alert-texture">
<p class="slds-tile__title slds-truncate">No. of Expenses</p>
<ui:outputNumber class="slds-truncate" value="{!v.exp}"/>
</div>
</div>
</div>
</div>
<!-- Display expense records -->
<div class="container slds-p-top--medium">
<div id="list" class="row">
<aura:iteration items="{!v.expenses}" var="expense">
<!--If you’re using a namespace, use myNamespace:expenseList instead-->
<c:expenseList expense="{!expense}"/>
</aura:iteration>
</div>
</div>
</aura:component>
change this line in your component
<ui:button label="Submit" class="slds-button slds-button--neutral" labelClass="label" press="{!c.createExpense}"/>
using c.createExpense instedOf c.createExpense
Thanks let me inform if it helps you and mark it best answer so it helps other in future :)
Cann you give me your Contact mail id for further help
sfdcjaipur@gmail.com
:)
i can't understand !v. and !c. in folowing objects,
"{!v.newExpense.Name}"
"{!v.total}"
"{!c.createExpense}"/>
what is the use of it?
and
{!c.createExpense} reffer to clinetSide contrller where you create createExpenses method.
i hop it helps you
Thanks
I want to create Custom App in salesforce lightning.i am using developer guide steps- From Setup, enter Apps in the Quick Find box, then select Apps.But there is no Apps option to select.Can you tell me How can i do it.i am waiting for your replay.