1.1 Analyzing Technical Architecture and Choosing Out-of-the-Box vs. Custom Solutions
Key Takeaways
- Every requirement should first be mapped to an out-of-the-box Power Platform component before custom development is considered.
- Logic that must run regardless of entry point (UI, import, or API) requires a Dataverse plug-in, not a business rule or client script.
- Custom connectors and Azure Functions are justified when external authentication, transformation, or long-running compute exceeds standard connector capability.
- Implementation choices should be weighed on maintainability, ALM complexity, licensing cost, performance, and team skill set.
- A defensible technical design documents why simpler declarative alternatives were rejected for each custom component.
As a PL-400 developer, your first job on any project is architecture: translating business requirements into a concrete map of Power Platform and Azure components, then deciding how much of that map can be built with clicks instead of code. The exam tests both halves of this skill — can you decompose a requirement into the right components, and can you justify when a custom solution is actually necessary.
Mapping Requirements to Solution Components
Every requirement in a discovery document maps to one or more implementation options. A mature architecture starts by cataloging what already exists in the platform before reaching for custom code.
| Requirement type | Likely component |
|---|---|
| End-user data entry, forms, dashboards | Canvas app or model-driven app |
| Structured, repeatable business process | Business process flow |
| Simple validation or field defaulting | Business rule or column formula |
| Multi-step automation with connectors | Power Automate cloud flow |
| Logic that must run on every code path (API, import, UI) | Dataverse plug-in |
| Reusable, complex UI control | Code component (PCF) |
| Call to an external REST API with no existing connector | Custom connector |
| Heavy compute, long-running, or external SDK-dependent logic | Azure Function |
Analyzing the technical architecture means walking through every requirement in this table, identifying which Power Platform surface owns it, and confirming the components integrate cleanly — for example, that a canvas app's data source, a cloud flow's trigger, and a plug-in's registered step are not duplicating the same business rule in three places.
The Out-of-the-Box-First Principle
Microsoft's guidance — and the exam's expectation — is to exhaust declarative, out-of-the-box (OOB) capability before writing code. Custom code costs more to build, test, secure, upgrade, and hand off to other makers. Before designing a plug-in or Azure Function, confirm the requirement cannot be met with:
- Business rules — client- and server-enforced field logic (show/hide, set value, validation) with no code, portable across model-driven forms and mobile
- Calculated and rollup columns — computed and aggregated values maintained automatically by Dataverse
- Business process flows — guided, stage-based processes across one or more tables
- Power Automate cloud flows — trigger-based automation using hundreds of prebuilt connectors
- Power Fx formulas — canvas app logic and, increasingly, Dataverse formula columns
- Views, forms, and dashboards — configuration-only presentation and filtering
When Out-of-the-Box Is Not Enough
Custom development becomes justified when a requirement exceeds what declarative tools express. Common triggers include:
- Guaranteed execution regardless of entry point. A business rule only fires from a form; if the same table can be updated through the Web API, a data import, or a Power Automate flow, only a plug-in registered on the table's core operation enforces the logic every time.
- Complex, conditional, or multi-entity logic. Business rules support limited condition branching. Plug-ins and custom APIs handle arbitrary C# logic, loops, and calls to the Organization service.
- External system calls that need custom authentication, transformation, or retries beyond what a standard or premium connector exposes — this points to a custom connector or Azure Function.
- Rich, interactive UI elements — maps, signature pads, custom charts — that canvas controls cannot render, which points to a PCF code component.
- Performance-sensitive or long-running processing that would time out a synchronous plug-in (2-minute limit) or exceed a cloud flow's practical use — this points to an asynchronous plug-in or an Azure Function.
Weighing the Implementation Approach
Once you know that custom development is needed, decide how to implement it by weighing:
- Maintainability — who supports this after go-live? A maker-owned cloud flow is easier to hand off than a compiled plug-in assembly.
- ALM complexity — code components require build pipelines, source control, and versioned assemblies; declarative components move through solutions with far less tooling.
- Licensing and consumption cost — premium connectors, custom connectors, and Azure resources carry separate licensing/consumption costs that a purely declarative design avoids.
- Performance requirements — synchronous plug-ins block the UI transaction; cloud flows introduce latency; Azure Functions scale independently but add network hops.
- Team skill set — a citizen developer team favors low-code; a pro-dev team can absorb plug-ins and Azure Functions without a support gap.
Documenting the Decision
A defensible technical design records, for every non-trivial requirement, which option was chosen and why the simpler alternatives were rejected. This traceability is what lets a future developer — or the exam's scenario questions — evaluate whether a design decision was correct, not just whether it works.
A Worked Example
Consider a requirement: "When a claim exceeds $10,000, the system must automatically require manager approval, and this must hold true no matter which channel submits the claim." A first pass might reach for a business rule, since approval routing sounds like a validation. But because claims can also arrive through a nightly batch import from a legacy system, a business rule would silently fail to enforce the threshold on imported records. The correct design instead registers a plug-in on the claim table's Create and Update messages to guarantee the check runs universally, and pairs it with a Power Automate flow — triggered by the plug-in setting a status field — to handle the actual approval routing and notification, since that part of the requirement is genuinely a multi-step orchestration rather than a single validation rule. Separating "must always be enforced" from "must be orchestrated" is exactly the kind of reasoning the exam rewards.
A requirement states that a validation rule must run correctly no matter whether a record is created from the model-driven form, imported in bulk, or created through the Dataverse Web API by an external system. Which implementation best satisfies this requirement?
Which factor is the strongest justification for choosing a custom Azure Function over a Power Automate cloud flow for a piece of business logic?