Files
2026-03-06 15:05:53 +08:00

378 lines
12 KiB
Dart

import 'package:flutter/material.dart';
import 'dart:async';
import 'package:cipher_guard_sdk/cipher_guard_sdk.dart';
void main() {
runApp(const MyApp());
}
class MyApp extends StatefulWidget {
const MyApp({super.key});
@override
State<MyApp> createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
String _platformVersion = 'Unknown';
final CipherGuardSdkApi _sdk = CipherGuardSdkApi();
// 加密相關狀態
RsaKeyPair? _keyPair;
String? _encryptedPrivateKey;
SessionKey? _sessionKey;
EncryptedMessage? _encryptedMessage;
String _decryptedMessage = '';
String _statusMessage = '';
@override
void initState() {
super.initState();
initPlatformState();
}
Future<void> initPlatformState() async {
String platformVersion;
try {
platformVersion = (await _sdk.platformVersion()) ?? 'Unknown platform version';
} catch (e) {
platformVersion = 'Failed to get platform version: $e';
}
if (!mounted) return;
setState(() {
_platformVersion = platformVersion;
});
}
// ==================== RSA 金鑰管理 ====================
Future<void> _generateRsaKeyPair() async
{
setState(() => _statusMessage = 'Generating RSA key pair...');
try {
final keyPair = await _sdk.generateRsaKeyPair(keySize: 1024);
setState(() {
_keyPair = keyPair;
_statusMessage = 'RSA key pair generated successfully!\nPublic Key: ${keyPair.publicKey.substring(0, 50)}...';
});
} catch (e) {
print("_generateRsaKeyPair error: $e");
setState(() => _statusMessage = 'Error: $e');
}
}
Future<void> _encryptPrivateKey() async
{
if (_keyPair == null) {
setState(() => _statusMessage = 'Please generate RSA key pair first!');
return;
}
const password = 'user_password_123';
setState(() => _statusMessage = 'Encrypting private key with password...');
try {
final encrypted = await _sdk.encryptPrivateKey(
privateKey: _keyPair!.privateKey,
password: password,
);
setState(() {
_encryptedPrivateKey = encrypted;
_statusMessage = 'Private key encrypted successfully!';
});
} catch (e) {
setState(() => _statusMessage = 'Error: $e');
}
}
Future<void> _decryptPrivateKey() async
{
if (_encryptedPrivateKey == null) {
setState(() => _statusMessage = 'No encrypted private key to decrypt!');
return;
}
const password = 'user_password_123';
setState(() => _statusMessage = 'Decrypting private key...');
try {
final decrypted = await _sdk.decryptPrivateKey(
encryptedPrivateKey: _encryptedPrivateKey!,
password: password,
);
setState(() {
_statusMessage = 'Private key decrypted successfully!\n$decrypted';
});
} catch (e) {
setState(() => _statusMessage = 'Error: $e');
}
}
// ==================== 會話金鑰管理 ====================
Future<void> _generateSessionKey() async
{
setState(() => _statusMessage = 'Generating session key...');
try {
final sessionKey = await _sdk.generateSessionKey(initialRound: 1);
setState(() {
_sessionKey = sessionKey;
_statusMessage = 'Session key generated!\nKey: ${sessionKey.key}\nRound: ${sessionKey.round}';
});
} catch (e) {
setState(() => _statusMessage = 'Error: $e');
}
}
Future<void> _encryptSessionKey() async
{
if (_sessionKey == null || _keyPair == null) {
setState(() => _statusMessage = 'Please generate session key and RSA key pair first!');
return;
}
setState(() => _statusMessage = 'Encrypting session key with RSA public key...');
try {
final encrypted = await _sdk.encryptSessionKey(
sessionKey: _sessionKey!.key,
publicKey: _keyPair!.publicKey,
);
setState(() {
_statusMessage = 'Session key encrypted successfully!\n$encrypted';
});
} catch (e) {
setState(() => _statusMessage = 'Error: $e');
}
}
Future<void> _decryptSessionKey() async
{
if (_keyPair == null) {
setState(() => _statusMessage = 'Please generate RSA key pair first!');
return;
}
// 這裡應該使用之前加密的會話金鑰
if (_sessionKey == null) {
setState(() => _statusMessage = 'Please generate session key first!');
return;
}
setState(() => _statusMessage = 'Decrypting session key...');
try {
// 先加密再解密測試
final encrypted = await _sdk.encryptSessionKey(
sessionKey: _sessionKey!.key,
publicKey: _keyPair!.publicKey,
);
final decrypted = await _sdk.decryptSessionKey(
encryptedSessionKey: encrypted,
privateKey: _keyPair!.privateKey,
);
setState(() {
_statusMessage = 'Session key decrypted successfully!\nOriginal: ${_sessionKey!.key}\nDecrypted: $decrypted';
});
} catch (e) {
setState(() => _statusMessage = 'Error: $e');
}
}
// ==================== 訊息加解密 ====================
Future<void> _encryptMessage() async
{
if (_sessionKey == null) {
setState(() => _statusMessage = 'Please generate session key first!');
return;
}
const plaintext = 'Hello, this is a secret message!';
setState(() => _statusMessage = 'Encrypting message...');
try {
final encrypted = await _sdk.encryptMessage(
plaintext: plaintext,
sessionKey: _sessionKey!.key,
round: _sessionKey!.round,
);
setState(() {
_encryptedMessage = encrypted;
_statusMessage = 'Message encrypted!\nRound: ${encrypted.round}\nData: ${encrypted.data}';
});
} catch (e) {
setState(() => _statusMessage = 'Error: $e');
}
}
Future<void> _decryptMessage() async
{
if (_encryptedMessage == null || _sessionKey == null) {
setState(() => _statusMessage = 'No encrypted message to decrypt!');
return;
}
setState(() => _statusMessage = 'Decrypting message...');
try {
final decrypted = await _sdk.decryptMessage(
encryptedData: _encryptedMessage!.data,
sessionKey: _sessionKey!.key,
round: _encryptedMessage!.round,
);
setState(() {
_decryptedMessage = decrypted;
_statusMessage = 'Message decrypted: $decrypted';
});
} catch (e) {
setState(() => _statusMessage = 'Error: $e');
}
}
// ==================== 原生平台同步 ====================
Future<void> _syncEncryptionKeys() async
{
if (_sessionKey == null) {
setState(() => _statusMessage = 'Please generate session key first!');
return;
}
setState(() => _statusMessage = 'Syncing encryption keys to native...');
try {
await _sdk.syncEncryptionKey(
chatId: 'test_chat_123',
activeRound: _sessionKey!.round,
round: _sessionKey!.round,
activeKey: _sessionKey!.key,
isSingle: false,
);
setState(() => _statusMessage = 'Encryption keys synced to native platform!');
} catch (e) {
setState(() => _statusMessage = 'Error: $e');
}
}
// ==================== 推送通知解密 ====================
Future<void> _setupAesSecret() async
{
// 設置 release.json 中的 AES_SECRET
const aesSecret = '468171c825c02408cc99935447c785a5';
setState(() => _statusMessage = 'Setting AES_SECRET...');
try {
await _sdk.setAesSecret(aesSecret: aesSecret);
setState(() => _statusMessage = 'AES_SECRET set successfully!');
} catch (e) {
setState(() => _statusMessage = 'Error: $e');
}
}
@override
Widget build(BuildContext context)
{
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('CipherGuard SDK Example'),
),
body: SingleChildScrollView(
padding: const EdgeInsets.all(16),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Text('Running on: $_platformVersion\n', style: Theme.of(context).textTheme.titleMedium),
const Text('=== RSA 金鑰管理 ===', style: TextStyle(fontWeight: FontWeight.bold)),
Row(
children: [
Expanded(
child:ElevatedButton(onPressed: _generateRsaKeyPair, child: const Text('生成 RSA 金鑰對',)
),
),
const SizedBox(width: 8),
Expanded(child: ElevatedButton(onPressed: _keyPair != null ? _encryptPrivateKey : null, child: const Text('加密私鑰',style: TextStyle(fontSize: 10),))),
const SizedBox(width: 8),
Expanded(child: ElevatedButton(onPressed: _encryptedPrivateKey != null ? _decryptPrivateKey : null, child: const Text('解密私鑰',style: TextStyle(fontSize: 10),)),),
],
),
const SizedBox(height: 8),
const Text('=== 會話金鑰管理 ===', style: TextStyle(fontWeight: FontWeight.bold)),
Row(
children: [
Expanded(
child: ElevatedButton(onPressed: _generateSessionKey, child: const Text('生成會話金鑰',style: TextStyle(fontSize: 10),)),
),
const SizedBox(width: 8),
Expanded(
child: ElevatedButton(
onPressed: (_sessionKey != null && _keyPair != null) ? _encryptSessionKey : null,
child: const Text('加密會話金鑰',style: TextStyle(fontSize: 10),)
),
),
const SizedBox(width: 8),
Expanded(
child: ElevatedButton(
onPressed: (_keyPair != null && _sessionKey != null) ? _decryptSessionKey : null,
child: const Text('解密會話金鑰',style: TextStyle(fontSize: 10),)
),
),
],
),
const SizedBox(height: 8),
const Text('=== 訊息加解密 ===', style: TextStyle(fontWeight: FontWeight.bold)),
Row(
children: [
ElevatedButton(
onPressed: _sessionKey != null ? _encryptMessage : null,
child: const Text('加密訊息')
),
const SizedBox(width: 8),
ElevatedButton(
onPressed: _encryptedMessage != null ? _decryptMessage : null,
child: const Text('解密訊息')
),
],
),
if (_decryptedMessage.isNotEmpty)
Text('解密結果: $_decryptedMessage', style: const TextStyle(color: Colors.green)),
const SizedBox(height: 8),
const Text('=== 原生平台同步 ===', style: TextStyle(fontWeight: FontWeight.bold)),
ElevatedButton(
onPressed: _sessionKey != null ? _syncEncryptionKeys : null,
child: const Text('同步加密金鑰到原生')
),
const SizedBox(height: 8),
const Text('=== 推送通知解密 ===', style: TextStyle(fontWeight: FontWeight.bold)),
ElevatedButton(onPressed: _setupAesSecret, child: const Text('設置 AES_SECRET')),
const SizedBox(height: 16),
Container(
padding: const EdgeInsets.all(12),
color: Colors.grey[200],
width: double.infinity,
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
const Text('狀態:', style: TextStyle(fontWeight: FontWeight.bold)),
Text(_statusMessage),
],
),
),
],
),
),
),
);
}
}