Repository: holoviz/panel

Issue:
Plotly App: Invalid property path 'mapbox._derived' for layout
I'm on the current master branch of Panel. Current released version is 0.12.1. Plotly is v5.3.1

When I maximize the panel I get 

```bash
 File "c:\repos\private\panel_docker\panel\panel\pane\plotly.py", line 154, in _update_figure_layout
    self._figure.plotly_relayout(self.relayout_data)
  File "c:\repos\private\panel_docker\panel\.venv\lib\site-packages\plotly\basedatatypes.patatypes.py", line 2601, in plotly_relayout
    relayout_changes = self._perform_plotly_relayout(relayout_data)
  File "c:\repos\private\panel_docker\panel\.venv\lib\site-packages\plotly\basedatatypes.patatypes.py", line 2637, in _perform_plotly_relayout
    raise ValueError(
ValueError:
Invalid property path 'mapbox._derived' for layout
```

https://user-images.githubusercontent.com/42288570/132114730-652e93b5-92f3-4eac-bc27-0c2c094e470f.mp4

```python
import plotly.express as px

import panel as pn

pn.sizing_mode="stretch_width"


def get_plotly_carshare_data():
    return px.data.carshare()


def plotly_carshare_plot(carshare):
    fig = px.scatter_mapbox(
        carshare,
        lat="centroid_lat",
        lon="centroid_lon",
        color="peak_hour",
        size="car_hours",
        color_continuous_scale=px.colors.cyclical.Phase,
        size_max=15,
        zoom=10,
        mapbox_style="carto-positron",
    )
    fig.layout.autosize = True
    return fig


data = get_plotly_carshare_data()
component = plotly_carshare_plot(data)
carshare_panel = pn.pane.Plotly(
    component,
    config={"responsive": True},
    background="yellow",
    sizing_mode="stretch_both",
)

ACCENT_BASE_COLOR = "#DAA520"

template = pn.template.FastListTemplate(
    site="Awesome Panel",
    title="PR to make Plotly Resize when window resizes",
    logo="https://panel.holoviz.org/_static/logo_stacked.png",
    header_background=ACCENT_BASE_COLOR,
    accent_base_color=ACCENT_BASE_COLOR,
    main=[component],
).servable()
```



Discussion:

Resolving patch:
diff --git a/panel/pane/plotly.py b/panel/pane/plotly.py
--- a/panel/pane/plotly.py
+++ b/panel/pane/plotly.py
@@ -45,7 +45,7 @@ class Plotly(PaneBase):
         * "mouseup": updates are synchronized when mouse button is
           released after panning
         * "continuous": updates are synchronized continually while panning
-        * "throttle": updates are synchronized while panning, at 
+        * "throttle": updates are synchronized while panning, at
           intervals determined by the viewport_update_throttle parameter
         """, objects=["mouseup", "continuous", "throttle"])
 
@@ -150,7 +150,14 @@ def _update_figure_style(self):
     def _update_figure_layout(self):
         if self._figure is None or self.relayout_data is None:
             return
-        self._figure.plotly_relayout(self.relayout_data)
+        relayout_data = self._clean_relayout_data(self.relayout_data)
+        self._figure.plotly_relayout(relayout_data)
+
+    @staticmethod
+    def _clean_relayout_data(relayout_data):
+        return {
+            key: val for key, val in relayout_data.items() if not key.endswith("._derived")
+        }
 
     def _send_update_msg(
         self, restyle_data, relayout_data, trace_indexes=None, source_view_id=None
@@ -210,7 +217,7 @@ def _plotly_json_wrapper(fig):
                 if isdatetime(data[idx][key]):
                     arr = data[idx][key]
                     if isinstance(arr, np.ndarray):
-                        arr = arr.astype(str) 
+                        arr = arr.astype(str)
                     else:
                         arr = [str(v) for v in arr]
                     data[idx][key] = arr


Test patch:
diff --git a/panel/tests/pane/test_plotly.py b/panel/tests/pane/test_plotly.py
--- a/panel/tests/pane/test_plotly.py
+++ b/panel/tests/pane/test_plotly.py
@@ -165,7 +165,7 @@ def test_plotly_pane_numpy_to_cds_traces(document, comm):
 @plotly_available
 def test_plotly_autosize(document, comm):
     trace = go.Scatter(x=[0, 1], y=[2, 3])
-    
+
     pane = Plotly(dict(data=[trace], layout={'autosize': True}))
 
     model = pane.get_root(document, comm=comm)
@@ -187,7 +187,7 @@ def test_plotly_autosize(document, comm):
 @plotly_available
 def test_plotly_tabs(document, comm):
     trace = go.Scatter(x=[0, 1], y=[2, 3])
-    
+
     pane1 = Plotly(dict(data=[trace], layout={'autosize': True}))
     pane2 = Plotly(dict(data=[trace], layout={'autosize': True}))
 
@@ -207,7 +207,31 @@ def test_plotly_tabs(document, comm):
     assert not model2.visible
     assert cb2.args['model'] is model2
     assert cb2.code == 'model.visible = (cb_obj.active == 1);'
-    
+
     tabs.insert(0, 'Blah')
     assert cb1.code == 'model.visible = (cb_obj.active == 1);'
     assert cb2.code == 'model.visible = (cb_obj.active == 2);'
+
+@plotly_available
+def test_clean_relayout_data():
+    relayout_data = {
+        "mapbox.center": {"lon": -73.59183434290809, "lat": 45.52341668343991},
+        "mapbox.zoom": 10,
+        "mapbox.bearing": 0,
+        "mapbox.pitch": 0,
+        "mapbox._derived": {
+            "coordinates": [
+                [-73.92279747767401, 45.597934047192865],
+                [-73.26087120814279, 45.597934047192865],
+                [-73.26087120814279, 45.44880048640681],
+                [-73.92279747767401, 45.44880048640681],
+            ]
+        },
+    }
+    result = Plotly._clean_relayout_data(relayout_data)
+    assert result == {
+        "mapbox.center": {"lon": -73.59183434290809, "lat": 45.52341668343991},
+        "mapbox.zoom": 10,
+        "mapbox.bearing": 0,
+        "mapbox.pitch": 0,
+    }
\ No newline at end of file