-
Notifications
You must be signed in to change notification settings - Fork 11
/
Copy pathweb.dart
98 lines (89 loc) · 3.75 KB
/
web.dart
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
/// Exposes interfaces implemented by database implementations on the web.
///
/// These expose methods allowing database instances to be shared across web
/// workers.
library sqlite_async.web;
import 'package:sqlite3_web/sqlite3_web.dart';
import 'package:web/web.dart';
import 'sqlite_async.dart';
import 'src/web/database.dart';
/// An endpoint that can be used, by any running JavaScript context in the same
/// website, to connect to an existing [WebSqliteConnection].
///
/// These endpoints are created by calling [WebSqliteConnection.exposeEndpoint]
/// and consist of a [MessagePort] and two [String]s internally identifying the
/// connection. Both objects can be transferred over send ports towards another
/// worker or context. That context can then use
/// [WebSqliteConnection.connectToEndpoint] to connect to the port already
/// opened.
typedef WebDatabaseEndpoint = ({
MessagePort connectPort,
String connectName,
String? lockName,
});
/// A [SqliteConnection] interface implemented by opened connections when
/// running on the web.
///
/// This adds the [exposeEndpoint], which uses `dart:js_interop` types not
/// supported on native Dart platforms. The method can be used to access an
/// opened database across different JavaScript contexts
/// (e.g. document windows and workers).
abstract class WebSqliteConnection implements SqliteConnection {
/// Returns a future that completes when this connection is closed.
///
/// This usually only happens when calling [close], but on the web
/// specifically, it can also happen when a remote context closes a database
/// accessed via [connectToEndpoint].
Future<void> get closedFuture;
/// Returns a [WebDatabaseEndpoint] - a structure that consists only of types
/// that can be transferred across a [MessagePort] in JavaScript.
///
/// After transferring this endpoint to another JavaScript context (e.g. a
/// worker), the worker can call [connectToEndpoint] to obtain a connection to
/// the same sqlite database.
Future<WebDatabaseEndpoint> exposeEndpoint();
/// Connect to an endpoint obtained through [exposeEndpoint].
///
/// The endpoint is transferrable in JavaScript, allowing multiple JavaScript
/// contexts to exchange opened database connections.
static Future<WebSqliteConnection> connectToEndpoint(
WebDatabaseEndpoint endpoint) async {
final rawSqlite = await WebSqlite.connectToPort(
(endpoint.connectPort, endpoint.connectName));
final database = WebDatabase(
rawSqlite,
switch (endpoint.lockName) {
var lock? => Mutex(identifier: lock),
null => null,
},
);
return database;
}
/// Same as [SqliteConnection.writeLock].
///
/// Has an additional [flush] (defaults to true). This can be set to false
/// to delay flushing changes to the database file, losing durability guarantees.
/// This only has an effect when IndexedDB storage is used.
///
/// See [flush] for details.
Future<T> writeLock<T>(Future<T> Function(SqliteWriteContext tx) callback,
{Duration? lockTimeout, String? debugContext, bool? flush});
/// Same as [SqliteConnection.writeTransaction].
///
/// Has an additional [flush] (defaults to true). This can be set to false
/// to delay flushing changes to the database file, losing durability guarantees.
/// This only has an effect when IndexedDB storage is used.
///
/// See [flush] for details.
Future<T> writeTransaction<T>(
Future<T> Function(SqliteWriteContext tx) callback,
{Duration? lockTimeout,
bool? flush});
/// Flush changes to the underlying storage.
///
/// When this returns, all changes previously written will be persisted
/// to storage.
///
/// This only has an effect when IndexedDB storage is used.
Future<void> flush();
}