import json from decimal import * from datetime import * # this program reads the json file describing a mortgage and calculate the actual and projected amortization # the first payment in the file should be the interest paid at closing # the interest at closing covers interest that would be incurred from the date of closing until the first day # that will be covered by the first loan payment # i.e., the first loan payment is expected a month and a half after closing, the first two weeks interest is due # at closing. The first payment will incur interest from one month before the bill is due. #read in the file #filename = "./10Kloan.txt" filename = "./dadmortgage.txt" #filename = "./brendamortgage.txt" #filename = "./greenfield_mortgage.txt" if filename: with open(filename, 'r') as f: datastore = json.load(f) #read in the loan profile information annual_rate = Decimal(datastore['interest rate'])/100 daily_interest_rate = annual_rate/360 principal = Decimal(datastore["principal"]).quantize(Decimal("1.00")) periods_per_year = Decimal(datastore["periods per year"]) total_periods = Decimal(datastore["periods"]) payment_day_of_month = int(datastore['payment day of month']) if "monthly_payment" in datastore: monthly_payment = Decimal(datastore["monthly_payment"]).quantize(Decimal("1.00")) else: #calculate expected monthly payment periodic_rate = annual_rate/periods_per_year discount_factor = (((1+periodic_rate)**total_periods)-1) / (periodic_rate * ((1+periodic_rate)**total_periods)) monthly_payment = (principal / discount_factor).quantize(Decimal("1.00")) print "Principal: ", principal print "Interest Rate: ", annual_rate print "Payments Per Year: ", periods_per_year print "Loan Term: ", total_periods print "Monthly Payment", monthly_payment print "Payments due day: ", payment_day_of_month print #loop over the payments and calculate the actual amortization actual_payments = datastore["payments"] remaining_principal = principal annual_interest = 0 total_interest = 0 interest_paid_through_date = datetime.strptime(datastore["start_interest_date"], "%Y-%m-%d").date() next_payment_date = datetime.strptime(datastore["first payment month"], '%Y-%m-%d').date() next_bill_date = date(year=next_payment_date.year, month=next_payment_date.month, day=payment_day_of_month) old_bill_date = next_bill_date payment_number = 1 current_year = next_bill_date.year print "Payment History:" print "\tBill\t\t\tPayment\tDays of\tPayment\t\tRemaining\t\tPrincipal\tInterest\t\t\tNew" print "#\tDate\t\t\tDate\tInterst\tAmount\t\tPrincipal\t\tPayment\t\tPayment\t\t\tBalance" for payment in actual_payments: payment_date = datetime.strptime((payment[0]), '%Y-%m-%d').date() payment_amount = Decimal(payment[1]).quantize(Decimal("1.00")) #print next_bill_date, "\t", next_payment_date, "\t", days_since_last_payment = (payment_date-interest_paid_through_date).days #print days_since_last_payment new_interest = (days_since_last_payment * remaining_principal * daily_interest_rate).quantize(Decimal("0.00")) # new_principal = monthly_payment - new_interest new_principal = payment_amount - new_interest print payment_number, " ", next_bill_date, "\t\t", payment_date, "\t", days_since_last_payment, "\t", payment_amount, "\t\t\t", remaining_principal, "\t\t", new_principal,\ "\t\t", new_interest, interest_paid_through_date = payment_date total_interest = total_interest + new_interest annual_interest=annual_interest+new_interest remaining_principal = remaining_principal - new_principal print "\t\t\t", remaining_principal payment_number=payment_number+1 old_bill_date = next_bill_date if old_bill_date.month < 12: next_bill_date = date(year=old_bill_date.year, month = old_bill_date.month + 1, day=payment_day_of_month) print "Total interest paid to date for", old_bill_date.year, " is", annual_interest else: next_bill_date = date(year=old_bill_date.year+1, month = 1, day=payment_day_of_month) print "Total interest for ", old_bill_date.year, " was ", annual_interest annual_interest = 0 print "Total interest paid to date on this loan is", total_interest #loop over remaining scheduled payments and present estimated amortization print "\nEstimated future amortization" while (payment_number <= total_periods) and (remaining_principal > 0): print payment_number, "\t", payment_number = payment_number+1 print next_bill_date, days_since_last_payment = (next_bill_date-interest_paid_through_date).days print days_since_last_payment, "\t", new_interest = (days_since_last_payment * remaining_principal * daily_interest_rate).quantize(Decimal("0.00")) #make sure the last payment isn't too much if new_interest+remaining_principal < monthly_payment: monthly_payment = new_interest + remaining_principal new_principal = monthly_payment - new_interest print monthly_payment, "\t\t\t", remaining_principal, "\t\t", new_principal,\ "\t\t", new_interest, remaining_principal = remaining_principal - new_principal print "\t", remaining_principal interest_paid_through_date = next_bill_date old_bill_date = next_bill_date if old_bill_date.month < 12: next_bill_date = date(year=old_bill_date.year, month = old_bill_date.month + 1, day=payment_day_of_month) else: next_bill_date = date(year=old_bill_date.year+1, month = 1, day=payment_day_of_month) if remaining_principal > 0: print 'Balloon payment due:', remaining_principal