pd_x12 1.4.8 → 1.5.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,15 +1,7 @@
1
1
  ---
2
- !binary "U0hBMQ==":
3
- metadata.gz: !binary |-
4
- NGMyNDQ1NzQ2MTYxNmE3ZmExY2QwNWE5MzYyNzY4MmIyYTc0OTEyYw==
5
- data.tar.gz: !binary |-
6
- ZjQwMmU2MmNhMDY2M2JlMWY2MTQ5OTcxMDc2MGJjY2M3MmE4OGNkZQ==
7
- !binary "U0hBNTEy":
8
- metadata.gz: !binary |-
9
- MjhlZTcwYzk1YjNlM2U0NDhjZWI2ZDFmN2ZmYTNiNzFmYjQwM2QwOTBmNjcw
10
- N2IzYmQ5NWJiMzBmNjJhYTJkZGIzZDBmYzA0MjBmY2IxMWI0NDY2NDliMWZl
11
- YTc4YjU4NzExZWU5MmY2ZDI0ZDA4YmRmMjBhNDc0M2Y2ZTQ4OTE=
12
- data.tar.gz: !binary |-
13
- OTkxN2JhZjIzY2VhZTc3ZmE0NTcyN2FmNDgwYjFiYjRiYmJjMDVjZTE3NTZi
14
- YTU5MjA0ZmMyYTJhNDgyNmZkNGU1MjZhYWY1NTM3ZDA4YWM2NTQzMzNlZDRk
15
- MzAxZWY1ZGJiYjI5OTc5OWVkYmQ1MzgzMDY1NmJlOWU2YzEwOTk=
2
+ SHA1:
3
+ metadata.gz: 7b0f3d7a04edbab0899aea20b8f9d05c89aaae44
4
+ data.tar.gz: b3bc5db7d9d6d92e19ff123cdb10bd603948aa8b
5
+ SHA512:
6
+ metadata.gz: 032582d5dfa38690ace90a558fc5d6ccab0db407fda69c093dafeb0a7316706cd2356f653ac25a065d764327a0b590f46edec64168ee52d5d267102c1d396bfa
7
+ data.tar.gz: 895464a84395e3733b5f2068a68afc6e5c0e03d33a26719b0a0d9769160156d4fea530bdda7229bf4cd11cc473dc6986399d8605ea99804124c74fe34444c251
data/README.md CHANGED
@@ -57,6 +57,9 @@ The authors of the project were inspired by the following works:
57
57
 
58
58
 
59
59
  # Change Log
60
+ 11/8/14 - release 1.5.0
61
+ * converted from ReXML to LibXML for speed improvement on XML parsing
62
+
60
63
  9/14/13 - release 1.4.7
61
64
  * Added 276 / 277 transaction messages
62
65
  * Fixed issue with 835.xml file
@@ -74,40 +77,3 @@ The authors of the project were inspired by the following works:
74
77
  * Renamed the gem to be all lower case so Rails and other frameworks autoload the project as a gem
75
78
  * Added an each method to segments to simplify looping through repeating segments
76
79
 
77
- 1/26/13 - relesase 1.3.6
78
- * changed the referencing of the misc directory so that local copies of the xml definitions are not required
79
- * added an init.rb file in the root
80
-
81
- 12/2/12 - release 1.3.2
82
- * Added the 835 transaction
83
-
84
- 12/1/12 - release 1.3.1
85
- * Added the 837p transaction
86
-
87
- 11/23/12 - release 1.3.0
88
- * Updated to work with Ruby version >= 1.9.1
89
- * includes bundle gem_tasks
90
- * In misc/T105.xml escaped ampersand in Dun & Bradstreet
91
-
92
- 4/18/12 - Release 1.2.0
93
- * Works with Ruby version >= 1.8.6
94
- * All the gem info has been changed to use bundler
95
- * Everything has been renamed to be lower case and work on case sensitive systems
96
- * Stopped including REXML, which was causing problems with Rails 3 and mailer
97
- * To use version 1.2.0, install with "$gem install sx12"
98
-
99
- 5/15/09 - Release 1.1.0
100
- * Ported X12 definitions and definition parser from proprietary d12 language to XML.
101
- * Added X12 definitions for 270 message and all its dependent segments and validation tables.
102
-
103
- 3/19/09 - Release 0.1.0
104
- * Implemented field constants.
105
- * Implemented separate definition files for segments and validation tables.
106
-
107
- 11/15/08 - Release 0.0.5, first public one
108
- * Added comments.
109
- * Added examples.
110
- * Wrote README
111
-
112
- 4/10/08 - Release 0.0.1
113
- * Internal release for testing
data/lib/x12.rb CHANGED
@@ -25,6 +25,9 @@
25
25
  #
26
26
  # Package implementing direct manipulation of X12 structures using Ruby syntax.
27
27
 
28
+ require "libxml"
29
+ require 'pp'
30
+
28
31
  require "x12/version"
29
32
  require 'x12/base'
30
33
  require 'x12/empty'
@@ -37,6 +40,8 @@ require 'x12/xmldefinitions'
37
40
  require 'x12/parser'
38
41
 
39
42
  module X12
43
+ include LibXML
44
+
40
45
  EMPTY = Empty.new()
41
46
  TEST_REPEAT = 100
42
47
 
@@ -23,16 +23,16 @@
23
23
  #
24
24
  module X12
25
25
 
26
- # $Id: Base.rb 70 2009-03-26 19:25:39Z ikk $
27
26
  #
28
27
  # Base class for Segment, Composite, and Loop. Contains setable
29
28
  # segment_separator, field_separator, and composite_separator fields.
30
-
29
+ #
30
+
31
31
  class Base
32
32
 
33
- attr_reader :name, :repeats
34
- attr_reader :segment_separator, :field_separator, :composite_separator, :next_repeat, :parsed_str, :nodes
35
- attr_writer :segment_separator, :field_separator, :composite_separator, :next_repeat, :parsed_str, :nodes
33
+ attr_reader :name, :repeats
34
+ attr_accessor :segment_separator, :field_separator, :composite_separator, :next_repeat, :parsed_str, :nodes
35
+
36
36
 
37
37
  # Creates a new base element with a given name, array of sub-elements, and array of repeats if any.
38
38
  def initialize(name, arr, repeats = nil)
@@ -23,9 +23,9 @@
23
23
  #
24
24
  module X12
25
25
 
26
- # $Id: Composite.rb 35 2008-11-13 18:33:44Z ikk $
27
26
  #
28
27
  # Class implementing a composite field.
28
+ #
29
29
 
30
30
  class Composite < Base
31
31
 
@@ -22,11 +22,11 @@
22
22
  #++
23
23
  #
24
24
  module X12
25
-
26
- # $Id: Empty.rb 35 2008-11-13 18:33:44Z ikk $
25
+
27
26
  #
28
27
  # Class indicating the absense of any X12 element, be it loop, segment, or anything else like that.
29
-
28
+ #
29
+
30
30
  class Empty < Base
31
31
 
32
32
  # Create a new empty
@@ -22,11 +22,11 @@
22
22
  #++
23
23
  #
24
24
  module X12
25
-
26
- # $Id: Field.rb 90 2009-05-13 19:51:27Z ikk $
25
+
27
26
  #
28
27
  # Class to represent a segment field. Please note, it's not a descendant of Base.
29
-
28
+ #
29
+
30
30
  class Field
31
31
  attr_reader :name, :type, :required, :min_length, :max_length, :validation
32
32
  attr_writer :content
@@ -22,8 +22,6 @@
22
22
  #++
23
23
  #
24
24
 
25
- require "rexml/document"
26
- require 'pp'
27
25
 
28
26
  module X12
29
27
 
@@ -34,20 +32,7 @@ module X12
34
32
  class Parser
35
33
 
36
34
  # These constitute prohibited file names under Microsoft
37
- MS_DEVICES = [
38
- 'CON',
39
- 'PRN',
40
- 'AUX',
41
- 'CLOCK$',
42
- 'NUL',
43
- 'COM1',
44
- 'LPT1',
45
- 'LPT2',
46
- 'LPT3',
47
- 'COM2',
48
- 'COM3',
49
- 'COM4',
50
- ]
35
+ MS_DEVICES = ['CON', 'PRN', 'AUX', 'CLOCK$', 'NUL', 'COM1', 'LPT1', 'LPT2', 'LPT3', 'COM2', 'COM3', 'COM4']
51
36
 
52
37
  # Creates a parser out of a definition
53
38
  def initialize(file_name)
@@ -22,10 +22,10 @@
22
22
  #++
23
23
  #
24
24
  module X12
25
-
26
- # $Id: Segment.rb 82 2009-05-13 18:07:22Z ikk $
25
+
27
26
  #
28
27
  # Implements a segment containing fields or composites
28
+ #
29
29
 
30
30
  class Segment < Base
31
31
 
@@ -22,11 +22,11 @@
22
22
  #++
23
23
  #
24
24
  module X12
25
-
26
- # $Id: Table.rb 35 2008-11-13 18:33:44Z ikk $
25
+
27
26
  #
28
27
  # This just a named hash to store validation tables.
29
-
28
+ #
29
+
30
30
  class Table < Hash
31
31
  attr_reader :name
32
32
 
@@ -1,3 +1,3 @@
1
1
  module X12
2
- VERSION = "1.4.8"
2
+ VERSION = "1.5.0"
3
3
  end
@@ -22,20 +22,18 @@
22
22
  #++
23
23
  #
24
24
 
25
- require "rexml/document"
26
25
 
27
26
  module X12
28
-
29
- # $Id: XMLDefinitions.rb 90 2009-05-13 19:51:27Z ikk $
30
27
  #
31
28
  # A class for parsing X12 message definition expressed in XML format.
32
-
29
+ #
30
+
33
31
  class XMLDefinitions < Hash
34
32
 
35
33
  # Parse definitions out of XML file
36
34
  def initialize(str)
37
- doc = REXML::Document.new(str)
38
- definitions = doc.root.name =~ /^Definition$/i ? doc.root.elements.to_a : [doc.root]
35
+ doc = LibXML::XML::Document.string(str)
36
+ definitions = doc.root.name =~ /^Definition$/i ? doc.root.find('*').to_a : [doc.root]
39
37
 
40
38
  definitions.each { |element|
41
39
  #puts element.name
@@ -130,7 +128,7 @@ module X12
130
128
  def parse_table(e)
131
129
  name, min, max, type, required, validation = parse_attributes(e)
132
130
 
133
- content = e.get_elements("Entry").inject({}) {|t, entry|
131
+ content = e.find("Entry").inject({}) {|t, entry|
134
132
  t[entry.attributes["name"]] = entry.attributes["value"]
135
133
  t
136
134
  }
@@ -140,7 +138,7 @@ module X12
140
138
  def parse_segment(e)
141
139
  name, min, max, type, required, validation = parse_attributes(e)
142
140
 
143
- fields = e.get_elements("Field").inject([]) {|f, field|
141
+ fields = e.find("Field").inject([]) {|f, field|
144
142
  f << parse_field(field)
145
143
  }
146
144
  Segment.new(name, fields, Range.new(min, max))
@@ -149,7 +147,7 @@ module X12
149
147
  def parse_composite(e)
150
148
  name, min, max, type, required, validation = parse_attributes(e)
151
149
 
152
- fields = e.get_elements("Field").inject([]) {|f, field|
150
+ fields = e.find("Field").inject([]) {|f, field|
153
151
  f << parse_field(field)
154
152
  }
155
153
  Composite.new(name, fields)
@@ -158,7 +156,7 @@ module X12
158
156
  def parse_loop(e)
159
157
  name, min, max, type, required, validation = parse_attributes(e)
160
158
 
161
- components = e.elements.to_a.inject([]){|r, element|
159
+ components = e.find('*').to_a.inject([]){|r, element|
162
160
  r << case element.name
163
161
  when /loop/i
164
162
  parse_loop(element)
@@ -2,8 +2,8 @@
2
2
  # This file is part of the X12Parser library that provides tools to
3
3
  # manipulate X12 messages using Ruby native syntax.
4
4
  #
5
- # http://x12parser.rubyforge.org
6
- #
5
+ # http://x12parser.rubyforge.org
6
+ #
7
7
  # Copyright (C) 2012 P&D Technical Solutions, LLC.
8
8
  #
9
9
  # This library is free software; you can redistribute it and/or
@@ -75,21 +75,74 @@ SE*45*0001~
75
75
  GE*1*45920001~
76
76
  IEA*1*000004592~"
77
77
 
78
-
79
- def setup
78
+ MESSAGE1 = "ISA*00* *00* *ZZ*5010TEST *ZZ*835RECVR *110930*1105*^*00501*000004592*0*T*:~
79
+ GS*HP*330897513*835RECVR*20140514*1605*188915716*X*005010X221A1~
80
+ ST*835*0001~
81
+ BPR*I*280.56*C*ACH*CCP*01*011900445*DA*0000009046*1066033492**01*031201360*DA*7869322623*20140519~
82
+ TRN*1*814133500000415*1066033492~
83
+ REF*EV*330897513~
84
+ DTM*405*20140514~
85
+ N1*PR*AETNA~
86
+ N3*151 FARMINGTON AVENUE~
87
+ N4*HARTFORD*CT*06156~
88
+ PER*BL*PROVIDER SERVICE~
89
+ N1*PE*SERVICES OF INTEREST*XX*1457686560~
90
+ N3*77 WILLIAM ST~
91
+ N4*SOUTH RIVER*NJ*088821072~
92
+ REF*PQ*149850620~
93
+ REF*TJ*263895688~
94
+ CLP*687400A140313*22*-150*-45**13*E7TWCV68K0000*11*1~
95
+ NM1*QC*1*BETTY*ELIZABETH****MI*W193272207~
96
+ NM1*82*1*HURTEM*DEBBIE****XX*1457686560~
97
+ REF*1L*0701087-022-00002-UA~
98
+ REF*CE*AETNA~
99
+ DTM*050*20140314~
100
+ DTM*232*20140308~
101
+ DTM*233*20140308~
102
+ PER*CX**TE*8886323862~
103
+ SVC*HC:90834*-150*-45**1~
104
+ DTM*472*20140308~
105
+ CAS*CO*45*-90~
106
+ CAS*PR*3*-15~
107
+ CLP*652000A140307*22*-150*-45**13*ECABDCJH40000*11*1~
108
+ NM1*QC*1*VANDERBROOK*JOHN~
109
+ NM1*IL*1*KRAFT*FRANK****MI*W142202122~
110
+ NM1*74*1**FRANCES*G~
111
+ NM1*82*1*HOMLEY*MEGAN****XX*1457686560~
112
+ REF*1L*0701087-022-00003-UA~
113
+ REF*CE*AETNA~
114
+ DTM*050*20140310~
115
+ DTM*232*20140306~
116
+ DTM*233*20140306~
117
+ PER*CX**TE*8886323862~
118
+ SVC*HC:90834*-150*-45**1~
119
+ DTM*472*20140306~
120
+ CAS*CO*45*-90~
121
+ CAS*PR*3*-15~
122
+ AMT*B6*60~
123
+ SE*44*0001~
124
+ GE*7*188915716~
125
+ IEA*1*188915716~"
126
+
127
+ def setup
80
128
  # readable format
81
129
  @message = MESSAGE
82
130
  # make the result usable in the tests
83
131
  @message.gsub!(/\n/,'')
84
-
85
- @parser = X12::Parser.new('835.xml')
86
- @r = @parser.parse('835', @message)
132
+
133
+ @parser = X12::Parser.new('835.xml')
134
+ @r = @parser.parse('835', @message)
135
+
136
+ # second message for testing negatives
137
+ @message1 = MESSAGE1
138
+ @message1.gsub!(/\n/,'')
139
+ @r1 = @parser.parse('835', @message1)
87
140
  end
88
-
141
+
89
142
  def teardown
90
143
  #nothing
91
144
  end
92
-
145
+
93
146
  def test_ISA_IEA
94
147
  assert_equal('ISA*00* *00* *ZZ*5010TEST *ZZ*835RECVR *110930*1105*^*00501*000004592*0*T*:~', @r.ISA.to_s)
95
148
  assert_equal('5010TEST ', @r.ISA.InterchangeSenderId)
@@ -101,17 +154,17 @@ IEA*1*000004592~"
101
154
  assert_equal("45920001", @r.GS.GroupControlNumber)
102
155
  assert_equal(@r.GS.GroupControlNumber, @r.GE.GroupControlNumber)
103
156
  end
104
-
157
+
105
158
  def test_segment_each0
106
159
  assert_equal(3, @r.L1000A.PER.size)
107
-
160
+
108
161
  # loop through the PER segment and find the CX record
109
162
  @r.L1000A.PER.each do |per|
110
163
  if per.ContactFunctionCode == "CX"
111
164
  assert_equal("TE", per.CommunicationNumberQualifier1)
112
165
  end
113
- end
114
-
166
+ end
167
+
115
168
  #loop through the PER segment anf find the BL record
116
169
  @r.L1000A.PER.each do |per|
117
170
  if per.ContactFunctionCode == "BL"
@@ -119,27 +172,37 @@ IEA*1*000004592~"
119
172
  assert_equal("TECHNICAL CONTACT", per.Name)
120
173
  assert_equal("EM", per.CommunicationNumberQualifier2)
121
174
  assert_equal("PAYER@PAYER.COM", per.CommunicationNumber2)
122
-
175
+
123
176
  end
124
- end
125
-
177
+ end
178
+
126
179
  #loop through and find the IC record
127
180
  @r.L1000A.PER.each do |per|
128
181
  if per.ContactFunctionCode == "IC"
129
182
  assert_equal("UR", per.CommunicationNumberQualifier1)
130
183
  assert_equal("WWW.PAYER.COM", per.CommunicationNumber1)
131
184
  end
132
- end
133
-
185
+ end
186
+
134
187
  end
135
-
188
+
136
189
  def test_L2000_loop
137
190
  assert_equal("1", @r.L2000.LX.AssignedNumber)
138
191
  assert_equal("CLP*EDI DENIAL*1*1088*0*1088*HM*CLAIMNUMBER1*21~", @r.L2000.L2100[0].CLP.to_s)
139
192
  assert_equal("CLP*EDI PAID*1*100*57.44*30*12*CLAIMNUMBER2*11~", @r.L2000[0].L2100[1].CLP.to_s)
140
193
  end
141
-
142
-
194
+
195
+
196
+ def test_negative
197
+ # puts @r1.L2000[0].L2100[1].CLP.inspect
198
+ assert_equal("-150", @r1.L2000[0].L2100[1].CLP.MonetaryAmount1)
199
+ m1 = @r1.L2000[0].L2100[1].CLP.MonetaryAmount1
200
+ assert_equal(-150, m1.to_i)
201
+
202
+ assert_equal("-45", @r1.L2000[0].L2100[1].CLP.MonetaryAmount2)
203
+ assert_equal(-45, @r1.L2000[0].L2100[1].CLP.MonetaryAmount2.to_i)
204
+ end
205
+
143
206
  def test_timing
144
207
  start = Time::now
145
208
  X12::TEST_REPEAT.times do
@@ -4,8 +4,8 @@ require File.expand_path('../lib/x12/version', __FILE__)
4
4
  Gem::Specification.new do |gem|
5
5
  gem.name = "pd_x12"
6
6
  gem.version = X12::VERSION
7
- gem.authors = ["App Design, Inc.", "Sean Walberg", "Marty Petersen", "William Bajzek"]
8
- gem.email = ["info@appdesign.com", "sean@ertw.com", "themooseman@comcast.net"]
7
+ gem.authors = ["Marty Petersen"]
8
+ gem.email = ["themooseman@comcast.net"]
9
9
  gem.description = %q{A gem to handle parsing and generation of ANSI X12 documents. Currently tested with Ruby >= 1.9.2. Gem supports X12 EDI transactions 270, 997, 837p and 835. Anyone wanting to create additional XML files for other transactions welcomed. }
10
10
  gem.summary = %q{A gem to handle parsing and generation of ANSI X12 documents}
11
11
  gem.homepage = "https://github.com/mjpete3/x12"
@@ -15,4 +15,7 @@ Gem::Specification.new do |gem|
15
15
  gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) }
16
16
  gem.test_files = gem.files.grep(%r{^(test|spec|features)/})
17
17
  gem.require_paths = ["lib"]
18
+
19
+ gem.add_dependency 'libxml-ruby'
20
+
18
21
  end
metadata CHANGED
@@ -1,31 +1,40 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: pd_x12
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.4.8
4
+ version: 1.5.0
5
5
  platform: ruby
6
6
  authors:
7
- - App Design, Inc.
8
- - Sean Walberg
9
7
  - Marty Petersen
10
- - William Bajzek
11
8
  autorequire:
12
9
  bindir: bin
13
10
  cert_chain: []
14
- date: 2014-05-04 00:00:00.000000000 Z
15
- dependencies: []
16
- description: ! 'A gem to handle parsing and generation of ANSI X12 documents. Currently
11
+ date: 2014-11-08 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: libxml-ruby
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ description: 'A gem to handle parsing and generation of ANSI X12 documents. Currently
17
28
  tested with Ruby >= 1.9.2. Gem supports X12 EDI transactions 270, 997, 837p and
18
29
  835. Anyone wanting to create additional XML files for other transactions welcomed. '
19
30
  email:
20
- - info@appdesign.com
21
- - sean@ertw.com
22
31
  - themooseman@comcast.net
23
32
  executables: []
24
33
  extensions: []
25
34
  extra_rdoc_files: []
26
35
  files:
27
- - .gitignore
28
- - .project
36
+ - ".gitignore"
37
+ - ".project"
29
38
  - Gemfile
30
39
  - LICENSE
31
40
  - README.md
@@ -1896,17 +1905,17 @@ require_paths:
1896
1905
  - lib
1897
1906
  required_ruby_version: !ruby/object:Gem::Requirement
1898
1907
  requirements:
1899
- - - ! '>='
1908
+ - - ">="
1900
1909
  - !ruby/object:Gem::Version
1901
1910
  version: '0'
1902
1911
  required_rubygems_version: !ruby/object:Gem::Requirement
1903
1912
  requirements:
1904
- - - ! '>='
1913
+ - - ">="
1905
1914
  - !ruby/object:Gem::Version
1906
1915
  version: '0'
1907
1916
  requirements: []
1908
1917
  rubyforge_project:
1909
- rubygems_version: 2.0.5
1918
+ rubygems_version: 2.2.2
1910
1919
  signing_key:
1911
1920
  specification_version: 4
1912
1921
  summary: A gem to handle parsing and generation of ANSI X12 documents