Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
张重言
rails
提交
580dd3b0
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,体验更适合开发者的 AI 搜索 >>
提交
580dd3b0
编写于
4月 27, 2010
作者:
N
Neeraj Singh
提交者:
José Valim
4月 29, 2010
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
array.to_xml should be able to handle all types of data elements [#4490 state:resolved]
Signed-off-by:
N
José Valim
<
jose.valim@gmail.com
>
上级
1b816d50
变更
7
隐藏空白更改
内联
并排
Showing
7 changed file
with
84 addition
and
72 deletion
+84
-72
activemodel/test/cases/serializeration/xml_serialization_test.rb
...odel/test/cases/serializeration/xml_serialization_test.rb
+5
-2
activesupport/lib/active_support/core_ext/array.rb
activesupport/lib/active_support/core_ext/array.rb
+1
-0
activesupport/lib/active_support/core_ext/array/conversions.rb
...esupport/lib/active_support/core_ext/array/conversions.rb
+13
-18
activesupport/lib/active_support/core_ext/hash.rb
activesupport/lib/active_support/core_ext/hash.rb
+1
-0
activesupport/lib/active_support/core_ext/hash/conversions.rb
...vesupport/lib/active_support/core_ext/hash/conversions.rb
+8
-47
activesupport/lib/active_support/core_ext/hash/conversions_xml_value.rb
...lib/active_support/core_ext/hash/conversions_xml_value.rb
+51
-0
activesupport/test/core_ext/array_ext_test.rb
activesupport/test/core_ext/array_ext_test.rb
+5
-5
未找到文件。
activemodel/test/cases/serializeration/xml_serialization_test.rb
浏览文件 @
580dd3b0
require
'cases/helper'
require
'models/contact'
require
'active_support/core_ext/object/instance_variables'
require
'ostruct'
class
Contact
extend
ActiveModel
::
Naming
...
...
@@ -23,7 +24,9 @@ def setup
@contact
.
age
=
25
@contact
.
created_at
=
Time
.
utc
(
2006
,
8
,
1
)
@contact
.
awesome
=
false
@contact
.
preferences
=
{
:gem
=>
'ruby'
}
customer
=
OpenStruct
.
new
customer
.
name
=
"John"
@contact
.
preferences
=
customer
end
test
"should serialize default root"
do
...
...
@@ -93,7 +96,7 @@ def setup
end
test
"should serialize yaml"
do
assert_match
%r{<preferences type=
\"
yaml
\"
>---
\n
:gem: ruby
\n
</preferences>}
,
@contact
.
to_xml
assert_match
%r{<preferences type=
\"
yaml
\"
>---
!ruby/object:OpenStruct
\n
table:
\s
*:name: John
\n
</preferences>}
,
@contact
.
to_xml
end
test
"should call proc on object"
do
...
...
activesupport/lib/active_support/core_ext/array.rb
浏览文件 @
580dd3b0
...
...
@@ -5,3 +5,4 @@
require
'active_support/core_ext/array/extract_options'
require
'active_support/core_ext/array/grouping'
require
'active_support/core_ext/array/random_access'
require
'active_support/core_ext/hash/conversions_xml_value'
activesupport/lib/active_support/core_ext/array/conversions.rb
浏览文件 @
580dd3b0
require
'active_support/core_ext/hash/keys'
require
'active_support/core_ext/hash/conversions_xml_value'
require
'active_support/core_ext/hash/reverse_merge'
require
'active_support/inflector'
...
...
@@ -51,6 +52,8 @@ def to_formatted_s(format = :default)
alias_method
:to_default_s
,
:to_s
alias_method
:to_s
,
:to_formatted_s
include
Hash
::
XmlValue
# Returns a string that represents this array in XML by sending +to_xml+
# to each element. Active Record collections delegate their representation
# in XML to this method.
...
...
@@ -127,34 +130,26 @@ def to_formatted_s(format = :default)
# </messages>
#
def
to_xml
(
options
=
{})
raise
"Not all elements respond to to_xml"
unless
all?
{
|
e
|
e
.
respond_to?
:to_xml
}
require
'builder'
unless
defined?
(
Builder
)
options
=
options
.
dup
options
[
:root
]
||=
all?
{
|
e
|
e
.
is_a?
(
first
.
class
)
&&
first
.
class
.
to_s
!=
"Hash"
}
?
ActiveSupport
::
Inflector
.
pluralize
(
ActiveSupport
::
Inflector
.
underscore
(
first
.
class
.
name
)).
tr
(
'/'
,
'_'
)
:
"records"
options
[
:children
]
||=
options
[
:root
].
singularize
options
[
:indent
]
||=
2
options
[
:builder
]
||=
Builder
::
XmlMarkup
.
new
(
:indent
=>
options
[
:indent
]
)
options
.
reverse_merge!
({
:builder
=>
Builder
::
XmlMarkup
.
new
(
:indent
=>
options
[
:indent
])
}
)
root
=
options
.
delete
(
:root
).
to_s
children
=
options
.
delete
(
:children
)
options
[
:root
]
||=
all?
{
|
e
|
e
.
is_a?
(
first
.
class
)
&&
first
.
class
.
to_s
!=
"Hash"
}
?
ActiveSupport
::
Inflector
.
pluralize
(
ActiveSupport
::
Inflector
.
underscore
(
first
.
class
.
name
)).
tr
(
'/'
,
'_'
)
:
"objects"
if
!
options
.
has_key?
(
:dasherize
)
||
options
[
:dasherize
]
root
=
root
.
dasherize
end
options
[
:builder
].
instruct!
unless
options
.
delete
(
:skip_instruct
)
root
=
rename_key
(
options
[
:root
].
to_s
,
options
)
opts
=
options
.
merge
({
:root
=>
children
})
options
[
:children
]
||=
options
[
:root
].
singularize
attributes
=
options
[
:skip_types
]
?
{}
:
{
:type
=>
"array"
}
return
options
[
:builder
].
tag!
(
root
,
attributes
)
if
empty?
xml
=
options
[
:builder
]
if
empty?
xml
.
tag!
(
root
,
options
[
:skip_types
]
?
{}
:
{
:type
=>
"array"
})
else
xml
.
tag!
(
root
,
options
[
:skip_types
]
?
{}
:
{
:type
=>
"array"
})
{
yield
xml
if
block_given?
each
{
|
e
|
e
.
to_xml
(
opts
.
merge
({
:skip_instruct
=>
true
}))
}
}
options
[
:builder
].
__send__
(
:method_missing
,
root
,
attributes
)
do
each
{
|
value
|
xml_value
(
options
[
:children
],
value
,
options
)
}
yield
options
[
:builder
]
if
block_given?
end
end
end
activesupport/lib/active_support/core_ext/hash.rb
浏览文件 @
580dd3b0
require
'active_support/core_ext/hash/conversions'
require
'active_support/core_ext/hash/conversions_xml_value'
require
'active_support/core_ext/hash/deep_merge'
require
'active_support/core_ext/hash/diff'
require
'active_support/core_ext/hash/except'
...
...
activesupport/lib/active_support/core_ext/hash/conversions.rb
浏览文件 @
580dd3b0
...
...
@@ -3,6 +3,7 @@
require
'active_support/core_ext/hash/reverse_merge'
require
'active_support/core_ext/object/blank'
require
'active_support/core_ext/string/inflections'
require
'active_support/core_ext/hash/conversions_xml_value'
class
Hash
# This module exists to decorate files deserialized using Hash.from_xml with
...
...
@@ -19,6 +20,8 @@ def content_type
end
end
include
XmlValue
XML_TYPE_NAMES
=
{
"Symbol"
=>
"symbol"
,
"Fixnum"
=>
"integer"
,
...
...
@@ -29,7 +32,9 @@ def content_type
"FalseClass"
=>
"boolean"
,
"Date"
=>
"date"
,
"DateTime"
=>
"datetime"
,
"Time"
=>
"datetime"
"Time"
=>
"datetime"
,
"Array"
=>
"array"
,
"Hash"
=>
"hash"
}
unless
defined?
(
XML_TYPE_NAMES
)
XML_FORMATTING
=
{
...
...
@@ -135,57 +140,13 @@ def to_xml(options = {})
:root
=>
"hash"
})
options
[
:builder
].
instruct!
unless
options
.
delete
(
:skip_instruct
)
root
=
rename_key
(
options
[
:root
].
to_s
,
options
)
# common upto this point
options
[
:builder
].
__send__
(
:method_missing
,
root
)
do
each
do
|
key
,
value
|
case
value
when
::
Hash
value
.
to_xml
(
options
.
merge
({
:root
=>
key
,
:skip_instruct
=>
true
}))
when
::
Array
value
.
to_xml
(
options
.
merge
({
:root
=>
key
,
:children
=>
key
.
to_s
.
singularize
,
:skip_instruct
=>
true
}))
when
::
Method
,
::
Proc
# If the Method or Proc takes two arguments, then
# pass the suggested child element name. This is
# used if the Method or Proc will be operating over
# multiple records and needs to create an containing
# element that will contain the objects being
# serialized.
if
1
==
value
.
arity
value
.
call
(
options
.
merge
({
:root
=>
key
,
:skip_instruct
=>
true
}))
else
value
.
call
(
options
.
merge
({
:root
=>
key
,
:skip_instruct
=>
true
}),
key
.
to_s
.
singularize
)
end
else
if
value
.
respond_to?
(
:to_xml
)
value
.
to_xml
(
options
.
merge
({
:root
=>
key
,
:skip_instruct
=>
true
}))
else
type_name
=
XML_TYPE_NAMES
[
value
.
class
.
name
]
key
=
rename_key
(
key
.
to_s
,
options
)
attributes
=
options
[
:skip_types
]
||
value
.
nil?
||
type_name
.
nil?
?
{
}
:
{
:type
=>
type_name
}
if
value
.
nil?
attributes
[
:nil
]
=
true
end
options
[
:builder
].
tag!
(
key
,
XML_FORMATTING
[
type_name
]
?
XML_FORMATTING
[
type_name
].
call
(
value
)
:
value
,
attributes
)
end
end
xml_value
(
key
,
value
,
options
)
end
yield
options
[
:builder
]
if
block_given?
end
end
def
rename_key
(
key
,
options
=
{})
camelize
=
options
.
has_key?
(
:camelize
)
&&
options
[
:camelize
]
dasherize
=
!
options
.
has_key?
(
:dasherize
)
||
options
[
:dasherize
]
key
=
key
.
camelize
if
camelize
dasherize
?
key
.
dasherize
:
key
end
class
<<
self
...
...
activesupport/lib/active_support/core_ext/hash/conversions_xml_value.rb
0 → 100644
浏览文件 @
580dd3b0
class
Hash
module
XmlValue
def
xml_value
(
key
,
value
,
options
)
case
value
when
::
Hash
value
.
to_xml
(
options
.
merge
({
:root
=>
key
,
:skip_instruct
=>
true
}))
when
::
Array
value
.
to_xml
(
options
.
merge
({
:root
=>
key
,
:children
=>
key
.
to_s
.
singularize
,
:skip_instruct
=>
true
}))
when
::
Method
,
::
Proc
# If the Method or Proc takes two arguments, then
# pass the suggested child element name. This is
# used if the Method or Proc will be operating over
# multiple records and needs to create an containing
# element that will contain the objects being
# serialized.
if
1
==
value
.
arity
value
.
call
(
options
.
merge
({
:root
=>
key
,
:skip_instruct
=>
true
}))
else
value
.
call
(
options
.
merge
({
:root
=>
key
,
:skip_instruct
=>
true
}),
key
.
to_s
.
singularize
)
end
else
if
value
.
respond_to?
(
:to_xml
)
value
.
to_xml
(
options
.
merge
({
:root
=>
key
,
:skip_instruct
=>
true
}))
else
type_name
=
XML_TYPE_NAMES
[
value
.
class
.
name
]
key
=
rename_key
(
key
.
to_s
,
options
)
attributes
=
options
[
:skip_types
]
||
value
.
nil?
||
type_name
.
nil?
?
{
}
:
{
:type
=>
type_name
}
if
value
.
nil?
attributes
[
:nil
]
=
true
end
options
[
:builder
].
tag!
(
key
,
XML_FORMATTING
[
type_name
]
?
XML_FORMATTING
[
type_name
].
call
(
value
)
:
value
,
attributes
)
end
end
#yield options[:builder] if block_given?
end
def
rename_key
(
key
,
options
=
{})
camelize
=
options
.
has_key?
(
:camelize
)
&&
options
[
:camelize
]
dasherize
=
!
options
.
has_key?
(
:dasherize
)
||
options
[
:dasherize
]
key
=
key
.
camelize
if
camelize
dasherize
?
key
.
dasherize
:
key
end
end
end
activesupport/test/core_ext/array_ext_test.rb
浏览文件 @
580dd3b0
...
...
@@ -211,7 +211,7 @@ def test_to_xml
{
:name
=>
"Jason"
,
:age
=>
31
,
:age_in_millis
=>
BigDecimal
.
new
(
'1.0'
)
}
].
to_xml
(
:skip_instruct
=>
true
,
:indent
=>
0
)
assert_equal
'<
records type="array"><record
>'
,
xml
.
first
(
30
)
assert_equal
'<
objects type="array"><object
>'
,
xml
.
first
(
30
)
assert
xml
.
include?
(
%(<age type="integer">26</age>)
),
xml
assert
xml
.
include?
(
%(<age-in-millis type="integer">820497600000</age-in-millis>)
),
xml
assert
xml
.
include?
(
%(<name>David</name>)
),
xml
...
...
@@ -233,7 +233,7 @@ def test_to_xml_with_options
{
:name
=>
"David"
,
:street_address
=>
"Paulina"
},
{
:name
=>
"Jason"
,
:street_address
=>
"Evergreen"
}
].
to_xml
(
:skip_instruct
=>
true
,
:skip_types
=>
true
,
:indent
=>
0
)
assert_equal
"<
records><record
>"
,
xml
.
first
(
17
)
assert_equal
"<
objects><object
>"
,
xml
.
first
(
17
)
assert
xml
.
include?
(
%(<street-address>Paulina</street-address>)
)
assert
xml
.
include?
(
%(<name>David</name>)
)
assert
xml
.
include?
(
%(<street-address>Evergreen</street-address>)
)
...
...
@@ -245,7 +245,7 @@ def test_to_xml_with_dasherize_false
{
:name
=>
"David"
,
:street_address
=>
"Paulina"
},
{
:name
=>
"Jason"
,
:street_address
=>
"Evergreen"
}
].
to_xml
(
:skip_instruct
=>
true
,
:skip_types
=>
true
,
:indent
=>
0
,
:dasherize
=>
false
)
assert_equal
"<
records><record
>"
,
xml
.
first
(
17
)
assert_equal
"<
objects><object
>"
,
xml
.
first
(
17
)
assert
xml
.
include?
(
%(<street_address>Paulina</street_address>)
)
assert
xml
.
include?
(
%(<street_address>Evergreen</street_address>)
)
end
...
...
@@ -255,7 +255,7 @@ def test_to_xml_with_dasherize_true
{
:name
=>
"David"
,
:street_address
=>
"Paulina"
},
{
:name
=>
"Jason"
,
:street_address
=>
"Evergreen"
}
].
to_xml
(
:skip_instruct
=>
true
,
:skip_types
=>
true
,
:indent
=>
0
,
:dasherize
=>
true
)
assert_equal
"<
records><record
>"
,
xml
.
first
(
17
)
assert_equal
"<
objects><object
>"
,
xml
.
first
(
17
)
assert
xml
.
include?
(
%(<street-address>Paulina</street-address>)
)
assert
xml
.
include?
(
%(<street-address>Evergreen</street-address>)
)
end
...
...
@@ -319,7 +319,7 @@ def test_extract_options_doesnt_extract_hash_subclasses
assert_equal
({},
options
)
assert_equal
[
hash
],
array
end
def
test_extract_options_extracts_extractable_subclass
hash
=
ExtractableHashSubclass
.
new
hash
[
:foo
]
=
1
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录