Ported duplicate logic to a mixin
This commit is contained in:
parent
b97c5944d2
commit
9bfbd9e904
4 changed files with 529 additions and 728 deletions
|
@ -138,72 +138,28 @@
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
import alertMixin from 'shared/mixins/alertMixin';
|
import alertMixin from 'shared/mixins/alertMixin';
|
||||||
import { required, requiredIf } from 'vuelidate/lib/validators';
|
import automationMixin from 'shared/mixins/automationMixin';
|
||||||
import filterInputBox from 'dashboard/components/widgets/FilterInput/Index.vue';
|
import filterInputBox from 'dashboard/components/widgets/FilterInput/Index.vue';
|
||||||
import automationActionInput from 'dashboard/components/widgets/AutomationActionInput.vue';
|
import automationActionInput from 'dashboard/components/widgets/AutomationActionInput.vue';
|
||||||
import languages from 'dashboard/components/widgets/conversation/advancedFilterItems/languages';
|
|
||||||
import countries from '/app/javascript/shared/constants/countries.js';
|
|
||||||
import {
|
import {
|
||||||
AUTOMATION_RULE_EVENTS,
|
AUTOMATION_RULE_EVENTS,
|
||||||
AUTOMATION_ACTION_TYPES,
|
AUTOMATION_ACTION_TYPES,
|
||||||
AUTOMATIONS,
|
AUTOMATIONS,
|
||||||
} from './constants';
|
} from './constants';
|
||||||
import filterQueryGenerator from 'dashboard/helper/filterQueryGenerator.js';
|
|
||||||
import actionQueryGenerator from 'dashboard/helper/actionQueryGenerator.js';
|
|
||||||
import * as OPERATORS from './operators';
|
|
||||||
export default {
|
export default {
|
||||||
components: {
|
components: {
|
||||||
filterInputBox,
|
filterInputBox,
|
||||||
automationActionInput,
|
automationActionInput,
|
||||||
},
|
},
|
||||||
mixins: [alertMixin],
|
mixins: [alertMixin, automationMixin],
|
||||||
props: {
|
props: {
|
||||||
onClose: {
|
onClose: {
|
||||||
type: Function,
|
type: Function,
|
||||||
default: () => {},
|
default: () => {},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
validations: {
|
|
||||||
automation: {
|
|
||||||
name: {
|
|
||||||
required,
|
|
||||||
},
|
|
||||||
description: {
|
|
||||||
required,
|
|
||||||
},
|
|
||||||
event_name: {
|
|
||||||
required,
|
|
||||||
},
|
|
||||||
conditions: {
|
|
||||||
required,
|
|
||||||
$each: {
|
|
||||||
values: {
|
|
||||||
required: requiredIf(prop => {
|
|
||||||
return !(
|
|
||||||
prop.filter_operator === 'is_present' ||
|
|
||||||
prop.filter_operator === 'is_not_present'
|
|
||||||
);
|
|
||||||
}),
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
actions: {
|
|
||||||
required,
|
|
||||||
$each: {
|
|
||||||
action_params: {
|
|
||||||
required: requiredIf(prop => {
|
|
||||||
if (prop.action_name === 'send_email_to_team') return true;
|
|
||||||
return !(
|
|
||||||
prop.action_name === 'mute_conversation' ||
|
|
||||||
prop.action_name === 'snooze_conversation' ||
|
|
||||||
prop.action_name === 'resolve_conversation'
|
|
||||||
);
|
|
||||||
}),
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
automationTypes: AUTOMATIONS,
|
automationTypes: AUTOMATIONS,
|
||||||
|
@ -233,6 +189,7 @@ export default {
|
||||||
},
|
},
|
||||||
showDeleteConfirmationModal: false,
|
showDeleteConfirmationModal: false,
|
||||||
allCustomAttributes: [],
|
allCustomAttributes: [],
|
||||||
|
mode: 'create',
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
|
@ -261,274 +218,7 @@ export default {
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
mounted() {
|
mounted() {
|
||||||
const customAttributesRaw = this.$store.getters['attributes/getAttributes'];
|
this.manifestCustomAttributes();
|
||||||
const customAttributeTypes = customAttributesRaw.map(attr => {
|
|
||||||
return {
|
|
||||||
key: attr.attribute_key,
|
|
||||||
name: attr.attribute_display_name,
|
|
||||||
inputType: this.customAttributeInputType(attr.attribute_display_type),
|
|
||||||
filterOperators: this.getOperatorTypes(attr.attribute_display_type),
|
|
||||||
};
|
|
||||||
});
|
|
||||||
AUTOMATIONS.message_created.conditions.push(...customAttributeTypes);
|
|
||||||
AUTOMATIONS.conversation_created.conditions.push(...customAttributeTypes);
|
|
||||||
AUTOMATIONS.conversation_updated.conditions.push(...customAttributeTypes);
|
|
||||||
},
|
|
||||||
methods: {
|
|
||||||
customAttributeInputType(key) {
|
|
||||||
switch (key) {
|
|
||||||
case 'date':
|
|
||||||
return 'date';
|
|
||||||
case 'text':
|
|
||||||
return 'plain_text';
|
|
||||||
case 'list':
|
|
||||||
return 'search_select';
|
|
||||||
case 'checkbox':
|
|
||||||
return 'search_select';
|
|
||||||
default:
|
|
||||||
return 'plain_text';
|
|
||||||
}
|
|
||||||
},
|
|
||||||
onEventChange() {
|
|
||||||
if (this.automation.event_name === 'message_created') {
|
|
||||||
this.automation.conditions = [
|
|
||||||
{
|
|
||||||
attribute_key: 'message_type',
|
|
||||||
filter_operator: 'equal_to',
|
|
||||||
values: '',
|
|
||||||
query_operator: 'and',
|
|
||||||
},
|
|
||||||
];
|
|
||||||
} else {
|
|
||||||
this.automation.conditions = [
|
|
||||||
{
|
|
||||||
attribute_key: 'status',
|
|
||||||
filter_operator: 'equal_to',
|
|
||||||
values: '',
|
|
||||||
query_operator: 'and',
|
|
||||||
},
|
|
||||||
];
|
|
||||||
}
|
|
||||||
this.automation.actions = [
|
|
||||||
{
|
|
||||||
action_name: 'assign_team',
|
|
||||||
action_params: [],
|
|
||||||
},
|
|
||||||
];
|
|
||||||
},
|
|
||||||
getAttributes(key) {
|
|
||||||
return this.automationTypes[key].conditions;
|
|
||||||
},
|
|
||||||
getInputType(key) {
|
|
||||||
const type = this.automationTypes[
|
|
||||||
this.automation.event_name
|
|
||||||
].conditions.find(condition => condition.key === key);
|
|
||||||
return type.inputType;
|
|
||||||
},
|
|
||||||
getOperators(key) {
|
|
||||||
const type = this.automationTypes[
|
|
||||||
this.automation.event_name
|
|
||||||
].conditions.find(condition => condition.key === key);
|
|
||||||
return type.filterOperators;
|
|
||||||
},
|
|
||||||
getOperatorTypes(key) {
|
|
||||||
switch (key) {
|
|
||||||
case 'list':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_1;
|
|
||||||
case 'text':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_3;
|
|
||||||
case 'number':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_1;
|
|
||||||
case 'link':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_1;
|
|
||||||
case 'date':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_4;
|
|
||||||
case 'checkbox':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_1;
|
|
||||||
default:
|
|
||||||
return OPERATORS.OPERATOR_TYPES_1;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
getConditionDropdownValues(type) {
|
|
||||||
const statusFilters = this.$t('CHAT_LIST.CHAT_STATUS_FILTER_ITEMS');
|
|
||||||
const allCustomAttributes = this.$store.getters[
|
|
||||||
'attributes/getAttributes'
|
|
||||||
];
|
|
||||||
|
|
||||||
const isCustomAttributeCheckbox = allCustomAttributes.find(attr => {
|
|
||||||
return (
|
|
||||||
attr.attribute_key === type &&
|
|
||||||
attr.attribute_display_type === 'checkbox'
|
|
||||||
);
|
|
||||||
});
|
|
||||||
if (isCustomAttributeCheckbox) {
|
|
||||||
return [
|
|
||||||
{
|
|
||||||
id: true,
|
|
||||||
name: this.$t('FILTER.ATTRIBUTE_LABELS.TRUE'),
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: false,
|
|
||||||
name: this.$t('FILTER.ATTRIBUTE_LABELS.FALSE'),
|
|
||||||
},
|
|
||||||
];
|
|
||||||
}
|
|
||||||
|
|
||||||
const isCustomAttributeList = allCustomAttributes.find(attr => {
|
|
||||||
return (
|
|
||||||
attr.attribute_key === type && attr.attribute_display_type === 'list'
|
|
||||||
);
|
|
||||||
});
|
|
||||||
|
|
||||||
if (isCustomAttributeList) {
|
|
||||||
return allCustomAttributes
|
|
||||||
.find(attr => attr.attribute_key === type)
|
|
||||||
.attribute_values.map(item => {
|
|
||||||
return {
|
|
||||||
id: item,
|
|
||||||
name: item,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
switch (type) {
|
|
||||||
case 'status':
|
|
||||||
return [
|
|
||||||
...Object.keys(statusFilters).map(status => {
|
|
||||||
return {
|
|
||||||
id: status,
|
|
||||||
name: statusFilters[status].TEXT,
|
|
||||||
};
|
|
||||||
}),
|
|
||||||
{
|
|
||||||
id: 'all',
|
|
||||||
name: this.$t('CHAT_LIST.FILTER_ALL'),
|
|
||||||
},
|
|
||||||
];
|
|
||||||
case 'assignee_id':
|
|
||||||
return this.$store.getters['agents/getAgents'];
|
|
||||||
case 'contact':
|
|
||||||
return this.$store.getters['contacts/getContacts'];
|
|
||||||
case 'inbox_id':
|
|
||||||
return this.$store.getters['inboxes/getInboxes'];
|
|
||||||
case 'team_id':
|
|
||||||
return this.$store.getters['teams/getTeams'];
|
|
||||||
case 'campaign_id':
|
|
||||||
return this.$store.getters['campaigns/getAllCampaigns'].map(i => {
|
|
||||||
return {
|
|
||||||
id: i.id,
|
|
||||||
name: i.title,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
case 'labels':
|
|
||||||
return this.$store.getters['labels/getLabels'].map(i => {
|
|
||||||
return {
|
|
||||||
id: i.title,
|
|
||||||
name: i.title,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
case 'browser_language':
|
|
||||||
return languages;
|
|
||||||
case 'country_code':
|
|
||||||
return countries;
|
|
||||||
default:
|
|
||||||
return undefined;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
getActionDropdownValues(type) {
|
|
||||||
switch (type) {
|
|
||||||
case 'assign_team':
|
|
||||||
case 'send_email_to_team':
|
|
||||||
return this.$store.getters['teams/getTeams'];
|
|
||||||
case 'add_label':
|
|
||||||
return this.$store.getters['labels/getLabels'].map(i => {
|
|
||||||
return {
|
|
||||||
id: i.title,
|
|
||||||
name: i.title,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
default:
|
|
||||||
return undefined;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
appendNewCondition() {
|
|
||||||
switch (this.automation.event_name) {
|
|
||||||
case 'message_created':
|
|
||||||
this.automation.conditions.push({
|
|
||||||
attribute_key: 'message_type',
|
|
||||||
filter_operator: 'equal_to',
|
|
||||||
values: '',
|
|
||||||
query_operator: 'and',
|
|
||||||
});
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
this.automation.conditions.push({
|
|
||||||
attribute_key: 'status',
|
|
||||||
filter_operator: 'equal_to',
|
|
||||||
values: '',
|
|
||||||
query_operator: 'and',
|
|
||||||
});
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
appendNewAction() {
|
|
||||||
this.automation.actions.push({
|
|
||||||
action_name: 'assign_team',
|
|
||||||
action_params: [],
|
|
||||||
});
|
|
||||||
},
|
|
||||||
removeFilter(index) {
|
|
||||||
if (this.automation.conditions.length <= 1) {
|
|
||||||
this.showAlert(this.$t('FILTER.FILTER_DELETE_ERROR'));
|
|
||||||
} else {
|
|
||||||
this.automation.conditions.splice(index, 1);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
removeAction(index) {
|
|
||||||
if (this.automation.actions.length <= 1) {
|
|
||||||
this.showAlert(this.$t('FILTER.FILTER_DELETE_ERROR'));
|
|
||||||
} else {
|
|
||||||
this.automation.actions.splice(index, 1);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
submitAutomation() {
|
|
||||||
this.$v.$touch();
|
|
||||||
if (this.$v.$invalid) return;
|
|
||||||
const automation = JSON.parse(JSON.stringify(this.automation));
|
|
||||||
automation.conditions[
|
|
||||||
automation.conditions.length - 1
|
|
||||||
].query_operator = null;
|
|
||||||
automation.conditions = filterQueryGenerator(
|
|
||||||
automation.conditions
|
|
||||||
).payload;
|
|
||||||
automation.actions = actionQueryGenerator(automation.actions);
|
|
||||||
this.$emit('saveAutomation', automation);
|
|
||||||
},
|
|
||||||
resetFilter(index, currentCondition) {
|
|
||||||
this.automation.conditions[index].filter_operator = this.automationTypes[
|
|
||||||
this.automation.event_name
|
|
||||||
].conditions.find(
|
|
||||||
condition => condition.key === currentCondition.attribute_key
|
|
||||||
).filterOperators[0].value;
|
|
||||||
this.automation.conditions[index].values = '';
|
|
||||||
},
|
|
||||||
resetAction(index) {
|
|
||||||
this.automation.actions[index].action_params = [];
|
|
||||||
},
|
|
||||||
showUserInput(operatorType) {
|
|
||||||
if (operatorType === 'is_present' || operatorType === 'is_not_present')
|
|
||||||
return false;
|
|
||||||
return true;
|
|
||||||
},
|
|
||||||
showActionInput(actionName) {
|
|
||||||
if (actionName === 'send_email_to_team' || actionName === 'send_message')
|
|
||||||
return false;
|
|
||||||
const type = AUTOMATION_ACTION_TYPES.find(
|
|
||||||
action => action.key === actionName
|
|
||||||
).inputType;
|
|
||||||
if (type === null) return false;
|
|
||||||
return true;
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
</script>
|
</script>
|
||||||
|
|
|
@ -144,25 +144,22 @@
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
import alertMixin from 'shared/mixins/alertMixin';
|
import alertMixin from 'shared/mixins/alertMixin';
|
||||||
import { required, requiredIf } from 'vuelidate/lib/validators';
|
import automationMixin from 'shared/mixins/automationMixin';
|
||||||
import filterInputBox from 'dashboard/components/widgets/FilterInput/Index.vue';
|
import filterInputBox from 'dashboard/components/widgets/FilterInput/Index.vue';
|
||||||
import automationActionInput from 'dashboard/components/widgets/AutomationActionInput.vue';
|
import automationActionInput from 'dashboard/components/widgets/AutomationActionInput.vue';
|
||||||
import languages from 'dashboard/components/widgets/conversation/advancedFilterItems/languages';
|
|
||||||
import countries from 'shared/constants/countries.js';
|
|
||||||
import {
|
import {
|
||||||
AUTOMATION_RULE_EVENTS,
|
AUTOMATION_RULE_EVENTS,
|
||||||
AUTOMATION_ACTION_TYPES,
|
AUTOMATION_ACTION_TYPES,
|
||||||
AUTOMATIONS,
|
AUTOMATIONS,
|
||||||
} from './constants';
|
} from './constants';
|
||||||
import filterQueryGenerator from 'dashboard/helper/filterQueryGenerator.js';
|
|
||||||
import actionQueryGenerator from 'dashboard/helper/actionQueryGenerator.js';
|
|
||||||
import * as OPERATORS from './operators';
|
|
||||||
export default {
|
export default {
|
||||||
components: {
|
components: {
|
||||||
filterInputBox,
|
filterInputBox,
|
||||||
automationActionInput,
|
automationActionInput,
|
||||||
},
|
},
|
||||||
mixins: [alertMixin],
|
mixins: [alertMixin, automationMixin],
|
||||||
props: {
|
props: {
|
||||||
onClose: {
|
onClose: {
|
||||||
type: Function,
|
type: Function,
|
||||||
|
@ -173,46 +170,7 @@ export default {
|
||||||
default: () => {},
|
default: () => {},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
validations: {
|
|
||||||
automation: {
|
|
||||||
name: {
|
|
||||||
required,
|
|
||||||
},
|
|
||||||
description: {
|
|
||||||
required,
|
|
||||||
},
|
|
||||||
event_name: {
|
|
||||||
required,
|
|
||||||
},
|
|
||||||
conditions: {
|
|
||||||
required,
|
|
||||||
$each: {
|
|
||||||
values: {
|
|
||||||
required: requiredIf(prop => {
|
|
||||||
return !(
|
|
||||||
prop.filter_operator === 'is_present' ||
|
|
||||||
prop.filter_operator === 'is_not_present'
|
|
||||||
);
|
|
||||||
}),
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
actions: {
|
|
||||||
required,
|
|
||||||
$each: {
|
|
||||||
action_params: {
|
|
||||||
required: requiredIf(prop => {
|
|
||||||
return !(
|
|
||||||
prop.action_name === 'mute_conversation' ||
|
|
||||||
prop.action_name === 'snooze_conversation' ||
|
|
||||||
prop.action_name === 'resolve_conversation'
|
|
||||||
);
|
|
||||||
}),
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
automationTypes: AUTOMATIONS,
|
automationTypes: AUTOMATIONS,
|
||||||
|
@ -242,6 +200,7 @@ export default {
|
||||||
},
|
},
|
||||||
showDeleteConfirmationModal: false,
|
showDeleteConfirmationModal: false,
|
||||||
allCustomAttributes: [],
|
allCustomAttributes: [],
|
||||||
|
mode: 'edit',
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
|
@ -262,374 +221,10 @@ export default {
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
mounted() {
|
mounted() {
|
||||||
const customAttributesRaw = this.$store.getters['attributes/getAttributes'];
|
this.manifestCustomAttributes();
|
||||||
const customAttributeTypes = customAttributesRaw.map(attr => {
|
|
||||||
return {
|
|
||||||
key: attr.attribute_key,
|
|
||||||
name: attr.attribute_display_name,
|
|
||||||
inputType: this.customAttributeInputType(attr.attribute_display_type),
|
|
||||||
filterOperators: this.getOperatorTypes(attr.attribute_display_type),
|
|
||||||
};
|
|
||||||
});
|
|
||||||
AUTOMATIONS.message_created.conditions.push(...customAttributeTypes);
|
|
||||||
AUTOMATIONS.conversation_created.conditions.push(...customAttributeTypes);
|
|
||||||
AUTOMATIONS.conversation_updated.conditions.push(...customAttributeTypes);
|
|
||||||
this.allCustomAttributes = this.$store.getters['attributes/getAttributes'];
|
this.allCustomAttributes = this.$store.getters['attributes/getAttributes'];
|
||||||
this.formatAutomation(this.selectedResponse);
|
this.formatAutomation(this.selectedResponse);
|
||||||
},
|
},
|
||||||
methods: {
|
|
||||||
onEventChange() {
|
|
||||||
if (this.automation.event_name === 'message_created') {
|
|
||||||
this.automation.conditions = [
|
|
||||||
{
|
|
||||||
attribute_key: 'message_type',
|
|
||||||
filter_operator: 'equal_to',
|
|
||||||
values: '',
|
|
||||||
query_operator: 'and',
|
|
||||||
},
|
|
||||||
];
|
|
||||||
} else {
|
|
||||||
this.automation.conditions = [
|
|
||||||
{
|
|
||||||
attribute_key: 'status',
|
|
||||||
filter_operator: 'equal_to',
|
|
||||||
values: '',
|
|
||||||
query_operator: 'and',
|
|
||||||
},
|
|
||||||
];
|
|
||||||
}
|
|
||||||
this.automation.actions = [
|
|
||||||
{
|
|
||||||
action_name: 'assign_team',
|
|
||||||
action_params: [],
|
|
||||||
},
|
|
||||||
];
|
|
||||||
},
|
|
||||||
getAttributes(key) {
|
|
||||||
return this.automationTypes[key].conditions;
|
|
||||||
},
|
|
||||||
isACustomAttribute(key) {
|
|
||||||
return this.allCustomAttributes.find(attr => {
|
|
||||||
return attr.attribute_key === key;
|
|
||||||
});
|
|
||||||
},
|
|
||||||
getInputType(key) {
|
|
||||||
const customAttribute = this.isACustomAttribute(key);
|
|
||||||
if (customAttribute) {
|
|
||||||
return this.customAttributeInputType(
|
|
||||||
customAttribute.attribute_display_type
|
|
||||||
);
|
|
||||||
}
|
|
||||||
const type = this.automationTypes[
|
|
||||||
this.automation.event_name
|
|
||||||
].conditions.find(condition => condition.key === key);
|
|
||||||
return type.inputType;
|
|
||||||
},
|
|
||||||
getOperators(key) {
|
|
||||||
const customAttribute = this.isACustomAttribute(key);
|
|
||||||
if (customAttribute) {
|
|
||||||
return this.getOperatorTypes(customAttribute.attribute_display_type);
|
|
||||||
}
|
|
||||||
const type = this.automationTypes[
|
|
||||||
this.automation.event_name
|
|
||||||
].conditions.find(condition => condition.key === key);
|
|
||||||
return type.filterOperators;
|
|
||||||
},
|
|
||||||
getConditionDropdownValues(type) {
|
|
||||||
const statusFilters = this.$t('CHAT_LIST.CHAT_STATUS_FILTER_ITEMS');
|
|
||||||
const allCustomAttributes = this.$store.getters[
|
|
||||||
'attributes/getAttributes'
|
|
||||||
];
|
|
||||||
|
|
||||||
const isCustomAttributeCheckbox = allCustomAttributes.find(attr => {
|
|
||||||
return (
|
|
||||||
attr.attribute_key === type &&
|
|
||||||
attr.attribute_display_type === 'checkbox'
|
|
||||||
);
|
|
||||||
});
|
|
||||||
if (isCustomAttributeCheckbox) {
|
|
||||||
return [
|
|
||||||
{
|
|
||||||
id: true,
|
|
||||||
name: this.$t('FILTER.ATTRIBUTE_LABELS.TRUE'),
|
|
||||||
},
|
|
||||||
{
|
|
||||||
id: false,
|
|
||||||
name: this.$t('FILTER.ATTRIBUTE_LABELS.FALSE'),
|
|
||||||
},
|
|
||||||
];
|
|
||||||
}
|
|
||||||
|
|
||||||
const isCustomAttributeList = allCustomAttributes.find(attr => {
|
|
||||||
return (
|
|
||||||
attr.attribute_key === type && attr.attribute_display_type === 'list'
|
|
||||||
);
|
|
||||||
});
|
|
||||||
|
|
||||||
if (isCustomAttributeList) {
|
|
||||||
return allCustomAttributes
|
|
||||||
.find(attr => attr.attribute_key === type)
|
|
||||||
.attribute_values.map(item => {
|
|
||||||
return {
|
|
||||||
id: item,
|
|
||||||
name: item,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
switch (type) {
|
|
||||||
case 'status':
|
|
||||||
return [
|
|
||||||
...Object.keys(statusFilters).map(status => {
|
|
||||||
return {
|
|
||||||
id: status,
|
|
||||||
name: statusFilters[status].TEXT,
|
|
||||||
};
|
|
||||||
}),
|
|
||||||
{
|
|
||||||
id: 'all',
|
|
||||||
name: this.$t('CHAT_LIST.FILTER_ALL'),
|
|
||||||
},
|
|
||||||
];
|
|
||||||
case 'assignee_id':
|
|
||||||
return this.$store.getters['agents/getAgents'];
|
|
||||||
case 'contact':
|
|
||||||
return this.$store.getters['contacts/getContacts'];
|
|
||||||
case 'inbox_id':
|
|
||||||
return this.$store.getters['inboxes/getInboxes'];
|
|
||||||
case 'team_id':
|
|
||||||
return this.$store.getters['teams/getTeams'];
|
|
||||||
case 'campaign_id':
|
|
||||||
return this.$store.getters['campaigns/getAllCampaigns'].map(i => {
|
|
||||||
return {
|
|
||||||
id: i.id,
|
|
||||||
name: i.title,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
case 'labels':
|
|
||||||
return this.$store.getters['labels/getLabels'].map(i => {
|
|
||||||
return {
|
|
||||||
id: i.title,
|
|
||||||
name: i.title,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
case 'browser_language':
|
|
||||||
return languages;
|
|
||||||
case 'country_code':
|
|
||||||
return countries;
|
|
||||||
default:
|
|
||||||
return undefined;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
getActionDropdownValues(type) {
|
|
||||||
switch (type) {
|
|
||||||
case 'assign_team':
|
|
||||||
case 'send_email_to_team':
|
|
||||||
return this.$store.getters['teams/getTeams'];
|
|
||||||
case 'add_label':
|
|
||||||
return this.$store.getters['labels/getLabels'].map(i => {
|
|
||||||
return {
|
|
||||||
id: i.title,
|
|
||||||
name: i.title,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
default:
|
|
||||||
return undefined;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
appendNewCondition() {
|
|
||||||
if (
|
|
||||||
!this.automation.conditions[this.automation.conditions.length - 1]
|
|
||||||
.query_operator
|
|
||||||
) {
|
|
||||||
this.automation.conditions[
|
|
||||||
this.automation.conditions.length - 1
|
|
||||||
].query_operator = 'and';
|
|
||||||
}
|
|
||||||
switch (this.automation.event_name) {
|
|
||||||
case 'message_created':
|
|
||||||
this.automation.conditions.push({
|
|
||||||
attribute_key: 'message_type',
|
|
||||||
filter_operator: 'equal_to',
|
|
||||||
values: '',
|
|
||||||
query_operator: 'and',
|
|
||||||
});
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
this.automation.conditions.push({
|
|
||||||
attribute_key: 'status',
|
|
||||||
filter_operator: 'equal_to',
|
|
||||||
values: '',
|
|
||||||
query_operator: 'and',
|
|
||||||
});
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
appendNewAction() {
|
|
||||||
this.automation.actions.push({
|
|
||||||
action_name: 'assign_team',
|
|
||||||
action_params: [],
|
|
||||||
});
|
|
||||||
},
|
|
||||||
removeFilter(index) {
|
|
||||||
if (this.automation.conditions.length <= 1) {
|
|
||||||
this.showAlert(this.$t('AUTOMATION.CONDITION.DELETE_MESSAGE'));
|
|
||||||
} else {
|
|
||||||
this.automation.conditions.splice(index, 1);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
removeAction(index) {
|
|
||||||
if (this.automation.actions.length <= 1) {
|
|
||||||
this.showAlert(this.$t('AUTOMATION.ACTION.DELETE_MESSAGE'));
|
|
||||||
} else {
|
|
||||||
this.automation.actions.splice(index, 1);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
submitAutomation() {
|
|
||||||
this.$v.$touch();
|
|
||||||
if (this.$v.$invalid) return;
|
|
||||||
const automation = JSON.parse(JSON.stringify(this.automation));
|
|
||||||
automation.conditions[
|
|
||||||
automation.conditions.length - 1
|
|
||||||
].query_operator = null;
|
|
||||||
automation.conditions = filterQueryGenerator(
|
|
||||||
automation.conditions
|
|
||||||
).payload;
|
|
||||||
automation.actions = actionQueryGenerator(automation.actions);
|
|
||||||
this.$emit('saveAutomation', automation, 'EDIT');
|
|
||||||
},
|
|
||||||
resetFilter(index, currentCondition) {
|
|
||||||
this.automation.conditions[index].filter_operator = this.automationTypes[
|
|
||||||
this.automation.event_name
|
|
||||||
].conditions.find(
|
|
||||||
condition => condition.key === currentCondition.attribute_key
|
|
||||||
).filterOperators[0].value;
|
|
||||||
this.automation.conditions[index].values = '';
|
|
||||||
},
|
|
||||||
showUserInput(operatorType) {
|
|
||||||
if (operatorType === 'is_present' || operatorType === 'is_not_present')
|
|
||||||
return false;
|
|
||||||
return true;
|
|
||||||
},
|
|
||||||
formatAutomation(automation) {
|
|
||||||
const allCustomAttributes = this.$store.getters[
|
|
||||||
'attributes/getAttributes'
|
|
||||||
];
|
|
||||||
const customAttributes = allCustomAttributes.map(attr => {
|
|
||||||
return {
|
|
||||||
key: attr.attribute_key,
|
|
||||||
name: attr.attribute_display_name,
|
|
||||||
type: attr.attribute_display_type,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
const formattedConditions = automation.conditions.map(condition => {
|
|
||||||
const isCustomAttribute = customAttributes.find(
|
|
||||||
attr => attr.key === condition.attribute_key
|
|
||||||
);
|
|
||||||
let inputType = 'plain_text';
|
|
||||||
if (isCustomAttribute) {
|
|
||||||
inputType = this.customAttributeInputType(isCustomAttribute.type);
|
|
||||||
} else {
|
|
||||||
inputType = this.automationTypes[
|
|
||||||
automation.event_name
|
|
||||||
].conditions.find(item => item.key === condition.attribute_key)
|
|
||||||
.inputType;
|
|
||||||
}
|
|
||||||
if (inputType === 'plain_text') {
|
|
||||||
return {
|
|
||||||
...condition,
|
|
||||||
values: condition.values[0],
|
|
||||||
};
|
|
||||||
}
|
|
||||||
return {
|
|
||||||
...condition,
|
|
||||||
values: [
|
|
||||||
...this.getConditionDropdownValues(condition.attribute_key),
|
|
||||||
].filter(item => [...condition.values].includes(item.id)),
|
|
||||||
};
|
|
||||||
});
|
|
||||||
const formattedActions = automation.actions.map(action => {
|
|
||||||
let actionParams = [];
|
|
||||||
if (action.action_params.length) {
|
|
||||||
const inputType = AUTOMATION_ACTION_TYPES.find(
|
|
||||||
item => item.key === action.action_name
|
|
||||||
).inputType;
|
|
||||||
if (inputType === 'multi_select') {
|
|
||||||
actionParams = [
|
|
||||||
...this.getActionDropdownValues(action.action_name),
|
|
||||||
].filter(item => [...action.action_params].includes(item.id));
|
|
||||||
} else if (inputType === 'team_message') {
|
|
||||||
actionParams = {
|
|
||||||
team_ids: [
|
|
||||||
...this.getActionDropdownValues(action.action_name),
|
|
||||||
].filter(item =>
|
|
||||||
[...action.action_params[0].team_ids].includes(item.id)
|
|
||||||
),
|
|
||||||
message: action.action_params[0].message,
|
|
||||||
};
|
|
||||||
} else actionParams = [...action.action_params];
|
|
||||||
}
|
|
||||||
return {
|
|
||||||
...action,
|
|
||||||
action_params: actionParams,
|
|
||||||
};
|
|
||||||
});
|
|
||||||
this.automation = {
|
|
||||||
...automation,
|
|
||||||
conditions: formattedConditions,
|
|
||||||
actions: formattedActions,
|
|
||||||
};
|
|
||||||
},
|
|
||||||
showActionInput(actionName) {
|
|
||||||
if (actionName === 'send_email_to_team' || actionName === 'send_message')
|
|
||||||
return false;
|
|
||||||
const type = AUTOMATION_ACTION_TYPES.find(
|
|
||||||
action => action.key === actionName
|
|
||||||
).inputType;
|
|
||||||
if (type === null) return false;
|
|
||||||
return true;
|
|
||||||
},
|
|
||||||
getOperatorTypes(key) {
|
|
||||||
switch (key) {
|
|
||||||
case 'list':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_1;
|
|
||||||
case 'text':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_3;
|
|
||||||
case 'number':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_1;
|
|
||||||
case 'link':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_1;
|
|
||||||
case 'date':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_4;
|
|
||||||
case 'checkbox':
|
|
||||||
return OPERATORS.OPERATOR_TYPES_1;
|
|
||||||
default:
|
|
||||||
return OPERATORS.OPERATOR_TYPES_1;
|
|
||||||
}
|
|
||||||
},
|
|
||||||
customAttributeInputType(key) {
|
|
||||||
switch (key) {
|
|
||||||
case 'date':
|
|
||||||
return 'date';
|
|
||||||
case 'text':
|
|
||||||
return 'plain_text';
|
|
||||||
case 'list':
|
|
||||||
return 'search_select';
|
|
||||||
case 'checkbox':
|
|
||||||
return 'search_select';
|
|
||||||
default:
|
|
||||||
return 'plain_text';
|
|
||||||
}
|
|
||||||
},
|
|
||||||
getFileName(id, actionType) {
|
|
||||||
if (!id) return '';
|
|
||||||
if (actionType === 'send_attachment') {
|
|
||||||
const file = this.automation.files.find(item => item.blob_id === id);
|
|
||||||
if (file) return file.filename.toString();
|
|
||||||
}
|
|
||||||
return '';
|
|
||||||
},
|
|
||||||
},
|
|
||||||
};
|
};
|
||||||
</script>
|
</script>
|
||||||
<style lang="scss" scoped>
|
<style lang="scss" scoped>
|
||||||
|
|
446
app/javascript/shared/mixins/automationMixin.js
Normal file
446
app/javascript/shared/mixins/automationMixin.js
Normal file
|
@ -0,0 +1,446 @@
|
||||||
|
import * as OPERATORS from '../../dashboard/routes/dashboard/settings/automation/operators';
|
||||||
|
import languages from '../../dashboard/components/widgets/conversation/advancedFilterItems/languages';
|
||||||
|
import countries from '../../shared/constants/countries';
|
||||||
|
import filterQueryGenerator from '../../dashboard/helper/filterQueryGenerator.js';
|
||||||
|
import actionQueryGenerator from '../../dashboard/helper/actionQueryGenerator.js';
|
||||||
|
import { required, requiredIf } from 'vuelidate/lib/validators';
|
||||||
|
|
||||||
|
export default {
|
||||||
|
validations: {
|
||||||
|
automation: {
|
||||||
|
name: {
|
||||||
|
required,
|
||||||
|
},
|
||||||
|
description: {
|
||||||
|
required,
|
||||||
|
},
|
||||||
|
event_name: {
|
||||||
|
required,
|
||||||
|
},
|
||||||
|
conditions: {
|
||||||
|
required,
|
||||||
|
$each: {
|
||||||
|
values: {
|
||||||
|
required: requiredIf(prop => {
|
||||||
|
return !(
|
||||||
|
prop.filter_operator === 'is_present' ||
|
||||||
|
prop.filter_operator === 'is_not_present'
|
||||||
|
);
|
||||||
|
}),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
actions: {
|
||||||
|
required,
|
||||||
|
$each: {
|
||||||
|
action_params: {
|
||||||
|
required: requiredIf(prop => {
|
||||||
|
return !(
|
||||||
|
prop.action_name === 'mute_conversation' ||
|
||||||
|
prop.action_name === 'snooze_conversation' ||
|
||||||
|
prop.action_name === 'resolve_conversation'
|
||||||
|
);
|
||||||
|
}),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
customAttributeInputType(key) {
|
||||||
|
switch (key) {
|
||||||
|
case 'date':
|
||||||
|
return 'date';
|
||||||
|
case 'text':
|
||||||
|
return 'plain_text';
|
||||||
|
case 'list':
|
||||||
|
return 'search_select';
|
||||||
|
case 'checkbox':
|
||||||
|
return 'search_select';
|
||||||
|
default:
|
||||||
|
return 'plain_text';
|
||||||
|
}
|
||||||
|
},
|
||||||
|
onEventChange() {
|
||||||
|
if (this.automation.event_name === 'message_created') {
|
||||||
|
this.automation.conditions = [
|
||||||
|
{
|
||||||
|
attribute_key: 'message_type',
|
||||||
|
filter_operator: 'equal_to',
|
||||||
|
values: '',
|
||||||
|
query_operator: 'and',
|
||||||
|
},
|
||||||
|
];
|
||||||
|
} else {
|
||||||
|
this.automation.conditions = [
|
||||||
|
{
|
||||||
|
attribute_key: 'status',
|
||||||
|
filter_operator: 'equal_to',
|
||||||
|
values: '',
|
||||||
|
query_operator: 'and',
|
||||||
|
},
|
||||||
|
];
|
||||||
|
}
|
||||||
|
this.automation.actions = [
|
||||||
|
{
|
||||||
|
action_name: 'assign_team',
|
||||||
|
action_params: [],
|
||||||
|
},
|
||||||
|
];
|
||||||
|
},
|
||||||
|
getAttributes(key) {
|
||||||
|
return this.automationTypes[key].conditions;
|
||||||
|
},
|
||||||
|
isACustomAttribute(key) {
|
||||||
|
return this.allCustomAttributes.find(attr => {
|
||||||
|
return attr.attribute_key === key;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
getInputType(key) {
|
||||||
|
const customAttribute = this.isACustomAttribute(key);
|
||||||
|
if (customAttribute) {
|
||||||
|
return this.customAttributeInputType(
|
||||||
|
customAttribute.attribute_display_type
|
||||||
|
);
|
||||||
|
}
|
||||||
|
const type = this.automationTypes[
|
||||||
|
this.automation.event_name
|
||||||
|
].conditions.find(condition => condition.key === key);
|
||||||
|
return type.inputType;
|
||||||
|
},
|
||||||
|
getOperators(key) {
|
||||||
|
if (this.mode === 'edit') {
|
||||||
|
const customAttribute = this.isACustomAttribute(key);
|
||||||
|
if (customAttribute) {
|
||||||
|
return this.getOperatorTypes(customAttribute.attribute_display_type);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
const type = this.automationTypes[
|
||||||
|
this.automation.event_name
|
||||||
|
].conditions.find(condition => condition.key === key);
|
||||||
|
return type.filterOperators;
|
||||||
|
},
|
||||||
|
getConditionDropdownValues(type) {
|
||||||
|
const statusFilters = this.$t('CHAT_LIST.CHAT_STATUS_FILTER_ITEMS');
|
||||||
|
const allCustomAttributes = this.$store.getters[
|
||||||
|
'attributes/getAttributes'
|
||||||
|
];
|
||||||
|
|
||||||
|
const isCustomAttributeCheckbox = allCustomAttributes.find(attr => {
|
||||||
|
return (
|
||||||
|
attr.attribute_key === type &&
|
||||||
|
attr.attribute_display_type === 'checkbox'
|
||||||
|
);
|
||||||
|
});
|
||||||
|
if (isCustomAttributeCheckbox) {
|
||||||
|
return [
|
||||||
|
{
|
||||||
|
id: true,
|
||||||
|
name: this.$t('FILTER.ATTRIBUTE_LABELS.TRUE'),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: false,
|
||||||
|
name: this.$t('FILTER.ATTRIBUTE_LABELS.FALSE'),
|
||||||
|
},
|
||||||
|
];
|
||||||
|
}
|
||||||
|
|
||||||
|
const isCustomAttributeList = allCustomAttributes.find(attr => {
|
||||||
|
return (
|
||||||
|
attr.attribute_key === type && attr.attribute_display_type === 'list'
|
||||||
|
);
|
||||||
|
});
|
||||||
|
|
||||||
|
if (isCustomAttributeList) {
|
||||||
|
return allCustomAttributes
|
||||||
|
.find(attr => attr.attribute_key === type)
|
||||||
|
.attribute_values.map(item => {
|
||||||
|
return {
|
||||||
|
id: item,
|
||||||
|
name: item,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (type) {
|
||||||
|
case 'status':
|
||||||
|
return [
|
||||||
|
...Object.keys(statusFilters).map(status => {
|
||||||
|
return {
|
||||||
|
id: status,
|
||||||
|
name: statusFilters[status].TEXT,
|
||||||
|
};
|
||||||
|
}),
|
||||||
|
{
|
||||||
|
id: 'all',
|
||||||
|
name: this.$t('CHAT_LIST.FILTER_ALL'),
|
||||||
|
},
|
||||||
|
];
|
||||||
|
case 'assignee_id':
|
||||||
|
return this.$store.getters['agents/getAgents'];
|
||||||
|
case 'contact':
|
||||||
|
return this.$store.getters['contacts/getContacts'];
|
||||||
|
case 'inbox_id':
|
||||||
|
return this.$store.getters['inboxes/getInboxes'];
|
||||||
|
case 'team_id':
|
||||||
|
return this.$store.getters['teams/getTeams'];
|
||||||
|
case 'campaign_id':
|
||||||
|
return this.$store.getters['campaigns/getAllCampaigns'].map(i => {
|
||||||
|
return {
|
||||||
|
id: i.id,
|
||||||
|
name: i.title,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
case 'labels':
|
||||||
|
return this.$store.getters['labels/getLabels'].map(i => {
|
||||||
|
return {
|
||||||
|
id: i.id,
|
||||||
|
name: i.title,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
case 'browser_language':
|
||||||
|
return languages;
|
||||||
|
case 'country_code':
|
||||||
|
return countries;
|
||||||
|
case 'message_type':
|
||||||
|
return [
|
||||||
|
{
|
||||||
|
id: 'incoming',
|
||||||
|
name: 'Incoming Message',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 'outgoing',
|
||||||
|
name: 'Outgoing Message',
|
||||||
|
},
|
||||||
|
];
|
||||||
|
default:
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
appendNewCondition() {
|
||||||
|
if (this.mode === 'edit') {
|
||||||
|
if (
|
||||||
|
!this.automation.conditions[this.automation.conditions.length - 1]
|
||||||
|
.query_operator
|
||||||
|
) {
|
||||||
|
this.automation.conditions[
|
||||||
|
this.automation.conditions.length - 1
|
||||||
|
].query_operator = 'and';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
switch (this.automation.event_name) {
|
||||||
|
case 'message_created':
|
||||||
|
this.automation.conditions.push({
|
||||||
|
attribute_key: 'message_type',
|
||||||
|
filter_operator: 'equal_to',
|
||||||
|
values: '',
|
||||||
|
query_operator: 'and',
|
||||||
|
});
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
this.automation.conditions.push({
|
||||||
|
attribute_key: 'status',
|
||||||
|
filter_operator: 'equal_to',
|
||||||
|
values: '',
|
||||||
|
query_operator: 'and',
|
||||||
|
});
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
appendNewAction() {
|
||||||
|
this.automation.actions.push({
|
||||||
|
action_name: 'assign_team',
|
||||||
|
action_params: [],
|
||||||
|
});
|
||||||
|
},
|
||||||
|
removeFilter(index) {
|
||||||
|
if (this.automation.conditions.length <= 1) {
|
||||||
|
this.showAlert(this.$t('AUTOMATION.CONDITION.DELETE_MESSAGE'));
|
||||||
|
} else {
|
||||||
|
this.automation.conditions.splice(index, 1);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
removeAction(index) {
|
||||||
|
if (this.automation.actions.length <= 1) {
|
||||||
|
this.showAlert(this.$t('AUTOMATION.ACTION.DELETE_MESSAGE'));
|
||||||
|
} else {
|
||||||
|
this.automation.actions.splice(index, 1);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
submitAutomation() {
|
||||||
|
this.$v.$touch();
|
||||||
|
if (this.$v.$invalid) return;
|
||||||
|
const automation = JSON.parse(JSON.stringify(this.automation));
|
||||||
|
automation.conditions[
|
||||||
|
automation.conditions.length - 1
|
||||||
|
].query_operator = null;
|
||||||
|
automation.conditions = filterQueryGenerator(
|
||||||
|
automation.conditions
|
||||||
|
).payload;
|
||||||
|
automation.actions = actionQueryGenerator(automation.actions);
|
||||||
|
this.$emit(
|
||||||
|
'saveAutomation',
|
||||||
|
automation,
|
||||||
|
this.mode === 'edit' ? 'EDIT' : null
|
||||||
|
);
|
||||||
|
},
|
||||||
|
resetFilter(index, currentCondition) {
|
||||||
|
this.automation.conditions[index].filter_operator = this.automationTypes[
|
||||||
|
this.automation.event_name
|
||||||
|
].conditions.find(
|
||||||
|
condition => condition.key === currentCondition.attribute_key
|
||||||
|
).filterOperators[0].value;
|
||||||
|
this.automation.conditions[index].values = '';
|
||||||
|
},
|
||||||
|
showUserInput(operatorType) {
|
||||||
|
if (operatorType === 'is_present' || operatorType === 'is_not_present')
|
||||||
|
return false;
|
||||||
|
return true;
|
||||||
|
},
|
||||||
|
showActionInput(actionName) {
|
||||||
|
if (actionName === 'send_email_to_team' || actionName === 'send_message')
|
||||||
|
return false;
|
||||||
|
const type = this.automationActionTypes.find(
|
||||||
|
action => action.key === actionName
|
||||||
|
).inputType;
|
||||||
|
if (type === null) return false;
|
||||||
|
return true;
|
||||||
|
},
|
||||||
|
resetAction(index) {
|
||||||
|
this.automation.actions[index].action_params = [];
|
||||||
|
},
|
||||||
|
formatAutomation(automation) {
|
||||||
|
const allCustomAttributes = this.$store.getters[
|
||||||
|
'attributes/getAttributes'
|
||||||
|
];
|
||||||
|
const customAttributes = allCustomAttributes.map(attr => {
|
||||||
|
return {
|
||||||
|
key: attr.attribute_key,
|
||||||
|
name: attr.attribute_display_name,
|
||||||
|
type: attr.attribute_display_type,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
const formattedConditions = automation.conditions.map(condition => {
|
||||||
|
const isCustomAttribute = customAttributes.find(
|
||||||
|
attr => attr.key === condition.attribute_key
|
||||||
|
);
|
||||||
|
let inputType = 'plain_text';
|
||||||
|
if (isCustomAttribute) {
|
||||||
|
inputType = this.customAttributeInputType(isCustomAttribute.type);
|
||||||
|
} else {
|
||||||
|
inputType = this.automationTypes[
|
||||||
|
automation.event_name
|
||||||
|
].conditions.find(item => item.key === condition.attribute_key)
|
||||||
|
.inputType;
|
||||||
|
}
|
||||||
|
if (inputType === 'plain_text') {
|
||||||
|
return {
|
||||||
|
...condition,
|
||||||
|
values: condition.values[0],
|
||||||
|
};
|
||||||
|
}
|
||||||
|
return {
|
||||||
|
...condition,
|
||||||
|
values: [
|
||||||
|
...this.getConditionDropdownValues(condition.attribute_key),
|
||||||
|
].filter(item => [...condition.values].includes(item.id)),
|
||||||
|
};
|
||||||
|
});
|
||||||
|
const formattedActions = automation.actions.map(action => {
|
||||||
|
let actionParams = [];
|
||||||
|
if (action.action_params.length) {
|
||||||
|
const inputType = this.automationActionTypes.find(
|
||||||
|
item => item.key === action.action_name
|
||||||
|
).inputType;
|
||||||
|
if (inputType === 'multi_select') {
|
||||||
|
actionParams = [
|
||||||
|
...this.getActionDropdownValues(action.action_name),
|
||||||
|
].filter(item => [...action.action_params].includes(item.id));
|
||||||
|
} else if (inputType === 'team_message') {
|
||||||
|
actionParams = {
|
||||||
|
team_ids: [
|
||||||
|
...this.getActionDropdownValues(action.action_name),
|
||||||
|
].filter(item =>
|
||||||
|
[...action.action_params[0].team_ids].includes(item.id)
|
||||||
|
),
|
||||||
|
message: action.action_params[0].message,
|
||||||
|
};
|
||||||
|
} else actionParams = [...action.action_params];
|
||||||
|
}
|
||||||
|
return {
|
||||||
|
...action,
|
||||||
|
action_params: actionParams,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
this.automation = {
|
||||||
|
...automation,
|
||||||
|
conditions: formattedConditions,
|
||||||
|
actions: formattedActions,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
getOperatorTypes(key) {
|
||||||
|
switch (key) {
|
||||||
|
case 'list':
|
||||||
|
return OPERATORS.OPERATOR_TYPES_1;
|
||||||
|
case 'text':
|
||||||
|
return OPERATORS.OPERATOR_TYPES_3;
|
||||||
|
case 'number':
|
||||||
|
return OPERATORS.OPERATOR_TYPES_1;
|
||||||
|
case 'link':
|
||||||
|
return OPERATORS.OPERATOR_TYPES_1;
|
||||||
|
case 'date':
|
||||||
|
return OPERATORS.OPERATOR_TYPES_4;
|
||||||
|
case 'checkbox':
|
||||||
|
return OPERATORS.OPERATOR_TYPES_1;
|
||||||
|
default:
|
||||||
|
return OPERATORS.OPERATOR_TYPES_1;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
getFileName(id, actionType) {
|
||||||
|
if (!id) return '';
|
||||||
|
if (actionType === 'send_attachment') {
|
||||||
|
const file = this.automation.files.find(item => item.blob_id === id);
|
||||||
|
if (file) return file.filename.toString();
|
||||||
|
}
|
||||||
|
return '';
|
||||||
|
},
|
||||||
|
getActionDropdownValues(type) {
|
||||||
|
switch (type) {
|
||||||
|
case 'assign_team':
|
||||||
|
case 'send_email_to_team':
|
||||||
|
return this.$store.getters['teams/getTeams'];
|
||||||
|
case 'add_label':
|
||||||
|
return this.$store.getters['labels/getLabels'].map(i => {
|
||||||
|
return {
|
||||||
|
id: i.title,
|
||||||
|
name: i.title,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
default:
|
||||||
|
return undefined;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
manifestCustomAttributes() {
|
||||||
|
const customAttributesRaw = this.$store.getters[
|
||||||
|
'attributes/getAttributes'
|
||||||
|
];
|
||||||
|
const customAttributeTypes = customAttributesRaw.map(attr => {
|
||||||
|
return {
|
||||||
|
key: attr.attribute_key,
|
||||||
|
name: attr.attribute_display_name,
|
||||||
|
inputType: this.customAttributeInputType(attr.attribute_display_type),
|
||||||
|
filterOperators: this.getOperatorTypes(attr.attribute_display_type),
|
||||||
|
};
|
||||||
|
});
|
||||||
|
this.automationTypes.message_created.conditions.push(
|
||||||
|
...customAttributeTypes
|
||||||
|
);
|
||||||
|
this.automationTypes.conversation_created.conditions.push(
|
||||||
|
...customAttributeTypes
|
||||||
|
);
|
||||||
|
this.automationTypes.conversation_updated.conditions.push(
|
||||||
|
...customAttributeTypes
|
||||||
|
);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
70
app/javascript/shared/mixins/specs/automationMixin.spec.js
Normal file
70
app/javascript/shared/mixins/specs/automationMixin.spec.js
Normal file
|
@ -0,0 +1,70 @@
|
||||||
|
import automationMixin from '../automationMixin';
|
||||||
|
import { shallowMount } from '@vue/test-utils';
|
||||||
|
import MockComponent from './MockComponent.vue';
|
||||||
|
|
||||||
|
describe('Automation Mixin function', () => {
|
||||||
|
const wrapper = shallowMount(MockComponent, {
|
||||||
|
mixins: [automationMixin],
|
||||||
|
});
|
||||||
|
|
||||||
|
it('customAttributeInputType should be defined', () => {
|
||||||
|
expect(wrapper.vm.customAttributeInputType).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('onEventChange should be defined', () => {
|
||||||
|
expect(wrapper.vm.onEventChange).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('getAttributes should be defined', () => {
|
||||||
|
expect(wrapper.vm.getAttributes).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('isACustomAttribute should be defined', () => {
|
||||||
|
expect(wrapper.vm.isACustomAttribute).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('getOperators should be defined', () => {
|
||||||
|
expect(wrapper.vm.getOperators).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('getConditionDropdownValues should be defined', () => {
|
||||||
|
expect(wrapper.vm.getConditionDropdownValues).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('appendNewCondition should be defined', () => {
|
||||||
|
expect(wrapper.vm.appendNewCondition).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('appendNewAction should be defined', () => {
|
||||||
|
expect(wrapper.vm.appendNewAction).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('removeFilter should be defined', () => {
|
||||||
|
expect(wrapper.vm.removeFilter).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('removeAction should be defined', () => {
|
||||||
|
expect(wrapper.vm.removeAction).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('submitAutomation should be defined', () => {
|
||||||
|
expect(wrapper.vm.submitAutomation).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('resetFilter should be defined', () => {
|
||||||
|
expect(wrapper.vm.resetFilter).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('showUserInput should be defined', () => {
|
||||||
|
expect(wrapper.vm.showUserInput).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('showActionInput should be defined', () => {
|
||||||
|
expect(wrapper.vm.showActionInput).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('resetAction should be defined', () => {
|
||||||
|
expect(wrapper.vm.resetAction).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('formatAutomation should be defined', () => {
|
||||||
|
expect(wrapper.vm.formatAutomation).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('getOperatorTypes should be defined', () => {
|
||||||
|
expect(wrapper.vm.getOperatorTypes).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('getFileName should be defined', () => {
|
||||||
|
expect(wrapper.vm.getFileName).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('getActionDropdownValues should be defined', () => {
|
||||||
|
expect(wrapper.vm.getActionDropdownValues).toBeTruthy();
|
||||||
|
});
|
||||||
|
it('manifestCustomAttributes should be defined', () => {
|
||||||
|
expect(wrapper.vm.manifestCustomAttributes).toBeTruthy();
|
||||||
|
});
|
||||||
|
});
|
Loading…
Reference in a new issue