Skip to content

Commit

Permalink
Merge pull request #9 from pennylane-hq/nb/add-operation-parsing
Browse files Browse the repository at this point in the history
Add operation parsing
  • Loading branch information
frantisekrokusek authored Sep 28, 2023
2 parents 506aa9d + 67c9028 commit 914dadf
Show file tree
Hide file tree
Showing 8 changed files with 198 additions and 1 deletion.
2 changes: 1 addition & 1 deletion cfonb.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

Gem::Specification.new do |s|
s.name = 'cfonb'
s.version = '0.0.3'
s.version = '0.0.4'
s.summary = 'CFONB parser'
s.description = 'An easy to use CFONB format parser'
s.authors = ['Johan Le Bray', 'Frantisek Rokusek']
Expand Down
4 changes: 4 additions & 0 deletions lib/cfonb.rb
Original file line number Diff line number Diff line change
Expand Up @@ -30,4 +30,8 @@ module CFONB
def self.parse(input, optimistic: false)
Parser.new(input).parse(optimistic: optimistic)
end

def self.parse_operation(input, optimistic: false)
Parser.new(input).parse_operation(optimistic: optimistic)
end
end
4 changes: 4 additions & 0 deletions lib/cfonb/error.rb
Original file line number Diff line number Diff line change
Expand Up @@ -12,4 +12,8 @@ class UnstartedStatementError < ParserError; end
class UnstartedOperationError < ParserError; end

class UnfinishedStatementError < ParserError; end

class AlreadyDefinedOperationError < ParserError; end

class UnhandledLineCodeError < ParserError; end
end
26 changes: 26 additions & 0 deletions lib/cfonb/parser.rb
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,15 @@ def parse(optimistic: false)
statements
end

def parse_operation(optimistic: false)
@current_operation = nil
@optimistic = optimistic

each_line { parse_operation_line(_1) }

current_operation
end

private

attr_reader :input, :statements, :current_statement, :current_operation, :optimistic
Expand Down Expand Up @@ -75,6 +84,23 @@ def parse_line(line)
handle_error(e)
end

def parse_operation_line(line)
line = CFONB::LineParser.parse(line)

case line.code
when OPERATION_CODE
return handle_error(AlreadyDefinedOperationError) if current_operation

@current_operation = CFONB::Operation.new(line)
when OPERATION_DETAIL_CODE
return handle_error(UnstartedOperationError) unless current_operation

current_operation.merge_detail(line)
else
return handle_error(UnhandledLineCodeError)
end
end

def handle_error(error)
raise error unless optimistic
end
Expand Down
148 changes: 148 additions & 0 deletions spec/cfonb/parser_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -467,4 +467,152 @@
end
end
end

describe '.parse_operation' do
subject(:operation) { described_class.new(input).parse_operation }

let(:input) { File.read('spec/files/operation.txt') }

context 'with a valid input' do
it 'returns CFONB::Operation' do
expect(operation).to be_an_instance_of(CFONB::Operation)
end

it 'parses correctly' do
expect(operation).to have_attributes(
amount: -32.21,
currency: 'EUR',
date: Date.new(2019, 5, 16),
exoneration_code: '0',
interbank_code: 'B1',
internal_code: '9162',
label: "PRLV SEPA TEST CABINET\nMENSUEAUHTR13133",
number: 0,
reference: 'REFERENCE - OTHER REFERENCE',
rejection_code: '',
unavailability_code: '0',
value_date: Date.new(2019, 5, 16),
original_currency: nil,
original_amount: nil,
debtor: 'INTERNET SFR'
)
end
end

context 'with an already defined operation' do
let(:input) { File.read('spec/files/operation_already_defined.txt') }

it 'raises AlreadyDefinedOperationError' do
expect do
operation
end.to raise_error(CFONB::AlreadyDefinedOperationError)
end
end

context 'with an unstarted operation' do
let(:input) { File.read('spec/files/operation_unstarted.txt') }

it 'raises UnstartedOperationError' do
expect do
operation
end.to raise_error(CFONB::UnstartedOperationError)
end
end

context 'with an unhandled line code' do
let(:input) { File.read('spec/files/example.txt') }

it 'raises UnhandledLineCodeError' do
expect do
operation
end.to raise_error(CFONB::UnhandledLineCodeError)
end
end

context 'with an optimistic parse' do
subject(:operation) { described_class.new(input).parse_operation(optimistic: true) }

context 'with a valid input' do
it 'returns CFONB::Operation' do
expect(operation).to be_an_instance_of(CFONB::Operation)
end

it 'parses correctly' do
expect(operation).to have_attributes(
amount: -32.21,
currency: 'EUR',
date: Date.new(2019, 5, 16),
exoneration_code: '0',
interbank_code: 'B1',
internal_code: '9162',
label: "PRLV SEPA TEST CABINET\nMENSUEAUHTR13133",
number: 0,
reference: 'REFERENCE - OTHER REFERENCE',
rejection_code: '',
unavailability_code: '0',
value_date: Date.new(2019, 5, 16),
original_currency: nil,
original_amount: nil,
debtor: 'INTERNET SFR'
)
end
end

context 'with an already defined operation' do
let(:input) { File.read('spec/files/operation_already_defined.txt') }

it 'ignores the second operation' do
expect(operation).to have_attributes(
amount: -32.21,
currency: 'EUR',
date: Date.new(2019, 5, 16),
exoneration_code: '0',
interbank_code: 'B1',
internal_code: '9162',
label: "PRLV SEPA TEST CABINET\nMENSUEAUHTR13133",
number: 0,
reference: 'REFERENCE - OTHER REFERENCE',
rejection_code: '',
unavailability_code: '0',
value_date: Date.new(2019, 5, 16),
original_currency: nil,
original_amount: nil,
debtor: 'INTERNET SFR'
)
end
end

context 'with an unstarted operation' do
let(:input) { File.read('spec/files/operation_unstarted.txt') }

it 'returns no operation' do
expect(operation).to be_nil
end
end

context 'with an unhandled line code' do
let(:input) { File.read('spec/files/example.txt') }

it 'ignores the unhandled lines' do
expect(operation).to have_attributes(
amount: -32.21,
currency: 'EUR',
date: Date.new(2019, 5, 16),
exoneration_code: '0',
interbank_code: 'B1',
internal_code: '9162',
label: "PRLV SEPA TEST CABINET\nMENSUEAUHTR13133\nP051928612 22793301700040",
number: 0,
reference: 'REFERENCE - OTHER REFERENCE',
rejection_code: '',
unavailability_code: '0',
value_date: Date.new(2019, 5, 16),
original_currency: nil,
original_amount: nil,
debtor: 'ELEC ERDF'
)
end
end
end
end
end
5 changes: 5 additions & 0 deletions spec/files/operation.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
0415589916200000EUR2 98765432100B1160519 160519PRLV SEPA TEST CABINET 0000000000000000000322J
0515589916200000EUR2 98765432100B1160519 LIBMENSUEAUHTR13133
0515589916200000EUR2 98765432100B1160519 REFREFERENCE
0515589916200000EUR2 98765432100B1160519 RCNOTHER REFERENCE PURPOSE
0515589916200000EUR2 98765432100B1160519 NPYINTERNET SFR
6 changes: 6 additions & 0 deletions spec/files/operation_already_defined.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
0415589916200000EUR2 98765432100B1160519 160519PRLV SEPA TEST CABINET 0000000000000000000322J
0515589916200000EUR2 98765432100B1160519 LIBMENSUEAUHTR13133
0515589916200000EUR2 98765432100B1160519 REFREFERENCE
0515589916200000EUR2 98765432100B1160519 RCNOTHER REFERENCE PURPOSE
0515589916200000EUR2 98765432100B1160519 NPYINTERNET SFR
0415589916200000EUR2 98765432100B1160519 160519PRLV SEPA TEST CABINET 0000000000000000000322J
4 changes: 4 additions & 0 deletions spec/files/operation_unstarted.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
0515589916200000EUR2 98765432100B1160519 LIBMENSUEAUHTR13133
0515589916200000EUR2 98765432100B1160519 REFREFERENCE
0515589916200000EUR2 98765432100B1160519 RCNOTHER REFERENCE PURPOSE
0515589916200000EUR2 98765432100B1160519 NPYINTERNET SFR

0 comments on commit 914dadf

Please sign in to comment.