Skip to content

Commit

Permalink
feat: add notification
Browse files Browse the repository at this point in the history
  • Loading branch information
mrcsilverfox committed May 21, 2024
1 parent f174fa4 commit bc5d9fc
Show file tree
Hide file tree
Showing 46 changed files with 2,759 additions and 137 deletions.
2 changes: 2 additions & 0 deletions app/lib/boot/get_it.dart
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ import '../db/isar_service.dart';
void initializeDependencies() {
GetIt.I.registerSingleton<MessageHelper>(MessageHelper());
GetIt.I.registerSingleton<IsarService>(IsarServiceImpl());
// TODO: move inside specific environment dependencies. We shoulb be pass
// is is prod or test
GetIt.I.registerSingleton<ProductsApiClient>(OpenFoodFactsApiClient());
GetIt.I.registerSingleton<StoragesRepository>(
StoragesRepositoryImpl(StoragesDbProvider(GetIt.I.get<IsarService>())),
Expand Down
7 changes: 6 additions & 1 deletion app/lib/db/isar_service.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import 'dart:io';

import 'package:a2f_sdk/a2f_sdk.dart';
import 'package:items_repository/items_repository.dart';
import 'package:notifications_repository/notifications_repository.dart';
import 'package:path/path.dart' as path;
import 'package:storages_repository/storages_repository.dart';
import 'package:uuid/uuid.dart';
Expand Down Expand Up @@ -58,7 +59,11 @@ class IsarServiceImpl implements IsarService {
!File(path.join(dir.path, '$dbName$ext')).existsSync();

final isar = await Isar.open(
[StorageDbModelSchema, ItemIsarModelSchema],
[
StorageDbModelSchema,
ItemIsarModelSchema,
NotificationIsarModelSchema,
],
name: 'db',
directory: dir.path,
);
Expand Down
1 change: 0 additions & 1 deletion app/lib/features/inventory/view/widgets/item_tile.dart
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ import 'package:a2f_sdk/a2f_sdk.dart';
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:items_repository/items_repository.dart';
import 'package:products_repository/products_repository.dart';

import '../../../../l10n/l10n.dart';
import '../../../../router/app_route.dart';
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@ import 'dart:async';
import 'package:a2f_sdk/a2f_sdk.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:items_repository/items_repository.dart';
import 'package:storages_repository/storages_repository.dart';

import '../../features.dart';

Expand Down
1 change: 0 additions & 1 deletion app/lib/features/item/cubit/item_cubit.dart
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@ import 'dart:async';
import 'package:a2f_sdk/a2f_sdk.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:items_repository/items_repository.dart';
import 'package:storages_repository/storages_repository.dart';

part 'item_state.dart';

Expand Down
1 change: 1 addition & 0 deletions app/pubspec.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ dependencies:
intl: ^0.18.0
items_repository: { path: ../packages/items_repository }
mobile_scanner: ^3.5.1
notifications_repository: { path: ../packages/notifications_repository }
path: ^1.8.3
products_repository: { path: ../packages/products_repository }
shimmer: ^3.0.0
Expand Down
4 changes: 3 additions & 1 deletion app/pubspec_overrides.yaml
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
# melos_managed_dependency_overrides: products_repository,storages_repository,items_repository,a2f_sdk
# melos_managed_dependency_overrides: products_repository,storages_repository,items_repository,a2f_sdk,notifications_repository
dependency_overrides:
a2f_sdk:
path: ../packages/a2f_sdk
items_repository:
path: ../packages/items_repository
notifications_repository:
path: ../packages/notifications_repository
products_repository:
path: ../packages/products_repository
storages_repository:
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import 'package:a2f_sdk/a2f_sdk.dart';
import 'package:products_repository/products_repository.dart';
import 'package:storages_repository/storages_repository.dart';

import '../../../items_repository.dart';
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import 'package:a2f_sdk/a2f_sdk.dart';
import 'package:products_repository/products_repository.dart';
import 'package:storages_repository/storages_repository.dart';

import '../../../items_repository.dart';
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import 'package:a2f_sdk/a2f_sdk.dart';
import 'package:get_it/get_it.dart';
import 'package:products_repository/products_repository.dart';
import 'package:storages_repository/storages_repository.dart';
Expand Down
44 changes: 44 additions & 0 deletions packages/notifications_repository/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
# Miscellaneous
*.class
*.log
*.pyc
*.swp
.DS_Store
.atom/
.buildlog/
.history
.svn/
migrate_working_dir/

# IntelliJ related
*.iml
*.ipr
*.iws
.idea/

# VSCode related
.vscode/*

# Flutter/Dart/Pub related
**/doc/api/
**/ios/Flutter/.last_build_id
.dart_tool/
.flutter-plugins
.flutter-plugins-dependencies
.packages
.pub-cache/
.pub/
/build/
pubspec.lock

# Web related
lib/generated_plugin_registrant.dart

# Symbolication related
app.*.symbols

# Obfuscation related
app.*.map.json

# Test related
coverage
67 changes: 67 additions & 0 deletions packages/notifications_repository/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
# Notifications Repository

[![style: very good analysis][very_good_analysis_badge]][very_good_analysis_link]
[![Powered by Mason](https://img.shields.io/endpoint?url=https%3A%2F%2Ftinyurl.com%2Fmason-badge)](https://github.com/felangel/mason)
[![License: MIT][license_badge]][license_link]

The notifications package

## Installation 💻

**❗ In order to start using Notifications Repository you must have the [Flutter SDK][flutter_install_link] installed on your machine.**

Install via `flutter pub add`:

```sh
dart pub add notifications_repository
```

---

## Continuous Integration 🤖

Notifications Repository comes with a built-in [GitHub Actions workflow][github_actions_link] powered by [Very Good Workflows][very_good_workflows_link] but you can also add your preferred CI/CD solution.

Out of the box, on each pull request and push, the CI `formats`, `lints`, and `tests` the code. This ensures the code remains consistent and behaves correctly as you add functionality or make changes. The project uses [Very Good Analysis][very_good_analysis_link] for a strict set of analysis options used by our team. Code coverage is enforced using the [Very Good Workflows][very_good_coverage_link].

---

## Running Tests 🧪

For first time users, install the [very_good_cli][very_good_cli_link]:

```sh
dart pub global activate very_good_cli
```

To run all unit tests:

```sh
very_good test --coverage
```

To view the generated coverage report you can use [lcov](https://github.com/linux-test-project/lcov).

```sh
# Generate Coverage Report
genhtml coverage/lcov.info -o coverage/

# Open Coverage Report
open coverage/index.html
```

[flutter_install_link]: https://docs.flutter.dev/get-started/install
[github_actions_link]: https://docs.github.com/en/actions/learn-github-actions
[license_badge]: https://img.shields.io/badge/license-MIT-blue.svg
[license_link]: https://opensource.org/licenses/MIT
[logo_black]: https://raw.githubusercontent.com/VGVentures/very_good_brand/main/styles/README/vgv_logo_black.png#gh-light-mode-only
[logo_white]: https://raw.githubusercontent.com/VGVentures/very_good_brand/main/styles/README/vgv_logo_white.png#gh-dark-mode-only
[mason_link]: https://github.com/felangel/mason
[very_good_analysis_badge]: https://img.shields.io/badge/style-very_good_analysis-B22C89.svg
[very_good_analysis_link]: https://pub.dev/packages/very_good_analysis
[very_good_cli_link]: https://pub.dev/packages/very_good_cli
[very_good_coverage_link]: https://github.com/marketplace/actions/very-good-coverage
[very_good_ventures_link]: https://verygood.ventures
[very_good_ventures_link_light]: https://verygood.ventures#gh-light-mode-only
[very_good_ventures_link_dark]: https://verygood.ventures#gh-dark-mode-only
[very_good_workflows_link]: https://github.com/VeryGoodOpenSource/very_good_workflows
20 changes: 20 additions & 0 deletions packages/notifications_repository/coverage_badge.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
/// The notifications package
library notifications_repository;

export 'src/notifications_repository.dart';
3 changes: 3 additions & 0 deletions packages/notifications_repository/lib/src/data/data.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export 'data_source/data_source.dart';
export 'models/models.dart';
export 'repository/notifications_repository_impl.dart';
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
export 'notifications_db_provider.dart';
export 'notifications_provider.dart';
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
import 'package:a2f_sdk/a2f_sdk.dart';

import '../../../notifications_repository.dart';

class NotificationsDbProvider implements NotificationsProvider {
const NotificationsDbProvider(this._dbService);

final IsarService _dbService;

@override
Future<NotificationModel> add(NotificationInput input) async {
final isar = await _dbService.db;
final createdAt = DateTime.now();

final notification = NotificationIsarModel()
..type = input.type
..createdAt = createdAt //.toUtc()
..scheduledAt = input.scheduledAt //.toUtc()
..intVal = input.intVal
..stringVal = input.stringVal
..boolVal = input.boolVal
..dateTimeVal = input.dateTimeVal
..location = input.location.name
..uuid = null
..readAt = null;

final id = await isar.writeTxn(
() async => isar.notificationIsarModels.put(notification),
);

final data =
await isar.notificationIsarModels.where().idEqualTo(id).findFirst();

return NotificationModel.fromData(data!);
}

@override
Future<List<NotificationModel>> fetch() async {
final isar = await _dbService.db;
final items = await isar.notificationIsarModels
.where()
.sortByScheduledAtDesc()
.findAll();
return items.map(NotificationModel.fromData).toList();
}

@override
Future<NotificationModel> read(int id) async {
final isar = await _dbService.db;

return isar.writeTxn(() async {
final notification =
await isar.notificationIsarModels.where().idEqualTo(id).findFirst();

if (notification == null) {
throw AssertionError('Notification must exist');
}

final updated = notification.copyWith(readAt: DateTime.now());
await isar.notificationIsarModels.put(updated);

return NotificationModel.fromData(updated);
});
}

@override
Future<bool> exists({
int? id,
NotificationType? type,
DateTime? scheduledAt,
}) async {
if (id == null && type == null && scheduledAt == null) {
throw AssertionError('At least one parameter must be provided.');
}
final isar = await _dbService.db;
if (id != null) {
final count =
await isar.notificationIsarModels.where().idEqualTo(id!).count();
return count > 0;
}
assert(type != null && scheduledAt != null, '');
final date = scheduledAt!;
final dateStart = DateTime.utc(date.year, date.month, date.day, 0, 0, 0);
final dateEnd = DateTime.utc(date.year, date.month, date.day, 23, 59, 59);
final count = await isar.notificationIsarModels
.filter()
.typeEqualTo(type!)
.and()
.scheduledAtBetween(dateStart, dateEnd)
.count();
return count > 0;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import '../../../notifications_repository.dart';

/// This provider return [NotificationEntity] object because does not exist a
/// concrete implementation of model that extends [NotificationEntity].
abstract class NotificationsProvider {
Future<NotificationModel> add(NotificationInput input);

Future<List<NotificationModel>> fetch();

Future<NotificationModel> read(int id);

Future<bool> exists({
int? id,
NotificationType? type,
DateTime? scheduledAt,
});
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
export 'notification_isar_model.dart';
export 'notification_model.dart';
Loading

0 comments on commit bc5d9fc

Please sign in to comment.