Coverage for databases/utils.py: 100%
45 statements
« prev ^ index » next coverage.py v7.2.7, created at 2024-08-27 18:25 +0000
« prev ^ index » next coverage.py v7.2.7, created at 2024-08-27 18:25 +0000
1from __future__ import annotations
3import os
4from typing import Set
5from pathlib import Path
6from typing_extensions import Literal, get_args, override
8from pydantic import BaseModel
9from syrupy.location import PyTestLocation
10from syrupy.extensions.amber import AmberSnapshotExtension
12from ._types import DatabaseMapping
13from ._compat import LiteralString
15DatabaseFeature = Literal[
16 'enum',
17 'json',
18 'date',
19 'arrays',
20 'array_push',
21 'json_arrays',
22 'raw_queries',
23 'create_many_skip_duplicates',
24 'transactions',
25 'case_sensitivity',
26 'full_text_search',
27]
30class DatabaseConfig(BaseModel):
31 id: str
32 name: str
33 env_var: str
34 bools_are_ints: bool
35 autoincrement_id: str
36 unsupported_features: Set[DatabaseFeature]
37 default_date_func: str
39 # TODO: run this under coverage
40 def supports_feature(self, feature: DatabaseFeature) -> bool: # pragma: no cover
41 if feature not in get_args(DatabaseFeature):
42 raise RuntimeError(f'Unknown feature: {feature}')
44 return feature not in self.unsupported_features
47# ------------------ Test helpers ------------------
49from .constants import TESTS_DIR, SYNC_TESTS_DIR
51SHARED_SNAPSHOTS_DIR = Path(__file__).parent.joinpath('__shared_snapshots__')
52CURRENT_DATABASE = os.environ.get('PRISMA_DATABASE')
55class AmberSharedExtension(AmberSnapshotExtension):
56 """Syrupy extension that stores the snapshots in a parent __shared_snapshots__ dir"""
58 @classmethod
59 @override
60 def dirname(cls, *, test_location: PyTestLocation) -> str:
61 test_dir = Path(test_location.filepath).parent
62 if test_dir.is_relative_to(SYNC_TESTS_DIR):
63 rel_dir = test_dir.relative_to(SYNC_TESTS_DIR)
64 else:
65 rel_dir = test_dir.relative_to(TESTS_DIR)
67 return str(SHARED_SNAPSHOTS_DIR.joinpath(rel_dir))
70class RawQueries(BaseModel):
71 """Raw queries defined globally so they can be easily referenced in test functions"""
73 count_posts: LiteralString
75 find_user_by_id: LiteralString
76 find_user_by_id_limit_1: LiteralString
78 find_post_by_id: LiteralString
79 find_posts_not_published: LiteralString
81 select_unknown_table: LiteralString
82 update_unique_post_title: LiteralString
83 update_unique_post_new_title: LiteralString
84 test_query_raw_no_result: LiteralString
85 test_execute_raw_no_result: LiteralString
88_mysql_queries = RawQueries(
89 count_posts="""
90 SELECT COUNT(*) as count
91 FROM Post
92 """,
93 find_post_by_id="""
94 SELECT *
95 FROM Post
96 WHERE id = ?
97 """,
98 find_user_by_id="""
99 SELECT *
100 FROM User
101 WHERE User.id = ?
102 """,
103 find_user_by_id_limit_1="""
104 SELECT *
105 FROM User
106 WHERE User.id = ?
107 LIMIT 1
108 """,
109 select_unknown_table="""
110 SELECT *
111 FROM bad_table;
112 """,
113 find_posts_not_published="""
114 SELECT id, published
115 FROM Post
116 WHERE published = false
117 """,
118 test_query_raw_no_result="""
119 SELECT *
120 FROM Post
121 WHERE id = 'sdldsd'
122 """,
123 update_unique_post_title="""
124 UPDATE Post
125 SET title = 'My edited title'
126 WHERE id = ?
127 """,
128 update_unique_post_new_title="""
129 UPDATE Post
130 SET title = 'My new title'
131 WHERE id = ?
132 """,
133 test_execute_raw_no_result="""
134 UPDATE Post
135 SET title = 'updated title'
136 WHERE id = 'sdldsd'
137 """,
138)
140_postgresql_queries = RawQueries(
141 count_posts="""
142 SELECT COUNT(*) as count
143 FROM "Post"
144 """,
145 find_post_by_id="""
146 SELECT *
147 FROM "Post"
148 WHERE id = $1
149 """,
150 find_user_by_id="""
151 SELECT *
152 FROM "User"
153 WHERE "User".id = $1
154 """,
155 find_user_by_id_limit_1="""
156 SELECT *
157 FROM "User"
158 WHERE "User".id = $1
159 LIMIT 1
160 """,
161 select_unknown_table="""
162 SELECT *
163 FROM bad_table;
164 """,
165 find_posts_not_published="""
166 SELECT id, published
167 FROM "Post"
168 WHERE published = false
169 """,
170 test_query_raw_no_result="""
171 SELECT *
172 FROM "Post"
173 WHERE id = 'sdldsd'
174 """,
175 update_unique_post_title="""
176 UPDATE "Post"
177 SET title = 'My edited title'
178 WHERE id = $1
179 """,
180 update_unique_post_new_title="""
181 UPDATE "Post"
182 SET title = 'My new title'
183 WHERE id = $1
184 """,
185 test_execute_raw_no_result="""
186 UPDATE "Post"
187 SET title = 'updated title'
188 WHERE id = 'sdldsd'
189 """,
190)
192RAW_QUERIES_MAPPING: DatabaseMapping[RawQueries] = {
193 'postgresql': _postgresql_queries,
194 'cockroachdb': _postgresql_queries,
195 'mysql': _mysql_queries,
196 'mariadb': _mysql_queries,
197 'sqlite': RawQueries(
198 count_posts="""
199 SELECT COUNT(*) as count
200 FROM Post
201 """,
202 find_post_by_id="""
203 SELECT *
204 FROM Post
205 WHERE id = ?
206 """,
207 find_user_by_id="""
208 SELECT *
209 FROM User
210 WHERE User.id = ?
211 """,
212 find_user_by_id_limit_1="""
213 SELECT *
214 FROM User
215 WHERE User.id = ?
216 LIMIT 1
217 """,
218 select_unknown_table="""
219 SELECT *
220 FROM bad_table;
221 """,
222 find_posts_not_published="""
223 SELECT id, published
224 FROM Post
225 WHERE published = false
226 """,
227 test_query_raw_no_result="""
228 SELECT *
229 FROM Post
230 WHERE id = 'sdldsd'
231 """,
232 update_unique_post_title="""
233 UPDATE Post
234 SET title = 'My edited title'
235 WHERE id = ?
236 """,
237 update_unique_post_new_title="""
238 UPDATE Post
239 SET title = 'My new title'
240 WHERE id = ?
241 """,
242 test_execute_raw_no_result="""
243 UPDATE Post
244 SET title = 'updated title'
245 WHERE id = 'sdldsd'
246 """,
247 ),
248}