class CrunchAPI
Attributes
oauth_token[R]
oauth_token_secret[R]
Public Class Methods
new(params={})
click to toggle source
# File lib/crunchaccounting-api.rb, line 13 def initialize(params={}) @vat_rate = VAT_RATE_DEFAULT params.each do |key, value| instance_variable_set("@" + key.to_s, value) end if @oauth_token and @oauth_token_secret initialise_consumer end end
Public Instance Methods
account_by_name(name)
click to toggle source
# File lib/crunchaccounting-api.rb, line 129 def account_by_name(name) if @accounts return @accounts[name] end accounts account_by_name name end
accounts(type: nil)
click to toggle source
# File lib/crunchaccounting-api.rb, line 111 def accounts(type: nil) if type return get("/rest/v2/accounts/#{type}") else @accounts = {} resp = get("/rest/v2/accounts") resp["bankAccounts"].each do |account| if !@accounts[account["account"]] @accounts[account["account"]] = account end end return resp end end
add_client_payment(params={})
click to toggle source
# File lib/crunchaccounting-api.rb, line 142 def add_client_payment(params={}) post "/rest/v2/client_payments", params end
add_expense(supplier_id:, date:, payment_date:, payment_method: nil, bank_account_id:, amount:, expense_type:, description:, director_id:nil, invoice:nil)
click to toggle source
# File lib/crunchaccounting-api.rb, line 213 def add_expense(supplier_id:, date:, payment_date:, payment_method: nil, bank_account_id:, amount:, expense_type:, description:, director_id:nil, invoice:nil) !payment_method and payment_method = "EFT" if subject_to_vat?(expense_type) gross_amount = amount vat_amount = ((amount / 100) * @vat_rate).round(2) net_amount = (amount - vat_amount).round(2) else gross_amount = amount vat_amount = 0 net_amount = amount end expense = { "amount" => amount, "expenseDetails" => { "supplier" => { "supplierId" => supplier_id }, "postingDate" => date }, "paymentDetails" => { "payment" => [{ "paymentDate" => payment_date, "paymentMethod" => payment_method, "bankAccount" => { "accountId" => bank_account_id }, "amount" => amount }] }, "expenseLineItems" => { "count": 1, "lineItemGrossTotal": gross_amount, "expenseLineItems" => [ { "expenseType" => expense_type, "benefitingDirector": director_id, "lineItemDescription" => description, "lineItemAmount" => { "currencyCode": "GBP", "netAmount" => net_amount, "grossAmount" => gross_amount, "vatAmount" => vat_amount } } ] } } if invoice mimetype = file_mimetype(invoice) filename = invoice.split("/").last expense["receipts"] = { "count" => 1, "receipt" => [ { "fileName" => filename, "contentType" => mimetype, "fileData": Base64.encode64(File.read(invoice)) } ] } end post "/rest/v2/expenses", expense end
authenticated?()
click to toggle source
# File lib/crunchaccounting-api.rb, line 36 def authenticated? @access_token ? true : false end
client_payments()
click to toggle source
# File lib/crunchaccounting-api.rb, line 138 def client_payments get "/rest/v2/client_payments" end
clients()
click to toggle source
# File lib/crunchaccounting-api.rb, line 384 def clients get "/rest/v2/clients" end
delete(uri)
click to toggle source
# File lib/crunchaccounting-api.rb, line 103 def delete(uri) !@consumer and @consumer = get_consumer(@api_endpoint) resp = @access_token.delete(uri, { "Accept" => "application/json" } ) JSON.parse(resp.body) end
delete_supplier(supplier_id)
click to toggle source
# File lib/crunchaccounting-api.rb, line 186 def delete_supplier(supplier_id) delete "/rest/v2/suppliers/#{supplier_id}" end
expense_types()
click to toggle source
# File lib/crunchaccounting-api.rb, line 146 def expense_types get "/rest/v2/expense_types" end
expenses()
click to toggle source
# File lib/crunchaccounting-api.rb, line 150 def expenses resp = get "/rest/v2/expenses" @expenses = [] resp["expense"].each do |expense| @expenses.push expense end @expenses end
file_mimetype(filename)
click to toggle source
# File lib/crunchaccounting-api.rb, line 352 def file_mimetype(filename) esc = Shellwords.escape(filename) `/usr/bin/file -bi #{esc}`.chomp.gsub(/;.*\z/, '') end
find_client(name)
click to toggle source
# File lib/crunchaccounting-api.rb, line 388 def find_client(name) clients["client"].each do |client| if client["name"] == name return client end end false end
find_client_payment(client_id:, date:, payment_method: nil, bank_account_id:, amount:, invoice_id:)
click to toggle source
# File lib/crunchaccounting-api.rb, line 450 def find_client_payment(client_id:, date:, payment_method: nil, bank_account_id:, amount:, invoice_id:) !payment_method and payment_method = "EFT" client_payments.each do |client_payment| if client_payment["paymentDate"] == date and client_payment["paymentMethod"] == payment_method and client_payment["bankAccount"]["accountId"] == bank_account_id and client_payment["amount"] == amount and client_payment["client"]["clientId"] == client_id and client_payment["salesInvoices"]["salesInvoice"][0]["salesInvoiceId"] == invoice_id return client_payment end end false end
find_draft_invoice(client_id, date)
click to toggle source
# File lib/crunchaccounting-api.rb, line 421 def find_draft_invoice(client_id, date) invoices["salesInvoice"].each do |invoice| if invoice["salesInvoiceDetails"]["client"]["clientId"] == client_id and invoice["salesInvoiceDetails"]["issuedDate"] == date and invoice["salesInvoiceDetails"]["state"] == "DRAFT" return invoice end end false end
find_expense(supplier_id:, date:, payment_date:, payment_method: nil, bank_account_id:, amount:, expense_type:, ignore_ids:[])
click to toggle source
# File lib/crunchaccounting-api.rb, line 357 def find_expense(supplier_id:, date:, payment_date:, payment_method: nil, bank_account_id:, amount:, expense_type:, ignore_ids:[]) !payment_method and payment_method = "EFT" if !@expenses expenses end @expenses.each do |expense| if ignore_ids.include?(expense["expenseId"]) next end if expense["expenseDetails"]["supplier"]["supplierId"] == supplier_id and expense["expenseDetails"]["postingDate"] == date and expense["paymentDetails"]["payment"][0]["paymentDate"] == payment_date and expense["paymentDetails"]["payment"][0]["paymentMethod"] == payment_method and expense["paymentDetails"]["payment"][0]["bankAccount"]["accountId"] == bank_account_id and expense["paymentDetails"]["payment"][0]["amount"] == amount and expense["expenseLineItems"]["expenseLineItems"][0]["expenseType"] == expense_type return expense end end false end
find_invoice(client_id, date)
click to toggle source
# File lib/crunchaccounting-api.rb, line 434 def find_invoice(client_id, date) invoices["salesInvoice"].each do |invoice| if invoice["salesInvoiceDetails"]["client"]["clientId"] == client_id and invoice["salesInvoiceDetails"]["issuedDate"] == date return invoice end end false end
find_outstanding_client_invoice(client_id, amount)
click to toggle source
# File lib/crunchaccounting-api.rb, line 402 def find_outstanding_client_invoice(client_id, amount) invoices["salesInvoice"].each do |invoice| total = 0 invoice["salesInvoiceLineItems"]["salesInvoiceLineItem"].each do |item| total += item["lineItemAmount"]["grossAmount"] end if invoice["salesInvoiceDetails"]["client"]["clientId"] == client_id and total == amount and invoice["salesInvoiceDetails"]["state"] != "SETTLED" return invoice end end false end
get(uri)
click to toggle source
# File lib/crunchaccounting-api.rb, line 81 def get(uri) !@consumer and @consumer = get_consumer(@api_endpoint) resp = @access_token.get(uri, { "Accept" => "application/json" } ) JSON.parse(resp.body) end
get_auth_url()
click to toggle source
# File lib/crunchaccounting-api.rb, line 56 def get_auth_url @consumer = get_consumer(@auth_endpoint) request_token = @consumer.get_request_token(:oauth_callback => "") @request_token = request_token.token @request_secret = request_token.secret return request_token.authorize_url(:oauth_callback => "") end
get_consumer(endpoint)
click to toggle source
# File lib/crunchaccounting-api.rb, line 40 def get_consumer(endpoint) consumer = OAuth::Consumer.new( @consumer_key, @consumer_secret, :scheme => :header, :site => endpoint, :request_token_path => "/crunch-core/oauth/request_token", :authorize_path => "/crunch-core/login/oauth-login.seam", :access_token_path => "/crunch-core/oauth/access_token" ) @debug and consumer.http.set_debug_output($stdout) consumer end
get_next_client_ref_for_client(client)
click to toggle source
# File lib/crunchaccounting-api.rb, line 495 def get_next_client_ref_for_client(client) abbr = "" for i in 0...client.length if client["name"][i].match(/[A-Z]/) abbr += client["name"][i] end end used = [] invoices["salesInvoice"].each do |invoice| if invoice["salesInvoiceDetails"]["client"]["clientId"] == client["clientId"] used.push invoice["salesInvoiceDetails"]["clientReference"] end end n = 1 ref = "#{abbr}#{n.to_s.rjust(3,'0')}" while used.include? ref n += 1 ref = "#{abbr}#{n.to_s.rjust(3,'0')}" end ref end
initialise_consumer()
click to toggle source
# File lib/crunchaccounting-api.rb, line 25 def initialise_consumer @consumer = get_consumer(@api_endpoint) @access_token = OAuth::AccessToken.from_hash( @consumer, { oauth_token: @oauth_token, oauth_token_secret: @oauth_token_secret } ) end
invoices()
click to toggle source
# File lib/crunchaccounting-api.rb, line 398 def invoices get "/rest/v2/sales_invoices" end
issue_invoice(invoice)
click to toggle source
# File lib/crunchaccounting-api.rb, line 446 def issue_invoice(invoice) put "/rest/v2/sales_invoices/#{invoice["salesInvoiceId"]}/issue" end
post(uri, params={})
click to toggle source
# File lib/crunchaccounting-api.rb, line 89 def post(uri, params={}) !@consumer and @consumer = get_consumer(@api_endpoint) resp = @access_token.post(uri, params.to_json, { "Content-Type" => "application/json", "Accept" => "application/json" } ) JSON.parse(resp.body) end
put(uri, params={})
click to toggle source
# File lib/crunchaccounting-api.rb, line 97 def put(uri, params={}) !@consumer and @consumer = get_consumer(@api_endpoint) resp = @access_token.put(uri, params.to_json, { "Content-Type" => "application/json", "Accept" => "application/json" } ) end
raise_invoice(client_id:,date:,client_ref:nil,description:,rate:,quantity:,add_vat:true)
click to toggle source
# File lib/crunchaccounting-api.rb, line 523 def raise_invoice(client_id:,date:,client_ref:nil,description:,rate:,quantity:,add_vat:true) amount = rate * quantity if add_vat vat = ((amount / 100) * @vat_rate).round(2) vat_type = "STANDARD" else vat = 0 vat_type = "OUTSIDE_SCOPE" end client = get "/rest/v2/clients/#{client_id}" if !client_ref client_ref = get_next_client_ref_for_client(client) end invoice = { "currency" => "GBP", "salesInvoiceLineItems" => { "salesInvoiceLineItem" => [ { "lineItemDescription" => description, "quantity" => quantity, "rate" => rate, "lineItemAmount" => { "netAmount" => amount, "grossAmount" => amount + vat, "vatAmount" => vat, "vatRate" => @vat_rate }, "vatType" => vat_type }, ], "count" => 1 }, "salesInvoiceDetails" => { "client" => { "clientId" => client_id, }, "clientReference" => client_ref, "issuedDate" => date, "paymentTermsDays" => client["paymentTermsDays"], } } post "/rest/v2/sales_invoices", invoice end
subject_to_vat?(expense_type)
click to toggle source
# File lib/crunchaccounting-api.rb, line 190 def subject_to_vat?(expense_type) if [ "GENERAL_INSURANCE", "MILEAGE_ALLOWANCE", "MEDICAL_INSURANCE_CONTRIBUTIONS", "BANK_CHARGES", "PENSION_SCHEME_CONTRIBUTIONS", "PUBLIC_TRANSPORT" ].include? expense_type return false end if [ "ACCOUNTANCY", "CHILDCARE_VOUCHER_ADMIN_FEES", "WEB_HOSTING_CLOUD_SERVICES" ].include? expense_type return true end raise "Don't know if #{expense_type} is subject to VAT" end
supplier_by_name(name)
click to toggle source
# File lib/crunchaccounting-api.rb, line 176 def supplier_by_name(name) if @suppliers return @suppliers[name] end suppliers supplier_by_name(name) end
suppliers()
click to toggle source
# File lib/crunchaccounting-api.rb, line 162 def suppliers resp = get "/rest/v2/suppliers" @suppliers = {} resp["supplier"].each do |supplier| if !@suppliers[supplier["name"]] @suppliers[supplier["name"]] = supplier end end @suppliers end
update_expense(expense_id:, supplier_id:, date:, payment_date:, payment_method: nil, bank_account_id:, amount:, expense_type:, description:, director_id:nil, invoice:nil)
click to toggle source
# File lib/crunchaccounting-api.rb, line 282 def update_expense(expense_id:, supplier_id:, date:, payment_date:, payment_method: nil, bank_account_id:, amount:, expense_type:, description:, director_id:nil, invoice:nil) !payment_method and payment_method = "EFT" if subject_to_vat?(expense_type) gross_amount = amount vat_amount = ((amount / 100) * @vat_rate).round(2) net_amount = (amount - vat_amount).round(2) else gross_amount = amount vat_amount = 0 net_amount = amount end expense = { "expenseId" => expense_id, "amount" => amount, "expenseDetails" => { "supplier" => { "supplierId" => supplier_id }, "postingDate" => date }, "paymentDetails" => { "payment" => [{ "paymentDate" => payment_date, "paymentMethod" => payment_method, "bankAccount" => { "accountId" => bank_account_id }, "amount" => amount }] }, "expenseLineItems" => { "count": 1, "lineItemGrossTotal": gross_amount, "expenseLineItems" => [ { "expenseType" => expense_type, "benefitingDirector": director_id, "lineItemDescription" => description, "lineItemAmount" => { "currencyCode": "GBP", "netAmount" => net_amount, "grossAmount" => gross_amount, "vatAmount" => vat_amount } } ] } } if invoice mimetype = file_mimetype(invoice) filename = invoice.split("/").last expense["receipts"] = { "count" => 1, "receipt" => [ { "fileName" => filename, "contentType" => mimetype, "fileData": Base64.encode64(File.read(invoice)) } ] } end put "/rest/v2/expenses", expense end
verify_token(oauth_verifier)
click to toggle source
# File lib/crunchaccounting-api.rb, line 67 def verify_token(oauth_verifier) hash = { oauth_token: @request_token, oauth_token_secret: @request_secret } request_token = OAuth::RequestToken.from_hash(@consumer, hash) @access_token = request_token.get_access_token(:oauth_verifier => oauth_verifier) @oauth_token = @access_token.params[:oauth_token] @oauth_token_secret = @access_token.params[:oauth_token_secret] initialise_consumer true end