Overview
AuthService is an Angular service that implements the UsuarioRepository interface to provide HTTP-based authentication functionality. It handles user login and registration operations by communicating with the backend REST API using Angular’s HttpClient.
Location: src/app/usuario/infrastructure/services/auth-service.ts
Complete Implementation
import { HttpClient } from '@angular/common/core';
import { Injectable } from '@angular/core';
import { Observable } from 'rxjs';
import { Usuario } from '../../domain/models/usuario';
import { UsuarioRepository } from '../../domain/repositories/usuario.repository';
@Injectable({
providedIn: 'root',
})
export class AuthService implements UsuarioRepository {
private readonly BASE_URL = 'http://localhost:8080/'
constructor(private httpClient: HttpClient) { }
loginUsuario(usuario: string, contrasena: string): Observable<Usuario> {
return this.httpClient.get<Usuario>(this.BASE_URL + 'login' + '/' + usuario + '/' + contrasena);
}
registrarUsuario(usuario: string, contrasena: string): Observable<Usuario> {
const body = { usuario, contrasena };
return this.httpClient.post<Usuario>(
`${this.BASE_URL}registro`,
body,
{ headers: { 'Content-Type': 'application/json' } }
);
}
}
Configuration
BASE_URL
BASE_URL
string
default:"http://localhost:8080/"
The base URL for all authentication API endpoints. This is a private readonly property that points to the backend server.
Dependency Injection
The service is provided at the root level (providedIn: 'root'), making it a singleton available throughout the application.
Constructor Dependencies
Angular’s HTTP client for making HTTP requests. Automatically injected by Angular’s DI system.
Methods
loginUsuario()
Authenticates a user by sending credentials to the backend API via GET request.
Signature:
loginUsuario(usuario: string, contrasena: string): Observable<Usuario>
Parameters:
The username to authenticate
HTTP Request:
- Method:
GET
- Endpoint:
/login/:usuario/:contrasena
- Full URL:
http://localhost:8080/login/{usuario}/{contrasena}
Returns:
An RxJS Observable that emits a Usuario object on successful authentication
Response Structure:
The unique identifier of the authenticated user
The username of the authenticated user
The user’s password (note: typically passwords should not be returned)
Example Usage:
import { Component } from '@angular/core';
import { UsuarioRepository } from '../../domain/repositories/usuario.repository';
import { tap } from 'rxjs';
@Component({
selector: 'app-login-page',
templateUrl: './login-page.html',
})
export class LoginPage {
constructor(private authService: UsuarioRepository) {}
login(usuario: string, contrasena: string) {
this.authService.loginUsuario(usuario, contrasena).pipe(
tap(usuario => {
console.log(usuario);
usuario
? alert('usuario y contraseña correctos!')
: alert('usuario o contraseña incorrectos');
})
).subscribe();
}
}
registrarUsuario()
Registers a new user by sending credentials to the backend API via POST request.
Signature:
registrarUsuario(usuario: string, contrasena: string): Observable<Usuario>
Parameters:
The desired username for the new account
The desired password for the new account
HTTP Request:
- Method:
POST
- Endpoint:
/registro
- Full URL:
http://localhost:8080/registro
- Headers:
Content-Type: application/json
Request Body:
{
"usuario": "string",
"contrasena": "string"
}
Returns:
An RxJS Observable that emits a Usuario object representing the newly created user
Response Structure:
The unique identifier assigned to the new user
The username of the newly registered user
The user’s password (note: typically passwords should not be returned)
Example Usage:
import { Component } from '@angular/core';
import { AuthService } from '../../../services/auth-service';
import { catchError, tap, throwError } from 'rxjs';
@Component({
selector: 'app-register-page',
templateUrl: './register-page.html',
})
export class RegisterPage {
constructor(private authService: AuthService) { }
registrar(usuario: string, contrasena: string) {
this.authService.registrarUsuario(usuario, contrasena).pipe(
tap(usuario => {
console.log('usuario', usuario);
usuario
? alert('usuario registrado correctamente')
: alert(usuario);
}),
catchError(err => {
const mensaje = err.error ? err.error : 'Error desconocido';
alert(`Error al registrar: ${mensaje}`);
return throwError(() => err);
})
).subscribe();
}
}
Architecture Integration
Implements UsuarioRepository
AuthService implements the abstract UsuarioRepository class defined in the domain layer, following the repository pattern and clean architecture principles:
export abstract class UsuarioRepository {
abstract loginUsuario(usuario: string, contrasena: string): Observable<Usuario>;
abstract registrarUsuario(usuario: string, contrasena: string): Observable<Usuario>;
}
Location: src/app/usuario/domain/repositories/usuario.repository.ts
This allows the service to be injected using the abstract repository type, enabling dependency inversion and easier testing.
Usuario Model
Both methods work with the Usuario interface:
export interface Usuario {
id: number,
usuario: string,
contrasena: string
}
Location: src/app/usuario/domain/models/usuario.ts
Observable Patterns
RxJS Integration
The service uses RxJS Observable as the return type for all methods, enabling:
- Lazy execution: HTTP requests are not made until
.subscribe() is called
- Cancellation: Unsubscribing cancels pending HTTP requests
- Operator chaining: Use operators like
tap, map, catchError for reactive programming
- Error handling: HTTP errors are propagated through the Observable stream
Common Patterns
Error Handling:
this.authService.registrarUsuario(usuario, contrasena).pipe(
catchError(err => {
console.error('Registration failed:', err);
return throwError(() => err);
})
).subscribe();
Side Effects with tap:
this.authService.loginUsuario(usuario, contrasena).pipe(
tap(user => console.log('Logged in user:', user))
).subscribe();
Transformation:
this.authService.loginUsuario(usuario, contrasena).pipe(
map(user => user.usuario)
).subscribe(username => console.log(username));
Security Considerations
The current implementation passes credentials in the URL path for the login endpoint (GET request). This is not recommended for production as:
- Credentials appear in server logs
- Credentials are visible in browser history
- URLs may be cached by proxies
Consider using POST requests with body payloads for both login and registration.
The API returns user passwords in the response. In production applications, passwords should never be returned to the client, even after successful authentication. Consider returning only non-sensitive user data or authentication tokens.