feat(wip): Update entities and adopt a proper repository workflow for trip "obtention"

This commit is contained in:
2025-12-29 00:23:10 +01:00
parent 239b63ca81
commit 81ed2fd8c3
34 changed files with 1929 additions and 1925 deletions

View File

@@ -24,5 +24,12 @@ linter:
# avoid_print: false # Uncomment to disable the `avoid_print` rule # avoid_print: false # Uncomment to disable the `avoid_print` rule
# prefer_single_quotes: true # Uncomment to enable the `prefer_single_quotes` rule # prefer_single_quotes: true # Uncomment to enable the `prefer_single_quotes` rule
# Exclude legacy/experimental code that is not part of the current
# refactor work. This prevents the analyzer from failing on old files
# in `lib/old` while we iterate on the new architecture in `lib/`.
analyzer:
exclude:
- lib/old/**
# Additional information about this file can be found at # Additional information about this file can be found at
# https://dart.dev/guides/language/analysis-options # https://dart.dev/guides/language/analysis-options

View File

@@ -1,5 +0,0 @@
import 'package:anyway/domain/entities/landmark.dart';
abstract class TripRemoteDataSource {
Future<List<Landmark>> fetchLandmarks();
}

View File

@@ -0,0 +1,142 @@
import 'dart:convert';
import 'dart:developer';
import 'package:dio/dio.dart';
abstract class TripRemoteDataSource {
/// Fetch available landmarks for the provided preferences/start payload.
Future<List<Map<String, dynamic>>> fetchLandmarks(Map<String, dynamic> body);
/// Create a new trip using the optimizer payload (that includes landmarks).
Future<Map<String, dynamic>> createTrip(Map<String, dynamic> body);
/// Fetch an existing trip by UUID
Future<Map<String, dynamic>> fetchTrip(String uuid);
}
class TripRemoteDataSourceImpl implements TripRemoteDataSource {
final Dio dio;
TripRemoteDataSourceImpl({required this.dio});
@override
Future<List<Map<String, dynamic>>> fetchLandmarks(Map<String, dynamic> body) async {
final response = await dio.post('/get/landmarks', data: body);
if (response.statusCode != 200) {
throw Exception('Server error fetching landmarks: ${response.statusCode}');
}
if (response.data is! List) {
throw Exception('Unexpected landmarks response format');
}
return _normalizeLandmarks(List<dynamic>.from(response.data as List));
}
@override
Future<Map<String, dynamic>> createTrip(Map<String, dynamic> body) async {
log('Creating trip with body: $body');
// convert body to actual json
String bodyJson = jsonEncode(body);
log('Trip request JSON: $bodyJson');
final response = await dio.post('/optimize/trip', data: body);
if (response.statusCode != 200) {
throw Exception('Server error: ${response.statusCode}');
}
if (response.data is! Map<String, dynamic>) {
throw Exception('Unexpected response format');
}
final Map<String, dynamic> json = Map<String, dynamic>.from(response.data as Map);
_ensureLandmarks(json);
if (json.containsKey('landmarks') && json['landmarks'] is List) {
return json;
}
final String? firstUuid = json['first_landmark_uuid'] as String?;
if (firstUuid == null) {
return json;
}
final List<Map<String, dynamic>> landmarks = [];
String? next = firstUuid;
while (next != null) {
final lm = await _fetchLandmarkByUuid(next);
landmarks.add(lm);
final dynamic nxt = lm['next_uuid'];
next = (nxt is String) ? nxt : null;
}
json['landmarks'] = landmarks;
return json;
}
@override
Future<Map<String, dynamic>> fetchTrip(String uuid) async {
final response = await dio.get('/trip/$uuid');
if (response.statusCode != 200) {
throw Exception('Server error: ${response.statusCode}');
}
if (response.data is! Map<String, dynamic>) {
throw Exception('Unexpected response format');
}
final Map<String, dynamic> json = Map<String, dynamic>.from(response.data as Map);
// Normalize same as createTrip: if trip contains first_landmark_uuid, expand chain
if (json.containsKey('landmarks') && json['landmarks'] is List) {
_ensureLandmarks(json);
return json;
}
final String? firstUuid = json['first_landmark_uuid'] as String?;
if (firstUuid == null) return json;
final List<Map<String, dynamic>> landmarks = [];
String? next = firstUuid;
while (next != null) {
final lm = await _fetchLandmarkByUuid(next);
landmarks.add(lm);
final dynamic nxt = lm['next_uuid'];
next = (nxt is String) ? nxt : null;
}
json['landmarks'] = landmarks;
return json;
}
// Fetch a single landmark by uuid via the /landmark/{landmark_uuid} endpoint
Future<Map<String, dynamic>> _fetchLandmarkByUuid(String uuid) async {
final response = await dio.get('/landmark/$uuid');
if (response.statusCode != 200) {
throw Exception('Failed to fetch landmark $uuid: ${response.statusCode}');
}
if (response.data is! Map<String, dynamic>) {
throw Exception('Unexpected landmark response format');
}
return _normalizeLandmark(Map<String, dynamic>.from(response.data as Map));
}
static void _ensureLandmarks(Map<String, dynamic> json) {
final raw = json['landmarks'];
if (raw is List) {
json['landmarks'] = _normalizeLandmarks(raw);
}
}
static List<Map<String, dynamic>> _normalizeLandmarks(List<dynamic> rawList) {
return rawList
.map((item) => _normalizeLandmark(Map<String, dynamic>.from(item as Map)))
.toList();
}
static Map<String, dynamic> _normalizeLandmark(Map<String, dynamic> source) {
final normalized = Map<String, dynamic>.from(source);
final typeValue = normalized['type'];
if (typeValue is String) {
normalized['type'] = {'type': typeValue};
}
return normalized;
}
}

View File

@@ -1,3 +1,4 @@
// TODO - I have the feeling this file is outdated and not used anymore
import 'package:anyway/domain/entities/landmark.dart'; import 'package:anyway/domain/entities/landmark.dart';
import 'package:anyway/domain/entities/landmark_description.dart'; import 'package:anyway/domain/entities/landmark_description.dart';
import 'package:anyway/domain/entities/landmark_type.dart'; import 'package:anyway/domain/entities/landmark_type.dart';
@@ -16,6 +17,8 @@ abstract class LandmarkModel with _$LandmarkModel {
required String description, required String description,
}) = _LandmarkModel; }) = _LandmarkModel;
const LandmarkModel._();
factory LandmarkModel.fromJson(Map<String, dynamic> json) => _$LandmarkModelFromJson(json); factory LandmarkModel.fromJson(Map<String, dynamic> json) => _$LandmarkModelFromJson(json);
Landmark toEntity() => Landmark( Landmark toEntity() => Landmark(
@@ -24,7 +27,6 @@ abstract class LandmarkModel with _$LandmarkModel {
location: location, location: location,
type: LandmarkType(type: LandmarkTypeEnum.values.firstWhere((e) => e.value == type)), type: LandmarkType(type: LandmarkTypeEnum.values.firstWhere((e) => e.value == type)),
isSecondary: isSecondary, isSecondary: isSecondary,
// TODO - try to set tags description: LandmarkDescription(description: description, tags: []),
description: LandmarkDescription(description: description, tags: [])
); );
} }

View File

@@ -14,71 +14,47 @@ T _$identity<T>(T value) => value;
/// @nodoc /// @nodoc
mixin _$LandmarkModel { mixin _$LandmarkModel {
String get uuid;
String get name;
List<double> get location;
String get type;
bool get isSecondary;
String get description;
String get uuid; String get name; List<double> get location; String get type; bool get isSecondary; String get description;
/// Create a copy of LandmarkModel /// Create a copy of LandmarkModel
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
$LandmarkModelCopyWith<LandmarkModel> get copyWith => $LandmarkModelCopyWith<LandmarkModel> get copyWith => _$LandmarkModelCopyWithImpl<LandmarkModel>(this as LandmarkModel, _$identity);
_$LandmarkModelCopyWithImpl<LandmarkModel>(
this as LandmarkModel, _$identity);
/// Serializes this LandmarkModel to a JSON map. /// Serializes this LandmarkModel to a JSON map.
Map<String, dynamic> toJson(); Map<String, dynamic> toJson();
@override @override
bool operator ==(Object other) { bool operator ==(Object other) {
return identical(this, other) || return identical(this, other) || (other.runtimeType == runtimeType&&other is LandmarkModel&&(identical(other.uuid, uuid) || other.uuid == uuid)&&(identical(other.name, name) || other.name == name)&&const DeepCollectionEquality().equals(other.location, location)&&(identical(other.type, type) || other.type == type)&&(identical(other.isSecondary, isSecondary) || other.isSecondary == isSecondary)&&(identical(other.description, description) || other.description == description));
(other.runtimeType == runtimeType &&
other is LandmarkModel &&
(identical(other.uuid, uuid) || other.uuid == uuid) &&
(identical(other.name, name) || other.name == name) &&
const DeepCollectionEquality().equals(other.location, location) &&
(identical(other.type, type) || other.type == type) &&
(identical(other.isSecondary, isSecondary) ||
other.isSecondary == isSecondary) &&
(identical(other.description, description) ||
other.description == description));
} }
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@override @override
int get hashCode => Object.hash( int get hashCode => Object.hash(runtimeType,uuid,name,const DeepCollectionEquality().hash(location),type,isSecondary,description);
runtimeType,
uuid,
name,
const DeepCollectionEquality().hash(location),
type,
isSecondary,
description);
@override @override
String toString() { String toString() {
return 'LandmarkModel(uuid: $uuid, name: $name, location: $location, type: $type, isSecondary: $isSecondary, description: $description)'; return 'LandmarkModel(uuid: $uuid, name: $name, location: $location, type: $type, isSecondary: $isSecondary, description: $description)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class $LandmarkModelCopyWith<$Res> { abstract mixin class $LandmarkModelCopyWith<$Res> {
factory $LandmarkModelCopyWith( factory $LandmarkModelCopyWith(LandmarkModel value, $Res Function(LandmarkModel) _then) = _$LandmarkModelCopyWithImpl;
LandmarkModel value, $Res Function(LandmarkModel) _then) =
_$LandmarkModelCopyWithImpl;
@useResult @useResult
$Res call( $Res call({
{String uuid, String uuid, String name, List<double> location, String type, bool isSecondary, String description
String name, });
List<double> location,
String type,
bool isSecondary,
String description});
}
}
/// @nodoc /// @nodoc
class _$LandmarkModelCopyWithImpl<$Res> class _$LandmarkModelCopyWithImpl<$Res>
implements $LandmarkModelCopyWith<$Res> { implements $LandmarkModelCopyWith<$Res> {
@@ -89,45 +65,21 @@ class _$LandmarkModelCopyWithImpl<$Res>
/// Create a copy of LandmarkModel /// Create a copy of LandmarkModel
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline') @override $Res call({Object? uuid = null,Object? name = null,Object? location = null,Object? type = null,Object? isSecondary = null,Object? description = null,}) {
@override
$Res call({
Object? uuid = null,
Object? name = null,
Object? location = null,
Object? type = null,
Object? isSecondary = null,
Object? description = null,
}) {
return _then(_self.copyWith( return _then(_self.copyWith(
uuid: null == uuid uuid: null == uuid ? _self.uuid : uuid // ignore: cast_nullable_to_non_nullable
? _self.uuid as String,name: null == name ? _self.name : name // ignore: cast_nullable_to_non_nullable
: uuid // ignore: cast_nullable_to_non_nullable as String,location: null == location ? _self.location : location // ignore: cast_nullable_to_non_nullable
as String, as List<double>,type: null == type ? _self.type : type // ignore: cast_nullable_to_non_nullable
name: null == name as String,isSecondary: null == isSecondary ? _self.isSecondary : isSecondary // ignore: cast_nullable_to_non_nullable
? _self.name as bool,description: null == description ? _self.description : description // ignore: cast_nullable_to_non_nullable
: name // ignore: cast_nullable_to_non_nullable
as String,
location: null == location
? _self.location
: location // ignore: cast_nullable_to_non_nullable
as List<double>,
type: null == type
? _self.type
: type // ignore: cast_nullable_to_non_nullable
as String,
isSecondary: null == isSecondary
? _self.isSecondary
: isSecondary // ignore: cast_nullable_to_non_nullable
as bool,
description: null == description
? _self.description
: description // ignore: cast_nullable_to_non_nullable
as String, as String,
)); ));
} }
} }
/// Adds pattern-matching-related methods to [LandmarkModel]. /// Adds pattern-matching-related methods to [LandmarkModel].
extension LandmarkModelPatterns on LandmarkModel { extension LandmarkModelPatterns on LandmarkModel {
/// A variant of `map` that fallback to returning `orElse`. /// A variant of `map` that fallback to returning `orElse`.
@@ -142,20 +94,15 @@ extension LandmarkModelPatterns on LandmarkModel {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeMap<TResult extends Object?>(TResult Function( _LandmarkModel value)? $default,{required TResult orElse(),}){
TResult maybeMap<TResult extends Object?>(
TResult Function(_LandmarkModel value)? $default, {
required TResult orElse(),
}) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _LandmarkModel() when $default != null: case _LandmarkModel() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// Callbacks receives the raw object, upcasted. /// Callbacks receives the raw object, upcasted.
@@ -169,19 +116,15 @@ extension LandmarkModelPatterns on LandmarkModel {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult map<TResult extends Object?>(TResult Function( _LandmarkModel value) $default,){
TResult map<TResult extends Object?>(
TResult Function(_LandmarkModel value) $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _LandmarkModel(): case _LandmarkModel():
return $default(_that); return $default(_that);case _:
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `map` that fallback to returning `null`. /// A variant of `map` that fallback to returning `null`.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -194,19 +137,15 @@ extension LandmarkModelPatterns on LandmarkModel {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? mapOrNull<TResult extends Object?>(TResult? Function( _LandmarkModel value)? $default,){
TResult? mapOrNull<TResult extends Object?>(
TResult? Function(_LandmarkModel value)? $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _LandmarkModel() when $default != null: case _LandmarkModel() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return null; return null;
}
}
}
}
/// A variant of `when` that fallback to an `orElse` callback. /// A variant of `when` that fallback to an `orElse` callback.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -219,23 +158,14 @@ extension LandmarkModelPatterns on LandmarkModel {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( String uuid, String name, List<double> location, String type, bool isSecondary, String description)? $default,{required TResult orElse(),}) {final _that = this;
TResult maybeWhen<TResult extends Object?>(
TResult Function(String uuid, String name, List<double> location,
String type, bool isSecondary, String description)?
$default, {
required TResult orElse(),
}) {
final _that = this;
switch (_that) { switch (_that) {
case _LandmarkModel() when $default != null: case _LandmarkModel() when $default != null:
return $default(_that.uuid, _that.name, _that.location, _that.type, return $default(_that.uuid,_that.name,_that.location,_that.type,_that.isSecondary,_that.description);case _:
_that.isSecondary, _that.description);
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// As opposed to `map`, this offers destructuring. /// As opposed to `map`, this offers destructuring.
@@ -249,22 +179,14 @@ extension LandmarkModelPatterns on LandmarkModel {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( String uuid, String name, List<double> location, String type, bool isSecondary, String description) $default,) {final _that = this;
TResult when<TResult extends Object?>(
TResult Function(String uuid, String name, List<double> location,
String type, bool isSecondary, String description)
$default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _LandmarkModel(): case _LandmarkModel():
return $default(_that.uuid, _that.name, _that.location, _that.type, return $default(_that.uuid,_that.name,_that.location,_that.type,_that.isSecondary,_that.description);case _:
_that.isSecondary, _that.description);
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `when` that fallback to returning `null` /// A variant of `when` that fallback to returning `null`
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -277,120 +199,77 @@ extension LandmarkModelPatterns on LandmarkModel {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( String uuid, String name, List<double> location, String type, bool isSecondary, String description)? $default,) {final _that = this;
TResult? whenOrNull<TResult extends Object?>(
TResult? Function(String uuid, String name, List<double> location,
String type, bool isSecondary, String description)?
$default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _LandmarkModel() when $default != null: case _LandmarkModel() when $default != null:
return $default(_that.uuid, _that.name, _that.location, _that.type, return $default(_that.uuid,_that.name,_that.location,_that.type,_that.isSecondary,_that.description);case _:
_that.isSecondary, _that.description);
case _:
return null; return null;
} }
} }
} }
/// @nodoc /// @nodoc
@JsonSerializable() @JsonSerializable()
class _LandmarkModel implements LandmarkModel {
const _LandmarkModel(
{required this.uuid,
required this.name,
required final List<double> location,
required this.type,
required this.isSecondary,
required this.description})
: _location = location;
factory _LandmarkModel.fromJson(Map<String, dynamic> json) =>
_$LandmarkModelFromJson(json);
@override class _LandmarkModel extends LandmarkModel {
final String uuid; const _LandmarkModel({required this.uuid, required this.name, required final List<double> location, required this.type, required this.isSecondary, required this.description}): _location = location,super._();
@override factory _LandmarkModel.fromJson(Map<String, dynamic> json) => _$LandmarkModelFromJson(json);
final String name;
@override final String uuid;
@override final String name;
final List<double> _location; final List<double> _location;
@override @override List<double> get location {
List<double> get location {
if (_location is EqualUnmodifiableListView) return _location; if (_location is EqualUnmodifiableListView) return _location;
// ignore: implicit_dynamic_type // ignore: implicit_dynamic_type
return EqualUnmodifiableListView(_location); return EqualUnmodifiableListView(_location);
} }
@override @override final String type;
final String type; @override final bool isSecondary;
@override @override final String description;
final bool isSecondary;
@override
final String description;
/// Create a copy of LandmarkModel /// Create a copy of LandmarkModel
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @JsonKey(includeFromJson: false, includeToJson: false)
@JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
_$LandmarkModelCopyWith<_LandmarkModel> get copyWith => _$LandmarkModelCopyWith<_LandmarkModel> get copyWith => __$LandmarkModelCopyWithImpl<_LandmarkModel>(this, _$identity);
__$LandmarkModelCopyWithImpl<_LandmarkModel>(this, _$identity);
@override @override
Map<String, dynamic> toJson() { Map<String, dynamic> toJson() {
return _$LandmarkModelToJson( return _$LandmarkModelToJson(this, );
this,
);
} }
@override @override
bool operator ==(Object other) { bool operator ==(Object other) {
return identical(this, other) || return identical(this, other) || (other.runtimeType == runtimeType&&other is _LandmarkModel&&(identical(other.uuid, uuid) || other.uuid == uuid)&&(identical(other.name, name) || other.name == name)&&const DeepCollectionEquality().equals(other._location, _location)&&(identical(other.type, type) || other.type == type)&&(identical(other.isSecondary, isSecondary) || other.isSecondary == isSecondary)&&(identical(other.description, description) || other.description == description));
(other.runtimeType == runtimeType &&
other is _LandmarkModel &&
(identical(other.uuid, uuid) || other.uuid == uuid) &&
(identical(other.name, name) || other.name == name) &&
const DeepCollectionEquality().equals(other._location, _location) &&
(identical(other.type, type) || other.type == type) &&
(identical(other.isSecondary, isSecondary) ||
other.isSecondary == isSecondary) &&
(identical(other.description, description) ||
other.description == description));
} }
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@override @override
int get hashCode => Object.hash( int get hashCode => Object.hash(runtimeType,uuid,name,const DeepCollectionEquality().hash(_location),type,isSecondary,description);
runtimeType,
uuid,
name,
const DeepCollectionEquality().hash(_location),
type,
isSecondary,
description);
@override @override
String toString() { String toString() {
return 'LandmarkModel(uuid: $uuid, name: $name, location: $location, type: $type, isSecondary: $isSecondary, description: $description)'; return 'LandmarkModel(uuid: $uuid, name: $name, location: $location, type: $type, isSecondary: $isSecondary, description: $description)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class _$LandmarkModelCopyWith<$Res> abstract mixin class _$LandmarkModelCopyWith<$Res> implements $LandmarkModelCopyWith<$Res> {
implements $LandmarkModelCopyWith<$Res> { factory _$LandmarkModelCopyWith(_LandmarkModel value, $Res Function(_LandmarkModel) _then) = __$LandmarkModelCopyWithImpl;
factory _$LandmarkModelCopyWith( @override @useResult
_LandmarkModel value, $Res Function(_LandmarkModel) _then) = $Res call({
__$LandmarkModelCopyWithImpl; String uuid, String name, List<double> location, String type, bool isSecondary, String description
@override });
@useResult
$Res call(
{String uuid,
String name,
List<double> location,
String type,
bool isSecondary,
String description});
}
}
/// @nodoc /// @nodoc
class __$LandmarkModelCopyWithImpl<$Res> class __$LandmarkModelCopyWithImpl<$Res>
implements _$LandmarkModelCopyWith<$Res> { implements _$LandmarkModelCopyWith<$Res> {
@@ -401,43 +280,19 @@ class __$LandmarkModelCopyWithImpl<$Res>
/// Create a copy of LandmarkModel /// Create a copy of LandmarkModel
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @pragma('vm:prefer-inline') $Res call({Object? uuid = null,Object? name = null,Object? location = null,Object? type = null,Object? isSecondary = null,Object? description = null,}) {
@pragma('vm:prefer-inline')
$Res call({
Object? uuid = null,
Object? name = null,
Object? location = null,
Object? type = null,
Object? isSecondary = null,
Object? description = null,
}) {
return _then(_LandmarkModel( return _then(_LandmarkModel(
uuid: null == uuid uuid: null == uuid ? _self.uuid : uuid // ignore: cast_nullable_to_non_nullable
? _self.uuid as String,name: null == name ? _self.name : name // ignore: cast_nullable_to_non_nullable
: uuid // ignore: cast_nullable_to_non_nullable as String,location: null == location ? _self._location : location // ignore: cast_nullable_to_non_nullable
as String, as List<double>,type: null == type ? _self.type : type // ignore: cast_nullable_to_non_nullable
name: null == name as String,isSecondary: null == isSecondary ? _self.isSecondary : isSecondary // ignore: cast_nullable_to_non_nullable
? _self.name as bool,description: null == description ? _self.description : description // ignore: cast_nullable_to_non_nullable
: name // ignore: cast_nullable_to_non_nullable
as String,
location: null == location
? _self._location
: location // ignore: cast_nullable_to_non_nullable
as List<double>,
type: null == type
? _self.type
: type // ignore: cast_nullable_to_non_nullable
as String,
isSecondary: null == isSecondary
? _self.isSecondary
: isSecondary // ignore: cast_nullable_to_non_nullable
as bool,
description: null == description
? _self.description
: description // ignore: cast_nullable_to_non_nullable
as String, as String,
)); ));
} }
} }
// dart format on // dart format on

View File

@@ -1,119 +1,89 @@
import 'dart:developer'; import 'package:anyway/domain/entities/landmark.dart';
import 'package:anyway/domain/entities/preferences.dart'; import 'package:anyway/domain/entities/preferences.dart';
import 'package:anyway/domain/entities/trip.dart'; import 'package:anyway/domain/entities/trip.dart';
import 'package:anyway/domain/repositories/trip_repository.dart'; import 'package:anyway/domain/repositories/trip_repository.dart';
import 'package:dio/dio.dart'; import 'package:anyway/data/datasources/trip_remote_datasource.dart';
// We can request a new trip from our backend API by passing it user preferences (which contain all the necessary data)
class BackendTripRepository implements TripRepository { class BackendTripRepository implements TripRepository {
final Dio dio; final TripRemoteDataSource remote;
BackendTripRepository({required this.dio});
BackendTripRepository({required this.remote});
@override @override
Future<Trip> getTrip({Preferences? preferences, String? tripUUID}) async { Future<Trip> getTrip({Preferences? preferences, String? tripUUID, List<Landmark>? landmarks}) async {
Map<String, dynamic> data = { try {
"preferences": preferences!.toJson(), Map<String, dynamic> json;
// "start": preferences!.startPoint.location,
if (tripUUID != null) {
json = await remote.fetchTrip(tripUUID);
} else {
if (preferences == null) {
throw ArgumentError('Either preferences or tripUUID must be provided');
}
final Map<String, dynamic> prefsPayload = _buildPreferencesPayload(preferences);
List<Map<String, dynamic>> landmarkBodies = landmarks != null
? landmarks.map((lm) => lm.toJson()).toList()
: await _fetchLandmarkPayloads(prefsPayload, preferences.startLocation);
// TODO: remove
// restrict the landmark list to 30 to iterate quickly
landmarkBodies = landmarkBodies.take(30).toList();
// change the json key because of backend inconsistency
for (var lm in landmarkBodies) {
if (lm.containsKey('type')) {
lm['type'] = "sightseeing";
}
lm['osm_type'] = 'node';
lm['osm_id'] = 1;
}
final Map<String, dynamic> body = {
'preferences': prefsPayload,
'landmarks': landmarkBodies,
'start': preferences.startLocation,
};
if (preferences.endLocation != null) {
body['end'] = preferences.endLocation;
}
if (preferences.detourToleranceMinutes != null) {
body['detour_tolerance_minute'] = preferences.detourToleranceMinutes;
}
json = await remote.createTrip(body);
}
return Trip.fromJson(json);
} catch (e) {
throw Exception('Failed to fetch trip: ${e.toString()}');
}
}
// TODO - maybe shorten this
@override
Future<List<Landmark>> searchLandmarks(Preferences preferences) async {
final Map<String, dynamic> prefsPayload = _buildPreferencesPayload(preferences);
final List<Map<String, dynamic>> rawLandmarks = await _fetchLandmarkPayloads(prefsPayload, preferences.startLocation);
return rawLandmarks.map((lmJson) => Landmark.fromJson(lmJson)).toList();
}
Future<List<Map<String, dynamic>>> _fetchLandmarkPayloads(
Map<String, dynamic> prefsPayload, List<double> startLocation) async {
final Map<String, dynamic> landmarkRequest = {
'preferences': prefsPayload,
'start': startLocation,
}; };
return await remote.fetchLandmarks(landmarkRequest);
late Response response;
try {
response = await dio.post(
"/trip/new",
data: data
);
} catch (e) {
trip.updateUUID("error");
// Format the error message to be more user friendly
String errorDescription;
if (e is DioException) {
errorDescription = e.message ?? "Unknown error";
} else if (e is SocketException) {
errorDescription = "No internet connection";
} else if (e is TimeoutException) {
errorDescription = "Request timed out";
} else {
errorDescription = "Unknown error";
} }
String errorMessage = """ Map<String, dynamic> _buildPreferencesPayload(Preferences preferences) {
We're sorry, the following error was generated: final Map<String, dynamic> prefsPayload = {};
preferences.scores.forEach((type, score) {
${errorDescription.trim()} prefsPayload[type] = {'type': type, 'score': score};
""".trim(); });
prefsPayload['max_time_minute'] = preferences.maxTimeMinutes;
trip.updateError(errorMessage); return prefsPayload;
log(e.toString());
log(errorMessage);
return;
}
// handle more specific errors
if (response.statusCode != 200) {
trip.updateUUID("error");
String errorDescription;
if (response.data.runtimeType == String) {
errorDescription = response.data;
} else if (response.data.runtimeType == Map<String, dynamic>) {
errorDescription = response.data["detail"] ?? "Unknown error";
} else {
errorDescription = "Unknown error";
}
String errorMessage = """
We're sorry, our servers generated the following error:
${errorDescription.trim()}
Please try again.
""".trim();
trip.updateError(errorMessage);
log(errorMessage);
// Actualy no need to throw an exception, we can just log the error and let the user retry
// throw Exception(errorDetail);
} else {
// if the response data is not json, throw an error
if (response.data is! Map<String, dynamic>) {
log("${response.data.runtimeType}");
trip.updateUUID("error");
String errorMessage = """
We're sorry, our servers generated the following error:
${response.data.trim()}
Please try again.
""".trim();
trip.updateError(errorMessage);
log(errorMessage);
return;
}
Map<String, dynamic> json = response.data;
// only fill in the trip "meta" data for now
trip.loadFromJson(json);
// now fill the trip with landmarks
// we are going to recreate ALL the landmarks from the information given by the api
trip.landmarks.remove(trip.landmarks.first);
String? nextUUID = json["first_landmark_uuid"];
while (nextUUID != null) {
var (landmark, newUUID) = await fetchLandmark(nextUUID);
trip.addLandmark(landmark);
nextUUID = newUUID;
}
log(response.data.toString());
// // Also save the trip for the user's convenience
// savedTrips.addTrip(trip);
}
} }
} }

View File

@@ -0,0 +1,18 @@
import 'package:shared_preferences/shared_preferences.dart';
import 'package:anyway/domain/repositories/onboarding_repository.dart';
class LocalOnboardingRepository implements OnboardingRepository {
static const _key = 'onboardingCompleted';
@override
Future<bool> isOnboarded() async {
final prefs = await SharedPreferences.getInstance();
return prefs.getBool(_key) ?? false;
}
@override
Future<void> setOnboarded(bool value) async {
final prefs = await SharedPreferences.getInstance();
await prefs.setBool(_key, value);
}
}

View File

@@ -0,0 +1,50 @@
import 'dart:convert';
import 'package:shared_preferences/shared_preferences.dart';
import 'package:anyway/domain/entities/preferences.dart';
import 'package:anyway/domain/repositories/preferences_repository.dart';
class PreferencesRepositoryImpl implements PreferencesRepository {
static const _key = 'userPreferences';
@override
Future<Preferences> getPreferences() async {
final prefs = await SharedPreferences.getInstance();
final raw = prefs.getString(_key);
if (raw == null) {
// TODO - rethink this
// return a sensible default
return Preferences(
scores: {
'sightseeing': 0,
'shopping': 0,
'nature': 0,
},
maxTimeMinutes: 120,
startLocation: const [48.8575, 2.3514],
);
}
try {
final map = json.decode(raw) as Map<String, dynamic>;
return Preferences.fromJson(map);
} catch (_) {
return Preferences(
scores: {
'sightseeing': 0,
'shopping': 0,
'nature': 0,
},
maxTimeMinutes: 120,
startLocation: const [48.8575, 2.3514],
);
}
}
@override
Future<void> savePreferences(Preferences preferences) async {
final prefs = await SharedPreferences.getInstance();
final raw = json.encode(preferences.toJson());
await prefs.setString(_key, raw);
}
}

View File

@@ -22,3 +22,14 @@ This is required boilerplate for all models. Then, we define the model itself us
The `*.frozen.dart` and `*.g.dart` are pure boilerplate and should not be touched. The `*.frozen.dart` and `*.g.dart` are pure boilerplate and should not be touched.
Note that the description of the data will losely follow the capabilities of the backend but does not need to reflect it exactly. That is where the `data` part is for: translating api calls into flutter objects. Note that the description of the data will losely follow the capabilities of the backend but does not need to reflect it exactly. That is where the `data` part is for: translating api calls into flutter objects.
To ensure the creation of the boilerplate code, run the following command in your terminal:
```bash
flutter pub run build_runner build --delete-conflicting-outputs
```
or interactively:
```
dart run build_runner watch -d
```

View File

@@ -12,9 +12,38 @@ abstract class Landmark with _$Landmark {
required String name, required String name,
required List<double> location, required List<double> location,
required LandmarkType type, required LandmarkType type,
required bool isSecondary,
required LandmarkDescription description, @JsonKey(name: 'is_secondary')
bool? isSecondary,
/// Optional rich description object (may be null if API returns plain string)
LandmarkDescription? description,
@JsonKey(name: 'name_en')
String? nameEn,
@JsonKey(name: 'website_url')
String? websiteUrl,
@JsonKey(name: 'image_url')
String? imageUrl,
@JsonKey(name: 'attractiveness')
int? attractiveness,
@JsonKey(name: 'n_tags')
int? tagCount,
/// Duration at landmark in minutes
@JsonKey(name: 'duration')
int? durationMinutes,
bool? visited,
@JsonKey(name: 'time_to_reach_next')
int? timeToReachNextMinutes,
}) = _Landmark; }) = _Landmark;
factory Landmark.fromJson(Map<String, Object?> json) => _$LandmarkFromJson(json); factory Landmark.fromJson(Map<String, Object?> json) => _$LandmarkFromJson(json);

View File

@@ -14,54 +14,47 @@ T _$identity<T>(T value) => value;
/// @nodoc /// @nodoc
mixin _$Landmark { mixin _$Landmark {
String get uuid;
set uuid(String value);
String get name;
set name(String value);
List<double> get location;
set location(List<double> value);
LandmarkType get type;
set type(LandmarkType value);
bool get isSecondary;
set isSecondary(bool value);
LandmarkDescription get description;
set description(LandmarkDescription value);
String get uuid; set uuid(String value); String get name; set name(String value); List<double> get location; set location(List<double> value); LandmarkType get type; set type(LandmarkType value);@JsonKey(name: 'is_secondary') bool? get isSecondary;@JsonKey(name: 'is_secondary') set isSecondary(bool? value);/// Optional rich description object (may be null if API returns plain string)
LandmarkDescription? get description;/// Optional rich description object (may be null if API returns plain string)
set description(LandmarkDescription? value);@JsonKey(name: 'name_en') String? get nameEn;@JsonKey(name: 'name_en') set nameEn(String? value);@JsonKey(name: 'website_url') String? get websiteUrl;@JsonKey(name: 'website_url') set websiteUrl(String? value);@JsonKey(name: 'image_url') String? get imageUrl;@JsonKey(name: 'image_url') set imageUrl(String? value);@JsonKey(name: 'attractiveness') int? get attractiveness;@JsonKey(name: 'attractiveness') set attractiveness(int? value);@JsonKey(name: 'n_tags') int? get tagCount;@JsonKey(name: 'n_tags') set tagCount(int? value);/// Duration at landmark in minutes
@JsonKey(name: 'duration') int? get durationMinutes;/// Duration at landmark in minutes
@JsonKey(name: 'duration') set durationMinutes(int? value); bool? get visited; set visited(bool? value);@JsonKey(name: 'time_to_reach_next') int? get timeToReachNextMinutes;@JsonKey(name: 'time_to_reach_next') set timeToReachNextMinutes(int? value);
/// Create a copy of Landmark /// Create a copy of Landmark
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
$LandmarkCopyWith<Landmark> get copyWith => $LandmarkCopyWith<Landmark> get copyWith => _$LandmarkCopyWithImpl<Landmark>(this as Landmark, _$identity);
_$LandmarkCopyWithImpl<Landmark>(this as Landmark, _$identity);
/// Serializes this Landmark to a JSON map. /// Serializes this Landmark to a JSON map.
Map<String, dynamic> toJson(); Map<String, dynamic> toJson();
@override @override
String toString() { String toString() {
return 'Landmark(uuid: $uuid, name: $name, location: $location, type: $type, isSecondary: $isSecondary, description: $description)'; return 'Landmark(uuid: $uuid, name: $name, location: $location, type: $type, isSecondary: $isSecondary, description: $description, nameEn: $nameEn, websiteUrl: $websiteUrl, imageUrl: $imageUrl, attractiveness: $attractiveness, tagCount: $tagCount, durationMinutes: $durationMinutes, visited: $visited, timeToReachNextMinutes: $timeToReachNextMinutes)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class $LandmarkCopyWith<$Res> { abstract mixin class $LandmarkCopyWith<$Res> {
factory $LandmarkCopyWith(Landmark value, $Res Function(Landmark) _then) = factory $LandmarkCopyWith(Landmark value, $Res Function(Landmark) _then) = _$LandmarkCopyWithImpl;
_$LandmarkCopyWithImpl;
@useResult @useResult
$Res call( $Res call({
{String uuid, String uuid, String name, List<double> location, LandmarkType type,@JsonKey(name: 'is_secondary') bool? isSecondary, LandmarkDescription? description,@JsonKey(name: 'name_en') String? nameEn,@JsonKey(name: 'website_url') String? websiteUrl,@JsonKey(name: 'image_url') String? imageUrl,@JsonKey(name: 'attractiveness') int? attractiveness,@JsonKey(name: 'n_tags') int? tagCount,@JsonKey(name: 'duration') int? durationMinutes, bool? visited,@JsonKey(name: 'time_to_reach_next') int? timeToReachNextMinutes
String name, });
List<double> location,
LandmarkType type,
bool isSecondary, $LandmarkTypeCopyWith<$Res> get type;$LandmarkDescriptionCopyWith<$Res>? get description;
LandmarkDescription description});
$LandmarkTypeCopyWith<$Res> get type;
$LandmarkDescriptionCopyWith<$Res> get description;
} }
/// @nodoc /// @nodoc
class _$LandmarkCopyWithImpl<$Res> implements $LandmarkCopyWith<$Res> { class _$LandmarkCopyWithImpl<$Res>
implements $LandmarkCopyWith<$Res> {
_$LandmarkCopyWithImpl(this._self, this._then); _$LandmarkCopyWithImpl(this._self, this._then);
final Landmark _self; final Landmark _self;
@@ -69,65 +62,50 @@ class _$LandmarkCopyWithImpl<$Res> implements $LandmarkCopyWith<$Res> {
/// Create a copy of Landmark /// Create a copy of Landmark
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline') @override $Res call({Object? uuid = null,Object? name = null,Object? location = null,Object? type = null,Object? isSecondary = freezed,Object? description = freezed,Object? nameEn = freezed,Object? websiteUrl = freezed,Object? imageUrl = freezed,Object? attractiveness = freezed,Object? tagCount = freezed,Object? durationMinutes = freezed,Object? visited = freezed,Object? timeToReachNextMinutes = freezed,}) {
@override
$Res call({
Object? uuid = null,
Object? name = null,
Object? location = null,
Object? type = null,
Object? isSecondary = null,
Object? description = null,
}) {
return _then(_self.copyWith( return _then(_self.copyWith(
uuid: null == uuid uuid: null == uuid ? _self.uuid : uuid // ignore: cast_nullable_to_non_nullable
? _self.uuid as String,name: null == name ? _self.name : name // ignore: cast_nullable_to_non_nullable
: uuid // ignore: cast_nullable_to_non_nullable as String,location: null == location ? _self.location : location // ignore: cast_nullable_to_non_nullable
as String, as List<double>,type: null == type ? _self.type : type // ignore: cast_nullable_to_non_nullable
name: null == name as LandmarkType,isSecondary: freezed == isSecondary ? _self.isSecondary : isSecondary // ignore: cast_nullable_to_non_nullable
? _self.name as bool?,description: freezed == description ? _self.description : description // ignore: cast_nullable_to_non_nullable
: name // ignore: cast_nullable_to_non_nullable as LandmarkDescription?,nameEn: freezed == nameEn ? _self.nameEn : nameEn // ignore: cast_nullable_to_non_nullable
as String, as String?,websiteUrl: freezed == websiteUrl ? _self.websiteUrl : websiteUrl // ignore: cast_nullable_to_non_nullable
location: null == location as String?,imageUrl: freezed == imageUrl ? _self.imageUrl : imageUrl // ignore: cast_nullable_to_non_nullable
? _self.location as String?,attractiveness: freezed == attractiveness ? _self.attractiveness : attractiveness // ignore: cast_nullable_to_non_nullable
: location // ignore: cast_nullable_to_non_nullable as int?,tagCount: freezed == tagCount ? _self.tagCount : tagCount // ignore: cast_nullable_to_non_nullable
as List<double>, as int?,durationMinutes: freezed == durationMinutes ? _self.durationMinutes : durationMinutes // ignore: cast_nullable_to_non_nullable
type: null == type as int?,visited: freezed == visited ? _self.visited : visited // ignore: cast_nullable_to_non_nullable
? _self.type as bool?,timeToReachNextMinutes: freezed == timeToReachNextMinutes ? _self.timeToReachNextMinutes : timeToReachNextMinutes // ignore: cast_nullable_to_non_nullable
: type // ignore: cast_nullable_to_non_nullable as int?,
as LandmarkType,
isSecondary: null == isSecondary
? _self.isSecondary
: isSecondary // ignore: cast_nullable_to_non_nullable
as bool,
description: null == description
? _self.description
: description // ignore: cast_nullable_to_non_nullable
as LandmarkDescription,
)); ));
} }
/// Create a copy of Landmark /// Create a copy of Landmark
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
$LandmarkTypeCopyWith<$Res> get type { $LandmarkTypeCopyWith<$Res> get type {
return $LandmarkTypeCopyWith<$Res>(_self.type, (value) { return $LandmarkTypeCopyWith<$Res>(_self.type, (value) {
return _then(_self.copyWith(type: value)); return _then(_self.copyWith(type: value));
}); });
} }/// Create a copy of Landmark
/// Create a copy of Landmark
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
$LandmarkDescriptionCopyWith<$Res> get description { $LandmarkDescriptionCopyWith<$Res>? get description {
return $LandmarkDescriptionCopyWith<$Res>(_self.description, (value) { if (_self.description == null) {
return null;
}
return $LandmarkDescriptionCopyWith<$Res>(_self.description!, (value) {
return _then(_self.copyWith(description: value)); return _then(_self.copyWith(description: value));
}); });
} }
} }
/// Adds pattern-matching-related methods to [Landmark]. /// Adds pattern-matching-related methods to [Landmark].
extension LandmarkPatterns on Landmark { extension LandmarkPatterns on Landmark {
/// A variant of `map` that fallback to returning `orElse`. /// A variant of `map` that fallback to returning `orElse`.
@@ -142,20 +120,15 @@ extension LandmarkPatterns on Landmark {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeMap<TResult extends Object?>(TResult Function( _Landmark value)? $default,{required TResult orElse(),}){
TResult maybeMap<TResult extends Object?>(
TResult Function(_Landmark value)? $default, {
required TResult orElse(),
}) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _Landmark() when $default != null: case _Landmark() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// Callbacks receives the raw object, upcasted. /// Callbacks receives the raw object, upcasted.
@@ -169,19 +142,15 @@ extension LandmarkPatterns on Landmark {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult map<TResult extends Object?>(TResult Function( _Landmark value) $default,){
TResult map<TResult extends Object?>(
TResult Function(_Landmark value) $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _Landmark(): case _Landmark():
return $default(_that); return $default(_that);case _:
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `map` that fallback to returning `null`. /// A variant of `map` that fallback to returning `null`.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -194,19 +163,15 @@ extension LandmarkPatterns on Landmark {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? mapOrNull<TResult extends Object?>(TResult? Function( _Landmark value)? $default,){
TResult? mapOrNull<TResult extends Object?>(
TResult? Function(_Landmark value)? $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _Landmark() when $default != null: case _Landmark() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return null; return null;
}
}
}
}
/// A variant of `when` that fallback to an `orElse` callback. /// A variant of `when` that fallback to an `orElse` callback.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -219,28 +184,14 @@ extension LandmarkPatterns on Landmark {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( String uuid, String name, List<double> location, LandmarkType type, @JsonKey(name: 'is_secondary') bool? isSecondary, LandmarkDescription? description, @JsonKey(name: 'name_en') String? nameEn, @JsonKey(name: 'website_url') String? websiteUrl, @JsonKey(name: 'image_url') String? imageUrl, @JsonKey(name: 'attractiveness') int? attractiveness, @JsonKey(name: 'n_tags') int? tagCount, @JsonKey(name: 'duration') int? durationMinutes, bool? visited, @JsonKey(name: 'time_to_reach_next') int? timeToReachNextMinutes)? $default,{required TResult orElse(),}) {final _that = this;
TResult maybeWhen<TResult extends Object?>(
TResult Function(
String uuid,
String name,
List<double> location,
LandmarkType type,
bool isSecondary,
LandmarkDescription description)?
$default, {
required TResult orElse(),
}) {
final _that = this;
switch (_that) { switch (_that) {
case _Landmark() when $default != null: case _Landmark() when $default != null:
return $default(_that.uuid, _that.name, _that.location, _that.type, return $default(_that.uuid,_that.name,_that.location,_that.type,_that.isSecondary,_that.description,_that.nameEn,_that.websiteUrl,_that.imageUrl,_that.attractiveness,_that.tagCount,_that.durationMinutes,_that.visited,_that.timeToReachNextMinutes);case _:
_that.isSecondary, _that.description);
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// As opposed to `map`, this offers destructuring. /// As opposed to `map`, this offers destructuring.
@@ -254,27 +205,14 @@ extension LandmarkPatterns on Landmark {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( String uuid, String name, List<double> location, LandmarkType type, @JsonKey(name: 'is_secondary') bool? isSecondary, LandmarkDescription? description, @JsonKey(name: 'name_en') String? nameEn, @JsonKey(name: 'website_url') String? websiteUrl, @JsonKey(name: 'image_url') String? imageUrl, @JsonKey(name: 'attractiveness') int? attractiveness, @JsonKey(name: 'n_tags') int? tagCount, @JsonKey(name: 'duration') int? durationMinutes, bool? visited, @JsonKey(name: 'time_to_reach_next') int? timeToReachNextMinutes) $default,) {final _that = this;
TResult when<TResult extends Object?>(
TResult Function(
String uuid,
String name,
List<double> location,
LandmarkType type,
bool isSecondary,
LandmarkDescription description)
$default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _Landmark(): case _Landmark():
return $default(_that.uuid, _that.name, _that.location, _that.type, return $default(_that.uuid,_that.name,_that.location,_that.type,_that.isSecondary,_that.description,_that.nameEn,_that.websiteUrl,_that.imageUrl,_that.attractiveness,_that.tagCount,_that.durationMinutes,_that.visited,_that.timeToReachNextMinutes);case _:
_that.isSecondary, _that.description);
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `when` that fallback to returning `null` /// A variant of `when` that fallback to returning `null`
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -287,98 +225,77 @@ extension LandmarkPatterns on Landmark {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( String uuid, String name, List<double> location, LandmarkType type, @JsonKey(name: 'is_secondary') bool? isSecondary, LandmarkDescription? description, @JsonKey(name: 'name_en') String? nameEn, @JsonKey(name: 'website_url') String? websiteUrl, @JsonKey(name: 'image_url') String? imageUrl, @JsonKey(name: 'attractiveness') int? attractiveness, @JsonKey(name: 'n_tags') int? tagCount, @JsonKey(name: 'duration') int? durationMinutes, bool? visited, @JsonKey(name: 'time_to_reach_next') int? timeToReachNextMinutes)? $default,) {final _that = this;
TResult? whenOrNull<TResult extends Object?>(
TResult? Function(
String uuid,
String name,
List<double> location,
LandmarkType type,
bool isSecondary,
LandmarkDescription description)?
$default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _Landmark() when $default != null: case _Landmark() when $default != null:
return $default(_that.uuid, _that.name, _that.location, _that.type, return $default(_that.uuid,_that.name,_that.location,_that.type,_that.isSecondary,_that.description,_that.nameEn,_that.websiteUrl,_that.imageUrl,_that.attractiveness,_that.tagCount,_that.durationMinutes,_that.visited,_that.timeToReachNextMinutes);case _:
_that.isSecondary, _that.description);
case _:
return null; return null;
} }
} }
} }
/// @nodoc /// @nodoc
@JsonSerializable() @JsonSerializable()
class _Landmark implements Landmark {
_Landmark(
{required this.uuid,
required this.name,
required this.location,
required this.type,
required this.isSecondary,
required this.description});
factory _Landmark.fromJson(Map<String, dynamic> json) =>
_$LandmarkFromJson(json);
@override class _Landmark implements Landmark {
String uuid; _Landmark({required this.uuid, required this.name, required this.location, required this.type, @JsonKey(name: 'is_secondary') this.isSecondary, this.description, @JsonKey(name: 'name_en') this.nameEn, @JsonKey(name: 'website_url') this.websiteUrl, @JsonKey(name: 'image_url') this.imageUrl, @JsonKey(name: 'attractiveness') this.attractiveness, @JsonKey(name: 'n_tags') this.tagCount, @JsonKey(name: 'duration') this.durationMinutes, this.visited, @JsonKey(name: 'time_to_reach_next') this.timeToReachNextMinutes});
@override factory _Landmark.fromJson(Map<String, dynamic> json) => _$LandmarkFromJson(json);
String name;
@override @override String uuid;
List<double> location; @override String name;
@override @override List<double> location;
LandmarkType type; @override LandmarkType type;
@override @override@JsonKey(name: 'is_secondary') bool? isSecondary;
bool isSecondary; /// Optional rich description object (may be null if API returns plain string)
@override @override LandmarkDescription? description;
LandmarkDescription description; @override@JsonKey(name: 'name_en') String? nameEn;
@override@JsonKey(name: 'website_url') String? websiteUrl;
@override@JsonKey(name: 'image_url') String? imageUrl;
@override@JsonKey(name: 'attractiveness') int? attractiveness;
@override@JsonKey(name: 'n_tags') int? tagCount;
/// Duration at landmark in minutes
@override@JsonKey(name: 'duration') int? durationMinutes;
@override bool? visited;
@override@JsonKey(name: 'time_to_reach_next') int? timeToReachNextMinutes;
/// Create a copy of Landmark /// Create a copy of Landmark
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @JsonKey(includeFromJson: false, includeToJson: false)
@JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
_$LandmarkCopyWith<_Landmark> get copyWith => _$LandmarkCopyWith<_Landmark> get copyWith => __$LandmarkCopyWithImpl<_Landmark>(this, _$identity);
__$LandmarkCopyWithImpl<_Landmark>(this, _$identity);
@override @override
Map<String, dynamic> toJson() { Map<String, dynamic> toJson() {
return _$LandmarkToJson( return _$LandmarkToJson(this, );
this,
);
} }
@override @override
String toString() { String toString() {
return 'Landmark(uuid: $uuid, name: $name, location: $location, type: $type, isSecondary: $isSecondary, description: $description)'; return 'Landmark(uuid: $uuid, name: $name, location: $location, type: $type, isSecondary: $isSecondary, description: $description, nameEn: $nameEn, websiteUrl: $websiteUrl, imageUrl: $imageUrl, attractiveness: $attractiveness, tagCount: $tagCount, durationMinutes: $durationMinutes, visited: $visited, timeToReachNextMinutes: $timeToReachNextMinutes)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class _$LandmarkCopyWith<$Res> abstract mixin class _$LandmarkCopyWith<$Res> implements $LandmarkCopyWith<$Res> {
implements $LandmarkCopyWith<$Res> { factory _$LandmarkCopyWith(_Landmark value, $Res Function(_Landmark) _then) = __$LandmarkCopyWithImpl;
factory _$LandmarkCopyWith(_Landmark value, $Res Function(_Landmark) _then) = @override @useResult
__$LandmarkCopyWithImpl; $Res call({
@override String uuid, String name, List<double> location, LandmarkType type,@JsonKey(name: 'is_secondary') bool? isSecondary, LandmarkDescription? description,@JsonKey(name: 'name_en') String? nameEn,@JsonKey(name: 'website_url') String? websiteUrl,@JsonKey(name: 'image_url') String? imageUrl,@JsonKey(name: 'attractiveness') int? attractiveness,@JsonKey(name: 'n_tags') int? tagCount,@JsonKey(name: 'duration') int? durationMinutes, bool? visited,@JsonKey(name: 'time_to_reach_next') int? timeToReachNextMinutes
@useResult });
$Res call(
{String uuid,
String name, @override $LandmarkTypeCopyWith<$Res> get type;@override $LandmarkDescriptionCopyWith<$Res>? get description;
List<double> location,
LandmarkType type,
bool isSecondary,
LandmarkDescription description});
@override
$LandmarkTypeCopyWith<$Res> get type;
@override
$LandmarkDescriptionCopyWith<$Res> get description;
} }
/// @nodoc /// @nodoc
class __$LandmarkCopyWithImpl<$Res> implements _$LandmarkCopyWith<$Res> { class __$LandmarkCopyWithImpl<$Res>
implements _$LandmarkCopyWith<$Res> {
__$LandmarkCopyWithImpl(this._self, this._then); __$LandmarkCopyWithImpl(this._self, this._then);
final _Landmark _self; final _Landmark _self;
@@ -386,41 +303,23 @@ class __$LandmarkCopyWithImpl<$Res> implements _$LandmarkCopyWith<$Res> {
/// Create a copy of Landmark /// Create a copy of Landmark
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @pragma('vm:prefer-inline') $Res call({Object? uuid = null,Object? name = null,Object? location = null,Object? type = null,Object? isSecondary = freezed,Object? description = freezed,Object? nameEn = freezed,Object? websiteUrl = freezed,Object? imageUrl = freezed,Object? attractiveness = freezed,Object? tagCount = freezed,Object? durationMinutes = freezed,Object? visited = freezed,Object? timeToReachNextMinutes = freezed,}) {
@pragma('vm:prefer-inline')
$Res call({
Object? uuid = null,
Object? name = null,
Object? location = null,
Object? type = null,
Object? isSecondary = null,
Object? description = null,
}) {
return _then(_Landmark( return _then(_Landmark(
uuid: null == uuid uuid: null == uuid ? _self.uuid : uuid // ignore: cast_nullable_to_non_nullable
? _self.uuid as String,name: null == name ? _self.name : name // ignore: cast_nullable_to_non_nullable
: uuid // ignore: cast_nullable_to_non_nullable as String,location: null == location ? _self.location : location // ignore: cast_nullable_to_non_nullable
as String, as List<double>,type: null == type ? _self.type : type // ignore: cast_nullable_to_non_nullable
name: null == name as LandmarkType,isSecondary: freezed == isSecondary ? _self.isSecondary : isSecondary // ignore: cast_nullable_to_non_nullable
? _self.name as bool?,description: freezed == description ? _self.description : description // ignore: cast_nullable_to_non_nullable
: name // ignore: cast_nullable_to_non_nullable as LandmarkDescription?,nameEn: freezed == nameEn ? _self.nameEn : nameEn // ignore: cast_nullable_to_non_nullable
as String, as String?,websiteUrl: freezed == websiteUrl ? _self.websiteUrl : websiteUrl // ignore: cast_nullable_to_non_nullable
location: null == location as String?,imageUrl: freezed == imageUrl ? _self.imageUrl : imageUrl // ignore: cast_nullable_to_non_nullable
? _self.location as String?,attractiveness: freezed == attractiveness ? _self.attractiveness : attractiveness // ignore: cast_nullable_to_non_nullable
: location // ignore: cast_nullable_to_non_nullable as int?,tagCount: freezed == tagCount ? _self.tagCount : tagCount // ignore: cast_nullable_to_non_nullable
as List<double>, as int?,durationMinutes: freezed == durationMinutes ? _self.durationMinutes : durationMinutes // ignore: cast_nullable_to_non_nullable
type: null == type as int?,visited: freezed == visited ? _self.visited : visited // ignore: cast_nullable_to_non_nullable
? _self.type as bool?,timeToReachNextMinutes: freezed == timeToReachNextMinutes ? _self.timeToReachNextMinutes : timeToReachNextMinutes // ignore: cast_nullable_to_non_nullable
: type // ignore: cast_nullable_to_non_nullable as int?,
as LandmarkType,
isSecondary: null == isSecondary
? _self.isSecondary
: isSecondary // ignore: cast_nullable_to_non_nullable
as bool,
description: null == description
? _self.description
: description // ignore: cast_nullable_to_non_nullable
as LandmarkDescription,
)); ));
} }
@@ -429,17 +328,20 @@ class __$LandmarkCopyWithImpl<$Res> implements _$LandmarkCopyWith<$Res> {
@override @override
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
$LandmarkTypeCopyWith<$Res> get type { $LandmarkTypeCopyWith<$Res> get type {
return $LandmarkTypeCopyWith<$Res>(_self.type, (value) { return $LandmarkTypeCopyWith<$Res>(_self.type, (value) {
return _then(_self.copyWith(type: value)); return _then(_self.copyWith(type: value));
}); });
} }/// Create a copy of Landmark
/// Create a copy of Landmark
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
$LandmarkDescriptionCopyWith<$Res> get description { $LandmarkDescriptionCopyWith<$Res>? get description {
return $LandmarkDescriptionCopyWith<$Res>(_self.description, (value) { if (_self.description == null) {
return null;
}
return $LandmarkDescriptionCopyWith<$Res>(_self.description!, (value) {
return _then(_self.copyWith(description: value)); return _then(_self.copyWith(description: value));
}); });
} }

View File

@@ -13,9 +13,20 @@ _Landmark _$LandmarkFromJson(Map<String, dynamic> json) => _Landmark(
.map((e) => (e as num).toDouble()) .map((e) => (e as num).toDouble())
.toList(), .toList(),
type: LandmarkType.fromJson(json['type'] as Map<String, dynamic>), type: LandmarkType.fromJson(json['type'] as Map<String, dynamic>),
isSecondary: json['isSecondary'] as bool, isSecondary: json['is_secondary'] as bool?,
description: LandmarkDescription.fromJson( description: json['description'] == null
json['description'] as Map<String, dynamic>), ? null
: LandmarkDescription.fromJson(
json['description'] as Map<String, dynamic>,
),
nameEn: json['name_en'] as String?,
websiteUrl: json['website_url'] as String?,
imageUrl: json['image_url'] as String?,
attractiveness: (json['attractiveness'] as num?)?.toInt(),
tagCount: (json['n_tags'] as num?)?.toInt(),
durationMinutes: (json['duration'] as num?)?.toInt(),
visited: json['visited'] as bool?,
timeToReachNextMinutes: (json['time_to_reach_next'] as num?)?.toInt(),
); );
Map<String, dynamic> _$LandmarkToJson(_Landmark instance) => <String, dynamic>{ Map<String, dynamic> _$LandmarkToJson(_Landmark instance) => <String, dynamic>{
@@ -23,6 +34,14 @@ Map<String, dynamic> _$LandmarkToJson(_Landmark instance) => <String, dynamic>{
'name': instance.name, 'name': instance.name,
'location': instance.location, 'location': instance.location,
'type': instance.type, 'type': instance.type,
'isSecondary': instance.isSecondary, 'is_secondary': instance.isSecondary,
'description': instance.description, 'description': instance.description,
'name_en': instance.nameEn,
'website_url': instance.websiteUrl,
'image_url': instance.imageUrl,
'attractiveness': instance.attractiveness,
'n_tags': instance.tagCount,
'duration': instance.durationMinutes,
'visited': instance.visited,
'time_to_reach_next': instance.timeToReachNextMinutes,
}; };

View File

@@ -3,7 +3,7 @@ part 'landmark_description.freezed.dart';
part 'landmark_description.g.dart'; part 'landmark_description.g.dart';
@Freezed(makeCollectionsUnmodifiable: false) @freezed
abstract class LandmarkDescription with _$LandmarkDescription { abstract class LandmarkDescription with _$LandmarkDescription {
const factory LandmarkDescription({ const factory LandmarkDescription({
required String description, required String description,

View File

@@ -14,50 +14,47 @@ T _$identity<T>(T value) => value;
/// @nodoc /// @nodoc
mixin _$LandmarkDescription { mixin _$LandmarkDescription {
String get description;
List<String> get tags;
String get description; List<String> get tags;
/// Create a copy of LandmarkDescription /// Create a copy of LandmarkDescription
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
$LandmarkDescriptionCopyWith<LandmarkDescription> get copyWith => $LandmarkDescriptionCopyWith<LandmarkDescription> get copyWith => _$LandmarkDescriptionCopyWithImpl<LandmarkDescription>(this as LandmarkDescription, _$identity);
_$LandmarkDescriptionCopyWithImpl<LandmarkDescription>(
this as LandmarkDescription, _$identity);
/// Serializes this LandmarkDescription to a JSON map. /// Serializes this LandmarkDescription to a JSON map.
Map<String, dynamic> toJson(); Map<String, dynamic> toJson();
@override @override
bool operator ==(Object other) { bool operator ==(Object other) {
return identical(this, other) || return identical(this, other) || (other.runtimeType == runtimeType&&other is LandmarkDescription&&(identical(other.description, description) || other.description == description)&&const DeepCollectionEquality().equals(other.tags, tags));
(other.runtimeType == runtimeType &&
other is LandmarkDescription &&
(identical(other.description, description) ||
other.description == description) &&
const DeepCollectionEquality().equals(other.tags, tags));
} }
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@override @override
int get hashCode => Object.hash( int get hashCode => Object.hash(runtimeType,description,const DeepCollectionEquality().hash(tags));
runtimeType, description, const DeepCollectionEquality().hash(tags));
@override @override
String toString() { String toString() {
return 'LandmarkDescription(description: $description, tags: $tags)'; return 'LandmarkDescription(description: $description, tags: $tags)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class $LandmarkDescriptionCopyWith<$Res> { abstract mixin class $LandmarkDescriptionCopyWith<$Res> {
factory $LandmarkDescriptionCopyWith( factory $LandmarkDescriptionCopyWith(LandmarkDescription value, $Res Function(LandmarkDescription) _then) = _$LandmarkDescriptionCopyWithImpl;
LandmarkDescription value, $Res Function(LandmarkDescription) _then) =
_$LandmarkDescriptionCopyWithImpl;
@useResult @useResult
$Res call({String description, List<String> tags}); $Res call({
} String description, List<String> tags
});
}
/// @nodoc /// @nodoc
class _$LandmarkDescriptionCopyWithImpl<$Res> class _$LandmarkDescriptionCopyWithImpl<$Res>
implements $LandmarkDescriptionCopyWith<$Res> { implements $LandmarkDescriptionCopyWith<$Res> {
@@ -68,25 +65,17 @@ class _$LandmarkDescriptionCopyWithImpl<$Res>
/// Create a copy of LandmarkDescription /// Create a copy of LandmarkDescription
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline') @override $Res call({Object? description = null,Object? tags = null,}) {
@override
$Res call({
Object? description = null,
Object? tags = null,
}) {
return _then(_self.copyWith( return _then(_self.copyWith(
description: null == description description: null == description ? _self.description : description // ignore: cast_nullable_to_non_nullable
? _self.description as String,tags: null == tags ? _self.tags : tags // ignore: cast_nullable_to_non_nullable
: description // ignore: cast_nullable_to_non_nullable
as String,
tags: null == tags
? _self.tags
: tags // ignore: cast_nullable_to_non_nullable
as List<String>, as List<String>,
)); ));
} }
} }
/// Adds pattern-matching-related methods to [LandmarkDescription]. /// Adds pattern-matching-related methods to [LandmarkDescription].
extension LandmarkDescriptionPatterns on LandmarkDescription { extension LandmarkDescriptionPatterns on LandmarkDescription {
/// A variant of `map` that fallback to returning `orElse`. /// A variant of `map` that fallback to returning `orElse`.
@@ -101,20 +90,15 @@ extension LandmarkDescriptionPatterns on LandmarkDescription {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeMap<TResult extends Object?>(TResult Function( _LandmarkDescription value)? $default,{required TResult orElse(),}){
TResult maybeMap<TResult extends Object?>(
TResult Function(_LandmarkDescription value)? $default, {
required TResult orElse(),
}) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _LandmarkDescription() when $default != null: case _LandmarkDescription() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// Callbacks receives the raw object, upcasted. /// Callbacks receives the raw object, upcasted.
@@ -128,19 +112,15 @@ extension LandmarkDescriptionPatterns on LandmarkDescription {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult map<TResult extends Object?>(TResult Function( _LandmarkDescription value) $default,){
TResult map<TResult extends Object?>(
TResult Function(_LandmarkDescription value) $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _LandmarkDescription(): case _LandmarkDescription():
return $default(_that); return $default(_that);case _:
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `map` that fallback to returning `null`. /// A variant of `map` that fallback to returning `null`.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -153,19 +133,15 @@ extension LandmarkDescriptionPatterns on LandmarkDescription {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? mapOrNull<TResult extends Object?>(TResult? Function( _LandmarkDescription value)? $default,){
TResult? mapOrNull<TResult extends Object?>(
TResult? Function(_LandmarkDescription value)? $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _LandmarkDescription() when $default != null: case _LandmarkDescription() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return null; return null;
}
}
}
}
/// A variant of `when` that fallback to an `orElse` callback. /// A variant of `when` that fallback to an `orElse` callback.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -178,20 +154,14 @@ extension LandmarkDescriptionPatterns on LandmarkDescription {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( String description, List<String> tags)? $default,{required TResult orElse(),}) {final _that = this;
TResult maybeWhen<TResult extends Object?>(
TResult Function(String description, List<String> tags)? $default, {
required TResult orElse(),
}) {
final _that = this;
switch (_that) { switch (_that) {
case _LandmarkDescription() when $default != null: case _LandmarkDescription() when $default != null:
return $default(_that.description, _that.tags); return $default(_that.description,_that.tags);case _:
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// As opposed to `map`, this offers destructuring. /// As opposed to `map`, this offers destructuring.
@@ -205,19 +175,14 @@ extension LandmarkDescriptionPatterns on LandmarkDescription {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( String description, List<String> tags) $default,) {final _that = this;
TResult when<TResult extends Object?>(
TResult Function(String description, List<String> tags) $default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _LandmarkDescription(): case _LandmarkDescription():
return $default(_that.description, _that.tags); return $default(_that.description,_that.tags);case _:
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `when` that fallback to returning `null` /// A variant of `when` that fallback to returning `null`
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -230,80 +195,73 @@ extension LandmarkDescriptionPatterns on LandmarkDescription {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( String description, List<String> tags)? $default,) {final _that = this;
TResult? whenOrNull<TResult extends Object?>(
TResult? Function(String description, List<String> tags)? $default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _LandmarkDescription() when $default != null: case _LandmarkDescription() when $default != null:
return $default(_that.description, _that.tags); return $default(_that.description,_that.tags);case _:
case _:
return null; return null;
} }
} }
} }
/// @nodoc /// @nodoc
@JsonSerializable() @JsonSerializable()
class _LandmarkDescription implements LandmarkDescription {
const _LandmarkDescription({required this.description, required this.tags});
factory _LandmarkDescription.fromJson(Map<String, dynamic> json) =>
_$LandmarkDescriptionFromJson(json);
@override class _LandmarkDescription implements LandmarkDescription {
final String description; const _LandmarkDescription({required this.description, required final List<String> tags}): _tags = tags;
@override factory _LandmarkDescription.fromJson(Map<String, dynamic> json) => _$LandmarkDescriptionFromJson(json);
final List<String> tags;
@override final String description;
final List<String> _tags;
@override List<String> get tags {
if (_tags is EqualUnmodifiableListView) return _tags;
// ignore: implicit_dynamic_type
return EqualUnmodifiableListView(_tags);
}
/// Create a copy of LandmarkDescription /// Create a copy of LandmarkDescription
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @JsonKey(includeFromJson: false, includeToJson: false)
@JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
_$LandmarkDescriptionCopyWith<_LandmarkDescription> get copyWith => _$LandmarkDescriptionCopyWith<_LandmarkDescription> get copyWith => __$LandmarkDescriptionCopyWithImpl<_LandmarkDescription>(this, _$identity);
__$LandmarkDescriptionCopyWithImpl<_LandmarkDescription>(
this, _$identity);
@override @override
Map<String, dynamic> toJson() { Map<String, dynamic> toJson() {
return _$LandmarkDescriptionToJson( return _$LandmarkDescriptionToJson(this, );
this,
);
} }
@override @override
bool operator ==(Object other) { bool operator ==(Object other) {
return identical(this, other) || return identical(this, other) || (other.runtimeType == runtimeType&&other is _LandmarkDescription&&(identical(other.description, description) || other.description == description)&&const DeepCollectionEquality().equals(other._tags, _tags));
(other.runtimeType == runtimeType &&
other is _LandmarkDescription &&
(identical(other.description, description) ||
other.description == description) &&
const DeepCollectionEquality().equals(other.tags, tags));
} }
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@override @override
int get hashCode => Object.hash( int get hashCode => Object.hash(runtimeType,description,const DeepCollectionEquality().hash(_tags));
runtimeType, description, const DeepCollectionEquality().hash(tags));
@override @override
String toString() { String toString() {
return 'LandmarkDescription(description: $description, tags: $tags)'; return 'LandmarkDescription(description: $description, tags: $tags)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class _$LandmarkDescriptionCopyWith<$Res> abstract mixin class _$LandmarkDescriptionCopyWith<$Res> implements $LandmarkDescriptionCopyWith<$Res> {
implements $LandmarkDescriptionCopyWith<$Res> { factory _$LandmarkDescriptionCopyWith(_LandmarkDescription value, $Res Function(_LandmarkDescription) _then) = __$LandmarkDescriptionCopyWithImpl;
factory _$LandmarkDescriptionCopyWith(_LandmarkDescription value, @override @useResult
$Res Function(_LandmarkDescription) _then) = $Res call({
__$LandmarkDescriptionCopyWithImpl; String description, List<String> tags
@override });
@useResult
$Res call({String description, List<String> tags});
}
}
/// @nodoc /// @nodoc
class __$LandmarkDescriptionCopyWithImpl<$Res> class __$LandmarkDescriptionCopyWithImpl<$Res>
implements _$LandmarkDescriptionCopyWith<$Res> { implements _$LandmarkDescriptionCopyWith<$Res> {
@@ -314,23 +272,15 @@ class __$LandmarkDescriptionCopyWithImpl<$Res>
/// Create a copy of LandmarkDescription /// Create a copy of LandmarkDescription
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @pragma('vm:prefer-inline') $Res call({Object? description = null,Object? tags = null,}) {
@pragma('vm:prefer-inline')
$Res call({
Object? description = null,
Object? tags = null,
}) {
return _then(_LandmarkDescription( return _then(_LandmarkDescription(
description: null == description description: null == description ? _self.description : description // ignore: cast_nullable_to_non_nullable
? _self.description as String,tags: null == tags ? _self._tags : tags // ignore: cast_nullable_to_non_nullable
: description // ignore: cast_nullable_to_non_nullable
as String,
tags: null == tags
? _self.tags
: tags // ignore: cast_nullable_to_non_nullable
as List<String>, as List<String>,
)); ));
} }
} }
// dart format on // dart format on

View File

@@ -13,8 +13,8 @@ _LandmarkDescription _$LandmarkDescriptionFromJson(Map<String, dynamic> json) =>
); );
Map<String, dynamic> _$LandmarkDescriptionToJson( Map<String, dynamic> _$LandmarkDescriptionToJson(
_LandmarkDescription instance) => _LandmarkDescription instance,
<String, dynamic>{ ) => <String, dynamic>{
'description': instance.description, 'description': instance.description,
'tags': instance.tags, 'tags': instance.tags,
}; };

View File

@@ -14,12 +14,16 @@ abstract class LandmarkType with _$LandmarkType {
@JsonEnum(alwaysCreate: true) @JsonEnum(alwaysCreate: true)
enum LandmarkTypeEnum { enum LandmarkTypeEnum {
@JsonValue('culture') @JsonValue('sightseeing')
culture, sightseeing,
@JsonValue('nature') @JsonValue('nature')
nature, nature,
@JsonValue('shopping') @JsonValue('shopping')
shopping, shopping,
@JsonValue('start')
start,
@JsonValue('finish')
finish,
} }
extension LandmarkTypeEnumExtension on LandmarkTypeEnum { extension LandmarkTypeEnumExtension on LandmarkTypeEnum {

View File

@@ -14,25 +14,21 @@ T _$identity<T>(T value) => value;
/// @nodoc /// @nodoc
mixin _$LandmarkType { mixin _$LandmarkType {
LandmarkTypeEnum get type;
LandmarkTypeEnum get type;
/// Create a copy of LandmarkType /// Create a copy of LandmarkType
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
$LandmarkTypeCopyWith<LandmarkType> get copyWith => $LandmarkTypeCopyWith<LandmarkType> get copyWith => _$LandmarkTypeCopyWithImpl<LandmarkType>(this as LandmarkType, _$identity);
_$LandmarkTypeCopyWithImpl<LandmarkType>(
this as LandmarkType, _$identity);
/// Serializes this LandmarkType to a JSON map. /// Serializes this LandmarkType to a JSON map.
Map<String, dynamic> toJson(); Map<String, dynamic> toJson();
@override @override
bool operator ==(Object other) { bool operator ==(Object other) {
return identical(this, other) || return identical(this, other) || (other.runtimeType == runtimeType&&other is LandmarkType&&(identical(other.type, type) || other.type == type));
(other.runtimeType == runtimeType &&
other is LandmarkType &&
(identical(other.type, type) || other.type == type));
} }
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@@ -43,19 +39,25 @@ mixin _$LandmarkType {
String toString() { String toString() {
return 'LandmarkType(type: $type)'; return 'LandmarkType(type: $type)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class $LandmarkTypeCopyWith<$Res> { abstract mixin class $LandmarkTypeCopyWith<$Res> {
factory $LandmarkTypeCopyWith( factory $LandmarkTypeCopyWith(LandmarkType value, $Res Function(LandmarkType) _then) = _$LandmarkTypeCopyWithImpl;
LandmarkType value, $Res Function(LandmarkType) _then) =
_$LandmarkTypeCopyWithImpl;
@useResult @useResult
$Res call({LandmarkTypeEnum type}); $Res call({
} LandmarkTypeEnum type
});
}
/// @nodoc /// @nodoc
class _$LandmarkTypeCopyWithImpl<$Res> implements $LandmarkTypeCopyWith<$Res> { class _$LandmarkTypeCopyWithImpl<$Res>
implements $LandmarkTypeCopyWith<$Res> {
_$LandmarkTypeCopyWithImpl(this._self, this._then); _$LandmarkTypeCopyWithImpl(this._self, this._then);
final LandmarkType _self; final LandmarkType _self;
@@ -63,20 +65,16 @@ class _$LandmarkTypeCopyWithImpl<$Res> implements $LandmarkTypeCopyWith<$Res> {
/// Create a copy of LandmarkType /// Create a copy of LandmarkType
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline') @override $Res call({Object? type = null,}) {
@override
$Res call({
Object? type = null,
}) {
return _then(_self.copyWith( return _then(_self.copyWith(
type: null == type type: null == type ? _self.type : type // ignore: cast_nullable_to_non_nullable
? _self.type
: type // ignore: cast_nullable_to_non_nullable
as LandmarkTypeEnum, as LandmarkTypeEnum,
)); ));
} }
} }
/// Adds pattern-matching-related methods to [LandmarkType]. /// Adds pattern-matching-related methods to [LandmarkType].
extension LandmarkTypePatterns on LandmarkType { extension LandmarkTypePatterns on LandmarkType {
/// A variant of `map` that fallback to returning `orElse`. /// A variant of `map` that fallback to returning `orElse`.
@@ -91,20 +89,15 @@ extension LandmarkTypePatterns on LandmarkType {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeMap<TResult extends Object?>(TResult Function( _LandmarkType value)? $default,{required TResult orElse(),}){
TResult maybeMap<TResult extends Object?>(
TResult Function(_LandmarkType value)? $default, {
required TResult orElse(),
}) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _LandmarkType() when $default != null: case _LandmarkType() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// Callbacks receives the raw object, upcasted. /// Callbacks receives the raw object, upcasted.
@@ -118,19 +111,15 @@ extension LandmarkTypePatterns on LandmarkType {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult map<TResult extends Object?>(TResult Function( _LandmarkType value) $default,){
TResult map<TResult extends Object?>(
TResult Function(_LandmarkType value) $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _LandmarkType(): case _LandmarkType():
return $default(_that); return $default(_that);case _:
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `map` that fallback to returning `null`. /// A variant of `map` that fallback to returning `null`.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -143,19 +132,15 @@ extension LandmarkTypePatterns on LandmarkType {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? mapOrNull<TResult extends Object?>(TResult? Function( _LandmarkType value)? $default,){
TResult? mapOrNull<TResult extends Object?>(
TResult? Function(_LandmarkType value)? $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _LandmarkType() when $default != null: case _LandmarkType() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return null; return null;
}
}
}
}
/// A variant of `when` that fallback to an `orElse` callback. /// A variant of `when` that fallback to an `orElse` callback.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -168,20 +153,14 @@ extension LandmarkTypePatterns on LandmarkType {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( LandmarkTypeEnum type)? $default,{required TResult orElse(),}) {final _that = this;
TResult maybeWhen<TResult extends Object?>(
TResult Function(LandmarkTypeEnum type)? $default, {
required TResult orElse(),
}) {
final _that = this;
switch (_that) { switch (_that) {
case _LandmarkType() when $default != null: case _LandmarkType() when $default != null:
return $default(_that.type); return $default(_that.type);case _:
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// As opposed to `map`, this offers destructuring. /// As opposed to `map`, this offers destructuring.
@@ -195,19 +174,14 @@ extension LandmarkTypePatterns on LandmarkType {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( LandmarkTypeEnum type) $default,) {final _that = this;
TResult when<TResult extends Object?>(
TResult Function(LandmarkTypeEnum type) $default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _LandmarkType(): case _LandmarkType():
return $default(_that.type); return $default(_that.type);case _:
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `when` that fallback to returning `null` /// A variant of `when` that fallback to returning `null`
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -220,51 +194,40 @@ extension LandmarkTypePatterns on LandmarkType {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( LandmarkTypeEnum type)? $default,) {final _that = this;
TResult? whenOrNull<TResult extends Object?>(
TResult? Function(LandmarkTypeEnum type)? $default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _LandmarkType() when $default != null: case _LandmarkType() when $default != null:
return $default(_that.type); return $default(_that.type);case _:
case _:
return null; return null;
} }
} }
} }
/// @nodoc /// @nodoc
@JsonSerializable() @JsonSerializable()
class _LandmarkType implements LandmarkType { class _LandmarkType implements LandmarkType {
const _LandmarkType({required this.type}); const _LandmarkType({required this.type});
factory _LandmarkType.fromJson(Map<String, dynamic> json) => factory _LandmarkType.fromJson(Map<String, dynamic> json) => _$LandmarkTypeFromJson(json);
_$LandmarkTypeFromJson(json);
@override @override final LandmarkTypeEnum type;
final LandmarkTypeEnum type;
/// Create a copy of LandmarkType /// Create a copy of LandmarkType
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @JsonKey(includeFromJson: false, includeToJson: false)
@JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
_$LandmarkTypeCopyWith<_LandmarkType> get copyWith => _$LandmarkTypeCopyWith<_LandmarkType> get copyWith => __$LandmarkTypeCopyWithImpl<_LandmarkType>(this, _$identity);
__$LandmarkTypeCopyWithImpl<_LandmarkType>(this, _$identity);
@override @override
Map<String, dynamic> toJson() { Map<String, dynamic> toJson() {
return _$LandmarkTypeToJson( return _$LandmarkTypeToJson(this, );
this,
);
} }
@override @override
bool operator ==(Object other) { bool operator ==(Object other) {
return identical(this, other) || return identical(this, other) || (other.runtimeType == runtimeType&&other is _LandmarkType&&(identical(other.type, type) || other.type == type));
(other.runtimeType == runtimeType &&
other is _LandmarkType &&
(identical(other.type, type) || other.type == type));
} }
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@@ -275,19 +238,22 @@ class _LandmarkType implements LandmarkType {
String toString() { String toString() {
return 'LandmarkType(type: $type)'; return 'LandmarkType(type: $type)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class _$LandmarkTypeCopyWith<$Res> abstract mixin class _$LandmarkTypeCopyWith<$Res> implements $LandmarkTypeCopyWith<$Res> {
implements $LandmarkTypeCopyWith<$Res> { factory _$LandmarkTypeCopyWith(_LandmarkType value, $Res Function(_LandmarkType) _then) = __$LandmarkTypeCopyWithImpl;
factory _$LandmarkTypeCopyWith( @override @useResult
_LandmarkType value, $Res Function(_LandmarkType) _then) = $Res call({
__$LandmarkTypeCopyWithImpl; LandmarkTypeEnum type
@override });
@useResult
$Res call({LandmarkTypeEnum type});
}
}
/// @nodoc /// @nodoc
class __$LandmarkTypeCopyWithImpl<$Res> class __$LandmarkTypeCopyWithImpl<$Res>
implements _$LandmarkTypeCopyWith<$Res> { implements _$LandmarkTypeCopyWith<$Res> {
@@ -298,18 +264,14 @@ class __$LandmarkTypeCopyWithImpl<$Res>
/// Create a copy of LandmarkType /// Create a copy of LandmarkType
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @pragma('vm:prefer-inline') $Res call({Object? type = null,}) {
@pragma('vm:prefer-inline')
$Res call({
Object? type = null,
}) {
return _then(_LandmarkType( return _then(_LandmarkType(
type: null == type type: null == type ? _self.type : type // ignore: cast_nullable_to_non_nullable
? _self.type
: type // ignore: cast_nullable_to_non_nullable
as LandmarkTypeEnum, as LandmarkTypeEnum,
)); ));
} }
} }
// dart format on // dart format on

View File

@@ -7,17 +7,15 @@ part of 'landmark_type.dart';
// ************************************************************************** // **************************************************************************
_LandmarkType _$LandmarkTypeFromJson(Map<String, dynamic> json) => _LandmarkType _$LandmarkTypeFromJson(Map<String, dynamic> json) =>
_LandmarkType( _LandmarkType(type: $enumDecode(_$LandmarkTypeEnumEnumMap, json['type']));
type: $enumDecode(_$LandmarkTypeEnumEnumMap, json['type']),
);
Map<String, dynamic> _$LandmarkTypeToJson(_LandmarkType instance) => Map<String, dynamic> _$LandmarkTypeToJson(_LandmarkType instance) =>
<String, dynamic>{ <String, dynamic>{'type': _$LandmarkTypeEnumEnumMap[instance.type]!};
'type': _$LandmarkTypeEnumEnumMap[instance.type]!,
};
const _$LandmarkTypeEnumEnumMap = { const _$LandmarkTypeEnumEnumMap = {
LandmarkTypeEnum.culture: 'culture', LandmarkTypeEnum.sightseeing: 'sightseeing',
LandmarkTypeEnum.nature: 'nature', LandmarkTypeEnum.nature: 'nature',
LandmarkTypeEnum.shopping: 'shopping', LandmarkTypeEnum.shopping: 'shopping',
LandmarkTypeEnum.start: 'start',
LandmarkTypeEnum.finish: 'finish',
}; };

View File

@@ -5,7 +5,20 @@ part 'preferences.g.dart';
@freezed @freezed
abstract class Preferences with _$Preferences { abstract class Preferences with _$Preferences {
const factory Preferences({ const factory Preferences({
required String test, /// Scores keyed by preference type (e.g. 'sightseeing', 'shopping', 'nature')
required Map<String, int> scores,
/// Maximum trip duration in minutes
required int maxTimeMinutes,
/// Required start location [lat, lon]
required List<double> startLocation,
/// Optional end location
List<double>? endLocation,
/// Optional detour tolerance in minutes
int? detourToleranceMinutes,
}) = _Preferences; }) = _Preferences;
factory Preferences.fromJson(Map<String, Object?> json) => _$PreferencesFromJson(json); factory Preferences.fromJson(Map<String, Object?> json) => _$PreferencesFromJson(json);

View File

@@ -14,47 +14,55 @@ T _$identity<T>(T value) => value;
/// @nodoc /// @nodoc
mixin _$Preferences { mixin _$Preferences {
String get test;
/// Scores keyed by preference type (e.g. 'sightseeing', 'shopping', 'nature')
Map<String, int> get scores;/// Maximum trip duration in minutes
int get maxTimeMinutes;/// Required start location [lat, lon]
List<double> get startLocation;/// Optional end location
List<double>? get endLocation;/// Optional detour tolerance in minutes
int? get detourToleranceMinutes;
/// Create a copy of Preferences /// Create a copy of Preferences
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
$PreferencesCopyWith<Preferences> get copyWith => $PreferencesCopyWith<Preferences> get copyWith => _$PreferencesCopyWithImpl<Preferences>(this as Preferences, _$identity);
_$PreferencesCopyWithImpl<Preferences>(this as Preferences, _$identity);
/// Serializes this Preferences to a JSON map. /// Serializes this Preferences to a JSON map.
Map<String, dynamic> toJson(); Map<String, dynamic> toJson();
@override @override
bool operator ==(Object other) { bool operator ==(Object other) {
return identical(this, other) || return identical(this, other) || (other.runtimeType == runtimeType&&other is Preferences&&const DeepCollectionEquality().equals(other.scores, scores)&&(identical(other.maxTimeMinutes, maxTimeMinutes) || other.maxTimeMinutes == maxTimeMinutes)&&const DeepCollectionEquality().equals(other.startLocation, startLocation)&&const DeepCollectionEquality().equals(other.endLocation, endLocation)&&(identical(other.detourToleranceMinutes, detourToleranceMinutes) || other.detourToleranceMinutes == detourToleranceMinutes));
(other.runtimeType == runtimeType &&
other is Preferences &&
(identical(other.test, test) || other.test == test));
} }
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@override @override
int get hashCode => Object.hash(runtimeType, test); int get hashCode => Object.hash(runtimeType,const DeepCollectionEquality().hash(scores),maxTimeMinutes,const DeepCollectionEquality().hash(startLocation),const DeepCollectionEquality().hash(endLocation),detourToleranceMinutes);
@override @override
String toString() { String toString() {
return 'Preferences(test: $test)'; return 'Preferences(scores: $scores, maxTimeMinutes: $maxTimeMinutes, startLocation: $startLocation, endLocation: $endLocation, detourToleranceMinutes: $detourToleranceMinutes)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class $PreferencesCopyWith<$Res> { abstract mixin class $PreferencesCopyWith<$Res> {
factory $PreferencesCopyWith( factory $PreferencesCopyWith(Preferences value, $Res Function(Preferences) _then) = _$PreferencesCopyWithImpl;
Preferences value, $Res Function(Preferences) _then) =
_$PreferencesCopyWithImpl;
@useResult @useResult
$Res call({String test}); $Res call({
} Map<String, int> scores, int maxTimeMinutes, List<double> startLocation, List<double>? endLocation, int? detourToleranceMinutes
});
}
/// @nodoc /// @nodoc
class _$PreferencesCopyWithImpl<$Res> implements $PreferencesCopyWith<$Res> { class _$PreferencesCopyWithImpl<$Res>
implements $PreferencesCopyWith<$Res> {
_$PreferencesCopyWithImpl(this._self, this._then); _$PreferencesCopyWithImpl(this._self, this._then);
final Preferences _self; final Preferences _self;
@@ -62,20 +70,20 @@ class _$PreferencesCopyWithImpl<$Res> implements $PreferencesCopyWith<$Res> {
/// Create a copy of Preferences /// Create a copy of Preferences
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline') @override $Res call({Object? scores = null,Object? maxTimeMinutes = null,Object? startLocation = null,Object? endLocation = freezed,Object? detourToleranceMinutes = freezed,}) {
@override
$Res call({
Object? test = null,
}) {
return _then(_self.copyWith( return _then(_self.copyWith(
test: null == test scores: null == scores ? _self.scores : scores // ignore: cast_nullable_to_non_nullable
? _self.test as Map<String, int>,maxTimeMinutes: null == maxTimeMinutes ? _self.maxTimeMinutes : maxTimeMinutes // ignore: cast_nullable_to_non_nullable
: test // ignore: cast_nullable_to_non_nullable as int,startLocation: null == startLocation ? _self.startLocation : startLocation // ignore: cast_nullable_to_non_nullable
as String, as List<double>,endLocation: freezed == endLocation ? _self.endLocation : endLocation // ignore: cast_nullable_to_non_nullable
as List<double>?,detourToleranceMinutes: freezed == detourToleranceMinutes ? _self.detourToleranceMinutes : detourToleranceMinutes // ignore: cast_nullable_to_non_nullable
as int?,
)); ));
} }
} }
/// Adds pattern-matching-related methods to [Preferences]. /// Adds pattern-matching-related methods to [Preferences].
extension PreferencesPatterns on Preferences { extension PreferencesPatterns on Preferences {
/// A variant of `map` that fallback to returning `orElse`. /// A variant of `map` that fallback to returning `orElse`.
@@ -90,20 +98,15 @@ extension PreferencesPatterns on Preferences {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeMap<TResult extends Object?>(TResult Function( _Preferences value)? $default,{required TResult orElse(),}){
TResult maybeMap<TResult extends Object?>(
TResult Function(_Preferences value)? $default, {
required TResult orElse(),
}) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _Preferences() when $default != null: case _Preferences() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// Callbacks receives the raw object, upcasted. /// Callbacks receives the raw object, upcasted.
@@ -117,19 +120,15 @@ extension PreferencesPatterns on Preferences {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult map<TResult extends Object?>(TResult Function( _Preferences value) $default,){
TResult map<TResult extends Object?>(
TResult Function(_Preferences value) $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _Preferences(): case _Preferences():
return $default(_that); return $default(_that);case _:
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `map` that fallback to returning `null`. /// A variant of `map` that fallback to returning `null`.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -142,19 +141,15 @@ extension PreferencesPatterns on Preferences {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? mapOrNull<TResult extends Object?>(TResult? Function( _Preferences value)? $default,){
TResult? mapOrNull<TResult extends Object?>(
TResult? Function(_Preferences value)? $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _Preferences() when $default != null: case _Preferences() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return null; return null;
}
}
}
}
/// A variant of `when` that fallback to an `orElse` callback. /// A variant of `when` that fallback to an `orElse` callback.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -167,20 +162,14 @@ extension PreferencesPatterns on Preferences {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( Map<String, int> scores, int maxTimeMinutes, List<double> startLocation, List<double>? endLocation, int? detourToleranceMinutes)? $default,{required TResult orElse(),}) {final _that = this;
TResult maybeWhen<TResult extends Object?>(
TResult Function(String test)? $default, {
required TResult orElse(),
}) {
final _that = this;
switch (_that) { switch (_that) {
case _Preferences() when $default != null: case _Preferences() when $default != null:
return $default(_that.test); return $default(_that.scores,_that.maxTimeMinutes,_that.startLocation,_that.endLocation,_that.detourToleranceMinutes);case _:
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// As opposed to `map`, this offers destructuring. /// As opposed to `map`, this offers destructuring.
@@ -194,19 +183,14 @@ extension PreferencesPatterns on Preferences {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( Map<String, int> scores, int maxTimeMinutes, List<double> startLocation, List<double>? endLocation, int? detourToleranceMinutes) $default,) {final _that = this;
TResult when<TResult extends Object?>(
TResult Function(String test) $default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _Preferences(): case _Preferences():
return $default(_that.test); return $default(_that.scores,_that.maxTimeMinutes,_that.startLocation,_that.endLocation,_that.detourToleranceMinutes);case _:
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `when` that fallback to returning `null` /// A variant of `when` that fallback to returning `null`
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -219,76 +203,101 @@ extension PreferencesPatterns on Preferences {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( Map<String, int> scores, int maxTimeMinutes, List<double> startLocation, List<double>? endLocation, int? detourToleranceMinutes)? $default,) {final _that = this;
TResult? whenOrNull<TResult extends Object?>(
TResult? Function(String test)? $default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _Preferences() when $default != null: case _Preferences() when $default != null:
return $default(_that.test); return $default(_that.scores,_that.maxTimeMinutes,_that.startLocation,_that.endLocation,_that.detourToleranceMinutes);case _:
case _:
return null; return null;
} }
} }
} }
/// @nodoc /// @nodoc
@JsonSerializable() @JsonSerializable()
class _Preferences implements Preferences {
const _Preferences({required this.test});
factory _Preferences.fromJson(Map<String, dynamic> json) =>
_$PreferencesFromJson(json);
@override class _Preferences implements Preferences {
final String test; const _Preferences({required final Map<String, int> scores, required this.maxTimeMinutes, required final List<double> startLocation, final List<double>? endLocation, this.detourToleranceMinutes}): _scores = scores,_startLocation = startLocation,_endLocation = endLocation;
factory _Preferences.fromJson(Map<String, dynamic> json) => _$PreferencesFromJson(json);
/// Scores keyed by preference type (e.g. 'sightseeing', 'shopping', 'nature')
final Map<String, int> _scores;
/// Scores keyed by preference type (e.g. 'sightseeing', 'shopping', 'nature')
@override Map<String, int> get scores {
if (_scores is EqualUnmodifiableMapView) return _scores;
// ignore: implicit_dynamic_type
return EqualUnmodifiableMapView(_scores);
}
/// Maximum trip duration in minutes
@override final int maxTimeMinutes;
/// Required start location [lat, lon]
final List<double> _startLocation;
/// Required start location [lat, lon]
@override List<double> get startLocation {
if (_startLocation is EqualUnmodifiableListView) return _startLocation;
// ignore: implicit_dynamic_type
return EqualUnmodifiableListView(_startLocation);
}
/// Optional end location
final List<double>? _endLocation;
/// Optional end location
@override List<double>? get endLocation {
final value = _endLocation;
if (value == null) return null;
if (_endLocation is EqualUnmodifiableListView) return _endLocation;
// ignore: implicit_dynamic_type
return EqualUnmodifiableListView(value);
}
/// Optional detour tolerance in minutes
@override final int? detourToleranceMinutes;
/// Create a copy of Preferences /// Create a copy of Preferences
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @JsonKey(includeFromJson: false, includeToJson: false)
@JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
_$PreferencesCopyWith<_Preferences> get copyWith => _$PreferencesCopyWith<_Preferences> get copyWith => __$PreferencesCopyWithImpl<_Preferences>(this, _$identity);
__$PreferencesCopyWithImpl<_Preferences>(this, _$identity);
@override @override
Map<String, dynamic> toJson() { Map<String, dynamic> toJson() {
return _$PreferencesToJson( return _$PreferencesToJson(this, );
this,
);
} }
@override @override
bool operator ==(Object other) { bool operator ==(Object other) {
return identical(this, other) || return identical(this, other) || (other.runtimeType == runtimeType&&other is _Preferences&&const DeepCollectionEquality().equals(other._scores, _scores)&&(identical(other.maxTimeMinutes, maxTimeMinutes) || other.maxTimeMinutes == maxTimeMinutes)&&const DeepCollectionEquality().equals(other._startLocation, _startLocation)&&const DeepCollectionEquality().equals(other._endLocation, _endLocation)&&(identical(other.detourToleranceMinutes, detourToleranceMinutes) || other.detourToleranceMinutes == detourToleranceMinutes));
(other.runtimeType == runtimeType &&
other is _Preferences &&
(identical(other.test, test) || other.test == test));
} }
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@override @override
int get hashCode => Object.hash(runtimeType, test); int get hashCode => Object.hash(runtimeType,const DeepCollectionEquality().hash(_scores),maxTimeMinutes,const DeepCollectionEquality().hash(_startLocation),const DeepCollectionEquality().hash(_endLocation),detourToleranceMinutes);
@override @override
String toString() { String toString() {
return 'Preferences(test: $test)'; return 'Preferences(scores: $scores, maxTimeMinutes: $maxTimeMinutes, startLocation: $startLocation, endLocation: $endLocation, detourToleranceMinutes: $detourToleranceMinutes)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class _$PreferencesCopyWith<$Res> abstract mixin class _$PreferencesCopyWith<$Res> implements $PreferencesCopyWith<$Res> {
implements $PreferencesCopyWith<$Res> { factory _$PreferencesCopyWith(_Preferences value, $Res Function(_Preferences) _then) = __$PreferencesCopyWithImpl;
factory _$PreferencesCopyWith( @override @useResult
_Preferences value, $Res Function(_Preferences) _then) = $Res call({
__$PreferencesCopyWithImpl; Map<String, int> scores, int maxTimeMinutes, List<double> startLocation, List<double>? endLocation, int? detourToleranceMinutes
@override });
@useResult
$Res call({String test});
}
}
/// @nodoc /// @nodoc
class __$PreferencesCopyWithImpl<$Res> implements _$PreferencesCopyWith<$Res> { class __$PreferencesCopyWithImpl<$Res>
implements _$PreferencesCopyWith<$Res> {
__$PreferencesCopyWithImpl(this._self, this._then); __$PreferencesCopyWithImpl(this._self, this._then);
final _Preferences _self; final _Preferences _self;
@@ -296,18 +305,18 @@ class __$PreferencesCopyWithImpl<$Res> implements _$PreferencesCopyWith<$Res> {
/// Create a copy of Preferences /// Create a copy of Preferences
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @pragma('vm:prefer-inline') $Res call({Object? scores = null,Object? maxTimeMinutes = null,Object? startLocation = null,Object? endLocation = freezed,Object? detourToleranceMinutes = freezed,}) {
@pragma('vm:prefer-inline')
$Res call({
Object? test = null,
}) {
return _then(_Preferences( return _then(_Preferences(
test: null == test scores: null == scores ? _self._scores : scores // ignore: cast_nullable_to_non_nullable
? _self.test as Map<String, int>,maxTimeMinutes: null == maxTimeMinutes ? _self.maxTimeMinutes : maxTimeMinutes // ignore: cast_nullable_to_non_nullable
: test // ignore: cast_nullable_to_non_nullable as int,startLocation: null == startLocation ? _self._startLocation : startLocation // ignore: cast_nullable_to_non_nullable
as String, as List<double>,endLocation: freezed == endLocation ? _self._endLocation : endLocation // ignore: cast_nullable_to_non_nullable
as List<double>?,detourToleranceMinutes: freezed == detourToleranceMinutes ? _self.detourToleranceMinutes : detourToleranceMinutes // ignore: cast_nullable_to_non_nullable
as int?,
)); ));
} }
} }
// dart format on // dart format on

View File

@@ -7,10 +7,22 @@ part of 'preferences.dart';
// ************************************************************************** // **************************************************************************
_Preferences _$PreferencesFromJson(Map<String, dynamic> json) => _Preferences( _Preferences _$PreferencesFromJson(Map<String, dynamic> json) => _Preferences(
test: json['test'] as String, scores: Map<String, int>.from(json['scores'] as Map),
maxTimeMinutes: (json['maxTimeMinutes'] as num).toInt(),
startLocation: (json['startLocation'] as List<dynamic>)
.map((e) => (e as num).toDouble())
.toList(),
endLocation: (json['endLocation'] as List<dynamic>?)
?.map((e) => (e as num).toDouble())
.toList(),
detourToleranceMinutes: (json['detourToleranceMinutes'] as num?)?.toInt(),
); );
Map<String, dynamic> _$PreferencesToJson(_Preferences instance) => Map<String, dynamic> _$PreferencesToJson(_Preferences instance) =>
<String, dynamic>{ <String, dynamic>{
'test': instance.test, 'scores': instance.scores,
'maxTimeMinutes': instance.maxTimeMinutes,
'startLocation': instance.startLocation,
'endLocation': instance.endLocation,
'detourToleranceMinutes': instance.detourToleranceMinutes,
}; };

View File

@@ -5,12 +5,17 @@ part 'trip.freezed.dart';
part 'trip.g.dart'; part 'trip.g.dart';
@Freezed(makeCollectionsUnmodifiable: false) @unfreezed
abstract class Trip with _$Trip { abstract class Trip with _$Trip {
const factory Trip({ factory Trip({
required String uuid, required String uuid,
// Duration totalTime, // Duration totalTime,
/// total time in minutes
int? totalTimeMinutes,
/// ordered list of landmarks in this trip
required List<Landmark> landmarks, required List<Landmark> landmarks,
}) = _Trip; }) = _Trip;

View File

@@ -14,49 +14,49 @@ T _$identity<T>(T value) => value;
/// @nodoc /// @nodoc
mixin _$Trip { mixin _$Trip {
String get uuid; // Duration totalTime,
List<Landmark> get landmarks;
String get uuid; set uuid(String value);// Duration totalTime,
/// total time in minutes
int? get totalTimeMinutes;// Duration totalTime,
/// total time in minutes
set totalTimeMinutes(int? value);/// ordered list of landmarks in this trip
List<Landmark> get landmarks;/// ordered list of landmarks in this trip
set landmarks(List<Landmark> value);
/// Create a copy of Trip /// Create a copy of Trip
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@JsonKey(includeFromJson: false, includeToJson: false) @JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
$TripCopyWith<Trip> get copyWith => $TripCopyWith<Trip> get copyWith => _$TripCopyWithImpl<Trip>(this as Trip, _$identity);
_$TripCopyWithImpl<Trip>(this as Trip, _$identity);
/// Serializes this Trip to a JSON map. /// Serializes this Trip to a JSON map.
Map<String, dynamic> toJson(); Map<String, dynamic> toJson();
@override
bool operator ==(Object other) {
return identical(this, other) ||
(other.runtimeType == runtimeType &&
other is Trip &&
(identical(other.uuid, uuid) || other.uuid == uuid) &&
const DeepCollectionEquality().equals(other.landmarks, landmarks));
}
@JsonKey(includeFromJson: false, includeToJson: false)
@override
int get hashCode => Object.hash(
runtimeType, uuid, const DeepCollectionEquality().hash(landmarks));
@override @override
String toString() { String toString() {
return 'Trip(uuid: $uuid, landmarks: $landmarks)'; return 'Trip(uuid: $uuid, totalTimeMinutes: $totalTimeMinutes, landmarks: $landmarks)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class $TripCopyWith<$Res> { abstract mixin class $TripCopyWith<$Res> {
factory $TripCopyWith(Trip value, $Res Function(Trip) _then) = factory $TripCopyWith(Trip value, $Res Function(Trip) _then) = _$TripCopyWithImpl;
_$TripCopyWithImpl;
@useResult @useResult
$Res call({String uuid, List<Landmark> landmarks}); $Res call({
} String uuid, int? totalTimeMinutes, List<Landmark> landmarks
});
}
/// @nodoc /// @nodoc
class _$TripCopyWithImpl<$Res> implements $TripCopyWith<$Res> { class _$TripCopyWithImpl<$Res>
implements $TripCopyWith<$Res> {
_$TripCopyWithImpl(this._self, this._then); _$TripCopyWithImpl(this._self, this._then);
final Trip _self; final Trip _self;
@@ -64,25 +64,18 @@ class _$TripCopyWithImpl<$Res> implements $TripCopyWith<$Res> {
/// Create a copy of Trip /// Create a copy of Trip
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline') @override $Res call({Object? uuid = null,Object? totalTimeMinutes = freezed,Object? landmarks = null,}) {
@override
$Res call({
Object? uuid = null,
Object? landmarks = null,
}) {
return _then(_self.copyWith( return _then(_self.copyWith(
uuid: null == uuid uuid: null == uuid ? _self.uuid : uuid // ignore: cast_nullable_to_non_nullable
? _self.uuid as String,totalTimeMinutes: freezed == totalTimeMinutes ? _self.totalTimeMinutes : totalTimeMinutes // ignore: cast_nullable_to_non_nullable
: uuid // ignore: cast_nullable_to_non_nullable as int?,landmarks: null == landmarks ? _self.landmarks : landmarks // ignore: cast_nullable_to_non_nullable
as String,
landmarks: null == landmarks
? _self.landmarks
: landmarks // ignore: cast_nullable_to_non_nullable
as List<Landmark>, as List<Landmark>,
)); ));
} }
} }
/// Adds pattern-matching-related methods to [Trip]. /// Adds pattern-matching-related methods to [Trip].
extension TripPatterns on Trip { extension TripPatterns on Trip {
/// A variant of `map` that fallback to returning `orElse`. /// A variant of `map` that fallback to returning `orElse`.
@@ -97,20 +90,15 @@ extension TripPatterns on Trip {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeMap<TResult extends Object?>(TResult Function( _Trip value)? $default,{required TResult orElse(),}){
TResult maybeMap<TResult extends Object?>(
TResult Function(_Trip value)? $default, {
required TResult orElse(),
}) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _Trip() when $default != null: case _Trip() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// Callbacks receives the raw object, upcasted. /// Callbacks receives the raw object, upcasted.
@@ -124,19 +112,15 @@ extension TripPatterns on Trip {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult map<TResult extends Object?>(TResult Function( _Trip value) $default,){
TResult map<TResult extends Object?>(
TResult Function(_Trip value) $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _Trip(): case _Trip():
return $default(_that); return $default(_that);case _:
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `map` that fallback to returning `null`. /// A variant of `map` that fallback to returning `null`.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -149,19 +133,15 @@ extension TripPatterns on Trip {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? mapOrNull<TResult extends Object?>(TResult? Function( _Trip value)? $default,){
TResult? mapOrNull<TResult extends Object?>(
TResult? Function(_Trip value)? $default,
) {
final _that = this; final _that = this;
switch (_that) { switch (_that) {
case _Trip() when $default != null: case _Trip() when $default != null:
return $default(_that); return $default(_that);case _:
case _:
return null; return null;
}
}
}
}
/// A variant of `when` that fallback to an `orElse` callback. /// A variant of `when` that fallback to an `orElse` callback.
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -174,20 +154,14 @@ extension TripPatterns on Trip {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( String uuid, int? totalTimeMinutes, List<Landmark> landmarks)? $default,{required TResult orElse(),}) {final _that = this;
TResult maybeWhen<TResult extends Object?>(
TResult Function(String uuid, List<Landmark> landmarks)? $default, {
required TResult orElse(),
}) {
final _that = this;
switch (_that) { switch (_that) {
case _Trip() when $default != null: case _Trip() when $default != null:
return $default(_that.uuid, _that.landmarks); return $default(_that.uuid,_that.totalTimeMinutes,_that.landmarks);case _:
case _:
return orElse(); return orElse();
}
}
}
}
/// A `switch`-like method, using callbacks. /// A `switch`-like method, using callbacks.
/// ///
/// As opposed to `map`, this offers destructuring. /// As opposed to `map`, this offers destructuring.
@@ -201,19 +175,14 @@ extension TripPatterns on Trip {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( String uuid, int? totalTimeMinutes, List<Landmark> landmarks) $default,) {final _that = this;
TResult when<TResult extends Object?>(
TResult Function(String uuid, List<Landmark> landmarks) $default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _Trip(): case _Trip():
return $default(_that.uuid, _that.landmarks); return $default(_that.uuid,_that.totalTimeMinutes,_that.landmarks);case _:
case _:
throw StateError('Unexpected subclass'); throw StateError('Unexpected subclass');
}
}
}
}
/// A variant of `when` that fallback to returning `null` /// A variant of `when` that fallback to returning `null`
/// ///
/// It is equivalent to doing: /// It is equivalent to doing:
@@ -226,78 +195,67 @@ extension TripPatterns on Trip {
/// } /// }
/// ``` /// ```
@optionalTypeArgs @optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( String uuid, int? totalTimeMinutes, List<Landmark> landmarks)? $default,) {final _that = this;
TResult? whenOrNull<TResult extends Object?>(
TResult? Function(String uuid, List<Landmark> landmarks)? $default,
) {
final _that = this;
switch (_that) { switch (_that) {
case _Trip() when $default != null: case _Trip() when $default != null:
return $default(_that.uuid, _that.landmarks); return $default(_that.uuid,_that.totalTimeMinutes,_that.landmarks);case _:
case _:
return null; return null;
} }
} }
} }
/// @nodoc /// @nodoc
@JsonSerializable() @JsonSerializable()
class _Trip implements Trip { class _Trip implements Trip {
const _Trip({required this.uuid, required this.landmarks}); _Trip({required this.uuid, this.totalTimeMinutes, required this.landmarks});
factory _Trip.fromJson(Map<String, dynamic> json) => _$TripFromJson(json); factory _Trip.fromJson(Map<String, dynamic> json) => _$TripFromJson(json);
@override @override String uuid;
final String uuid;
// Duration totalTime, // Duration totalTime,
@override /// total time in minutes
final List<Landmark> landmarks; @override int? totalTimeMinutes;
/// ordered list of landmarks in this trip
@override List<Landmark> landmarks;
/// Create a copy of Trip /// Create a copy of Trip
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @JsonKey(includeFromJson: false, includeToJson: false)
@JsonKey(includeFromJson: false, includeToJson: false)
@pragma('vm:prefer-inline') @pragma('vm:prefer-inline')
_$TripCopyWith<_Trip> get copyWith => _$TripCopyWith<_Trip> get copyWith => __$TripCopyWithImpl<_Trip>(this, _$identity);
__$TripCopyWithImpl<_Trip>(this, _$identity);
@override @override
Map<String, dynamic> toJson() { Map<String, dynamic> toJson() {
return _$TripToJson( return _$TripToJson(this, );
this,
);
} }
@override
bool operator ==(Object other) {
return identical(this, other) ||
(other.runtimeType == runtimeType &&
other is _Trip &&
(identical(other.uuid, uuid) || other.uuid == uuid) &&
const DeepCollectionEquality().equals(other.landmarks, landmarks));
}
@JsonKey(includeFromJson: false, includeToJson: false)
@override
int get hashCode => Object.hash(
runtimeType, uuid, const DeepCollectionEquality().hash(landmarks));
@override @override
String toString() { String toString() {
return 'Trip(uuid: $uuid, landmarks: $landmarks)'; return 'Trip(uuid: $uuid, totalTimeMinutes: $totalTimeMinutes, landmarks: $landmarks)';
} }
} }
/// @nodoc /// @nodoc
abstract mixin class _$TripCopyWith<$Res> implements $TripCopyWith<$Res> { abstract mixin class _$TripCopyWith<$Res> implements $TripCopyWith<$Res> {
factory _$TripCopyWith(_Trip value, $Res Function(_Trip) _then) = factory _$TripCopyWith(_Trip value, $Res Function(_Trip) _then) = __$TripCopyWithImpl;
__$TripCopyWithImpl; @override @useResult
@override $Res call({
@useResult String uuid, int? totalTimeMinutes, List<Landmark> landmarks
$Res call({String uuid, List<Landmark> landmarks}); });
}
}
/// @nodoc /// @nodoc
class __$TripCopyWithImpl<$Res> implements _$TripCopyWith<$Res> { class __$TripCopyWithImpl<$Res>
implements _$TripCopyWith<$Res> {
__$TripCopyWithImpl(this._self, this._then); __$TripCopyWithImpl(this._self, this._then);
final _Trip _self; final _Trip _self;
@@ -305,23 +263,16 @@ class __$TripCopyWithImpl<$Res> implements _$TripCopyWith<$Res> {
/// Create a copy of Trip /// Create a copy of Trip
/// with the given fields replaced by the non-null parameter values. /// with the given fields replaced by the non-null parameter values.
@override @override @pragma('vm:prefer-inline') $Res call({Object? uuid = null,Object? totalTimeMinutes = freezed,Object? landmarks = null,}) {
@pragma('vm:prefer-inline')
$Res call({
Object? uuid = null,
Object? landmarks = null,
}) {
return _then(_Trip( return _then(_Trip(
uuid: null == uuid uuid: null == uuid ? _self.uuid : uuid // ignore: cast_nullable_to_non_nullable
? _self.uuid as String,totalTimeMinutes: freezed == totalTimeMinutes ? _self.totalTimeMinutes : totalTimeMinutes // ignore: cast_nullable_to_non_nullable
: uuid // ignore: cast_nullable_to_non_nullable as int?,landmarks: null == landmarks ? _self.landmarks : landmarks // ignore: cast_nullable_to_non_nullable
as String,
landmarks: null == landmarks
? _self.landmarks
: landmarks // ignore: cast_nullable_to_non_nullable
as List<Landmark>, as List<Landmark>,
)); ));
} }
} }
// dart format on // dart format on

View File

@@ -8,6 +8,7 @@ part of 'trip.dart';
_Trip _$TripFromJson(Map<String, dynamic> json) => _Trip( _Trip _$TripFromJson(Map<String, dynamic> json) => _Trip(
uuid: json['uuid'] as String, uuid: json['uuid'] as String,
totalTimeMinutes: (json['totalTimeMinutes'] as num?)?.toInt(),
landmarks: (json['landmarks'] as List<dynamic>) landmarks: (json['landmarks'] as List<dynamic>)
.map((e) => Landmark.fromJson(e as Map<String, dynamic>)) .map((e) => Landmark.fromJson(e as Map<String, dynamic>))
.toList(), .toList(),
@@ -15,5 +16,6 @@ _Trip _$TripFromJson(Map<String, dynamic> json) => _Trip(
Map<String, dynamic> _$TripToJson(_Trip instance) => <String, dynamic>{ Map<String, dynamic> _$TripToJson(_Trip instance) => <String, dynamic>{
'uuid': instance.uuid, 'uuid': instance.uuid,
'totalTimeMinutes': instance.totalTimeMinutes,
'landmarks': instance.landmarks, 'landmarks': instance.landmarks,
}; };

View File

@@ -0,0 +1,7 @@
abstract class OnboardingRepository {
/// Returns true when the user accepted the onboarding agreement
Future<bool> isOnboarded();
/// Sets the onboarding completion flag
Future<void> setOnboarded(bool value);
}

View File

@@ -2,4 +2,5 @@ import 'package:anyway/domain/entities/preferences.dart';
abstract class PreferencesRepository { abstract class PreferencesRepository {
Future<Preferences> getPreferences(); Future<Preferences> getPreferences();
Future<void> savePreferences(Preferences preferences);
} }

View File

@@ -1,6 +1,9 @@
import 'package:anyway/domain/entities/landmark.dart';
import 'package:anyway/domain/entities/preferences.dart'; import 'package:anyway/domain/entities/preferences.dart';
import 'package:anyway/domain/entities/trip.dart'; import 'package:anyway/domain/entities/trip.dart';
abstract class TripRepository { abstract class TripRepository {
Future<Trip> getTrip({Preferences? preferences, String? tripUUID}); Future<Trip> getTrip({Preferences? preferences, String? tripUUID, List<Landmark>? landmarks});
Future<List<Landmark>> searchLandmarks(Preferences preferences);
} }

View File

@@ -3,6 +3,7 @@ import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:anyway/presentation/providers/onboarding_state_provider.dart'; import 'package:anyway/presentation/providers/onboarding_state_provider.dart';
import 'package:anyway/presentation/pages/login.dart'; import 'package:anyway/presentation/pages/login.dart';
import 'package:anyway/presentation/pages/onboarding.dart'; import 'package:anyway/presentation/pages/onboarding.dart';
import 'package:anyway/presentation/pages/new_trip_preferences.dart';
// Example providers (replace these with your actual providers) // Example providers (replace these with your actual providers)
// final onboardingStateProvider = Provider<bool>((ref) => true); // Replace with actual onboarding state logic // final onboardingStateProvider = Provider<bool>((ref) => true); // Replace with actual onboarding state logic
@@ -80,7 +81,16 @@ class TripCreationPage extends StatelessWidget {
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return Scaffold( return Scaffold(
body: Center(child: Text('Trip Creation Page')), appBar: AppBar(title: const Text('Create a Trip')),
body: Center(
child: ElevatedButton.icon(
icon: const Icon(Icons.tune),
label: const Text('Set Preferences'),
onPressed: () {
Navigator.of(context).push(MaterialPageRoute(builder: (_) => const NewTripPreferencesPage()));
},
),
),
); );
} }
} }

View File

@@ -0,0 +1,49 @@
import 'package:anyway/core/dio_client.dart';
import 'package:anyway/data/repositories/local_onboarding_repository.dart';
import 'package:anyway/domain/repositories/onboarding_repository.dart';
import 'package:anyway/domain/repositories/trip_repository.dart';
import 'package:anyway/data/repositories/backend_trip_repository.dart';
import 'package:anyway/data/datasources/trip_remote_datasource.dart';
import 'package:anyway/data/repositories/preferences_repository_impl.dart';
import 'package:anyway/domain/repositories/preferences_repository.dart';
import 'dart:io';
import 'package:dio/dio.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
/// Provide a configured Dio instance (used by data layer)
final dioProvider = Provider<Dio>((ref) {
// baseUrl can be configured via environment; use a sensible default
return Dio(BaseOptions(
baseUrl: 'https://anyway.anydev.info',
connectTimeout: const Duration(seconds: 5),
receiveTimeout: const Duration(seconds: 120),
headers: {
HttpHeaders.acceptHeader: 'application/json',
HttpHeaders.contentTypeHeader: 'application/json',
},
));
});
/// Provide a simple wrapper client if needed elsewhere
final dioClientProvider = Provider<DioClient>((ref) {
final dio = ref.read(dioProvider);
return DioClient(baseUrl: dio.options.baseUrl);
});
/// Onboarding repository backed by SharedPreferences
final onboardingRepositoryProvider = Provider<OnboardingRepository>((ref) {
return LocalOnboardingRepository();
});
/// Preferences repository (local persistence)
final preferencesRepositoryProvider = Provider<PreferencesRepository>((ref) {
return PreferencesRepositoryImpl();
});
/// Trip repository backed by the backend
final tripRepositoryProvider = Provider<TripRepository>((ref) {
final dio = ref.read(dioProvider);
final remote = TripRemoteDataSourceImpl(dio: dio);
return BackendTripRepository(remote: remote);
});

View File

@@ -0,0 +1,16 @@
import 'package:anyway/domain/entities/landmark.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
class IntermediateLandmarksNotifier extends Notifier<List<Landmark>> {
@override
List<Landmark> build() => [];
void setLandmarks(List<Landmark> landmarks) {
state = List.unmodifiable(landmarks);
}
void clear() => state = [];
}
final intermediateLandmarksProvider =
NotifierProvider<IntermediateLandmarksNotifier, List<Landmark>>(IntermediateLandmarksNotifier.new);

View File

@@ -1,9 +1,10 @@
import 'package:flutter_riverpod/flutter_riverpod.dart'; import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:shared_preferences/shared_preferences.dart'; import 'package:anyway/domain/repositories/onboarding_repository.dart';
import 'package:anyway/presentation/providers/core_providers.dart';
final onboardingStateProvider = FutureProvider<bool>((ref) async { final onboardingStateProvider = FutureProvider<bool>((ref) async {
final prefs = await SharedPreferences.getInstance(); final repo = ref.watch(onboardingRepositoryProvider);
return prefs.getBool('onboardingCompleted') ?? false; return repo.isOnboarded();
}); });
@@ -16,9 +17,10 @@ class OnboardingController {
OnboardingController(this.ref); OnboardingController(this.ref);
Future<void> setOnboarded(bool value) async { Future<void> setOnboarded(bool value) async {
final prefs = await SharedPreferences.getInstance(); final repo = ref.read(onboardingRepositoryProvider);
await prefs.setBool('onboardingCompleted', value); await repo.setOnboarded(value);
// refresh the read provider so UI updates // refresh the read provider so UI updates
ref.invalidate(onboardingStateProvider); ref.invalidate(onboardingStateProvider);
} }
} }

View File

@@ -1,6 +1,16 @@
// import 'package:anyway/data/repositories/trip_repository.dart'; import 'package:anyway/domain/entities/preferences.dart';
// import 'package:flutter_riverpod/flutter_riverpod.dart'; import 'package:anyway/domain/entities/trip.dart';
import 'package:anyway/presentation/providers/landmark_providers.dart';
// final weatherRepositoryProvider = Provider<TripRepository>((ref) { import 'package:flutter_riverpod/flutter_riverpod.dart';
// return TripRepositoryImpl(???); import 'package:anyway/presentation/providers/core_providers.dart';
// });
// Provides a function that creates a trip given preferences.
final createTripProvider = Provider<Future<Trip> Function(Preferences)>((ref) {
return (Preferences prefs) async {
final repo = ref.read(tripRepositoryProvider);
final landmarks = await repo.searchLandmarks(prefs);
ref.read(intermediateLandmarksProvider.notifier).setLandmarks(landmarks);
return repo.getTrip(preferences: prefs, landmarks: landmarks);
};
});

View File

@@ -708,26 +708,26 @@ packages:
dependency: transitive dependency: transitive
description: description:
name: leak_tracker name: leak_tracker
sha256: "6bb818ecbdffe216e81182c2f0714a2e62b593f4a4f13098713ff1685dfb6ab0" sha256: "33e2e26bdd85a0112ec15400c8cbffea70d0f9c3407491f672a2fad47915e2de"
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "10.0.9" version: "11.0.2"
leak_tracker_flutter_testing: leak_tracker_flutter_testing:
dependency: transitive dependency: transitive
description: description:
name: leak_tracker_flutter_testing name: leak_tracker_flutter_testing
sha256: f8b613e7e6a13ec79cfdc0e97638fddb3ab848452eff057653abd3edba760573 sha256: "1dbc140bb5a23c75ea9c4811222756104fbcd1a27173f0c34ca01e16bea473c1"
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "3.0.9" version: "3.0.10"
leak_tracker_testing: leak_tracker_testing:
dependency: transitive dependency: transitive
description: description:
name: leak_tracker_testing name: leak_tracker_testing
sha256: "6ba465d5d76e67ddf503e1161d1f4a6bc42306f9d66ca1e8f079a47290fb06d3" sha256: "8d5a2d49f4a66b49744b23b018848400d23e54caf9463f4eb20df3eb8acb2eb1"
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "3.0.1" version: "3.0.2"
lints: lints:
dependency: transitive dependency: transitive
description: description:
@@ -772,10 +772,10 @@ packages:
dependency: transitive dependency: transitive
description: description:
name: meta name: meta
sha256: e3641ec5d63ebf0d9b41bd43201a66e3fc79a65db5f61fc181f04cd27aab950c sha256: "23f08335362185a5ea2ad3a4e597f1375e78bce8a040df5c600c8d3552ef2394"
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "1.16.0" version: "1.17.0"
mime: mime:
dependency: transitive dependency: transitive
description: description:
@@ -1273,26 +1273,26 @@ packages:
dependency: transitive dependency: transitive
description: description:
name: test name: test
sha256: "301b213cd241ca982e9ba50266bd3f5bd1ea33f1455554c5abb85d1be0e2d87e" sha256: "75906bf273541b676716d1ca7627a17e4c4070a3a16272b7a3dc7da3b9f3f6b7"
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "1.25.15" version: "1.26.3"
test_api: test_api:
dependency: transitive dependency: transitive
description: description:
name: test_api name: test_api
sha256: fb31f383e2ee25fbbfe06b40fe21e1e458d14080e3c67e7ba0acfde4df4e0bbd sha256: ab2726c1a94d3176a45960b6234466ec367179b87dd74f1611adb1f3b5fb9d55
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "0.7.4" version: "0.7.7"
test_core: test_core:
dependency: transitive dependency: transitive
description: description:
name: test_core name: test_core
sha256: "84d17c3486c8dfdbe5e12a50c8ae176d15e2a771b96909a9442b40173649ccaa" sha256: "0cc24b5ff94b38d2ae73e1eb43cc302b77964fbf67abad1e296025b78deb53d0"
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "0.6.8" version: "0.6.12"
timing: timing:
dependency: transitive dependency: transitive
description: description:
@@ -1409,10 +1409,10 @@ packages:
dependency: transitive dependency: transitive
description: description:
name: vector_math name: vector_math
sha256: "80b3257d1492ce4d091729e3a67a60407d227c27241d6927be0130c98e741803" sha256: d530bd74fea330e6e364cda7a85019c434070188383e1cd8d9777ee586914c5b
url: "https://pub.dev" url: "https://pub.dev"
source: hosted source: hosted
version: "2.1.4" version: "2.2.0"
vm_service: vm_service:
dependency: transitive dependency: transitive
description: description: