Understanding updateRecord in Lightning Data Service (LDS) for LWC

Understanding updateRecord in Lightning Data Service (LDS)
Chinmaya By Chinmaya
9 Min Read

Introduction

updateRecord is a crucial function in Lightning Data Service (LDS) that allows you to update Salesforce records without writing Apex code.
While it’s not a wire adapter like getRecord, it’s equally important in the LDS toolkit.

In this comprehensive guide, we’ll explore everything you need to know about updateRecord in LDS, from basic usage to advanced patterns and best practices.

What is Lightning Data Service ?

Before diving into updateRecord, let’s understand LDS’s role:

    • Client-side caching: LDS maintains a client-side cache of records

    • Shared data: Components accessing the same record share a single source of truth

    • Automatic UI updates: Changes propagate to all components using the same record

    • Reduced server trips: Minimizes API calls by leveraging the cache

    • Built-in security: Respects field-level security and sharing settings

Understanding updateRecord

The updateRecord function is part of the lightning/uiRecordApi module and provides a declarative way to update Salesforce records in LWC.

Key Features of updateRecord

✅  No Apex required – Pure client-side operation.
✅  Automatic Refresh – Updates all components using the same record.
✅  Automatic security checks – Respects Field Level Security (FLS) and sharing rules.
✅  Optimised performance – Minimizes network calls.
✅  Optimistic UI – Immediate UI update with rollback on failure.
✅  Validation Aware – Honors all standard validation rules.

How to Use 'updateRecord'?

Basic Syntax

				
					import { updateRecord } from 'lightning/uiRecordApi';
import { ShowToastEvent } from 'lightning/platformShowToastEvent';

// 1. Prepare fields to update
const fields = {};
fields['Id'] = recordId; // Required
fields['Account.Name'] = 'New Account Name';

// 2. Execute update
try {
  await updateRecord({ fields });
  // Show success message
  this.dispatchEvent(
    new ShowToastEvent({
      title: 'Success',
      message: 'Record updated',
      variant: 'success'
    })
  );
} catch (error) {
  // Handle error
}
				
			

Complete Example: Updating an Account

Let’s walk through a complete example of updating an Account record.

1. Create the Component

				
					<!-- updateAccount.html -->
<template>
    <lightning-card title="Update Account" icon-name="standard:account">
        <div class="slds-p-around_medium">
            <lightning-input
                label="Account Name"
                value={accountName}
                onchange={handleNameChange}
            ></lightning-input>
            <lightning-button
                label="Update Account"
                variant="brand"
                onclick={handleUpdate}
                class="slds-m-top_medium"
            ></lightning-button>
        </div>
    </lightning-card>
</template>
				
			

2. Javascript Controller

				
					// updateAccount.js
import { LightningElement, api, wire } from 'lwc';
import { getRecord, updateRecord } from 'lightning/uiRecordApi';
import { ShowToastEvent } from 'lightning/platformShowToastEvent';
import ACCOUNT_NAME_FIELD from '@salesforce/schema/Account.Name';
import ACCOUNT_ID_FIELD from '@salesforce/schema/Account.Id';

export default class UpdateAccount extends LightningElement {
    @api recordId; // Automatically populated when component is placed on a record page
    accountName;
    accountFields = [ACCOUNT_NAME_FIELD];

    // Wire service to get the current record
    @wire(getRecord, { recordId: '$recordId', fields: '$accountFields' })
    wiredAccount({ error, data }) {
        if (data) {
            this.accountName = data.fields.Name.value;
        } else if (error) {
            this.showToast('Error', error.body.message, 'error');
        }
    }

    handleNameChange(event) {
        this.accountName = event.target.value;
    }

    async handleUpdate() {
        try {
            // Create the record input
            const fields = {};
            fields[ACCOUNT_ID_FIELD.fieldApiName] = this.recordId;
            fields[ACCOUNT_NAME_FIELD.fieldApiName] = this.accountName;

            const recordInput = { fields };

            // Update the record
            await updateRecord(recordInput);

            // Show success message
            this.showToast('Success', 'Account updated successfully', 'success');
        } catch (error) {
            this.showToast('Error updating record', error.body.message, 'error');
        }
    }

    showToast(title, message, variant) {
        this.dispatchEvent(
            new ShowToastEvent({
                title,
                message,
                variant
            })
        );
    }
}
				
			

How updateRecord Works Under the Hood

    1. Request Preparation: LDS prepares the update request with only changed fields

    2. Client-Side Validation: Checks for required fields and basic validations

    3. Server Call: Makes an API call to update the record

    4. Cache Update: Updates the client-side cache if successful

    5. UI Notification: Propagates changes to all components using the record

    6. Error Handling: Reverts changes and notifies if the update fails

Important Notes About updateRecord

    1. Requires Record ID: You must always include the record Id

    2. Field API Names: Use the full field path (e.g., Account.Name)

    3. Error Handling: Always wrap in try-catch

    4. No Wire Adapter: Unlike getRecord, this is a function you call

Key Benefits of Using updateRecord

    1. Simplified Code: No need to write Apex for basic updates

    2. Automatic Sharing Enforcement: Respects org sharing settings

    3. Field-Level Security: Only updates fields the user has edit access to

    4. Performance: Optimistic UI updates make applications feel faster

    5. Consistency: All components show the same data simultaneously

    6. Reduced Boilerplate: Handles many common patterns automatically

Advanced Patterns

1. Updating Multiple Fields

				
					import NAME_FIELD from '@salesforce/schema/Account.Name';
import INDUSTRY_FIELD from '@salesforce/schema/Account.Industry';
import PHONE_FIELD from '@salesforce/schema/Account.Phone';

// In your update method:
const fields = {};
fields[ID_FIELD.fieldApiName] = this.recordId;
fields[NAME_FIELD.fieldApiName] = this.accountName;
fields[INDUSTRY_FIELD.fieldApiName] = this.industry;
fields[PHONE_FIELD.fieldApiName] = this.phone;

const recordInput = { fields };
await updateRecord(recordInput);
				
			

You can update fields on related records using dot notation:

				
					import CONTACT_NAME_FIELD from '@salesforce/schema/Account.PrimaryContact.Name';

const fields = {};
fields[ID_FIELD.fieldApiName] = this.recordId;
fields[CONTACT_NAME_FIELD.fieldApiName] = 'New Contact Name';

const recordInput = { fields };
await updateRecord(recordInput);
				
			

3. Combining with getRecordUi

For more complex scenarios, you can combine with getRecordUi:

				
					import { getRecordUi, updateRecord } from 'lightning/uiRecordApi';

async handleUpdate() {
    // First get the record UI for additional metadata
    const recordUi = await getRecordUi({
        recordIds: [this.recordId],
        layoutTypes: ['Full'],
        modes: ['Edit']
    });
    
    // Then perform the update
    const fields = { /* ... */ };
    await updateRecord({ fields });
}
				
			

Error Handling Best Practices

Proper error handling is crucial for a good user experience:

				
					async handleUpdate() {
    try {
        await updateRecord(recordInput);
        this.showToast('Success', 'Record updated', 'success');
    } catch (error) {
        let message = 'Unknown error';
        if (Array.isArray(error.body)) {
            message = error.body.map(e => e.message).join(', ');
        } else if (typeof error.body.message === 'string') {
            message = error.body.message;
        }
        this.showToast('Error updating', message, 'error');
    }
}
				
			

Performance Considerations

    1. Bulk Updates: For multiple records, consider using Apex

    2. Field Selection: Only include fields you need to update

    3. Network Conditions: Handle poor connectivity gracefully

    4. Caching: LDS automatically caches, but be mindful of stale data

Comparison with Similar Methods

MethodTypePurposeReal-time Sync
updateRecordFunctionUpdate records✅ Yes
getRecordWire AdapterRead records✅ Yes
deleteRecordFunctionDelete records✅ Yes

When to use updateRecord vs Apex

Use updateRecord when:

    1. Doing simple field updates

    2. You want automatic UI refresh

    3. No complex validation needed

Use Apex when:

    1. Need complex business logic

    2. Updating related records

    3. Require transaction control

When Not to Use updateRecord

While powerful, updateRecord isn’t always the right choice:

    1. Complex Business Logic: Requires Apex

    2. Batch Updates: For multiple records, consider Apex

    3. Cross-Object Updates: Limited support for complex relationships

    4. Custom Save Behavior: Need fine-grained control over the save process

Best Practices

    1. Refresh UI: Use refreshApex if needed.

    2. Handle errors: Always show user feedback.

    3. Validate data: Check values before saving.

    4. Handle Errors Gracefully: Provide meaningful feedback to users.

    5. Clean Up Data: Validate and sanitize inputs before updating.

    6. Consider User Context: Remember field-level security and sharing rules.

    7. Optimistic UI: Design for immediate feedback with rollback capability.

    8. Minimize Fields: Only update fields that have actually changed.

    9. Always Use Schema Imports:
				
					import NAME_FIELD from '@salesforce/schema/Account.Name';
				
			

Conclusion

The updateRecord function in Lightning Data Service provides LWC developers with a powerful, secure, and efficient way to update Salesforce records without writing Apex code. By understanding its capabilities, limitations, and best practices, you can build responsive, data-driven components that provide excellent user experiences while respecting all Salesforce platform protections.

Key takeaways:

    1. Use updateRecord for simple to moderately complex single-record updates

    2. Leverage schema imports for maintainable code

    3. Implement robust error handling

    4. Combine with other LDS functions like getRecord for complete solutions

    5. Know when to switch to Apex for more complex requirements

By mastering updateRecord, you’ll be able to build more efficient Lightning Web Components that handle data updates with minimal code while maximizing platform capabilities.

Share This Article
Follow:
Chinmaya is working as a Senior Consultant with a deep expertise in Salesforce. Holding multiple Salesforce certifications, he is dedicated to designing and implementing cutting-edge CRM solutions. As the creator of Writtee.com, Chinmaya shares his knowledge on educational and technological topics, helping others excel in Salesforce and related domains.
Leave a comment