Once your CSV is ready, the actual upload step in Bulk Import is straightforward: drop the file on the page, review the preview table, and click Import.
The preview gives you a row-by-row look at exactly what will land in your ledger before anything is committed — including which prices the import derived for you and where every row will be slotted.
This article walks through that flow, screen by screen.
If your CSV isn't ready yet, start with Preparing your CSV and come back when you have a file in hand.
Opening the Bulk Import page
Open the Bulk Import page from the Bulk Import button in the top-right of the Add Purchase form. The button is visible on the Premium plan only — Starter and Pro accounts don't see it.
Step 1: Confirm where rows will land
Before you upload anything, glance at the bottom of the How it works panel. There's a small notice there that names the destination portfolio for every row in your upload.
Blue notice: A specific portfolio is currently selected in the portfolio switcher at the top of the app, and the notice tells you which one. Every row in your upload will land in that portfolio.
Amber notice: "All Portfolios" is selected. The import will fall back to your first portfolio, and the notice tells you which one. Switch the portfolio selector at the top of the app to the specific portfolio you want, and the amber notice becomes a blue confirmation.
The notice is always on screen, so you'll see it before you upload rather than discovering the destination after a mistaken import. If you maintain separate portfolios for, say, personal versus household stack, set the selector before you start.
Step 2: Drop your file on the page
The lower half of the page is a dashed drop zone labelled Drop your CSV here or click to browse.
Drag and drop: Drag the .csv file from your file browser onto the drop zone. The page parses it as soon as you release.
Click to browse: Click anywhere inside the drop zone to open a file picker. Pick your CSV and the page parses it the same way.
Only files with a .csv extension are accepted. If you've been editing the file in Excel, save or export it as CSV (Comma delimited) before you upload. The import doesn't read .xlsx files directly.
The page processes the file locally as soon as it lands; nothing is created in your ledger yet. What you get next is the preview.
Step 3: Read the preview
When the file parses, the drop zone is replaced by a preview panel. This is where you confirm everything looks right before committing.
The preview header
A small bar across the top of the preview shows three things:
The filename: Sanity check that you uploaded the file you meant to.
A row count and validity summary: "3 rows · All rows valid" when everything passed, or "4 rows · 1 error" when at least one row tripped a validation check.
The Replace and Clear buttons: Covered in the next section.
The preview table
Each row in your CSV becomes a row in the preview table. The columns mirror what will end up on the transaction:
#: The row number from your CSV, so a flagged row is easy to find in your spreadsheet.
Date: The purchase date as parsed from your date column.
Product / Catalog ID: Either the catalog_id you supplied (with the matched product name above it) or the product_name from the row's custom fields. The label (from custom) next to the product tells you the row came in via the no-catalog-id path.
Metal: The metal for the product on the row.
Qty: The quantity from your CSV — also the number of inventory items the row will create.
Price / Unit: The price per unit from your CSV, in USD.
Premium / Unit: Either the value from your premium_per_unit column, or (calculated) if the import derived it from price and spot.
Spot at Time: The spot price per troy ounce in USD. Either the value from your spot_at_time column, or one of two derived-value markers — see below.
Shipping: The value from your shipping_cost column, in USD.
Dealer: The free-text dealer name from your dealer column.
Status: OK for a row that passed validation, Invalid for a row that didn't.
Derived-value markers
When the import calculates a price field from the others, it tells you so in the preview rather than silently filling a number in. The three markers you'll see:
(calculated): Appears under Premium / Unit when the row left premium_per_unit blank. The import derived the premium from price_per_unit minus the row's melt value at the recorded spot.
(from price + premium): Appears under Spot at Time when the row left spot_at_time blank but filled in premium_per_unit. The import worked backwards to figure out what spot must have been at the time of purchase.
(current): Appears under Spot at Time when the row left both spot_at_time and premium_per_unit blank. The import fell back to today's live spot for the metal — fine for a row dated today, worth a second look for a row dated years ago.
If you see (current) on a historical row by accident, cancel the import, fill in spot_at_time (or premium_per_unit) from your invoice, and re-upload. Recorded spot drives cost basis math, so getting it right matters.
Step 4: Use Replace or Clear if you need a do-over
Two controls at the top-right of the preview let you start over without leaving the page:
Replace: Opens the file picker so you can swap in a different CSV. Use this when you've edited the file in your spreadsheet app and want to re-run validation on the new version. The preview re-parses from scratch.
Clear: Discards the upload entirely and returns the page to its empty state. Use this if you've decided not to import after all, or if you want to take another pass at the CSV before re-uploading.
Neither button creates anything in your ledger — only the Import button does that.
Step 5: Click Import
The button at the bottom-right of the preview is labelled Import N transactions, where N is the number of valid rows. Two behaviors worth knowing:
When every row is valid, the button is active and shows the full row count. Clicking it commits every row to your ledger as its own BUY transaction.
When at least one row is invalid, the button shows Import 0 transactions and is inactive. Bulk Import is all-or-nothing — even the valid rows are held until the invalid ones are fixed. Edit your CSV to clear the flagged rows, save, and use Replace to re-upload. For the longer version of what triggers a flag.
The Cancel button next to it discards the upload without importing anything and returns you to the prior screen.
What happens after you click Import
The page commits the upload and routes you to the Transactions History page. The full list of what changes downstream is in the overview — see the After import section in Bulk import overview — but the short version:
The Transactions History page lists each imported row as its own BUY transaction, dated to the purchase date from your CSV.
The Holdings page picks up every individual coin and bar as its own item record.
The Dashboard and Analytics pages update Total Portfolio Value, allocation, and the cost-basis-driven charts.
Custom items created on the fly show up on the My Custom Items tab of the Catalog.
If you spot a mistake on a specific row after the fact, you can edit or delete that single transaction from the History page.
Where to go next
Preparing your CSV: The column-by-column reference for the template.
Fixing common CSV errors: What the validation step looks for and how to clear the most common flags.
Bulk import overview: The conceptual tour of how Bulk Import fits together as a feature.
Bulk upload and your transaction limit: How imported transactions count against your plan's transaction cap.
Editing a transaction after the fact: Fixing entries after they're in your ledger.
Deleting a buy transaction: And what happens to the inventory items it created.


