Welcome to the Treehouse Community

Want to collaborate on code errors? Have bugs you need feedback on? Looking for an extra set of eyes on your latest project? Get support with fellow developers, designers, and programmers of all backgrounds and skill levels here with the Treehouse Community! While you're at it, check out some resources Treehouse students have shared here.

Looking to learn something new?

Treehouse offers a seven day free trial for new students. Get access to thousands of hours of content and join thousands of Treehouse students and alumni in the community today.

Start your free trial

Ruby

Need help with a ruby on rails bike rental application

I've got the application partially working using devices to authenicate and then user can selects the bike he wants and add it to the class.

User goes back and adds it again to extend the duration.

Want to add a calendar functionality with the start and end date user needs to select.

This then to go to a booking controller which will record all the rentals and update the bikes availability.

class CartController < ApplicationController
  before_action :authenticate_user!


  def add
    # get the ID of the product
    id = params[:id]

    # if the cart is already been created, use the existing cart
    # else create a blank cart
    if session[:cart] then
      cart = session[:cart]
    else
      session[:cart] = {}
      cart = session[:cart]
    end

    # if the product has already been added to the cart, increment the value
    # else set the value to 1
    if cart[id] then
      cart[id] = cart[id] + 1
    else
      cart[id] = 1
    end

    # redirect to the cart display page
    redirect_to :action => :index

  end

  def clearCart
    # set the session variable to nil and redirect
    session[:cart] = nil
    redirect_to :action => :index
  end 

  def index
    # if there is a cart, pass it to the page for display
    # else pass an empty value
    if session[:cart] then
      @cart = session[:cart]
    else
      @cart = {}
    end
  end

end
class ItemsController < ApplicationController
  before_action :authenticate_user!
  before_action :ensure_admin, :only => [:edit, :destroy]
  before_action :set_item, only: [:show, :edit, :update, :destroy]

  # GET /items Only admin can edit delete items
  # GET /items.json
  def index
    @items = Item.all
  end

  # GET /items/1
  # GET /items/1.json
  def show
  end

  # GET /items/new
  def new
    @item = Item.new
  end

  # GET /items/1/edit
  def edit
  end

  # POST /items
  # POST /items.json
  def create

    puts "debug +++++++++++++++++++++++++++++++++++++++++++++++++++"
    puts params.inspect
    puts "debug +++++++++++++++++++++++++++++++++++++++++++++++++++"

    @item = Item.new(item_params)

    respond_to do |format|
      if @item.save
        format.html { redirect_to @item, notice: 'Item was successfully created.' }
        format.json { render :show, status: :created, location: @item }
      else
        format.html { render :new }
        format.json { render json: @item.errors, status: :unprocessable_entity }
      end
    end
  end

  # PATCH/PUT /items/1
  # PATCH/PUT /items/1.json
  def update
    respond_to do |format|
      if @item.update(item_params)
        format.html { redirect_to @item, notice: 'Item was successfully updated.' }
        format.json { render :show, status: :ok, location: @item }
      else
        format.html { render :edit }
        format.json { render json: @item.errors, status: :unprocessable_entity }
      end
    end
  end

  # DELETE /items/1
  # DELETE /items/1.json
  def destroy
    @item.destroy
    respond_to do |format|
      format.html { redirect_to items_url, notice: 'Item was successfully destroyed.' }
      format.json { head :no_content }
    end
  end

  def ensure_admin
    unless current_user && current_user.admin?
      render :text => "Access Error Message", :status => :unauthorized
    end
  end

  private
    # Use callbacks to share common setup or constraints between actions.
    def set_item
      @item = Item.find(params[:id])
    end

    # Never trust parameters from the scary internet, only allow the white list through.
    def item_params
      params.require(:item).permit(:title, :description, :price, :image_url, :category, :brand)
    end
end
<h1>Your Cart</h1>

<% if @cart.empty? %>
    <p>Your Cart is empty</p>
<% end %>

<% total = 0 %>

<table class="cart">
    <tr>
        <td class="legend"></td>
        <td class="legend">Item</td>
        <td class="legend">Price</td>
        <td class="legend">Length</td>
        <td class="legend">Total</td>
    </tr>

<% @cart.each do | id, quantity | %>
    <% item = Item.find_by_id(id) %>
    <tr>
        <td>
            <div class="image">
                <%= link_to (image_tag item.image_url, :style => "height:40px"), item %>
            </div>
        </td>
        <td class="title"><%= link_to item.title, item %></td>
        <td class="price"><%= number_to_currency(item.price) %></td>
        <td class="quantity"><%= quantity %><br /></td>
        <td class="price"><%= number_to_currency(quantity * item.price, :unit => "€") %></td>
            %input{:type =>'text', :placeholder => params[:startdate] != nil ? params[:startdate] : "from date", :id => 'startdate', :name => "startdate", :style => 'width: 100px'}
            %input{:type =>'text', :placeholder => params[:startdate] != nil ? params[:enddate] : "to date", :id => 'enddate', :name => "enddate", :style => 'width: 100px'}
    </tr>
    <% total += quantity * item.price %>
<% end %>

    <tr>
        <td colspan="4">
            <div class="total">Total:</div>
        </td>
        <td>
            <div class="price"><%= number_to_currency(total, :unit => "Eur") %></div>
        </td>
    </tr>
</table>

<p>
    <%= link_to 'Make a booking', :controller => :items %>
</p>

routes.rb

Rails.application.routes.draw do

  resources :bookings
  get 'bookings/index'

  get 'bookings/show'

  get 'bookings/new'

  get 'bookings/edit'

  get 'bookings/destroy'

  resources :profiles
 get 'bookings/index'

  get 'bookings/show'

  get 'bookings/new'

  get 'bookings/edit'

  get 'bookings/destroy'

  resources :profiles

  devise_for :users
  get '/about' => 'site#about'
  get '/contact' => 'site#contact'
  get '/admin' => 'user#admin_login'
  get '/logout' => 'user#logout'
  get '/cart' => 'cart#index' 
  get '/cart/:id' => 'cart#add'
  get '/cart/clear' => 'cart#clearCart' 
  get '/signedinuserprofile' => 'profiles#signedinuserprofile'
  get '/product' => 'catalog#view'

  resources :items

  # The priority is based upon order of creation: first created -> highest priority.
  # See how all your routes lay out with "rake routes".

  # You can have the root of your site routed with "root"
  root 'items#index'

  # Example of regular route:
     get 'products/:id' => 'catalog#view'

  # Example of named route that can be invoked with purchase_url(id: product.id)
     get 'products/:id/purchase' => 'catalog#purchase', as: :purchase

  # Example resource route (maps HTTP verbs to controller actions automatically):
  #   resources :products

  # Example resource route with options:
  #   resources :products do
  #     member do
  #       get 'short'
  #       post 'toggle'
  #     end
  #
  #     collection do
  #       get 'sold'
  #     end
  #   end

  # Example resource route with sub-resources:
  #   resources :products do
  #     resources :comments, :sales
  #     resource :seller
  #   end

  # Example resource route with more complex sub-resources:
  #   resources :products do
  #     resources :comments
  #     resources :sales do
  #       get 'recent', on: :collection
  #     end
  #   end

  # Example resource route with concerns:
  #   concern :toggleable do
  #     post 'toggle'
  #   end
  #   resources :posts, concerns: :toggleable
  #   resources :photos, concerns: :toggleable

  # Example resource route within a namespace:
  #   namespace :admin do
  #     # Directs /admin/products/* to Admin::ProductsController
  #     # (app/controllers/admin/products_controller.rb)
  #     resources :products
  #   end
end

Can you let me know if you have advise.

Thanks

1 Answer

Jay McGavren
STAFF
Jay McGavren
Treehouse Teacher

Hi, Anastasios Christopoulos ,

This is a good start! If I were doing this, I would probably create a Booking model that has_many :items. You can add an attribute to a model with a type of date or datetime to store a date. Try this (either in your main app or a separate test app) to see some example code, complete with a date/time picker:

bin/rails g scaffold Booking date:datetime