web/satellite: migrate ProjectMemberListItem component to use SFC composition api
Change-Id: I232f06b5828c9f93917070621de66463c479d8fe
This commit is contained in:
parent
d0620405e5
commit
a5d9caa5a5
@ -13,33 +13,34 @@
|
|||||||
/>
|
/>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script lang="ts">
|
<script setup lang="ts">
|
||||||
import { Component, Prop } from 'vue-property-decorator';
|
import { computed } from 'vue';
|
||||||
|
|
||||||
import { ProjectMember } from '@/types/projectMembers';
|
import { ProjectMember } from '@/types/projectMembers';
|
||||||
|
import { useResize } from '@/composables/resize';
|
||||||
|
import { useStore } from '@/utils/hooks';
|
||||||
|
|
||||||
import TableItem from '@/components/common/TableItem.vue';
|
import TableItem from '@/components/common/TableItem.vue';
|
||||||
import Resizable from '@/components/common/Resizable.vue';
|
|
||||||
|
|
||||||
// @vue/component
|
const { isMobile, isTablet } = useResize();
|
||||||
@Component({
|
const store = useStore();
|
||||||
components: { TableItem },
|
|
||||||
})
|
|
||||||
export default class ProjectMemberListItem extends Resizable {
|
|
||||||
@Prop({ default: new ProjectMember('', '', '', new Date(), '') })
|
|
||||||
public itemData: ProjectMember;
|
|
||||||
|
|
||||||
public get isProjectOwner(): boolean {
|
const props = withDefaults(defineProps<{
|
||||||
return this.itemData.user.id === this.$store.getters.selectedProject.ownerId;
|
itemData: ProjectMember;
|
||||||
}
|
}>(), {
|
||||||
|
itemData: () => new ProjectMember('', '', '', new Date(), ''),
|
||||||
|
});
|
||||||
|
|
||||||
public get itemToRender(): { [key: string]: string | string[] } {
|
const isProjectOwner = computed((): boolean => {
|
||||||
if (!this.isMobile && !this.isTablet) return { name: this.itemData.name, date: this.itemData.localDate(), email: this.itemData.email };
|
return props.itemData.user.id === store.getters.selectedProject.ownerId;
|
||||||
|
});
|
||||||
|
|
||||||
// TODO: change after adding actions button to list item
|
const itemToRender = computed((): { [key: string]: string | string[] } => {
|
||||||
return { name: this.itemData.name, email: this.itemData.email };
|
if (!isMobile.value && !isTablet.value) return { name: props.itemData.name, date: props.itemData.localDate(), email: props.itemData.email };
|
||||||
}
|
|
||||||
}
|
// TODO: change after adding actions button to list item
|
||||||
|
return { name: props.itemData.name, email: props.itemData.email };
|
||||||
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style scoped lang="scss">
|
<style scoped lang="scss">
|
||||||
|
@ -0,0 +1,165 @@
|
|||||||
|
// Copyright (C) 2019 Storj Labs, Inc.
|
||||||
|
// See LICENSE for copying information.
|
||||||
|
|
||||||
|
import Vuex from 'vuex';
|
||||||
|
import { createLocalVue, shallowMount } from '@vue/test-utils';
|
||||||
|
|
||||||
|
import { ProjectMembersApiMock } from 'tests/unit/mock/api/projectMembers';
|
||||||
|
import { ProjectsApiMock } from 'tests/unit/mock/api/projects';
|
||||||
|
import { FrontendConfigApiMock } from 'tests/unit/mock/api/config';
|
||||||
|
import { makeAppStateModule } from '@/store/modules/appState';
|
||||||
|
import { makeProjectMembersModule, PROJECT_MEMBER_MUTATIONS } from '@/store/modules/projectMembers';
|
||||||
|
import { makeProjectsModule } from '@/store/modules/projects';
|
||||||
|
import { ProjectMember, ProjectMembersPage } from '@/types/projectMembers';
|
||||||
|
import { Project } from '@/types/projects';
|
||||||
|
|
||||||
|
import ProjectMembersArea from '@/components/team/ProjectMembersArea.vue';
|
||||||
|
|
||||||
|
const localVue = createLocalVue();
|
||||||
|
localVue.use(Vuex);
|
||||||
|
|
||||||
|
const appStateModule = makeAppStateModule(new FrontendConfigApiMock());
|
||||||
|
const pmApi = new ProjectMembersApiMock();
|
||||||
|
const projectMembersModule = makeProjectMembersModule(pmApi);
|
||||||
|
const projectsApi = new ProjectsApiMock();
|
||||||
|
const projectsModule = makeProjectsModule(projectsApi);
|
||||||
|
const { FETCH } = PROJECT_MEMBER_MUTATIONS;
|
||||||
|
const store = new Vuex.Store({ modules: { projectsModule, projectMembersModule, appStateModule } });
|
||||||
|
|
||||||
|
describe('ProjectMembersArea.vue', () => {
|
||||||
|
const project = new Project('id', 'projectName', 'projectDescription', 'test', 'testOwnerId', true);
|
||||||
|
projectsApi.setMockProjects([project]);
|
||||||
|
const date = new Date(0);
|
||||||
|
const projectMember1 = new ProjectMember('testFullName1', 'testShortName1', 'test1@example.com', date, '1');
|
||||||
|
const projectMember2 = new ProjectMember('testFullName2', 'testShortName2', 'test2@example.com', date, '2');
|
||||||
|
|
||||||
|
const testProjectMembersPage = new ProjectMembersPage();
|
||||||
|
testProjectMembersPage.projectMembers = [projectMember1];
|
||||||
|
testProjectMembersPage.totalCount = 1;
|
||||||
|
testProjectMembersPage.pageCount = 1;
|
||||||
|
|
||||||
|
pmApi.setMockPage(testProjectMembersPage);
|
||||||
|
|
||||||
|
it('renders correctly', async (): Promise<void> => {
|
||||||
|
const wrapper = shallowMount<ProjectMembersArea>(ProjectMembersArea, {
|
||||||
|
store,
|
||||||
|
localVue,
|
||||||
|
});
|
||||||
|
|
||||||
|
await wrapper.setData({ areMembersFetching: false });
|
||||||
|
|
||||||
|
expect(wrapper).toMatchSnapshot();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('function fetchProjectMembers works correctly', () => {
|
||||||
|
store.commit(FETCH, testProjectMembersPage);
|
||||||
|
|
||||||
|
const wrapper = shallowMount<ProjectMembersArea>(ProjectMembersArea, {
|
||||||
|
store,
|
||||||
|
localVue,
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(wrapper.vm.projectMembers).toEqual([projectMember1]);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('team area renders correctly', async (): Promise<void> => {
|
||||||
|
store.commit(FETCH, testProjectMembersPage);
|
||||||
|
|
||||||
|
const wrapper = shallowMount<ProjectMembersArea>(ProjectMembersArea, {
|
||||||
|
store,
|
||||||
|
localVue,
|
||||||
|
});
|
||||||
|
|
||||||
|
await wrapper.setData({ areMembersFetching: false });
|
||||||
|
|
||||||
|
const emptySearchResultArea = wrapper.findAll('.team-area__empty-search-result-area');
|
||||||
|
expect(emptySearchResultArea.length).toBe(0);
|
||||||
|
|
||||||
|
const teamContainer = wrapper.findAll('.team-area__table');
|
||||||
|
expect(teamContainer.length).toBe(1);
|
||||||
|
|
||||||
|
expect(wrapper).toMatchSnapshot();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('action on toggle works correctly', () => {
|
||||||
|
store.commit(FETCH, testProjectMembersPage);
|
||||||
|
|
||||||
|
const wrapper = shallowMount<ProjectMembersArea>(ProjectMembersArea, {
|
||||||
|
store,
|
||||||
|
localVue,
|
||||||
|
});
|
||||||
|
|
||||||
|
wrapper.vm.onMemberCheckChange(projectMember1);
|
||||||
|
|
||||||
|
expect(store.getters.selectedProjectMembers.length).toBe(1);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('clear selection works correctly', () => {
|
||||||
|
const date = new Date(0);
|
||||||
|
const projectMember3 = new ProjectMember('testFullName1', 'testShortName1', 'test1@example.com', date, '1');
|
||||||
|
projectMember3.isSelected = true;
|
||||||
|
const testProjectMembersPage = new ProjectMembersPage();
|
||||||
|
testProjectMembersPage.projectMembers = [projectMember3];
|
||||||
|
testProjectMembersPage.totalCount = 1;
|
||||||
|
testProjectMembersPage.pageCount = 1;
|
||||||
|
store.commit(FETCH, testProjectMembersPage);
|
||||||
|
|
||||||
|
const wrapper = shallowMount<ProjectMembersArea>(ProjectMembersArea, {
|
||||||
|
store,
|
||||||
|
localVue,
|
||||||
|
});
|
||||||
|
|
||||||
|
wrapper.vm.onMemberCheckChange(projectMember3);
|
||||||
|
|
||||||
|
expect(store.getters.selectedProjectMembers.length).toBe(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('Reversing list order triggers rerender', () => {
|
||||||
|
const testPage = new ProjectMembersPage();
|
||||||
|
testPage.projectMembers = [projectMember1, projectMember2];
|
||||||
|
testPage.totalCount = 2;
|
||||||
|
testPage.pageCount = 1;
|
||||||
|
pmApi.setMockPage(testPage);
|
||||||
|
|
||||||
|
store.commit(FETCH, testPage);
|
||||||
|
|
||||||
|
const wrapper = shallowMount<ProjectMembersArea>(ProjectMembersArea, {
|
||||||
|
store,
|
||||||
|
localVue,
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(wrapper.vm.projectMembers[0].user.id).toBe(projectMember1.user.id);
|
||||||
|
|
||||||
|
testProjectMembersPage.projectMembers = [projectMember2, projectMember1];
|
||||||
|
|
||||||
|
store.commit(FETCH, testProjectMembersPage);
|
||||||
|
|
||||||
|
expect(wrapper.vm.projectMembers[0].user.id).toBe(projectMember2.user.id);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('empty search result area render correctly', async (): Promise<void> => {
|
||||||
|
const testPage1 = new ProjectMembersPage();
|
||||||
|
testPage1.projectMembers = [];
|
||||||
|
testPage1.totalCount = 0;
|
||||||
|
testPage1.pageCount = 0;
|
||||||
|
testPage1.search = 'testSearch';
|
||||||
|
pmApi.setMockPage(testPage1);
|
||||||
|
|
||||||
|
store.commit(FETCH, testPage1);
|
||||||
|
|
||||||
|
const wrapper = shallowMount<ProjectMembersArea>(ProjectMembersArea, {
|
||||||
|
store,
|
||||||
|
localVue,
|
||||||
|
});
|
||||||
|
|
||||||
|
await wrapper.setData({ areMembersFetching: false });
|
||||||
|
|
||||||
|
const emptySearchResultArea = wrapper.findAll('.team-area__empty-search-result-area');
|
||||||
|
expect(emptySearchResultArea.length).toBe(1);
|
||||||
|
|
||||||
|
const teamContainer = wrapper.findAll('.team-area__container');
|
||||||
|
expect(teamContainer.length).toBe(0);
|
||||||
|
|
||||||
|
expect(wrapper).toMatchSnapshot();
|
||||||
|
});
|
||||||
|
});
|
Loading…
Reference in New Issue
Block a user