1// Copyright (C) 2019 Storj Labs, Inc. 2// See LICENSE for copying information. 3 4import { StoreModule } from '@/store'; 5import { SortDirection } from '@/types/common'; 6import { 7 ProjectMember, 8 ProjectMemberCursor, 9 ProjectMemberOrderBy, 10 ProjectMembersApi, 11 ProjectMembersPage, 12} from '@/types/projectMembers'; 13 14export const PROJECT_MEMBER_MUTATIONS = { 15 FETCH: 'fetchProjectMembers', 16 TOGGLE_SELECTION: 'toggleSelection', 17 CLEAR_SELECTION: 'clearSelection', 18 CLEAR: 'clearProjectMembers', 19 CHANGE_SORT_ORDER: 'changeProjectMembersSortOrder', 20 CHANGE_SORT_ORDER_DIRECTION: 'changeProjectMembersSortOrderDirection', 21 SET_SEARCH_QUERY: 'setProjectMembersSearchQuery', 22 SET_PAGE: 'setProjectMembersPage', 23}; 24 25const { 26 FETCH, 27 TOGGLE_SELECTION, 28 CLEAR_SELECTION, 29 CLEAR, 30 CHANGE_SORT_ORDER, 31 CHANGE_SORT_ORDER_DIRECTION, 32 SET_SEARCH_QUERY, 33 SET_PAGE, 34} = PROJECT_MEMBER_MUTATIONS; 35 36export class ProjectMembersState { 37 public cursor: ProjectMemberCursor = new ProjectMemberCursor(); 38 public page: ProjectMembersPage = new ProjectMembersPage(); 39 public selectedProjectMembersEmails: string[] = []; 40} 41 42interface ProjectMembersContext { 43 state: ProjectMembersState 44 commit: (string, ...unknown) => void 45 rootGetters: { 46 selectedProject: { 47 id: string 48 } 49 } 50} 51 52export function makeProjectMembersModule(api: ProjectMembersApi): StoreModule<ProjectMembersState, ProjectMembersContext> { 53 return { 54 state: new ProjectMembersState(), 55 mutations: { 56 [FETCH](state: ProjectMembersState, page: ProjectMembersPage) { 57 state.page = page; 58 state.page.projectMembers = state.page.projectMembers.map(member => { 59 if (state.selectedProjectMembersEmails.includes(member.user.email)) { 60 member.isSelected = true; 61 } 62 63 return member; 64 }); 65 }, 66 [SET_PAGE](state: ProjectMembersState, page: number) { 67 state.cursor.page = page; 68 }, 69 [SET_SEARCH_QUERY](state: ProjectMembersState, search: string) { 70 state.cursor.search = search; 71 }, 72 [CHANGE_SORT_ORDER](state: ProjectMembersState, order: ProjectMemberOrderBy) { 73 state.cursor.order = order; 74 }, 75 [CHANGE_SORT_ORDER_DIRECTION](state: ProjectMembersState, direction: SortDirection) { 76 state.cursor.orderDirection = direction; 77 }, 78 [CLEAR](state: ProjectMembersState) { 79 state.cursor = new ProjectMemberCursor(); 80 state.page = new ProjectMembersPage(); 81 state.selectedProjectMembersEmails = []; 82 }, 83 [TOGGLE_SELECTION](state: ProjectMembersState, projectMember: ProjectMember) { 84 if (!state.selectedProjectMembersEmails.includes(projectMember.user.email)) { 85 projectMember.isSelected = true; 86 state.selectedProjectMembersEmails.push(projectMember.user.email); 87 88 return; 89 } 90 91 projectMember.isSelected = false; 92 state.selectedProjectMembersEmails = state.selectedProjectMembersEmails.filter(projectMemberEmail => { 93 return projectMemberEmail !== projectMember.user.email; 94 }); 95 }, 96 [CLEAR_SELECTION](state: ProjectMembersState) { 97 state.selectedProjectMembersEmails = []; 98 state.page.projectMembers = state.page.projectMembers.map((projectMember: ProjectMember) => { 99 projectMember.isSelected = false; 100 101 return projectMember; 102 }); 103 }, 104 }, 105 actions: { 106 addProjectMembers: async function ({rootGetters}: ProjectMembersContext, emails: string[]): Promise<void> { 107 const projectId = rootGetters.selectedProject.id; 108 109 await api.add(projectId, emails); 110 }, 111 deleteProjectMembers: async function ({rootGetters, state, commit}: ProjectMembersContext): Promise<void> { 112 const projectId = rootGetters.selectedProject.id; 113 114 await api.delete(projectId, state.selectedProjectMembersEmails); 115 116 commit(CLEAR_SELECTION); 117 }, 118 fetchProjectMembers: async function ({commit, rootGetters, state}: ProjectMembersContext, page: number): Promise<ProjectMembersPage> { 119 const projectID = rootGetters.selectedProject.id; 120 121 commit(SET_PAGE, page); 122 123 const projectMembersPage: ProjectMembersPage = await api.get(projectID, state.cursor); 124 125 commit(FETCH, projectMembersPage); 126 127 return projectMembersPage; 128 }, 129 setProjectMembersSearchQuery: function ({commit}: ProjectMembersContext, search: string) { 130 commit(SET_SEARCH_QUERY, search); 131 }, 132 setProjectMembersSortingBy: function ({commit}: ProjectMembersContext, order: ProjectMemberOrderBy) { 133 commit(CHANGE_SORT_ORDER, order); 134 }, 135 setProjectMembersSortingDirection: function ({commit}: ProjectMembersContext, direction: SortDirection) { 136 commit(CHANGE_SORT_ORDER_DIRECTION, direction); 137 }, 138 clearProjectMembers: function ({commit}: ProjectMembersContext) { 139 commit(CLEAR); 140 commit(CLEAR_SELECTION); 141 }, 142 toggleProjectMemberSelection: function ({commit}: ProjectMembersContext, projectMember: ProjectMember) { 143 commit(TOGGLE_SELECTION, projectMember); 144 }, 145 clearProjectMemberSelection: function ({commit}: ProjectMembersContext) { 146 commit(CLEAR_SELECTION); 147 }, 148 }, 149 getters: { 150 selectedProjectMembers: (state: ProjectMembersState) => 151 state.page.projectMembers.filter((member: ProjectMember) => 152 state.selectedProjectMembersEmails.includes(member.user.email)), 153 }, 154 }; 155} 156