Proxy Pattern¶
An object-design pattern in which an interface-compatible surrogate receives a client request, governs or mediates access, and delegates the admissible operation to a real subject.
Core Idea¶
The Proxy Pattern inserts a surrogate object on the access path to a real subject. Client code addresses the subject interface; a proxy implements that interface, receives the request, applies access, lifecycle, location, or bookkeeping logic, and forwards an admissible operation to the real subject. The GoF formulation calls the proxy a surrogate or placeholder that controls access to another object.[1]
The identity is not “any intermediary.” Interface compatibility lets the proxy stand where the real subject is expected, while a reference or resolution path connects it to that subject. Indirection has an explicit access purpose: deferring expensive construction, crossing a process boundary, enforcing authorization, caching, reference counting, or similar mediation. Variants alter the policy, but preserve the client–proxy–subject role package.[2]
Structural Signature¶
Recognition roles:
- subject contract: operations exposed to clients;
- real subject: the object that owns or performs the underlying service;
- proxy: a subject-compatible stand-in;
- client: invokes the contract without needing the real subject's access details;
- reference or resolver: gives the proxy a path to the real subject, immediately or lazily;
- mediation policy: authorization, activation, remoting, caching, counting, synchronization, or another access concern; and
- delegation invariant: admissible requests retain subject semantics after mediation.
A qualifying implementation need not use an inheritance hierarchy; interfaces, protocols, generated stubs, or language-level dispatch may supply substitutability. But if the wrapper cannot be used through the subject contract, or if it does not govern access to a subject, the Proxy identity is weak.
What It Is Not¶
A Decorator also shares an interface and delegates, but its primary intent is to add composable responsibilities to the object. A Proxy's primary intent is to regulate or make access possible. An Adapter changes one interface into another, defeating the interface-compatibility role. A Facade supplies a simplified entry point to a subsystem rather than standing in for one subject.[1]
A network reverse proxy, web proxy, voting proxy, legal proxy, and statistical proxy variable are established but different abstractions. They share broad intermediation, not necessarily the object-design contract. A language's dynamic-proxy facility is an implementation mechanism; it can implement Proxy, logging, interception, or other patterns and is not itself the pattern.[3]
Scope of Application¶
Remote proxies represent objects in another address space and hide marshalling, transport, and reference management. Virtual proxies postpone creation or loading of expensive objects. Protection proxies check credentials or capabilities before forwarding. Smart references add bookkeeping when a reference is used. Implementations can combine these functions.[1][2]
The pattern appears in object databases, remote procedure systems, lazy-loading object graphs, graphical resources, access-controlled services, and instrumentation. Its scope does not include every middleware hop. A gateway translating protocols, a message broker decoupling publishers and subscribers, or a service mesh sidecar may have proxy-like aspects, but qualifies here only when the subject-compatible surrogate and controlled-delegation roles are actually present.
Clarity¶
Use a three-part test. Can the client address the proxy under substantially the same contract as the real subject? Does the proxy identify or resolve that real subject? Does the proxy perform a policy-relevant action on the access path before or after delegation? Three “yes” answers strongly identify Proxy.
Transparency is relative, not absolute. A remote call can raise network failures and have latency absent from a local call; a virtual proxy may expose loading delay; a protection proxy may deny an operation. Interface compatibility does not promise identical nonfunctional behavior. Good documentation identifies which semantic and failure differences cross the boundary.
Manages Complexity¶
Proxy localizes access concerns that otherwise spread across clients. Remote clients need not duplicate serialization code. Consumers of a large image need not decide when to load it. Business objects need not embed every authorization check. The subject can remain focused on domain work while the proxy owns the cross-cutting access policy.
Indirection also creates costs: additional objects, hidden I/O, confusing identity, caching coherence, reentrancy, and distributed-failure semantics. A proxy reduces one kind of coupling while creating another operational layer. The pattern manages complexity only when that layer has a coherent policy and observable behavior.
Abstract Reasoning¶
The role package predicts design consequences. Because the proxy and real subject share a contract, clients can often be configured with either. Because every request crosses the proxy, it forms an enforcement or observation point. Because the proxy may resolve the subject lazily, construction can move from configuration time to first use.
Those predictions have limits. A bypass path defeats protection. A cached proxy can return stale results. A remote proxy cannot make a network operation semantically identical to an in-process call. Equality and identity can diverge when both proxy and subject references circulate. Correct reasoning therefore audits access-path completeness, delegation preservation, and the advertised transparency boundary rather than merely finding a class named Proxy.[4]
Knowledge Transfer¶
The literal pattern transfers among graphical applications, enterprise systems, distributed objects, persistence layers, and security wrappers. The subject contract, surrogate, policy, and delegation roles remain stable while technologies change.
Beyond software, an authorized representative may mediate access to a principal, but object identity, interfaces, and delegation semantics do not transfer literally enough to classify those arrangements here. Their shared residue belongs to Interface, Intermediation, Substitutability, and Delegation-like catalog structures.
Examples¶
Virtual image proxy. A document holds an image subject reference. The proxy knows dimensions, displays a placeholder, and loads the full image only when rendering requires it. After loading, drawing requests delegate to the real image. The access purpose is lifecycle deferral.[1]
Protection proxy. A file-service proxy implements the same operations as the service. It validates the caller's authority and forwards permitted reads or writes. If clients can obtain the real service directly, the security claim fails even though the class structure resembles Proxy.
Remote proxy. A generated client stub exposes subject operations, marshals arguments, sends a request, and unmarshals the result from a remote object. Location transparency is partial because latency, timeouts, and partial failure remain materially different.[2]
Nonexample—Adapter. A wrapper accepts a new payment interface and translates it to an incompatible legacy API. Its load-bearing purpose is contract conversion, not same-contract access control, so Adapter is the better identity.
Structural Tensions¶
- Transparency versus operational difference. A proxy should substitute for the subject, but remoting or loading adds failures and latency. Diagnostic: list every observable difference the client must handle.
- Central control versus bypass. Mediation works only if access flows through the proxy. Diagnostic: trace all reference-acquisition paths and demonstrate that protected clients cannot obtain the subject directly.
- Lazy efficiency versus surprise cost. Deferred work improves startup but can cause first-use latency. Diagnostic: measure where activation occurs and expose it in the performance contract.
- Caching versus semantic freshness. A proxy cache saves work but can violate subject state. Diagnostic: specify invalidation and test reads across mutations.
- Autonomy versus wrapper composition. Interface, Delegation, and Access Control are components. Diagnostic: remove same-contract surrogate access; if the variant ceases to be recognizable, Proxy retains an autonomous residual.
Structural–Framed Character¶
Proxy has a stable structural skeleton and policy-framed variants. The skeleton fixes client, subject contract, surrogate, real subject, mediation, and delegation. The frame selects why access is mediated and which differences are permissible. A remote proxy and protection proxy are not merely examples of one algorithm, but adaptations of one role structure.
Structural Core vs. Domain Accent¶
The transferable core is controlled intermediation under substitutability. The software accent supplies objects, interfaces, method invocation, references, lifecycle, serialization, caching, and exceptions. Removing that accent broadens the term “proxy” beyond this design pattern.
The candidate is domain-specific. prime:design_patterns captures reusable solution forms generally; Proxy supplies one named object-design organization with its own failure tests.
Instantiates / Related Primes¶
Proxy is a strict specialization of prime:design_patterns, the minimal proposed parent. It also instantiates Interface and Substitutability through the subject contract, and relates to Indirection and Access Control. These relations are explanatory rather than additional DAG parents.
Relationships to Other Abstractions¶
Current abstraction Proxy Pattern Domain-specific
Parents (1) — more general patterns this builds on
-
Proxy Pattern is a kind of Design Patterns Prime
Proxy is a strict specialization of
prime:design_patterns, the minimal proposed parent.It also instantiates Interface and Substitutability through the subject contract, and relates to Indirection and Access Control. These relations are explanatory rather than additional DAG parents.
Hierarchy path (1) — routes to 1 parentless root
- Proxy Pattern → Design Patterns → Abstraction
Neighborhood in Abstraction Space¶
Proxy Pattern sits in a sparse region of the domain-specific corpus (86th percentile for distinctiveness): few abstractions share its structure, so a faithful description tends to retrieve it precisely.
Family — Unclustered & Miscellaneous (1565 abstractions)
Nearest neighbors
- Object-Oriented Operating System — 0.82
- Transitive Set — 0.81
- Canonical Data Model — 0.80
- URL Redirection — 0.79
- Distributed Object — 0.79
Computed from structural-signature embeddings · 2026-09-08
Not to Be Confused With¶
- Decorator: same-interface delegation whose primary intent is responsibility composition.
- Adapter: converts incompatible contracts.
- Facade: simplifies access to a subsystem rather than substituting for one subject.
- Mediator: coordinates colleague objects rather than standing in for one.
- Gateway: encapsulates access to an external system and may translate contracts.
- Dynamic proxy: runtime mechanism capable of implementing multiple interception purposes.
- Web/network proxy: traffic intermediary that need not satisfy the object-pattern roles.
- Proxy variable/person: unrelated statistical or representative meanings.
References¶
[1] Erich Gamma, Richard Helm, Ralph Johnson, and John Vlissides, Design Patterns: Elements of Reusable Object-Oriented Software, Addison-Wesley, 1994, “Proxy,” pp. 207–217, ISBN 978-0-201-63361-0. registry ↩a ↩b ↩c ↩d
[2] Frank Buschmann et al., Pattern-Oriented Software Architecture, Volume 1: A System of Patterns, Wiley, 1996, patterns for distributed access and forwarding, ISBN 978-0-471-95869-7. registry ↩a ↩b ↩c
[3] Oracle, Java Platform specification for java.lang.reflect.Proxy, a runtime mechanism for interface-dispatch proxy classes, https://docs.oracle.com/en/java/javase/21/docs/api/java.base/java/lang/reflect/Proxy.html. registry ↩
[4] Martin Fowler, Patterns of Enterprise Application Architecture, Addison-Wesley, 2002, Remote Proxy and Lazy Load discussions, https://martinfowler.com/eaaCatalog/remoteProxy.html. registry ↩