Je suis assez nouveau pour Rails et j'ai essayé de résoudre ça toute la nuit sans succès.
J'ai créé 3 modèles: users
, businesses
et business_hours
. J'ai également ajouté les associations (business_hours belongs_to businesses which belongs_to users
) et (user has_one business which has_many business_hours
).
En lisant les documents en ligne, il semble que je dois maintenant créer les clés étrangères pour ces relations dans mes tables de base de données. Comment faire cela en utilisant Rails Migrations ActiveRecord? J'utilise PostgreSQL comme base de données.
Tout d'abord, lorsque vous utilisez la méthode Appartient à, n'utilisez pas s
à la fin du mot: business_hours belongs_to business which belongs_to user
.
Créez maintenant une migration:
Rails generate migration migration_name
Et dans la migration, ajoutez des colonnes:
class MigrationName < ActiveRecord::Migration
def change
add_foreign_key :business_hours, :businesses
add_foreign_key :businesses, :users
end
end
Courir rake db:migrate
. C'est ça.
La réponse actuellement acceptée à ce sujet n'est pas vraiment exacte car elle n'ajoute pas de clé étrangère de base de données. Il s'agit simplement d'ajouter des colonnes entières.
Dans Rails 4.2.x , l'approche actuelle est la suivante:
http://guides.rubyonrails.org/active_record_migrations.html#foreign-keys
Créez une migration:
Rails generate migration migration_name
Pour les colonnes existantes , dans la migration, ajoutez les clés étrangères comme ceci:
class MigrationName < ActiveRecord::Migration
def change
add_foreign_key :business_hours, :businesses
add_foreign_key :businesses, :users
end
end
Pour Rails 4.x ou si vous ajoutez une nouvelle colonne et que ce soit une clé étrangère, vous pouvez le faire, où vous voudrez probablement aussi spécifier l'index comme vrai, mais cela ne fait pas partie de l'exigence pour la clé étrangère:
http://edgeguides.rubyonrails.org/active_record_migrations.html#creating-a-migration
class MigrationName < ActiveRecord::Migration
def change
add_reference :business_hours, :business, index: true, foreign_key: true
add_reference :businesses, :user, index: true, foreign_key: true
end
end
Je ne l'ai pas essayé avec PostgreSQL mais au moins avec MySQL Rails NE PAS créer de clés étrangères, je veux dire pas de vraies clés étrangères de niveau db. Tout ce qu'elles créent est un entier qui est nommé d'après Cela signifie que hors de la boîte, vous n'obtenez pas l'index sur cette fausse clé étrangère (pour une recherche plus rapide) et il n'y a pas non plus de vérification d'intégrité référentielle au niveau db. Pour obtenir cela, vous devez faire quelque chose comme:
ALTER TABLE your_table ADD CONSTRAINT fk_whatever_you_want_to_name_it FOREIGN KEY (foreign_key_name) REFERENCES another_table(its_primary_key)
Dans une migration Rails vous pouvez passer ceci comme un argument de chaîne à la fonction "exécuter". L'ajout d'une "vraie" clé étrangère crée également automatiquement un index. Au moins pour moi, c'était plutôt désagréable surprise.
Rails 5 peut désormais ajouter une clé étrangère dans les migrations, voir http://devdocs.io/Rails~5.0/activerecord/connectionadapters/schemastatements#method-i-add_foreign_key . Alors
add_foreign_key :articles, :authors
crée
ALTER TABLE "articles" ADD CONSTRAINT fk_Rails_e74ce85cbc FOREIGN KEY ("author_id") REFERENCES "authors" ("id")
Si vous avez un modèle de données non standard, vous pouvez le faire.
add_foreign_key :articles, :users, column: :author_id, primary_key: "lng_id"
ce qui crée
ALTER TABLE "articles" ADD CONSTRAINT fk_Rails_58ca3d3a82 FOREIGN KEY ("author_id") REFERENCES "users" ("lng_id")