1 # Service Development Guidelines
7 The top-level `//services` directory contains the sources, public Mojo interface
8 definitions, and public client libraries for a number of essential services,
9 designated as **Chrome Foundation Services**. If you think of Chrome as a
10 "portable OS," Chrome Foundation Services can be thought of as the core system
13 Each subdirectory here corresponds to a service that:
15 - generally focuses on a subset of functionality or features which are
16 thematically or functionally related in a way that makes sense given the name
18 - could logically run in an isolated process for security or performance
19 isolation, depending on the constraints of the host OS
22 Note that there are other parts of the tree which aggregate
23 slightly-less-than-foundational service definitions, such as services specific
24 to the Chrome browser defined in `//chrome/services` or reusable services for
25 Content or its embedders, defined in `//components/services`. The motivations,
26 advice, and standards discussed in this document apply to all service
27 definitions in the Chromium tree.
30 One of the main motivations for expressing Chromium as a collection of services
31 is long-term maintainability and code health. Because service API boundaries are
32 strictly limited to Mojo interfaces, state owned and managed by each service is
33 strongly isolated from other components in the system.
35 Another key motivation is general modularity and reusability: in the past there
36 have been a number of missed opportunities for potential new features or
37 Chromium-based products due to the browser's generally monolothic and inflexible
38 system design. With the services providing scaffolding for system components, it
39 becomes progressively easier to build out newer use cases with *e.g.* a smaller
40 resource footprint, or a different process model, or even a more granular binary
45 As outlined above, individual services are intended for graceful reusability
46 across a broad variety of use cases. To enable this goal, we have rigorous
47 standards on services' structure and public API design. Before doing significant
48 work in `//services` (or other places where services are defined), please
49 internalize these standards. All Chromium developers are responsible for
52 ### Public Service APIs
54 In creating and maintaining a service's public API, please respect the following
57 - The purpose of a service should be readily apparent.
58 - The supported client use cases of the service should be easy for a new
59 consumer to understand.
60 - The service should use idioms and design patterns consistent with other
62 - From the service's public API documentation and tests, it should be feasible
63 to develop a new implementation of the service which satisfies existing
64 clients and doesn't require mimicking internal implementation details of the
66 - Perhaps most important of all, a service's public API should be designed with
67 multiple hypothetical clients in mind, *not* focused on supporting only a
68 single narrow use known at development time. **Always be thinking about the
71 If you're working on a new service and have concerns or doubts about API design,
73 [services-dev@chromium.org](https://groups.google.com/a/chromium.org/forum#!forum/services-dev)
74 and ask for help. The list is generally quite responsive, and it's loaded with
75 people who have done a lot of work on services.
77 ### Service API Design Tips
79 #### Using Interface Factories to Establish Context
81 One common pitfall when designing service APIs is to write something like:
84 interface GoatTeleporter {
85 // Sets the client interface pipe for this teleporter. Must be called before
86 // other interface methods.
87 SetClient(GoatTeleporterClient client);
89 TeleportGoat(string name);
92 interface GoatTeleporterClient {
97 The problem with this approach is that a client may easily fail to call
98 `SetClient` before calling `TeleportGoat`. When such ordering requirements are
99 necessary, the service can benefit clients by designing an API that is harder
100 to fail at. For example:
103 interface GoatTeleporterFactory {
104 GetGoatTeleporter(GoatTeleporter& request, GoatTeleporterClient client);
107 interface GoatTeleporter {
108 TeleportGoat(string name);
112 Instead of exposing `GoatTeleporter` directly to other services, the service can
113 expose `GoatTeleporterFactory` instead. Now it's impossible for a client to
114 acquire a functioning `GoatTeleporter` pipe without also providing a
115 corresponding client pipe to complement it.
119 Just some basic tips for service and interface naming:
121 - Strive to give your service's main interface a name that directly conveys the
122 general purpose of the service (*e.g.*, `NetworkService`, `StorageService`)
123 rather than a meaningless codename like `Cromulator`.
125 - Strive to avoid conceptual layering violations in naming and documentation --
126 *e.g.*, avoid referencing Blink or Content concepts like "renderers" or
129 - Use the names `FooClient` and `FooObserver` consistently in interfaces. If
130 there is an expected 1:1 correspondence between a Foo and its client interface
131 counterpart, that counterpart should most likely be called `FooClient`. If
132 there is expected to be 1-to-many correspondence between a Foo and its
133 counterpart clients, the client interface may be better named `FooObserver`.
135 ### Service Directory & Dependency Structure
137 Services typically follow a canonical directory structure:
140 //services/service_name/ # Private implementation
142 mojom/ # Mojom interfaces
143 cpp/ # C++ client libraries (optional)
144 java/ # Java client libararies (optional, rare)
145 js/ # JS client libraries (optional, rare)
148 As a general rule, **nothing below `/public` can depend on the private service
149 implementation** (*i.e.* things above `/public`). Enforcing this principle makes
150 it much easier to keep the service's state well-isolated from the rest of the
153 Generally the language-specific client libraries are built against only the
154 public mojom API of the service (and usually few other common dependencies like
155 `//base` and `//mojo`).
157 Even in the private service implementation, services should not depend on very
158 large components like Content, Chrome, or Blink.
161 NOTE: Exceptions to the above rule are made in rare cases where Blink or V8 is
162 actually required as part of the service implementation. For example
163 `"data_decoder"` uses Blink implementation to decode common image formats, and
164 `"proxy_resolver"` uses V8 to execute proxy autoconfig scripts.
167 ### Service Documentation
169 - Every service should have a top-level `README.md` that explains the purpose and
170 supported usage models of the service.
172 - Every public interface should be documented within its Mojom file at both the
173 interface level and indivudal message level.
175 - Interface documentation should be complete enough to serve as test
176 specifications. If the method returns information of a user's accounts, what
177 should happen if the user is not signed in? If the method makes a request for
178 an access token, what happens if a client makes a second method call before
179 the first one has completed? If the method returns a nullable object, under
180 which conditions will it be null?
182 - Avoid writing interface documentation which is unnecessarily prescriptive
183 about implementation details. Keep in mind that these are **interface**
184 definitions, not implementations thereof.
186 - Avoid writing documentation which is tailored to a specific client.
190 - Try to cover service implementation details with unit tests tied as closely
191 as possible to the private implementation object or method being tested,
192 rather than exercising implementation details through public API surface.
194 - For integration tests, try to have tests cover as much of the public API
195 surface as possible while mocking out as little of the underlying service as
198 - Treat the public API tests as "conformance tests" which clearly demonstrate
199 what expectations and guarantees are supposed to be upheld by *any*
200 implementation of the service's APIs.
202 ## Adding a New Service
204 Please start a thread on
205 [services-dev@chromium.org](https://groups.google.com/a/chromium.org/forum/#!forum/services-dev)
206 if you want to propose the introduction of a new service.
208 If you are servicifying an existing Chromium feature, please check out
209 [Servicifying Chromium Features](/docs/servicification.md).
213 Here are some other external documents that aren't quite fully captured by any
214 documents in the Chromium tree. Beware of obsolete information:
216 - [High-level Design Doc](https://docs.google.com/document/d/15I7sQyQo6zsqXVNAlVd520tdGaS8FCicZHrN0yRu-oU)
217 - [Servicification Homepage](https://sites.google.com/a/chromium.org/dev/servicification)
219 ## Additional Support
221 You can always post to
222 [services-dev@chromium.org](https://groups.google.com/a/chromium.org/forum#!forum/services-dev)
223 with questions or concerns about anything related to service development.