2

我想修改 Devise 以使其与带有 PostgreSQL 的 UUID 主键的用户表一起使用。

这是迁移:

class DeviseCreateUsers < ActiveRecord::Migration

  def change
    create_table :users, id: false do |t|
      t.uuid :uuid, null: false
      # ...
    end

    change_table :users do |t|
      t.index :uuid, unique: true
      # ...
    end
  end

  def migrate(direction)
    super
    if direction == :up
      # This is only necessary because the following does not work:
      # t.uuid :uuid, primary: true, null: false
      execute "ALTER TABLE users ADD PRIMARY KEY (uuid);"
    end
  end
end

这是User模型:

class User < ActiveRecord::Base

  primary_key = :uuid

  devise :database_authenticatable, :recoverable, :registerable,
    :rememberable, :trackable, :validatable

  validates :uuid, presence: true
  before_validation :ensure_uuid
  def ensure_uuid; self.uuid ||= SecureRandom.uuid end

end

这是错误:

PG::Error: ERROR:  operator does not exist: uuid = integer
LINE 1: ...ECT  "users".* FROM "users"  WHERE "users"."uuid" = 1  ORDER...
                                                             ^
HINT:  No operator matches the given name and argument type(s). You might need to add explicit type casts.
: SELECT  "users".* FROM "users"  WHERE "users"."uuid" = 1  ORDER BY "users"."uuid" ASC LIMIT 1

Extracted source (around line #5):

1    .navbar-inner
2      .container
3        = a_nav_tag "App", root_path
4        - if user_signed_in?
5          %ul.nav.pull-right
6            %li.dropdown#user_menu
7              %a.dropdown-toggle(data-toggle="dropdown" href="#")

如您在上面看到的,user_signed_in?已损坏。我预计从“正常”自动递增 ID 到 UUID 需要进行一些更改。

现在,我只是发布问题。我将在今天晚些时候对此进行讨论。如果您碰巧知道如何做到这一点——或者知道 Devise fork,我将不胜感激。

4

3 回答 3

10

我在 Rails 4 中通过在创建表时将 id 列设置为 uuid 数据类型来完成此操作,并且没有任何其他配置更改。IE。不要创建名为“uuid”的列,只需将“id”列的类型更改为 uuid。

于 2013-04-14T12:02:53.067 回答
3

只需清除 Web 应用程序的浏览器 cookie(在我的例子中是localhost)。上面的错误是因为会话保留了旧用户主键,1.

在那之后,事情在我的测试中起作用。我希望这不仅仅是运气,如果 Devise 不知道主键,这将是一个很好的设计。(在 Devise 的代码中,我发现在某些测试中没有使用.idexcept。)

于 2013-04-13T22:16:30.207 回答
2

2020年答案:

创建用户表时,将ID设置为uuid

def change
  enable_extension 'pgcrypto' # needed if not already enabled 
  create_table :users, id: :uuid do |t|
    t.string :email,
    ...
于 2020-06-28T12:20:59.310 回答