Subversion-Projekte lars-tiefland.laravel_shop

Revision

Details | Letzte Änderung | Log anzeigen | RSS feed

Revision Autor Zeilennr. Zeile
148 lars 1
<?php
2
 
3
namespace Illuminate\Database\Schema;
4
 
5
use Exception;
6
use Illuminate\Database\Connection;
7
use Illuminate\Support\Str;
8
use Symfony\Component\Process\Process;
9
 
10
class MySqlSchemaState extends SchemaState
11
{
12
    /**
13
     * Dump the database's schema into a file.
14
     *
15
     * @param  \Illuminate\Database\Connection  $connection
16
     * @param  string  $path
17
     * @return void
18
     */
19
    public function dump(Connection $connection, $path)
20
    {
21
        $this->executeDumpProcess($this->makeProcess(
22
            $this->baseDumpCommand().' --routines --result-file="${:LARAVEL_LOAD_PATH}" --no-data'
23
        ), $this->output, array_merge($this->baseVariables($this->connection->getConfig()), [
24
            'LARAVEL_LOAD_PATH' => $path,
25
        ]));
26
 
27
        $this->removeAutoIncrementingState($path);
28
 
29
        $this->appendMigrationData($path);
30
    }
31
 
32
    /**
33
     * Remove the auto-incrementing state from the given schema dump.
34
     *
35
     * @param  string  $path
36
     * @return void
37
     */
38
    protected function removeAutoIncrementingState(string $path)
39
    {
40
        $this->files->put($path, preg_replace(
41
            '/\s+AUTO_INCREMENT=[0-9]+/iu',
42
            '',
43
            $this->files->get($path)
44
        ));
45
    }
46
 
47
    /**
48
     * Append the migration data to the schema dump.
49
     *
50
     * @param  string  $path
51
     * @return void
52
     */
53
    protected function appendMigrationData(string $path)
54
    {
55
        $process = $this->executeDumpProcess($this->makeProcess(
56
            $this->baseDumpCommand().' '.$this->migrationTable.' --no-create-info --skip-extended-insert --skip-routines --compact'
57
        ), null, array_merge($this->baseVariables($this->connection->getConfig()), [
58
            //
59
        ]));
60
 
61
        $this->files->append($path, $process->getOutput());
62
    }
63
 
64
    /**
65
     * Load the given schema file into the database.
66
     *
67
     * @param  string  $path
68
     * @return void
69
     */
70
    public function load($path)
71
    {
72
        $command = 'mysql '.$this->connectionString().' --database="${:LARAVEL_LOAD_DATABASE}" < "${:LARAVEL_LOAD_PATH}"';
73
 
74
        $process = $this->makeProcess($command)->setTimeout(null);
75
 
76
        $process->mustRun(null, array_merge($this->baseVariables($this->connection->getConfig()), [
77
            'LARAVEL_LOAD_PATH' => $path,
78
        ]));
79
    }
80
 
81
    /**
82
     * Get the base dump command arguments for MySQL as a string.
83
     *
84
     * @return string
85
     */
86
    protected function baseDumpCommand()
87
    {
88
        $command = 'mysqldump '.$this->connectionString().' --no-tablespaces --skip-add-locks --skip-comments --skip-set-charset --tz-utc --column-statistics=0';
89
 
90
        if (! $this->connection->isMaria()) {
91
            $command .= ' --set-gtid-purged=OFF';
92
        }
93
 
94
        return $command.' "${:LARAVEL_LOAD_DATABASE}"';
95
    }
96
 
97
    /**
98
     * Generate a basic connection string (--socket, --host, --port, --user, --password) for the database.
99
     *
100
     * @return string
101
     */
102
    protected function connectionString()
103
    {
104
        $value = ' --user="${:LARAVEL_LOAD_USER}" --password="${:LARAVEL_LOAD_PASSWORD}"';
105
 
106
        $config = $this->connection->getConfig();
107
 
108
        $value .= $config['unix_socket'] ?? false
109
                        ? ' --socket="${:LARAVEL_LOAD_SOCKET}"'
110
                        : ' --host="${:LARAVEL_LOAD_HOST}" --port="${:LARAVEL_LOAD_PORT}"';
111
 
112
        if (isset($config['options'][\PDO::MYSQL_ATTR_SSL_CA])) {
113
            $value .= ' --ssl-ca="${:LARAVEL_LOAD_SSL_CA}"';
114
        }
115
 
116
        return $value;
117
    }
118
 
119
    /**
120
     * Get the base variables for a dump / load command.
121
     *
122
     * @param  array  $config
123
     * @return array
124
     */
125
    protected function baseVariables(array $config)
126
    {
127
        $config['host'] ??= '';
128
 
129
        return [
130
            'LARAVEL_LOAD_SOCKET' => $config['unix_socket'] ?? '',
131
            'LARAVEL_LOAD_HOST' => is_array($config['host']) ? $config['host'][0] : $config['host'],
132
            'LARAVEL_LOAD_PORT' => $config['port'] ?? '',
133
            'LARAVEL_LOAD_USER' => $config['username'],
134
            'LARAVEL_LOAD_PASSWORD' => $config['password'] ?? '',
135
            'LARAVEL_LOAD_DATABASE' => $config['database'],
136
            'LARAVEL_LOAD_SSL_CA' => $config['options'][\PDO::MYSQL_ATTR_SSL_CA] ?? '',
137
        ];
138
    }
139
 
140
    /**
141
     * Execute the given dump process.
142
     *
143
     * @param  \Symfony\Component\Process\Process  $process
144
     * @param  callable  $output
145
     * @param  array  $variables
146
     * @return \Symfony\Component\Process\Process
147
     */
148
    protected function executeDumpProcess(Process $process, $output, array $variables)
149
    {
150
        try {
151
            $process->setTimeout(null)->mustRun($output, $variables);
152
        } catch (Exception $e) {
153
            if (Str::contains($e->getMessage(), ['column-statistics', 'column_statistics'])) {
154
                return $this->executeDumpProcess(Process::fromShellCommandLine(
155
                    str_replace(' --column-statistics=0', '', $process->getCommandLine())
156
                ), $output, $variables);
157
            }
158
 
159
            if (str_contains($e->getMessage(), 'set-gtid-purged')) {
160
                return $this->executeDumpProcess(Process::fromShellCommandLine(
161
                    str_replace(' --set-gtid-purged=OFF', '', $process->getCommandLine())
162
                ), $output, $variables);
163
            }
164
 
165
            throw $e;
166
        }
167
 
168
        return $process;
169
    }
170
}