100% Free Forever
AI-Powered Learning
Industry Expert Content
Certificates & Badges
Learn At Your Own Pace
.NET Framework

Service Contracts

How the ServiceContract and OperationContract attributes define the public interface of a WCF service, and the rules that govern them.

FoundationsBeginner8 min readJul 10, 2026
Analogies

What Is a Service Contract?

A service contract is the formal declaration of what operations a WCF service exposes to the outside world. It is defined by applying the [ServiceContract] attribute to a .NET interface (the recommended approach) or a class, and then marking each publicly callable method with [OperationContract]. Only methods marked [OperationContract] are exposed as part of the service's public surface; any other members on the interface or implementing class are invisible to clients. Applying the contract to an interface rather than the concrete class decouples the publicly agreed shape of the service from its implementation, letting you version, mock, or swap implementations without breaking existing clients.

🏏

Cricket analogy: A service contract is like a bowler's registered action submitted to the ICC — only the deliveries within that legal action are 'sanctioned' for match play, just as only [OperationContract]-marked methods are exposed to WCF clients.

Interfaces, Naming, and Versioning

The [ServiceContract] attribute accepts a Namespace property (defaulting to http://tempuri.org/, which should always be overridden with a real, versioned namespace such as http://mycompany.com/services/2026/07) and a Name property that controls the WSDL portType name if it must differ from the interface name. Because SOAP and WSDL contracts are tightly coupled to signatures, adding a new operation to an existing interface is a backward-compatible change for existing clients, but changing an existing operation's parameters, return type, or removing it is a breaking change; the common mitigation is to version contracts explicitly, for example IOrderServiceV2, or to add new optional operations rather than modifying existing ones.

🏏

Cricket analogy: Overriding the default tempuri.org namespace with a real one is like a domestic team retiring its generic 'Team A' placeholder jersey for an officially registered franchise name and crest before playing any sanctioned matches.

Contract Inheritance and Session Behavior

A service contract interface can inherit from another interface marked with [ServiceContract], and WCF will merge the operations from both into a single exposed contract; however, a class can only implement one top-level service contract per endpoint. The [ServiceContract] attribute also has a SessionMode property (Allowed, Required, or NotAllowed) that, combined with the chosen binding's session support, determines whether calls from the same client are correlated into a stateful session or treated as fully independent, stateless calls; requiring a session on a binding that doesn't support one (like basicHttpBinding without WS-ReliableMessaging) throws a configuration exception at service startup.

🏏

Cricket analogy: SessionMode is like deciding whether a bowler's spell is tracked ball-by-ball as a continuous over (a session) or whether each delivery is scored as an isolated event with no memory of the previous ball.

csharp
[ServiceContract(Namespace = "http://mycompany.com/services/2026/07", SessionMode = SessionMode.Allowed)]
public interface IOrderService
{
    [OperationContract]
    int CreateOrder(OrderRequest request);

    [OperationContract]
    OrderStatus GetOrderStatus(int orderId);

    // Not exposed to clients -- no [OperationContract]
    // internal void RecalculateShipping(int orderId) { ... }
}

// Inheriting and extending a contract
[ServiceContract]
public interface IOrderServiceV2 : IOrderService
{
    [OperationContract]
    void CancelOrder(int orderId);
}

Always set an explicit Namespace on [ServiceContract]. Leaving it at the default http://tempuri.org/ works fine in development but is a common source of confusion and accidental contract collisions when multiple services are deployed together.

Changing the signature (parameters or return type) of an existing [OperationContract] method is a breaking change for every already-deployed client with a generated proxy. Prefer adding new operations or introducing a versioned contract interface instead of modifying an operation in place.

  • A service contract is declared with [ServiceContract] on an interface, and exposed operations are marked [OperationContract].
  • Only [OperationContract]-marked methods are visible to clients; everything else is hidden.
  • Applying the contract to an interface rather than a class decouples the public shape from the implementation.
  • Always override the default tempuri.org namespace with a real, versioned namespace.
  • Adding new operations is backward-compatible; changing existing operation signatures is a breaking change.
  • Service contracts can inherit from other service contracts, merging their operations.
  • SessionMode (Allowed/Required/NotAllowed) must be compatible with the chosen binding's session support.

Practice what you learned

Was this page helpful?

Topics covered

#NETFramework#WCFWindowsCommunicationFoundationStudyNotes#MicrosoftTechnologies#ServiceContracts#Service#Contracts#Contract#Interfaces#StudyNotes#SkillVeris