Repository: plotly/dash-html-components (language: python)

Issue:
missing some attributes for `Iframe`?
- frameborder
- scrolling
missing some attributes for `Iframe`?
- frameborder
- scrolling


Discussion / hints:
Also missing "allow" attribute

(https://community.plot.ly/t/using-keywords-in-dash-iframe/13485)
Missing "allowfullscreen" attribute,too.
autoplay (allow) and loop attribute would be nice.
Until these are available, one solution would be to use 
```
    dash_dangerously_set_inner_html.DangerouslySetInnerHTML('''
        <iframe ...
    '''),
```

as per https://github.com/plotly/dash-dangerously-set-inner-html

This is still a good issue and one worth fixing.
Are there any updates on supporting features like the `allowFullScreen` for embedded youtube videos?
This hasn't bubbled up to the top of the list for anyone at Plotly yet, but we'd be happy to review a PR!
Also missing "allow" attribute

(https://community.plot.ly/t/using-keywords-in-dash-iframe/13485)
Missing "allowfullscreen" attribute,too.
autoplay (allow) and loop attribute would be nice.
Until these are available, one solution would be to use 
```
    dash_dangerously_set_inner_html.DangerouslySetInnerHTML('''
        <iframe ...
    '''),
```

as per https://github.com/plotly/dash-dangerously-set-inner-html

This is still a good issue and one worth fixing.
Are there any updates on supporting features like the `allowFullScreen` for embedded youtube videos?
This hasn't bubbled up to the top of the list for anyone at Plotly yet, but we'd be happy to review a PR!

Fix patch:
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 9a250adc..002ee1cf 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -4,6 +4,8 @@ This project adheres to [Semantic Versioning](http://semver.org/).
 
 ## UNRELEASED
 ### Fixed
+- [#179](https://github.com/plotly/dash-html-components/pull/178) - Fixes [#77](https://github.com/plotly/dash-html-components/issues/77) Added `allow` and `referrerPolicy` properties to `html.Iframe`
+
 - [#178](https://github.com/plotly/dash-html-components/pull/178) - Fix [#161](https://github.com/plotly/dash-html-components/issues/161) <object> `data` property, and fix [#129](https://github.com/plotly/dash-html-components/issues/129) obsolete, deprecated, and discouraged elements. No elements were removed, but comments were added to the documentation about these elements detailing their limitations.
 
 ## [1.1.2] - 2021-01-19
diff --git a/scripts/extract-attributes.js b/scripts/extract-attributes.js
index 997a34b8..6e43864d 100644
--- a/scripts/extract-attributes.js
+++ b/scripts/extract-attributes.js
@@ -12,7 +12,7 @@ const htmlPath = './data/attributes.html';
 // From https://facebook.github.io/react/docs/tags-and-attributes.html#supported-attributes
 // less the special `className` and `htmlFor` props,
 // and `httpEquiv` + `acceptCharset` which are already correctly camelCased.
-const supportedAttributes = ['accept', 'accessKey', 'action',
+const supportedAttributes = ['accept', 'accessKey', 'action', 'allow',
 'allowFullScreen', 'allowTransparency', 'alt', 'async', 'autoComplete',
 'autoFocus', 'autoPlay', 'capture', 'cellPadding', 'cellSpacing', 'challenge',
 'charSet', 'checked', 'cite', 'classID', 'colSpan', 'cols', 'content',
@@ -25,8 +25,8 @@ const supportedAttributes = ['accept', 'accessKey', 'action',
 'manifest', 'marginHeight', 'marginWidth', 'max', 'maxLength', 'media',
 'mediaGroup', 'method', 'min', 'minLength', 'multiple', 'muted', 'name',
 'noValidate', 'nonce', 'open', 'optimum', 'pattern', 'placeholder', 'poster',
-'preload', 'profile', 'radioGroup', 'readOnly', 'rel', 'required', 'reversed',
-'role', 'rowSpan', 'rows', 'sandbox', 'scope', 'scoped', 'scrolling',
+'preload', 'profile', 'radioGroup', 'readOnly', 'referrerPolicy', 'rel', 'required', 
+'reversed', 'role', 'rowSpan', 'rows', 'sandbox', 'scope', 'scoped', 'scrolling',
 'seamless', 'selected', 'shape', 'size', 'sizes', 'span', 'spellCheck', 'src',
 'srcDoc', 'srcLang', 'srcSet', 'start', 'step', 'style', 'summary', 'tabIndex',
 'target', 'title', 'type', 'useMap', 'value', 'width', 'wmode', 'wrap'];


Test patch:
diff --git a/tests/test_integration.py b/tests/test_integration.py
index 313ad503..f4043abb 100644
--- a/tests/test_integration.py
+++ b/tests/test_integration.py
@@ -7,93 +7,102 @@
 
 
 def test_click_simple(dash_duo):
-    call_count = Value('i', 0)
+    call_count = Value("i", 0)
 
     app = dash.Dash(__name__)
-    app.layout = html.Div([
-        html.Div(id='container'),
-        html.Button('Click', id='button', n_clicks=0)
-    ])
-
-    @app.callback(Output('container', 'children'), Input('button', 'n_clicks'))
+    app.layout = html.Div(
+        [
+            html.Div(id="container"),
+            html.Button("Click", id="button", n_clicks=0),
+            html.Iframe(id="video", allow="fullscreen", referrerPolicy="origin"),
+        ]
+    )
+
+    @app.callback(Output("container", "children"), Input("button", "n_clicks"))
     def update_output(n_clicks):
         call_count.value += 1
-        return 'clicked {} times'.format(n_clicks)
+        return "clicked {} times".format(n_clicks)
 
     dash_duo.start_server(app)
 
-    dash_duo.find_element('#container')
+    dash_duo.find_element("#container")
 
-    dash_duo.wait_for_text_to_equal(
-        '#container', 'clicked 0 times')
+    dash_duo.wait_for_text_to_equal("#container", "clicked 0 times")
     assert call_count.value == 1
-    dash_duo.percy_snapshot('button initialization')
+    dash_duo.percy_snapshot("button initialization")
 
-    dash_duo.find_element('#button').click()
+    dash_duo.find_element("#button").click()
 
-    dash_duo.wait_for_text_to_equal(
-        '#container', 'clicked 1 times')
+    dash_duo.wait_for_text_to_equal("#container", "clicked 1 times")
     assert call_count.value == 2
-    dash_duo.percy_snapshot('button click')
+    dash_duo.percy_snapshot("button click")
 
     assert not dash_duo.get_logs()
 
+    assert dash_duo.find_element("#video").get_attribute("allow") == "fullscreen"
+    assert dash_duo.find_element("#video").get_attribute("referrerpolicy") == "origin"
+
 
 def test_click_prev(dash_duo):
-    call_count = Value('i', 0)
-    timestamp_1 = Value('d', -5)
-    timestamp_2 = Value('d', -5)
+    call_count = Value("i", 0)
+    timestamp_1 = Value("d", -5)
+    timestamp_2 = Value("d", -5)
 
     app = dash.Dash(__name__)
-    app.layout = html.Div([
-        html.Div(id='container'),
-        html.Button('Click', id='button-1', n_clicks=0, n_clicks_timestamp=-1),
-        html.Button('Click', id='button-2', n_clicks=0, n_clicks_timestamp=-1)
-    ])
+    app.layout = html.Div(
+        [
+            html.Div(id="container"),
+            html.Button("Click", id="button-1", n_clicks=0, n_clicks_timestamp=-1),
+            html.Button("Click", id="button-2", n_clicks=0, n_clicks_timestamp=-1),
+        ]
+    )
 
     @app.callback(
-        Output('container', 'children'),
-        [Input('button-1', 'n_clicks'),
-         Input('button-1', 'n_clicks_timestamp'),
-         Input('button-2', 'n_clicks'),
-         Input('button-2', 'n_clicks_timestamp')])
+        Output("container", "children"),
+        [
+            Input("button-1", "n_clicks"),
+            Input("button-1", "n_clicks_timestamp"),
+            Input("button-2", "n_clicks"),
+            Input("button-2", "n_clicks_timestamp"),
+        ],
+    )
     def update_output(*args):
         print(args)
         call_count.value += 1
         timestamp_1.value = args[1]
         timestamp_2.value = args[3]
-        return '{}, {}'.format(args[0], args[2])
+        return "{}, {}".format(args[0], args[2])
 
     dash_duo.start_server(app)
 
-    dash_duo.wait_for_text_to_equal('#container', '0, 0')
+    dash_duo.wait_for_text_to_equal("#container", "0, 0")
     assert timestamp_1.value == -1
     assert timestamp_2.value == -1
     assert call_count.value == 1
-    dash_duo.percy_snapshot('button initialization 1')
+    dash_duo.percy_snapshot("button initialization 1")
 
-    dash_duo.find_element('#button-1').click()
-    dash_duo.wait_for_text_to_equal('#container', '1, 0')
+    dash_duo.find_element("#button-1").click()
+    dash_duo.wait_for_text_to_equal("#container", "1, 0")
     assert timestamp_1.value > ((time.time() - (24 * 60 * 60)) * 1000)
     assert timestamp_2.value == -1
     assert call_count.value == 2
-    dash_duo.percy_snapshot('button-1 click')
+    dash_duo.percy_snapshot("button-1 click")
     prev_timestamp_1 = timestamp_1.value
 
-    dash_duo.find_element('#button-2').click()
-    dash_duo.wait_for_text_to_equal('#container', '1, 1')
+    dash_duo.find_element("#button-2").click()
+    dash_duo.wait_for_text_to_equal("#container", "1, 1")
     assert timestamp_1.value == prev_timestamp_1
     assert timestamp_2.value > ((time.time() - 24 * 60 * 60) * 1000)
     assert call_count.value == 3
-    dash_duo.percy_snapshot('button-2 click')
+    dash_duo.percy_snapshot("button-2 click")
     prev_timestamp_2 = timestamp_2.value
 
-    dash_duo.find_element('#button-2').click()
-    dash_duo.wait_for_text_to_equal('#container', '1, 2')
+    dash_duo.find_element("#button-2").click()
+    dash_duo.wait_for_text_to_equal("#container", "1, 2")
     assert timestamp_1.value == prev_timestamp_1
     assert timestamp_2.value > prev_timestamp_2
     assert timestamp_2.value > timestamp_1.value
     assert call_count.value == 4
-    dash_duo.percy_snapshot('button-2 click again')
+    dash_duo.percy_snapshot("button-2 click again")
 
     assert not dash_duo.get_logs()