当前位置:网站首页>Use of shutter SQLite
Use of shutter SQLite
2022-07-01 13:13:00 【xiangxiongfly915】
List of articles
Flutter SQLite Use
summary
Saving data locally is one of the most important functions of an application , For example, the following scenes : A news or blog application , Open it and go to the home page , If the data is not saved locally , You need to get data through the Internet , Before returning data , What the user sees is a blank page , And if you keep some news locally , This part of the data is displayed , When waiting for the latest data to return, refresh it , For the user experience , Obviously the second experience is better .
SQLite Is currently one of the most popular local storage frameworks .
Add dependency
dependencies:
path_provider: ^2.0.11
sqflite: ^2.0.2+1
Use SQLite
Use a singleton class
class DBManager {
static final DBManager _instance = DBManager._internal();
factory DBManager() {
return _instance;
}
DBManager._internal();
}
initialization
class DBManager {
static Database? _db;
Future<Database?> get db async {
// if (_db != null) {
// return _db;
// }
// _db = await _initDB();
// return _db;
return _db ??= await _initDB();
}
/// Initialize database
Future<Database> _initDB() async {
Directory directory = await getApplicationDocumentsDirectory();
String path = join(directory.path, "dbName");
return await openDatabase(
path,
version: 1,
onCreate: _onCreate,
onUpgrade: _onUpgrade,
);
}
/// Create table
Future _onCreate(Database db, int version) async {
const String sql = """
CREATE TABLE Student(
id INTEGER primary key AUTOINCREMENT,
name TEXT,
age INTEGER,
sex INTEGER
)
""";
return await db.execute(sql);
}
/// Update table
Future _onUpgrade(Database db, int oldVersion, int newVersion) async {}
}
Add, delete, change and check operation
/// Save the data
Future saveData(Student student) async {
var _db = await db;
return await _db?.insert("Student", student.toJson());
}
/// Use SQL Save the data
Future saveDataBySQL(Student student) async {
const String sql = """
INSERT INTO Student(name,age,sex) values(?,?,?)
""";
var _db = await db;
return await _db?.rawInsert(sql, [student.name, student.age, student.sex]);
}
/// Query all data
Future<List<Student>?> findAll() async {
var _db = await db;
List<Map<String, Object?>>? result = await _db?.query("Student");
if (result == null) {
return null;
} else {
if (result.isNotEmpty) {
return result.map((e) => Student.fromJson(e)).toList();
} else {
return [];
}
}
}
/// Conditions of the query
Future<List<Student>?> find(int sex) async {
var _db = await db;
List<Map<String, dynamic>>? result = await _db?.query("Student", where: "sex=?", whereArgs: [sex]);
if (result == null) {
return null;
} else {
if (result.isNotEmpty) {
return result.map((e) => Student.fromJson(e)).toList();
} else {
return [];
}
}
}
/// modify
Future<int> update(Student student) async {
var _db = await db;
student.age = 99;
int? count = await _db?.update("Student", student.toJson(), where: "id=?", whereArgs: [student.id]);
return count ?? 0;
}
/// Delete
Future<int> delete(int id) async {
var _db = await db;
int? count = await _db?.delete("Student", where: "id=?", whereArgs: [id]);
return count ?? 0;
}
/// Delete all
Future<int> deleteAll() async {
var _db = await db;
int? count = await _db?.delete("Student");
return count ?? 0;
}
The complete code is as follows
Database management class
class DBManager {
static final DBManager _instance = DBManager._internal();
factory DBManager() {
return _instance;
}
DBManager._internal();
static Database? _db;
Future<Database?> get db async {
// if (_db != null) {
// return _db;
// }
// _db = await _initDB();
// return _db;
return _db ??= await _initDB();
}
/// Initialize database
Future<Database> _initDB() async {
Directory directory = await getApplicationDocumentsDirectory();
String path = join(directory.path, "dbName");
return await openDatabase(
path,
version: 1,
onCreate: _onCreate,
onUpgrade: _onUpgrade,
);
}
/// Create table
Future _onCreate(Database db, int version) async {
const String sql = """
CREATE TABLE Student(
id INTEGER primary key AUTOINCREMENT,
name TEXT,
age INTEGER,
sex INTEGER
)
""";
return await db.execute(sql);
}
/// Update table
Future _onUpgrade(Database db, int oldVersion, int newVersion) async {}
/// Save the data
Future saveData(Student student) async {
var _db = await db;
return await _db?.insert("Student", student.toJson());
}
/// Use SQL Save the data
Future saveDataBySQL(Student student) async {
const String sql = """
INSERT INTO Student(name,age,sex) values(?,?,?)
""";
var _db = await db;
return await _db?.rawInsert(sql, [student.name, student.age, student.sex]);
}
/// Query all data
Future<List<Student>?> findAll() async {
var _db = await db;
List<Map<String, Object?>>? result = await _db?.query("Student");
if (result == null) {
return null;
} else {
if (result.isNotEmpty) {
return result.map((e) => Student.fromJson(e)).toList();
} else {
return [];
}
}
}
/// Conditions of the query
Future<List<Student>?> find(int age) async {
var _db = await db;
List<Map<String, dynamic>>? result = await _db?.query("Student", where: "age=?", whereArgs: [age]);
if (result == null) {
return null;
} else {
if (result.isNotEmpty) {
return result.map((e) => Student.fromJson(e)).toList();
} else {
return [];
}
}
}
/// modify
Future<int> update(Student student) async {
var _db = await db;
student.age = 99;
int? count = await _db?.update("Student", student.toJson(), where: "id=?", whereArgs: [student.id]);
return count ?? 0;
}
/// Delete
Future<int> delete(int id) async {
var _db = await db;
int? count = await _db?.delete("Student", where: "id=?", whereArgs: [id]);
return count ?? 0;
}
/// Delete all
Future<int> deleteAll() async {
var _db = await db;
int? count = await _db?.delete("Student");
return count ?? 0;
}
}
Defining entity classes
Student studentFromJson(String str) => Student.fromJson(json.decode(str));
String studentToJson(Student data) => json.encode(data.toJson());
class Student {
Student({
this.id,
this.name,
this.age,
this.sex,
});
Student.fromJson(dynamic json) {
id = json['id'];
name = json['name'];
age = json['age'];
sex = json['sex'];
}
int? id;
String? name;
int? age;
int? sex;
Map<String, dynamic> toJson() {
final map = <String, dynamic>{};
map['id'] = id;
map['name'] = name;
map['age'] = age;
map['sex'] = sex;
return map;
}
}
Home code
class SqlitePage extends StatefulWidget {
const SqlitePage({Key? key}) : super(key: key);
@override
State<StatefulWidget> createState() {
return _SqlitePageState();
}
}
class _SqlitePageState extends State<SqlitePage> {
List<Student>? _studentList;
loadAllData() async {
_studentList = await DBManager().findAll();
setState(() {});
}
loadData() async {
_studentList = await DBManager().find(1);
setState(() {});
}
updateData(Student student) async {
var count = await DBManager().update(student);
if (count > 0) {
showSnackBar(context, " Modification successful ");
} else {
showSnackBar(context, " Modification failed ");
}
}
deleteData(int id) async {
var count = await DBManager().delete(id);
if (count > 0) {
showSnackBar(context, " Delete successful ");
} else {
showSnackBar(context, " Delete failed ");
}
}
deleteAllData() async {
var count = await DBManager().deleteAll();
if (count > 0) {
showSnackBar(context, " Delete successful ");
} else {
showSnackBar(context, " Delete failed ");
}
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text("SQLite"),
actions: [
IconButton(
icon: const Icon(Icons.add),
onPressed: () {
Navigator.push(context, MaterialPageRoute(builder: (context) {
return const AddStudentPage();
}));
},
)
],
),
body: SingleChildScrollView(
child: Center(
child: Column(
children: [
ElevatedButton(
onPressed: () {
loadAllData();
},
child: const Text(" Query all the data "),
),
ElevatedButton(
onPressed: () {
loadData();
},
child: const Text(" Conditions of the query "),
),
ElevatedButton(
onPressed: () {
deleteAllData();
},
child: const Text(" Delete all "),
),
Padding(
padding: const EdgeInsets.all(10),
child: _buildTable(),
),
],
),
),
),
);
}
_buildTable() {
return Table(
border: TableBorder.all(),
defaultVerticalAlignment: TableCellVerticalAlignment.middle,
children: [
const TableRow(children: [
TableCell(child: Text("id")),
TableCell(child: Text(" full name ")),
TableCell(child: Text(" Age ")),
TableCell(child: Text(" Gender ")),
TableCell(child: Text(" modify ")),
TableCell(child: Text(" Delete ")),
]),
...?_studentList
?.map((e) => TableRow(children: [
TableCell(child: Text("${e.id}")),
TableCell(child: Text("${e.name}")),
TableCell(child: Text("${e.age}")),
TableCell(child: Text("${e.sex}")),
TableCell(
child: TextButton(
onPressed: () {
updateData(e);
},
child: const Text(" modify "),
),
),
TableCell(
child: TextButton(
onPressed: () {
deleteData(e.id!);
},
child: const Text(" Delete "),
),
),
]))
.toList(),
],
);
}
}
Add data pages
class AddStudentPage extends StatefulWidget {
const AddStudentPage({Key? key}) : super(key: key);
@override
State<StatefulWidget> createState() {
return _AddStudentPageState();
}
}
class _AddStudentPageState extends State<AddStudentPage> {
int _sexValue = 0;
late TextEditingController _nameController;
late TextEditingController _ageController;
@override
void initState() {
_nameController = TextEditingController();
_ageController = TextEditingController();
super.initState();
}
@override
void dispose() {
_nameController.dispose();
_ageController.dispose();
super.dispose();
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text(" Add students "),
),
body: Padding(
padding: const EdgeInsets.all(8.0),
child: Column(
children: [
TextField(
controller: _nameController,
decoration: const InputDecoration(labelText: " full name :"),
),
TextField(
controller: _ageController,
decoration: const InputDecoration(labelText: " Age :"),
inputFormatters: [
FilteringTextInputFormatter.digitsOnly,
],
),
Row(
children: [
Expanded(
child: RadioListTile<int>(
title: const Text(" Woman "),
value: 0,
groupValue: _sexValue,
onChanged: (value) {
setState(() {
_sexValue = value!;
});
},
),
),
Expanded(
child: RadioListTile<int>(
title: const Text(" male "),
value: 1,
groupValue: _sexValue,
onChanged: (value) {
setState(() {
_sexValue = value!;
});
},
),
),
],
),
Builder(builder: (BuildContext context) {
return Column(
children: [
ElevatedButton(
onPressed: () async {
var student = Student(
name: _nameController.text.toString(),
age: int.parse(_ageController.text.toString()),
sex: _sexValue,
);
int result = await DBManager().saveData(student);
if (result > 0) {
showSnackBar(context, ' Data saved successfully ,result:$result');
} else {
showSnackBar(context, ' Failed to save data ,result:$result');
}
},
child: const Text(" Save the data "),
),
ElevatedButton(
onPressed: () async {
var student = Student(
name: _nameController.text.toString(),
age: int.parse(_ageController.text.toString()),
sex: _sexValue,
);
int result = await DBManager().saveDataBySQL(student);
if (result > 0) {
showSnackBar(context, ' Data saved successfully ,result:$result');
} else {
showSnackBar(context, ' Failed to save data ,result:$result');
}
},
child: const Text(" Use SQL Save the data "),
),
],
);
}),
],
),
),
);
}
}
边栏推荐
- 流量管理技术
- 学历、长相、家境普通的人,未来的发展方向是什么?00后的职业规划都已经整得明明白白......
- The sky is blue and misty
- 软件测试中功能测试流程
- 简单的两个圆球loading加载
- I spent tens of thousands of dollars to learn and bring goods: I earned 3 yuan in three days, and the transaction depends on the bill
- Router. use() requires a middleware function but got a Object
- 逆向调试入门-PE结构-输入表输出表05/07
- China NdYAG crystal market research conclusion and development strategy proposal report Ⓥ 2022 ~ 2028
- 运行Powershell脚本提示“因为在此系统上禁止运行脚本”解决办法
猜你喜欢
[Niu Ke's questions -sql big factory interview real questions] no2 User growth scenario (a certain degree of information flow)
Redis explores cache consistency
ZABBIX 6.0 source code installation and ha configuration
codeforces -- 4B. Before an Exam
Wang Xing's infinite game ushers in the "ultimate" battle
Vs code setting Click to open a new file window without overwriting the previous window
Fiori applications are shared through the enhancement of adaptation project
leetcode:329. The longest incremental path in the matrix [DFS + cache + no backtracking + elegance]
The popular major I chose became "Tiankeng" four years later
1553B环境搭建
随机推荐
Nexus builds NPM dependent private database
oracle cdc 数据传输时,clob类型字段,在update时值会丢失,update前有值,但
MySQL Replication中的并行复制示例详解
CV顶会最佳论文得主分享:好论文是怎么炼成的?
从数据库中更新一条数据,用cdc会同时获得op字段分别为d和c的两条数据吗?我记得之前是只有op为u
Feign & Eureka & Zuul & Hystrix 流程
商汤科技崩盘 :IPO时已写好的剧本
Svg diamond style code
Tencent always takes epoll, which is annoying
What are the solutions for session sharing of highly paid programmers & interview questions series 118?
Reasons for MySQL reporting 1040too many connections and Solutions
MySQL报错1040Too many connections的原因以及解决方案
5G工业网关的科技治超应用 超限超重超速非现场联合执法
Who should I know when opening a stock account? Is it actually safe to open an account online?
请问flink mysql cdc 全量读取mysql某个表数据,对原始的mysql数据库有影响吗
Zabbix 6.0 源码安装以及 HA 配置
Report on the "14th five year plan" and scale prospect prediction of China's laser processing equipment manufacturing industry Ⓢ 2022 ~ 2028
Meta再放大招!VR新模型登CVPR Oral:像人一样「读」懂语音
Topic 1004: the story of cows (recursion)
R language uses conf of yardstick package_ The mat function calculates the confusion matrix of the multiclass model on each fold of each cross validation (or resampling), and uses the summary to outpu