Skip to content

Commit

Permalink
Merge pull request #18 from marcel-strzalka/feature/more-dry-validations
Browse files Browse the repository at this point in the history
Feature/more dry validations
  • Loading branch information
marcel-strzalka authored Oct 26, 2022
2 parents fe581e4 + 5a6f6d9 commit 7834ef4
Show file tree
Hide file tree
Showing 8 changed files with 44 additions and 19 deletions.
8 changes: 8 additions & 0 deletions app/contracts/movie_contract.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
# frozen_string_literal: true

class MovieContract < ApplicationContract
params do
required(:title).filled(:string)
required(:length_in_minutes).value(:integer, gteq?: 1, lteq?: 300)
end
end
18 changes: 11 additions & 7 deletions app/controllers/movies_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -16,11 +16,15 @@ def new
end

def create
@movie = authorize Movie.new(movie_params)
@movie = authorize Movie.new
result = MovieContract.new.call(params[:movie].to_unsafe_h)
@movie.attributes = result.to_h

if @movie.save
if result.success?
@movie.save
redirect_to @movie
else
@errors = result.errors(full: true)
render :new, status: :unprocessable_entity
end
end
Expand All @@ -31,10 +35,14 @@ def edit

def update
authorize find_movie
result = MovieContract.new.call(params[:movie].to_unsafe_h)
@movie.attributes = result.to_h

if @movie.update(movie_params)
if result.success?
@movie.save
redirect_to @movie
else
@errors = result.errors(full: true)
render :edit, status: :unprocessable_entity
end
end
Expand All @@ -49,10 +57,6 @@ def destroy

private

def movie_params
params.require(:movie).permit(:title, :length_in_minutes)
end

def find_movie
@movie = Movie.find(params[:id])
end
Expand Down
3 changes: 0 additions & 3 deletions app/models/movie.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,5 @@
class Movie < ApplicationRecord
has_many :shows, dependent: :destroy

validates :title, length: { minimum: 1 }
validates :length_in_minutes, numericality: { in: 1..300 }

scope :sorted_alphabetically, -> { order(:title) }
end
4 changes: 2 additions & 2 deletions app/views/movies/_form.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,8 @@
<div><%= form.number_field :length_in_minutes, in: 1..300 %></div>
</div>
<div>
<% movie.errors.any? do |error| %>
<%= error.full_message %>
<% errors&.any? do |error| %>
<%= error.text %>
<% end %>
</div>
<div>
Expand Down
2 changes: 1 addition & 1 deletion app/views/movies/edit.html.erb
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
<h1>Edit movie</h1>

<%= render "form", movie: @movie %>
<%= render "form", movie: @movie, errors: @errors %>
2 changes: 1 addition & 1 deletion app/views/movies/new.html.erb
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
<h1>Add new movie</h1>

<%= render "form", movie: @movie %>
<%= render "form", movie: @movie, errors: @errors %>
10 changes: 5 additions & 5 deletions spec/contracts/hall_contract_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -4,24 +4,24 @@

RSpec.describe HallContract do
let(:hall_params) { { name: 'H', capacity: 1 } }
subject { described_class.new(hall: Hall.new).call(hall_params) }
subject(:result) { described_class.new(hall: Hall.new).call(hall_params) }

describe '#call' do
context 'when name is already taken' do
let!(:hall) { create :hall, name: 'H' }
before { create(:hall, name: 'H') }

it 'returns failure' do
expect(subject.failure?).to be(true)
expect(result.failure?).to be(true)
end

it 'adds an error' do
expect(subject.errors.to_h).to eq({ name: ['is taken'] })
expect(result.errors.to_h).to eq({ name: ['is taken'] })
end
end

context 'when hall params are valid' do
it 'returns success' do
expect(subject.success?).to be(true)
expect(result.success?).to be(true)
end
end
end
Expand Down
16 changes: 16 additions & 0 deletions spec/contracts/movie_contract_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
# frozen_string_literal: true

require 'rails_helper'

RSpec.describe MovieContract do
let(:movie_params) { { title: 'T', length_in_minutes: 1 } }
subject(:result) { described_class.new.call(movie_params) }

describe '#call' do
context 'when hall params are valid' do
it 'returns success' do
expect(result.success?).to be(true)
end
end
end
end

0 comments on commit 7834ef4

Please sign in to comment.