Forum: Italian Ruby user group Oggetti "composti"

Posted by Silvio Dell'Oste (silviodel)
on 2011-12-28 19:33
piano piano sto leggendo il libro agile web development with rails ma mi
pare di allontanarmi sempre più da quello che dovrei fare :(

tra partial e simboli mi sto perdendo e non riesco neanche a fare (beh a
meno che non è realmente difficile) una vista con oggetti "composti"...

esempio?

un utente che ha tra i suoi parametri nome, cognome e per esempio
indirizzo (che è una classe a parte)

ho fatto le associazioni e creato le viste... per lo show non ho
moltissimi problemi, che invece vengono con l'edit, il destroy e la
new...

credo che il problema sia nei controller... diciamo che mi basterebbe
sapere come manipolare nei form i campi di tipo Address gestiti nelle
pagine di inserimento, modifica e distruzione di User che ha un campo
Address...

ecco il mio ultimo codice... ovviamente spara errori a raffica...

il modello User has_one :address e Address belongs_to :user

Vista per il new:
<h1>Inserisci un nuovo utente</h1>

<% form_for(@user) do |f| %>
  <%= f.error_messages %>

<p>
    <%= f.label :nick %><br />
    <%= f.text_field :nick %>
  </p>
<p>
    <%= f.label :nome %><br />
    <%= f.text_field :nome %>
  </p>
  <p>
    <%= f.label :cognome %><br />
    <%= f.text_field :cognome %>
  </p>
  <p>
    <%= f.label :email %><br />
    <%= f.text_field :email %>
  </p>



  <% f.fields_for @address do |address_fields| %>
       via  : <%= address_fields.text_field :indirizzo %>
        citta: <%= address_fields.text_field :citta %>
      <%# end %>
     <% end %>



  <p>
    <%= f.submit 'Crea' %>
  </p>
<% end %>

<%= link_to 'Indietro', users_path %>

Vista per l'edit (ci sono un sacco di cose commentate.. sono le
prove...)
<h1>Modifica utente</h1>

<% form_for(@user) do |f| %>
  <%= f.error_messages %>

<p>
    <%= f.label :nome %><br />
    <%= f.text_field :nome %>
  </p>
<p>
    <%= f.label :cognome %><br />
    <%= f.text_field :cognome %>
  </p>

  <p>
    <%= f.label :email %><br />
    <%= f.text_field :email %>
  </p>

  <p>
    <%= f.label :nick %><br />
    <%= a= :nick

    #nome=@user.nome
    #text=@user.nome
    %>
    lll
    <%= f.text_field :nick %>
  </p>

  <%# form_for @person, :url => { :action => "update" } do |person_form|
%>
    <%# person_form.fields_for :address do |address_fields| %>
  <% f.fields_for :address do |address_fields| %>
       Street  : <%= address_fields.text_field :indirizzo %>
        Zip code: <%= address_fields.text_field :citta %>
      <%# end %>
     <% end %>


   <%#*<p>%>
    <%#= f.label :indirizzo %><br />
    <%#= f.text_field :address %>
  <%#*</p>%>

   <%#*<p>%>
    <%#= f.label :citta %><br />
    <%#= f.text_field :citta %>
  <%#*</p>%>

    <p>
    <b>Indirizzo:</b>
    <%= @user.address.indirizzo if @user.address!=nil%>
    <b>-</b>
    <%= @user.address.citta if @user.address!=nil%>
    <%#= t.label :@user.address.citta %>
  </p>
 <%#= @addr.citta %>


    <%# for @address in @user.address %>
  <%#= error_messages_for :address %>
  <%# fields_for "address[]" do |f| %>
    <%#*<p><%= f.text_field :name %></p>%>
  <%# end %>
<%# end %>


    <fieldset>
<legend>Territorio di competenza<legend>
  <%# fields_for :address do |t| %>

  <%#*<p>%>
  <%#= t.label :carica %>
  <%#= t.text_field :carica%>
  <%#*</p>%>

    <%#= @address=@address[0] %>
    <%#= @address %>

  <%#*<p>%>
  <%#= t.label :indirizzo %>
  <%#= t.text_field :indirizzo%>
  <%#*</p>%>

  <%#*<p>%>
  <%#= t.label :citta %>
  <%#= t.text_field :citta%>
  <%#*</p>%>

  <%# end %>

</fieldset>




  <p>
    <%= f.submit 'Aggiorna' %>
  </p>
<% end %>

<%= link_to 'Mostra', @user %> |
<%= link_to 'Indietro', users_path %>



Controller:

class UsersController < ApplicationController
  def index
    @users = User.all

    respond_to do |format|
      format.html # index.html.erb
      format.xml  { render :xml => @users }
    end
  end

  def show
    @user = User.find(params[:id])
    @address = Address.find(:all, :conditions => ['user_id = ?',
@user.id])

    respond_to do |format|
      format.html # show.html.erb
      format.xml  { render :xml => @user }
    end
  end

  def new
    @user = User.new
    @address = Address.new

    respond_to do |format|
      format.html # new.html.erb
      format.xml  { render :xml => @user }
    end
  end

  # GET /users/1/edit
  def edit
    @user = User.find(params[:id])

#    @address = @user.address
@address = Address.find_by_sql("select * from users, addresses " + "
where user_id = users.id ")

  end

  def create
    @user = User.new(params[:user])
@address = Address.new(params[:address])
#    @address = @user.address[0].build(params[:address])

    User.transaction do
@address.save!
@user.address = @address
@user.save!
redirect_to :action => :show, :id => @user
end
rescue ActiveRecord::RecordInvalid => e
@address.valid? # force checking of errors even if products failed
render :action => :new
#end



    respond_to do |format|
      if @user.save
        format.html { redirect_to(@user, :notice => 'Utente creato con
successo') }
        format.xml  { render :xml => @user, :status => :created,
:location => @user }
      else
        format.html { render :action => "new" }
        format.xml  { render :xml => @user.errors, :status =>
:unprocessable_entity }
      end
    end
  end

  def update
    @user = User.find(params[:id])

    @address = @user.address

    respond_to do |format|
      if @user.update_attributes(params[:user])
        format.html { redirect_to(@user, :notice => 'Modifica effettuata
con successo.') }
        format.xml  { head :ok }
      else
        format.html { render :action => "edit" }
        format.xml  { render :xml => @user.errors, :status =>
:unprocessable_entity }
      end
    end
  end

  def destroy
    @user = User.find(params[:id])
    @user.destroy

    respond_to do |format|
      format.html { redirect_to(users_url) }
      format.xml  { head :ok }
    end
  end



end

grazie a tutti voi che mi sopportate :(
Posted by Silvio Dell'Oste (silviodel)
on 2011-12-29 10:12
aiutino... please :(
Posted by Luca Barone (cloud-walker)
on 2011-12-29 10:16
(Received via mailing list)
io non saprei proprio cosa dirti xD sono ancora ai primi capitoli del
libro, sono messo peggio di te T_T

Il giorno 29 dicembre 2011 10:12, Silvio Dell'Oste
<silviodel@infinito.it>ha scritto:
Posted by Paolo Perego (Guest)
on 2011-12-29 10:23
(Received via mailing list)
2011/12/28 Silvio Dell'Oste <silviodel@infinito.it>
[snip]

 ecco il mio ultimo codice... ovviamente spara errori a raffica...
>
[snip]
Suggerimenti che non c'entrano col tuo codice ma che aiutano nel
troubleshooting in generale:
a) usiamo gist/pastebin per incollare codice... aiuta nella lettura 
della
email
b) posta anche l'errore che ti da cos possiamo darti una mano.

[1]https://gist.github.com/
[2]http://pastebin.com/

HTH

--
"... static analysis is fun, again!"

life from an application security guy ~> http://thesp0nge.com
Posted by Matteo Canato (Guest)
on 2011-12-29 10:44
(Received via mailing list)
Credo che ti convenga dare un occhiata alla serie di RailsCasts sui
nested model TI giro i link degli asciicast.

http://railscasts.com/episodes/196-nested-model-fo...
http://railscasts.com/episodes/197-nested-model-fo...

MC


Il 29 dicembre 2011 10:22, Paolo Perego <thesp0nge@gmail.com> ha 
scritto:
> b) posta anche l'errore che ti da cos possiamo darti una mano.
> _______________________________________________
> Ml mailing list
> Ml@lists.ruby-it.org
> http://lists.ruby-it.org/mailman/listinfo/ml



--
Matteo Canato
Ufficio Reti e Sistemi
Universit degli Studi di Ferrara
Tel. 0532 97 4153
Posted by Silvio Dell'Oste (silviodel)
on 2011-12-29 12:06
ecco qua l'errore...

git://gist.github.com/1533515.git

ActiveRecord::AssociationTypeMismatch in UsersController#create

Address(#3524) expected, got HashWithIndifferentAccess(#3526)

RAILS_ROOT: 
C:/Users/Silvio/Documents/NetBeansProjects/RailsApplicationSilvio
Application Trace | Framework Trace | Full Trace

C:/Program Files/NetBeans 
6.9.1/ruby/jruby-1.5.1/lib/ruby/gems/1.8/gems/activerecord-2.3.8/lib/active_record/associations/association_proxy.rb:259:in 
`raise_on_type_mismatch'
C:/Program Files/NetBeans 
6.9.1/ruby/jruby-1.5.1/lib/ruby/gems/1.8/gems/activerecord-2.3.8/lib/active_record/associations/has_one_association.rb:55:in 
`replace'
C:/Program Files/NetBeans 
6.9.1/ruby/jruby-1.5.1/lib/ruby/gems/1.8/gems/activerecord-2.3.8/lib/active_record/associations.rb:1287:in 
`address='
C:/Program Files/NetBeans 
6.9.1/ruby/jruby-1.5.1/lib/ruby/gems/1.8/gems/activerecord-2.3.8/lib/active_record/base.rb:2906:in 
`assign_attributes'
C:/Program Files/NetBeans 
6.9.1/ruby/jruby-1.5.1/lib/ruby/gems/1.8/gems/activerecord-2.3.8/lib/active_record/base.rb:2902:in 
`each'
C:/Program Files/NetBeans 
6.9.1/ruby/jruby-1.5.1/lib/ruby/gems/1.8/gems/activerecord-2.3.8/lib/active_record/base.rb:2902:in 
`assign_attributes'
C:/Program Files/NetBeans 
6.9.1/ruby/jruby-1.5.1/lib/ruby/gems/1.8/gems/activerecord-2.3.8/lib/active_record/base.rb:2775:in 
`attributes='
C:/Program Files/NetBeans 
6.9.1/ruby/jruby-1.5.1/lib/ruby/gems/1.8/gems/activerecord-2.3.8/lib/active_record/base.rb:2473:in 
`initialize'
C:/Users/Silvio/Documents/NetBeansProjects/RailsApplicationSilvio/app/controllers/users_controller.rb:61:in 
`new'
C:/Users/Silvio/Documents/NetBeansProjects/RailsApplicationSilvio/app/controllers/users_controller.rb:61:in 
`create'

Request

Parameters:

{"authenticity_token"=>"iXQRCyle/pQSb/FEPcg1H8DU8HE/9EdGOnCZ9v/xAyk=",
"user"=>{"nick"=>"",
"nome"=>"",
"cognome"=>"",
"email"=>"",
"address"=>{"indirizzo"=>"",
"citta"=>""}},
"commit"=>"Crea"}

Matteo Canato wrote in post #1038664:
> Credo che ti convenga dare un occhiata alla serie di RailsCasts sui
> nested model TI giro i link degli asciicast.
>
> 
http://railscasts.com/episodes/196-nested-model-fo...
> 
http://railscasts.com/episodes/197-nested-model-fo...
>
> MC
>
>

purtroppo ho già visto quelle lezioni... così come quelle vecchie 
(73-74-75) ma mi hanno solo confuso le idee introducendo cose nuove... 
tipo i partial che ancora non comprendo a pieno (anche se ho capito a 
cosa servono)

io per ora vorrei solo sapere come si fa a modificare, inserire e 
distruggere oggetti "multipli" in una sola vista... ovvero avere nella 
stessa pagina la possibilità di manipolare i dati dell'utente e il 
relativo indirizzo nel mio esempio...

diciamo che mi basterebbe capire forse come funzionano i simboli... dato 
che nel form_for su @users se scrivo

 <%= f.label :nome %><br />
    <%= f.text_field :nome %>

tutto funziona alla grande... ma ovviamente non posso scrivere 
:indirizzo, potrei scrivere :address ma non avrebbe senso... ma non 
posso scrivere qualcosa del tipo :address.indirizzo o qualcosa del 
genere...

quindi faccio

fields_for @address do |address_fields| %>
       Street  : <%= address_fields.text_field :indirizzo %>
        Zip code: <%= address_fields.text_field :citta %>
      <% end %>

ma poi l'azione è sempre su @user... quindi dovrei forse passare anche 
@address e modificare il controller...

grazie a tutti
Posted by Silvio Dell'Oste (silviodel)
on 2011-12-29 20:57
risolto... anche se... con la magina :(

nel senso che ho usato accepts_nested_attributes_for che esiste da non 
so quanto... precedentemente immagino che si doveva scrivere qualcosa...

comunque posto il codice così se qualcuno dovesse avere lo stesso 
problema risolve...

https://gist.github.com/1535921
<script src="https://gist.github.com/1535921.js"> </script>

user.rb

class User < ActiveRecord::Base
has_one :address, :dependent => :destroy

  validates_presence_of :nome, :nick, :cognome, :message => "è un campo 
obbligatorio"
  validates_uniqueness_of :nick, :message => "è un camppo univoco, 
ripeti inserendo un nuovo nick"

  accepts_nested_attributes_for :address, :allow_destroy => true

end

new.html.erb

<h1>Inserisci un nuovo utente</h1>

<% form_for(@user) do |f| %>
<%= f.error_messages %>

<p>
<%= f.label :nick %><br />
    <%= f.text_field :nick %>
</p>
<p>
<%= f.label :nome %><br />
    <%= f.text_field :nome %>
</p>
<p>
<%= f.label :cognome %><br />
    <%= f.text_field :cognome %>
</p>
<p>
<%= f.label :email %><br />
    <%= f.text_field :email %>
</p>


<fieldset>
<p>Indirizzo
<% f.fields_for :address do |address_fields| %>
<p> Via : <%= address_fields.text_field :indirizzo %> </p>
      <p> Città: <%= address_fields.text_field :citta %> </p>
<% end %>
</p>
</fieldset>



<p>
<%= f.submit 'Crea' %>
</p>
<% end %>

<%= link_to 'Indietro', users_path %>

address.rb
class Address < ActiveRecord::Base
  belongs_to :user

end

user_controller.rb

class UsersController < ApplicationController
  # GET /users
  # GET /users.xml
  def index

    @users = User.all

    respond_to do |format|
      format.html # index.html.erb
      format.xml { render :xml => @users }
    end
  end

  # GET /users/1
  # GET /users/1.xml
  def show
    @user = User.find(params[:id])

    @address=@user.address

    respond_to do |format|
      format.html # show.html.erb
      format.xml { render :xml => @user }
    end
  end

  # GET /users/new
  # GET /users/new.xml
  def new
    @user = User.new

      @address=@user.build_address
    respond_to do |format|
      format.html # new.html.erb
      format.xml { render :xml => @user }
    end
  end

  # GET /users/1/edit
  def edit
    @user = User.find(params[:id])
    @address=@user.address

  end

  # POST /users
  # POST /users.xml
  def create
    @user = User.new(params[:user])

      if @user.save
            redirect_to :action => 'show', :id => @user
            flash[:notice] = "Your record has been saved."
      else
            render :action => 'new'
      end


  end

  # PUT /users/1
  # PUT /users/1.xml
  def update
    @user = User.find(params[:id])



    respond_to do |format|
      if @user.update_attributes(params[:user])
        format.html { redirect_to(@user, :notice => 'Modifica effettuata 
con successo.') }
        format.xml { head :ok }
      else
        format.html { render :action => "edit" }
        format.xml { render :xml => @user.errors, :status => 
:unprocessable_entity }
      end
    end
  end

  # DELETE /users/1
  # DELETE /users/1.xml
  def destroy
    @user = User.find(params[:id])
    @user.destroy

    respond_to do |format|
      format.html { redirect_to(users_url) }
      format.xml { head :ok }
    end
  end
end
Please log in before posting. Registration is free and takes only a minute.
Existing account (Switch to SSL-encrypted connection)
NEW: Do you have a Google/GoogleMail or Yahoo account? No registration required!
Log in with Google account | Log in with Yahoo account
No account? Register here.