Browse Source

feat: correctly identify permissions when using setPermissionRequestHandler (#26172) (#26353)

(cherry picked from commit 7f9b21daa0fd98f5311d87165b4ab2fe1231ad1d)
John Kleinschmidt 4 years ago
parent
commit
98b6403e3b
3 changed files with 97 additions and 1 deletions
  1. 1 0
      docs/api/session.md
  2. 43 1
      shell/common/gin_converters/content_converter.cc
  3. 53 0
      spec-main/chromium-spec.ts

+ 1 - 0
docs/api/session.md

@@ -349,6 +349,7 @@ win.webContents.session.setCertificateVerifyProc((request, callback) => {
 * `handler` Function | null
   * `webContents` [WebContents](web-contents.md) - WebContents requesting the permission.  Please note that if the request comes from a subframe you should use `requestingUrl` to check the request origin.
   * `permission` String - The type of requested permission.
+    * `clipboard-read` - Request access to read from the clipboard.
     * `media` -  Request access to media devices such as camera, microphone and speakers.
     * `mediaKeySystem` - Request access to DRM protected content.
     * `geolocation` - Request access to user's current location.

+ 43 - 1
shell/common/gin_converters/content_converter.cc

@@ -174,11 +174,41 @@ v8::Local<v8::Value> Converter<content::PermissionType>::ToV8(
     v8::Isolate* isolate,
     const content::PermissionType& val) {
   using PermissionType = electron::WebContentsPermissionHelper::PermissionType;
+  // Based on mappings from content/browser/devtools/protocol/browser_handler.cc
+  // Not all permissions are currently used by Electron but this will future
+  // proof these conversions.
   switch (val) {
+    case content::PermissionType::ACCESSIBILITY_EVENTS:
+      return StringToV8(isolate, "accessibility-events");
+    case content::PermissionType::AR:
+      return StringToV8(isolate, "ar");
+    case content::PermissionType::BACKGROUND_FETCH:
+      return StringToV8(isolate, "background-fetch");
+    case content::PermissionType::BACKGROUND_SYNC:
+      return StringToV8(isolate, "background-sync");
+    case content::PermissionType::CLIPBOARD_READ_WRITE:
+      return StringToV8(isolate, "clipboard-read");
+    case content::PermissionType::CLIPBOARD_SANITIZED_WRITE:
+      return StringToV8(isolate, "clipboard-sanitized-write");
+    case content::PermissionType::FLASH:
+      return StringToV8(isolate, "flash");
+    case content::PermissionType::CAMERA_PAN_TILT_ZOOM:
+    case content::PermissionType::FONT_ACCESS:
+      return StringToV8(isolate, "font-access");
+    case content::PermissionType::IDLE_DETECTION:
+      return StringToV8(isolate, "idle-detection");
     case content::PermissionType::MIDI_SYSEX:
       return StringToV8(isolate, "midiSysex");
+    case content::PermissionType::NFC:
+      return StringToV8(isolate, "nfc");
     case content::PermissionType::NOTIFICATIONS:
       return StringToV8(isolate, "notifications");
+    case content::PermissionType::PAYMENT_HANDLER:
+      return StringToV8(isolate, "payment-handler");
+    case content::PermissionType::PERIODIC_BACKGROUND_SYNC:
+      return StringToV8(isolate, "periodic-background-sync");
+    case content::PermissionType::DURABLE_STORAGE:
+      return StringToV8(isolate, "persistent-storage");
     case content::PermissionType::GEOLOCATION:
       return StringToV8(isolate, "geolocation");
     case content::PermissionType::AUDIO_CAPTURE:
@@ -188,7 +218,19 @@ v8::Local<v8::Value> Converter<content::PermissionType>::ToV8(
       return StringToV8(isolate, "mediaKeySystem");
     case content::PermissionType::MIDI:
       return StringToV8(isolate, "midi");
-    default:
+    case content::PermissionType::WAKE_LOCK_SCREEN:
+      return StringToV8(isolate, "screen-wake-lock");
+    case content::PermissionType::SENSORS:
+      return StringToV8(isolate, "sensors");
+    case content::PermissionType::STORAGE_ACCESS_GRANT:
+      return StringToV8(isolate, "storage-access");
+    case content::PermissionType::VR:
+      return StringToV8(isolate, "vr");
+    case content::PermissionType::WAKE_LOCK_SYSTEM:
+      return StringToV8(isolate, "system-wake-lock");
+    case content::PermissionType::WINDOW_PLACEMENT:
+      return StringToV8(isolate, "window-placement");
+    case content::PermissionType::NUM:
       break;
   }
 

+ 53 - 0
spec-main/chromium-spec.ts

@@ -1463,3 +1463,56 @@ describe('iframe using HTML fullscreen API while window is OS-fullscreened', ()
     expect(width).to.equal(0);
   });
 });
+
+describe('navigator.clipboard', () => {
+  let w: BrowserWindow;
+  before(async () => {
+    w = new BrowserWindow({
+      show: false,
+      webPreferences: {
+        enableBlinkFeatures: 'Serial'
+      }
+    });
+    await w.loadFile(path.join(fixturesPath, 'pages', 'blank.html'));
+  });
+
+  const readClipboard: any = () => {
+    return w.webContents.executeJavaScript(`
+      navigator.clipboard.read().then(clipboard => clipboard.toString()).catch(err => err.message);
+    `, true);
+  };
+
+  after(closeAllWindows);
+  afterEach(() => {
+    session.defaultSession.setPermissionRequestHandler(null);
+  });
+
+  it('returns clipboard contents when a PermissionRequestHandler is not defined', async () => {
+    const clipboard = await readClipboard();
+    expect(clipboard).to.not.equal('Read permission denied.');
+  });
+
+  it('returns an error when permission denied', async () => {
+    session.defaultSession.setPermissionRequestHandler((wc, permission, callback) => {
+      if (permission === 'clipboard-read') {
+        callback(false);
+      } else {
+        callback(true);
+      }
+    });
+    const clipboard = await readClipboard();
+    expect(clipboard).to.equal('Read permission denied.');
+  });
+
+  it('returns clipboard contents when permission is granted', async () => {
+    session.defaultSession.setPermissionRequestHandler((wc, permission, callback) => {
+      if (permission === 'clipboard-read') {
+        callback(true);
+      } else {
+        callback(false);
+      }
+    });
+    const clipboard = await readClipboard();
+    expect(clipboard).to.not.equal('Read permission denied.');
+  });
+});