epics 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (82) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +19 -0
  3. data/.rspec +2 -0
  4. data/.travis.yml +6 -0
  5. data/CONTRIBUTING.md +5 -0
  6. data/Gemfile +4 -0
  7. data/LICENSE.txt +165 -0
  8. data/README.md +197 -0
  9. data/Rakefile +7 -0
  10. data/epics.gemspec +50 -0
  11. data/lib/epics.rb +35 -0
  12. data/lib/epics/cct.rb +42 -0
  13. data/lib/epics/cd1.rb +42 -0
  14. data/lib/epics/cdd.rb +42 -0
  15. data/lib/epics/client.rb +216 -0
  16. data/lib/epics/error.rb +324 -0
  17. data/lib/epics/generic_request.rb +99 -0
  18. data/lib/epics/generic_upload_request.rb +89 -0
  19. data/lib/epics/haa.rb +40 -0
  20. data/lib/epics/hia.rb +78 -0
  21. data/lib/epics/hpb.rb +29 -0
  22. data/lib/epics/hpd.rb +40 -0
  23. data/lib/epics/htd.rb +40 -0
  24. data/lib/epics/ini.rb +69 -0
  25. data/lib/epics/key.rb +79 -0
  26. data/lib/epics/mgf.rb +41 -0
  27. data/lib/epics/middleware/parse_ebics.rb +15 -0
  28. data/lib/epics/middleware/xmlsig.rb +18 -0
  29. data/lib/epics/ptk.rb +52 -0
  30. data/lib/epics/response.rb +93 -0
  31. data/lib/epics/signer.rb +40 -0
  32. data/lib/epics/sta.rb +52 -0
  33. data/lib/epics/version.rb +3 -0
  34. data/lib/letter/ini.erb +231 -0
  35. data/spec/client_spec.rb +98 -0
  36. data/spec/fixtures/a006.pem +28 -0
  37. data/spec/fixtures/bank_e.pem +6 -0
  38. data/spec/fixtures/e002.pem +28 -0
  39. data/spec/fixtures/x002.pem +28 -0
  40. data/spec/fixtures/xml/cd1.xml +87 -0
  41. data/spec/fixtures/xml/ebics_business_nok.xml +21 -0
  42. data/spec/fixtures/xml/ebics_technical_nok.xml +12 -0
  43. data/spec/fixtures/xml/hia.xml +2 -0
  44. data/spec/fixtures/xml/hia_request_order_data.xml +2 -0
  45. data/spec/fixtures/xml/hpb.xml +34 -0
  46. data/spec/fixtures/xml/hpb_request.xml +34 -0
  47. data/spec/fixtures/xml/hpb_response.xml +21 -0
  48. data/spec/fixtures/xml/hpb_response_order.xml +22 -0
  49. data/spec/fixtures/xml/htd_order_data.xml +153 -0
  50. data/spec/fixtures/xml/ini.xml +2 -0
  51. data/spec/fixtures/xml/signature_pub_key_order_data.xml +2 -0
  52. data/spec/fixtures/xml/upload_init_response.xml +31 -0
  53. data/spec/hpb_spec.rb +15 -0
  54. data/spec/key_spec.rb +35 -0
  55. data/spec/mgf_spec.rb +36 -0
  56. data/spec/middleware/parse_ebics_spec.rb +18 -0
  57. data/spec/orders/cct_spec.rb +17 -0
  58. data/spec/orders/cd1_spec.rb +17 -0
  59. data/spec/orders/cdd_spec.rb +17 -0
  60. data/spec/orders/haa_spec.rb +11 -0
  61. data/spec/orders/hia_spec.rb +34 -0
  62. data/spec/orders/hpb_spec.rb +11 -0
  63. data/spec/orders/hpd_spec.rb +11 -0
  64. data/spec/orders/htd_spec.rb +11 -0
  65. data/spec/orders/ini_spec.rb +36 -0
  66. data/spec/orders/ptk_spec.rb +11 -0
  67. data/spec/orders/sta_spec.rb +11 -0
  68. data/spec/response_spec.rb +34 -0
  69. data/spec/signer_spec.rb +34 -0
  70. data/spec/spec_helper.rb +43 -0
  71. data/spec/support/ebics_matcher.rb +22 -0
  72. data/spec/xsd/ebics_H004.xsd +11 -0
  73. data/spec/xsd/ebics_hev.xsd +135 -0
  74. data/spec/xsd/ebics_keymgmt_request_H004.xsd +543 -0
  75. data/spec/xsd/ebics_keymgmt_response_H004.xsd +137 -0
  76. data/spec/xsd/ebics_orders_H004.xsd +1892 -0
  77. data/spec/xsd/ebics_request_H004.xsd +355 -0
  78. data/spec/xsd/ebics_response_H004.xsd +166 -0
  79. data/spec/xsd/ebics_signature.xsd +217 -0
  80. data/spec/xsd/ebics_types_H004.xsd +2426 -0
  81. data/spec/xsd/xmldsig-core-schema.xsd +318 -0
  82. metadata +319 -0
@@ -0,0 +1,99 @@
1
+ class Epics::GenericRequest
2
+ extend Forwardable
3
+ attr_accessor :client
4
+
5
+ def initialize(client)
6
+ self.client = client
7
+ end
8
+
9
+ def nonce
10
+ SecureRandom.hex(16)
11
+ end
12
+
13
+ def timestamp
14
+ Time.now.utc.iso8601
15
+ end
16
+
17
+ def_delegators :client, :host_id, :user_id, :partner_id
18
+
19
+ def root
20
+ "ebicsRequest"
21
+ end
22
+
23
+ def body
24
+ ""
25
+ end
26
+
27
+ def auth_signature
28
+ {
29
+ "ds:SignedInfo" => {
30
+ "ds:CanonicalizationMethod/" => {
31
+ :@Algorithm => "http://www.w3.org/TR/2001/REC-xml-c14n-20010315"
32
+ },
33
+ "ds:SignatureMethod/" => {
34
+ :@Algorithm => "http://www.w3.org/2001/04/xmldsig-more#rsa-sha256"
35
+ },
36
+ "ds:Reference/" => {
37
+ :@URI => "#xpointer(//*[@authenticate='true'])",
38
+ "ds:Transforms" => {
39
+ "ds:Transform/" => {
40
+ :@Algorithm => "http://www.w3.org/TR/2001/REC-xml-c14n-20010315"
41
+ }
42
+ },
43
+ "ds:DigestMethod/" => {
44
+ :@Algorithm => "http://www.w3.org/2001/04/xmlenc#sha256"
45
+ },
46
+ "ds:DigestValue/" => ""
47
+ }
48
+ },
49
+ "ds:SignatureValue/" => ""
50
+ }
51
+ end
52
+
53
+ def to_transfer_xml
54
+ Nokogiri::XML.parse(Gyoku.xml({
55
+ root => {
56
+ :"@xmlns:ds" => "http://www.w3.org/2000/09/xmldsig#",
57
+ :@xmlns => "urn:org:ebics:H004",
58
+ :@Version => "H004",
59
+ :@Revision => "1",
60
+ "header" => {
61
+ :@authenticate => true,
62
+ "static" => {
63
+ "HostID" => host_id,
64
+ "TransactionID" => transaction_id
65
+ },
66
+ "mutable" => {
67
+ "TransactionPhase" => "Transfer",
68
+ "SegmentNumber" => {
69
+ :@lastSegment => true,
70
+ :content! => 1
71
+ }
72
+ }
73
+ },
74
+ "AuthSignature" => auth_signature,
75
+ "body" => {
76
+ "DataTransfer" => {
77
+ "OrderData" => encrypted_order_data
78
+ }
79
+ }
80
+ }
81
+ }), nil, "utf-8").to_xml(save_with: Nokogiri::XML::Node::SaveOptions::AS_XML)
82
+ end
83
+
84
+ def to_xml
85
+ Nokogiri::XML.parse(Gyoku.xml( {
86
+ root => {
87
+ :"@xmlns:ds" => "http://www.w3.org/2000/09/xmldsig#",
88
+ :@xmlns => "urn:org:ebics:H004",
89
+ :@Version => "H004",
90
+ :@Revision => "1",
91
+ :header => header,
92
+ "AuthSignature" => auth_signature,
93
+ "body" => body
94
+ }
95
+ }), nil, "utf-8").to_xml(save_with: Nokogiri::XML::Node::SaveOptions::AS_XML)
96
+ end
97
+
98
+
99
+ end
@@ -0,0 +1,89 @@
1
+ class Epics::GenericUploadRequest < Epics::GenericRequest
2
+
3
+ attr_accessor :key
4
+ attr_accessor :document
5
+ attr_accessor :transaction_id
6
+
7
+ def initialize(client, document)
8
+ super(client)
9
+ self.document = document
10
+ self.key ||= cipher.random_key
11
+ end
12
+
13
+ def cipher
14
+ @cipher ||= OpenSSL::Cipher::Cipher.new("aes-128-cbc")
15
+ end
16
+
17
+ def digester
18
+ @digester ||= OpenSSL::Digest::SHA256.new
19
+ end
20
+
21
+ def body
22
+ {
23
+ "DataTransfer" => {
24
+ "DataEncryptionInfo" => {
25
+ :@authenticate => true,
26
+ "EncryptionPubKeyDigest" => {
27
+ :"@Version" => "E002",
28
+ :"@Algorithm" => "http://www.w3.org/2001/04/xmlenc#sha256",
29
+ :content! => client.bank_e.public_digest
30
+ },
31
+ "TransactionKey" => Base64.encode64(client.bank_e.key.public_encrypt(self.key)).gsub(/\n/,'')
32
+ },
33
+ "SignatureData" => {
34
+ :@authenticate => true,
35
+ :content! => encrypted_order_signature
36
+ }
37
+ }
38
+ }
39
+ end
40
+
41
+ def order_signature
42
+ Gyoku.xml("UserSignatureData" => {
43
+ :"@xmlns" => "http://www.ebics.org/S001",
44
+ :"@xmlns:xsi" => "http://www.w3.org/2001/XMLSchema-instance",
45
+ :"@xsi:schemaLocation" => "http://www.ebics.org/S001 http://www.ebics.org/S001/ebics_signature.xsd",
46
+ "OrderSignatureData" => {
47
+ "SignatureVersion" => "A006",
48
+ "SignatureValue" => signature_value,
49
+ "PartnerID" => partner_id,
50
+ "UserID" => user_id
51
+ }
52
+ })
53
+ end
54
+
55
+ def signature_value
56
+ Base64.encode64(client.a.sign( digester.digest(document.gsub(/\n|\r/, "")) )).gsub(/\n/, "")
57
+ end
58
+
59
+ def encrypt(d)
60
+ cipher.encrypt
61
+ cipher.padding = 0
62
+ cipher.key = self.key
63
+ (cipher.update(pad(d)) + cipher.final)
64
+ end
65
+
66
+ def encrypted_order_data
67
+ dst = Zlib::Deflate.deflate(document)
68
+
69
+ Base64.encode64(encrypt(dst)).gsub(/\n/,'')
70
+ end
71
+
72
+ def encrypted_order_signature
73
+ dst = Zlib::Deflate.deflate(order_signature)
74
+
75
+ Base64.encode64(encrypt(dst)).gsub(/\n/,'')
76
+ end
77
+
78
+ def pad(d)
79
+ if d.size % 32 == 0
80
+ return d
81
+ else
82
+ len = 32*((d.size / 32)+1)
83
+ padded = d.ljust(len, "\x01")
84
+ padded[-1] = ["#{len - d.size}".rjust(2, "0")].pack("*H")
85
+ padded
86
+ end
87
+ end
88
+
89
+ end
data/lib/epics/haa.rb ADDED
@@ -0,0 +1,40 @@
1
+ class Epics::HAA < Epics::GenericRequest
2
+
3
+ def header
4
+ {
5
+ :@authenticate => true,
6
+ static: {
7
+ "HostID" => host_id,
8
+ "Nonce" => nonce,
9
+ "Timestamp" => timestamp,
10
+ "PartnerID" => partner_id,
11
+ "UserID" => user_id,
12
+ "Product" => {
13
+ :@Language => "de",
14
+ :content! => "EPICS - a ruby ebics kernel"
15
+ },
16
+ "OrderDetails" => {
17
+ "OrderType" => "HAA",
18
+ "OrderAttribute" => "DZHNN",
19
+ "StandardOrderParams/" => ""
20
+ },
21
+ "BankPubKeyDigests" => {
22
+ "Authentication" => {
23
+ :@Version => "X002",
24
+ :@Algorithm => "http://www.w3.org/2001/04/xmlenc#sha256",
25
+ :content! => client.bank_x.public_digest
26
+ },
27
+ "Encryption" => {
28
+ :@Version => "E002",
29
+ :@Algorithm => "http://www.w3.org/2001/04/xmlenc#sha256",
30
+ :content! => client.bank_e.public_digest
31
+ }
32
+ },
33
+ "SecurityMedium" => "0000"
34
+ },
35
+ "mutable" => {
36
+ "TransactionPhase" => "Initialisation"
37
+ }
38
+ }
39
+ end
40
+ end
data/lib/epics/hia.rb ADDED
@@ -0,0 +1,78 @@
1
+ class Epics::HIA < Epics::GenericRequest
2
+
3
+ def root
4
+ "ebicsUnsecuredRequest"
5
+ end
6
+
7
+ def header
8
+ {
9
+ :@authenticate => true,
10
+ static: {
11
+ "HostID" => host_id,
12
+ "PartnerID" => partner_id,
13
+ "UserID" => user_id,
14
+ "Product" => {
15
+ :@Language => "de",
16
+ :content! => "EPICS - a ruby ebics kernel"
17
+ },
18
+ "OrderDetails" => {
19
+ "OrderType" => "HIA",
20
+ "OrderAttribute" => "DZNNN"
21
+ },
22
+ "SecurityMedium" => "0000"
23
+ },
24
+ "mutable" => ""
25
+ }
26
+ end
27
+
28
+ def body
29
+ {
30
+ "DataTransfer" => {
31
+ "OrderData" => Base64.strict_encode64(Zlib::Deflate.deflate(order_data))
32
+ }
33
+ }
34
+ end
35
+
36
+ def order_data
37
+ "<?xml version='1.0' encoding='utf-8'?>\n"+
38
+ Gyoku.xml("HIARequestOrderData" => {
39
+ :"@xmlns:ds" => "http://www.w3.org/2000/09/xmldsig#",
40
+ :"@xmlns" => "urn:org:ebics:H004",
41
+ "AuthenticationPubKeyInfo" => {
42
+ "PubKeyValue" => {
43
+ "ds:RSAKeyValue" => {
44
+ "ds:Modulus" => Base64.strict_encode64([client.x.n].pack("H*")),
45
+ "ds:Exponent" => Base64.strict_encode64(client.x.key.e.to_s(2))
46
+ }
47
+ },
48
+ "AuthenticationVersion" => "X002"
49
+ },
50
+ "EncryptionPubKeyInfo" => {
51
+ "PubKeyValue" => {
52
+ "ds:RSAKeyValue" => {
53
+ "ds:Modulus" => Base64.strict_encode64([client.e.n].pack("H*")),
54
+ "ds:Exponent" => Base64.strict_encode64(client.e.key.e.to_s(2))
55
+ }
56
+ },
57
+ "EncryptionVersion" => "E002"
58
+ },
59
+
60
+ "PartnerID" => partner_id,
61
+ "UserID" => user_id
62
+ })
63
+ end
64
+
65
+ def to_xml
66
+ Nokogiri::XML.parse(Gyoku.xml( {
67
+ root => {
68
+ :"@xmlns:ds" => "http://www.w3.org/2000/09/xmldsig#",
69
+ :@xmlns => "urn:org:ebics:H004",
70
+ :@Version => "H004",
71
+ :@Revision => "1",
72
+ :header => header,
73
+ "body" => body
74
+ }
75
+ }), nil, "utf-8").to_xml(save_with: Nokogiri::XML::Node::SaveOptions::AS_XML)
76
+ end
77
+
78
+ end
data/lib/epics/hpb.rb ADDED
@@ -0,0 +1,29 @@
1
+ class Epics::HPB < Epics::GenericRequest
2
+
3
+ def root
4
+ "ebicsNoPubKeyDigestsRequest"
5
+ end
6
+
7
+ def header
8
+ {
9
+ :@authenticate => true,
10
+ static: {
11
+ "HostID" => host_id,
12
+ "Nonce" => nonce,
13
+ "Timestamp" => timestamp,
14
+ "PartnerID" => partner_id,
15
+ "UserID" => user_id,
16
+ "Product" => {
17
+ :@Language => "de",
18
+ :content! => "EPICS - a ruby ebics kernel"
19
+ },
20
+ "OrderDetails" => {
21
+ "OrderType" => "HPB",
22
+ "OrderAttribute" => "DZHNN"
23
+ },
24
+ "SecurityMedium" => "0000"
25
+ },
26
+ "mutable/" => ""
27
+ }
28
+ end
29
+ end
data/lib/epics/hpd.rb ADDED
@@ -0,0 +1,40 @@
1
+ class Epics::HPD < Epics::GenericRequest
2
+
3
+ def header
4
+ {
5
+ :@authenticate => true,
6
+ static: {
7
+ "HostID" => host_id,
8
+ "Nonce" => nonce,
9
+ "Timestamp" => timestamp,
10
+ "PartnerID" => partner_id,
11
+ "UserID" => user_id,
12
+ "Product" => {
13
+ :@Language => "de",
14
+ :content! => "EPICS - a ruby ebics kernel"
15
+ },
16
+ "OrderDetails" => {
17
+ "OrderType" => "HPD",
18
+ "OrderAttribute" => "DZHNN",
19
+ "StandardOrderParams/" => ""
20
+ },
21
+ "BankPubKeyDigests" => {
22
+ "Authentication" => {
23
+ :@Version => "X002",
24
+ :@Algorithm => "http://www.w3.org/2001/04/xmlenc#sha256",
25
+ :content! => client.bank_x.public_digest
26
+ },
27
+ "Encryption" => {
28
+ :@Version => "E002",
29
+ :@Algorithm => "http://www.w3.org/2001/04/xmlenc#sha256",
30
+ :content! => client.bank_e.public_digest
31
+ }
32
+ },
33
+ "SecurityMedium" => "0000"
34
+ },
35
+ "mutable" => {
36
+ "TransactionPhase" => "Initialisation"
37
+ }
38
+ }
39
+ end
40
+ end
data/lib/epics/htd.rb ADDED
@@ -0,0 +1,40 @@
1
+ class Epics::HTD < Epics::GenericRequest
2
+
3
+ def header
4
+ {
5
+ :@authenticate => true,
6
+ static: {
7
+ "HostID" => host_id,
8
+ "Nonce" => nonce,
9
+ "Timestamp" => timestamp,
10
+ "PartnerID" => partner_id,
11
+ "UserID" => user_id,
12
+ "Product" => {
13
+ :@Language => "de",
14
+ :content! => "EPICS - a ruby ebics kernel"
15
+ },
16
+ "OrderDetails" => {
17
+ "OrderType" => "HTD",
18
+ "OrderAttribute" => "DZHNN",
19
+ "StandardOrderParams/" => ""
20
+ },
21
+ "BankPubKeyDigests" => {
22
+ "Authentication" => {
23
+ :@Version => "X002",
24
+ :@Algorithm => "http://www.w3.org/2001/04/xmlenc#sha256",
25
+ :content! => client.bank_x.public_digest
26
+ },
27
+ "Encryption" => {
28
+ :@Version => "E002",
29
+ :@Algorithm => "http://www.w3.org/2001/04/xmlenc#sha256",
30
+ :content! => client.bank_e.public_digest
31
+ }
32
+ },
33
+ "SecurityMedium" => "0000"
34
+ },
35
+ "mutable" => {
36
+ "TransactionPhase" => "Initialisation"
37
+ }
38
+ }
39
+ end
40
+ end
data/lib/epics/ini.rb ADDED
@@ -0,0 +1,69 @@
1
+ class Epics::INI < Epics::GenericRequest
2
+
3
+ def root
4
+ "ebicsUnsecuredRequest"
5
+ end
6
+
7
+ def header
8
+ {
9
+ :@authenticate => true,
10
+ static: {
11
+ "HostID" => host_id,
12
+ "PartnerID" => partner_id,
13
+ "UserID" => user_id,
14
+ "Product" => {
15
+ :@Language => "de",
16
+ :content! => "EPICS - a ruby ebics kernel"
17
+ },
18
+ "OrderDetails" => {
19
+ "OrderType" => "INI",
20
+ "OrderAttribute" => "DZNNN"
21
+ },
22
+ "SecurityMedium" => "0000"
23
+ },
24
+ "mutable" => ""
25
+ }
26
+ end
27
+
28
+ def body
29
+ {
30
+ "DataTransfer" => {
31
+ "OrderData" => Base64.strict_encode64(Zlib::Deflate.deflate(key_signature))
32
+ }
33
+ }
34
+ end
35
+
36
+ def key_signature
37
+ "<?xml version='1.0' encoding='utf-8'?>\n"+
38
+ Gyoku.xml("SignaturePubKeyOrderData" => {
39
+ :"@xmlns:ds" => "http://www.w3.org/2000/09/xmldsig#",
40
+ :"@xmlns" => "http://www.ebics.org/S001",
41
+ "SignaturePubKeyInfo" => {
42
+ "PubKeyValue" => {
43
+ "ds:RSAKeyValue" => {
44
+ "ds:Modulus" => Base64.strict_encode64([client.a.n].pack("H*")),
45
+ "ds:Exponent" => Base64.strict_encode64(client.a.key.e.to_s(2))
46
+ },
47
+ "TimeStamp" => timestamp
48
+ },
49
+ "SignatureVersion" => "A006"
50
+ },
51
+ "PartnerID" => partner_id,
52
+ "UserID" => user_id
53
+ })
54
+ end
55
+
56
+ def to_xml
57
+ Nokogiri::XML.parse(Gyoku.xml( {
58
+ root => {
59
+ :"@xmlns:ds" => "http://www.w3.org/2000/09/xmldsig#",
60
+ :@xmlns => "urn:org:ebics:H004",
61
+ :@Version => "H004",
62
+ :@Revision => "1",
63
+ :header => header,
64
+ "body" => body
65
+ }
66
+ }), nil, "utf-8").to_xml(save_with: Nokogiri::XML::Node::SaveOptions::AS_XML)
67
+ end
68
+
69
+ end