From 951e360405fdb98d9bee609c125e08c3f09f3ff1 Mon Sep 17 00:00:00 2001 From: Ahmed Bouhuolia Date: Tue, 3 Oct 2023 22:05:57 +0200 Subject: [PATCH] chore(webapp): add missing packages --- package.json | 6 +- packages/webapp/package.json | 17 ++-- .../Accounts/AccountsTypesSelect.tsx | 1 - .../src/components/Accounts/_components.tsx | 1 - .../AdvancedFilter/AdvancedFilterDropdown.tsx | 2 +- packages/webapp/src/components/App.tsx | 1 - .../src/components/Dashboard/SplashScreen.tsx | 1 - .../src/components/DialogsContainer.tsx | 2 - packages/webapp/src/components/Utils/For.tsx | 1 - .../src/containers/Authentication/Login.tsx | 1 - .../PaymentReceiveDetailHeader.tsx | 1 - .../PaymentReceiveDetailTab.tsx | 1 - .../PaymentReceiveGLEntriesPanel.tsx | 1 - .../CashFlowStatementGeneralPanel.tsx | 2 - .../CustomersBalanceSummaryActionsBar.tsx | 1 - ...omersBalanceSummaryGeneralPanelContent.tsx | 1 - .../ItemsCategoryActionsBar.tsx | 1 - .../Preferences/PreferencesPageLoader.tsx | 1 - packages/webapp/src/style/App.scss | 17 +--- packages/webapp/src/style/Base.scss | 3 - packages/webapp/src/style/_base.scss | 3 + packages/webapp/src/style/_functions.scss | 54 +++++++++++++ .../style/{normalize.scss => _normalize.scss} | 0 .../style/{variables.scss => _variables.scss} | 2 +- packages/webapp/src/style/functions.scss | 40 ---------- packages/webapp/src/utils/index.tsx | 7 +- packages/webapp/src/utils/map-key-deep.ts | 79 +++++++++++++++++++ pnpm-lock.yaml | 54 +++++++++---- 28 files changed, 193 insertions(+), 108 deletions(-) delete mode 100644 packages/webapp/src/style/Base.scss create mode 100644 packages/webapp/src/style/_base.scss create mode 100644 packages/webapp/src/style/_functions.scss rename packages/webapp/src/style/{normalize.scss => _normalize.scss} (100%) rename packages/webapp/src/style/{variables.scss => _variables.scss} (99%) delete mode 100644 packages/webapp/src/style/functions.scss create mode 100644 packages/webapp/src/utils/map-key-deep.ts diff --git a/package.json b/package.json index ebdcc185a..3c8555f4c 100644 --- a/package.json +++ b/package.json @@ -2,7 +2,7 @@ "name": "bigcapital-monorepo", "private": true, "scripts": { - "bootstrap": "lerna exec npm install", + "bootstrap": "lerna exec pnpm install", "dev": "lerna run dev", "build": "lerna run build", "dev:webapp": "lerna run dev --scope \"@bigcapital/webapp\"", @@ -13,10 +13,6 @@ "test:e2e": "playwright test", "prepare": "husky install" }, - "workspaces": [ - "packages/*", - "shared/*" - ], "devDependencies": { "@commitlint/cli": "^17.4.2", "@commitlint/config-conventional": "^17.4.2", diff --git a/packages/webapp/package.json b/packages/webapp/package.json index 3dedabd58..b936de867 100644 --- a/packages/webapp/package.json +++ b/packages/webapp/package.json @@ -6,6 +6,7 @@ "@blueprintjs-formik/core": "^0.3.6", "@blueprintjs-formik/datetime": "^0.3.7", "@blueprintjs-formik/select": "^0.3.5", + "@blueprintjs/colors": "4.1.19", "@blueprintjs/core": "^4.20.2", "@blueprintjs/datetime": "^4.4.37", "@blueprintjs/popover2": "^0.11.1", @@ -26,6 +27,7 @@ "@types/ramda": "^0.28.14", "@types/react": "^16.14.28", "@types/react-body-classname": "^1.1.7", + "@types/react-dom": "^16.9.16", "@types/react-redux": "^7.1.24", "@types/react-router-dom": "^5.3.3", "@types/react-transition-group": "^4.4.5", @@ -38,8 +40,8 @@ "axios": "^0.21.2", "basscss": "^8.0.2", "camelcase": "^5.3.1", + "classnames": "^2.3.2", "cross-env": "^7.0.2", - "deep-map-keys": "^2.0.1", "deepdash": "^5.3.9", "dependency-graph": "^0.11.0", "dotenv-webpack": "^8.0.1", @@ -47,16 +49,19 @@ "fast-deep-equal": "^3.1.3", "flat": "^5.0.2", "formik": "^2.2.5", + "history": "4.10.1", "http-proxy-middleware": "^1.0.0", "jest": "24.9.0", "jest-environment-jsdom-fourteen": "1.0.1", "jest-resolve": "24.9.0", "jest-watch-typeahead": "0.4.2", + "js-cookie": "2.2.1", "js-money": "^0.6.3", "lodash": "^4.17.15", "moment": "^2.24.0", "moment-timezone": "^0.5.33", "path-browserify": "^1.0.1", + "prop-types": "15.8.1", "query-string": "^7.1.1", "ramda": "^0.27.1", "react": "^18.2.0", @@ -67,12 +72,14 @@ "react-dom": "^18.2.0", "react-dropzone": "^11.0.1", "react-error-boundary": "^3.0.2", + "react-error-overlay": "^6.0.9", "react-hotkeys-hook": "^3.0.3", "react-intl-universal": "^2.4.7", "react-loadable": "^5.5.0", "react-query": "^3.6.0", "react-query-devtools": "^2.1.1", "react-redux": "^7.2.9", + "react-router": "5.3.4", "react-router-breadcrumbs-hoc": "^3.2.10", "react-router-dom": "^5.3.3", "react-scripts": "5.0.1", @@ -90,7 +97,9 @@ "redux-devtools": "^3.5.0", "redux-persist": "^6.0.0", "redux-thunk": "^2.4.2", + "reselect": "4.1.7", "rtl-detect": "^1.0.3", + "sass": "^1.68.0", "semver": "6.3.0", "style-loader": "0.23.1", "styled-components": "^5.3.1", @@ -105,14 +114,10 @@ "storybook": "start-storybook -p 6006" }, "proxy": "http://localhost:3000/", - "devDependencies": { - "@types/react-dom": "^16.9.16", - "react-error-overlay": "^6.0.9", - "sass": "^1.68.0" - }, "resolutions": { "react-error-overlay": "6.0.9" }, + "browserslist": { "production": [ ">0.2%", diff --git a/packages/webapp/src/components/Accounts/AccountsTypesSelect.tsx b/packages/webapp/src/components/Accounts/AccountsTypesSelect.tsx index 5357ae95b..7295a9c80 100644 --- a/packages/webapp/src/components/Accounts/AccountsTypesSelect.tsx +++ b/packages/webapp/src/components/Accounts/AccountsTypesSelect.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import { FSelect } from '@/components/Forms'; export function AccountsTypesSelect({ ...props }) { diff --git a/packages/webapp/src/components/Accounts/_components.tsx b/packages/webapp/src/components/Accounts/_components.tsx index 85bbd50a6..c791bf466 100644 --- a/packages/webapp/src/components/Accounts/_components.tsx +++ b/packages/webapp/src/components/Accounts/_components.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; // Filters accounts items. export const accountPredicate = (query, account, _index, exactMatch) => { diff --git a/packages/webapp/src/components/AdvancedFilter/AdvancedFilterDropdown.tsx b/packages/webapp/src/components/AdvancedFilter/AdvancedFilterDropdown.tsx index 3f27c928a..c7b2fa2d0 100644 --- a/packages/webapp/src/components/AdvancedFilter/AdvancedFilterDropdown.tsx +++ b/packages/webapp/src/components/AdvancedFilter/AdvancedFilterDropdown.tsx @@ -1,6 +1,6 @@ // @ts-nocheck import React from 'react'; -import { Formik, FastField, FieldArray, useFormikContext } from 'formik'; +import { Formik, FastField, FieldArray } from 'formik'; import { Button, FormGroup, diff --git a/packages/webapp/src/components/App.tsx b/packages/webapp/src/components/App.tsx index 0ad264ee8..949a1861f 100644 --- a/packages/webapp/src/components/App.tsx +++ b/packages/webapp/src/components/App.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import { Router, Switch, Route } from 'react-router'; import { createBrowserHistory } from 'history'; import { QueryClientProvider, QueryClient } from 'react-query'; diff --git a/packages/webapp/src/components/Dashboard/SplashScreen.tsx b/packages/webapp/src/components/Dashboard/SplashScreen.tsx index 1815bd3c9..e24587841 100644 --- a/packages/webapp/src/components/Dashboard/SplashScreen.tsx +++ b/packages/webapp/src/components/Dashboard/SplashScreen.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import * as R from 'ramda'; import BigcapitalLoading from './BigcapitalLoading'; import withDashboard from '@/containers/Dashboard/withDashboard'; diff --git a/packages/webapp/src/components/DialogsContainer.tsx b/packages/webapp/src/components/DialogsContainer.tsx index cad11bebb..2ee579980 100644 --- a/packages/webapp/src/components/DialogsContainer.tsx +++ b/packages/webapp/src/components/DialogsContainer.tsx @@ -1,5 +1,3 @@ -import React from 'react'; - import AccountDialog from '@/containers/Dialogs/AccountDialog'; import InviteUserDialog from '@/containers/Dialogs/InviteUserDialog'; import UserFormDialog from '@/containers/Dialogs/UserFormDialog'; diff --git a/packages/webapp/src/components/Utils/For.tsx b/packages/webapp/src/components/Utils/For.tsx index 64cbffa18..fa7935894 100644 --- a/packages/webapp/src/components/Utils/For.tsx +++ b/packages/webapp/src/components/Utils/For.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import PropTypes from 'prop-types'; export const For = ({ render, of }) => diff --git a/packages/webapp/src/containers/Authentication/Login.tsx b/packages/webapp/src/containers/Authentication/Login.tsx index 641e5e213..9efbac5e9 100644 --- a/packages/webapp/src/containers/Authentication/Login.tsx +++ b/packages/webapp/src/containers/Authentication/Login.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import { Formik } from 'formik'; import { Link } from 'react-router-dom'; diff --git a/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveDetailHeader.tsx b/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveDetailHeader.tsx index f6d273b4f..df251fed2 100644 --- a/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveDetailHeader.tsx +++ b/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveDetailHeader.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import intl from 'react-intl-universal'; import { defaultTo } from 'lodash'; diff --git a/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveDetailTab.tsx b/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveDetailTab.tsx index 8dab1a377..f352e6b97 100644 --- a/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveDetailTab.tsx +++ b/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveDetailTab.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import styled from 'styled-components'; import { CommercialDocBox } from '@/components'; diff --git a/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveGLEntriesPanel.tsx b/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveGLEntriesPanel.tsx index b7b6a6bc7..049738795 100644 --- a/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveGLEntriesPanel.tsx +++ b/packages/webapp/src/containers/Drawers/PaymentReceiveDetailDrawer/PaymentReceiveGLEntriesPanel.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import styled from 'styled-components'; import { Card } from '@/components'; diff --git a/packages/webapp/src/containers/FinancialStatements/CashFlowStatement/CashFlowStatementGeneralPanel.tsx b/packages/webapp/src/containers/FinancialStatements/CashFlowStatement/CashFlowStatementGeneralPanel.tsx index b1aeda98f..de7a3c012 100644 --- a/packages/webapp/src/containers/FinancialStatements/CashFlowStatement/CashFlowStatementGeneralPanel.tsx +++ b/packages/webapp/src/containers/FinancialStatements/CashFlowStatement/CashFlowStatementGeneralPanel.tsx @@ -1,6 +1,4 @@ // @ts-nocheck -import React from 'react'; - import { Row, Col } from '@/components'; import FinancialStatementDateRange from '../FinancialStatementDateRange'; import FinancialStatementsFilter from '../FinancialStatementsFilter'; diff --git a/packages/webapp/src/containers/FinancialStatements/CustomersBalanceSummary/CustomersBalanceSummaryActionsBar.tsx b/packages/webapp/src/containers/FinancialStatements/CustomersBalanceSummary/CustomersBalanceSummaryActionsBar.tsx index 7d85ac02e..81d8a7848 100644 --- a/packages/webapp/src/containers/FinancialStatements/CustomersBalanceSummary/CustomersBalanceSummaryActionsBar.tsx +++ b/packages/webapp/src/containers/FinancialStatements/CustomersBalanceSummary/CustomersBalanceSummaryActionsBar.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import { NavbarGroup, Button, diff --git a/packages/webapp/src/containers/FinancialStatements/CustomersBalanceSummary/CustomersBalanceSummaryGeneralPanelContent.tsx b/packages/webapp/src/containers/FinancialStatements/CustomersBalanceSummary/CustomersBalanceSummaryGeneralPanelContent.tsx index 227929af3..dc0d2ae5e 100644 --- a/packages/webapp/src/containers/FinancialStatements/CustomersBalanceSummary/CustomersBalanceSummaryGeneralPanelContent.tsx +++ b/packages/webapp/src/containers/FinancialStatements/CustomersBalanceSummary/CustomersBalanceSummaryGeneralPanelContent.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import { FastField } from 'formik'; import { DateInput } from '@blueprintjs/datetime'; import { FormGroup, Position, Checkbox } from '@blueprintjs/core'; diff --git a/packages/webapp/src/containers/ItemsCategories/ItemsCategoryActionsBar.tsx b/packages/webapp/src/containers/ItemsCategories/ItemsCategoryActionsBar.tsx index 8faf951ac..9258dec22 100644 --- a/packages/webapp/src/containers/ItemsCategories/ItemsCategoryActionsBar.tsx +++ b/packages/webapp/src/containers/ItemsCategories/ItemsCategoryActionsBar.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import { NavbarGroup, NavbarDivider, diff --git a/packages/webapp/src/containers/Preferences/PreferencesPageLoader.tsx b/packages/webapp/src/containers/Preferences/PreferencesPageLoader.tsx index 4413f5ca5..25e8b5eb1 100644 --- a/packages/webapp/src/containers/Preferences/PreferencesPageLoader.tsx +++ b/packages/webapp/src/containers/Preferences/PreferencesPageLoader.tsx @@ -1,5 +1,4 @@ // @ts-nocheck -import React from 'react'; import ContentLoader from 'react-content-loader'; export default function PreferencesPageLoader(props) { diff --git a/packages/webapp/src/style/App.scss b/packages/webapp/src/style/App.scss index a37a32c1a..f18606673 100644 --- a/packages/webapp/src/style/App.scss +++ b/packages/webapp/src/style/App.scss @@ -1,25 +1,10 @@ @import './normalize.scss'; -@import './Base.scss'; +@import './_base.scss'; -$svg-icon-map: ( - '16px/small-minus.svg': "path fill-rule='evenodd' clip-rule='evenodd' d='M11 7H5c-.55 0-1 .45-1 1s.45 1 1 1h6c.55 0 1-.45 1-1s-.45-1-1-1z' fill='%23fff'/", - '16px/small-tick.svg': "path fill-rule='evenodd' clip-rule='evenodd' d='M12 5c-.28 0-.53.11-.71.29L7 9.59l-2.29-2.3a1.003 1.003 0 0 0-1.42 1.42l3 3c.18.18.43.29.71.29s.53-.11.71-.29l5-5A1.003 1.003 0 0 0 12 5z' fill='%23fff'/", - '16px/chevron-right.svg': "path fill-rule='evenodd' clip-rule='evenodd' d='M10.71 7.29l-4-4a1.003 1.003 0 0 0-1.42 1.42L8.59 8 5.3 11.29c-.19.18-.3.43-.3.71a1.003 1.003 0 0 0 1.71.71l4-4c.18-.18.29-.43.29-.71 0-.28-.11-.53-.29-.71z' fill='%235C7080'/", - '16px/more.svg': "g fill='%235C7080'%3E%3Ccircle cx='2' cy='8.03' r='2'/%3E%3Ccircle cx='14' cy='8.03' r='2'/%3E%3Ccircle cx='8' cy='8.03' r='2'/%3E%3C/g", -); - -@function svg-icon($inline-svg, $fill-color) { - @return url("data:image/svg+xml;charset=utf-8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3C"+ map-get($svg-icon-map, $inline-svg) + "%3E%3C/svg%3E") -} - - -// Blueprint framework. @import '@blueprintjs/core/src/blueprint.scss'; @import '@blueprintjs/datetime/src/blueprint-datetime.scss'; @import '@blueprintjs/popover2/src/blueprint-popover2.scss'; -@import 'basscss'; - // Objects @import 'objects/form'; @import 'objects/switch'; diff --git a/packages/webapp/src/style/Base.scss b/packages/webapp/src/style/Base.scss deleted file mode 100644 index e8fa8c7d3..000000000 --- a/packages/webapp/src/style/Base.scss +++ /dev/null @@ -1,3 +0,0 @@ - -@import 'variables'; -@import 'functions'; \ No newline at end of file diff --git a/packages/webapp/src/style/_base.scss b/packages/webapp/src/style/_base.scss new file mode 100644 index 000000000..6fc81a8fb --- /dev/null +++ b/packages/webapp/src/style/_base.scss @@ -0,0 +1,3 @@ + +@import '_variables'; +@import '_functions'; \ No newline at end of file diff --git a/packages/webapp/src/style/_functions.scss b/packages/webapp/src/style/_functions.scss new file mode 100644 index 000000000..fb20330ee --- /dev/null +++ b/packages/webapp/src/style/_functions.scss @@ -0,0 +1,54 @@ +// Characters which are escaped by the escape-svg function +$escaped-characters: (("<", "%3c"), + (">", "%3e"), + ("#", "%23"), + ("(", "%28"), + (")", "%29"), +) !default; + +$svg-icon-map: ('16px/small-minus.svg': "path fill-rule='evenodd' clip-rule='evenodd' d='M11 7H5c-.55 0-1 .45-1 1s.45 1 1 1h6c.55 0 1-.45 1-1s-.45-1-1-1z' fill='%23fff'/", + '16px/small-tick.svg': "path fill-rule='evenodd' clip-rule='evenodd' d='M12 5c-.28 0-.53.11-.71.29L7 9.59l-2.29-2.3a1.003 1.003 0 0 0-1.42 1.42l3 3c.18.18.43.29.71.29s.53-.11.71-.29l5-5A1.003 1.003 0 0 0 12 5z' fill='%23fff'/", + '16px/chevron-right.svg': "path fill-rule='evenodd' clip-rule='evenodd' d='M10.71 7.29l-4-4a1.003 1.003 0 0 0-1.42 1.42L8.59 8 5.3 11.29c-.19.18-.3.43-.3.71a1.003 1.003 0 0 0 1.71.71l4-4c.18-.18.29-.43.29-.71 0-.28-.11-.53-.29-.71z' fill='%235C7080'/", + '16px/more.svg': "g fill='%235C7080'%3E%3Ccircle cx='2' cy='8.03' r='2'/%3E%3Ccircle cx='14' cy='8.03' r='2'/%3E%3Ccircle cx='8' cy='8.03' r='2'/%3E%3C/g", +) !default; + +// Replace `$search` with `$replace` in `$string` +// Used on our SVG icon backgrounds for custom forms. +// +// @author Hugo Giraudel +// @param {String} $string - Initial string +// @param {String} $search - Substring to replace +// @param {String} $replace ('') - New value +// @return {String} - Updated string +@function str-replace($string, $search, $replace: "") { + $index: str-index($string, $search); + + @if $index { + @return str-slice($string, 1, $index - 1)+$replace+str-replace(str-slice($string, $index + str-length($search)), $search, $replace); + } + + @return $string; +} + +@function escape-svg($string) { + @if str-index($string, "data:image/svg+xml") { + + @each $char, + $encoded in $escaped-characters { + + @if str-index($string, "url(")==1 { + $string: url("#{str-replace(str-slice($string, 6, -3), $char, $encoded)}"); + } + + @else { + $string: str-replace($string, $char, $encoded); + } + } + } + + @return $string; +} + +@function svg-icon($inline-svg, $fill-color) { + @return url("data:image/svg+xml;charset=utf-8,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3C"+ map-get($svg-icon-map, $inline-svg) + "%3E%3C/svg%3E") +} \ No newline at end of file diff --git a/packages/webapp/src/style/normalize.scss b/packages/webapp/src/style/_normalize.scss similarity index 100% rename from packages/webapp/src/style/normalize.scss rename to packages/webapp/src/style/_normalize.scss diff --git a/packages/webapp/src/style/variables.scss b/packages/webapp/src/style/_variables.scss similarity index 99% rename from packages/webapp/src/style/variables.scss rename to packages/webapp/src/style/_variables.scss index 41f427703..de79cd5ab 100644 --- a/packages/webapp/src/style/variables.scss +++ b/packages/webapp/src/style/_variables.scss @@ -48,4 +48,4 @@ $form-check-input-checked-bg-image: "" !default; // z-indexs $zindex-dashboard-splash-screen: 39; -$zindex-toast: 40; \ No newline at end of file +$zindex-toast: 40; diff --git a/packages/webapp/src/style/functions.scss b/packages/webapp/src/style/functions.scss deleted file mode 100644 index 50d4e4497..000000000 --- a/packages/webapp/src/style/functions.scss +++ /dev/null @@ -1,40 +0,0 @@ - -// Characters which are escaped by the escape-svg function -$escaped-characters: ( - ("<","%3c"), - (">","%3e"), - ("#","%23"), - ("(","%28"), - (")","%29"), -) !default; - -// Replace `$search` with `$replace` in `$string` -// Used on our SVG icon backgrounds for custom forms. -// -// @author Hugo Giraudel -// @param {String} $string - Initial string -// @param {String} $search - Substring to replace -// @param {String} $replace ('') - New value -// @return {String} - Updated string -@function str-replace($string, $search, $replace: "") { - $index: str-index($string, $search); - - @if $index { - @return str-slice($string, 1, $index - 1) + $replace + str-replace(str-slice($string, $index + str-length($search)), $search, $replace); - } - @return $string; -} - -@function escape-svg($string) { - @if str-index($string, "data:image/svg+xml") { - @each $char, $encoded in $escaped-characters { - - @if str-index($string, "url(") == 1 { - $string: url("#{str-replace(str-slice($string, 6, -3), $char, $encoded)}"); - } @else { - $string: str-replace($string, $char, $encoded); - } - } - } - @return $string; -} diff --git a/packages/webapp/src/utils/index.tsx b/packages/webapp/src/utils/index.tsx index 4674efb50..07e357515 100644 --- a/packages/webapp/src/utils/index.tsx +++ b/packages/webapp/src/utils/index.tsx @@ -1,22 +1,19 @@ // @ts-nocheck -import React from 'react'; import moment from 'moment'; import _ from 'lodash'; import * as R from 'ramda'; import Currencies from 'js-money/lib/currency'; import clsx from 'classnames'; - import { Intent } from '@blueprintjs/core'; import Currency from 'js-money/lib/currency'; import accounting from 'accounting'; -import deepMapKeys from 'deep-map-keys'; import { createSelectorCreator, defaultMemoize } from 'reselect'; import { isEqual, castArray, isEmpty, includes, pickBy } from 'lodash'; - import jsCookie from 'js-cookie'; - +import { deepMapKeys } from './map-key-deep'; export * from './deep'; + export const getCookie = (name, defaultValue) => _.defaultTo(jsCookie.get(name), defaultValue); diff --git a/packages/webapp/src/utils/map-key-deep.ts b/packages/webapp/src/utils/map-key-deep.ts new file mode 100644 index 000000000..869bd5161 --- /dev/null +++ b/packages/webapp/src/utils/map-key-deep.ts @@ -0,0 +1,79 @@ +import { isArray, isFunction, isNil, isObject } from 'lodash'; + +interface NonPrimitive extends Object { + [key: string]: any; + [index: number]: any; +} + +export interface MapFn { + (key: string, value: any): string; +} + +export interface Opts { + thisArg?: any; +} + +export class DeepMapKeys { + private cache = new WeakMap(); + + constructor(private mapFn: MapFn, private opts: Opts) {} + + public map(value: any): any { + return isArray(value) + ? this.mapArray(value) + : isObject(value) + ? this.mapObject(value) + : value; + } + + private mapArray(arr: any[]): any[] { + if (this.cache.has(arr)) { + return this.cache.get(arr); + } + + let length = arr.length; + let result: any[] = []; + this.cache.set(arr, result); + + for (let i = 0; i < length; i++) { + result.push(this.map(arr[i])); + } + + return result; + } + + private mapObject(obj: NonPrimitive): NonPrimitive { + if (this.cache.has(obj)) { + return this.cache.get(obj); + } + + let { + mapFn, + opts: { thisArg }, + } = this; + let result: NonPrimitive = {}; + this.cache.set(obj, result); + + for (let key in obj) { + if (obj.hasOwnProperty(key)) { + result[mapFn.call(thisArg, key, obj[key])] = this.map(obj[key]); + } + } + + return result; + } +} + +export function deepMapKeys(object: any, mapFn: MapFn, options?: Opts): T { + options = isNil(options) ? {} : options; + + if (!mapFn) { + throw new Error('mapFn is required'); + } else if (!isFunction(mapFn)) { + throw new TypeError('mapFn must be a function'); + } else if (!isObject(options)) { + throw new TypeError('options must be an object'); + } + + return new DeepMapKeys(mapFn, options).map(object); +} diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 3f4a40315..caaf8712c 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -417,6 +417,9 @@ importers: '@blueprintjs-formik/select': specifier: ^0.3.5 version: 0.3.5(@blueprintjs/core@4.20.2)(@blueprintjs/select@4.9.24)(formik@2.2.9)(react-dom@18.2.0)(react@18.2.0) + '@blueprintjs/colors': + specifier: 4.1.19 + version: 4.1.19 '@blueprintjs/core': specifier: ^4.20.2 version: 4.20.2(@types/react@16.14.35)(react-dom@18.2.0)(react@18.2.0) @@ -477,6 +480,9 @@ importers: '@types/react-body-classname': specifier: ^1.1.7 version: 1.1.7 + '@types/react-dom': + specifier: ^16.9.16 + version: 16.9.17 '@types/react-redux': specifier: ^7.1.24 version: 7.1.25 @@ -513,6 +519,9 @@ importers: camelcase: specifier: ^5.3.1 version: 5.3.1 + classnames: + specifier: ^2.3.2 + version: 2.3.2 cross-env: specifier: ^7.0.2 version: 7.0.3 @@ -540,6 +549,9 @@ importers: formik: specifier: ^2.2.5 version: 2.2.9(react@18.2.0) + history: + specifier: 4.10.1 + version: 4.10.1 http-proxy-middleware: specifier: ^1.0.0 version: 1.3.1 @@ -555,6 +567,9 @@ importers: jest-watch-typeahead: specifier: 0.4.2 version: 0.4.2 + js-cookie: + specifier: 2.2.1 + version: 2.2.1 js-money: specifier: ^0.6.3 version: 0.6.3 @@ -570,6 +585,9 @@ importers: path-browserify: specifier: ^1.0.1 version: 1.0.1 + prop-types: + specifier: 15.8.1 + version: 15.8.1 query-string: specifier: ^7.1.1 version: 7.1.3 @@ -600,6 +618,9 @@ importers: react-error-boundary: specifier: ^3.0.2 version: 3.1.4(react@18.2.0) + react-error-overlay: + specifier: ^6.0.9 + version: 6.0.11 react-hotkeys-hook: specifier: ^3.0.3 version: 3.4.7(react-dom@18.2.0)(react@18.2.0) @@ -618,6 +639,9 @@ importers: react-redux: specifier: ^7.2.9 version: 7.2.9(react-dom@18.2.0)(react@18.2.0) + react-router: + specifier: 5.3.4 + version: 5.3.4(react@18.2.0) react-router-breadcrumbs-hoc: specifier: ^3.2.10 version: 3.4.0(react-router@5.3.4)(react@18.2.0) @@ -669,9 +693,15 @@ importers: redux-thunk: specifier: ^2.4.2 version: 2.4.2(redux@4.2.1) + reselect: + specifier: 4.1.7 + version: 4.1.7 rtl-detect: specifier: ^1.0.3 version: 1.0.4 + sass: + specifier: ^1.68.0 + version: 1.68.0 semver: specifier: 6.3.0 version: 6.3.0 @@ -690,16 +720,6 @@ importers: yup: specifier: ^0.28.1 version: 0.28.5 - devDependencies: - '@types/react-dom': - specifier: ^16.9.16 - version: 16.9.17 - react-error-overlay: - specifier: ^6.0.9 - version: 6.0.11 - sass: - specifier: ^1.68.0 - version: 1.68.0 packages: @@ -3276,8 +3296,8 @@ packages: web-vitals: 2.1.4 dev: false - /@blueprintjs/colors@4.1.14: - resolution: {integrity: sha512-MT++a/OSGui8tMpo5dEogrTV/PJCsHuhXTmdsGQtzivlLwBAp1XKe/Np4vaX6seJqRgR0oyXgS9kVvomCl463Q==} + /@blueprintjs/colors@4.1.19: + resolution: {integrity: sha512-x5mDo4Ue9rAdbMHvOm0dNru9MSZqgs9Dd/l/2rgjzottthjsq1XjkiVae6evX4EGNM0I/bZKjTT8ccvqCqn4yw==} dev: false /@blueprintjs/colors@4.2.1: @@ -3293,7 +3313,7 @@ packages: react: ^15.3.0 || 16 || 17 react-dom: ^15.3.0 || 16 || 17 dependencies: - '@blueprintjs/colors': 4.1.14 + '@blueprintjs/colors': 4.1.19 '@blueprintjs/icons': 3.33.0 '@juggle/resize-observer': 3.4.0 '@types/dom4': 2.0.2 @@ -6256,6 +6276,7 @@ packages: /@types/prop-types@15.7.5: resolution: {integrity: sha512-JCB8C6SnDoQf0cNycqd/35A7MjcnK+ZTqE7judS6o7utxUCg6imJg3QK2qzHKszlTjcj2cn+NwMB2i96ubpj7w==} + dev: false /@types/q@1.5.5: resolution: {integrity: sha512-L28j2FcJfSZOnL1WBjDYp2vUHCeIFlyYI/53EwD/rKUBQ7MtUUfbQWiyKJGpcnv4/WgrhWsFKrcPstcAt/J0tQ==} @@ -6291,7 +6312,7 @@ packages: resolution: {integrity: sha512-qSRyxEsrm5btPXnowDOs5jSkgT8ldAA0j6Qp+otHUh+xHzy3sXmgNfyhucZjAjkgpdAUw9rJe0QRtX/l+yaS4g==} dependencies: '@types/react': 16.14.35 - dev: true + dev: false /@types/react-dom@18.0.10: resolution: {integrity: sha512-E42GW/JA4Qv15wQdqJq8DL4JhNpB3prJgjgapN3qJT9K2zO5IIAQh4VXvCEDupoqAwnz0cY4RlXeC/ajX5SFHg==} @@ -6335,6 +6356,7 @@ packages: '@types/prop-types': 15.7.5 '@types/scheduler': 0.16.2 csstype: 3.1.1 + dev: false /@types/react@18.0.27: resolution: {integrity: sha512-3vtRKHgVxu3Jp9t718R9BuzoD4NcQ8YJ5XRzsSKxNDiDonD2MXIT1TmSkenxuCycZJoQT5d2vE8LwWJxBC1gmA==} @@ -6362,6 +6384,7 @@ packages: /@types/scheduler@0.16.2: resolution: {integrity: sha512-hppQEBDmlwhFAXKJX2KnWLYu5yMfi91yazPb2l+lbJiwW+wdo1gNeRA+3RgNSO39WYX2euey41KEwnqesU2Jew==} + dev: false /@types/semver@7.3.13: resolution: {integrity: sha512-21cFJr9z3g5dW8B0CVI9g2O9beqaThGQ6ZFBqHfwhzLDKUxaqTIy3vnfah/UPkfOiF2pLq+tGz+W8RyCskuslw==} @@ -10107,6 +10130,7 @@ packages: /csstype@3.1.1: resolution: {integrity: sha512-DJR/VvkAvSZW9bTouZue2sSxDwdTN92uHjqeKVm+0dAqdfNykRzQ95tay8aXMBAAPpUiq4Qcug2L7neoRh2Egw==} + dev: false /csurf@1.11.0: resolution: {integrity: sha512-UCtehyEExKTxgiu8UHdGvHj4tnpE/Qctue03Giq5gPgMQ9cg/ciod5blZQ5a4uCEenNQjxyGuzygLdKUmee/bQ==} @@ -20286,6 +20310,7 @@ packages: /react-error-overlay@6.0.11: resolution: {integrity: sha512-/6UZ2qgEyH2aqzYZgQPxEnz33NJ2gNsnHA2o5+o4wW9bLM/JYQitNP9xPhsXwC08hMMovfGe/8retsdDsczPRg==} + dev: false /react-fast-compare@2.0.4: resolution: {integrity: sha512-suNP+J1VU1MWFKcyt7RtjiSWUjvidmQSlqu+eHslq+342xCbGTYmC0mEhPCOHxlW0CywylOC1u2DFAT+bv4dBw==} @@ -21633,6 +21658,7 @@ packages: chokidar: 3.5.3 immutable: 4.2.4 source-map-js: 1.0.2 + dev: false /sax@1.2.4: resolution: {integrity: sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==}