Preparing Your Patient Notes Data for Upload to Brim: Common Gotchas and How to Fix Them

Brim expects a very specific CSV structure. Clinical notes data is especially tricky because the text of notes often contains commas, line breaks, and quotation marks, the same characters that give a CSV file its structure. This guide walks through the most common issues and how to resolve them before uploading.


Here's what Brim expects:


The data CSV has one document per row, and should be formatted as described below. Note that the field name must be in the CSV header.


Each row must have a unique pair of NOTE_ID and PATIENT_ID fields in order to be successfully imported.


Field Name Field Description Notes
NOTE_ID Alphanumeric identifier of the Note The combination of NOTE_ID and PATIENT_ID must be unique for each row.
PATIENT_ID Alphanumeric identifier for the Patient The combination of NOTE_ID and PATIENT_ID must be unique for each row.
NOTE_DATETIME Timestamp when a note was written. Format must be: "YYYY-MM-DD HH:MM:SS" Other formats that are also accepted are MM/DD/YYYY HH:MM:SS and MM/DD/YYYY. When in doubt, use the recommended format to avoid ambiguity.
NOTE_TEXT The text of the note. Note text fields are wrapped in double quotes.
NOTE_TITLE The title of the note. It is helpful if the notes have meaningful titles that contain the note type e.g. "Pathology Report", "ED Intake". If NOTE_TITLE is missing or empty for a row, Brim will not error, it will substitute the placeholder text "Note Type" as the title. If you see "Note Type" appearing in Brim where you expected a meaningful title, check your NOTE_TITLE column for empty values.

Note: The alphanumeric identifier for the Patient may be specified using either PERSON_ID or PATIENT_ID as the header. Both formats are accepted and treated equivalently. The alphanumeric identifier for Note may be specified using either NOTE_ID or DOCUMENT_ID. Both formats are accepted and treated equivalently.

Two ways an upload can go wrong

Uploads are easier to monitor, diagnose, and fix. Knowing which of these two things happened tells you where to go looking.


Brim stops the file before it starts. Brim now checks your file's header the moment you select it. If something is wrong with the file itself (wrong format, missing columns, no data), you get a popup right away in plain language explaining what Brim found. Nothing uploads, and no entry appears in Upload History. If you're hunting for a failed upload in Upload History and can't find one, this is why: the file never got that far.


Brim accepts the file and rejects individual rows. If the header is valid, the upload runs to completion. One bad row will not cause a file to fail to upload. Instead Brim will reject the row and upload the good lines in the file. The upload appears in Upload History with a specific, actionable error, and for files with rejected rows you can download just the rejected lines with a column explaining why each was rejected, then fix and re-upload.

Problems Brim catches before you upload

The header check confirms that your file is really a CSV or TSV rather than a renamed Excel workbook, that it's UTF-8 text, that all five required columns are present and each appears only once, and that there's at least one data row. If any of that fails, the popup names the problem and usually contains the fix. Every popup message is listed in the decoder at the end of this article.


Headers are case-sensitive and must match exactly: NOTE_ID, PATIENT_ID (or PERSON_ID), NOTE_DATETIME, NOTE_TEXT, NOTE_TITLE. These will fail: Note ID, NoteID, text.


Two things you don't need to clean up first: extra spaces around your column names, and blank lines above the header row. Brim handles both.

Common Gotchas

Here are some common reasons you may be having issues with your file:


Gotcha 1: Opening the CSV in Excel — and then saving it. When Excel opens a CSV and you save it, Excel silently reformats dates (2023-01-15 09:30:00 → 1/15/2023 or worse) and strips time components, truncates note text longer than 32,767 characters with no warning, adds or removes quotes in ways that break field boundaries, and converts numeric NOTE_IDs or PATIENT_IDs to scientific notation (e.g., 1234567890 → 1.23457E+09).


Fix: Do not open your final CSV in Excel. Use Notepad/TextEdit in plain text mode. If you must use Excel, export to CSV only from its original source, and never re-save a CSV that Excel has opened.


Gotcha 2: Commas, line breaks, and quotation marks inside note text. These are the same characters that give a CSV its structure, so if a text field isn't wrapped in double quotes, Brim reads them as structure rather than content:


  • A note saying "Patient has hypertension, diabetes, and hyperlipidemia" has its row split at every comma. The rejected row reads "Row has 6 values but the header has 5 columns."
  • Clinical notes almost always have line breaks, "Chief Complaint:" on one line and the actual complaint on the next. An unquoted line break is read as a new row, so one note becomes 10 rows and the entire file falls apart.
  • A note containing Patient reported "no pain" needs those quotes doubled: Patient reported ""no pain"". A single unescaped quote corrupts everything from that point forward, and Brim will name the line: "Could not read line 4."
  • If a quoted field is opened and never closed, Brim keeps reading into the rows below it looking for the closing quote. One missing quote can cost you several notes, and the reason names the whole range: "Could not read lines 4 to 5." If a note is missing from Brim, check the rows immediately above it too.

Fix: Wrap all NOTE_TEXT and NOTE_TITLE fields in double quotes, preserve internal line breaks inside those quotes, find-and-replace all " with "" inside text fields, and confirm every opening quote has a matching closing quote.


Heads up: when a row has been split by an unquoted line break, there often isn't enough of it left for Brim to report back. The rejected rows file will show you the line numbers, but the note text column may be empty. Use the line numbers to find those notes in your source file.


Gotcha 3: Duplicate NOTE_ID + PATIENT_ID pairs. If the same note appears twice for the same patient (e.g., from a data export that joined tables incorrectly), Brim keeps the first occurrence and skips the later one. The rest of the file uploads normally, and the skipped row shows up in your rejected rows download with a reason like "Duplicate NOTE_ID 'N003' for PATIENT_ID 'P001' — this row repeats an earlier row in the file."


Because Brim keeps the first copy, check which version you actually wanted. If your export produced two rows with the same NOTE_ID but different note text, the one Brim kept may not be the one you meant to load.


Fix: Before uploading, check for duplicates.


Gotcha 4: File encoding issues. Excel on Windows saves CSVs in Windows-1252 encoding by default, not UTF-8. Clinical notes often contain smart quotes, em dashes, and other characters that get garbled when the encoding is wrong. You might see characters like “ instead of ".


A different encoding problem comes from saving as "Unicode Text" in Excel, which produces a UTF-16 file. Brim catches this one before the file uploads and names the cause: "The file is not UTF-8 text. It looks UTF-16 encoded, which Excel's Unicode Text export produces. Save it as CSV UTF-8."


Fix: When saving from Excel, choose "CSV UTF-8 (Comma delimited)" from the Save As format dropdown. Not just "CSV," and not "Unicode Text." If your export tool offers an encoding option, set it to UTF-8.


Gotcha 5: Multiple Notes Concatenated in One Row. If your file has multiple notes combined into a single row, Brim will treat the entire contents as one note rather than separate documents. For example, you might expect a patient to have 10 individual documents in Brim, but instead see only one. This means all of that patient's notes were concatenated into a single row before upload.


Important: Brim will not show an error. The file will upload successfully, making this easy to miss.


Fix: This cannot be corrected by reformatting the file. Go back to your data source and re-export, ensuring the file is structured with one note per row before uploading.


Gotcha 6: Empty values in required fields. If your file contains one or more rows with an empty value in a required column, those rows can't be imported. For example, a row without a value in NOTE_DATETIME will be rejected. Fix: Ensure every required column has a value for each row, then re-upload the rejected rows.


Gotcha 7: Empty NOTE_TEXT fields are silently skipped. If a row has no value in the NOTE_TEXT column, Brim will not show an error. The file will upload successfully, but that row will be quietly dropped and the note will not appear in Brim. You won't know a row was skipped unless you compare your expected document count against what actually loaded. Fix: Before uploading, filter your data to ensure every row has a value in NOTE_TEXT. If some notes genuinely have no text, go back to your data source and investigate before uploading.

Before You Upload — Common Things to Check For:

  • File is saved as .csv or .tsv, not .xlsx
  • Headers are exactly NOTE_ID, PATIENT_ID (or PERSON_ID), NOTE_DATETIME, NOTE_TEXT, NOTE_TITLE
  • No column appears twice in the header
  • File has at least one data row
  • NOTE_DATETIME is YYYY-MM-DD HH:MM:SS. Other formats that are also accepted are MM/DD/YYYY HH:MM:SS and MM/DD/YYYY. When in doubt, use the recommended format to avoid ambiguity.
  • Note text fields are wrapped in double quotes
  • Quotation marks inside note text are doubled ("")
  • No line breaks outside of quoted fields
  • No duplicate NOTE_ID + PATIENT_ID combinations
  • Every row has a value in NOTE_TEXT
  • File saved as UTF-8 encoding

Brim Error Message Decoder

Nothing appears in Upload History for these. Fix the file and select it again.


Brim says… What it means Common cause What to do
No file uploaded. Please select a CSV file. No file was attached when upload was attempted Form submitted without selecting a file first Select a file before clicking upload
This is an Excel workbook, not a CSV. The file is an .xlsx or .xls workbook A workbook was renamed to .csv instead of being exported as one Open in Excel and Save As "CSV UTF-8 (Comma delimited)"
The file looks tab-separated… The file uses tabs as separators but has a .csv extension Data exported from a database client or pasted out of a query tool Save the file with the .tsv extension, or re-export as comma-delimited
The file is not UTF-8 text. It looks UTF-16 encoded, which Excel's Unicode Text export produces. Save it as CSV UTF-8. The file is UTF-16 rather than UTF-8 Saved from Excel as "Unicode Text" instead of "CSV UTF-8 (Comma delimited)." Some database and PowerShell exports also default to UTF-16. Re-save the file as CSV UTF-8
The file is empty. The file has no content at all An export wrote a zero-byte file Re-run your export and confirm the file size before uploading
The file has a header row but no data rows. Headers are present but there are no notes The query behind the export returned no results Confirm your export returned rows before uploading
Missing required column NOTE_TITLE. Columns found: NOTE_ID, PATIENT_ID, NOTE_DATETIME, NOTE_TEXT. A required column is absent or misnamed Column was renamed, deleted, or never included. Brim checks for exact matches: NOTE_ID, NOTE_DATETIME, NOTE_TEXT, NOTE_TITLE, PATIENT_ID (or PERSON_ID) Compare your headers against the list shown in the message. Restore or rename the column named in the error.
Column NOTE_DATETIME, NOTE_ID, PERSON_ID appears more than once. Each column name may appear only once. One or more column names are in the header twice. Every duplicated column is named in the message. A join or merge duplicated columns in the export Delete or rename the duplicate columns. If several are listed, check whether your export is joining the same table twice.
This is not a csv or tsv file. File format is not accepted and doesn't match one of the specific cases above File was exported in a format other than CSV or TSV Re-export your data as a .csv or .tsv file

Upload History messages, shown after the file uploads

The file uploaded. Download the rejected rows for the detail, fix them, and re-upload.


Brim says… What it means Common cause What to do
Row has 6 values but the header has 5 columns A row has more fields than the header allows An unquoted comma inside note text or a title split the row Wrap NOTE_TEXT and NOTE_TITLE in double quotes
Could not read line 4 A row couldn't be parsed An unescaped quotation mark inside a quoted field Double the internal quotes ("") inside text fields
Could not read lines 4 to 5 A range of rows couldn't be parsed A quoted field was opened and never closed, so the rows below it were swallowed Find the unclosed quote. The notes below it are affected too.
Missing NOTE_ID field NOTE_ID is missing or blank One or more rows have no value in the NOTE_ID column Check that every row has a value in that column
Missing PATIENT_ID field PATIENT_ID is missing or blank One or more rows have no value in the PATIENT_ID column Check that every row has a value in that column
Invalid PATIENT_ID: {mrn} An MRN value contains characters Brim can't accept MRN contains unsupported characters. Letters, numbers, and underscores are allowed. Spaces, hyphens, and punctuation (e.g. #, @, -) will cause this error. Review the MRN values in your source data and remove any special characters
Invalid PATIENT_ID: {mrn} (type mismatch variant) An MRN value is in a format Brim can't read as an identifier MRN column contains a value in an incompatible data type, possibly a float or other non-string value. May also be caused by Excel converting long numeric IDs to scientific notation (e.g. 1.23E+10) Check that MRN values are plain text. If using Excel, format the PATIENT_ID column as Text before exporting to prevent scientific notation conversion.
Duplicate NOTE_ID '{note_id}' for PATIENT_ID '{mrn}' — this row repeats an earlier row in the file. Two rows share the same NOTE_ID + PATIENT_ID combination. Brim kept the first one and skipped this one. Duplicate rows in source data, a join error in your export, or a single note split across multiple rows Search for the NOTE_ID and PATIENT_ID shown in the error. Confirm the copy Brim kept is the one you wanted, then remove or merge the duplicates in your source data.
Unable to process date: {date} A date value in NOTE_DATETIME can't be parsed Date is in an unexpected format, or contains a non-date value (e.g. blank, placeholder text, or a number) Check the NOTE_DATETIME column for the value shown in the error. Ensure all dates follow the expected format before re-uploading.
Missing field {column} in {row} A required column is present in the header but has no value in a specific row A cell is blank in a required column, or a row has fewer columns than the header (e.g. due to a stray line break in the data) Find the row indicated and fill in the missing value for the column shown. Check for line breaks embedded in cell values.
Error: could not get PATIENT_ID in {row} {number} An unexpected error occurred while reading the PATIENT_ID value from a row Technical exception, likely a data format issue in that row rather than something the file header would catch Review the row indicated. If the issue isn't obvious, contact your Brim administrator with the full error message.
Error bulk creating patients…, Error acquiring create patient lock…, or Upload failed: {filename}. Something went wrong on Brim's end rather than in your file A system-level error, or another upload for the same project running at the same time Wait for any other active uploads to finish, then try again. Check the Upload History table for a more specific error on the same file. If it persists, contact your Brim administrator with the full error message.

Uploading through the API

If you post files to /api/v1/upload/csv/, the same header check runs before the file is accepted. A file that fails it returns a 400, and the response detail contains the same plain-language message you'd see in the popup. You can read and act on it the same way.

Did this answer your question? Thanks for the feedback There was a problem submitting your feedback. Please try again later.