Refactor markup and specs

This commit is contained in:
fayazara 2022-10-10 19:31:01 +05:30
parent 56bb2a9121
commit 47d8c9335d
11 changed files with 267 additions and 101 deletions

View file

@ -0,0 +1,71 @@
export const teams = [
{
id: 1,
name: '⚙️ sales team',
description: 'This is our internal sales team',
allow_auto_assign: true,
account_id: 1,
is_member: true,
},
{
id: 2,
name: '🤷‍♂️ fayaz',
description: 'Test',
allow_auto_assign: true,
account_id: 1,
is_member: true,
},
{
id: 3,
name: '🇮🇳 apac sales',
description: 'Sales team for France Territory',
allow_auto_assign: true,
account_id: 1,
is_member: true,
},
];
export const labels = [
{
id: 6,
title: 'sales',
description: 'sales team',
color: '#8EA20F',
show_on_sidebar: true,
},
{
id: 2,
title: 'billing',
description: 'billing',
color: '#4077DA',
show_on_sidebar: true,
},
{
id: 1,
title: 'snoozed',
description: 'Items marked for later',
color: '#D12F42',
show_on_sidebar: true,
},
{
id: 5,
title: 'mobile-app',
description: 'tech team',
color: '#2DB1CC',
show_on_sidebar: true,
},
{
id: 14,
title: 'human-resources-department-with-long-title',
description: 'Test',
color: '#FF6E09',
show_on_sidebar: true,
},
{
id: 22,
title: 'priority',
description: 'For important sales leads',
color: '#7E7CED',
show_on_sidebar: true,
},
];

View file

@ -0,0 +1,53 @@
import { MACRO_ACTION_TYPES } from '../../routes/dashboard/settings/macros/constants';
import { teams, labels } from './macrosFixtures';
import {
resolveActionName,
emptyMacro,
resolveLabels,
resolveTeamIds,
} from '../../routes/dashboard/settings/macros/macroHelper';
describe('#resolveActionName', () => {
it('resolve action name from key and return the correct label', () => {
expect(resolveActionName(MACRO_ACTION_TYPES[0].key)).toEqual(
MACRO_ACTION_TYPES[0].label
);
expect(resolveActionName(MACRO_ACTION_TYPES[1].key)).toEqual(
MACRO_ACTION_TYPES[1].label
);
expect(resolveActionName(MACRO_ACTION_TYPES[1].key)).not.toEqual(
MACRO_ACTION_TYPES[0].label
);
});
});
describe('#emptyMacro', () => {
const defaultMacro = {
name: '',
actions: [
{
action_name: 'assign_team',
action_params: [],
},
],
visibility: 'global',
};
it('returns the default macro', () => {
expect(emptyMacro).toEqual(defaultMacro);
});
});
describe('#resolveTeamIds', () => {
it('resolves team names from ids, and returns a joined string', () => {
const resolvedTeams = '⚙️ sales team, 🤷‍♂️ fayaz';
expect(resolveTeamIds(teams, [1, 2])).toEqual(resolvedTeams);
});
});
describe('#resolveLabels', () => {
it('resolves labels names from ids and returns a joined string', () => {
const resolvedLabels = 'sales, billing';
expect(resolveLabels(labels, ['sales', 'billing'])).toEqual(resolvedLabels);
});
});

View file

@ -88,12 +88,12 @@
"VISIBILITY": {
"LABEL": "Macro Visibility",
"GLOBAL": {
"LABEL": "Global",
"DESCRIPTION": "This macro is available globally for all agents in this account."
"LABEL": "Public",
"DESCRIPTION": "This macro is available publicly for all agents in this account."
},
"PERSONAL": {
"LABEL": "Personal",
"DESCRIPTION": "This macro will be personal to you and not be available to others."
"LABEL": "Private",
"DESCRIPTION": "This macro will be private to you and not be available to others."
}
}
},

View file

@ -15,8 +15,8 @@ import {
resolveActionName,
resolveTeamIds,
resolveLabels,
resolveSendEmailToTeam,
} from 'dashboard/routes/dashboard/settings/macros/macroHelper.js';
import { mapGetters } from 'vuex';
export default {
props: {
@ -37,23 +37,25 @@ export default {
};
});
},
...mapGetters({
labels: 'labels/getLabels',
teams: 'teams/getTeams',
}),
},
methods: {
getActionValue(key, params) {
switch (key) {
case 'assign_team':
return resolveTeamIds(this.$store, params);
return resolveTeamIds(this.teams, params);
case 'add_label':
return resolveLabels(this.$store, params);
case 'send_email_to_team':
case 'send_email_transcript':
return resolveSendEmailToTeam(params[0]);
return resolveLabels(this.labels, params);
case 'mute_conversation':
case 'snooze_conversation':
case 'resolve_conversation':
return null;
case 'send_webhook_event':
case 'send_message':
case 'send_email_transcript':
return params[0];
default:
return '';

View file

@ -31,45 +31,12 @@
</th>
</thead>
<tbody>
<tr v-for="(macro, index) in records" :key="index">
<td>{{ macro.name }}</td>
<td>
<div class="avatar-container">
<thumbnail :username="macro.created_by.name" size="24px" />
<span class="ml-2">{{ macro.created_by.name }}</span>
</div>
</td>
<td>
<div class="avatar-container">
<thumbnail :username="macro.updated_by.name" size="24px" />
<span class="ml-2">{{ macro.updated_by.name }}</span>
</div>
</td>
<td class="macro-visibility">{{ macro.visibility }}</td>
<td class="button-wrapper">
<router-link
:to="addAccountScoping(`settings/macros/${macro.id}/edit`)"
>
<woot-button
v-tooltip.top="$t('MACROS.FORM.EDIT')"
variant="smooth"
size="tiny"
color-scheme="secondary"
class-names="grey-btn"
icon="edit"
<macros-table-row
v-for="(macro, index) in records"
:key="index"
:macro="macro"
@delete="openDeletePopup(macro, index)"
/>
</router-link>
<woot-button
v-tooltip.top="$t('MACROS.FORM.DELETE')"
variant="smooth"
color-scheme="alert"
size="tiny"
icon="dismiss-circle"
class-names="grey-btn"
@click="openDeletePopup(macro, index)"
/>
</td>
</tr>
</tbody>
</table>
</div>
@ -93,11 +60,11 @@
<script>
import { mapGetters } from 'vuex';
import alertMixin from 'shared/mixins/alertMixin';
import Thumbnail from 'dashboard/components/widgets/Thumbnail';
import accountMixin from 'dashboard/mixins/account.js';
import MacrosTableRow from './MacrosTableRow';
export default {
components: {
Thumbnail,
MacrosTableRow,
},
mixins: [alertMixin, accountMixin],
data() {
@ -112,7 +79,6 @@ export default {
records: ['macros/getMacros'],
uiFlags: 'macros/getUIFlags',
}),
// Delete Modal
deleteConfirmText() {
return `${this.$t('MACROS.DELETE.CONFIRM.YES')} ${
this.selectedResponse.name
@ -155,18 +121,3 @@ export default {
},
};
</script>
<style scoped lang="scss">
.avatar-container {
display: flex;
align-items: center;
span {
margin-left: var(--space-one);
}
}
.macro-visibility {
text-transform: capitalize;
}
</style>

View file

@ -15,15 +15,16 @@
import MacroForm from './MacroForm';
import { MACRO_ACTION_TYPES } from './constants';
import { mapGetters } from 'vuex';
import { getDropdownValues, emptyMacro } from './macroHelper';
import { emptyMacro } from './macroHelper';
import actionQueryGenerator from 'dashboard/helper/actionQueryGenerator.js';
import alertMixin from 'shared/mixins/alertMixin';
import macrosMixin from './macrosMixin';
export default {
components: {
MacroForm,
},
mixins: [alertMixin],
mixins: [alertMixin, macrosMixin],
provide() {
return {
macroActionTypes: this.macroActionTypes,
@ -39,6 +40,8 @@ export default {
computed: {
...mapGetters({
uiFlags: 'macros/getUIFlags',
labels: 'labels/getLabels',
teams: 'teams/getTeams',
}),
macroId() {
return this.$route.params.macroId;
@ -86,12 +89,12 @@ export default {
).inputType;
if (inputType === 'multi_select') {
actionParams = [
...getDropdownValues(action.action_name, this.$store),
...this.getDropdownValues(action.action_name, this.$store),
].filter(item => [...action.action_params].includes(item.id));
} else if (inputType === 'team_message') {
actionParams = {
team_ids: [
...getDropdownValues(action.action_name, this.$store),
...this.getDropdownValues(action.action_name, this.$store),
].filter(item =>
[...action.action_params[0].team_ids].includes(item.id)
),

View file

@ -37,12 +37,15 @@
<script>
import ActionInput from 'dashboard/components/widgets/AutomationActionInput';
import MacroActionButton from './ActionButton.vue';
import { getDropdownValues } from './macroHelper';
import macrosMixin from './macrosMixin';
import { mapGetters } from 'vuex';
export default {
components: {
ActionInput,
MacroActionButton,
},
mixins: [macrosMixin],
inject: ['macroActionTypes', '$v'],
props: {
singleNode: {
@ -59,6 +62,10 @@ export default {
},
},
computed: {
...mapGetters({
labels: 'labels/getLabels',
teams: 'teams/getTeams',
}),
actionData: {
get() {
return this.value;
@ -81,7 +88,7 @@ export default {
},
methods: {
dropdownValues() {
return getDropdownValues(this.value.action_name, this.$store);
return this.getDropdownValues(this.value.action_name, this.$store);
},
hasError(v) {
return !!(v.action_params.$dirty && v.action_params.$error);

View file

@ -134,6 +134,15 @@ export default {
color: var(--s-500);
}
.title {
display: block;
margin: 0;
font-size: var(--font-size-small);
font-weight: var(--font-weight-medium);
line-height: 1.8;
color: var(--color-body);
}
.visibility-check {
position: absolute;
color: var(--w-500);

View file

@ -0,0 +1,74 @@
<template>
<tr>
<td>{{ macro.name }}</td>
<td>
<div class="avatar-container">
<thumbnail :username="macro.created_by.name" size="24px" />
<span class="ml-2">{{ macro.created_by.name }}</span>
</div>
</td>
<td>
<div class="avatar-container">
<thumbnail :username="macro.updated_by.name" size="24px" />
<span class="ml-2">{{ macro.updated_by.name }}</span>
</div>
</td>
<td>{{ visibilityLabel }}</td>
<td class="button-wrapper">
<router-link :to="addAccountScoping(`settings/macros/${macro.id}/edit`)">
<woot-button
v-tooltip.top="$t('MACROS.FORM.EDIT')"
variant="smooth"
size="tiny"
color-scheme="secondary"
class-names="grey-btn"
icon="edit"
/>
</router-link>
<woot-button
v-tooltip.top="$t('MACROS.FORM.DELETE')"
variant="smooth"
color-scheme="alert"
size="tiny"
icon="dismiss-circle"
class-names="grey-btn"
@click="$emit('delete')"
/>
</td>
</tr>
</template>
<script>
import Thumbnail from 'dashboard/components/widgets/Thumbnail';
import accountMixin from 'dashboard/mixins/account.js';
export default {
components: {
Thumbnail,
},
mixins: [accountMixin],
props: {
macro: {
type: Object,
required: true,
},
},
computed: {
visibilityLabel() {
return this.macro.visibility === 'global'
? this.$t('MACROS.EDITOR.VISIBILITY.GLOBAL.LABEL')
: this.$t('MACROS.EDITOR.VISIBILITY.PERSONAL.LABEL');
},
},
};
</script>
<style scoped lang="scss">
.avatar-container {
display: flex;
align-items: center;
span {
margin-left: var(--space-one);
}
}
</style>

View file

@ -4,48 +4,24 @@ export const resolveActionName = key => {
return macroActionTypes.find(i => i.key === key).label;
};
export const resolveTeamIds = (store, ids) => {
const allTeams = store.getters['teams/getTeams'];
export const resolveTeamIds = (teams, ids) => {
return ids
.map(id => {
const team = allTeams.find(i => i.id === id);
const team = teams.find(i => i.id === id);
return team ? team.name : '';
})
.join(', ');
};
export const resolveLabels = (store, ids) => {
const allLabels = store.getters['labels/getLabels'];
export const resolveLabels = (labels, ids) => {
return ids
.map(id => {
const label = allLabels.find(i => i.title === id);
const label = labels.find(i => i.title === id);
return label ? label.title : '';
})
.join(', ');
};
export const resolveSendEmailToTeam = obj => {
return ` ${obj.message} -
${resolveTeamIds(obj.team_ids)}`;
};
export const getDropdownValues = (type, store) => {
switch (type) {
case 'assign_team':
case 'send_email_to_team':
return store.getters['teams/getTeams'];
case 'add_label':
return store.getters['labels/getLabels'].map(i => {
return {
id: i.title,
name: i.title,
};
});
default:
return [];
}
};
export const emptyMacro = {
name: '',
actions: [

View file

@ -0,0 +1,20 @@
export default {
methods: {
getDropdownValues(type) {
switch (type) {
case 'assign_team':
case 'send_email_to_team':
return this.teams;
case 'add_label':
return this.labels.map(i => {
return {
id: i.title,
name: i.title,
};
});
default:
return [];
}
},
},
};