# Data flow — 2dust/v2rayN

> Canonical page: https://codevetter.com/unpack/v2rayn/data-flow

# Data flow — 2dust/v2rayN

Scanned commit 28139853a8087d81e1ac7ffaf7013b937958f5d2 (2026-09-20). Generated by codevetter codevetter 1.12.0 on 2026-09-22.

Input boundaries are subscription URLs, share URIs (clipboard/QR/image), dialogs, and GitHub release APIs. Everything lands in the Config object (guiNConfig.json) or SQLite guiNDB.db entities via AppManager query helpers and ConfigHandler writers. The hot path to the network boundary is: ProfileItem + Config -> CoreConfigContextBuilder.Build/BuildAll -> immutable CoreConfigContext snapshot -> CoreConfigSingboxService/CoreConfigV2rayService -> config.json under binConfigs/ -> ProcessService spawning the core binary. Output boundaries are the spawned core's local SOCKS/API ports, the OS system proxy, and files under bin/, guiConfigs/, guiLogs/, guiTemps/, guiBackups/.
- Config is loaded at startup by ConfigHandler.LoadConfig from guiNConfig.json and normalized with ~40 defaults (inbound socks on 10808, TunModeItem MTU 9000, SpeedTestItem urls, mux/fragment/happy-eyeballs blocks, language from culture); SaveConfig writes it back and TaskManager re-saves every 20 minutes. — [v2rayN/ServiceLib/Handler/ConfigHandler.cs#L19-197](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Handler/ConfigHandler.cs#L19-L197) [v2rayN/ServiceLib/Manager/TaskManager.cs#L43-56](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Manager/TaskManager.cs#L43-L56)
- SQLiteHelper is the single owner of guiNDB.db, exposing sync CreateTable and async TableAsync/QueryAsync/ExecuteAsync; AppManager wraps it with typed queries (ProfileItems, SubItems, RoutingItems, DNSItems, ProfileModels join query with subRemarks). — [v2rayN/ServiceLib/Helper/SqliteHelper.cs#L14-88](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Helper/SqliteHelper.cs#L14-L88) [v2rayN/ServiceLib/Manager/AppManager.cs#L175-230](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Manager/AppManager.cs#L175-L230)
- Subscription text flows: DownloadService.TryDownloadString (HttpClient with proxy fallback to Downloader library) -> optional base64 decode -> ConfigHandler.AddBatchServers -> FmtHandler.Resolve per line -> ProfileItem rows tagged with the SubItem id; the sub's UpdateTime is stamped by TaskManager for the auto-update interval. — [v2rayN/ServiceLib/Handler/SubscriptionHandler.cs#L102-229](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Handler/SubscriptionHandler.cs#L102-L229) [v2rayN/ServiceLib/Services/DownloadService.cs#L195-251](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Services/DownloadService.cs#L195-L251) [v2rayN/ServiceLib/Handler/ConfigHandler.cs#L2037-2135](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Handler/ConfigHandler.cs#L2037-L2135)
- CoreConfigContextBuilder.Build assembles an immutable CoreConfigContext: resolves the effective node (possibly wrapping it in a subscription prev/next ProxyChain via BuildSubscriptionChainNodeAsync), registers routing-rule outbound nodes into AllProxiesMap, validates TunModeItem.RouteExcludeAddress CIDRs with IPNetwork2, and snapshots DNS/routing/template items from SQLite. — [v2rayN/ServiceLib/Handler/Builder/CoreConfigContextBuilder.cs#L34-138](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Handler/Builder/CoreConfigContextBuilder.cs#L34-L138) [v2rayN/ServiceLib/Handler/Builder/CoreConfigContextBuilder.cs#L258-315](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Handler/Builder/CoreConfigContextBuilder.cs#L258-L315)
- BuildAll optionally produces a second 'pre-socks' context (BuildPreSocksIfNeeded) used for TUN protection or upstream chaining; when present the main context gets IsTunEnabled=false and merged ProtectDomainList/ProtectCoreTypeList so the generated config and launch mode always agree. — [v2rayN/ServiceLib/Handler/Builder/CoreConfigContextBuilder.cs#L145-214](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Handler/Builder/CoreConfigContextBuilder.cs#L145-L214)
- CoreConfigHandler.GenerateClientConfig dispatches on node type: Custom -> file copy (or CoreConfigClashService for mihomo mixin), RunCoreType==sing_box -> CoreConfigSingboxService.GenerateClientConfigContent, otherwise CoreConfigV2rayService; the result JSON is written to binConfigs/config.json (or configPre.json for the pre-socks core). — [v2rayN/ServiceLib/Handler/CoreConfigHandler.cs#L10-42](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Handler/CoreConfigHandler.cs#L10-L42) [v2rayN/ServiceLib/Manager/CoreManager.cs#L74-104](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Manager/CoreManager.cs#L74-L104) [v2rayN/ServiceLib/Global.cs#L13-15](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Global.cs#L13-L15)
- Per-core config generation is decomposed into services per concern: Singbox = Log/Inbound/Outbound/Routing/Dns/Ruleset/Statistic/ConfigTemplate services; V2ray = Log/Inbound/Outbound/Routing/Dns/Balancer/Statistic/ConfigTemplate services — each mutating a shared config model rooted at Models/CoreConfigs. — [v2rayN/ServiceLib/Services/CoreConfig/Singbox/CoreConfigSingboxService.cs](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Services/CoreConfig/Singbox/CoreConfigSingboxService.cs) [v2rayN/ServiceLib/Services/CoreConfig/V2ray/CoreConfigV2rayService.cs](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Services/CoreConfig/V2ray/CoreConfigV2rayService.cs) [v2rayN/ServiceLib/Models/CoreConfigs/V2rayConfig.cs](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Models/CoreConfigs/V2rayConfig.cs)
- Outbound traffic routing decisions come from RoutingItem.RuleSet JSON deserialized to List<RulesItem>; rules whose OutboundTag is not a built-in tag are resolved by remarks to ProfileItems and injected into AllProxiesMap as 'remark:<tag>' entries. — [v2rayN/ServiceLib/Handler/Builder/CoreConfigContextBuilder.cs#L63-98](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Handler/Builder/CoreConfigContextBuilder.cs#L63-L98)
- All outbound HTTP(S) fetching funnels through DownloadService: it builds a WebProxy socks5://127.0.0.1:{localPort} only after SocksPortCheck confirms the local core answers a SOCKS5 greeting, applies CertPemManager certificate chain policy when configured, sets Basic auth from URL userinfo, and uses short connect timeouts (5s direct / 10s proxy). — [v2rayN/ServiceLib/Services/DownloadService.cs#L256-427](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Services/DownloadService.cs#L256-L427) [v2rayN/ServiceLib/Manager/CertPemManager.cs](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Manager/CertPemManager.cs)
- Statistics flow: StatisticsXrayService/StatisticsSingboxService poll the running cores -> UpdateServerStatHandler aggregates into ServerStatItem rows -> AppEvents.DispatcherStatisticsRequested pushes ServerSpeedItem to the status bar; SaveTo persists on exit and CloneServerStatItem carries stats across subscription refreshes. — [v2rayN/ServiceLib/Manager/StatisticsManager.cs#L18-98](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Manager/StatisticsManager.cs#L18-L98) [v2rayN/ServiceLib/Handler/ConfigHandler.cs#L2120-2132](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Handler/ConfigHandler.cs#L2120-L2132)
- The local API ports derive from the socks inbound localPort (default 10808): AppManager.GetLocalPort(protocol) = localPort + (int)EInboundProtocol, with StatePort/StatePort2 lazily reassigned to free ports via Utils.GetFreePort. — [v2rayN/ServiceLib/Manager/AppManager.cs#L15-31](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Manager/AppManager.cs#L15-L31) [v2rayN/ServiceLib/Manager/AppManager.cs#L165-169](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Manager/AppManager.cs#L165-L169)
- Self-update flow terminates in AmazTool: UpdateService downloads the release zip to guiTemps, the app launches AmazTool with the URL-encoded path, and UpgradeApp.Upgrade kills running v2rayN processes, renames its own exe to .tmp, extracts the zip (skipping existing bin/ payloads), then restarts via Utils.StartV2RayN. — [v2rayN/AmazTool/UpgradeApp.cs#L9-107](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/AmazTool/UpgradeApp.cs#L9-L107) [v2rayN/AmazTool/Program.cs#L39-44](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/AmazTool/Program.cs#L39-L44) [v2rayN/ServiceLib/Services/UpdateService.cs#L9-47](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Services/UpdateService.cs#L9-L47)
- File-system layout under StartupPath(): bin/ holds core binaries and geo files (per-core subdirs by lowercase CoreType), binConfigs/ holds generated config.json/configPre.json/configTest*.json, guiConfigs/ holds guiNConfig.json + guiNDB.db + pac.txt, guiTemps/ downloads, guiBackups/ backups, guiLogs/ NLog output. — [v2rayN/ServiceLib/Common/Utils.cs#L1152-1288](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Common/Utils.cs#L1152-L1288) [v2rayN/ServiceLib/Manager/TaskManager.cs#L61-65](https://github.com/2dust/v2rayN/blob/28139853a8087d81e1ac7ffaf7013b937958f5d2/v2rayN/ServiceLib/Manager/TaskManager.cs#L61-L65)

Every claim links to its cited files at the pinned commit. Citations identify source evidence; they do not establish runtime correctness. Independent CodeVetter scan — not reviewed by upstream maintainers.

## Public product links

- [CodeVetter](https://codevetter.com/)
- [Download](https://codevetter.com/download)
- [Documentation](https://codevetter.com/docs/)
- [Source](https://github.com/Codevetter/codevetter)
