Skip to content

Commit ac71352

Browse files
committed
POST: Customize database table column and association naming in Prisma ORM
1 parent fa1610b commit ac71352

File tree

2 files changed

+109
-1
lines changed

2 files changed

+109
-1
lines changed

_includes/footer.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,7 @@ <h2 class="FooterActions-title">Get in Contact with Me</h2>
5959

6060
<section class="Footer-actions-copyright">
6161
<p>© 2011-{{ "now" | date: "%Y" }}+ Josh Frankel. {{ site.title }}. All rights reserved</p>
62-
<p class="Footer-actions-copyright-small">All content on this website is protected by copyright law and may not be reproduced, distributed,
62+
<p class="Footer-actions-copyright-small">All content, media, ideas, and code on this website is protected by copyright law and may not be reproduced, distributed,
6363
transmitted, cached, or otherwise used for training AI models, large language models (LLMs), large reasoning models (LRMs), machine learning systems,
6464
or other artificial intelligence applications without explicit written permission and proper attribution to the original author.
6565
Unauthorized use and/or duplication of this material is strictly prohibited.</p>
Lines changed: 108 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,108 @@
1+
---
2+
layout: post
3+
title: Customizing Database Table, Column, and Association Naming in Prisma ORM
4+
categories:
5+
- articles
6+
tags:
7+
- prisma
8+
- databases
9+
- javascript
10+
---
11+
12+
I've been working with Prisma as an object-relational mapping tool for my projects. Coming from a background of using raw SQL along with ActiveRecord, I've noticed that default Prisma caters to JavaScript over other established standards. Ensuring database table columns are snake_case along with creating associations that are lowercase and plural doesn't come for free but Prisma does provide a way to configure these within your schema.
13+
14+
<!--excerpt-->
15+
16+
## Prisma Schema
17+
18+
[Prisma](https://www.prisma.io/) provides a schema to help define the model and database layers of your application. By definition it is mapping the concept of a Model to a database table. Now out-of-the-box if you were to create a new table your schema may look something like this. We'll use an example of a blog application where a User can have many Posts.
19+
20+
```js
21+
model User {
22+
id String @id @default(uuid())
23+
email String @unique
24+
emailVerified DateTime?
25+
name String?
26+
createdAt DateTime @default(now())
27+
updatedAt DateTime @updatedAt
28+
}
29+
30+
model Posts {
31+
id String @id @default(uuid())
32+
title String
33+
content String?
34+
publishedAt DateTime?
35+
authorId String
36+
author User @relation(fields: [authorId], references: [id])
37+
}
38+
```
39+
40+
Now migrating this schema you'd end up with a **Users** and **Posts** table with that casing. Generally this isn't an issue but the general best practice is to use plural snake_case conventions for table names. Additionally, several of the columns like **publishedAt**, **authorId**, and **emailVerified** follow camelCase conventions which typically isn't found at the database level.
41+
42+
## The @map and @@map directives
43+
44+
Prisma provides two Schema directives that allow you to control the naming conventions of your table names along with column names. We can use the `@map` directive to control the column names to adhere to snake_case conventions.
45+
46+
{% include blockquote.html quote="@map: Maps a field name or enum value from the Prisma schema to a column or document field with a different name in the database. @@map: Maps the Prisma schema model name to a table (relational databases) or collection (MongoDB) with a different name." source_link="https://www.prisma.io/docs/orm/reference/prisma-schema-reference#map" source_text="Prisma Documentation" %}
47+
48+
```js
49+
model User {
50+
id String @id @default(uuid())
51+
email String @unique
52+
emailVerified DateTime? @map("email_verified")
53+
name String?
54+
createdAt DateTime @default(now()) @map("created_at")
55+
updatedAt DateTime @updatedAt @map("updated_at")
56+
}
57+
58+
model Posts {
59+
id String @id @default(uuid()) @map("id")
60+
title String
61+
content String?
62+
publishedAt DateTime? @map("published_at")
63+
authorId String @map("author_id")
64+
author User @relation(fields: [authorId], references: [id])
65+
}
66+
```
67+
68+
This has the benefit of connecting the model to the database table while preserving the correct naming conventions in both use-cases. The model can still utilize camelCase to interact at the JavaScript layer, while the database table uses the more commonly found snake_case equivlent.
69+
70+
For table naming, the `@@map` directive can be used in much the same way. We'll use it to ensure that our database tables are named **users** and **posts** respectively.
71+
72+
```js
73+
model User {
74+
id String @id @default(uuid())
75+
76+
@@map("users")
77+
}
78+
79+
model Posts {
80+
id String @id @default(uuid())
81+
82+
@@map("posts")
83+
}
84+
```
85+
86+
We now have SQL that uses database naming conventions while the Prisma models use camelCase conventions to better integrate with the JavaScript language.
87+
88+
## Associations
89+
90+
This same approach can also be used for associations. For example, if there were a join table between Users and Posts, you could name the association with camelCase conventions. In this case, @map and @@map are not needed since Prisma provides a built-in mechanism to define the relationship. This relationship is virtual and does not exist in the database layer.
91+
92+
```js
93+
model User {
94+
id String @id @default(uuid())
95+
96+
userPosts Post[]
97+
}
98+
99+
// Prisma used elsewhere in the codebase
100+
// Collection of Posts associated with the User
101+
user.userPosts
102+
```
103+
104+
## Conclusion
105+
106+
And with all of that you can keep both the Database and JavaScript layers focused on their own conventions.
107+
108+
Know about a trick with Prisma? Let me know in the comments below!

0 commit comments

Comments
 (0)