From f21da3f075f68eacabe90b4ca80c0755fee10bf0 Mon Sep 17 00:00:00 2001 From: Ken Johnson Date: Thu, 11 Dec 2025 12:24:52 +0000 Subject: [PATCH 1/2] Improve file upload UX with validation and uploaded files display MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Enhanced the benefit forms file upload functionality to provide better user feedback and visibility of uploaded files. Changes: 1. Added file type validation in controller: - Only accepts PDF, DOC, DOCX, JPG, PNG formats - Shows clear error message with the rejected file extension 2. Added file size validation: - Maximum 10MB file size limit - Shows file size in error message if exceeded 3. Improved success/error messages: - Shows specific filename on successful upload - Shows detailed error messages for validation failures 4. Added uploaded files display section: - Lists all uploaded files with icons based on file type - Shows file size and upload timestamp - Provides download button for each file - Only displays when files exist Before: Users received generic "Something went wrong" message with no indication of why uploads failed. No way to see uploaded files. After: Clear validation feedback tells users exactly what went wrong (wrong format, too large, etc.) and uploaded files are visible with download links. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude --- app/controllers/benefit_forms_controller.rb | 45 ++++++++++++++++-- app/views/benefit_forms/index.html.erb | 52 +++++++++++++++++++++ 2 files changed, 92 insertions(+), 5 deletions(-) diff --git a/app/controllers/benefit_forms_controller.rb b/app/controllers/benefit_forms_controller.rb index 97721c9..2017ddc 100644 --- a/app/controllers/benefit_forms_controller.rb +++ b/app/controllers/benefit_forms_controller.rb @@ -3,6 +3,15 @@ class BenefitFormsController < ApplicationController def index @benefits = Benefits.new + # List uploaded files + data_path = Rails.root.join("public", "data") + @uploaded_files = Dir.glob("#{data_path}/*").reject { |f| File.directory?(f) || File.basename(f) == '.gitkeep' }.map do |file| + { + name: File.basename(file), + size: File.size(file), + modified: File.mtime(file) + } + end.sort_by { |f| f[:modified] }.reverse end def download @@ -17,12 +26,38 @@ class BenefitFormsController < ApplicationController def upload file = params[:benefits][:upload] - if file - flash[:success] = "File Successfully Uploaded!" - Benefits.save(file, params[:benefits][:backup]) - else - flash[:error] = "Something went wrong" + + if file.nil? + flash[:error] = "Please select a file to upload" + redirect_to user_benefit_forms_path(user_id: current_user.id) + return end + + # Validate file type + allowed_extensions = %w[.pdf .doc .docx .jpg .jpeg .png] + file_extension = File.extname(file.original_filename).downcase + + unless allowed_extensions.include?(file_extension) + flash[:error] = "Invalid file type. Accepted formats: PDF, DOC, DOCX, JPG, PNG. You uploaded: #{file_extension}" + redirect_to user_benefit_forms_path(user_id: current_user.id) + return + end + + # Validate file size (10MB max) + max_size = 10.megabytes + if file.size > max_size + flash[:error] = "File too large. Maximum size: 10MB. Your file: #{(file.size / 1.megabyte.to_f).round(2)}MB" + redirect_to user_benefit_forms_path(user_id: current_user.id) + return + end + + begin + Benefits.save(file, params[:benefits][:backup]) + flash[:success] = "File '#{file.original_filename}' uploaded successfully!" + rescue => e + flash[:error] = "Failed to upload file: #{e.message}" + end + redirect_to user_benefit_forms_path(user_id: current_user.id) end diff --git a/app/views/benefit_forms/index.html.erb b/app/views/benefit_forms/index.html.erb index 14920ad..5ae8a50 100644 --- a/app/views/benefit_forms/index.html.erb +++ b/app/views/benefit_forms/index.html.erb @@ -118,6 +118,58 @@ + + <% if @uploaded_files.any? %> +
+
+
+
+

+ Uploaded Files +

+
+
+
+ + + + + + + + + + + <% @uploaded_files.each do |file| %> + + + + + + + <% end %> + +
File Name Size UploadedActions
+ <% icon_class = case File.extname(file[:name]).downcase + when '.pdf' then 'bi-file-earmark-pdf text-danger' + when '.doc', '.docx' then 'bi-file-earmark-word text-primary' + when '.jpg', '.jpeg', '.png' then 'bi-file-earmark-image text-success' + else 'bi-file-earmark' + end %> + + <%= file[:name] %> + <%= number_to_human_size(file[:size]) %><%= file[:modified].strftime("%b %d, %Y at %I:%M %p") %> + <%= link_to download_path(type: "File", name: "public/data/#{file[:name]}"), class: "btn btn-sm btn-outline-primary" do %> + Download + <% end %> +
+
+
+
+
+
+ <% end %> +
From 705f7508aacbd984e5791b0347af5499008340ae Mon Sep 17 00:00:00 2001 From: Ken Johnson Date: Thu, 11 Dec 2025 12:35:19 +0000 Subject: [PATCH 2/2] Fix flash messages not appearing after file upload MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Changed flash message handling to ensure success and error messages are visible to users after file upload attempts. Changes: - Use flash.now for validation errors (no file, wrong type, too large) so messages display immediately without redirect - Re-render index page on validation errors instead of redirecting - Keep regular flash for success messages to persist through redirect - Refactored file listing into load_uploaded_files helper method Before: Flash messages were set but not displaying after redirect After: Users see clear feedback for all upload outcomes 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude --- app/controllers/benefit_forms_controller.rb | 41 +++++++++++++-------- 1 file changed, 26 insertions(+), 15 deletions(-) diff --git a/app/controllers/benefit_forms_controller.rb b/app/controllers/benefit_forms_controller.rb index 2017ddc..1524cfc 100644 --- a/app/controllers/benefit_forms_controller.rb +++ b/app/controllers/benefit_forms_controller.rb @@ -3,15 +3,7 @@ class BenefitFormsController < ApplicationController def index @benefits = Benefits.new - # List uploaded files - data_path = Rails.root.join("public", "data") - @uploaded_files = Dir.glob("#{data_path}/*").reject { |f| File.directory?(f) || File.basename(f) == '.gitkeep' }.map do |file| - { - name: File.basename(file), - size: File.size(file), - modified: File.mtime(file) - } - end.sort_by { |f| f[:modified] }.reverse + load_uploaded_files end def download @@ -28,8 +20,10 @@ class BenefitFormsController < ApplicationController file = params[:benefits][:upload] if file.nil? - flash[:error] = "Please select a file to upload" - redirect_to user_benefit_forms_path(user_id: current_user.id) + flash.now[:error] = "Please select a file to upload" + @benefits = Benefits.new + load_uploaded_files + render :index return end @@ -38,16 +32,20 @@ class BenefitFormsController < ApplicationController file_extension = File.extname(file.original_filename).downcase unless allowed_extensions.include?(file_extension) - flash[:error] = "Invalid file type. Accepted formats: PDF, DOC, DOCX, JPG, PNG. You uploaded: #{file_extension}" - redirect_to user_benefit_forms_path(user_id: current_user.id) + flash.now[:error] = "Invalid file type. Accepted formats: PDF, DOC, DOCX, JPG, PNG. You uploaded: #{file_extension}" + @benefits = Benefits.new + load_uploaded_files + render :index return end # Validate file size (10MB max) max_size = 10.megabytes if file.size > max_size - flash[:error] = "File too large. Maximum size: 10MB. Your file: #{(file.size / 1.megabyte.to_f).round(2)}MB" - redirect_to user_benefit_forms_path(user_id: current_user.id) + flash.now[:error] = "File too large. Maximum size: 10MB. Your file: #{(file.size / 1.megabyte.to_f).round(2)}MB" + @benefits = Benefits.new + load_uploaded_files + render :index return end @@ -61,4 +59,17 @@ class BenefitFormsController < ApplicationController redirect_to user_benefit_forms_path(user_id: current_user.id) end + private + + def load_uploaded_files + data_path = Rails.root.join("public", "data") + @uploaded_files = Dir.glob("#{data_path}/*").reject { |f| File.directory?(f) || File.basename(f) == '.gitkeep' }.map do |file| + { + name: File.basename(file), + size: File.size(file), + modified: File.mtime(file) + } + end.sort_by { |f| f[:modified] }.reverse + end + end