refs #812 adds some unset hash, fix a bug in restore backup, adds in the 200 response the new subnets in the backup restore endpoint. Adds a new schema in nelmio yaml configuration and changes the project name
testing/og-dhcp-API/pipeline/head There was a failure building this commit
Details
testing/og-dhcp-API/pipeline/head There was a failure building this commit
Details
parent
d68208357c
commit
db9ce9c90e
|
@ -1,9 +1,32 @@
|
||||||
nelmio_api_doc:
|
nelmio_api_doc:
|
||||||
documentation:
|
documentation:
|
||||||
info:
|
info:
|
||||||
title: My App
|
title: OgDHCP API
|
||||||
description: This is an awesome app!
|
description: OgDHCP API documentation
|
||||||
version: 1.0.0
|
version: 1.0.0
|
||||||
|
components:
|
||||||
|
schemas:
|
||||||
|
Subnet:
|
||||||
|
type: object
|
||||||
|
properties:
|
||||||
|
id:
|
||||||
|
type: integer
|
||||||
|
description: The ID of the subnet
|
||||||
|
subnet:
|
||||||
|
type: string
|
||||||
|
description: The name of the subnet
|
||||||
|
nextServer:
|
||||||
|
type: string
|
||||||
|
description: The next server in the subnet
|
||||||
|
bootFileName:
|
||||||
|
type: string
|
||||||
|
description: The boot file name for the subnet
|
||||||
|
reservations:
|
||||||
|
type: array
|
||||||
|
items:
|
||||||
|
type: object
|
||||||
|
description: The reservations in the subnet
|
||||||
|
|
||||||
areas: # to filter documented areas
|
areas: # to filter documented areas
|
||||||
path_patterns:
|
path_patterns:
|
||||||
- ^/ogdhcp/ # Accepts routes under /api except /api/doc
|
- ^/ogdhcp/ # Accepts routes under /api except /api/doc
|
||||||
|
|
|
@ -16,25 +16,7 @@ use Exception;
|
||||||
class DhcpController
|
class DhcpController
|
||||||
{
|
{
|
||||||
private $logger;
|
private $logger;
|
||||||
/**
|
|
||||||
* @OA\Info(title="Ogdhcp API", version="1.0")
|
|
||||||
*/
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @OA\Schema(
|
|
||||||
* schema="Subnet",
|
|
||||||
* type="object",
|
|
||||||
* @OA\Property(property="id", type="integer", description="The ID of the subnet"),
|
|
||||||
* @OA\Property(property="subnet", type="string", description="The name of the subnet"),
|
|
||||||
* @OA\Property(property="next-server", type="string", description="The next server in the subnet"),
|
|
||||||
* @OA\Property(property="boot-file-name", type="string", description="The boot file name for the subnet"),
|
|
||||||
* @OA\Property(
|
|
||||||
* property="reservations",
|
|
||||||
* type="array",
|
|
||||||
* @OA\Items(type="object", description="The reservations in the subnet")
|
|
||||||
* )
|
|
||||||
* )
|
|
||||||
*/
|
|
||||||
private $curlKeaService;
|
private $curlKeaService;
|
||||||
|
|
||||||
public function __construct(CurlKeaService $curlKeaService, LoggerInterface $logger)
|
public function __construct(CurlKeaService $curlKeaService, LoggerInterface $logger)
|
||||||
|
@ -42,6 +24,8 @@ class DhcpController
|
||||||
$this->curlKeaService = $curlKeaService;
|
$this->curlKeaService = $curlKeaService;
|
||||||
$this->logger = $logger;
|
$this->logger = $logger;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @Route("/ogdhcp/v1/status", name="getDhcpStatus", methods={"GET"})
|
* @Route("/ogdhcp/v1/status", name="getDhcpStatus", methods={"GET"})
|
||||||
* @OA\Get(
|
* @OA\Get(
|
||||||
|
@ -337,22 +321,27 @@ public function getSubnets(): JsonResponse
|
||||||
* @OA\JsonContent(
|
* @OA\JsonContent(
|
||||||
* oneOf={
|
* oneOf={
|
||||||
* @OA\Schema(
|
* @OA\Schema(
|
||||||
* @OA\Property(property="error", type="string", example="Error: La subred con el nombre 'subnetName' ya existe.")
|
* @OA\Property(property="error", type="string", example="La subred con el nombre 'subnetName' ya existe.")
|
||||||
* ),
|
* ),
|
||||||
* @OA\Schema(
|
* @OA\Schema(
|
||||||
* @OA\Property(property="error", type="string", example="Error: La subred con el ID 'subnetId' ya existe.")
|
* @OA\Property(property="error", type="string", example="La subred con el ID 'subnetId' ya existe.")
|
||||||
* )
|
* )
|
||||||
* }
|
* }
|
||||||
* ),
|
* ),
|
||||||
* @OA\Examples(
|
* @OA\Examples(
|
||||||
* example="nameConflict",
|
* example="nameConflict",
|
||||||
* summary="Subnet name already exists",
|
* summary="Subnet name already exists",
|
||||||
* value={"error": "Error: La subred con el nombre 'subnetName' ya existe."}
|
* value={"error": "La subred con la ip 'subnetName' ya existe."}
|
||||||
* ),
|
* ),
|
||||||
* @OA\Examples(
|
* @OA\Examples(
|
||||||
* example="idConflict",
|
* example="idConflict",
|
||||||
* summary="Subnet ID already exists",
|
* summary="Subnet ID already exists",
|
||||||
* value={"error": "Error: La subred con el ID 'subnetId' ya existe."}
|
* value={"error": "La subred con el ID 'subnetId' ya existe."}
|
||||||
|
* ),
|
||||||
|
* @OA\Examples(
|
||||||
|
* example="subnetCreatedNotFound",
|
||||||
|
* summary="Subnet created not found",
|
||||||
|
* value={"error": "No se pudo encontrar la subred creada"}
|
||||||
* )
|
* )
|
||||||
* ),
|
* ),
|
||||||
* @OA\Response(
|
* @OA\Response(
|
||||||
|
@ -408,9 +397,9 @@ public function addDhcpSubnet(Request $request): JsonResponse
|
||||||
}, false);
|
}, false);
|
||||||
|
|
||||||
if ($subnetNameExists) {
|
if ($subnetNameExists) {
|
||||||
return new JsonResponse(['error' => "Error: La subred con el nombre '$subnetName' ya existe."], 400);
|
return new JsonResponse(['error' => "La subred con la ip '$subnetName' ya existe."], 400);
|
||||||
} elseif ($subnetIdExists) {
|
} elseif ($subnetIdExists) {
|
||||||
return new JsonResponse(['error' => "Error: La subred con el ID '$subnetId' ya existe."], 400);
|
return new JsonResponse(['error' => "La subred con el ID '$subnetId' ya existe."], 400);
|
||||||
} else {
|
} else {
|
||||||
$response[0]['arguments']['Dhcp4']['subnet4'][] = $newSubnet;
|
$response[0]['arguments']['Dhcp4']['subnet4'][] = $newSubnet;
|
||||||
|
|
||||||
|
@ -446,7 +435,7 @@ public function addDhcpSubnet(Request $request): JsonResponse
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($createdSubnet === null) {
|
if ($createdSubnet === null) {
|
||||||
return new JsonResponse(['error' => "Error: No se pudo encontrar la subred creada."], 400);
|
return new JsonResponse(['error' => "No se pudo encontrar la subred creada"], 400);
|
||||||
}
|
}
|
||||||
|
|
||||||
return new JsonResponse(['success' => "Subred agregada correctamente", 'message' => $createdSubnet], 200);
|
return new JsonResponse(['success' => "Subred agregada correctamente", 'message' => $createdSubnet], 200);
|
||||||
|
@ -525,7 +514,7 @@ public function addDhcpSubnet(Request $request): JsonResponse
|
||||||
* description="Subnet not found",
|
* description="Subnet not found",
|
||||||
* @OA\JsonContent(
|
* @OA\JsonContent(
|
||||||
* type="object",
|
* type="object",
|
||||||
* @OA\Property(property="error", type="string", example="Error: La subred con el id '2' no existe")
|
* @OA\Property(property="error", type="string", example="La subred con el id '2' no existe")
|
||||||
* )
|
* )
|
||||||
* ),
|
* ),
|
||||||
* @OA\Response(
|
* @OA\Response(
|
||||||
|
@ -556,7 +545,7 @@ public function addDhcpSubnet(Request $request): JsonResponse
|
||||||
$subnetIndex = array_search($subnetId, array_column($response[0]['arguments']['Dhcp4']['subnet4'], 'id'));
|
$subnetIndex = array_search($subnetId, array_column($response[0]['arguments']['Dhcp4']['subnet4'], 'id'));
|
||||||
|
|
||||||
if ($subnetIndex === false) {
|
if ($subnetIndex === false) {
|
||||||
$responseError = "Error: La subred con el id '$subnetId' no existe";
|
$responseError = "La subred con el id '$subnetId' no existe";
|
||||||
return new JsonResponse(['error' => $responseError], 404);
|
return new JsonResponse(['error' => $responseError], 404);
|
||||||
} else {
|
} else {
|
||||||
//Borramos la subred con ese id
|
//Borramos la subred con ese id
|
||||||
|
@ -726,9 +715,14 @@ public function addDhcpSubnet(Request $request): JsonResponse
|
||||||
"boot-file-name" => $bootFileName,
|
"boot-file-name" => $bootFileName,
|
||||||
"reservations" => []
|
"reservations" => []
|
||||||
];
|
];
|
||||||
|
// Eliminar el campo 'hash' si existe
|
||||||
|
if (isset($response[0]['arguments']['hash'])) {
|
||||||
|
unset($response[0]['arguments']['hash']);
|
||||||
|
}
|
||||||
$array_encoded = json_encode($response[0]['arguments']);
|
$array_encoded = json_encode($response[0]['arguments']);
|
||||||
$configurationParsed = str_replace('\\', '', $array_encoded);
|
$configurationParsed = str_replace('\\', '', $array_encoded);
|
||||||
$configuration = json_decode($configurationParsed);
|
$configuration = json_decode($configurationParsed);
|
||||||
|
|
||||||
$responseTest = $this->curlKeaService->executeCurlCommand('config-test', $configuration);
|
$responseTest = $this->curlKeaService->executeCurlCommand('config-test', $configuration);
|
||||||
|
|
||||||
if ($responseTest[0]["result"] == 0) {
|
if ($responseTest[0]["result"] == 0) {
|
||||||
|
@ -742,8 +736,14 @@ public function addDhcpSubnet(Request $request): JsonResponse
|
||||||
$responseError = "Error al escribir en la configuración en Kea DHCP: " . $responseWrite[0]["text"];
|
$responseError = "Error al escribir en la configuración en Kea DHCP: " . $responseWrite[0]["text"];
|
||||||
return new JsonResponse(['error' => $responseError], 400);
|
return new JsonResponse(['error' => $responseError], 400);
|
||||||
} else {
|
} else {
|
||||||
|
// Volvemos a consultar la configuración para devolver la subred modificada
|
||||||
|
$updatedResponse = $this->curlKeaService->executeCurlCommand('config-get');
|
||||||
|
$updatedSubnet = array_filter($updatedResponse[0]['arguments']['Dhcp4']['subnet4'], function ($subnet) use ($subnetId) {
|
||||||
|
return $subnet['id'] == $subnetId;
|
||||||
|
});
|
||||||
|
|
||||||
$responseSuccess = "Subred modificada correctamente";
|
$responseSuccess = "Subred modificada correctamente";
|
||||||
return new JsonResponse(['success' => $responseSuccess], 200);
|
return new JsonResponse(['success' => $responseSuccess,'subnet' => reset($updatedSubnet)], 200);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
@ -1262,7 +1262,7 @@ public function updateDhcpHost(Request $request, $subnetId): JsonResponse
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
$input = json_decode($request->getContent());
|
$input = json_decode($request->getContent());
|
||||||
$host = htmlspecialchars($input->host);
|
$host = htmlspecialchars($input->hostname);
|
||||||
$oldMacAddress = htmlspecialchars($input->oldMacAddress);
|
$oldMacAddress = htmlspecialchars($input->oldMacAddress);
|
||||||
$macAddress = htmlspecialchars($input->macAddress);
|
$macAddress = htmlspecialchars($input->macAddress);
|
||||||
$address = htmlspecialchars($input->address);
|
$address = htmlspecialchars($input->address);
|
||||||
|
@ -1422,27 +1422,44 @@ public function getLatestBackupConfiguration(): JsonResponse
|
||||||
* @OA\Post(
|
* @OA\Post(
|
||||||
* path="/ogdhcp/v1/backup/restore",
|
* path="/ogdhcp/v1/backup/restore",
|
||||||
* summary="Restore the latest DHCP configuration from backup",
|
* summary="Restore the latest DHCP configuration from backup",
|
||||||
* description="This endpoint restores the last saved DHCP configuration from a backup file and applies it to the Kea DHCP server.",
|
* description="This endpoint restores the last saved DHCP configuration from a backup file and applies it to the Kea DHCP server, returning all currently loaded subnets.",
|
||||||
* @OA\Response(
|
* @OA\Response(
|
||||||
* response=200,
|
* response=200,
|
||||||
* description="Configuration restored successfully",
|
* description="Configuration restored successfully",
|
||||||
* @OA\JsonContent(
|
* @OA\JsonContent(
|
||||||
* type="object",
|
* type="object",
|
||||||
* @OA\Property(property="success", type="string", example="Configuración cargada correctamente")
|
* @OA\Property(property="success", type="string", example="Configuración cargada correctamente"),
|
||||||
|
* @OA\Property(property="subnets", type="array",
|
||||||
|
* @OA\Items(
|
||||||
|
* type="object",
|
||||||
|
* @OA\Property(property="id", type="integer", example=1),
|
||||||
|
* @OA\Property(property="subnet", type="string", example="192.168.1.0/24"),
|
||||||
|
* @OA\Property(property="pools", type="array",
|
||||||
|
* @OA\Items(
|
||||||
|
* type="object",
|
||||||
|
* @OA\Property(property="pool", type="string", example="192.168.1.10-192.168.1.100")
|
||||||
|
* )
|
||||||
|
* ),
|
||||||
|
* @OA\Property(property="reservations", type="array",
|
||||||
|
* @OA\Items(
|
||||||
|
* type="object",
|
||||||
|
* @OA\Property(property="ip-address", type="string", example="192.168.1.20"),
|
||||||
|
* @OA\Property(property="hw-address", type="string", example="00:0c:29:6b:5e:71")
|
||||||
|
* )
|
||||||
|
* )
|
||||||
|
* )
|
||||||
|
* )
|
||||||
* )
|
* )
|
||||||
* ),
|
* ),
|
||||||
* @OA\Response(
|
* @OA\Response(
|
||||||
* response=400,
|
* response=400,
|
||||||
* description="Error occurred while adding the host",
|
* description="Error occurred while restoring the configuration",
|
||||||
* @OA\JsonContent(
|
* @OA\JsonContent(
|
||||||
* oneOf={
|
* oneOf={
|
||||||
* @OA\Schema(
|
* @OA\Schema(
|
||||||
* @OA\Property(property="error", type="string", example="No se encontraron archivos de backup")
|
* @OA\Property(property="error", type="string", example="No se encontraron archivos de backup")
|
||||||
* ),
|
* ),
|
||||||
* @OA\Schema(
|
* @OA\Schema(
|
||||||
* @OA\Property(property="error", type="string", example="El host con la MAC '$mac' no existe en las reservaciones")
|
|
||||||
* ),
|
|
||||||
* @OA\Schema(
|
|
||||||
* @OA\Property(property="error", type="string", example="Error configuracion de kea invalido")
|
* @OA\Property(property="error", type="string", example="Error configuracion de kea invalido")
|
||||||
* ),
|
* ),
|
||||||
* @OA\Schema(
|
* @OA\Schema(
|
||||||
|
@ -1459,11 +1476,6 @@ public function getLatestBackupConfiguration(): JsonResponse
|
||||||
* value={"error": "No se encontraron archivos de backup"}
|
* value={"error": "No se encontraron archivos de backup"}
|
||||||
* ),
|
* ),
|
||||||
* @OA\Examples(
|
* @OA\Examples(
|
||||||
* example="hostNotFound",
|
|
||||||
* summary="Host not found",
|
|
||||||
* value={"error": "El host con la MAC '$mac' no existe en las reservaciones"}
|
|
||||||
* ),
|
|
||||||
* @OA\Examples(
|
|
||||||
* example="invalidKea",
|
* example="invalidKea",
|
||||||
* summary="Error in config-test in kea",
|
* summary="Error in config-test in kea",
|
||||||
* value={"error": "Error configuracion de kea invalido"}
|
* value={"error": "Error configuracion de kea invalido"}
|
||||||
|
@ -1478,55 +1490,66 @@ public function getLatestBackupConfiguration(): JsonResponse
|
||||||
* summary="Error in config-write in kea",
|
* summary="Error in config-write in kea",
|
||||||
* value={"error": "Error al escribir en la configuración en Kea DHCP"}
|
* value={"error": "Error al escribir en la configuración en Kea DHCP"}
|
||||||
* )
|
* )
|
||||||
* ),
|
* )
|
||||||
* )
|
* )
|
||||||
* @Route("/ogdhcp/v1/backup/restore", methods={"POST"})
|
* @Route("/ogdhcp/v1/backup/restore", methods={"POST"})
|
||||||
*/
|
*/
|
||||||
|
public function restoreDhcpConfiguration(): JsonResponse
|
||||||
|
{
|
||||||
|
$backup_dir = '/opt/ogdhcp/etc/kea/backup';
|
||||||
|
try {
|
||||||
|
$backup_files = glob($backup_dir . '/*.conf');
|
||||||
|
if (empty($backup_files)) {
|
||||||
|
$response = "No se encontraron archivos de backup";
|
||||||
|
return new JsonResponse(['error' => $response], 400);
|
||||||
|
} else {
|
||||||
|
usort($backup_files, function ($a, $b) {
|
||||||
|
return filemtime($b) - filemtime($a);
|
||||||
|
});
|
||||||
|
$backup_file = reset($backup_files);
|
||||||
|
$config = file_get_contents($backup_file);
|
||||||
|
// Eliminar el campo 'hash' si existe
|
||||||
|
$configuration = json_decode($config);
|
||||||
|
if (isset($configuration->hash)) {
|
||||||
|
unset($configuration->hash);
|
||||||
|
}
|
||||||
|
|
||||||
public function restoreDhcpConfiguration(): JsonResponse
|
$test_command = 'config-test';
|
||||||
{
|
$test_output = $this->curlKeaService->executeCurlCommand($test_command, $configuration);
|
||||||
$backup_dir = '/opt/opengnsys/etc/kea/backup';
|
if ($test_output == false || $test_output[0]["result"] != 0) {
|
||||||
try {
|
$responseError = "Error al comprobar la configuración de Kea: " . $test_output[0]["text"];
|
||||||
$backup_files = glob($backup_dir . '/*.conf');
|
return new JsonResponse(['error' => $responseError], 400);
|
||||||
if (empty($backup_files)) {
|
|
||||||
$response = "No se encontraron archivos de backup";
|
|
||||||
return new JsonResponse(['error' => $response], 400);
|
|
||||||
} else {
|
} else {
|
||||||
usort($backup_files, function ($a, $b) {
|
$set_command = 'config-set';
|
||||||
return filemtime($b) - filemtime($a);
|
$set_output = $this->curlKeaService->executeCurlCommand($set_command, $configuration, false);
|
||||||
});
|
if ($set_output == false || $set_output[0]["result"] != 0) {
|
||||||
$backup_file = reset($backup_files);
|
$responseError = "Error al guardar la última configuración de Kea: " . $set_output[0]["text"];
|
||||||
$config = file_get_contents($backup_file);
|
|
||||||
$configuration = json_decode($config);
|
|
||||||
$test_command = 'config-test';
|
|
||||||
$test_output = $this->curlKeaService->executeCurlCommand($test_command, $configuration);
|
|
||||||
if ($test_output == false || $test_output[0]["result"] != 0) {
|
|
||||||
$responseError = "Error al comprobar la configuración de Kea: " . $test_output[0]["text"];
|
|
||||||
return new JsonResponse(['error' => $responseError], 400);
|
return new JsonResponse(['error' => $responseError], 400);
|
||||||
} else {
|
} else {
|
||||||
$set_command = 'config-set';
|
unlink($backup_file);
|
||||||
$set_output = $this->curlKeaService->executeCurlCommand($set_command, $configuration, false);
|
$responseWrite = $this->curlKeaService->executeCurlCommand('config-write', $configuration);
|
||||||
if ($set_output == false || $set_output[0]["result"] != 0) {
|
if ($responseWrite == false || $responseWrite[0]["result"] != 0) {
|
||||||
$responseError = "Error al guardar la última configuración de Kea: " . $set_output[0]["text"];
|
$responseError = "Error al guardar la configuración en Kea DHCP: " . $responseWrite[0]["text"];
|
||||||
return new JsonResponse(['error' => $responseError], 400);
|
return new JsonResponse(['error' => $responseError], 400);
|
||||||
} else {
|
} else {
|
||||||
unlink($backup_file);
|
// Consultar las subredes cargadas
|
||||||
$responseWrite = $this->curlKeaService->executeCurlCommand('config-write', $configuration);
|
$config_get = $this->curlKeaService->executeCurlCommand('config-get');
|
||||||
if ($responseWrite == false || $responseWrite[0]["result"] != 0) {
|
if ($config_get == false || $config_get[0]["result"] != 0) {
|
||||||
$responseError = "Error al guardar la configuración en Kea DHCP: " . $responseWrite[0]["text"];
|
return new JsonResponse(['error' => 'Error al obtener la configuración de Kea DHCP'], 500);
|
||||||
return new JsonResponse(['error' => $responseError], 400);
|
|
||||||
} else {
|
|
||||||
$responseSuccess = "Configuración cargada correctamente";
|
|
||||||
return new JsonResponse(['success' => $responseSuccess], 200);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$subnets = $config_get[0]['arguments']['Dhcp4']['subnet4'] ?? [];
|
||||||
|
return new JsonResponse(['success' => "Configuración cargada correctamente", 'subnets' => $subnets], 200);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} catch (Exception $e) {
|
|
||||||
$responseError = "Error al restaurar la configuración: " . $e->getMessage();
|
|
||||||
return new JsonResponse(['error' => $responseError], 400);
|
|
||||||
}
|
}
|
||||||
|
} catch (Exception $e) {
|
||||||
|
$responseError = "Error al restaurar la configuración: " . $e->getMessage();
|
||||||
|
return new JsonResponse(['error' => $responseError], 400);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,7 +28,8 @@ class CurlKeaService
|
||||||
} else {
|
} else {
|
||||||
return "Error: Comando no válido";
|
return "Error: Comando no válido";
|
||||||
}
|
}
|
||||||
if (($command == 'config-set' || $command == 'config-write') && $create_backup) {
|
//f (($command == 'config-set' || $command == 'config-write') && $create_backup) {
|
||||||
|
if ($command == 'config-set' && $create_backup) {
|
||||||
$this->backupConfig();
|
$this->backupConfig();
|
||||||
}
|
}
|
||||||
$jsonData = json_encode($requestData);
|
$jsonData = json_encode($requestData);
|
||||||
|
|
Loading…
Reference in New Issue