1
0
mirror of https://gitlab.com/comunic/comunicmobile synced 2025-06-19 08:15:16 +00:00

Start to fix null safety migration errors

This commit is contained in:
2022-03-10 19:39:57 +01:00
parent ab2c5da0da
commit 3a997cdc56
258 changed files with 2879 additions and 2912 deletions

View File

@ -26,14 +26,14 @@ enum CreateAccountResult {
class AccountHelper {
// Current user ID
static int _currentUserID = -1;
static int? _currentUserID = -1;
/// Checkout whether current user is signed in or not
///
/// Warning : This method MUST BE CALLED AT LEAST ONCE AFTER APP START !!!
Future<bool> signedIn() async {
bool signedIn =
(await PreferencesHelper.getInstance()).getLoginToken() != null;
(await PreferencesHelper.getInstance())!.getLoginToken() != null;
// Load current user ID for later use
if (signedIn && _currentUserID == -1) await _loadCurrentUserID();
@ -56,8 +56,8 @@ class AccountHelper {
else if (response.code != 200) return AuthResult.NETWORK_ERROR;
// Save login token
await (await PreferencesHelper.getInstance())
.setLoginToken(response.getObject()["token"]);
await (await PreferencesHelper.getInstance())!
.setLoginToken(response.getObject()!["token"]);
// Get current user ID
final userID = await _downloadCurrentUserID();
@ -67,7 +67,7 @@ class AccountHelper {
}
// Save current user ID
final preferences = await PreferencesHelper.getInstance();
final preferences = await (PreferencesHelper.getInstance());
await preferences.setInt(PreferencesKeyList.USER_ID, userID);
_currentUserID = userID;
@ -130,27 +130,27 @@ class AccountHelper {
.getObject()["exists"];
/// Get current user email address
static Future<String> getCurrentAccountEmailAddress() async =>
static Future<String?> getCurrentAccountEmailAddress() async =>
(await APIRequest.withLogin("account/mail")
.execWithThrowGetObject())["mail"];
.execWithThrowGetObject())!["mail"];
/// Check out whether security questions have been set for an account or not
///
/// Throws in case of failure
static Future<bool> hasSecurityQuestions(String email) async =>
static Future<bool?> hasSecurityQuestions(String email) async =>
(await APIRequest.withoutLogin("account/has_security_questions")
.addString("email", email)
.execWithThrow())
.getObject()["defined"];
.getObject()!["defined"];
/// Get the security questions of the user
///
/// Throws in case of failure
static Future<List<String>> getSecurityQuestions(String email) async =>
static Future<List<String>?> getSecurityQuestions(String? email) async =>
((await APIRequest.withoutLogin("account/get_security_questions")
.addString("email", email)
.execWithThrow())
.getObject()["questions"])
.getObject()!["questions"])
.cast<String>();
/// Validate given security answers
@ -158,14 +158,14 @@ class AccountHelper {
/// Throws an [Exception] in case of failure
///
/// Returns a password reset token in case of success
static Future<String> checkAnswers(
String email, List<String> answers) async =>
static Future<String?> checkAnswers(
String? email, List<String> answers) async =>
(await APIRequest.withoutLogin("account/check_security_answers")
.addString("email", email)
.addString("answers",
answers.map((f) => Uri.encodeComponent(f)).join("&"))
.execWithThrow())
.getObject()["reset_token"];
.getObject()!["reset_token"];
/// Check a password reset token
///
@ -195,25 +195,26 @@ class AccountHelper {
.execWithThrow();
/// Get current user ID from the server
Future<int> _downloadCurrentUserID() async {
Future<int?> _downloadCurrentUserID() async {
final response = await APIRequest.withLogin("account/id").exec();
if (response.code != 200) return null;
return response.getObject()["userID"];
return response.getObject()!["userID"];
}
/// Get the ID of the currently signed in user
Future<void> _loadCurrentUserID() async {
final preferences = await PreferencesHelper.getInstance();
final preferences =
await PreferencesHelper.getInstance();
_currentUserID = preferences.getInt(PreferencesKeyList.USER_ID);
}
/// Check if current user ID is loaded or not
static bool get isUserIDLoaded => _currentUserID > 0;
static bool get isUserIDLoaded => _currentUserID! > 0;
/// Get the ID of the currently signed in user
static int getCurrentUserID() {
static int? getCurrentUserID() {
if (_currentUserID == -1) throw "Current user ID has not been loaded yet!";
return _currentUserID;
}

View File

@ -23,7 +23,7 @@ class APIHelper {
//Add user token (if required)
if (request.needLogin) {
final token = (await PreferencesHelper.getInstance()).getLoginToken();
final token = (await PreferencesHelper.getInstance())!.getLoginToken();
if (token == null) {
EventsHelper.emit(InvalidLoginTokensEvent());
@ -41,13 +41,13 @@ class APIHelper {
else
url = Uri.https(config().apiServerName, path);
final data = FormData.fromMap(request.args);
final data = FormData.fromMap(request.args!);
// Process files (if required)
if (multipart) {
// Process filesystem files
for (final key in request.files.keys) {
var v = request.files[key];
var v = request.files[key]!;
data.files.add(MapEntry(
key,
await MultipartFile.fromFile(v.path,
@ -56,11 +56,11 @@ class APIHelper {
// Process in-memory files
for (final key in request.bytesFiles.keys) {
var v = request.bytesFiles[key];
var v = request.bytesFiles[key]!;
data.files.add(MapEntry(
key,
MultipartFile.fromBytes(
v.bytes,
v.bytes!,
filename: v.filename.split("/").last,
contentType: v.type,
)));
@ -85,9 +85,9 @@ class APIHelper {
EventsHelper.emit(InvalidLoginTokensEvent());
if (response.statusCode != HttpStatus.ok)
return APIResponse(response.statusCode, response.data);
return APIResponse(response.statusCode!, response.data);
return APIResponse(response.statusCode, response.data);
return APIResponse(response.statusCode!, response.data);
} catch (e, stack) {
print(e.toString());
print("Could not execute a request!");

View File

@ -39,12 +39,12 @@ class CallsHelper {
.cast<CallMember>());
/// Request an offer to access another peer's stream
static Future<void> requestOffer(int callID, int peerID) async =>
static Future<void> requestOffer(int callID, int? peerID) async =>
await ws("calls/request_offer", {"callID": callID, "peerID": peerID});
/// Send a Session Description message to the server
static Future<void> sendSessionDescription(
int callID, int peerID, RTCSessionDescription sdp) async =>
int callID, int? peerID, RTCSessionDescription sdp) async =>
await ws("calls/signal", {
"callID": callID,
"peerID": peerID,
@ -54,7 +54,7 @@ class CallsHelper {
/// Send an IceCandidate
static Future<void> sendIceCandidate(
int callID, int peerID, RTCIceCandidate candidate) async =>
int callID, int? peerID, RTCIceCandidate candidate) async =>
await ws("calls/signal", {
"callID": callID,
"peerID": peerID,

View File

@ -27,7 +27,7 @@ class CommentsHelper {
}
/// Get a single comment from the server, specified by its [id]
Future<Comment> getSingle(int id) async {
Future<Comment?> getSingle(int id) async {
final response = await APIRequest(
uri: "comments/get_single",
needLogin: true,
@ -39,7 +39,7 @@ class CommentsHelper {
}
/// Update comment content
Future<bool> updateContent(int id, String newContent) async {
Future<bool> updateContent(int id, String? newContent) async {
return (await APIRequest(uri: "comments/edit", needLogin: true, args: {
"commentID": id.toString(),
"content": newContent,

View File

@ -21,7 +21,6 @@ import 'package:comunic/utils/account_utils.dart';
import 'package:comunic/utils/color_utils.dart';
import 'package:comunic/utils/dart_color.dart';
import 'package:dio/dio.dart';
import 'package:meta/meta.dart';
/// Conversation helper
///
@ -47,13 +46,13 @@ class ConversationsHelper {
.addBool("canEveryoneAddMembers", settings.canEveryoneAddMembers)
.execWithThrow();
return response.getObject()["conversationID"];
return response.getObject()!["conversationID"];
}
/// Add a member to a conversation.
///
/// Throws in case of failure
static Future<void> addMember(int convID, int userID) async =>
static Future<void> addMember(int? convID, int? userID) async =>
await APIRequest.withLogin("conversations/addMember")
.addInt("convID", convID)
.addInt("userID", userID)
@ -62,7 +61,7 @@ class ConversationsHelper {
/// Remove a member from a conversation.
///
/// Throws in case of failure
static Future<void> removeMember(int convID, int userID) async =>
static Future<void> removeMember(int? convID, int? userID) async =>
await APIRequest.withLogin("conversations/removeMember")
.addInt("convID", convID)
.addInt("userID", userID)
@ -71,7 +70,7 @@ class ConversationsHelper {
/// Update admin status of a user in a conversation
///
/// Throws in case of failure
static Future<void> setAdmin(int/*!*/ convID, int/*!*/ userID, bool admin) async =>
static Future<void> setAdmin(int convID, int userID, bool admin) async =>
await APIRequest.withLogin("conversations/setAdmin")
.addInt("convID", convID)
.addInt("userID", userID)
@ -91,7 +90,7 @@ class ConversationsHelper {
if (settings.isComplete)
request
.addString("name", settings.name ?? "")
.addBool("canEveryoneAddMembers", settings.canEveryoneAddMembers)
.addBool("canEveryoneAddMembers", settings.canEveryoneAddMembers!)
.addString("color", colorToHex(settings.color));
await request.execWithThrow();
@ -104,7 +103,7 @@ class ConversationsHelper {
/// Set a new conversation logo
///
/// Throws in case of failure
static Future<void> changeImage(int convID, BytesFile file) async =>
static Future<void> changeImage(int? convID, BytesFile file) async =>
await APIRequest.withLogin("conversations/change_image")
.addInt("convID", convID)
.addBytesFile("file", file)
@ -113,13 +112,13 @@ class ConversationsHelper {
/// Remove conversation logo
///
/// Throws in case of failure
static Future<void> removeLogo(int convID) async =>
static Future<void> removeLogo(int? convID) async =>
await APIRequest.withLogin("conversations/delete_image")
.addInt("convID", convID)
.execWithThrow();
/// Delete a conversation specified by its [id]
Future<void> deleteConversation(int id) async =>
Future<void> deleteConversation(int? id) async =>
await APIRequest.withLogin("conversations/delete")
.addInt("conversationID", id)
.execWithThrow();
@ -132,7 +131,7 @@ class ConversationsHelper {
await APIRequest.withLogin("conversations/getList").execWithThrow();
ConversationsList list = ConversationsList();
response.getArray().forEach((f) => list.add(apiToConversation(f)));
response.getArray()!.forEach((f) => list.add(apiToConversation(f)));
// Update the database
await ConversationsSerializationHelper().setList(list);
@ -148,13 +147,13 @@ class ConversationsHelper {
}
/// Get information about a single conversation specified by its [id]
Future<Conversation> _downloadSingle(int id) async {
Future<Conversation> _downloadSingle(int? id) async {
final response = await APIRequest(
uri: "conversations/get_single",
needLogin: true,
args: {"conversationID": id.toString()}).execWithThrow();
final conversation = apiToConversation(response.getObject());
final conversation = apiToConversation(response.getObject()!);
await ConversationsSerializationHelper()
.insertOrReplaceElement((c) => c.id == conversation.id, conversation);
@ -167,7 +166,7 @@ class ConversationsHelper {
/// case of failure
///
/// Return value of this method is never null.
Future<Conversation> getSingle(int id, {bool force = false}) async {
Future<Conversation> getSingle(int? id, {bool force = false}) async {
if (force ||
!await ConversationsSerializationHelper().any((c) => c.id == id))
return await _downloadSingle(id);
@ -178,19 +177,19 @@ class ConversationsHelper {
/// Get the name of a [conversation]. This requires information
/// about the users of this conversation
static String getConversationName(
Conversation conversation, UsersList users) {
if (conversation.hasName) return conversation.name;
Conversation conversation, UsersList? users) {
if (conversation.hasName) return conversation.name!;
String name = "";
int count = 0;
for (int i = 0; i < 3 && i < conversation.members.length; i++)
if (conversation.members[i].userID != userID()) {
for (int i = 0; i < 3 && i < conversation.members!.length; i++)
if (conversation.members![i].userID != userID()) {
name += (count > 0 ? ", " : "") +
users.getUser(conversation.members[i].userID).fullName;
users!.getUser(conversation.members![i].userID).fullName;
count++;
}
if (conversation.members.length > 3) name += ", ...";
if (conversation.members!.length > 3) name += ", ...";
return name;
}
@ -200,7 +199,7 @@ class ConversationsHelper {
/// true
///
/// Throws an exception in case of failure
Future<int> getPrivate(int userID, {bool allowCreate = true}) async {
Future<int> getPrivate(int? userID, {bool allowCreate = true}) async {
final response = await APIRequest(
uri: "conversations/getPrivate",
needLogin: true,
@ -211,7 +210,7 @@ class ConversationsHelper {
).execWithThrow();
// Get and return conversation ID
return int.parse(response.getObject()["conversationsID"][0].toString());
return int.parse(response.getObject()!["conversationsID"][0].toString());
}
/// Asynchronously get the name of the conversation
@ -222,7 +221,7 @@ class ConversationsHelper {
/// Throws an exception in case of failure
static Future<String> getConversationNameAsync(
Conversation conversation) async {
if (conversation.hasName) return conversation.name;
if (conversation.hasName) return conversation.name!;
//Get information about the members of the conversation
final members = await UsersHelper().getList(conversation.membersID);
@ -273,7 +272,7 @@ class ConversationsHelper {
// Parse the response of the server
ConversationMessagesList list = ConversationMessagesList();
response.getArray().forEach((f) {
response.getArray()!.forEach((f) {
list.add(
apiToConversationMessage(f),
);
@ -294,7 +293,7 @@ class ConversationsHelper {
/// Throws an exception in case of failure
Future<ConversationMessagesList> _downloadNewMessagesSingle(
int conversationID,
{int lastMessageID = 0}) async {
{int? lastMessageID = 0}) async {
// Execute the request on the server
final response = await APIRequest(
uri: "conversations/refresh_single",
@ -311,8 +310,8 @@ class ConversationsHelper {
///
/// Throws in case of failure
Future<ConversationMessagesList> getOlderMessages({
@required int conversationID,
@required int oldestMessagesID,
required int conversationID,
required int? oldestMessagesID,
int limit = 15,
}) async {
// Perform the request online
@ -334,8 +333,8 @@ class ConversationsHelper {
///
/// Throws in case of failure
Future<ConversationMessagesList> getNewMessages(
{@required int conversationID,
int lastMessageID = 0,
{required int conversationID,
int? lastMessageID = 0,
bool online = true}) async {
if (online)
return await _downloadNewMessagesSingle(conversationID,
@ -348,8 +347,8 @@ class ConversationsHelper {
/// Send a new message to the server
Future<SendMessageResult> sendMessage(
NewConversationMessage message, {
ProgressCallback sendProgress,
CancelToken cancelToken,
ProgressCallback? sendProgress,
CancelToken? cancelToken,
}) async {
final request = APIRequest.withLogin("conversations/sendMessage")
.addInt("conversationID", message.conversationID)
@ -388,7 +387,7 @@ class ConversationsHelper {
await ConversationsMessagesSerializationHelper(msg.convID).remove(msg);
/// Update a message content
Future<bool> updateMessage(int id, String newContent) async {
Future<bool> updateMessage(int? id, String newContent) async {
final response = await APIRequest(
uri: "conversations/updateMessage",
needLogin: true,
@ -400,7 +399,7 @@ class ConversationsHelper {
}
/// Delete permanently a message specified by its [id]
Future<bool> deleteMessage(int id) async {
Future<bool> deleteMessage(int? id) async {
// Delete the message online
final response = await APIRequest(
uri: "conversations/deleteMessage",
@ -418,7 +417,7 @@ class ConversationsHelper {
static Future<UnreadConversationsList> getListUnread() async {
final list = (await APIRequest.withLogin("conversations/get_list_unread")
.execWithThrow())
.getArray();
.getArray()!;
return UnreadConversationsList()
..addAll(list.map((f) => UnreadConversation(
@ -431,7 +430,7 @@ class ConversationsHelper {
/// conversation through WebSocket
Future<void> registerConversationEvents(int id) async {
if (_registeredConversations.containsKey(id))
_registeredConversations[id]++;
_registeredConversations.update(id, (value) => value + 1);
else {
_registeredConversations[id] = 1;
await ws("\$main/register_conv", {"convID": id});
@ -442,16 +441,16 @@ class ConversationsHelper {
Future<void> unregisterConversationEvents(int id) async {
if (!_registeredConversations.containsKey(id)) return;
_registeredConversations[id]--;
_registeredConversations.update(id, (value) => value - 1);
if (_registeredConversations[id] <= 0) {
if (_registeredConversations[id]! <= 0) {
_registeredConversations.remove(id);
await ws("\$main/unregister_conv", {"convID": id});
}
}
/// Send a notification to inform that the user is writing a message
static Future<void> sendWritingEvent(int convID) async =>
static Future<void> sendWritingEvent(int? convID) async =>
await ws("conversations/is_writing", {"convID": convID});
/// Turn an API response into a ConversationMessage object

View File

@ -9,11 +9,11 @@ import 'package:sqflite/sqflite.dart';
/// @author Pierre HUBERT
abstract class DatabaseHelper {
static Database _db;
static Database? _db;
/// Open the database
static Future<void> open() async {
if (_db != null && _db.isOpen) return;
if (_db != null && _db!.isOpen) return;
var databasePath = await getDatabasesPath();
_db = await openDatabase(
@ -24,7 +24,7 @@ abstract class DatabaseHelper {
}
/// Get a database instance
static Future<Database> get() async {
static Future<Database?> get() async {
await open();
return _db;
}

View File

@ -18,12 +18,12 @@ abstract class ModelDatabaseHelper<T extends CacheModel> {
/// Insert an entry in the database
Future<void> _insertDB(T el) async {
await (await DatabaseHelper.get()).insert(tableName(), el.toMap());
await (await DatabaseHelper.get())!.insert(tableName(), el.toMap());
}
/// Update an element in the database
Future<void> _updateDB(T el) async {
await (await DatabaseHelper.get()).update(
await (await DatabaseHelper.get())!.update(
tableName(),
el.toMap(),
where: "${BaseTableContract.C_ID} = ?",
@ -34,14 +34,14 @@ abstract class ModelDatabaseHelper<T extends CacheModel> {
/// Get an element from the database with a specified [id]
///
/// Returns null if none found
Future<T> get(int id) async {
List<Map> maps = await (await DatabaseHelper.get()).query(
Future<T?> get(int id) async {
List<Map> maps = await (await DatabaseHelper.get())!.query(
tableName(),
where: '${BaseTableContract.C_ID} = ?',
whereArgs: [id],
);
if (maps.length > 0) return initializeFromMap(maps[0]);
if (maps.length > 0) return initializeFromMap(maps[0] as Map<String, dynamic>);
return null;
}
@ -50,7 +50,7 @@ abstract class ModelDatabaseHelper<T extends CacheModel> {
///
/// Return true if at least one entry was deleted / false else
Future<bool> delete(int id) async {
return await (await DatabaseHelper.get()).delete(
return await (await DatabaseHelper.get())!.delete(
tableName(),
where: '${BaseTableContract.C_ID} = ?',
whereArgs: [id],
@ -59,22 +59,22 @@ abstract class ModelDatabaseHelper<T extends CacheModel> {
/// Get all the entries from the table
Future<List<T>> getAll() async {
List<Map> maps = await (await DatabaseHelper.get()).query(tableName());
return maps.map((f) => initializeFromMap(f)).toList();
List<Map> maps = await (await DatabaseHelper.get())!.query(tableName());
return maps.map((f) => initializeFromMap(f as Map<String, dynamic>)).toList();
}
/// Get some entries from the table based on some conditions
Future<List<T>> getMultiple(
{bool distinct,
List<String> columns,
String where,
List<dynamic> whereArgs,
String groupBy,
String having,
String orderBy,
int limit,
int offset}) async {
List<Map> maps = await (await DatabaseHelper.get()).query(
{bool? distinct,
List<String>? columns,
String? where,
List<dynamic>? whereArgs,
String? groupBy,
String? having,
String? orderBy,
int? limit,
int? offset}) async {
List<Map> maps = await (await DatabaseHelper.get())!.query(
tableName(),
distinct: distinct,
columns: columns,
@ -86,12 +86,12 @@ abstract class ModelDatabaseHelper<T extends CacheModel> {
limit: limit,
offset: offset,
);
return maps.map((f) => initializeFromMap(f)).toList();
return maps.map((f) => initializeFromMap(f as Map<String, dynamic>)).toList();
}
/// Empty the table
Future<void> clearTable() async {
await (await DatabaseHelper.get()).execute("DELETE FROM ${tableName()}");
await (await DatabaseHelper.get())!.execute("DELETE FROM ${tableName()}");
}
/// Check out whether an element specified with its [id] is present

View File

@ -17,14 +17,14 @@ class WSClosedEvent {}
/// New number of notifications
class NewNumberNotifsEvent {
final int newNum;
final int? newNum;
NewNumberNotifsEvent(this.newNum);
}
/// New number of unread conversations
class NewNumberUnreadConversations {
final int newNum;
final int? newNum;
NewNumberUnreadConversations(this.newNum);
}
@ -45,15 +45,15 @@ class UpdatedCommentEvent {
/// Deleted comment
class DeletedCommentEvent {
final int commentID;
final int? commentID;
DeletedCommentEvent(this.commentID);
}
/// Writing message in conversation event
class WritingMessageInConversationEvent {
final int convID;
final int userID;
final int? convID;
final int? userID;
WritingMessageInConversationEvent(this.convID, this.userID);
}
@ -81,31 +81,31 @@ class DeletedConversationMessageEvent {
/// Remove user from conversation
class RemovedUserFromConversationEvent {
final int convID;
final int userID;
final int? convID;
final int? userID;
RemovedUserFromConversationEvent(this.convID, this.userID);
}
/// Deleted conversation
class DeletedConversationEvent {
final int convID;
final int? convID;
DeletedConversationEvent(this.convID);
}
/// User joined call event
class UserJoinedCallEvent {
final int callID;
final int userID;
final int? callID;
final int? userID;
UserJoinedCallEvent(this.callID, this.userID);
}
/// User left call event
class UserLeftCallEvent {
final int callID;
final int userID;
final int? callID;
final int? userID;
UserLeftCallEvent(this.callID, this.userID);
}
@ -114,12 +114,12 @@ class UserLeftCallEvent {
class NewCallSignalEvent {
final int callID;
final int peerID;
final RTCSessionDescription sessionDescription;
final RTCIceCandidate candidate;
final RTCSessionDescription? sessionDescription;
final RTCIceCandidate? candidate;
const NewCallSignalEvent({
this.callID,
this.peerID,
required this.callID,
required this.peerID,
this.sessionDescription,
this.candidate,
}) : assert(callID != null),
@ -129,23 +129,23 @@ class NewCallSignalEvent {
/// Call peer ready event
class CallPeerReadyEvent {
final int callID;
final int peerID;
final int? callID;
final int? peerID;
CallPeerReadyEvent(this.callID, this.peerID);
}
/// Call peer interrupted streaming event
class CallPeerInterruptedStreamingEvent {
final int callID;
final int peerID;
final int? callID;
final int? peerID;
CallPeerInterruptedStreamingEvent(this.callID, this.peerID);
}
/// Call closed event
class CallClosedEvent {
final int callID;
final int? callID;
CallClosedEvent(this.callID);
}

View File

@ -20,7 +20,7 @@ class FirebaseMessagingHelper {
}
/// Get a Firebase access token
static Future<String> getToken() async {
static Future<String?> getToken() async {
return await FirebaseMessaging.instance.getToken();
}
}

View File

@ -11,7 +11,7 @@ import 'package:comunic/models/group.dart';
class ForezGroupsHelper {
static Future<List<Group>> getForezGroups() async {
return (await APIRequest.withLogin("forez/get_groups").execWithThrow())
.getArray()
.getArray()!
.cast<Map<String, dynamic>>()
.map(GroupsHelper.getGroupFromAPI)
.toList();
@ -21,10 +21,10 @@ class ForezGroupsHelper {
///
/// This methods throws an exception in case of failure
static Future<AdvancedUserInfo> getMemberInfo(int groupID, int userID) async {
final response = await APIRequest.withLogin("forez/get_member_info")
final response = await (APIRequest.withLogin("forez/get_member_info")
.addInt("group", groupID)
.addInt("user", userID)
.execWithThrowGetObject();
.execWithThrowGetObject());
return UsersHelper.apiToAdvancedUserInfo(response);
}

View File

@ -6,8 +6,8 @@ import 'package:comunic/models/forez_presence.dart';
///
/// @author Pierre Hubert
int _cachedGroup;
PresenceSet _cache;
int? _cachedGroup;
PresenceSet? _cache;
class ForezPresenceHelper {
/// Refresh presence cache
@ -40,16 +40,16 @@ class ForezPresenceHelper {
/// Get the presences of a given user
///
/// Throws in case of failure
static Future<PresenceSet> getForUser(int groupID, int userID) async {
static Future<PresenceSet> getForUser(int groupID, int? userID) async {
await _checkCache(groupID);
return _cache.getForUser(userID);
return _cache!.getForUser(userID);
}
/// Get all the available presences
///
/// Throws in case of failure
static Future<PresenceSet> getAll(int groupID) async {
static Future<PresenceSet?> getAll(int groupID) async {
await _checkCache(groupID);
return _cache;
}

View File

@ -3,7 +3,6 @@ import 'package:comunic/lists/friends_list.dart';
import 'package:comunic/models/api_request.dart';
import 'package:comunic/models/friend.dart';
import 'package:comunic/models/friend_status.dart';
import 'package:meta/meta.dart';
/// Friends helper
///
@ -16,7 +15,7 @@ class FriendsHelper {
///
/// Returns the list of friends in case of success, or null if an error
/// occurred
Future<FriendsList> _downloadList() async {
Future<FriendsList?> _downloadList() async {
final response = await APIRequest(
uri: "friends/getList",
needLogin: true,
@ -30,7 +29,7 @@ class FriendsHelper {
// Parse and return the list of friends
FriendsList list = FriendsList()
..addAll(response
.getArray()
.getArray()!
.cast<Map<String, dynamic>>()
.map(apiToFriend)
.toList());
@ -54,7 +53,7 @@ class FriendsHelper {
}
/// Get the list, either from an online or an offline source
Future<FriendsList> getList({@required bool online}) async {
Future<FriendsList?> getList({required bool online}) async {
if (online)
return await _downloadList();
else
@ -108,7 +107,7 @@ class FriendsHelper {
if (response.code != 200)
throw Exception("Could not get friendship status!");
final obj = response.getObject();
final obj = response.getObject()!;
return FriendStatus(
userID: userID,
@ -132,7 +131,7 @@ class FriendsHelper {
if (response.code != 200)
throw new Exception("Could not get the list of friends of this user!");
return Set<int>.from(response.getArray());
return Set<int>.from(response.getArray()!);
}
/// Send a friendship request to a specified user

View File

@ -49,7 +49,7 @@ enum GetAdvancedInfoStatus { SUCCESS, ACCESS_DENIED }
class GetAdvancedInfoResult {
final GetAdvancedInfoStatus status;
final AdvancedGroupInfo info;
final AdvancedGroupInfo? info;
GetAdvancedInfoResult(this.status, this.info) : assert(status != null);
}
@ -57,7 +57,7 @@ class GetAdvancedInfoResult {
/// Groups helper
class GroupsHelper {
/// Download a list of groups information from the server
Future<GroupsList> _downloadList(Set<int> groups) async {
Future<GroupsList?> _downloadList(Set<int?> groups) async {
final response = await APIRequest(
uri: "groups/get_multiple_info",
needLogin: true,
@ -69,7 +69,7 @@ class GroupsHelper {
final list = GroupsList();
response
.getObject()
.getObject()!
.forEach((k, d) => list[int.parse(k)] = getGroupFromAPI(d));
return list;
@ -77,7 +77,7 @@ class GroupsHelper {
/// Get a list of groups from the server. In case of error, this method throws
/// an exception
Future<GroupsList> getListOrThrow(Set<int> groups,
Future<GroupsList> getListOrThrow(Set<int?> groups,
{bool force = false}) async {
final list = await getList(groups, force: force);
@ -87,11 +87,11 @@ class GroupsHelper {
}
/// Get a list of groups from the server
Future<GroupsList> getList(Set<int> groups, {bool force = false}) async {
Future<GroupsList?> getList(Set<int?> groups, {bool force = false}) async {
final list = GroupsList();
// Check which groups information to download
final toDownload = Set<int>();
final toDownload = Set<int?>();
groups.forEach((groupID) {
if (!force && _groupsListCache.containsKey(groupID))
list[groupID] = _groupsListCache[groupID];
@ -122,10 +122,10 @@ class GroupsHelper {
}
/// Get the list of groups of a user
Future<Set<int>> getListUser() async =>
Future<Set<int?>> getListUser() async =>
(await APIRequest(uri: "groups/get_my_list", needLogin: true).exec())
.assertOk()
.getArray()
.getArray()!
.map((f) => cast<int>(f))
.toSet();
@ -142,7 +142,7 @@ class GroupsHelper {
/// Perform a simple membership request
static Future<bool> _simpleMembershipRequest(int groupID, String uri,
{Map<String, String> args}) async =>
{Map<String, String>? args}) async =>
(await (APIRequest.withLogin(uri)
..addInt("id", groupID)
..addArgs(args == null ? Map() : args))
@ -176,7 +176,7 @@ class GroupsHelper {
.isOK;
/// Get advanced information about the user
Future<GetAdvancedInfoResult> getAdvancedInfo(int groupID) async {
Future<GetAdvancedInfoResult> getAdvancedInfo(int? groupID) async {
// Get advanced information about the user
final result =
await (APIRequest(uri: "groups/get_advanced_info", needLogin: true)
@ -189,7 +189,7 @@ class GroupsHelper {
case 200:
return GetAdvancedInfoResult(GetAdvancedInfoStatus.SUCCESS,
_getAdvancedGroupInfoFromAPI(result.getObject()));
_getAdvancedGroupInfoFromAPI(result.getObject()!));
default:
throw Exception("Could not get advanced group information!");
@ -202,7 +202,7 @@ class GroupsHelper {
/// change in the future
///
/// Throws in case of error
Future<AdvancedGroupInfo> getSettings(int groupID) async {
Future<AdvancedGroupInfo?> getSettings(int groupID) async {
final groupInfo = await getAdvancedInfo(groupID);
if (groupInfo.status != GetAdvancedInfoStatus.SUCCESS)
@ -239,7 +239,7 @@ class GroupsHelper {
"posts_level",
invertMap(
_APIGroupsPostsCreationLevelsMap)[settings.postCreationLevel])
.addBool("is_members_list_public", settings.isMembersListPublic)
.addBool("is_members_list_public", settings.isMembersListPublic!)
.addString("description", settings.description)
.addString("url", settings.url)
.execWithThrow();
@ -248,7 +248,7 @@ class GroupsHelper {
/// Upload a new logo
///
/// Throws in case of failure
static Future<void> uploadNewLogo(int groupID, Uint8List bytes) async =>
static Future<void> uploadNewLogo(int groupID, Uint8List? bytes) async =>
await APIRequest(uri: "groups/upload_logo", needLogin: true)
.addInt("id", groupID)
.addBytesFile("logo", BytesFile("logo.png", bytes))
@ -279,7 +279,7 @@ class GroupsHelper {
..addAll((await APIRequest(uri: "groups/get_members", needLogin: true)
.addInt("id", groupID)
.execWithThrow())
.getArray()
.getArray()!
.map((f) => _apiToGroupMembership(f))
.toList());
@ -295,7 +295,7 @@ class GroupsHelper {
/// Cancel a group membership invitation
///
/// Throws an exception in case of failure
static Future<void> cancelInvitation(int groupID, int userID) async =>
static Future<void> cancelInvitation(int groupID, int? userID) async =>
await APIRequest.withLogin("groups/cancel_invitation")
.addInt("groupID", groupID)
.addInt("userID", userID)
@ -305,7 +305,7 @@ class GroupsHelper {
///
/// Throws an exception in case of failure
static Future<void> respondRequest(
int groupID, int userID, bool accept) async =>
int groupID, int? userID, bool accept) async =>
await APIRequest.withLogin("groups/respond_request")
.addInt("groupID", groupID)
.addInt("userID", userID)
@ -351,7 +351,7 @@ class GroupsHelper {
///
/// Throws in case of failure
static Future<void> setConversationVisibility(
int convID, GroupMembershipLevel newLevel) async =>
int? convID, GroupMembershipLevel? newLevel) async =>
await APIRequest.withLogin("groups/set_conversation_visibility")
.addInt("conv_id", convID)
.addString(
@ -364,7 +364,7 @@ class GroupsHelper {
/// Delete a group's conversation
///
/// Throws in case of failure
static Future<void> deleteConversation(int convID) async =>
static Future<void> deleteConversation(int? convID) async =>
await APIRequest.withLogin("groups/delete_conversation")
.addInt("conv_id", convID)
.execWithThrow();
@ -376,11 +376,11 @@ class GroupsHelper {
name: map["name"],
iconURL: map["icon_url"],
numberMembers: map["number_members"],
membershipLevel: APIGroupsMembershipLevelsMap[map["membership"]],
visibilityLevel: _APIGroupsVisibilityLevelsMap[map["visibility"]],
membershipLevel: APIGroupsMembershipLevelsMap[map["membership"]]!,
visibilityLevel: _APIGroupsVisibilityLevelsMap[map["visibility"]]!,
registrationLevel:
_APIGroupsRegistrationLevelsMap[map["registration_level"]],
postCreationLevel: _APIGroupsPostsCreationLevelsMap[map["posts_level"]],
_APIGroupsRegistrationLevelsMap[map["registration_level"]]!,
postCreationLevel: _APIGroupsPostsCreationLevelsMap[map["posts_level"]]!,
virtualDirectory: nullToEmpty(map["virtual_directory"]),
following: map["following"]);
}
@ -392,11 +392,11 @@ class GroupsHelper {
name: map["name"],
iconURL: map["icon_url"],
numberMembers: map["number_members"],
membershipLevel: APIGroupsMembershipLevelsMap[map["membership"]],
visibilityLevel: _APIGroupsVisibilityLevelsMap[map["visibility"]],
membershipLevel: APIGroupsMembershipLevelsMap[map["membership"]]!,
visibilityLevel: _APIGroupsVisibilityLevelsMap[map["visibility"]]!,
registrationLevel:
_APIGroupsRegistrationLevelsMap[map["registration_level"]],
postCreationLevel: _APIGroupsPostsCreationLevelsMap[map["posts_level"]],
_APIGroupsRegistrationLevelsMap[map["registration_level"]]!,
postCreationLevel: _APIGroupsPostsCreationLevelsMap[map["posts_level"]]!,
isMembersListPublic: map["is_members_list_public"],
virtualDirectory: nullToEmpty(map["virtual_directory"]),
following: map["following"],
@ -418,6 +418,6 @@ class GroupsHelper {
userID: row["user_id"],
groupID: row["group_id"],
timeCreate: row["time_create"],
level: APIGroupsMembershipLevelsMap[row["level"]],
level: APIGroupsMembershipLevelsMap[row["level"]]!,
);
}

View File

@ -29,7 +29,7 @@ class IndependentPushNotificationsHelper {
}
/// Configure independent push notification services with a pull URL
static Future<void> configure(String wsURL) async {
static Future<void> configure(String? wsURL) async {
await platform.invokeMethod("configure", wsURL);
}

View File

@ -1,6 +1,5 @@
import 'package:comunic/enums/likes_type.dart';
import 'package:comunic/helpers/websocket_helper.dart';
import 'package:meta/meta.dart';
/// Likes helper
///
@ -16,9 +15,9 @@ const LikesAPIMap = {
class LikesHelper {
/// Update liking status of an element
Future<void> setLiking({
@required LikesType type,
@required bool like,
@required int id,
required LikesType type,
required bool like,
required int id,
}) async {
return (await ws("likes/update", {
"type": LikesAPIMap[type],

View File

@ -55,7 +55,7 @@ class NotificationsHelper {
await APIRequest(uri: "notifications/count_all_news", needLogin: true)
.exec();
final content = response.assertOk().getObject();
final content = response.assertOk().getObject()!;
return CountUnreadNotifications(
notifications: content["notifications"],
@ -75,15 +75,15 @@ class NotificationsHelper {
// Parse the list of notifications
return NotificationsList()
..addAll(response
.getArray()
.getArray()!
.map((f) => Notification(
id: f["id"],
timeCreate: f["time_create"],
seen: f["seen"],
fromUser: f["from_user_id"],
onElemId: f["on_elem_id"],
onElemType: _NotificationElementTypeAPImapping[f["on_elem_type"]],
type: _NotificationsTypeAPImapping[f["type"]],
onElemType: _NotificationElementTypeAPImapping[f["on_elem_type"]]!,
type: _NotificationsTypeAPImapping[f["type"]]!,
fromContainerId: f["from_container_id"],
fromContainerType: f["from_container_type"] == ""
? null

View File

@ -55,7 +55,7 @@ class PostsHelper {
/// Get the list of latest posts. Return the list of posts or null in case of
/// failure
Future<PostsList> getLatest({int from = 0}) async {
Future<PostsList?> getLatest({int from = 0}) async {
final response =
await APIRequest(uri: "posts/get_latest", needLogin: true, args: {
"include_groups": true.toString(),
@ -66,7 +66,8 @@ class PostsHelper {
try {
// Parse & return the list of posts
return PostsList()..addAll(response.getArray().map((f) => _apiToPost(f)));
return PostsList()
..addAll(response.getArray()!.map((f) => _apiToPost(f)));
} catch (e) {
print(e.toString());
return null;
@ -74,7 +75,7 @@ class PostsHelper {
}
/// Get the list of posts of a user
Future<PostsList> getUserPosts(int userID, {int from = 0}) async {
Future<PostsList?> getUserPosts(int? userID, {int from = 0}) async {
final response = await (APIRequest(uri: "posts/get_user", needLogin: true)
..addInt("userID", userID)
..addInt("startFrom", from == 0 ? 0 : from - 1))
@ -84,7 +85,8 @@ class PostsHelper {
try {
// Parse & return the list of posts
return PostsList()..addAll(response.getArray().map((f) => _apiToPost(f)));
return PostsList()
..addAll(response.getArray()!.map((f) => _apiToPost(f)));
} catch (e) {
print(e.toString());
return null;
@ -92,7 +94,7 @@ class PostsHelper {
}
/// Get the list of posts of a group
Future<PostsList> getGroupPosts(int groupID, {int from = 0}) async {
Future<PostsList?> getGroupPosts(int groupID, {int from = 0}) async {
final response = await (APIRequest(uri: "posts/get_group", needLogin: true)
..addInt("groupID", groupID)
..addInt("startFrom", from == 0 ? 0 : from - 1))
@ -102,7 +104,8 @@ class PostsHelper {
try {
// Parse & return the list of posts
return PostsList()..addAll(response.getArray().map((f) => _apiToPost(f)));
return PostsList()
..addAll(response.getArray()!.map((f) => _apiToPost(f)));
} catch (e) {
print(e.toString());
return null;
@ -120,7 +123,7 @@ class PostsHelper {
if (!response.isOK)
throw Exception("Could not get information about the post!");
return _apiToPost(response.getObject());
return _apiToPost(response.getObject()!);
}
/// Create a new post
@ -158,13 +161,14 @@ class PostsHelper {
case PostKind.COUNTDOWN:
request.addInt(
"time-end", (post.timeEnd.millisecondsSinceEpoch / 1000).floor());
"time-end", (post.timeEnd!.millisecondsSinceEpoch / 1000).floor());
break;
case PostKind.SURVEY:
request.addString("question", post.survey.question);
request.addString("answers", post.survey.answers.join("<>"));
request.addBool("allowNewAnswers", post.survey.allowNewChoicesCreation);
request.addString("question", post.survey!.question);
request.addString("answers", post.survey!.answers.join("<>"));
request.addBool(
"allowNewAnswers", post.survey!.allowNewChoicesCreation);
break;
case PostKind.YOUTUBE:
@ -221,7 +225,7 @@ class PostsHelper {
/// Register to a post events
Future<void> registerPostEvents(int id) async {
if (_registeredPosts.containsKey(id))
_registeredPosts[id]++;
_registeredPosts.update(id, (v) => v + 1);
else {
_registeredPosts[id] = 1;
await ws("\$main/register_post", {"postID": id});
@ -232,9 +236,9 @@ class PostsHelper {
Future<void> unregisterPostEvents(int id) async {
if (!_registeredPosts.containsKey(id)) return;
_registeredPosts[id]--;
_registeredPosts.update(id, (v) => v - 1);
if (_registeredPosts[id] <= 0) {
if (_registeredPosts[id]! <= 0) {
_registeredPosts.remove(id);
await ws("\$main/unregister_post", {"postID": id});
}
@ -242,14 +246,14 @@ class PostsHelper {
/// Turn an API entry into a [Post] object
Post _apiToPost(Map<String, dynamic> map) {
final postKind = _APIPostsKindsMap[map["kind"]];
final postKind = _APIPostsKindsMap[map["kind"]]!;
// Parse comments
CommentsList comments;
CommentsList? comments;
if (map["comments"] != null) {
comments = CommentsList();
map["comments"]
.forEach((v) => comments.add(CommentsHelper.apiToComment(v)));
.forEach((v) => comments!.add(CommentsHelper.apiToComment(v)));
}
final survey = postKind == PostKind.SURVEY
@ -263,7 +267,7 @@ class PostsHelper {
groupID: map["group_id"],
timeSent: map["post_time"],
content: DisplayedString(map["content"]),
visibilityLevel: _APIPostsVisibilityLevelMap[map["visibility_level"]],
visibilityLevel: _APIPostsVisibilityLevelMap[map["visibility_level"]]!,
kind: postKind,
fileSize: map["file_size"],
fileType: map["file_type"],
@ -276,7 +280,7 @@ class PostsHelper {
linkImage: map["link_image"],
likes: map["likes"],
userLike: map["userlike"],
access: _APIUserAccessMap[map["user_access"]],
access: _APIUserAccessMap[map["user_access"]]!,
comments: comments,
survey: survey);
}

View File

@ -30,7 +30,7 @@ const _PreferenceKeysName = {
};
class PreferencesHelper {
static PreferencesHelper _instance;
static PreferencesHelper? _instance;
static Future<PreferencesHelper> getInstance() async {
if (_instance == null) {
@ -38,10 +38,10 @@ class PreferencesHelper {
await _init();
}
return _instance;
return _instance!;
}
static SharedPreferences _sharedPreferences;
static late SharedPreferences _sharedPreferences;
PreferencesHelper._();
@ -50,7 +50,7 @@ class PreferencesHelper {
}
/// Set new login tokens
Future<void> setLoginToken(String token) async {
Future<void> setLoginToken(String? token) async {
if (token != null)
await setString(PreferencesKeyList.LOGIN_TOKEN, token);
else
@ -58,7 +58,7 @@ class PreferencesHelper {
}
/// Get current [LoginTokens]. Returns null if none or in case of failure
String getLoginToken() {
String? getLoginToken() {
try {
final string = getString(PreferencesKeyList.LOGIN_TOKEN);
return string;
@ -69,35 +69,35 @@ class PreferencesHelper {
}
bool containsKey(PreferencesKeyList key) {
return _sharedPreferences.containsKey(_PreferenceKeysName[key]);
return _sharedPreferences.containsKey(_PreferenceKeysName[key]!);
}
Future<bool> removeKey(PreferencesKeyList key) async {
return await _sharedPreferences.remove(_PreferenceKeysName[key]);
return await _sharedPreferences.remove(_PreferenceKeysName[key]!);
}
Future<bool> setString(PreferencesKeyList key, String value) async {
return await _sharedPreferences.setString(_PreferenceKeysName[key], value);
return await _sharedPreferences.setString(_PreferenceKeysName[key]!, value);
}
String getString(PreferencesKeyList key) {
return _sharedPreferences.getString(_PreferenceKeysName[key]);
String? getString(PreferencesKeyList key) {
return _sharedPreferences.getString(_PreferenceKeysName[key]!);
}
Future<bool> setBool(PreferencesKeyList key, bool value) async {
return await _sharedPreferences.setBool(_PreferenceKeysName[key], value);
return await _sharedPreferences.setBool(_PreferenceKeysName[key]!, value);
}
Future<bool> setInt(PreferencesKeyList key, int value) async {
return await _sharedPreferences.setInt(_PreferenceKeysName[key], value);
return await _sharedPreferences.setInt(_PreferenceKeysName[key]!, value);
}
int getInt(PreferencesKeyList key) {
return _sharedPreferences.getInt(_PreferenceKeysName[key]);
int? getInt(PreferencesKeyList key) {
return _sharedPreferences.getInt(_PreferenceKeysName[key]!);
}
bool getBool(PreferencesKeyList key, {bool alternative = false}) {
final v = _sharedPreferences.getBool(_PreferenceKeysName[key]);
final v = _sharedPreferences.getBool(_PreferenceKeysName[key]!);
return v == null ? alternative : v;
}
@ -115,7 +115,7 @@ class PreferencesHelper {
}
}
PreferencesHelper preferences() {
PreferencesHelper? preferences() {
if (PreferencesHelper._instance == null)
throw Exception("Try to get preference before their initialization!");

View File

@ -21,14 +21,14 @@ const _PushNotificationsAPIMap = {
class PushNotificationsHelper {
/// Get cached status of push notifications
static Future<PushNotificationsStatus> getLocalStatus() async {
static Future<PushNotificationsStatus?> getLocalStatus() async {
final pref = await PreferencesHelper.getInstance();
if (!pref.containsKey(PreferencesKeyList.PUSH_NOTIFICATIONS_STATUS))
return PushNotificationsStatus.UNDEFINED;
return _PushNotificationsAPIMap[
pref.getString(PreferencesKeyList.PUSH_NOTIFICATIONS_STATUS)];
pref.getString(PreferencesKeyList.PUSH_NOTIFICATIONS_STATUS)!];
}
/// Refresh local status with information from server
@ -47,13 +47,13 @@ class PushNotificationsHelper {
response["independent_push_url"]);
}
await (await PreferencesHelper.getInstance()).setString(
await (await PreferencesHelper.getInstance())!.setString(
PreferencesKeyList.PUSH_NOTIFICATIONS_STATUS, response["status"]);
}
/// Clear local push notifications status
static Future<void> clearLocalStatus() async {
await (await PreferencesHelper.getInstance())
await (await PreferencesHelper.getInstance())!
.removeKey(PreferencesKeyList.PUSH_NOTIFICATIONS_STATUS);
// Stop local refresh notification refresh
@ -62,8 +62,8 @@ class PushNotificationsHelper {
/// Configure push notifications
static Future<void> configure(
BuildContext context, PushNotificationsStatus newStatus) async {
String firebaseToken = "";
BuildContext context, PushNotificationsStatus? newStatus) async {
String? firebaseToken = "";
switch (newStatus) {
case PushNotificationsStatus.DISABLED:
break;
@ -90,8 +90,8 @@ class PushNotificationsHelper {
/// Set new push notification status on the server
static Future<void> setNewStatus(
PushNotificationsStatus newStatus, {
String firebaseToken = "",
PushNotificationsStatus? newStatus, {
String? firebaseToken = "",
}) async =>
await APIRequest.withLogin("push_notifications/configure")
.addString(
@ -104,6 +104,6 @@ class PushNotificationsHelper {
/// Is true if possible if push notifications are configurable
static bool get arePushNotificationsAvailable =>
srvConfig.notificationsPolicy.hasFirebase ||
(isAndroid && srvConfig.notificationsPolicy.hasIndependent);
srvConfig!.notificationsPolicy.hasFirebase ||
(isAndroid && srvConfig!.notificationsPolicy.hasIndependent);
}

View File

@ -13,7 +13,7 @@ class SearchHelper {
/// Search for user. This method returns information about the target users
///
/// Returns information about the target users or null if an error occurred
Future<UsersList> searchUser(String query) async {
Future<UsersList?> searchUser(String query) async {
// Execute the query on the server
final response = await APIRequest(
uri: "user/search", needLogin: true, args: {"query": query}).exec();
@ -21,7 +21,7 @@ class SearchHelper {
if (response.code != 200) return null;
return await UsersHelper()
.getUsersInfo(response.getArray().map((f) => cast<int>(f)).toList());
.getUsersInfo(response.getArray()!.map((f) => cast<int>(f)).toList());
}
/// Perform a global search
@ -31,7 +31,7 @@ class SearchHelper {
result.assertOk();
return SearchResultsList()..addAll(result.getArray().map((f) {
return SearchResultsList()..addAll(result.getArray()!.map((f) {
switch (f["kind"]) {
case "user":
return SearchResult(id: f["id"], kind: SearchResultKind.USER);

View File

@ -17,7 +17,7 @@ abstract class SerializableElement<T> extends Comparable<T> {
abstract class BaseSerializationHelper<T extends SerializableElement> {
/// List cache
List<T> _cache;
List<T>? _cache;
/// The name of the type of data to serialise
String get type;
@ -48,12 +48,15 @@ abstract class BaseSerializationHelper<T extends SerializableElement> {
try {
final file = await _getFilePath();
if (!await file.exists()) return _cache = [];
if (!await file.exists()) {
_cache = [];
return;
}
final List<dynamic> json = jsonDecode(await file.readAsString());
_cache = json.cast<Map<String, dynamic>>().map(parse).toList();
_cache.sort();
_cache!.sort();
} catch (e, s) {
logError(e, s);
print("Failed to read serialized data!");
@ -67,8 +70,10 @@ abstract class BaseSerializationHelper<T extends SerializableElement> {
try {
final file = await _getFilePath();
await file.writeAsString(jsonEncode(
_cache.map((e) => e.toJson()).toList().cast<Map<String, dynamic>>()));
await file.writeAsString(jsonEncode(_cache!
.map((e) => e.toJson())
.toList()
.cast<Map<String, dynamic>>()));
} catch (e, s) {
print("Failed to write file!");
logError(e, s);
@ -78,7 +83,7 @@ abstract class BaseSerializationHelper<T extends SerializableElement> {
/// Get the current list of elements
Future<List<T>> getList() async {
await _loadCache();
return List.from(_cache);
return List.from(_cache!);
}
/// Set a new list of conversations
@ -90,23 +95,23 @@ abstract class BaseSerializationHelper<T extends SerializableElement> {
/// Insert new element
Future<void> insert(T el) async {
await _loadCache();
_cache.add(el);
_cache.sort();
_cache!.add(el);
_cache!.sort();
await _saveCache();
}
/// Insert new element
Future<void> insertMany(List<T> els) async {
await _loadCache();
_cache.addAll(els);
_cache.sort();
_cache!.addAll(els);
_cache!.sort();
await _saveCache();
}
/// Check if any entry in the last match the predicate
Future<bool> any(bool isContained(T t)) async {
await _loadCache();
return _cache.any((element) => isContained(element));
return _cache!.any((element) => isContained(element));
}
Future<bool> has(T el) => any((t) => t == el);
@ -114,7 +119,7 @@ abstract class BaseSerializationHelper<T extends SerializableElement> {
/// Check if any entry in the last match the predicate
Future<T> first(bool filter(T t)) async {
await _loadCache();
return _cache.firstWhere((element) => filter(element));
return _cache!.firstWhere((element) => filter(element));
}
/// Replace an element with another one
@ -122,10 +127,10 @@ abstract class BaseSerializationHelper<T extends SerializableElement> {
await _loadCache();
// Insert or replace the element
_cache = _cache.where((element) => !isToReplace(element)).toList();
_cache.add(newEl);
_cache = _cache!.where((element) => !isToReplace(element)).toList();
_cache!.add(newEl);
_cache.sort();
_cache!.sort();
await _saveCache();
}
@ -133,8 +138,8 @@ abstract class BaseSerializationHelper<T extends SerializableElement> {
Future<void> insertOrReplaceElements(List<T> list) async {
await _loadCache();
_cache.removeWhere((element) => list.any((newEl) => element == newEl));
_cache.addAll(list);
_cache!.removeWhere((element) => list.any((newEl) => element == newEl));
_cache!.addAll(list);
await _saveCache();
}
@ -142,7 +147,7 @@ abstract class BaseSerializationHelper<T extends SerializableElement> {
/// Remove elements
Future<void> removeElement(bool isToRemove(T t)) async {
await _loadCache();
_cache.removeWhere((element) => isToRemove(element));
_cache!.removeWhere((element) => isToRemove(element));
await _saveCache();
}

View File

@ -8,7 +8,7 @@ import 'package:comunic/models/conversation_message.dart';
///
/// @author Pierre Hubert
HashMap<int, ConversationsMessagesSerializationHelper> _instances;
HashMap<int?, ConversationsMessagesSerializationHelper>? _instances;
class ConversationsMessagesSerializationHelper
extends BaseSerializationHelper<ConversationMessage> {
@ -18,13 +18,13 @@ class ConversationsMessagesSerializationHelper
: convID = convID,
assert(convID != null);
factory ConversationsMessagesSerializationHelper(int convID) {
factory ConversationsMessagesSerializationHelper(int? convID) {
if (_instances == null) _instances = HashMap();
if (!_instances.containsKey(convID))
_instances[convID] = ConversationsMessagesSerializationHelper._(convID);
if (!_instances!.containsKey(convID))
_instances![convID] = ConversationsMessagesSerializationHelper._(convID!);
return _instances[convID];
return _instances![convID]!;
}
@override

View File

@ -28,5 +28,5 @@ class ConversationsSerializationHelper
ConversationsList()..addAll(await super.getList());
/// Get a conversation
Future<Conversation> get(int id) => first((t) => t.id == id);
Future<Conversation> get(int? id) => first((t) => t.id == id);
}

View File

@ -5,7 +5,7 @@ import 'package:comunic/models/user.dart';
///
/// @author Pierre Hubert
UsersListSerialisationHelper _singleton;
UsersListSerialisationHelper? _singleton;
class UsersListSerialisationHelper extends BaseSerializationHelper<User> {
UsersListSerialisationHelper._();
@ -13,7 +13,7 @@ class UsersListSerialisationHelper extends BaseSerializationHelper<User> {
factory UsersListSerialisationHelper() {
if (_singleton == null) _singleton = UsersListSerialisationHelper._();
return _singleton;
return _singleton!;
}
@override
@ -23,6 +23,6 @@ class UsersListSerialisationHelper extends BaseSerializationHelper<User> {
User parse(Map<String, dynamic> m) => User.fromJson(m);
/// Remove a user by its ID
Future<void> removeUserByID(int userID) =>
Future<void> removeUserByID(int? userID) =>
removeElement((t) => t.id == userID);
}

View File

@ -7,7 +7,7 @@ import 'package:version/version.dart';
/// @author Pierre Hubert
class ServerConfigurationHelper {
static ServerConfig _config;
static ServerConfig? _config;
/// Make sure the configuration has been correctly loaded
static Future<void> ensureLoaded() async {
@ -15,7 +15,7 @@ class ServerConfigurationHelper {
final response =
(await APIRequest.withoutLogin("server/config").execWithThrow())
.getObject();
.getObject()!;
final banner = response["banner"];
final pushNotificationsPolicy = response["push_notifications"];
@ -97,7 +97,7 @@ class ServerConfigurationHelper {
}
/// Get current server configuration, throwing if it is not loaded yet
static ServerConfig get config {
static ServerConfig? get config {
if (_config == null)
throw Exception(
"Trying to access server configuration but it is not loaded yet!");
@ -107,6 +107,6 @@ class ServerConfigurationHelper {
}
/// Shortcut for server configuration
ServerConfig get srvConfig => ServerConfigurationHelper.config;
ServerConfig? get srvConfig => ServerConfigurationHelper.config;
bool get showBanner => srvConfig.banner != null && srvConfig.banner.visible;
bool get showBanner => srvConfig!.banner != null && srvConfig!.banner!.visible;

View File

@ -25,7 +25,7 @@ class SettingsHelper {
final response =
(await APIRequest(uri: "settings/get_general", needLogin: true).exec())
.assertOk()
.getObject();
.getObject()!;
return GeneralSettings(
email: response["email"],
@ -88,13 +88,13 @@ class SettingsHelper {
(await APIRequest(uri: "settings/get_account_image", needLogin: true)
.exec())
.assertOk()
.getObject();
.getObject()!;
return AccountImageSettings(
hasImage: response["has_image"],
imageURL: response["image_url"],
visibility:
_APIAccountImageVisibilityAPILevels[response["visibility"]]);
_APIAccountImageVisibilityAPILevels[response["visibility"]]!);
}
/// Upload a new account image
@ -143,7 +143,7 @@ class SettingsHelper {
/// Delete a custom emoji
///
/// Throws in case of failure
static Future<void> deleteCustomEmoji(int emojiID) async =>
static Future<void> deleteCustomEmoji(int? emojiID) async =>
(await APIRequest(uri: "settings/delete_custom_emoji", needLogin: true)
.addInt("emojiID", emojiID)
.exec())
@ -175,7 +175,7 @@ class SettingsHelper {
(await APIRequest(uri: "settings/get_security", needLogin: true)
.addString("password", password)
.execWithThrow())
.getObject();
.getObject()!;
return SecuritySettings(
securityQuestion1: response["security_question_1"],
@ -207,7 +207,7 @@ class SettingsHelper {
final response =
(await APIRequest.withLogin("settings/get_data_conservation_policy")
.execWithThrow())
.getObject();
.getObject()!;
return DataConservationPolicySettings(
inactiveAccountLifeTime: response["inactive_account_lifetime"],
@ -223,7 +223,7 @@ class SettingsHelper {
///
/// Throws in case of failure
static Future<void> setDataConservationPolicy(
String password, DataConservationPolicySettings newSettings) async {
String? password, DataConservationPolicySettings newSettings) async {
await APIRequest(
uri: "settings/set_data_conservation_policy", needLogin: true)
.addString("password", password)

View File

@ -1,7 +1,6 @@
import 'package:comunic/models/api_request.dart';
import 'package:comunic/models/survey.dart';
import 'package:comunic/models/survey_choice.dart';
import 'package:meta/meta.dart';
/// Survey helper
///
@ -13,7 +12,7 @@ class SurveyHelper {
apiToSurvey((await APIRequest.withLogin("surveys/get_info")
.addInt("postID", postID)
.execWithThrow())
.getObject());
.getObject()!);
/// Cancel the response of a user to a survey
Future<bool> cancelResponse(Survey survey) async {
@ -26,7 +25,7 @@ class SurveyHelper {
/// Send the response of a user to a survey
Future<bool> respondToSurvey(
{@required Survey survey, @required SurveyChoice choice}) async {
{required Survey survey, required SurveyChoice choice}) async {
assert(survey != null);
assert(choice != null);

View File

@ -31,7 +31,7 @@ class UsersHelper {
///
/// Return the list of users information in case of success, null in case of
/// failure
Future<UsersList> _downloadInfo(List<int> users) async {
Future<UsersList?> _downloadInfo(List<int?> users) async {
// Execute the request
final response = await APIRequest(
uri: "user/getInfoMultiple",
@ -42,7 +42,7 @@ class UsersHelper {
if (response.code != 200) return null;
final list = UsersList();
response.getObject().forEach(
response.getObject()!.forEach(
(k, v) => list.add(
User(
id: v["userID"],
@ -69,7 +69,7 @@ class UsersHelper {
/// Get users information from a given [Set]. Throws an exception in case
/// of failure
Future<UsersList> getListWithThrow(Set<int> users,
Future<UsersList> getListWithThrow(Set<int?> users,
{bool forceDownload = false}) async {
final list =
await getUsersInfo(users.toList(), forceDownload: forceDownload);
@ -82,16 +82,16 @@ class UsersHelper {
}
/// Get information about a single user. Throws in case of failure
Future<User> getSingleWithThrow(int user,
Future<User> getSingleWithThrow(int? user,
{bool forceDownload = false}) async {
return (await getListWithThrow(Set<int>()..add(user),
return (await getListWithThrow(Set<int?>()..add(user),
forceDownload: forceDownload))[0];
}
/// Get users information from a given [Set]
///
/// Throws in case of failure
Future<UsersList> getList(Set<int> users,
Future<UsersList> getList(Set<int?> users,
{bool forceDownload = false}) async {
final list = await getUsersInfo(users.toList());
@ -104,13 +104,13 @@ class UsersHelper {
///
/// If [forceDownload] is set to true, the data will always be retrieved from
/// the server, otherwise cached data will be used if available
Future<UsersList> getUsersInfo(List<int> users,
Future<UsersList?> getUsersInfo(List<int?> users,
{bool forceDownload = false}) async {
List<int> toDownload = [];
List<int?> toDownload = [];
UsersList list = UsersList();
// Check cache
for (int userID in users) {
for (int? userID in users) {
if (!forceDownload &&
await UsersListSerialisationHelper().any((u) => u.id == userID))
list.add(
@ -151,7 +151,7 @@ class UsersHelper {
throw new GetUserAdvancedUserError(cause);
}
return apiToAdvancedUserInfo(response.getObject());
return apiToAdvancedUserInfo(response.getObject()!);
}
/// Parse the list of custom emojies

View File

@ -7,15 +7,15 @@ import 'package:version/version.dart';
/// @author Pierre Hubert
class VersionHelper {
static PackageInfo _info;
static PackageInfo? _info;
static Future<void> ensureLoaded() async {
if (!isWeb) _info = await PackageInfo.fromPlatform();
}
/// Get current version information
static PackageInfo get info => _info;
static PackageInfo? get info => _info;
/// Get current application version, in parsed format
static Version get version => Version.parse(info.version);
static Version get version => Version.parse(info!.version);
}

View File

@ -1,5 +1,4 @@
import 'package:comunic/models/api_request.dart';
import 'package:flutter/material.dart';
/// Virtual directory helper
///
@ -9,10 +8,10 @@ enum VirtualDirectoryType { USER, GROUP, NONE }
class VirtualDirectoryResult {
final VirtualDirectoryType type;
final int id;
final int? id;
const VirtualDirectoryResult({
@required this.type,
required this.type,
this.id,
}) : assert(type != null);
}
@ -30,8 +29,8 @@ class VirtualDirectoryHelper {
return VirtualDirectoryResult(type: VirtualDirectoryType.NONE);
case 200:
final id = response.getObject()["id"];
final kind = response.getObject()["kind"];
final id = response.getObject()!["id"];
final kind = response.getObject()!["kind"];
switch (kind) {
case "user":
return VirtualDirectoryResult(

View File

@ -15,7 +15,7 @@ class WebAppHelper {
static Future<MembershipList> getMemberships() async {
final response =
(await APIRequest.withLogin("webApp/getMemberships").execWithThrow())
.getArray();
.getArray()!;
return MembershipList()
..addAll(response
@ -26,7 +26,7 @@ class WebAppHelper {
}
/// Turn an API entry into a membership entry
static Membership _apiToMembership(Map<String, dynamic> entry) {
static Membership? _apiToMembership(Map<String, dynamic> entry) {
switch (entry["type"]) {
case "conversation":
return Membership.conversation(

View File

@ -15,7 +15,7 @@ import 'package:web_socket_channel/web_socket_channel.dart';
/// @author Pierre Hubert
class WebSocketHelper {
static WebSocketChannel _ws;
static WebSocketChannel? _ws;
static int _counter = 0;
@ -23,14 +23,14 @@ class WebSocketHelper {
/// Check out whether we are currently connected to WebSocket or not
static bool isConnected() {
return _ws != null && _ws.closeCode == null;
return _ws != null && _ws!.closeCode == null;
}
/// Get WebSocket access token
static Future<String> _getWsToken() async =>
static Future<String?> _getWsToken() async =>
(await APIRequest(uri: "ws/token", needLogin: true).exec())
.assertOk()
.getObject()["token"];
.getObject()!["token"];
/// Connect to WebSocket
static connect() async {
@ -47,7 +47,7 @@ class WebSocketHelper {
// Connect
_ws = WebSocketChannel.connect(wsURI);
_ws.stream.listen(
_ws!.stream.listen(
// When we got data
(data) {
print("WS New data: $data");
@ -75,7 +75,7 @@ class WebSocketHelper {
/// Close current WebSocket (if any)
static close() {
if (isConnected()) _ws.sink.close();
if (isConnected()) _ws!.sink.close();
}
/// Send a new message
@ -93,7 +93,7 @@ class WebSocketHelper {
print("WS Send message: $msg");
_ws.sink.add(msg);
_ws!.sink.add(msg);
_requests[id] = completer;
return completer.future;
@ -240,11 +240,11 @@ class WebSocketHelper {
// Handles errors
if (msg.title != "success") {
completer.completeError(Exception("Could not process request!"));
completer!.completeError(Exception("Could not process request!"));
return;
}
completer.complete(msg.data);
completer!.complete(msg.data);
}
}