[英]How to save nested list with sqflite in flutter?
在这里,我想在我的
flutter
新闻应用程序中添加bookmark
功能。 我从APIs
get
数据。 我在下面显示该数据。
我正在使用这个片段来保存下面显示的
SQflite
数据。 我用名称bookmark_db_provider.dart
保存这个文件。
import 'dart:io';
import 'home_screen_data.dart';
import 'package:path/path.dart';
import 'package:path_provider/path_provider.dart';
import 'package:sqflite/sqflite.dart';
class DBProvider {
static Database _database;
static final DBProvider db = DBProvider._();
DBProvider._();
Future<Database> get database async {
if (_database != null) _database = await initDB();
return _database;
}
initDB() async {
Directory documentsDirectory = await getApplicationDocumentsDirectory();
final path = join(documentsDirectory.path, 'ProductData.db');
return await openDatabase(path, version: 1, onOpen: (db) {},
onCreate: (Database db, int version) async {
await db.execute('CREATE TABLE ProductData('
'id INTEGER PRIMARY KEY,' //id
'categoryName Text,' //headline
'publisherName Text,' //description
'isAvailable Text,' //content
'categoryImgUrl Text' //image
')');
});
}
createProductData(ProductData productData) async {
await deleteAllProductData();
final db = await database;
final res = await db.insert('ProductData', productData.toJson());
return res;
}
Future<int> deleteAllProductData() async {
final db = await database;
final res = await db.delete('DELETE FROM ProductData');
return res;
}
Future<List<ProductData>> getProductDataList() async {
final db = await database;
final res = await db.rawQuery("SELECT * FROM ProductData");
List<ProductData> list = res.isNotEmpty ? res.map((x) => ProductData.fromJson(x)).toList() : [];
return list;
}
}
所以,我想了解如何使用 flutter 中的flutter
SQflite database
save data
和get data
。 我如何做到这一点?
你的问题我可能不清楚,但根据我的理解,
您需要使用所需的数据调用此提供程序的方法:
DBProvider.init() // Use this only one which when the application is instaled
之后,您可以从任何地方调用这些方法来放置和获取数据
DBProvider.createProductData(productData) //insert data
获取数据
DBProvider.getProductDataList() //get data
这是一个老问题,希望你已经得到了答案。 但是,许多使用 sqflite 的 flutter 开发人员在处理上述类型的嵌套数组格式的数据时遇到了困难,例如
``` {
"id": 1,
"name": "xyz",
"images": [
{
"imageId": 1,
"image": "image1"
},
{
"imageId": 2,
"image": "image2"
}
]
}
```
由于 json 处理目前不是 sqflite 的一部分,因此建议这样做; a.,将内部数组保存为表“数据”的“图像”列中的字符串/文本字段,如**
"[{"imageId": 1, "image": 'image1'}, {"imageId": 2, "image": 'image2'},}"
**,无担保。
或者,b.,将内部数组展平,以便只有 **
数据[id,名称,image1,image2,image3,...]。
** 这种方法可能在给定的简单数组中但在复杂系统中是可能的。 变平可能真的很麻烦。
我的建议是,创建两个表,一个用于数据,另一个用于图像。 让图像表的每一行都与对应的数据表行有引用或关系。 您的数据 class 和图像 class 将类似于,
```
class Data {
int dataId;
String name;
List<Image> images;
data({this.id, this.images, this.name});
...
```
和
```
class Image {
int imageId;
int dataId;
String image;
Image({this.imageId, this.dataId, this.image});
...
}
```
您的 sqflite 表数据将只有两个字段“dataId”和“name”,并且图像表必须包含“dataId”作为两个表之间的关系。
要保存数据,您可以使用交易,例如
```
void saveData(Data data, Map<String, Object> map) async {
await db.execute(""" INSERT INTO "data" (name) values (?) """, [data.name]);
// retrieve dataId of the new row inserted. last_inserted_rowid can also be used if the database does not contain several tables that may have been updated or saved before completing the transaction.
int dataId;
List<Map> x = await db.query('data', columns: ['dataId'], where: 'name = ?', whereArgs: [data.name]);
dataId = x[x.length - 1]['dataId'];
db.transaction((txn) async {
var batch = txn.batch();
data.images
.map((e) => {
batch.rawInsert(
""" INSERT INTO "images" (dataId,image,) values (?,?,?,? ) """, [dataId, e.image])
}).toList();
});
}
```
要检索数据和图像,您可以尝试类似
```
Data _data = new Data();
Future<void> fetchData() async {
if (db != null) {
// do not execute if db is not instantiate
//retrieve all data from data table and store in instantiated, also instantiate images array as empty list
final dataList = await db.query(data);
_data = (dataList as List)
.map(
(data) => Data(
dataId: data['dataId'],
name: data['name'],
images: data['images'] != null ? data['images'] : []
)) .toList();
_data.forEach((data) async {if (data.images != null) {
List<Image> _images = [];
var imageResults = await db.query(images,where: 'dataId =?', whereArgs: [data.dataId]);
_images = (imageResults as List).map((e) => Image(
imageId: e['imageId'],
dataId: e['dataId'],
image: e['image']
)).toList();
_data.images.addAll(_images);
} });
}
}
```
使用这种方法,您应该能够处理 flutter 和 sqflite 中的嵌套数组
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.