Developer Tips

Automating FileMaker Data Imports with Scripts

How experienced FileMaker developers build scripted data imports that are repeatable, reviewable, and safer to run in production.

Automating a FileMaker data import is not the same thing as clicking through the import dialog faster. A real import script has to protect record identity, relationships, validation rules, audit history, and the developer who may need to explain the result two weeks later.

For FileMaker developers, the dangerous part is rarely the Import Records step by itself. The dangerous part is everything around it: source data that changed since the last test, reused serial numbers, child records that no longer have valid parents, unstored calculations that hide bad mappings, and a production window where everyone wants the result to be both fast and reversible.

This is where FMDojo should be part of the workflow. Before writing the import scripts, import or connect the file context in FMDojo, review the schema in Snapshots, use AI Chat with that context to challenge the import plan, and keep the final runbook tied to the approval and release notes. The goal is not to let AI "do the import." The goal is to give an expert FileMaker developer better evidence before they touch production data.

This post is about record-level imports: staging rows, validating source data, matching target records, and writing creates or updates safely. It is not about moving a FileMaker Server, SSL certificates, DNS, schedules, or a full production cutover.

Map the source and target before writing scripts

Start in FMDojo Snapshots with a current Save as XML export or LiveConnect-backed context for the files involved. The point is to see the real tables, fields, keys, relationships, scripts, and layout context before you invent an import path from memory.

FMDojo Snapshot schema context used to review source and target tables before writing an import script

For each imported entity, write the mapping like a developer handoff, not like a loose spreadsheet:

Entity: Contacts
Source: LegacyContacts
Target: Contact
Source key: LegacyContacts::ContactID
Target key: Contact::zLegacyContactID
Parent dependency: Account via LegacyAccounts::AccountID -> Account::zLegacyAccountID
Create rule: Create when no Contact::zLegacyContactID match exists
Update rule: Update only fields owned by the import
Skip rule: LegacyContacts::Status = "Deleted"
Stop rule: active contact with no Account match

In FMDojo, open the Snapshot and check the table occurrence names and key fields against the actual relationship graph. Then ask AI Chat something specific:

Using this FileMaker schema context, review my Contacts import mapping.
Find parent-child risks, missing key fields, validation conflicts, and any
place where a script rerun could create duplicates.

That prompt is useful because it is grounded in the file context. A generic "write an import script" prompt is not.

Use staging tables, not direct imports into production tables

For production imports, I normally do not import directly into the final table first. I import into a staging table, validate the staged rows, produce a reviewable plan, and only then write to the target table.

A practical staging table for a Contacts import might include:

ContactImportStaging
  BatchID
  SourceContactID
  SourceAccountID
  TargetContactID
  TargetAccountID
  RawName
  RawEmail
  NormalizedEmail
  PlannedAction
  ValidationStatus
  ValidationError
  ImportStatus
  LastFileMakerError
  ImportedAt

That table gives you a place to answer the questions that matter before the target data changes:

  • Which rows will be created?
  • Which rows will update an existing target record?
  • Which rows are blocked because the parent Account is missing?
  • Which rows will be skipped intentionally?
  • Can the script be stopped and safely resumed?

This is the difference between an import dialog and a controlled import workflow.

Build the controller as a runbook

Your top-level FileMaker script should read like a runbook. It should call smaller scripts that each have one job and return a meaningful result.

FMDojo workspace map showing the kind of FileMaker context that should be reviewed while building the import runbook

For example:

IMPORT - Contacts - Controller
  1. Require import approval and backup confirmation
  2. Create Batch record
  3. Clear prior staging rows for this BatchID
  4. Import LegacyContacts into ContactImportStaging
  5. Normalize staged values
  6. Resolve Account and Contact target keys
  7. Validate staged rows
  8. Stop if blocking errors exist
  9. Write Contact creates
  10. Write Contact updates
  11. Reconcile counts
  12. Mark Batch complete

Each child script should use Set Error Capture [ On ], write its own phase result, and return a simple JSON result to the controller:

{
  "phase": "Validate staged contacts",
  "status": "blocked",
  "blockingErrors": 14,
  "warningCount": 27
}

In FileMaker, this keeps the controller simple. In FMDojo, paste the script outline into AI Chat and ask for a review against the schema context:

Review this FileMaker import controller for rerun safety. Assume the script
may stop after target creates but before target updates. What fields or phase
guards are missing?

That is the kind of review another senior developer would do before a production import window.

Make the import idempotent

If an import cannot be rerun safely, it is not ready for a production window.

For each staged row, calculate a PlannedAction before changing target records:

Create
Update
Skip
Error

Then store the target primary key back on the staging row before writing field values. Do not rely on names, email addresses, or found-set position. Use stable legacy IDs when they exist, and create review queues when they do not.

The core loop for target writes should be boring:

Go to Layout [ ContactImportStaging ]
Enter Find Mode [ Pause: Off ]
Set Field [ ContactImportStaging::BatchID ; $batchId ]
Set Field [ ContactImportStaging::PlannedAction ; "Create" ]
Set Field [ ContactImportStaging::ImportStatus ; "Ready" ]
Perform Find

Loop
  Exit Loop If [ Get ( FoundCount ) = 0 or Get ( RecordNumber ) > Get ( FoundCount ) ]
  Set Variable [ $sourceId ; ContactImportStaging::SourceContactID ]

  New Window [ Style: Document ; Name: "ImportWrite" ]
  Go to Layout [ Contact ]
  New Record/Request
  Set Field [ Contact::zLegacyContactID ; $sourceId ]
  Set Field [ Contact::Name ; ContactImportStaging::RawName ]
  Set Field [ Contact::Email ; ContactImportStaging::NormalizedEmail ]
  Commit Records/Requests [ With dialog: Off ]
  Set Variable [ $error ; Get ( LastError ) ]
  Close Window [ Current Window ]

  Perform Script [ "IMPORT - Log Row Result" ; Parameter: JSONSetElement ( "{}" ;
    [ "sourceId" ; $sourceId ; JSONString ] ;
    [ "error" ; $error ; JSONNumber ]
  ) ]

  Go to Record/Request/Page [ Next ; Exit after last: On ]
End Loop

The exact script steps will differ by solution, but the pattern should not: find a controlled set, write one row at a time, commit deliberately, capture Get ( LastError ), and record what happened.

Review relationships before the first write

Most bad imports are relationship failures wearing a field-mapping costume. A Contact import that does not resolve Account correctly will look fine until a portal, report, script, or integration depends on that relationship.

FMDojo relationship diagram context used to check parent-child dependencies before a scripted import writes target records

Before the write phase, produce relationship checks from staging:

  • Every child row has a resolved parent target key.
  • Every join table row has both sides resolved.
  • No source key maps to more than one target key.
  • No target key will be overwritten by multiple source rows.
  • Required relationship predicates are populated, including tenant, organization, or active flags.

This is a good place to use FMDojo with the Snapshot relationship context. Ask:

Given this FileMaker relationship graph, which target tables should be loaded
before Contacts, and what relationship predicates could make a staged match look
valid in one table occurrence but fail in another?

That question is specific to FileMaker. It catches problems that a generic database import checklist misses.

Keep dry runs and production runs separate

Build a dry-run mode into the controller. A dry run should import into staging, normalize, resolve keys, validate, and reconcile expected counts. It should not create or update target records.

For production, record the run context:

  • Import name and version
  • FileMaker file names and hosted server
  • Source export timestamp or snapshot ID
  • Batch ID
  • Operator
  • Approval note or ticket
  • Backup timestamp
  • Start and finish times
  • Created, updated, skipped, warning, and error counts

FM Deploy can help keep the operational side honest when a scripted import is part of a broader release. Use it to record approval context, rollback expectations, and post-run checks around the change. The import scripts still need to be written and tested by a FileMaker developer, but the release should not live only in someone's memory.

Reconcile like you expect a support call

The script reaching the last line is not the definition of done.

Reconcile from both directions:

eligible source rows = created + updated + skipped + error
staged parent matches = target parent records found
staged child rows = created child rows + intentionally skipped child rows
blocking errors = 0 before production writes

Then spot-check records from the business side:

  • A customer with multiple contacts
  • A contact with no email but valid phone
  • A customer intentionally skipped
  • A record with historical notes
  • A record touched by an integration
  • A record with container data, if containers are in scope

If a client asks why a record changed, you should be able to answer from the import tables without rerunning the script or reading logs from memory.

The FMDojo workflow I would use

Here is the practical FMDojo flow for this kind of import work:

  1. Export the current FileMaker file as XML or connect the file context through LiveConnect.
  2. Open Snapshots in FMDojo and verify the source and target tables, keys, relationships, and scripts.
  3. Draft the import contract and staging table design.
  4. Use AI Chat with the Snapshot context to challenge the mapping, rerun safety, relationship order, and validation gates.
  5. Write the FileMaker import scripts in phases.
  6. Run a dry run against a restored copy of production data.
  7. Record approval, backup, rollback, and reconciliation notes before the production run.

That workflow respects the craft. FMDojo supplies context, review pressure, and release evidence. The FileMaker developer still owns the script, the data rules, and the decision to run it.

What is new in FMDojo related to this

FMDojo gives FileMaker developers a better review path for scripted imports. Use Snapshots to inspect table, field, script, and relationship context before writing the import. Use AI Chat with that context to review the staging design and controller script. Use FM Deploy planning notes when the import is tied to a controlled release that needs approval, rollback, and reconciliation evidence.

Start with Snapshots for schema context, or open AI Chat when you want an import runbook reviewed against the actual FileMaker file.