diff --git a/package-lock.json b/package-lock.json index e9b195a..87b19e0 100644 --- a/package-lock.json +++ b/package-lock.json @@ -9,8 +9,8 @@ "version": "0.0.0", "license": "Apache-2.0", "dependencies": { - "react": "^17.0.1", - "react-dom": "^17.0.1" + "react": "^18.0.0", + "react-dom": "^18.0.0" }, "devDependencies": { "bower": "^1.8.12", @@ -2970,6 +2970,7 @@ "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=", + "dev": true, "engines": { "node": ">=0.10.0" } @@ -3361,9 +3362,9 @@ "dev": true }, "node_modules/purescript": { - "version": "0.15.2", - "resolved": "https://registry.npmjs.org/purescript/-/purescript-0.15.2.tgz", - "integrity": "sha512-7pn9nMnLOA88Yl2khlF0Y3xOTRjFxPWMnY8OKVDakZciM2udBWgwtxFLXb+DMUequ88vT1+KeY1Z71Tq6g8Qfg==", + "version": "0.15.4", + "resolved": "https://registry.npmjs.org/purescript/-/purescript-0.15.4.tgz", + "integrity": "sha512-6Ge3IMcIxKkOUXg91cBgvjbqu5SxdfwbvWi1P4g+E2maxfvDv+roWAmLyOteTsxQE4SEa/wWoCZvnZ/AEjvrMw==", "dev": true, "hasInstallScript": true, "dependencies": { @@ -3488,28 +3489,26 @@ } }, "node_modules/react": { - "version": "17.0.1", - "resolved": "https://registry.npmjs.org/react/-/react-17.0.1.tgz", - "integrity": "sha512-lG9c9UuMHdcAexXtigOZLX8exLWkW0Ku29qPRU8uhF2R9BN96dLCt0psvzPLlHc5OWkgymP3qwTRgbnw5BKx3w==", + "version": "18.2.0", + "resolved": "https://registry.npmjs.org/react/-/react-18.2.0.tgz", + "integrity": "sha512-/3IjMdb2L9QbBdWiW5e3P2/npwMBaU9mHCSCUzNln0ZCYbcfTsGbTJrU/kGemdH2IWmB2ioZ+zkxtmq6g09fGQ==", "dependencies": { - "loose-envify": "^1.1.0", - "object-assign": "^4.1.1" + "loose-envify": "^1.1.0" }, "engines": { "node": ">=0.10.0" } }, "node_modules/react-dom": { - "version": "17.0.1", - "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-17.0.1.tgz", - "integrity": "sha512-6eV150oJZ9U2t9svnsspTMrWNyHc6chX0KzDeAOXftRa8bNeOKTTfCJ7KorIwenkHd2xqVTBTCZd79yk/lx/Ug==", + "version": "18.2.0", + "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-18.2.0.tgz", + "integrity": "sha512-6IMTriUmvsjHUjNtEDudZfuDQUoWXVxKHhlEGSk81n4YFS+r/Kl99wXiwlVXtPBtJenozv2P+hxDsw9eA7Xo6g==", "dependencies": { "loose-envify": "^1.1.0", - "object-assign": "^4.1.1", - "scheduler": "^0.20.1" + "scheduler": "^0.23.0" }, "peerDependencies": { - "react": "17.0.1" + "react": "^18.2.0" } }, "node_modules/read": { @@ -3735,12 +3734,11 @@ } }, "node_modules/scheduler": { - "version": "0.20.1", - "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.20.1.tgz", - "integrity": "sha512-LKTe+2xNJBNxu/QhHvDR14wUXHRQbVY5ZOYpOGWRzhydZUqrLb2JBvLPY7cAqFmqrWuDED0Mjk7013SZiOz6Bw==", + "version": "0.23.0", + "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.23.0.tgz", + "integrity": "sha512-CtuThmgHNg7zIZWAXi3AsyIzA3n4xx7aNyjwC2VJldO2LMVDhFK+63xGqq6CsJH4rTAt6/M+N4GhZiDYPx9eUw==", "dependencies": { - "loose-envify": "^1.1.0", - "object-assign": "^4.1.1" + "loose-envify": "^1.1.0" } }, "node_modules/semver": { @@ -7058,7 +7056,8 @@ "object-assign": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" + "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=", + "dev": true }, "object-inspect": { "version": "1.9.0", @@ -7384,9 +7383,9 @@ "dev": true }, "purescript": { - "version": "0.15.2", - "resolved": "https://registry.npmjs.org/purescript/-/purescript-0.15.2.tgz", - "integrity": "sha512-7pn9nMnLOA88Yl2khlF0Y3xOTRjFxPWMnY8OKVDakZciM2udBWgwtxFLXb+DMUequ88vT1+KeY1Z71Tq6g8Qfg==", + "version": "0.15.4", + "resolved": "https://registry.npmjs.org/purescript/-/purescript-0.15.4.tgz", + "integrity": "sha512-6Ge3IMcIxKkOUXg91cBgvjbqu5SxdfwbvWi1P4g+E2maxfvDv+roWAmLyOteTsxQE4SEa/wWoCZvnZ/AEjvrMw==", "dev": true, "requires": { "purescript-installer": "^0.2.6" @@ -7485,22 +7484,20 @@ } }, "react": { - "version": "17.0.1", - "resolved": "https://registry.npmjs.org/react/-/react-17.0.1.tgz", - "integrity": "sha512-lG9c9UuMHdcAexXtigOZLX8exLWkW0Ku29qPRU8uhF2R9BN96dLCt0psvzPLlHc5OWkgymP3qwTRgbnw5BKx3w==", + "version": "18.2.0", + "resolved": "https://registry.npmjs.org/react/-/react-18.2.0.tgz", + "integrity": "sha512-/3IjMdb2L9QbBdWiW5e3P2/npwMBaU9mHCSCUzNln0ZCYbcfTsGbTJrU/kGemdH2IWmB2ioZ+zkxtmq6g09fGQ==", "requires": { - "loose-envify": "^1.1.0", - "object-assign": "^4.1.1" + "loose-envify": "^1.1.0" } }, "react-dom": { - "version": "17.0.1", - "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-17.0.1.tgz", - "integrity": "sha512-6eV150oJZ9U2t9svnsspTMrWNyHc6chX0KzDeAOXftRa8bNeOKTTfCJ7KorIwenkHd2xqVTBTCZd79yk/lx/Ug==", + "version": "18.2.0", + "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-18.2.0.tgz", + "integrity": "sha512-6IMTriUmvsjHUjNtEDudZfuDQUoWXVxKHhlEGSk81n4YFS+r/Kl99wXiwlVXtPBtJenozv2P+hxDsw9eA7Xo6g==", "requires": { "loose-envify": "^1.1.0", - "object-assign": "^4.1.1", - "scheduler": "^0.20.1" + "scheduler": "^0.23.0" } }, "read": { @@ -7688,12 +7685,11 @@ } }, "scheduler": { - "version": "0.20.1", - "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.20.1.tgz", - "integrity": "sha512-LKTe+2xNJBNxu/QhHvDR14wUXHRQbVY5ZOYpOGWRzhydZUqrLb2JBvLPY7cAqFmqrWuDED0Mjk7013SZiOz6Bw==", + "version": "0.23.0", + "resolved": "https://registry.npmjs.org/scheduler/-/scheduler-0.23.0.tgz", + "integrity": "sha512-CtuThmgHNg7zIZWAXi3AsyIzA3n4xx7aNyjwC2VJldO2LMVDhFK+63xGqq6CsJH4rTAt6/M+N4GhZiDYPx9eUw==", "requires": { - "loose-envify": "^1.1.0", - "object-assign": "^4.1.1" + "loose-envify": "^1.1.0" } }, "semver": { diff --git a/package.json b/package.json index 879061e..30f1064 100644 --- a/package.json +++ b/package.json @@ -14,8 +14,8 @@ }, "homepage": "https://github.com/lumihq/purescript-react-basic-dom#readme", "dependencies": { - "react": "^17.0.1", - "react-dom": "^17.0.1" + "react": "^18.0.0", + "react-dom": "^18.0.0" }, "devDependencies": { "bower": "^1.8.12", diff --git a/src/React/Basic/DOM.purs b/src/React/Basic/DOM.purs index a5209cc..fc20ffb 100644 --- a/src/React/Basic/DOM.purs +++ b/src/React/Basic/DOM.purs @@ -17,7 +17,9 @@ module React.Basic.DOM ) where import Prelude + import Effect (Effect) +import Prim.TypeError (class Warn, Text) import React.Basic (JSX) import React.Basic.DOM.Generated (Props_a, Props_abbr, Props_address, Props_area, Props_article, Props_aside, Props_audio, Props_b, Props_base, Props_bdi, Props_bdo, Props_blockquote, Props_body, Props_br, Props_button, Props_canvas, Props_caption, Props_cite, Props_code, Props_col, Props_colgroup, Props_data, Props_datalist, Props_dd, Props_del, Props_details, Props_dfn, Props_dialog, Props_div, Props_dl, Props_dt, Props_em, Props_embed, Props_fieldset, Props_figcaption, Props_figure, Props_footer, Props_form, Props_h1, Props_h2, Props_h3, Props_h4, Props_h5, Props_h6, Props_head, Props_header, Props_hgroup, Props_hr, Props_html, Props_i, Props_iframe, Props_img, Props_input, Props_ins, Props_kbd, Props_keygen, Props_label, Props_legend, Props_li, Props_link, Props_main, Props_map, Props_mark, Props_math, Props_menu, Props_menuitem, Props_meta, Props_meter, Props_nav, Props_noscript, Props_object, Props_ol, Props_optgroup, Props_option, Props_output, Props_p, Props_param, Props_picture, Props_pre, Props_progress, Props_q, Props_rb, Props_rp, Props_rt, Props_rtc, Props_ruby, Props_s, Props_samp, Props_script, Props_section, Props_select, Props_slot, Props_small, Props_source, Props_span, Props_strong, Props_style, Props_sub, Props_summary, Props_sup, Props_table, Props_tbody, Props_td, Props_template, Props_textarea, Props_tfoot, Props_th, Props_thead, Props_time, Props_title, Props_tr, Props_track, Props_u, Props_ul, Props_var, Props_video, Props_wbr, a, a', a_, abbr, abbr', abbr_, address, address', address_, area, area', article, article', article_, aside, aside', aside_, audio, audio', audio_, b, b', b_, base, base', bdi, bdi', bdi_, bdo, bdo', bdo_, blockquote, blockquote', blockquote_, body, body', body_, br, br', button, button', button_, canvas, canvas', canvas_, caption, caption', caption_, cite, cite', cite_, code, code', code_, col, col', colgroup, colgroup', colgroup_, data', data'', data_, datalist, datalist', datalist_, dd, dd', dd_, del, del', del_, details, details', details_, dfn, dfn', dfn_, dialog, dialog', dialog_, div, div', div_, dl, dl', dl_, dt, dt', dt_, em, em', em_, embed, embed', fieldset, fieldset', fieldset_, figcaption, figcaption', figcaption_, figure, figure', figure_, footer, footer', footer_, form, form', form_, h1, h1', h1_, h2, h2', h2_, h3, h3', h3_, h4, h4', h4_, h5, h5', h5_, h6, h6', h6_, head, head', head_, header, header', header_, hgroup, hgroup', hgroup_, hr, hr', html, html', html_, i, i', i_, iframe, iframe', iframe_, img, img', input, input', ins, ins', ins_, kbd, kbd', kbd_, keygen, keygen', keygen_, label, label', label_, legend, legend', legend_, li, li', li_, link, link', main, main', main_, map, map', map_, mark, mark', mark_, math, math', math_, menu, menu', menu_, menuitem, menuitem', menuitem_, meta, meta', meter, meter', meter_, nav, nav', nav_, noscript, noscript', noscript_, object, object', object_, ol, ol', ol_, optgroup, optgroup', optgroup_, option, option', option_, output, output', output_, p, p', p_, param, param', picture, picture', picture_, pre, pre', pre_, progress, progress', progress_, q, q', q_, rb, rb', rb_, rp, rp', rp_, rt, rt', rt_, rtc, rtc', rtc_, ruby, ruby', ruby_, s, s', s_, samp, samp', samp_, script, script', script_, section, section', section_, select, select', select_, slot, slot', slot_, small, small', small_, source, source', span, span', span_, strong, strong', strong_, style, style', style_, sub, sub', sub_, summary, summary', summary_, sup, sup', sup_, table, table', table_, tbody, tbody', tbody_, td, td', td_, template, template', template_, textarea, textarea', textarea_, tfoot, tfoot', tfoot_, th, th', th_, thead, thead', thead_, time, time', time_, title, title', title_, tr, tr', tr_, track, track', u, u', u_, ul, ul', ul_, var, var', var_, video, video', video_, wbr, wbr') as Generated import React.Basic.DOM.Internal (CSS, css, mergeStyles, unsafeCreateDOMComponent) as Internal @@ -28,7 +30,11 @@ import Web.DOM (Element) -- | a DOM element. -- | -- | __*Note:* Relies on `ReactDOM.render`__ -render :: JSX -> Element -> Effect Unit +render + :: Warn (Text "`render` has been replaced with `createRoot` in React 18") + => JSX + -> Element + -> Effect Unit render jsx node = render' jsx node (pure unit) -- | Render or update/re-render a component tree into @@ -36,7 +42,13 @@ render jsx node = render' jsx node (pure unit) -- | DOM update is complete. -- | -- | __*Note:* Relies on `ReactDOM.render`__ -render' :: JSX -> Element -> Effect Unit -> Effect Unit +-- | __*Note:* `render` has been replaced with `createRoot` in React 18 +render' + :: Warn (Text "`render` has been replaced with `createRoot` in React 18") + => JSX + -> Element + -> Effect Unit + -> Effect Unit render' = renderThen foreign import renderThen :: JSX -> Element -> Effect Unit -> Effect Unit @@ -48,7 +60,11 @@ foreign import renderThen :: JSX -> Element -> Effect Unit -> Effect Unit -- | __*Note:* Relies on `ReactDOM.hydrate`, generally only -- | used with `ReactDOMServer.renderToNodeStream` or -- | `ReactDOMServer.renderToString`__ -hydrate :: JSX -> Element -> Effect Unit +hydrate + :: Warn (Text "`hydrate` has been replaced with `hydrateRoot` in React 18") + => JSX + -> Element + -> Effect Unit hydrate jsx node = hydrate' jsx node (pure unit) -- | Render or update/re-render a component tree into @@ -59,7 +75,12 @@ hydrate jsx node = hydrate' jsx node (pure unit) -- | __*Note:* Relies on `ReactDOM.hydrate`, generally only -- | used with `ReactDOMServer.renderToNodeStream` or -- | `ReactDOMServer.renderToString`__ -hydrate' :: JSX -> Element -> Effect Unit -> Effect Unit +hydrate' + :: Warn (Text "`hydrate` has been replaced with `hydrateRoot` in React 18") + => JSX + -> Element + -> Effect Unit + -> Effect Unit hydrate' = hydrateThen foreign import hydrateThen :: JSX -> Element -> Effect Unit -> Effect Unit @@ -69,6 +90,7 @@ foreign import hydrateThen :: JSX -> Element -> Effect Unit -> Effect Unit -- | if an app existed and was unmounted successfully. -- | -- | __*Note:* Relies on `ReactDOM.unmountComponentAtNode`__ +-- | __*Note:* `unmount` has been replaced with `Client.unmountRoot` in React 18 foreign import unmount :: Element -> Effect Boolean -- | Divert a render tree into a separate DOM node. The node's @@ -78,4 +100,4 @@ foreign import createPortal :: JSX -> Element -> JSX -- | Create a text node. text :: String -> JSX -text = unsafeCoerce +text = unsafeCoerce \ No newline at end of file diff --git a/src/React/Basic/DOM/Client.js b/src/React/Basic/DOM/Client.js new file mode 100644 index 0000000..6300ddd --- /dev/null +++ b/src/React/Basic/DOM/Client.js @@ -0,0 +1,11 @@ +import ReactDOMClient from "react-dom/client"; + +export const createRoot = (container) => () => + ReactDOMClient.createRoot(container); + +export const hydrateRoot = (container) => (initialChildren) => () => + ReactDOMClient.hydrateRoot(container, initialChildren); + +export const renderRoot = (root) => (children) => () => root.render(children); + +export const unmountRoot = (root) => () => root.unmount(root); diff --git a/src/React/Basic/DOM/Client.purs b/src/React/Basic/DOM/Client.purs new file mode 100644 index 0000000..7858a49 --- /dev/null +++ b/src/React/Basic/DOM/Client.purs @@ -0,0 +1,23 @@ +module React.Basic.DOM.Client where + +import Prelude +import React.Basic (JSX) +import Web.DOM (Element) +import Effect (Effect) + +foreign import data ReactRoot :: Type + +-- | Create a React root for the supplied container and return the root. +-- | The root can be used to render a React element into the DOM with `render.` +-- | Replaces `ReactDOM.render` when the `.render` method is called and enables Concurrent Mode. +foreign import createRoot :: Element -> Effect ReactRoot + +-- | Same as `createRoot`, but is used to hydrate a container whose HTML contents were rendered by ReactDOMServer. +-- | React will attempt to attach event listeners to the existing markup. +foreign import hydrateRoot :: Element -> JSX -> Effect ReactRoot + +-- | Render children in `ReactRoot` +foreign import renderRoot :: ReactRoot -> JSX -> Effect Unit + +-- | Unmount the react root +foreign import unmountRoot :: ReactRoot -> Effect Unit \ No newline at end of file diff --git a/src/React/Basic/DOM/Concurrent.js b/src/React/Basic/DOM/Concurrent.js deleted file mode 100644 index b693a89..0000000 --- a/src/React/Basic/DOM/Concurrent.js +++ /dev/null @@ -1,16 +0,0 @@ -import ReactDOM from "react-dom"; -const createRoot = ReactDOM.createRoot || ReactDOM.unstable_createRoot; -const createBlockingRoot = - ReactDOM.createBlockingRoot || ReactDOM.unstable_createBlockingRoot; - -export function createRoot(element) { - return () => createRoot(element); -} - -export function createBlockingRoot(element) { - return () => createBlockingRoot(element); -} - -export function renderRoot(root) { - return (jsx) => () => root.render(jsx); -} diff --git a/src/React/Basic/DOM/Concurrent.purs b/src/React/Basic/DOM/Concurrent.purs deleted file mode 100644 index 818bc84..0000000 --- a/src/React/Basic/DOM/Concurrent.purs +++ /dev/null @@ -1,16 +0,0 @@ --- Warning: The concurrent-mode API is experimental and not yet intended for --- use in production applications. See the React docs for more info. -module React.Basic.DOM.Concurrent where - -import Prelude -import Effect (Effect) -import React.Basic (JSX) -import Web.DOM (Element) - -foreign import data ReactRoot :: Type - -foreign import createRoot :: Element -> Effect ReactRoot - -foreign import createBlockingRoot :: Element -> Effect ReactRoot - -foreign import renderRoot :: ReactRoot -> JSX -> Effect Unit diff --git a/src/React/Basic/DOM/Server.js b/src/React/Basic/DOM/Server.js index 62b5750..f783adb 100644 --- a/src/React/Basic/DOM/Server.js +++ b/src/React/Basic/DOM/Server.js @@ -1,3 +1 @@ -import ReactDOMServer from "react-dom/server.js"; -export var renderToString = ReactDOMServer.renderToString; -export var renderToStaticMarkup = ReactDOMServer.renderToStaticMarkup; +export { renderToString, renderToStaticMarkup } from "react-dom/server";