Coverage for databases/tests/test_find_first.py: 100%
105 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
1import pytest
3from prisma import Prisma
4from prisma.types import UserWhereInput
7@pytest.mark.asyncio
8async def test_find_first(client: Prisma) -> None:
9 """Skips multiple non-matching records"""
10 posts = [
11 await client.post.create(
12 {
13 'title': 'Test post 1',
14 'published': False,
15 'views': 100,
16 }
17 ),
18 await client.post.create(
19 {
20 'title': 'Test post 2',
21 'published': False,
22 }
23 ),
24 await client.post.create(
25 {
26 'title': 'Test post 3',
27 'published': False,
28 }
29 ),
30 await client.post.create(
31 {
32 'title': 'Test post 4',
33 'published': True,
34 'views': 500,
35 }
36 ),
37 await client.post.create(
38 {
39 'title': 'Test post 5',
40 'published': False,
41 }
42 ),
43 await client.post.create(
44 {
45 'title': 'Test post 6',
46 'published': True,
47 }
48 ),
49 ]
51 post = await client.post.find_first(
52 where={
53 'published': True,
54 },
55 order={
56 'title': 'asc',
57 },
58 )
59 assert post is not None
60 assert post.id == posts[3].id
61 assert post.title == 'Test post 4'
62 assert post.published is True
64 post = await client.post.find_first(
65 where={
66 'title': {
67 'contains': 'not found',
68 }
69 }
70 )
71 assert post is None
73 post = await client.post.find_first(
74 where={
75 'published': True,
76 },
77 order={
78 'title': 'asc',
79 },
80 skip=1,
81 )
82 assert post is not None
83 assert post.id == posts[5].id
84 assert post.title == 'Test post 6'
85 assert post.published is True
87 post = await client.post.find_first(
88 where={
89 'NOT': [
90 {
91 'published': True,
92 },
93 ],
94 },
95 order={
96 'created_at': 'asc',
97 },
98 )
99 assert post is not None
100 assert post.title == 'Test post 1'
102 post = await client.post.find_first(
103 where={
104 'NOT': [
105 {
106 'title': {
107 'contains': '1',
108 },
109 },
110 {
111 'title': {
112 'contains': '2',
113 },
114 },
115 ],
116 },
117 order={
118 'created_at': 'asc',
119 },
120 )
121 assert post is not None
122 assert post.title == 'Test post 3'
124 post = await client.post.find_first(
125 where={
126 'title': {
127 'contains': 'Test',
128 },
129 'AND': [
130 {
131 'published': True,
132 },
133 ],
134 },
135 order={
136 'created_at': 'asc',
137 },
138 )
139 assert post is not None
140 assert post.title == 'Test post 4'
142 post = await client.post.find_first(
143 where={
144 'AND': [
145 {
146 'published': True,
147 },
148 {
149 'title': {
150 'contains': 'Test',
151 }
152 },
153 ],
154 },
155 order={
156 'created_at': 'asc',
157 },
158 )
159 assert post is not None
160 assert post.title == 'Test post 4'
162 post = await client.post.find_first(
163 where={
164 'views': {
165 'gt': 100,
166 },
167 'OR': [
168 {
169 'published': False,
170 },
171 ],
172 }
173 )
174 assert post is None
176 post = await client.post.find_first(
177 where={
178 'OR': [
179 {
180 'views': {
181 'gt': 100,
182 },
183 },
184 {
185 'published': False,
186 },
187 ]
188 },
189 order={
190 'created_at': 'asc',
191 },
192 )
193 assert post is not None
194 assert post.title == 'Test post 1'
196 post = await client.post.find_first(
197 where={
198 'OR': [
199 {
200 'views': {
201 'gt': 100,
202 },
203 },
204 ]
205 }
206 )
207 assert post is not None
208 assert post.title == 'Test post 4'
211@pytest.mark.asyncio
212async def test_filtering_one_to_one_relation(client: Prisma) -> None:
213 """Filtering by a 1-1 relational field and negating the filter"""
214 async with client.batch_() as batcher:
215 batcher.user.create(
216 {
217 'name': 'Robert',
218 'profile': {
219 'create': {
220 'description': 'My very cool bio.',
221 'country': 'Scotland',
222 },
223 },
224 },
225 )
226 batcher.user.create(
227 {
228 'name': 'Tegan',
229 'profile': {
230 'create': {
231 'description': 'Hello world, this is my bio.',
232 'country': 'Scotland',
233 },
234 },
235 },
236 )
237 batcher.user.create({'name': 'Callum'})
239 user = await client.user.find_first(
240 where={
241 'profile': {
242 'is': {
243 'description': {
244 'contains': 'cool',
245 }
246 }
247 }
248 }
249 )
250 assert user is not None
251 assert user.name == 'Robert'
252 assert user.profile is None
254 user = await client.user.find_first(
255 where={
256 'profile': {
257 'is_not': {
258 'description': {
259 'contains': 'bio',
260 }
261 }
262 }
263 }
264 )
265 assert user is not None
266 assert user.name == 'Callum'
267 assert user.profile is None
270@pytest.mark.asyncio
271async def test_filtering_and_ordering_one_to_many_relation(
272 client: Prisma,
273) -> None:
274 """Filtering with every, some, none and ordering by a 1-M relational field"""
275 async with client.batch_() as batcher:
276 batcher.user.create(
277 {
278 'name': 'Robert',
279 'posts': {
280 'create': [
281 {'title': 'My first post', 'published': True},
282 {'title': 'My second post', 'published': False},
283 ]
284 },
285 }
286 )
287 batcher.user.create(
288 {
289 'name': 'Tegan',
290 'posts': {
291 'create': [
292 {'title': 'Hello, world!', 'published': True},
293 {'title': 'My test post', 'published': False},
294 ]
295 },
296 }
297 )
298 batcher.user.create({'name': 'Callum'})
300 user = await client.user.find_first(
301 where={
302 'posts': {
303 'every': {
304 'title': {
305 'contains': 'post',
306 }
307 }
308 }
309 },
310 )
311 assert user is not None
312 assert user.name == 'Robert'
314 user = await client.user.find_first(
315 where={
316 'posts': {
317 'none': {
318 'title': {
319 'contains': 'Post',
320 }
321 }
322 }
323 },
324 order={
325 'name': 'asc',
326 },
327 )
328 assert user is not None
329 assert user.name == 'Callum'
331 user = await client.user.find_first(
332 where={
333 'posts': {
334 'some': {
335 'title': 'foo',
336 }
337 }
338 }
339 )
340 assert user is None
342 # ordering
344 user = await client.user.find_first(
345 where={
346 'posts': {
347 'some': {
348 'title': {
349 'contains': 'post',
350 }
351 }
352 }
353 },
354 order={'name': 'asc'},
355 )
356 assert user is not None
357 assert user.name == 'Robert'
359 user = await client.user.find_first(
360 where={
361 'posts': {
362 'some': {
363 'title': {
364 'contains': 'post',
365 }
366 }
367 }
368 },
369 order={'name': 'desc'},
370 )
371 assert user is not None
372 assert user.name == 'Tegan'
375@pytest.mark.asyncio
376async def test_list_wrapper_query_transformation(client: Prisma) -> None:
377 """Queries wrapped within a list transform global aliases"""
378 query: UserWhereInput = {
379 'OR': [
380 {'name': {'startswith': '40'}},
381 {'name': {'contains': ', 40'}},
382 {'name': {'contains': 'house'}},
383 ]
384 }
386 await client.user.create({'name': 'Robert house'})
387 found = await client.user.find_first(where=query, order={'created_at': 'asc'})
388 assert found is not None
389 assert found.name == 'Robert house'
391 await client.user.create({'name': '40 robert'})
392 found = await client.user.find_first(skip=1, where=query, order={'created_at': 'asc'})
393 assert found is not None
394 assert found.name == '40 robert'
397@pytest.mark.asyncio
398async def test_distinct(client: Prisma) -> None:
399 """Filtering by distinct combinations of fields"""
400 users = [
401 await client.user.create(
402 data={
403 'name': 'Robert',
404 },
405 ),
406 await client.user.create(
407 data={
408 'name': 'Tegan',
409 },
410 ),
411 await client.user.create(
412 data={
413 'name': 'Patrick',
414 },
415 ),
416 ]
417 async with client.batch_() as batcher:
418 batcher.profile.create(
419 {
420 'city': 'Dundee',
421 'country': 'Scotland',
422 'description': 'Foo',
423 'user_id': users[0].id,
424 }
425 )
426 batcher.profile.create(
427 {
428 'city': 'Edinburgh',
429 'country': 'Scotland',
430 'description': 'Foo',
431 'user_id': users[1].id,
432 }
433 )
434 batcher.profile.create(
435 {
436 'city': 'London',
437 'country': 'England',
438 'description': 'Foo',
439 'user_id': users[2].id,
440 }
441 )
443 found = await client.profile.find_first(
444 where={'country': 'Scotland'},
445 distinct=['city'],
446 order={'city': 'asc'},
447 )
448 assert found is not None
449 assert found.city == 'Dundee'
451 found = await client.profile.find_first(
452 where={'country': 'Scotland'},
453 distinct=['city'],
454 order={'city': 'desc'},
455 )
456 assert found is not None
457 assert found.city == 'Edinburgh'
460@pytest.mark.asyncio
461async def test_distinct_relations(client: Prisma) -> None:
462 """Using `distinct` across relations"""
463 user = await client.user.create(
464 {
465 'name': 'Robert',
466 'posts': {
467 'create': [
468 {
469 'title': 'Post 1',
470 'published': True,
471 },
472 {
473 'title': 'Post 2',
474 'published': False,
475 },
476 {
477 'title': 'Post 3',
478 'published': True,
479 },
480 ]
481 },
482 }
483 )
485 found = await client.user.find_first(
486 where={
487 'id': user.id,
488 },
489 include={
490 'posts': {
491 'order_by': {'title': 'asc'},
492 'distinct': ['published'],
493 }
494 },
495 )
496 assert found is not None
497 assert found.posts is not None
498 assert len(found.posts) == 2
499 assert found.posts[0].published is True
500 assert found.posts[1].published is False