Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Version 1.0 #23

Open
wants to merge 10 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,6 @@ Bug reports and pull requests are welcome on GitHub at https://github.com/fintas


## Hbci Documentation

* [FinTS 3.0 Formals](http://www.hbci-zka.de/dokumente/spezifikation_deutsch/fintsv3/FinTS_3.0_Formals_2017-10-06_final_version.pdf)
* [FinTS 3.0 Messages](https://www.hbci-zka.de/dokumente/spezifikation_deutsch/fintsv3/FinTS_3.0_Messages_Geschaeftsvorfaelle_2015-08-07_final_version.pdf)
* [FinTS 3.0 Sicherheitsverfahren](https://www.hbci-zka.de/dokumente/spezifikation_deutsch/fintsv3/FinTS_3.0_Security_Sicherheitsverfahren_HBCI_Rel_20130718_final_version.pdf)
Expand Down
4,068 changes: 4,068 additions & 0 deletions config/bank_list.json

Large diffs are not rendered by default.

24 changes: 15 additions & 9 deletions examples/credentials.rb
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
# frozen_string_literal: true

require 'optparse'
require 'active_support'
require 'active_support/core_ext'

@options = {
url: nil,
Expand All @@ -11,11 +9,12 @@
user_id: nil,
pin: nil,
tan: nil,
system_id: 0
system_id: 0,
product_name: nil
}

OptionParser.new do |opts|
opts.banner = 'Usage: example.rb iban [options]'
opts.banner = 'Usage: example.rb IBAN [options]'

opts.on '-v', '--hbci_version=VERSION', 'Version' do |arg|
@options[:hbci_version] = arg
Expand All @@ -41,6 +40,10 @@
@options[:system_id] = arg
end

opts.on '-pn', '--product_name=PRODUCT_NAME', 'PIN' do |arg|
@options[:product_name] = arg
end

opts.on('-h', '--help', 'Prints this help') do
puts opts
exit
Expand All @@ -51,8 +54,11 @@
raise 'missing iban' unless @iban

@hbci_version = @options[:hbci_version] ? @options[:hbci_version].to_i : nil
@credentials = BankCredentials::Hbci.new(
bank_code: @options[:bank_code],
user_id: @options[:user_id],
pin: @options[:pin]
)
Hbci.configure do |config|
config.product_name = @options[:product_name]
config.user_id = @options[:user_id]
config.pin = @options[:pin]
end



26 changes: 20 additions & 6 deletions examples/get_accounts.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,25 @@
require_relative '../lib/hbci'
require_relative 'credentials'

Hbci::Connector.open(@credentials) do |connector|
Hbci::Dialog.open(connector, tan: @options[:tan]) do |dialog|
accounts = Hbci::Services::AccountsReceiver.new(dialog).perform
accounts.each do |account|
puts account
end
Hbci::Connector.open(@iban) do |connector|
session_service = Hbci::Services::Session.new(connector)
session_service.perform

connector.session_service_response = session_service.response

dialog_service = Hbci::Services::Dialog.new(connector)
dialog_service.perform

connector.dialog_service_response = dialog_service.response

hnvsd = connector.dialog_service_response.hbci.find_segments('HNVSD').first
hnvsd_data_block = Hbci::Message.new(hnvsd[2].to_s.sub(/@[0-9]+@/, ''))

hnvsd_data_block.find_segments('HIUPD').each do |segment|
account_number = segment[2][1]
bank_code = segment[2][4]
iban = segment[3]
owner = segment[7]
puts "#{account_number}, #{bank_code}, #{iban}, #{owner}"
end
end
18 changes: 14 additions & 4 deletions examples/get_balance.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,18 @@
require_relative '../lib/hbci'
require_relative 'credentials'

Hbci::Connector.open(@credentials) do |connector|
Hbci::Dialog.open(connector, tan: @options[:tan]) do |dialog|
puts Hbci::Services::BalanceReceiver.new(connector, dialog, @iban).perform
end
Hbci::Connector.open(@iban) do |connector|
session_service = Hbci::Services::Session.new(connector)
session_service.perform

connector.session_service_response = session_service.response

dialog_service = Hbci::Services::Dialog.new(connector)
dialog_service.perform

connector.dialog_service_response = dialog_service.response

balance_receiver = Hbci::Services::BalanceReceiver.new(connector)
balance_receiver.perform
end

32 changes: 23 additions & 9 deletions examples/get_transactions.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,14 +3,28 @@
require_relative '../lib/hbci'
require_relative 'credentials'

start_date = 3.day.ago
end_date = Time.now

Hbci::Connector.open(@credentials) do |connector|
Hbci::Dialog.open(connector, tan: @options[:tan]) do |dialog|
transactions = Hbci::Services::TransactionsReceiver.new(connector, dialog, @iban, @hbci_version).perform(start_date, end_date)
transactions.each do |transaction|
puts transaction
end
Hbci::Connector.open(@iban) do |connector|
session_service = Hbci::Services::Session.new(connector)
session_service.perform

connector.session_service_response = session_service.response

dialog_service = Hbci::Services::Dialog.new(connector)
dialog_service.perform

connector.dialog_service_response = dialog_service.response

transactions_receiver = Hbci::Services::TransactionsReceiver.new(connector, Time.now, Time.now)
response = transactions_receiver.perform

hnvsd = Hbci::Message.new(response.to_s).find_segments('HNVSD').first
hnvsd_data_block = Hbci::Message.new(hnvsd[2].to_s.sub(/@[0-9]+@/, ''))

hikaz = hnvsd_data_block.find_segments('HIKAZ').first
hikaz_data_block = Hbci::Message.new(hikaz[2].to_s.sub(/@[0-9]+@/, ''))

statements = Cmxl.parse(hikaz_data_block[1].to_s.delete_suffix("'").force_encoding('ISO-8859-1').encode('UTF-8'))
statements.each do |statement|
puts statement.transactions.inspect
end
end
15 changes: 5 additions & 10 deletions hbci.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -18,18 +18,13 @@ Gem::Specification.new do |spec|
spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
spec.require_paths = ['lib']

spec.add_runtime_dependency 'bank_credentials'
spec.add_runtime_dependency 'cmxl', '~> 1.4'
spec.add_runtime_dependency 'httparty', '~> 0.16'
spec.add_runtime_dependency 'ibanizator', '~> 0.3'
spec.add_runtime_dependency 'monetize', ['>=1.8', '<2.0.0']
spec.add_runtime_dependency 'money', ['>=6.11', '<7.0.0']

spec.add_development_dependency 'activesupport', '~> 5.2'
spec.add_development_dependency 'byebug', '~> 11.0'
spec.add_development_dependency 'rake', '~> 12.3'
spec.add_development_dependency 'rspec', '~> 3.8'
spec.add_development_dependency 'rubocop', '~> 0.60'
spec.add_development_dependency 'timecop', '~> 0.9'
spec.add_development_dependency 'webmock', '~> 3.4'
spec.add_development_dependency 'rake'
spec.add_development_dependency 'rspec'
spec.add_development_dependency 'rubocop'
spec.add_development_dependency 'timecop'
spec.add_development_dependency 'webmock'
end
26 changes: 0 additions & 26 deletions lib/development_profiler.rb

This file was deleted.

50 changes: 16 additions & 34 deletions lib/hbci.rb
Original file line number Diff line number Diff line change
@@ -1,53 +1,35 @@
# frozen_string_literal: true

# External gems
require 'httparty'
require 'money'
require 'monetize'
require 'cmxl'
require 'ibanizator'

require 'bank_credentials'
require 'hbci/errors/error'

# Internal logic
require 'hbci/version'
require 'hbci/config'
require 'hbci/connector'
require 'hbci/response'
require 'hbci/parser'
require 'hbci/segment_factory'
require 'hbci/dialog'
require 'hbci/message'
require 'hbci/request'
require 'hbci/response'
require 'hbci/element_unparser'
require 'hbci/connector'
require 'hbci/message_factory'

# Errors
require 'hbci/errors/hbci/base_error'
require 'hbci/errors/hbci/dialog_error'
require 'hbci/errors/hbci/service_unavailable'

# Element groups
require 'hbci/element_group'
require 'hbci/element_groups/segment_head'
require 'hbci/element_groups/unknown'
require 'hbci/element_groups/generated_element_groups'

# Segments
require 'hbci/segment'
Dir["#{File.expand_path('..', __dir__)}/lib/hbci/segments/*.rb"].each { |f| require f }
require 'hbci/segment_element'

# Services
require 'hbci/services/base'
require 'hbci/services/base_receiver'
require 'hbci/services/transactions_receiver'
require 'hbci/services/balance_receiver'
require 'hbci/services/accounts_receiver'

I18n.enforce_available_locales = false if I18n.available_locales.none?

Money.locale_backend = nil
Dir["#{File.expand_path('..', __dir__)}/lib/hbci/errors/*.rb"].each { |f| require f }
Dir["#{File.expand_path('..', __dir__)}/lib/hbci/services/*.rb"].each { |f| require f }

module Hbci
def self.logger
@logger ||= Logger.new(STDOUT, level: Logger::DEBUG)
end

def self.configure
yield Hbci::Config if block_given?
end

def self.config
Hbci::Config
end
end
7 changes: 7 additions & 0 deletions lib/hbci/config.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
module Hbci
module Config
class << self
attr_accessor :url, :user_id, :pin, :product_name
end
end
end
49 changes: 34 additions & 15 deletions lib/hbci/connector.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,40 +2,59 @@

module Hbci
class Connector
BANK_LIST = File.join(File.dirname(__FILE__), '../../config/bank_list.json')

attr_accessor :message_number
attr_reader :credentials
attr_reader :iban
attr_accessor :session_service_response
attr_accessor :dialog_service_response

def self.open(credentials)
connector = new(credentials)
def self.open(iban)
connector = new(iban)
yield connector
connector.reset_message_number
end

def initialize(credentials)
self.credentials = credentials
def initialize(iban)
@iban = Ibanizator.iban_from_string(iban)
reset_message_number
end

def credentials=(credentials)
raise ArgumentError, "#{self.class.name}#initialize expects a BankCredentials::Hbci object" unless credentials.is_a?(BankCredentials::Hbci)

credentials.validate!
@credentials = credentials
end

def reset_message_number
@message_number = 1
end

def url
@url ||= bank['pinTanURL']
end

def post(request_message, count_messages = true)
Hbci.logger.debug("Request: #{request_message}")
req = HTTParty.post(@credentials.url, body: request_message.to_base64)
Hbci.logger.debug("Request to #{url}: #{request_message}")
req = HTTParty.post(url, body: request_message.to_base64)
@message_number += 1 if count_messages
raise "Error in https communication with bank: #{req.response.inspect}" unless req.success?
raise "Error in https #{url} communication with bank: #{req.response.inspect}" unless req.success?

decode_response = Base64.decode64(req.response.body)
Hbci.logger.debug("Response: #{decode_response}")
decode_response
end

private

def bank
bank = bank_list.find { |b| b['blz'] == @iban.extended_data.bank_code }
raise Errors::Config, "Bank \"#{bank_code}\" not found in bank list" unless bank

bank
end

def bank_list
File.open(BANK_LIST, 'r') { |f| @bank_list = JSON.parse(f.read) } unless @bank_list
raise Errors::Config, 'Bank list is empty' if @bank_list.empty?

@bank_list
rescue OpenURI::HTTPError
raise Errors::Config, 'Bank list not loadable'
end
end
end
Loading