diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..e69de29 diff --git a/doc/architecture/API.md b/doc/architecture/API.md new file mode 100644 index 0000000..d50a354 --- /dev/null +++ b/doc/architecture/API.md @@ -0,0 +1,25 @@ +Organizations + +Contacts + +Locations + +Phones + +Postal Addresses + +Programs + +Holiday Schedules + +Languages + +Services + +Physical Addresses + +Regular Schedules + +Taxonomies + +Eligibilities diff --git a/link-admin/.eslintrc.js b/link-admin/.eslintrc.js new file mode 100644 index 0000000..d07758e --- /dev/null +++ b/link-admin/.eslintrc.js @@ -0,0 +1,88 @@ +const OFF = 0 +const WARN = 1 +const ERROR = 2 + +module.exports = { + root: true, + env: { + es6: true, + browser: true, + 'jest/globals': true, + node: true + }, + extends: [ + 'eslint:recommended', + 'plugin:react/recommended' + ], + parserOptions: { + ecmaVersion: 2018, + experimentalObjectRestSpread: true, + jsx: true, + sourceType: 'module' + }, + plugins: [ + 'react', + 'jest', + 'jsx-a11y', + 'import' + ], + settings: { + 'import/extensions': [ + '.js', + '.jsx', + '.css' + ], + 'react': { + 'version': 'detect' + } + }, + rules: { + 'indent': [ERROR, 2, { + 'SwitchCase': 1 + }], + 'semi': [ERROR, 'never'], + 'brace-style': [ERROR, '1tbs', { + allowSingleLine: true + }], + 'object-curly-spacing': [ERROR, 'always'], + 'array-bracket-spacing': [ERROR, 'never'], + 'space-before-blocks': [ERROR, 'always'], + 'class-methods-use-this': OFF, + 'comma-dangle': [ERROR, 'never'], + 'jest/no-disabled-tests': ERROR, + 'jest/no-focused-tests': ERROR, + 'jest/no-identical-title': ERROR, + 'jest/prefer-to-have-length': ERROR, + 'jest/valid-expect': ERROR, + 'jsx-a11y/anchor-is-valid': [ERROR, { + components: ['Link'], + specialLink: ['to'], + aspects: ['noHref', 'invalidHref', 'preferButton'] + }], + 'function-paren-newline': OFF, + 'import/extensions': [ERROR, 'never', { + 'css': 'ignorePackages', + 'svg': 'ignorePackages', + 'jpg': 'ignorePackages', + 'png': 'ignorePackages', + 'gif': 'ignorePackages' + }], + 'no-unused-expressions': [ERROR, { + allowShortCircuit: false, + allowTernary: false + }], + 'no-unused-vars': WARN, + 'object-curly-newline': OFF, + 'quotes': [ERROR, 'single', { + allowTemplateLiterals: true + }], + 'react/jsx-curly-spacing': [ERROR, 'always', { + spacing: { objectLiterals: 'never' } + }], + 'react/no-redundant-should-component-update': ERROR, + 'react/no-unused-prop-types': WARN, + 'react/no-typos': ERROR, + 'react/prefer-stateless-function': OFF, + 'eol-last': [ERROR, 'always'] + } +} diff --git a/link-admin/.storybook/main.js b/link-admin/.storybook/main.js index 05984d8..925097d 100644 --- a/link-admin/.storybook/main.js +++ b/link-admin/.storybook/main.js @@ -12,4 +12,4 @@ module.exports = { ) return config } -} \ No newline at end of file +} diff --git a/link-admin/.storybook/preview.js b/link-admin/.storybook/preview.js index 6f9f164..6035105 100644 --- a/link-admin/.storybook/preview.js +++ b/link-admin/.storybook/preview.js @@ -1,21 +1,13 @@ import React from 'react' -import { RendererProvider as FelaProvider } from 'react-fela' import { configure, addDecorator } from '@storybook/react' -import { Provider } from 'react-redux' +import { Provider as ReduxProvider } from 'react-redux' import store from 'store' -import { createRenderer } from 'fela' -import '../src/index.css' - -const renderer = createRenderer() - -const withFelaProvider = story => ( - { story() } -) +import StyleProviders from '../src/app/providers/style' const withReduxProvider = story => ( - { story() } + { story() } ) const req = require.context('../src', true, /\.stories.js$/) @@ -24,6 +16,13 @@ function loadStories() { req.keys().forEach(filename => req(filename)) } -addDecorator(withFelaProvider) addDecorator(withReduxProvider) configure(loadStories, module) + +export const decorators = [ + (Story) => ( + + + + ) +] diff --git a/link-admin/craco.config.js b/link-admin/craco.config.js new file mode 100644 index 0000000..604a907 --- /dev/null +++ b/link-admin/craco.config.js @@ -0,0 +1,10 @@ +module.exports = { + style: { + postcss: { + plugins: [ + require('tailwindcss'), + require('autoprefixer') + ] + } + } +} diff --git a/link-admin/package.json b/link-admin/package.json index c9d1a84..b86c131 100644 --- a/link-admin/package.json +++ b/link-admin/package.json @@ -3,9 +3,9 @@ "version": "0.1.0", "private": true, "scripts": { - "start": "HOST=blomp.localhost PORT=3001 react-scripts start", - "build": "react-scripts build", - "test": "react-scripts test --env=jsdom", + "start": "HOST=blomp.localhost PORT=3001 craco start", + "build": "craco build", + "test": "craco test --env=jsdom", "eject": "react-scripts eject", "storybook": "start-storybook -p 9009 -s public", "build-storybook": "build-storybook -s public" @@ -22,33 +22,41 @@ "@zendeskgarden/react-tags": "^8.21.2", "@zendeskgarden/react-theming": "^8.21.2", "@zendeskgarden/react-typography": "^8.21.2", + "@zendeskgarden/svg-icons": "^6.27.0", + "@zendeskgarden/tailwindcss": "^1.1.0", "axios": "^0.20.0", + "classnames": "^2.2.6", "connected-react-router": "^6.8.0", - "fela": "^11.3.1", "global": "^4.3.2", "link-rest-client": "^1.0.0", "lodash": "^4.17.20", "prop-types": "^15.7.2", "react": "^16.13.1", "react-dom": "^16.13.1", - "react-fela": "^11.3.1", + "react-hook-form": "^6.14.0", "react-redux": "^7.2.1", "react-router": "^5.2.0", "react-router-dom": "^5.2.0", "react-scripts": "^3.4.3", "redux": "^4.0.5", "redux-loop": "^6.0.1", - "styled-components": "^5.1.1" + "styled-components": "^5.1.1", + "tailwindcss": "npm:@tailwindcss/postcss7-compat" }, "devDependencies": { + "@craco/craco": "^5.9.0", "@storybook/addon-actions": "^6.0.21", "@storybook/addon-links": "^6.0.21", "@storybook/addons": "^6.0.21", "@storybook/preset-create-react-app": "^3.1.4", "@storybook/react": "^6.0.21", + "autoprefixer": "^9.8.6", "enzyme": "^3.11.0", "enzyme-adapter-react-16": "^1.15.4", + "eslint-plugin-jest": "^24.1.3", "jest": "^26.4.2", + "jest-styled-components": "^7.0.3", + "postcss": "^7.0.35", "prettier": "^2.1.1", "react-test-renderer": "^16.13.1", "redux-devtools": "^3.6.1" diff --git a/link-admin/src/App.jsx b/link-admin/src/App.jsx deleted file mode 100644 index 9db5b52..0000000 --- a/link-admin/src/App.jsx +++ /dev/null @@ -1,27 +0,0 @@ -import React from 'react' - -import { Provider } from 'react-redux' -import { RendererProvider as FelaProvider } from 'react-fela' -import { createRenderer } from 'fela' - -import { ConnectedRouter } from 'connected-react-router' -import { ThemeProvider } from '@zendeskgarden/react-theming' - -import store, { history } from 'store' -import Router from 'Router' - -const renderer = createRenderer() - -const App = () => ( - - - - - - - - - -) - -export default App diff --git a/link-admin/src/App.test.js b/link-admin/src/App.test.js deleted file mode 100644 index a754b20..0000000 --- a/link-admin/src/App.test.js +++ /dev/null @@ -1,9 +0,0 @@ -import React from 'react'; -import ReactDOM from 'react-dom'; -import App from './App'; - -it('renders without crashing', () => { - const div = document.createElement('div'); - ReactDOM.render(, div); - ReactDOM.unmountComponentAtNode(div); -}); diff --git a/link-admin/src/Router/index.jsx b/link-admin/src/Router/index.jsx deleted file mode 100644 index 8a6bf21..0000000 --- a/link-admin/src/Router/index.jsx +++ /dev/null @@ -1,39 +0,0 @@ -import React from 'react' -import { Route, Switch } from 'react-router' -import Landing from 'pages/Landing' -import Organization from 'pages/Organization' -import AddOrganization from 'pages/Organization/AddOrganization' -import FourOhFour from 'pages/FourOhFour' - -const base = '/organizations' -const tabRegex = 'details|locations' - -const AdminRouter = () => { - return ( - - - - - - - - - - - - ) -} - -export default AdminRouter diff --git a/link-admin/src/app/App.jsx b/link-admin/src/app/App.jsx new file mode 100644 index 0000000..866877c --- /dev/null +++ b/link-admin/src/app/App.jsx @@ -0,0 +1,17 @@ +import React from 'react' + +import { Provider as ReduxProvider } from 'react-redux' +import store from 'store' + +import StyleProviders from 'app/providers/style' +import Router from 'app/router' + +const App = () => ( + + + + + +) + +export default App diff --git a/link-admin/src/app/App.test.js b/link-admin/src/app/App.test.js new file mode 100644 index 0000000..4bf1935 --- /dev/null +++ b/link-admin/src/app/App.test.js @@ -0,0 +1,9 @@ +import React from 'react' +import ReactDOM from 'react-dom' +import App from './App' + +it('renders without crashing', () => { + const div = document.createElement('div') + ReactDOM.render(, div) + ReactDOM.unmountComponentAtNode(div) +}) diff --git a/link-admin/src/app/index.css b/link-admin/src/app/index.css new file mode 100644 index 0000000..f34129d --- /dev/null +++ b/link-admin/src/app/index.css @@ -0,0 +1,15 @@ +@tailwind base; +@tailwind components; +@tailwind utilities; + +/* Something's wrong with the preflight setting for border values. https://github.com/tailwindlabs/tailwindcss/pull/116 */ +*, +*:before, +*:after { + border-width: 0; +} + +html { + /* Unsetting this property set by zendeskgarden base theme */ + overflow-y: unset; +} diff --git a/link-admin/src/app/layout/admin/Footer/index.jsx b/link-admin/src/app/layout/admin/Footer/index.jsx new file mode 100644 index 0000000..e7d962b --- /dev/null +++ b/link-admin/src/app/layout/admin/Footer/index.jsx @@ -0,0 +1,11 @@ +import React from 'react' + +const Footer = () => { + return ( +
+
©2020
+
+ ) +} + +export default Footer diff --git a/link-admin/src/app/layout/admin/Sidebar/index.jsx b/link-admin/src/app/layout/admin/Sidebar/index.jsx new file mode 100644 index 0000000..048e1f7 --- /dev/null +++ b/link-admin/src/app/layout/admin/Sidebar/index.jsx @@ -0,0 +1,22 @@ +import React from 'react' +import styled from 'styled-components' + +import MenuToggleButton from 'components/MenuToggleButton' + +const Sidebar = () => { + return ( + + + + ) +} + +const SidebarContainer = styled.div` + z-index: 1000; +` + +export default Sidebar diff --git a/link-admin/src/app/layout/admin/Topbar/index.jsx b/link-admin/src/app/layout/admin/Topbar/index.jsx new file mode 100644 index 0000000..925e1e1 --- /dev/null +++ b/link-admin/src/app/layout/admin/Topbar/index.jsx @@ -0,0 +1,23 @@ +import React from 'react' + +import Link from 'components/Routing/Link' + +import logo from 'images/link-sf.png' +import MenuToggleButton from 'components/MenuToggleButton' + +const Topbar = () => { + return ( +
+
+
+ +
+
+ + + +
+ ) +} + +export default Topbar diff --git a/link-admin/src/app/layout/admin/index.jsx b/link-admin/src/app/layout/admin/index.jsx new file mode 100644 index 0000000..1a31d44 --- /dev/null +++ b/link-admin/src/app/layout/admin/index.jsx @@ -0,0 +1,92 @@ +import React from 'react' +import PropTypes from 'prop-types' +import styled from 'styled-components' +import classnames from 'classnames' + +import Topbar from './Topbar' +import Sidebar from './Sidebar' +import Footer from './Footer' +import { useSelector } from 'react-redux' + +const AdminLayout = ({ children }) => { + const app = useSelector(state => state.app) + + return ( + + + + +
+
+ { children } +
+
+ +