bare-browser README

The project's README from github.com/BareBrowser/bare-browser. As one markdown file: README.md.

Bare Browser

Shaped by the community

Extensions. Privacy. Freedom

barebrowser.org


Bare is a de-Googled Chromium build for Android, designed to give you more privacy, control and freedom on the web. It strips Google tracking, telemetry and AI integration while keeping powerful features like browser extensions and uBlock Origin. Bare also adds background video playback, the ability to save media from sites that normally block it, support for choosing your preferred download manager, and much more.

It is a patch series rather than a fork: 99 patches against one pinned revision of Chromium Desktop Android, so what this repository holds is exactly the difference between stock Chromium and Bare, and nothing else.

Built and used on a Pixel 10 Pro XL. Not affiliated with Google or the Chromium project.

What you get

Screenshots

Screenshot 1 Screenshot 2
Screenshot 3 Screenshot 4
Screenshot 5 Screenshot 6

Support the project

Bare is one person and one phone. There is no company behind it, nothing in the browser sells you anything, and there is nothing to upsell you to later, which is rather the point of it.

If it is useful to you, you can buy me a coffee. Entirely optional. It buys build hours and a second device to test on, and it changes nothing about the browser either way.

Buy me a coffee

Why

Chromium's Desktop Android build supports real browser extensions, which mobile Chrome does not. That makes it a genuinely better browser to live in, but it still ships Google's AI stack, phones home on a schedule, and hands your links to other apps. Bare fixes that as a patch series rather than a fork, so every change stays readable and reviewable.

What the patches do

Ninety-one patches against one pinned Chromium revision: crash fixes, the extensions toolbar on phone layouts, every Google callback and AI surface removed, and the features Bare adds on top.

The full list, patch by patch, is in docs/patches.md along with what is removed by build flag instead of by patch, and what is deliberately kept.

Network behaviour

Measured on a Pixel 3 running Android 12 and an Android 17 emulator, by watching the sockets opened under Bare's own uid on a wiped profile. What follows is what was actually observed, not what was intended.

On a second and later start, with an established profile, one host is contacted without being asked: update.googleapis.com. That is Chromium's component updater. It is kept deliberately, because the components left registered are the ones that carry security or web compatibility:

Component Why it stays
CRLSet certificate revocation
PKIMetadata Certificate Transparency
SSLErrorAssistant quality of the TLS interstitial
FileTypePolicies download danger classification
OriginTrials web compatibility
Widevine DRM playback
SafetyTips, CrowdDeny lookalike-domain and abusive-notification lists, applied locally

Registration tells Google an install exists, along with a component id, a version, an install date and a cohort. Twelve other components were dropped in patch 0085 for buying nothing here: the Privacy Sandbox set, Google's omnibox suggestion model, the optimization-hints feed, shopping and checkout heuristics, on-device AI history strings, and two Safe Browsing lists that nothing can consult. Three more, ActorSafetyLists, Indigo and CaptchaProvider, are still registered because their purpose is not clear enough in the tree to remove them confidently.

On the first run of a fresh profile there is more, and almost all of it is uBlock Origin fetching the filter lists it ships enabled, from the list maintainers and their CDNs rather than from Google. That happens once and then on the extension's own schedule.

The update check contacts GitHub, and only after the welcome screen has been completed and an update preference stored. It is at most one request a day, to a public release feed, sending User-Agent: Bare/<version> and nothing else: no identifier, no cookies, no version in the request. Choosing manual means nothing leaves the device until the Check for updates row is tapped.

What no longer happens, each verified by re-running the same capture:

Traffic from Android itself and from Google Play Services is separate from all of this and is not affected by anything Bare does.

Safe Browsing does not work in this build, and no longer claims to. Chromium Android performs lookups through a handler that Google injects in its own build and that no public build has. The settings, the Safety Hub module and the promotional cards all described protection that never ran, so patch 0080 removed them. Bare shows no phishing or malware interstitial. Treat unknown links with the caution you would give a browser with no such feature, because that is what this is.

Requirements

Builds run in an x86-64 Ubuntu 22.04 container. On Apple Silicon this means Rosetta emulation, and a full build takes hours.

Build it yourself

Everything runs in the container. The Chromium checkout stays in its volume, because building from a macOS bind mount is slow and unreliable; only small files cross to the host, through exchange/, which is the one directory shared with the container.

1. Start the container.

./builder.sh build
./builder.sh start

2. Put what the build needs where the container can see it.

cp -R patches exchange/
cp third_party/ublock_origin/uBlockOrigin-1.73.0.crx exchange/
tools/version.py gn arm64 > exchange/version-args.gn

3. Fetch Chromium. Inside the container (./builder.sh shell). depot_tools is on the PATH but not installed, so clone it first. This part is Chromium's own procedure rather than anything specific to Bare. See the upstream Android build instructions if a step needs explaining. Expect hours and about 50 GB.

git clone https://chromium.googlesource.com/chromium/tools/depot_tools.git ~/depot_tools
mkdir -p /work/chromium && cd /work/chromium
fetch --nohooks android
cd src
git checkout 945b5115
gclient sync -D --force --reset
./build/install-build-deps.sh --android

4. Apply the series, and drop in the extension. uBlock Origin is kept out of the patches because a 4 MB signed binary as base64 would be unreviewable, so it is copied in separately. Without it the build fails at packaging.

git am /exchange/patches/*.patch
mkdir -p chrome/browser/resources/bare
cp /exchange/uBlockOrigin-1.73.0.crx chrome/browser/resources/bare/ublock_origin.crx

5. Configure. This is the complete configuration the published release was built with, nothing omitted:

target_os = "android"
target_cpu = "arm64"
is_desktop_android = true
is_official_build = true
is_debug = false
is_java_debug = false
is_component_build = false
dcheck_always_on = false
android_static_analysis = "off"
symbol_level = 0
blink_symbol_level = 0
v8_symbol_level = 0
use_remoteexec = false
use_reclient = false

proprietary_codecs = true
ffmpeg_branding = "Chrome"

use_mlkit_for_aicore = false
enable_glic_internal_resources = false
enable_reporting = false
enable_service_discovery = false
enable_mdns = false
enable_arcore = false
enable_cardboard = false
enable_openxr = false

chrome_public_manifest_package = "org.barebrowser"
android_override_version_code = "801000035"
android_override_version_name = "1.0.0-alpha.2"

The last two lines are what tools/version.py gn arm64 emits, and they matter: they are written into the manifest, so a build without them will not match the release.

The 32-bit build differs in exactly three lines: target_cpu = "arm", the version code 801000020 that tools/version.py gn arm emits, and clang_use_default_sample_profile = false, which stops GN demanding an AFDO profile this checkout never syncs.

mkdir -p out/Bare
$EDITOR out/Bare/args.gn          # paste the block above
gn gen out/Bare
autoninja -C out/Bare chrome_public_apk

6. Compare. Your APK will not be byte-identical to the published one, because that one carries a signature only its key can produce. Everything else should match:

tools/apk-content-hash.py out/Bare/apks/ChromePublic.apk Bare-1.0.0-alpha.1.apk

See BUILDING.md for the rest of the workflow, including versioning and how releases are signed.

Verifying a build

Three questions, and they have different answers.

Is this the file that was published? Compare its SHA-256 against the one on the release page. That catches a truncated or tampered download and nothing else: the hash is published by the same person as the file, so on its own it proves nothing about where the file came from.

Is it genuinely Bare? Check who signed it. Nothing signed by any other key is Bare.

apksigner verify --print-certs Bare-1.0.0-alpha.1.apk
SHA-256  ae:2a:0e:7f:b7:a1:32:ec:51:7d:26:a8:e7:c8:3d:27
         5e:83:74:7b:0a:77:7d:4a:42:22:5b:1d:34:32:71:a0
subject  CN=Bare Browser, O=Bare Browser, OU=Release
key      RSA 4096

Releases before v1.0.0-alpha.1 were signed with Chromium's debug key, which is checked into Chromium's tree and therefore public. Anyone can build an APK that installs as an update over one of those. If you are running a Chromium Extend build, uninstall it rather than updating; a Bare release cannot replace it in place anyway, because the signing identity deliberately changed.

Can you rebuild it yourself? Yes, and that is the only one of the three that proves where a binary came from. The signature is deliberately not reproducible, since nobody but the key holder can produce it, but everything else is. Follow Build it yourself exactly, including the version arguments, then compare:

tools/apk-content-hash.py out/Bare/apks/ChromePublic.apk Bare-1.0.0-alpha.1.apk

It hashes every entry except the signature, so two builds of the same source agree whoever signed them. What has been measured, and what has not.

Known limitations

Not done yet

Each has an exact file and line reference in docs/stage-1-2.md:

bare-browser (BareBrowser/bare-browser)

Searching Database…

这是什么?Bare 是一个面向 Android 的去 Google 化 Chromium 构建,它移除了 Google 的追踪、遥测和 AI 集成,同时让浏览器扩展和 uBlock Origin 保持可用,并添加了后台视频播放、媒体保存等功能。
Bare 是 Chromium 的 fork,还是别的什么?它是一组补丁,不是 fork:在一个锁定的 Chromium 桌面 Android 构建修订版上应用 99 个补丁,因此仓库里只包含原版 Chromium 与 Bare 之间的差异。
怎么把 Bare 装到我的手机上?从发布页面下载已签名的 APK 并校验其 SHA-256 哈希,或者在提供的 Docker 容器内自行从源码构建:把补丁系列应用到一个锁定的 Chromium 检出上。
强制所有链接都留在浏览器内会导致问题吗?会——让 http(s) 导航留在 Bare 内而不交给其他应用的补丁被描述为简单粗暴,因此一些预期由其他应用接管的 OAuth 流程和深度链接无法再使用。
Bare 到底会不会回传信息?仍有两件事会自行连接服务器:一是 Chromium 的组件更新器会为 CRLSet 和 Widevine 等安全相关组件联系 update.googleapis.com,二是 Bare 自身对 GitHub 的更新检查,该检查每天最多一次,且只发送一个简单的 User-Agent 字符串。
为什么 Bare 保留 uBlock Origin 的完整版,而不是 Manifest V3 Lite 版?Bare 的桌面 Android 基线仍支持 Manifest V2,因此它完全按照作者发布的形式附带完整版 uBlock Origin,而不是大多数移动 Chromium 浏览器被迫使用的功能受限的 Manifest V3 Lite 版本。
如何验证下载的 APK 是真正的 Bare 且未被篡改?把 APK 的 SHA-256 与发布页面对照,确认它由 Bare 的 RSA 4096 发布密钥签名(v1.0.0-alpha.1 之前用的是 Chromium 的公开调试密钥,两者身份不同),或者自行重新构建并比较除签名之外的所有内容。
Bare 基于哪个 Chromium 版本和什么设备构建?它针对 arm64 桌面 Android 为 Chromium 153.0.7999.0(commit 945b5115)打补丁,并在 Pixel 10 Pro XL 上持续构建和测试。
Size
22.6 MB
Stars
576
Age
2mo
Commits · 90 Days