vpnhide/CONTRIBUTING.md
Danila Gornushko 1582efa067
docs: refresh installation/backend docs + 1.0.0 screenshots (#224)
* docs: refresh installation and backend docs

* docs: fix review findings and add KPM to update-json

Cross-checked the docs refresh against the code and corrected:
- protocol.md: config parser is vpnhide_parse_config (not the legacy
  vpnhide_parse_target_uids); path is kmod/shared/vpnhide_logic.h; drop the
  unverified 0x2026 KPatch-Next marker (activator drives it via the CLI).
- zygisk/README: module declares Zygisk API v2 (not v5); add the recv hook
  row and the if<N> renamed-netdev match.
- README (en/ru): live-check counts are 13 native / 12 Java; Diagnostics is
  under Settings, not a tab; mention the Statistics tab; note KPM beta parity.
- detection-vectors: KPM host-route helper is kpm_is_public_host_route{4,6};
  restore CONFIG_KPROBES and the Zygisk qualifiers; codegen renders four targets.
- storage.md: legacy files are no longer user-managed (migration inputs), not
  'gone'. CLAUDE.md: activator has four bins (kmod/kpm/zygisk/ports).
- development/ROADMAP/kmod/lsposed/portshide READMEs + AGENTS.md: assorted
  accuracy fixes (KPM needs a KernelPatch runtime, per-KMI kmod zip name, etc.).
- CONTRIBUTING.md: clang-format uses scripts/clang-format-c.sh (covers KPM src).
- portshide customize.sh: 'Hiding -> Ports' (renamed tab).
- update-json.sh: emit update-kpm.json so KPM gets Magisk/KSU update checks.

* docs: correct diagnostics check count (25, not 26 vectors)

* docs: refresh README screenshots for the 1.0.0 UI

Replace the v0.5.3-era screenshots (old per-tab Protection UI) with a
new 1.0.0 set: VPN-hidden dashboard, the unified Hiding list with
J/N/A/P, the Statistics tab + per-hook breakdown, per-app hook selection,
diagnostics, settings, and the community screen. Extra shots
(statistics-apps, settings-advanced, diagnostics-java, settings-developer)
are included for the release notes.

* docs: fix the how-it-works layer breakdown

The old 'Layer 3 — additional app-level controls' bucket was wrong:
interface hiding is what Layers 1+2 already do, app-hiding is done by the
LSPosed/Java layer (system_server PackageManager hooks), and ports is a
separate module. Fold app-hiding into Layer 1 (LSPosed) and make Layer 3
the standalone portshide module.

* docs: conceptual-coherence pass on the 5 core docs

Second review pass, this time for architectural coherence rather than
code-facts. Fixes:
- README (en/ru): 'What vpnhide hides' stopped reifying interface hiding
  as a standalone 'layer'/'role' and now ties the three hiding goals to
  the four J/N/A/P roles (interface = Java + Native, toggled independently)
- README (ru): add the KPM-beta hook-parity caveat (parity with the EN side)
- protocol.md: app-hiding is a normal lsposed mask bit, not a separate
  'package/observer records' entry in the §6 profile table
- detection-vectors.md: a complete install is two components (native + lsposed),
  not 'two roles'; name both lsposed jobs
- storage.md: scope the text protocol to the config wire (LSPosed reuses the
  format for its state file); 'by function' not 'by role'; note the Apps role
  shares the same resolver; heading no longer files ports under 'Native layer'
2026-07-02 00:03:17 +03:00

2.3 KiB

Contributing to vpnhide

Thanks for your interest. This file covers the contribution process; for build and setup instructions see docs/development.md.

Before you start

  • For non-trivial changes, open an issue first to discuss the approach.
  • Make sure your change builds locally and passes the CI lints listed in docs/development.md.

Commits

Use conventional-style prefixes, matching the existing history:

  • fix: — bug fix
  • feat: — new feature
  • refactor: — code change without behaviour change
  • docs: — documentation only
  • chore: — tooling, release, CI, build
  • ci: — CI-only changes

Scope the prefix where useful: fix(zygisk): …, feat(lsposed): …, fix(kmod): ….

Keep messages focused on why, not what — the diff already shows what changed.

Changelog entry (required for user-visible changes)

Before opening a PR, add a changelog entry:

./scripts/changelog.py <type> "<EN text>" "<RU text>"
# types: added | changed | fixed | removed | deprecated | security

This writes a new Markdown fragment to changelog.d/. That's the only file changed — CHANGELOG.md is regenerated only at release time, which is what keeps concurrent PRs from conflicting. Commit just the fragment alongside your code change. Run ./scripts/preview-changelog.py to see the pending entries together.

Skip the entry for internal refactors with no behaviour change, docs-only, CI-only, and test-only changes.

See docs/changelog.md for the full changelog workflow.

Pull requests

  • Target the main branch.
  • Keep PRs focused — one logical change per PR.
  • Include a "why" in the PR description, and a brief "Testing" section if you verified anything manually that CI doesn't cover (hardware testing, specific device models, edge cases).
  • CI must pass before merge.

Code style

All style is enforced by CI — run the checks locally before pushing:

  • Rust: cargo fmt + cargo clippy -- -D warnings
  • C: scripts/clang-format-c.sh --check (all tracked kmod C sources)
  • Kotlin: ktlint
  • Android: ./gradlew :app:lint

License

By contributing, you agree that your contributions will be licensed under the MIT License that covers the project.