Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
86 commits
Select commit Hold shift + click to select a range
9a98dce
Add shared preferences devtools
adsonpleal May 21, 2024
f6a1ce9
Add docs
adsonpleal May 21, 2024
b9c0b6b
change version constraint
adsonpleal May 21, 2024
e2f1478
update readme
adsonpleal May 21, 2024
b798091
pr requested changes
adsonpleal May 21, 2024
0115bea
fix broken test
adsonpleal May 21, 2024
421d981
remove icons from manifest
adsonpleal May 22, 2024
bf23f70
Use InheritedModel to avoid unnecessary rebuilds
adsonpleal May 23, 2024
2402e78
change search bar
adsonpleal May 23, 2024
215d551
PR requested changes
adsonpleal May 24, 2024
18ac82b
Fix wrong change
adsonpleal May 24, 2024
16f30fc
add TestOn annotations
adsonpleal May 24, 2024
c14409e
lint fix and update dependencies
adsonpleal May 24, 2024
382f612
revert vm_service version change
adsonpleal May 24, 2024
aba50c5
fix licenses
adsonpleal May 24, 2024
a118924
solve some CI checks
adsonpleal May 27, 2024
0604550
Add web unavailable message
adsonpleal May 28, 2024
eb6dc64
Add codeowners and allowed unpinned deps
adsonpleal May 28, 2024
c9dab29
PR requested changes
adsonpleal May 28, 2024
1627ec8
update codeowners
adsonpleal May 28, 2024
c7c3eb5
fix typo
adsonpleal May 28, 2024
bb58727
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal May 28, 2024
ee1d2f4
Remove chared preferences changes and change codeowners
adsonpleal Jun 18, 2024
01d7f5c
Remove asyncEval call
adsonpleal Jun 18, 2024
39b3990
remove commented code
adsonpleal Jun 18, 2024
00e568c
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Jun 18, 2024
21202e6
pr requested changes
adsonpleal Jun 18, 2024
e489086
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Jun 20, 2024
c32457f
Merge branch 'main' into add-shared-preferences-devtools
stuartmorgan-g Jun 21, 2024
c6c8068
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Jun 24, 2024
c4be218
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Jul 29, 2024
862938b
Add pre_publish.dart and extension config.yaml to shared_preferences
adsonpleal Jul 29, 2024
84c6103
fix changelog and license validations
adsonpleal Jul 29, 2024
866ef50
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Jul 31, 2024
7b1a151
Support new API and update changelog
adsonpleal Aug 1, 2024
bffbe95
also update the version in pubspec
adsonpleal Aug 1, 2024
d8af525
Merge remote-tracking branch 'origin/main' into add-shared-preference…
adsonpleal Aug 1, 2024
26f186b
revert changes to pubspec
adsonpleal Aug 1, 2024
8b005d9
add empty line back to pubspec
adsonpleal Aug 1, 2024
2dc2a33
update minor version
adsonpleal Aug 1, 2024
5b7cbbf
Fix android support
adsonpleal Aug 2, 2024
c497026
Add api switcher
adsonpleal Aug 2, 2024
bc887de
add missing license
adsonpleal Aug 2, 2024
ffd64a9
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Aug 5, 2024
e95d285
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Aug 5, 2024
ed56a14
resolve conflicts
adsonpleal Aug 8, 2024
8936da6
Merge branch 'add-shared-preferences-devtools' of github.com:adsonple…
adsonpleal Aug 8, 2024
966d0fc
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Aug 9, 2024
3267c1b
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Aug 12, 2024
1acebd4
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Aug 12, 2024
3846f73
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Aug 15, 2024
6eb1b4f
Merge remote-tracking branch 'origin/main' into add-shared-preference…
adsonpleal Aug 15, 2024
d3fea9e
Merge branch 'flutter:main' into add-shared-preferences-devtools
adsonpleal Sep 2, 2024
af0dfca
Add devtool_eval_test to shared_preferences
adsonpleal Sep 2, 2024
107fc82
apply requested changes to devtools_eval_test
adsonpleal Sep 5, 2024
4b2f619
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Sep 5, 2024
6abec8a
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Sep 30, 2024
a45bc1c
Add license header to devtools_eval_test
adsonpleal Sep 30, 2024
c1a9c85
Update libraries
adsonpleal Sep 30, 2024
612e118
Merge branch 'add-shared-preferences-devtools' of github.com:adsonple…
adsonpleal Sep 30, 2024
ea80fce
remove error holder
adsonpleal Sep 30, 2024
1ef04f6
remove error holder
adsonpleal Sep 30, 2024
4df0393
replace text with circular progress indicator
adsonpleal Oct 1, 2024
2f8e7ea
fix broken test
adsonpleal Oct 1, 2024
b77893c
Apply suggested changes
adsonpleal Oct 7, 2024
7a3ec34
Merge remote-tracking branch 'origin/main' into add-shared-preference…
adsonpleal Nov 6, 2024
e9b913c
add devtools_extension.dart file
adsonpleal Nov 7, 2024
8362269
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Nov 7, 2024
119df62
update pre_publish.dart
adsonpleal Nov 7, 2024
38954ba
pin vm service version
adsonpleal Nov 8, 2024
e3c39f2
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Nov 8, 2024
9f7cdd4
Fix mockito generated code
adsonpleal Nov 8, 2024
026b225
Merge branch 'add-shared-preferences-devtools' of github.com:adsonple…
adsonpleal Nov 8, 2024
659b9cd
Change vm_service version
adsonpleal Nov 8, 2024
7bd20c1
Merge remote-tracking branch 'origin/main' into add-shared-preference…
adsonpleal Nov 11, 2024
d672329
add missing license
adsonpleal Nov 11, 2024
e6da5b8
add path as a dev_dependency
adsonpleal Nov 11, 2024
3c5cecd
change path version
adsonpleal Nov 11, 2024
c761404
requested changes
adsonpleal Nov 12, 2024
2b7d31f
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Nov 12, 2024
c80795a
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Nov 22, 2024
bb0b9be
rename lib/src/shared_preferences_dev_tools_extension_data.dart to li…
adsonpleal Nov 22, 2024
4f6e93b
Merge branch 'add-shared-preferences-devtools' of github.com:adsonple…
adsonpleal Nov 22, 2024
4f2d2fd
rename test file
adsonpleal Nov 22, 2024
9838731
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Nov 27, 2024
a783959
Merge branch 'main' into add-shared-preferences-devtools
adsonpleal Nov 28, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Fix android support
  • Loading branch information
adsonpleal committed Aug 2, 2024
commit 5b7cbbf7adcd10eef0afbf605a9eb20431187c61
Original file line number Diff line number Diff line change
Expand Up @@ -14,13 +14,17 @@ import 'async_state.dart';
class SharedPreferencesState {
/// Default constructor for [SharedPreferencesState].
const SharedPreferencesState({
this.allKeys = const <String>[],
this.asyncKeys = const <String>[],
this.legacyKeys = const <String>[],
this.selectedKey,
this.editing = false,
});

/// A list of all keys in the shared preferences of the target debug session.
final List<String> allKeys;
/// A list of all keys in the shared preferences of the target debug session using the async API.
final List<String> asyncKeys;

/// A list of all keys in the shared preferences of the target debug session using the legacy API.
final List<String> legacyKeys;

/// The user selected key and its value in the shared preferences
/// of the target debug session.
Expand All @@ -32,12 +36,14 @@ class SharedPreferencesState {
/// Creates a copy of this [SharedPreferencesState] but replacing the given
/// fields with the new values.
SharedPreferencesState copyWith({
List<String>? allKeys,
List<String>? asyncKeys,
List<String>? legacyKeys,
SelectedSharedPreferencesKey? selectedKey,
bool? editing,
}) {
return SharedPreferencesState(
allKeys: allKeys ?? this.allKeys,
asyncKeys: asyncKeys ?? this.asyncKeys,
legacyKeys: legacyKeys ?? this.legacyKeys,
selectedKey: selectedKey ?? this.selectedKey,
editing: editing ?? this.editing,
);
Expand All @@ -47,18 +53,23 @@ class SharedPreferencesState {
bool operator ==(Object other) {
return identical(this, other) ||
(other is SharedPreferencesState &&
listEquals(other.allKeys, allKeys) &&
listEquals(other.asyncKeys, asyncKeys) &&
listEquals(other.legacyKeys, legacyKeys) &&
other.selectedKey == selectedKey &&
other.editing == editing);
}

@override
int get hashCode =>
allKeys.hashCode ^ selectedKey.hashCode ^ editing.hashCode;
int get hashCode => Object.hash(
asyncKeys,
legacyKeys,
selectedKey,
editing,
);

@override
String toString() {
return 'SharedPreferencesState(allKeys: $allKeys, selectedKey: $selectedKey, editing: $editing)';
return 'SharedPreferencesState(asyncKeys: $asyncKeys, legacyKeys: $legacyKeys, selectedKey: $selectedKey, editing: $editing)';
}
}

Expand All @@ -71,15 +82,19 @@ class SelectedSharedPreferencesKey {
const SelectedSharedPreferencesKey({
required this.key,
required this.value,
required this.legacy,
});

/// The user selected key
/// The user selected key.
final String key;

/// The value of the selected key in the shared preferences of the target
/// debug session.
final AsyncState<SharedPreferencesData> value;

/// Whether or not this is a legacy key.
final bool legacy;

@override
bool operator ==(Object other) {
return identical(this, other) ||
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,17 +21,29 @@ class SharedPreferencesStateNotifier extends ValueNotifier<_State> {

final SharedPreferencesToolEval _eval;

List<String> _keys = <String>[];
List<String> _asyncKeys = const <String>[];
List<String> _legacyKeys = const <String>[];

/// Retrieves all keys from the shared preferences of the target debug session.
///
/// If this is called when data already exists, it will update the list of keys.
Future<void> fetchAllKeys() async {
value = const _State.loading();
try {
_keys = await _eval.fetchAllKeys();
final KeysResult allKeys = await _eval.fetchAllKeys();
_legacyKeys = allKeys.legacyKeys;
// Platforms other than Android also add the legacy keys to the async keys
// in the pattern `flutter.$key`, so we need to remove them to avoid duplicates.
const String legacyPrefix = 'flutter.';
_asyncKeys = <String>[
for (final String key in allKeys.asyncKeys)
if (!(key.startsWith(legacyPrefix) &&
_legacyKeys.contains(key.replaceAll(legacyPrefix, ''))))
key,
];
value = _State.data(SharedPreferencesState(
allKeys: _keys,
asyncKeys: _asyncKeys,
legacyKeys: _legacyKeys,
));
} catch (error, stackTrace) {
value = _State.error(error, stackTrace);
Expand All @@ -41,35 +53,41 @@ class SharedPreferencesStateNotifier extends ValueNotifier<_State> {
void _setSelectedKeyValue(
String key,
AsyncState<SharedPreferencesData> asyncValue,
bool legacy,
) {
value = value.whenData(
(SharedPreferencesState data) => data.copyWith(
selectedKey: SelectedSharedPreferencesKey(
key: key,
value: asyncValue,
legacy: legacy,
),
),
);
}

/// Set the key as selected and retrieve the value from the shared preferences of the target debug session.
Future<void> selectKey(String key) async {
Future<void> selectKey(String key, bool legacy) async {
stopEditing();
_setSelectedKeyValue(
key,
const AsyncState<SharedPreferencesData>.loading(),
legacy,
);

try {
final SharedPreferencesData keyValue = await _eval.fetchValue(key);
final SharedPreferencesData keyValue =
await _eval.fetchValue(key, legacy);
_setSelectedKeyValue(
key,
AsyncState<SharedPreferencesData>.data(keyValue),
legacy,
);
} catch (error, stackTrace) {
_setSelectedKeyValue(
key,
AsyncState<SharedPreferencesData>.error(error, stackTrace),
legacy,
);
}
}
Expand All @@ -84,36 +102,47 @@ class SharedPreferencesStateNotifier extends ValueNotifier<_State> {
/// If all characters from the token are found in the key, the key is included in the result.
void filter(String token) {
final String lowercaseToken = token.toLowerCase();

bool filter(String key) {
String currentSubstring = key.toLowerCase();
for (final String char in lowercaseToken.characters) {
final int currentIndex = currentSubstring.indexOf(char);
if (currentIndex == -1) {
return false;
}
currentSubstring = currentSubstring.substring(currentIndex + 1);
}
return true;
}

value = value.whenData((SharedPreferencesState data) {
return data.copyWith(
allKeys: _keys.where(
(String key) {
String currentSubstring = key.toLowerCase();
for (final String char in lowercaseToken.characters) {
final int currentIndex = currentSubstring.indexOf(char);
if (currentIndex == -1) {
return false;
}
currentSubstring = currentSubstring.substring(currentIndex + 1);
}
return true;
},
).toList());
asyncKeys: _asyncKeys.where(filter).toList(),
legacyKeys: _legacyKeys.where(filter).toList(),
);
});
}

/// Changes the value of the selected key in the shared preferences of the target debug session.
Future<void> changeValue(String key, SharedPreferencesData newValue) async {
await _eval.changeValue(key, newValue);
await selectKey(key);
stopEditing();
Future<void> changeValue(
SharedPreferencesData newValue,
) async {
if (value.dataOrNull?.selectedKey
case final SelectedSharedPreferencesKey selectedKey) {
await _eval.changeValue(selectedKey.key, newValue, selectedKey.legacy);
await selectKey(selectedKey.key, selectedKey.legacy);
stopEditing();
}
}

/// Deletes the selected key from the shared preferences of the target debug session.
Future<void> deleteKey(String selectedKey) async {
await _eval.deleteKey(selectedKey);
await fetchAllKeys();
stopEditing();
Future<void> deleteSelectedKey() async {
if (value.dataOrNull?.selectedKey
case final SelectedSharedPreferencesKey selectedKey) {
await _eval.deleteKey(selectedKey.key, selectedKey.legacy);
await fetchAllKeys();
stopEditing();
}
}

/// Change the editing state to true, allowing the user to edit the value of the selected key.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,12 @@ import 'shared_preferences_state.dart';
import 'shared_preferences_state_notifier.dart';
import 'shared_preferences_tool_eval.dart';

/// A record that holds the string key and wether or not it is a legacy key.
typedef KeyData = ({
String key,
bool legacy,
});

/// A class that provides a [SharedPreferencesStateNotifier] to its descendants
/// without listening to state changes.
///
Expand Down Expand Up @@ -79,11 +85,14 @@ class _SharedPreferencesStateInheritedModel
}

extension on AsyncState<SharedPreferencesState> {
AsyncState<List<String>> get keysListState => mapWhenData(
(SharedPreferencesState data) => data.allKeys,
AsyncState<List<KeyData>> get keysListState => mapWhenData(
(SharedPreferencesState data) => <KeyData>[
for (final String key in data.asyncKeys) (key: key, legacy: false),
for (final String key in data.legacyKeys) (key: key, legacy: true),
],
);

String? get selectedKeyState => dataOrNull?.selectedKey?.key;
SelectedSharedPreferencesKey? get selectedKeyState => dataOrNull?.selectedKey;

AsyncState<SharedPreferencesData?> get selectedKeyDataState =>
flatMapWhenData(
Expand Down Expand Up @@ -148,13 +157,13 @@ class SharedPreferencesStateProvider extends StatefulWidget {
required this.child,
});

/// Returns the async state of the list of keys from the closest
/// Returns the async state of the list of all keys.
/// [_SharedPreferencesStateInheritedModel] ancestor.
///
/// Use of this method will cause the given [context] to rebuild whenever the
/// list of keys changes, including loading and error states.
/// This will not cause a rebuild when any other part of the state changes.
static AsyncState<List<String>> keysListStateOf(BuildContext context) {
static AsyncState<List<KeyData>> keysListStateOf(BuildContext context) {
return context
.dependOnInheritedWidgetOfExactType<
_SharedPreferencesStateInheritedModel>(
Expand All @@ -170,7 +179,7 @@ class SharedPreferencesStateProvider extends StatefulWidget {
/// Use of this method will cause the given [context] to rebuild whenever the
/// selected key changes, including loading and error states.
/// This will not cause a rebuild when any other part of the state changes.
static String? selectedKeyOf(BuildContext context) {
static SelectedSharedPreferencesKey? selectedKeyOf(BuildContext context) {
return context
.dependOnInheritedWidgetOfExactType<
_SharedPreferencesStateInheritedModel>(
Expand All @@ -184,7 +193,8 @@ class SharedPreferencesStateProvider extends StatefulWidget {
/// [_SharedPreferencesStateInheritedModel] ancestor.
///
/// Throws an error if the selected key is null.
static String requireSelectedKeyOf(BuildContext context) {
static SelectedSharedPreferencesKey requireSelectedKeyOf(
BuildContext context) {
return selectedKeyOf(context)!;
}

Expand Down Expand Up @@ -235,12 +245,21 @@ class _SharedPreferencesStateProviderState
@override
void initState() {
super.initState();
final EvalOnDartLibrary eval = EvalOnDartLibrary(
final EvalOnDartLibrary asyncEval = EvalOnDartLibrary(
'package:shared_preferences/src/shared_preferences_async.dart',
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we need to eval the exact library, evaluating a exports file throws a not found error.

serviceManager.service!,
serviceManager: serviceManager,
);
final SharedPreferencesToolEval toolEval = SharedPreferencesToolEval(eval);
final EvalOnDartLibrary legacyEval = EvalOnDartLibrary(
'package:shared_preferences/src/shared_preferences_legacy.dart',
serviceManager.service!,
serviceManager: serviceManager,
);
final SharedPreferencesToolEval toolEval = SharedPreferencesToolEval(
asyncEval,
legacyEval,
serviceManager.connectedApp?.isFlutterWebAppNow ?? false,
);
_notifier = SharedPreferencesStateNotifier(toolEval);
_notifier.fetchAllKeys();
}
Expand Down
Loading