DEV Community

pjparham
pjparham

Posted on

1

Ruby on Rails relationships for models that join on multiple tables.

Ruby on Rails offers many tools to link models in your database, sometimes so many that it can be confusing to find the correct solution for your problem. I recently had two models, User and Image, that joined on two tables, Reviews and Favorites. Finding the right solution for this issue took some leg work, but eventually I implemented a clean solution that worked just as I needed it to. Keep reading if you too want to discover how to handle models that join on multiple tables.

The problem

I made a web app that had Users and Images. Users and Images both had many favorites and many reviews. Favorites are created when a user favorites an image, and reviews are created when a user reviews an image.

DB Layout

I needed both my users to both access what images they have liked and what images they have favorited, and the reciprocal for my images.

If I only had one joins table, I would achieve this relationship with the following code:

class User < ApplicationRecord
has_many :images, through: :reviews
Enter fullscreen mode Exit fullscreen mode

However, things start to look wrong when you add in the second relationship:

has_many :images, through: :reviews
has_many :images, through: :favorites
Enter fullscreen mode Exit fullscreen mode

The solution

Solving the above problem required me to search in a variety of places and was not the easiest to find, however the solution itself is very simple.

has_many :reviewed_images, :through => :reviews, :source => :image
has_many :favorite_images, :through => :favorites, :source => :image
Enter fullscreen mode Exit fullscreen mode

This allows me to access the necessary data easily.

Usage

Let's say I was playing around with this code in my Ruby console. If I set an instance of my user class equal to u1, I could call that user's favorite images with the syntax u1.favorite_images, and I could call their reviewed images with u1.reviewed_images. Pairing this access with my Controllers and Serializers, we can now send the nested data to the front end so our app operates the way we want it to.

AWS Q Developer image

Your AI Code Assistant

Automate your code reviews. Catch bugs before your coworkers. Fix security issues in your code. Built to handle large projects, Amazon Q Developer works alongside you from idea to production code.

Get started free in your IDE

Top comments (0)

AWS Security LIVE!

Join us for AWS Security LIVE!

Discover the future of cloud security. Tune in live for trends, tips, and solutions from AWS and AWS Partners.

Learn More

👋 Kindness is contagious

Please leave a ❤️ or a friendly comment on this post if you found it helpful!

Okay