在 Sequel Pro 中,使用以下语句创建了一个表:
CREATE TABLE dogs(
id INT PRIMARY KEY NOT NULL,
name TEXT,
color TEXT
);
*auto increment, under extra in structures, is checked so Sequel Pro generate primary keys automatically*
使用 mysql2,我在 ruby 文件 classdog.rb 中编写了 insert 方法,以将新狗插入到 Dogs 表中。
classdog.rb 的完整内容如下:
require 'mysql2'
require "debugger"
class Dog
attr_accessor :name, :color, :id,
@@db = Mysql2::Client.new(:host => '127.0.0.1', :username => 'root', :database => 'dogs')
def initialize(name, color)
@name = name
@color = color
end
def self.db
@@db
end
def db
@@db
end
def insert
db.query("INSERT INTO dogs(name, color) VALUE('#{name}', '#{color}')")
end
end
dog = Dog.new("simba", "grey")
puts dog.insert
为了检查我的代码是否正常工作,我创建了这个 rspec 文件:
require "./classdog"
describe Dog do
describe "#insert" do
it "should insert a dog into the database" do
dog = Dog.new("simba", "grey")
sql_command = "SELECT * FROM dogs WHERE name = '#{dog.name}'";
row_hash = {"id" => 1, "name" => "simba", "color" => "grey"}
expect(Dog.db.query(sql_command).first).to eq(row_hash)
end
end
end
当我使用以下命令在 ruby 中运行规范文件时:
rspec spec_classdog.rb
我的测试通过了。
但是有两件事我不明白:
当我使用 rspec 运行规范文件 spec_classdog.rb 时,表本身仅插入一条新狗。但是当我运行我的 ruby 文件 classdog.rb 时,没有插入新的狗。
- 为什么会发生这种情况?我预计运行我的 ruby 文件可能会导致新的插入,而 rspec 只是检查以确保我的方法有效。这是因为我没有将参数名称和颜色传递给插入方法(意思是这样的:dog.insert(“spot”,“black”)?
当我的 classdog.rb 文件中有以下代码时:
dog = Dog.new("simba", "grey") puts dog.inspect puts dog.name puts dog.color puts dog.id
ruby 看跌期权:
请注意,dog.id 没有输出,如下所示:
dog = Dog.new("simba", "grey")
puts dog.id
- 为什么 ruby 没有在dog.id中显示狗的id?
- 是因为创建TABLE Dog时将id设置为主键吗?
- 添加名为 dog_id 的特定列会有帮助吗?
@PeterAlfvin:这是一张显示运行 putsdog.insert
输出的图像
最佳答案
这至少是您的一些问题:
- Mysql 不会自动为您创建主键列,除非您在列上指定
auto_increment
insert
方法不提供id
值,因此它总是会失败,因为id
要求为非空。- 鉴于上述情况,数据库中的任何条目都不是由您显示的代码创建的。
既然您已经解决了这个问题,那么您就得到了以下结果:
id
值仅由 mysql 在数据库中创建,而不是在 RubyDog
对象中创建,因此它始终为nil
在对象中,除非/直到您设置它(您当前没有这样做)。- 它与
id
作为主键无关 - 创建
dog_id
属性/列/字段不会对此产生影响 - Ruby 正在揭示
dog.id
的值;它的字符串表示形式恰好是空字符串
关于mysql 和 rspec 错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20669104/