Dart空安全适配:如何返回空的PostgreSQLResult抽象类数据集
空PostgreSQLResult结果集实现方案
由于PostgreSQLResult是抽象类无法直接实例化,你可以自定义一个符合空结果特征的实现类,配合Dart的ListMixin可以快速完成列表相关方法的代理,无需手动实现全部List接口方法。
完整实现代码
import 'dart:collection'; // 空结果实现类 class EmptyPostgreSQLResult with ListMixin<PostgreSQLResultRow> implements PostgreSQLResult { // 空查询影响行数为0 @override final int affectedRowCount = 0; // 空结果无列描述 @override final List<ColumnDescription> columnDescriptions = const []; // 内置不可变空行列表 final List<PostgreSQLResultRow> _rows = const []; @override int get length => _rows.length; @override set length(int newLength) => _rows.length = newLength; @override PostgreSQLResultRow operator [](int index) => _rows[index]; @override void operator []=(int index, PostgreSQLResultRow value) => _rows[index] = value; } // 全局单例,避免重复创建实例 final emptyPostgreSQLResult = EmptyPostgreSQLResult();
业务代码改造
PostgreSQLResult getResultFromCache(sqlQuery) { for (var req in requestsCacheList) { if(req.requestHash == sqlQuery.hashCode) { return req.requestResult; } } // 缓存未命中直接返回空结果单例 return emptyPostgreSQLResult; }
可选补充:空PostgreSQLResultRow实现
如果你的业务逻辑存在特殊场景可能会访问空结果集的行数据,可以补充实现空的行类,避免运行时异常:
class EmptyPostgreSQLResultRow with ListMixin implements PostgreSQLResultRow { @override final List<ColumnDescription> columnDescriptions = const []; final List _values = const []; @override Map<String, Map<String, dynamic>> toTableColumnMap() => const {}; @override Map<String, dynamic> toColumnMap() => const {}; @override int get length => _values.length; @override set length(int newLength) => _values.length = newLength; @override operator [](int index) => _values[index]; @override void operator []=(int index, value) => _values[index] = value; }
该实现的行为和数据库返回的空查询结果完全一致,上层逻辑可以正常使用isEmpty、affectedRowCount等属性判断结果状态,无需额外适配。
内容的提问来源于stack exchange,提问作者Dmitry Bubnenkov
相关产品推荐
相关产品推荐

