fix: 迁移导致的部分内容没有更新现在修正

This commit is contained in:
LXP 2026-08-25 15:24:01 +08:00
parent 9ece3c7c48
commit 2d67fa4b0e
6 changed files with 136 additions and 38 deletions

View File

@ -0,0 +1,94 @@
import { readFileSync } from 'node:fs';
import * as path from 'node:path';
import { describe, expect, it } from 'vitest';
function readBuildProfile() {
const profilePath = path.resolve(__dirname, '../../build-profile.json');
return JSON.parse(readFileSync(profilePath, 'utf8')) as {
android: {
_comment?: { desc?: string; dexClassRemap?: string };
dexClassRemap?: Record<string, string>;
};
};
}
describe('build-profile.json android._comment', () => {
const profile = readBuildProfile();
const comment = profile.android._comment;
it('_comment 存在', () => {
expect(comment).toBeDefined();
expect(typeof comment).toBe('object');
});
it('desc 字段存在且非空', () => {
expect(comment!.desc).toBeDefined();
expect(typeof comment!.desc).toBe('string');
expect(comment!.desc!.length).toBeGreaterThan(0);
});
it('dexClassRemap 说明字段存在且非空', () => {
expect(comment!.dexClassRemap).toBeDefined();
expect(typeof comment!.dexClassRemap).toBe('string');
expect(comment!.dexClassRemap!.length).toBeGreaterThan(0);
});
});
describe('build-profile.json android.dexClassRemap', () => {
const profile = readBuildProfile();
const remap = profile.android.dexClassRemap ?? {};
const entries = Object.entries(remap);
it('dexClassRemap 存在且非空', () => {
expect(profile.android.dexClassRemap).toBeDefined();
expect(entries.length).toBeGreaterThan(0);
});
it('所有 key/value 字节长度一致(.so 二进制等长替换约束)', () => {
const mismatches: Array<{ key: string; value: string; keyLen: number; valueLen: number }> = [];
for (const [k, v] of entries) {
const keyLen = Buffer.byteLength(k, 'utf8');
const valueLen = Buffer.byteLength(v, 'utf8');
if (keyLen !== valueLen) {
mismatches.push({ key: k, value: v, keyLen, valueLen });
}
}
if (mismatches.length > 0) {
const detail = mismatches
.map((m) => ` key="${m.key}"(${m.keyLen}) value="${m.value}"(${m.valueLen})`)
.join('\n');
throw new Error(
`以下 ${mismatches.length} 个映射的 key/value 字节长度不一致,\n` +
`会导致 .so 二进制 FindClass 路径替换失败:\n${detail}`,
);
}
});
it('没有 key === value 的自映射', () => {
const selfMappings = entries.filter(([k, v]) => k === v);
expect(selfMappings).toEqual([]);
});
it('没有空 key 或空 value', () => {
for (const [k, v] of entries) {
expect(k.trim().length).toBeGreaterThan(0);
expect(v.trim().length).toBeGreaterThan(0);
}
});
it('所有 key 都是斜杠分隔的 Java 包路径格式', () => {
const javaPathPattern = /^[a-z][a-z0-9]*(\/[a-z][a-z0-9]*)*$/;
for (const [k] of entries) {
expect(k).toMatch(javaPathPattern);
}
});
it('所有 value 都是斜杠分隔的 Java 包路径格式', () => {
const javaPathPattern = /^[a-z][a-z0-9]*(\/[a-z][a-z0-9]*)*$/;
for (const [, v] of entries) {
expect(v).toMatch(javaPathPattern);
}
});
});

View File

@ -467,7 +467,7 @@ describe('screens/main/ProfileScreen', () => {
await versionTrigger.props.onLongPress();
});
expect(setClipboardStringMock).toHaveBeenCalledWith('v1.0.0.default.100');
expect(setClipboardStringMock).toHaveBeenCalledWith('v1.0.0.default.release.100');
expect(toastSuccessMock).toHaveBeenCalledWith('版本号已复制');
});
});

View File

@ -80,7 +80,7 @@ describe('screens/main/helpers', () => {
'../../../src/screens/main/helpers'
);
const label = await getAppVersionLabelAsync();
expect(label).toBe('v1.0.0.default.100');
expect(label).toBe('v1.0.0.default.release.100');
});
});

View File

@ -5,4 +5,4 @@ import com.flutter.proxyruntime.bg.ProxyEngineVpnService
/**
* 品牌侧 VPN Service 包装类用于隔离公共模块默认类名前缀
*/
class YijianlianVpnService : ProxyEngineVpnService()
class QihangVpnService : ProxyEngineVpnService()

View File

@ -3,10 +3,10 @@ package com.jsq.qihang.runtime.bridge
import android.util.Log
/**
* Yijianlian 专属 JNI bridgeRust 侧通过 RegisterNatives 绑定到该类
* Qihang 专属 JNI bridgeRust 侧通过 RegisterNatives 绑定到该类
*/
object YijianlianNativeBridge {
private const val TAG = "YijianlianNativeBridge"
object QihangNativeBridge {
private const val TAG = "QihangNativeBridge"
private const val LIB_NAME = "sslocal"
@Volatile

View File

@ -137,39 +137,43 @@
"uniquePathSalt": "jsq-qihang-v2-qh-path",
"uniqueContentSalt": "jsq-qihang-v2-qh-unique"
},
"_comment": {
"desc":"StoragePlatformBridge class not found出现的原因就是'com/flutter/storage:com/qh/app/storage'长度不一致",
"dexClassRemap": "DEX 可不等长替换;但包含 native .so FindClass/JNI 路径的包必须保持 key/value 等长,否则 .so 二进制替换不会生效。"
},
"dexClassRemap": {
"com/flutter/clipboard": "com/qh/app/clipboard",
"com/flutter/filemanager": "com/qh/app/filemanager",
"com/flutter/inapppurchase": "com/qh/app/inapppurchase",
"com/flutter/storage": "com/qh/app/storage",
"com/flutter/uploadqueue": "com/qh/app/uploadqueue",
"com/flutter/apiclient": "com/qh/app/apiclient",
"com/flutter/dnsclient": "com/qh/app/dnsclient",
"com/example/channel": "com/qh/app/channel",
"com/geolib/data": "com/qh/geodata",
"com/diagnostickit": "com/qh/diagtools",
"com/reactnativeexitapp": "com/qh/app/exitbridge",
"com/flutter/proxyruntime": "com/qh/app/proxyruntime",
"com/flutter/baiduocpc": "com/qh/app/baiduocpc",
"com/antidebugcollector/bridge": "com/qh/shieldmg/w/b/c/d/e/fj",
"com/pushnotification/bridge": "com/qh/msgrelay/d/e/f/g/hm",
"com/reactnativedeviceid/bridge": "com/qh/hwuuid/g/h/i/j/k/m/n/p",
"com/reactnativedevicemodel/bridge": "com/qh/hwmodeldata/j/k/m/n/p/q/r",
"com/reactnativedevicename/bridge": "com/qh/hwdisplayname/n/p/q/r/sw",
"com/reactnativesystemversion/bridge": "com/qh/platformbuild/r/s/t/u/v/w/b",
"com/reactnativeversioninfo/bridge": "com/qh/releasestamp/u/v/w/b/c/dh",
"com/rntoast/bridge": "com/qh/tips/f/g/h",
"google/appintegrity/bridge": "com/qh/appvalid/b/c/d/e/f",
"com/domaindiscover0/bridge": "com/qh/dnspool0/e/f/g/h/i",
"com/domaindiscover1/bridge": "com/qh/dnspool1/h/i/j/k/m",
"com/customerservice/bridge": "com/qh/srvchat/k/m/n/p/qu",
"com/reactnativebugly/bridge": "com/qh/dmpcrsh/p/q/r/s/t/u",
"com/reactnativeoaid/bridge": "com/qh/adident/s/t/u/v/we",
"com/prod/sentry/bridge": "com/qh/caplog/v/w/b/c",
"com/prod/sentry": "com/qh/caplg/c",
"com/modal/bridge": "com/qh/pop/i/jp",
"com/batterysettings/bridge": "com/qh/enrgmgr/m/n/p/q/rv",
"com/reactnativenetworkinfo/bridge": "com/qh/linkstatinfo/q/r/s/t/u/vd"
"com/flutter/clipboard": "com/qh/apps/clipboard",
"com/flutter/filemanager": "com/qh/apps/filemanager",
"com/flutter/inapppurchase": "com/qh/apps/inapppurchase",
"com/flutter/storage": "com/qh/apps/storage",
"com/flutter/uploadqueue": "com/qh/apps/uploadqueue",
"com/flutter/apiclient": "com/qh/apps/apiclient",
"com/flutter/dnsclient": "com/qh/apps/dnsclient",
"com/example/channel": "com/qh/apps/channel",
"com/geolib/data": "com/qh/geodataa",
"com/diagnostickit": "com/qh/diagtoolsa",
"com/reactnativeexitapp": "com/qh/apps/exitbridge",
"com/flutter/proxyruntime": "com/qh/apps/proxyruntime",
"com/flutter/baiduocpc": "com/qh/apps/baiduocpc",
"com/antidebugcollector/bridge": "com/qh/shieldmg/w/b/c/d/e/fja",
"com/pushnotification/bridge": "com/qh/msgrelay/d/e/f/g/hma",
"com/reactnativedeviceid/bridge": "com/qh/hwuuid/g/h/i/j/k/m/n/pa",
"com/reactnativedevicemodel/bridge": "com/qh/hwmodeldata/j/k/m/n/p/q/ra",
"com/reactnativedevicename/bridge": "com/qh/hwdisplayname/n/p/q/r/swa",
"com/reactnativesystemversion/bridge": "com/qh/platformbuild/r/s/t/u/v/w/ba",
"com/reactnativeversioninfo/bridge": "com/qh/releasestamp/u/v/w/b/c/dha",
"com/rntoast/bridge": "com/qh/tips/f/g/ha",
"google/appintegrity/bridge": "com/qh/appvalid/b/c/d/e/fa",
"com/domaindiscover0/bridge": "com/qh/dnspool0/e/f/g/h/ia",
"com/domaindiscover1/bridge": "com/qh/dnspool1/h/i/j/k/ma",
"com/customerservice/bridge": "com/qh/srvchat/k/m/n/p/qua",
"com/reactnativebugly/bridge": "com/qh/dmpcrsh/p/q/r/s/t/ua",
"com/reactnativeoaid/bridge": "com/qh/adident/s/t/u/v/wea",
"com/prod/sentry/bridge": "com/qh/caplog/v/w/b/ca",
"com/prod/sentry": "com/qh/caplg/ca",
"com/modal/bridge": "com/qh/pop/i/jpa",
"com/batterysettings/bridge": "com/qh/enrgmgr/m/n/p/q/rva",
"com/reactnativenetworkinfo/bridge": "com/qh/linkstatinfo/q/r/s/t/u/vda"
}
},
"rust": {