Rails 4.1 Carrierwave not uploading images - ruby-on-rails

I am using the carrierwave gem to upload images of movie listings. I have created a migration creating a image column to my listings database.
updated the Listing model.rb file
class Listing < ActiveRecord::Base
mount_uploader :image, ImageUploader
belongs_to :user
end
added the :html = > { multipart: true } command to my simple form
<div class="wizard-container">
<%= simple_form_for(#listing, url: new_user_registration_path, method: :get, :html => { multipart: true } ) do |f| %>
<div class="card wizard-card ct-wizard-orange" id="wizard">
<!-- You can switch "ct-wizard-orange" with one of the next bright colors: "ct-wizard-blue", "ct-wizard-green", "ct-wizard-orange", "ct-wizard-red" -->
<div class="wizard-header">
<h3>
<b>LIST</b> YOUR MOVIE <br>
<small>This information will let us know more about your movie</small>
</h3>
</div>
And the image field to my listing.html.erb file
<div class="row">
<div class="col-sm-10 col-sm-offset-1">
<%= f.file_field :image %><br>
</div>
</div>
but when i create a listing the folloeing information , appears in console
Started GET "/users/sign_up?utf8=%E2%9C%93&listing%5Btitle%5D=Top+Gun&listing%5Btime%5D=14.35&listing%5Bdate%5D=24%2F03%2F2016&listing%5Bseats%5D=5&listing%5Bvenue_name%5D=Preston+Library&listing%5Bimage%5D=IMG_0892.JPG&listing%5Bprice%5D=2.3&listing%5Blocation%5D=Preston+Town+Hall&listing%5Bother_info%5D=This+is+a+great+venue&listing%5Bprojector%5D=0&listing%5Bcables%5D=0&listing%5Blaptops%5D=0&listing%5Bseating%5D=0&listing%5Bblinds%5D=0&listing%5Binternet%5D=0&listing%5Blighting%5D=0&listing%5Bcamcorder%5D=0&listing%5Bcatering%5D=0&listing%5Btoilets%5D=0&listing%5Bfire%5D=0&listing%5Bfire%5D=1&commit=Create+Listing" for 127.0.0.1 at 2015-03-24 14:36:31 +0000
Processing by Devise::RegistrationsController#new as HTML
Parameters: {"utf8"=>"✓", "listing"=>{"title"=>"Top Gun", "time"=>"14.35", "date"=>"24/03/2016", "seats"=>"5", "venue_name"=>"Preston Library", **"image"=>"IMG_0892.JPG",** "price"=>"2.3", "location"=>"Preston Town Hall", "other_info"=>"This is a great venue", "projector"=>"0", "cables"=>"0", "laptops"=>"0", "seating"=>"0", "blinds"=>"0", "internet"=>"0", "lighting"=>"0", "camcorder"=>"0", "catering"=>"0", "toilets"=>"0", "fire"=>"1"}, "commit"=>"Create Listing"}
So it captures the image but does mot display the image?
this app is slightly different to what i normally do , I make the user sign in first and then create details ,this app you create listings and then create an account
new.html.erb
<%= render 'layouts/header' %>
<h2 class="text-center">Sign up</h2>
<%
if !user_signed_in?
resource.listings.build
resource.listings[0].title = params[:listing][:title]
resource.listings[0].time = params[:listing][:time]
resource.listings[0].date = params[:listing][:date]
resource.listings[0].seats = params[:listing][:seats]
resource.listings[0].venue_name = params[:listing][:venue_name]
resource.listings[0].location = params[:listing][:location]
resource.listings[0].other_info = params[:listing][:other_info]
resource.listings[0].price = params[:listing][:price]
resource.listings[0].projector = params[:listing][:projector]
resource.listings[0].cables = params[:listing][:cables]
resource.listings[0].laptops = params[:listing][:laptops]
resource.listings[0].seating = params[:listing][:seating]
resource.listings[0].blinds = params[:listing][:blinds]
resource.listings[0].lighting = params[:listing][:lighting]
resource.listings[0].camcorder = params[:listing][:camcorder]
resource.listings[0].catering = params[:listing][:catering]
resource.listings[0].toilets = params[:listing][:toilets]
resource.listings[0].fire = params[:listing][:fire]
resource.listings[0].internet = params[:listing][:internet]
end
%>
<%= simple_form_for(resource, as: resource_name, url: registration_path(resource_name), html: {class: "form-signin"}) do |f| %>
<%= f.error_notification %>
<%= f.input :name, required: true, autofocus: true, label: false, placeholder: "Name", input_html: {class: "form-control"} %>
<%= f.input :email, required: true, label: false, placeholder: "Email", input_html: {class: "form-control"} %>
<%= f.input :password, required: true, label: false, placeholder: "Password", input_html: {class: "form-control"} %>
<%= f.input :password_confirmation, required: true, label: false, placeholder: "Password Confirmation", input_html: {class: "form-control"} %>
<div style="display:none">
<%= f.fields_for :listings do |listing_form| %>
<%= listing_form.input :title, label: false, placeholder: "Movie Title", input_html: {class: "form-control"} %>
<%= listing_form.input :time, label: false, placeholder: "What time does your movie start?", input_html: {class: "form-control"} %>
<%= listing_form.input :date, label: false, placeholder: "What date", input_html: {class: "form-control"} %>
<%= listing_form.input :seats, label: false, placeholder: "Number of seats", input_html: {class: "form-control"} %>
<%= listing_form.input :venue_name, label: false, placeholder: "Name of venue", input_html: {class: "form-control"} %>
<%= listing_form.input :location, label: false, placeholder: "Address", input_html: {class: "form-control", rows: 5 } %>
<%= listing_form.input :other_info, label: false, placeholder: "Other information", input_html: {class: "form-control", rows: 5} %>
<%= listing_form.input :price, label: false, placeholder: "Ticket Price (£)", input_html: {class: "form-control"} %>
<p> Projector </p>
<%= listing_form.input :projector, required: false, label: false %>
<p> Cable </p>
<%= listing_form.input :cables, required: false, label: false %>
<p> Laptop </p>
<%= listing_form.input :laptops, required: false, label: false %>
<p> Seating </p>
<%= listing_form.input :seating, required: false, label: false %>
<p> Blinds </p>
<%= listing_form.input :blinds, required: false, label: false %>
<p> Lighting </p>
<%= listing_form.input :lighting, required: false, label: false %>
<p> Camcorder </p>
<%= listing_form.input :camcorder, required: false, label: false %>
<p> Catering </p>
<%= listing_form.input :catering, required: false, label: false %>
<p> Toilets </p>
<%= listing_form.input :toilets, required: false, label: false %>
<p> Fire alarm </p>
<%= listing_form.input :fire, required: false, label: false %>
<p> Wifi/internet </p>
<%= listing_form.input :internet, required: false, label: false %>
<% end %>
</div>
<%= f.button :submit, "Sign up", class: "btn btn-primary btn-block" %>
<%= render "devise/shared/links" %>
<% end %>
application_controller.rb
class ApplicationController < ActionController::Base
# Prevent CSRF attacks by raising an exception.
# For APIs, you may want to use :null_session instead.
protect_from_forgery with: :exception
before_filter :configure_permitted_parameters, if: :devise_controller?
protected
def configure_permitted_parameters
devise_parameter_sanitizer.for(:sign_up) do |u|
u.permit(
:name,
:email, :password, :confirmation_password,
listings_attributes: [
:title, :time, :date, :seats,
:venue_name, :location, :other_info,
:price, :projector, :cables,
:laptops, :seating, :blinds,
:lighting, :camcorder, :catering,
:toilets, :fire, :internet, :image
]
)
end
devise_parameter_sanitizer.for(:account_update) << :name
end
end
any thoughts
Neil
rake routes
Rails.application.routes.draw do
resources :listings
devise_for :users
root 'pages#home'
get 'about' => 'pages#about'
get 'pages/contact'
get 'dashboard' => 'pages#dashboard'
get 'start' => 'listings#listing'

Related

Simple Form For that adapts based on checkbox input

I am working on a personal project where I want users to be able to create profiles (I am using Devise to handle users). These can either be public or private, whereby public profiles require more input fields than private profiles. Is there any way I can cause these additional form fields to only appear if the user chooses his profile to be public?
I tried looking on StackOverflow and previous threads on here but couldn't find anything. I saw a few suggestions for the Cocoon gem but couldn't get that to work.
<%= simple_form_for(#User, url: registration_path(#User)) do |f| %>
<%= f.error_notification %>
<div class="form-inputs">
<%= f.input :first_name, required: true, autofocus: true %>
<%= f.input :email,
required: true,
input_html: { autocomplete: "email" }%>
<%= f.input :public, required: false, label: "Enable public profile?" %>
## Ideally the following two-fields would only show if public is clicked
## Best case they would be required fields if this happens and not required if
it does not
<%= f.input :linkedin_link, required: false, label: "Linked-In Profile Link" %>
<%= f.input :photo, as: :file, label: "Profile Picture", accept: "image/*", hint: "Why not use your Linked-In profile picture? (png and jpg only)" %>
<%= f.input :password, required: true, hint: ("#{#minimum_password_length} characters minimum" if #minimum_password_length), input_html: { autocomplete: "new-password" } %>
<%= f.input :password_confirmation, required: true, input_html: { autocomplete: "new-password" } %>
<%= f.button :submit, "Sign up", class: "btn-success btn-full-width" %>
</div>
<% end %>
Looking forward to learning something new :) Thanks a lot for your help!
Managed to solve it with this.
JS:
$(function () {
$('div[name="showthis"]').hide();
//show it when the checkbox is clicked
$('input[type="checkbox"]').on('change', function () {
if ($(this).prop('checked')) {
$('div[name="showthis"]').fadeIn();
} else {
$('div[name="showthis"]').hide();
}
});
});
HTML:
<div class="form-inputs">
<%= f.input :first_name, required: true, autofocus: true %>
<%= f.input :email, required: true, input_html: { autocomplete: "email" }%>
<%= f.input :public, required: false, label: "Enable public profile?" %>
<div name="showthis">
<%= f.input :linkedin_link, required: false, label: "Linked-In Profile Link" %>
<%= f.input :photo, as: :file, label: "Profile Picture", accept: "image/*", hint: "Why not use your Linked-In profile picture? (png and jpg only)" %>
</div>
<%= f.input :password, required: true, hint: ("#{#minimum_password_length} characters minimum" if #minimum_password_length), input_html: { autocomplete: "new-password" } %>
<%= f.input :password_confirmation, required: true, input_html: { autocomplete: "new-password" } %>
<%= f.button :submit, "Sign up", class: "btn-success btn-full-width" %>
</div>

Rails adding error to :base not working as expected

I have a double nested form:
<%= simple_form_for #item, html: { class: "create-item-form" } do |item_builder| %>
<div class="well">
<%= item_builder.input :name, required: false, error: false, label: "item name" %>
<%= item_builder.input :description, as: :text, required: false, error: false, label: "How do users earn this item?" %>
<%= item_builder.input :tag_list, required: false, label: "Tags (these will help users find your item)" %>
<%= item_builder.simple_fields_for :user_items do |user_item_builder| %>
<%= user_item_builder.input :foo, as: :hidden, input_html: { value: "bar" } %>
<%= user_item_builder.simple_fields_for :user_item_images do |user_item_images_builder| %>
<%= user_item_images_builder.input :foo, as: :hidden, input_html: { value: "bar" } %>
<%= user_item_images_builder.input :picture, as: :file, required: false,
error: false, label: "Pictures of you earning this item",
input_html: { multiple: true,
name: "item[user_items_attributes][0][user_item_images_attributes][][picture]" } %>
<% end %>
<% end %>
</div>
<div class="clearfix">
<%= item_builder.submit 'Submit new item request', class: "btn btn-primary pull-right inherit-width" %>
</div>
<% end %>
When a user doesn't upload a file for the user_item_image I need to display an error message. I wrote a custom validation:
user_item_image.rb
class UserItemImage < ActiveRecord::Base
include PicturesHelper
attr_accessor :foo
mount_uploader :picture, PictureUploader
belongs_to :user_item
validate :picture_size
validate :has_picture
private
def has_picture
errors.add(:base, 'You must include at least one picture.') if picture.blank?
end
end
But I get the error message:
User items user item images base You must include at least one picture.
How can I rewrite the validation so that it doesn't show the attribute and only shows the message.
Why not use
validates :picture, presence: true
on your useritem model

Ruby on Rails - Adding a human security field into the simple_form gem?

I currently have a form created using the simple_form gem in Ruby on Rails but I would like to add a sort of 'What is 1+1?' question and input field as the last question to remove the risk of bots etc. How would I add this function into my form?
My form consists of the following:
<%= simple_form_for #job, html: { multipart: true } do |form| %>
<h2>Job Position:</h2>
<%= form.input :position, input_html: { maxlength: 60 }, placeholder: "Job Position", label: false %>
<%= form.input :company, input_html: { maxlength: 60 }, placeholder: "Company name", label: false %>
<%= form.input :salary, input_html: { maxlength: 60 }, placeholder: "Salary", label: false %>
<%= form.input :contract, input_html: { maxlength: 60 }, placeholder: "Contract Type", label: false, collection: ['full time', 'part time', 'internship'], prompt: "Contract Type" %>
<%= form.input :city, input_html: { maxlength: 60 }, placeholder: "City", label: false %>
<%= form.input :expirydate, input_html: { maxlength: 60 }, placeholder: "Expiry date", label: false %>
<%= form.input :description, input_html: { maxlength: 60 }, placeholder: "Full job description", label: false %>
<%= form.input :apply, input_html: { maxlength: 60 }, placeholder: "How to apply", label: false %>
<h2>Your Contact Details:</h2>
<%= form.input :contactname, input_html: { maxlength: 60 }, placeholder: "Contact Name", label: false %>
<%= form.input :contactemail, input_html: { maxlength: 60 }, placeholder: "Contact Email", label: false %>
<%= form.input :contactphone, input_html: { maxlength: 60 }, placeholder: "Contact Telephone", label: false %>
<%= form.button :submit %>
<% end %>
You can add a validation to your model like this:
class Job < ActiveRecord::Base
attr_accessor :human_sum
validate :not_a_bot
private
def not_a_bot
if human_sum.to_i != 2
errors.add(:human_sum, 'Get out, you bot!')
end
end
end
And then in your form:
<%= simple_form_for #job, html: { multipart: true } do |form| %>
...
<%= form.input :human_sum, label: 'What is 1+1?'
<% end %>
Don't forget to add :human_sum to your permitted params in your controller as well.

Rails 4.1: NameError in Jobs#new

Want to show different job categories for my jobs board , using the simple form gem I have added the following to my jobs form.
_form.html.erb
<%= simple_form_for(#job, html: { class: 'form-horizontal' }) do |f| %>
<%= f.collection_select :category_id, Category.all, :id, :name, {prompt: "Choose a category" }, input_html: { class: "dropdown-toggle" } %>
<%= f.input :title, label: "Job Title", input_html: { class: "form-control" } %>
<%= f.input :description, label: "Job Description", input_html: { class: "form-control" } %>
<%= f.input :company, label: "Your Company", input_html: {class: "form-control" } %>
<%= f.input :url, label: "Link to Job", input_html: { class: "form-control" } %>
<br/>
<div class="form-group">
<%= f.submit class: "btn btn-primary" %>
</div>
<% end %>
but when i go to jobs.new.html it generates the following error
NameError in Jobs#new
Showing /Users/neilpatel/Desktop/Rails/jobs_board/app/views/jobs/_form.html.erb where line #3 raised:
uninitialized constant ActionView::CompiledTemplates::Category
<%= simple_form_for(#job, html: { class: 'form-horizontal' }) do |f| %>
**<%= f.collection_select :category_id, Category.all, :id, :name, {prompt: "Choose a category" }, input_html: { class: "dropdown-toggle" } %>** -<error
<%= f.input :title, label: "Job Title", input_html: { class: "form-control" } %>
Error specifies you don't have Category Model in your application. That's why rails considering Category as constant and throwing this error uninitialized constant. Try add Category Model in you app/models directory.
<%= f.collection_select :category_id, Category.all, :id, :name, {prompt: "Choose a category" }, input_html: { class: "dropdown-toggle" } %>
Category.all Should be Modelname.all

Rails - simple form

I use simple_form gem in my Rails app. When I use code like this
= f.input_field :name, label: false, placeholder: 'Name'
= f.input_field :price, label: false, placeholder: 'Price'
= f.input_field :description, label: false, placeholder: 'Description'
= f.input_field :image, label: false, placeholder: 'Image'
I get HTML for input:
<input class="string required textform" id="item_name" label="false" maxlength="255" name="item[name]" placeholder="Имя" size="255" type="text">
As you can see size of input is 255 now. Actually it's much more than enough. How can specify the size of inputs?
Following is from simple_form documentation here
It is also possible to pass any html attribute straight to the input,
by using the :input_html option, for instance:
<%= simple_form_for #user do |f| %>
<%= f.input :username, input_html: { class: 'special' } %>
<%= f.input :password, input_html: { maxlength: 20 } %>
<%= f.input :remember_me, input_html: { value: '1' } %>
<%= f.button :submit %>
<% end %>
To set size of 100 for name input:
= f.input :name, label: false, placeholder: 'Name', input_html: { size: 100 }

Resources