Chapter 4

Fee Management

school_admin

Overview

Fees in CampusOS are built in layers rather than as one flat "fee amount" field, because real schools need to change one part (say, this year's Library Fee) without rebuilding everything, discount an individual student without touching the whole class's plan, and add a new charge (a school trip, a uniform set) without writing code. This chapter also covers the biggest change to this module recently: a Fee Structure's due-date calendar is no longer something you build by hand — saving Group Configuration now keeps it in sync automatically, and every structure moves through a real Draft → Active → Archived lifecycle that controls exactly when it can be assigned, edited, or deleted.

Key concepts

  • 1. Fee ComponentA single named charge, e.g. "Tuition Fee," "Computer Lab Fee," or a Transport route's own fee. Components are reusable — the same component can appear in every class's Fee Structure. The amount you enter is always the annual figure, however often the student actually gets billed.
  • 2. Fee StructureA class's complete fee plan for an academic year. You no longer build its Installments by hand — you configure which groups (Academic, Transport, Hostel, Miscellaneous) are enabled and how often each bills, and the due-date calendar generates and stays in sync automatically.
  • 3. Structure LifecycleEvery Fee Structure is draft, active, or archived. Only active can be assigned to a student or billed; once active, its own setup is locked; archiving requires zero students still assigned.
  • 4. ConcessionA discount rule (percentage or fixed amount) applied to one student — e.g. a 10% Sibling Discount — optionally requiring a real uploaded document before it can be applied. Applying one after invoices already exist offers an explicit choice: recompute those too, or start from the next Generate.
  • 5. InvoiceThe final, computed, per-student bill for one due date: every attached component's amount, minus whatever concessions apply to that student. Consolidated mode merges every group's charges due on the same date onto one invoice; Group-wise never merges them.

Why this order matters: a Structure can't be activated with nothing configured, and Generate needs an Active structure with at least one enabled group — Concessions can be created any time, but only change what's billed once applied to a student.

4.1 Fee Components

A Fee Component is the reusable building block every Fee Structure, Transport route, Store item, and ad-hoc charge is ultimately made of. Create the ones your school actually charges once, then reuse them everywhere.

The Fee Components list
Figure 4.43. Fee Components — the catalog of billable items reused across Fee Structures, Transport, and Store.
The blank New Fee Component form
Figure 4.44. The New Fee Component form.
The New Fee Component form rejecting a save with Name and Category empty
Figure 4.45. Negative scenario — Name and Category are both required; the form is rejected with a clear message before anything is saved.
Computer Lab Fee filled in as a mandatory Academic component
Figure 4.46. "Computer Lab Fee" filled in under Tuition & Academic, marked Mandatory — every enrolled student is charged it automatically once attached to a Fee Structure.
The Fee Components list now including Computer Lab Fee
Figure 4.47. Saved — Computer Lab Fee now appears in the catalog, still unpriced (Default Amount is only for opt-in components).
Default Amount is always the annual figure

For any opt-in (non-mandatory) component, Default Amount pre-fills a student's subscription rate — but whatever number you enter is always interpreted as the annual total, however often the group actually bills. ₹1,200 entered here becomes ₹100/month if the group is monthly, or the full ₹1,200 if annual. It's also now a required field for an opt-in component — you cannot save one, or tag a student to it, without a real positive amount first.

Field reference
FieldRequiredDescription
NameRequiredMust be unique.
CategoryRequiredWhich group (Academic, Transport, Hostel, Miscellaneous, Ad-hoc) this component belongs to — or create a new category inline.
Default Amount (₹)Required for opt-in componentsThe annual figure a subscription defaults to; not shown at all for Mandatory components (their price lives on the Fee Structure's own Academic Components list instead).
Ledger CodeOptionalFor accounting/export reconciliation.
Display SequenceOptionalControls ordering on invoices and lists.
Mandatory componentOn: every student on a Fee Structure that includes it is billed automatically. Off: opt-in — a specific student must be tagged (a subscription) before it ever bills.

4.2 Linking Transport & Store items to a fee

A Transport route's stop and a Store item (Uniform, Books) each automatically get their own linked Fee Component the moment you create them — you never create these fee components directly. Price them right here on the Fee Components page, exactly like any other component.

Transport

The Route Manager list
Figure 4.48. Route Manager.
New Route form filled in for Manual Route A
Figure 4.49. A new route, "Manual Route A."
Add Stop form filled in for Vijayanagar Circle
Figure 4.50. Adding a stop, "Vijayanagar Circle."
Route with the new stop added
Figure 4.51. The stop added — its own Fee Component now exists, unpriced.
The stop's Fee Component before a price is set
Figure 4.52. Back on Fee Components — the stop's own component, before pricing.
Default Amount filled in as 1200 for the stop
Figure 4.53. Default Amount set to ₹1,200/year.
Fee Components list showing the Transport stop now priced
Figure 4.54. Priced — ready to tag a student onto this route.

Store (Uniform, Books)

Store Category Manager
Figure 4.55. Store → Category Manager.
New Category form filled in for Uniform
Figure 4.56. A new category, "Uniform."
New Item form before Billable is checked
Figure 4.57. A new item, "Uniform Set — Class 3," before marking it Billable.
The item marked Billable
Figure 4.58. Marked Billable — this is what creates the linked Fee Component.
Item Catalog Manager showing the new item
Figure 4.59. The Item Catalog.
Default Amount filled in as 1500 for the Uniform item
Figure 4.60. Priced at ₹1,500 on the Fee Components page.
Fee Components list showing Uniform now priced
Figure 4.61. Ready to tag onto a student's Optional Charges.

Ad-hoc charges (one-off, no Store item)

For a genuine one-off (a school trip, a special event fee) that doesn't need a Store item or Transport route behind it, create the component directly under a new Ad-hoc category.

Creating a new Ad-hoc category, Educational Trip
Figure 4.62. Creating a new Ad-hoc category, "Educational Trip," inline from the component form.
Industrial Visit component filled in at 850
Figure 4.63. "Industrial Visit — Grade 3" at ₹850.
Fee Components list including the Ad-hoc component
Figure 4.64. The full catalog so far.

4.3 Fee Structure — Group Configuration auto-syncs the calendar

This is the biggest change to this module: Installments are no longer a screen you manage by hand. A Fee Structure has one real per-group setting screen — Group Configuration — and saving it is the only action that ever touches the underlying due-date calendar. Enable Academic at Half-yearly and Transport at Monthly, click Save, and both calendars generate themselves; change Academic to Quarterly later and its calendar regenerates automatically, reproportioning the same annual total across the new number of cycles instead of silently changing what each cycle costs.

Fee Structures list
Figure 4.65. Fee Structures — set up once per year, then expand a row to configure it.
Blank New Fee Structure form
Figure 4.66. The New Fee Structure form.
New Fee Structure filled in for Class 2, Consolidated mode
Figure 4.67. Filled in for Class 2, Consolidated invoice grouping.
Fee Structures list showing the new structure, status Draft
Figure 4.68. Created — notice its Status is Draft automatically; nothing about it is usable yet.

Group Configuration

Group Configuration panel, nothing enabled yet
Figure 4.69. Group Configuration — nothing enabled yet.
Academic and Transport enabled with their own frequencies
Figure 4.70. Academic (Half-yearly) and Transport (Monthly) enabled — each group keeps its own independent cadence.
Group Configuration saved, Academic Fee Components panel now visible below
Figure 4.71. Saved — the due-date calendar for both groups generated itself; no separate "Auto-generate" step exists any more.
Pick the frequency before you Save — the draft dropdown value is not what bills

Selecting a new frequency in the dropdown updates what you see, but the calendar behind it only changes once you actually click Save Group Configuration. A red "Unsaved changes" warning appears the moment your on-screen selection diverges from what's actually saved, specifically so this can't happen silently.

Academic Fee Components

Transport, Hostel, and Miscellaneous each get their price from the Fee Component's own Default Amount the moment a student subscribes. Academic is different — its components are attached directly to the structure, in one action that fans them out across every Academic installment at once.

Add Academic Components form with Computer Lab Fee checked and amount 2000
Figure 4.72. Adding Computer Lab Fee at ₹2,000/year across every Academic installment.
Academic Fee Components table showing Computer Lab Fee attached
Figure 4.73. Attached — every Academic installment now carries this component's per-cycle share.

Consolidated vs. Group-wise

Structure activated, status now Active
Figure 4.74. Activated — ready to be assigned to students and billed.
A second structure created in Group-wise mode
Figure 4.75. A second structure for the same class, in Group-wise mode instead.
Fee Structures list showing both modes side by side
Figure 4.76. Both exist side by side — a student is assigned to exactly one.
Two or more groups are due on the exact same date — what happens at Generate?

The generation mode lives on the Fee Structure itself (Consolidated is the default), and can be overridden for one specific run.

Merged
Consolidated mode, and the due dates genuinely coincide

Every group due that date lands on one invoice — e.g. Academic (quarterly) + Transport (quarterly, same effective date) merge onto a single ₹3,300 invoice instead of two.

Kept separate
Group-wise mode, OR the due dates don't actually coincide

Each group gets its own invoice. This is also why a Transport/Hostel tag can look like it's "not showing" under Consolidated — see Billing Diagnostics below.

Field reference
FieldRequiredDescription
NameRequired 
Academic YearRequired 
Invoice GroupingRequiredConsolidated (merge same-due-date groups) or Group-wise (never merge).
Class / SectionOptionalLeave blank for "all" — applies school-wide until a more specific one exists.
Group Configuration (per group)At least one enabledEach enabled group needs its own frequency; saving with none enabled is rejected.

4.4 Fee Structure Lifecycle

Every Fee Structure moves through exactly one forward path: Draft → Active → Archived. This exists specifically so a structure that's still being set up can never accidentally get assigned to a student or billed, and so a structure that's finished being used can be retired without anyone accidentally reviving or editing it.

A newly-created structure showing status Draft
Figure 4.77. A brand-new structure always starts as Draft — freely editable, but invisible to every "assign a Fee Structure" picker in the app.
The structure activated
Figure 4.78. Switched to Active — it now appears in every Fee Structure picker (Add Student, Class Promotion, Admission) and can be Generated against.
Editing an Active structure shows a locked message
Figure 4.79. Once Active, editing is locked outright — even before anyone is assigned. The message says so plainly; use "Duplicate as New Version" to make a changed copy instead. The same table also shows several other structures at a glance: some Locked (in use), some still Draft, one Active-and-editable.
The structure archived, Delete now enabled
Figure 4.80. Archived — this is only allowed once zero students are currently assigned to it. Delete, previously greyed out while Active, is now available.
What can I actually do at each status?
StatusEditable?Assignable / billable?Deletable?Can move to
DraftYes, freelyNoYesActive, Archived
ActiveNo — not at allYesNo — archive firstArchived only
ArchivedNoNoYesNowhere — terminal

Archived is deliberately a dead end — there is no "reactivate." If you need a similar structure again, duplicate an existing one as a new version instead of trying to revive an old one.

4.5 Concessions

Concession Rules list, empty
Figure 4.81. Concession Rules — empty.
New Concession Rule filled in, targeting Computer Lab Fee specifically
Figure 4.82. "Sibling Discount — Computer Lab," a 10% rule scoped to one specific component (not the whole invoice).
Concession Rules list showing the new rule
Figure 4.83. Saved.
Field reference
FieldRequiredDescription
NameRequired 
Discount ValueRequired0–100 for a percentage rule; any positive figure for a fixed amount.
Applies ToRequiredWhole Invoice, a Fee Category, or specific Fee Components — scopes exactly what the discount reduces.
Document RequiredOptionalWhen on, applying the rule requires a real uploaded file — not a typed-in link.

Applying a concession — before vs. after Generate

Applying a concession before a student's invoices exist bakes it in automatically, exactly as before. Applying one after real invoices already exist now offers an explicit choice: recompute those existing unpaid invoices too, or leave them as-is and only apply from the next Generate onward. A partially-paid invoice is always excluded — its charges are already frozen the moment any payment lands on it.

A document-required rule selected, showing the real file upload field
Figure 4.84. Selecting a document-required rule reveals a real file upload — not a URL text box. Whatever is uploaded is also filed under the student's own Documents tab.
Apply blocked with an error because no document was attached
Figure 4.85. Negative scenario — applying a document-required rule with nothing attached is rejected before any request is even sent.
Sibling Discount applied to Ananya Rao, retroactive summary shown
Figure 4.86. Applied to a student who already had two unpaid invoices — the summary reports exactly how many were recomputed and the total discounted.
Both existing invoices now showing the discount and reduced balance
Figure 4.87. Proof it actually landed — both already-issued invoices now show the ₹200 discount and the reduced ₹1,800 balance, not just the concession record.

4.6 Tagging a student at Admission

Everything above comes together at Add Student: pick (or override) the Fee Structure, override a specific group's cadence just for this student if needed, enroll them in Transport, tick any optional components (Uniform), and apply a concession — all in the same form, before the student even has an ID.

Add Student basic details filled in
Figure 4.88. Basic details.
Fee structure explicitly selected instead of class default
Figure 4.89. Fee Structure explicitly picked — only Active structures ever appear in this list.
Transport group frequency overridden for just this student
Figure 4.90. Overriding Transport's cadence for just this one student, without touching the structure itself.
Enroll in Transport checked
Figure 4.91. Enrolling in Transport.
Uniform optional component checked
Figure 4.92. Ticking the optional Uniform component.
Student created, onboarding logins shown
Figure 4.93. Created — parent/student portal login details are shown once, right here.

4.7 The Student Fee Profile & Generating Invoices

Right after a student is created, a "Generate this student's first invoice" shortcut appears on their Overview tab — a fast path into Fees & Payments without hunting through menus. From there, Generate always targets whatever Fee Structure is actually assigned, using its own Consolidated/Group-wise setting unless you override it for this one run.

Fees & Payments tab, Generate remaining invoices section
Figure 4.94. Fees & Payments — Generate remaining invoices, scrolled straight to from the Overview shortcut.
Real invoices generated for the student
Figure 4.95. Real invoices generated — Collect Payment, Record Cheque, Send Link, and Waive are all available per row from here.

4.8 Billing Diagnostics — "why isn't this billing?"

A student can be tagged for Transport, Hostel, or a Uniform, yet see nothing charged for it — usually because the subscription started after that group's only due date under the current cadence (an annual group only gets one due date a year). This used to be silent. It no longer is: both the Optional Charges list and the Generate screen now say exactly what's wrong and what to change.

Generate section showing a red warning about a stuck subscription, and the Optional Charges list showing a Stuck badge with explanation
Figure 4.96. Both diagnostics on the same page: a red callout above Generate names the exact charge and reason, and the Optional Charges row itself carries a "Stuck — no upcoming due date" status with the same explanation.
Optional Charges — Billing status meanings
StatusMeaning
InvoicedA real invoice already carries this charge.
Pending — bills {date}Not yet billed, but a real upcoming due date exists — the next Generate will pick it up.
Stuck — no upcoming due dateNo due date under the group's current frequency falls on/after this subscription's Effective From. Change the group's frequency in Group Configuration so a new cycle lands after that date, or correct Effective From if service genuinely started earlier.

Validation rules & common errors

Validation rules & common errors
TriggerError shownResolution
Fee Component saved with no Name/CategoryName and category are requiredFill both before saving.
Opt-in component saved with no Default AmountDefault Amount is required for an opt-in (non-mandatory) componentEnter a positive annual amount.
Group Configuration saved with nothing enabledEnable at least one group before savingEnable at least one group and give it a frequency.
Editing an Active or Archived Fee StructureCannot edit a Fee Structure once it is active/archivedDuplicate it as a new version instead.
Archiving a structure with students still assignedN student(s) are still assigned to this Fee Structure — reassign them first before archivingReassign or unassign every student first.
Deleting an Active Fee StructureCannot delete an Active Fee Structure — archive it firstArchive it, then delete.
Generating invoices against a draft/archived structureThis Fee Structure is not ActiveActivate it first.
Assigning a draft/archived structure to a studentOnly an Active Fee Structure can be assigned to a studentOnly Active structures ever appear in the picker — activate the one you need.
Concession discount value out of rangeDiscount value out of rangeEnter a percentage between 0 and 100 (or switch to a fixed amount).
Document-required concession applied without an uploadA supporting document is required for this concessionAttach a real file before applying.
Verify with a real invoice, every time

After building or changing a Fee Structure or Concession, generate one real invoice for a real student and check the breakdown — it's the fastest way to catch a misconfigured group cadence or a concession that isn't computing as expected.