Browse Source

neon,neon_files,neon_news,neon_notes,neon_notifications: Use Result helper methods

pull/406/head
jld3103 1 year ago
parent
commit
42495461f0
No known key found for this signature in database
GPG Key ID: 9062417B9E8EB7B3
  1. 11
      packages/neon/neon/lib/src/blocs/apps.dart
  2. 10
      packages/neon/neon/lib/src/pages/account_settings.dart
  3. 4
      packages/neon/neon/lib/src/pages/home.dart
  4. 2
      packages/neon/neon/lib/src/pages/login.dart
  5. 10
      packages/neon/neon/lib/src/pages/settings.dart
  6. 4
      packages/neon/neon/lib/src/utils/account_options.dart
  7. 2
      packages/neon/neon/lib/src/utils/request_manager.dart
  8. 2
      packages/neon/neon/lib/src/utils/result.dart
  9. 4
      packages/neon/neon/lib/src/widgets/account_tile.dart
  10. 2
      packages/neon/neon/lib/src/widgets/cached_image.dart
  11. 10
      packages/neon/neon/lib/src/widgets/drawer_destination.dart
  12. 2
      packages/neon/neon/lib/src/widgets/user_avatar.dart
  13. 2
      packages/neon/neon_files/lib/dialogs/choose_folder.dart
  14. 16
      packages/neon/neon_files/lib/widgets/browser_view.dart
  15. 5
      packages/neon/neon_news/lib/blocs/news.dart
  16. 6
      packages/neon/neon_news/lib/dialogs/add_feed.dart
  17. 4
      packages/neon/neon_news/lib/widgets/articles_view.dart
  18. 8
      packages/neon/neon_news/lib/widgets/feeds_view.dart
  19. 10
      packages/neon/neon_news/lib/widgets/folders_view.dart
  20. 4
      packages/neon/neon_notes/lib/dialogs/create_note.dart
  21. 4
      packages/neon/neon_notes/lib/dialogs/select_category.dart
  22. 2
      packages/neon/neon_notes/lib/widgets/categories_view.dart
  23. 4
      packages/neon/neon_notifications/lib/blocs/notifications.dart

11
packages/neon/neon/lib/src/blocs/apps.dart

@ -34,17 +34,17 @@ class AppsBloc extends InteractiveBloc implements AppsBlocEvents, AppsBlocStates
});
appImplementations.listen((final result) {
if (result.data != null) {
if (result.hasData) {
final options = _accountsBloc.getOptionsFor(_account);
unawaited(
options.initialApp.stream.first.then((var initialApp) async {
if (initialApp == null) {
if (result.data!.find('files') != null) {
if (result.requireData.find('files') != null) {
initialApp = 'files';
} else if (result.data!.isNotEmpty) {
} else if (result.requireData.isNotEmpty) {
// This should never happen, because the files app is always installed and can not be removed, but just in
// case this changes at a later point.
initialApp = result.data!.first.id;
initialApp = result.requireData.first.id;
}
}
if (!activeAppID.hasValue) {
@ -176,7 +176,8 @@ class AppsBloc extends InteractiveBloc implements AppsBlocEvents, AppsBlocStates
@override
Future setActiveApp(final String? appID) async {
if (appID != null && (await appImplementations.firstWhere((final a) => a.data != null)).data!.find(appID) != null) {
if (appID != null &&
(await appImplementations.firstWhere((final a) => a.hasData)).requireData.find(appID) != null) {
if (activeAppID.valueOrNull != appID) {
activeAppID.add(appID);
}

10
packages/neon/neon/lib/src/pages/account_settings.dart

@ -71,9 +71,9 @@ class AccountSettingsPage extends StatelessWidget {
title: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
if (userDetails.data != null) ...[
if (userDetails.hasData) ...[
LinearProgressIndicator(
value: userDetails.data!.quota.relative / 100,
value: userDetails.requireData.quota.relative / 100,
backgroundColor: Theme.of(context).colorScheme.primary.withOpacity(0.3),
),
const SizedBox(
@ -81,9 +81,9 @@ class AccountSettingsPage extends StatelessWidget {
),
Text(
AppLocalizations.of(context).accountOptionsQuotaUsedOf(
filesize(userDetails.data!.quota.used, 1),
filesize(userDetails.data!.quota.total, 1),
userDetails.data!.quota.relative.toString(),
filesize(userDetails.requireData.quota.used, 1),
filesize(userDetails.requireData.quota.total, 1),
userDetails.requireData.quota.relative.toString(),
),
),
],

4
packages/neon/neon/lib/src/pages/home.dart

@ -109,8 +109,8 @@ class _HomePageState extends State<HomePage> {
Widget body = Builder(
builder: (final context) => Column(
children: [
if (appImplementations.data != null) ...[
if (appImplementations.data!.isEmpty) ...[
if (appImplementations.hasData) ...[
if (appImplementations.requireData.isEmpty) ...[
Expanded(
child: Center(
child: Text(

2
packages/neon/neon/lib/src/pages/login.dart

@ -137,7 +137,7 @@ class _LoginPageState extends State<LoginPage> {
},
),
actions: [
if (serverConnectionStateSnapshot.data != null) ...[
if (serverConnectionStateSnapshot.hasData) ...[
IconButton(
onPressed: _loginBloc.refresh,
tooltip: AppLocalizations.of(context).loginRestart,

10
packages/neon/neon/lib/src/pages/settings.dart

@ -51,7 +51,7 @@ class _SettingsPageState extends State<SettingsPage> {
appImplementations: appImplementations,
accountSpecificOptions: {
if (accountsSnapshot.hasData) ...{
for (final account in accountsSnapshot.data!) ...{
for (final account in accountsSnapshot.requireData) ...{
account: accountsBloc.getOptionsFor(account).options,
},
},
@ -114,8 +114,8 @@ class _SettingsPageState extends State<SettingsPage> {
SettingsCategory(
title: Text(AppLocalizations.of(context).optionsCategoryPushNotifications),
tiles: [
if (pushNotificationsEnabledEnabledSnapshot.data != null &&
!pushNotificationsEnabledEnabledSnapshot.data!) ...[
if (pushNotificationsEnabledEnabledSnapshot.hasData &&
!pushNotificationsEnabledEnabledSnapshot.requireData) ...[
NeonTextSettingsTile(
text: AppLocalizations.of(context).globalOptionsPushNotificationsEnabledDisabledNotice,
style: const TextStyle(
@ -164,7 +164,7 @@ class _SettingsPageState extends State<SettingsPage> {
SettingsCategory(
title: Text(AppLocalizations.of(context).optionsCategoryAccounts),
tiles: [
if (accountsSnapshot.data!.length > 1) ...[
if (accountsSnapshot.requireData.length > 1) ...[
CheckBoxSettingsTile(
option: globalOptions.rememberLastUsedAccount,
),
@ -172,7 +172,7 @@ class _SettingsPageState extends State<SettingsPage> {
option: globalOptions.initialAccount,
),
],
for (final account in accountsSnapshot.data!) ...[
for (final account in accountsSnapshot.requireData) ...[
NeonAccountSettingsTile(
account: account,
onTap: () {

4
packages/neon/neon/lib/src/utils/account_options.dart

@ -6,10 +6,10 @@ class AccountSpecificOptions {
this._appsBloc,
) {
_appsBloc.appImplementations.listen((final result) {
if (result.data != null) {
if (result.hasData) {
_appIDsSubject.add({
null: (final context) => AppLocalizations.of(context).accountOptionsAutomatic,
for (final app in result.data!) ...{
for (final app in result.requireData) ...{
app.id: app.name,
},
});

2
packages/neon/neon/lib/src/utils/request_manager.dart

@ -63,7 +63,7 @@ class RequestManager {
final bool emitEmptyCache,
final int retries,
) async {
if (subject.valueOrNull?.data != null) {
if (subject.valueOrNull?.hasData ?? false) {
subject.add(
Result(
subject.value.data,

2
packages/neon/neon/lib/src/utils/result.dart

@ -36,7 +36,7 @@ class Result<T> {
final bool isCached;
Result<R> transform<R>(final R? Function(T data) call) => Result(
data != null ? call(data as T) : null,
hasData ? call(data as T) : null,
error,
isLoading: isLoading,
isCached: isCached,

4
packages/neon/neon/lib/src/widgets/account_tile.dart

@ -40,10 +40,10 @@ class NeonAccountTile extends StatelessWidget {
stream: userDetailsBloc.userDetails,
builder: (final context, final userDetails) => Row(
children: [
if (userDetails.data != null) ...[
if (userDetails.hasData) ...[
Flexible(
child: Text(
userDetails.data!.displayname,
userDetails.requireData.displayname,
style: Theme.of(context).textTheme.bodyLarge!.copyWith(
color: textColor,
),

2
packages/neon/neon/lib/src/widgets/cached_image.dart

@ -35,7 +35,7 @@ class _NeonCachedImageState extends State<NeonCachedImage> {
future: future,
builder: (final context, final fileSnapshot) {
if (fileSnapshot.hasData) {
final content = fileSnapshot.data!.readAsBytesSync();
final content = fileSnapshot.requireData.readAsBytesSync();
try {
// TODO: Is this safe enough?

10
packages/neon/neon/lib/src/widgets/drawer_destination.dart

@ -35,7 +35,7 @@ extension NavigationRailDestinationExtension on NavigationRailDestination {
builder: (final context, final snapshot) {
final colorScheme = Theme.of(context).colorScheme;
final color = snapshot.data! > 0 ? colorScheme.primary : colorScheme.onBackground;
final color = snapshot.requireData > 0 ? colorScheme.primary : colorScheme.onBackground;
const size = Size.square(kAvatarSize * 2 / 3);
final icon = Container(
@ -43,7 +43,7 @@ extension NavigationRailDestinationExtension on NavigationRailDestination {
child: neonDestination.icon(size: size, color: color),
);
if (snapshot.data! <= 0) {
if (snapshot.requireData <= 0) {
return icon;
}
@ -55,7 +55,7 @@ extension NavigationRailDestinationExtension on NavigationRailDestination {
);
return Text(
snapshot.data!.toString(),
snapshot.requireData.toString(),
style: style,
);
},
@ -87,7 +87,7 @@ extension NavigationDrawerDestinationExtension on NavigationDrawerDestination {
builder: (final context, final snapshot) {
final label = Text(neonDestination.label);
if (snapshot.data! <= 0) {
if (snapshot.requireData <= 0) {
return label;
}
@ -102,7 +102,7 @@ extension NavigationDrawerDestinationExtension on NavigationDrawerDestination {
);
return Text(
snapshot.data!.toString(),
snapshot.requireData.toString(),
style: style,
);
},

2
packages/neon/neon/lib/src/widgets/user_avatar.dart

@ -107,7 +107,7 @@ class _UserAvatarState extends State<NeonUserAvatar> {
fontSize: 16,
),
);
} else if (result.data != null) {
} else if (result.hasData) {
decoration = BoxDecoration(
shape: BoxShape.circle,
color: _userStatusToColor(result.data!.status),

2
packages/neon/neon_files/lib/dialogs/choose_folder.dart

@ -44,7 +44,7 @@ class FilesChooseFolderDialog extends StatelessWidget {
builder: (final context) => const FilesCreateFolderDialog(),
);
if (result != null) {
bloc.createFolder([...pathSnapshot.data!, ...result]);
bloc.createFolder([...pathSnapshot.requireData, ...result]);
}
},
child: Text(AppLocalizations.of(context).folderCreate),

16
packages/neon/neon_files/lib/widgets/browser_view.dart

@ -46,7 +46,7 @@ class _FilesBrowserViewState extends State<FilesBrowserView> {
? Container()
: BackButtonListener(
onBackButtonPressed: () async {
final path = pathSnapshot.data!;
final path = pathSnapshot.requireData;
if (path.isNotEmpty) {
widget.bloc.setPath(path.sublist(0, path.length - 1));
return true;
@ -59,12 +59,12 @@ class _FilesBrowserViewState extends State<FilesBrowserView> {
sortBoxOrderOption: widget.bloc.options.filesSortBoxOrderOption,
input: files.data,
builder: (final context, final sorted) => NeonListView<Widget>(
scrollKey: 'files-${pathSnapshot.data!.join('/')}',
scrollKey: 'files-${pathSnapshot.requireData.join('/')}',
withFloatingActionButton: true,
items: [
for (final uploadTask in sorted == null
? <UploadTask>[]
: uploadTasksSnapshot.data!.where(
: uploadTasksSnapshot.requireData.where(
(final task) =>
sorted.where((final file) => _pathMatchesFile(task.path, file.name)).isEmpty,
)) ...[
@ -95,9 +95,9 @@ class _FilesBrowserViewState extends State<FilesBrowserView> {
if (!widget.onlyShowDirectories || file.isDirectory) ...[
Builder(
builder: (final context) {
final matchingUploadTasks = uploadTasksSnapshot.data!
final matchingUploadTasks = uploadTasksSnapshot.requireData
.where((final task) => _pathMatchesFile(task.path, file.name));
final matchingDownloadTasks = downloadTasksSnapshot.data!
final matchingDownloadTasks = downloadTasksSnapshot.requireData
.where((final task) => _pathMatchesFile(task.path, file.name));
return StreamBuilder<int?>(
@ -165,10 +165,10 @@ class _FilesBrowserViewState extends State<FilesBrowserView> {
widget.bloc.setPath([]);
},
),
for (var i = 0; i < pathSnapshot.data!.length; i++) ...[
for (var i = 0; i < pathSnapshot.requireData.length; i++) ...[
Builder(
builder: (final context) {
final path = pathSnapshot.data!.sublist(0, i + 1);
final path = pathSnapshot.requireData.sublist(0, i + 1);
return Tooltip(
message: AppLocalizations.of(context).goToPath(path.join('/')),
excludeFromSemantics: true,
@ -177,7 +177,7 @@ class _FilesBrowserViewState extends State<FilesBrowserView> {
widget.bloc.setPath(path);
},
child: Text(
pathSnapshot.data![i],
pathSnapshot.requireData[i],
semanticsLabel: AppLocalizations.of(context).goToPath(path.join('/')),
),
),

5
packages/neon/neon_news/lib/blocs/news.dart

@ -35,9 +35,10 @@ class NewsBloc extends InteractiveBloc implements NewsBlocEvents, NewsBlocStates
this.client,
) {
mainArticlesBloc.articles.listen((final result) {
if (result.data != null) {
if (result.hasData) {
final type = mainArticlesBloc.filterType.valueOrNull;
unreadCounter.add(result.data!.where((final a) => type == FilterType.starred ? a.starred : a.unread).length);
unreadCounter
.add(result.requireData.where((final a) => type == FilterType.starred ? a.starred : a.unread).length);
}
});

6
packages/neon/neon_news/lib/dialogs/add_feed.dart

@ -77,9 +77,9 @@ class _NewsAddFeedDialogState extends State<NewsAddFeedDialog> {
visible: folders.isLoading,
),
),
if (folders.data != null) ...[
if (folders.hasData) ...[
NewsFolderSelect(
folders: folders.data!,
folders: folders.requireData,
value: folder,
onChanged: (final f) {
setState(() {
@ -90,7 +90,7 @@ class _NewsAddFeedDialogState extends State<NewsAddFeedDialog> {
],
],
ElevatedButton(
onPressed: folders.data != null ? submit : null,
onPressed: folders.hasData ? submit : null,
child: Text(AppLocalizations.of(context).feedAdd),
),
],

4
packages/neon/neon_news/lib/widgets/articles_view.dart

@ -36,7 +36,7 @@ class _NewsArticlesViewState extends State<NewsArticlesView> {
input: articles.data,
builder: (final context, final sorted) => NeonListView<NextcloudNewsArticle>(
scrollKey: 'news-articles',
items: feeds.data == null ? null : sorted,
items: feeds.hasData ? sorted : null,
isLoading: articles.isLoading || feeds.isLoading,
error: articles.error ?? feeds.error,
onRefresh: () async {
@ -48,7 +48,7 @@ class _NewsArticlesViewState extends State<NewsArticlesView> {
builder: (final context, final article) => _buildArticle(
context,
article,
feeds.data!.singleWhere((final feed) => feed.id == article.feedId),
feeds.requireData.singleWhere((final feed) => feed.id == article.feedId),
),
topFixedChildren: [
StreamBuilder<FilterType>(

8
packages/neon/neon_news/lib/widgets/feeds_view.dart

@ -19,9 +19,9 @@ class NewsFeedsView extends StatelessWidget {
sortBox: feedsSortBox,
sortPropertyOption: bloc.options.feedsSortPropertyOption,
sortBoxOrderOption: bloc.options.feedsSortBoxOrderOption,
input: folders.data == null
? null
: feeds.data?.where((final f) => folderID == null || f.folderId == folderID).toList(),
input: folders.hasData
? feeds.data?.where((final f) => folderID == null || f.folderId == folderID).toList()
: null,
builder: (final context, final sorted) => NeonListView<NextcloudNewsFeed>(
scrollKey: 'news-feeds',
withFloatingActionButton: true,
@ -32,7 +32,7 @@ class NewsFeedsView extends StatelessWidget {
builder: (final context, final feed) => _buildFeed(
context,
feed,
folders.data!,
folders.requireData,
),
),
),

10
packages/neon/neon_news/lib/widgets/folders_view.dart

@ -17,15 +17,15 @@ class NewsFoldersView extends StatelessWidget {
sortBox: foldersSortBox,
sortPropertyOption: bloc.options.foldersSortPropertyOption,
sortBoxOrderOption: bloc.options.foldersSortBoxOrderOption,
input: feeds.data == null
? null
: folders.data?.map((final folder) {
final feedsInFolder = feeds.data!.where((final feed) => feed.folderId == folder.id);
input: feeds.hasData
? folders.data?.map((final folder) {
final feedsInFolder = feeds.requireData.where((final feed) => feed.folderId == folder.id);
final feedCount = feedsInFolder.length;
final unreadCount = feedsInFolder.fold(0, (final a, final b) => a + b.unreadCount!);
return (folder, feedCount, unreadCount);
}).toList(),
}).toList()
: null,
builder: (final context, final sorted) => NeonListView<FolderFeedsWrapper>(
scrollKey: 'news-folders',
withFloatingActionButton: true,

4
packages/neon/neon_notes/lib/dialogs/create_note.dart

@ -59,9 +59,9 @@ class _NotesCreateNoteDialogState extends State<NotesCreateNoteDialog> {
visible: notes.isLoading,
),
),
if (notes.data != null) ...[
if (notes.hasData) ...[
NotesCategorySelect(
categories: notes.data!.map((final note) => note.category).toSet().toList(),
categories: notes.requireData.map((final note) => note.category).toSet().toList(),
onChanged: (final category) {
selectedCategory = category;
},

4
packages/neon/neon_notes/lib/dialogs/select_category.dart

@ -47,9 +47,9 @@ class _NotesSelectCategoryDialogState extends State<NotesSelectCategoryDialog> {
visible: notes.isLoading,
),
),
if (notes.data != null) ...[
if (notes.hasData) ...[
NotesCategorySelect(
categories: notes.data!.map((final note) => note.category).toSet().toList(),
categories: notes.requireData.map((final note) => note.category).toSet().toList(),
initialValue: widget.initialCategory,
onChanged: (final category) {
selectedCategory = category;

2
packages/neon/neon_notes/lib/widgets/categories_view.dart

@ -21,7 +21,7 @@ class NotesCategoriesView extends StatelessWidget {
.map(
(final category) => NoteCategory(
category,
notes.data!.where((final note) => note.category == category).length,
notes.requireData.where((final note) => note.category == category).length,
),
)
.toList(),

4
packages/neon/neon_notifications/lib/blocs/notifications.dart

@ -20,8 +20,8 @@ class NotificationsBloc extends InteractiveBloc
this._client,
) {
notifications.listen((final result) {
if (result.data != null) {
unreadCounter.add(result.data!.length);
if (result.hasData) {
unreadCounter.add(result.requireData.length);
}
});

Loading…
Cancel
Save