Skip to content

Commit 1a80673

Browse files
fix(storage): persistent SQLite migration flag (#827)
1 parent 29d7dc0 commit 1a80673

4 files changed

Lines changed: 65 additions & 20 deletions

File tree

src/main/index.ts

Lines changed: 35 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -181,29 +181,44 @@ else {
181181
= (store.preferences.get('storage.vaultPath') as string | null)
182182
|| path.join(storagePath, 'markdown-vault')
183183
ensureFlatSpacesLayout(vaultPath)
184-
const { hasMarkdownVaultData } = lazyRequire(
185-
'./storage/providers/markdown',
186-
) as typeof import('./storage/providers/markdown')
187-
const vaultHasData = hasMarkdownVaultData(vaultPath)
188-
189-
if (!vaultHasData) {
190-
const { closeDB } = lazyRequire('./db') as typeof import('./db')
191-
const { migrateSqliteToMarkdownStorage } = lazyRequire(
192-
'./storage/providers/markdown',
193-
) as typeof import('./storage/providers/markdown')
194184

195-
try {
196-
migrationResult = migrateSqliteToMarkdownStorage()
185+
// Авто-миграция из SQLite выполняется только один раз. Флаг
186+
// storage.sqliteMigrated персистентно блокирует повтор, иначе ручная
187+
// очистка vault при сохранившемся massCode.db триггерила бы миграцию
188+
// заново и возвращала удалённые данные.
189+
const alreadyMigrated
190+
= store.preferences.get('storage.sqliteMigrated') === true
197191

198-
store.preferences.delete('storage.engine' as any)
199-
store.preferences.delete('backup' as any)
200-
201-
// eslint-disable-next-line no-console
202-
console.log('[Auto-migration complete]', migrationResult)
203-
}
204-
finally {
205-
closeDB()
192+
if (!alreadyMigrated) {
193+
const { hasMarkdownVaultData } = lazyRequire(
194+
'./storage/providers/markdown',
195+
) as typeof import('./storage/providers/markdown')
196+
const vaultHasData = hasMarkdownVaultData(vaultPath)
197+
198+
if (!vaultHasData) {
199+
const { closeDB } = lazyRequire('./db') as typeof import('./db')
200+
const { migrateSqliteToMarkdownStorage } = lazyRequire(
201+
'./storage/providers/markdown',
202+
) as typeof import('./storage/providers/markdown')
203+
204+
try {
205+
migrationResult = migrateSqliteToMarkdownStorage()
206+
207+
store.preferences.delete('storage.engine' as any)
208+
store.preferences.delete('backup' as any)
209+
210+
// eslint-disable-next-line no-console
211+
console.log('[Auto-migration complete]', migrationResult)
212+
}
213+
finally {
214+
closeDB()
215+
}
206216
}
217+
218+
// Помечаем миграцию как выполненную в обоих случаях: после успешной
219+
// миграции и как backfill для пользователей, уже мигрировавших в
220+
// прошлых версиях (vault с данными, но без флага).
221+
store.preferences.set('storage.sqliteMigrated', true)
207222
}
208223
}
209224
}

src/main/store/__tests__/preferences.test.ts

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -170,6 +170,30 @@ describe('preferences store sanitization', () => {
170170
).toBeUndefined()
171171
})
172172

173+
it('keeps persisted sqliteMigrated flag and defaults it to false', async () => {
174+
persistedStateByName.preferences = {
175+
storage: {
176+
sqliteMigrated: true,
177+
},
178+
}
179+
180+
const { default: preferences } = await import('../module/preferences')
181+
182+
expect(preferences.get('storage.sqliteMigrated' as any)).toBe(true)
183+
})
184+
185+
it('defaults sqliteMigrated to false for invalid or missing value', async () => {
186+
persistedStateByName.preferences = {
187+
storage: {
188+
sqliteMigrated: 'bad',
189+
},
190+
}
191+
192+
const { default: preferences } = await import('../module/preferences')
193+
194+
expect(preferences.get('storage.sqliteMigrated' as any)).toBe(false)
195+
})
196+
173197
it('keeps persisted http settings and prunes stale values', async () => {
174198
persistedStateByName.preferences = {
175199
http: {

src/main/store/module/preferences.ts

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,7 @@ const PREFERENCES_DEFAULTS: PreferencesStore = {
5858
storage: {
5959
rootPath: storagePath,
6060
vaultPath: null,
61+
sqliteMigrated: false,
6162
},
6263
editor: {
6364
code: EDITOR_DEFAULTS,
@@ -307,6 +308,10 @@ function sanitizePreferences(value: unknown): PreferencesStore {
307308
'vaultPath',
308309
PREFERENCES_DEFAULTS.storage.vaultPath,
309310
),
311+
sqliteMigrated:
312+
typeof storageSource.sqliteMigrated === 'boolean'
313+
? storageSource.sqliteMigrated
314+
: PREFERENCES_DEFAULTS.storage.sqliteMigrated,
310315
},
311316
editor: {
312317
code: sanitizeCodeEditorSettings(codeEditorSource),

src/main/store/types/index.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -190,6 +190,7 @@ export interface MarkdownSettings {
190190

191191
export interface StorageSettings {
192192
vaultPath: string | null
193+
sqliteMigrated: boolean
193194
}
194195

195196
export interface NotesEditorSettings {

0 commit comments

Comments
 (0)