Skip to content
Snippets Groups Projects
Commit 9ab342bc authored by robban64's avatar robban64
Browse files

add: statistics route

parent d3425300
No related branches found
No related tags found
1 merge request!80Resolve "Dashboard api calls"
import axios from 'axios'
import { AppDispatch } from './../store'
import Types from './types'
export const getStatistics = () => async (dispatch: AppDispatch) => {
await axios
.get('/misc/statistics')
.then((res) => {
dispatch({
type: Types.SET_STATISTICS,
payload: res.data,
})
})
.catch((err) => console.log(err))
}
...@@ -29,4 +29,5 @@ export default { ...@@ -29,4 +29,5 @@ export default {
SET_CITIES_TOTAL: 'SET_CITIES_TOTAL', SET_CITIES_TOTAL: 'SET_CITIES_TOTAL',
SET_CITIES_COUNT: 'SET_CITIES_COUNT', SET_CITIES_COUNT: 'SET_CITIES_COUNT',
SET_TYPES: 'SET_TYPES', SET_TYPES: 'SET_TYPES',
SET_STATISTICS: 'SET_STATISTICS',
} }
...@@ -20,6 +20,7 @@ import React, { useEffect } from 'react' ...@@ -20,6 +20,7 @@ import React, { useEffect } from 'react'
import { Link, Route, Switch, useRouteMatch } from 'react-router-dom' import { Link, Route, Switch, useRouteMatch } from 'react-router-dom'
import { getCities } from '../../actions/cities' import { getCities } from '../../actions/cities'
import { getRoles } from '../../actions/roles' import { getRoles } from '../../actions/roles'
import { getStatistics } from '../../actions/statistics'
import { getTypes } from '../../actions/typesAction' import { getTypes } from '../../actions/typesAction'
import { logoutUser } from '../../actions/user' import { logoutUser } from '../../actions/user'
import { useAppDispatch, useAppSelector } from '../../hooks' import { useAppDispatch, useAppSelector } from '../../hooks'
...@@ -71,6 +72,7 @@ const AdminView: React.FC = () => { ...@@ -71,6 +72,7 @@ const AdminView: React.FC = () => {
dispatch(getCities()) dispatch(getCities())
dispatch(getRoles()) dispatch(getRoles())
dispatch(getTypes()) dispatch(getTypes())
dispatch(getStatistics())
}, []) }, [])
const menuAdminItems = [ const menuAdminItems = [
......
import { Box, Typography } from '@material-ui/core' import { Box, Typography } from '@material-ui/core'
import React, { useEffect } from 'react' import React from 'react'
import { getCompetitions } from '../../../../actions/competitions' import { useAppSelector } from '../../../../hooks'
import { useAppDispatch, useAppSelector } from '../../../../hooks'
const NumberOfCompetitions: React.FC = () => { const NumberOfCompetitions: React.FC = () => {
const competitions = useAppSelector((state) => state.competitions.competitions) const competitions = useAppSelector((state) => state.statistics.competitions)
const dispatch = useAppDispatch()
const handleCount = () => { const handleCount = () => {
if (competitions.length >= 1000000) { if (competitions >= 1000000) {
;<div>{competitions.length / 1000000 + 'M'}</div> ;<div>{competitions / 1000000 + 'M'}</div>
} else if (competitions.length >= 1000) { } else if (competitions >= 1000) {
;<div>{competitions.length / 1000 + 'K'}</div> ;<div>{competitions / 1000 + 'K'}</div>
} }
return <div>{competitions.length}</div> return <div>{competitions}</div>
} }
useEffect(() => {
dispatch(getCompetitions())
}, [])
return ( return (
<div> <div>
<Box width="100%" height="100%"> <Box width="100%" height="100%">
......
...@@ -4,7 +4,7 @@ import { getCities } from '../../../../actions/cities' ...@@ -4,7 +4,7 @@ import { getCities } from '../../../../actions/cities'
import { useAppDispatch, useAppSelector } from '../../../../hooks' import { useAppDispatch, useAppSelector } from '../../../../hooks'
const NumberOfRegions: React.FC = () => { const NumberOfRegions: React.FC = () => {
const regions = useAppSelector((state) => state.cities.total) const regions = useAppSelector((state) => state.statistics.regions)
const dispatch = useAppDispatch() const dispatch = useAppDispatch()
const handleCount = () => { const handleCount = () => {
......
...@@ -4,7 +4,7 @@ import { getSearchUsers } from '../../../../actions/searchUser' ...@@ -4,7 +4,7 @@ import { getSearchUsers } from '../../../../actions/searchUser'
import { useAppDispatch, useAppSelector } from '../../../../hooks' import { useAppDispatch, useAppSelector } from '../../../../hooks'
const NumberOfUsers: React.FC = () => { const NumberOfUsers: React.FC = () => {
const usersTotal = useAppSelector((state) => state.searchUsers.total) const usersTotal = useAppSelector((state) => state.statistics.users)
const dispatch = useAppDispatch() const dispatch = useAppDispatch()
const handleCount = () => { const handleCount = () => {
......
...@@ -7,6 +7,7 @@ import editorReducer from './editorReducer' ...@@ -7,6 +7,7 @@ import editorReducer from './editorReducer'
import presentationReducer from './presentationReducer' import presentationReducer from './presentationReducer'
import rolesReducer from './rolesReducer' import rolesReducer from './rolesReducer'
import searchUserReducer from './searchUserReducer' import searchUserReducer from './searchUserReducer'
import statisticsReducer from './statisticsReducer'
import typesReducer from './typesReducer' import typesReducer from './typesReducer'
import uiReducer from './uiReducer' import uiReducer from './uiReducer'
import userReducer from './userReducer' import userReducer from './userReducer'
...@@ -22,5 +23,6 @@ const allReducers = combineReducers({ ...@@ -22,5 +23,6 @@ const allReducers = combineReducers({
roles: rolesReducer, roles: rolesReducer,
searchUsers: searchUserReducer, searchUsers: searchUserReducer,
types: typesReducer, types: typesReducer,
statistics: statisticsReducer,
}) })
export default allReducers export default allReducers
import { AnyAction } from 'redux'
import Types from '../actions/types'
interface StatisticsState {
users: number
competitions: number
regions: number
}
const initialState: StatisticsState = {
users: 0,
competitions: 0,
regions: 0,
}
export default function (state = initialState, action: AnyAction) {
switch (action.type) {
case Types.SET_STATISTICS:
state = action.payload as StatisticsState
return state
default:
return state
}
}
import app.database.controller as dbc import app.database.controller as dbc
from app.apis import check_jwt, item_response, list_response from app.apis import check_jwt, item_response, list_response
from app.core import http_codes
from app.core.dto import MiscDTO from app.core.dto import MiscDTO
from app.database.models import City, ComponentType, MediaType, QuestionType, Role, ViewType from app.database.models import City, Competition, ComponentType, MediaType, QuestionType, Role, User, ViewType
from flask_jwt_extended import jwt_required from flask_jwt_extended import jwt_required
from flask_restx import Resource, reqparse from flask_restx import Resource, reqparse
...@@ -72,3 +73,13 @@ class Cities(Resource): ...@@ -72,3 +73,13 @@ class Cities(Resource):
dbc.delete.default(item) dbc.delete.default(item)
items = dbc.get.all(City) items = dbc.get.all(City)
return list_response(city_schema.dump(items)) return list_response(city_schema.dump(items))
@api.route("/statistics")
class Statistics(Resource):
@check_jwt(editor=True)
def get(self):
user_count = User.query.count()
competition_count = Competition.query.count()
region_count = City.query.count()
return {"users": user_count, "competitions": competition_count, "regions": region_count}, http_codes.OK
import app.core.http_codes as codes
import app.database.controller as dbc
from app.apis import check_jwt, item_response, list_response
from app.core.dto import UserDTO
from app.core.parsers import user_parser, user_search_parser
from app.database.models import City, Competition, User
from flask import request
from flask_jwt_extended import get_jwt_identity, jwt_required
from flask_restx import Namespace, Resource
api = Namespace("statistics")
@api.route("/")
class Statistics(Resource):
@check_jwt(editor=True)
def get(self):
user_count = User.query.count()
competition_count = Competition.query.count()
region_count = City.query.count()
return {"users": user_count, "competitions": competition_count, "regions": region_count}, codes.OK
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment