Skip to content

Commit 93a9289

Browse files
migrates geolocator_web to package:web (#1475)
* migrates geolocator_web to package:web * fix: depends on geolocator web 4.0 * Apply suggestions from code review Co-authored-by: Maurits van Beusekom <[email protected]> * fix: returns a known exception from getCurrentPosition * style: formatting * fix: uses PositionUpdateException rather than PlatformException * fix: remove unused import, fix deprecation warning when using background color --------- Co-authored-by: Maurits van Beusekom <[email protected]>
1 parent ca5469f commit 93a9289

File tree

10 files changed

+102
-98
lines changed

10 files changed

+102
-98
lines changed

geolocator/CHANGELOG.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,7 @@
1+
## 12.0.0
2+
3+
- **BREAKING CHANGE:** Updates dependency on geolocator_web to version [4.0.0](https://pub.dev/packages/geolocator_web/changelog).
4+
15
## 11.1.0
26

37
- Expose `AndroidPosition` from geolocator.

geolocator/example/lib/main.dart

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -118,7 +118,7 @@ class _GeolocatorWidgetState extends State<GeolocatorWidget> {
118118
ExamplePage(
119119
Icons.location_on,
120120
(context) => Scaffold(
121-
backgroundColor: Theme.of(context).colorScheme.background,
121+
backgroundColor: Theme.of(context).colorScheme.surface,
122122
body: ListView.builder(
123123
itemCount: _positionItems.length,
124124
itemBuilder: (context, index) {

geolocator/pubspec.yaml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ name: geolocator
22
description: Geolocation plugin for Flutter. This plugin provides a cross-platform (iOS, Android) API for generic location (GPS etc.) functions.
33
repository: https://github.com/baseflow/flutter-geolocator/tree/main/geolocator
44
issue_tracker: https://github.com/baseflow/flutter-geolocator/issues?q=is%3Aissue+is%3Aopen
5-
version: 11.1.0
5+
version: 12.0.0
66

77
environment:
88
sdk: ">=2.15.0 <4.0.0"
@@ -29,7 +29,7 @@ dependencies:
2929
geolocator_platform_interface: ^4.1.0
3030
geolocator_android: ^4.3.0
3131
geolocator_apple: ^2.3.0
32-
geolocator_web: ^3.0.0
32+
geolocator_web: ^4.0.0
3333
geolocator_windows: ^0.2.2
3434

3535
dev_dependencies:

geolocator_web/CHANGELOG.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,9 @@
1+
## 4.0.0
2+
3+
**BREAKING CHANGE:**
4+
- Migrates from dart:html to package:web and dart:js_interop
5+
- Migrates to Dart SDK 3.3.0 and Flutter 3.16.0.
6+
17
## 3.0.0
28

39
**BREAKING CHANGE:**
Lines changed: 49 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,46 +1,78 @@
1-
import 'dart:html' as html;
1+
import 'dart:async';
2+
import 'dart:js_interop';
23

34
import 'package:geolocator_platform_interface/geolocator_platform_interface.dart';
5+
import 'package:web/web.dart' as web;
46

57
import 'geolocation_manager.dart';
68
import 'utils.dart';
79

810
/// Implementation of the [GeolocationManager] interface based on the
911
/// [html.Geolocation] class.
1012
class HtmlGeolocationManager implements GeolocationManager {
11-
final html.Geolocation _geolocation;
13+
final web.Geolocation _geolocation;
1214

1315
/// Creates a new instance of the [HtmlGeolocationManager] class.
14-
HtmlGeolocationManager() : _geolocation = html.window.navigator.geolocation;
16+
HtmlGeolocationManager() : _geolocation = web.window.navigator.geolocation;
1517

1618
@override
1719
Future<Position> getCurrentPosition({
1820
bool? enableHighAccuracy,
1921
Duration? timeout,
2022
}) async {
23+
Completer<Position> completer = Completer();
2124
try {
22-
final geoPosition = await _geolocation.getCurrentPosition(
23-
enableHighAccuracy: enableHighAccuracy,
24-
timeout: timeout,
25+
_geolocation.getCurrentPosition(
26+
(web.GeolocationPosition position) {
27+
completer.complete(toPosition(position));
28+
}.toJS,
29+
(web.GeolocationPositionError error) {
30+
completer.completeError(convertPositionError(error));
31+
}.toJS,
32+
web.PositionOptions(
33+
enableHighAccuracy: enableHighAccuracy ?? false,
34+
timeout:
35+
timeout?.inMicroseconds ?? const Duration(days: 1).inMilliseconds,
36+
),
2537
);
26-
27-
return toPosition(geoPosition);
28-
} on html.PositionError catch (e) {
29-
throw convertPositionError(e);
38+
} catch (e) {
39+
completer.completeError(const PositionUpdateException(
40+
"Something went wrong while getting current position"));
3041
}
42+
43+
return completer.future;
3144
}
3245

3346
@override
3447
Stream<Position> watchPosition({
3548
bool? enableHighAccuracy,
3649
Duration? timeout,
3750
}) {
38-
return _geolocation
39-
.watchPosition(
40-
enableHighAccuracy: enableHighAccuracy,
41-
timeout: timeout,
42-
)
43-
.handleError((error) => throw convertPositionError(error))
44-
.map((geoPosition) => toPosition(geoPosition));
51+
int? watchId;
52+
StreamController<Position> controller = StreamController<Position>(
53+
sync: true,
54+
onCancel: () {
55+
assert(watchId != null);
56+
_geolocation.clearWatch(watchId!);
57+
});
58+
59+
controller.onListen = () {
60+
assert(watchId == null);
61+
watchId = _geolocation.watchPosition(
62+
(web.GeolocationPosition position) {
63+
controller.add(toPosition(position));
64+
}.toJS,
65+
(web.GeolocationPositionError error) {
66+
controller.addError(convertPositionError(error));
67+
}.toJS,
68+
web.PositionOptions(
69+
enableHighAccuracy: enableHighAccuracy ?? false,
70+
timeout:
71+
timeout?.inMicroseconds ?? const Duration(days: 1).inMilliseconds,
72+
),
73+
);
74+
};
75+
76+
return controller.stream;
4577
}
4678
}

geolocator_web/lib/src/html_permissions_manager.dart

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,17 @@
1-
import 'dart:html' as html;
2-
31
import 'package:geolocator_platform_interface/geolocator_platform_interface.dart';
4-
2+
import 'package:web/web.dart' as web;
3+
import 'dart:js_interop';
54
import 'permissions_manager.dart';
65
import 'utils.dart';
76

87
/// Implementation of the [GeolocationManager] interface based on the
98
/// [html.Permissions] class.
109
class HtmlPermissionsManager implements PermissionsManager {
1110
static const _permissionQuery = {'name': 'geolocation'};
12-
final html.Permissions? _permissions;
11+
final web.Permissions? _permissions;
1312

1413
/// Creates a new instance of the HtmlPermissionsManager class.
15-
HtmlPermissionsManager() : _permissions = html.window.navigator.permissions;
14+
HtmlPermissionsManager() : _permissions = web.window.navigator.permissions;
1615

1716
@override
1817
bool get permissionsSupported => _permissions != null;
@@ -23,11 +22,11 @@ class HtmlPermissionsManager implements PermissionsManager {
2322
return LocationPermission.unableToDetermine;
2423
}
2524

26-
final html.PermissionStatus status = await _permissions!.query(
27-
_permissionQuery,
28-
);
25+
// navigator.permissions.query({ name: "geolocation" })
26+
final web.PermissionStatus? status =
27+
await _permissions?.query(_permissionQuery.jsify() as JSObject).toDart;
2928

30-
return status.state != null
29+
return status != null
3130
? toLocationPermission(status.state)
3231
: LocationPermission.denied;
3332
}

geolocator_web/lib/src/utils.dart

Lines changed: 4 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,22 +1,16 @@
11
import 'dart:async';
2-
import 'dart:html' as html;
2+
import 'package:web/web.dart' as web;
33
import 'package:flutter/services.dart';
44
import 'package:geolocator_platform_interface/geolocator_platform_interface.dart';
55

66
/// Converts the Geoposition object into a [Position] object.
7-
Position toPosition(html.Geoposition webPosition) {
7+
Position toPosition(web.GeolocationPosition webPosition) {
88
final coords = webPosition.coords;
99

10-
if (coords == null) {
11-
throw const PositionUpdateException('Received invalid position result.');
12-
}
13-
1410
return Position(
1511
latitude: coords.latitude as double,
1612
longitude: coords.longitude as double,
17-
timestamp: webPosition.timestamp != null
18-
? DateTime.fromMillisecondsSinceEpoch(webPosition.timestamp!)
19-
: DateTime.now(),
13+
timestamp: DateTime.fromMillisecondsSinceEpoch(webPosition.timestamp),
2014
altitude: coords.altitude as double? ?? 0.0,
2115
altitudeAccuracy: coords.altitudeAccuracy as double? ?? 0.0,
2216
accuracy: coords.accuracy as double? ?? 0.0,
@@ -47,7 +41,7 @@ LocationPermission toLocationPermission(String? webPermission) {
4741

4842
/// Converts an error received from the browser into a custom Geolocator
4943
/// exception.
50-
Exception convertPositionError(html.PositionError error) {
44+
Exception convertPositionError(web.GeolocationPositionError error) {
5145
switch (error.code) {
5246
case 1:
5347
return PermissionDeniedException(error.message);

geolocator_web/pubspec.yaml

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ name: geolocator_web
22
description: Official web implementation of the geolocator plugin.
33
repository: https://github.com/baseflow/flutter-geolocator/tree/main/geolocator_web
44
issue_tracker: https://github.com/baseflow/flutter-geolocator/issues?q=is%3Aissue+is%3Aopen
5-
version: 3.0.0
5+
version: 4.0.0
66

77
flutter:
88
plugin:
@@ -17,7 +17,8 @@ dependencies:
1717
sdk: flutter
1818
flutter_web_plugins:
1919
sdk: flutter
20-
geolocator_platform_interface: ^4.1.0
20+
geolocator_platform_interface: ^4.2.2
21+
web: ^0.5.1
2122

2223
dev_dependencies:
2324
build_runner: ^2.4.8
@@ -28,5 +29,5 @@ dev_dependencies:
2829

2930

3031
environment:
31-
sdk: '>=2.15.0 <4.0.0'
32-
flutter: ">=2.8.0"
32+
sdk: '>=3.3.0 <4.0.0'
33+
flutter: ">=3.16.0"
Lines changed: 23 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1,28 +1,26 @@
1+
@TestOn('browser')
2+
library;
3+
14
import 'dart:async';
2-
import 'dart:html';
5+
import 'dart:js_interop';
36

47
import 'package:flutter/services.dart';
58
import 'package:flutter_test/flutter_test.dart';
6-
import 'package:mockito/annotations.dart';
7-
import 'package:mockito/mockito.dart';
89
import 'package:geolocator_platform_interface/geolocator_platform_interface.dart';
910
import 'package:geolocator_web/src/utils.dart';
11+
import 'package:web/web.dart' as web;
1012

11-
import 'geolocator_utils_test.mocks.dart';
13+
@JSExport()
14+
class MockGeolocationPositionError {
15+
final int code;
16+
final String message;
1217

13-
@GenerateNiceMocks([
14-
MockSpec<Geoposition>(),
15-
MockSpec<PositionError>(),
16-
])
17-
void main() {
18-
test('toPosition should throw a exception if coords is null', () {
19-
final geoposition = MockGeoposition();
20-
when(geoposition.coords).thenReturn(null);
18+
MockGeolocationPositionError({required this.code, required this.message});
19+
}
2120

22-
expect(
23-
() => toPosition(geoposition), throwsA(isA<PositionUpdateException>()));
24-
});
21+
typedef GeolocationPosition = web.GeolocationPosition;
2522

23+
void main() {
2624
test('toLocationPermission returns the correct LocationPermission', () {
2725
expect(toLocationPermission('granted'), LocationPermission.whileInUse);
2826
expect(toLocationPermission('prompt'), LocationPermission.denied);
@@ -31,19 +29,20 @@ void main() {
3129
});
3230

3331
test('convertPositionError returns the correct exception', () {
34-
final positionError = MockPositionError();
32+
web.GeolocationPositionError createError(int code) {
33+
return createJSInteropWrapper<MockGeolocationPositionError>(
34+
MockGeolocationPositionError(code: code, message: 'message'))
35+
as web.GeolocationPositionError;
36+
}
3537

36-
when(positionError.code).thenReturn(1);
3738
expect(
38-
convertPositionError(positionError), isA<PermissionDeniedException>());
39+
convertPositionError(createError(1)), isA<PermissionDeniedException>());
3940

40-
when(positionError.code).thenReturn(2);
41-
expect(convertPositionError(positionError), isA<PositionUpdateException>());
41+
expect(
42+
convertPositionError(createError(2)), isA<PositionUpdateException>());
4243

43-
when(positionError.code).thenReturn(3);
44-
expect(convertPositionError(positionError), isA<TimeoutException>());
44+
expect(convertPositionError(createError(3)), isA<TimeoutException>());
4545

46-
when(positionError.code).thenReturn(4);
47-
expect(convertPositionError(positionError), isA<PlatformException>());
46+
expect(convertPositionError(createError(4)), isA<PlatformException>());
4847
});
4948
}

geolocator_web/test/geolocator_utils_test.mocks.dart

Lines changed: 0 additions & 31 deletions
This file was deleted.

0 commit comments

Comments
 (0)