eddy 0.8.3 → 0.10.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (111) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +4 -4
  3. data/CHANGELOG.md +51 -1
  4. data/Gemfile.lock +8 -8
  5. data/README.md +1 -1
  6. data/data/code-lists/333.tsv +8 -0
  7. data/data/segments/amt.segment.yml +7 -0
  8. data/data/segments/bia.segment.yml +10 -0
  9. data/data/segments/cur.segment.yml +8 -0
  10. data/data/segments/dtm.segment.yml +1 -0
  11. data/data/segments/fob.segment.yml +8 -0
  12. data/data/segments/itd.segment.yml +13 -0
  13. data/data/segments/mtx.segment.yml +7 -0
  14. data/data/segments/n9.segment.yml +7 -0
  15. data/data/segments/per.segment.yml +13 -0
  16. data/data/segments/po1.segment.yml +6 -0
  17. data/data/segments/po3.segment.yml +13 -0
  18. data/data/segments/qty.segment.yml +10 -0
  19. data/data/segments/ref.segment.yml +1 -0
  20. data/data/segments/sac.segment.yml +4 -0
  21. data/data/segments/sch.segment.yml +7 -0
  22. data/data/segments/sdq.segment.yml +8 -0
  23. data/data/segments/txi.segment.yml +9 -0
  24. data/data/transaction_sets/810.edi.yml +93 -0
  25. data/data/transaction_sets/846.edi.yml +57 -0
  26. data/data/transaction_sets/850.edi.yml +73 -0
  27. data/data/transaction_sets/855.edi.yml +74 -0
  28. data/data/transaction_sets/856.edi.yml +54 -0
  29. data/eddy.gemspec +1 -1
  30. data/exe/eddy +1 -0
  31. data/lib/definitions/elements/generated/100.currency_code.rb +200 -0
  32. data/lib/definitions/elements/generated/146.shipment_method_of_payment.rb +65 -0
  33. data/lib/definitions/elements/generated/1551.message_text.rb +29 -0
  34. data/lib/definitions/elements/generated/280.exchange_rate.rb +29 -0
  35. data/lib/definitions/elements/generated/309.location_qualifier.rb +209 -0
  36. data/lib/definitions/elements/generated/310.location_identifier.rb +29 -0
  37. data/lib/definitions/elements/generated/311.shipment_type_code.rb +42 -0
  38. data/lib/definitions/elements/generated/322.load_empty_status_code.rb +40 -0
  39. data/lib/definitions/elements/generated/325.tax_identification_number.rb +29 -0
  40. data/lib/definitions/elements/generated/333.terms_basis_date_code.rb +44 -0
  41. data/lib/definitions/elements/generated/336.terms_type_code.rb +102 -0
  42. data/lib/definitions/elements/generated/338.terms_discount_percent.rb +29 -0
  43. data/lib/definitions/elements/generated/351.terms_discount_days_due.rb +30 -0
  44. data/lib/definitions/elements/generated/363.note_reference_code.rb +278 -0
  45. data/lib/definitions/elements/generated/364.communication_number.rb +29 -0
  46. data/lib/definitions/elements/generated/365.communication_number_qualifier.rb +77 -0
  47. data/lib/definitions/elements/generated/366.contact_function_code.rb +267 -0
  48. data/lib/definitions/elements/generated/369.free_form_description.rb +29 -0
  49. data/lib/definitions/elements/generated/370.terms_discount_due_date.rb +29 -0
  50. data/lib/definitions/elements/generated/371.change_reason_code.rb +67 -0
  51. data/lib/definitions/elements/generated/378.allowance_charge_percent_qualifier.rb +48 -0
  52. data/lib/definitions/elements/generated/386.terms_net_days.rb +30 -0
  53. data/lib/definitions/elements/generated/446.terms_net_due_date.rb +29 -0
  54. data/lib/definitions/elements/generated/522.amount_qualifier_code.rb +1510 -0
  55. data/lib/definitions/elements/generated/673.quantity_qualifier.rb +869 -0
  56. data/lib/definitions/elements/generated/755.report_type_code.rb +559 -0
  57. data/lib/definitions/elements/generated/954.percent.rb +29 -0
  58. data/lib/definitions/elements/generated/963.tax_type_code.rb +111 -0
  59. data/lib/definitions/elements/manual/156.state_or_province_code.rb +16 -1
  60. data/lib/definitions/elements/manual/i/I10.interchange_control_standards_identifier.rb +2 -2
  61. data/lib/definitions/elements/manual/i/I11.interchange_control_version_number.rb +1 -0
  62. data/lib/definitions/segments/generated/amt.rb +56 -0
  63. data/lib/definitions/segments/generated/bia.rb +107 -0
  64. data/lib/definitions/segments/generated/cur.rb +73 -0
  65. data/lib/definitions/segments/generated/dtm.rb +17 -0
  66. data/lib/definitions/segments/generated/fob.rb +73 -0
  67. data/lib/definitions/segments/generated/hl.rb +90 -0
  68. data/lib/definitions/segments/generated/itd.rb +158 -0
  69. data/lib/definitions/segments/generated/mtx.rb +56 -0
  70. data/lib/definitions/segments/generated/n2.rb +56 -0
  71. data/lib/definitions/segments/generated/n9.rb +56 -0
  72. data/lib/definitions/segments/generated/per.rb +158 -0
  73. data/lib/definitions/segments/generated/po1.rb +102 -0
  74. data/lib/definitions/segments/generated/po3.rb +158 -0
  75. data/lib/definitions/segments/generated/qty.rb +73 -0
  76. data/lib/definitions/segments/generated/ref.rb +17 -0
  77. data/lib/definitions/segments/generated/sac.rb +68 -0
  78. data/lib/definitions/segments/generated/sch.rb +56 -0
  79. data/lib/definitions/segments/generated/sdq.rb +73 -0
  80. data/lib/definitions/segments/generated/txi.rb +90 -0
  81. data/lib/definitions/transaction_sets/manual/846/846.rb +122 -0
  82. data/lib/definitions/transaction_sets/manual/846/loops/lin.rb +155 -0
  83. data/lib/definitions/transaction_sets/manual/846/loops/n1.rb +107 -0
  84. data/lib/definitions/transaction_sets/manual/846/loops/qty.rb +75 -0
  85. data/lib/definitions/transaction_sets/manual/846/loops/sch.rb +59 -0
  86. data/lib/definitions/transaction_sets/manual/846/loops/sln.rb +59 -0
  87. data/lib/definitions/transaction_sets/manual/850/850.rb +108 -1
  88. data/lib/definitions/transaction_sets/manual/850/loops/ctp.rb +47 -0
  89. data/lib/definitions/transaction_sets/manual/850/loops/n1.rb +31 -10
  90. data/lib/definitions/transaction_sets/manual/850/loops/n9.rb +59 -0
  91. data/lib/definitions/transaction_sets/manual/850/loops/pid.rb +47 -0
  92. data/lib/definitions/transaction_sets/manual/850/loops/po1.rb +78 -10
  93. data/lib/definitions/transaction_sets/manual/850/loops/sac.rb +47 -0
  94. data/lib/eddy.rb +49 -3
  95. data/lib/eddy/build/transaction_set_builder.rb +1 -1
  96. data/lib/eddy/config.rb +0 -21
  97. data/lib/eddy/data.rb +0 -40
  98. data/lib/eddy/data/persistence/base.rb +5 -11
  99. data/lib/eddy/data/persistence/memory.rb +14 -22
  100. data/lib/eddy/errors.rb +13 -9
  101. data/lib/eddy/models/element/composite.rb +2 -0
  102. data/lib/eddy/models/element/id.rb +1 -1
  103. data/lib/eddy/models/element/r.rb +1 -0
  104. data/lib/eddy/models/functional_group.rb +3 -2
  105. data/lib/eddy/models/interchange.rb +5 -1
  106. data/lib/eddy/parse.rb +4 -56
  107. data/lib/eddy/parse/interchange.rb +58 -0
  108. data/lib/eddy/summary/loop.rb +1 -1
  109. data/lib/eddy/summary/segment.rb +2 -1
  110. data/lib/eddy/version.rb +1 -1
  111. metadata +78 -5
@@ -0,0 +1,47 @@
1
+ module Eddy
2
+ module TransactionSets
3
+ module TS850
4
+ module Loops
5
+ module SAC
6
+
7
+ # ### Loop Summary:
8
+ #
9
+ # - Repeat: 25
10
+ # - Components:
11
+ # - SAC
12
+ class Base < Eddy::Models::Loop::Base
13
+ # @param store [Eddy::Data::Store]
14
+ # @return [void]
15
+ def initialize(store)
16
+ @repeat_limit = 25
17
+ super(store, Repeat)
18
+ end
19
+ end
20
+
21
+ # (see Eddy::TransactionSets::TS850::Loops::SAC::Base)
22
+ class Repeat < Eddy::Models::Loop::Repeat
23
+ # @param store [Eddy::Data::Store]
24
+ # @return [void]
25
+ def initialize(store)
26
+ @sac = Eddy::Segments::SAC.new(store)
27
+ super(
28
+ store,
29
+ @sac,
30
+ )
31
+ end
32
+
33
+ # (see Eddy::Segments::SAC)
34
+ #
35
+ # @yieldparam [Eddy::Segments::SAC]
36
+ # @return [Eddy::Segments::SAC]
37
+ def SAC()
38
+ yield(@sac) if block_given?
39
+ return @sac
40
+ end
41
+ end
42
+
43
+ end
44
+ end
45
+ end
46
+ end
47
+ end
@@ -1,6 +1,3 @@
1
- # EDI Toolkit.
2
- module Eddy; end
3
-
4
1
  require "eddy/version"
5
2
  require "eddy/errors"
6
3
  require "eddy/util"
@@ -16,3 +13,52 @@ Dir.glob(File.join(__dir__, "definitions", "segments", "**", "*.rb")).sort.each
16
13
  Dir.glob(File.join(__dir__, "definitions", "transaction_sets", "**", "*.rb")).sort.each { |file| require file }
17
14
 
18
15
  require "eddy/cli"
16
+
17
+ # EDI Toolkit.
18
+ module Eddy
19
+ # Configuration for Eddy.
20
+ #
21
+ # @return [Eddy::Config]
22
+ def self.config()
23
+ @config ||= Config.new
24
+ end
25
+
26
+ # Modify Eddy's current config.
27
+ #
28
+ # @example
29
+ # Eddy.configure do |config|
30
+ # config.persistence_method = :file
31
+ # end
32
+ #
33
+ # @yieldparam [Eddy::Config] config current Eddy config
34
+ # @return [void]
35
+ def self.configure()
36
+ yield self.config()
37
+ end
38
+
39
+ # Persistent data used by Eddy.
40
+ #
41
+ # @return [Eddy::Data::Persistence::Base]
42
+ def self.data
43
+ return @data if defined?(@data) && !@data.nil?
44
+ case Eddy.config.persistence_method
45
+ when :memory then @data = Eddy::Data::Persistence::Memory.new()
46
+ when :file then raise NotImplementedError
47
+ when :active_record
48
+ if defined?(Rails) && defined?(Eddy::Rails)
49
+ @data = Eddy::Data::Persistence::ActiveRecord.new()
50
+ else
51
+ raise Eddy::Errors::Error, "ActiveRecord persistence method can currently only be used with Ruby on Rails"
52
+ end
53
+ else raise Eddy::Errors::Error, "Unsupported persistence method: #{Eddy.config.persistence_method}"
54
+ end
55
+ return @data
56
+ end
57
+
58
+ # Set `@data` to `nil` so that a new persistence_method can be set up.
59
+ #
60
+ # @return [void]
61
+ def self.clear_data()
62
+ @data = nil
63
+ end
64
+ end
@@ -58,7 +58,7 @@ module Eddy
58
58
  def build_loops()
59
59
  FileUtils.mkdir_p(File.join(self.folder, "loops"))
60
60
  self.summary.unique_loops.each do |looop|
61
- File.open(File.join(self.folder, "loops", "#{looop.normalized_name}.rb"), "a") do |f|
61
+ File.open(File.join(self.folder, "loops", "#{looop.class_name}.rb"), "a") do |f|
62
62
  f.write(Eddy::Build::Loop.render(looop, self.normalized_name) + "\n")
63
63
  end
64
64
  end
@@ -41,25 +41,4 @@ module Eddy
41
41
  end
42
42
 
43
43
  end
44
-
45
- # Configuration for Eddy
46
- #
47
- # @return [Eddy::Config]
48
- def self.config()
49
- @config ||= Config.new
50
- end
51
-
52
- # Modify Eddy's current config
53
- #
54
- # @example
55
- # Eddy.configure do |config|
56
- # config.persistence_method = :file
57
- # end
58
- #
59
- # @yieldparam [Eddy::Config] config current Eddy config
60
- # @return [void]
61
- def self.configure()
62
- yield self.config
63
- end
64
-
65
44
  end
@@ -3,36 +3,8 @@ require "eddy/data/persistence/base"
3
3
  require "eddy/data/persistence/memory"
4
4
 
5
5
  module Eddy
6
-
7
- # Persistent data used by Eddy.
8
- #
9
- # @return [Eddy::Data::Persistence::Base]
10
- def self.data
11
- return @data if defined?(@data) && !@data.nil?
12
- case Eddy.config.persistence_method
13
- when :memory then @data = Eddy::Data::Persistence::Memory.new()
14
- when :file then raise NotImplementedError
15
- when :active_record
16
- if defined?(Rails) && defined?(Eddy::Rails)
17
- @data = Eddy::Data::Persistence::ActiveRecord.new()
18
- else
19
- raise Eddy::Errors::Error, "ActiveRecord persistence method can currently only be used with Ruby on Rails"
20
- end
21
- else raise Eddy::Errors::Error, "Unsupported persistence method: #{Eddy.config.persistence_method}"
22
- end
23
- return @data
24
- end
25
-
26
- # Set `@data` to `nil` so that a new persistence_method can be set up.
27
- #
28
- # @return [void]
29
- def self.clear_data()
30
- @data = nil
31
- end
32
-
33
6
  # Code for storing & generating data used by Eddy when generating EDI documents.
34
7
  module Data
35
-
36
8
  # Return a new, unique number.
37
9
  #
38
10
  # @return [Integer]
@@ -53,17 +25,5 @@ module Eddy
53
25
  Eddy.data.add_transaction_set_control_number(transaction_set_id, new_ctrl_num)
54
26
  return new_ctrl_num
55
27
  end
56
-
57
- # Return a new, unique number.
58
- #
59
- # @param functional_group [String]
60
- # @return [Integer]
61
- def self.new_functional_group_control_number(functional_group)
62
- existing = Eddy.data.functional_group_control_numbers(functional_group)
63
- new_ctrl_num = Eddy::Util.new_number(existing)
64
- Eddy.data.add_functional_group_control_number(functional_group, new_ctrl_num)
65
- return new_ctrl_num
66
- end
67
-
68
28
  end
69
29
  end
@@ -4,14 +4,15 @@ module Eddy
4
4
  # Base class for data persistence wrappers.
5
5
  class Base
6
6
 
7
- # @return [Array<Integer>]
8
- def interchange_control_numbers()
7
+ # Clear persisted data.
8
+ #
9
+ # @return [void]
10
+ def reset()
9
11
  raise NotImplementedError
10
12
  end
11
13
 
12
- # @param _functional_group [String]
13
14
  # @return [Array<Integer>]
14
- def functional_group_control_numbers(_functional_group)
15
+ def interchange_control_numbers()
15
16
  raise NotImplementedError
16
17
  end
17
18
 
@@ -27,13 +28,6 @@ module Eddy
27
28
  raise NotImplementedError
28
29
  end
29
30
 
30
- # @param _functional_group [String]
31
- # @param _new_ctrl_num [Integer]
32
- # @return [Array<Integer>]
33
- def add_functional_group_control_number(_functional_group, _new_ctrl_num)
34
- raise NotImplementedError
35
- end
36
-
37
31
  # @param _transaction_set_id [String]
38
32
  # @param _new_ctrl_num [Integer]
39
33
  # @return [Array<Integer>]
@@ -8,23 +8,23 @@ module Eddy
8
8
  def initialize()
9
9
  @data = {
10
10
  interchange_control_numbers: [],
11
- functional_group_control_numbers: {},
12
11
  transaction_set_control_numbers: {},
13
12
  }
14
13
  end
15
14
 
16
- # @return [Array<Integer>]
17
- def interchange_control_numbers()
18
- return @data[:interchange_control_numbers]
15
+ # Clear persisted data.
16
+ #
17
+ # @return [void]
18
+ def reset()
19
+ @data = {
20
+ interchange_control_numbers: [],
21
+ transaction_set_control_numbers: {},
22
+ }
19
23
  end
20
24
 
21
- # @param functional_group [String]
22
25
  # @return [Array<Integer>]
23
- def functional_group_control_numbers(functional_group)
24
- unless @data[:functional_group_control_numbers].key?(functional_group)
25
- @data[:functional_group_control_numbers][functional_group] = []
26
- end
27
- return @data[:functional_group_control_numbers][functional_group]
26
+ def interchange_control_numbers()
27
+ return @data[:interchange_control_numbers]
28
28
  end
29
29
 
30
30
  # @param transaction_set_id [String]
@@ -37,26 +37,18 @@ module Eddy
37
37
  end
38
38
 
39
39
  # @param new_ctrl_num [Integer]
40
- # @return [void]
40
+ # @return [Array<Integer>]
41
41
  def add_interchange_control_number(new_ctrl_num)
42
42
  self.interchange_control_numbers.append(new_ctrl_num)
43
- return nil
44
- end
45
-
46
- # @param functional_group [String]
47
- # @param new_ctrl_num [Integer]
48
- # @return [void]
49
- def add_functional_group_control_number(functional_group, new_ctrl_num)
50
- self.functional_group_control_numbers(functional_group).append(new_ctrl_num)
51
- return nil
43
+ return self.interchange_control_numbers()
52
44
  end
53
45
 
54
46
  # @param transaction_set_id [String]
55
47
  # @param new_ctrl_num [Integer]
56
- # @return [void]
48
+ # @return [Array<Integer>]
57
49
  def add_transaction_set_control_number(transaction_set_id, new_ctrl_num)
58
50
  self.transaction_set_control_numbers(transaction_set_id).append(new_ctrl_num)
59
- return nil
51
+ return self.transaction_set_control_numbers(transaction_set_id)
60
52
  end
61
53
 
62
54
  end
@@ -4,6 +4,18 @@ module Eddy
4
4
  # Exceptions raised by Eddy inherit from Error.
5
5
  class Error < StandardError; end
6
6
 
7
+ # Exception raised when an issue occurs while generating code.
8
+ class BuildError < Error; end
9
+
10
+ # Exception raised from a `render` method.
11
+ class RenderError < Error; end
12
+
13
+ # Exception raised when a definition file can't be found.
14
+ class MissingDefinitionError < Error; end
15
+
16
+ # Exception raised when a definition file can't be found.
17
+ class ParseError < Error; end
18
+
7
19
  # @!group Element Validation Errors
8
20
 
9
21
  # Exception raised by descendents of {Eddy::Models::Element::Base}.
@@ -99,15 +111,7 @@ module Eddy
99
111
  end
100
112
  end
101
113
 
102
- # @!endgroup Element Validation Errors
114
+ # @!endgroup
103
115
 
104
- # Exception raised when an issue occurs while generating code.
105
- class BuildError < Error; end
106
-
107
- # Exception raised from a `render` method.
108
- class RenderError < Error; end
109
-
110
- # Exception raised when a definition file can't be found.
111
- class MissingDefinitionError < Error; end
112
116
  end
113
117
  end
@@ -2,6 +2,8 @@ module Eddy
2
2
  module Models
3
3
  module Element
4
4
  # - [References to Component Data Elements - X12 RFI](http://www.x12.org/rfis/References%20to%20Component%20Data%20Elements.pdf)
5
+ # - [What’s the Repetition Separator Character in 5010 X12?](http://www.rdpcrystal.com/whats-the-repetition-separator-character-in-5010-x12/)
6
+ # - [Delimiters in data fields (RFI 1815)](http://rfi.x12.org/Request/Details/1815?stateViewModel=WPC.RFI.Models.ViewModels.RequestViewModel)
5
7
  class Composite; end
6
8
  end
7
9
  end
@@ -1,7 +1,7 @@
1
1
  module Eddy
2
2
  module Models
3
3
  module Element
4
- # Identifier (works with a code list specified by the dictionary).
4
+ # Identifier. Works with a code list specified by the dictionary.
5
5
  class ID < Base
6
6
 
7
7
  # @param min [Integer]
@@ -70,6 +70,7 @@ module Eddy
70
70
  when Integer
71
71
  return val.to_s.slice(0..max)
72
72
  when Float
73
+ # FIXME: This isn't correct.
73
74
  return val.to_s.slice(0..(max + 1))
74
75
  when Complex
75
76
  # TODO: Handle case
@@ -16,17 +16,18 @@ module Eddy
16
16
  attr_accessor :transaction_sets
17
17
 
18
18
  # @param store [Eddy::Data::Store]
19
+ # @param control_number [Integer]
19
20
  # @param transaction_sets [Eddy::Models::TransactionSet]
20
21
  # @return [void]
21
- def initialize(store, *transaction_sets)
22
+ def initialize(store, control_number, *transaction_sets)
22
23
  self.store = store
24
+ self.control_number = control_number
23
25
  transaction_sets.flatten!
24
26
  self.transaction_sets = transaction_sets || []
25
27
  if self.transaction_sets.length == 0
26
28
  raise ArgumentError, "At least one transaction set is required to create a functional group"
27
29
  end
28
30
  @id = self.transaction_sets.first.functional_group
29
- self.control_number = Eddy::Data.new_functional_group_control_number(@id)
30
31
  end
31
32
 
32
33
  # @return [Array<#render>]
@@ -44,7 +44,11 @@ module Eddy
44
44
  sorted_sets[ts.functional_group] ||= []
45
45
  sorted_sets[ts.functional_group] << ts
46
46
  end
47
- return sorted_sets.map { |_, value| Eddy::Models::FunctionalGroup.new(self.store, *value) }
47
+ i = 0
48
+ return sorted_sets.map do |_, value|
49
+ i += 1
50
+ Eddy::Models::FunctionalGroup.new(self.store, i, *value)
51
+ end
48
52
  end
49
53
 
50
54
  private
@@ -1,58 +1,6 @@
1
- module Eddy
2
- module Parse
3
- # Wrapper around an interchange file or string.
4
- class Interchange
5
-
6
- # Raw content of the interchange.
7
- # @return [String]
8
- attr_accessor :document
9
- # Component Element Separator
10
- # @return [String] (">")
11
- attr_accessor :component_separator
12
- # @return [String] ("~")
13
- attr_accessor :segment_separator
14
- # Data Element Separator
15
- # @return [String] ("\*")
16
- attr_accessor :element_separator
17
-
18
- # @param doc [String] EDI document.
19
- # @param component_separator [String] (">")
20
- # @param segment_separator [String] ("~")
21
- # @param element_separator [String] ("\*")
22
- # @return [void]
23
- def initialize(doc, component_separator: ">", segment_separator: "~", element_separator: "*")
24
- self.document = doc
25
- self.component_separator = component_separator
26
- self.segment_separator = segment_separator
27
- self.element_separator = element_separator
28
- end
29
-
30
- # @param path [String]
31
- # @return [self]
32
- def self.from_file(path, **kwargs)
33
- return self.new(File.read(path), **kwargs)
34
- end
1
+ require "eddy/parse/interchange"
35
2
 
36
- # @return [Array<Hash>]
37
- def parse()
38
- doc = self.document.gsub(/\n/, "")
39
- segments = doc.split(self.segment_separator)
40
- segments.map { |seg| self.parse_segment(seg) }
41
- end
42
-
43
- # @param seg [String]
44
- # @return [Hash]
45
- def parse_segment(seg)
46
- name, *elements = seg.split(self.element_separator)
47
- res = { name: name, elements: {} }
48
- elements.each_with_index do |value, index|
49
- next if value == ""
50
- key = sprintf("%s%02d", name, index + 1)
51
- res[:elements][key] = value
52
- end
53
- return res
54
- end
55
-
56
- end
57
- end
3
+ module Eddy
4
+ # Code for reading EDI documents.
5
+ module Parse; end
58
6
  end