ソースを参照

update admin page

Alex 2 年 前
コミット
f866f20ba0

+ 280 - 0
package-lock.json

@@ -31,6 +31,7 @@
         "react-redux": "^7.2.6",
         "react-router-dom": "^5.3.0",
         "react-scripts": "5.0.0",
+        "react-swipeable-views": "^0.14.0",
         "redux": "^4.1.2",
         "redux-form": "^8.3.8",
         "redux-thunk": "^2.4.1",
@@ -12140,6 +12141,11 @@
         "node": ">=4.0"
       }
     },
+    "node_modules/keycode": {
+      "version": "2.2.1",
+      "resolved": "https://registry.npmjs.org/keycode/-/keycode-2.2.1.tgz",
+      "integrity": "sha512-Rdgz9Hl9Iv4QKi8b0OlCRQEzp4AgVxyCtz5S/+VIHezDmrDhkp2N2TqBWOLz0/gbeREXOOiI9/4b8BY9uw2vFg=="
+    },
     "node_modules/kind-of": {
       "version": "6.0.3",
       "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz",
@@ -15322,6 +15328,134 @@
         }
       }
     },
+    "node_modules/react-swipeable-views": {
+      "version": "0.14.0",
+      "resolved": "https://registry.npmjs.org/react-swipeable-views/-/react-swipeable-views-0.14.0.tgz",
+      "integrity": "sha512-wrTT6bi2nC3JbmyNAsPXffUXLn0DVT9SbbcFr36gKpbaCgEp7rX/OFxsu5hPc/NBsUhHyoSRGvwqJNNrWTwCww==",
+      "dependencies": {
+        "@babel/runtime": "7.0.0",
+        "prop-types": "^15.5.4",
+        "react-swipeable-views-core": "^0.14.0",
+        "react-swipeable-views-utils": "^0.14.0",
+        "warning": "^4.0.1"
+      },
+      "engines": {
+        "node": ">=6.0.0"
+      },
+      "peerDependencies": {
+        "react": "^15.3.0 || ^16.0.0 || ^17.0.0"
+      }
+    },
+    "node_modules/react-swipeable-views-core": {
+      "version": "0.14.0",
+      "resolved": "https://registry.npmjs.org/react-swipeable-views-core/-/react-swipeable-views-core-0.14.0.tgz",
+      "integrity": "sha512-0W/e9uPweNEOSPjmYtuKSC/SvKKg1sfo+WtPdnxeLF3t2L82h7jjszuOHz9C23fzkvLfdgkaOmcbAxE9w2GEjA==",
+      "dependencies": {
+        "@babel/runtime": "7.0.0",
+        "warning": "^4.0.1"
+      },
+      "engines": {
+        "node": ">=6.0.0"
+      }
+    },
+    "node_modules/react-swipeable-views-core/node_modules/@babel/runtime": {
+      "version": "7.0.0",
+      "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.0.0.tgz",
+      "integrity": "sha512-7hGhzlcmg01CvH1EHdSPVXYX1aJ8KCEyz6I9xYIi/asDtzBPMyMhVibhM/K6g/5qnKBwjZtp10bNZIEFTRW1MA==",
+      "dependencies": {
+        "regenerator-runtime": "^0.12.0"
+      }
+    },
+    "node_modules/react-swipeable-views-core/node_modules/regenerator-runtime": {
+      "version": "0.12.1",
+      "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.12.1.tgz",
+      "integrity": "sha512-odxIc1/vDlo4iZcfXqRYFj0vpXFNoGdKMAUieAlFYO6m/nl5e9KR/beGf41z4a1FI+aQgtjhuaSlDxQ0hmkrHg=="
+    },
+    "node_modules/react-swipeable-views-utils": {
+      "version": "0.14.0",
+      "resolved": "https://registry.npmjs.org/react-swipeable-views-utils/-/react-swipeable-views-utils-0.14.0.tgz",
+      "integrity": "sha512-W+fXBOsDqgFK1/g7MzRMVcDurp3LqO3ksC8UgInh2P/tKgb5DusuuB1geKHFc6o1wKl+4oyER4Zh3Lxmr8xbXA==",
+      "dependencies": {
+        "@babel/runtime": "7.0.0",
+        "keycode": "^2.1.7",
+        "prop-types": "^15.6.0",
+        "react-event-listener": "^0.6.0",
+        "react-swipeable-views-core": "^0.14.0",
+        "shallow-equal": "^1.2.1"
+      },
+      "engines": {
+        "node": ">=6.0.0"
+      }
+    },
+    "node_modules/react-swipeable-views-utils/node_modules/@babel/runtime": {
+      "version": "7.0.0",
+      "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.0.0.tgz",
+      "integrity": "sha512-7hGhzlcmg01CvH1EHdSPVXYX1aJ8KCEyz6I9xYIi/asDtzBPMyMhVibhM/K6g/5qnKBwjZtp10bNZIEFTRW1MA==",
+      "dependencies": {
+        "regenerator-runtime": "^0.12.0"
+      }
+    },
+    "node_modules/react-swipeable-views-utils/node_modules/react": {
+      "version": "16.14.0",
+      "resolved": "https://registry.npmjs.org/react/-/react-16.14.0.tgz",
+      "integrity": "sha512-0X2CImDkJGApiAlcf0ODKIneSwBPhqJawOa5wCtKbu7ZECrmS26NvtSILynQ66cgkT/RJ4LidJOc3bUESwmU8g==",
+      "peer": true,
+      "dependencies": {
+        "loose-envify": "^1.1.0",
+        "object-assign": "^4.1.1",
+        "prop-types": "^15.6.2"
+      },
+      "engines": {
+        "node": ">=0.10.0"
+      }
+    },
+    "node_modules/react-swipeable-views-utils/node_modules/react-event-listener": {
+      "version": "0.6.6",
+      "resolved": "https://registry.npmjs.org/react-event-listener/-/react-event-listener-0.6.6.tgz",
+      "integrity": "sha512-+hCNqfy7o9wvO6UgjqFmBzARJS7qrNoda0VqzvOuioEpoEXKutiKuv92dSz6kP7rYLmyHPyYNLesi5t/aH1gfw==",
+      "dependencies": {
+        "@babel/runtime": "^7.2.0",
+        "prop-types": "^15.6.0",
+        "warning": "^4.0.1"
+      },
+      "peerDependencies": {
+        "react": "^16.3.0"
+      }
+    },
+    "node_modules/react-swipeable-views-utils/node_modules/react-event-listener/node_modules/@babel/runtime": {
+      "version": "7.16.7",
+      "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.16.7.tgz",
+      "integrity": "sha512-9E9FJowqAsytyOY6LG+1KuueckRL+aQW+mKvXRXnuFGyRAyepJPmEo9vgMfXUA6O9u3IeEdv9MAkppFcaQwogQ==",
+      "dependencies": {
+        "regenerator-runtime": "^0.13.4"
+      },
+      "engines": {
+        "node": ">=6.9.0"
+      }
+    },
+    "node_modules/react-swipeable-views-utils/node_modules/react-event-listener/node_modules/regenerator-runtime": {
+      "version": "0.13.9",
+      "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.9.tgz",
+      "integrity": "sha512-p3VT+cOEgxFsRRA9X4lkI1E+k2/CtnKtU4gcxyaCUreilL/vqI6CdZ3wxVUx3UOUg+gnUOQQcRI7BmSI656MYA=="
+    },
+    "node_modules/react-swipeable-views-utils/node_modules/regenerator-runtime": {
+      "version": "0.12.1",
+      "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.12.1.tgz",
+      "integrity": "sha512-odxIc1/vDlo4iZcfXqRYFj0vpXFNoGdKMAUieAlFYO6m/nl5e9KR/beGf41z4a1FI+aQgtjhuaSlDxQ0hmkrHg=="
+    },
+    "node_modules/react-swipeable-views/node_modules/@babel/runtime": {
+      "version": "7.0.0",
+      "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.0.0.tgz",
+      "integrity": "sha512-7hGhzlcmg01CvH1EHdSPVXYX1aJ8KCEyz6I9xYIi/asDtzBPMyMhVibhM/K6g/5qnKBwjZtp10bNZIEFTRW1MA==",
+      "dependencies": {
+        "regenerator-runtime": "^0.12.0"
+      }
+    },
+    "node_modules/react-swipeable-views/node_modules/regenerator-runtime": {
+      "version": "0.12.1",
+      "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.12.1.tgz",
+      "integrity": "sha512-odxIc1/vDlo4iZcfXqRYFj0vpXFNoGdKMAUieAlFYO6m/nl5e9KR/beGf41z4a1FI+aQgtjhuaSlDxQ0hmkrHg=="
+    },
     "node_modules/react-transition-group": {
       "version": "4.4.2",
       "resolved": "https://registry.npmjs.org/react-transition-group/-/react-transition-group-4.4.2.tgz",
@@ -16450,6 +16584,11 @@
       "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz",
       "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw=="
     },
+    "node_modules/shallow-equal": {
+      "version": "1.2.1",
+      "resolved": "https://registry.npmjs.org/shallow-equal/-/shallow-equal-1.2.1.tgz",
+      "integrity": "sha512-S4vJDjHHMBaiZuT9NPb616CSmLf618jawtv3sufLl6ivK8WocjAo58cXwbRV1cgqxH0Qbv+iUt6m05eqEa2IRA=="
+    },
     "node_modules/shebang-command": {
       "version": "2.0.0",
       "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz",
@@ -17860,6 +17999,14 @@
         "makeerror": "1.0.12"
       }
     },
+    "node_modules/warning": {
+      "version": "4.0.3",
+      "resolved": "https://registry.npmjs.org/warning/-/warning-4.0.3.tgz",
+      "integrity": "sha512-rpJyN222KWIvHJ/F53XSZv0Zl/accqHR8et1kpaMTD/fLCRxtV8iX8czMzY7sVZupTI3zcUTg8eycS2kNF9l6w==",
+      "dependencies": {
+        "loose-envify": "^1.0.0"
+      }
+    },
     "node_modules/watchpack": {
       "version": "2.3.1",
       "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.3.1.tgz",
@@ -27462,6 +27609,11 @@
         "object.assign": "^4.1.2"
       }
     },
+    "keycode": {
+      "version": "2.2.1",
+      "resolved": "https://registry.npmjs.org/keycode/-/keycode-2.2.1.tgz",
+      "integrity": "sha512-Rdgz9Hl9Iv4QKi8b0OlCRQEzp4AgVxyCtz5S/+VIHezDmrDhkp2N2TqBWOLz0/gbeREXOOiI9/4b8BY9uw2vFg=="
+    },
     "kind-of": {
       "version": "6.0.3",
       "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.3.tgz",
@@ -29648,6 +29800,121 @@
         "workbox-webpack-plugin": "^6.4.1"
       }
     },
+    "react-swipeable-views": {
+      "version": "0.14.0",
+      "resolved": "https://registry.npmjs.org/react-swipeable-views/-/react-swipeable-views-0.14.0.tgz",
+      "integrity": "sha512-wrTT6bi2nC3JbmyNAsPXffUXLn0DVT9SbbcFr36gKpbaCgEp7rX/OFxsu5hPc/NBsUhHyoSRGvwqJNNrWTwCww==",
+      "requires": {
+        "@babel/runtime": "7.0.0",
+        "prop-types": "^15.5.4",
+        "react-swipeable-views-core": "^0.14.0",
+        "react-swipeable-views-utils": "^0.14.0",
+        "warning": "^4.0.1"
+      },
+      "dependencies": {
+        "@babel/runtime": {
+          "version": "7.0.0",
+          "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.0.0.tgz",
+          "integrity": "sha512-7hGhzlcmg01CvH1EHdSPVXYX1aJ8KCEyz6I9xYIi/asDtzBPMyMhVibhM/K6g/5qnKBwjZtp10bNZIEFTRW1MA==",
+          "requires": {
+            "regenerator-runtime": "^0.12.0"
+          }
+        },
+        "regenerator-runtime": {
+          "version": "0.12.1",
+          "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.12.1.tgz",
+          "integrity": "sha512-odxIc1/vDlo4iZcfXqRYFj0vpXFNoGdKMAUieAlFYO6m/nl5e9KR/beGf41z4a1FI+aQgtjhuaSlDxQ0hmkrHg=="
+        }
+      }
+    },
+    "react-swipeable-views-core": {
+      "version": "0.14.0",
+      "resolved": "https://registry.npmjs.org/react-swipeable-views-core/-/react-swipeable-views-core-0.14.0.tgz",
+      "integrity": "sha512-0W/e9uPweNEOSPjmYtuKSC/SvKKg1sfo+WtPdnxeLF3t2L82h7jjszuOHz9C23fzkvLfdgkaOmcbAxE9w2GEjA==",
+      "requires": {
+        "@babel/runtime": "7.0.0",
+        "warning": "^4.0.1"
+      },
+      "dependencies": {
+        "@babel/runtime": {
+          "version": "7.0.0",
+          "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.0.0.tgz",
+          "integrity": "sha512-7hGhzlcmg01CvH1EHdSPVXYX1aJ8KCEyz6I9xYIi/asDtzBPMyMhVibhM/K6g/5qnKBwjZtp10bNZIEFTRW1MA==",
+          "requires": {
+            "regenerator-runtime": "^0.12.0"
+          }
+        },
+        "regenerator-runtime": {
+          "version": "0.12.1",
+          "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.12.1.tgz",
+          "integrity": "sha512-odxIc1/vDlo4iZcfXqRYFj0vpXFNoGdKMAUieAlFYO6m/nl5e9KR/beGf41z4a1FI+aQgtjhuaSlDxQ0hmkrHg=="
+        }
+      }
+    },
+    "react-swipeable-views-utils": {
+      "version": "0.14.0",
+      "resolved": "https://registry.npmjs.org/react-swipeable-views-utils/-/react-swipeable-views-utils-0.14.0.tgz",
+      "integrity": "sha512-W+fXBOsDqgFK1/g7MzRMVcDurp3LqO3ksC8UgInh2P/tKgb5DusuuB1geKHFc6o1wKl+4oyER4Zh3Lxmr8xbXA==",
+      "requires": {
+        "@babel/runtime": "7.0.0",
+        "keycode": "^2.1.7",
+        "prop-types": "^15.6.0",
+        "react-event-listener": "^0.6.0",
+        "react-swipeable-views-core": "^0.14.0",
+        "shallow-equal": "^1.2.1"
+      },
+      "dependencies": {
+        "@babel/runtime": {
+          "version": "7.0.0",
+          "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.0.0.tgz",
+          "integrity": "sha512-7hGhzlcmg01CvH1EHdSPVXYX1aJ8KCEyz6I9xYIi/asDtzBPMyMhVibhM/K6g/5qnKBwjZtp10bNZIEFTRW1MA==",
+          "requires": {
+            "regenerator-runtime": "^0.12.0"
+          }
+        },
+        "react": {
+          "version": "16.14.0",
+          "resolved": "https://registry.npmjs.org/react/-/react-16.14.0.tgz",
+          "integrity": "sha512-0X2CImDkJGApiAlcf0ODKIneSwBPhqJawOa5wCtKbu7ZECrmS26NvtSILynQ66cgkT/RJ4LidJOc3bUESwmU8g==",
+          "peer": true,
+          "requires": {
+            "loose-envify": "^1.1.0",
+            "object-assign": "^4.1.1",
+            "prop-types": "^15.6.2"
+          }
+        },
+        "react-event-listener": {
+          "version": "0.6.6",
+          "resolved": "https://registry.npmjs.org/react-event-listener/-/react-event-listener-0.6.6.tgz",
+          "integrity": "sha512-+hCNqfy7o9wvO6UgjqFmBzARJS7qrNoda0VqzvOuioEpoEXKutiKuv92dSz6kP7rYLmyHPyYNLesi5t/aH1gfw==",
+          "requires": {
+            "@babel/runtime": "^7.2.0",
+            "prop-types": "^15.6.0",
+            "warning": "^4.0.1"
+          },
+          "dependencies": {
+            "@babel/runtime": {
+              "version": "7.16.7",
+              "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.16.7.tgz",
+              "integrity": "sha512-9E9FJowqAsytyOY6LG+1KuueckRL+aQW+mKvXRXnuFGyRAyepJPmEo9vgMfXUA6O9u3IeEdv9MAkppFcaQwogQ==",
+              "requires": {
+                "regenerator-runtime": "^0.13.4"
+              }
+            },
+            "regenerator-runtime": {
+              "version": "0.13.9",
+              "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.13.9.tgz",
+              "integrity": "sha512-p3VT+cOEgxFsRRA9X4lkI1E+k2/CtnKtU4gcxyaCUreilL/vqI6CdZ3wxVUx3UOUg+gnUOQQcRI7BmSI656MYA=="
+            }
+          }
+        },
+        "regenerator-runtime": {
+          "version": "0.12.1",
+          "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.12.1.tgz",
+          "integrity": "sha512-odxIc1/vDlo4iZcfXqRYFj0vpXFNoGdKMAUieAlFYO6m/nl5e9KR/beGf41z4a1FI+aQgtjhuaSlDxQ0hmkrHg=="
+        }
+      }
+    },
     "react-transition-group": {
       "version": "4.4.2",
       "resolved": "https://registry.npmjs.org/react-transition-group/-/react-transition-group-4.4.2.tgz",
@@ -30503,6 +30770,11 @@
       "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz",
       "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw=="
     },
+    "shallow-equal": {
+      "version": "1.2.1",
+      "resolved": "https://registry.npmjs.org/shallow-equal/-/shallow-equal-1.2.1.tgz",
+      "integrity": "sha512-S4vJDjHHMBaiZuT9NPb616CSmLf618jawtv3sufLl6ivK8WocjAo58cXwbRV1cgqxH0Qbv+iUt6m05eqEa2IRA=="
+    },
     "shebang-command": {
       "version": "2.0.0",
       "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz",
@@ -31589,6 +31861,14 @@
         "makeerror": "1.0.12"
       }
     },
+    "warning": {
+      "version": "4.0.3",
+      "resolved": "https://registry.npmjs.org/warning/-/warning-4.0.3.tgz",
+      "integrity": "sha512-rpJyN222KWIvHJ/F53XSZv0Zl/accqHR8et1kpaMTD/fLCRxtV8iX8czMzY7sVZupTI3zcUTg8eycS2kNF9l6w==",
+      "requires": {
+        "loose-envify": "^1.0.0"
+      }
+    },
     "watchpack": {
       "version": "2.3.1",
       "resolved": "https://registry.npmjs.org/watchpack/-/watchpack-2.3.1.tgz",

+ 1 - 0
package.json

@@ -26,6 +26,7 @@
     "react-redux": "^7.2.6",
     "react-router-dom": "^5.3.0",
     "react-scripts": "5.0.0",
+    "react-swipeable-views": "^0.14.0",
     "redux": "^4.1.2",
     "redux-form": "^8.3.8",
     "redux-thunk": "^2.4.1",

+ 1 - 1
src/App.js

@@ -44,7 +44,7 @@ function App() {
                   <Route path="/basket" component={CartPage} />
                   <Route path="/wish-list" component={WishListPage} />
                   <Route path="/my-orders" component={MyOrdersPage} />
-                  <Route path="/profile" component={ProfilePage} />
+                  <CPRoute roles={["user", "admin"]} path="/profile" fallback='/my-account' component={ProfilePage} />
                   <CPRoute roles={["admin"]} path="/admin" fallback='/my-account' component={AdminPage} />
                   <Route path="*" component={Page404} />
               </Switch>

+ 1 - 0
src/actions/ActionCategory.js

@@ -29,6 +29,7 @@ export const actionFullRootCats = () =>
     }
 
 const actionCatById = (_id) => {
+    console.log(JSON.stringify([{_id}]))
     return actionPromise('catById', gql(`query catById($q: String){
             CategoryFindOne(query: $q){
                 _id goods {

+ 19 - 0
src/actions/ActionDashboard.js

@@ -0,0 +1,19 @@
+import {actionPromise} from "../reducers/PromiseReducer";
+import {gql} from "./PathDB";
+
+export const actionGetAllUser = (count=100) => {
+    console.log(`[{},${JSON.stringify({skip: [count], limit: [100]})}]`)
+    return actionPromise('allUsers', gql(`query allUsers($q: String){
+            UserFind(query: $q) {
+                _id
+                createdAt
+                login
+                nick 
+                acl 
+                avatar{
+                  _id url
+                }
+            }
+        }`), {q: `[{},${JSON.stringify({skip: [count], limit: [100]})}]`}
+    )
+}

+ 10 - 3
src/components/Header.jsx

@@ -14,7 +14,7 @@ import {backURL} from "../actions/PathDB";
 import userDefault from "../img/header/userDefault.png"
 
 const pages = ['catalog', 'about us', 'our team', 'faq', 'contact']
-const settingsDefaultUserAuth = ['Profile', 'Admin', 'Logout']
+const settingsDefaultUserAuth = ['Profile', 'Dashboard', 'Logout']
 
 const Header = ({user={}}) => {
     const [anchorElNav, setAnchorElNav] = useState(null);
@@ -148,8 +148,15 @@ const Header = ({user={}}) => {
                                 if (item === 'Logout') {
                                     return <CButtonLogOut key={'Logout'}/>
                                 }
-                                return <ItemAuth key={item.toString()} text={item}
-                                                 link={Array.from(item.toLowerCase()).map(i => i === ' ' ? '-' : i).join('')}/>
+                                else if(item === 'Dashboard'){
+                                    if (auth.payload?.sub?.acl[2]){
+                                        return <ItemAuth link={'admin'} text={'Dashboard'} key={'admin'}/>
+                                    }
+                                }
+                                else if(item !== 'Dashboard') {
+                                    return <ItemAuth key={item.toString()} text={item}
+                                                     link={Array.from(item.toLowerCase()).map(i => i === ' ' ? '-' : i).join('')}/>
+                                }
                             })}
                         </Menu>
                     </>

+ 125 - 5
src/pages/AdminPage.jsx

@@ -1,13 +1,133 @@
+import {Button, Container, useMediaQuery} from "@mui/material";
 import Breadcrumb from "../components/Breadcrumbs";
+import PropTypes from 'prop-types';
+import SwipeableViews from 'react-swipeable-views';
+import { useTheme } from '@mui/material/styles';
+import AppBar from '@mui/material/AppBar';
+import Tabs from '@mui/material/Tabs';
+import Tab from '@mui/material/Tab';
+import Typography from '@mui/material/Typography';
+import Box from '@mui/material/Box';
+import {useState} from "react";
+import PersonIcon from '@mui/icons-material/Person';
+import CategoryIcon from '@mui/icons-material/Category';
+import HistoryIcon from '@mui/icons-material/History';
 import {connect} from "react-redux";
-import Redirect from "react-router-dom/es/Redirect";
+import {actionGetAllUser} from "../actions/ActionDashboard";
 
-const AdminPage = ({auth}) => {
+const defaultTabs = [{icon: PersonIcon, text: 'clients'}, {icon: HistoryIcon, text: 'orders'}, {icon: CategoryIcon, text: 'categories'}]
+
+function TabPanel(props) {
+    const { children, value, index, ...other } = props;
+
+    return (
+        <div
+            role="tabpanel"
+            hidden={value !== index}
+            id={`full-width-tabpanel-${index}`}
+            aria-labelledby={`full-width-tab-${index}`}
+            {...other}
+        >
+            {value === index && (
+                <Box sx={{ p: 3 }}>
+                    <Typography>{children}</Typography>
+                </Box>
+            )}
+        </div>
+    );
+}
+TabPanel.propTypes = {
+    children: PropTypes.node,
+    index: PropTypes.number.isRequired,
+    value: PropTypes.number.isRequired,
+};
+function a11yProps(index) {
+    return {
+        id: `full-width-tab-${index}`,
+        'aria-controls': `full-width-tabpanel-${index}`,
+    };
+}
+
+const IconHeader = ({Icon}) => {
+    return <Icon/>
+}
+const Clients = ({users={}, getAllClients}) => {
+    // if (!users?.payload) getAllClients()
+    return (
+        <>
+            <Button onClick={() => {getAllClients()}}>click</Button>
+            {users?.payload && Object.entries(users.payload).length > 0 &&
+                Object.values(users.payload).map(item => {
+                    return <Typography>
+                        {item.login}
+                    </Typography>
+                })
+            }
+        </>
+    )
+}
+const CClients = connect(state => ({users: state.promise?.allUsers}), {getAllClients: actionGetAllUser})(Clients)
+
+const FullWidthTabs = () => {
+    const theme = useTheme();
+    const [value, setValue] = useState(0);
+
+    const handleChange = (event, newValue) => {
+        setValue(newValue);
+    };
+
+    const handleChangeIndex = (index) => {
+        setValue(index);
+    };
+
+    return (
+        <Box sx={{ bgcolor: '#fff', width: '100%', borderRadius: '20px', borderTopLeftRadius: '20px', borderTopRightRadius: '20px', overflow: 'hidden'}}>
+            <AppBar position="static" sx={{boxShadow: 'none'}}>
+                <Tabs
+                    value={value}
+                    onChange={handleChange}
+                    TabIndicatorProps={{style: {background:'#616161', height: '1px'}}}
+                    textColor="inherit"
+                    sx={{backgroundColor:'#fff', color: '#000'}}
+                    variant="fullWidth"
+                    aria-label="full width tabs example"
+                >
+                    {defaultTabs.map((item, index) =>
+                        <Tab key={index} sx={{borderBottom: '1px solid #dedede'}} label={<Box display='flex' alignItems='center'><IconHeader Icon={item.icon}/><Typography marginLeft='20px'>{item.text}</Typography></Box>} {...a11yProps(index)} />)
+                    }
+                </Tabs>
+            </AppBar>
+            <SwipeableViews
+                axis={theme.direction === 'rtl' ? 'x-reverse' : 'x'}
+                index={value}
+                onChangeIndex={handleChangeIndex}
+            >
+                <TabPanel value={value} index={0} dir={theme.direction}>
+                    <CClients/>
+                </TabPanel>
+                <TabPanel value={value} index={1} dir={theme.direction}>
+                    Item Two
+                </TabPanel>
+                <TabPanel value={value} index={2} dir={theme.direction}>
+                    Item Three
+                </TabPanel>
+            </SwipeableViews>
+        </Box>
+    );
+}
+
+const AdminPage = () => {
+    const matches = useMediaQuery('(max-width:768px)')
     return(
         <>
-            <Breadcrumb links={['admin']}/>
+            <Breadcrumb links={['admin']} title={'Dashboard'}/>
+            <main style={{backgroundColor: "#f3f3f3", padding: matches ? "20px 0" : "50px 0", minHeight:'300px'}}>
+                <Container maxWidth="lg">
+                    <FullWidthTabs/>
+                </Container>
+            </main>
         </>
     )
 }
-const CAdminPage = connect(state=>({auth: state.auth}))(AdminPage)
-export default CAdminPage
+
+export default AdminPage

+ 2 - 2
src/pages/CartPage.jsx

@@ -9,7 +9,7 @@ import imgUrl from "../img/not-found/3.png";
 import AddShoppingCartIcon from "@mui/icons-material/AddShoppingCart";
 import {SetCount} from "../components/SetCount";
 import {useEffect, useState} from "react";
-import {actionClearOrder} from "../reducers/PromiseReducer";
+import {actionClearPromise} from "../reducers/PromiseReducer";
 import CheckCircleOutlineIcon from '@mui/icons-material/CheckCircleOutline';
 
 const CartGoodLine = ({item, onCartRemove, onCardChange}) => {
@@ -186,5 +186,5 @@ const CartPage = ({order, cart, onCardChange, onCartClear, onCartRemove, onOrder
         </>
     )
 }
-const CCartPage = connect(state=>({cart: state.cart, order: state.promise?.order}), {onCardChange: actionCardChange, onCartClear: actionCardClear, onCartRemove: actionCardRemove, onOrderUpsert: ActionFullOrder, actionClearOrder: actionClearOrder})(CartPage)
+const CCartPage = connect(state=>({cart: state.cart, order: state.promise?.order}), {onCardChange: actionCardChange, onCartClear: actionCardClear, onCartRemove: actionCardRemove, onOrderUpsert: ActionFullOrder, actionClearOrder: actionClearPromise})(CartPage)
 export default CCartPage

+ 6 - 3
src/pages/MyAccountPage.jsx

@@ -14,11 +14,14 @@ import Link from "react-router-dom/es/Link";
 import {connect} from 'react-redux';
 import {actionFullLogin, actionFullRegister} from "../actions/ActionLogin";
 import Redirect from "react-router-dom/es/Redirect";
+import {actionClearPromise} from "../reducers/PromiseReducer";
 
-const MyAccountPage = ({auth, promise, user, onLogin, onRegister}) => {
+const MyAccountPage = ({auth, promise, user, onLogin, onRegister, onClear}) => {
     const matches = useMediaQuery('(max-width:899px)')
     const [status, setStatus] = useState('login')
-
+    if (auth?.payload && Object.keys(user).length !== 0){
+        onClear('login'); onClear('register');
+    }
     const Form = ({title, target, onClickEvent, children}) => {
         const matches2 = useMediaQuery('(max-width:450px)')
 
@@ -145,6 +148,6 @@ const MyAccountPage = ({auth, promise, user, onLogin, onRegister}) => {
         </>
     )
 }
-const CLoginForm = connect(state => ({auth: state.auth, promise: state.promise, user: state.user}), {onLogin: actionFullLogin, onRegister: actionFullRegister})(MyAccountPage)
+const CLoginForm = connect(state => ({auth: state.auth, promise: state.promise, user: state.user}), {onLogin: actionFullLogin, onRegister: actionFullRegister, onClear: actionClearPromise})(MyAccountPage)
 
 export default CLoginForm

+ 1 - 1
src/pages/ProfilePage.jsx

@@ -228,7 +228,7 @@ const ProfilePage = ({user = {}, promise, authLogOut, userLogOut}) => {
     }
 
     return (
-        Object.keys(user).length === 0 ? <Redirect to={'/my-account'}/> :
+        Object.keys(user).length > 1 &&
             <>
                 <Breadcrumb links={['Profile']}/>
                 <main style={{backgroundColor: "#f3f3f3", padding: matches ? "20px 0" : "50px 0"}}>

+ 1 - 1
src/reducers/PromiseReducer.js

@@ -17,7 +17,7 @@ export const PromiseReducer = (state = {}, { type, status, payload, error, name
 const actionPending = name => ({ type: 'PROMISE', status: 'PENDING', name })
 const actionResolved = (name, payload) => ({ type: 'PROMISE', status: 'RESOLVED', name, payload })
 const actionRejected = (name, error) => ({ type: 'PROMISE', status: 'REJECTED', name, error })
-export const actionClearOrder = (name) => ({ type: 'PROMISE_REMOVE', status: 'RESOLVED', name})
+export const actionClearPromise = (name) => ({ type: 'PROMISE_REMOVE', status: 'RESOLVED', name})
 
 export const actionPromise = (name, promise) =>
     async dispatch => {