Skip to content

Commit

Permalink
Internal refactoring (rrousselGit#813)
Browse files Browse the repository at this point in the history
  • Loading branch information
rrousselGit authored Oct 18, 2021
1 parent f410a75 commit eb40ee8
Show file tree
Hide file tree
Showing 7 changed files with 366 additions and 346 deletions.
6 changes: 5 additions & 1 deletion packages/riverpod/lib/src/framework.dart
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,12 @@ import 'package:meta/meta.dart';
import 'provider.dart';
import 'value_provider.dart';

part 'framework/always_alive.dart';
part 'framework/auto_dispose.dart';
part 'framework/base_provider.dart';
part 'framework/provider_base.dart';
part 'framework/container.dart';
part 'framework/family.dart';
part 'framework/foundation.dart';
part 'framework/ref.dart';
part 'framework/selector.dart';
part 'framework/scheduler.dart';
36 changes: 36 additions & 0 deletions packages/riverpod/lib/src/framework/always_alive.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
part of '../framework.dart';

/// A base class for all providers, used to consume a provider.
///
/// It is used by [ProviderContainer.listen] and `ref.watch` to listen to
/// both a provider and `provider.select`.
///
/// Do not implement or extend.
mixin AlwaysAliveProviderListenable<State>
implements ProviderListenable<State> {}

/// A base class for providers that never disposes themselves.
///
/// This is the default base class for providers, unless a provider was marked
/// with the `.autoDispose` modifier, like: `Provider.autoDispose(...)`
abstract class AlwaysAliveProviderBase<State> extends ProviderBase<State>
implements AlwaysAliveProviderListenable<State> {
/// Creates an [AlwaysAliveProviderBase].
AlwaysAliveProviderBase({required String? name}) : super(name: name);

@override
ProviderElementBase<State> createElement();

@override
AlwaysAliveProviderListenable<Selected> select<Selected>(
Selected Function(State value) selector,
) {
return _AlwaysAliveProviderSelector<State, Selected>(
provider: this,
selector: selector,
);
}
}

class _AlwaysAliveProviderSelector<Input, Output> = _ProviderSelector<Input,
Output> with AlwaysAliveProviderListenable<Output>;
1 change: 1 addition & 0 deletions packages/riverpod/lib/src/framework/auto_dispose.dart
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ abstract class AutoDisposeRef extends Ref {
///
/// Defaults to `false`.
bool get maintainState;
// TODO deprecate in favour of "keepAlive().cancel()"
set maintainState(bool value);

@override
Expand Down
69 changes: 69 additions & 0 deletions packages/riverpod/lib/src/framework/foundation.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
part of '../framework.dart';

/// A common interface shared by [ProviderBase] and [Family]
@sealed
abstract class ProviderOrFamily {
/// The list of providers that this provider potentially depends on.
///
/// Specifying this list will tell Riverpod to automatically scope this provider
/// if one of its dependency is overridden.
/// The downside is that it prevents `ref.watch` & co to be used with a provider
/// that isn't listed in [dependencies].
List<ProviderOrFamily>? get dependencies;

/// All the dependencies of a provider and their dependencies too.
late final allTransitiveDependencies =
dependencies == null ? null : _allTransitiveDependencies(dependencies!);
}

List<ProviderOrFamily> _allTransitiveDependencies(
List<ProviderOrFamily> dependencies) {
final result = <ProviderOrFamily>{};

void visitDependency(ProviderOrFamily dep) {
if (result.add(dep) && dep.dependencies != null) {
dep.dependencies!.forEach(visitDependency);
}
}

dependencies.forEach(visitDependency);

return List.unmodifiable(result);
}

// Copied from Flutter
/// Returns a summary of the runtime type and hash code of `object`.
///
/// See also:
///
/// * [Object.hashCode], a value used when placing an object in a [Map] or
/// other similar data structure, and which is also used in debug output to
/// distinguish instances of the same class (hash collisions are
/// possible, but rare enough that its use in debug output is useful).
/// * [Object.runtimeType], the [Type] of an object.
String describeIdentity(Object? object) {
return '${object.runtimeType}#${shortHash(object)}';
}

// Copied from Flutter
/// [Object.hashCode]'s 20 least-significant bits.
String shortHash(Object? object) {
return object.hashCode.toUnsigned(20).toRadixString(16).padLeft(5, '0');
}

/// A base class for all providers, used to consume a provider.
///
/// It is used by [ProviderContainer.listen] and `ref.watch` to listen to
/// both a provider and `provider.select`.
///
/// Do not implement or extend.
abstract class ProviderListenable<State> {}

/// Represents the subscription to a provider
abstract class ProviderSubscription<State> {
/// Stops listening to the provider
void close();

/// Obtain the latest value emitted by the provider
State read();
}
Loading

0 comments on commit eb40ee8

Please sign in to comment.