@bobfrankston/rmfmail 1.0.480 → 1.0.482

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -65,8 +65,12 @@ async function idbDelete(key: string): Promise<void> {
65
65
 
66
66
  /** GDrive folder ID for the ".rmfmail" app folder */
67
67
  let gDriveFolderId: string | null = null;
68
- /** GDrive folder name (resolved from query — "rmfmail" today, but kept dynamic in case the query changes) */
68
+ /** GDrive folder name (resolved from query — ".rmfmail" today, but kept dynamic in case the query changes) */
69
69
  let gDriveFolderName: string | null = null;
70
+ /** Full path "My Drive/home/.rmfmail" — surfaced in About so the user can verify */
71
+ let gDriveFolderPath: string | null = null;
72
+ /** Owner email of the matched .rmfmail folder — surfaces wrong-account picks (e.g. spouse's shared folder) */
73
+ let gDriveFolderOwner: string | null = null;
70
74
  /** OAuth token provider — set by bootstrap */
71
75
  let tokenProvider: (() => Promise<string>) | null = null;
72
76
 
@@ -74,9 +78,11 @@ export function setGDriveTokenProvider(provider: () => Promise<string>): void {
74
78
  tokenProvider = provider;
75
79
  }
76
80
 
77
- export function setGDriveFolderId(folderId: string, folderName?: string): void {
81
+ export function setGDriveFolderId(folderId: string, folderName?: string, ownerEmail?: string, folderPath?: string): void {
78
82
  gDriveFolderId = folderId;
79
83
  if (folderName) gDriveFolderName = folderName;
84
+ if (ownerEmail) gDriveFolderOwner = ownerEmail;
85
+ if (folderPath) gDriveFolderPath = folderPath;
80
86
  }
81
87
 
82
88
  async function gDriveRead(filename: string): Promise<string | null> {
@@ -474,12 +480,14 @@ export async function getPrefetch(): Promise<boolean> {
474
480
  }
475
481
 
476
482
  /** Get storage info */
477
- export function getStorageInfo(): { provider: string; mode: string; folderId?: string; folderName?: string } {
483
+ export function getStorageInfo(): { provider: string; mode: string; folderId?: string; folderName?: string; folderPath?: string; folderOwner?: string } {
478
484
  return {
479
485
  provider: gDriveFolderId ? "gdrive" : "local",
480
486
  mode: gDriveFolderId ? "api" : "local",
481
487
  folderId: gDriveFolderId || undefined,
482
488
  folderName: gDriveFolderName || undefined,
489
+ folderPath: gDriveFolderPath || undefined,
490
+ folderOwner: gDriveFolderOwner || undefined,
483
491
  };
484
492
  }
485
493
 
@@ -64,12 +64,31 @@ function createTokenProvider(email) {
64
64
  // ── GDrive folder lookup ──
65
65
  async function findGDriveMailxFolder(tokenProvider) {
66
66
  const token = await tokenProvider();
67
- const r = await fetch(`https://www.googleapis.com/drive/v3/files?q=name='.rmfmail' and mimeType='application/vnd.google-apps.folder' and trashed=false&fields=files(id,name)`, { headers: { "Authorization": `Bearer ${token}` } });
67
+ const headers = { "Authorization": `Bearer ${token}` };
68
+ // Two-step path traversal: My Drive root → home/ → .rmfmail
69
+ const homeQ = encodeURIComponent("name='home' and mimeType='application/vnd.google-apps.folder' and 'root' in parents and trashed=false");
70
+ const homeRes = await fetch(`https://www.googleapis.com/drive/v3/files?q=${homeQ}&fields=files(id,name)&spaces=drive`, { headers });
71
+ if (!homeRes.ok)
72
+ return null;
73
+ const home = (await homeRes.json()).files?.[0];
74
+ if (!home?.id)
75
+ return null;
76
+ const q = encodeURIComponent(`name='.rmfmail' and mimeType='application/vnd.google-apps.folder' and '${home.id}' in parents and trashed=false`);
77
+ const r = await fetch(`https://www.googleapis.com/drive/v3/files?q=${q}&fields=files(id,name,owners(emailAddress))&spaces=drive`, { headers });
68
78
  if (!r.ok)
69
79
  return null;
70
80
  const data = await r.json();
71
81
  const folder = data.files?.[0];
72
- return folder?.id ? { id: folder.id, name: folder.name || ".rmfmail" } : null;
82
+ if (!folder?.id)
83
+ return null;
84
+ const homeName = home.name || "home";
85
+ const folderName = folder.name || ".rmfmail";
86
+ return {
87
+ id: folder.id,
88
+ name: folderName,
89
+ path: `My Drive/${homeName}/${folderName}`,
90
+ ownerEmail: folder.owners?.[0]?.emailAddress,
91
+ };
73
92
  }
74
93
  // ── Message handler ──
75
94
  self.onmessage = async (e) => {
@@ -155,8 +174,8 @@ async function initialize() {
155
174
  });
156
175
  }
157
176
  else {
158
- setGDriveFolderId(folder.id, folder.name);
159
- console.log(`[worker] GDrive ${folder.name} folder: ${folder.id}`);
177
+ setGDriveFolderId(folder.id, folder.name, folder.ownerEmail, folder.path);
178
+ console.log(`[worker] GDrive ${folder.path} folder: ${folder.id} (owner=${folder.ownerEmail || "?"})`);
160
179
  // Load accounts from cloud
161
180
  const cloudAccounts = await loadAccountsFromCloud();
162
181
  if (cloudAccounts && cloudAccounts.length > 0) {
@@ -1 +1 @@
1
- {"version":3,"file":"worker-entry.js","sourceRoot":"","sources":["worker-entry.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"worker-entry.js","sourceRoot":"","sources":["worker-entry.ts"],"names":[],"mappings":"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"}
@@ -78,16 +78,35 @@ function createTokenProvider(email: string): () => Promise<string> {
78
78
 
79
79
  // ── GDrive folder lookup ──
80
80
 
81
- async function findGDriveMailxFolder(tokenProvider: () => Promise<string>): Promise<{ id: string; name: string } | null> {
81
+ async function findGDriveMailxFolder(tokenProvider: () => Promise<string>): Promise<{ id: string; name: string; path: string; ownerEmail?: string } | null> {
82
82
  const token = await tokenProvider();
83
+ const headers = { "Authorization": `Bearer ${token}` };
84
+ // Two-step path traversal: My Drive root → home/ → .rmfmail
85
+ const homeQ = encodeURIComponent("name='home' and mimeType='application/vnd.google-apps.folder' and 'root' in parents and trashed=false");
86
+ const homeRes = await fetch(
87
+ `https://www.googleapis.com/drive/v3/files?q=${homeQ}&fields=files(id,name)&spaces=drive`,
88
+ { headers }
89
+ );
90
+ if (!homeRes.ok) return null;
91
+ const home = (await homeRes.json() as any).files?.[0];
92
+ if (!home?.id) return null;
93
+ const q = encodeURIComponent(`name='.rmfmail' and mimeType='application/vnd.google-apps.folder' and '${home.id}' in parents and trashed=false`);
83
94
  const r = await fetch(
84
- `https://www.googleapis.com/drive/v3/files?q=name='.rmfmail' and mimeType='application/vnd.google-apps.folder' and trashed=false&fields=files(id,name)`,
85
- { headers: { "Authorization": `Bearer ${token}` } }
95
+ `https://www.googleapis.com/drive/v3/files?q=${q}&fields=files(id,name,owners(emailAddress))&spaces=drive`,
96
+ { headers }
86
97
  );
87
98
  if (!r.ok) return null;
88
99
  const data = await r.json();
89
100
  const folder = data.files?.[0];
90
- return folder?.id ? { id: folder.id, name: folder.name || ".rmfmail" } : null;
101
+ if (!folder?.id) return null;
102
+ const homeName = home.name || "home";
103
+ const folderName = folder.name || ".rmfmail";
104
+ return {
105
+ id: folder.id,
106
+ name: folderName,
107
+ path: `My Drive/${homeName}/${folderName}`,
108
+ ownerEmail: folder.owners?.[0]?.emailAddress,
109
+ };
91
110
  }
92
111
 
93
112
  // ── Message handler ──
@@ -182,8 +201,8 @@ async function initialize(): Promise<void> {
182
201
  message: "GDrive folder '.rmfmail' not found — app cannot start. Create it or sign in with the correct Google account.",
183
202
  });
184
203
  } else {
185
- setGDriveFolderId(folder.id, folder.name);
186
- console.log(`[worker] GDrive ${folder.name} folder: ${folder.id}`);
204
+ setGDriveFolderId(folder.id, folder.name, folder.ownerEmail, folder.path);
205
+ console.log(`[worker] GDrive ${folder.path} folder: ${folder.id} (owner=${folder.ownerEmail || "?"})`);
187
206
 
188
207
  // Load accounts from cloud
189
208
  const cloudAccounts = await loadAccountsFromCloud();