# How Instatic Super Import Converts HTML and CSS Sites

> Learn how Instatic Super Import converts HTML CSS sites using a two-phase headless pipeline for seamless site transformation. Analyze and persist your data effortlessly.

- Repository: [CoreBunch/Instatic](https://github.com/CoreBunch/Instatic)
- Tags: internals
- Published: 2026-07-31

---

**Instatic Super Import is a two-phase, headless pipeline that transforms arbitrary HTML, CSS, and asset files into a fully-featured Instatic site through an analysis phase that builds an ImportPlan and an atomic commit phase that persists the data.**

Instatic's Super Import feature, implemented in the [CoreBunch/Instatic](https://github.com/CoreBunch/Instatic) repository, provides a pure, functional approach to site migration. The system operates without browser rendering, instead using static analysis to parse source files and construct a complete migration plan before writing anything to the database. This architecture ensures that users can preview exactly what will be imported—including potential conflicts—before making any changes to their live site.

## Overview of the Super Import Pipeline

The conversion process splits cleanly into two distinct phases. **Phase 1 (Analysis)** is orchestrated by `buildImportPlan` in [`src/core/siteImport/buildPlan.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/buildPlan.ts) and performs all parsing, classification, and conflict detection. **Phase 2 (Commit)** is handled by `commitImportPlan` in [`src/core/siteImport/commitPlan.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/commitPlan.ts) and handles asset uploads, URL rewriting, and the final atomic transaction that writes pages, style rules, and tokens to the site.

This separation makes the analysis instant and fully testable while ensuring that the actual import is an all-or-nothing operation that can be undone with a single undo command.

## Phase 1: Building the Import Plan

The `buildImportPlan` function receives a **FileMap** (a map of all imported files) and the current `SiteDocument`, returning an `ImportPlan` that powers the preview wizard. The pipeline executes several discrete steps in sequence.

### File Classification and HTML Parsing

First, `classifyFiles` in [`src/core/siteImport/classifyFiles.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/classifyFiles.ts) tags every entry as HTML, CSS, asset, or other. Then, `makeHtmlPagePlan` in [`src/core/siteImport/htmlPagePlan.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/htmlPagePlan.ts) parses each HTML file using `DOMParser` (or a regex fallback) to extract the page title, linked stylesheet hrefs, script tags, and body content.

The function calls `importHtml` to convert the body into a node fragment while preserving the document structure for later conversion into Instatic's native page format.

### CSS to StyleRule Conversion

Raw CSS text is transformed into Instatic's native format by `cssToStyleRules` in [`src/core/siteImport/cssToStyleRules.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/cssToStyleRules.ts). This pure parser produces **StyleRule** objects that respect `@media` queries using the site's defined breakpoints, records asset URLs found within declarations, and emits warnings for duplicate class names across the stylesheet.

The system also expands `@import` chains and partitions linked stylesheets into those that will be kept as raw CSS versus those converted to Instatic style tokens.

### Asset and Font Detection

`extractGoogleFontImports` in [`src/core/siteImport/fontImports.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/fontImports.ts) scans every CSS source for `@font-face` rules referencing Google Font URLs, deduplicates font families, and merges variant lists. Simultaneously, `buildAssetPlan` in [`src/core/siteImport/assetPlan.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/assetPlan.ts) normalizes all URLs (including those inside CSS), creates `Asset` objects for files requiring upload, and resolves `@font-face` blocks to ensure fonts are available after migration.

### Conflict Detection

Before returning the plan, `detectCrossSheetClassConflicts` in [`src/core/siteImport/classCascades.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/classCascades.ts) identifies classes defined differently across multiple stylesheets. The system also checks the existing site for conflicts involving page paths, class rules, and color or font tokens, surfacing these as UI-friendly warnings in the wizard.

The resulting `ImportPlan` contains parsed page fragments, complete style rules, asset upload specifications, and a comprehensive conflict report.

## Phase 2: Committing the Import Plan

When the user confirms the import (or a programmatic caller invokes the commit), `commitImportPlan` executes three major steps in sequence.

### Asset Upload and URL Rewriting

`uploadPlanAssets` streams each asset through `adapter.uploadAsset`. Successful uploads generate a `rewriteMap` mapping `sourcePath` to `mediaUrl`, while failures produce `asset-upload-failed` warnings. `applyAssetRewrites` then traverses the entire `ImportPlan`, replacing every `url(...)` payload with the newly minted media URL.

### Google Font Installation

`installPlanGoogleFonts` asks the adapter to install each detected Google Font family. This step communicates with the server's font installation endpoints to ensure that referenced typography is available in the Instatic editor immediately after import.

### Atomic Transaction Commit

All persistent changes occur within a single `adapter.commit` block. The transaction adds conditions, commits color tokens, installs fonts, writes font tokens, persists style rules, creates pages using `mintPageIds` for stable identifiers, and commits page-scoped files. 

Internal links are rewritten using `mintPageIds` before the commit, converting `<a href="page.html">` references into `cms:page:<id>` references that survive future slug changes. Because the entire operation wraps in a history snapshot, users can undo the entire import with **Cmd+Z**.

## Integration with the Admin UI

The Super Import wizard is exposed through the Spotlight command **Site Import** in [`src/admin/spotlight/commands/siteImport.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/admin/spotlight/commands/siteImport.ts). The wizard wires the pipeline via `createSiteImportAdapter` in [`src/admin/modals/SiteImport/shared/createSiteImportAdapter.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/admin/modals/SiteImport/shared/createSiteImportAdapter.ts), which supplies the `SiteImportAdapter` implementation communicating with server-side import endpoints.

```typescript
// UI side – start the wizard
await startSiteImportWizard({
  buildPlan: (fileMap, currentSite) => buildImportPlan({ fileMap, currentSite }),
  commitPlan: (plan) => commitImportPlan(plan, siteImportAdapter),
});

```

The adapter abstraction allows the same core logic to run in different contexts while handling server-specific concerns like authentication and endpoint routing.

## Programmatic Usage Examples

You can trigger Super Import outside the admin UI using the core functions directly:

```typescript
import { buildImportPlan, commitImportPlan } from '@core/siteImport';

async function importFromZip(zipBytes: Uint8Array, currentSite, adapter) {
  // 1. Convert zip to FileMap (implementation dependent on your utils)
  const fileMap = await makeFileMapFromZip(zipBytes);
  
  // 2. Build analysis plan
  const plan = buildImportPlan({ fileMap, currentSite });
  
  // 3. Modify plan to resolve conflicts if needed
  
  // 4. Atomic commit
  const result = await commitImportPlan(plan, adapter);
  console.log('Imported:', result.pages.length, 'pages');
}

```

For link rewriting, import [`src/core/siteImport/linkRewrite.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/linkRewrite.ts) to handle internal href conversion before committing pages.

## Summary

- **Instatic Super Import** uses a two-phase pipeline: pure analysis (`buildImportPlan`) followed by atomic commitment (`commitImportPlan`).
- The analysis phase classifies files in [`src/core/siteImport/classifyFiles.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/classifyFiles.ts), parses HTML in [`src/core/siteImport/htmlPagePlan.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/htmlPagePlan.ts), and converts CSS via [`src/core/siteImport/cssToStyleRules.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/cssToStyleRules.ts).
- Asset handling and Google Font detection occur in [`src/core/siteImport/assetPlan.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/assetPlan.ts) and [`src/core/siteImport/fontImports.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/fontImports.ts).
- The commit phase uploads assets, rewrites URLs, installs fonts, and performs a single transactional write through the `SiteImportAdapter`.
- All operations are undoable as a single history snapshot, and internal links are preserved through stable ID minting.

## Frequently Asked Questions

### What file types does Instatic Super Import support?

Instatic Super Import processes HTML files (converted to pages), CSS files (converted to StyleRules or preserved as raw CSS), and arbitrary asset files including images, fonts, and binary downloads. The `classifyFiles` function in [`src/core/siteImport/classifyFiles.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/classifyFiles.ts) determines the processing path for each file based on extension and content type.

### How does Super Import handle conflicting CSS classes?

During the analysis phase, `detectCrossSheetClassConflicts` in [`src/core/siteImport/classCascades.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/classCascades.ts) identifies classes defined with different properties across multiple stylesheets. These conflicts are flagged in the `ImportPlan` and presented in the wizard for resolution, allowing users to choose which definition to keep or rename before the commit occurs.

### Is the import process reversible?

Yes. The commit phase in [`src/core/siteImport/commitPlan.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/commitPlan.ts) executes as a single atomic transaction wrapped in a history snapshot. Because the entire import—pages, style rules, tokens, and assets—commits as one operation, users can undo the complete import with a single undo command (Cmd+Z), restoring the site to its pre-import state.

### Can Super Import be used programmatically outside the admin UI?

Absolutely. The core logic in [`src/core/siteImport/buildPlan.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/buildPlan.ts) and [`src/core/siteImport/commitPlan.ts`](https://github.com/CoreBunch/Instatic/blob/main/src/core/siteImport/commitPlan.ts) is headless and framework-agnostic. By providing a custom `SiteImportAdapter` implementation, developers can trigger imports from command-line scripts, custom plugins, or automated migration tools without loading the React-based admin interface.