Files
Genarrative/apps/mobile-shell/src/host-bridge/clipboard.ts
T
kdletters 568010b31b 收口移动壳剪贴板诊断日志
移动壳剪贴板 HostBridge 失败日志只记录稳定标签

更新剪贴板失败测试避免断言原生错误对象外泄

扩展移动壳配置门禁禁止剪贴板日志打印原生 error 对象
2026-06-20 22:51:10 +08:00

73 lines
1.9 KiB
TypeScript

import * as Clipboard from 'expo-clipboard';
import {
type ClipboardReadTextResult,
type ClipboardWriteTextPayload,
type HostBridgeError,
type HostBridgeRequest,
normalizeHostBridgeClipboardText,
} from '../../../../packages/shared/src/contracts/hostBridge';
import { invalidRequest, ok } from './protocol';
function logMobileClipboardFailure(label: string, _error: unknown) {
console.warn(`mobile clipboard failed for ${label}`);
}
export async function writeMobileClipboardText(rawText: unknown) {
const clipboardText = normalizeHostBridgeClipboardText(rawText);
if (!clipboardText) {
return false;
}
try {
await Clipboard.setStringAsync(clipboardText.text);
} catch (error) {
logMobileClipboardFailure('write.set_string', error);
throw {
code: 'host_error',
message: 'clipboard write unavailable',
} satisfies HostBridgeError;
}
return true;
}
export async function writeMobileHostBridgeClipboardText(
request: HostBridgeRequest,
) {
const text = (request.payload as ClipboardWriteTextPayload | undefined)?.text;
if (!(await writeMobileClipboardText(text))) {
throw invalidRequest('text is required');
}
return ok(request, true);
}
export async function readMobileHostBridgeClipboardText(
request: HostBridgeRequest,
) {
return ok(request, await readMobileClipboardText());
}
export async function readMobileClipboardText(): Promise<ClipboardReadTextResult> {
let rawText: unknown;
try {
rawText = await Clipboard.getStringAsync();
} catch (error) {
logMobileClipboardFailure('read.get_string', error);
throw {
code: 'host_error',
message: 'clipboard read unavailable',
} satisfies HostBridgeError;
}
const result = normalizeHostBridgeClipboardText(rawText);
if (!result) {
throw {
code: 'host_error',
message: 'clipboard text unavailable',
} satisfies HostBridgeError;
}
return result;
}