top of page

NHS Easy Wins : Part 2

The concluding journey of my experience building a tool for the betterment of doctor-kind.

Well, that's a bit of an exaggeration - It's a tool to speed up clinic prep.

But, it's done, it was fun - and maybe you can do something like it too!



For those of you who missed it, here's part one :


What is left

Now I won't follow on from the previous post outlining every bit of code and why, because that would be too long-winded and frankly a bit boring.


The repository is on GitHub if you want to have a play: https://github.com/samjm000/The_Clinic_Prepper/tree/main


But, I do want to talk about some of the challenges I had in building it.

Because these are the sort of challenges you will probably face if you're building something similar.


Why end-user testing is so important

Problem numero uno. Straight off the batt, reading in the Excel file.


Surprisingly enough, people will not do what you think they are going to do.

This is where error handling comes in. Even if it can't be done wrong, trust me, it can - and will. There are many ways to skin a cat.

(That really is a bizarre analogy - I can only think of one way to do it.)


The Getting the CHI Numbers Problem

Code for the enthusiasts, chat below:

# function to return a dicitonary of times and chi numbers from excel 

def get_chi_numbers(excelFile):
    print(f"Running Excel import from {excelFile}")
    clinic_file = pd.ExcelFile(excelFile)

    # Read in sheet 1 CHI numbers and time
    clinic_sheet = clinic_file.parse("Sheet1", converters={"Time": str, "CHI": str})

    # Normalize the column names to lowercase
    clinic_sheet.columns = [col.strip().lower() for col in clinic_sheet.columns]

    # Drop the rows where 'CHI' is NaN
    clinic_sheet = clinic_sheet.dropna(subset=["chi"])

 ....

Excel Files

This kept coming back to haunt me - because I assumed that there was only one way to copy something into Excel from the EHR.

... select the field, copy the field, paste the field... label the field headings, I mean, how hard can it be right?! ...


Well, let me tell you - it's pretty embarrassing trying to show off your new program to your professor, and as they click on your import Excel file on your shiny GUI and it just immediately hangs, it can leave you more than just a little red in the face.

Even more so when they are being really kind about it, and saying things like, "I'm sure it'll work, just give it a couple more seconds..." when you can see it has paled out and clearly crashed catastrophically in the background.


It should be noted that handling Excel imports is the easiest thing in the world - if someone is doing exactly what you're doing when copying information from one source to the other.

But actually, everyone seems to do the most simple things slightly differently.


The endless possible iterations of possibility:

Did they copy all in lower case, or is it in upper case, did they label the identification column 'CHI, or chi, or Chi'?

What if the CHI number was saved in a numerical format rather than text?

What if they have a birthday that starts with a single digit and their CHI number defaults to 9 characters rather than 10 in length?


All of these things will crash the process unless you have thought about it and handled it.

This is why test-driven development is so successful :)

(And why when you really can't be arsed to write tests because it all feels more long-winded that way, and then you end up writing endless test loops to work out where the problem is, you have only yourself to blame!)





How to navigate the pitfalls

So in this example, I have created a function called 'get_chi_numbers' I've made all the columns lowercase by default and pulled in the whole line as it copies and pastes directly from the EHR page.

This way, no one has to select a portion to copy and paste, hopefully removing the 'personal quips' to some extent.

You can see that I'm pulling the appt_time, chi_number, first_name and last_name from the spreadsheet into the program, and I've made sure everything is lower_case, whilst also ensuring that both time and chi are strings.

Uniformity is key for downstream processing.


   ....
	# save data from sheet as series
    appt_time = clinic_sheet["time"]
    chi_number = clinic_sheet["chi"]
    first_name = clinic_sheet["fname"]
    last_name = clinic_sheet["lname"]

    # remove '(b)' from time string
    appt_time = appt_time.str.replace("(b)", ":00", case=False)

    # Combine the data into a dictionary with CHI as the key
    combined_data = {
        chi: {"time": time, "fname": fname, "lname": lname}
        for chi, time, fname, lname in zip(chi_number, appt_time, first_name, last_name)
    }
    return combined_data

The overbooked problem

You may wonder what the 'b' part of the string is about.

This is for dealing with the 'overbooked' problem.

This is where patients are double booked into a time slot. My first rodeo down this path of pulling in clinic info I was using the appointment time as the unique field.

This would fail if there were two patients at the same time. This is indicated by replacing the minutes with a (b) in our EHR.


This was a mistake. I thought of the clinic process in the way I see the clinic - a patient at each time, time being the primary field of the data.


Time isn't the primary field. The patient is.

But, and this is somewhat an ironic testament to how we are perhaps now missing the point as clinicians. How we are perhaps seeing the clinics these days, as the time being the primary field and getting through patients quickly enough is the most important part of the job. Time isn't the primary field. The patient is.


They are the unique and primary field. You should never have the same patient on your list twice - then something has definitely gone wrong ! ;D

So I left that in as it kept the timings clean, but it isn't necessary. I really liked the sentiment of it though.


Takeaways

I think this journey highlights how programming isn't just about taking a system and translating it to a digital form. You've got to think about it. You need to understand it and the nuances of how it works from a practical sense.

You also need to think about the end user, especially clinicians trying to navigate the multiple different user interfaces and systems all the time.

A bit of ease and simplicity will go a long way.


Here's the repo if you want to have a look.


Have a fantastic evening and I look forward to updating you with my LLM adventures in the extremely near future.


Peace!

Sam



Doctors That Code
© 2024 : Powered and secured by Wix

bottom of page