|
322 | 322 | const normalize = useDirs ? u => u.replace(/[^/]+$/, '') : u => u; |
323 | 323 | url = normalize(url); |
324 | 324 | const contextUrl = normalize(sender.tab.url || documentUrl); |
| 325 | + const ctxKey = Sites.optimalKey(contextUrl); |
325 | 326 |
|
326 | 327 | const origin = Sites.origin(url); |
327 | 328 | const {siteKey} = Sites.parse(url); |
328 | | - const options = [ |
329 | | - {label: _("allowLocal", siteKey), checked: true} |
| 329 | + |
| 330 | + const forcedTemp = sender.tab.incognito; |
| 331 | + |
| 332 | + const allowLabel = forcedTemp ? "allowTemp" : "allowLocal"; |
| 333 | + |
| 334 | + const options = [ |
| 335 | + { |
| 336 | + label: _(allowLabel, siteKey), |
| 337 | + checked: true, |
| 338 | + _key: siteKey, |
| 339 | + }, |
330 | 340 | ]; |
331 | 341 | if (!(url.startsWith("blob:") || useDirs)) { |
332 | 342 | if (siteKey === origin) { |
333 | 343 | origin = new URL(url).protocol; |
334 | 344 | } |
335 | | - options.push({label: _("allowLocal", origin)}); |
| 345 | + options.push({ label: _(allowLabel, origin), _key: origin }); |
| 346 | + } |
| 347 | + |
| 348 | + options.push({ label: _("CollapseBlockedObjects"), _collapse: true }); |
| 349 | + |
| 350 | + const checks = [ |
| 351 | + { label: _("capsContext") + `\n${ctxKey}`, checked: true, _val: "ctx" }, |
| 352 | + ]; |
| 353 | + |
| 354 | + if (!forcedTemp) { |
| 355 | + checks.unshift( |
| 356 | + { label: _("allowTemp", TAG), checked: true, _val: "temp" }, |
| 357 | + ); |
336 | 358 | } |
337 | | - const OPT_COLLAPSE = options.length; |
338 | | - options.push({label: _("CollapseBlockedObjects")}); |
339 | | - let t = u => `${TAG}@${u}`; |
| 359 | + |
340 | 360 | let ret = await Prompts.prompt({ |
341 | 361 | title: _("BlockedObjects"), |
342 | | - message: _("allowLocal", TAG), |
343 | | - options}); |
| 362 | + message: _(allowLabel, TAG), |
| 363 | + options, |
| 364 | + checks, |
| 365 | + }); |
| 366 | + |
344 | 367 | debug(`Prompt returned`, ret, sender); // DEV_ONLY |
| 368 | + |
345 | 369 | if (ret.button !== 0) return; |
346 | | - if (ret.option === OPT_COLLAPSE) { |
347 | | - return {collapse: "all"}; |
| 370 | + |
| 371 | + const choice = options[ret.option]; |
| 372 | + if (choice._collapse) { |
| 373 | + return { collapse: "all" }; |
348 | 374 | } |
349 | | - let key = [siteKey, origin][ret.option || 0]; |
| 375 | + |
| 376 | + const key = choice._key; |
350 | 377 | if (!key) return; |
351 | 378 |
|
352 | | - let {siteMatch, contextMatch, perms} = ns.policy.get(key, contextUrl); |
353 | | - let {capabilities} = perms; |
354 | | - if (!capabilities.has(policyType)) { |
355 | | - let temp = sender.tab.incognito; // we don't want to store in PBM |
356 | | - perms = new Permissions(capabilities, temp); |
357 | | - perms.capabilities.add(policyType); |
358 | | - /* TODO: handle contextual permissions |
359 | | - if (contextUrl) { |
360 | | - let context = Sites.optimalKey(contextUrl); |
361 | | - let contextualSites = new Sites([[context, perms]]); |
362 | | - perms = new Permissions(new Set(capabilities), false, contextualSites); |
| 379 | + const checked = ret.checks.map((i) => checks[i]._val); |
| 380 | + |
| 381 | + let { siteMatch, contextMatch, perms } = ns.policy.get(key, contextUrl); |
| 382 | + |
| 383 | + if (!perms.capabilities.has(policyType)) { |
| 384 | + if (!contextMatch) { |
| 385 | + perms = perms.clone(); |
| 386 | + ns.policy.set(key, perms); |
| 387 | + if (ctxKey && checked.includes("ctx")) { |
| 388 | + perms.contextual.set(ctxKey, perms = perms.clone(/* noContext = */ true)); |
| 389 | + } |
363 | 390 | } |
364 | | - */ |
365 | | - ns.policy.set(key, perms); |
| 391 | + perms.capabilities.add(policyType); |
| 392 | + perms.temp = forcedTemp || checked.includes("temp"); |
| 393 | + |
366 | 394 | await ns.savePolicy(); |
367 | 395 | await RequestGuard.DNRPolicy?.update(); |
368 | 396 | } |
|
0 commit comments