From 9f63c14f8a9ebd28261e8fbd3c475b177c3beb68 Mon Sep 17 00:00:00 2001 From: cryptogopher Date: Thu, 2 Apr 2020 02:23:53 +0200 Subject: [PATCH] Adding MeasurementRoutine selection/editing support --- app/controllers/concerns/finders.rb | 16 ++++++++--- app/controllers/ingredients_controller.rb | 1 + .../measurement_routines_controller.rb | 12 +++++++++ app/controllers/measurements_controller.rb | 20 ++++++++++---- app/helpers/measurement_routines_helper.rb | 2 ++ app/models/measurement.rb | 1 + app/views/measurement_routines/_form.html.erb | 7 +++++ app/views/measurement_routines/_show.html.erb | 3 +++ .../measurement_routines/_show_form.html.erb | 27 +++++++++++++++++++ app/views/measurement_routines/edit.js.erb | 1 + app/views/measurement_routines/show.js.erb | 1 + app/views/measurements/_form.html.erb | 19 ++++++------- config/locales/en.yml | 1 + config/routes.rb | 2 +- init.rb | 2 ++ 15 files changed, 94 insertions(+), 21 deletions(-) create mode 100644 app/controllers/measurement_routines_controller.rb create mode 100644 app/helpers/measurement_routines_helper.rb create mode 100644 app/views/measurement_routines/_form.html.erb create mode 100644 app/views/measurement_routines/_show.html.erb create mode 100644 app/views/measurement_routines/_show_form.html.erb create mode 100644 app/views/measurement_routines/edit.js.erb create mode 100644 app/views/measurement_routines/show.js.erb diff --git a/app/controllers/concerns/finders.rb b/app/controllers/concerns/finders.rb index 2937225..ea0eae5 100644 --- a/app/controllers/concerns/finders.rb +++ b/app/controllers/concerns/finders.rb @@ -10,7 +10,8 @@ module Concerns::Finders def find_measurement @measurement = Measurement.find(params[:id]) - @project = @measurement.routine.project + @routine = @measurement.routine + @project = @routine.project rescue ActiveRecord::RecordNotFound render_404 end @@ -22,15 +23,22 @@ module Concerns::Finders render_404 end - def find_quantity(id = :id) - @quantity = Quantity.find(params[id]) + def find_measurement_routine(id = params[:id]) + @routine = MeasurementRoutine.find(id) + @project = @routine.project + rescue ActiveRecord::RecordNotFound + render_404 + end + + def find_quantity(id = params[:id]) + @quantity = Quantity.find(id) @project = @quantity.project rescue ActiveRecord::RecordNotFound render_404 end def find_quantity_by_quantity_id - find_quantity(:quantity_id) + find_quantity(params[:quantity_id]) end def find_unit diff --git a/app/controllers/ingredients_controller.rb b/app/controllers/ingredients_controller.rb index b62fdf5..4bc4e88 100644 --- a/app/controllers/ingredients_controller.rb +++ b/app/controllers/ingredients_controller.rb @@ -23,6 +23,7 @@ class IngredientsController < ApplicationController def new @ingredient = @project.ingredients.new # passing attr for Nutrient after_initialize + # FIXME: is this necessary when creating through association? @ingredient.nutrients.new(ingredient: @ingredient) end diff --git a/app/controllers/measurement_routines_controller.rb b/app/controllers/measurement_routines_controller.rb new file mode 100644 index 0000000..bd34ffc --- /dev/null +++ b/app/controllers/measurement_routines_controller.rb @@ -0,0 +1,12 @@ +class MeasurementRoutinesController < ApplicationController + include Concerns::Finders + + before_action :find_measurement_routine, only: [:show, :edit] + before_action :authorize + + def show + end + + def edit + end +end diff --git a/app/controllers/measurements_controller.rb b/app/controllers/measurements_controller.rb index ed20b2c..4f2b779 100644 --- a/app/controllers/measurements_controller.rb +++ b/app/controllers/measurements_controller.rb @@ -18,16 +18,25 @@ class MeasurementsController < ApplicationController def new @measurement = @project.measurements.new - @measurement.build_routine + @routine = @measurement.build_routine @measurement.readouts.new end def create - @measurement = @project.measurements.new(measurement_params) + # Nested attributes cannot create outer object (Measurement) and at the same time edit + # existing nested object (MeasurementRoutine) if it's not associated with outer object + # https://stackoverflow.com/questions/6346134/ + # That's why routine needs to be found and associated before measurement initialization + @measurement = @project.measurements.new do |m| + routine_id = params[:measurement][:routine_attributes][:id] + m.routine = @project.measurement_routines.find_by(id: routine_id) if routine_id + end + @measurement.attributes = measurement_params @measurement.routine.project = @project + @routine = @measurement.routine if @measurement.save - if @measurement.routine.columns.empty? - @measurement.routine.quantities << @measurement.readouts.map(&:quantity).first(6) + if @routine.columns.empty? + @routine.quantities << @measurement.readouts.map(&:quantity).first(6) end flash[:notice] = 'Created new measurement' @@ -93,6 +102,7 @@ class MeasurementsController < ApplicationController :source_id, routine_attributes: [ + :id, :name, :description ], @@ -118,7 +128,7 @@ class MeasurementsController < ApplicationController end def prepare_readouts - @quantities = @measurement.routine.quantities.includes(:formula) + @quantities = @routine.quantities.includes(:formula) @measurements, @requested_r, @extra_r, @formula_q = @routine.measurements .includes(:routine, :source) .filter(session[:m_filters], @quantities) diff --git a/app/helpers/measurement_routines_helper.rb b/app/helpers/measurement_routines_helper.rb new file mode 100644 index 0000000..16fa09d --- /dev/null +++ b/app/helpers/measurement_routines_helper.rb @@ -0,0 +1,2 @@ +module MeasurementRoutinesHelper +end diff --git a/app/models/measurement.rb b/app/models/measurement.rb index 7ea473e..780a1d1 100644 --- a/app/models/measurement.rb +++ b/app/models/measurement.rb @@ -5,6 +5,7 @@ class Measurement < ActiveRecord::Base attrs['name'].blank? } after_destroy { self.routine.destroy if self.routine.measurements.empty? } + has_one :project, through: :routine belongs_to :source, required: false diff --git a/app/views/measurement_routines/_form.html.erb b/app/views/measurement_routines/_form.html.erb new file mode 100644 index 0000000..35ede9e --- /dev/null +++ b/app/views/measurement_routines/_form.html.erb @@ -0,0 +1,7 @@ +
+ <%= fields_for 'measurement[routine_attributes]', @routine do |ff| %> + <%= ff.hidden_field :id %> +

<%= ff.text_field :name, required: true, style: "width: 95%;" %>

+

<%= ff.text_area :description, cols: 40, rows: 3, style: "width: 95%;" %>

+ <% end %> +
diff --git a/app/views/measurement_routines/_show.html.erb b/app/views/measurement_routines/_show.html.erb new file mode 100644 index 0000000..57d9bc1 --- /dev/null +++ b/app/views/measurement_routines/_show.html.erb @@ -0,0 +1,3 @@ +<% unless @routine.description.empty? %> +

<%= @routine.description %>

+<% end %> diff --git a/app/views/measurement_routines/_show_form.html.erb b/app/views/measurement_routines/_show_form.html.erb new file mode 100644 index 0000000..3a91dd0 --- /dev/null +++ b/app/views/measurement_routines/_show_form.html.erb @@ -0,0 +1,27 @@ +
+<%= f.fields_for :routine do |ff| %> +

+ <%= ff.select :id, + options_from_collection_for_select(@project.measurement_routines, + :id, :name, @routine.id), + {label: :field_measurement_routine, required: true}, + onchange: "var mr_id = $('#measurement_routine_attributes_id option:selected').val(); + $.ajax({ + url: '#{measurement_routine_path(id: :mr_id)}'.replace('mr_id', mr_id), + dataType: 'script' + }); + return false;" %> + <%= link_to l(:button_edit), '#', + onclick: "var mr_id = $('#measurement_routine_attributes_id option:selected').val(); + $.ajax({ + url: '#{edit_measurement_routine_path(id: :mr_id)}'.replace('mr_id', mr_id), + dataType: 'script' + }); + return false;", + class: 'icon icon-edit' %> +

+<% end %> +
+ <%= render partial: 'measurement_routines/show' %> +
+
diff --git a/app/views/measurement_routines/edit.js.erb b/app/views/measurement_routines/edit.js.erb new file mode 100644 index 0000000..45983e2 --- /dev/null +++ b/app/views/measurement_routines/edit.js.erb @@ -0,0 +1 @@ +$('#measurement-routine-form').html('<%= j render partial: 'measurement_routines/form' %>'); diff --git a/app/views/measurement_routines/show.js.erb b/app/views/measurement_routines/show.js.erb new file mode 100644 index 0000000..0bb0ad2 --- /dev/null +++ b/app/views/measurement_routines/show.js.erb @@ -0,0 +1 @@ +$('#measurement-routine').html('<%= j render partial: 'measurement_routines/show' %>'); diff --git a/app/views/measurements/_form.html.erb b/app/views/measurements/_form.html.erb index 7f8b8aa..f2c4184 100644 --- a/app/views/measurements/_form.html.erb +++ b/app/views/measurements/_form.html.erb @@ -1,17 +1,14 @@ <%= error_messages_for @measurement %> -
- <%= t('.label_routine') %> -
- <%= f.fields_for :routine do |ff| %> -

<%= ff.text_field :name, required: true, style: "width: 95%;" %>

-

<%= ff.text_area :description, cols: 40, rows: 3, style: "width: 95%;" %>

+
+
+ <% if @routine.persisted? %> + <%= render partial: 'measurement_routines/show_form', locals: {f: f} %> + <% else %> + <%= render partial: 'measurement_routines/form', locals: {f: f} %> <% end %>
-
- -
- <%= t('.label_measurement') %> +

<%= f.select :source_id, source_options, {required: false, include_blank: t('.null_source')} %>

@@ -42,7 +39,7 @@ onclick: 'newReadout(); return false;' %>

-
+ <%= javascript_tag do %> function newReadout() { diff --git a/config/locales/en.yml b/config/locales/en.yml index 067c0b6..6eb1375 100644 --- a/config/locales/en.yml +++ b/config/locales/en.yml @@ -1,6 +1,7 @@ # English strings go here for Rails i18n en: body_trackers_menu_caption: 'Body trackers' + field_measurement_routine: 'Routine' field_readouts: 'Readouts' field_taken_at_date: 'Taken at' field_order: 'Order' diff --git a/config/routes.rb b/config/routes.rb index 39d5f23..20b21ae 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -7,7 +7,7 @@ resources :projects, shallow: true do post 'defaults' end end - resources :measurement_routines, only: [] do + resources :measurement_routines, only: [:show, :edit] do member do get 'readouts', to: 'measurements#readouts' post 'toggle_column', to: 'measurements#toggle_column' diff --git a/init.rb b/init.rb index 6e04db0..7751344 100644 --- a/init.rb +++ b/init.rb @@ -13,6 +13,7 @@ Redmine::Plugin.register :body_tracking do project_module :body_tracking do permission :view_body_trackers, { body_trackers: [:index], + measurement_routines: [:show], measurements: [:index, :readouts, :filter], ingredients: [:index, :nutrients, :filter], sources: [:index], @@ -21,6 +22,7 @@ Redmine::Plugin.register :body_tracking do }, read: true permission :manage_common, { body_trackers: [:defaults], + measurement_routines: [:edit], measurements: [:new, :create, :edit, :update, :destroy, :retake, :toggle_column], ingredients: [:new, :create, :edit, :update, :destroy, :toggle, :toggle_column, :import],