- Published on
Lending Systems and the LOS — Architecture from Loan Application to Disbursement
- Authors

- Name
- Youngju Kim
- @fjvbn20031
- Introduction
- The Lending Domain at a Glance
- The LOS Pipeline — From Application to Disbursement
- The Real-Time Pipeline for Digital Lending
- The Limit Management System
- The Collateral Management System
- Pricing — How the Rate Is Built
- Agreement and Disbursement — Booking and Ledger Integration
- External Integration Map
- State Machine Design
- Re-underwriting, Amendments, and Refinancing
- Pitfalls in System Design
- Test Scenarios
- Closing
- References
Introduction
In a core banking system, lending stands alongside deposits as one of the two great pillars. While deposits are a relatively simple ledger structure — "receive money and hold it" — lending is a domain with a long lifecycle that stretches from application intake through underwriting, approval, agreement, disbursement, and then years of repayment and post-disbursement servicing. The systems are correspondingly complex. As a single loan flows through, a credit scoring system (CSS), a limit management system, a collateral management system, a pricing engine, the core banking ledger, credit bureaus, and guarantee institutions all interlock and turn together.
In this post we first sketch the big picture of the lending domain, then walk step by step through the architecture from application to disbursement, centered on the LOS (Loan Origination System) — the system responsible for the "birth" of a loan. We cover the real-time underwriting pipeline for digital (branchless) lending, the limit/collateral/pricing subsystems, external institution integrations, and finally state machine design and test scenarios — the topics you actually collide with in practice.
A disclaimer up front: this is a technical article about system architecture, not a solicitation for any financial product nor investment or legal advice. Regulatory content reflects a general understanding as of the time of writing; for real projects, always have your compliance and legal teams review.
The Lending Domain at a Glance
Axes of Classification
Loan products are usually classified along three axes. These axes become the dimensions of your data model, so it pays to understand them precisely.
| Axis | Categories | System-Level Difference |
|---|---|---|
| Borrower type | Retail / Corporate | Completely different scoring models (CSS vs corporate rating), limit schemes, required documents |
| Collateral | Secured / Unsecured | Whether collateral system integration and LTV validation logic exist |
| Limit type | Revolving credit line / Term (per-drawdown) loan | Different ledger structure — committed limit and individual drawdowns managed separately |
Retail lending processes standardized products (unsecured personal loans, mortgage loans, lease-deposit loans, etc.) at high volume, so automation rates are high; corporate lending involves large per-deal amounts and qualitative underwriting, so it is designed around workflow. For revolving facilities, the "committed limit" and the "drawn balance" must be managed separately, and from an accounting/risk standpoint it matters that even the undrawn portion counts toward exposure via a credit conversion factor when computing BIS capital ratios.
Map of the Lending Landscape
+------------------------------------------------------------------+
| Channels |
| Mobile app / Internet banking / Branch teller / Call center / |
| Partner platforms (loan marketplaces) |
+---------------------------+--------------------------------------+
|
v
+------------------------------------------------------------------+
| LOS (Loan Origination System) |
| Application -> Underwriting -> Approval -> Agreement -> |
| Disbursement orchestration |
+--+----------+----------+----------+----------+-------------------+
| | | | |
v v v v v
+------+ +--------+ +---------+ +--------+ +-----------+
| CSS | | Limit | |Collateral| | Pricing| | External |
|Credit| | Mgmt | | Mgmt | | Engine | | Gateway |
|Score | | System | | System | | | | (EAI/ESB) |
+------+ +--------+ +---------+ +--------+ +-----+-----+
|
+-------------------------------------------------+
| Credit info registry / Bureaus (NICE, KCB) / Guarantors /
| Open banking and MyData providers
v
+------------------------------------------------------------------+
| Core Banking Ledger |
| Loan ledger / Deposit ledger / Accounting / EOD batch |
+------------------------------------------------------------------+
The LOS orchestrates "the process by which a loan comes into being"; once disbursement completes, the loan account moves to the core banking loan ledger and becomes the territory of the LMS (Loan Management System, i.e., servicing). This post focuses on the LOS segment.
The LOS Pipeline — From Application to Disbursement
The Five-Stage Pipeline
[Application] [Underwriting] [Approval] [Agreement] [Disbursement]
Application -> Underwriting -> Approval -> Agreement -> Disbursement
| | | | |
Identity (KYC) Bureau pull Delegated Contract Booking entry
Product select CSS score authority drafting Ledger account
Data entry Limit check Approve / Rate lock creation
Documents Collateral Conditional / Collateral Funds transfer
Consents valuation Decline perfection Guarantee
Policy rules Validity period Terms fixed confirmation
The system-level essence of each stage:
Application — Receive the request from a channel and create the application entity. The crux is consent management. You cannot call a credit bureau before collecting consent for credit inquiry and for collection/use/provision of personal credit information, so guaranteeing the ordering between the consent event and the inquiry call matters for audit. Record the consent form version, timestamp, and channel as immutable history.
Underwriting — The heart of the pipeline. Credit bureau (CB) pulls, CSS score calculation, policy rule checks (age, annual income, regulatory ratios such as DSR/DTI/LTV, multiple-debt flags), and limit derivation all happen here. The routing logic that splits fully automated decisions from cases escalated to a human underwriter also lives here.
Approval — Apply delegation-of-authority rules to the underwriting result. Depending on amount and grade bands, the approval line differs — auto-approval, branch manager sign-off, head-office credit committee — and every approval carries a validity period (e.g., 30 days). The fact that an expired approval requires re-underwriting must be reflected in the state machine design.
Agreement — Fix the loan terms (amount, rate, tenor, repayment method) and execute an electronic or paper agreement. For secured loans, collateral perfection steps such as registering a mortgage lien slot in between this stage and disbursement. The terms at agreement time must be preserved as an immutable snapshot; later changes are handled as separate amendment agreements.
Disbursement — Often called "booking" or the funding entry. Create the loan account in the loan ledger, post the accounting entry (debit loan asset / credit customer deposit), and transfer funds to the designated account. Disbursement must have crisp transaction boundaries, with compensation handling designed for partial failures.
A Principle for Cross-Stage Data Flow
One principle that practitioners repeat constantly: freeze every fact used at decision time as a snapshot. Store the CB results, the score, income data, the applied policy rule version, and the limit computation as immutable records attached to the application. Months later, when an audit or a customer complaint arrives, you must be able to reproduce "why this decision was made at that point in time." If you only hold reference pointers into master data, the basis for past decisions evaporates the moment the master is updated.
The Real-Time Pipeline for Digital Lending
If the branch-era LOS was a workflow engine measured in days, the LOS for branchless unsecured lending is a real-time pipeline that finishes in tens of seconds. Internet-only banks and fintech loan-comparison marketplaces drove this shift.
Customer App LOS External Parties
| | |
|--- Limit inquiry -->| |
| |--- CB pull ---------->| NICE / KCB
| |<-- Score / debts -----|
| |--- Income/asset ----->| MyData providers
| |<-- Accounts/cards ----| (or certificate-based
| | | scraping: health
| | | insurance, tax office)
| |-- Income estimation --|
| |-- CSS scoring --|
| |-- Policy rules / DSR--|
| |-- Limit & pricing --|
|<-- Pre-approval ----| |
| (limit / rate) | |
|--- Proceed -------->| |
|<-- E-sign / fund ---| |
Design points worth calling out:
- Income estimation: Instead of collecting employment/income documents, gather national health insurance payment history and tax-office income certification data via MyData (licensed personal credit information management) APIs or certificate-based scraping, then estimate income. Applying a conservative haircut to estimated income is standard practice.
- Separating pre-approval from final underwriting: The "limit inquiry" on a marketplace is a soft assessment; final underwriting runs again right before the agreement. You must design the validity window of the pre-approval and the customer notification flow for when final terms differ.
- Distinguishing inquiry types: Use an inquiry type that does not affect the credit score during the limit-check stage, and perform the formal inquiry at actual application time — the CB call types must be deliberately separated.
- Timeouts and fallbacks: So that one slow external institution does not stall the whole pipeline, set per-step timeouts and a fallback-to-manual-review path for partial failures.
- Idempotency: A customer retrying in the app can push the same application through twice. Defend against duplicate applications and duplicate CB pulls with an application-scoped idempotency key.
The Limit Management System
Two Layers of Limits
Limits are managed at two layers: the customer/borrower-level limit ("how much for this customer in total") and the product/account-level limit ("how much through this product"). In corporate lending, a regulatory layer is added on top: single-borrower / connected-borrower limits. Under banking law, credit extended to the same person or entity and parties sharing credit risk with them (a connected borrower group) may not exceed a set fraction of the bank's equity capital, so before approval you must aggregate exposure across the entire borrower group and validate.
Exposure Aggregation
Exposure aggregation is not as simple as it sounds. It must include not only loan balances but undrawn committed limits, guarantees issued, and credit-equivalent amounts of derivatives, summed across the borrower group (affiliate relationships).
-- Borrower-group exposure aggregation (conceptual example)
SELECT g.borrower_group_id,
SUM(CASE WHEN e.exposure_type = 'LOAN_BALANCE'
THEN e.amount END) AS loan_balance,
SUM(CASE WHEN e.exposure_type = 'UNDRAWN_LIMIT'
THEN e.amount * e.ccf END) AS undrawn_equiv,
SUM(CASE WHEN e.exposure_type = 'GUARANTEE'
THEN e.amount END) AS guarantee_amt,
SUM(e.amount * COALESCE(e.ccf, 1.0)) AS total_exposure
FROM exposure_snapshot e
JOIN borrower_group_map g
ON e.borrower_id = g.borrower_id
WHERE g.borrower_group_id = :group_id
AND e.base_date = :base_date
GROUP BY g.borrower_group_id;
Here ccf is the Credit Conversion Factor. The key design decision is whether aggregation is real-time or based on a daily batch snapshot. The common pattern is a hybrid: a snapshot built by the end-of-day batch plus same-day approvals layered on top. Because another deal can disburse between your approval moment and your disbursement moment and eat into the limit, the safe pattern is to soft-reserve the limit at approval and confirm it at disbursement.
The Collateral Management System
Appraisal and Collateral Recognition
For secured lending, the collateral management system owns the collateral master (real estate, deposits, guarantee letters, movables, etc.), appraisal history, lien/perfection records (mortgage registrations and the like), and the calculation of recognized collateral value. For real estate, the basis is an external appraisal firm's valuation or market price data, from which senior liens and tenant deposits (statutory small-tenant deductions, etc.) are subtracted to derive effective collateral value.
LTV Calculation
LTV (Loan To Value) = loan amount / collateral value * 100
Effective collateral value = appraised value * recognition ratio
- senior lien amounts
- tenant deposits / statutory deductions
Example:
Apartment market value : 1,000,000,000 KRW
Regulatory LTV cap : 50% -> LTV-based ceiling = 500,000,000 KRW
Senior mortgage : 100,000,000 KRW
Actual lendable amount : 500M - 100M = 400,000,000 KRW
(varies by policy)
Regulatory LTV caps vary by region (regulated zone or not), number of owned homes, and product type — and they are amended frequently. So never hardcode LTV rules; externalize them into a rule table keyed by effective date. At underwriting time, look up the rule version in force, apply it, and record the applied rule version ID into the underwriting snapshot — that is one complete unit of work.
One more thing: collateral value changes over time. Periodic revaluation happens during servicing, and a deteriorating LTV can trigger additional collateral demands or limit reductions, so model the collateral-to-loan relationship not as 1:1 but as N:M (joint collateral, additional collateral).
Pricing — How the Rate Is Built
Base Rate Plus Spread
A loan rate is broadly derived as "base rate + spread - preferential discounts."
Final rate = base rate + spread - preferential discount
Base rate:
COFIX (new-volume / balance-based), bank debenture yields, CD rate, etc.
-> Floating-rate products reset at each repricing cycle (3/6/12 months)
Spread:
+ Credit cost : expected loss by borrower grade (PD x LGD)
+ Capital cost : cost of regulatory capital
+ Operating cost : staffing / systems overhead
+ Liquidity premium
+ Target margin
Preferential discount:
- Conditional reductions for salary transfer, card usage, savings
- If conditions lapse, the discount is removed -> re-evaluated by a
recurring servicing batch
Three system-level points:
- Base rate master management: Maintain base rates as a history table keyed by publication date; the repricing batch for floating-rate accounts reads from it. "Which publication value applies on the reset date" (publication date vs effective date) must match the product disclosure documents exactly.
- Preserve the spread decomposition: Do not store only the single final rate number. Because there are disclosure and inspection expectations around the reasonableness of rate-setting frameworks, you must preserve the per-component decomposition as of calculation time.
- Post-hoc evaluation of discounts: Whether preferential conditions are met is re-evaluated by a monthly batch, with rate changes taking effect from the next interest cycle. The job dependency — this batch must run before the interest accrual batch — has to be encoded into the EOD schedule.
Agreement and Disbursement — Booking and Ledger Integration
Disbursement (booking) is where the LOS meets the core ledger, and it is the segment of a lending system that must be engineered most conservatively.
LOS Loan Ledger Accounting/Treasury
| | |
|-- 1. Disburse request->| |
| (approval ID, terms) | |
| |-- 2. Create account |
| | (build repayment |
| | schedule) |
| |-- 3. Journal entry ->|
| | Dr loan asset |
| | Cr customer deposit|
| |<- 4. Entry posted ---|
|<- 5. Disburse done ----| |
| (acct no, entry no) | |
|-- 6. State transition | |
| APPROVED->DISBURSED | |
Design principles:
- A single booking transaction: Bundle account creation, journal posting, and crediting into one transaction inside the ledger — or, if impossible, define compensating transactions in a Saga. The most dangerous state is "the account exists but the money never arrived."
- Idempotency keys are mandatory: The LOS disbursement request carries a unique key derived from the approval; the ledger rejects duplicate bookings with the same key. On retry after a timeout, this key is what prevents double funding.
- Final validation before funding: Re-verify the approval validity period, the limit reservation, collateral perfection (lien registration confirmed), and guarantee issuance status immediately before disbursing — days can pass between approval and funding.
- Relationship with EOD: Be explicit about cutover policy — whether bookings are blocked during the end-of-day close, and how next-business-date bookings are value-dated after the close.
External Integration Map
A lending pipeline does not exist without external institution integrations. They are usually unified behind an external gateway.
+----------------------+
| External Gateway |
LOS / CSS <--------->| (format conversion, |
| retry, history, |
| monitoring) |
+---+----+----+----+----+
| | | |
+------------------+ | | +-------------------+
v v v v
Korea Credit Info NICE KCB Guarantee bodies
Services (registry) (retail CB) (retail CB) (Korea Housing Finance
- centralized loan/ - score / report pulls Corp, KODIT, KIBO,
delinquency data - corporate CB separate regional funds)
- mandatory reporting - issue / verify
- fee settlement
+---------------------+--------------------+
v v v
MyData providers Government networks KFTC
(asset/debt data) (income/employment) (account verification,
transfers)
What to take care of in integration design:
- Both directions — inquiry and reporting: You do not just query the CBs; you are also obligated to report loan originations, balances, and delinquencies to the centralized credit information registry. A missed post-disbursement reporting batch is a regulatory issue.
- Format and code mapping: Each institution speaks its own wire format (fixed-length messages, XML, JSON), so the gateway converts to an internal canonical format and maintains mapping tables between institution codes and internal codes.
- Failure isolation: Per-institution circuit breakers and queue-based retries; distinguish mandatory integrations (CB pull) from enrichment integrations (supplementary data) so the latter can be skipped.
State Machine Design
The application state transitions are the skeleton of the LOS. Scattering states and transitions across if-statements makes the system unmaintainable, so centralize them in an explicit state machine.
from enum import Enum
class AppState(str, Enum):
DRAFT = "DRAFT" # being filled out
SUBMITTED = "SUBMITTED" # application complete
SCREENING = "SCREENING" # automated underwriting
MANUAL_REVIEW = "MANUAL_REVIEW" # human underwriter review
APPROVED = "APPROVED" # approved (carries validity period)
CONDITIONAL = "CONDITIONAL" # conditionally approved
DECLINED = "DECLINED" # declined
AGREED = "AGREED" # agreement executed
DISBURSED = "DISBURSED" # funded
EXPIRED = "EXPIRED" # approval validity lapsed
CANCELLED = "CANCELLED" # customer cancelled/withdrew
TRANSITIONS: dict[AppState, set[AppState]] = {
AppState.DRAFT: {AppState.SUBMITTED, AppState.CANCELLED},
AppState.SUBMITTED: {AppState.SCREENING, AppState.CANCELLED},
AppState.SCREENING: {AppState.APPROVED, AppState.CONDITIONAL,
AppState.DECLINED, AppState.MANUAL_REVIEW},
AppState.MANUAL_REVIEW: {AppState.APPROVED, AppState.CONDITIONAL,
AppState.DECLINED},
AppState.CONDITIONAL: {AppState.APPROVED, AppState.DECLINED,
AppState.CANCELLED},
AppState.APPROVED: {AppState.AGREED, AppState.EXPIRED,
AppState.CANCELLED},
AppState.AGREED: {AppState.DISBURSED, AppState.CANCELLED},
AppState.DISBURSED: set(), # beyond this is LMS (servicing)
AppState.DECLINED: set(),
AppState.EXPIRED: set(),
AppState.CANCELLED: set(),
}
def transit(app, to_state: AppState, actor: str, reason: str | None = None):
cur = AppState(app.state)
if to_state not in TRANSITIONS[cur]:
raise InvalidTransition(f"{cur} -> {to_state} is not allowed")
app.state = to_state
# transition history goes into an append-only table:
# (app_id, from, to, actor, reason, ts)
append_history(app.id, cur, to_state, actor, reason)
A few field-tested tips:
- History is append-only: Independently of the current-state column, record who transitioned what, when, and why as immutable history. This is the baseline for audits and complaint handling.
- Time-based transitions run in batch: APPROVED to EXPIRED is performed by a daily batch, not a user action. To prevent funding against an expired approval if the batch is missed, keep a second validation at disbursement time.
- Codify decline reasons: A DECLINED transition must carry a structured reason code. It serves both the adverse-action notification obligation and as training data for improving underwriting models.
Re-underwriting, Amendments, and Refinancing
Re-underwriting
Approval expiry, information changes between pre-approval and final underwriting, and limit-increase requests all trigger re-underwriting. The clean approach is not to rewind the existing application but to create a new assessment round. Model assessment as 1:N under the application, with each round owning its own CB pull, score, and rule snapshot.
Amendments
Post-disbursement maturity extensions, rate condition changes, and repayment method changes are handled as "amendment agreements." Rather than mutating the original agreement, append an amendment record and regenerate the ledger repayment schedule only for the period after the amendment date. Never retroactively modify past periods — doing so corrupts interest accrual history and accounting.
Refinancing
Refinancing is a compound transaction where a new loan disbursement and an existing loan payoff interlock. An internal (same-institution) refinance can be wrapped in one transaction, but an external refinance becomes an asynchronous flow: wire the new proceeds to the other institution's payoff account and confirm the payoff. Where an interbank refinancing infrastructure (a switching hub) is involved, design the whole thing as a Saga up to receipt of the payoff-confirmation callback, and always include a manual intervention queue for mid-flight failures (funds sent but no payoff confirmation received).
Pitfalls in System Design
Pitfalls found repeatedly in real projects:
- Ignoring the approval-to-funding gap: If you trust validation at approval time and skip re-validation at funding time, another loan disbursed in between can push DSR or limits over the line — and you still fund.
- Losing decision evidence via master-data references: Holding customer income, rule versions, and rate components only as pointers means a master update destroys your ability to reproduce a past decision. Snapshots are the answer.
- Conflating state with history: Managing only a current-state column with UPDATEs makes audits impossible; deriving current state from the history table on every read kills performance. You need both.
- Limit deduction without concurrency control: Without a lock or reservation between limit check and deduction, two concurrent applications both pass. Defend with a limit reservation record plus a unique constraint.
- Propagating external timeouts: One CB hanging for 30 seconds exhausts a shared thread pool and cascades into an all-channel outage. Per-integration pool isolation and circuit breakers are mandatory.
- Floating point for money: Using float for interest and fee calculations produces unit-level errors. Use integers (minor units) or fixed-point decimals, and specify truncation/rounding rules as product terms.
- No external simulators in test environments: CB and guarantor test networks cover few cases. If you do not build a scenario-replay simulator for integration responses early, integration testing becomes your bottleneck.
Test Scenarios
Testing a lending system should focus on boundaries and concurrency rather than the happy path. Representative scenarios:
| Area | Scenario | Expected Result |
|---|---|---|
| Underwriting | CB timeout then retry | Only one inquiry recorded, retry succeeds |
| Underwriting | Policy rule effective-date boundary | Correct rule version applied by application date |
| Limits | Two simultaneous applications, same customer | Reservation lets only one pass, or combined check |
| Approval | Funding attempted day after expiry | Funding rejected, EXPIRED transition verified |
| Disbursement | Ledger response lost mid-booking, then retry | Idempotency key prevents double booking |
| Disbursement | Journal posted, transfer failed | Compensating rollback, alert raised |
| Refinance | Payoff confirmation callback never arrives | Queued for manual intervention, state held |
| Pricing | Reset date vs base-rate publication boundary | Publication value matches product disclosure |
| Collateral | Senior lien changes, then revaluation | Effective value and LTV recomputed correctly |
| EOD | Booking requested during close | Blocked or value-dated per policy |
On top of these, a backtest (shadow evaluation) environment that replays past applications through a new rule set before deploying rule changes lets you quantify approval/decline rate shifts in advance and sharply reduces operational risk.
Closing
Behind the deceptively simple notion of "one loan," the lending domain is a precise interlocking of underwriting, limits, collateral, pricing, ledger, and external integrations. If the LOS portion of this post had to be compressed into one line: make every decision reproducible via snapshots, centralize state transitions, and make every money-moving segment idempotent.
In the next post we open up the brain of underwriting — the credit scoring system (CSS): scorecards, ML models, and the decision engine. The post after that explores the world after funding: servicing, delinquency, provisioning, and NPL. Once more, this article is a technical architecture walkthrough, not a financial product solicitation or legal advice.
References
- BIS — Basel Framework (CRE: Credit Risk)
- BIS — Large Exposures Framework (LEX)
- Financial Supervisory Service (Korea)
- Financial Services Commission (Korea)
- Korea Credit Information Services
- Korea Financial Telecommunications and Clearings Institute (KFTC)
- NICE Information Service
- Korea Credit Bureau (KCB)
- Korea Housing Finance Corporation
- Korean Law Information Center — Banking Act / Credit Information Act
- ISO 20022 — Universal Financial Industry Message Scheme