mirror of
https://github.com/twonlyapp/twonly-app.git
synced 2026-01-15 09:28:41 +00:00
fix #172
This commit is contained in:
parent
f3c9dbb796
commit
87bc1ed824
18 changed files with 3909 additions and 402 deletions
1
drift_schemas/twonly_database/drift_schema_v9.json
Normal file
1
drift_schemas/twonly_database/drift_schema_v9.json
Normal file
File diff suppressed because one or more lines are too long
|
|
@ -129,8 +129,8 @@ class _AppState extends State<App> with WidgetsBindingObserver {
|
||||||
themeMode: context.watch<SettingsChangeProvider>().themeMode,
|
themeMode: context.watch<SettingsChangeProvider>().themeMode,
|
||||||
initialRoute: '/',
|
initialRoute: '/',
|
||||||
routes: {
|
routes: {
|
||||||
"/": (context) => AppMainWidget(initialPage: 0),
|
"/": (context) => AppMainWidget(initialPage: 1),
|
||||||
"/chats": (context) => AppMainWidget(initialPage: 1)
|
"/chats": (context) => AppMainWidget(initialPage: 0)
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
|
|
|
||||||
|
|
@ -2,16 +2,18 @@ import 'dart:convert';
|
||||||
import 'package:drift/drift.dart';
|
import 'package:drift/drift.dart';
|
||||||
|
|
||||||
enum UploadState {
|
enum UploadState {
|
||||||
pending,
|
// legacy
|
||||||
addedToMessagesDb,
|
addedToMessagesDb,
|
||||||
// added .compressed to filename
|
|
||||||
isCompressed,
|
isCompressed,
|
||||||
// added .encypted to filename
|
|
||||||
isEncrypted,
|
isEncrypted,
|
||||||
hasUploadToken,
|
hasUploadToken,
|
||||||
isUploaded,
|
isUploaded,
|
||||||
|
// ^^ legacy ^^
|
||||||
|
|
||||||
|
pending,
|
||||||
|
readyToUpload,
|
||||||
receiverNotified,
|
receiverNotified,
|
||||||
// after all users notified all media files that are not storeable by the other person will be deleted
|
// after all users notified all media files that are not storable by the other person will be deleted
|
||||||
}
|
}
|
||||||
|
|
||||||
@DataClassName('MediaUpload')
|
@DataClassName('MediaUpload')
|
||||||
|
|
@ -20,7 +22,8 @@ class MediaUploads extends Table {
|
||||||
TextColumn get state =>
|
TextColumn get state =>
|
||||||
textEnum<UploadState>().withDefault(Constant(UploadState.pending.name))();
|
textEnum<UploadState>().withDefault(Constant(UploadState.pending.name))();
|
||||||
|
|
||||||
TextColumn get metadata => text().map(MediaUploadMetadataConverter())();
|
TextColumn get metadata =>
|
||||||
|
text().map(MediaUploadMetadataConverter()).nullable()();
|
||||||
|
|
||||||
/// exists in UploadState.addedToMessagesDb
|
/// exists in UploadState.addedToMessagesDb
|
||||||
TextColumn get messageIds => text().map(IntListTypeConverter()).nullable()();
|
TextColumn get messageIds => text().map(IntListTypeConverter()).nullable()();
|
||||||
|
|
|
||||||
|
|
@ -43,7 +43,7 @@ class TwonlyDatabase extends _$TwonlyDatabase {
|
||||||
TwonlyDatabase.forTesting(DatabaseConnection super.connection);
|
TwonlyDatabase.forTesting(DatabaseConnection super.connection);
|
||||||
|
|
||||||
@override
|
@override
|
||||||
int get schemaVersion => 8;
|
int get schemaVersion => 9;
|
||||||
|
|
||||||
static QueryExecutor _openConnection() {
|
static QueryExecutor _openConnection() {
|
||||||
return driftDatabase(
|
return driftDatabase(
|
||||||
|
|
@ -57,34 +57,34 @@ class TwonlyDatabase extends _$TwonlyDatabase {
|
||||||
@override
|
@override
|
||||||
MigrationStrategy get migration {
|
MigrationStrategy get migration {
|
||||||
return MigrationStrategy(
|
return MigrationStrategy(
|
||||||
onUpgrade: stepByStep(
|
onUpgrade: stepByStep(from1To2: (m, schema) async {
|
||||||
from1To2: (m, schema) async {
|
m.addColumn(schema.messages, schema.messages.errorWhileSending);
|
||||||
m.addColumn(schema.messages, schema.messages.errorWhileSending);
|
}, from2To3: (m, schema) async {
|
||||||
},
|
m.addColumn(schema.contacts, schema.contacts.archived);
|
||||||
from2To3: (m, schema) async {
|
m.addColumn(
|
||||||
m.addColumn(schema.contacts, schema.contacts.archived);
|
schema.contacts, schema.contacts.deleteMessagesAfterXMinutes);
|
||||||
m.addColumn(
|
}, from3To4: (m, schema) async {
|
||||||
schema.contacts, schema.contacts.deleteMessagesAfterXMinutes);
|
m.createTable(mediaUploads);
|
||||||
},
|
}, from4To5: (m, schema) async {
|
||||||
from3To4: (m, schema) async {
|
m.createTable(mediaDownloads);
|
||||||
m.createTable(mediaUploads);
|
m.addColumn(schema.messages, schema.messages.mediaDownloadId);
|
||||||
},
|
m.addColumn(schema.messages, schema.messages.mediaUploadId);
|
||||||
from4To5: (m, schema) async {
|
}, from5To6: (m, schema) async {
|
||||||
m.createTable(mediaDownloads);
|
m.addColumn(schema.messages, schema.messages.mediaStored);
|
||||||
m.addColumn(schema.messages, schema.messages.mediaDownloadId);
|
}, from6To7: (m, schema) async {
|
||||||
m.addColumn(schema.messages, schema.messages.mediaUploadId);
|
m.addColumn(schema.contacts, schema.contacts.pinned);
|
||||||
},
|
}, from7To8: (m, schema) async {
|
||||||
from5To6: (m, schema) async {
|
m.addColumn(schema.contacts, schema.contacts.alsoBestFriend);
|
||||||
m.addColumn(schema.messages, schema.messages.mediaStored);
|
m.addColumn(schema.contacts, schema.contacts.lastFlameSync);
|
||||||
},
|
}, from8To9: (m, schema) async {
|
||||||
from6To7: (m, schema) async {
|
await m.alterTable(TableMigration(
|
||||||
m.addColumn(schema.contacts, schema.contacts.pinned);
|
schema.mediaUploads,
|
||||||
},
|
columnTransformer: {
|
||||||
from7To8: (m, schema) async {
|
schema.mediaUploads.metadata:
|
||||||
m.addColumn(schema.contacts, schema.contacts.alsoBestFriend);
|
schema.mediaUploads.metadata.cast<String>(),
|
||||||
m.addColumn(schema.contacts, schema.contacts.lastFlameSync);
|
},
|
||||||
},
|
));
|
||||||
),
|
}),
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1934,11 +1934,11 @@ class $MediaUploadsTable extends MediaUploads
|
||||||
defaultValue: Constant(UploadState.pending.name))
|
defaultValue: Constant(UploadState.pending.name))
|
||||||
.withConverter<UploadState>($MediaUploadsTable.$converterstate);
|
.withConverter<UploadState>($MediaUploadsTable.$converterstate);
|
||||||
@override
|
@override
|
||||||
late final GeneratedColumnWithTypeConverter<MediaUploadMetadata, String>
|
late final GeneratedColumnWithTypeConverter<MediaUploadMetadata?, String>
|
||||||
metadata = GeneratedColumn<String>('metadata', aliasedName, false,
|
metadata = GeneratedColumn<String>('metadata', aliasedName, true,
|
||||||
type: DriftSqlType.string, requiredDuringInsert: true)
|
type: DriftSqlType.string, requiredDuringInsert: false)
|
||||||
.withConverter<MediaUploadMetadata>(
|
.withConverter<MediaUploadMetadata?>(
|
||||||
$MediaUploadsTable.$convertermetadata);
|
$MediaUploadsTable.$convertermetadatan);
|
||||||
@override
|
@override
|
||||||
late final GeneratedColumnWithTypeConverter<List<int>?, String> messageIds =
|
late final GeneratedColumnWithTypeConverter<List<int>?, String> messageIds =
|
||||||
GeneratedColumn<String>('message_ids', aliasedName, true,
|
GeneratedColumn<String>('message_ids', aliasedName, true,
|
||||||
|
|
@ -2006,9 +2006,9 @@ class $MediaUploadsTable extends MediaUploads
|
||||||
state: $MediaUploadsTable.$converterstate.fromSql(attachedDatabase
|
state: $MediaUploadsTable.$converterstate.fromSql(attachedDatabase
|
||||||
.typeMapping
|
.typeMapping
|
||||||
.read(DriftSqlType.string, data['${effectivePrefix}state'])!),
|
.read(DriftSqlType.string, data['${effectivePrefix}state'])!),
|
||||||
metadata: $MediaUploadsTable.$convertermetadata.fromSql(attachedDatabase
|
metadata: $MediaUploadsTable.$convertermetadatan.fromSql(attachedDatabase
|
||||||
.typeMapping
|
.typeMapping
|
||||||
.read(DriftSqlType.string, data['${effectivePrefix}metadata'])!),
|
.read(DriftSqlType.string, data['${effectivePrefix}metadata'])),
|
||||||
messageIds: $MediaUploadsTable.$convertermessageIdsn.fromSql(
|
messageIds: $MediaUploadsTable.$convertermessageIdsn.fromSql(
|
||||||
attachedDatabase.typeMapping.read(
|
attachedDatabase.typeMapping.read(
|
||||||
DriftSqlType.string, data['${effectivePrefix}message_ids'])),
|
DriftSqlType.string, data['${effectivePrefix}message_ids'])),
|
||||||
|
|
@ -2033,6 +2033,9 @@ class $MediaUploadsTable extends MediaUploads
|
||||||
const EnumNameConverter<UploadState>(UploadState.values);
|
const EnumNameConverter<UploadState>(UploadState.values);
|
||||||
static JsonTypeConverter2<MediaUploadMetadata, String, Map<String, Object?>>
|
static JsonTypeConverter2<MediaUploadMetadata, String, Map<String, Object?>>
|
||||||
$convertermetadata = MediaUploadMetadataConverter();
|
$convertermetadata = MediaUploadMetadataConverter();
|
||||||
|
static JsonTypeConverter2<MediaUploadMetadata?, String?,
|
||||||
|
Map<String, Object?>?> $convertermetadatan =
|
||||||
|
JsonTypeConverter2.asNullable($convertermetadata);
|
||||||
static TypeConverter<List<int>, String> $convertermessageIds =
|
static TypeConverter<List<int>, String> $convertermessageIds =
|
||||||
IntListTypeConverter();
|
IntListTypeConverter();
|
||||||
static TypeConverter<List<int>?, String?> $convertermessageIdsn =
|
static TypeConverter<List<int>?, String?> $convertermessageIdsn =
|
||||||
|
|
@ -2054,7 +2057,7 @@ class $MediaUploadsTable extends MediaUploads
|
||||||
class MediaUpload extends DataClass implements Insertable<MediaUpload> {
|
class MediaUpload extends DataClass implements Insertable<MediaUpload> {
|
||||||
final int mediaUploadId;
|
final int mediaUploadId;
|
||||||
final UploadState state;
|
final UploadState state;
|
||||||
final MediaUploadMetadata metadata;
|
final MediaUploadMetadata? metadata;
|
||||||
|
|
||||||
/// exists in UploadState.addedToMessagesDb
|
/// exists in UploadState.addedToMessagesDb
|
||||||
final List<int>? messageIds;
|
final List<int>? messageIds;
|
||||||
|
|
@ -2070,7 +2073,7 @@ class MediaUpload extends DataClass implements Insertable<MediaUpload> {
|
||||||
const MediaUpload(
|
const MediaUpload(
|
||||||
{required this.mediaUploadId,
|
{required this.mediaUploadId,
|
||||||
required this.state,
|
required this.state,
|
||||||
required this.metadata,
|
this.metadata,
|
||||||
this.messageIds,
|
this.messageIds,
|
||||||
this.encryptionData,
|
this.encryptionData,
|
||||||
this.uploadTokens,
|
this.uploadTokens,
|
||||||
|
|
@ -2083,9 +2086,9 @@ class MediaUpload extends DataClass implements Insertable<MediaUpload> {
|
||||||
map['state'] =
|
map['state'] =
|
||||||
Variable<String>($MediaUploadsTable.$converterstate.toSql(state));
|
Variable<String>($MediaUploadsTable.$converterstate.toSql(state));
|
||||||
}
|
}
|
||||||
{
|
if (!nullToAbsent || metadata != null) {
|
||||||
map['metadata'] = Variable<String>(
|
map['metadata'] = Variable<String>(
|
||||||
$MediaUploadsTable.$convertermetadata.toSql(metadata));
|
$MediaUploadsTable.$convertermetadatan.toSql(metadata));
|
||||||
}
|
}
|
||||||
if (!nullToAbsent || messageIds != null) {
|
if (!nullToAbsent || messageIds != null) {
|
||||||
map['message_ids'] = Variable<String>(
|
map['message_ids'] = Variable<String>(
|
||||||
|
|
@ -2110,7 +2113,9 @@ class MediaUpload extends DataClass implements Insertable<MediaUpload> {
|
||||||
return MediaUploadsCompanion(
|
return MediaUploadsCompanion(
|
||||||
mediaUploadId: Value(mediaUploadId),
|
mediaUploadId: Value(mediaUploadId),
|
||||||
state: Value(state),
|
state: Value(state),
|
||||||
metadata: Value(metadata),
|
metadata: metadata == null && nullToAbsent
|
||||||
|
? const Value.absent()
|
||||||
|
: Value(metadata),
|
||||||
messageIds: messageIds == null && nullToAbsent
|
messageIds: messageIds == null && nullToAbsent
|
||||||
? const Value.absent()
|
? const Value.absent()
|
||||||
: Value(messageIds),
|
: Value(messageIds),
|
||||||
|
|
@ -2131,8 +2136,8 @@ class MediaUpload extends DataClass implements Insertable<MediaUpload> {
|
||||||
mediaUploadId: serializer.fromJson<int>(json['mediaUploadId']),
|
mediaUploadId: serializer.fromJson<int>(json['mediaUploadId']),
|
||||||
state: $MediaUploadsTable.$converterstate
|
state: $MediaUploadsTable.$converterstate
|
||||||
.fromJson(serializer.fromJson<String>(json['state'])),
|
.fromJson(serializer.fromJson<String>(json['state'])),
|
||||||
metadata: $MediaUploadsTable.$convertermetadata.fromJson(
|
metadata: $MediaUploadsTable.$convertermetadatan.fromJson(
|
||||||
serializer.fromJson<Map<String, Object?>>(json['metadata'])),
|
serializer.fromJson<Map<String, Object?>?>(json['metadata'])),
|
||||||
messageIds: serializer.fromJson<List<int>?>(json['messageIds']),
|
messageIds: serializer.fromJson<List<int>?>(json['messageIds']),
|
||||||
encryptionData: $MediaUploadsTable.$converterencryptionDatan.fromJson(
|
encryptionData: $MediaUploadsTable.$converterencryptionDatan.fromJson(
|
||||||
serializer.fromJson<Map<String, Object?>?>(json['encryptionData'])),
|
serializer.fromJson<Map<String, Object?>?>(json['encryptionData'])),
|
||||||
|
|
@ -2148,8 +2153,8 @@ class MediaUpload extends DataClass implements Insertable<MediaUpload> {
|
||||||
'mediaUploadId': serializer.toJson<int>(mediaUploadId),
|
'mediaUploadId': serializer.toJson<int>(mediaUploadId),
|
||||||
'state': serializer
|
'state': serializer
|
||||||
.toJson<String>($MediaUploadsTable.$converterstate.toJson(state)),
|
.toJson<String>($MediaUploadsTable.$converterstate.toJson(state)),
|
||||||
'metadata': serializer.toJson<Map<String, Object?>>(
|
'metadata': serializer.toJson<Map<String, Object?>?>(
|
||||||
$MediaUploadsTable.$convertermetadata.toJson(metadata)),
|
$MediaUploadsTable.$convertermetadatan.toJson(metadata)),
|
||||||
'messageIds': serializer.toJson<List<int>?>(messageIds),
|
'messageIds': serializer.toJson<List<int>?>(messageIds),
|
||||||
'encryptionData': serializer.toJson<Map<String, Object?>?>(
|
'encryptionData': serializer.toJson<Map<String, Object?>?>(
|
||||||
$MediaUploadsTable.$converterencryptionDatan.toJson(encryptionData)),
|
$MediaUploadsTable.$converterencryptionDatan.toJson(encryptionData)),
|
||||||
|
|
@ -2162,7 +2167,7 @@ class MediaUpload extends DataClass implements Insertable<MediaUpload> {
|
||||||
MediaUpload copyWith(
|
MediaUpload copyWith(
|
||||||
{int? mediaUploadId,
|
{int? mediaUploadId,
|
||||||
UploadState? state,
|
UploadState? state,
|
||||||
MediaUploadMetadata? metadata,
|
Value<MediaUploadMetadata?> metadata = const Value.absent(),
|
||||||
Value<List<int>?> messageIds = const Value.absent(),
|
Value<List<int>?> messageIds = const Value.absent(),
|
||||||
Value<MediaEncryptionData?> encryptionData = const Value.absent(),
|
Value<MediaEncryptionData?> encryptionData = const Value.absent(),
|
||||||
Value<MediaUploadTokens?> uploadTokens = const Value.absent(),
|
Value<MediaUploadTokens?> uploadTokens = const Value.absent(),
|
||||||
|
|
@ -2170,7 +2175,7 @@ class MediaUpload extends DataClass implements Insertable<MediaUpload> {
|
||||||
MediaUpload(
|
MediaUpload(
|
||||||
mediaUploadId: mediaUploadId ?? this.mediaUploadId,
|
mediaUploadId: mediaUploadId ?? this.mediaUploadId,
|
||||||
state: state ?? this.state,
|
state: state ?? this.state,
|
||||||
metadata: metadata ?? this.metadata,
|
metadata: metadata.present ? metadata.value : this.metadata,
|
||||||
messageIds: messageIds.present ? messageIds.value : this.messageIds,
|
messageIds: messageIds.present ? messageIds.value : this.messageIds,
|
||||||
encryptionData:
|
encryptionData:
|
||||||
encryptionData.present ? encryptionData.value : this.encryptionData,
|
encryptionData.present ? encryptionData.value : this.encryptionData,
|
||||||
|
|
@ -2232,7 +2237,7 @@ class MediaUpload extends DataClass implements Insertable<MediaUpload> {
|
||||||
class MediaUploadsCompanion extends UpdateCompanion<MediaUpload> {
|
class MediaUploadsCompanion extends UpdateCompanion<MediaUpload> {
|
||||||
final Value<int> mediaUploadId;
|
final Value<int> mediaUploadId;
|
||||||
final Value<UploadState> state;
|
final Value<UploadState> state;
|
||||||
final Value<MediaUploadMetadata> metadata;
|
final Value<MediaUploadMetadata?> metadata;
|
||||||
final Value<List<int>?> messageIds;
|
final Value<List<int>?> messageIds;
|
||||||
final Value<MediaEncryptionData?> encryptionData;
|
final Value<MediaEncryptionData?> encryptionData;
|
||||||
final Value<MediaUploadTokens?> uploadTokens;
|
final Value<MediaUploadTokens?> uploadTokens;
|
||||||
|
|
@ -2249,12 +2254,12 @@ class MediaUploadsCompanion extends UpdateCompanion<MediaUpload> {
|
||||||
MediaUploadsCompanion.insert({
|
MediaUploadsCompanion.insert({
|
||||||
this.mediaUploadId = const Value.absent(),
|
this.mediaUploadId = const Value.absent(),
|
||||||
this.state = const Value.absent(),
|
this.state = const Value.absent(),
|
||||||
required MediaUploadMetadata metadata,
|
this.metadata = const Value.absent(),
|
||||||
this.messageIds = const Value.absent(),
|
this.messageIds = const Value.absent(),
|
||||||
this.encryptionData = const Value.absent(),
|
this.encryptionData = const Value.absent(),
|
||||||
this.uploadTokens = const Value.absent(),
|
this.uploadTokens = const Value.absent(),
|
||||||
this.alreadyNotified = const Value.absent(),
|
this.alreadyNotified = const Value.absent(),
|
||||||
}) : metadata = Value(metadata);
|
});
|
||||||
static Insertable<MediaUpload> custom({
|
static Insertable<MediaUpload> custom({
|
||||||
Expression<int>? mediaUploadId,
|
Expression<int>? mediaUploadId,
|
||||||
Expression<String>? state,
|
Expression<String>? state,
|
||||||
|
|
@ -2278,7 +2283,7 @@ class MediaUploadsCompanion extends UpdateCompanion<MediaUpload> {
|
||||||
MediaUploadsCompanion copyWith(
|
MediaUploadsCompanion copyWith(
|
||||||
{Value<int>? mediaUploadId,
|
{Value<int>? mediaUploadId,
|
||||||
Value<UploadState>? state,
|
Value<UploadState>? state,
|
||||||
Value<MediaUploadMetadata>? metadata,
|
Value<MediaUploadMetadata?>? metadata,
|
||||||
Value<List<int>?>? messageIds,
|
Value<List<int>?>? messageIds,
|
||||||
Value<MediaEncryptionData?>? encryptionData,
|
Value<MediaEncryptionData?>? encryptionData,
|
||||||
Value<MediaUploadTokens?>? uploadTokens,
|
Value<MediaUploadTokens?>? uploadTokens,
|
||||||
|
|
@ -2306,7 +2311,7 @@ class MediaUploadsCompanion extends UpdateCompanion<MediaUpload> {
|
||||||
}
|
}
|
||||||
if (metadata.present) {
|
if (metadata.present) {
|
||||||
map['metadata'] = Variable<String>(
|
map['metadata'] = Variable<String>(
|
||||||
$MediaUploadsTable.$convertermetadata.toSql(metadata.value));
|
$MediaUploadsTable.$convertermetadatan.toSql(metadata.value));
|
||||||
}
|
}
|
||||||
if (messageIds.present) {
|
if (messageIds.present) {
|
||||||
map['message_ids'] = Variable<String>(
|
map['message_ids'] = Variable<String>(
|
||||||
|
|
@ -4549,7 +4554,7 @@ typedef $$MediaUploadsTableCreateCompanionBuilder = MediaUploadsCompanion
|
||||||
Function({
|
Function({
|
||||||
Value<int> mediaUploadId,
|
Value<int> mediaUploadId,
|
||||||
Value<UploadState> state,
|
Value<UploadState> state,
|
||||||
required MediaUploadMetadata metadata,
|
Value<MediaUploadMetadata?> metadata,
|
||||||
Value<List<int>?> messageIds,
|
Value<List<int>?> messageIds,
|
||||||
Value<MediaEncryptionData?> encryptionData,
|
Value<MediaEncryptionData?> encryptionData,
|
||||||
Value<MediaUploadTokens?> uploadTokens,
|
Value<MediaUploadTokens?> uploadTokens,
|
||||||
|
|
@ -4559,7 +4564,7 @@ typedef $$MediaUploadsTableUpdateCompanionBuilder = MediaUploadsCompanion
|
||||||
Function({
|
Function({
|
||||||
Value<int> mediaUploadId,
|
Value<int> mediaUploadId,
|
||||||
Value<UploadState> state,
|
Value<UploadState> state,
|
||||||
Value<MediaUploadMetadata> metadata,
|
Value<MediaUploadMetadata?> metadata,
|
||||||
Value<List<int>?> messageIds,
|
Value<List<int>?> messageIds,
|
||||||
Value<MediaEncryptionData?> encryptionData,
|
Value<MediaEncryptionData?> encryptionData,
|
||||||
Value<MediaUploadTokens?> uploadTokens,
|
Value<MediaUploadTokens?> uploadTokens,
|
||||||
|
|
@ -4583,7 +4588,7 @@ class $$MediaUploadsTableFilterComposer
|
||||||
column: $table.state,
|
column: $table.state,
|
||||||
builder: (column) => ColumnWithTypeConverterFilters(column));
|
builder: (column) => ColumnWithTypeConverterFilters(column));
|
||||||
|
|
||||||
ColumnWithTypeConverterFilters<MediaUploadMetadata, MediaUploadMetadata,
|
ColumnWithTypeConverterFilters<MediaUploadMetadata?, MediaUploadMetadata,
|
||||||
String>
|
String>
|
||||||
get metadata => $composableBuilder(
|
get metadata => $composableBuilder(
|
||||||
column: $table.metadata,
|
column: $table.metadata,
|
||||||
|
|
@ -4661,7 +4666,7 @@ class $$MediaUploadsTableAnnotationComposer
|
||||||
GeneratedColumnWithTypeConverter<UploadState, String> get state =>
|
GeneratedColumnWithTypeConverter<UploadState, String> get state =>
|
||||||
$composableBuilder(column: $table.state, builder: (column) => column);
|
$composableBuilder(column: $table.state, builder: (column) => column);
|
||||||
|
|
||||||
GeneratedColumnWithTypeConverter<MediaUploadMetadata, String> get metadata =>
|
GeneratedColumnWithTypeConverter<MediaUploadMetadata?, String> get metadata =>
|
||||||
$composableBuilder(column: $table.metadata, builder: (column) => column);
|
$composableBuilder(column: $table.metadata, builder: (column) => column);
|
||||||
|
|
||||||
GeneratedColumnWithTypeConverter<List<int>?, String> get messageIds =>
|
GeneratedColumnWithTypeConverter<List<int>?, String> get messageIds =>
|
||||||
|
|
@ -4709,7 +4714,7 @@ class $$MediaUploadsTableTableManager extends RootTableManager<
|
||||||
updateCompanionCallback: ({
|
updateCompanionCallback: ({
|
||||||
Value<int> mediaUploadId = const Value.absent(),
|
Value<int> mediaUploadId = const Value.absent(),
|
||||||
Value<UploadState> state = const Value.absent(),
|
Value<UploadState> state = const Value.absent(),
|
||||||
Value<MediaUploadMetadata> metadata = const Value.absent(),
|
Value<MediaUploadMetadata?> metadata = const Value.absent(),
|
||||||
Value<List<int>?> messageIds = const Value.absent(),
|
Value<List<int>?> messageIds = const Value.absent(),
|
||||||
Value<MediaEncryptionData?> encryptionData = const Value.absent(),
|
Value<MediaEncryptionData?> encryptionData = const Value.absent(),
|
||||||
Value<MediaUploadTokens?> uploadTokens = const Value.absent(),
|
Value<MediaUploadTokens?> uploadTokens = const Value.absent(),
|
||||||
|
|
@ -4727,7 +4732,7 @@ class $$MediaUploadsTableTableManager extends RootTableManager<
|
||||||
createCompanionCallback: ({
|
createCompanionCallback: ({
|
||||||
Value<int> mediaUploadId = const Value.absent(),
|
Value<int> mediaUploadId = const Value.absent(),
|
||||||
Value<UploadState> state = const Value.absent(),
|
Value<UploadState> state = const Value.absent(),
|
||||||
required MediaUploadMetadata metadata,
|
Value<MediaUploadMetadata?> metadata = const Value.absent(),
|
||||||
Value<List<int>?> messageIds = const Value.absent(),
|
Value<List<int>?> messageIds = const Value.absent(),
|
||||||
Value<MediaEncryptionData?> encryptionData = const Value.absent(),
|
Value<MediaEncryptionData?> encryptionData = const Value.absent(),
|
||||||
Value<MediaUploadTokens?> uploadTokens = const Value.absent(),
|
Value<MediaUploadTokens?> uploadTokens = const Value.absent(),
|
||||||
|
|
|
||||||
|
|
@ -1701,6 +1701,184 @@ i1.GeneratedColumn<bool> _column_54(String aliasedName) =>
|
||||||
i1.GeneratedColumn<DateTime> _column_55(String aliasedName) =>
|
i1.GeneratedColumn<DateTime> _column_55(String aliasedName) =>
|
||||||
i1.GeneratedColumn<DateTime>('last_flame_sync', aliasedName, true,
|
i1.GeneratedColumn<DateTime>('last_flame_sync', aliasedName, true,
|
||||||
type: i1.DriftSqlType.dateTime);
|
type: i1.DriftSqlType.dateTime);
|
||||||
|
|
||||||
|
final class Schema9 extends i0.VersionedSchema {
|
||||||
|
Schema9({required super.database}) : super(version: 9);
|
||||||
|
@override
|
||||||
|
late final List<i1.DatabaseSchemaEntity> entities = [
|
||||||
|
contacts,
|
||||||
|
messages,
|
||||||
|
mediaUploads,
|
||||||
|
mediaDownloads,
|
||||||
|
signalIdentityKeyStores,
|
||||||
|
signalPreKeyStores,
|
||||||
|
signalSenderKeyStores,
|
||||||
|
signalSessionStores,
|
||||||
|
];
|
||||||
|
late final Shape12 contacts = Shape12(
|
||||||
|
source: i0.VersionedTable(
|
||||||
|
entityName: 'contacts',
|
||||||
|
withoutRowId: false,
|
||||||
|
isStrict: false,
|
||||||
|
tableConstraints: [
|
||||||
|
'PRIMARY KEY(user_id)',
|
||||||
|
],
|
||||||
|
columns: [
|
||||||
|
_column_0,
|
||||||
|
_column_1,
|
||||||
|
_column_2,
|
||||||
|
_column_3,
|
||||||
|
_column_4,
|
||||||
|
_column_5,
|
||||||
|
_column_6,
|
||||||
|
_column_7,
|
||||||
|
_column_8,
|
||||||
|
_column_9,
|
||||||
|
_column_39,
|
||||||
|
_column_53,
|
||||||
|
_column_54,
|
||||||
|
_column_40,
|
||||||
|
_column_10,
|
||||||
|
_column_11,
|
||||||
|
_column_12,
|
||||||
|
_column_13,
|
||||||
|
_column_14,
|
||||||
|
_column_55,
|
||||||
|
_column_15,
|
||||||
|
_column_16,
|
||||||
|
],
|
||||||
|
attachedDatabase: database,
|
||||||
|
),
|
||||||
|
alias: null);
|
||||||
|
late final Shape10 messages = Shape10(
|
||||||
|
source: i0.VersionedTable(
|
||||||
|
entityName: 'messages',
|
||||||
|
withoutRowId: false,
|
||||||
|
isStrict: false,
|
||||||
|
tableConstraints: [],
|
||||||
|
columns: [
|
||||||
|
_column_17,
|
||||||
|
_column_18,
|
||||||
|
_column_19,
|
||||||
|
_column_48,
|
||||||
|
_column_49,
|
||||||
|
_column_20,
|
||||||
|
_column_21,
|
||||||
|
_column_22,
|
||||||
|
_column_52,
|
||||||
|
_column_23,
|
||||||
|
_column_24,
|
||||||
|
_column_25,
|
||||||
|
_column_26,
|
||||||
|
_column_27,
|
||||||
|
_column_28,
|
||||||
|
_column_29,
|
||||||
|
_column_30,
|
||||||
|
],
|
||||||
|
attachedDatabase: database,
|
||||||
|
),
|
||||||
|
alias: null);
|
||||||
|
late final Shape7 mediaUploads = Shape7(
|
||||||
|
source: i0.VersionedTable(
|
||||||
|
entityName: 'media_uploads',
|
||||||
|
withoutRowId: false,
|
||||||
|
isStrict: false,
|
||||||
|
tableConstraints: [],
|
||||||
|
columns: [
|
||||||
|
_column_41,
|
||||||
|
_column_42,
|
||||||
|
_column_56,
|
||||||
|
_column_44,
|
||||||
|
_column_45,
|
||||||
|
_column_46,
|
||||||
|
_column_47,
|
||||||
|
],
|
||||||
|
attachedDatabase: database,
|
||||||
|
),
|
||||||
|
alias: null);
|
||||||
|
late final Shape9 mediaDownloads = Shape9(
|
||||||
|
source: i0.VersionedTable(
|
||||||
|
entityName: 'media_downloads',
|
||||||
|
withoutRowId: false,
|
||||||
|
isStrict: false,
|
||||||
|
tableConstraints: [],
|
||||||
|
columns: [
|
||||||
|
_column_50,
|
||||||
|
_column_51,
|
||||||
|
],
|
||||||
|
attachedDatabase: database,
|
||||||
|
),
|
||||||
|
alias: null);
|
||||||
|
late final Shape2 signalIdentityKeyStores = Shape2(
|
||||||
|
source: i0.VersionedTable(
|
||||||
|
entityName: 'signal_identity_key_stores',
|
||||||
|
withoutRowId: false,
|
||||||
|
isStrict: false,
|
||||||
|
tableConstraints: [
|
||||||
|
'PRIMARY KEY(device_id, name)',
|
||||||
|
],
|
||||||
|
columns: [
|
||||||
|
_column_31,
|
||||||
|
_column_32,
|
||||||
|
_column_33,
|
||||||
|
_column_10,
|
||||||
|
],
|
||||||
|
attachedDatabase: database,
|
||||||
|
),
|
||||||
|
alias: null);
|
||||||
|
late final Shape3 signalPreKeyStores = Shape3(
|
||||||
|
source: i0.VersionedTable(
|
||||||
|
entityName: 'signal_pre_key_stores',
|
||||||
|
withoutRowId: false,
|
||||||
|
isStrict: false,
|
||||||
|
tableConstraints: [
|
||||||
|
'PRIMARY KEY(pre_key_id)',
|
||||||
|
],
|
||||||
|
columns: [
|
||||||
|
_column_34,
|
||||||
|
_column_35,
|
||||||
|
_column_10,
|
||||||
|
],
|
||||||
|
attachedDatabase: database,
|
||||||
|
),
|
||||||
|
alias: null);
|
||||||
|
late final Shape4 signalSenderKeyStores = Shape4(
|
||||||
|
source: i0.VersionedTable(
|
||||||
|
entityName: 'signal_sender_key_stores',
|
||||||
|
withoutRowId: false,
|
||||||
|
isStrict: false,
|
||||||
|
tableConstraints: [
|
||||||
|
'PRIMARY KEY(sender_key_name)',
|
||||||
|
],
|
||||||
|
columns: [
|
||||||
|
_column_36,
|
||||||
|
_column_37,
|
||||||
|
],
|
||||||
|
attachedDatabase: database,
|
||||||
|
),
|
||||||
|
alias: null);
|
||||||
|
late final Shape5 signalSessionStores = Shape5(
|
||||||
|
source: i0.VersionedTable(
|
||||||
|
entityName: 'signal_session_stores',
|
||||||
|
withoutRowId: false,
|
||||||
|
isStrict: false,
|
||||||
|
tableConstraints: [
|
||||||
|
'PRIMARY KEY(device_id, name)',
|
||||||
|
],
|
||||||
|
columns: [
|
||||||
|
_column_31,
|
||||||
|
_column_32,
|
||||||
|
_column_38,
|
||||||
|
_column_10,
|
||||||
|
],
|
||||||
|
attachedDatabase: database,
|
||||||
|
),
|
||||||
|
alias: null);
|
||||||
|
}
|
||||||
|
|
||||||
|
i1.GeneratedColumn<String> _column_56(String aliasedName) =>
|
||||||
|
i1.GeneratedColumn<String>('metadata', aliasedName, true,
|
||||||
|
type: i1.DriftSqlType.string);
|
||||||
i0.MigrationStepWithVersion migrationSteps({
|
i0.MigrationStepWithVersion migrationSteps({
|
||||||
required Future<void> Function(i1.Migrator m, Schema2 schema) from1To2,
|
required Future<void> Function(i1.Migrator m, Schema2 schema) from1To2,
|
||||||
required Future<void> Function(i1.Migrator m, Schema3 schema) from2To3,
|
required Future<void> Function(i1.Migrator m, Schema3 schema) from2To3,
|
||||||
|
|
@ -1709,6 +1887,7 @@ i0.MigrationStepWithVersion migrationSteps({
|
||||||
required Future<void> Function(i1.Migrator m, Schema6 schema) from5To6,
|
required Future<void> Function(i1.Migrator m, Schema6 schema) from5To6,
|
||||||
required Future<void> Function(i1.Migrator m, Schema7 schema) from6To7,
|
required Future<void> Function(i1.Migrator m, Schema7 schema) from6To7,
|
||||||
required Future<void> Function(i1.Migrator m, Schema8 schema) from7To8,
|
required Future<void> Function(i1.Migrator m, Schema8 schema) from7To8,
|
||||||
|
required Future<void> Function(i1.Migrator m, Schema9 schema) from8To9,
|
||||||
}) {
|
}) {
|
||||||
return (currentVersion, database) async {
|
return (currentVersion, database) async {
|
||||||
switch (currentVersion) {
|
switch (currentVersion) {
|
||||||
|
|
@ -1747,6 +1926,11 @@ i0.MigrationStepWithVersion migrationSteps({
|
||||||
final migrator = i1.Migrator(database, schema);
|
final migrator = i1.Migrator(database, schema);
|
||||||
await from7To8(migrator, schema);
|
await from7To8(migrator, schema);
|
||||||
return 8;
|
return 8;
|
||||||
|
case 8:
|
||||||
|
final schema = Schema9(database: database);
|
||||||
|
final migrator = i1.Migrator(database, schema);
|
||||||
|
await from8To9(migrator, schema);
|
||||||
|
return 9;
|
||||||
default:
|
default:
|
||||||
throw ArgumentError.value('Unknown migration from $currentVersion');
|
throw ArgumentError.value('Unknown migration from $currentVersion');
|
||||||
}
|
}
|
||||||
|
|
@ -1761,6 +1945,7 @@ i1.OnUpgrade stepByStep({
|
||||||
required Future<void> Function(i1.Migrator m, Schema6 schema) from5To6,
|
required Future<void> Function(i1.Migrator m, Schema6 schema) from5To6,
|
||||||
required Future<void> Function(i1.Migrator m, Schema7 schema) from6To7,
|
required Future<void> Function(i1.Migrator m, Schema7 schema) from6To7,
|
||||||
required Future<void> Function(i1.Migrator m, Schema8 schema) from7To8,
|
required Future<void> Function(i1.Migrator m, Schema8 schema) from7To8,
|
||||||
|
required Future<void> Function(i1.Migrator m, Schema9 schema) from8To9,
|
||||||
}) =>
|
}) =>
|
||||||
i0.VersionedSchema.stepByStepHelper(
|
i0.VersionedSchema.stepByStepHelper(
|
||||||
step: migrationSteps(
|
step: migrationSteps(
|
||||||
|
|
@ -1771,4 +1956,5 @@ i1.OnUpgrade stepByStep({
|
||||||
from5To6: from5To6,
|
from5To6: from5To6,
|
||||||
from6To7: from6To7,
|
from6To7: from6To7,
|
||||||
from7To8: from7To8,
|
from7To8: from7To8,
|
||||||
|
from8To9: from8To9,
|
||||||
));
|
));
|
||||||
|
|
|
||||||
|
|
@ -1545,6 +1545,70 @@ class ApplicationData_UploadData extends $pb.GeneratedMessage {
|
||||||
void clearChecksum() => clearField(4);
|
void clearChecksum() => clearField(4);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class ApplicationData_UploadDone extends $pb.GeneratedMessage {
|
||||||
|
factory ApplicationData_UploadDone({
|
||||||
|
$core.List<$core.int>? uploadToken,
|
||||||
|
$core.int? recipientsCount,
|
||||||
|
}) {
|
||||||
|
final $result = create();
|
||||||
|
if (uploadToken != null) {
|
||||||
|
$result.uploadToken = uploadToken;
|
||||||
|
}
|
||||||
|
if (recipientsCount != null) {
|
||||||
|
$result.recipientsCount = recipientsCount;
|
||||||
|
}
|
||||||
|
return $result;
|
||||||
|
}
|
||||||
|
ApplicationData_UploadDone._() : super();
|
||||||
|
factory ApplicationData_UploadDone.fromBuffer($core.List<$core.int> i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromBuffer(i, r);
|
||||||
|
factory ApplicationData_UploadDone.fromJson($core.String i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromJson(i, r);
|
||||||
|
|
||||||
|
static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'ApplicationData.UploadDone', package: const $pb.PackageName(_omitMessageNames ? '' : 'client_to_server'), createEmptyInstance: create)
|
||||||
|
..a<$core.List<$core.int>>(1, _omitFieldNames ? '' : 'uploadToken', $pb.PbFieldType.OY)
|
||||||
|
..a<$core.int>(2, _omitFieldNames ? '' : 'recipientsCount', $pb.PbFieldType.OU3)
|
||||||
|
..hasRequiredFields = false
|
||||||
|
;
|
||||||
|
|
||||||
|
@$core.Deprecated(
|
||||||
|
'Using this can add significant overhead to your binary. '
|
||||||
|
'Use [GeneratedMessageGenericExtensions.deepCopy] instead. '
|
||||||
|
'Will be removed in next major version')
|
||||||
|
ApplicationData_UploadDone clone() => ApplicationData_UploadDone()..mergeFromMessage(this);
|
||||||
|
@$core.Deprecated(
|
||||||
|
'Using this can add significant overhead to your binary. '
|
||||||
|
'Use [GeneratedMessageGenericExtensions.rebuild] instead. '
|
||||||
|
'Will be removed in next major version')
|
||||||
|
ApplicationData_UploadDone copyWith(void Function(ApplicationData_UploadDone) updates) => super.copyWith((message) => updates(message as ApplicationData_UploadDone)) as ApplicationData_UploadDone;
|
||||||
|
|
||||||
|
$pb.BuilderInfo get info_ => _i;
|
||||||
|
|
||||||
|
@$core.pragma('dart2js:noInline')
|
||||||
|
static ApplicationData_UploadDone create() => ApplicationData_UploadDone._();
|
||||||
|
ApplicationData_UploadDone createEmptyInstance() => create();
|
||||||
|
static $pb.PbList<ApplicationData_UploadDone> createRepeated() => $pb.PbList<ApplicationData_UploadDone>();
|
||||||
|
@$core.pragma('dart2js:noInline')
|
||||||
|
static ApplicationData_UploadDone getDefault() => _defaultInstance ??= $pb.GeneratedMessage.$_defaultFor<ApplicationData_UploadDone>(create);
|
||||||
|
static ApplicationData_UploadDone? _defaultInstance;
|
||||||
|
|
||||||
|
@$pb.TagNumber(1)
|
||||||
|
$core.List<$core.int> get uploadToken => $_getN(0);
|
||||||
|
@$pb.TagNumber(1)
|
||||||
|
set uploadToken($core.List<$core.int> v) { $_setBytes(0, v); }
|
||||||
|
@$pb.TagNumber(1)
|
||||||
|
$core.bool hasUploadToken() => $_has(0);
|
||||||
|
@$pb.TagNumber(1)
|
||||||
|
void clearUploadToken() => clearField(1);
|
||||||
|
|
||||||
|
@$pb.TagNumber(2)
|
||||||
|
$core.int get recipientsCount => $_getIZ(1);
|
||||||
|
@$pb.TagNumber(2)
|
||||||
|
set recipientsCount($core.int v) { $_setUnsignedInt32(1, v); }
|
||||||
|
@$pb.TagNumber(2)
|
||||||
|
$core.bool hasRecipientsCount() => $_has(1);
|
||||||
|
@$pb.TagNumber(2)
|
||||||
|
void clearRecipientsCount() => clearField(2);
|
||||||
|
}
|
||||||
|
|
||||||
class ApplicationData_DownloadData extends $pb.GeneratedMessage {
|
class ApplicationData_DownloadData extends $pb.GeneratedMessage {
|
||||||
factory ApplicationData_DownloadData({
|
factory ApplicationData_DownloadData({
|
||||||
$core.List<$core.int>? downloadToken,
|
$core.List<$core.int>? downloadToken,
|
||||||
|
|
@ -1609,6 +1673,56 @@ class ApplicationData_DownloadData extends $pb.GeneratedMessage {
|
||||||
void clearOffset() => clearField(2);
|
void clearOffset() => clearField(2);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class ApplicationData_DownloadDone extends $pb.GeneratedMessage {
|
||||||
|
factory ApplicationData_DownloadDone({
|
||||||
|
$core.List<$core.int>? downloadToken,
|
||||||
|
}) {
|
||||||
|
final $result = create();
|
||||||
|
if (downloadToken != null) {
|
||||||
|
$result.downloadToken = downloadToken;
|
||||||
|
}
|
||||||
|
return $result;
|
||||||
|
}
|
||||||
|
ApplicationData_DownloadDone._() : super();
|
||||||
|
factory ApplicationData_DownloadDone.fromBuffer($core.List<$core.int> i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromBuffer(i, r);
|
||||||
|
factory ApplicationData_DownloadDone.fromJson($core.String i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromJson(i, r);
|
||||||
|
|
||||||
|
static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'ApplicationData.DownloadDone', package: const $pb.PackageName(_omitMessageNames ? '' : 'client_to_server'), createEmptyInstance: create)
|
||||||
|
..a<$core.List<$core.int>>(1, _omitFieldNames ? '' : 'downloadToken', $pb.PbFieldType.OY)
|
||||||
|
..hasRequiredFields = false
|
||||||
|
;
|
||||||
|
|
||||||
|
@$core.Deprecated(
|
||||||
|
'Using this can add significant overhead to your binary. '
|
||||||
|
'Use [GeneratedMessageGenericExtensions.deepCopy] instead. '
|
||||||
|
'Will be removed in next major version')
|
||||||
|
ApplicationData_DownloadDone clone() => ApplicationData_DownloadDone()..mergeFromMessage(this);
|
||||||
|
@$core.Deprecated(
|
||||||
|
'Using this can add significant overhead to your binary. '
|
||||||
|
'Use [GeneratedMessageGenericExtensions.rebuild] instead. '
|
||||||
|
'Will be removed in next major version')
|
||||||
|
ApplicationData_DownloadDone copyWith(void Function(ApplicationData_DownloadDone) updates) => super.copyWith((message) => updates(message as ApplicationData_DownloadDone)) as ApplicationData_DownloadDone;
|
||||||
|
|
||||||
|
$pb.BuilderInfo get info_ => _i;
|
||||||
|
|
||||||
|
@$core.pragma('dart2js:noInline')
|
||||||
|
static ApplicationData_DownloadDone create() => ApplicationData_DownloadDone._();
|
||||||
|
ApplicationData_DownloadDone createEmptyInstance() => create();
|
||||||
|
static $pb.PbList<ApplicationData_DownloadDone> createRepeated() => $pb.PbList<ApplicationData_DownloadDone>();
|
||||||
|
@$core.pragma('dart2js:noInline')
|
||||||
|
static ApplicationData_DownloadDone getDefault() => _defaultInstance ??= $pb.GeneratedMessage.$_defaultFor<ApplicationData_DownloadDone>(create);
|
||||||
|
static ApplicationData_DownloadDone? _defaultInstance;
|
||||||
|
|
||||||
|
@$pb.TagNumber(1)
|
||||||
|
$core.List<$core.int> get downloadToken => $_getN(0);
|
||||||
|
@$pb.TagNumber(1)
|
||||||
|
set downloadToken($core.List<$core.int> v) { $_setBytes(0, v); }
|
||||||
|
@$pb.TagNumber(1)
|
||||||
|
$core.bool hasDownloadToken() => $_has(0);
|
||||||
|
@$pb.TagNumber(1)
|
||||||
|
void clearDownloadToken() => clearField(1);
|
||||||
|
}
|
||||||
|
|
||||||
enum ApplicationData_ApplicationData {
|
enum ApplicationData_ApplicationData {
|
||||||
textmessage,
|
textmessage,
|
||||||
getuserbyusername,
|
getuserbyusername,
|
||||||
|
|
@ -1629,6 +1743,8 @@ enum ApplicationData_ApplicationData {
|
||||||
redeemadditionalcode,
|
redeemadditionalcode,
|
||||||
removeadditionaluser,
|
removeadditionaluser,
|
||||||
updateplanoptions,
|
updateplanoptions,
|
||||||
|
downloaddone,
|
||||||
|
uploaddone,
|
||||||
notSet
|
notSet
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1653,6 +1769,8 @@ class ApplicationData extends $pb.GeneratedMessage {
|
||||||
ApplicationData_RedeemAdditionalCode? redeemadditionalcode,
|
ApplicationData_RedeemAdditionalCode? redeemadditionalcode,
|
||||||
ApplicationData_RemoveAdditionalUser? removeadditionaluser,
|
ApplicationData_RemoveAdditionalUser? removeadditionaluser,
|
||||||
ApplicationData_UpdatePlanOptions? updateplanoptions,
|
ApplicationData_UpdatePlanOptions? updateplanoptions,
|
||||||
|
ApplicationData_DownloadDone? downloaddone,
|
||||||
|
ApplicationData_UploadDone? uploaddone,
|
||||||
}) {
|
}) {
|
||||||
final $result = create();
|
final $result = create();
|
||||||
if (textmessage != null) {
|
if (textmessage != null) {
|
||||||
|
|
@ -1712,6 +1830,12 @@ class ApplicationData extends $pb.GeneratedMessage {
|
||||||
if (updateplanoptions != null) {
|
if (updateplanoptions != null) {
|
||||||
$result.updateplanoptions = updateplanoptions;
|
$result.updateplanoptions = updateplanoptions;
|
||||||
}
|
}
|
||||||
|
if (downloaddone != null) {
|
||||||
|
$result.downloaddone = downloaddone;
|
||||||
|
}
|
||||||
|
if (uploaddone != null) {
|
||||||
|
$result.uploaddone = uploaddone;
|
||||||
|
}
|
||||||
return $result;
|
return $result;
|
||||||
}
|
}
|
||||||
ApplicationData._() : super();
|
ApplicationData._() : super();
|
||||||
|
|
@ -1738,10 +1862,12 @@ class ApplicationData extends $pb.GeneratedMessage {
|
||||||
17 : ApplicationData_ApplicationData.redeemadditionalcode,
|
17 : ApplicationData_ApplicationData.redeemadditionalcode,
|
||||||
18 : ApplicationData_ApplicationData.removeadditionaluser,
|
18 : ApplicationData_ApplicationData.removeadditionaluser,
|
||||||
19 : ApplicationData_ApplicationData.updateplanoptions,
|
19 : ApplicationData_ApplicationData.updateplanoptions,
|
||||||
|
20 : ApplicationData_ApplicationData.downloaddone,
|
||||||
|
21 : ApplicationData_ApplicationData.uploaddone,
|
||||||
0 : ApplicationData_ApplicationData.notSet
|
0 : ApplicationData_ApplicationData.notSet
|
||||||
};
|
};
|
||||||
static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'ApplicationData', package: const $pb.PackageName(_omitMessageNames ? '' : 'client_to_server'), createEmptyInstance: create)
|
static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'ApplicationData', package: const $pb.PackageName(_omitMessageNames ? '' : 'client_to_server'), createEmptyInstance: create)
|
||||||
..oo(0, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19])
|
..oo(0, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21])
|
||||||
..aOM<ApplicationData_TextMessage>(1, _omitFieldNames ? '' : 'textmessage', subBuilder: ApplicationData_TextMessage.create)
|
..aOM<ApplicationData_TextMessage>(1, _omitFieldNames ? '' : 'textmessage', subBuilder: ApplicationData_TextMessage.create)
|
||||||
..aOM<ApplicationData_GetUserByUsername>(2, _omitFieldNames ? '' : 'getuserbyusername', subBuilder: ApplicationData_GetUserByUsername.create)
|
..aOM<ApplicationData_GetUserByUsername>(2, _omitFieldNames ? '' : 'getuserbyusername', subBuilder: ApplicationData_GetUserByUsername.create)
|
||||||
..aOM<ApplicationData_GetPrekeysByUserId>(3, _omitFieldNames ? '' : 'getprekeysbyuserid', subBuilder: ApplicationData_GetPrekeysByUserId.create)
|
..aOM<ApplicationData_GetPrekeysByUserId>(3, _omitFieldNames ? '' : 'getprekeysbyuserid', subBuilder: ApplicationData_GetPrekeysByUserId.create)
|
||||||
|
|
@ -1761,6 +1887,8 @@ class ApplicationData extends $pb.GeneratedMessage {
|
||||||
..aOM<ApplicationData_RedeemAdditionalCode>(17, _omitFieldNames ? '' : 'redeemadditionalcode', subBuilder: ApplicationData_RedeemAdditionalCode.create)
|
..aOM<ApplicationData_RedeemAdditionalCode>(17, _omitFieldNames ? '' : 'redeemadditionalcode', subBuilder: ApplicationData_RedeemAdditionalCode.create)
|
||||||
..aOM<ApplicationData_RemoveAdditionalUser>(18, _omitFieldNames ? '' : 'removeadditionaluser', subBuilder: ApplicationData_RemoveAdditionalUser.create)
|
..aOM<ApplicationData_RemoveAdditionalUser>(18, _omitFieldNames ? '' : 'removeadditionaluser', subBuilder: ApplicationData_RemoveAdditionalUser.create)
|
||||||
..aOM<ApplicationData_UpdatePlanOptions>(19, _omitFieldNames ? '' : 'updateplanoptions', subBuilder: ApplicationData_UpdatePlanOptions.create)
|
..aOM<ApplicationData_UpdatePlanOptions>(19, _omitFieldNames ? '' : 'updateplanoptions', subBuilder: ApplicationData_UpdatePlanOptions.create)
|
||||||
|
..aOM<ApplicationData_DownloadDone>(20, _omitFieldNames ? '' : 'downloaddone', subBuilder: ApplicationData_DownloadDone.create)
|
||||||
|
..aOM<ApplicationData_UploadDone>(21, _omitFieldNames ? '' : 'uploaddone', subBuilder: ApplicationData_UploadDone.create)
|
||||||
..hasRequiredFields = false
|
..hasRequiredFields = false
|
||||||
;
|
;
|
||||||
|
|
||||||
|
|
@ -1996,6 +2124,28 @@ class ApplicationData extends $pb.GeneratedMessage {
|
||||||
void clearUpdateplanoptions() => clearField(19);
|
void clearUpdateplanoptions() => clearField(19);
|
||||||
@$pb.TagNumber(19)
|
@$pb.TagNumber(19)
|
||||||
ApplicationData_UpdatePlanOptions ensureUpdateplanoptions() => $_ensure(18);
|
ApplicationData_UpdatePlanOptions ensureUpdateplanoptions() => $_ensure(18);
|
||||||
|
|
||||||
|
@$pb.TagNumber(20)
|
||||||
|
ApplicationData_DownloadDone get downloaddone => $_getN(19);
|
||||||
|
@$pb.TagNumber(20)
|
||||||
|
set downloaddone(ApplicationData_DownloadDone v) { setField(20, v); }
|
||||||
|
@$pb.TagNumber(20)
|
||||||
|
$core.bool hasDownloaddone() => $_has(19);
|
||||||
|
@$pb.TagNumber(20)
|
||||||
|
void clearDownloaddone() => clearField(20);
|
||||||
|
@$pb.TagNumber(20)
|
||||||
|
ApplicationData_DownloadDone ensureDownloaddone() => $_ensure(19);
|
||||||
|
|
||||||
|
@$pb.TagNumber(21)
|
||||||
|
ApplicationData_UploadDone get uploaddone => $_getN(20);
|
||||||
|
@$pb.TagNumber(21)
|
||||||
|
set uploaddone(ApplicationData_UploadDone v) { setField(21, v); }
|
||||||
|
@$pb.TagNumber(21)
|
||||||
|
$core.bool hasUploaddone() => $_has(20);
|
||||||
|
@$pb.TagNumber(21)
|
||||||
|
void clearUploaddone() => clearField(21);
|
||||||
|
@$pb.TagNumber(21)
|
||||||
|
ApplicationData_UploadDone ensureUploaddone() => $_ensure(20);
|
||||||
}
|
}
|
||||||
|
|
||||||
class Response_PreKey extends $pb.GeneratedMessage {
|
class Response_PreKey extends $pb.GeneratedMessage {
|
||||||
|
|
|
||||||
|
|
@ -155,8 +155,10 @@ const ApplicationData$json = {
|
||||||
{'1': 'redeemadditionalcode', '3': 17, '4': 1, '5': 11, '6': '.client_to_server.ApplicationData.RedeemAdditionalCode', '9': 0, '10': 'redeemadditionalcode'},
|
{'1': 'redeemadditionalcode', '3': 17, '4': 1, '5': 11, '6': '.client_to_server.ApplicationData.RedeemAdditionalCode', '9': 0, '10': 'redeemadditionalcode'},
|
||||||
{'1': 'removeadditionaluser', '3': 18, '4': 1, '5': 11, '6': '.client_to_server.ApplicationData.RemoveAdditionalUser', '9': 0, '10': 'removeadditionaluser'},
|
{'1': 'removeadditionaluser', '3': 18, '4': 1, '5': 11, '6': '.client_to_server.ApplicationData.RemoveAdditionalUser', '9': 0, '10': 'removeadditionaluser'},
|
||||||
{'1': 'updateplanoptions', '3': 19, '4': 1, '5': 11, '6': '.client_to_server.ApplicationData.UpdatePlanOptions', '9': 0, '10': 'updateplanoptions'},
|
{'1': 'updateplanoptions', '3': 19, '4': 1, '5': 11, '6': '.client_to_server.ApplicationData.UpdatePlanOptions', '9': 0, '10': 'updateplanoptions'},
|
||||||
|
{'1': 'downloaddone', '3': 20, '4': 1, '5': 11, '6': '.client_to_server.ApplicationData.DownloadDone', '9': 0, '10': 'downloaddone'},
|
||||||
|
{'1': 'uploaddone', '3': 21, '4': 1, '5': 11, '6': '.client_to_server.ApplicationData.UploadDone', '9': 0, '10': 'uploaddone'},
|
||||||
],
|
],
|
||||||
'3': [ApplicationData_TextMessage$json, ApplicationData_GetUserByUsername$json, ApplicationData_UpdateGoogleFcmToken$json, ApplicationData_GetUserById$json, ApplicationData_RedeemVoucher$json, ApplicationData_SwitchToPayedPlan$json, ApplicationData_UpdatePlanOptions$json, ApplicationData_CreateVoucher$json, ApplicationData_GetLocation$json, ApplicationData_GetVouchers$json, ApplicationData_GetAvailablePlans$json, ApplicationData_GetAddAccountsInvites$json, ApplicationData_GetCurrentPlanInfos$json, ApplicationData_RedeemAdditionalCode$json, ApplicationData_RemoveAdditionalUser$json, ApplicationData_GetPrekeysByUserId$json, ApplicationData_GetUploadToken$json, ApplicationData_UploadData$json, ApplicationData_DownloadData$json],
|
'3': [ApplicationData_TextMessage$json, ApplicationData_GetUserByUsername$json, ApplicationData_UpdateGoogleFcmToken$json, ApplicationData_GetUserById$json, ApplicationData_RedeemVoucher$json, ApplicationData_SwitchToPayedPlan$json, ApplicationData_UpdatePlanOptions$json, ApplicationData_CreateVoucher$json, ApplicationData_GetLocation$json, ApplicationData_GetVouchers$json, ApplicationData_GetAvailablePlans$json, ApplicationData_GetAddAccountsInvites$json, ApplicationData_GetCurrentPlanInfos$json, ApplicationData_RedeemAdditionalCode$json, ApplicationData_RemoveAdditionalUser$json, ApplicationData_GetPrekeysByUserId$json, ApplicationData_GetUploadToken$json, ApplicationData_UploadData$json, ApplicationData_UploadDone$json, ApplicationData_DownloadData$json, ApplicationData_DownloadDone$json],
|
||||||
'8': [
|
'8': [
|
||||||
{'1': 'ApplicationData'},
|
{'1': 'ApplicationData'},
|
||||||
],
|
],
|
||||||
|
|
@ -304,6 +306,15 @@ const ApplicationData_UploadData$json = {
|
||||||
],
|
],
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@$core.Deprecated('Use applicationDataDescriptor instead')
|
||||||
|
const ApplicationData_UploadDone$json = {
|
||||||
|
'1': 'UploadDone',
|
||||||
|
'2': [
|
||||||
|
{'1': 'upload_token', '3': 1, '4': 1, '5': 12, '10': 'uploadToken'},
|
||||||
|
{'1': 'recipients_count', '3': 2, '4': 1, '5': 13, '10': 'recipientsCount'},
|
||||||
|
],
|
||||||
|
};
|
||||||
|
|
||||||
@$core.Deprecated('Use applicationDataDescriptor instead')
|
@$core.Deprecated('Use applicationDataDescriptor instead')
|
||||||
const ApplicationData_DownloadData$json = {
|
const ApplicationData_DownloadData$json = {
|
||||||
'1': 'DownloadData',
|
'1': 'DownloadData',
|
||||||
|
|
@ -313,6 +324,14 @@ const ApplicationData_DownloadData$json = {
|
||||||
],
|
],
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@$core.Deprecated('Use applicationDataDescriptor instead')
|
||||||
|
const ApplicationData_DownloadDone$json = {
|
||||||
|
'1': 'DownloadDone',
|
||||||
|
'2': [
|
||||||
|
{'1': 'download_token', '3': 1, '4': 1, '5': 12, '10': 'downloadToken'},
|
||||||
|
],
|
||||||
|
};
|
||||||
|
|
||||||
/// Descriptor for `ApplicationData`. Decode as a `google.protobuf.DescriptorProto`.
|
/// Descriptor for `ApplicationData`. Decode as a `google.protobuf.DescriptorProto`.
|
||||||
final $typed_data.Uint8List applicationDataDescriptor = $convert.base64Decode(
|
final $typed_data.Uint8List applicationDataDescriptor = $convert.base64Decode(
|
||||||
'Cg9BcHBsaWNhdGlvbkRhdGESUQoLdGV4dG1lc3NhZ2UYASABKAsyLS5jbGllbnRfdG9fc2Vydm'
|
'Cg9BcHBsaWNhdGlvbkRhdGESUQoLdGV4dG1lc3NhZ2UYASABKAsyLS5jbGllbnRfdG9fc2Vydm'
|
||||||
|
|
@ -348,26 +367,32 @@ final $typed_data.Uint8List applicationDataDescriptor = $convert.base64Decode(
|
||||||
'Y2xpZW50X3RvX3NlcnZlci5BcHBsaWNhdGlvbkRhdGEuUmVtb3ZlQWRkaXRpb25hbFVzZXJIAF'
|
'Y2xpZW50X3RvX3NlcnZlci5BcHBsaWNhdGlvbkRhdGEuUmVtb3ZlQWRkaXRpb25hbFVzZXJIAF'
|
||||||
'IUcmVtb3ZlYWRkaXRpb25hbHVzZXISYwoRdXBkYXRlcGxhbm9wdGlvbnMYEyABKAsyMy5jbGll'
|
'IUcmVtb3ZlYWRkaXRpb25hbHVzZXISYwoRdXBkYXRlcGxhbm9wdGlvbnMYEyABKAsyMy5jbGll'
|
||||||
'bnRfdG9fc2VydmVyLkFwcGxpY2F0aW9uRGF0YS5VcGRhdGVQbGFuT3B0aW9uc0gAUhF1cGRhdG'
|
'bnRfdG9fc2VydmVyLkFwcGxpY2F0aW9uRGF0YS5VcGRhdGVQbGFuT3B0aW9uc0gAUhF1cGRhdG'
|
||||||
'VwbGFub3B0aW9ucxpqCgtUZXh0TWVzc2FnZRIXCgd1c2VyX2lkGAEgASgDUgZ1c2VySWQSEgoE'
|
'VwbGFub3B0aW9ucxJUCgxkb3dubG9hZGRvbmUYFCABKAsyLi5jbGllbnRfdG9fc2VydmVyLkFw'
|
||||||
'Ym9keRgDIAEoDFIEYm9keRIgCglwdXNoX2RhdGEYBCABKAxIAFIIcHVzaERhdGGIAQFCDAoKX3'
|
'cGxpY2F0aW9uRGF0YS5Eb3dubG9hZERvbmVIAFIMZG93bmxvYWRkb25lEk4KCnVwbG9hZGRvbm'
|
||||||
'B1c2hfZGF0YRovChFHZXRVc2VyQnlVc2VybmFtZRIaCgh1c2VybmFtZRgBIAEoCVIIdXNlcm5h'
|
'UYFSABKAsyLC5jbGllbnRfdG9fc2VydmVyLkFwcGxpY2F0aW9uRGF0YS5VcGxvYWREb25lSABS'
|
||||||
'bWUaNQoUVXBkYXRlR29vZ2xlRmNtVG9rZW4SHQoKZ29vZ2xlX2ZjbRgBIAEoCVIJZ29vZ2xlRm'
|
'CnVwbG9hZGRvbmUaagoLVGV4dE1lc3NhZ2USFwoHdXNlcl9pZBgBIAEoA1IGdXNlcklkEhIKBG'
|
||||||
'NtGiYKC0dldFVzZXJCeUlkEhcKB3VzZXJfaWQYASABKANSBnVzZXJJZBopCg1SZWRlZW1Wb3Vj'
|
'JvZHkYAyABKAxSBGJvZHkSIAoJcHVzaF9kYXRhGAQgASgMSABSCHB1c2hEYXRhiAEBQgwKCl9w'
|
||||||
'aGVyEhgKB3ZvdWNoZXIYASABKAlSB3ZvdWNoZXIacAoRU3dpdGNoVG9QYXllZFBsYW4SFwoHcG'
|
'dXNoX2RhdGEaLwoRR2V0VXNlckJ5VXNlcm5hbWUSGgoIdXNlcm5hbWUYASABKAlSCHVzZXJuYW'
|
||||||
'xhbl9pZBgBIAEoCVIGcGxhbklkEh8KC3BheV9tb250aGx5GAIgASgIUgpwYXlNb250aGx5EiEK'
|
'1lGjUKFFVwZGF0ZUdvb2dsZUZjbVRva2VuEh0KCmdvb2dsZV9mY20YASABKAlSCWdvb2dsZUZj'
|
||||||
'DGF1dG9fcmVuZXdhbBgDIAEoCFILYXV0b1JlbmV3YWwaNgoRVXBkYXRlUGxhbk9wdGlvbnMSIQ'
|
'bRomCgtHZXRVc2VyQnlJZBIXCgd1c2VyX2lkGAEgASgDUgZ1c2VySWQaKQoNUmVkZWVtVm91Y2'
|
||||||
'oMYXV0b19yZW5ld2FsGAEgASgIUgthdXRvUmVuZXdhbBowCg1DcmVhdGVWb3VjaGVyEh8KC3Zh'
|
'hlchIYCgd2b3VjaGVyGAEgASgJUgd2b3VjaGVyGnAKEVN3aXRjaFRvUGF5ZWRQbGFuEhcKB3Bs'
|
||||||
'bHVlX2NlbnRzGAEgASgNUgp2YWx1ZUNlbnRzGg0KC0dldExvY2F0aW9uGg0KC0dldFZvdWNoZX'
|
'YW5faWQYASABKAlSBnBsYW5JZBIfCgtwYXlfbW9udGhseRgCIAEoCFIKcGF5TW9udGhseRIhCg'
|
||||||
'JzGhMKEUdldEF2YWlsYWJsZVBsYW5zGhcKFUdldEFkZEFjY291bnRzSW52aXRlcxoVChNHZXRD'
|
'xhdXRvX3JlbmV3YWwYAyABKAhSC2F1dG9SZW5ld2FsGjYKEVVwZGF0ZVBsYW5PcHRpb25zEiEK'
|
||||||
'dXJyZW50UGxhbkluZm9zGjcKFFJlZGVlbUFkZGl0aW9uYWxDb2RlEh8KC2ludml0ZV9jb2RlGA'
|
'DGF1dG9fcmVuZXdhbBgBIAEoCFILYXV0b1JlbmV3YWwaMAoNQ3JlYXRlVm91Y2hlchIfCgt2YW'
|
||||||
'IgASgJUgppbnZpdGVDb2RlGi8KFFJlbW92ZUFkZGl0aW9uYWxVc2VyEhcKB3VzZXJfaWQYASAB'
|
'x1ZV9jZW50cxgBIAEoDVIKdmFsdWVDZW50cxoNCgtHZXRMb2NhdGlvbhoNCgtHZXRWb3VjaGVy'
|
||||||
'KANSBnVzZXJJZBotChJHZXRQcmVrZXlzQnlVc2VySWQSFwoHdXNlcl9pZBgBIAEoA1IGdXNlck'
|
'cxoTChFHZXRBdmFpbGFibGVQbGFucxoXChVHZXRBZGRBY2NvdW50c0ludml0ZXMaFQoTR2V0Q3'
|
||||||
'lkGjsKDkdldFVwbG9hZFRva2VuEikKEHJlY2lwaWVudHNfY291bnQYASABKA1SD3JlY2lwaWVu'
|
'VycmVudFBsYW5JbmZvcxo3ChRSZWRlZW1BZGRpdGlvbmFsQ29kZRIfCgtpbnZpdGVfY29kZRgC'
|
||||||
'dHNDb3VudBqJAQoKVXBsb2FkRGF0YRIhCgx1cGxvYWRfdG9rZW4YASABKAxSC3VwbG9hZFRva2'
|
'IAEoCVIKaW52aXRlQ29kZRovChRSZW1vdmVBZGRpdGlvbmFsVXNlchIXCgd1c2VyX2lkGAEgAS'
|
||||||
'VuEhYKBm9mZnNldBgCIAEoDVIGb2Zmc2V0EhIKBGRhdGEYAyABKAxSBGRhdGESHwoIY2hlY2tz'
|
'gDUgZ1c2VySWQaLQoSR2V0UHJla2V5c0J5VXNlcklkEhcKB3VzZXJfaWQYASABKANSBnVzZXJJ'
|
||||||
'dW0YBCABKAxIAFIIY2hlY2tzdW2IAQFCCwoJX2NoZWNrc3VtGk0KDERvd25sb2FkRGF0YRIlCg'
|
'ZBo7Cg5HZXRVcGxvYWRUb2tlbhIpChByZWNpcGllbnRzX2NvdW50GAEgASgNUg9yZWNpcGllbn'
|
||||||
'5kb3dubG9hZF90b2tlbhgBIAEoDFINZG93bmxvYWRUb2tlbhIWCgZvZmZzZXQYAiABKA1SBm9m'
|
'RzQ291bnQaiQEKClVwbG9hZERhdGESIQoMdXBsb2FkX3Rva2VuGAEgASgMUgt1cGxvYWRUb2tl'
|
||||||
'ZnNldEIRCg9BcHBsaWNhdGlvbkRhdGE=');
|
'bhIWCgZvZmZzZXQYAiABKA1SBm9mZnNldBISCgRkYXRhGAMgASgMUgRkYXRhEh8KCGNoZWNrc3'
|
||||||
|
'VtGAQgASgMSABSCGNoZWNrc3VtiAEBQgsKCV9jaGVja3N1bRpaCgpVcGxvYWREb25lEiEKDHVw'
|
||||||
|
'bG9hZF90b2tlbhgBIAEoDFILdXBsb2FkVG9rZW4SKQoQcmVjaXBpZW50c19jb3VudBgCIAEoDV'
|
||||||
|
'IPcmVjaXBpZW50c0NvdW50Gk0KDERvd25sb2FkRGF0YRIlCg5kb3dubG9hZF90b2tlbhgBIAEo'
|
||||||
|
'DFINZG93bmxvYWRUb2tlbhIWCgZvZmZzZXQYAiABKA1SBm9mZnNldBo1CgxEb3dubG9hZERvbm'
|
||||||
|
'USJQoOZG93bmxvYWRfdG9rZW4YASABKAxSDWRvd25sb2FkVG9rZW5CEQoPQXBwbGljYXRpb25E'
|
||||||
|
'YXRh');
|
||||||
|
|
||||||
@$core.Deprecated('Use responseDescriptor instead')
|
@$core.Deprecated('Use responseDescriptor instead')
|
||||||
const Response$json = {
|
const Response$json = {
|
||||||
|
|
|
||||||
|
|
@ -1524,6 +1524,50 @@ class Response_UploadToken extends $pb.GeneratedMessage {
|
||||||
$core.List<$core.List<$core.int>> get downloadTokens => $_getList(1);
|
$core.List<$core.List<$core.int>> get downloadTokens => $_getList(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class Response_DownloadTokens extends $pb.GeneratedMessage {
|
||||||
|
factory Response_DownloadTokens({
|
||||||
|
$core.Iterable<$core.List<$core.int>>? downloadTokens,
|
||||||
|
}) {
|
||||||
|
final $result = create();
|
||||||
|
if (downloadTokens != null) {
|
||||||
|
$result.downloadTokens.addAll(downloadTokens);
|
||||||
|
}
|
||||||
|
return $result;
|
||||||
|
}
|
||||||
|
Response_DownloadTokens._() : super();
|
||||||
|
factory Response_DownloadTokens.fromBuffer($core.List<$core.int> i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromBuffer(i, r);
|
||||||
|
factory Response_DownloadTokens.fromJson($core.String i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromJson(i, r);
|
||||||
|
|
||||||
|
static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'Response.DownloadTokens', package: const $pb.PackageName(_omitMessageNames ? '' : 'server_to_client'), createEmptyInstance: create)
|
||||||
|
..p<$core.List<$core.int>>(1, _omitFieldNames ? '' : 'downloadTokens', $pb.PbFieldType.PY)
|
||||||
|
..hasRequiredFields = false
|
||||||
|
;
|
||||||
|
|
||||||
|
@$core.Deprecated(
|
||||||
|
'Using this can add significant overhead to your binary. '
|
||||||
|
'Use [GeneratedMessageGenericExtensions.deepCopy] instead. '
|
||||||
|
'Will be removed in next major version')
|
||||||
|
Response_DownloadTokens clone() => Response_DownloadTokens()..mergeFromMessage(this);
|
||||||
|
@$core.Deprecated(
|
||||||
|
'Using this can add significant overhead to your binary. '
|
||||||
|
'Use [GeneratedMessageGenericExtensions.rebuild] instead. '
|
||||||
|
'Will be removed in next major version')
|
||||||
|
Response_DownloadTokens copyWith(void Function(Response_DownloadTokens) updates) => super.copyWith((message) => updates(message as Response_DownloadTokens)) as Response_DownloadTokens;
|
||||||
|
|
||||||
|
$pb.BuilderInfo get info_ => _i;
|
||||||
|
|
||||||
|
@$core.pragma('dart2js:noInline')
|
||||||
|
static Response_DownloadTokens create() => Response_DownloadTokens._();
|
||||||
|
Response_DownloadTokens createEmptyInstance() => create();
|
||||||
|
static $pb.PbList<Response_DownloadTokens> createRepeated() => $pb.PbList<Response_DownloadTokens>();
|
||||||
|
@$core.pragma('dart2js:noInline')
|
||||||
|
static Response_DownloadTokens getDefault() => _defaultInstance ??= $pb.GeneratedMessage.$_defaultFor<Response_DownloadTokens>(create);
|
||||||
|
static Response_DownloadTokens? _defaultInstance;
|
||||||
|
|
||||||
|
@$pb.TagNumber(1)
|
||||||
|
$core.List<$core.List<$core.int>> get downloadTokens => $_getList(0);
|
||||||
|
}
|
||||||
|
|
||||||
enum Response_Ok_Ok {
|
enum Response_Ok_Ok {
|
||||||
none,
|
none,
|
||||||
userid,
|
userid,
|
||||||
|
|
@ -1537,6 +1581,7 @@ enum Response_Ok_Ok {
|
||||||
planballance,
|
planballance,
|
||||||
vouchers,
|
vouchers,
|
||||||
addaccountsinvites,
|
addaccountsinvites,
|
||||||
|
downloadtokens,
|
||||||
notSet
|
notSet
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1554,6 +1599,7 @@ class Response_Ok extends $pb.GeneratedMessage {
|
||||||
Response_PlanBallance? planballance,
|
Response_PlanBallance? planballance,
|
||||||
Response_Vouchers? vouchers,
|
Response_Vouchers? vouchers,
|
||||||
Response_AddAccountsInvites? addaccountsinvites,
|
Response_AddAccountsInvites? addaccountsinvites,
|
||||||
|
Response_DownloadTokens? downloadtokens,
|
||||||
}) {
|
}) {
|
||||||
final $result = create();
|
final $result = create();
|
||||||
if (none != null) {
|
if (none != null) {
|
||||||
|
|
@ -1592,6 +1638,9 @@ class Response_Ok extends $pb.GeneratedMessage {
|
||||||
if (addaccountsinvites != null) {
|
if (addaccountsinvites != null) {
|
||||||
$result.addaccountsinvites = addaccountsinvites;
|
$result.addaccountsinvites = addaccountsinvites;
|
||||||
}
|
}
|
||||||
|
if (downloadtokens != null) {
|
||||||
|
$result.downloadtokens = downloadtokens;
|
||||||
|
}
|
||||||
return $result;
|
return $result;
|
||||||
}
|
}
|
||||||
Response_Ok._() : super();
|
Response_Ok._() : super();
|
||||||
|
|
@ -1611,10 +1660,11 @@ class Response_Ok extends $pb.GeneratedMessage {
|
||||||
10 : Response_Ok_Ok.planballance,
|
10 : Response_Ok_Ok.planballance,
|
||||||
11 : Response_Ok_Ok.vouchers,
|
11 : Response_Ok_Ok.vouchers,
|
||||||
12 : Response_Ok_Ok.addaccountsinvites,
|
12 : Response_Ok_Ok.addaccountsinvites,
|
||||||
|
13 : Response_Ok_Ok.downloadtokens,
|
||||||
0 : Response_Ok_Ok.notSet
|
0 : Response_Ok_Ok.notSet
|
||||||
};
|
};
|
||||||
static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'Response.Ok', package: const $pb.PackageName(_omitMessageNames ? '' : 'server_to_client'), createEmptyInstance: create)
|
static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'Response.Ok', package: const $pb.PackageName(_omitMessageNames ? '' : 'server_to_client'), createEmptyInstance: create)
|
||||||
..oo(0, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12])
|
..oo(0, [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13])
|
||||||
..aOB(1, _omitFieldNames ? '' : 'None', protoName: 'None')
|
..aOB(1, _omitFieldNames ? '' : 'None', protoName: 'None')
|
||||||
..aInt64(2, _omitFieldNames ? '' : 'userid')
|
..aInt64(2, _omitFieldNames ? '' : 'userid')
|
||||||
..a<$core.List<$core.int>>(3, _omitFieldNames ? '' : 'authchallenge', $pb.PbFieldType.OY)
|
..a<$core.List<$core.int>>(3, _omitFieldNames ? '' : 'authchallenge', $pb.PbFieldType.OY)
|
||||||
|
|
@ -1627,6 +1677,7 @@ class Response_Ok extends $pb.GeneratedMessage {
|
||||||
..aOM<Response_PlanBallance>(10, _omitFieldNames ? '' : 'planballance', subBuilder: Response_PlanBallance.create)
|
..aOM<Response_PlanBallance>(10, _omitFieldNames ? '' : 'planballance', subBuilder: Response_PlanBallance.create)
|
||||||
..aOM<Response_Vouchers>(11, _omitFieldNames ? '' : 'vouchers', subBuilder: Response_Vouchers.create)
|
..aOM<Response_Vouchers>(11, _omitFieldNames ? '' : 'vouchers', subBuilder: Response_Vouchers.create)
|
||||||
..aOM<Response_AddAccountsInvites>(12, _omitFieldNames ? '' : 'addaccountsinvites', subBuilder: Response_AddAccountsInvites.create)
|
..aOM<Response_AddAccountsInvites>(12, _omitFieldNames ? '' : 'addaccountsinvites', subBuilder: Response_AddAccountsInvites.create)
|
||||||
|
..aOM<Response_DownloadTokens>(13, _omitFieldNames ? '' : 'downloadtokens', subBuilder: Response_DownloadTokens.create)
|
||||||
..hasRequiredFields = false
|
..hasRequiredFields = false
|
||||||
;
|
;
|
||||||
|
|
||||||
|
|
@ -1777,6 +1828,17 @@ class Response_Ok extends $pb.GeneratedMessage {
|
||||||
void clearAddaccountsinvites() => clearField(12);
|
void clearAddaccountsinvites() => clearField(12);
|
||||||
@$pb.TagNumber(12)
|
@$pb.TagNumber(12)
|
||||||
Response_AddAccountsInvites ensureAddaccountsinvites() => $_ensure(11);
|
Response_AddAccountsInvites ensureAddaccountsinvites() => $_ensure(11);
|
||||||
|
|
||||||
|
@$pb.TagNumber(13)
|
||||||
|
Response_DownloadTokens get downloadtokens => $_getN(12);
|
||||||
|
@$pb.TagNumber(13)
|
||||||
|
set downloadtokens(Response_DownloadTokens v) { setField(13, v); }
|
||||||
|
@$pb.TagNumber(13)
|
||||||
|
$core.bool hasDownloadtokens() => $_has(12);
|
||||||
|
@$pb.TagNumber(13)
|
||||||
|
void clearDownloadtokens() => clearField(13);
|
||||||
|
@$pb.TagNumber(13)
|
||||||
|
Response_DownloadTokens ensureDownloadtokens() => $_ensure(12);
|
||||||
}
|
}
|
||||||
|
|
||||||
enum Response_Response {
|
enum Response_Response {
|
||||||
|
|
|
||||||
|
|
@ -92,7 +92,7 @@ const Response$json = {
|
||||||
{'1': 'ok', '3': 1, '4': 1, '5': 11, '6': '.server_to_client.Response.Ok', '9': 0, '10': 'ok'},
|
{'1': 'ok', '3': 1, '4': 1, '5': 11, '6': '.server_to_client.Response.Ok', '9': 0, '10': 'ok'},
|
||||||
{'1': 'error', '3': 2, '4': 1, '5': 14, '6': '.error.ErrorCode', '9': 0, '10': 'error'},
|
{'1': 'error', '3': 2, '4': 1, '5': 14, '6': '.error.ErrorCode', '9': 0, '10': 'error'},
|
||||||
],
|
],
|
||||||
'3': [Response_Authenticated$json, Response_Plan$json, Response_Plans$json, Response_AddAccountsInvite$json, Response_AddAccountsInvites$json, Response_Transaction$json, Response_AdditionalAccount$json, Response_Voucher$json, Response_Vouchers$json, Response_PlanBallance$json, Response_Location$json, Response_PreKey$json, Response_UserData$json, Response_UploadToken$json, Response_Ok$json],
|
'3': [Response_Authenticated$json, Response_Plan$json, Response_Plans$json, Response_AddAccountsInvite$json, Response_AddAccountsInvites$json, Response_Transaction$json, Response_AdditionalAccount$json, Response_Voucher$json, Response_Vouchers$json, Response_PlanBallance$json, Response_Location$json, Response_PreKey$json, Response_UserData$json, Response_UploadToken$json, Response_DownloadTokens$json, Response_Ok$json],
|
||||||
'4': [Response_TransactionTypes$json],
|
'4': [Response_TransactionTypes$json],
|
||||||
'8': [
|
'8': [
|
||||||
{'1': 'Response'},
|
{'1': 'Response'},
|
||||||
|
|
@ -258,6 +258,14 @@ const Response_UploadToken$json = {
|
||||||
],
|
],
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@$core.Deprecated('Use responseDescriptor instead')
|
||||||
|
const Response_DownloadTokens$json = {
|
||||||
|
'1': 'DownloadTokens',
|
||||||
|
'2': [
|
||||||
|
{'1': 'download_tokens', '3': 1, '4': 3, '5': 12, '10': 'downloadTokens'},
|
||||||
|
],
|
||||||
|
};
|
||||||
|
|
||||||
@$core.Deprecated('Use responseDescriptor instead')
|
@$core.Deprecated('Use responseDescriptor instead')
|
||||||
const Response_Ok$json = {
|
const Response_Ok$json = {
|
||||||
'1': 'Ok',
|
'1': 'Ok',
|
||||||
|
|
@ -274,6 +282,7 @@ const Response_Ok$json = {
|
||||||
{'1': 'planballance', '3': 10, '4': 1, '5': 11, '6': '.server_to_client.Response.PlanBallance', '9': 0, '10': 'planballance'},
|
{'1': 'planballance', '3': 10, '4': 1, '5': 11, '6': '.server_to_client.Response.PlanBallance', '9': 0, '10': 'planballance'},
|
||||||
{'1': 'vouchers', '3': 11, '4': 1, '5': 11, '6': '.server_to_client.Response.Vouchers', '9': 0, '10': 'vouchers'},
|
{'1': 'vouchers', '3': 11, '4': 1, '5': 11, '6': '.server_to_client.Response.Vouchers', '9': 0, '10': 'vouchers'},
|
||||||
{'1': 'addaccountsinvites', '3': 12, '4': 1, '5': 11, '6': '.server_to_client.Response.AddAccountsInvites', '9': 0, '10': 'addaccountsinvites'},
|
{'1': 'addaccountsinvites', '3': 12, '4': 1, '5': 11, '6': '.server_to_client.Response.AddAccountsInvites', '9': 0, '10': 'addaccountsinvites'},
|
||||||
|
{'1': 'downloadtokens', '3': 13, '4': 1, '5': 11, '6': '.server_to_client.Response.DownloadTokens', '9': 0, '10': 'downloadtokens'},
|
||||||
],
|
],
|
||||||
'8': [
|
'8': [
|
||||||
{'1': 'Ok'},
|
{'1': 'Ok'},
|
||||||
|
|
@ -347,21 +356,23 @@ final $typed_data.Uint8List responseDescriptor = $convert.base64Decode(
|
||||||
'9wdWJsaWNfaWRlbnRpdHlfa2V5QhAKDl9zaWduZWRfcHJla2V5QhoKGF9zaWduZWRfcHJla2V5'
|
'9wdWJsaWNfaWRlbnRpdHlfa2V5QhAKDl9zaWduZWRfcHJla2V5QhoKGF9zaWduZWRfcHJla2V5'
|
||||||
'X3NpZ25hdHVyZUITChFfc2lnbmVkX3ByZWtleV9pZBpZCgtVcGxvYWRUb2tlbhIhCgx1cGxvYW'
|
'X3NpZ25hdHVyZUITChFfc2lnbmVkX3ByZWtleV9pZBpZCgtVcGxvYWRUb2tlbhIhCgx1cGxvYW'
|
||||||
'RfdG9rZW4YASABKAxSC3VwbG9hZFRva2VuEicKD2Rvd25sb2FkX3Rva2VucxgCIAMoDFIOZG93'
|
'RfdG9rZW4YASABKAxSC3VwbG9hZFRva2VuEicKD2Rvd25sb2FkX3Rva2VucxgCIAMoDFIOZG93'
|
||||||
'bmxvYWRUb2tlbnMa0wUKAk9rEhQKBE5vbmUYASABKAhIAFIETm9uZRIYCgZ1c2VyaWQYAiABKA'
|
'bmxvYWRUb2tlbnMaOQoORG93bmxvYWRUb2tlbnMSJwoPZG93bmxvYWRfdG9rZW5zGAEgAygMUg'
|
||||||
'NIAFIGdXNlcmlkEiYKDWF1dGhjaGFsbGVuZ2UYAyABKAxIAFINYXV0aGNoYWxsZW5nZRJKCgt1'
|
'5kb3dubG9hZFRva2VucxqoBgoCT2sSFAoETm9uZRgBIAEoCEgAUgROb25lEhgKBnVzZXJpZBgC'
|
||||||
'cGxvYWR0b2tlbhgEIAEoCzImLnNlcnZlcl90b19jbGllbnQuUmVzcG9uc2UuVXBsb2FkVG9rZW'
|
'IAEoA0gAUgZ1c2VyaWQSJgoNYXV0aGNoYWxsZW5nZRgDIAEoDEgAUg1hdXRoY2hhbGxlbmdlEk'
|
||||||
'5IAFILdXBsb2FkdG9rZW4SQQoIdXNlcmRhdGEYBSABKAsyIy5zZXJ2ZXJfdG9fY2xpZW50LlJl'
|
'oKC3VwbG9hZHRva2VuGAQgASgLMiYuc2VydmVyX3RvX2NsaWVudC5SZXNwb25zZS5VcGxvYWRU'
|
||||||
'c3BvbnNlLlVzZXJEYXRhSABSCHVzZXJkYXRhEh4KCWF1dGh0b2tlbhgGIAEoDEgAUglhdXRodG'
|
'b2tlbkgAUgt1cGxvYWR0b2tlbhJBCgh1c2VyZGF0YRgFIAEoCzIjLnNlcnZlcl90b19jbGllbn'
|
||||||
'9rZW4SQQoIbG9jYXRpb24YByABKAsyIy5zZXJ2ZXJfdG9fY2xpZW50LlJlc3BvbnNlLkxvY2F0'
|
'QuUmVzcG9uc2UuVXNlckRhdGFIAFIIdXNlcmRhdGESHgoJYXV0aHRva2VuGAYgASgMSABSCWF1'
|
||||||
'aW9uSABSCGxvY2F0aW9uElAKDWF1dGhlbnRpY2F0ZWQYCCABKAsyKC5zZXJ2ZXJfdG9fY2xpZW'
|
'dGh0b2tlbhJBCghsb2NhdGlvbhgHIAEoCzIjLnNlcnZlcl90b19jbGllbnQuUmVzcG9uc2UuTG'
|
||||||
'50LlJlc3BvbnNlLkF1dGhlbnRpY2F0ZWRIAFINYXV0aGVudGljYXRlZBI4CgVwbGFucxgJIAEo'
|
'9jYXRpb25IAFIIbG9jYXRpb24SUAoNYXV0aGVudGljYXRlZBgIIAEoCzIoLnNlcnZlcl90b19j'
|
||||||
'CzIgLnNlcnZlcl90b19jbGllbnQuUmVzcG9uc2UuUGxhbnNIAFIFcGxhbnMSTQoMcGxhbmJhbG'
|
'bGllbnQuUmVzcG9uc2UuQXV0aGVudGljYXRlZEgAUg1hdXRoZW50aWNhdGVkEjgKBXBsYW5zGA'
|
||||||
'xhbmNlGAogASgLMicuc2VydmVyX3RvX2NsaWVudC5SZXNwb25zZS5QbGFuQmFsbGFuY2VIAFIM'
|
'kgASgLMiAuc2VydmVyX3RvX2NsaWVudC5SZXNwb25zZS5QbGFuc0gAUgVwbGFucxJNCgxwbGFu'
|
||||||
'cGxhbmJhbGxhbmNlEkEKCHZvdWNoZXJzGAsgASgLMiMuc2VydmVyX3RvX2NsaWVudC5SZXNwb2'
|
'YmFsbGFuY2UYCiABKAsyJy5zZXJ2ZXJfdG9fY2xpZW50LlJlc3BvbnNlLlBsYW5CYWxsYW5jZU'
|
||||||
'5zZS5Wb3VjaGVyc0gAUgh2b3VjaGVycxJfChJhZGRhY2NvdW50c2ludml0ZXMYDCABKAsyLS5z'
|
'gAUgxwbGFuYmFsbGFuY2USQQoIdm91Y2hlcnMYCyABKAsyIy5zZXJ2ZXJfdG9fY2xpZW50LlJl'
|
||||||
'ZXJ2ZXJfdG9fY2xpZW50LlJlc3BvbnNlLkFkZEFjY291bnRzSW52aXRlc0gAUhJhZGRhY2NvdW'
|
'c3BvbnNlLlZvdWNoZXJzSABSCHZvdWNoZXJzEl8KEmFkZGFjY291bnRzaW52aXRlcxgMIAEoCz'
|
||||||
'50c2ludml0ZXNCBAoCT2silgEKEFRyYW5zYWN0aW9uVHlwZXMSCgoGUmVmdW5kEAASEwoPVm91'
|
'ItLnNlcnZlcl90b19jbGllbnQuUmVzcG9uc2UuQWRkQWNjb3VudHNJbnZpdGVzSABSEmFkZGFj'
|
||||||
'Y2hlclJlZGVlbWVkEAESEgoOVm91Y2hlckNyZWF0ZWQQAhIICgRDYXNoEAMSDwoLUGxhblVwZ3'
|
'Y291bnRzaW52aXRlcxJTCg5kb3dubG9hZHRva2VucxgNIAEoCzIpLnNlcnZlcl90b19jbGllbn'
|
||||||
'JhZGUQBBILCgdVbmtub3duEAUSFAoQVGhhbmtzRm9yVGVzdGluZxAGEg8KC0F1dG9SZW5ld2Fs'
|
'QuUmVzcG9uc2UuRG93bmxvYWRUb2tlbnNIAFIOZG93bmxvYWR0b2tlbnNCBAoCT2silgEKEFRy'
|
||||||
'EAdCCgoIUmVzcG9uc2U=');
|
'YW5zYWN0aW9uVHlwZXMSCgoGUmVmdW5kEAASEwoPVm91Y2hlclJlZGVlbWVkEAESEgoOVm91Y2'
|
||||||
|
'hlckNyZWF0ZWQQAhIICgRDYXNoEAMSDwoLUGxhblVwZ3JhZGUQBBILCgdVbmtub3duEAUSFAoQ'
|
||||||
|
'VGhhbmtzRm9yVGVzdGluZxAGEg8KC0F1dG9SZW5ld2FsEAdCCgoIUmVzcG9uc2U=');
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,6 @@
|
||||||
import 'dart:async';
|
import 'dart:async';
|
||||||
import 'dart:convert';
|
import 'dart:convert';
|
||||||
|
import 'package:flutter_secure_storage/flutter_secure_storage.dart';
|
||||||
import 'package:http/http.dart' as http;
|
import 'package:http/http.dart' as http;
|
||||||
import 'dart:io';
|
import 'dart:io';
|
||||||
import 'dart:typed_data';
|
import 'dart:typed_data';
|
||||||
|
|
@ -18,6 +19,7 @@ import 'package:twonly/src/model/json/message.dart';
|
||||||
import 'package:twonly/src/model/protobuf/api/error.pb.dart';
|
import 'package:twonly/src/model/protobuf/api/error.pb.dart';
|
||||||
import 'package:twonly/src/model/protobuf/api/server_to_client.pb.dart';
|
import 'package:twonly/src/model/protobuf/api/server_to_client.pb.dart';
|
||||||
import 'package:twonly/src/providers/api/api.dart';
|
import 'package:twonly/src/providers/api/api.dart';
|
||||||
|
import 'package:twonly/src/providers/api/api_utils.dart';
|
||||||
import 'package:twonly/src/providers/api/media_received.dart';
|
import 'package:twonly/src/providers/api/media_received.dart';
|
||||||
import 'package:twonly/src/services/notification_service.dart';
|
import 'package:twonly/src/services/notification_service.dart';
|
||||||
import 'package:twonly/src/utils/misc.dart';
|
import 'package:twonly/src/utils/misc.dart';
|
||||||
|
|
@ -49,48 +51,17 @@ Future<ErrorCode?> isAllowedToSend() async {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Process the image up to the point more user informations are required
|
/// States:
|
||||||
/// Returns the media upload id
|
/// when user recorded an video
|
||||||
Future<int> preSendMediaFile(Uint8List imageBytes, File? videoFilePath) async {
|
/// 1. Compress video
|
||||||
return 0;
|
/// when user clicked the send button (direct send) or share with
|
||||||
}
|
/// 2. Encrypt media files
|
||||||
|
/// 3. Upload media files
|
||||||
|
/// click send button
|
||||||
|
/// 4. Finalize upload by websocket -> get download tokens
|
||||||
|
/// 5. Send all users the message
|
||||||
|
|
||||||
Future cancelSendMediaFile(int mediaUploadId) async {}
|
/// Create a new entry in the database
|
||||||
|
|
||||||
Future finalizeSendMediaFile(int mediaUploadId, List<int> userIds,
|
|
||||||
bool isRealTwonly, bool isVideo, bool mirrorVideo, int maxShowTime) async {}
|
|
||||||
|
|
||||||
Future sendMediaFile(
|
|
||||||
List<int> userIds,
|
|
||||||
Uint8List imageBytes,
|
|
||||||
bool isRealTwonly,
|
|
||||||
int maxShowTime,
|
|
||||||
File? videoFilePath,
|
|
||||||
bool mirrorVideo,
|
|
||||||
) async {
|
|
||||||
MediaUploadMetadata metadata = MediaUploadMetadata();
|
|
||||||
metadata.contactIds = userIds;
|
|
||||||
metadata.isRealTwonly = isRealTwonly;
|
|
||||||
metadata.messageSendAt = DateTime.now();
|
|
||||||
metadata.isVideo = videoFilePath != null;
|
|
||||||
metadata.maxShowTime = maxShowTime;
|
|
||||||
metadata.mirrorVideo = mirrorVideo;
|
|
||||||
|
|
||||||
int? mediaUploadId = await twonlyDatabase.mediaUploadsDao.insertMediaUpload(
|
|
||||||
MediaUploadsCompanion(
|
|
||||||
metadata: Value(metadata),
|
|
||||||
),
|
|
||||||
);
|
|
||||||
|
|
||||||
if (mediaUploadId != null) {
|
|
||||||
if (videoFilePath != null) {
|
|
||||||
String basePath = await getMediaFilePath(mediaUploadId, "send");
|
|
||||||
await videoFilePath.rename("$basePath.orginal.mp4");
|
|
||||||
}
|
|
||||||
await writeMediaFile(mediaUploadId, "orginal.png", imageBytes);
|
|
||||||
await handleSingleMediaFile(mediaUploadId, imageBytes);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
final lockingHandleMediaFile = Mutex();
|
final lockingHandleMediaFile = Mutex();
|
||||||
Future retryMediaUpload({int maxRetries = 3}) async {
|
Future retryMediaUpload({int maxRetries = 3}) async {
|
||||||
|
|
@ -99,7 +70,22 @@ Future retryMediaUpload({int maxRetries = 3}) async {
|
||||||
await twonlyDatabase.mediaUploadsDao.getMediaUploadsForRetry();
|
await twonlyDatabase.mediaUploadsDao.getMediaUploadsForRetry();
|
||||||
if (mediaFiles.isEmpty) return;
|
if (mediaFiles.isEmpty) return;
|
||||||
for (final mediaFile in mediaFiles) {
|
for (final mediaFile in mediaFiles) {
|
||||||
await handleSingleMediaFile(mediaFile.mediaUploadId, null);
|
if (mediaFile.messageIds == null || mediaFile.metadata == null) {
|
||||||
|
// the media upload was canceled,
|
||||||
|
if (mediaFile.uploadTokens != null) {
|
||||||
|
/// the file was already uploaded.
|
||||||
|
/// notify the server to remove the upload
|
||||||
|
}
|
||||||
|
Logger("media_send.dart").shout(
|
||||||
|
"upload can be removed, the finalized function was never called...");
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mediaFile.state == UploadState.readyToUpload) {
|
||||||
|
await handleNextMediaUploadSteps(mediaFile.mediaUploadId);
|
||||||
|
} else {
|
||||||
|
await handlePreProcessingState(mediaFile);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
if (maxRetries == 0) return;
|
if (maxRetries == 0) return;
|
||||||
|
|
@ -109,131 +95,19 @@ Future retryMediaUpload({int maxRetries = 3}) async {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
Future handleSingleMediaFile(
|
Future<int?> initMediaUpload() async {
|
||||||
int mediaUploadId, Uint8List? tmpCurrentImageBytes) async {
|
return await twonlyDatabase.mediaUploadsDao
|
||||||
MediaUpload? media = await twonlyDatabase.mediaUploadsDao
|
.insertMediaUpload(MediaUploadsCompanion());
|
||||||
.getMediaUploadById(mediaUploadId)
|
|
||||||
.getSingleOrNull();
|
|
||||||
if (media == null) return;
|
|
||||||
|
|
||||||
try {
|
|
||||||
switch (media.state) {
|
|
||||||
case UploadState.pending:
|
|
||||||
await handleAddToMessageDb(media);
|
|
||||||
break;
|
|
||||||
case UploadState.addedToMessagesDb:
|
|
||||||
tmpCurrentImageBytes =
|
|
||||||
await handleCompressionState(media, tmpCurrentImageBytes);
|
|
||||||
break;
|
|
||||||
case UploadState.isCompressed:
|
|
||||||
tmpCurrentImageBytes =
|
|
||||||
await handleEncryptionState(media, tmpCurrentImageBytes);
|
|
||||||
break;
|
|
||||||
case UploadState.isEncrypted:
|
|
||||||
if (!await handleGetUploadToken(media)) {
|
|
||||||
return; // recoverable error. try again when connected again to the server...
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case UploadState.hasUploadToken:
|
|
||||||
if (!await handleUploadHttp(media, tmpCurrentImageBytes)) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
// if (!await handleUpload(media, tmpCurrentImageBytes)) {
|
|
||||||
// return; // recoverable error. try again when connected again to the server...
|
|
||||||
// }
|
|
||||||
break;
|
|
||||||
case UploadState.isUploaded:
|
|
||||||
if (!await handleNotifyReceiver(media)) {
|
|
||||||
return; // recoverable error. try again when connected again to the server...
|
|
||||||
}
|
|
||||||
try {
|
|
||||||
// delete non compressed media files
|
|
||||||
await deleteMediaFile(media.mediaUploadId, "orginal.png");
|
|
||||||
await deleteMediaFile(media.mediaUploadId, "orginal.mp4");
|
|
||||||
await deleteMediaFile(media.mediaUploadId, "encrypted");
|
|
||||||
} catch (e) {
|
|
||||||
Logger("media_send.dart").shout("$e");
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case UploadState.receiverNotified:
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
} catch (e) {
|
|
||||||
// if the messageIds are already there notify the user about this error...
|
|
||||||
if (media.messageIds != null) {
|
|
||||||
for (int messageId in media.messageIds!) {
|
|
||||||
await twonlyDatabase.messagesDao.updateMessageByMessageId(
|
|
||||||
messageId,
|
|
||||||
MessagesCompanion(
|
|
||||||
errorWhileSending: Value(true),
|
|
||||||
),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
await twonlyDatabase.mediaUploadsDao.deleteMediaUpload(mediaUploadId);
|
|
||||||
Logger("media_send.dart")
|
|
||||||
.shout("Non recoverable error while sending media file: $e");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
// this will be called until there is an recoverable error OR
|
|
||||||
// the upload is ready
|
|
||||||
await handleSingleMediaFile(mediaUploadId, tmpCurrentImageBytes);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Future handleAddToMessageDb(MediaUpload media) async {
|
Future<bool> addVideoToUpload(int mediaUploadId, File videoFilePath) async {
|
||||||
List<int> messageIds = [];
|
String basePath = await getMediaFilePath(mediaUploadId, "send");
|
||||||
|
await videoFilePath.rename("$basePath.original.mp4");
|
||||||
for (final contactId in media.metadata.contactIds) {
|
return await compressVideoIfExists(mediaUploadId);
|
||||||
int? messageId = await twonlyDatabase.messagesDao.insertMessage(
|
|
||||||
MessagesCompanion(
|
|
||||||
contactId: Value(contactId),
|
|
||||||
kind: Value(MessageKind.media),
|
|
||||||
sendAt: Value(media.metadata.messageSendAt),
|
|
||||||
downloadState: Value(DownloadState.pending),
|
|
||||||
mediaUploadId: Value(media.mediaUploadId),
|
|
||||||
contentJson: Value(
|
|
||||||
jsonEncode(
|
|
||||||
MediaMessageContent(
|
|
||||||
maxShowTime: media.metadata.maxShowTime,
|
|
||||||
isRealTwonly: media.metadata.isRealTwonly,
|
|
||||||
isVideo: media.metadata.isVideo,
|
|
||||||
mirrorVideo: media.metadata.mirrorVideo,
|
|
||||||
).toJson(),
|
|
||||||
),
|
|
||||||
),
|
|
||||||
),
|
|
||||||
); // dearchive contact when sending a new message
|
|
||||||
await twonlyDatabase.contactsDao.updateContact(
|
|
||||||
contactId,
|
|
||||||
ContactsCompanion(
|
|
||||||
archived: Value(false),
|
|
||||||
),
|
|
||||||
);
|
|
||||||
if (messageId != null) {
|
|
||||||
messageIds.add(messageId);
|
|
||||||
} else {
|
|
||||||
Logger("media_send.dart")
|
|
||||||
.shout("Error inserting media upload message in database.");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
await twonlyDatabase.mediaUploadsDao.updateMediaUpload(
|
|
||||||
media.mediaUploadId,
|
|
||||||
MediaUploadsCompanion(
|
|
||||||
state: Value(UploadState.addedToMessagesDb),
|
|
||||||
messageIds: Value(messageIds),
|
|
||||||
),
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<Uint8List?> handleCompressionState(
|
Future<Uint8List> addOrModifyImageToUpload(
|
||||||
MediaUpload media,
|
int mediaUploadId, Uint8List imageBytes) async {
|
||||||
Uint8List? tmpCurrentImageBytes,
|
|
||||||
) async {
|
|
||||||
Uint8List imageBytes = (tmpCurrentImageBytes != null)
|
|
||||||
? tmpCurrentImageBytes
|
|
||||||
: await readMediaFile(media, "orginal.png");
|
|
||||||
|
|
||||||
Uint8List imageBytesCompressed;
|
Uint8List imageBytesCompressed;
|
||||||
try {
|
try {
|
||||||
imageBytesCompressed = await FlutterImageCompress.compressWithList(
|
imageBytesCompressed = await FlutterImageCompress.compressWithList(
|
||||||
|
|
@ -242,84 +116,62 @@ Future<Uint8List?> handleCompressionState(
|
||||||
quality: 90,
|
quality: 90,
|
||||||
);
|
);
|
||||||
|
|
||||||
if (imageBytesCompressed.length >= 1 * 1000 * 1000) {
|
if (imageBytesCompressed.length >= 2 * 1000 * 1000) {
|
||||||
// if the media file is over 1MB compress it with 60%
|
// if the media file is over 2MB compress it with 60%
|
||||||
imageBytesCompressed = await FlutterImageCompress.compressWithList(
|
imageBytesCompressed = await FlutterImageCompress.compressWithList(
|
||||||
format: CompressFormat.png,
|
format: CompressFormat.png,
|
||||||
imageBytes,
|
imageBytes,
|
||||||
quality: 60,
|
quality: 60,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
await writeMediaFile(media.mediaUploadId, "png", imageBytesCompressed);
|
await writeMediaFile(mediaUploadId, "png", imageBytesCompressed);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
Logger("media_send.dart").shout("$e");
|
Logger("media_send.dart").shout("$e");
|
||||||
// as a fall back use the orginal image
|
// as a fall back use the original image
|
||||||
await writeMediaFile(media.mediaUploadId, "png", imageBytes);
|
await writeMediaFile(mediaUploadId, "png", imageBytes);
|
||||||
imageBytesCompressed = imageBytes;
|
imageBytesCompressed = imageBytes;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (media.metadata.isVideo) {
|
/// in case the media file was already encrypted of even uploaded
|
||||||
String basePath = await getMediaFilePath(media.mediaUploadId, "send");
|
/// remove the data so it will be done again.
|
||||||
File videoOriginalFile = File("$basePath.orginal.mp4");
|
/// TODO: when the uploadTokens are already set notify the server...
|
||||||
File videoCompressedFile = File("$basePath.mp4");
|
|
||||||
|
|
||||||
MediaInfo? mediaInfo;
|
|
||||||
|
|
||||||
try {
|
|
||||||
mediaInfo = await VideoCompress.compressVideo(
|
|
||||||
videoOriginalFile.path,
|
|
||||||
quality: VideoQuality.Res1280x720Quality,
|
|
||||||
deleteOrigin: false,
|
|
||||||
includeAudio:
|
|
||||||
true, // https://github.com/jonataslaw/VideoCompress/issues/184
|
|
||||||
);
|
|
||||||
|
|
||||||
if (mediaInfo!.filesize! >= 30 * 1000 * 1000) {
|
|
||||||
// if the media file is over 20MB compress it with low quality
|
|
||||||
mediaInfo = await VideoCompress.compressVideo(
|
|
||||||
videoOriginalFile.path,
|
|
||||||
quality: VideoQuality.Res960x540Quality,
|
|
||||||
deleteOrigin: false,
|
|
||||||
includeAudio: true,
|
|
||||||
);
|
|
||||||
}
|
|
||||||
} catch (e) {
|
|
||||||
Logger("media_send.dart").shout("Video compression: $e");
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mediaInfo == null) {
|
|
||||||
Logger("media_send.dart").shout("Error compressing video.");
|
|
||||||
// as a fall back use the non compressed version
|
|
||||||
await videoOriginalFile.copy(videoCompressedFile.path);
|
|
||||||
await videoOriginalFile.delete();
|
|
||||||
} else {
|
|
||||||
await mediaInfo.file!.copy(videoCompressedFile.path);
|
|
||||||
await mediaInfo.file!.delete();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
await twonlyDatabase.mediaUploadsDao.updateMediaUpload(
|
await twonlyDatabase.mediaUploadsDao.updateMediaUpload(
|
||||||
media.mediaUploadId,
|
mediaUploadId,
|
||||||
MediaUploadsCompanion(
|
MediaUploadsCompanion(
|
||||||
state: Value(UploadState.isCompressed),
|
encryptionData: Value(null),
|
||||||
|
uploadTokens: Value(null),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
|
|
||||||
return imageBytesCompressed;
|
return imageBytesCompressed;
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<Uint8List> handleEncryptionState(
|
Future handlePreProcessingState(MediaUpload media) async {
|
||||||
MediaUpload media, Uint8List? tmpCurrentImageBytes) async {
|
try {
|
||||||
var state = MediaEncryptionData();
|
final imageHandler = readMediaFile(media.mediaUploadId, "png");
|
||||||
|
final videoHandler = compressVideoIfExists(media.mediaUploadId);
|
||||||
Uint8List dataToEncrypt = (tmpCurrentImageBytes != null)
|
await encryptAndPreUploadMediaFiles(
|
||||||
? tmpCurrentImageBytes
|
media.mediaUploadId,
|
||||||
: await readMediaFile(media, "png");
|
imageHandler,
|
||||||
|
videoHandler,
|
||||||
if (media.metadata.isVideo) {
|
);
|
||||||
Uint8List compressedVideo = await readMediaFile(media, "mp4");
|
} catch (e) {
|
||||||
dataToEncrypt = combineUint8Lists(dataToEncrypt, compressedVideo);
|
await handleUploadError(media);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Future encryptAndPreUploadMediaFiles(
|
||||||
|
int mediaUploadId, Future imageHandler, Future<bool>? videoHandler) async {
|
||||||
|
Uint8List dataToEncrypt = await imageHandler;
|
||||||
|
|
||||||
|
/// if there is a video wait until it is finished with compression
|
||||||
|
if (videoHandler != null) {
|
||||||
|
if (await videoHandler) {
|
||||||
|
Uint8List compressedVideo = await readMediaFile(mediaUploadId, "mp4");
|
||||||
|
dataToEncrypt = combineUint8Lists(dataToEncrypt, compressedVideo);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
var state = MediaEncryptionData();
|
||||||
|
|
||||||
final xchacha20 = Xchacha20.poly1305Aead();
|
final xchacha20 = Xchacha20.poly1305Aead();
|
||||||
SecretKeyData secretKey = await (await xchacha20.newSecretKey()).extract();
|
SecretKeyData secretKey = await (await xchacha20.newSecretKey()).extract();
|
||||||
|
|
@ -340,26 +192,161 @@ Future<Uint8List> handleEncryptionState(
|
||||||
|
|
||||||
final encryptedBytes = Uint8List.fromList(secretBox.cipherText);
|
final encryptedBytes = Uint8List.fromList(secretBox.cipherText);
|
||||||
await writeMediaFile(
|
await writeMediaFile(
|
||||||
media.mediaUploadId,
|
mediaUploadId,
|
||||||
"encrypted",
|
"encrypted",
|
||||||
encryptedBytes,
|
encryptedBytes,
|
||||||
);
|
);
|
||||||
|
|
||||||
await twonlyDatabase.mediaUploadsDao.updateMediaUpload(
|
await twonlyDatabase.mediaUploadsDao.updateMediaUpload(
|
||||||
media.mediaUploadId,
|
mediaUploadId,
|
||||||
MediaUploadsCompanion(
|
MediaUploadsCompanion(
|
||||||
state: Value(UploadState.isEncrypted),
|
state: Value(UploadState.readyToUpload),
|
||||||
encryptionData: Value(state),
|
encryptionData: Value(state),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
return encryptedBytes;
|
await handleNextMediaUploadSteps(mediaUploadId);
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<bool> handleGetUploadToken(MediaUpload media) async {
|
Future cancelSendMediaFile(int mediaUploadId) async {
|
||||||
final res =
|
await twonlyDatabase.mediaUploadsDao.deleteMediaUpload(mediaUploadId);
|
||||||
await apiProvider.getUploadToken(media.metadata.contactIds.length);
|
|
||||||
|
|
||||||
if (res.isError || !res.value.hasUploadtoken()) {
|
/// server should purge the uploads... when it did not receive a
|
||||||
|
}
|
||||||
|
|
||||||
|
Future finalizeUpload(int mediaUploadId, List<int> contactIds,
|
||||||
|
bool isRealTwonly, bool isVideo, bool mirrorVideo, int maxShowTime) async {
|
||||||
|
MediaUploadMetadata metadata = MediaUploadMetadata();
|
||||||
|
metadata.contactIds = contactIds;
|
||||||
|
metadata.isRealTwonly = isRealTwonly;
|
||||||
|
metadata.messageSendAt = DateTime.now();
|
||||||
|
metadata.isVideo = isVideo;
|
||||||
|
metadata.maxShowTime = maxShowTime;
|
||||||
|
metadata.mirrorVideo = mirrorVideo;
|
||||||
|
|
||||||
|
List<int> messageIds = [];
|
||||||
|
|
||||||
|
for (final contactId in contactIds) {
|
||||||
|
int? messageId = await twonlyDatabase.messagesDao.insertMessage(
|
||||||
|
MessagesCompanion(
|
||||||
|
contactId: Value(contactId),
|
||||||
|
kind: Value(MessageKind.media),
|
||||||
|
sendAt: Value(metadata.messageSendAt),
|
||||||
|
downloadState: Value(DownloadState.pending),
|
||||||
|
mediaUploadId: Value(mediaUploadId),
|
||||||
|
contentJson: Value(
|
||||||
|
jsonEncode(
|
||||||
|
MediaMessageContent(
|
||||||
|
maxShowTime: maxShowTime,
|
||||||
|
isRealTwonly: isRealTwonly,
|
||||||
|
isVideo: isVideo,
|
||||||
|
mirrorVideo: mirrorVideo,
|
||||||
|
).toJson(),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
// de-archive contact when sending a new message
|
||||||
|
await twonlyDatabase.contactsDao.updateContact(
|
||||||
|
contactId,
|
||||||
|
ContactsCompanion(
|
||||||
|
archived: Value(false),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
if (messageId != null) {
|
||||||
|
messageIds.add(messageId);
|
||||||
|
} else {
|
||||||
|
Logger("media_send.dart")
|
||||||
|
.shout("Error inserting media upload message in database.");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
await twonlyDatabase.mediaUploadsDao.updateMediaUpload(
|
||||||
|
mediaUploadId,
|
||||||
|
MediaUploadsCompanion(
|
||||||
|
messageIds: Value(messageIds),
|
||||||
|
metadata: Value(metadata),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
final lockingHandleNextMediaUploadStep = Mutex();
|
||||||
|
Future handleNextMediaUploadSteps(int mediaUploadId) async {
|
||||||
|
bool rerun = await lockingHandleNextMediaUploadStep.protect<bool>(() async {
|
||||||
|
var mediaUpload = await twonlyDatabase.mediaUploadsDao
|
||||||
|
.getMediaUploadById(mediaUploadId)
|
||||||
|
.getSingleOrNull();
|
||||||
|
|
||||||
|
if (mediaUpload == null) return false;
|
||||||
|
if (mediaUpload.state == UploadState.receiverNotified) {
|
||||||
|
/// Upload done and all users are notified :)
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
/// Stage 1: media files are not yet encrypted...
|
||||||
|
if (mediaUpload.encryptionData == null) {
|
||||||
|
// when set this function will be called again by encryptAndPreUploadMediaFiles...
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mediaUpload.uploadTokens == null) {
|
||||||
|
/// the files are not yet uploaded, handle upload...
|
||||||
|
/// if the upload succeed the uploadTokens was updated and this function
|
||||||
|
/// can be called again to processed the upload done
|
||||||
|
return await handleMediaUpload(mediaUploadId);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mediaUpload.messageIds == null || mediaUpload.metadata == null) {
|
||||||
|
/// the finalize function was not called yet...
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// at this point the media file is uploaded and the receiver are known.
|
||||||
|
final downloadTokens = mediaUpload.uploadTokens!.downloadTokens;
|
||||||
|
if (downloadTokens.isEmpty) {
|
||||||
|
/// there are no download tokens yet, request them...
|
||||||
|
return await handleUploadDone(mediaUpload);
|
||||||
|
}
|
||||||
|
|
||||||
|
// download tokens are known so send the media file to the receivers
|
||||||
|
await handleNotifyReceiver(mediaUpload);
|
||||||
|
} catch (e) {
|
||||||
|
Logger("media_send.dart")
|
||||||
|
.shout("Non recoverable error while sending media file: $e");
|
||||||
|
await handleUploadError(mediaUpload);
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
});
|
||||||
|
if (rerun) {
|
||||||
|
handleNextMediaUploadSteps(mediaUploadId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
///
|
||||||
|
/// -- private functions --
|
||||||
|
///
|
||||||
|
///
|
||||||
|
///
|
||||||
|
Future handleUploadError(MediaUpload mediaUpload) async {
|
||||||
|
// if the messageIds are already there notify the user about this error...
|
||||||
|
if (mediaUpload.messageIds != null) {
|
||||||
|
for (int messageId in mediaUpload.messageIds!) {
|
||||||
|
await twonlyDatabase.messagesDao.updateMessageByMessageId(
|
||||||
|
messageId,
|
||||||
|
MessagesCompanion(
|
||||||
|
errorWhileSending: Value(true),
|
||||||
|
),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
await twonlyDatabase.mediaUploadsDao
|
||||||
|
.deleteMediaUpload(mediaUpload.mediaUploadId);
|
||||||
|
}
|
||||||
|
|
||||||
|
Future<bool> handleUploadDone(MediaUpload media) async {
|
||||||
|
Result res = await apiProvider.getDownloadTokens(
|
||||||
|
media.uploadTokens!.uploadToken, media.messageIds!.length);
|
||||||
|
|
||||||
|
if (res.isError || !res.value.hasDownloadtokens()) {
|
||||||
if (res.isError) {
|
if (res.isError) {
|
||||||
if (res.error == ErrorCode.PlanNotAllowed) {
|
if (res.error == ErrorCode.PlanNotAllowed) {
|
||||||
throw Exception("PlanNotAllowed");
|
throw Exception("PlanNotAllowed");
|
||||||
|
|
@ -369,36 +356,33 @@ Future<bool> handleGetUploadToken(MediaUpload media) async {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Logger("media_send.dart")
|
Logger("media_send.dart")
|
||||||
.shout("Will be tried again when reconnected to server!");
|
.info("Upload done will be tried again when reconnected to server!");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
Response_UploadToken tokens = res.value.uploadtoken;
|
Response_DownloadTokens tokens = res.value.downloadtokens;
|
||||||
|
|
||||||
var token = MediaUploadTokens();
|
var token = MediaUploadTokens();
|
||||||
token.uploadToken = tokens.uploadToken;
|
token.uploadToken = media.uploadTokens!.uploadToken;
|
||||||
token.downloadTokens = tokens.downloadTokens;
|
token.downloadTokens = tokens.downloadTokens;
|
||||||
|
|
||||||
await twonlyDatabase.mediaUploadsDao.updateMediaUpload(
|
await twonlyDatabase.mediaUploadsDao.updateMediaUpload(
|
||||||
media.mediaUploadId,
|
media.mediaUploadId,
|
||||||
MediaUploadsCompanion(
|
MediaUploadsCompanion(
|
||||||
state: Value(UploadState.hasUploadToken),
|
|
||||||
uploadTokens: Value(token),
|
uploadTokens: Value(token),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
String uint8ListToHex(List<int> bytes) {
|
Future<bool> handleMediaUpload(int mediaUploadId) async {
|
||||||
return bytes.map((byte) => byte.toRadixString(16).padLeft(2, '0')).join();
|
Uint8List bytesToUpload = await readMediaFile(mediaUploadId, "encrypted");
|
||||||
}
|
|
||||||
|
|
||||||
Future<bool> handleUploadHttp(
|
final storage = FlutterSecureStorage();
|
||||||
MediaUpload media, Uint8List? tmpCurrentImageBytes) async {
|
String? apiAuthToken = await storage.read(key: "api_auth_token");
|
||||||
Uint8List bytesToUpload = (tmpCurrentImageBytes != null)
|
if (apiAuthToken == null) {
|
||||||
? tmpCurrentImageBytes
|
Logger("media_send.dart").shout("api auth token not defined.");
|
||||||
: await readMediaFile(media, "encrypted");
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
String apiUrl =
|
String apiUrl =
|
||||||
"http${apiProvider.apiSecure}://${apiProvider.apiHost}/api/upload";
|
"http${apiProvider.apiSecure}://${apiProvider.apiHost}/api/upload";
|
||||||
|
|
@ -407,33 +391,45 @@ Future<bool> handleUploadHttp(
|
||||||
"POST",
|
"POST",
|
||||||
Uri.parse(apiUrl),
|
Uri.parse(apiUrl),
|
||||||
);
|
);
|
||||||
|
requestMultipart.headers['x-twonly-auth-token'] =
|
||||||
|
uint8ListToHex(base64Decode(apiAuthToken));
|
||||||
|
|
||||||
requestMultipart.files.add(http.MultipartFile.fromBytes(
|
requestMultipart.files.add(http.MultipartFile.fromBytes(
|
||||||
"file",
|
"file",
|
||||||
bytesToUpload,
|
bytesToUpload,
|
||||||
filename: uint8ListToHex(media.uploadTokens!.uploadToken),
|
filename: "upload",
|
||||||
));
|
));
|
||||||
|
|
||||||
try {
|
try {
|
||||||
var streamedResponse = await requestMultipart.send();
|
var streamedResponse = await requestMultipart.send();
|
||||||
|
|
||||||
await streamedResponse.stream.drain();
|
final response = await http.Response.fromStream(streamedResponse);
|
||||||
Logger("media_send.dart").info("Uploaded: ${streamedResponse.statusCode}");
|
|
||||||
|
if (response.statusCode == 200) {
|
||||||
|
Logger("media_send.dart").info("Uploaded: $response");
|
||||||
|
if (response.body.length != 64) {
|
||||||
|
Logger("media_send.dart").info("Got invalid upload token.");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
final uploadToken = hexToUint8List(response.body);
|
||||||
|
|
||||||
|
var token = MediaUploadTokens();
|
||||||
|
token.uploadToken = uploadToken;
|
||||||
|
token.downloadTokens = [];
|
||||||
|
|
||||||
if (streamedResponse.statusCode == 200) {
|
|
||||||
await twonlyDatabase.mediaUploadsDao.updateMediaUpload(
|
await twonlyDatabase.mediaUploadsDao.updateMediaUpload(
|
||||||
media.mediaUploadId,
|
mediaUploadId,
|
||||||
MediaUploadsCompanion(
|
MediaUploadsCompanion(
|
||||||
state: Value(UploadState.isUploaded),
|
uploadTokens: Value(token),
|
||||||
),
|
),
|
||||||
);
|
);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return false;
|
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
Logger("media_send.dart").shout("Exception during upload: $e");
|
Logger("media_send.dart").shout("Exception during upload: $e");
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<bool> handleNotifyReceiver(MediaUpload media) async {
|
Future<bool> handleNotifyReceiver(MediaUpload media) async {
|
||||||
|
|
@ -466,19 +462,19 @@ Future<bool> handleNotifyReceiver(MediaUpload media) async {
|
||||||
messageId: messageId,
|
messageId: messageId,
|
||||||
content: MediaMessageContent(
|
content: MediaMessageContent(
|
||||||
downloadToken: media.uploadTokens!.downloadTokens[i],
|
downloadToken: media.uploadTokens!.downloadTokens[i],
|
||||||
maxShowTime: media.metadata.maxShowTime,
|
maxShowTime: media.metadata!.maxShowTime,
|
||||||
isRealTwonly: media.metadata.isRealTwonly,
|
isRealTwonly: media.metadata!.isRealTwonly,
|
||||||
isVideo: media.metadata.isVideo,
|
isVideo: media.metadata!.isVideo,
|
||||||
mirrorVideo: media.metadata.mirrorVideo,
|
mirrorVideo: media.metadata!.mirrorVideo,
|
||||||
encryptionKey: media.encryptionData!.encryptionKey,
|
encryptionKey: media.encryptionData!.encryptionKey,
|
||||||
encryptionMac: media.encryptionData!.encryptionMac,
|
encryptionMac: media.encryptionData!.encryptionMac,
|
||||||
encryptionNonce: media.encryptionData!.encryptionNonce,
|
encryptionNonce: media.encryptionData!.encryptionNonce,
|
||||||
),
|
),
|
||||||
timestamp: media.metadata.messageSendAt,
|
timestamp: media.metadata!.messageSendAt,
|
||||||
),
|
),
|
||||||
pushKind: (media.metadata.isRealTwonly)
|
pushKind: (media.metadata!.isRealTwonly)
|
||||||
? PushKind.twonly
|
? PushKind.twonly
|
||||||
: (media.metadata.isVideo)
|
: (media.metadata!.isVideo)
|
||||||
? PushKind.video
|
? PushKind.video
|
||||||
: PushKind.image,
|
: PushKind.image,
|
||||||
);
|
);
|
||||||
|
|
@ -501,10 +497,61 @@ Future<bool> handleNotifyReceiver(MediaUpload media) async {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Future<bool> compressVideoIfExists(int mediaUploadId) async {
|
||||||
|
String basePath = await getMediaFilePath(mediaUploadId, "send");
|
||||||
|
File videoOriginalFile = File("$basePath.orginal.mp4");
|
||||||
|
File videoCompressedFile = File("$basePath.mp4");
|
||||||
|
|
||||||
|
if (videoCompressedFile.existsSync()) {
|
||||||
|
// file is already compressed and exists
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!videoOriginalFile.existsSync()) {
|
||||||
|
// media upload does not have a video
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
MediaInfo? mediaInfo;
|
||||||
|
|
||||||
|
try {
|
||||||
|
mediaInfo = await VideoCompress.compressVideo(
|
||||||
|
videoOriginalFile.path,
|
||||||
|
quality: VideoQuality.Res1280x720Quality,
|
||||||
|
deleteOrigin: false,
|
||||||
|
includeAudio:
|
||||||
|
true, // https://github.com/jonataslaw/VideoCompress/issues/184
|
||||||
|
);
|
||||||
|
|
||||||
|
if (mediaInfo!.filesize! >= 30 * 1000 * 1000) {
|
||||||
|
// if the media file is over 20MB compress it with low quality
|
||||||
|
mediaInfo = await VideoCompress.compressVideo(
|
||||||
|
videoOriginalFile.path,
|
||||||
|
quality: VideoQuality.Res960x540Quality,
|
||||||
|
deleteOrigin: false,
|
||||||
|
includeAudio: true,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
Logger("media_send.dart").shout("Video compression: $e");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mediaInfo == null) {
|
||||||
|
Logger("media_send.dart").shout("Error compressing video.");
|
||||||
|
// as a fall back use the non compressed version
|
||||||
|
await videoOriginalFile.copy(videoCompressedFile.path);
|
||||||
|
await videoOriginalFile.delete();
|
||||||
|
} else {
|
||||||
|
await mediaInfo.file!.copy(videoCompressedFile.path);
|
||||||
|
await mediaInfo.file!.delete();
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
/// --- helper functions ---
|
/// --- helper functions ---
|
||||||
|
|
||||||
Future<Uint8List> readMediaFile(MediaUpload media, String type) async {
|
Future<Uint8List> readMediaFile(int mediaUploadId, String type) async {
|
||||||
String basePath = await getMediaFilePath(media.mediaUploadId, "send");
|
String basePath = await getMediaFilePath(mediaUploadId, "send");
|
||||||
File file = File("$basePath.$type");
|
File file = File("$basePath.$type");
|
||||||
if (!await file.exists()) {
|
if (!await file.exists()) {
|
||||||
throw Exception("$file not found");
|
throw Exception("$file not found");
|
||||||
|
|
@ -562,3 +609,11 @@ Future<void> purgeSendMediaFiles() async {
|
||||||
final directory = Directory(join(basedir.path, 'media', "send"));
|
final directory = Directory(join(basedir.path, 'media', "send"));
|
||||||
await purgeMediaFiles(directory);
|
await purgeMediaFiles(directory);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
String uint8ListToHex(List<int> bytes) {
|
||||||
|
return bytes.map((byte) => byte.toRadixString(16).padLeft(2, '0')).join();
|
||||||
|
}
|
||||||
|
|
||||||
|
Uint8List hexToUint8List(String hex) => Uint8List.fromList(List<int>.generate(
|
||||||
|
hex.length ~/ 2,
|
||||||
|
(i) => int.parse(hex.substring(i * 2, i * 2 + 2), radix: 16)));
|
||||||
|
|
|
||||||
|
|
@ -362,6 +362,16 @@ class ApiProvider {
|
||||||
return await sendRequestSync(req);
|
return await sendRequestSync(req);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Future<Result> getDownloadTokens(
|
||||||
|
List<int> uploadToken, int recipientsCount) async {
|
||||||
|
var get = ApplicationData_UploadDone()
|
||||||
|
..uploadToken = uploadToken
|
||||||
|
..recipientsCount = recipientsCount;
|
||||||
|
var appData = ApplicationData()..uploaddone = get;
|
||||||
|
var req = createClientToServerFromApplicationData(appData);
|
||||||
|
return await sendRequestSync(req);
|
||||||
|
}
|
||||||
|
|
||||||
Future<Result> getCurrentLocation() async {
|
Future<Result> getCurrentLocation() async {
|
||||||
var get = ApplicationData_GetLocation();
|
var get = ApplicationData_GetLocation();
|
||||||
var appData = ApplicationData()..getlocation = get;
|
var appData = ApplicationData()..getlocation = get;
|
||||||
|
|
|
||||||
|
|
@ -267,7 +267,7 @@ class _CameraPreviewViewState extends State<CameraPreviewView> {
|
||||||
if (shoudReturn != null && shoudReturn) {
|
if (shoudReturn != null && shoudReturn) {
|
||||||
// ignore: use_build_context_synchronously
|
// ignore: use_build_context_synchronously
|
||||||
if (widget.sendTo == null) {
|
if (widget.sendTo == null) {
|
||||||
globalUpdateOfHomeViewPageIndex(1);
|
globalUpdateOfHomeViewPageIndex(0);
|
||||||
} else {
|
} else {
|
||||||
Navigator.pop(context);
|
Navigator.pop(context);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -52,23 +52,26 @@ class ShareImageEditorView extends StatefulWidget {
|
||||||
|
|
||||||
class _ShareImageEditorView extends State<ShareImageEditorView> {
|
class _ShareImageEditorView extends State<ShareImageEditorView> {
|
||||||
bool _isRealTwonly = false;
|
bool _isRealTwonly = false;
|
||||||
bool videoWithAudio = true;
|
|
||||||
int maxShowTime = gMediaShowInfinite;
|
int maxShowTime = gMediaShowInfinite;
|
||||||
String? sendNextMediaToUserName;
|
String? sendNextMediaToUserName;
|
||||||
double tabDownPostion = 0;
|
double tabDownPosition = 0;
|
||||||
bool sendingOrLoadingImage = true;
|
bool sendingOrLoadingImage = true;
|
||||||
bool isDisposed = false;
|
bool isDisposed = false;
|
||||||
HashSet<int> selectedUserIds = HashSet();
|
HashSet<int> selectedUserIds = HashSet();
|
||||||
double widthRatio = 1, heightRatio = 1, pixelRatio = 1;
|
double widthRatio = 1, heightRatio = 1, pixelRatio = 1;
|
||||||
VideoPlayerController? videoController;
|
VideoPlayerController? videoController;
|
||||||
|
|
||||||
ImageItem currentImage = ImageItem();
|
ImageItem currentImage = ImageItem();
|
||||||
ScreenshotController screenshotController = ScreenshotController();
|
ScreenshotController screenshotController = ScreenshotController();
|
||||||
|
|
||||||
|
/// Media upload variables
|
||||||
|
int? mediaUploadId;
|
||||||
|
Future<bool>? videoUploadHandler;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void initState() {
|
void initState() {
|
||||||
super.initState();
|
super.initState();
|
||||||
initAsync();
|
initAsync();
|
||||||
|
initMediaFileUpload();
|
||||||
if (widget.imageBytes != null) {
|
if (widget.imageBytes != null) {
|
||||||
loadImage(widget.imageBytes!);
|
loadImage(widget.imageBytes!);
|
||||||
} else if (widget.videoFilePath != null) {
|
} else if (widget.videoFilePath != null) {
|
||||||
|
|
@ -97,6 +100,19 @@ class _ShareImageEditorView extends State<ShareImageEditorView> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Future initMediaFileUpload() async {
|
||||||
|
// media init was already called...
|
||||||
|
if (mediaUploadId != null) return;
|
||||||
|
|
||||||
|
mediaUploadId = await initMediaUpload();
|
||||||
|
|
||||||
|
if (widget.videoFilePath != null && mediaUploadId != null) {
|
||||||
|
// start with the video compression...
|
||||||
|
videoUploadHandler =
|
||||||
|
addVideoToUpload(mediaUploadId!, widget.videoFilePath!);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void dispose() {
|
void dispose() {
|
||||||
isDisposed = true;
|
isDisposed = true;
|
||||||
|
|
@ -221,19 +237,6 @@ class _ShareImageEditorView extends State<ShareImageEditorView> {
|
||||||
},
|
},
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
// https://github.com/jonataslaw/VideoCompress/issues/184
|
|
||||||
// if (widget.videoFilePath != null) const SizedBox(height: 8),
|
|
||||||
// if (widget.videoFilePath != null)
|
|
||||||
// ActionButton(
|
|
||||||
// (videoWithAudio) ? Icons.volume_up_rounded : Icons.volume_off_rounded,
|
|
||||||
// tooltipText: context.lang.protectAsARealTwonly,
|
|
||||||
// color: Colors.white,
|
|
||||||
// onPressed: () async {
|
|
||||||
// setState(() {
|
|
||||||
// videoWithAudio = !videoWithAudio;
|
|
||||||
// });
|
|
||||||
// },
|
|
||||||
// ),
|
|
||||||
const SizedBox(height: 8),
|
const SizedBox(height: 8),
|
||||||
ActionButton(
|
ActionButton(
|
||||||
FontAwesomeIcons.shieldHeart,
|
FontAwesomeIcons.shieldHeart,
|
||||||
|
|
@ -312,8 +315,13 @@ class _ShareImageEditorView extends State<ShareImageEditorView> {
|
||||||
}
|
}
|
||||||
|
|
||||||
Future pushShareImageView() async {
|
Future pushShareImageView() async {
|
||||||
|
if (mediaUploadId == null) {
|
||||||
|
await initMediaFileUpload();
|
||||||
|
if (mediaUploadId == null) return;
|
||||||
|
}
|
||||||
Future<Uint8List?> imageBytes = getMergedImage();
|
Future<Uint8List?> imageBytes = getMergedImage();
|
||||||
videoController?.pause();
|
videoController?.pause();
|
||||||
|
if (isDisposed || !context.mounted) return;
|
||||||
bool? wasSend = await Navigator.push(
|
bool? wasSend = await Navigator.push(
|
||||||
context,
|
context,
|
||||||
MaterialPageRoute(
|
MaterialPageRoute(
|
||||||
|
|
@ -323,7 +331,8 @@ class _ShareImageEditorView extends State<ShareImageEditorView> {
|
||||||
maxShowTime: maxShowTime,
|
maxShowTime: maxShowTime,
|
||||||
selectedUserIds: selectedUserIds,
|
selectedUserIds: selectedUserIds,
|
||||||
updateStatus: updateStatus,
|
updateStatus: updateStatus,
|
||||||
videoFilePath: widget.videoFilePath,
|
videoUploadHandler: videoUploadHandler,
|
||||||
|
mediaUploadId: mediaUploadId!,
|
||||||
mirrorVideo: widget.mirrorVideo,
|
mirrorVideo: widget.mirrorVideo,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
|
@ -402,14 +411,26 @@ class _ShareImageEditorView extends State<ShareImageEditorView> {
|
||||||
);
|
);
|
||||||
}));
|
}));
|
||||||
} else {
|
} else {
|
||||||
sendMediaFile(
|
Future imageHandler =
|
||||||
|
addOrModifyImageToUpload(mediaUploadId!, imageBytes);
|
||||||
|
|
||||||
|
// first finalize the upload
|
||||||
|
await finalizeUpload(
|
||||||
|
mediaUploadId!,
|
||||||
[widget.sendTo!.userId],
|
[widget.sendTo!.userId],
|
||||||
imageBytes,
|
|
||||||
_isRealTwonly,
|
_isRealTwonly,
|
||||||
maxShowTime,
|
widget.videoFilePath != null,
|
||||||
widget.videoFilePath,
|
|
||||||
widget.mirrorVideo,
|
widget.mirrorVideo,
|
||||||
|
maxShowTime,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
/// then call the upload process in the background
|
||||||
|
encryptAndPreUploadMediaFiles(
|
||||||
|
mediaUploadId!,
|
||||||
|
imageHandler,
|
||||||
|
videoUploadHandler,
|
||||||
|
);
|
||||||
|
|
||||||
if (context.mounted) {
|
if (context.mounted) {
|
||||||
// ignore: use_build_context_synchronously
|
// ignore: use_build_context_synchronously
|
||||||
Navigator.pop(context, true);
|
Navigator.pop(context, true);
|
||||||
|
|
@ -434,9 +455,9 @@ class _ShareImageEditorView extends State<ShareImageEditorView> {
|
||||||
GestureDetector(
|
GestureDetector(
|
||||||
onTapDown: (details) {
|
onTapDown: (details) {
|
||||||
if (details.globalPosition.dy > 60) {
|
if (details.globalPosition.dy > 60) {
|
||||||
tabDownPostion = details.globalPosition.dy - 60;
|
tabDownPosition = details.globalPosition.dy - 60;
|
||||||
} else {
|
} else {
|
||||||
tabDownPostion = details.globalPosition.dy;
|
tabDownPosition = details.globalPosition.dy;
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
onTap: () {
|
onTap: () {
|
||||||
|
|
@ -446,7 +467,7 @@ class _ShareImageEditorView extends State<ShareImageEditorView> {
|
||||||
undoLayers.clear();
|
undoLayers.clear();
|
||||||
removedLayers.clear();
|
removedLayers.clear();
|
||||||
layers.add(TextLayerData(
|
layers.add(TextLayerData(
|
||||||
offset: Offset(0, tabDownPostion),
|
offset: Offset(0, tabDownPosition),
|
||||||
textLayersBefore: layers.whereType<TextLayerData>().length,
|
textLayersBefore: layers.whereType<TextLayerData>().length,
|
||||||
));
|
));
|
||||||
setState(() {});
|
setState(() {});
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,5 @@
|
||||||
import 'dart:async';
|
import 'dart:async';
|
||||||
import 'dart:collection';
|
import 'dart:collection';
|
||||||
import 'dart:io';
|
|
||||||
import 'dart:typed_data';
|
import 'dart:typed_data';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:font_awesome_flutter/font_awesome_flutter.dart';
|
import 'package:font_awesome_flutter/font_awesome_flutter.dart';
|
||||||
|
|
@ -26,16 +25,18 @@ class ShareImageView extends StatefulWidget {
|
||||||
required this.maxShowTime,
|
required this.maxShowTime,
|
||||||
required this.selectedUserIds,
|
required this.selectedUserIds,
|
||||||
required this.updateStatus,
|
required this.updateStatus,
|
||||||
required this.videoFilePath,
|
required this.videoUploadHandler,
|
||||||
|
required this.mediaUploadId,
|
||||||
this.enableVideoAudio});
|
this.enableVideoAudio});
|
||||||
final Future<Uint8List?> imageBytesFuture;
|
final Future<Uint8List?> imageBytesFuture;
|
||||||
final bool isRealTwonly;
|
final bool isRealTwonly;
|
||||||
final bool mirrorVideo;
|
final bool mirrorVideo;
|
||||||
final int maxShowTime;
|
final int maxShowTime;
|
||||||
final File? videoFilePath;
|
|
||||||
final HashSet<int> selectedUserIds;
|
final HashSet<int> selectedUserIds;
|
||||||
final bool? enableVideoAudio;
|
final bool? enableVideoAudio;
|
||||||
|
final int mediaUploadId;
|
||||||
final Function(int, bool) updateStatus;
|
final Function(int, bool) updateStatus;
|
||||||
|
final Future<bool>? videoUploadHandler;
|
||||||
|
|
||||||
@override
|
@override
|
||||||
State<ShareImageView> createState() => _ShareImageView();
|
State<ShareImageView> createState() => _ShareImageView();
|
||||||
|
|
@ -73,6 +74,13 @@ class _ShareImageView extends State<ShareImageView> {
|
||||||
|
|
||||||
Future initAsync() async {
|
Future initAsync() async {
|
||||||
imageBytes = await widget.imageBytesFuture;
|
imageBytes = await widget.imageBytesFuture;
|
||||||
|
if (imageBytes != null) {
|
||||||
|
final imageHandler =
|
||||||
|
addOrModifyImageToUpload(widget.mediaUploadId, imageBytes!);
|
||||||
|
// start with the pre upload of the media file...
|
||||||
|
encryptAndPreUploadMediaFiles(
|
||||||
|
widget.mediaUploadId, imageHandler, widget.videoUploadHandler);
|
||||||
|
}
|
||||||
setState(() {});
|
setState(() {});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -287,14 +295,18 @@ class _ShareImageView extends State<ShareImageView> {
|
||||||
sendingImage = true;
|
sendingImage = true;
|
||||||
});
|
});
|
||||||
|
|
||||||
sendMediaFile(
|
await finalizeUpload(
|
||||||
|
widget.mediaUploadId,
|
||||||
widget.selectedUserIds.toList(),
|
widget.selectedUserIds.toList(),
|
||||||
imageBytes!,
|
|
||||||
widget.isRealTwonly,
|
widget.isRealTwonly,
|
||||||
widget.maxShowTime,
|
widget.videoUploadHandler != null,
|
||||||
widget.videoFilePath,
|
|
||||||
widget.mirrorVideo,
|
widget.mirrorVideo,
|
||||||
|
widget.maxShowTime,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
/// trigger the upload of the media file.
|
||||||
|
handleNextMediaUploadSteps(widget.mediaUploadId);
|
||||||
|
|
||||||
if (context.mounted) {
|
if (context.mounted) {
|
||||||
Navigator.pop(context, true);
|
Navigator.pop(context, true);
|
||||||
// if (widget.preselectedUser != null) {
|
// if (widget.preselectedUser != null) {
|
||||||
|
|
|
||||||
|
|
@ -39,7 +39,7 @@ class HomeViewState extends State<HomeView> {
|
||||||
|
|
||||||
selectNotificationStream.stream
|
selectNotificationStream.stream
|
||||||
.listen((NotificationResponse? response) async {
|
.listen((NotificationResponse? response) async {
|
||||||
globalUpdateOfHomeViewPageIndex(1);
|
globalUpdateOfHomeViewPageIndex(0);
|
||||||
});
|
});
|
||||||
initAsync();
|
initAsync();
|
||||||
}
|
}
|
||||||
|
|
@ -50,7 +50,7 @@ class HomeViewState extends State<HomeView> {
|
||||||
|
|
||||||
if (notificationAppLaunchDetails != null) {
|
if (notificationAppLaunchDetails != null) {
|
||||||
if (notificationAppLaunchDetails.didNotificationLaunchApp) {
|
if (notificationAppLaunchDetails.didNotificationLaunchApp) {
|
||||||
globalUpdateOfHomeViewPageIndex(1);
|
globalUpdateOfHomeViewPageIndex(0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -11,6 +11,7 @@ import 'schema_v5.dart' as v5;
|
||||||
import 'schema_v6.dart' as v6;
|
import 'schema_v6.dart' as v6;
|
||||||
import 'schema_v7.dart' as v7;
|
import 'schema_v7.dart' as v7;
|
||||||
import 'schema_v8.dart' as v8;
|
import 'schema_v8.dart' as v8;
|
||||||
|
import 'schema_v9.dart' as v9;
|
||||||
|
|
||||||
class GeneratedHelper implements SchemaInstantiationHelper {
|
class GeneratedHelper implements SchemaInstantiationHelper {
|
||||||
@override
|
@override
|
||||||
|
|
@ -32,10 +33,12 @@ class GeneratedHelper implements SchemaInstantiationHelper {
|
||||||
return v7.DatabaseAtV7(db);
|
return v7.DatabaseAtV7(db);
|
||||||
case 8:
|
case 8:
|
||||||
return v8.DatabaseAtV8(db);
|
return v8.DatabaseAtV8(db);
|
||||||
|
case 9:
|
||||||
|
return v9.DatabaseAtV9(db);
|
||||||
default:
|
default:
|
||||||
throw MissingSchemaException(version, versions);
|
throw MissingSchemaException(version, versions);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static const versions = const [1, 2, 3, 4, 5, 6, 7, 8];
|
static const versions = const [1, 2, 3, 4, 5, 6, 7, 8, 9];
|
||||||
}
|
}
|
||||||
|
|
|
||||||
2963
test/drift/twonly_database/generated/schema_v9.dart
Normal file
2963
test/drift/twonly_database/generated/schema_v9.dart
Normal file
File diff suppressed because it is too large
Load diff
Loading…
Reference in a new issue