Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
张重言
rails
提交
70de7dda
R
rails
项目概览
张重言
/
rails
通知
1
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
R
rails
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
70de7dda
编写于
6月 19, 2014
作者:
R
Rafael Mendonça França
浏览文件
操作
浏览文件
下载
差异文件
Merge pull request #15818 from sgrif/sg-attribute-set
Introduce an object to aid in creation and management of `@attributes`
上级
c36e77a9
099af48d
变更
8
显示空白变更内容
内联
并排
Showing
8 changed file
with
120 addition
and
23 deletion
+120
-23
activerecord/lib/active_record.rb
activerecord/lib/active_record.rb
+1
-0
activerecord/lib/active_record/attribute_methods.rb
activerecord/lib/active_record/attribute_methods.rb
+2
-8
activerecord/lib/active_record/attribute_set.rb
activerecord/lib/active_record/attribute_set.rb
+51
-0
activerecord/lib/active_record/attributes.rb
activerecord/lib/active_record/attributes.rb
+5
-4
activerecord/lib/active_record/core.rb
activerecord/lib/active_record/core.rb
+3
-4
activerecord/lib/active_record/model_schema.rb
activerecord/lib/active_record/model_schema.rb
+8
-2
activerecord/lib/active_record/persistence.rb
activerecord/lib/active_record/persistence.rb
+1
-5
activerecord/test/cases/attribute_set_test.rb
activerecord/test/cases/attribute_set_test.rb
+49
-0
未找到文件。
activerecord/lib/active_record.rb
浏览文件 @
70de7dda
...
...
@@ -32,6 +32,7 @@ module ActiveRecord
extend
ActiveSupport
::
Autoload
autoload
:Attribute
autoload
:AttributeSet
autoload
:Base
autoload
:Callbacks
autoload
:Core
...
...
activerecord/lib/active_record/attribute_methods.rb
浏览文件 @
70de7dda
...
...
@@ -230,7 +230,7 @@ def respond_to?(name, include_private = false)
# For queries selecting a subset of columns, return false for unselected columns.
# We check defined?(@attributes) not to issue warnings if called on objects that
# have been allocated but not yet initialized.
if
defined?
(
@attributes
)
&&
@attributes
.
any?
&&
self
.
class
.
column_names
.
include?
(
name
)
if
defined?
(
@attributes
)
&&
self
.
class
.
column_names
.
include?
(
name
)
return
has_attribute?
(
name
)
end
...
...
@@ -247,7 +247,7 @@ def respond_to?(name, include_private = false)
# person.has_attribute?('age') # => true
# person.has_attribute?(:nothing) # => false
def
has_attribute?
(
attr_name
)
@attributes
.
has_key
?
(
attr_name
.
to_s
)
@attributes
.
include
?
(
attr_name
.
to_s
)
end
# Returns an array of names for the attributes available on this object.
...
...
@@ -367,12 +367,6 @@ def []=(attr_name, value)
protected
def
clone_attributes
# :nodoc:
@attributes
.
each_with_object
({})
do
|
(
name
,
attr
),
h
|
h
[
name
]
=
attr
.
dup
end
end
def
clone_attribute_value
(
reader_method
,
attribute_name
)
# :nodoc:
value
=
send
(
reader_method
,
attribute_name
)
value
.
duplicable?
?
value
.
clone
:
value
...
...
activerecord/lib/active_record/attribute_set.rb
0 → 100644
浏览文件 @
70de7dda
module
ActiveRecord
class
AttributeSet
# :nodoc:
delegate
:[]
,
:[]=
,
:fetch
,
:include?
,
:keys
,
:each_with_object
,
to: :attributes
def
initialize
(
attributes
)
@attributes
=
attributes
end
def
update
(
other
)
attributes
.
update
(
other
.
attributes
)
end
def
freeze
@attributes
.
freeze
super
end
def
initialize_dup
(
_
)
@attributes
=
attributes
.
dup
attributes
.
each
do
|
key
,
attr
|
attributes
[
key
]
=
attr
.
dup
end
super
end
def
initialize_clone
(
_
)
@attributes
=
attributes
.
clone
super
end
class
Builder
def
initialize
(
types
)
@types
=
types
end
def
build_from_database
(
values
,
additional_types
=
{})
attributes
=
values
.
each_with_object
({})
do
|
(
name
,
value
),
hash
|
type
=
additional_types
.
fetch
(
name
,
@types
[
name
])
hash
[
name
]
=
Attribute
.
from_database
(
value
,
type
)
end
AttributeSet
.
new
(
attributes
)
end
end
protected
attr_reader
:attributes
end
end
activerecord/lib/active_record/attributes.rb
浏览文件 @
70de7dda
...
...
@@ -109,13 +109,14 @@ def add_user_provided_columns(schema_columns)
end
def
clear_caches_calculated_from_columns
@columns
=
nil
@columns_hash
=
nil
@column_types
=
nil
@attributes_builder
=
nil
@column_defaults
=
nil
@raw_column_defaults
=
nil
@column_names
=
nil
@column_types
=
nil
@columns
=
nil
@columns_hash
=
nil
@content_columns
=
nil
@raw_column_defaults
=
nil
end
end
end
...
...
activerecord/lib/active_record/core.rb
浏览文件 @
70de7dda
...
...
@@ -251,11 +251,10 @@ def relation #:nodoc:
def
initialize
(
attributes
=
nil
,
options
=
{})
defaults
=
{}
self
.
class
.
raw_column_defaults
.
each
do
|
k
,
v
|
default
=
v
.
duplicable?
?
v
.
dup
:
v
defaults
[
k
]
=
Attribute
.
from_database
(
default
,
type_for_attribute
(
k
))
defaults
[
k
]
=
v
.
duplicable?
?
v
.
dup
:
v
end
@attributes
=
defaults
@attributes
=
self
.
class
.
attributes_builder
.
build_from_database
(
defaults
)
@column_types
=
self
.
class
.
column_types
init_internals
...
...
@@ -325,7 +324,7 @@ def init_with(coder)
##
def
initialize_dup
(
other
)
# :nodoc:
pk
=
self
.
class
.
primary_key
@attributes
=
other
.
clone_attributes
@attributes
=
@attributes
.
dup
@attributes
[
pk
]
=
Attribute
.
from_database
(
nil
,
type_for_attribute
(
pk
))
run_callbacks
(
:initialize
)
unless
_initialize_callbacks
.
empty?
...
...
activerecord/lib/active_record/model_schema.rb
浏览文件 @
70de7dda
...
...
@@ -219,12 +219,18 @@ def table_exists?
connection
.
schema_cache
.
table_exists?
(
table_name
)
end
def
attributes_builder
# :nodoc:
@attributes_builder
||=
AttributeSet
::
Builder
.
new
(
column_types
)
end
def
column_types
# :nodoc:
@column_types
||=
Hash
[
columns
.
map
{
|
column
|
[
column
.
name
,
column
.
cast_type
]
}]
@column_types
||=
Hash
.
new
(
Type
::
Value
.
new
).
tap
do
|
column_types
|
columns
.
each
{
|
column
|
column_types
[
column
.
name
]
=
column
.
cast_type
}
end
end
def
type_for_attribute
(
attr_name
)
# :nodoc:
column_types
.
fetch
(
attr_name
)
{
Type
::
Value
.
new
}
column_types
[
attr_name
]
end
# Returns a hash where the keys are column names and the values are
...
...
activerecord/lib/active_record/persistence.rb
浏览文件 @
70de7dda
...
...
@@ -48,11 +48,7 @@ def create(attributes = nil, &block)
# how this "single-table" inheritance mapping is implemented.
def
instantiate
(
attributes
,
column_types
=
{})
klass
=
discriminate_class_for_record
(
attributes
)
attributes
=
attributes
.
each_with_object
({})
do
|
(
name
,
value
),
h
|
type
=
column_types
.
fetch
(
name
)
{
klass
.
type_for_attribute
(
name
)
}
h
[
name
]
=
Attribute
.
from_database
(
value
,
type
)
end
attributes
=
klass
.
attributes_builder
.
build_from_database
(
attributes
,
column_types
)
klass
.
allocate
.
init_with
(
'attributes'
=>
attributes
,
'new_record'
=>
false
)
end
...
...
activerecord/test/cases/attribute_set_test.rb
0 → 100644
浏览文件 @
70de7dda
require
'cases/helper'
module
ActiveRecord
class
AttributeSetTest
<
ActiveRecord
::
TestCase
test
"building a new set from raw attributes"
do
builder
=
AttributeSet
::
Builder
.
new
(
foo:
Type
::
Integer
.
new
,
bar:
Type
::
Float
.
new
)
attributes
=
builder
.
build_from_database
(
foo:
'1.1'
,
bar:
'2.2'
)
assert_equal
1
,
attributes
[
:foo
].
value
assert_equal
2.2
,
attributes
[
:bar
].
value
end
test
"building with custom types"
do
builder
=
AttributeSet
::
Builder
.
new
(
foo:
Type
::
Float
.
new
)
attributes
=
builder
.
build_from_database
({
foo:
'3.3'
,
bar:
'4.4'
},
{
bar:
Type
::
Integer
.
new
})
assert_equal
3.3
,
attributes
[
:foo
].
value
assert_equal
4
,
attributes
[
:bar
].
value
end
test
"duping creates a new hash and dups each attribute"
do
builder
=
AttributeSet
::
Builder
.
new
(
foo:
Type
::
Integer
.
new
,
bar:
Type
::
String
.
new
)
attributes
=
builder
.
build_from_database
(
foo:
1
,
bar:
'foo'
)
# Ensure the type cast value is cached
attributes
[
:foo
].
value
attributes
[
:bar
].
value
duped
=
attributes
.
dup
duped
[
:foo
]
=
Attribute
.
from_database
(
2
,
Type
::
Integer
.
new
)
duped
[
:bar
].
value
<<
'bar'
assert_equal
1
,
attributes
[
:foo
].
value
assert_equal
2
,
duped
[
:foo
].
value
assert_equal
'foo'
,
attributes
[
:bar
].
value
assert_equal
'foobar'
,
duped
[
:bar
].
value
end
test
"freezing cloned set does not freeze original"
do
attributes
=
AttributeSet
.
new
({})
clone
=
attributes
.
clone
clone
.
freeze
assert
clone
.
frozen?
assert_not
attributes
.
frozen?
end
end
end
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录