diff --git a/backend-dart/lib/application/service/auth_service.dart b/backend-dart/lib/application/service/auth_service.dart index 36996e7..12be71a 100644 --- a/backend-dart/lib/application/service/auth_service.dart +++ b/backend-dart/lib/application/service/auth_service.dart @@ -1,11 +1,14 @@ import 'dart:convert'; + import 'package:backend_dart/application/service/dto/auth_dto.dart'; +import 'package:backend_dart/application/service/helper.dart'; import 'package:backend_dart/common/request_helper.dart'; import 'package:backend_dart/common/response_helpers.dart'; import 'package:backend_dart/common/secure_hash.dart'; import 'package:backend_dart/common/validation.dart'; import 'package:backend_dart/domain/entities/user.dart'; import 'package:backend_dart/domain/errors/app_error.dart'; +import 'package:backend_dart/domain/errors/error.dart'; import 'package:backend_dart/domain/repository/auth_repository.dart'; import 'package:backend_dart/domain/repository/user_repository.dart'; import 'package:fpdart/fpdart.dart'; @@ -37,20 +40,28 @@ class AuthService { ), ), ) - .flatMap((user) => authRepository.generateToken(user.id).map((token) => - TokenResponseDTO(token: token, userId: user.id).toJson())) - .map(jsonEncode) - .toResponse() + .flatMap((user) => authRepository.generateToken(user.id).map( + (token) => Response.ok( + jsonEncode( + TokenResponseDTO(token: token, userId: user.id).toJson(), + ), + headers: { + 'Set-Cookie': + 'session_token=$token; HttpOnly; Path=/, user_id=${user.id}; HttpOnly; Path=/', + 'Content-Type': 'application/json', + }, + ), + )) + .getOrElse(ResponseHelpers.fromError) .run(); } /// Route to validate a token @Route.post('/validate') Future validateToken(Request request) async { - return requestToJson(request) - .flatMap(validateJsonKeys(['token'])) - .flatMap((json) => decodeJson(json, TokenRequestDTO.fromJson)) - .map((tokenRequest) => tokenRequest.token) + return readCookie(request, 'session_token') + .toTaskEither(() => AppError.authenticationError( + message: 'No token found in the request')) .flatMap((token) => authRepository.validateToken(token).map((userId) => TokenResponseDTO(token: token, userId: userId).toJson())) .map(jsonEncode) @@ -61,14 +72,20 @@ class AuthService { /// Route to revoke a token @Route.post('/logout') Future logout(Request request) async { - return requestToJson(request) - .flatMap(validateJsonKeys(['token'])) - .flatMap((json) => decodeJson(json, TokenRequestDTO.fromJson)) - .map((tokenRequest) => tokenRequest.token) + return readCookie(request, 'session_token') + .toTaskEither(() => AppError.authenticationError( + message: 'No token found in the request')) .flatMap(authRepository.revokeToken) - .map((_) => {'message': 'Token revoked successfully'}) - .map(jsonEncode) - .toResponse() + .map((_) => Response.ok( + jsonEncode({'message': 'Token revoked successfully'}), + headers: { + // Clear cookies by setting Max-Age to 0 + 'Set-Cookie': + 'session_token=; Max-Age=0; HttpOnly; Path=/, user_id=; Max-Age=0; HttpOnly; Path=/', + 'Content-Type': 'application/json', + }, + )) + .getOrElse(ResponseHelpers.fromError) .run(); } diff --git a/backend-dart/lib/application/service/dto/auth_dto.dart b/backend-dart/lib/application/service/dto/auth_dto.dart index d839b68..f25bfd9 100644 --- a/backend-dart/lib/application/service/dto/auth_dto.dart +++ b/backend-dart/lib/application/service/dto/auth_dto.dart @@ -16,18 +16,6 @@ class TokenResponseDTO with _$TokenResponseDTO { _$TokenResponseDTOFromJson(json); } -/// TokenRequestDTO represents a request for operations involving tokens. -@freezed -class TokenRequestDTO with _$TokenRequestDTO { - const factory TokenRequestDTO({ - required String token, - }) = _TokenRequestDTO; - - /// JSON serialization - factory TokenRequestDTO.fromJson(Map json) => - _$TokenRequestDTOFromJson(json); -} - /// LoginRequestDTO represents the login request. @freezed class LoginRequestDTO with _$LoginRequestDTO { diff --git a/backend-dart/lib/application/service/dto/auth_dto.freezed.dart b/backend-dart/lib/application/service/dto/auth_dto.freezed.dart index ef0c95f..4b2ba9c 100644 --- a/backend-dart/lib/application/service/dto/auth_dto.freezed.dart +++ b/backend-dart/lib/application/service/dto/auth_dto.freezed.dart @@ -182,157 +182,6 @@ abstract class _TokenResponseDTO implements TokenResponseDTO { throw _privateConstructorUsedError; } -TokenRequestDTO _$TokenRequestDTOFromJson(Map json) { - return _TokenRequestDTO.fromJson(json); -} - -/// @nodoc -mixin _$TokenRequestDTO { - String get token => throw _privateConstructorUsedError; - - /// Serializes this TokenRequestDTO to a JSON map. - Map toJson() => throw _privateConstructorUsedError; - - /// Create a copy of TokenRequestDTO - /// with the given fields replaced by the non-null parameter values. - @JsonKey(includeFromJson: false, includeToJson: false) - $TokenRequestDTOCopyWith get copyWith => - throw _privateConstructorUsedError; -} - -/// @nodoc -abstract class $TokenRequestDTOCopyWith<$Res> { - factory $TokenRequestDTOCopyWith( - TokenRequestDTO value, $Res Function(TokenRequestDTO) then) = - _$TokenRequestDTOCopyWithImpl<$Res, TokenRequestDTO>; - @useResult - $Res call({String token}); -} - -/// @nodoc -class _$TokenRequestDTOCopyWithImpl<$Res, $Val extends TokenRequestDTO> - implements $TokenRequestDTOCopyWith<$Res> { - _$TokenRequestDTOCopyWithImpl(this._value, this._then); - - // ignore: unused_field - final $Val _value; - // ignore: unused_field - final $Res Function($Val) _then; - - /// Create a copy of TokenRequestDTO - /// with the given fields replaced by the non-null parameter values. - @pragma('vm:prefer-inline') - @override - $Res call({ - Object? token = null, - }) { - return _then(_value.copyWith( - token: null == token - ? _value.token - : token // ignore: cast_nullable_to_non_nullable - as String, - ) as $Val); - } -} - -/// @nodoc -abstract class _$$TokenRequestDTOImplCopyWith<$Res> - implements $TokenRequestDTOCopyWith<$Res> { - factory _$$TokenRequestDTOImplCopyWith(_$TokenRequestDTOImpl value, - $Res Function(_$TokenRequestDTOImpl) then) = - __$$TokenRequestDTOImplCopyWithImpl<$Res>; - @override - @useResult - $Res call({String token}); -} - -/// @nodoc -class __$$TokenRequestDTOImplCopyWithImpl<$Res> - extends _$TokenRequestDTOCopyWithImpl<$Res, _$TokenRequestDTOImpl> - implements _$$TokenRequestDTOImplCopyWith<$Res> { - __$$TokenRequestDTOImplCopyWithImpl( - _$TokenRequestDTOImpl _value, $Res Function(_$TokenRequestDTOImpl) _then) - : super(_value, _then); - - /// Create a copy of TokenRequestDTO - /// with the given fields replaced by the non-null parameter values. - @pragma('vm:prefer-inline') - @override - $Res call({ - Object? token = null, - }) { - return _then(_$TokenRequestDTOImpl( - token: null == token - ? _value.token - : token // ignore: cast_nullable_to_non_nullable - as String, - )); - } -} - -/// @nodoc -@JsonSerializable() -class _$TokenRequestDTOImpl implements _TokenRequestDTO { - const _$TokenRequestDTOImpl({required this.token}); - - factory _$TokenRequestDTOImpl.fromJson(Map json) => - _$$TokenRequestDTOImplFromJson(json); - - @override - final String token; - - @override - String toString() { - return 'TokenRequestDTO(token: $token)'; - } - - @override - bool operator ==(Object other) { - return identical(this, other) || - (other.runtimeType == runtimeType && - other is _$TokenRequestDTOImpl && - (identical(other.token, token) || other.token == token)); - } - - @JsonKey(includeFromJson: false, includeToJson: false) - @override - int get hashCode => Object.hash(runtimeType, token); - - /// Create a copy of TokenRequestDTO - /// with the given fields replaced by the non-null parameter values. - @JsonKey(includeFromJson: false, includeToJson: false) - @override - @pragma('vm:prefer-inline') - _$$TokenRequestDTOImplCopyWith<_$TokenRequestDTOImpl> get copyWith => - __$$TokenRequestDTOImplCopyWithImpl<_$TokenRequestDTOImpl>( - this, _$identity); - - @override - Map toJson() { - return _$$TokenRequestDTOImplToJson( - this, - ); - } -} - -abstract class _TokenRequestDTO implements TokenRequestDTO { - const factory _TokenRequestDTO({required final String token}) = - _$TokenRequestDTOImpl; - - factory _TokenRequestDTO.fromJson(Map json) = - _$TokenRequestDTOImpl.fromJson; - - @override - String get token; - - /// Create a copy of TokenRequestDTO - /// with the given fields replaced by the non-null parameter values. - @override - @JsonKey(includeFromJson: false, includeToJson: false) - _$$TokenRequestDTOImplCopyWith<_$TokenRequestDTOImpl> get copyWith => - throw _privateConstructorUsedError; -} - LoginRequestDTO _$LoginRequestDTOFromJson(Map json) { return _LoginRequestDTO.fromJson(json); } diff --git a/backend-dart/lib/application/service/dto/auth_dto.g.dart b/backend-dart/lib/application/service/dto/auth_dto.g.dart index 18b05dd..95b6272 100644 --- a/backend-dart/lib/application/service/dto/auth_dto.g.dart +++ b/backend-dart/lib/application/service/dto/auth_dto.g.dart @@ -20,18 +20,6 @@ Map _$$TokenResponseDTOImplToJson( 'userId': instance.userId, }; -_$TokenRequestDTOImpl _$$TokenRequestDTOImplFromJson( - Map json) => - _$TokenRequestDTOImpl( - token: json['token'] as String, - ); - -Map _$$TokenRequestDTOImplToJson( - _$TokenRequestDTOImpl instance) => - { - 'token': instance.token, - }; - _$LoginRequestDTOImpl _$$LoginRequestDTOImplFromJson( Map json) => _$LoginRequestDTOImpl( diff --git a/backend-dart/lib/application/service/helper.dart b/backend-dart/lib/application/service/helper.dart new file mode 100644 index 0000000..1d98a61 --- /dev/null +++ b/backend-dart/lib/application/service/helper.dart @@ -0,0 +1,33 @@ +import 'package:backend_dart/domain/errors/app_error.dart'; +import 'package:backend_dart/domain/errors/error.dart'; +import 'package:backend_dart/domain/repository/auth_repository.dart'; +import 'package:fpdart/fpdart.dart'; +import 'package:shelf/shelf.dart'; + +TaskOption readCookie(Request request, String cookieName) { + // Retrieve the "Cookie" header + final cookieHeader = request.headers['cookie']; + if (cookieHeader == null) return TaskOption.none(); + // No cookies found + + // Split the cookies into individual key-value pairs + final cookies = cookieHeader.split(';'); + + // Find the cookie with the matching name + for (var cookie in cookies) { + final parts = cookie.trim().split('='); + if (parts.length == 2 && parts[0] == cookieName && parts[1].isNotEmpty) { + return TaskOption.some(parts[1]); + } + } + + return TaskOption.none(); // Cookie not found +} + +TaskEither checkAuth( + Request request, AuthRepository authRepository) { + return readCookie(request, 'session_token') + .toTaskEither(() => AppError.authenticationError( + message: 'No token found in the request')) + .flatMap(authRepository.validateToken); +} diff --git a/backend-dart/lib/application/service/project_service.dart b/backend-dart/lib/application/service/project_service.dart index 6654887..017186a 100644 --- a/backend-dart/lib/application/service/project_service.dart +++ b/backend-dart/lib/application/service/project_service.dart @@ -1,10 +1,12 @@ import 'dart:convert'; import 'package:backend_dart/application/service/dto/project_dto.dart'; +import 'package:backend_dart/application/service/helper.dart'; import 'package:backend_dart/application/service/mapper/project_dto_mapper.dart'; import 'package:backend_dart/common/request_helper.dart'; import 'package:backend_dart/common/response_helpers.dart'; import 'package:backend_dart/common/validation.dart'; +import 'package:backend_dart/domain/repository/auth_repository.dart'; import 'package:backend_dart/domain/repository/project_repository.dart'; import 'package:shelf/shelf.dart'; import 'package:shelf_router/shelf_router.dart'; @@ -13,13 +15,14 @@ part 'project_service.g.dart'; // generated with 'pub run build_runner build' class ProjectService { final ProjectRepository projects; + final AuthRepository authRepository; final ProjectDtoMapper mapper = ProjectDtoMapper(); - ProjectService(this.projects); + ProjectService(this.projects, this.authRepository); @Route.get('/') Future listProjects(Request request) async { - return projects - .findAll() + return checkAuth(request, authRepository) + .flatMap((_) => projects.findAll()) .flatMap(mapper.listTo) .map((projects) => projects.map((project) => project.toJson()).toList()) .map(jsonEncode) @@ -29,8 +32,8 @@ class ProjectService { @Route.get('/') Future fetchProject(Request request, String projectId) async { - return projects - .findById(projectId) + return checkAuth(request, authRepository) + .flatMap((_) => projects.findById(projectId)) .flatMap(mapper.to) .map((dto) => dto.toJson()) .toResponse() @@ -39,7 +42,8 @@ class ProjectService { @Route.post('/') Future createProject(Request request) async { - return requestToJson(request) + return checkAuth(request, authRepository) + .flatMap((_) => requestToJson(request)) .flatMap(validateJsonKeys(['name', 'userId'])) // Add required fields .flatMap((json) => decodeJson(json, ProjectCreateDto.fromJson)) .flatMap(mapper.fromCreateTo) @@ -52,7 +56,8 @@ class ProjectService { @Route.put('/') Future updateProject(Request request, String projectId) async { - return requestToJson(request) + return checkAuth(request, authRepository) + .flatMap((_) => requestToJson(request)) .flatMap(validateJsonKeys([])) .flatMap((json) => decodeJson(json, ProjectUpdateDto.fromJson)) .flatMap((dto) => mapper.fromUpdateTo(dto, projectId)) @@ -65,8 +70,8 @@ class ProjectService { @Route.delete('/') Future deleteProject(Request request, String projectId) async { - return projects - .delete(projectId) + return checkAuth(request, authRepository) + .flatMap((_) => projects.delete(projectId)) .flatMap(mapper.to) .map((dto) => dto.toJson()) .toResponse() diff --git a/backend-dart/lib/application/service/project_task_service.dart b/backend-dart/lib/application/service/project_task_service.dart index abf41a4..6d4ceba 100644 --- a/backend-dart/lib/application/service/project_task_service.dart +++ b/backend-dart/lib/application/service/project_task_service.dart @@ -1,10 +1,12 @@ import 'dart:convert'; import 'package:backend_dart/application/service/dto/project_task_dto.dart'; +import 'package:backend_dart/application/service/helper.dart'; import 'package:backend_dart/application/service/mapper/project_task_dto_mapper.dart'; import 'package:backend_dart/common/request_helper.dart'; import 'package:backend_dart/common/response_helpers.dart'; import 'package:backend_dart/common/validation.dart'; +import 'package:backend_dart/domain/repository/auth_repository.dart'; import 'package:backend_dart/domain/repository/project_task_repository.dart'; import 'package:shelf/shelf.dart'; import 'package:shelf_router/shelf_router.dart'; @@ -13,13 +15,15 @@ part 'project_task_service.g.dart'; // Generated with 'pub run build_runner buil class ProjectTaskService { final ProjectTaskRepository tasks; + final AuthRepository authRepository; + final ProjectTaskDtoMapper mapper = ProjectTaskDtoMapper(); - ProjectTaskService(this.tasks); + ProjectTaskService(this.tasks, this.authRepository); @Route.get('/') Future listTasks(Request request) async { - return tasks - .findAll() + return checkAuth(request, authRepository) + .flatMap((_) => tasks.findAll()) .flatMap(mapper.listTo) .map((tasks) => tasks.map((task) => task.toJson()).toList()) .map(jsonEncode) @@ -29,8 +33,8 @@ class ProjectTaskService { @Route.get('/') Future fetchTask(Request request, String taskId) async { - return tasks - .findById(taskId) + return checkAuth(request, authRepository) + .flatMap((_) => tasks.findById(taskId)) .flatMap(mapper.to) .map((dto) => dto.toJson()) .toResponse() @@ -39,7 +43,8 @@ class ProjectTaskService { @Route.post('/') Future createTask(Request request) async { - return requestToJson(request) + return checkAuth(request, authRepository) + .flatMap((_) => requestToJson(request)) .flatMap(validateJsonKeys(['name', 'projectId'])) // Add required fields .flatMap((json) => decodeJson(json, ProjectTaskCreateDto.fromJson)) .flatMap(mapper.fromCreateTo) @@ -52,7 +57,8 @@ class ProjectTaskService { @Route.put('/') Future updateTask(Request request, String taskId) async { - return requestToJson(request) + return checkAuth(request, authRepository) + .flatMap((_) => requestToJson(request)) .flatMap(validateJsonKeys([])) .flatMap((json) => decodeJson(json, ProjectTaskUpdateDto.fromJson)) .flatMap((dto) => mapper.fromUpdateTo(dto, taskId)) @@ -65,8 +71,8 @@ class ProjectTaskService { @Route.delete('/') Future deleteTask(Request request, String taskId) async { - return tasks - .delete(taskId) + return checkAuth(request, authRepository) + .flatMap((_) => tasks.delete(taskId)) .flatMap(mapper.to) .map((dto) => dto.toJson()) .toResponse() diff --git a/backend-dart/lib/application/service/service_provider.dart b/backend-dart/lib/application/service/service_provider.dart index b1640d8..19573f1 100644 --- a/backend-dart/lib/application/service/service_provider.dart +++ b/backend-dart/lib/application/service/service_provider.dart @@ -8,22 +8,26 @@ import 'package:riverpod/riverpod.dart'; final userServiceProvider = Provider((ref) { final database = ref.read(userRepoProvider); - return UserService(database); + final authRepository = ref.read(authProvider); + return UserService(database, authRepository); }); final projectServiceProvider = Provider((ref) { final database = ref.read(projectProvider); - return ProjectService(database); + final authRepository = ref.read(authProvider); + return ProjectService(database, authRepository); }); final projectTaskServiceProvider = Provider((ref) { final database = ref.read(projectTaskProvider); - return ProjectTaskService(database); + final authRepository = ref.read(authProvider); + return ProjectTaskService(database, authRepository); }); final timeEntryServiceProvider = Provider((ref) { final database = ref.read(timeEntryProvider); - return TimeEntryService(database); + final authRepository = ref.read(authProvider); + return TimeEntryService(database, authRepository); }); final authServiceProvider = Provider((ref) { diff --git a/backend-dart/lib/application/service/time_entry_service.dart b/backend-dart/lib/application/service/time_entry_service.dart index 2864fe6..1763442 100644 --- a/backend-dart/lib/application/service/time_entry_service.dart +++ b/backend-dart/lib/application/service/time_entry_service.dart @@ -1,10 +1,12 @@ import 'dart:convert'; import 'package:backend_dart/application/service/dto/time_entry_dto.dart'; +import 'package:backend_dart/application/service/helper.dart'; import 'package:backend_dart/application/service/mapper/time_entry_dto_mapper.dart'; import 'package:backend_dart/common/request_helper.dart'; import 'package:backend_dart/common/response_helpers.dart'; import 'package:backend_dart/common/validation.dart'; +import 'package:backend_dart/domain/repository/auth_repository.dart'; import 'package:backend_dart/domain/repository/time_entry_repository.dart'; import 'package:shelf/shelf.dart'; import 'package:shelf_router/shelf_router.dart'; @@ -13,13 +15,14 @@ part 'time_entry_service.g.dart'; // Generated with 'pub run build_runner build' class TimeEntryService { final TimeEntryRepository entries; + final AuthRepository authRepository; final TimeEntryDtoMapper mapper = TimeEntryDtoMapper(); - TimeEntryService(this.entries); + TimeEntryService(this.entries, this.authRepository); @Route.get('/') Future listEntries(Request request) async { - return entries - .findAll() + return checkAuth(request, authRepository) + .flatMap((_) => entries.findAll()) .flatMap(mapper.listTo) .map((entries) => entries.map((entry) => entry.toJson()).toList()) .map(jsonEncode) @@ -29,8 +32,8 @@ class TimeEntryService { @Route.get('/') Future fetchEntry(Request request, String entryId) async { - return entries - .findById(entryId) + return checkAuth(request, authRepository) + .flatMap((_) => entries.findById(entryId)) .flatMap(mapper.to) .map((dto) => dto.toJson()) .toResponse() @@ -39,7 +42,8 @@ class TimeEntryService { @Route.post('/') Future createEntry(Request request) async { - return requestToJson(request) + return checkAuth(request, authRepository) + .flatMap((_) => requestToJson(request)) .flatMap( validateJsonKeys(['startTime', 'endTime', 'userId', 'projectId'])) .flatMap((json) => decodeJson(json, TimeEntryCreateDto.fromJson)) @@ -53,7 +57,8 @@ class TimeEntryService { @Route.put('/') Future updateEntry(Request request, String entryId) async { - return requestToJson(request) + return checkAuth(request, authRepository) + .flatMap((_) => requestToJson(request)) .flatMap(validateJsonKeys([])) .flatMap((json) => decodeJson(json, TimeEntryUpdateDto.fromJson)) .flatMap((dto) => mapper.fromUpdateTo(dto, entryId)) @@ -66,8 +71,8 @@ class TimeEntryService { @Route.delete('/') Future deleteEntry(Request request, String entryId) async { - return entries - .delete(entryId) + return checkAuth(request, authRepository) + .flatMap((_) => entries.delete(entryId)) .map((dto) => dto.toJson()) .toResponse() .run(); diff --git a/backend-dart/lib/application/service/user_service.dart b/backend-dart/lib/application/service/user_service.dart index 4596bdf..b7a0c9a 100644 --- a/backend-dart/lib/application/service/user_service.dart +++ b/backend-dart/lib/application/service/user_service.dart @@ -1,10 +1,12 @@ import 'dart:convert'; import 'package:backend_dart/application/service/dto/user_dto.dart'; +import 'package:backend_dart/application/service/helper.dart'; import 'package:backend_dart/application/service/mapper/user_dto_mapper.dart'; import 'package:backend_dart/common/request_helper.dart'; import 'package:backend_dart/common/response_helpers.dart'; import 'package:backend_dart/common/validation.dart'; +import 'package:backend_dart/domain/repository/auth_repository.dart'; import 'package:backend_dart/domain/repository/user_repository.dart'; import 'package:shelf/shelf.dart'; import 'package:shelf_router/shelf_router.dart'; @@ -13,13 +15,15 @@ part 'user_service.g.dart'; // generated with 'pub run build_runner build' class UserService { final UserRepository users; + final AuthRepository authRepository; + final UserDtoMapper mapper = UserDtoMapper(); - UserService(this.users); + UserService(this.users, this.authRepository); @Route.get('/') Future listUsers(Request request) async { - return users - .findAll() + return checkAuth(request, authRepository) + .flatMap((_) => users.findAll()) .flatMap(mapper.listTo) .map((users) => users.map((user) => user.toJson()).toList()) .map(jsonEncode) @@ -29,8 +33,8 @@ class UserService { @Route.get('/') Future fetchUser(Request request, String userId) async { - return users - .findById(userId) + return checkAuth(request, authRepository) + .flatMap((_) => users.findById(userId)) .flatMap(mapper.to) .map((dto) => dto.toJson()) .toResponse() @@ -48,11 +52,22 @@ class UserService { .map((dto) => dto.toJson()) .toResponse() .run(); + //return checkAuth(request, authRepository) // ignore auth for initial user creation + // .flatMap((_) => requestToJson(request)) + // .flatMap(validateJsonKeys(['name', 'email', 'password'])) + // .flatMap((json) => decodeJson(json, UserCreateDto.fromJson)) + // .flatMap(mapper.fromCreateTo) + // .flatMap(users.create) + // .flatMap(mapper.to) + // .map((dto) => dto.toJson()) + // .toResponse() + // .run(); } @Route.put('/') Future updateUser(Request request, String userId) async { - return requestToJson(request) + return checkAuth(request, authRepository) + .flatMap((_) => requestToJson(request)) .flatMap(validateJsonKeys([])) .flatMap((json) => decodeJson(json, UserUpdateDto.fromJson)) .flatMap((dto) => mapper.fromUpdateTo(dto, userId)) @@ -65,8 +80,8 @@ class UserService { @Route.delete('/') Future deleteUser(Request request, String userId) async { - return users - .delete(userId) + return checkAuth(request, authRepository) + .flatMap((_) => users.delete(userId)) .flatMap(mapper.to) .map((dto) => dto.toJson()) .toResponse() diff --git a/backend-dart/lib/common/response_helpers.dart b/backend-dart/lib/common/response_helpers.dart index 79bb197..5ca8cd7 100644 --- a/backend-dart/lib/common/response_helpers.dart +++ b/backend-dart/lib/common/response_helpers.dart @@ -14,8 +14,8 @@ extension TaskEitherResponseExtensions extension TaskEitherResponseExtensionsFromString on TaskEither { Task toResponse() => match( - (left) => ResponseHelpers.fromError(left), - (right) => Response.ok(right), + ResponseHelpers.fromError, + Response.ok, ); } diff --git a/backend-go/internal/application/services/auth_service.go b/backend-go/internal/application/services/auth_service.go index b7426eb..40a3543 100644 --- a/backend-go/internal/application/services/auth_service.go +++ b/backend-go/internal/application/services/auth_service.go @@ -106,15 +106,15 @@ func (s *AuthService) Logout(c *gin.Context) { func setSessionTokenCookie(c *gin.Context, user entities.User) func(token string) string { return func(token string) string { - c.SetCookie("session_token", token, 3600, "/", "localhost", false, true) - c.SetCookie("user_id", user.ID, 3600, "/", "localhost", false, true) + c.SetCookie("session_token", token, 3600, "/", "", false, true) + c.SetCookie("user_id", user.ID, 3600, "/", "", false, true) return token } } func deleteSessionTokenCookie(c *gin.Context) { - c.SetCookie("session_token", "", -1, "/", "localhost", false, true) - c.SetCookie("user_id", "", -1, "/", "localhost", false, true) + c.SetCookie("session_token", "", -1, "/", "", false, true) + c.SetCookie("user_id", "", -1, "/", "", false, true) } func validatePassword(password string) func(user entities.User) E.Either[error, entities.User] { diff --git a/backend-go/internal/application/services/dto/auth_dto.go b/backend-go/internal/application/services/dto/auth_dto.go index 79e5e69..d337b3e 100644 --- a/backend-go/internal/application/services/dto/auth_dto.go +++ b/backend-go/internal/application/services/dto/auth_dto.go @@ -3,7 +3,7 @@ package dto // TokenResponseDTO represents the response for a token generation or validation. type TokenResponseDTO struct { Token string `json:"token"` - UserID string `json:"user_id"` + UserID string `json:"userId"` } // LoginRequestDTO represents the login request.