| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101 |
- import 'package:dio/dio.dart';
- import 'package:flutter/foundation.dart';
- import '../../../core/network/api_response.dart';
- import '../models/market/funding_rate.dart';
- /// 资金费率接口
- class FundingRateService {
- const FundingRateService(this._dio);
- final Dio _dio;
- static bool _isNoData(DioException e) =>
- e.response?.statusCode == 404 || e.error is ApiException;
- /// 当前资金费率
- /// GET /swap/funding-rate/current?contractCoinId=1
- Future<FundingRateCurrent?> getCurrent(int contractCoinId) async {
- try {
- final response = await _dio.get<Map<String, dynamic>>(
- 'swap/funding-rate/current',
- queryParameters: {'contractCoinId': contractCoinId},
- );
- final data = response.data?['data'];
- if (data is Map<String, dynamic>) {
- return FundingRateCurrent.fromJson(data);
- }
- return null;
- } on DioException catch (e) {
- if (_isNoData(e)) {
- debugPrint('[FundingRate] getCurrent no-data: ${e.error}');
- return null;
- }
- rethrow;
- }
- }
- /// 拉取单页历史记录
- Future<List<FundingRateHistoryItem>> _fetchPage(
- int contractCoinId, int pageNo, int pageSize) async {
- final response = await _dio.get<Map<String, dynamic>>(
- 'swap/funding-rate/history',
- queryParameters: {
- 'contractCoinId': contractCoinId,
- 'pageNo': pageNo,
- 'pageSize': pageSize,
- },
- );
- final data = response.data?['data'] ?? response.data;
- List? raw;
- if (data is Map<String, dynamic>) {
- raw = data['content'] as List?;
- } else if (data is List) {
- raw = data;
- }
- return (raw ?? [])
- .whereType<Map<String, dynamic>>()
- .map((e) => FundingRateHistoryItem.fromJson(e))
- .toList();
- }
- /// 资金费率历史——多页拉取,直到覆盖最近 [days] 天或服务端无更多数据
- /// GET /swap/funding-rate/history?contractCoinId=1&pageNo=N&pageSize=N
- Future<List<FundingRateHistoryItem>> getHistory({
- required int contractCoinId,
- int pageSize = 20,
- int days = 7,
- }) async {
- try {
- final cutoff = DateTime.now().subtract(Duration(days: days));
- final result = <FundingRateHistoryItem>[];
- int pageNo = 1;
- // 最多拉 10 页,防止死循环
- const maxPages = 10;
- while (pageNo <= maxPages) {
- final page = await _fetchPage(contractCoinId, pageNo, pageSize);
- result.addAll(page);
- // 服务端返回不足一页 → 已无更多数据
- if (page.length < pageSize) break;
- // 最早一条已早于 cutoff → 足够了
- final oldest = page
- .map((e) => e.fundingTime)
- .reduce((a, b) => a.isBefore(b) ? a : b);
- if (oldest.isBefore(cutoff)) break;
- pageNo++;
- }
- return result;
- } on DioException catch (e) {
- if (_isNoData(e)) {
- debugPrint('[FundingRate] getHistory no-data: ${e.error}');
- return [];
- }
- rethrow;
- }
- }
- }
|