# net-merge/android architecture

> Architecture diagram of the GitHub repository net-merge/android, generated by GitDiagram from its file tree, README and a sample of source files (last updated 2026-11-09). It is an AI-made overview: check details against the source.

- Interactive diagram: https://gitdiagram.com/net-merge/android
- Repository: https://github.com/net-merge/android

## Overview

net-merge is an Android local VPN that keeps Wi-Fi and mobile data available, then distributes separate app connections across them. The workflow runs from the power control or Quick Settings tile through the VPN service, which tracks networks and sends their details to the Go engine; the engine forwards traffic and reports per-network stats for the UI. The graph includes the documented VPN, balancing, probing, and socket-binding stages. Some Go internal call relationships are not shown because the sampled excerpts do not establish them.

Main entry points: [`app/src/main/java/org/netmerge/android/MergeVpnService.kt`](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/MergeVpnService.kt) (VPN service), [`app/src/main/java/org/netmerge/android/Engine.kt`](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/Engine.kt) (Shared app state), [`golib/netmerge/netmerge.go`](https://github.com/net-merge/android/blob/main/golib/netmerge/netmerge.go) (Go mobile API), [`app/src/main/java/org/netmerge/android/MainActivity.kt`](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/MainActivity.kt) (Main activity)

## Diagram (Mermaid)

```mermaid
flowchart TD

subgraph group_controls["App controls"]
  node_main_activity["Main activity<br/>[MainActivity.kt]"]
  node_quick_tile["Quick Settings tile"]
  node_main_screen["Main screen<br/>[MainScreen.kt]"]
  node_power_button["Power button<br/>[PowerButton.kt]"]
  node_live_chart["Live chart<br/>[LiveChart.kt]"]
end

subgraph group_android_runtime["Android runtime"]
  node_vpn_service["VPN service<br/>[MergeVpnService.kt]"]
  node_network_tracker["Network tracker<br/>[NetworkTracker.kt]"]
  node_vpn_interface["VPN interface<br/>[MergeVpnService.kt]"]
end

subgraph group_engine_api["Engine interface"]
  node_mobile_api["Go mobile API<br/>[netmerge.go]"]
end

subgraph group_traffic_engine["Traffic engine"]
  node_tun_forwarder["TUN forwarding<br/>[forward.go]"]
  node_flow_balancer["Flow balancer<br/>[balancer.go]"]
  node_flow_scheduler["Flow scheduler<br/>[sched.go]"]
  node_internet_probe["Internet probes<br/>[probe.go]"]
  node_flow_connections["Flow connections<br/>[flowconn.go]"]
  node_socks5["SOCKS5 handling<br/>[socks5.go]"]
  node_network_egress["Network-bound sockets<br/>[egress_android.go]"]
end

subgraph group_telemetry["Status and telemetry"]
  node_shared_state["Shared app state<br/>[Engine.kt]"]
  node_stats_parser["Stats parser<br/>[Stats.kt]"]
end

node_user(("User"))

node_user -->|"opens app"| node_main_activity
node_user -->|"toggles merging"| node_quick_tile
node_main_activity -->|"renders"| node_main_screen
node_main_screen -->|"renders"| node_power_button
node_main_screen -->|"renders"| node_live_chart
node_main_activity -->|"starts or stops"| node_vpn_service
node_quick_tile -->|"starts or stops"| node_vpn_service
node_vpn_service -->|"starts tracking"| node_network_tracker
node_network_tracker -->|"reports networks"| node_vpn_service
node_vpn_service -->|"establishes"| node_vpn_interface
node_vpn_service -->|"sets networks"| node_mobile_api
node_vpn_service -->|"updates phase"| node_shared_state
node_shared_state -->|"sets balancing mode"| node_mobile_api
node_shared_state -->|"reads engine stats"| node_mobile_api
node_mobile_api -->|"returns stats"| node_shared_state
node_shared_state -->|"parses stats"| node_stats_parser
node_main_activity -->|"observes state"| node_shared_state
node_main_screen -->|"displays state"| node_shared_state
node_mobile_api -->|"starts TUN forwarding"| node_tun_forwarder
node_mobile_api -->|"updates networks and ticks"| node_flow_scheduler
node_tun_forwarder -.->|"forwards through"| node_flow_balancer
node_flow_balancer -.->|"selects flows"| node_flow_scheduler
node_flow_scheduler -.->|"checks links"| node_internet_probe
node_flow_balancer -.->|"manages flows"| node_flow_connections
node_flow_connections -.->|"handles proxy flows"| node_socks5
node_flow_connections -.->|"opens bound sockets"| node_network_egress

click node_main_activity "https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/MainActivity.kt"
click node_quick_tile "https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/MergeTileService.kt"
click node_main_screen "https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/ui/MainScreen.kt"
click node_power_button "https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/ui/PowerButton.kt"
click node_live_chart "https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/ui/LiveChart.kt"
click node_vpn_service "https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/MergeVpnService.kt"
click node_network_tracker "https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/NetworkTracker.kt"
click node_vpn_interface "https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/MergeVpnService.kt"
click node_shared_state "https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/Engine.kt"
click node_stats_parser "https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/Stats.kt"
click node_mobile_api "https://github.com/net-merge/android/blob/main/golib/netmerge/netmerge.go"
click node_tun_forwarder "https://github.com/net-merge/android/blob/main/golib/internal/tun/forward.go"
click node_flow_balancer "https://github.com/net-merge/android/blob/main/golib/internal/engine/balancer.go"
click node_flow_scheduler "https://github.com/net-merge/android/blob/main/golib/internal/engine/sched.go"
click node_internet_probe "https://github.com/net-merge/android/blob/main/golib/internal/engine/probe.go"
click node_flow_connections "https://github.com/net-merge/android/blob/main/golib/internal/engine/flowconn.go"
click node_socks5 "https://github.com/net-merge/android/blob/main/golib/internal/engine/socks5.go"
click node_network_egress "https://github.com/net-merge/android/blob/main/golib/internal/nics/egress_android.go"

classDef toneNeutral fill:#f8fafc,stroke:#334155,stroke-width:1.5px,color:#0f172a
classDef toneBlue fill:#dbeafe,stroke:#2563eb,stroke-width:1.5px,color:#172554
classDef toneAmber fill:#fef3c7,stroke:#d97706,stroke-width:1.5px,color:#78350f
classDef toneMint fill:#dcfce7,stroke:#16a34a,stroke-width:1.5px,color:#14532d
classDef toneRose fill:#ffe4e6,stroke:#e11d48,stroke-width:1.5px,color:#881337
classDef toneIndigo fill:#e0e7ff,stroke:#4f46e5,stroke-width:1.5px,color:#312e81
classDef toneTeal fill:#ccfbf1,stroke:#0f766e,stroke-width:1.5px,color:#134e4a
class node_main_activity,node_quick_tile,node_main_screen,node_power_button,node_live_chart,node_user toneBlue
class node_vpn_service,node_network_tracker,node_vpn_interface toneAmber
class node_mobile_api toneMint
class node_tun_forwarder,node_flow_balancer,node_flow_scheduler,node_internet_probe,node_flow_connections,node_socks5,node_network_egress toneRose
class node_shared_state,node_stats_parser toneIndigo
```

## Components

### App controls

- [Main activity](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/MainActivity.kt): `app/src/main/java/org/netmerge/android/MainActivity.kt`
- [Quick Settings tile](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/MergeTileService.kt): `app/src/main/java/org/netmerge/android/MergeTileService.kt`
- [Main screen](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/ui/MainScreen.kt): `app/src/main/java/org/netmerge/android/ui/MainScreen.kt`
- [Power button](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/ui/PowerButton.kt): `app/src/main/java/org/netmerge/android/ui/PowerButton.kt`
- [Live chart](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/ui/LiveChart.kt): `app/src/main/java/org/netmerge/android/ui/LiveChart.kt`

### Android runtime

- [VPN service](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/MergeVpnService.kt): `app/src/main/java/org/netmerge/android/MergeVpnService.kt`
- [Network tracker](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/NetworkTracker.kt): `app/src/main/java/org/netmerge/android/NetworkTracker.kt`
- [VPN interface](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/MergeVpnService.kt): `app/src/main/java/org/netmerge/android/MergeVpnService.kt`

### Engine interface

- [Go mobile API](https://github.com/net-merge/android/blob/main/golib/netmerge/netmerge.go): `golib/netmerge/netmerge.go`

### Traffic engine

- [TUN forwarding](https://github.com/net-merge/android/blob/main/golib/internal/tun/forward.go): `golib/internal/tun/forward.go`
- [Flow balancer](https://github.com/net-merge/android/blob/main/golib/internal/engine/balancer.go): `golib/internal/engine/balancer.go`
- [Flow scheduler](https://github.com/net-merge/android/blob/main/golib/internal/engine/sched.go): `golib/internal/engine/sched.go`
- [Internet probes](https://github.com/net-merge/android/blob/main/golib/internal/engine/probe.go): `golib/internal/engine/probe.go`
- [Flow connections](https://github.com/net-merge/android/blob/main/golib/internal/engine/flowconn.go): `golib/internal/engine/flowconn.go`
- [SOCKS5 handling](https://github.com/net-merge/android/blob/main/golib/internal/engine/socks5.go): `golib/internal/engine/socks5.go`
- [Network-bound sockets](https://github.com/net-merge/android/blob/main/golib/internal/nics/egress_android.go): `golib/internal/nics/egress_android.go`

### Status and telemetry

- [Shared app state](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/Engine.kt): `app/src/main/java/org/netmerge/android/Engine.kt`
- [Stats parser](https://github.com/net-merge/android/blob/main/app/src/main/java/org/netmerge/android/Stats.kt): `app/src/main/java/org/netmerge/android/Stats.kt`

### Other components

- **User**

## Connections

- User → Main activity: opens app (evidence: `README.md`)
- User → Quick Settings tile: toggles merging (evidence: `README.md`)
- Main activity → Main screen: renders (evidence: `app/src/main/java/org/netmerge/android/MainActivity.kt`)
- Main screen → Power button: renders (evidence: `app/src/main/java/org/netmerge/android/ui/MainScreen.kt`)
- Main screen → Live chart: renders (evidence: `app/src/main/java/org/netmerge/android/ui/MainScreen.kt`)
- Main activity → VPN service: starts or stops (evidence: `app/src/main/java/org/netmerge/android/MainActivity.kt`)
- Quick Settings tile → VPN service: starts or stops (evidence: `app/src/main/java/org/netmerge/android/MergeTileService.kt`)
- VPN service → Network tracker: starts tracking (evidence: `app/src/main/java/org/netmerge/android/MergeVpnService.kt`)
- Network tracker → VPN service: reports networks (evidence: `app/src/main/java/org/netmerge/android/MergeVpnService.kt`)
- VPN service → VPN interface: establishes (evidence: `app/src/main/java/org/netmerge/android/MergeVpnService.kt`)
- VPN service → Go mobile API: sets networks (evidence: `app/src/main/java/org/netmerge/android/MergeVpnService.kt`)
- VPN service → Shared app state: updates phase (evidence: `app/src/main/java/org/netmerge/android/MergeVpnService.kt`)
- Shared app state → Go mobile API: sets balancing mode (evidence: `app/src/main/java/org/netmerge/android/Engine.kt`)
- Shared app state → Go mobile API: reads engine stats (evidence: `app/src/main/java/org/netmerge/android/Engine.kt`)
- Go mobile API → Shared app state: returns stats (evidence: `app/src/main/java/org/netmerge/android/Engine.kt`)
- Shared app state → Stats parser: parses stats (evidence: `app/src/main/java/org/netmerge/android/Engine.kt`)
- Main activity → Shared app state: observes state (evidence: `app/src/main/java/org/netmerge/android/MainActivity.kt`)
- Main screen → Shared app state: displays state (evidence: `app/src/main/java/org/netmerge/android/ui/MainScreen.kt`)
- Go mobile API → TUN forwarding: starts TUN forwarding (evidence: `golib/netmerge/netmerge.go`)
- Go mobile API → Flow scheduler: updates networks and ticks (evidence: `golib/netmerge/netmerge.go`)
- TUN forwarding → Flow balancer: forwards through (evidence: `README.md`)
- Flow balancer → Flow scheduler: selects flows
- Flow scheduler → Internet probes: checks links
- Flow balancer → Flow connections: manages flows
- Flow connections → SOCKS5 handling: handles proxy flows
- Flow connections → Network-bound sockets: opens bound sockets (evidence: `README.md`)
