react-dnd: Cannot have two HTML5 backends at the same time

Describe the bug I use different react-table draggable in different react-tabs My Index.js contains:

import { HTML5Backend } from 'react-dnd-html5-backend';
import { DndProvider } from 'react-dnd';

ReactDOM.render(
   <DndProvider backend={HTML5Backend}>
      <BrowserRouter basename={baseUrl}>
         <App />
      </BrowserRouter>,
   </DndProvider>,
  rootElement);

each time I navigate into my components insinde <App/> and come back to the component with the react-table inside react-tabs, this following error is triggered:

HTML5BackendImpl.js:423 Uncaught Error: Cannot have two HTML5 backends at the same time.
    at HTML5BackendImpl.setup (HTML5BackendImpl.js:423)
    at DragDropManagerImpl.handleRefCountChange (DragDropManagerImpl.js:21)
    at Object.dispatch (redux.js:222)
    at HandlerRegistryImpl.addTarget (HandlerRegistryImpl.js:101)
    at registerTarget (registration.js:3)
    at registerDropTarget (useRegisteredDropTarget.js:23)
    at commitHookEffectListMount (react-dom.development.js:19731)
    at commitLifeCycles (react-dom.development.js:19787)
    at commitLayoutEffects (react-dom.development.js:22803)
    at HTMLUnknownElement.callCallback (react-dom.development.js:188)

I also try those workaround:

But both doesn’t solve my problem

Expected behavior I would like to change tab without trigger this error, I am unable to use it without having this error.

Desktop (please complete the following information):

  • OS: Win10
  • Browser: Chrome Version 89.0.4389.114 (Build officiel) (64 bits)
  • Version: [“react-dnd”: “^14.0.2”, “react-dnd-html5-backend”: “^14.0.0”]

About this issue

  • Original URL
  • State: open
  • Created 3 years ago
  • Reactions: 4
  • Comments: 15

Most upvoted comments

I found a way that fix the problem but it’s not satisfying:

  • Downgrade react-dnd and react-dnd-html5-backend to the same version used by our version of react-sortable-tree (11.1.3)
  • create a file like dnd-context.js:
    import React, { useRef } from 'react';
    import PropTypes from 'prop-types';
    //import { createDragDropManager } from 'dnd-core';
    import { DndProvider } from 'react-dnd';
    import { HTML5Backend } from 'react-dnd-html5-backend';
    
    //const DNDManager = createDragDropManager(HTML5Backend);
    export const GlobalDndContext = (props) =>
    {
       //const manager = useRef(DNDManager);
       // the following line solve the problem only with key property
       return <DndProvider backend={HTML5Backend} key={1}>{props.children}</DndProvider>
    }
    
    GlobalDndContext.PropTypes = { children: PropTypes.node };
    
    export default GlobalDndContext;
    
  • In index.js that render <App/>:
    ReactDOM.render(
       <GlobalDndContext>
         <BrowserRouter basename={baseUrl}>
           <App />
         </BrowserRouter>
      </GlobalDndContext>,
    rootElement);
    

Help source: MJGang answer, milban answer

if (window.__isReactDndBackendSetUp) { window.__isReactDndBackendSetUp = false }

关联 https://github.com/react-dnd/react-dnd/issues/3257 一般都是嵌套了两个 试试 context={window}

Happens in my project too, when react-dnd is used in multiple forms and more than one of them is rendered at the same time. This footgun makes react-dnd basically unusable 😢

Edit: seems to only happen sometimes. I have no idea what is going on…

const myFirstId = 'first-DnD-Containier';
const mySecondId = 'second-DnD-Containier';

export const DndWrapper = React.memo((props) => {
  const [context, setContext] = useState(null);

  useEffect(() => {
    setContext(document.getElementById(props.id))
  },[props.id])

  return context ? (
      <DndProvider backend={HTML5Backend} options={{ rootElement: context}}>
          {props.children}
      </DndProvider>
  ) : null;
});

export default function App() {
  return (
    <div>
      <div id={myFirstId}>
        <DndWrapper id={myFirstId}>
               <MyOtherComponents /> 
        </DndWrapper>
      </div>
      <div id={mySecondId}>
          <DndWrapper id={mySecondId}>
            <MyOtherComponents />
          </DndWrapper>
      </div>
    </div>
  );
}

i tried like above, but still same error, any way to fix it, it take me along time

@ffan0811 I have absolutely no idea why key={1} solve the problem, and it works too with Math.random() but as I try first with 1 and it were working, I let it.