Merging class records without touching the source.
A rule-based merge tool for district administrators managing student roster data, built around a hard constraint: the operation had to feel safe enough that someone would actually run it on live enrollment records.
Work shown with enterprise-identifying details removed. Product name and interface are my own; original assets are not shown.
Schools and their software have to agree on what a class is.
School districts run a student information system that holds every student, teacher, course, and class section. That data has to reach dozens of learning applications, and it has to arrive in a shape those applications can read. A roster platform sits between the two, pulling data out of the district's system, transforming it, and syncing it onward.
The person doing that work is a district data administrator. They are technical, but they are not engineers, and the records they are handling are real students in real classrooms. A bad sync does not produce a bug report. It produces a teacher who cannot see half their roster on the first day of school.
One real class, scattered across many records.
Student information systems frequently split a single real-world class into several separate records. The same teacher, same course, same room, but recorded once per period, per section, or per term depending on how the district set things up years ago.
Downstream, every one of those fragments syncs as its own distinct class. A teacher who runs one combined section sees three. Applications that assign work by class assign it three times. And there was no way to combine them during the import at all.
- Restructure the data upstream in the student information system, which is slow, political, and often not theirs to change
- Accept the duplicates and let every connected application inherit the fragmentation
- Maintain manual workarounds per vendor, repeated every time the roster refreshed
The word "merge" was the hardest part.
Building a rule builder was the tractable half. The difficult half was that merge, to almost everyone, means combine and destroy. Two things go in, one thing comes out, and the originals are gone.
This feature does not work that way. It creates a new class from the matching ones and leaves every original record exactly as it was. Nothing is deleted, no schedule changes, no student is permanently moved. It adds structure rather than replacing it.
Which made the mental model the actual deliverable. If the interface could not make the non-destructive behavior obvious before someone clicked anything, the merge logic underneath it did not matter, because nobody would trust it enough to use it.
Three decisions, in order, one at a time.
I structured the merge as three sequential steps rather than a single configuration form. Each step asks one question, and the answer to the first determines what the next two can even offer.
- No way to combine class records during the import at all
- A single real class arrives downstream as several separate records
- The only remedies sit outside the tool: restructure the source system, or accept the duplicates
- Every connected application inherits the fragmentation
- Merge rules defined in three ordered steps
- Match fields, resolution rules, and the merged title each decided explicitly
- The result previewed against real records before anything is saved
- Original records untouched; merged classes added alongside them
Each step collapses to a single summary line once answered, so the full rule stays readable at a glance without a separate review screen.
The rule has to be legible while you build it.
A completed step collapses to one line stating what was chosen. Three answered steps become three short sentences, which means the administrator can read their entire rule back before running anything.
That removed the need for a dedicated confirmation screen. A review step that introduces information the user has not already seen is a warning sign; a review step that only repeats it is a delay. Keeping the summary inline meant the rule was always under review.
Half the guidance is about what the tool refuses to do.
A guide panel sits beside the configuration and changes with the step in view. On step one it explains that matching is strict. On step two it explains that a rule can be left open. On step three it explains which title fields are available and why.
Before any step is opened, it explains the model itself: what a merge creates, what happens to the originals, and what the feature will never do.
- Does not delete classes
- Does not modify schedules
- Does not move students permanently
- Does not replace source data
That list is the piece of this project I would defend hardest. It is not documentation and it is not a disclaimer. It is the thing that lets an administrator run a bulk operation on student enrollment records without hesitating, because it answers the question they are actually asking, which is not how does this work but what could this break.
The merge panel, rebuilt and interactive.
I rebuilt this as a standalone prototype with fictional records, embedded below. Select match fields and watch the result preview. Source records stay exactly where they are; the merged class appears alongside them.
Strict matching, or close enough?
Step one requires classes to match every selected field. There is no partial match, no similarity threshold, and no confidence score. Given how differently districts structure their data, a looser rule would have caught more of the fragments administrators actually wanted combined.
I chose strict anyway. A fuzzy match that merges two classes an administrator did not intend to merge is a silent error on live enrollment records, and the entire feature rests on the promise that nothing surprising happens. Catching fewer fragments is a cost the administrator can see and correct. Merging the wrong ones is not.
A structural fix that districts can make themselves.
The feature shipped to production and is in use by districts today. Fragmented class records can now be resolved during the import itself, without restructuring the student information system and without per-vendor workarounds downstream.
Because merges create new records rather than altering existing ones, administrators can define a rule, see the result, and adjust it without any risk to their source data. The reversibility is what made the feature usable at all.
The rule builder was never the hard part.
The interface question was how to combine two class records. The design question was how to make someone believe nothing would be lost when they did.