cashumit/lib/screens/transaction_screen.dart

251 lines
7.5 KiB
Dart

// lib/screens/transaction_screen.dart
import 'package:flutter/material.dart';
import 'package:shared_preferences/shared_preferences.dart';
import '../models/firefly_account.dart';
import '../services/firefly_api_service.dart';
class TransactionScreen extends StatefulWidget {
const TransactionScreen({super.key});
@override
State<TransactionScreen> createState() => _TransactionScreenState();
}
class _TransactionScreenState extends State<TransactionScreen> {
List<FireflyAccount> _revenueAccounts = [];
List<FireflyAccount> _assetAccounts = [];
FireflyAccount? _selectedSourceAccount;
FireflyAccount? _selectedDestinationAccount;
bool _isLoading = false;
String _message = '';
String? _fireflyUrl;
String? _accessToken;
@override
void initState() {
super.initState();
_loadCredentialsAndAccounts();
}
/// Memuat kredensial dari shared preferences dan kemudian memuat akun.
Future<void> _loadCredentialsAndAccounts() async {
final prefs = await SharedPreferences.getInstance();
final url = prefs.getString('firefly_url');
final token = prefs.getString('firefly_token');
if (url == null || token == null || url.isEmpty || token.isEmpty) {
setState(() {
_message = 'Kredensial Firefly III belum dikonfigurasi. Silakan atur di menu konfigurasi.';
});
return;
}
setState(() {
_fireflyUrl = url;
_accessToken = token;
});
// Jika kredensial ada, lanjutkan untuk memuat akun
_loadAccounts();
}
/// Memuat daftar akun sumber (revenue) dan tujuan (asset) dari API.
Future<void> _loadAccounts() async {
if (_fireflyUrl == null || _accessToken == null) {
return;
}
setState(() {
_isLoading = true;
_message = 'Memuat daftar akun...';
});
try {
// Mengambil akun revenue
final revenueAccounts = await FireflyApiService.fetchAccounts(
baseUrl: _fireflyUrl!,
accessToken: _accessToken!,
type: 'revenue',
);
// Mengambil akun asset
final assetAccounts = await FireflyApiService.fetchAccounts(
baseUrl: _fireflyUrl!,
accessToken: _accessToken!,
type: 'asset',
);
setState(() {
_revenueAccounts = revenueAccounts;
_assetAccounts = assetAccounts;
// Reset pilihan jika daftar akun berubah
_selectedSourceAccount = null;
_selectedDestinationAccount = null;
_message = 'Daftar akun berhasil dimuat.';
});
} catch (error) {
setState(() {
_message = 'Gagal memuat akun: $error';
});
} finally {
setState(() {
_isLoading = false;
});
}
}
/// Mengirim transaksi dummy menggunakan akun yang dipilih.
Future<void> _submitTransaction() async {
if (_fireflyUrl == null || _accessToken == null) {
setState(() {
_message = 'Kredensial tidak lengkap.';
return;
}
);
}
if (_selectedSourceAccount == null || _selectedDestinationAccount == null) {
setState(() {
_message = 'Silakan pilih akun sumber dan tujuan.';
});
return;
}
setState(() {
_isLoading = true;
_message = 'Mengirim transaksi...';
});
try {
final success = await FireflyApiService.submitDummyTransaction(
baseUrl: _fireflyUrl!,
accessToken: _accessToken!,
sourceId: _selectedSourceAccount!.id,
destinationId: _selectedDestinationAccount!.id,
type: 'deposit', // Sesuaikan dengan logika bisnis
description: 'Transaksi Dummy dari Aplikasi Flutter',
);
setState(() {
_message = success != null
? 'Transaksi berhasil dikirim!'
: 'Gagal mengirim transaksi. Periksa log.';
});
} catch (error) {
setState(() {
_message = 'Terjadi kesalahan: $error';
});
} finally {
setState(() {
_isLoading = false;
});
}
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Kirim Transaksi ke Firefly III'),
actions: [
IconButton(
icon: const Icon(Icons.settings),
onPressed: () {
// Navigasi ke ConfigScreen
Navigator.pushNamed(context, '/config');
},
),
],
),
body: Padding(
padding: const EdgeInsets.all(16.0),
child: Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
// Pesan status
if (_message.isNotEmpty)
Text(_message,
style: TextStyle(
color: _message.contains('berhasil')
? Colors.green
: (_message.contains('belum') || _message.contains('tidak')) ? Colors.orange : Colors.red)),
const SizedBox(height: 10),
if (_fireflyUrl != null && _accessToken != null) ...[
// Dropdown untuk Akun Sumber (Revenue)
const Text('Pilih Akun Sumber (Revenue):',
style: TextStyle(fontWeight: FontWeight.bold)),
DropdownButton<FireflyAccount>(
isExpanded: true,
hint: const Text('Pilih akun sumber'),
value: _selectedSourceAccount,
items: _revenueAccounts.map((account) {
return DropdownMenuItem<FireflyAccount>(
value: account,
child: Text(account.name),
);
}).toList(),
onChanged: (account) {
setState(() {
_selectedSourceAccount = account;
});
},
),
const SizedBox(height: 20),
// Dropdown untuk Akun Tujuan (Asset)
const Text('Pilih Akun Tujuan (Asset):',
style: TextStyle(fontWeight: FontWeight.bold)),
DropdownButton<FireflyAccount>(
isExpanded: true,
hint: const Text('Pilih akun tujuan'),
value: _selectedDestinationAccount,
items: _assetAccounts.map((account) {
return DropdownMenuItem<FireflyAccount>(
value: account,
child: Text(account.name),
);
}).toList(),
onChanged: (account) {
setState(() {
_selectedDestinationAccount = account;
});
},
),
const SizedBox(height: 20),
// Tombol untuk memuat ulang akun
ElevatedButton.icon(
onPressed: _isLoading ? null : _loadAccounts,
icon: const Icon(Icons.refresh),
label: const Text('Muat Ulang Akun'),
),
const SizedBox(height: 10),
// Tombol untuk mengirim transaksi
ElevatedButton.icon(
onPressed: _isLoading ? null : _submitTransaction,
icon: const Icon(Icons.send),
label: const Text('Kirim Transaksi Dummy'),
),
const SizedBox(height: 20),
],
// Status dan pesan loading
if (_isLoading)
const Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
CircularProgressIndicator(),
SizedBox(width: 10),
Text('Sedang diproses...'),
],
),
],
),
),
);
}
}