moxml 0.1.25 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/workflows/release.yml +9 -0
- data/.github/workflows/windows.yml +62 -0
- data/Gemfile +3 -1
- data/README.adoc +133 -6
- data/docs/signature/algorithms.md +108 -0
- data/docs/signature/architecture.md +148 -0
- data/docs/signature/c14n.md +110 -0
- data/docs/signature/examples.md +109 -0
- data/docs/signature/flows.md +132 -0
- data/docs/signature/quick-reference.md +115 -0
- data/docs/signature/security.md +143 -0
- data/examples/signature/auto_key_extraction.rb +24 -0
- data/examples/signature/enveloped_rsa.rb +45 -0
- data/examples/signature/hmac.rb +33 -0
- data/lib/compat/opal/moxml_boot.rb +5 -0
- data/lib/moxml/adapter/base.rb +53 -49
- data/lib/moxml/adapter/customized_leptris/declaration.rb +32 -0
- data/lib/moxml/adapter/customized_leptris/doctype.rb +31 -0
- data/lib/moxml/adapter/customized_leptris/entity_reference.rb +12 -0
- data/lib/moxml/adapter/customized_leptris/text_segment.rb +26 -0
- data/lib/moxml/adapter/customized_leptris.rb +16 -0
- data/lib/moxml/adapter/customized_libxml/cdata.rb +3 -12
- data/lib/moxml/adapter/customized_libxml/comment.rb +2 -9
- data/lib/moxml/adapter/customized_libxml/declaration.rb +1 -10
- data/lib/moxml/adapter/customized_libxml/node.rb +8 -0
- data/lib/moxml/adapter/customized_libxml/processing_instruction.rb +2 -10
- data/lib/moxml/adapter/customized_libxml/text.rb +2 -9
- data/lib/moxml/adapter/customized_oga/entity_decoder.rb +37 -0
- data/lib/moxml/adapter/customized_oga/raw_value_override.rb +52 -0
- data/lib/moxml/adapter/customized_oga/xml_generator.rb +4 -34
- data/lib/moxml/adapter/customized_oga.rb +2 -0
- data/lib/moxml/adapter/customized_ox/entity_reference.rb +1 -17
- data/lib/moxml/adapter/customized_rexml/entity_reference.rb +1 -11
- data/lib/moxml/adapter/headed_ox.rb +9 -128
- data/lib/moxml/adapter/leptris.rb +965 -0
- data/lib/moxml/adapter/libxml.rb +131 -99
- data/lib/moxml/adapter/nokogiri.rb +29 -8
- data/lib/moxml/adapter/oga.rb +91 -54
- data/lib/moxml/adapter/ox.rb +93 -137
- data/lib/moxml/adapter/rexml.rb +61 -50
- data/lib/moxml/adapter.rb +2 -1
- data/lib/moxml/attribute.rb +8 -4
- data/lib/moxml/attribute_resolver.rb +189 -0
- data/lib/moxml/c14n/attribute_handler.rb +71 -0
- data/lib/moxml/c14n/character_encoder.rb +29 -0
- data/lib/moxml/c14n/data_model.rb +145 -0
- data/lib/moxml/c14n/exclusive.rb +188 -0
- data/lib/moxml/c14n/inclusive_10.rb +42 -0
- data/lib/moxml/c14n/inclusive_11.rb +21 -0
- data/lib/moxml/c14n/namespace_context.rb +68 -0
- data/lib/moxml/c14n/namespace_handler.rb +71 -0
- data/lib/moxml/c14n/node.rb +42 -0
- data/lib/moxml/c14n/nodes/attribute_node.rb +50 -0
- data/lib/moxml/c14n/nodes/comment_node.rb +29 -0
- data/lib/moxml/c14n/nodes/element_node.rb +62 -0
- data/lib/moxml/c14n/nodes/namespace_node.rb +41 -0
- data/lib/moxml/c14n/nodes/processing_instruction_node.rb +30 -0
- data/lib/moxml/c14n/nodes/root_node.rb +22 -0
- data/lib/moxml/c14n/nodes/text_node.rb +29 -0
- data/lib/moxml/c14n/nodes.rb +17 -0
- data/lib/moxml/c14n/processor.rb +118 -0
- data/lib/moxml/c14n/writer.rb +121 -0
- data/lib/moxml/c14n/xml_base_handler.rb +140 -0
- data/lib/moxml/c14n.rb +96 -0
- data/lib/moxml/config.rb +29 -3
- data/lib/moxml/context.rb +12 -0
- data/lib/moxml/element.rb +29 -12
- data/lib/moxml/entity/reference.rb +28 -0
- data/lib/moxml/entity.rb +125 -0
- data/lib/moxml/node.rb +90 -1
- data/lib/moxml/sax/namespace_splitter.rb +5 -2
- data/lib/moxml/signature/algorithms/base64_transform.rb +40 -0
- data/lib/moxml/signature/algorithms/canonicalization_base.rb +87 -0
- data/lib/moxml/signature/algorithms/digest_base.rb +51 -0
- data/lib/moxml/signature/algorithms/dsa_sha.rb +107 -0
- data/lib/moxml/signature/algorithms/ecdsa_sha.rb +125 -0
- data/lib/moxml/signature/algorithms/enveloped_signature_transform.rb +79 -0
- data/lib/moxml/signature/algorithms/exc_c14n_10.rb +23 -0
- data/lib/moxml/signature/algorithms/hmac_sha.rb +117 -0
- data/lib/moxml/signature/algorithms/inclusive_c14n_10.rb +21 -0
- data/lib/moxml/signature/algorithms/inclusive_c14n_11.rb +23 -0
- data/lib/moxml/signature/algorithms/rsa_pkcs1_sha.rb +56 -0
- data/lib/moxml/signature/algorithms/sha1.rb +13 -0
- data/lib/moxml/signature/algorithms/sha224.rb +13 -0
- data/lib/moxml/signature/algorithms/sha256.rb +13 -0
- data/lib/moxml/signature/algorithms/sha384.rb +13 -0
- data/lib/moxml/signature/algorithms/sha512.rb +13 -0
- data/lib/moxml/signature/algorithms/signature_method_base.rb +58 -0
- data/lib/moxml/signature/algorithms/transform_base.rb +40 -0
- data/lib/moxml/signature/algorithms.rb +113 -0
- data/lib/moxml/signature/errors.rb +99 -0
- data/lib/moxml/signature/key_extractor.rb +172 -0
- data/lib/moxml/signature/model/algorithm_method.rb +18 -0
- data/lib/moxml/signature/model/digest_method.rb +15 -0
- data/lib/moxml/signature/model/key/dsa_key_value.rb +28 -0
- data/lib/moxml/signature/model/key/ec_key_value.rb +22 -0
- data/lib/moxml/signature/model/key/rsa_key_value.rb +19 -0
- data/lib/moxml/signature/model/key/x509_data.rb +32 -0
- data/lib/moxml/signature/model/key/x509_digest.rb +19 -0
- data/lib/moxml/signature/model/key/x509_issuer_serial.rb +19 -0
- data/lib/moxml/signature/model/key_info.rb +21 -0
- data/lib/moxml/signature/model/key_value.rb +20 -0
- data/lib/moxml/signature/model/object_element.rb +18 -0
- data/lib/moxml/signature/model/reference.rb +22 -0
- data/lib/moxml/signature/model/signature.rb +21 -0
- data/lib/moxml/signature/model/signature_value.rb +16 -0
- data/lib/moxml/signature/model/signed_info.rb +20 -0
- data/lib/moxml/signature/model/transform.rb +16 -0
- data/lib/moxml/signature/model/transforms.rb +36 -0
- data/lib/moxml/signature/model.rb +35 -0
- data/lib/moxml/signature/parser.rb +270 -0
- data/lib/moxml/signature/reference_resolver.rb +79 -0
- data/lib/moxml/signature/reference_result.rb +22 -0
- data/lib/moxml/signature/serializer.rb +163 -0
- data/lib/moxml/signature/signer.rb +73 -0
- data/lib/moxml/signature/single_verification_result.rb +31 -0
- data/lib/moxml/signature/transform_pipeline.rb +106 -0
- data/lib/moxml/signature/verification_result.rb +27 -0
- data/lib/moxml/signature/verifier.rb +129 -0
- data/lib/moxml/signature.rb +94 -0
- data/lib/moxml/version.rb +1 -1
- data/lib/moxml/xml_emitter.rb +71 -0
- data/lib/moxml/xpath/compiler.rb +60 -7
- data/lib/moxml/xpath/parser.rb +22 -15
- data/lib/moxml.rb +5 -0
- data/reference-docs/w3c-xmldsig-bestpractices.md +216 -0
- data/reference-docs/w3c-xmldsig-core.md +400 -0
- data/spec/examples/readme_examples_spec.rb +0 -4
- data/spec/examples/xpath_examples_spec.rb +0 -11
- data/spec/fixtures/xmldsig/keys/rsa_private.pem +28 -0
- data/spec/fixtures/xmldsig/keys/rsa_public.pem +9 -0
- data/spec/fixtures/xmldsig/keys/rsa_ref.pem +15 -0
- data/spec/fixtures/xmldsig/keys/rsa_ref.pub +6 -0
- data/spec/fixtures/xmldsig/sign2-doc.xml +6 -0
- data/spec/fixtures/xmldsig/sign2-result.xml +25 -0
- data/spec/fixtures/xmldsig/sign3-result.xml +39 -0
- data/spec/integration/all_adapters_spec.rb +17 -0
- data/spec/integration/sax_parity_spec.rb +58 -0
- data/spec/integration/shared_examples/edge_cases.rb +0 -10
- data/spec/integration/shared_examples/integration_workflows.rb +0 -10
- data/spec/integration/shared_examples/node_wrappers/attribute_behavior.rb +98 -0
- data/spec/integration/shared_examples/node_wrappers/namespace_behavior.rb +26 -0
- data/spec/integration/shared_examples/node_wrappers/node_behavior.rb +0 -8
- data/spec/moxml/adapter/leptris_spec.rb +75 -0
- data/spec/moxml/adapter/ox_spec.rb +20 -6
- data/spec/moxml/adapter/platform_spec.rb +15 -2
- data/spec/moxml/adapter/shared_examples/adapter_contract.rb +180 -0
- data/spec/moxml/attribute_resolver_spec.rb +108 -0
- data/spec/moxml/c14n/api_spec.rb +117 -0
- data/spec/moxml/c14n/c14n_spec.rb +88 -0
- data/spec/moxml/c14n/comments_pis_spec.rb +65 -0
- data/spec/moxml/c14n/inclusive10_spec.rb +60 -0
- data/spec/moxml/c14n/namespace_edge_cases_spec.rb +88 -0
- data/spec/moxml/c14n/xml_attributes_spec.rb +54 -0
- data/spec/moxml/doctype_spec.rb +1 -1
- data/spec/moxml/entity_spec.rb +76 -0
- data/spec/moxml/node_spec.rb +104 -0
- data/spec/moxml/sax_entity_parity_spec.rb +358 -0
- data/spec/moxml/signature/algorithms/base64_transform_spec.rb +26 -0
- data/spec/moxml/signature/algorithms/digest_base_spec.rb +72 -0
- data/spec/moxml/signature/algorithms/dsa_sha_spec.rb +46 -0
- data/spec/moxml/signature/algorithms/ecdsa_sha_spec.rb +72 -0
- data/spec/moxml/signature/algorithms/enveloped_signature_transform_spec.rb +40 -0
- data/spec/moxml/signature/algorithms/hmac_sha_spec.rb +71 -0
- data/spec/moxml/signature/algorithms/rsa_pkcs1_sha_spec.rb +55 -0
- data/spec/moxml/signature/algorithms_spec.rb +76 -0
- data/spec/moxml/signature/cross_verify_spec.rb +64 -0
- data/spec/moxml/signature/edge_cases_spec.rb +284 -0
- data/spec/moxml/signature/fixtures_spec.rb +80 -0
- data/spec/moxml/signature/key_extractor_spec.rb +96 -0
- data/spec/moxml/signature/model_spec.rb +54 -0
- data/spec/moxml/signature/round_trip_spec.rb +113 -0
- data/spec/moxml/xml_emitter_spec.rb +64 -0
- data/spec/moxml/xpath/axes_spec.rb +72 -0
- data/spec/moxml/xpath/parser_spec.rb +6 -0
- data/spec/moxml/xpath_capabilities_spec.rb +5 -3
- data/spec/performance/benchmark_spec.rb +13 -6
- data/spec/performance/thread_safety_spec.rb +0 -4
- data/spec/spec_helper.rb +5 -1
- metadata +130 -2
|
@@ -0,0 +1,216 @@
|
|
|
1
|
+
# XML Signature Best Practices
|
|
2
|
+
|
|
3
|
+
W3C Working Group Note 11 April 2013
|
|
4
|
+
|
|
5
|
+
- This version: http://www.w3.org/TR/2013/NOTE-xmldsig-bestpractices-20130411/
|
|
6
|
+
- Latest published version: http://www.w3.org/TR/xmldsig-bestpractices/
|
|
7
|
+
- Latest editor's draft: http://www.w3.org/2008/xmlsec/Drafts/best-practices/Overview.html
|
|
8
|
+
- Previous version: http://www.w3.org/TR/2013/NOTE-xmldsig-bestpractices-20130124/
|
|
9
|
+
- Editors: Frederick Hirsch (Nokia), Pratik Datta (Oracle)
|
|
10
|
+
|
|
11
|
+
Copyright © 2013 W3C® (MIT, ERCIM, Keio, Beihang), All Rights Reserved.
|
|
12
|
+
|
|
13
|
+
## Abstract
|
|
14
|
+
|
|
15
|
+
This document collects best practices for implementers and users of the XML
|
|
16
|
+
Signature specification [XMLDSIG-CORE1]. Most of these best practices are
|
|
17
|
+
related to improving security and mitigating attacks, yet others are for best
|
|
18
|
+
practices in the practical use of XML Signature, such as signing XML that
|
|
19
|
+
doesn't use namespaces, for example.
|
|
20
|
+
|
|
21
|
+
## 1. Overview
|
|
22
|
+
|
|
23
|
+
The XML Signature specification [XMLDSIG-CORE1] offers powerful and flexible
|
|
24
|
+
mechanisms to support a variety of use cases. This flexibility has the downside
|
|
25
|
+
of increasing the number of possible attacks. One countermeasure to the
|
|
26
|
+
increased number of threats is to follow best practices, including a
|
|
27
|
+
simplification of use of XML Signature where possible.
|
|
28
|
+
|
|
29
|
+
## 2. Best Practices for Implementers
|
|
30
|
+
|
|
31
|
+
### 2.1 Reduce the opportunities for denial of service attacks
|
|
32
|
+
|
|
33
|
+
XML Signature may be used in application server systems, where multiple incoming
|
|
34
|
+
messages are being processed simultaneously. In this situation incoming messages
|
|
35
|
+
should be assumed to be possibly hostile with the concern that a single poison
|
|
36
|
+
message could bring down an entire set of web applications and services.
|
|
37
|
+
|
|
38
|
+
**Best Practice 1**: Mitigate denial of service attacks by executing potentially
|
|
39
|
+
dangerous operations only after successfully authenticating the signature.
|
|
40
|
+
|
|
41
|
+
Validate the `ds:Reference` elements for a signature only after establishing
|
|
42
|
+
trust, for example by verifying the key and validating `ds:SignedInfo` first.
|
|
43
|
+
|
|
44
|
+
Recommended order of operations:
|
|
45
|
+
|
|
46
|
+
1. **Step 1** — fetch the verification key and establish trust in that key.
|
|
47
|
+
2. **Step 2** — validate `ds:SignedInfo` with that key.
|
|
48
|
+
3. **Step 3** — validate the references.
|
|
49
|
+
|
|
50
|
+
**Best Practice 2**: Establish trust in the verification/validation key (validate
|
|
51
|
+
X.509 certificates, certificate chains and revocation status).
|
|
52
|
+
|
|
53
|
+
#### 2.1.1 XSLT transform that causes denial of service
|
|
54
|
+
|
|
55
|
+
A nested-loop XSLT can require O(N^4) operations on a document with N elements.
|
|
56
|
+
|
|
57
|
+
**Best Practice 3**: Consider avoiding XSLT Transforms.
|
|
58
|
+
|
|
59
|
+
#### 2.1.2 XSLT transform that executes arbitrary code
|
|
60
|
+
|
|
61
|
+
XSLT user-defined extensions can execute arbitrary code (e.g., shell commands).
|
|
62
|
+
|
|
63
|
+
**Best Practice 4**: When XSLT is required disallow the use of user-defined
|
|
64
|
+
extensions.
|
|
65
|
+
|
|
66
|
+
#### 2.1.3 XPath Filtering transform that causes denial of service
|
|
67
|
+
|
|
68
|
+
A document with N namespaces and N elements produces N×N namespace nodes; an
|
|
69
|
+
XPath Filter evaluates the expression once per node, giving O(N^4) cost.
|
|
70
|
+
|
|
71
|
+
**Best Practice 5**: Try to avoid or limit XPath transforms.
|
|
72
|
+
|
|
73
|
+
#### 2.1.4 XPath selection DoS in streaming mode
|
|
74
|
+
|
|
75
|
+
Wildcard axes (descendant, following, etc.) cause search-context explosion in
|
|
76
|
+
streaming verifiers.
|
|
77
|
+
|
|
78
|
+
**Best Practice 6**: Avoid using "descendant", "descendant-or-self",
|
|
79
|
+
"following-sibling", and "following" axes when using streaming XPaths.
|
|
80
|
+
|
|
81
|
+
#### 2.1.5 Retrieval method that causes an infinite loop
|
|
82
|
+
|
|
83
|
+
`ds:RetrievalMethod` may form cyclic references.
|
|
84
|
+
|
|
85
|
+
**Best Practice 7**: Try to avoid or limit `ds:RetrievalMethod` support with
|
|
86
|
+
`ds:KeyInfo`.
|
|
87
|
+
|
|
88
|
+
#### 2.1.6 Problematic external references
|
|
89
|
+
|
|
90
|
+
External URI references can read sensitive files or trigger side effects on
|
|
91
|
+
other sites.
|
|
92
|
+
|
|
93
|
+
**Best Practice 8**: Control external references (mitigate query parameters,
|
|
94
|
+
unknown URI schemes, inappropriate content).
|
|
95
|
+
|
|
96
|
+
#### 2.1.7 Denial of service caused by too many transforms
|
|
97
|
+
|
|
98
|
+
A reference may carry thousands of C14N transforms.
|
|
99
|
+
|
|
100
|
+
**Best Practice 9**: Limit the number of `ds:Reference` transforms allowed.
|
|
101
|
+
|
|
102
|
+
### 2.2 Provide a mechanism to determine what was signed
|
|
103
|
+
|
|
104
|
+
**Best Practice 10**: Offer interfaces for the application to learn what was
|
|
105
|
+
signed (return pre-digested data and pre-C14N data).
|
|
106
|
+
|
|
107
|
+
### 2.3 Be aware of certificate encoding issues
|
|
108
|
+
|
|
109
|
+
**Best Practice 11**: Do not re-encode certificates; use DER when possible with
|
|
110
|
+
the `X509Certificate` element. Re-encoding can break the signature on the
|
|
111
|
+
certificate.
|
|
112
|
+
|
|
113
|
+
## 3. Best Practices for Applications
|
|
114
|
+
|
|
115
|
+
### 3.1 Check what is signed
|
|
116
|
+
|
|
117
|
+
**Best Practice 12**: Enable verifier to automate "see what is signed"
|
|
118
|
+
functionality.
|
|
119
|
+
|
|
120
|
+
**Best Practice 13**: When applying XML Signatures using XPath it is recommended
|
|
121
|
+
to always actively verify that the signature protects the intended elements and
|
|
122
|
+
not more or less.
|
|
123
|
+
|
|
124
|
+
**Best Practice 14**: When checking a reference URI, don't just check the name of
|
|
125
|
+
the element (wrapping attack mitigation — also check position).
|
|
126
|
+
|
|
127
|
+
### 3.2 Prevent replay attacks
|
|
128
|
+
|
|
129
|
+
**Best Practice 15**: Unless impractical, sign all parts of the document.
|
|
130
|
+
|
|
131
|
+
**Best Practice 16**: Use a nonce in combination with signing time.
|
|
132
|
+
|
|
133
|
+
**Best Practice 17**: Do not rely on application logic to prevent replay attacks
|
|
134
|
+
since applications may change.
|
|
135
|
+
|
|
136
|
+
**Best Practice 18**: Nonce and signing time must be signature protected.
|
|
137
|
+
|
|
138
|
+
### 3.3 Enable Long-Lived Signatures
|
|
139
|
+
|
|
140
|
+
**Best Practice 19**: Use Timestamp tokens issued by Timestamp authorities for
|
|
141
|
+
long lived signatures.
|
|
142
|
+
|
|
143
|
+
**Best Practice 20**: Long lived signatures should include a `xsd:dateTime` field
|
|
144
|
+
to indicate the time of signing.
|
|
145
|
+
|
|
146
|
+
### 3.4 Signing XML without namespace information ("legacy XML")
|
|
147
|
+
|
|
148
|
+
**Best Practice 21**: When creating an enveloping signature over XML without
|
|
149
|
+
namespace information, take steps to avoid having that content inherit the XML
|
|
150
|
+
Signature namespace (insert an empty default namespace declaration, or define a
|
|
151
|
+
namespace prefix for the Signature namespace).
|
|
152
|
+
|
|
153
|
+
### 3.5 Prefer the XPath Filter 2 Transform
|
|
154
|
+
|
|
155
|
+
**Best Practice 22**: Prefer the XPath Filter 2 Transform to the XPath Filter
|
|
156
|
+
Transform if possible.
|
|
157
|
+
|
|
158
|
+
## 4. Best Practices for Signers and Verifiers
|
|
159
|
+
|
|
160
|
+
### 4.1 Do not transmit external unparsed entity references
|
|
161
|
+
|
|
162
|
+
**Best Practice 23**: Do not transmit unparsed external entity references in
|
|
163
|
+
signed material. Expand all entity references before creating the cleartext.
|
|
164
|
+
|
|
165
|
+
### 4.2 Be aware of schema processing
|
|
166
|
+
|
|
167
|
+
**Best Practice 24**: Do not rely on a validating processor on the consumer's end
|
|
168
|
+
to normalize XML documents.
|
|
169
|
+
|
|
170
|
+
**Best Practice 25**: Avoid destructive validation before signature validation.
|
|
171
|
+
|
|
172
|
+
### 4.3 HMAC truncation
|
|
173
|
+
|
|
174
|
+
**Best Practice 26**: When using an HMAC, set the HMAC Output Length to one half
|
|
175
|
+
the number of bits in the hash size.
|
|
176
|
+
|
|
177
|
+
### 4.4 Distinct keys for sign and encrypt
|
|
178
|
+
|
|
179
|
+
**Best Practice 27**: When encrypting and signing use distinct keys.
|
|
180
|
+
|
|
181
|
+
## 5. Best Practices Summary
|
|
182
|
+
|
|
183
|
+
1. Mitigate DoS by authenticating before dangerous operations.
|
|
184
|
+
2. Establish trust in the verification key.
|
|
185
|
+
3. Avoid XSLT transforms.
|
|
186
|
+
4. Disallow XSLT user-defined extensions.
|
|
187
|
+
5. Avoid/limit XPath transforms.
|
|
188
|
+
6. Avoid wildcard axes in streaming XPaths.
|
|
189
|
+
7. Avoid/limit `ds:RetrievalMethod`.
|
|
190
|
+
8. Control external references.
|
|
191
|
+
9. Limit number of transforms per Reference.
|
|
192
|
+
10. Offer interfaces to learn what was signed.
|
|
193
|
+
11. Don't re-encode certificates; prefer DER.
|
|
194
|
+
12. Enable verifier to "see what is signed".
|
|
195
|
+
13. With XPath, verify the signature actually protects intended elements.
|
|
196
|
+
14. When checking reference URI, check both name and position.
|
|
197
|
+
15. Sign all parts of the document unless impractical.
|
|
198
|
+
16. Use nonce + signing time.
|
|
199
|
+
17. Don't rely solely on application logic for replay prevention.
|
|
200
|
+
18. Nonce and signing time must be signature protected.
|
|
201
|
+
19. Use TSA-issued timestamp tokens for long-lived signatures.
|
|
202
|
+
20. Include `xsd:dateTime` for signing time in long-lived signatures.
|
|
203
|
+
21. Avoid namespace inheritance in enveloping signatures over legacy XML.
|
|
204
|
+
22. Prefer XPath Filter 2 over XPath Filter.
|
|
205
|
+
23. Don't transmit unparsed external entity references.
|
|
206
|
+
24. Don't rely on validating parser on consumer's end.
|
|
207
|
+
25. Avoid destructive validation before signature validation.
|
|
208
|
+
26. Truncate HMAC to half hash size.
|
|
209
|
+
27. Use distinct keys for signing and encryption.
|
|
210
|
+
|
|
211
|
+
## References
|
|
212
|
+
|
|
213
|
+
- [XMLDSIG-CORE1] — XML Signature Syntax and Processing Version 1.1
|
|
214
|
+
- [XADES] — XML Advanced Electronic Signatures (ETSI TS 101 903)
|
|
215
|
+
- [RFC3161] — Internet X.509 PKI Time-Stamp Protocol (TSP)
|
|
216
|
+
- [MCINTOSH-WRAP] — XML signature element wrapping attacks and countermeasures
|
|
@@ -0,0 +1,400 @@
|
|
|
1
|
+
# XML Signature Syntax and Processing Version 1.1 (W3C Recommendation, 11 April 2013)
|
|
2
|
+
|
|
3
|
+
Curated implementation-focused extract. Source: https://www.w3.org/TR/xmldsig-core/
|
|
4
|
+
|
|
5
|
+
Editors: Donald Eastlake, Joseph Reagle, David Solo, Frederick Hirsch, Magnus Nyström, Thomas Roessler, Kelvin Yiu.
|
|
6
|
+
|
|
7
|
+
## Abstract
|
|
8
|
+
|
|
9
|
+
XML Signatures provide integrity, message authentication, and/or signer
|
|
10
|
+
authentication services for data of any type, whether located within the XML
|
|
11
|
+
that includes the signature or elsewhere.
|
|
12
|
+
|
|
13
|
+
## Namespaces
|
|
14
|
+
|
|
15
|
+
| URI | prefix |
|
|
16
|
+
| --- | --- |
|
|
17
|
+
| `http://www.w3.org/2000/09/xmldsig#` | `ds:` / `dsig:` |
|
|
18
|
+
| `http://www.w3.org/2009/xmldsig11#` | `dsig11:` |
|
|
19
|
+
|
|
20
|
+
Algorithm identifiers in the `http://www.w3.org/2001/04/xmldsig-more#` namespace
|
|
21
|
+
are defined by RFC 6931.
|
|
22
|
+
|
|
23
|
+
## Signature Structure
|
|
24
|
+
|
|
25
|
+
```
|
|
26
|
+
<Signature ID?>
|
|
27
|
+
<SignedInfo>
|
|
28
|
+
<CanonicalizationMethod />
|
|
29
|
+
<SignatureMethod />
|
|
30
|
+
(<Reference URI? >
|
|
31
|
+
(<Transforms>)?
|
|
32
|
+
<DigestMethod>
|
|
33
|
+
<DigestValue>
|
|
34
|
+
</Reference>)+
|
|
35
|
+
</SignedInfo>
|
|
36
|
+
<SignatureValue>
|
|
37
|
+
(<KeyInfo>)?
|
|
38
|
+
(<Object ID?>)*
|
|
39
|
+
</Signature>
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
## Processing Rules
|
|
43
|
+
|
|
44
|
+
### 3.1 Signature Generation
|
|
45
|
+
|
|
46
|
+
#### 3.1.1 Reference Generation
|
|
47
|
+
|
|
48
|
+
For each data object being signed:
|
|
49
|
+
|
|
50
|
+
1. Apply the `Transforms`, as determined by the application, to the data object.
|
|
51
|
+
2. Calculate the digest value over the resulting data object.
|
|
52
|
+
3. Create a `Reference` element, including the (optional) identification of the
|
|
53
|
+
data object, any (optional) transform elements, the digest algorithm and the
|
|
54
|
+
`DigestValue`.
|
|
55
|
+
|
|
56
|
+
#### 3.1.2 Signature Generation
|
|
57
|
+
|
|
58
|
+
1. Create `SignedInfo` element with `SignatureMethod`, `CanonicalizationMethod`
|
|
59
|
+
and `Reference`(s).
|
|
60
|
+
2. Canonicalize and then calculate the `SignatureValue` over `SignedInfo` based
|
|
61
|
+
on algorithms specified in `SignedInfo`.
|
|
62
|
+
3. Construct the `Signature` element that includes `SignedInfo`, `Object`(s),
|
|
63
|
+
`KeyInfo` (if required), and `SignatureValue`.
|
|
64
|
+
|
|
65
|
+
### 3.2 Core Validation
|
|
66
|
+
|
|
67
|
+
The required steps of core validation include:
|
|
68
|
+
|
|
69
|
+
1. **Reference validation** — verification of the digest contained in each
|
|
70
|
+
`Reference` in `SignedInfo`.
|
|
71
|
+
2. **Signature validation** — cryptographic signature validation of the signature
|
|
72
|
+
calculated over `SignedInfo`.
|
|
73
|
+
|
|
74
|
+
Comparison of each value is over the numeric (integer) or decoded octet sequence
|
|
75
|
+
of the value.
|
|
76
|
+
|
|
77
|
+
#### 3.2.1 Reference Validation
|
|
78
|
+
|
|
79
|
+
1. Canonicalize the `SignedInfo` element based on the `CanonicalizationMethod`.
|
|
80
|
+
2. For each `Reference` in `SignedInfo`:
|
|
81
|
+
1. Obtain the data object (dereference `URI`, execute `Transforms`, or fetch
|
|
82
|
+
from local cache).
|
|
83
|
+
2. Digest using the `DigestMethod`.
|
|
84
|
+
3. Compare against `DigestValue`; mismatch ⇒ validation fails.
|
|
85
|
+
|
|
86
|
+
#### 3.2.2 Signature Validation
|
|
87
|
+
|
|
88
|
+
1. Obtain the keying information from `KeyInfo` or external source.
|
|
89
|
+
2. Obtain the canonical form of `SignedInfo` using `CanonicalizationMethod` and
|
|
90
|
+
confirm the `SignatureValue` over `SignedInfo`.
|
|
91
|
+
|
|
92
|
+
## Schema
|
|
93
|
+
|
|
94
|
+
### `ds:CryptoBinary`
|
|
95
|
+
|
|
96
|
+
Integer-to-octet conversion equivalent to IEEE 1363 I2OSP with minimal length,
|
|
97
|
+
then base64-encoded.
|
|
98
|
+
|
|
99
|
+
### 4.2 `Signature`
|
|
100
|
+
|
|
101
|
+
```xml
|
|
102
|
+
<element name="Signature" type="ds:SignatureType"/>
|
|
103
|
+
<complexType name="SignatureType">
|
|
104
|
+
<sequence>
|
|
105
|
+
<element ref="ds:SignedInfo"/>
|
|
106
|
+
<element ref="ds:SignatureValue"/>
|
|
107
|
+
<element ref="ds:KeyInfo" minOccurs="0"/>
|
|
108
|
+
<element ref="ds:Object" minOccurs="0" maxOccurs="unbounded"/>
|
|
109
|
+
</sequence>
|
|
110
|
+
<attribute name="Id" type="ID" use="optional"/>
|
|
111
|
+
</complexType>
|
|
112
|
+
```
|
|
113
|
+
|
|
114
|
+
### 4.3 `SignatureValue`
|
|
115
|
+
|
|
116
|
+
```xml
|
|
117
|
+
<complexType name="SignatureValueType">
|
|
118
|
+
<simpleContent>
|
|
119
|
+
<extension base="base64Binary">
|
|
120
|
+
<attribute name="Id" type="ID" use="optional"/>
|
|
121
|
+
</extension>
|
|
122
|
+
</simpleContent>
|
|
123
|
+
</complexType>
|
|
124
|
+
```
|
|
125
|
+
|
|
126
|
+
### 4.4 `SignedInfo`
|
|
127
|
+
|
|
128
|
+
```xml
|
|
129
|
+
<complexType name="SignedInfoType">
|
|
130
|
+
<sequence>
|
|
131
|
+
<element ref="ds:CanonicalizationMethod"/>
|
|
132
|
+
<element ref="ds:SignatureMethod"/>
|
|
133
|
+
<element ref="ds:Reference" maxOccurs="unbounded"/>
|
|
134
|
+
</sequence>
|
|
135
|
+
<attribute name="Id" type="ID" use="optional"/>
|
|
136
|
+
</complexType>
|
|
137
|
+
```
|
|
138
|
+
|
|
139
|
+
### 4.4.1 `CanonicalizationMethod`
|
|
140
|
+
|
|
141
|
+
```xml
|
|
142
|
+
<complexType name="CanonicalizationMethodType" mixed="true">
|
|
143
|
+
<sequence>
|
|
144
|
+
<any namespace="##any" minOccurs="0" maxOccurs="unbounded"/>
|
|
145
|
+
</sequence>
|
|
146
|
+
<attribute name="Algorithm" type="anyURI" use="required"/>
|
|
147
|
+
</complexType>
|
|
148
|
+
```
|
|
149
|
+
|
|
150
|
+
### 4.4.2 `SignatureMethod`
|
|
151
|
+
|
|
152
|
+
```xml
|
|
153
|
+
<complexType name="SignatureMethodType" mixed="true">
|
|
154
|
+
<sequence>
|
|
155
|
+
<element name="HMACOutputLength" minOccurs="0" type="ds:HMACOutputLengthType"/>
|
|
156
|
+
<any namespace="##other" minOccurs="0" maxOccurs="unbounded"/>
|
|
157
|
+
</sequence>
|
|
158
|
+
<attribute name="Algorithm" type="anyURI" use="required"/>
|
|
159
|
+
</complexType>
|
|
160
|
+
```
|
|
161
|
+
|
|
162
|
+
Signatures MUST be deemed invalid if the HMAC truncation length is below the
|
|
163
|
+
larger of (a) half the underlying hash output length, and (b) 80 bits.
|
|
164
|
+
|
|
165
|
+
### 4.4.3 `Reference`
|
|
166
|
+
|
|
167
|
+
```xml
|
|
168
|
+
<complexType name="ReferenceType">
|
|
169
|
+
<sequence>
|
|
170
|
+
<element ref="ds:Transforms" minOccurs="0"/>
|
|
171
|
+
<element ref="ds:DigestMethod"/>
|
|
172
|
+
<element ref="ds:DigestValue"/>
|
|
173
|
+
</sequence>
|
|
174
|
+
<attribute name="Id" type="ID" use="optional"/>
|
|
175
|
+
<attribute name="URI" type="anyURI" use="optional"/>
|
|
176
|
+
<attribute name="Type" type="anyURI" use="optional"/>
|
|
177
|
+
</complexType>
|
|
178
|
+
```
|
|
179
|
+
|
|
180
|
+
#### 4.4.3.2 Reference Processing Model
|
|
181
|
+
|
|
182
|
+
Result of URI dereferencing or transforms is either octet stream or XPath node-set.
|
|
183
|
+
|
|
184
|
+
Defaults:
|
|
185
|
+
- octet stream + node-set transform expected ⇒ parse octets as XML.
|
|
186
|
+
- node-set + octet transform expected ⇒ canonicalize via C14N.
|
|
187
|
+
|
|
188
|
+
A **same-document reference** is a URI-Reference that consists of `#` followed by
|
|
189
|
+
a fragment, or an empty URI.
|
|
190
|
+
|
|
191
|
+
- `URI=""` ⇒ node-set (minus comments) of the entire document.
|
|
192
|
+
- `URI="#id"` ⇒ node-set of the element with that ID + descendants + in-scope
|
|
193
|
+
namespaces/attributes, no comments.
|
|
194
|
+
- `#xpointer(/)` retains comments at root.
|
|
195
|
+
- `#xpointer(id('ID'))` retains comments for the element.
|
|
196
|
+
|
|
197
|
+
### 4.4.3.4 `Transforms`
|
|
198
|
+
|
|
199
|
+
```xml
|
|
200
|
+
<complexType name="TransformsType">
|
|
201
|
+
<sequence>
|
|
202
|
+
<element ref="ds:Transform" maxOccurs="unbounded"/>
|
|
203
|
+
</sequence>
|
|
204
|
+
</complexType>
|
|
205
|
+
|
|
206
|
+
<complexType name="TransformType" mixed="true">
|
|
207
|
+
<choice minOccurs="0" maxOccurs="unbounded">
|
|
208
|
+
<any namespace="##other" processContents="lax"/>
|
|
209
|
+
<element name="XPath" type="string"/>
|
|
210
|
+
</choice>
|
|
211
|
+
<attribute name="Algorithm" type="anyURI" use="required"/>
|
|
212
|
+
</complexType>
|
|
213
|
+
```
|
|
214
|
+
|
|
215
|
+
### 4.5 `KeyInfo`
|
|
216
|
+
|
|
217
|
+
```xml
|
|
218
|
+
<complexType name="KeyInfoType" mixed="true">
|
|
219
|
+
<choice maxOccurs="unbounded">
|
|
220
|
+
<element ref="ds:KeyName"/>
|
|
221
|
+
<element ref="ds:KeyValue"/>
|
|
222
|
+
<element ref="ds:RetrievalMethod"/>
|
|
223
|
+
<element ref="ds:X509Data"/>
|
|
224
|
+
<element ref="ds:PGPData"/>
|
|
225
|
+
<element ref="ds:SPKIData"/>
|
|
226
|
+
<element ref="ds:MgmtData"/>
|
|
227
|
+
<any processContents="lax" namespace="##other"/>
|
|
228
|
+
</choice>
|
|
229
|
+
<attribute name="Id" type="ID" use="optional"/>
|
|
230
|
+
</complexType>
|
|
231
|
+
```
|
|
232
|
+
|
|
233
|
+
`KeyValue` contains one of `DSAKeyValue`, `RSAKeyValue`, or (1.1) `ECKeyValue`.
|
|
234
|
+
|
|
235
|
+
X509Data child elements: `X509IssuerSerial` (deprecated), `X509SKI`,
|
|
236
|
+
`X509SubjectName`, `X509Certificate`, `X509CRL`, `dsig11:X509Digest`.
|
|
237
|
+
|
|
238
|
+
### 4.6 `Object`
|
|
239
|
+
|
|
240
|
+
Optional element for including data objects. Has `Id`, `MimeType`, `Encoding`
|
|
241
|
+
attributes.
|
|
242
|
+
|
|
243
|
+
## Additional Syntax
|
|
244
|
+
|
|
245
|
+
### 5.1 `Manifest`
|
|
246
|
+
|
|
247
|
+
A list of `Reference`s where digest checking is application-defined (not core).
|
|
248
|
+
|
|
249
|
+
### 5.2 `SignatureProperties`
|
|
250
|
+
|
|
251
|
+
For signature-time, hardware serial, etc. `SignatureProperty` has required
|
|
252
|
+
`Target` attribute referencing the `Signature` element.
|
|
253
|
+
|
|
254
|
+
### 5.3 PIs and 5.4 Comments
|
|
255
|
+
|
|
256
|
+
Unless `CanonicalizationMethod` strips comments or PIs, they are signed.
|
|
257
|
+
|
|
258
|
+
## Algorithms
|
|
259
|
+
|
|
260
|
+
### Mandatory & Recommended URIs
|
|
261
|
+
|
|
262
|
+
**Digest**:
|
|
263
|
+
- Required: SHA1 `http://www.w3.org/2000/09/xmldsig#sha1` (discouraged); SHA256
|
|
264
|
+
`http://www.w3.org/2001/04/xmlenc#sha256`
|
|
265
|
+
- Optional: SHA224 `…xmldsig-more#sha224`; SHA384 `…xmldsig-more#sha384`; SHA512
|
|
266
|
+
`…xmlenc#sha512`
|
|
267
|
+
|
|
268
|
+
**MAC**:
|
|
269
|
+
- Required: HMAC-SHA1 `…xmldsig#hmac-sha1` (discouraged); HMAC-SHA256
|
|
270
|
+
`…xmldsig-more#hmac-sha256`
|
|
271
|
+
- Recommended: HMAC-SHA384, HMAC-SHA512
|
|
272
|
+
|
|
273
|
+
**Signature**:
|
|
274
|
+
- Required: RSA-SHA256 `…xmldsig-more#rsa-sha256`; ECDSA-SHA256
|
|
275
|
+
`…xmldsig-more#ecdsa-sha256`; DSA-SHA1 (verification only) `…xmldsig#dsa-sha1`
|
|
276
|
+
- Recommended: RSA-SHA1 (verification; discouraged for generation)
|
|
277
|
+
- Optional: RSA-{SHA224,SHA384,SHA512}; ECDSA-{SHA1,SHA224,SHA384,SHA512};
|
|
278
|
+
DSA-SHA256 `…xmldsig11#dsa-sha256`
|
|
279
|
+
|
|
280
|
+
**Canonicalization**:
|
|
281
|
+
- Required:
|
|
282
|
+
- Canonical XML 1.0 (omit comments): `http://www.w3.org/TR/2001/REC-xml-c14n-20010315`
|
|
283
|
+
- Canonical XML 1.1 (omit comments): `http://www.w3.org/2006/12/xml-c14n11`
|
|
284
|
+
- Exclusive XML Canonicalization 1.0 (omit comments): `http://www.w3.org/2001/10/xml-exc-c14n#`
|
|
285
|
+
- Recommended variants append `#WithComments`
|
|
286
|
+
|
|
287
|
+
**Transform**:
|
|
288
|
+
- Required: base64 `…xmldsig#base64`; Enveloped Signature
|
|
289
|
+
`…xmldsig#enveloped-signature`
|
|
290
|
+
- Recommended: XPath `…REC-xpath-19991116`; XPath Filter 2.0
|
|
291
|
+
`…2002/06/xmldsig-filter2`
|
|
292
|
+
- Optional: XSLT `…REC-xslt-19991116`
|
|
293
|
+
|
|
294
|
+
### Digest Algorithms
|
|
295
|
+
|
|
296
|
+
- SHA-1: 160-bit / 20 octets, base64-encoded.
|
|
297
|
+
- SHA-256: 256-bit / 32 octets.
|
|
298
|
+
- SHA-384: 384-bit / 48 octets.
|
|
299
|
+
- SHA-512: 512-bit / 64 octets.
|
|
300
|
+
|
|
301
|
+
### HMAC
|
|
302
|
+
|
|
303
|
+
Identifier family: `…xmldsig#hmac-sha1`, `…xmldsig-more#hmac-{sha224,sha256,sha384,sha512}`.
|
|
304
|
+
Truncation length (`HMACOutputLength`) MUST be a multiple of 8 bits. If below
|
|
305
|
+
half the hash output length, signature MUST be deemed invalid.
|
|
306
|
+
|
|
307
|
+
### DSA
|
|
308
|
+
|
|
309
|
+
Identifier: `…xmldsig#dsa-sha1` (1024/160), `…xmldsig11#dsa-sha256` (2048/256 or
|
|
310
|
+
3072/256).
|
|
311
|
+
|
|
312
|
+
Output (r, s): base64-encoded concatenation of two octet streams using I2OSP with
|
|
313
|
+
length parameter 20 (for SHA-1) or `N` (for SHA-256 with N=|q|).
|
|
314
|
+
|
|
315
|
+
### RSA (PKCS#1 v1.5)
|
|
316
|
+
|
|
317
|
+
Identifiers: `…xmldsig#rsa-sha1`, `…xmldsig-more#rsa-{sha224,sha256,sha384,sha512}`.
|
|
318
|
+
RSASSA-PKCS1-v1_5 per RFC 3447 §8.2.1.
|
|
319
|
+
|
|
320
|
+
### ECDSA
|
|
321
|
+
|
|
322
|
+
Identifiers: `…xmldsig-more#ecdsa-{sha1,sha224,sha256,sha384,sha512}`.
|
|
323
|
+
Output (r, s): base64-encoded concatenation of I2OSP of r and s, each of length
|
|
324
|
+
equal to the base point order in bytes (32 for P-256, 66 for P-521).
|
|
325
|
+
|
|
326
|
+
Required curve: P-256 (FIPS 186-3 §D.2.3). Recommended: P-384, P-521.
|
|
327
|
+
|
|
328
|
+
### Canonicalization
|
|
329
|
+
|
|
330
|
+
All algorithms take octet-stream or node-set, produce octet-stream output.
|
|
331
|
+
Output is UTF-8 (no BOM), NFC. See [XML-C14N], [XML-C14N11], [XML-EXC-C14N].
|
|
332
|
+
|
|
333
|
+
### Transforms
|
|
334
|
+
|
|
335
|
+
- **base64** (octet→octet, node-set→octet): decodes base64. For node-set input,
|
|
336
|
+
logically applies `self::text()`, sorts by document order, concatenates.
|
|
337
|
+
- **XPath Filtering** (octet|node-set → node-set): evaluates XPath per node,
|
|
338
|
+
includes nodes where boolean result is true. Includes `here()` function.
|
|
339
|
+
- **Enveloped Signature**: removes the containing `Signature` element from
|
|
340
|
+
digest calculation. Equivalent to specific XPath.
|
|
341
|
+
- **XSLT**: octet-stream → octet-stream via XSL stylesheet (sole child).
|
|
342
|
+
|
|
343
|
+
## XML Canonicalization Considerations
|
|
344
|
+
|
|
345
|
+
Signatures only work if verification uses the same bits as signing. XML surface
|
|
346
|
+
forms vary, so canonicalization standardizes before signing/verification.
|
|
347
|
+
|
|
348
|
+
Categories of change to canonicalize:
|
|
349
|
+
1. XML 1.0 syntax (line endings, attribute defaults, entity refs, attribute
|
|
350
|
+
normalization).
|
|
351
|
+
2. DOM/SAX information loss (attribute order, insignificant whitespace, namespace
|
|
352
|
+
declaration locations).
|
|
353
|
+
3. Charset conversion.
|
|
354
|
+
4. Namespace inheritance/context.
|
|
355
|
+
|
|
356
|
+
All canonicalization algorithms identified use UTF-8 (no BOM) and do not perform
|
|
357
|
+
character normalization. Applications SHOULD produce content in NFC.
|
|
358
|
+
|
|
359
|
+
### Namespace Context and Portable Signatures
|
|
360
|
+
|
|
361
|
+
Inclusive canonicalization "attracts" ancestor namespace context, breaking
|
|
362
|
+
signatures when subdocuments are moved. Exclusive canonicalization "repels"
|
|
363
|
+
ancestor context, preserving portability.
|
|
364
|
+
|
|
365
|
+
## Security Considerations
|
|
366
|
+
|
|
367
|
+
### 8.1 Transforms
|
|
368
|
+
|
|
369
|
+
- Only what is signed is secure.
|
|
370
|
+
- Only what is "seen" should be signed.
|
|
371
|
+
- "See" what is signed (operate over canonicalized form).
|
|
372
|
+
|
|
373
|
+
### 8.2 Security Models
|
|
374
|
+
|
|
375
|
+
Public-key signatures vs keyed-hash MACs have different trust models. Public
|
|
376
|
+
keys verify; only private-key holders can sign. MAC keys are shared; any
|
|
377
|
+
verifier can forge.
|
|
378
|
+
|
|
379
|
+
### 8.3 Algorithms, Key Lengths, Certificates
|
|
380
|
+
|
|
381
|
+
Conforming implementations MUST support RSA signature generation and
|
|
382
|
+
verification with public keys at least 2048 bits. 3072-bit recommended for
|
|
383
|
+
signatures verified beyond 2030.
|
|
384
|
+
|
|
385
|
+
### 8.4 Error Messages
|
|
386
|
+
|
|
387
|
+
Generic error responses; avoid leaking specifics about algorithm processing.
|
|
388
|
+
|
|
389
|
+
## References
|
|
390
|
+
|
|
391
|
+
- [XML-C14N] Canonical XML 1.0
|
|
392
|
+
- [XML-C14N11] Canonical XML 1.1
|
|
393
|
+
- [XML-EXC-C14N] Exclusive XML Canonicalization 1.0
|
|
394
|
+
- [PKCS1] RFC 3447 (RSA Cryptography Specifications v2.1)
|
|
395
|
+
- [FIPS-186-3] Digital Signature Standard
|
|
396
|
+
- [FIPS-180-3] Secure Hash Standard
|
|
397
|
+
- [HMAC] RFC 2104
|
|
398
|
+
- [RFC6931] Additional XML Security URIs
|
|
399
|
+
- [XPATH] XML Path Language 1.0
|
|
400
|
+
- [XMLDSIG-BESTPRACTICES] XML Signature Best Practices
|
|
@@ -110,10 +110,6 @@ RSpec.shared_examples "README Examples" do
|
|
|
110
110
|
describe "Error handling example" do
|
|
111
111
|
it "handles errors as shown in README" do
|
|
112
112
|
context = Moxml.new
|
|
113
|
-
if context.config.adapter_name == :ox
|
|
114
|
-
pending "Ox doesn't have a native XPath"
|
|
115
|
-
end
|
|
116
|
-
|
|
117
113
|
expect do
|
|
118
114
|
context.parse("<invalid>")
|
|
119
115
|
end.to raise_error(Moxml::ParseError)
|
|
@@ -24,20 +24,12 @@ RSpec.shared_examples "XPath Examples" do
|
|
|
24
24
|
end
|
|
25
25
|
|
|
26
26
|
it "finds nodes with namespaces" do
|
|
27
|
-
if context.config.adapter_name == :ox
|
|
28
|
-
pending "Ox doesn't have a native XPath"
|
|
29
|
-
end
|
|
30
|
-
|
|
31
27
|
titles = doc.xpath("//dc:title",
|
|
32
28
|
"dc" => "http://purl.org/dc/elements/1.1/")
|
|
33
29
|
expect(titles.map(&:text)).to eq(%w[First Second])
|
|
34
30
|
end
|
|
35
31
|
|
|
36
32
|
it "finds nodes by attributes" do
|
|
37
|
-
if %i[ox headed_ox].include?(context.config.adapter_name)
|
|
38
|
-
pending "Ox doesn't have native XPath, HeadedOx parser doesn't support .// syntax yet"
|
|
39
|
-
end
|
|
40
|
-
|
|
41
33
|
book = doc.at_xpath('//book[@id="2"]')
|
|
42
34
|
expect(book).not_to be_nil
|
|
43
35
|
title = book.at_xpath(".//dc:title",
|
|
@@ -46,9 +38,6 @@ RSpec.shared_examples "XPath Examples" do
|
|
|
46
38
|
end
|
|
47
39
|
|
|
48
40
|
it "finds nested attributes efficiently" do
|
|
49
|
-
if %i[ox headed_ox].include?(context.config.adapter_name)
|
|
50
|
-
pending "Ox doesn't have native XPath, HeadedOx parser doesn't support .// syntax yet"
|
|
51
|
-
end
|
|
52
41
|
# More efficient - specific path
|
|
53
42
|
titles1 = doc.xpath("//book/dc:title")
|
|
54
43
|
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
-----BEGIN PRIVATE KEY-----
|
|
2
|
+
MIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQC8F3ut738mezjz
|
|
3
|
+
Wg6J11OJCe28lyJXHcb6PbMJVm9NUC3MeMr27PI9s7ildxEodm9bOkXTIGD1ev4Y
|
|
4
|
+
4p69cjMeyn1vFoxUyE+IN9+0pSVs/ABf19/349MFMTC1mpWlBvRtOKyCkLObQ0hn
|
|
5
|
+
i+lMd4mQ+Ht+6+ZQNpNGIE0HcUUTH/r13AkmYLGYjlf2BwiqLP5MaxsdARormXwJ
|
|
6
|
+
wsJD92us5MHN2P4Pew+J+TyCMdM94h7TCR4vmhZrX7EQcbIfsIEYpfRs3IeORW90
|
|
7
|
+
CoXt7AgLmC+myMt8N/VF6OTKzXrShjGGeF88sikG0GSsIVWy7+tReqe4rfx/iavd
|
|
8
|
+
da0LhPJVAgMBAAECggEAMSugaPmFj11CJ5fg2hcA3v/J9vW5g/WkWTG89pFyek8e
|
|
9
|
+
Eeh4ArIxp4Cuog7s3NuNQ9eJfmZmAnZ7K60+mz7Z71A3F03ZNKbC59TXdeWAUavV
|
|
10
|
+
Ozj3c1nLBf30gl0dhq05Q74/lshWM54UtQEF5bgQLeZPfoATzt9dg8UY7ful95f/
|
|
11
|
+
StU1jJB16r7l8Oy1KyJE094ZL+dYSAaJaG/kb/hq857UJxU/9mmnqq0AsAseXrHm
|
|
12
|
+
9T4AR5vJjhh71+3BHsQNxP6oO2ErV+Bd4MddMRYZbyo7jVIN6t6nti+uB+reKAi0
|
|
13
|
+
FdcKNL+zldxPyKzt/dXh43M1Y60aFJ9jre/x+aqW9wKBgQDmGrguBixFJiBYdJXw
|
|
14
|
+
NXyIDKDYPRlP3+B28piybne3JVvnyZQ+v5KmDCAtE4i/hIkX9/pdyXAoAfsEI8dc
|
|
15
|
+
sarcFPynMjl+BpBxRKiMgIJvAsRh83HfrkewUTk9uhD3hqW4RlKZZIRlsPuEhIcG
|
|
16
|
+
2oWJzwuDlRsZyrlqLef94O59FwKBgQDRQmJgZm0faJfIFkmy17iCSmpLCHsef3iJ
|
|
17
|
+
gKr2yQBxOJMwConPauZEQ+YdTjk2XPo81TNpjWyBKZD+1RPPpJ5sFzUAfAqCfsxY
|
|
18
|
+
EZWCzuZKntiegwOsdRrp5FdAFrFCmttW0p5AnTH23PMKxT+7fMDmuwq1X3pS712X
|
|
19
|
+
hGujrnXncwKBgDKKrefWDUVHAZXMTd7MMMVFWNMGYJftycT2tlmC8CK3Pv+jhD9g
|
|
20
|
+
HtsAENU11DSU7PPp0QFmrI7tGHCpVzHiCHB8353t5zjqQjHO7eKmm3+8sNv++AU0
|
|
21
|
+
p6Rvws3vH6ju11mpgJ0WugoIHMbXwTzdJLXHV3UYfDJnF+DdonZeQKQTAoGAIo7K
|
|
22
|
+
/k6MAN7eCg4cN6vGbcXqTd/lrUCx4EtecIj7SLdmH03uOlHWGzn3W6maay7pqHgx
|
|
23
|
+
GGJho+cAagU4U1dFTmZ6u0zA05IrHvQwc7zFbVdUQME0LxvbyPqLqirVNUGrrWf0
|
|
24
|
+
+Ii9Qp50iLfQcZ8FoFUNTKyq391l4Gre99YM5J8CgYEA2EsA5AVf3Q4hkY5ImWN9
|
|
25
|
+
hWgcvKaa1Fw8n59iGExgoh1Zr4p9SWxaNxa/iY3q0wdiQBMihEgFdc3JMBiS3RSe
|
|
26
|
+
KZCpPAFeNW9RnXIQwnW06oyaiZkymLq96cYT5ToSLEoFl9/Z+ulMAYrfRJGszyR+
|
|
27
|
+
hJAW5QUsrp1RKksKftYOAlA=
|
|
28
|
+
-----END PRIVATE KEY-----
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
-----BEGIN PUBLIC KEY-----
|
|
2
|
+
MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAvBd7re9/Jns481oOiddT
|
|
3
|
+
iQntvJciVx3G+j2zCVZvTVAtzHjK9uzyPbO4pXcRKHZvWzpF0yBg9Xr+GOKevXIz
|
|
4
|
+
Hsp9bxaMVMhPiDfftKUlbPwAX9ff9+PTBTEwtZqVpQb0bTisgpCzm0NIZ4vpTHeJ
|
|
5
|
+
kPh7fuvmUDaTRiBNB3FFEx/69dwJJmCxmI5X9gcIqiz+TGsbHQEaK5l8CcLCQ/dr
|
|
6
|
+
rOTBzdj+D3sPifk8gjHTPeIe0wkeL5oWa1+xEHGyH7CBGKX0bNyHjkVvdAqF7ewI
|
|
7
|
+
C5gvpsjLfDf1Rejkys160oYxhnhfPLIpBtBkrCFVsu/rUXqnuK38f4mr3XWtC4Ty
|
|
8
|
+
VQIDAQAB
|
|
9
|
+
-----END PUBLIC KEY-----
|