Advanced 30 min read

Secure the Data Access

By the end of this lesson, you'll be able to:

  • Apply with sharing to the service class, with explicit reasoning
  • Check field-level access before reading the fields each metric needs
  • Apply Module 28's full security toolkit to a real dashboard feature

Prerequisites: "Build the Service Layer"

Reasoning through the sharing choice

public with sharing class AccountHealthService {
    // ...
}

Applying Module 30's "Secure Data Access" question directly: does this dashboard need to see Cases or Contacts the running user couldn't normally access? No — a support manager viewing a dashboard should only ever see health data for Accounts they already have access to. with sharing is the clear, deliberate choice.

Checking field-level access before reading

public Integer getOpenCaseCount(Id accountId) {
    if (! Schema.sObjectType.Case.isAccessible()) {
        return 0;
    }
    return [SELECT COUNT() FROM Case WHERE AccountId = :accountId AND IsClosed = false];
}

This is Module 28's CRUD-check pattern, applied to a genuinely realistic scenario: a user with dashboard access but no Case object permission shouldn't see a broken component — returning 0 gracefully (rather than a permissions error) keeps the dashboard usable even for a user with narrower access.

Using WITH USER_MODE for automatic enforcement

public Decimal getTotalWonRevenue(Id accountId) {
    List<Account> accounts = [
        SELECT Total_Won_Revenue__c FROM Account WHERE Id = :accountId WITH USER_MODE
    ];
    if (accounts.isEmpty()) {
        return 0;
    }
    return accounts[0].Total_Won_Revenue__c == null ? 0 : accounts[0].Total_Won_Revenue__c;
}

Module 28's WITH USER_MODE handles field-level security automatically for this query, rather than manually checking Total_Won_Revenue__c.isAccessible() — and switching to a List query (instead of assuming exactly one record) means a user without access to any matching Account, or the field itself, simply gets an empty result instead of a runtime error.

Exercise

As a comment, write the reasoning for why AccountHealthService should be with sharing rather than without sharing.

Show hint

Follow Module 30's "does this genuinely need to bypass the running user's access?" question.

APEX

Secure the Data Access Quiz

1. Why does getOpenCaseCount return 0 rather than throwing an error when the user lacks Case access?

Log in to submit the quiz and save your score.

My Notes

Log in to keep private notes on this lesson.

Questions about this lesson

No questions yet — be the first to ask.

Log in to ask a question about this lesson.

Summary

This lesson secures AccountHealthService following Module 28's full toolkit — sharing, field-level access, and the reasoning behind each choice, not just the mechanical application.