feat(website-extras): enhance toggle functionality and update related tests; add additional info configuration to tenant extras

This commit is contained in:
2026-08-03 09:10:50 -03:00
parent f1df6a5918
commit 4a51f3afde
10 changed files with 134 additions and 17 deletions

View File

@@ -65,7 +65,10 @@ class WebsiteExtraController extends Controller
return WebsiteExtrasResource::make(
$this->loadTenant($request->user())
);
)->additional([
'code' => 'tenant.website_extra_toggled',
'message' => __('api.tenant.website_extra_toggled'),
]);
}
private function loadTenant(User $user): Tenant

View File

@@ -174,7 +174,15 @@ class WebsiteExtraService
$websiteExtra = $tenant->websiteExtras()
->where('website_type_extra_id', $definition->id)
->lockForUpdate()
->firstOrFail();
->first();
if (! $websiteExtra) {
return $tenant->websiteExtras()->create([
'website_type_extra_id' => $definition->id,
'config' => [],
'is_enabled' => true,
]);
}
$websiteExtra->update([
'is_enabled' => ! $websiteExtra->is_enabled,

View File

@@ -120,7 +120,6 @@ class TenantSeeder extends Seeder
'extras' => [
'heroConfig' => [
'title_html' => '<h1>Fiesta Fútbol Infantil</h1>',
'description_html' => '<p>Viví una jornada inolvidable de fútbol infantil.</p>',
'button_text' => 'Comprar entradas',
'button_href' => '/tickets',
'background_image_id' => $this->uploadedImage(
@@ -133,10 +132,21 @@ class TenantSeeder extends Seeder
'location' => 'Rosario, Santa Fe',
'dates_text' => '9, 10, 11 y 12 de Octubre 2026',
'dates' => [
'2026-12-05',
'2026-12-06',
[
'date' => '2026-12-05',
'start_time' => '09:00',
'end_time' => '18:00',
],
[
'date' => '2026-12-06',
'start_time' => '09:00',
'end_time' => '18:00',
],
],
],
'additionalInfoConfig' => [
'description' => '<p>Viví una jornada inolvidable de fútbol infantil.</p>',
],
],
]);
}

View File

@@ -107,7 +107,30 @@ class WebsiteTypeSeeder extends Seeder
'location' => 'nullable|string',
'dates_text' => 'nullable|string|max:255',
'dates' => 'nullable|array',
'dates.*' => 'required|date_format:Y-m-d|distinct',
'dates.*' => 'required|array:date,start_time,end_time',
'dates.*.date' => 'required|date_format:Y-m-d|distinct',
'dates.*.start_time' => 'required|date_format:H:i',
'dates.*.end_time' => 'required|date_format:H:i',
'contact' => 'nullable|array:whatsapp_url,instagram_url,facebook_url',
'contact.whatsapp_url' => 'nullable|url|max:2048',
'contact.instagram_url' => 'nullable|url|max:2048',
'contact.facebook_url' => 'nullable|url|max:2048',
],
'transforms' => [],
],
],
);
$onTicket->extras()->updateOrCreate(
['codigo' => 'additionalInfoConfig'],
[
'nombre' => 'Información adicional',
'descripcion' => 'Información adicional visible en la página del evento.',
'is_required' => false,
'config_schema' => [
'request_rules' => [
'$' => 'required|array',
'description' => 'nullable|string',
],
'transforms' => [],
],

View File

@@ -94,6 +94,9 @@ return [
'schema_required' => 'The schema is required for static menus.',
'not_found' => 'The specified menu does not exist.',
],
'tenant' => [
'website_extra_toggled' => 'The section status was updated successfully.',
],
'errors' => [
'forbidden' => 'You do not have permission to perform this action.',
'not_found' => 'The requested resource was not found.',

View File

@@ -94,6 +94,9 @@ return [
'schema_required' => 'El schema es obligatorio para los menús estáticos.',
'not_found' => 'El menú indicado no existe.',
],
'tenant' => [
'website_extra_toggled' => 'El estado de la sección se actualizó correctamente.',
],
'errors' => [
'forbidden' => 'No tienes permiso para realizar esta acción.',
'not_found' => 'El recurso solicitado no fue encontrado.',

View File

@@ -84,12 +84,13 @@ class TenantSeederTest extends TestCase
$extras = $fiesta->websiteExtras->keyBy('websiteTypeExtra.codigo');
$this->assertEqualsCanonicalizing(
['heroConfig', 'eventConfig'],
['heroConfig', 'eventConfig', 'additionalInfoConfig'],
$extras->keys()->all(),
);
$heroConfig = $extras->get('heroConfig')->config;
$this->assertSame('<h1>Fiesta Fútbol Infantil</h1>', $heroConfig['title_html']);
$this->assertArrayNotHasKey('description_html', $heroConfig);
$this->assertIsInt($heroConfig['background_image_id']);
$this->assertDatabaseHas('attachments', [
'id' => $heroConfig['background_image_id'],
@@ -101,9 +102,21 @@ class TenantSeederTest extends TestCase
'location' => 'Rosario, Santa Fe',
'dates_text' => '9, 10, 11 y 12 de Octubre 2026',
'dates' => [
'2026-12-05',
'2026-12-06',
[
'date' => '2026-12-05',
'start_time' => '09:00',
'end_time' => '18:00',
],
[
'date' => '2026-12-06',
'start_time' => '09:00',
'end_time' => '18:00',
],
],
], $extras->get('eventConfig')->config);
$this->assertSame([
'description' => '<p>Viví una jornada inolvidable de fútbol infantil.</p>',
], $extras->get('additionalInfoConfig')->config);
}
}

View File

@@ -78,7 +78,7 @@ class WebsiteTypeSeederTest extends TestCase
$this->assertNotSame($shopIt->site_logo, $onTicket->site_logo);
$this->assertNotSame($shopIt->footer_logo, $onTicket->footer_logo);
$this->assertEqualsCanonicalizing(
['heroConfig', 'eventConfig'],
['heroConfig', 'eventConfig', 'additionalInfoConfig'],
$onTicket->extras->pluck('codigo')->all(),
);
@@ -108,9 +108,27 @@ class WebsiteTypeSeederTest extends TestCase
'location' => 'nullable|string',
'dates_text' => 'nullable|string|max:255',
'dates' => 'nullable|array',
'dates.*' => 'required|date_format:Y-m-d|distinct',
'dates.*' => 'required|array:date,start_time,end_time',
'dates.*.date' => 'required|date_format:Y-m-d|distinct',
'dates.*.start_time' => 'required|date_format:H:i',
'dates.*.end_time' => 'required|date_format:H:i',
'contact' => 'nullable|array:whatsapp_url,instagram_url,facebook_url',
'contact.whatsapp_url' => 'nullable|url|max:2048',
'contact.instagram_url' => 'nullable|url|max:2048',
'contact.facebook_url' => 'nullable|url|max:2048',
],
'transforms' => [],
], $eventSchema);
$additionalInfoSchema = $onTicket->extras
->firstWhere('codigo', 'additionalInfoConfig')
->config_schema;
$this->assertSame([
'request_rules' => [
'$' => 'required|array',
'description' => 'nullable|string',
],
'transforms' => [],
], $additionalInfoSchema);
}
}

View File

@@ -195,6 +195,8 @@ class AdminAppWebsiteExtraControllerTest extends TestCase
$this->patchJson('/api/v1/adminapp/tenant/website-extras/contactConfig/toggle')
->assertOk()
->assertJsonPath('code', 'tenant.website_extra_toggled')
->assertJsonPath('message', 'El estado de la sección se actualizó correctamente.')
->assertJsonPath('data.definitions.contactConfig.is_enabled', true);
$this->assertTrue($websiteExtra->refresh()->is_enabled);
@@ -206,13 +208,21 @@ class AdminAppWebsiteExtraControllerTest extends TestCase
$this->assertFalse($websiteExtra->refresh()->is_enabled);
}
public function test_toggle_returns_not_found_for_an_extra_without_a_tenant_value(): void
public function test_toggle_enables_an_extra_without_a_tenant_value(): void
{
$tenant = $this->createTenant('acme');
Sanctum::actingAs($this->createAdminAppUser($tenant));
$this->patchJson('/api/v1/adminapp/tenant/website-extras/contactConfig/toggle')
->assertNotFound();
->assertOk()
->assertJsonPath('data.definitions.contactConfig.is_enabled', true)
->assertJsonPath('data.extras.contactConfig', []);
$this->assertDatabaseHas('websites_extras', [
'website_code' => $tenant->codigo,
'website_type_extra_id' => $this->websiteType->extras()->firstOrFail()->id,
'is_enabled' => true,
]);
}
private function createTenant(string $code): Tenant

View File

@@ -31,7 +31,18 @@ class StoreTenantWithExtrasTest extends TestCase
'title' => 'Festival',
'location' => 'Buenos Aires',
'dates_text' => '10 y 11 de octubre de 2026',
'dates' => ['2026-10-10', '2026-10-11'],
'dates' => [
[
'date' => '2026-10-10',
'start_time' => '09:00',
'end_time' => '18:00',
],
[
'date' => '2026-10-11',
'start_time' => '10:00',
'end_time' => '17:00',
],
],
],
],
]));
@@ -52,7 +63,18 @@ class StoreTenantWithExtrasTest extends TestCase
'title' => 'Festival',
'location' => 'Buenos Aires',
'dates_text' => '10 y 11 de octubre de 2026',
'dates' => ['2026-10-10', '2026-10-11'],
'dates' => [
[
'date' => '2026-10-10',
'start_time' => '09:00',
'end_time' => '18:00',
],
[
'date' => '2026-10-11',
'start_time' => '10:00',
'end_time' => '17:00',
],
],
],
$tenant->websiteExtras()->sole()->config
);
@@ -80,12 +102,16 @@ class StoreTenantWithExtrasTest extends TestCase
'website_type_code' => 'onticket',
'extras' => [
'eventConfig' => [
'dates' => ['not-a-date'],
'dates' => [[
'date' => 'not-a-date',
'start_time' => '09:00',
'end_time' => '18:00',
]],
],
],
]))
->assertUnprocessable()
->assertJsonValidationErrors(['extras.eventConfig.dates.0']);
->assertJsonValidationErrors(['extras.eventConfig.dates.0.date']);
$this->assertDatabaseMissing('tenants', ['codigo' => 'festival']);
}