android_webview
apps
ash
base
build
build_overrides
buildtools
cc
chrome
chromecast
chromeos
clank
codelabs
components
content
crypto
dbus
device
docs
accessibility
autofill
chromeos
code.md
esim_policy_architecture.md
design
enterprise
experiments
fuchsia
gpu
graphics
images
infra
intl
ios
linux
login
mac
media
memory
memory-infra
patterns
privacy
privacy_budget
process
security
speed
speed_metrics
standards
telemetry_extension
testing
transcripts
ui
updater
webapps
website
workflow
DIR_METADATA
OWNERS
README.md
accessibility.md
ad_tagging.md
adding_to_third_party.md
android_accessing_cpp_enums_in_java.md
android_accessing_cpp_features_in_java.md
android_accessing_cpp_switches_in_java.md
android_build_instructions.md
android_cast_build_instructions.md
android_debugging_instructions.md
android_dynamic_feature_modules.md
android_emulator.md
android_isolated_splits.md
android_jni_ownership_best_practices.md
android_logging.md
android_native_libraries.md
android_studio.md
angle_in_chromium.md
api_keys.md
asan.md
atom.md
benchmark_performance_regressions.md
bfcache.md
bitmap_pipeline.md
branch_gardener.md
building_old_revisions.md
callback.md
ccache_mac.md
chrome_browser_design_principles.md
chrome_os_logging.md
chrome_settings.md
chrome_untrusted.md
chromedriver_status.md
chromeos_build_instructions.md
chromeos_glossary.md
chromium_browser_vs_google_chrome.md
cipd_and_3pp.md
cl_respect.md
cl_tips.md
clang.md
clang_code_coverage_wrapper.md
clang_format.md
clang_gardening.md
clang_sheriffing.md
clang_static_analyzer.md
clang_tidy.md
clang_tool_refactoring.md
clangd.md
clion.md
closure_compilation.md
cocoa_tips_and_tricks.md
code_review_owners.md
code_reviews.md
commit_checklist.md
component_build.md
configuration.md
contributing.md
cq_fault_attribution.md
cr_respect.md
cr_user_manual.md
cross_platform_ui.md
cygwin_dll_remapping_failure.md
dangling_ptr.md
dangling_ptr_guide.md
dbus_mojo_connection_service.md
debugging_with_crash_keys.md
dependencies.md
deterministic_builds.md
disassemble_code.md
documentation_best_practices.md
documentation_guidelines.md
early-hints.md
eclipse.md
emacs.md
erc_irc.md
flag_expiry.md
flag_guarding_guidelines.md
flag_ownership.md
frame_trees.md
gardener.md
gcs_dependencies.md
gdbinit.md
get_the_code.md
git_cookbook.md
git_submodules.md
git_tips.md
google_chrome_branded_builds.md
google_play_services.md
graphical_debugging_aid_chromium_views.md
gwp_asan.md
history_manipulation_intervention.md
how_cc_works.md
how_to_add_your_feature_flag.md
how_to_extend_web_test_framework.md
idn.md
initialize_blink_features.md
inlined_stack_traces.md
installation_at_vmware.md
ios_build_instructions.md
ios_infra.md
ios_voiceover.md
kiosk_mode.md
life_of_a_frame.md
lldbinit.md
mac_arm64.md
mac_build_instructions.md
mac_lld.md
modifying_session_history_serialization.md
modules.md
mojo_and_services.md
mojo_ipc_conversion.md
mojo_testing.md
native_relocations.md
navbar.md
navigation-request-navigation-state.gv
navigation-request-navigation-state.png
navigation.md
navigation_concepts.md
network_traffic_annotations.md
no_sources_assignment_filter.md
optimizing_web_uis.md
orderfile.md
origin_trials_integration.md
ozone_overview.md
parsing_test_results.md
pgo.md
piranha_plant.md
process_model_and_site_isolation.md
profiling.md
profiling_content_shell_on_android.md
proxy_auto_config.md
qtcreator.md
release_branch_guidance.md
render-frame-host-lifecycle-state.gv
render-frame-host-lifecycle-state.png
render_document.md
rust-unsafe.md
rust.md
seccomp_sandbox_crash_dumping.md
servicification.md
session_history.md
sheriff.md
shutdown.md
special_case_urls.md
static_initializers.md
sublime_ide.md
system_hardening_features.md
tab_helpers.md
testing_webui.md
threading_and_tasks.md
threading_and_tasks_faq.md
threading_and_tasks_testing.md
toolchain_support.md
tour_of_luci_ui.md
tpm_quick_ref.md
translation_screenshots.md
trusted_types_on_webui.md
unretained_dangling_ptr_guide.md
unsafe_buffers.md
updating_clang.md
updating_clang_format_binaries.md
use_counter_wiki.md
useful_urls.md
user_data_dir.md
user_data_storage.md
user_handle_mapping.md
vanilla_msysgit_workflow.md
vscode.md
vscode_python.md
webui_build_configuration.md
webui_code_sharing.md
webui_explainer.md
webui_in_chrome.md
webui_in_components.md
webui_using_lit.md
webview_policies.md
win_cross.md
win_order_files.md
windows_build_instructions.md
windows_native_window_occlusion_tracking.md
windows_pwa_integration.md
windows_shortcut_and_taskbar_handling.md
windows_split_dll.md
windows_virtual_desktop_handling.md
wmax_tokens.md
working_remotely_with_android.md
writing_clang_plugins.md
extensions
fuchsia_web
gin
google_apis
gpu
headless
infra
internal
ios
ios_internal
ipc
media
mojo
native_client
native_client_sdk
net
pdf
ppapi
printing
remoting
rlz
sandbox
services
signing_keys
skia
sql
storage
styleguide
testing
third_party
tools
ui
url
v8
webkit
.clang-format
.clang-tidy
.clangd
.git-blame-ignore-revs
.gitallowed
.gitattributes
.gitignore
.gitmodules
.gn
.mailmap
.rustfmt.toml
.vpython3
.yapfignore
ATL_OWNERS
AUTHORS
BUILD.gn
CODE_OF_CONDUCT.md
CPPLINT.cfg
CRYPTO_OWNERS
DEPS
DIR_METADATA
LICENSE
LICENSE.chromium_os
OWNERS
PRESUBMIT.py
PRESUBMIT_test.py
PRESUBMIT_test_mocks.py
README.md
WATCHLISTS
codereview.settings

In one section, the guidelines say: Instead of using ProfileKeyedServiceFactory (in //chrome), consider using BrowserContextKeyedServiceFactory (in //components) instead. But in the "Desired State" section, it says: The //content directory is the API for building a web browser. Even though Ash does use web technology for rendering many things, it is not itself a web browser and there should be no OS code in this directory or calling directly into it. And also: New features should be designed to adhere to the “desired state” as closely as practical. To resolve some confusion here, explicitly call out BrowserContext as allowed despite contradicting the desired state. Change-Id: Iba72f48d9dc054d5012325bc4f384d036cc68b99 Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/6093907 Reviewed-by: Michael Cui <mlcui@google.com> Reviewed-by: Kyle Horimoto <khorimoto@chromium.org> Commit-Queue: Darren Shen <shend@chromium.org> Cr-Commit-Position: refs/heads/main@{#1396991}
171 lines
9.5 KiB
Markdown
171 lines
9.5 KiB
Markdown
# The architecture of Browser/ChromeOS code
|
||
|
||
## Overview
|
||
|
||
We want to have clean code, good architecture, and clear ownership to ensure
|
||
everybody can efficiently deliver high quality products. Toward this goal, this
|
||
document discusses how code in the Chromium git repository is and should be
|
||
architected between the browser and ChromeOS code.
|
||
|
||
## Background
|
||
|
||
Originally, ChromeOS was just the Linux Chrome browser with a few extra
|
||
additions for UI system management. As such, and to keep the system requirements
|
||
very low, the entire ChromeOS UI was built into the Chrome "browser" process.
|
||
Over time, ChromeOS has gotten substantially more sophisticated and capable.
|
||
Many important services run in separate processes, services, or VMs, but most of
|
||
the UI still runs in the main browser process.
|
||
|
||
The Lacros project aimed to separate the Linux processes and the software
|
||
releases between the browser and the OS shell by shipping the Chrome web browser
|
||
as a standalone app which could be updated independently of ChromeOS. Lacros
|
||
communicated between the Chrome browser and ChromeOS via an IPC interface called
|
||
crosapi. However, the Lacros project has been deprioritized and relevant code is
|
||
in the process of being deprecated and deleted.
|
||
|
||
### Definitions
|
||
|
||
- **Browser:** General term referring to a process with web browsing capabilities.
|
||
|
||
- **Ash:** The ChromeOS system UI. In this document, this term is used broadly
|
||
to include most of the non-browser UI features including the app launcher, the
|
||
system tray and notifications, the window manager, the system compositor, and
|
||
the login UI.
|
||
|
||
- **Lacros (deprecate, being deleted):** The ChromeOS-specific browser that does
|
||
not include Ash. This is similar to the Linux browser but with ChromeOS-
|
||
specific features and integrations.
|
||
|
||
- **Ash Browser:** The "classic" (non-Lacros) ChromeOS software that includes
|
||
Ash and the browser in one process.
|
||
|
||
- **Browser code:** Code required to build a browser. This includes
|
||
platform-specific integrations with the host OS rather than just the
|
||
cross-platform parts. For ChromeOS, this includes many important ChromeOS
|
||
browser features but does not include anything considered "Ash."
|
||
|
||
- **OS code:** Any ChromeOS-specific code that isn’t "browser code." This is
|
||
mostly Ash when referring to code in the Chromium repository.
|
||
|
||
- **Shared code:** Code used in both browser and OS code including `//base`,
|
||
`//mojo`, `//ui`, and some components.
|
||
|
||
## Desired state
|
||
|
||
_This section describes the long-term architectural goal rather than the current
|
||
state or the current requirements. See below for what to do for current work._
|
||
|
||
The desired end-state is that "browser code" (including ChromeOS-specific
|
||
browser features) and "OS code" have a clear separation. Communication between
|
||
these layers should be done using well-defined APIs. Function calls in the code
|
||
happen "down" the stack from the browser to the OS, and any calls "up" from the
|
||
OS to the browser happen via events, observers, and callbacks configured by the
|
||
browser layers.
|
||
|
||
Shared code like `//views` may have ChromeOS-specific parts and take
|
||
contributions from anyone, but the Browser and OS teams should agree that the
|
||
code is appropriate for such sharing.
|
||
|
||
In this desired state:
|
||
|
||
- The `//chrome` directory is for the implementation of the Chrome browser. It
|
||
should not have any OS code in it (for example, `//chrome/browser/ash` is
|
||
undesirable) and OS code should not call directly into `//chrome` code outside
|
||
of the above-mentioned callbacks.
|
||
|
||
- The `//content` directory is the API for building a web browser. Even though
|
||
Ash does use web technology for rendering many things, it is not itself a web
|
||
browser and there should be no OS code in this directory or calling directly
|
||
into it.
|
||
|
||
- Browser code should only call into OS code through well-defined APIs (e.g.,
|
||
extension APIs). This provides a conceptual separation between browser and OS
|
||
concerns.
|
||
|
||
Not all parts of the product fit neatly into the browser and OS layers, with
|
||
extensions and apps being big examples. How web page embedding should be done
|
||
from Ash is an area of active design and there is not currently good guidance
|
||
for this. In these less well-defined areas, work toward as clear a separation as
|
||
practical given the current state and the long-term requirements of that
|
||
component.
|
||
|
||
## Current policies
|
||
|
||
New features should be designed to adhere to the "desired state" as closely as
|
||
practical. However, it is currently not possible to implement all functionality
|
||
in Ash according to that state:
|
||
|
||
- Some functionality (e.g., the `Profile` or `BrowserContext` classes) are only
|
||
available in `//chrome` or `//content`, and there are no clear alternatives
|
||
to use.
|
||
|
||
- Legacy code still has significant `//chrome` dependencies and has not been
|
||
migrated away from this state.
|
||
|
||
Thus, we must be pragmatic about implementing Ash features in the meantime,
|
||
using the following guidance:
|
||
|
||
- Any new Ash functionality should add its core functionality outside of
|
||
`//chrome`.
|
||
- In this context, "core" functionality includes the primary business logic of
|
||
a feature.
|
||
- Guidance on where this code should exist:
|
||
- **Ash-only code which is not system UI:** `//chromeos/ash/components`
|
||
- **Ash-only system UI code:** `//ash`
|
||
- **Shared by both Ash and Lacros:**
|
||
- *UI code:* `//chromeos/ui`
|
||
- *Non-UI code:* `//chromeos/components`
|
||
- **NOTE:** Lacros is in the process of being deprecated. Do not add any
|
||
new Lacros code.
|
||
- **Shared between ChromeOS (i.e., ash-chrome) and other platforms:**
|
||
`//components`
|
||
|
||
- For code which must depend on `//chrome`, push logic down lower in the
|
||
dependency graph as much as possible, and only implement a thin wrapper in
|
||
`//chrome`. With this pattern, the code in `//chrome` is mostly "glue" or
|
||
initialization code, which will minimize the effort required in the future to
|
||
break these dependencies completely.
|
||
- Example 1: Phone Hub's [`BrowserTabsModelProvider`](https://source.chromium.org/chromium/chromium/src/+/main:chromeos/ash/components/phonehub/browser_tabs_model_provider.h;drc=2a153c1bc9f24cae375eee3cc875903866997918)
|
||
is declared in `//chromeos/ash/components` alongside related code logic, but
|
||
[`BrowserTabsModelProviderImpl`](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ash/phonehub/browser_tabs_model_provider_impl.h;drc=fe132eeb21687c455d695d6af346f15454828d01)
|
||
(in `//chrome`) implements the interface using a `//chrome` dependency.
|
||
- Example 2: Phone Hub's [`PhoneHubManagerImpl`](https://source.chromium.org/chromium/chromium/src/+/main:chromeos/ash/components/phonehub/phone_hub_manager_impl.h;drc=6b2b6f5aa258a1616fab24634c4e9477cfef5daf)
|
||
is declared in `//chromeos/ash/components` and has dependencies outside of
|
||
`//chrome`, but the concrete implementations of some of these components are
|
||
[`KeyedService`](https://source.chromium.org/chromium/chromium/src/+/main:components/keyed_service/core/keyed_service.h;drc=d23075f3066f6aab6fd5f8446ea5dde3ebff1097)s
|
||
requiring `//chrome`. In this case, [`PhoneHubManagerFactory`](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/ash/phonehub/phone_hub_manager_factory.h;drc=d23075f3066f6aab6fd5f8446ea5dde3ebff1097)
|
||
instantiates [`PhoneHubManagerImpl`](https://source.chromium.org/chromium/chromium/src/+/main:chromeos/ash/components/phonehub/phone_hub_manager_impl.h;drc=6b2b6f5aa258a1616fab24634c4e9477cfef5daf)
|
||
in `//chrome` (serving as a thin wrapper around the dependencies), but the
|
||
vast majority of logic is lower in the dependency graph.
|
||
|
||
- A few common `//chrome` dependencies that may be able to be broken easily:
|
||
- Instead of using [`ProfileKeyedServiceFactory`](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/profiles/profile_keyed_service_factory.h;drc=77a7a02b1822640e35cac72c0ddd7af7275eeb9b)
|
||
(in `//chrome`), consider using [`BrowserContextKeyedServiceFactory`](https://source.chromium.org/chromium/chromium/src/+/main:components/keyed_service/content/browser_context_keyed_service_factory.h;drc=371515598109bf869e1acbe5ea67813fc1a4cc3d)
|
||
(in `//components`) instead.
|
||
- Instead of using a [`Profile`](https://source.chromium.org/chromium/chromium/src/+/main:chrome/browser/profiles/profile.h;l=308-311;drc=3f4203f7dca2f7e804f30cfa783e24f90acd9059)
|
||
(in `//chrome`) to access user prefs, consider using
|
||
[`User::GetProfilePrefs()`](https://source.chromium.org/chromium/chromium/src/+/main:components/user_manager/user.h;l=127-131;drc=e49b1aec9585b0a527c24502dd4b0ee94b142c3c)
|
||
(in `//components`) instead.
|
||
|
||
- For any new code added in `//chrome/browser/ash`, a `DEPS` file must be created
|
||
which explicitly declares `//chrome` dependencies. People residing in
|
||
`//chrome/OWNERS` can help suggest alternatives to these dependencies if
|
||
possible when reviewing the code which adds this new `DEPS` file. See
|
||
[b/332805865](http://b/332805865) for more details.
|
||
|
||
If you need advice to help you make a decision regarding your design, please
|
||
reach out to ash-chrome-refactor@google.com for feedback.
|
||
|
||
## Path forward
|
||
|
||
The current policy aims to stop accumulating more undesirable OS/browser
|
||
dependencies while acknowledging there is a large amount of legacy code that
|
||
does not follow the guidelines. The team is moving toward the desired state
|
||
using the following approach outlined in go/ash-chrome-refactor:
|
||
|
||
- Ensure that all Ash code in `//chrome` is defined using granular BUILD.gn
|
||
files. Each directory should define its own build targets and list dependencies
|
||
explicitly.
|
||
- See https://crbug.com/335314438, https://crbug.com/351889236.
|
||
- ...more to come as the Ash //chrome Refactor makes progress.
|