Skip to content

Commit

Permalink
feat(frontend/hooks): replace 3rd-party BroadcastChannel with native …
Browse files Browse the repository at this point in the history
…Web API equivalence (apache#29584)

Signed-off-by: hainenber <[email protected]>
  • Loading branch information
hainenber committed Jul 17, 2024
1 parent 3ade01f commit ae6e58f
Show file tree
Hide file tree
Showing 4 changed files with 92 additions and 105 deletions.
109 changes: 18 additions & 91 deletions superset-frontend/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 0 additions & 1 deletion superset-frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,6 @@
"babel-plugin-typescript-to-proptypes": "^2.0.0",
"bootstrap": "^3.4.1",
"brace": "^0.11.1",
"broadcast-channel": "^4.10.0",
"chrono-node": "^2.7.5",
"classnames": "^2.2.5",
"core-js": "^3.37.1",
Expand Down
63 changes: 63 additions & 0 deletions superset-frontend/src/hooks/strictBroadcastChannel.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
/**
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*/

// Credit to Eric Wong at https://stackoverflow.com/a/78491331
interface StrictBroadcastChannelEventMap<T> {
message: MessageEvent<T>;
messageerror: MessageEvent<T>;
}

export interface StrictBroadcastChannel<T> extends EventTarget {
readonly name: string;
onmessage: ((this: BroadcastChannel, ev: MessageEvent<T>) => any) | null;
onmessageerror: ((this: BroadcastChannel, ev: MessageEvent<T>) => any) | null;
close(): void;
postMessage(message: T): void;
addEventListener<K extends keyof StrictBroadcastChannelEventMap<T>>(
type: K,
listener: (
this: BroadcastChannel,
ev: StrictBroadcastChannelEventMap<T>[K],
) => any,
options?: boolean | AddEventListenerOptions,
): void;
addEventListener(
type: string,
listener: EventListenerOrEventListenerObject,
options?: boolean | AddEventListenerOptions,
): void;
removeEventListener<K extends keyof StrictBroadcastChannelEventMap<T>>(
type: K,
listener: (
this: BroadcastChannel,
ev: StrictBroadcastChannelEventMap<T>[K],
) => any,
options?: boolean | EventListenerOptions,
): void;
removeEventListener(
type: string,
listener: EventListenerOrEventListenerObject,
options?: boolean | EventListenerOptions,
): void;
}

export interface TabIdChannelMessage {
type: 'REQUESTING_TAB_ID' | 'TAB_ID_DENIED';
tabId: string;
}
24 changes: 11 additions & 13 deletions superset-frontend/src/hooks/useTabId.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,17 +18,15 @@
*/
import { useEffect, useState } from 'react';
import { nanoid } from 'nanoid';
import { BroadcastChannel } from 'broadcast-channel';
import {
StrictBroadcastChannel,
TabIdChannelMessage,
} from './strictBroadcastChannel';

interface TabIdChannelMessage {
type: 'REQUESTING_TAB_ID' | 'TAB_ID_DENIED';
tabId: string;
}
const TAB_ID_CHANNEL_NAME = 'tab_id_channel';

// TODO: We are using broadcast-channel to support Safari.
// The native BroadcastChannel API will be supported in Safari version 15.4.
// After that, we should remove this dependency and use the native API.
const channel = new BroadcastChannel<TabIdChannelMessage>('tab_id_channel');
const channel: StrictBroadcastChannel<TabIdChannelMessage> =
new BroadcastChannel(TAB_ID_CHANNEL_NAME);

export function useTabId() {
const [tabId, setTabId] = useState<string>();
Expand Down Expand Up @@ -83,14 +81,14 @@ export function useTabId() {
}

channel.onmessage = messageEvent => {
if (messageEvent.tabId === tabId) {
if (messageEvent.type === 'REQUESTING_TAB_ID') {
if (messageEvent.data.tabId === tabId) {
if (messageEvent.data.type === 'REQUESTING_TAB_ID') {
const message: TabIdChannelMessage = {
type: 'TAB_ID_DENIED',
tabId: messageEvent.tabId,
tabId: messageEvent.data.tabId,
};
channel.postMessage(message);
} else if (messageEvent.type === 'TAB_ID_DENIED') {
} else if (messageEvent.data.type === 'TAB_ID_DENIED') {
updateTabId();
}
}
Expand Down

0 comments on commit ae6e58f

Please sign in to comment.