Skip to content

Commit e08ef38

Browse files
committed
Update the backlink naming scheme for ORM generators.
The backlinks are going to have simpler and shorter names mimicking the EdgeQL `.<link[is Type]` by using the `_link_Type` naming format.
1 parent bc0aab4 commit e08ef38

8 files changed

+63
-97
lines changed

gel/orm/django/generator.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,7 @@ def table(self):
8585
return self.meta['db_table'].strip("'")
8686

8787
def get_backlink_name(self, name, srcname):
88-
return self.backlink_renames.get(name, f'back_to_{srcname}')
88+
return f'_{name}_{srcname}'
8989

9090

9191
class ModelGenerator(FilePrinter):

gel/orm/introspection.py

+2-27
Original file line numberDiff line numberDiff line change
@@ -189,7 +189,8 @@ def _process_links(types, modules):
189189

190190
objtype = type_map[target]
191191
objtype['backlinks'].append({
192-
'name': f'back_to_{sql_source}',
192+
# naming scheme mimics .<link[is Type]
193+
'name': f'_{sql_name}_{sql_source}',
193194
'fwname': sql_name,
194195
# flip cardinality and exclusivity
195196
'cardinality': 'One' if exclusive else 'Many',
@@ -198,7 +199,6 @@ def _process_links(types, modules):
198199
'has_link_object': False,
199200
})
200201

201-
202202
link['has_link_object'] = False
203203
# Any link with properties should become its own intermediate
204204
# object, since ORMs generally don't have a special convenient
@@ -232,31 +232,6 @@ def _process_links(types, modules):
232232
'target': target,
233233
})
234234

235-
# Go over backlinks and resolve any name collisions using the type map.
236-
for spec in types:
237-
mod = spec["name"].rsplit('::', 1)[0]
238-
sql_source = get_sql_name(spec["name"])
239-
240-
# Find collisions in backlink names
241-
bk = collections.defaultdict(list)
242-
for link in spec['backlinks']:
243-
if link['name'].startswith('back_to_'):
244-
bk[link['name']].append(link)
245-
246-
for bklinks in bk.values():
247-
if len(bklinks) > 1:
248-
# We have a collision, so each backlink in it must now be
249-
# disambiguated.
250-
for link in bklinks:
251-
origsrc = get_sql_name(link['target']['name'])
252-
lname = link['name']
253-
fwname = link['fwname']
254-
link['name'] = f'follow_{fwname}_{lname}'
255-
# Also update the original source of the link with the
256-
# special backlink name.
257-
source = type_map[link['target']['name']]
258-
source['backlink_renames'][fwname] = link['name']
259-
260235
return {
261236
'modules': modules,
262237
'object_types': types,

gel/orm/sqla.py

+2-5
Original file line numberDiff line numberDiff line change
@@ -282,10 +282,7 @@ def render_link_object(self, spec, modules):
282282
bklink = source_link
283283
else:
284284
src = modules[mod]['object_types'][source_name]
285-
bklink = src['backlink_renames'].get(
286-
source_link,
287-
f'back_to_{source_name}',
288-
)
285+
bklink = f'_{source_link}_{source_name}'
289286

290287
self.write(
291288
f'{lname}: orm.Mapped[{pyname}] = '
@@ -418,7 +415,7 @@ def render_link(self, spec, mod, parent, modules):
418415
tmod, target = get_mod_and_name(spec['target']['name'])
419416
source = modules[mod]['object_types'][parent]
420417
cardinality = spec['cardinality']
421-
bklink = source['backlink_renames'].get(name, f'back_to_{parent}')
418+
bklink = f'_{name}_{parent}'
422419

423420
if spec.get('has_link_object'):
424421
# intermediate object will have the actual source and target

gel/orm/sqlmodel.py

+2-5
Original file line numberDiff line numberDiff line change
@@ -317,10 +317,7 @@ def render_link_object(self, spec, modules):
317317
bklink = source_link
318318
else:
319319
src = modules[mod]['object_types'][source_name]
320-
bklink = src['backlink_renames'].get(
321-
source_link,
322-
f'back_to_{source_name}',
323-
)
320+
bklink = f'_{source_link}_{source_name}'
324321

325322
self.write(
326323
f'{lname}: {pyname} = sm.Relationship(')
@@ -452,7 +449,7 @@ def render_link(self, spec, mod, parent, modules):
452449
tmod, target = get_mod_and_name(spec['target']['name'])
453450
source = modules[mod]['object_types'][parent]
454451
cardinality = spec['cardinality']
455-
bklink = source['backlink_renames'].get(name, f'back_to_{parent}')
452+
bklink = f'_{name}_{parent}'
456453

457454
if tmod != 'default':
458455
warnings.warn(

tests/test_django_basic.py

+18-18
Original file line numberDiff line numberDiff line change
@@ -118,7 +118,7 @@ def test_django_read_models_02(self):
118118
# use backlink
119119
res = self.m.User.objects.order_by('name').all()
120120
vals = [
121-
(u.name, {p.body for p in u.back_to_Post.all()})
121+
(u.name, {p.body for p in u._author_Post.all()})
122122
for u in res
123123
]
124124
self.assertEqual(
@@ -149,10 +149,10 @@ def test_django_read_models_03(self):
149149
)
150150

151151
# prefetch via backlink
152-
res = self.m.User.objects.prefetch_related('back_to_Post') \
153-
.order_by('back_to_Post__body')
152+
res = self.m.User.objects.prefetch_related('_author_Post') \
153+
.order_by('_author_Post__body')
154154
vals = {
155-
(u.name, tuple(p.body for p in u.back_to_Post.all()))
155+
(u.name, tuple(p.body for p in u._author_Post.all()))
156156
for u in res
157157
}
158158
self.assertEqual(
@@ -184,7 +184,7 @@ def test_django_read_models_04(self):
184184
# use backlink
185185
res = self.m.User.objects.all()
186186
vals = {
187-
(u.name, tuple(g.num for g in u.back_to_GameSession.all()))
187+
(u.name, tuple(g.num for g in u._players_GameSession.all()))
188188
for u in res
189189
}
190190
self.assertEqual(
@@ -216,9 +216,9 @@ def test_django_read_models_05(self):
216216
)
217217

218218
# prefetch via backlink
219-
res = self.m.User.objects.prefetch_related('back_to_GameSession')
219+
res = self.m.User.objects.prefetch_related('_players_GameSession')
220220
vals = {
221-
(u.name, tuple(g.num for g in u.back_to_GameSession.all()))
221+
(u.name, tuple(g.num for g in u._players_GameSession.all()))
222222
for u in res
223223
}
224224
self.assertEqual(
@@ -251,7 +251,7 @@ def test_django_read_models_06(self):
251251
# use backlink
252252
res = self.m.User.objects.order_by('name').all()
253253
vals = [
254-
(u.name, {g.name for g in u.back_to_UserGroup.all()})
254+
(u.name, {g.name for g in u._users_UserGroup.all()})
255255
for u in res
256256
]
257257
self.assertEqual(
@@ -284,9 +284,9 @@ def test_django_read_models_07(self):
284284
)
285285

286286
# prefetch via backlink
287-
res = self.m.User.objects.prefetch_related('back_to_UserGroup')
287+
res = self.m.User.objects.prefetch_related('_users_UserGroup')
288288
vals = {
289-
(u.name, tuple(sorted(g.name for g in u.back_to_UserGroup.all())))
289+
(u.name, tuple(sorted(g.name for g in u._users_UserGroup.all())))
290290
for u in res
291291
}
292292
self.assertEqual(
@@ -347,7 +347,7 @@ def test_django_create_models_02(self):
347347
user = self.m.User.objects.get(name=name)
348348

349349
self.assertEqual(user.name, name)
350-
self.assertEqual(user.back_to_UserGroup.all()[0].name, 'cyan')
350+
self.assertEqual(user._users_UserGroup.all()[0].name, 'cyan')
351351
self.assertIsInstance(user.id, uuid.UUID)
352352

353353
def test_django_create_models_03(self):
@@ -359,8 +359,8 @@ def test_django_create_models_03(self):
359359
y.save()
360360
cyan.save()
361361

362-
x.back_to_UserGroup.add(cyan)
363-
y.back_to_UserGroup.add(cyan)
362+
x._users_UserGroup.add(cyan)
363+
y._users_UserGroup.add(cyan)
364364

365365
group = self.m.UserGroup.objects.get(name='cyan')
366366
self.assertEqual(group.name, 'cyan')
@@ -443,8 +443,8 @@ def test_django_delete_models_05(self):
443443

444444
group.delete()
445445
# make sure the user object is no longer a link target
446-
user.back_to_UserGroup.clear()
447-
user.back_to_GameSession.clear()
446+
user._users_UserGroup.clear()
447+
user._players_GameSession.clear()
448448
user.delete()
449449

450450
vals = self.m.UserGroup.objects.filter(name='green').all()
@@ -476,13 +476,13 @@ def test_django_update_models_02(self):
476476
blue.users.add(user)
477477

478478
self.assertEqual(
479-
{g.name for g in user.back_to_UserGroup.all()},
479+
{g.name for g in user._users_UserGroup.all()},
480480
{'red', 'blue'},
481481
)
482482
self.assertEqual(user.name, 'Yvonne')
483483
self.assertIsInstance(user.id, uuid.UUID)
484484

485-
group = [g for g in user.back_to_UserGroup.all()
485+
group = [g for g in user._users_UserGroup.all()
486486
if g.name == 'red'][0]
487487
self.assertEqual(
488488
{u.name for u in group.users.all()},
@@ -493,7 +493,7 @@ def test_django_update_models_03(self):
493493
user0 = self.m.User.objects.get(name='Elsa')
494494
user1 = self.m.User.objects.get(name='Zoe')
495495
# Replace the author or a post
496-
post = user0.back_to_Post.all()[0]
496+
post = user0._author_Post.all()[0]
497497
body = post.body
498498
post.author = user1
499499
post.save()

tests/test_sqla_basic.py

+18-18
Original file line numberDiff line numberDiff line change
@@ -113,7 +113,7 @@ def test_sqla_read_models_02(self):
113113
# use backlink
114114
res = self.sess.query(self.sm.User).order_by(self.sm.User.name).all()
115115
vals = [
116-
(u.name, {p.body for p in u.back_to_Post})
116+
(u.name, {p.body for p in u._author_Post})
117117
for u in res
118118
]
119119
self.assertEqual(
@@ -149,13 +149,13 @@ def test_sqla_read_models_03(self):
149149
# join via backlink
150150
res = self.sess.execute(
151151
select(self.sm.Post, self.sm.User)
152-
.join(self.sm.User.back_to_Post)
152+
.join(self.sm.User._author_Post)
153153
.order_by(self.sm.Post.body)
154154
)
155155
# We'll get a cross-product, so we need to jump through some hoops to
156156
# remove duplicates
157157
vals = {
158-
(u.name, tuple(p.body for p in u.back_to_Post))
158+
(u.name, tuple(p.body for p in u._author_Post))
159159
for (_, u) in res
160160
}
161161
self.assertEqual(
@@ -170,11 +170,11 @@ def test_sqla_read_models_03(self):
170170
# LEFT OUTER join via backlink
171171
res = self.sess.execute(
172172
select(self.sm.Post, self.sm.User)
173-
.join(self.sm.User.back_to_Post, isouter=True)
173+
.join(self.sm.User._author_Post, isouter=True)
174174
.order_by(self.sm.Post.body)
175175
)
176176
vals = {
177-
(u.name, tuple(p.body for p in u.back_to_Post))
177+
(u.name, tuple(p.body for p in u._author_Post))
178178
for (p, u) in res
179179
}
180180
self.assertEqual(
@@ -209,7 +209,7 @@ def test_sqla_read_models_04(self):
209209
# use backlink
210210
res = self.sess.query(self.sm.User).all()
211211
vals = {
212-
(u.name, tuple(g.num for g in u.back_to_GameSession))
212+
(u.name, tuple(g.num for g in u._players_GameSession))
213213
for u in res
214214
}
215215
self.assertEqual(
@@ -248,10 +248,10 @@ def test_sqla_read_models_05(self):
248248
# LEFT OUTER join via backlink
249249
res = self.sess.execute(
250250
select(self.sm.GameSession, self.sm.User)
251-
.join(self.sm.User.back_to_GameSession, isouter=True)
251+
.join(self.sm.User._players_GameSession, isouter=True)
252252
)
253253
vals = {
254-
(u.name, tuple(g.num for g in u.back_to_GameSession))
254+
(u.name, tuple(g.num for g in u._players_GameSession))
255255
for (_, u) in res
256256
}
257257
self.assertEqual(
@@ -287,7 +287,7 @@ def test_sqla_read_models_06(self):
287287
# use backlink
288288
res = self.sess.query(self.sm.User).order_by(self.sm.User.name).all()
289289
vals = [
290-
(u.name, {g.name for g in u.back_to_UserGroup})
290+
(u.name, {g.name for g in u._users_UserGroup})
291291
for u in res
292292
]
293293
self.assertEqual(
@@ -328,10 +328,10 @@ def test_sqla_read_models_07(self):
328328
# LEFT OUTER join via backlink
329329
res = self.sess.execute(
330330
select(self.sm.UserGroup, self.sm.User)
331-
.join(self.sm.User.back_to_UserGroup, isouter=True)
331+
.join(self.sm.User._users_UserGroup, isouter=True)
332332
)
333333
vals = {
334-
(u.name, tuple(sorted(g.name for g in u.back_to_UserGroup)))
334+
(u.name, tuple(sorted(g.name for g in u._users_UserGroup)))
335335
for (_, u) in res
336336
}
337337
self.assertEqual(
@@ -400,16 +400,16 @@ def test_sqla_create_models_02(self):
400400
user = self.sess.query(self.sm.User).filter_by(name=name).one()
401401

402402
self.assertEqual(user.name, name)
403-
self.assertEqual(user.back_to_UserGroup[0].name, 'cyan')
403+
self.assertEqual(user._users_UserGroup[0].name, 'cyan')
404404
self.assertIsInstance(user.id, uuid.UUID)
405405

406406
def test_sqla_create_models_03(self):
407407
user0 = self.sm.User(name='Yvonne')
408408
user1 = self.sm.User(name='Xander')
409409
cyan = self.sm.UserGroup(name='cyan')
410410

411-
user0.back_to_UserGroup.append(cyan)
412-
user1.back_to_UserGroup.append(cyan)
411+
user0._users_UserGroup.append(cyan)
412+
user1._users_UserGroup.append(cyan)
413413

414414
self.sess.add(cyan)
415415
self.sess.flush()
@@ -418,7 +418,7 @@ def test_sqla_create_models_03(self):
418418
user = self.sess.query(self.sm.User).filter_by(name=name).one()
419419

420420
self.assertEqual(user.name, name)
421-
self.assertEqual(user.back_to_UserGroup[0].name, 'cyan')
421+
self.assertEqual(user._users_UserGroup[0].name, 'cyan')
422422
self.assertIsInstance(user.id, uuid.UUID)
423423

424424
def test_sqla_create_models_04(self):
@@ -557,13 +557,13 @@ def test_sqla_update_models_02(self):
557557
self.sess.flush()
558558

559559
self.assertEqual(
560-
{g.name for g in user.back_to_UserGroup},
560+
{g.name for g in user._users_UserGroup},
561561
{'red', 'blue'},
562562
)
563563
self.assertEqual(user.name, 'Yvonne')
564564
self.assertIsInstance(user.id, uuid.UUID)
565565

566-
group = [g for g in user.back_to_UserGroup if g.name == 'red'][0]
566+
group = [g for g in user._users_UserGroup if g.name == 'red'][0]
567567
self.assertEqual(
568568
{u.name for u in group.users},
569569
{'Alice', 'Billie', 'Cameron', 'Dana', 'Yvonne'},
@@ -573,7 +573,7 @@ def test_sqla_update_models_03(self):
573573
user0 = self.sess.query(self.sm.User).filter_by(name='Elsa').one()
574574
user1 = self.sess.query(self.sm.User).filter_by(name='Zoe').one()
575575
# Replace the author or a post
576-
post = user0.back_to_Post[0]
576+
post = user0._author_Post[0]
577577
body = post.body
578578
post.author = user1
579579

tests/test_sqla_features.py

+4-7
Original file line numberDiff line numberDiff line change
@@ -224,24 +224,21 @@ def test_sqla_bklink_01(self):
224224

225225
# only one link from Bar 123 to foo
226226
self.assertEqual(
227-
[obj.n for obj in foo.follow_foo_back_to_Bar],
227+
[obj.n for obj in foo._foo_Bar],
228228
[123],
229229
)
230230
# only one link from Who 456 to oof
231231
self.assertEqual(
232-
[obj.x for obj in oof.follow_foo_back_to_Who],
232+
[obj.x for obj in oof._foo_Who],
233233
[456],
234234
)
235235

236236
# foo is linked via `many_foo` from both Bar and Who
237237
self.assertEqual(
238-
[obj.n for obj in foo.follow_many_foo_back_to_Bar],
238+
[obj.n for obj in foo._many_foo_Bar],
239239
[123],
240240
)
241241
self.assertEqual(
242-
[
243-
(obj.note, obj.source.x)
244-
for obj in foo.follow_many_foo_back_to_Who
245-
],
242+
[(obj.note, obj.source.x) for obj in foo._many_foo_Who],
246243
[('just one', 456)],
247244
)

0 commit comments

Comments
 (0)