如何判断 ActiveRecord "where"方法是否创建了新行,还是获取了现有行?



如何判断以下代码是创建了新记录,还是返回了现有记录?我假设where方法在这里创建一个新用户(如果不存在的话)。

# Create User Model Instance
user = User.where(:provider => auth["provider"], :uid => auth["uid"]).first_or_initialize(
  :refresh_token => auth["credentials"]["refresh_token"],
  :access_token => auth["credentials"]["token"],
  :expires => Time.at(auth["credentials"]["expires_at"]).to_datetime,
  :expires_str => auth["credentials"]["expires_at"],
  :name => auth["info"]["name"],
)
# Save User
if user.save
  session[:user_id] = user.id
  notice = "Signed in!"
  logger.debug "URL to redirect to: #{url}"
  redirect_to url, :notice => notice
else
  raise "Failed to login"
end

我假设where方法在这里创建一个新用户(如果不存在的话)。

这是错误的。where永远不会创建新行,它只用于查询记录。

其工作方式是,first_or_initialize找到第一个匹配的记录,或者如果没有找到新的未保存的记录,则实例化该记录。在这种情况下,数据库中还没有新的记录。

接下来,您调用user.save!在记录不存在的情况下创建该记录。where与该唱片的创作无关。

至于判断ActiveRecord对象是来自数据库还是仅存在于内存中,您正在寻找persisted?。如果对象尚未保存到数据库中,则返回false。

# Create User Model Instance
user = User.where(:provider => auth["provider"], :uid => auth["uid"]).first_or_initialize(
  :refresh_token => auth["credentials"]["refresh_token"],
  :access_token => auth["credentials"]["token"],
  :expires => Time.at(auth["credentials"]["expires_at"]).to_datetime,
  :expires_str => auth["credentials"]["expires_at"],
  :name => auth["info"]["name"],
)
# At this point, if user.persisted? is true, the user was found in the database.
# The below call to `save` will update the record.
# OR
# If false, the user doesn't exist in the database yet.
# The below call to save will insert the record
# Save User
if user.save
  session[:user_id] = user.id
  notice = "Signed in!"
  logger.debug "URL to redirect to: #{url}"
  redirect_to url, :notice => notice
else
  raise "Failed to login"
end

最新更新