using System.Net;
using System.Net.Http.Json;
using System.Text;
using RobotNet10.CustomConfigurationEditor.Models;
namespace RobotNet10.CustomConfigurationEditor.Services.API;
///
/// Service cho giao tiếp với Config REST API
///
public class ConfigApiService(HttpClient httpClient)
{
private readonly HttpClient _httpClient = httpClient;
private readonly string? _baseUrl = httpClient.BaseAddress?.AbsoluteUri;
private const string ApiPath = "api/configs";
// ==========================================
// CONFIG FILE MANAGEMENT
// ==========================================
///
/// Lấy tất cả configs (metadata only)
///
public async Task> GetAllConfigsAsync(string? search = null)
{
var url = $"{_baseUrl}{ApiPath}";
if (!string.IsNullOrEmpty(search))
url += $"?search={Uri.EscapeDataString(search)}";
return await _httpClient.GetFromJsonAsync>(url) ?? [];
}
///
/// Lấy config theo ID
///
public async Task GetConfigByIdAsync(Guid id)
{
return await _httpClient.GetFromJsonAsync($"{_baseUrl}{ApiPath}/{id}");
}
///
/// Lấy config theo ConfigType
///
public async Task GetConfigByTypeAsync(string configType)
{
return await _httpClient.GetFromJsonAsync($"{_baseUrl}{ApiPath}/by-type/{Uri.EscapeDataString(configType)}");
}
///
/// Kiểm tra ConfigType có tồn tại không
///
public async Task ConfigTypeExistsAsync(string configType)
{
return await _httpClient.GetFromJsonAsync($"{_baseUrl}{ApiPath}/exists/{Uri.EscapeDataString(configType)}");
}
///
/// Tạo config mới
///
public async Task CreateConfigAsync(string configType, List variables, string? description = null)
{
var request = new
{
ConfigType = configType,
Variables = variables,
Description = description
};
var response = await _httpClient.PostAsJsonAsync($"{_baseUrl}{ApiPath}", request);
if (!response.IsSuccessStatusCode)
{
var errorMessage = await HttpErrorHelper.GetErrorMessageAsync(response);
throw new HttpRequestException(errorMessage);
}
return await response.Content.ReadFromJsonAsync()
?? throw new Exception("Failed to create config. Invalid response from server.");
}
///
/// Cập nhật config
///
public async Task UpdateConfigAsync(Guid id, List? variables = null, string? description = null)
{
var request = new
{
Variables = variables,
Description = description
};
var response = await _httpClient.PutAsJsonAsync($"{_baseUrl}{ApiPath}/{id}", request);
if (!response.IsSuccessStatusCode)
{
var errorMessage = await HttpErrorHelper.GetErrorMessageAsync(response);
throw new HttpRequestException(errorMessage);
}
return await response.Content.ReadFromJsonAsync()
?? throw new Exception("Failed to update config. Invalid response from server.");
}
///
/// Xóa config
///
public async Task DeleteConfigAsync(Guid id)
{
var response = await _httpClient.DeleteAsync($"{_baseUrl}{ApiPath}/{id}");
if (!response.IsSuccessStatusCode)
{
var errorMessage = await HttpErrorHelper.GetErrorMessageAsync(response);
throw new HttpRequestException(errorMessage);
}
}
// ==========================================
// IMPORT/EXPORT
// ==========================================
///
/// Import config từ JSON file
///
public async Task ImportConfigAsync(Stream fileStream, string fileName, string configType, string? description = null)
{
using var content = new MultipartFormDataContent();
var streamContent = new StreamContent(fileStream);
streamContent.Headers.ContentType = new System.Net.Http.Headers.MediaTypeHeaderValue("application/json");
content.Add(streamContent, "file", fileName);
content.Add(new StringContent(configType), "configType");
if (!string.IsNullOrWhiteSpace(description))
{
content.Add(new StringContent(description), "description");
}
var response = await _httpClient.PostAsync($"{_baseUrl}{ApiPath}/import", content);
if (!response.IsSuccessStatusCode)
{
var errorMessage = await HttpErrorHelper.GetErrorMessageAsync(response);
throw new HttpRequestException(errorMessage);
}
return await response.Content.ReadFromJsonAsync()
?? throw new Exception("Failed to import config. Invalid response from server.");
}
///
/// Export config ra JSON file
///
public async Task ExportConfigAsync(Guid id)
{
var response = await _httpClient.GetAsync($"{_baseUrl}{ApiPath}/{id}/export");
if (!response.IsSuccessStatusCode)
{
var errorMessage = await HttpErrorHelper.GetErrorMessageAsync(response);
throw new HttpRequestException(errorMessage);
}
try
{
// Read content as byte array first, then create memory stream
var bytes = await response.Content.ReadAsByteArrayAsync();
var memoryStream = new MemoryStream(bytes);
memoryStream.Position = 0; // Reset position to beginning
return memoryStream;
}
catch (Exception ex)
{
throw new HttpRequestException($"Failed to read export data: {HttpErrorHelper.GetErrorMessage(ex)}", ex);
}
}
// ==========================================
// VARIABLE MANAGEMENT
// ==========================================
///
/// Cập nhật giá trị của một variable
///
public async Task UpdateVariableAsync(Guid configId, string variableName, object? value)
{
var request = new { Value = value };
var response = await _httpClient.PutAsJsonAsync($"{_baseUrl}{ApiPath}/{configId}/variables/{Uri.EscapeDataString(variableName)}", request);
if (!response.IsSuccessStatusCode)
{
var errorMessage = await HttpErrorHelper.GetErrorMessageAsync(response);
throw new HttpRequestException(errorMessage);
}
return await response.Content.ReadFromJsonAsync()
?? throw new Exception("Failed to update variable. Invalid response from server.");
}
///
/// Thêm variable mới vào config
///
public async Task AddVariableAsync(Guid configId, ConfigVariableModel variable)
{
var response = await _httpClient.PostAsJsonAsync($"{_baseUrl}{ApiPath}/{configId}/variables", variable);
if (!response.IsSuccessStatusCode)
{
var errorMessage = await HttpErrorHelper.GetErrorMessageAsync(response);
throw new HttpRequestException(errorMessage);
}
return await response.Content.ReadFromJsonAsync()
?? throw new Exception("Failed to add variable. Invalid response from server.");
}
///
/// Xóa variable khỏi config
///
public async Task RemoveVariableAsync(Guid configId, string variableName)
{
var response = await _httpClient.DeleteAsync($"{_baseUrl}{ApiPath}/{configId}/variables/{Uri.EscapeDataString(variableName)}");
if (!response.IsSuccessStatusCode)
{
var errorMessage = await HttpErrorHelper.GetErrorMessageAsync(response);
throw new HttpRequestException(errorMessage);
}
return await response.Content.ReadFromJsonAsync()
?? throw new Exception("Failed to remove variable. Invalid response from server.");
}
}