feat: Toggle automation status (#3991)

This commit is contained in:
Muhsin Keloth 2022-03-01 14:14:23 +05:30 committed by GitHub
parent a3cb26a317
commit f08d1b35d0
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
8 changed files with 185 additions and 12 deletions

View file

@ -3,7 +3,7 @@ class Api::V1::Accounts::AutomationRulesController < Api::V1::Accounts::BaseCont
before_action :fetch_automation_rule, only: [:show, :update, :destroy, :clone] before_action :fetch_automation_rule, only: [:show, :update, :destroy, :clone]
def index def index
@automation_rules = Current.account.automation_rules.active @automation_rules = Current.account.automation_rules
end end
def create def create
@ -32,7 +32,7 @@ class Api::V1::Accounts::AutomationRulesController < Api::V1::Accounts::BaseCont
def automation_rules_permit def automation_rules_permit
params.permit( params.permit(
:name, :description, :event_name, :account_id, :name, :description, :event_name, :account_id, :active,
conditions: [:attribute_key, :filter_operator, :query_operator, { values: [] }], conditions: [:attribute_key, :filter_operator, :query_operator, { values: [] }],
actions: [:action_name, { action_params: [] }] actions: [:action_name, { action_params: [] }]
) )

View file

@ -21,6 +21,7 @@ import SubmitButton from './buttons/FormSubmitButton';
import Tabs from './ui/Tabs/Tabs'; import Tabs from './ui/Tabs/Tabs';
import TabsItem from './ui/Tabs/TabsItem'; import TabsItem from './ui/Tabs/TabsItem';
import Thumbnail from './widgets/Thumbnail.vue'; import Thumbnail from './widgets/Thumbnail.vue';
import ConfirmModal from './widgets/modal/ConfirmationModal.vue';
const WootUIKit = { const WootUIKit = {
AvatarUploader, AvatarUploader,
@ -45,6 +46,7 @@ const WootUIKit = {
Tabs, Tabs,
TabsItem, TabsItem,
Thumbnail, Thumbnail,
ConfirmModal,
install(Vue) { install(Vue) {
const keys = Object.keys(this); const keys = Object.keys(this);
keys.pop(); // remove 'install' from keys keys.pop(); // remove 'install' from keys

View file

@ -20,7 +20,8 @@
data-view-component="true" data-view-component="true"
label="Beta" label="Beta"
class="beta" class="beta"
>Beta >
{{ $t('SIDEBAR.BETA') }}
</span> </span>
</router-link> </router-link>
@ -233,7 +234,7 @@ export default {
padding-left: var(--space-smaller) !important; padding-left: var(--space-smaller) !important;
margin-left: var(--space-half) !important; margin-left: var(--space-half) !important;
display: inline-block; display: inline-block;
font-size: var(--font-size-mini); font-size: var(--font-size-micro);
font-weight: var(--font-weight-medium); font-weight: var(--font-weight-medium);
line-height: 18px; line-height: 18px;
border: 1px solid transparent; border: 1px solid transparent;

View file

@ -0,0 +1,75 @@
<template>
<modal :show.sync="show" :on-close="cancel">
<div class="column content-box">
<woot-modal-header :header-title="title"> </woot-modal-header>
<div class="row modal-content">
<div class="medium-12 columns">
<p>
{{ description }}
</p>
</div>
<div class="modal-footer">
<div class="medium-12 columns">
<woot-button @click="confirm">
{{ confirmLabel }}
</woot-button>
<button class="button clear" @click="cancel">
{{ cancelLabel }}
</button>
</div>
</div>
</div>
</div>
</modal>
</template>
<script>
import Modal from '../../Modal';
export default {
components: {
Modal,
},
props: {
title: {
type: String,
default: 'This is a title',
},
description: {
type: String,
default: 'This is your description',
},
confirmLabel: {
type: String,
default: 'Yes',
},
cancelLabel: {
type: String,
default: 'No',
},
},
data: () => ({
show: false,
resolvePromise: undefined,
rejectPromise: undefined,
}),
methods: {
showConfirmation() {
this.show = true;
return new Promise((resolve, reject) => {
this.resolvePromise = resolve;
this.rejectPromise = reject;
});
},
confirm() {
this.resolvePromise(true);
this.show = false;
},
cancel() {
this.resolvePromise(false);
this.show = false;
},
},
};
</script>

View file

@ -90,6 +90,18 @@
}, },
"ACTION": { "ACTION": {
"DELETE_MESSAGE": "You need to have atleast one action to save" "DELETE_MESSAGE": "You need to have atleast one action to save"
},
"TOGGLE": {
"ACTIVATION_TITLE": "Activate Automation Rule",
"DEACTIVATION_TITLE": "Deactivate Automation Rule",
"ACTIVATION_DESCRIPTION": "This action will activate the automation rule '{automationName}'. Are you sure you want to proceed?",
"DEACTIVATION_DESCRIPTION": "This action will deactivate the automation rule '{automationName}'. Are you sure you want to proceed?",
"ACTIVATION_SUCCESFUL": "Automation Rule Activated Successfully",
"DEACTIVATION_SUCCESFUL": "Automation Rule Deactivated Successfully",
"ACTIVATION_ERROR": "Could not Activate Automation, Please try again later",
"DEACTIVATION_ERROR": "Could not Deactivate Automation, Please try again later",
"CONFIRMATION_LABEL": "Yes",
"CANCEL_LABEL": "No"
} }
} }
} }

View file

@ -178,7 +178,8 @@
"REPORTS_LABEL": "Labels", "REPORTS_LABEL": "Labels",
"REPORTS_INBOX": "Inbox", "REPORTS_INBOX": "Inbox",
"REPORTS_TEAM": "Team", "REPORTS_TEAM": "Team",
"SET_AVAILABILITY_TITLE": "Set yourself as" "SET_AVAILABILITY_TITLE": "Set yourself as",
"BETA": "Beta"
}, },
"CREATE_ACCOUNT": { "CREATE_ACCOUNT": {
"NO_ACCOUNT_WARNING": "Uh oh! We could not find any Chatwoot accounts. Please create a new account to continue.", "NO_ACCOUNT_WARNING": "Uh oh! We could not find any Chatwoot accounts. Please create a new account to continue.",

View file

@ -34,12 +34,19 @@
<td>{{ automation.name }}</td> <td>{{ automation.name }}</td>
<td>{{ automation.description }}</td> <td>{{ automation.description }}</td>
<td> <td>
<fluent-icon <button
v-if="automation.active" type="button"
icon="checkmark-square" class="toggle-button"
type="solid" :class="{ active: automation.active }"
/> role="switch"
<fluent-icon v-else icon="square" /> :aria-checked="automation.active.toString()"
@click="toggleAutomation(automation, automation.active)"
>
<span
aria-hidden="true"
:class="{ active: automation.active }"
></span>
</button>
</td> </td>
<td>{{ readableTime(automation.created_on) }}</td> <td>{{ readableTime(automation.created_on) }}</td>
<td class="button-wrapper"> <td class="button-wrapper">
@ -120,6 +127,11 @@
@saveAutomation="submitAutomation" @saveAutomation="submitAutomation"
/> />
</woot-modal> </woot-modal>
<woot-confirm-modal
ref="confirmDialog"
:title="toggleModalTitle"
:description="toggleModalDescription"
/>
</div> </div>
</template> </template>
<script> <script>
@ -142,6 +154,10 @@ export default {
showEditPopup: false, showEditPopup: false,
showDeleteConfirmationPopup: false, showDeleteConfirmationPopup: false,
selectedResponse: {}, selectedResponse: {},
toggleModalTitle: this.$t('AUTOMATION.TOGGLE.ACTIVATION_TITLE'),
toggleModalDescription: this.$t(
'AUTOMATION.TOGGLE.ACTIVATION_DESCRIPTION'
),
}; };
}, },
computed: { computed: {
@ -235,6 +251,34 @@ export default {
this.showAlert(errorMessage); this.showAlert(errorMessage);
} }
}, },
async toggleAutomation(automation, status) {
try {
this.toggleModalTitle = status
? this.$t('AUTOMATION.TOGGLE.DEACTIVATION_TITLE')
: this.$t('AUTOMATION.TOGGLE.ACTIVATION_TITLE');
this.toggleModalDescription = status
? this.$t('AUTOMATION.TOGGLE.DEACTIVATION_DESCRIPTION', {
automationName: automation.name,
})
: this.$t('AUTOMATION.TOGGLE.ACTIVATION_DESCRIPTION', {
automationName: automation.name,
});
// Check if uses confirms to proceed
const ok = await this.$refs.confirmDialog.showConfirmation();
if (ok) {
await await this.$store.dispatch('automations/update', {
id: automation.id,
active: !status,
});
const message = status
? this.$t('AUTOMATION.TOGGLE.DEACTIVATION_SUCCESFUL')
: this.$t('AUTOMATION.TOGGLE.ACTIVATION_SUCCESFUL');
this.showAlert(message);
}
} catch (error) {
this.showAlert(this.$t('AUTOMATION.EDIT.API.ERROR_MESSAGE'));
}
},
readableTime(date) { readableTime(date) {
return this.messageStamp(new Date(date), 'LLL d, h:mm a'); return this.messageStamp(new Date(date), 'LLL d, h:mm a');
}, },
@ -246,4 +290,41 @@ export default {
.automation__status-checkbox { .automation__status-checkbox {
margin: 0; margin: 0;
} }
.toggle-button {
background-color: var(--s-200);
position: relative;
display: inline-flex;
height: 19px;
width: 34px;
border: 2px solid transparent;
border-radius: var(--border-radius-large);
cursor: pointer;
transition-property: background-color;
transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);
transition-duration: 200ms;
flex-shrink: 0;
}
.toggle-button.active {
background-color: var(--w-500);
}
.toggle-button span {
--space-one-point-five: 1.5rem;
height: var(--space-one-point-five);
width: var(--space-one-point-five);
display: inline-block;
background-color: var(--white);
box-shadow: rgb(255, 255, 255) 0px 0px 0px 0px,
rgba(59, 130, 246, 0.5) 0px 0px 0px 0px, rgba(0, 0, 0, 0.1) 0px 1px 3px 0px,
rgba(0, 0, 0, 0.06) 0px 1px 2px 0px;
transform: translate(0, 0);
border-radius: 100%;
transition-property: transform;
transition-timing-function: cubic-bezier(0.4, 0, 0.2, 1);
transition-duration: 200ms;
}
.toggle-button span.active {
transform: translate(var(--space-one-point-five), var(--space-zero));
}
</style> </style>

View file

@ -45,7 +45,8 @@ class AutomationRuleListener < BaseListener
@rules = AutomationRule.where( @rules = AutomationRule.where(
event_name: event_name, event_name: event_name,
account_id: conversation.account_id account_id: conversation.account_id,
active: true
) )
@rules.any? @rules.any?
end end