packages/sql-faker/tests/Unit/MySql/Generation/Rewrite/AlterEventRuleTest.php

1<?php
2
3declare(strict_types=1);
4
5namespace Tests\Unit\SqlFaker\MySql\Generation\Rewrite;
6
7use PHPUnit\Framework\Attributes\CoversClass;
8use PHPUnit\Framework\Attributes\DataProvider;
9use PHPUnit\Framework\Attributes\UsesClass;
10use PHPUnit\Framework\TestCase;
11use SqlFaker\Generation\Token\ProductionOccurrence;
12use SqlFaker\Generation\Token\TerminalOccurrence;
13use SqlFaker\Generation\Token\TerminalSequence;
14use SqlFaker\MySql\Generation\Rewrite\AlterEventRule;
15
16#[CoversClass(AlterEventRule::class)]
17#[UsesClass(ProductionOccurrence::class)]
18#[UsesClass(TerminalOccurrence::class)]
19#[UsesClass(TerminalSequence::class)]
20final class AlterEventRuleTest extends TestCase
21{
22    public function testRewriteAddsStatusOnlyWhenEveryAlterationWasOmitted(): void
23    {
24        $name = new TerminalOccurrence('IDENT', 3, [0, 1], ['alter_event_stmt', 'sp_name']);
25        $input = new TerminalSequence([$name], [$name], [], [new ProductionOccurrence(0, null, 'alter_event_stmt', 0), new ProductionOccurrence(1, 0, 'sp_name', 0), new ProductionOccurrence(2, 0, 'opt_ev_status', 0)]);
26        $rule = new AlterEventRule();
27        $result = $rule->rewrite($input);
28        self::assertSame(['IDENT', 'ENABLE_SYM'], $result->names());
29        self::assertSame([0, 2], $result->terminals[1]->ancestors);
30        self::assertSame($input->original, $result->original);
31        self::assertCount(count($result->terminals), array_unique(array_map(static fn ($terminal): int => $terminal->id, $result->terminals)));
32        self::assertSame($result, $rule->rewrite($result));
33    }
34
35    #[DataProvider('providerAlterations')]
36    public function testRewriteKeepsExistingAlterationsAndUnrelatedStatements(string $scope, string $clause): void
37    {
38        $name = new TerminalOccurrence('IDENT', 3, [0, 1], [$scope, 'sp_name']);
39        $alteration = new TerminalOccurrence('EXISTING', 4, [0, 2], [$scope, $clause]);
40        $input = new TerminalSequence([$name, $alteration], [], [], [new ProductionOccurrence(0, null, $scope, 0), new ProductionOccurrence(1, 0, 'sp_name', 0), new ProductionOccurrence(2, 0, $clause, 0)]);
41        self::assertSame($input, (new AlterEventRule())->rewrite($input));
42    }
43
44    /**
45     * @return list<array{string, string}>
46     */
47    public static function providerAlterations(): array
48    {
49        return [['alter_event_stmt', 'ev_alter_on_schedule_completion'], ['alter_event_stmt', 'opt_ev_rename_to'], ['alter_event_stmt', 'opt_ev_status'], ['alter_event_stmt', 'opt_ev_comment'], ['alter_event_stmt', 'opt_ev_sql_stmt'], ['create_event_stmt', 'opt_ev_status']];
50    }
51}
52