Dictionaries can't find keys

No retained should be in credit. At this stage, I only want to know if “retained” is in “credit” or “debit”. “credit” and “debit” are important later on in determining certain calculations, but at this time, I only want to know if a key is in the Dictionary general_ledger.

This sounds like

if !haskey(general_ledger["debit"], debit_ledger_entries[i]) &&
           !haskey(general_ledger["credit"], debit_ledger_entries[i])
            return "Error -- "*debit_ledger_entries[i]*" not found"

would be the right check?

The following implementation shows my understanding of the requirements

function get_ledger_entry(general_ledger, ledger_entry)
	if haskey(general_ledger["debit"], ledger_entry)
		return general_ledger["debit"][ledger_entry]
	elseif haskey(general_ledger["credit"], ledger_entry)
		return general_ledger["credit"][ledger_entry]
	else
		return nothing
	end
end

function get_account_entry(ledger_entry, account_entry)
	if haskey(ledger_entry, account_entry)
		return ledger_entry[account_entry]
	else
		return nothing
	end
end

function transaction(memo, date,
	debit_ledger_entries=[], debit_account_entries=[],
	debit_amount_entries=[], credit_ledger_entries=[],
	credit_account_entries=[], credit_amount_entries=[],
	general_ledger=general_ledger)

	if length(credit_ledger_entries) != length(credit_account_entries)
		return "Error--there must be the same number of credit legders and accounts"
	end
	if length(credit_account_entries) != length(credit_amount_entries)
		return "Error-- each account needs a value and vice versa"
	end
	if length(debit_ledger_entries) != length(debit_account_entries)
	    return "Error--there must be the same number of debit legders and accounts"
	end
	if length(debit_account_entries) != length(debit_amount_entries)
		return "Error-- each debit account needs a value and vice versa"
	end
	if (round(Dec64(sum(debit_amount_entries)),digits=2)
	  -round(Dec64(sum(credit_amount_entries)),digits=2))!=0
		return "Error-total credits does not match total debits"
	end

	journal_entry=DataFrame(Date=[date],
							DebitedAccounts=[""],
							CreditedAccounts=[""],
							Debits=Vector{Dec64}([0.00]),
							Credits=Vector{Dec64}([0.00]),
							Balance=Vector{Dec64}([0.00]))

	i=1
	while i <= length(debit_amount_entries)
		ledger_entry = get_ledger_entry(general_ledger, debit_ledger_entries[i])
		if ledger_entry == nothing
        	return "Error -- "*debit_ledger_entries[i]*" not found"
		end
		account_entry = get_account_entry(ledger_entry, credit_account_entries[i])
		if account_entry == nothing
        	return "Error -- "*debit_account_entries[i]*" not found in"*debit_ledger_entries[i]*"."
        end

        debit_amount_entries[i]=round(Dec64(debit_amount_entries[i]),digits=2)
    	i+=1
    end

	i=1
	while i <= length(credit_amount_entries)
		ledger_entry = get_ledger_entry(general_ledger, credit_ledger_entries[i])
		if ledger_entry == nothing
			return "Error -- "*credit_ledger_entries[i]*" not found"
		end
		account_entry = get_account_entry(ledger_entry, credit_account_entries[i])
		if account_entry == nothing
			return "Error -- "*credit_account_entries[i]*" not found in"*credit_ledger_entries[i]*"."
        end

        credit_amount_entries[i]=round(Dec64(credit_amount_entries[i]),digits=2)
    	i+=1
    end

	i=1
  	while i <= length(debit_ledger_entries)
        debit_ledger_name=debit_ledger_entries[i]
        debit_amount = round(debit_amount_entries[i];digits=2)
        debit_account=debit_account_entries[i]
        calc_debit_balance!(
                    general_ledger,
                    journal_entry,
                    date,
                    debit_ledger_name,
                    debit_account,
                    debit_amount,
                    memo)
        i+=1
    end

    i=1
	while i <= length(credit_ledger_entries)
        credit_ledger_name=credit_ledger_entries[i]
        credit_account=credit_account_entries[i]
        credit_amount=floor(credit_amount_entries[i];digits=2)
        calc_credit_balance!(
                    general_ledger,
                    journal_entry,
                    date,
                    credit_ledger_name,
                    credit_account,
                    credit_amount,
                    memo)
        i+=1
    end

    push!(journal_entry,["","Total","Transaction",
                round(sum(journal_entry.Debits); digits=2),
                round(sum(journal_entry.Credits); digits=2),0])
    return (journal_entry, memo)
end;

and runs into

ERROR: LoadError: UndefVarError: calc_debit_balance! not defined
function transaction(memo, date,
	debit_ledger_entries=[], debit_account_entries=[],
	debit_amount_entries=[], credit_ledger_entries=[],
	credit_account_entries=[], credit_amount_entries=[],
	general_ledger=general_ledger)

	if length(credit_ledger_entries) != length(credit_account_entries)
		return "Error--there must be the same number of credit legders and accounts"
	end
	if length(credit_account_entries) != length(credit_amount_entries)
		return "Error-- each account needs a value and vice versa"
	end
	if length(debit_ledger_entries) != length(debit_account_entries)
	    return "Error--there must be the same number of debit legders and accounts"
	end
	if length(debit_account_entries) != length(debit_amount_entries)
		return "Error-- each debit account needs a value and vice versa"
	end
	if (round(Dec64(sum(debit_amount_entries)),digits=2)
	  -round(Dec64(sum(credit_amount_entries)),digits=2))!=0
		return "Error-total credits does not match total debits"
	end

	journal_entry=DataFrame(Date=[date],
							DebitedAccounts=[""],
							CreditedAccounts=[""],
							Debits=Vector{Dec64}([0.00]),
							Credits=Vector{Dec64}([0.00]),
							Balance=Vector{Dec64}([0.00]))

	i=1
	while i <= length(debit_amount_entries)
		if !haskey(general_ledger["debit"], debit_ledger_entries[i]) &&
           	!haskey(general_ledger["credit"], debit_ledger_entries[i])
            	return "Error -- "*debit_ledger_entries[i]*" not found"
		end
		if !haskey(general_ledger["debit"][debit_ledger_entries[i]], credit_account_entries[i]) &&
           !haskey(general_ledger["credit"][debit_ledger_entries[i]], credit_account_entries[i])
        	return "Error -- "*debit_account_entries[i]*" not found in"*debit_ledger_entries[i]*"."
        end

        debit_amount_entries[i]=round(Dec64(debit_amount_entries[i]),digits=2)
    	i+=1
    end

	i=1
	while i <= length(credit_amount_entries)
        if !haskey(general_ledger["debit"], credit_ledger_entries[i]) &&
           !haskey(general_ledger["credit"], credit_ledger_entries[i])
            return "Error -- "*credit_ledger_entries[i]*" not found"
        end
        if !haskey(general_ledger["debit"][credit_ledger_entries[i]], credit_account_entries[i]) &&
            !haskey(general_ledger["credit"][credit_ledger_entries[i]], credit_account_entries[i])
            return "Error -- "*credit_account_entries[i]*" not found in"*credit_ledger_entries[i]*"."
        end

        credit_amount_entries[i]=round(Dec64(credit_amount_entries[i]),digits=2)
    	i+=1
    end

	i=1
  	while i <= length(debit_ledger_entries)
        debit_ledger_name=debit_ledger_entries[i]
        debit_amount = round(debit_amount_entries[i];digits=2)
        debit_account=debit_account_entries[i]
        calc_debit_balance!(
                    general_ledger,
                    journal_entry,
                    date,
                    debit_ledger_name,
                    debit_account,
                    debit_amount,
                    memo)
        i+=1
    end

    i=1
	while i <= length(credit_ledger_entries)
        credit_ledger_name=credit_ledger_entries[i]
        credit_account=credit_account_entries[i]
        credit_amount=floor(credit_amount_entries[i];digits=2)
        calc_credit_balance!(
                    general_ledger,
                    journal_entry,
                    date,
                    credit_ledger_name,
                    credit_account,
                    credit_amount,
                    memo)
        i+=1
    end

    push!(journal_entry,["","Total","Transaction",
                round(sum(journal_entry.Debits); digits=2),
                round(sum(journal_entry.Credits); digits=2),0])
    return (journal_entry, memo)
end;

This gives me the same error, that I had before.

getindex(::Dict{String, Dict{Any, Any}}, ::String)@dict.jl:481
transaction(::String, ::String, ::Vector{String}, ::Vector{String}, ::Vector{Float64}, ::Vector{String}, ::Vector{String}, ::Vector{Float64}, ::Dict{String, Dict{String}})@AccountingProgram.jl:548
transaction(::String, ::String, ::Vector{String}, ::Vector{String}, ::Vector{Float64}, ::Vector{String}, ::Vector{String}, ::Vector{Float64})@AccountingProgram.jl:518
top-level scope@Local: 1[inlined]

It seems to me the error is missing?

Are you testing our MWE or your application?

Do you get an error, that calc_debit_balance is not found?

So I wrote.Should I repost the complete MWE or update the MWE above?


starting_balance=starting_balance=Dict(
	# Starting Balance consists of a dictionary, containing debit and credit dictionaries, containing accounts as empty dictionaries.

	#accounts are organized into credit and debit, then into subledgers based on DEALER acrynym
	
	#Debit Accounts
		#Drawings
		#Expenses
		#Assets
	#Credit Accounts
		#Liabilities
		#Equity
		#Revenue
	
		#Year End Accounts   # These are used to close temporary accounts
			# Gross Revenue
			# Gross Expenses
			# Earned Income
	"debit"=>Dict(
					# balance = Σdebit - Σcredit		
		"drawings"=>Dict(),	#debit normal ledgers
		"expenses"=>Dict(),
		"assets"=>Dict()),
	"credit"=>Dict(  # revenue, liabilities, equtiy, and year_end, are credit normal
					 # balance = Σcredit -  Σdebit
		"liabilities"=>Dict(),
		"equity"=>Dict(),
		"revenue"=>Dict(),
			"retained"=> Dict( #Closing Accounts - No Balance Until Temp Accounts Closed
			"Retained Earnings"=>DataFrame(
        date=Vector{String}(),
		memo=Vector{String}(),
        debit=Vector{Dec64}(),
        credit=Vector{Dec64}(),
		balance=Vector{Dec64}()),
			"Gross Income"=>DataFrame(
        date=Vector{String}(),
		memo=Vector{String}(),
        debit=Vector{Dec64}(),
        credit=Vector{Dec64}(),
		balance=Vector{Dec64}()),
			"Gross Expenses"=>DataFrame(
        date=Vector{String}(),
		memo=Vector{String}(),
        debit=Vector{Dec64}(),
        credit=Vector{Dec64}(),
		balance=Vector{Dec64}()),
			"Net Income"=>DataFrame(
        date=Vector{String}(),
		memo=Vector{String}(),
        debit=Vector{Dec64}(),
        credit=Vector{Dec64}(),
		balance=Vector{Dec64}()),
			"Total Drawings"=>DataFrame(
        date=Vector{String}(),
		memo=Vector{String}(),
        debit=Vector{Dec64}(),
        credit=Vector{Dec64}(),
		balance=Vector{Dec64}()),
		)
	)
	)

function transaction(memo, date,
	debit_ledger_entries=[], debit_account_entries=[],
	debit_amount_entries=[], credit_ledger_entries=[],
	credit_account_entries=[], credit_amount_entries=[],
	general_ledger=general_ledger)

	if length(credit_ledger_entries) != length(credit_account_entries)
		return "Error--there must be the same number of credit legders and accounts"
	end
	if length(credit_account_entries) != length(credit_amount_entries)
		return "Error-- each account needs a value and vice versa"
	end
	if length(debit_ledger_entries) != length(debit_account_entries)
	    return "Error--there must be the same number of debit legders and accounts"
	end
	if length(debit_account_entries) != length(debit_amount_entries)
		return "Error-- each debit account needs a value and vice versa"
	end
	if (round(Dec64(sum(debit_amount_entries)),digits=2)
	  -round(Dec64(sum(credit_amount_entries)),digits=2))!=0
		return "Error-total credits does not match total debits"
	end

	journal_entry=DataFrame(Date=[date],
							DebitedAccounts=[""],
							CreditedAccounts=[""],
							Debits=Vector{Dec64}([0.00]),
							Credits=Vector{Dec64}([0.00]),
							Balance=Vector{Dec64}([0.00]))

	i=1
	while i <= length(debit_amount_entries)
		if !haskey(general_ledger["debit"], debit_ledger_entries[i]) &&
           	!haskey(general_ledger["credit"], debit_ledger_entries[i])
            	return "Error -- "*debit_ledger_entries[i]*" not found"
		end
		if !haskey(general_ledger["debit"][debit_ledger_entries[i]], credit_account_entries[i]) &&
           !haskey(general_ledger["credit"][debit_ledger_entries[i]], credit_account_entries[i])
        	return "Error -- "*debit_account_entries[i]*" not found in"*debit_ledger_entries[i]*"."
        end

        debit_amount_entries[i]=round(Dec64(debit_amount_entries[i]),digits=2)
    	i+=1
    end

	i=1
	while i <= length(credit_amount_entries)
        if !haskey(general_ledger["debit"], credit_ledger_entries[i]) &&
           !haskey(general_ledger["credit"], credit_ledger_entries[i])
            return "Error -- "*credit_ledger_entries[i]*" not found"
        end
        if !haskey(general_ledger["debit"][credit_ledger_entries[i]], credit_account_entries[i]) &&
            !haskey(general_ledger["credit"][credit_ledger_entries[i]], credit_account_entries[i])
            return "Error -- "*credit_account_entries[i]*" not found in"*credit_ledger_entries[i]*"."
        end

        credit_amount_entries[i]=round(Dec64(credit_amount_entries[i]),digits=2)
    	i+=1
    end

	i=1
  	while i <= length(debit_ledger_entries)
        debit_ledger_name=debit_ledger_entries[i]
        debit_amount = round(debit_amount_entries[i];digits=2)
        debit_account=debit_account_entries[i]
        calc_debit_balance!(
                    general_ledger,
                    journal_entry,
                    date,
                    debit_ledger_name,
                    debit_account,
                    debit_amount,
                    memo)
        i+=1
    end

    i=1
	while i <= length(credit_ledger_entries)
        credit_ledger_name=credit_ledger_entries[i]
        credit_account=credit_account_entries[i]
        credit_amount=floor(credit_amount_entries[i];digits=2)
        calc_credit_balance!(
                    general_ledger,
                    journal_entry,
                    date,
                    credit_ledger_name,
                    credit_account,
                    credit_amount,
                    memo)
        i+=1
    end

    push!(journal_entry,["","Total","Transaction",
                round(sum(journal_entry.Debits); digits=2),
                round(sum(journal_entry.Credits); digits=2),0])
    return (journal_entry, memo)
end;

transaction("Weird Example",
	"Jan 2 2021",
	["retained"],
	["Gross Income"],
	[100.00],
				["asset"],
				["Land"],
				[100.00],
starting_balance)

Sorry for the confusion. Here is my current complete version

using DataFrames, DecFP

starting_balance=starting_balance=Dict(
	"debit"=>Dict(
		"drawings"=>Dict(),	#debit normal ledgers
		"expenses"=>Dict(),
		"assets"=>Dict()),
	"credit"=>Dict(
		"liabilities"=>Dict(),
		"equity"=>Dict(),
		"revenue"=>Dict(),
		"retained"=> Dict( #Closing Accounts - No Balance Until Temp Accounts Closed
			"Retained Earnings"=>DataFrame(
        date=Vector{String}(),
		memo=Vector{String}(),
        debit=Vector{Dec64}(),
        credit=Vector{Dec64}(),
		balance=Vector{Dec64}()),
			"Gross Income"=>DataFrame(
        date=Vector{String}(),
		memo=Vector{String}(),
        debit=Vector{Dec64}(),
        credit=Vector{Dec64}(),
		balance=Vector{Dec64}()),
			"Gross Expenses"=>DataFrame(
        date=Vector{String}(),
		memo=Vector{String}(),
        debit=Vector{Dec64}(),
        credit=Vector{Dec64}(),
		balance=Vector{Dec64}()),
			"Net Income"=>DataFrame(
        date=Vector{String}(),
		memo=Vector{String}(),
        debit=Vector{Dec64}(),
        credit=Vector{Dec64}(),
		balance=Vector{Dec64}()),
			"Total Drawings"=>DataFrame(
        date=Vector{String}(),
		memo=Vector{String}(),
        debit=Vector{Dec64}(),
        credit=Vector{Dec64}(),
		balance=Vector{Dec64}())))
)

function get_ledger_entry(general_ledger, ledger_entry)
	if haskey(general_ledger["debit"], ledger_entry)
		return general_ledger["debit"][ledger_entry]
	elseif haskey(general_ledger["credit"], ledger_entry)
		return general_ledger["credit"][ledger_entry]
	else
		return nothing
	end
end

function get_account_entry(ledger_entry, account_entry)
	if haskey(ledger_entry, account_entry)
		return ledger_entry[account_entry]
	else
		return nothing
	end
end

function transaction(memo, date,
	debit_ledger_entries=[], debit_account_entries=[],
	debit_amount_entries=[], credit_ledger_entries=[],
	credit_account_entries=[], credit_amount_entries=[],
	general_ledger=general_ledger)

	if length(credit_ledger_entries) != length(credit_account_entries)
		return "Error--there must be the same number of credit legders and accounts"
	end
	if length(credit_account_entries) != length(credit_amount_entries)
		return "Error-- each account needs a value and vice versa"
	end
	if length(debit_ledger_entries) != length(debit_account_entries)
	    return "Error--there must be the same number of debit legders and accounts"
	end
	if length(debit_account_entries) != length(debit_amount_entries)
		return "Error-- each debit account needs a value and vice versa"
	end
	if (round(Dec64(sum(debit_amount_entries)),digits=2)
	  -round(Dec64(sum(credit_amount_entries)),digits=2))!=0
		return "Error-total credits does not match total debits"
	end

	journal_entry=DataFrame(Date=[date],
							DebitedAccounts=[""],
							CreditedAccounts=[""],
							Debits=Vector{Dec64}([0.00]),
							Credits=Vector{Dec64}([0.00]),
							Balance=Vector{Dec64}([0.00]))

	i=1
	while i <= length(debit_amount_entries)
		ledger_entry = get_ledger_entry(general_ledger, debit_ledger_entries[i])
		if ledger_entry == nothing
        	return "Error -- "*debit_ledger_entries[i]*" not found"
		end
		account_entry = get_account_entry(ledger_entry, credit_account_entries[i])
		if account_entry == nothing
        	return "Error -- "*debit_account_entries[i]*" not found in"*debit_ledger_entries[i]*"."
        end

        debit_amount_entries[i]=round(Dec64(debit_amount_entries[i]),digits=2)
    	i+=1
    end

	i=1
	while i <= length(credit_amount_entries)
		ledger_entry = get_ledger_entry(general_ledger, credit_ledger_entries[i])
		if ledger_entry == nothing
			return "Error -- "*credit_ledger_entries[i]*" not found"
		end
		account_entry = get_account_entry(ledger_entry, credit_account_entries[i])
		if account_entry == nothing
			return "Error -- "*credit_account_entries[i]*" not found in"*credit_ledger_entries[i]*"."
        end

        credit_amount_entries[i]=round(Dec64(credit_amount_entries[i]),digits=2)
    	i+=1
    end

	i=1
  	while i <= length(debit_ledger_entries)
        debit_ledger_name=debit_ledger_entries[i]
        debit_amount = round(debit_amount_entries[i];digits=2)
        debit_account=debit_account_entries[i]
        calc_debit_balance!(
                    general_ledger,
                    journal_entry,
                    date,
                    debit_ledger_name,
                    debit_account,
                    debit_amount,
                    memo)
        i+=1
    end

    i=1
	while i <= length(credit_ledger_entries)
        credit_ledger_name=credit_ledger_entries[i]
        credit_account=credit_account_entries[i]
        credit_amount=floor(credit_amount_entries[i];digits=2)
        calc_credit_balance!(
                    general_ledger,
                    journal_entry,
                    date,
                    credit_ledger_name,
                    credit_account,
                    credit_amount,
                    memo)
        i+=1
    end

    push!(journal_entry,["","Total","Transaction",
                round(sum(journal_entry.Debits); digits=2),
                round(sum(journal_entry.Credits); digits=2),0])
    return (journal_entry, memo)
end;

transaction("Weird Example", "Jan 2 2021",
	["retained"], ["Gross Income"], [100.00], ["retained"],
	["Net Income"], [100.00], starting_balance)

resulting in

ERROR: LoadError: UndefVarError: calc_debit_balance! not defined

I get “Gross Income not found in retained.”

Could we please get a third opinion before continuing the analysis?

OK. when I entered the MWE it works like yours, but when I insert it into my own program, it doesn’t work.

Your cite is dubious. If the problem persists in your application you should be able to demonstrate them via other call setups of transaction, no?

Otherwise you might open another discussion.

I might, I’ll keep looking at it’ and see what my problem is.

Now I got everything to work. If I have everything spelled right it works, if the ledger is spelled wrong, it returns *debit_account* not found, but if I spell the ledger right, but misspell the account, it goes through, and I get the standard key not found error.

KeyError: key "Gross Incme" not found

getindex(::Dict{String, DataFrames.DataFrame}, ::String)@dict.jl:481
calc_debit_balance!(::Dict{String, Dict{String}}, ::DataFrames.DataFrame, ::String, ::String, ::String, ::Float64, ::String)@Other: 48
transaction(::String, ::String, ::Vector{String}, ::Vector{String}, ::Vector{Float64}, ::Vector{String}, ::Vector{String}, ::Vector{Float64}, ::Dict{String, Dict{String}})@Other: 66
top-level scope@Local: 1[inlined]