v2rayA/v2rayA · error

core version mismatch

Error message

core version mismatch

What it means

CoreVersionMismatchError is the sentinel error (wrapped with %w) signaling that the v2raya_core binary's version does not match the v2rayA service version. It exists so callers can detect a mismatch specifically with errors.Is, even though the concrete message adds versions. In release builds both binaries come from the same source tree so versions must match exactly; dev builds ('debug','unstable') are exempt.

Source

Thrown at service/kernel/v2ray/service/service.go:16

package service

import (
	"bytes"
	"fmt"
	"os/exec"
	"strings"

	"github.com/v2rayA/v2rayA/common"
	"github.com/v2rayA/v2rayA/conf"
	"github.com/v2rayA/v2rayA/kernel/iptables"
	"github.com/v2rayA/v2rayA/kernel/v2ray/asset"
	"github.com/v2rayA/v2rayA/kernel/v2ray/where"
)

var CoreVersionMismatchError = fmt.Errorf("core version mismatch")

func IsV2rayServiceValid() bool {
	if !asset.DoesV2rayAssetExist("geoip.dat") || !asset.DoesV2rayAssetExist("geosite.dat") {
		return false
	}
	_, ver, err := where.GetV2rayServiceVersion()
	return err == nil && ver != ""
}

func IfTProxyModLoaded() bool {
	out, err := exec.Command("sh", "-c", "lsmod|grep xt_TPROXY").Output()
	return err == nil && len(bytes.TrimSpace(out)) > 0
}

func CheckAndProbeTProxy() (err error) {
	if !IfTProxyModLoaded() && !common.IsDocker() && !iptables.IsNft() { //docker下无法判断,nft不需要
		var out []byte
		out, err = exec.Command("sh", "-c", "modprobe xt_TPROXY").CombinedOutput()

View on GitHub (pinned to 71e5442fc5)

Solutions

  1. Upgrade v2rayA and its bundled core together (same package/image) so both binaries share one version string
  2. Check the reported versions in the wrapped message and reinstall the older component from the same release
  3. If developing, build with the 'debug' or 'unstable' version prefix to skip strict matching

Example fix

// caller-side detection
if err := CheckCoreVersionMatch(); err != nil {
    if errors.Is(err, CoreVersionMismatchError) {
        // prompt user to update v2rayA + core together
    }
}
Defensive patterns

Strategy: type-guard

Validate before calling

_, coreVer, err := where.GetV2rayServiceVersion()
if err == nil && coreVer != conf.Version {
    // trigger upgrade flow before starting the core
}

Type guard

func versionsMatch() bool {
    _, coreVer, err := where.GetV2rayServiceVersion()
    return err == nil && (coreVer == conf.Version ||
        common.PrefixListSatisfyString([]string{"debug", "unstable"}, coreVer) != -1 ||
        common.PrefixListSatisfyString([]string{"debug", "unstable"}, conf.Version) != -1)
}

Try / catch

if err := CheckCoreVersionMatch(); err != nil {
    if errors.Is(err, CoreVersionMismatchError) {
        // surface upgrade prompt; do not start mismatched binaries
    }
    return err
}

Prevention

When it happens

Trigger: CheckCoreVersionMatch() (called from GetVersion) reads where.GetV2rayServiceVersion(), gets coreVer != conf.Version, and neither version has a 'debug'/'unstable' prefix.

Common situations: Upgrading v2rayA but the core binary (v2raya_core) stayed at an old version, or vice versa; mixing binaries from different packages or manual installs; container images where only one binary was replaced.

Related errors


AI-assisted analysis of v2rayA/v2rayA@71e5442fc5 (2026-09-05). Data as JSON: /api/errors/556b156e6e121017. Report an issue: GitHub.