diff --git a/Directory.Packages.props b/Directory.Packages.props
index ac15e67..7a7d3e4 100644
--- a/Directory.Packages.props
+++ b/Directory.Packages.props
@@ -27,6 +27,7 @@
+
diff --git a/fe/src/App.vue b/fe/src/App.vue
index 9ea996c..a86ef4a 100644
--- a/fe/src/App.vue
+++ b/fe/src/App.vue
@@ -291,10 +291,17 @@
Calendar
-
+
@@ -485,6 +492,7 @@ import {
PhDownload,
PhCheckCircle,
PhList,
+ PhFolderOpen,
} from '@phosphor-icons/vue'
import { ref, computed, onMounted, onUnmounted, nextTick, watch } from 'vue'
import { useEventListener } from '@vueuse/core'
diff --git a/fe/src/components/domain/audiobook/LibraryImportFooter.vue b/fe/src/components/domain/audiobook/LibraryImportFooter.vue
new file mode 100644
index 0000000..d105ef3
--- /dev/null
+++ b/fe/src/components/domain/audiobook/LibraryImportFooter.vue
@@ -0,0 +1,205 @@
+
+
+
+
+
+
+
diff --git a/fe/src/components/domain/audiobook/LibraryImportRow.vue b/fe/src/components/domain/audiobook/LibraryImportRow.vue
new file mode 100644
index 0000000..af9b250
--- /dev/null
+++ b/fe/src/components/domain/audiobook/LibraryImportRow.vue
@@ -0,0 +1,291 @@
+
+
+
+
+
+
+
+
+
+ {{ item.folderName }}
+
+ {{ [item.detectedTitle, item.detectedAuthor].filter(Boolean).join(' · ') }}
+
+
+
+
+
+ {{ item.format }}
+ {{ item.fileCount }} files
+
+
+
+
+
+
+
+
+
+
+
+
+ {{ item.selectedMatch.title }}
+
+
+ {{ item.selectedMatch.authors[0]?.name }}
+
+
×
+
+
+
+
+
+
+
+ —
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/fe/src/components/domain/audiobook/LibraryImportSearchModal.vue b/fe/src/components/domain/audiobook/LibraryImportSearchModal.vue
new file mode 100644
index 0000000..2ef5a7e
--- /dev/null
+++ b/fe/src/components/domain/audiobook/LibraryImportSearchModal.vue
@@ -0,0 +1,227 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+ {{ result.title }}
+
+ {{ result.authors?.[0]?.name }}
+ · {{ Array.isArray(result.series) ? (result.series as any)[0]?.name : result.series }}
+ · {{ result.asin }}
+
+
+
+
+
+
+ No results for "{{ searchQuery }}"{{ authorQuery ? ` by "${authorQuery}"` : '' }}
+
+
+
+ Type a title or paste an ASIN to search
+
+
+
+
+
+
+
+
+
diff --git a/fe/src/components/feedback/UnmatchedFilesModal.vue b/fe/src/components/feedback/UnmatchedFilesModal.vue
new file mode 100644
index 0000000..0b025cc
--- /dev/null
+++ b/fe/src/components/feedback/UnmatchedFilesModal.vue
@@ -0,0 +1,652 @@
+
+
+
+
+
+
+
+
+
+
+
+
Scanning {{ rootFolderName }} for audio files not in your library…
+
+
+
+
+
+
+
+
+
No scan results yet
+
Click Scan to search {{ rootFolderName }} for audio files not in your library.
+
+
+
+
+
+
+
All files are in your library
+
No unmatched audio files were found in {{ rootFolderName }} .
+
+
+
+
+ Found {{ items.length }} folder{{ items.length !== 1 ? 's' : '' }} with audio files not in your library.
+ Last scanned {{ timeAgo(lastScannedAt) }}
+
+
+
+
+
+
+ Title
+ Author
+ Series
+ Year
+ Narrator
+ Files
+ Format
+
+
+
+
+
+
+ {{ item.title || item.relativePath }}
+
+ {{ item.author || '—' }}
+
+ {{ item.series }} #{{ item.seriesNumber }}
+ —
+
+ {{ item.year || '—' }}
+ {{ item.narrator || '—' }}
+ {{ item.fileCount }}
+ {{ item.format }}
+
+
+ Add
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ {{ fileActionLabel }}:
+
+ {{ f.name }}
+
+
+
+ {{ asinCount }} item{{ asinCount !== 1 ? 's' : '' }} with ASIN
+
+
+
+ Adding {{ bulkDone }} / {{ bulkTotal }}…
+
+
+
+
+ Add All (ASIN match)
+
+
+
+ Scan
+
+ Close
+
+
+
+
+
+
+
+
+
+
+
diff --git a/fe/src/components/settings/DownloadSettingsSection.vue b/fe/src/components/settings/DownloadSettingsSection.vue
index 167712c..ebb3ad0 100644
--- a/fe/src/components/settings/DownloadSettingsSection.vue
+++ b/fe/src/components/settings/DownloadSettingsSection.vue
@@ -8,6 +8,10 @@
updateField('maxConcurrentDownloads', Number((e.target as HTMLInputElement).value || 1))" type="number" min="1" max="10" />
+
+ updateField('unmatchedScanConcurrency', Number((e.target as HTMLInputElement).value || 2))" type="number" min="1" max="8" />
+
+
updateField('pollingIntervalSeconds', Number((e.target as HTMLInputElement).value || 10))" type="number" min="10" max="300" />
diff --git a/fe/src/components/settings/RootFoldersSettings.vue b/fe/src/components/settings/RootFoldersSettings.vue
index ffb5cf3..a7470fc 100644
--- a/fe/src/components/settings/RootFoldersSettings.vue
+++ b/fe/src/components/settings/RootFoldersSettings.vue
@@ -39,6 +39,14 @@