njwest

njwest

Polymorphic/Many-to-Many table relationship with dynamic IDs

Hiya, we’re designing PostgreSQL schemas for an app that has Users, and the user has Things of different types as well as Affinities for those Things, through a dynamic many-to-many table:

users_things_and_affinities table:

user_id
thing_type
thing_id
affinity_id

The idea is to have various many-to-many relationships between users and different tables within a certain category through this table (as an efficiency for a different feature of the app).

Things can refer to various different tables (e.g. tools, locations, buildings, etc)

Example record:

user_id = 1, thing_type = buildings, thing_id = 5, affinity_id = 4

Is there an efficient way to make dynamic foreign keys such as this using Ecto, or are we better off with a table with nullable Thing columns such as:

user_id
affinity_id
building_id
tool_id
location_id
person_id
activity_id

where a possible record could be:

user_id = 1
affinity_id = 4
building_id = null
tool_id = 10
book_id = null
person_id = null
activity_id = null

We’re opting to go with a dynamic many-to-many table such as this one rather than creating a bunch of different user_x_and_affinity many-to-many tables so we don’t have to do lots of joins/subqueries when calculating this user data altogether, but I am very open to other viewpoints :stuck_out_tongue:

Most Liked

al2o3cr

al2o3cr

You could use an additional intermediate table as a “handle” to the many kinds of things:

user_things_and_affinities:
user_id
thing_id
affinity_id

things:
type
building_id
tool_id
location_id
person_id
activity_id
etc

This way, for M users and N things there are only N rows with mostly NULL instead of O(M*N).

You could also copy some data to the things table from each kind of record - for instance, a “display name” so that UI code doesn’t need to load the associated record just for a name.

Where Next?

Popular in Questions Top

rms.mrcs
Hi, I need to transform a list of numbers into a map where the keys are the indexes and the values are the original values of the list. ...
New
minhajuddin
I have seen a lot of code which picks the first element from a list using Enum.at(0) instead of List.first. Is there a reason why people ...
New
openscript
Hello! Sorry for this astonishing simple question, but I’m really stuck. I try to set up the intellij-elixir plugin, but I don’t know ho...
New
Fl4m3Ph03n1x
About me? ( if you have nothing better to do than reading about some random guy in the internet :stuck_out_tongue: ) Hello all, this is ...
New
greenz1
I have a phoenix application from which a user can download multiple(5-6) files of size 1MB. I couldn’t find anything related to sending ...
New
shijith.k
I am trying to start a new phoenix project with elixir 1.9, but mix phx.new does not work. It says that ** (Mix) The task "phx.new" could...
New
dblack
I’ve got an issue with an app and I’ve no idea of how to troubleshoot it. I’m hoping someone here might have seen something similar. I p...
New

Other popular topics Top

vertexbuffer
Hello, can anybody help here..? I have a list of players and I what to delete an element, but every for loop the list is reverting to ori...
New
vonH
In asking this question I am more interested about the expressiveness of the language itself and less concerned about the availability of...
New
greenz1
I have a phoenix application from which a user can download multiple(5-6) files of size 1MB. I couldn’t find anything related to sending ...
New
gausby
I asked this very same question on twitter and got some interesting feedback, but I thought it would be a good question to ask here as we...
1207 40165 209
New
dblack
I’ve got an issue with an app and I’ve no idea of how to troubleshoot it. I’m hoping someone here might have seen something similar. I p...
New
Patoshizzle
After calling mix ecto.create I get this error: 17:00:32.162 [error] GenServer #PID<0.412.0> terminating ** (Postgrex.Error) FATAL...
New

We're in Beta

About us Mission Statement