RunSqlCommandTest.php 4.13 KB
Newer Older
1 2
<?php

3
namespace Doctrine\DBAL\Tests\Tools\Console;
4

Sergei Morozov's avatar
Sergei Morozov committed
5
use Doctrine\DBAL\Connection;
6 7
use Doctrine\DBAL\Tools\Console\Command\RunSqlCommand;
use Doctrine\DBAL\Tools\Console\ConsoleRunner;
Sergei Morozov's avatar
Sergei Morozov committed
8 9 10
use LogicException;
use PHPUnit\Framework\TestCase;
use RuntimeException;
11 12 13
use Symfony\Component\Console\Application;
use Symfony\Component\Console\Tester\CommandTester;

Sergei Morozov's avatar
Sergei Morozov committed
14
class RunSqlCommandTest extends TestCase
15 16 17 18 19 20
{
    /** @var CommandTester */
    private $commandTester;
    /** @var RunSqlCommand */
    private $command;

Sergei Morozov's avatar
Sergei Morozov committed
21
    /** @var Connection */
22 23
    private $connectionMock;

24
    protected function setUp() : void
25 26 27 28
    {
        $application = new Application();
        $application->add(new RunSqlCommand());

Sergei Morozov's avatar
Sergei Morozov committed
29
        $this->command       = $application->find('dbal:run-sql');
30 31
        $this->commandTester = new CommandTester($this->command);

Sergei Morozov's avatar
Sergei Morozov committed
32
        $this->connectionMock = $this->createMock(Connection::class);
33
        $this->connectionMock->method('fetchAll')
Sergei Morozov's avatar
Sergei Morozov committed
34
            ->willReturn([[1]]);
35 36 37 38 39 40 41
        $this->connectionMock->method('executeUpdate')
            ->willReturn(42);

        $helperSet = ConsoleRunner::createHelperSet($this->connectionMock);
        $this->command->setHelperSet($helperSet);
    }

42
    public function testMissingSqlArgument() : void
43 44
    {
        try {
Sergei Morozov's avatar
Sergei Morozov committed
45
            $this->commandTester->execute([
46 47
                'command' => $this->command->getName(),
                'sql' => null,
Sergei Morozov's avatar
Sergei Morozov committed
48
            ]);
49
            self::fail('Expected a runtime exception when omitting sql argument');
Sergei Morozov's avatar
Sergei Morozov committed
50
        } catch (RuntimeException $e) {
51
            self::assertStringContainsString("Argument 'SQL", $e->getMessage());
52 53 54
        }
    }

55
    public function testIncorrectDepthOption() : void
56 57
    {
        try {
Sergei Morozov's avatar
Sergei Morozov committed
58
            $this->commandTester->execute([
59 60 61
                'command' => $this->command->getName(),
                'sql' => 'SELECT 1',
                '--depth' => 'string',
Sergei Morozov's avatar
Sergei Morozov committed
62
            ]);
63
            self::fail('Expected a logic exception when executing with a stringy depth');
Sergei Morozov's avatar
Sergei Morozov committed
64
        } catch (LogicException $e) {
65
            self::assertStringContainsString("Option 'depth'", $e->getMessage());
66 67 68
        }
    }

69
    public function testSelectStatementsPrintsResult() : void
70 71 72
    {
        $this->expectConnectionFetchAll();

73
        $exitCode = $this->commandTester->execute([
74 75
            'command' => $this->command->getName(),
            'sql' => 'SELECT 1',
Sergei Morozov's avatar
Sergei Morozov committed
76
        ]);
77
        self::assertSame(0, $exitCode);
78

79 80
        self::assertMatchesRegularExpression('@int.*1.*@', $this->commandTester->getDisplay());
        self::assertMatchesRegularExpression('@array.*1.*@', $this->commandTester->getDisplay());
81 82
    }

83
    public function testUpdateStatementsPrintsAffectedLines() : void
84 85 86
    {
        $this->expectConnectionExecuteUpdate();

Sergei Morozov's avatar
Sergei Morozov committed
87
        $this->commandTester->execute([
88 89
            'command' => $this->command->getName(),
            'sql' => 'UPDATE foo SET bar = 42',
Sergei Morozov's avatar
Sergei Morozov committed
90
        ]);
91

92 93
        self::assertMatchesRegularExpression('@int.*42.*@', $this->commandTester->getDisplay());
        self::assertDoesNotMatchRegularExpression('@array.*1.*@', $this->commandTester->getDisplay());
94 95
    }

96
    private function expectConnectionExecuteUpdate() : void
97 98
    {
        $this->connectionMock
99
            ->expects(self::exactly(1))
100 101
            ->method('executeUpdate');
        $this->connectionMock
102
            ->expects(self::exactly(0))
103 104 105
            ->method('fetchAll');
    }

106
    private function expectConnectionFetchAll() : void
107 108
    {
        $this->connectionMock
109
            ->expects(self::exactly(0))
110 111
            ->method('executeUpdate');
        $this->connectionMock
112
            ->expects(self::exactly(1))
113 114
            ->method('fetchAll');
    }
115

116
    public function testStatementsWithFetchResultPrintsResult() : void
117 118 119
    {
        $this->expectConnectionFetchAll();

Sergei Morozov's avatar
Sergei Morozov committed
120
        $this->commandTester->execute([
121 122
            'command' => $this->command->getName(),
            'sql' => '"WITH bar as (SELECT 1) SELECT * FROM bar',
123
            '--force-fetch' => true,
Sergei Morozov's avatar
Sergei Morozov committed
124
        ]);
125

126 127
        self::assertMatchesRegularExpression('@int.*1.*@', $this->commandTester->getDisplay());
        self::assertMatchesRegularExpression('@array.*1.*@', $this->commandTester->getDisplay());
128
    }
129
}