Bonjour à tous,
En gros, je souhaiterais commencer un projet très simple pour apprendre RoR. Mais même avec un projet très simple, j'ai déjà un problème. Je pense que le plus efficace est de citer une à une chaque étape et de vous présenter le problème lorsqu'il survient...
Ma base de données test contient 2 tables. Schématiquement, mes tables sont liées comme ceci :
Afin d'être le plus clair possible, voici le dump de l'ensemble :users (1,1) -> (0,*) homes
Et voici un apperçu de mes 2 tables à ce stade.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18 CREATE TABLE `homes` ( `id` int(11) NOT NULL auto_increment, `name` varchar(32) NOT NULL, PRIMARY KEY (`id`), UNIQUE KEY `name` (`name`) ) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=2 ; INSERT INTO `homes` (`id`, `name`) VALUES (1, 'Blue home'); CREATE TABLE `users` ( `id` int(11) NOT NULL auto_increment, `name` varchar(32) NOT NULL, `home_id` int(11) NOT NULL, PRIMARY KEY (`id`), UNIQUE KEY `name` (`name`) ) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=2 ; INSERT INTO `users` (`id`, `name`, `home_id`) VALUES (1, 'Jo', 1);
- homes
id name
1 MyHome- users
id name home_id
1 Jo 1
Jusque là, tout va bien en fait. Voici ensuite les commandes que j'exécute :
Code : Sélectionner tout - Visualiser dans une fenêtre à part home:~/www/rails cyril$ rails testMon projet est crée. Je l'ouvre.create
create app/controllers
create app/helpers
create app/models
create app/views/layouts
create config/environments
create components
create db
create doc
create lib
create lib/tasks
create log
create public/images
create public/javascripts
create public/stylesheets
create script/performance
create script/process
create test/fixtures
create test/functional
create test/integration
create test/mocks/development
create test/mocks/test
create test/unit
create vendor
create vendor/plugins
create tmp/sessions
create tmp/sockets
create tmp/cache
create Rakefile
create README
create app/controllers/application.rb
create app/helpers/application_helper.rb
create test/test_helper.rb
create config/database.yml
create config/routes.rb
create public/.htaccess
create config/boot.rb
create config/environment.rb
create config/environments/production.rb
create config/environments/development.rb
create config/environments/test.rb
create script/about
create script/breakpointer
create script/console
create script/destroy
create script/generate
create script/performance/benchmarker
create script/performance/profiler
create script/process/reaper
create script/process/spawner
create script/runner
create script/server
create script/plugin
create public/dispatch.rb
create public/dispatch.cgi
create public/dispatch.fcgi
create public/404.html
create public/500.html
create public/index.html
create public/favicon.ico
create public/robots.txt
create public/images/rails.png
create public/javascripts/prototype.js
create public/javascripts/effects.js
create public/javascripts/dragdrop.js
create public/javascripts/controls.js
create public/javascripts/application.js
create doc/README_FOR_APP
create log/server.log
create log/production.log
create log/development.log
create log/test.log
Maintenant, j'édite le fichier database.yml.
Code : Sélectionner tout - Visualiser dans une fenêtre à part home:~/www/rails cyril$ cd test/
Ma base de données est maintenant accessible par RoR. De plus, elle est conforme aux conventions de RoR :
Code : Sélectionner tout - Visualiser dans une fenêtre à part home:~/www/rails/test cyril$ vi config/database.yml
- les clefs primaires sont nommées id ;
- la clef étrangère de la table users se nomme home_id ;
- les tables sont au pluriel.
Je demande donc à RoR de créer deux échaffaudages (un par table) :
- homes
Code : Sélectionner tout - Visualiser dans une fenêtre à part home:~/www/rails/test cyril$ ruby script/generate scaffold homeexists app/controllers/
exists app/helpers/
create app/views/homes
exists test/functional/
dependency model
exists app/models/
exists test/unit/
exists test/fixtures/
create app/models/home.rb
create test/unit/home_test.rb
create test/fixtures/homes.yml
create app/views/homes/_form.rhtml
create app/views/homes/list.rhtml
create app/views/homes/show.rhtml
create app/views/homes/new.rhtml
create app/views/homes/edit.rhtml
create app/controllers/homes_controller.rb
create test/functional/homes_controller_test.rb
create app/helpers/homes_helper.rb
create app/views/layouts/homes.rhtml
create public/stylesheets/scaffold.css- users
Code : Sélectionner tout - Visualiser dans une fenêtre à part home:~/www/rails/test cyril$ ruby script/generate scaffold userexists app/controllers/
exists app/helpers/
create app/views/users
exists test/functional/
dependency model
exists app/models/
exists test/unit/
exists test/fixtures/
create app/models/user.rb
create test/unit/user_test.rb
create test/fixtures/users.yml
create app/views/users/_form.rhtml
create app/views/users/list.rhtml
create app/views/users/show.rhtml
create app/views/users/new.rhtml
create app/views/users/edit.rhtml
create app/controllers/users_controller.rb
create test/functional/users_controller_test.rb
create app/helpers/users_helper.rb
create app/views/layouts/users.rhtml
identical public/stylesheets/scaffold.css
Bizarrement, d'après ce que j'ai pu lire comme information, il semblairait qu'il faille encore préciser, dans chaque modele, la relation affectée. J'ai donc entré pour le modèle Home :
Et j'ai ajouté ça :
Code : Sélectionner tout - Visualiser dans une fenêtre à part home:~/www/rails/test cyril$ vi app/models/home.rb
Puis pour le modèle User :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3 class Home < ActiveRecord::Base has_many :users endJ'y ai ajouté ça :
Code : Sélectionner tout - Visualiser dans une fenêtre à part home:~/www/rails/test cyril$ vi app/models/user.rb
Pour ma part, je trouve ça bizarre car RoR est censé ~comprendre~ tout via des conventions. En gros, RoR n'a besoin que du minimum de configuration possible. Pourtant, il semble nécessaire d'ajouter ces précisions malgré le fait que la structure de la base test l'indique implicitement.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3 class User < ActiveRecord::Base belongs_to :home end
Bref, c'est le 1er point qui pour moi est louche.
Ensuite, j'exécute le serveur Web.
Et aussitôt, je tape dans Firefox (pour ne pas le citer ) l'adresse : http://127.0.0.1:3000/users/new. Voici une copie de la source du formulaire affiché :
Code : Sélectionner tout - Visualiser dans une fenêtre à part home:~/www/rails/test cyril$ ruby script/server
Et là, je constate une 2ème bizarrerie : il n'y a pas d'entrée home_id.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8 <form action="/users/create" method="post"> <!--[form:user]--> <p><label for="user_name">Name</label><br/> <input id="user_name" name="user[name]" size="30" type="text" value="" /></p> <!--[eoform:user]--> <input name="commit" type="submit" value="Create" /> </form>
Du coup, si je remplie ce formulaire dans mon navigateur (avec par exemple la chaîne "mike" pour le champ name), après la soumission, je m'apperçoie que dans la table users de ma base de données, la valeur du champ home_id de l'occurrence que je viens d'ajouter est égale à 0. Là ça devient plus que louche et la relation ne peut pas fonctionner (car aucune occurrence de la table homes n'a de champ id égal à 0, donc y'aura jamais de liaison entre mes 2 tables).
Afin d'être aussi clair que possible, voici un 2ème apperçu de mes 2 tables à ce stade.
- homes
id name
1 MyHome- users
id name home_id
1 Jo 1
2 Mike 0
On y voit la dernière ligne où le bug a été mit en rouge.
Bref, si vous avez une idée pour m'aider à le corriger, ça serait parfait.
Désolé, c'était un peu long.
Merci en tout cas pour votre aide
Partager