mirror of
https://github.com/martinlegend/neogdsync.git
synced 2026-07-22 06:08:29 +00:00
Correctness: - Edits made while a sync runs are no longer dropped. Vault event handlers now ignore only paths the sync itself wrote (Syncer.syncWrites) instead of suppressing all events behind a global flag, and pending ops are cleared per-op right after success instead of in a bulk sweep that also wiped ops re-queued mid-sync. - Renames now propagate to Drive: handlePush compares the Drive-side name and calls files.rename, so a local a.md -> b.md no longer leaves the old name on Drive (which later caused duplicate uploads after a rebuild). - A 'modify' op with no index entry (index lost/reset) looks the file up on Drive by path before uploading, preventing duplicate files on Drive. - Excluded paths queued in pendingOps are cleared instead of sticking in the "N pending" counter forever; exclusion logic is now shared between event handlers and the sync engine (src/exclude.ts), so user glob patterns apply consistently. computeDiff no longer reports newly-excluded snapshot entries as deletions. - Files first seen via unknown Drive changes (syncedAt=0) now go through conflict handling instead of silently overwriting the remote copy. - index.db is written via tmp-file + rename with recovery on load, so a crash mid-save can no longer silently reset the index. - Multipart upload boundary is randomized; a file containing the fixed boundary string no longer corrupts the upload. Auth / settings: - authProxyUrl is actually used now (it was silently ignored) and is editable in settings; DriveApi credentials update in place so PathIndex never holds a stale instance; token cache is keyed by token+proxy. - Exclude patterns are editable in settings (README advertised this but there was no UI). Performance / UX: - Force Pull and pull-new-from-Drive download with a small concurrency pool (settings.concurrency, previously dead config). - Unknown-change resolution fetches each file's metadata once instead of twice. - First run with a non-empty vault shows a notice explaining that an initial Force Push/Pull is required. Security / hygiene: - OAuth proxy escapes HTML in the callback pages (reflected XSS via ?error=...), and README now accurately describes that token refresh goes through the proxy and how to self-host it. - Removed stale compiled artifacts (src/*.js) and dead code (listRevisions); fixed package.json metadata (MIT, author, scripts). - Added vitest with unit tests for exclusion, snapshot diffing, and index persistence/recovery (17 tests). Claude-Session: https://claude.ai/code/session_011DimwV9zDr1ViCXRCZPxC9 Co-authored-by: Claude <noreply@anthropic.com>
2.4 KiB
2.4 KiB
NeoGDSync
Lightweight Google Drive sync plugin for Obsidian.
Features
- Smart Sync — auto conflict detection, only syncs changed files
- Force Push — local vault → Google Drive
- Force Pull — Google Drive → local vault
- Conflict handling — saves Drive copy as a conflict file, never overwrites silently
- Path-based index — fast, no full crawl needed after first sync
- Version history — optionally keep file revisions on Drive
- Configurable excludes — glob patterns to skip files/folders
- URI handler —
obsidian://neogdsync?mode=smart|push|pullfor automation
Setup
- Install the plugin
- Go to Settings → NeoGDSync
- Enter your Google OAuth2 Refresh Token
- Enter your Google Drive Vault Root Folder ID (the Drive folder that maps to your vault root)
- Click the ☁ ribbon icon or run a command to sync
Getting a Refresh Token
This plugin uses a standard OAuth2 refresh token with read/write access to Google Drive.
You can obtain one via:
- The Google Drive for Desktop OAuth flow
- Any OAuth2 tool using scope
https://www.googleapis.com/auth/drive
The refresh token is stored locally in your vault's plugin data. To obtain short-lived access tokens, the plugin sends the refresh token to an OAuth proxy (by default the NeoGDSync Cloudflare Worker, see oauth-proxy/worker.js), which exchanges it with Google and returns the access token. The proxy does not store tokens. If you prefer not to route through the shared proxy, deploy your own Worker (instructions in oauth-proxy/worker.js) and set its URL in Settings → NeoGDSync → Auth proxy URL.
Commands
| Command | Description |
|---|---|
| Smart Sync | Detect and sync only changed files, with conflict detection |
| Force Push | Upload all local changes to Drive |
| Force Pull | Download all Drive changes to local |
| Rebuild Drive Index | Re-crawl Drive vault folder to rebuild index |
| Show Conflicts | View detected conflicts |
URI Handler
Trigger sync from outside Obsidian (Shortcuts, scripts, etc.):
obsidian://neogdsync?mode=smart
obsidian://neogdsync?mode=push
obsidian://neogdsync?mode=pull
License
MIT