Teams should keep security functions out of application code when those controls are common, repetitive, or easy to misconfigure. Shared services can reduce duplicated effort, improve consistency, and lower the chance that critical controls are reimplemented differently across teams. The key decision is whether the control is core product logic or a reusable security capability that benefits from centralised governance.
What belongs in application code, and what belongs in shared security services?
Separate functions by how often they repeat, how risky they are to implement inconsistently, and how much they benefit from a single trusted implementation. Things like credential validation, token handling, encryption primitives, rate limiting, and request filtering usually belong in shared services or libraries because they need one well-governed behaviour across many apps. Business-specific enforcement still belongs in the application when only the product logic can decide it correctly.
A good mental model is to ask whether a control is part of the product’s decision-making or part of the platform’s security baseline. If a rule is inherently tied to workflow, customer state, or domain logic, keeping it in the app preserves correctness. If it is a reusable control that should behave the same way everywhere, centralising it reduces drift, maintenance overhead, and the chance of subtle security gaps.
Shared services are strongest when the security function is stable, testable, and broadly reusable. That includes functions where a small implementation error would create a common failure mode across multiple teams. Application code is the better home when the control needs local context, tight coupling to product behaviour, or rapid iteration that would be slowed by platform change control.
Where the boundary usually breaks down in practice
The hardest cases are functions that look generic but depend on application context. Authorization is the classic example: coarse controls can be centralised, but decisions about who may do what often need application-aware policy inputs. The same is true for session handling, secrets usage, and data access, where the shared mechanism should be standardised but the exact permission or exposure decision is often product-specific.
Engineering teams also need to distinguish “secure by default” from “securely centralised.” A shared service can enforce consistency, but it can also become a single point of failure if it is poorly versioned, weakly observed, or too broad in scope. That is why a central service should expose a narrow interface, emit audit signals, and fail closed in a predictable way. OWASP ASVS is a useful reference for deciding which app-facing security requirements must still be verified at the application boundary.
For teams building on containers or service platforms, the same logic applies to platform-level controls such as image policy, runtime guardrails, and environment isolation. Those belong closer to shared infrastructure because they are cross-cutting controls with consistent enforcement needs. NIST SP 800-190 Container Security is a strong fit when the decision involves platform-enforced protections rather than product-specific business rules.
Risk and Threat Considerations
When security functions are reimplemented inside each application, the main risk is inconsistency. Small differences in parsing, validation, expiry handling, or privilege checks can create exploitable gaps, and attackers often look for the weakest implementation in a fleet. Centralising common controls reduces that spread, but it also concentrates trust, so a defect in the shared service can affect many applications at once.
Failure mechanism: Teams duplicate security logic in slightly different ways, or they centralise it without enough governance, testing, and monitoring. Either path can produce silent bypasses, misconfiguration, or overly broad trust in the shared layer.
Impact: The result is usually larger blast radius, harder incident response, and a control posture that looks standard on paper but behaves differently across applications. In identity-heavy systems, that can turn a routine integration mistake into broad access exposure.
Standards & Framework Alignment
This section maps relevant standards and security frameworks to the operational risks and controls described in this guidance.
OWASP Non-Human Identity Top 10 address the attack and risk surface, while NIST CSF 2.0, CIS Controls v8 and NIST SP 800-63 set the governance and control requirements practitioners need to meet.
| Framework | Control / Reference | Relevance |
|---|---|---|
| OWASP Non-Human Identity Top 10 | NHI-01 — Secrets and Credential Management | Shared services should centralise reusable secret-handling controls. |
| NHI-03 — Privilege and Access Minimisation | App-specific authorization decisions shape least-privilege enforcement. | |
| Recommendation — Centralise secret handling in a governed service and avoid duplicating credential logic in app code. Keep app-specific privilege decisions in the product layer and standardise only the reusable enforcement mechanism. | ||
| NIST CSF 2.0 | PR.AC-4 — Access Permissions and Authorization | The question is fundamentally about where authorization controls should live. |
| PR.DS-1 — Data-at-Rest Protection | Shared security services often carry reusable encryption and protection functions. | |
| Recommendation — Apply consistent authorization controls at the most reusable enforcement point. Standardise reusable data-protection services so applications do not reimplement encryption differently. | ||
| CIS Controls v8 | 6.3 — Access Authorization Maintenance | Deciding which controls stay shared versus app-local affects authorization consistency. |
| 16.5 — Malware Defenses | Shared security services reduce duplicated defensive logic and inconsistent enforcement. | |
| Recommendation — Use a central control plane for repeated authorization logic and keep business-specific checks in the application. Consolidate repeatable defensive functions into managed services to reduce drift across applications. | ||
| NIST SP 800-63 | AAL2 — Authentication Assurance Level 2 | Centralised authentication services often underpin application security decisions. |
| Recommendation — Use a shared authentication service that consistently enforces the required assurance level across apps. | ||
Practitioner Guidance
What to prioritise: Standardise the controls that are repetitive, difficult to implement safely, or likely to be copied across many services. Keep domain decisions in the application when the security outcome depends on business context, not just a generic rule.
What to verify: Before moving a function into a shared service, confirm that the service can express the needed policy granularity, fail safely, and produce enough logging for audit and incident response. If it cannot, only the common mechanism should be shared, not the final decision.
Common mistake: Treating “centralised” as automatically “safer.” A shared control is only an improvement when teams can prove it is more consistent, more observable, and no harder to operate than the code it replaces.
Practitioner takeaway: Use shared services for controls that must be uniform, but keep the final security decision as close as possible to the business logic when context determines the correct answer.
Related resources from NHI Mgmt Group
- How do security teams decide which agent identity controls belong in orchestration versus infrastructure layers?
- How do security teams decide when to use automation versus human review for AI-driven code changes?
- How should security teams use application usage data to decide whether an app is still worth renewing?
- How should security teams decide which mobile app code paths need stronger protection first?
Deepen Your Knowledge
Reviewed and updated by the NHIMG editorial team on September 20, 2026.
NHI Mgmt Group — the #1 independent authority on Non-Human Identity, IAM, and Agentic AI security. nhimg.org