Skip to content

Commit

Permalink
Finally, proper book export/import
Browse files Browse the repository at this point in the history
  • Loading branch information
epugh committed Sep 19, 2023
1 parent 0c2d2f3 commit f9edf81
Show file tree
Hide file tree
Showing 19 changed files with 339 additions and 107 deletions.
1 change: 1 addition & 0 deletions app/controllers/api/v1/export/books_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ class BooksController < Api::ApiController
before_action :check_book

def show
respond_with @book
end
end
end
Expand Down
94 changes: 94 additions & 0 deletions app/controllers/api/v1/import/books_controller.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
# frozen_string_literal: true

module Api
module V1
module Import
class BooksController < Api::ApiController
# before_action :find_book
# before_action :check_case

# rubocop:disable Metrics/MethodLength
# rubocop:disable Metrics/AbcSize
# rubocop:disable Metrics/CyclomaticComplexity
# rubocop:disable Metrics/PerceivedComplexity
# rubocop:disable Layout/LineLength
def create
team_id = params.require(:team_id)
params_to_use = book_params.to_h.deep_symbolize_keys

@book = Book.new

@book.team = Team.find(team_id)

scorer_name = params_to_use[:scorer][:name]
unless Scorer.exists?(name: scorer_name)
@book.errors.add(:base, "Scorer with name '#{scorer_name}' needs to be migrated over first.")
end

selection_strategy_name = params_to_use[:selection_strategy][:name]
unless SelectionStrategy.exists?(name: selection_strategy_name)
@book.errors.add(:selection_strategy,
"Selection strategy with name '#{selection_strategy_name}' needs to be migrated over first.")
end

if params_to_use[:query_doc_pairs]
list_of_emails_of_users = []
params_to_use[:query_doc_pairs].each do |query_doc_pair|
next unless query_doc_pair[:judgements]

query_doc_pair[:judgements].each do |judgement|
list_of_emails_of_users << judgement[:user_email]
end
end
list_of_emails_of_users.uniq!
list_of_emails_of_users.each do |email|
unless User.exists?(email: email)
@book.errors.add(:base, "User with email '#{email}' needs to be migrated over first.")
end
end
end

unless @book.errors.empty?
render json: @book.errors, status: :bad_request
return
end

# passed first set of validations.
@book.name = params_to_use[:name]
@book.show_rank = params_to_use[:show_rank]
@book.support_implicit_judgements = params_to_use[:support_implicit_judgements]

@book.scorer = Scorer.find_by(name: scorer_name)
@book.selection_strategy = SelectionStrategy.find_by(name: selection_strategy_name)

params_to_use[:query_doc_pairs]&.each do |query_doc_pair|
qdp = @book.query_doc_pairs.build(query_doc_pair.except(:judgements))
next unless query_doc_pair[:judgements]

query_doc_pair[:judgements].each do |judgement|
judgement[:user] = User.find_by(email: judgement[:user_email])
qdp.judgements.build(judgement.except(:user_email))
end
end

if @book.save
respond_with @book
else
render json: @book.errors, status: :bad_request
end
end
# rubocop:enable Metrics/MethodLength
# rubocop:enable Metrics/AbcSize
# rubocop:enable Metrics/CyclomaticComplexity
# rubocop:enable Metrics/PerceivedComplexity
# rubocop:enable Layout/LineLength

private

def book_params
params.require(:book).permit!
end
end
end
end
end
26 changes: 1 addition & 25 deletions app/views/api/v1/books/_book.json.jbuilder
Original file line number Diff line number Diff line change
@@ -1,28 +1,4 @@
# frozen_string_literal: true

export = @export ||= false

json.name book.name
json.book_id book.id unless export
json.show_rank book.show_rank
json.support_implicit_judgements book.support_implicit_judgements

if export
if book.scorer.present?
json.scorer do
json.partial! 'api/v1/scorers/scorer', scorer: book.scorer, export: export
end
end

if book.selection_strategy.present?
json.selection_strategy do
json.partial! 'selection_strategy', selection_strategy: book.selection_strategy
end
end
end

json.query_doc_pairs do
json.array! book.query_doc_pairs,
partial: 'api/v1/books/query_doc_pairs', as: :query_doc_pair,
export: export
end
json.book_id book.id
10 changes: 0 additions & 10 deletions app/views/api/v1/books/_judgements.json.jbuilder

This file was deleted.

12 changes: 0 additions & 12 deletions app/views/api/v1/books/_query_doc_pairs.json.jbuilder

This file was deleted.

2 changes: 1 addition & 1 deletion app/views/api/v1/books/create.json.jbuilder
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
# frozen_string_literal: true

json.partial! 'book', book: @book, export: false
json.partial! 'book', book: @book
2 changes: 1 addition & 1 deletion app/views/api/v1/books/show.json.jbuilder
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
# frozen_string_literal: true

json.partial! 'book', book: @book, export: false
json.partial! 'book', book: @book
2 changes: 1 addition & 1 deletion app/views/api/v1/books/update.json.jbuilder
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
# frozen_string_literal: true

json.partial! 'book', book: @book, export: false
json.partial! 'book', book: @book
22 changes: 22 additions & 0 deletions app/views/api/v1/export/books/_book.json.jbuilder
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
# frozen_string_literal: true

json.name book.name
json.show_rank book.show_rank
json.support_implicit_judgements book.support_implicit_judgements

if book.scorer.present?
json.scorer do
json.partial! 'api/v1/scorers/scorer', scorer: book.scorer, export: true
end
end

if book.selection_strategy.present?
json.selection_strategy do
json.partial! 'selection_strategy', selection_strategy: book.selection_strategy
end
end

json.query_doc_pairs do
json.array! book.query_doc_pairs,
partial: 'query_doc_pair', as: :query_doc_pair
end
5 changes: 5 additions & 0 deletions app/views/api/v1/export/books/_judgements.json.jbuilder
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
# frozen_string_literal: true

json.rating judgement.rating
json.unrateable judgement.unrateable
json.user_email judgement.user.email if judgement.user
10 changes: 10 additions & 0 deletions app/views/api/v1/export/books/_query_doc_pair.json.jbuilder
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# frozen_string_literal: true

json.query_text query_doc_pair.query_text
json.doc_id query_doc_pair.doc_id
json.position query_doc_pair.position
json.document_fields query_doc_pair.document_fields

json.judgements do
json.array! query_doc_pair.judgements, partial: 'judgements', as: :judgement
end
3 changes: 3 additions & 0 deletions app/views/api/v1/export/books/show.json.jbuilder
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# frozen_string_literal: true

json.partial! 'book', book: @book
2 changes: 2 additions & 0 deletions config/routes.rb
Original file line number Diff line number Diff line change
Expand Up @@ -174,6 +174,7 @@

# Imports
namespace :import do
resources :books, only: [ :create ]
resources :ratings, only: [ :create ]
namespace :queries do
resources :information_needs, only: [ :create ], param: :case_id
Expand All @@ -182,6 +183,7 @@

# Exports
namespace :export do
resources :books, only: [ :show ], param: :book_id
resources :ratings, only: [ :show ], param: :case_id
namespace :queries do
resources :information_needs, only: [ :show ], param: :case_id
Expand Down
55 changes: 2 additions & 53 deletions test/controllers/api/v1/books_controller_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -89,61 +89,10 @@ class BooksControllerTest < ActionController::TestCase
assert_response :ok

body = response.parsed_body
assert_not assigns(:export)

assert_equal body['name'].size, book.name.size
assert_equal body['query_doc_pairs'][0]['query'], book.query_doc_pairs[0].query_text
assert_nil body['query_doc_pairs'][0]['document_fields']
end

test 'returns book info with export specified' do
get :show, params: { id: book.id, export: false }
assert_response :ok

body = response.parsed_body
assert_not assigns(:export)

assert_equal body['name'].size, book.name.size
assert_equal body['query_doc_pairs'][0]['query'], book.query_doc_pairs[0].query_text
assert_nil body['query_doc_pairs'][0]['document_fields']
end

test 'returns detailed query_doc_pair and judgement info' do
get :show, params: { id: book.id, export: true }
assert_response :ok

body = response.parsed_body
puts body
assert assigns(:export)

assert_equal body['name'].size, book.name.size
assert_equal body['query_doc_pairs'][0]['query'], book.query_doc_pairs[0].query_text
assert_equal body['query_doc_pairs'][0]['document_fields'], book.query_doc_pairs[0].document_fields
end
end

describe 'Exporting a book in json' do
let(:book) { books(:james_bond_movies) }
let(:judgement) { judgements(:jbm_qdp10_judgement) }
let(:doug) { users(:doug) }
let(:random_user) { users(:random) }

test 'the AR object ids are replaced with names' do
get :show, params: { id: book.id, export: true }
assert_response :ok
body = response.parsed_body
require 'json'
puts JSON.pretty_generate(body)
assert_nil body['book_id']
assert_not_nil body['name']

assert_nil body['scorer_id']
assert_not_nil body['scorer']
assert_nil body['scorer']['scorer_id']
assert_empty body['scorer']['teams']

assert_nil body['selection_strategy_id']
assert_not_nil body['selection_strategy']
# assert_equal body['query_doc_pairs'][0]['query'], book.query_doc_pairs[0].query_text
# assert_nil body['query_doc_pairs'][0]['document_fields']
end
end

Expand Down
42 changes: 42 additions & 0 deletions test/controllers/api/v1/export/books_controller_test.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
# frozen_string_literal: true

require 'test_helper'
require 'csv'
module Api
module V1
module Export
class BooksControllerTest < ActionController::TestCase
let(:doug) { users(:doug) }

before do
@controller = Api::V1::Export::BooksController.new

login_user doug
end

describe 'Exporting a book in json' do
let(:book) { books(:james_bond_movies) }
let(:doug) { users(:doug) }

test 'the AR object ids are replaced with names' do
get :show, params: { book_id: book.id }
assert_response :ok
body = response.parsed_body
require 'json'
puts JSON.pretty_generate(body)
assert_nil body['book_id']
assert_not_nil body['name']

assert_nil body['scorer_id']
assert_not_nil body['scorer']
assert_nil body['scorer']['scorer_id']
assert_empty body['scorer']['teams']

assert_nil body['selection_strategy_id']
assert_not_nil body['selection_strategy']
end
end
end
end
end
end
Loading

0 comments on commit f9edf81

Please sign in to comment.