Completed
Pull Request — master (#22)
by Peter
01:47
created

Pgsql::getSequences()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 9
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 9
rs 9.6666
c 0
b 0
f 0
cc 1
eloc 5
nc 1
nop 1
1
<?php
2
3
namespace Spatie\MigrateFresh\TableDroppers;
4
5
use DB;
6
use Illuminate\Support\Collection;
7
8
class Pgsql implements TableDropper
9
{
10
    public function dropAllTables()
11
    {
12
        $schema = $this->getSchema();
13
14
        $this->dropViews($this->getViews($schema));
15
        $this->dropTables($this->getTables($schema));
16
        $this->dropFunctions($this->getFunctions($schema));
17
        $this->dropSequences($this->getSequences($schema));
18
        $this->dropDomains($this->getDomains($schema));
19
        $this->dropCustomTypes($this->getCustomTypes($schema));
20
    }
21
22
    /**
23
     * Drop all custom types in the schema.
24
     *
25
     * @param \Illuminate\Support\Collection $types
26
     */
27
    public function dropCustomTypes($types)
28
    {
29
        DB::statement("DROP TYPE IF EXISTS {$types->implode(',')} CASCADE");
30
    }
31
32
    /**
33
     * Get a list of all custom types in the schema.
34
     *
35
     * @param $schema
36
     * @return \Illuminate\Support\Collection
37
     */
38
    public function getCustomTypes($schema)
39
    {
40
        // For some reason imformation_schema.user_defined_types doesn't return the types
41
        // See http://stackoverflow.com/questions/3660787/how-to-list-custom-types-using-postgres-information-schema/3703727#3703727
42
        $sql = <<<'SQL'
43
SELECT t.typname AS object_name 
44
  FROM pg_type t LEFT JOIN pg_catalog.pg_namespace n 
45
    ON n.oid = t.typnamespace 
46
 WHERE (t.typrelid = 0 OR (SELECT c.relkind = 'c' FROM pg_catalog.pg_class c WHERE c.oid = t.typrelid)) 
47
   AND NOT EXISTS(SELECT 1 FROM pg_catalog.pg_type el WHERE el.oid = t.typelem AND el.typarray = t.oid)
48
   AND t.typtype NOT IN('d')
49
   AND n.nspname = ?
50
SQL;
51
        return $this->select($sql, $schema);
52
    }
53
54
    /**
55
     * Drop all domains in the schema.
56
     *
57
     * @param \Illuminate\Support\Collection $domains
58
     */
59
    public function dropDomains($domains)
60
    {
61
        DB::statement("DROP DOMAIN IF EXISTS {$domains->implode(',')} CASCADE");
62
    }
63
64
    /**
65
     * Get a list of all domains in the schema.
66
     *
67
     * @param $schema
68
     * @return \Illuminate\Support\Collection
69
     */
70
    public function getDomains($schema)
71
    {
72
        $sql = <<<'SQL'
73
SELECT domain_name AS object_name
74
  FROM information_schema.domains 
75
 WHERE domain_schema = ?
76
SQL;
77
        return $this->select($sql, $schema);
78
    }
79
80
    /**
81
     * Drop all functions in the schema.
82
     *
83
     * @param \Illuminate\Support\Collection $functions
84
     */
85
    public function dropFunctions($functions)
86
    {
87
        $functions->each(function ($function) {
88
            DB::statement("DROP FUNCTION IF EXISTS $function CASCADE");
89
        });
90
    }
91
92
    /**
93
     * Get a list of all functions in the schema.
94
     *
95
     * @param $schema
96
     * @return \Illuminate\Support\Collection
97
     */
98
    public function getFunctions($schema)
99
    {
100
        $sql = <<<'SQL'
101
SELECT proname || '(' || oidvectortypes(proargtypes) || ')' AS object_name
102
  FROM pg_proc INNER JOIN pg_namespace ns 
103
    ON pg_proc.pronamespace = ns.oid
104
 WHERE ns.nspname = ?  
105
 ORDER BY proname;
106
SQL;
107
108
        return $this->select($sql, $schema);
109
    }
110
111
    /**
112
     * Drop all sequences in the schema.
113
     *
114
     * @param \Illuminate\Support\Collection $sequences
115
     */
116
    public function dropSequences(Collection $sequences)
117
    {
118
        if ($sequences->isEmpty()) {
119
            return;
120
        }
121
122
        DB::statement("DROP SEQUENCE IF EXISTS {$sequences->implode(',')} CASCADE");
123
    }
124
125
    /**
126
     * Get a list of all sequences in the schema.
127
     *
128
     * @param $schema
129
     * @return \Illuminate\Support\Collection
130
     */
131
    public function getSequences($schema)
132
    {
133
        $sql = <<<'SQL'
134
SELECT sequence_name AS object_name
135
  FROM information_schema.sequences 
136
 WHERE sequence_schema = ?
137
SQL;
138
        return $this->select($sql, $schema);
139
    }
140
141
    /**
142
     * Drop tables.
143
     *
144
     * @param \Illuminate\Support\Collection $tables
145
     */
146
    protected function dropTables(Collection $tables)
147
    {
148
        if ($tables->isEmpty()) {
149
            return;
150
        }
151
152
        DB::statement("DROP TABLE IF EXISTS {$tables->implode(',')} CASCADE");
153
    }
154
155
    /**
156
     * Get a list of all tables in the schema.
157
     *
158
     * @param $schema
159
     * @return \Illuminate\Support\Collection
160
     */
161
    protected function getTables($schema)
162
    {
163
        $sql = <<<'SQL'
164
SELECT tablename AS object_name
165
  FROM pg_catalog.pg_tables 
166
 WHERE schemaname = ?
167
SQL;
168
169
        return $this->select($sql, $schema);
170
    }
171
172
    /**
173
     * Drop all views in the schema.
174
     *
175
     * @param \Illuminate\Support\Collection $views
176
     */
177
    public function dropViews($views)
178
    {
179
        DB::statement("DROP VIEW IF EXISTS {$views->implode(',')} CASCADE");
180
    }
181
182
    /**
183
     * Get a list of all views in the schema.
184
     *
185
     * @param $schema
186
     * @return \Illuminate\Support\Collection
187
     */
188
    public function getViews($schema)
189
    {
190
        $sql = <<<'SQL'
191
SELECT table_name AS object_name
192
  FROM information_schema.views 
193
 WHERE table_schema = ?
194
SQL;
195
        return $this->select($sql, $schema);
196
    }
197
198
    /**
199
     * Get schema name for the connection.
200
     *
201
     * @return string
202
     */
203
    protected function getSchema()
204
    {
205
        return DB::getConfig('schema');
206
    }
207
208
    /**
209
     * Execute the query and returns the list of values.
210
     *
211
     * @param string $sql
212
     * @param array $bindings
213
     * @param string $column
214
     * @return \Illuminate\Support\Collection
215
     */
216
    protected function select($sql, $bindings = [], $column = 'object_name')
217
    {
218
        return collect(
219
            DB::select($sql, collect($bindings)->all())
220
        )->pluck($column);
221
    }
222
}
223