Creating Feature in our Rails blog App to Add Article and Enable Reviews

Khemlall Mangal
4 min readMar 1, 2021

--

Ok as part of this effort and series to create a blog, lets have our front end work with the newest technology. Hence we will use React Js as our front end and rails as our backend.

Let Create our model:

Rails g Model Article name image_url slug

Rails g Model Review title description score:integer article:belongs_to

If we go into Model we will see our model article and review model.

class Article < ApplicationRecord
has_many :reviews


before_create :slugify
def slugify
self.slug = name.parameterize
end

def avg_score
reviews.average(:score).round(2).to_f
end
end

Review Model

class Review < ApplicationRecord
belongs_to :article
end

If you Jump to db migrate folder you will see rails create 2 migration for us. Rails uses active model which tightly couple our models with structure of our database.

Run

Rail db:migrate

Add has_many relationship

has_many :reviews

Let set the slug for our database before we create it in our database.

What is Slugify? well let explain

Let go to rails console.

rails c

If we have

"Hello Khemlall".parameterized

It will change the structure to lower case and hyphenated.

Lets seed some data: Go to Seeds → db → Migrate

articles = Article.create([
{
name: "How to c#",
image_url: "https://www.motc.gov.qa/sites/default/files/c-programming.png"
},
{
name: "pictures of nature",
image_url: "https://thumbs.dreamstime.com/z/scenic-nature-landscape-path-near-lake-forest-path-tunnel-trees-near-lake-scenic-nature-autumn-landscape-panorama-view-115358410.jpg"
}
])
reviews = Review.create([
{
title: 'Great article',
description: 'i learn something new',
score: 5,
article: articles.first
},
{
title: 'Wow Great article i love it!',
description: 'i learn something new',
score: 5,
article: articles.first
}])

Then we need to go back to console and run the following

rails db:seed

Now lets test that everything is working

article = Article.first 
Article Load (0.2ms) SELECT "articles".* FROM "articles" ORDER BY "articles"."id" ASC LIMIT ? [["LIMIT", 1]]
=> #<Article id: 1, name: "How to c#", image_url: "https://www.motc.gov.qa/sites/default/files/c-prog...", slug: "how-to-c", created_at: "2021-02-28 22:51:45.357842000 +0000", updated_at: "20...
Article Load (0.2ms) SELECT "articles".* FROM "articles" ORDER BY "articles"."id" ASC LIMIT ? [["LIMIT", 1]]
=> #<Article id: 1, name: "How to c#", image_url: "https://www.motc.gov.qa/sites/default/files/c-prog...", slug: "how-to-c", created_at: "2021-02-28 22:51:45.357842000 +0000", updated_at: "20...
3.0.0 :009 > article.slug
Article Load (0.2ms) SELECT "articles".* FROM "articles" ORDER BY "articles"."id" ASC LIMIT ? [["LIMIT", 1]]
=> #<Article id: 1, name: "How to c#", image_url: "https://www.motc.gov.qa/sites/default/files/c-prog...", slug: "how-to-c", created_at: "2021-02-28 22:51:45.357842000 +0000", updated_at: "20...
3.0.0 :009 > article.slug=> "how-to-c"
article.reviews
Review Load (0.3ms) SELECT "reviews".* FROM "reviews" WHERE "reviews"."article_id" = ? /* loading for inspect */ LIMIT ? [["article_id", 1], ["LIMIT", 11]]
=> #<ActiveRecord::Associations::CollectionProxy [#<Review id: 1, title: "Great article", description: "i learn something new", score: 5, article_id: 1, created_at: "2021-02-28 22:51:45.439789000 +0000", updated_at: "2021-02-28 22:51:45.439789000 +0000">, #<Review id: 2, title: "Wow Great article i love it!", description: "i learn something new", score: 5, article_id: 1, created_at: "2021-02-28 22:51:45.456268000 +0000", updated_at: "2021-02-28 22:51:45.456268000 +0000">]>
3.0.0 :011 > article.reviews.count
(0.3ms) SELECT COUNT(*) FROM "reviews" WHERE "reviews"."article_id" = ? [["article_id", 1]]
=> 2

Now lets Create Api using Fast json api gem. open Gemfile and add the following

gem ‘fast_jsonapi’ 
Then run bundle

Let now create a serializer for these two model

rails g serializer Article name image_url slug

This will create a article_serializer in the following place:

app/serializers/article_serializer.rb

let do the same for Review

rails g serializer Review title description score article_id

it should create the following here:

app/serializers/review_serializer.rb

Article Serializer

class ArticleSerializer
include FastJsonapi::ObjectSerializer
attributes :name, :image_url, :slug

has_many :reviews
end

Review Serializer

class ReviewSerializer
include FastJsonapi::ObjectSerializer
attributes :title, :description, :score, :article_id
end

Lets test out this in our Raisl console.

rails c

Say we have our first article

article = Article.first

Now let create a new instance of our article serializer

ArtitleSerializer.new(article)

results

.0.0 :003 > ArticleSerializer.new(article)
=> #<ArticleSerializer:0x00000000064e11e0 @fieldsets={}, @params={}, @resource=#<Article id: 1, name: "How to c#", image_url: "https://www.motc.gov.qa/sites/default/files/c-prog...", slug: "how-to-c", created_at: "2021-02-28 22:51:45.357842000 +0000", updated_at: "2021-02-28 22:51:45.357842000 +0000">>
3.0.0 :004 > ArticleSerializer.new(article).seroa;ozed_json

ArticleSerializer.new(article).serialized_json

ArticleSerializer.new(article).serialized_json
(0.2ms) SELECT "reviews"."id" FROM "reviews" WHERE "reviews"."article_id" = ? [["article_id", 1]]
=> "{\"data\":{\"id\":\"1\",\"type\":\"article\",\"attributes\":{\"name\":\"How to c#\",\"image_url\":\"https://www.motc.gov.qa/sites/default/files/c-programming.png\",\"slug\":\"how-to-c\"},\"relationships\":{\"reviews\":{\"data\":[{\"id\":\"1\",\"type\":\"review\"},{\"id\":\"2\",\"type\":\"review\"}]}}}}"

--

--

Khemlall Mangal

I am a passionate coder, QA Engineer, and someone who enjoys the outdoors.