Skip to content

Implement DELETE endpoint for heroes API #48

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
wants to merge 4 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
42 changes: 42 additions & 0 deletions docs/api-reference.md
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,42 @@ Recupera la información detallada de un héroe específico usando su ID.
}
```

### Eliminar un héroe por ID

Elimina un héroe específico usando su ID.

**Endpoint**: `DELETE /api/heroes/:id`

**Parámetros de ruta**:

| Parámetro | Tipo | Descripción | Ejemplo |
|-----------|--------|------------------|-----------|
| id | number | ID del héroe | /api/heroes/1 |

**Respuesta exitosa** (código 200):

```json
{
"message": "Hero deleted successfully"
}
```

**Respuesta de error** (código 404):

```json
{
"error": "Hero not found"
}
```

**Respuesta de error** (código 400):

```json
{
"error": "Invalid hero ID. ID must be a number."
}
```

## Manejo de Errores

La API utiliza los siguientes códigos de estado HTTP:
Expand Down Expand Up @@ -158,4 +194,10 @@ curl http://localhost:3000/api/heroes/1

```bash
curl http://localhost:3000/api/heroes?team=Justice&page=1&limit=2
```

### Eliminar un héroe específico

```bash
curl -X DELETE http://localhost:3000/api/heroes/1
```
25 changes: 25 additions & 0 deletions docs/basic-usage.md
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,25 @@ La API proporciona los siguientes endpoints principales:
- `PUT /api/heroes/:id`: Actualiza un héroe existente
- `DELETE /api/heroes/:id`: Elimina un héroe por su ID

#### Eliminar un héroe por ID

- **Endpoint**: `DELETE /api/heroes/:id`
- **Descripción**: Elimina un héroe específico de la base de datos
- **Parámetros de ruta**:
- `id`: ID numérico del héroe
- **Respuesta exitosa** (código 200):
```json
{
"message": "Hero deleted successfully"
}
```
- **Respuesta de error** (código 404):
```json
{
"error": "Hero not found"
}
```

## Ejemplos de Uso

### Obtener todos los héroes
Expand Down Expand Up @@ -177,6 +196,12 @@ curl http://localhost:3000/api/heroes?name=man&page=1&limit=3
curl http://localhost:3000/api/heroes/1
```

### Eliminar un héroe por ID

```bash
curl -X DELETE http://localhost:3000/api/heroes/1
```

## Próximos Pasos

Para desarrollar en entornos más avanzados, consulta:
Expand Down
5 changes: 4 additions & 1 deletion heroes.http
Original file line number Diff line number Diff line change
Expand Up @@ -71,4 +71,7 @@ Content-Type: {{contentType}}
"alterEgo": "Spider-Man",
"powers": ["Wall-Crawling", "Spider-Sense", "Super Strength"],
"team": "Avengers"
}
}

### Delete a hero by ID
DELETE {{baseUrl}}/heroes/1 HTTP/1.1
37 changes: 36 additions & 1 deletion src/controllers/hero.controller.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@
import { Request, Response, NextFunction } from 'express';
import { HeroService, HeroFilterOptions, CreateHeroResult } from '../services/hero.service.js';
import {
HeroService,
HeroFilterOptions,
CreateHeroResult,
DeleteHeroResult,
} from '../services/hero.service.js';
import { Hero } from '../models/hero.model.js';

export class HeroController {
Expand Down Expand Up @@ -141,4 +146,34 @@ export class HeroController {
next(error);
}
}

/**
* Delete a hero by ID
* @route DELETE /api/heroes/:id
* @param {number} id - Hero ID
* @returns {Object} Success message or error if not found
*/
async deleteHero(req: Request, res: Response, next: NextFunction): Promise<void> {
try {
const id = Number(req.params.id);

if (isNaN(id)) {
res.status(400).json({ error: 'Invalid hero ID. ID must be a number.' });
return;
}

const result: DeleteHeroResult = await this.heroService.deleteHeroById(id);

if (!result.success) {
res.status(404).json({ error: result.error });
return;
}

res.status(200).json({
message: 'Hero deleted successfully',
});
} catch (error) {
next(error);
}
}
}
1 change: 1 addition & 0 deletions src/routes/hero.routes.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,5 +8,6 @@ const heroController = new HeroController();
router.get('/', (req, res, next) => heroController.getHeroes(req, res, next));
router.get('/:id', (req, res, next) => heroController.getHeroById(req, res, next));
router.post('/', (req, res, next) => heroController.createHero(req, res, next));
router.delete('/:id', (req, res, next) => heroController.deleteHero(req, res, next));

export default router;
34 changes: 34 additions & 0 deletions src/services/hero.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,12 @@ export interface CreateHeroResult {
error?: string;
}

// Define interface for hero deletion result
export interface DeleteHeroResult {
success: boolean;
error?: string;
}

export class HeroService {
/**
* Get heroes from the database with filtering and pagination
Expand Down Expand Up @@ -146,4 +152,32 @@ export class HeroService {
};
}
}

/**
* Delete a hero by id from the database
* @param id Hero id to delete
* @returns Promise resolving to delete result with success flag and error if applicable
*/
async deleteHeroById(id: number): Promise<DeleteHeroResult> {
try {
const deletedHero = await HeroModel.findOneAndDelete({ id });

if (!deletedHero) {
return {
success: false,
error: 'Hero not found',
};
}

return {
success: true,
};
} catch (error) {
console.error(`Error deleting hero with id ${id}:`, error);
return {
success: false,
error: 'An unexpected error occurred while deleting the hero',
};
}
}
}