Skip to content

Commit 7ae4f3c

Browse files
m0ksemasvae
andauthored
Projects page (#985)
* fix: show vuestic-ui types * raw: init users page * chore: update vuestic-ui and remove hotfixes * fix: satiesfies eslint error * fix: statiesfies prettier warning * chore: apply prettier fixes * feat(users): finish users page * chore: small refactoring * chore: fix vue warning * chore(users): remove extra stores and components * feat(users): add confirmation window and toasts. * fix(users): add active checkbox to edit form * fix(users): blob avatar rendering * chore: remove todo * chore: eslint fixes * chore: improve users page * init projects page * feat(projects): finish projects page * fix: typo * chore(users): more meaningful projects column * chore: fix ts issues * fix: date format in project creation * chore: add ProjectStatusBadge component and update UsersPage and ProjectsTable * chore: refactor projects. allow to select project in user edit form. * fix: correct track-by for selects * chore: eslint fix --------- Co-authored-by: Yauheni Prakopchyk <[email protected]>
1 parent a0f15b4 commit 7ae4f3c

27 files changed

+1665
-7
lines changed

package.json

+1
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
"@fortawesome/fontawesome-free": "^6.1.1",
2727
"@gtm-support/vue-gtm": "^2.0.0",
2828
"@vuestic/tailwind": "^0.1.3",
29+
"@vueuse/core": "^10.6.1",
2930
"axios": "^1.6.1",
3031
"chart.js": "^3.8.0",
3132
"epic-spinners": "^2.0.0",

src/components/sidebar/NavigationRoutes.ts

+8
Original file line numberDiff line numberDiff line change
@@ -229,6 +229,14 @@ export default {
229229
name: 'pricing-plans',
230230
displayName: 'menu.pricing-plans',
231231
},
232+
{
233+
name: 'users',
234+
displayName: 'menu.users',
235+
},
236+
{
237+
name: 'projects',
238+
displayName: 'menu.projects',
239+
},
232240
{
233241
name: 'settings',
234242
displayName: 'menu.settings',

src/data/pages/projects-db.json

+82
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
[
2+
{
3+
"id": 0,
4+
"project_name": "A Vuestic",
5+
"project_owner": 13,
6+
"team": [13, 5, 28, 14, 17, 28, 23, 11, 16, 19, 12, 28, 11],
7+
"status": "in progress",
8+
"creation_date": "20 Nov 2023"
9+
},
10+
{
11+
"id": 1,
12+
"project_name": "Mood board",
13+
"project_owner": 28,
14+
"team": [28, 10, 12, 28, 14, 27, 5, 4, 8, 23, 19, 18, 24, 11, 18, 12, 28],
15+
"status": "important",
16+
"creation_date": "16 Oct 2023"
17+
},
18+
{
19+
"id": 2,
20+
"project_name": "J Jenkins",
21+
"project_owner": 3,
22+
"team": [3, 21, 7, 19, 4, 4, 7, 24],
23+
"status": "important",
24+
"creation_date": "1 Oct 2023"
25+
},
26+
{
27+
"id": 3,
28+
"project_name": "S Springfield media",
29+
"project_owner": 17,
30+
"team": [17, 25, 21, 9, 18, 12, 15, 0, 7, 2, 7],
31+
"status": "important",
32+
"creation_date": "19 Sept 2023"
33+
},
34+
{
35+
"id": 4,
36+
"project_name": "G Galileo",
37+
"project_owner": 7,
38+
"team": [7, 1, 28, 19, 3],
39+
"status": "completed",
40+
"creation_date": "23 Sept 2023"
41+
},
42+
{
43+
"id": 5,
44+
"project_name": "O Website Redesign",
45+
"project_owner": 24,
46+
"team": [24, 19, 1, 8, 9],
47+
"status": "completed",
48+
"creation_date": "9 Sept 2023"
49+
},
50+
{
51+
"id": 6,
52+
"project_name": "U Website Redesign",
53+
"project_owner": 15,
54+
"team": [15, 16, 8, 6, 11, 21, 3, 20],
55+
"status": "archived",
56+
"creation_date": "17 Aug 2023"
57+
},
58+
{
59+
"id": 7,
60+
"project_name": "L Complete Product Redesign",
61+
"project_owner": 25,
62+
"team": [25, 18, 24, 13, 5, 3, 4, 16, 25, 12, 18, 9, 22],
63+
"status": "completed",
64+
"creation_date": "11 Aug 2023"
65+
},
66+
{
67+
"id": 8,
68+
"project_name": "Design Team Project",
69+
"project_owner": 17,
70+
"team": [17, 6, 21, 17, 7, 6, 14, 13, 27, 7, 20],
71+
"status": "archived",
72+
"creation_date": "9 Aug 2023"
73+
},
74+
{
75+
"id": 9,
76+
"project_name": "R Regular logistics",
77+
"project_owner": 3,
78+
"team": [3, 26, 8, 15, 21, 23, 18, 11, 22, 6, 20, 9],
79+
"status": "archived",
80+
"creation_date": "2 Aug 2023"
81+
}
82+
]

src/data/pages/projects.ts

+82
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
import { sleep } from '../../services/utils'
2+
import projectsDb from './projects-db.json'
3+
import usersDb from './users-db.json'
4+
5+
// Simulate API calls
6+
export type Pagination = {
7+
page: number
8+
perPage: number
9+
total: number
10+
}
11+
12+
export type Sorting = {
13+
sortBy: keyof (typeof projectsDb)[number] | undefined
14+
sortingOrder: 'asc' | 'desc' | null
15+
}
16+
17+
export const getProjects = async (options: Sorting & Pagination) => {
18+
await sleep(1000)
19+
20+
const projects = projectsDb.map((project) => ({
21+
...project,
22+
project_owner: usersDb.find((user) => user.id === project.project_owner)! as (typeof usersDb)[number],
23+
team: usersDb.filter((user) => project.team.includes(user.id)) as (typeof usersDb)[number][],
24+
}))
25+
26+
if (options.sortBy && options.sortingOrder) {
27+
projects.sort((a, b) => {
28+
if (a[options.sortBy!] < b[options.sortBy!]) {
29+
return options.sortingOrder === 'asc' ? -1 : 1
30+
}
31+
if (a[options.sortBy!] > b[options.sortBy!]) {
32+
return options.sortingOrder === 'asc' ? 1 : -1
33+
}
34+
return 0
35+
})
36+
}
37+
38+
return {
39+
data: projects,
40+
pagination: {
41+
page: options.page,
42+
perPage: options.perPage,
43+
total: projectsDb.length,
44+
},
45+
}
46+
}
47+
48+
export const addProject = async (project: Omit<(typeof projectsDb)[number], 'id' | 'creation_date'>) => {
49+
await sleep(1000)
50+
51+
const newProject = {
52+
...project,
53+
id: projectsDb.length + 1,
54+
creation_date: new Date().toLocaleDateString('gb', { day: 'numeric', month: 'short', year: 'numeric' }),
55+
}
56+
57+
projectsDb.push(newProject)
58+
59+
return {
60+
...newProject,
61+
project_owner: usersDb.find((user) => user.id === project.project_owner)! as (typeof usersDb)[number],
62+
team: usersDb.filter((user) => project.team.includes(user.id)) as (typeof usersDb)[number][],
63+
}
64+
}
65+
66+
export const updateProject = async (project: (typeof projectsDb)[number]) => {
67+
await sleep(1000)
68+
69+
const index = projectsDb.findIndex((p) => p.id === project.id)
70+
projectsDb[index] = project
71+
72+
return project
73+
}
74+
75+
export const removeProject = async (project: (typeof projectsDb)[number]) => {
76+
await sleep(1000)
77+
78+
const index = projectsDb.findIndex((p) => p.id === project.id)
79+
projectsDb.splice(index, 1)
80+
81+
return project
82+
}

0 commit comments

Comments
 (0)