How to get this one-to-one assoication working? - ruby-on-rails

I've created a one-to-one association between my Admin and Report models and it isn't working just yet. I'm using Devise to log in via an Admin model so in the controller I'm using the current_admin helper. Silly question, but what migration do I need to run to get this working?
Error
ActiveRecord::StatementInvalid (PGError: ERROR: column reports.admin_id does not exist
2011-10-14T09:16:57+00:00 app[web.1]: LINE 1: SELECT "reports".* FROM "reports" WHERE ("reports".admin_id = ...
Report model
belongs_to :admin, :foreign_key => "admin_id"
Admin model
has_one :report, :foreign_key => "admin_id"
Controller
#report = current_admin.report
Schema
create_table "reports", :force => true do |t|
t.string "name"
t.string "description"
t.datetime "created_at"
t.datetime "updated_at"
t.string "user_id"
end
create_table "admins", :force => true do |t|
t.string "email", :default => "", :null => false
t.string "encrypted_password", :limit => 128, :default => "", :null => false
t.string "reset_password_token"
t.datetime "reset_password_sent_at"
t.datetime "remember_created_at"
t.integer "sign_in_count", :default => 0
t.datetime "current_sign_in_at"
t.datetime "last_sign_in_at"
t.string "current_sign_in_ip"
t.string "last_sign_in_ip"
t.datetime "created_at"
t.datetime "updated_at"
end

You need admin_id in reports. You can remove the foreign_key stuff in your models. That's done automatically. Create a migration, add
add_column :reports, :admin_id, :integer
Run rake db:migrate and you're done.

Related

Why ActiveRecord::StatementInvalid: SQLite3::SQLException: near ")": syntax error: INSERT INTO "user_friendships" () VALUES ()

Why Why ActiveRecord::StatementInvalid: SQLite3::SQLException: near ")": syntax error: INSERT INTO "user_friendships" () VALUES ()
When trying to test:
$ ruby -I test test/unit/user_friendships_test.rb
require 'test_helper'
class UserFriendshipsTest < ActiveSupport::TestCase
should belong_to (:user)
should belong_to (:friend)
test "that creating a frinedship works without raising an exception" do
assert_nothing_raised do
UserFriendship.create user: users(:a), friend: friends(:b)
end
end
end
Any idea?
UPDATE: his is part of the Schema.rb
create_table "user_friendships", :force => true do |t|
t.integer "user_id"
t.integer "friend_id"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
add_index "user_friendships", ["user_id", "friend_id"], :name => "index_user_friendships_on_user_id_and_friend_id"
create_table "users", :force => true do |t|
t.string "first_name"
t.string "last_name"
t.string "profile_name"
t.string "email", :default => "", :null => false
t.string "encrypted_password", :default => "", :null => false
t.string "reset_password_token"
t.datetime "reset_password_sent_at"
t.datetime "remember_created_at"
t.integer "sign_in_count", :default => 0, :null => false
t.datetime "current_sign_in_at"
t.datetime "last_sign_in_at"
t.string "current_sign_in_ip"
t.string "last_sign_in_ip"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
add_index "users", ["email"], :name => "index_users_on_email", :unique => true
add_index "users", ["reset_password_token"], :name => "index_users_on_reset_password_token", :unique => true
end
I ran into this as well. It seems to be related to screwing up the rails naming conventions. In my case, doing "rails g model activity_item" instead of "rails g model activity_items" solved the issue.

Migrations were shown as down but already migrated?

I've rails app that has some migrations. When I hit rake db:migrate:status to see what status is set, all except ********** NO FILE ********** were down. But the migrations have already made, so there seems no problem about model side. Here are files may help to explain:
Output of rake db:migrate:status:
up 20130727003912 ********** NO FILE **********
down 20130728000151 Devise create users
down 20130728000335 Create friends
down 20130728000346 Create addresses
down 20130728000356 Create authies
down 20130728000413 Add indexes
At this time, rake db:migrate output:
== DeviseCreateUsers: migrating ==============================================
-- create_table(:users)
NOTICE: CREATE TABLE will create implicit sequence "users_id_seq1" for serial column "users.id"
rake aborted!
An error has occurred, this and all later migrations canceled:
PG::DuplicateTable: ERROR: relation "users" already exists
: CREATE TABLE "users" ("id" serial primary key, "username" character varying(255), "email" character varying(255) DEFAULT '' NOT NULL, "encrypted_password" character varying(255) DEFAULT '' NOT NULL, "reset_password_token" character varying(255), "reset_password_sent_at" timestamp, "remember_created_at" timestamp, "sign_in_count" integer DEFAULT 0, "current_sign_in_at" timestamp, "last_sign_in_at" timestamp, "current_sign_in_ip" character varying(255), "last_sign_in_ip" character varying(255), "created_at" timestamp NOT NULL, "updated_at" timestamp NOT NULL) /home/ekrem/workspace/contactman/db/migrate/20130728000151_devise_create_users.rb:3:in `change'
Tasks: TOP => db:migrate
(See full trace by running task with --trace)
db/schema.rb:
ActiveRecord::Schema.define(:version => 20130727003912) do
create_table "addresses", :force => true do |t|
t.string "title"
t.text "address"
t.string "phone"
t.string "city"
t.integer "friend_id"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
t.string "slug"
t.string "country"
end
add_index "addresses", ["friend_id"], :name => "index_addresses_on_friend_id"
add_index "addresses", ["slug"], :name => "index_addresses_on_slug", :unique => true
create_table "authies", :force => true do |t|
t.string "provider"
t.string "uid"
t.integer "user_id"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
add_index "authies", ["user_id"], :name => "index_authies_on_user_id"
create_table "friends", :force => true do |t|
t.string "name"
t.string "surname"
t.integer "user_id"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
t.string "slug"
t.string "imported_file_name"
t.string "imported_content_type"
t.integer "imported_file_size"
t.datetime "imported_updated_at"
end
add_index "friends", ["slug"], :name => "index_friends_on_slug", :unique => true
add_index "friends", ["user_id"], :name => "index_friends_on_user_id"
create_table "users", :force => true do |t|
t.string "email", :default => "", :null => false
t.string "encrypted_password", :default => "", :null => false
t.string "reset_password_token"
t.datetime "reset_password_sent_at"
t.datetime "remember_created_at"
t.integer "sign_in_count", :default => 0
t.datetime "current_sign_in_at"
t.datetime "last_sign_in_at"
t.string "current_sign_in_ip"
t.string "last_sign_in_ip"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
t.string "username"
end
add_index "users", ["email"], :name => "index_users_on_email", :unique => true
add_index "users", ["reset_password_token"], :name => "index_users_on_reset_password_token", :unique => true
end
How can I fix this issue to make all migrations seem up?
Your users tables is already created in your database but your schema migration is not updated with latest migration. I dont no why it has not been updated. You need to fix it then you can do it in two ways 1. drop the database and create one more or 2. run the down migration then up migration
rake db:drop
rake db:create
rake db:migrate
You can set force to true:
create_table :users, force: true do
...
end
in your migration and delete the migration key in your "schema_migrations" table by hand and rerun the migration.
this worked perfectly for me:
rails db:drop
rails db:create
rails db:migrate
You will notice that the file developmen.sqlite3 was removed and created again and now everything will be up and running rails db:migrate:status

students and teachers in a class_instruction

Setting up the database, I am just curious if I did it correctly, as it looks a bit off. There are people, who have a user account, and a role (teacher or student). they are participants in a class (where a class has many students and teachers; a student has many classes; a teacher has many classes). I think my class_instruction model is off in the DB, but please tell me if it will work, or if there is a better way (like maybe with a has_many_through table of participants)
schema.rb:
ActiveRecord::Schema.define(:version => 20130524160107) do
create_table "class_instructions", :force => true do |t|
t.string "name"
t.datetime "time"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
t.integer "person_id"
end
add_index "class_instructions", ["person_id"], :name => "index_class_instructions_on_person_id"
create_table "people", :force => true do |t|
t.string "firstName"
t.string "lastName"
t.integer "user_id"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
add_index "people", ["user_id"], :name => "index_people_on_user_id"
create_table "roles", :force => true do |t|
t.string "name"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
create_table "user_roles", :force => true do |t|
t.integer "user_id"
t.integer "role_id"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
add_index "user_roles", ["role_id"], :name => "index_user_roles_on_role_id"
add_index "user_roles", ["user_id"], :name => "index_user_roles_on_user_id"
create_table "users", :force => true do |t|
t.string "email", :default => "", :null => false
t.string "encrypted_password", :default => "", :null => false
t.string "reset_password_token"
t.datetime "reset_password_sent_at"
t.datetime "remember_created_at"
t.integer "sign_in_count", :default => 0
t.datetime "current_sign_in_at"
t.datetime "last_sign_in_at"
t.string "current_sign_in_ip"
t.string "last_sign_in_ip"
end
add_index "users", ["email"], :name => "index_users_on_email", :unique => true
add_index "users", ["reset_password_token"], :name => "index_users_on_reset_password_token", :unique => true
end
My concern is that the person_id is part of the class. Is this correct?
ClassInsturction.rb :
class ClassInstruction < ActiveRecord::Base
belongs_to :people
has_many :cassignments
has_many :assignments, :through => :cassignments
def className
self.name
end
def classAssignments
return self.cassignments
end
end
I would make a joining table that has both class and people and use has many through. If people have many classes and classes have many people you can not do this any other way.
I have seen usually belongs_to with singular form:
belongs_to :person
I am not sure if this is what you are asking for though.

Rails Notifications of New Posts

I am developing a rails app where users can post, must like facebook. I want to implement a notification systems that alerts users to new posts. However, I am having trouble on how to tell if a user has viewed posts or not. I am literally clueless.
I am using devise gem which gives me access to certain user stats (if this helps):
create_table "users", :force => true do |t|
t.string "email", :default => "", :null => false
t.string "encrypted_password", :default => "", :null => false
t.string "reset_password_token"
t.datetime "reset_password_sent_at"
t.datetime "remember_created_at"
t.integer "sign_in_count", :default => 0
t.datetime "current_sign_in_at"
t.datetime "last_sign_in_at"
t.string "current_sign_in_ip"
t.string "last_sign_in_ip"
t.string "confirmation_token"
t.datetime "confirmed_at"
t.datetime "confirmation_sent_at"
t.string "unconfirmed_email"
t.integer "failed_attempts", :default => 0
t.string "unlock_token"
t.datetime "locked_at"
t.string "authentication_token"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
t.string "username", :default => "", :null => false
t.integer "admin", :default => 0
end
And my post model:
create_table "posts", :force => true do |t|
t.integer "user_id"
t.text "content"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
How can I implement a system that knows if a user has seen a post or not?
simple aproach would be like that:
create a model called Seen
rails g model Seen post:references user:references
models/seen.rb
belongs_to :user
belongs_to :post
models/user.rb
has_many :seens
has_many :seen_posts, through: :seens, source: :post
models/post.rb
has_many :seens
has_many :seen_users, through: :seens, source: :user
and you can create a method something like that
models/post.rb
def seen_by?(user)
seen_user_ids.include?(user.id)
end
controllers/posts_controller.rb
def show
#post = Post.find(params[:id])
current_user.seen_posts << #post unless #post.seen_by?(current_user)
end

Active Admin NoMethodError Error

Im setting up active admin on my rails app. I ran the generator to create the user resource but when i click on the users link on the admin dashboard i get:
NoMethodError in Admin/users#index
Showing /Users/nelsonkeating/.rvm/rubies/ruby-1.9.2-p290/lib/ruby/gems/1.9.1/gems/activeadmin-0.4.4/app/views/active_admin/resource/index.html.arb where line #1 raised:
undefined method `city_id_contains' for #<MetaSearch::Searches::User:0x007fde92d69840>
Extracted source (around line #1):
1: render renderer_for(:index)
I have no clue what is generating this or where the error is coming from.. Any ideas? Thanks! (please let me know if you need to see any other files)
Models:
user.rb
class User < ActiveRecord::Base
rolify
devise :database_authenticatable, :registerable, :confirmable,
:recoverable, :rememberable, :trackable, :validatable
attr_accessible :province_id, :city_id
belongs_to :province
belongs_to :city
province.rb
class Province < ActiveRecord::Base
has_many :cities
has_many :users
end
city.rb
class City < ActiveRecord::Base
belongs_to :province
has_many :users
end
schema.rb
create_table "users", :force => true do |t|
t.string "email", :default => "", :null => false
t.string "encrypted_password", :default => "", :null => false
t.string "reset_password_token"
t.datetime "reset_password_sent_at"
t.datetime "remember_created_at"
t.integer "sign_in_count", :default => 0
t.datetime "current_sign_in_at"
t.datetime "last_sign_in_at"
t.string "current_sign_in_ip"
t.string "last_sign_in_ip"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
t.string "name"
t.date "date_of_birth"
t.string "address"
t.string "gender"
t.integer "zipcode"
t.string "city"
t.string "status"
t.string "confirmation_token"
t.datetime "confirmed_at"
t.datetime "confirmation_sent_at"
t.string "unconfirmed_email"
t.integer "province_id"
t.integer "city_id"
end
create_table "provinces", :force => true do |t|
t.string "name"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
create_table "cities", :force => true do |t|
t.string "name"
t.integer "province_id"
t.datetime "created_at", :null => false
t.datetime "updated_at", :null => false
end
This question helped me solve my problem. I had to read the comments to figure out how to solve it so I am providing the answer here:
If you have a model that contains a belongs_to relationship, Active Admin will not like it if you have a column name that matches your belongs to foreign key id column name.
For instance in this case your foreign key is 'city_id' but you also have a column named 'city'. Active Admin doesn't like this. And likewise it really doesn't make sense to have that column to begin with. Since you will access the city through the relationship.
To fix this you should create a migration that removes the city column.
class RemoveCityFromUser < ActiveRecord::Migration
def up
remove_column :users, :city
end
end

Resources