Skip to Content
硬件接入传输协议React Native BLE

React Native BLE (hd-ble-sdk)

注意: 演示:React Native / Expo 示例 → react-native-demo 

本指南展示如何使用纯 React Native BLE 堆栈与 @onekeyfe/hd-ble-sdk 和 @onekeyfe/hd-transport-react-native。无需 WebView 或底层适配器。链 API 的使用方式与快速开始中相同。

安装

我们建议在应用层安装 RN 原生依赖,以便自动链接将原生模块包含在您的 Dev Client 构建中:

npm i @onekeyfe/hd-ble-sdk @onekeyfe/hd-transport-react-native \ @onekeyfe/react-native-ble-utils react-native-ble-plx \ buffer process react-native-get-random-values react-native-url-polyfill

在您的应用入口(例如 index.js 或 App.tsx):

// Polyfills(根据项目需要调整) import 'react-native-get-random-values'; import 'react-native-url-polyfill/auto'; // @ts-ignore global.Buffer = global.Buffer || require('buffer').Buffer; // @ts-ignore global.process = global.process || require('process'); // 在 SDK 初始化之前注册 RN transport 副作用 import '@onekeyfe/hd-transport-react-native'; import HardwareSDK from '@onekeyfe/hd-ble-sdk';

Android 设置

下面的声明适用于不通过 BLE 扫描推断位置的客户端。只有应用确实满足该条件时,才使用 neverForLocation:

<uses-permission android:name="android.permission.INTERNET"/> <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" android:maxSdkVersion="30"/> <uses-permission android:name="android.permission.BLUETOOTH" android:maxSdkVersion="30"/> <uses-permission android:name="android.permission.BLUETOOTH_ADMIN" android:maxSdkVersion="30"/> <uses-permission android:name="android.permission.BLUETOOTH_SCAN" android:usesPermissionFlags="neverForLocation"/> <uses-permission android:name="android.permission.BLUETOOTH_CONNECT"/>

Android 12+ 在运行时请求 BLUETOOTH_SCAN 和 BLUETOOTH_CONNECT。是否需要位置权限取决于目标 SDK、应用是否推断位置以及 BLE 库配置,并非所有 Android 12+ 应用都需要。旧版 Android 使用对应的旧版蓝牙与位置权限。参见 Android 权限指南 。

iOS 设置

添加到 Info.plist:

  • NSBluetoothAlwaysUsageDescription(必需)
  • 可选的 NSBluetoothPeripheralUsageDescription 用于旧版 iOS
  • 如果您的应用使用相机(例如二维码扫描),添加 NSCameraUsageDescription

如果使用 Expo,您可以在 app.json 中的 expo.ios.infoPlist 和 expo.android.permissions 下声明这些。

Metro 配置(polyfills 和 exports)

如果 Metro 报告缺少 Node 核心 API,只映射依赖树实际需要的模块。先安装每个 require.resolve 引用的包,再将条目合并进现有 resolver,不要覆盖框架默认配置。下面只是可选的映射片段,不是完整 Metro 配置:

// metro.config.js config.resolver.extraNodeModules = { buffer: require.resolve('buffer/'), crypto: require.resolve('crypto-browserify'), stream: require.resolve('stream-browserify'), process: require.resolve('process/browser'), events: require.resolve('events/'), http: require.resolve('http-browserify'), https: require.resolve('https-browserify'), zlib: require.resolve('browserify-zlib'), util: require.resolve('util/'), url: require.resolve('url/'), path: require.resolve('path-browserify'), }; config.resolver.unstable_enablePackageExports = true;

构建 Dev Client(真实设备)

Expo Go 不包含您的原生 BLE 模块。构建 Dev Client:

# iOS expo run:ios --device # Android expo run:android --device # 为 Dev Client 启动 bundler expo start --dev-client -c

初始化并订阅事件

export async function setupBle() { const initialized = await HardwareSDK.init({ env: 'react-native', // React Native BLE transport debug: false, fetchConfig: true, }); if (!initialized) throw new Error('SDK initialization failed'); // Subscribe to UI events (PIN / Passphrase / confirmations) // import { UI_EVENT, UI_REQUEST, UI_RESPONSE } from '@onekeyfe/hd-core' // HardwareSDK.on(UI_EVENT, (msg) => { /* open dialogs and reply via HardwareSDK.uiResponse(...) */ }); }

发现设备并识别 device_id

const devices = await HardwareSDK.searchDevices(); if (!devices.success) throw new Error(devices.payload.error); // BLE 返回 id + name;用 getDeviceState 读 identity // Select explicitly in the application when more than one device is available. if (devices.payload.length !== 1) throw new Error('Select exactly one device before continuing'); const candidate = devices.payload[0]; const connectId = candidate?.connectId; if (!connectId) throw new Error("No device connection"); const state = await HardwareSDK.getDeviceState(connectId); if (!state.success) throw new Error(state.payload.error); const deviceId = state.payload.identity.deviceId; if (!deviceId) throw new Error("Device has no wallet identity");

保存 connectId 和 deviceId(大多数链 API 都需要两者)。

第一个调用示例(BTC 地址)

const res = await HardwareSDK.btcGetAddress(connectId, deviceId, { path: "m/44'/0'/0'/0/0", coin: 'btc', showOnOneKey: true, useEmptyPassphrase: true, }); if (res.success) { console.log('BTC address:', res.payload.address); } else { console.error('Error:', res.payload.error, res.payload.code); }

提示

  • 始终尽早订阅 UI_EVENT,以免 PIN/密码短语/确认阻塞请求。参见 配置事件。
  • 保持 BLE 权限与操作系统版本同步。在物理设备上测试。
  • 更多示例请查看:react-native-demo 

继续

最后更新于