From 7212121cad97028b007e974956dc951ce89d683c Mon Sep 17 00:00:00 2001 From: mayakoneval Date: Thu, 15 Jun 2023 15:20:01 -0700 Subject: [PATCH] Add opt out option `allowDynamicStyling` for CSP enforcers (#261) * add readme * accept allowDynamicStyling * changeset * Update packages/explorer/src/EmbeddedExplorer.ts Co-authored-by: Trevor Scheer * Update packages/sandbox/src/EmbeddedSandbox.ts Co-authored-by: Trevor Scheer --------- Co-authored-by: Trevor Scheer --- .changeset/quick-points-drop.md | 6 ++++++ packages/explorer/README.md | 10 ++++++++++ packages/explorer/src/EmbeddedExplorer.ts | 20 +++++++++++++++----- packages/sandbox/README.md | 8 ++++++++ packages/sandbox/src/EmbeddedSandbox.ts | 18 ++++++++++++++---- 5 files changed, 53 insertions(+), 9 deletions(-) create mode 100644 .changeset/quick-points-drop.md diff --git a/.changeset/quick-points-drop.md b/.changeset/quick-points-drop.md new file mode 100644 index 00000000..baac4fcf --- /dev/null +++ b/.changeset/quick-points-drop.md @@ -0,0 +1,6 @@ +--- +'@apollo/explorer': minor +'@apollo/sandbox': minor +--- + +Allow opting out of adding dynamic styles to the iframe rendered by Embedded Explorer / Sandbox diff --git a/packages/explorer/README.md b/packages/explorer/README.md index 60f60ba4..a415e18f 100644 --- a/packages/explorer/README.md +++ b/packages/explorer/README.md @@ -74,6 +74,16 @@ me { } +... +// style the iframe for your site + +
``` ### Examples from the raw cdn hosted umd file diff --git a/packages/explorer/src/EmbeddedExplorer.ts b/packages/explorer/src/EmbeddedExplorer.ts index b501f5b9..c88f62da 100644 --- a/packages/explorer/src/EmbeddedExplorer.ts +++ b/packages/explorer/src/EmbeddedExplorer.ts @@ -72,6 +72,14 @@ export interface BaseEmbeddableExplorerOptions { accountId: string; inviteToken: string; }; + + /** + * optional. defaults to true. + * If false, the `width: 100%` and `height: 100%` are not applied to the iframe dynamically. + * You might pass false here if you enforce a Content Security Policy that disallows dynamic + * style injection. + */ + allowDynamicStyles?: boolean; } interface EmbeddableExplorerOptionsWithSchema @@ -153,11 +161,13 @@ export class EmbeddedExplorer { iframeElement.src = this.embeddedExplorerURL; iframeElement.id = IFRAME_DOM_ID(this.uniqueEmbedInstanceId); - iframeElement.setAttribute( - 'style', - 'height: 100%; width: 100%; border: none;' - ); - + // default to `true` (`true` and `undefined` both ok) + if (this.options.allowDynamicStyles !== false) { + iframeElement.setAttribute( + 'style', + 'height: 100%; width: 100%; border: none;' + ); + } element?.appendChild(iframeElement); // inject the Apollo favicon if there is not one on this page diff --git a/packages/sandbox/README.md b/packages/sandbox/README.md index 85239a49..c39a830c 100644 --- a/packages/sandbox/README.md +++ b/packages/sandbox/README.md @@ -43,6 +43,14 @@ function App() { } ... +// style the iframe for your site +
``` diff --git a/packages/sandbox/src/EmbeddedSandbox.ts b/packages/sandbox/src/EmbeddedSandbox.ts index 24e93b25..7d98990b 100644 --- a/packages/sandbox/src/EmbeddedSandbox.ts +++ b/packages/sandbox/src/EmbeddedSandbox.ts @@ -72,6 +72,13 @@ export interface EmbeddableSandboxOptions { * If false, the endpoint box at the top of sandbox will be `initialEndpoint` permanently */ endpointIsEditable?: boolean; + /** + * optional. defaults to true. + * If false, the `width: 100%` and `height: 100%` are not applied to the iframe dynamically. + * You might pass false here if you enforce a Content Security Policy that disallows dynamic + * style injection. + */ + allowDynamicStyles?: boolean; } type InternalEmbeddableSandboxOptions = EmbeddableSandboxOptions & { @@ -180,10 +187,13 @@ export class EmbeddedSandbox { )}?${queryString}`; iframeElement.id = IFRAME_DOM_ID(this.uniqueEmbedInstanceId); - iframeElement.setAttribute( - 'style', - 'height: 100%; width: 100%; border: none;' - ); + // default to `true` (`true` and `undefined` both ok) + if (this.options.allowDynamicStyles !== false) { + iframeElement.setAttribute( + 'style', + 'height: 100%; width: 100%; border: none;' + ); + } element?.appendChild(iframeElement);