Feature: Slack - receive messages, create threads, send replies (#974)

Co-authored-by: Pranav Raj S <pranav@thoughtwoot.com>
This commit is contained in:
Sojan Jose
2020-06-22 13:19:26 +05:30
committed by GitHub
parent aa8a85b8bd
commit 1ef8d03e18
53 changed files with 815 additions and 188 deletions

View File

@@ -2,7 +2,7 @@
<div class="settings-header">
<h1 class="page-title">
<woot-sidemenu-icon></woot-sidemenu-icon>
<back-button v-if="showBackButton"></back-button>
<back-button v-if="showBackButton" :back-url="backUrl"></back-button>
<i :class="iconClass"></i>
<span>{{ headerTitle }}</span>
</h1>
@@ -45,6 +45,10 @@ export default {
},
showBackButton: { type: Boolean, default: false },
showNewButton: { type: Boolean, default: false },
backUrl: {
type: [String, Object],
default: '',
},
},
computed: {
...mapGetters({

View File

@@ -6,6 +6,7 @@
:header-title="$t(headerTitle)"
:button-text="$t(headerButtonText)"
:show-back-button="showBackButton"
:back-url="backUrl"
:show-new-button="showNewButton"
/>
<keep-alive>
@@ -34,6 +35,10 @@ export default {
type: Boolean,
default: false,
},
backUrl: {
type: [String, Object],
default: '',
},
},
data() {
return {};

View File

@@ -3,38 +3,19 @@
<div class="row">
<div class="small-8 columns integrations-wrap">
<div class="row integrations">
<div class="small-12 columns integration">
<div class="row">
<div class="integration--image">
<img src="~dashboard/assets/images/integrations/cable.svg" />
</div>
<div class="column">
<h3 class="integration--title">
{{ $t('INTEGRATION_SETTINGS.WEBHOOK.TITLE') }}
</h3>
<p class="integration--description">
{{
useInstallationName(
$t('INTEGRATION_SETTINGS.WEBHOOK.INTEGRATION_TXT'),
globalConfig.installationName
)
}}
</p>
</div>
<div class="small-2 column button-wrap">
<router-link
:to="
frontendURL(
`accounts/${accountId}/settings/integrations/webhook`
)
"
>
<button class="button success nice">
{{ $t('INTEGRATION_SETTINGS.WEBHOOK.CONFIGURE') }}
</button>
</router-link>
</div>
</div>
<div
v-for="item in integrationsList"
:key="item.id"
class="small-12 columns integration"
>
<integration
:integration-id="item.id"
:integration-logo="item.logo"
:integration-name="item.name"
:integration-description="item.description"
:integration-enabled="item.enabled"
:integration-action="item.action"
/>
</div>
</div>
</div>
@@ -43,20 +24,19 @@
</template>
<script>
import { mapGetters } from 'vuex';
import { frontendURL } from '../../../../helper/URLHelper';
import globalConfigMixin from 'shared/mixins/globalConfigMixin';
import Integration from './Integration';
export default {
mixins: [globalConfigMixin],
components: {
Integration,
},
computed: {
...mapGetters({
currentUser: 'getCurrentUser',
globalConfig: 'globalConfig/get',
accountId: 'getCurrentAccountId',
integrationsList: 'integrations/getIntegrations',
}),
},
methods: {
frontendURL,
mounted() {
this.$store.dispatch('integrations/get');
},
};
</script>

View File

@@ -0,0 +1,114 @@
<template>
<div class="row">
<div class="integration--image">
<img :src="'/assets/dashboard/integrations/' + integrationLogo" />
</div>
<div class="column">
<h3 class="integration--title">
{{ integrationName }}
</h3>
<p class="integration--description">
{{ integrationDescription }}
</p>
</div>
<div class="small-2 column button-wrap">
<router-link
:to="
frontendURL(
`accounts/${accountId}/settings/integrations/` + integrationId
)
"
>
<div v-if="integrationEnabled">
<div v-if="integrationAction === 'disconnect'">
<div @click="openDeletePopup()">
<woot-submit-button
:button-text="
$t('INTEGRATION_SETTINGS.WEBHOOK.DELETE.BUTTON_TEXT')
"
icon-class="ion-close-circled"
button-class="nice alert"
/>
</div>
</div>
<div v-else>
<button class="button nice">
{{ $t('INTEGRATION_SETTINGS.WEBHOOK.CONFIGURE') }}
</button>
</div>
</div>
</router-link>
<div v-if="!integrationEnabled">
<a :href="integrationAction" class="button success nice">
{{ $t('INTEGRATION_SETTINGS.CONNECT.BUTTON_TEXT') }}
</a>
</div>
</div>
<woot-delete-modal
:show.sync="showDeleteConfirmationPopup"
:on-close="closeDeletePopup"
:on-confirm="confirmDeletion"
:title="$t('INTEGRATION_SETTINGS.WEBHOOK.DELETE.CONFIRM.TITLE')"
:message="$t('INTEGRATION_SETTINGS.WEBHOOK.DELETE.CONFIRM.MESSAGE')"
:confirm-text="$t('INTEGRATION_SETTINGS.WEBHOOK.DELETE.CONFIRM.YES')"
:reject-text="$t('INTEGRATION_SETTINGS.WEBHOOK.DELETE.CONFIRM.NO')"
/>
</div>
</template>
<script>
import { mapGetters } from 'vuex';
import { frontendURL } from '../../../../helper/URLHelper';
import alertMixin from 'shared/mixins/alertMixin';
export default {
mixins: [alertMixin],
props: [
'integrationId',
'integrationLogo',
'integrationName',
'integrationDescription',
'integrationEnabled',
'integrationAction',
],
data() {
return {
showDeleteConfirmationPopup: false,
};
},
computed: {
...mapGetters({
currentUser: 'getCurrentUser',
accountId: 'getCurrentAccountId',
}),
},
methods: {
frontendURL,
openDeletePopup() {
this.showDeleteConfirmationPopup = true;
},
closeDeletePopup() {
this.showDeleteConfirmationPopup = false;
},
confirmDeletion() {
this.closeDeletePopup();
this.deleteIntegration(this.deleteIntegration);
this.$router.push({ name: 'settings_integrations' });
},
async deleteIntegration() {
try {
await this.$store.dispatch(
'integrations/deleteIntegration',
this.integrationId
);
this.showAlert(
this.$t('INTEGRATION_SETTINGS.DELETE.API.SUCCESS_MESSAGE')
);
} catch (error) {
this.showAlert(
this.$t('INTEGRATION_SETTINGS.WEBHOOK.DELETE.API.ERROR_MESSAGE')
);
}
},
},
};
</script>

View File

@@ -0,0 +1,70 @@
<template>
<div class="column content-box">
<div class="row">
<div class="small-8 columns integrations-wrap">
<div class="row integrations">
<div v-if="integrationLoaded" class="small-12 columns integration">
<integration
:integration-id="integration.id"
:integration-logo="integration.logo"
:integration-name="integration.name"
:integration-description="integration.description"
:integration-enabled="integration.enabled"
:integration-action="integrationAction()"
/>
</div>
</div>
</div>
</div>
</div>
</template>
<script>
import { mapGetters } from 'vuex';
import globalConfigMixin from 'shared/mixins/globalConfigMixin';
import Integration from './Integration';
export default {
components: {
Integration,
},
mixins: [globalConfigMixin],
props: ['integrationId', 'code'],
data() {
return {
integrationLoaded: false,
};
},
computed: {
integration() {
return this.$store.getters['integrations/getIntegration'](
this.integrationId
);
},
...mapGetters({
currentUser: 'getCurrentUser',
globalConfig: 'globalConfig/get',
accountId: 'getCurrentAccountId',
}),
},
mounted() {
this.intializeSlackIntegration();
},
methods: {
integrationAction() {
if (this.integration.enabled) {
return 'disconnect';
}
return this.integration.action;
},
async intializeSlackIntegration() {
await this.$store.dispatch('integrations/get', this.integrationId);
if (this.code) {
await this.$store.dispatch('integrations/connectSlack', this.code);
// we are clearing code from the path as subsequent request would throw error
this.$router.replace(this.$route.path);
}
this.integrationLoaded = true;
},
},
};
</script>

View File

@@ -82,16 +82,16 @@
</div>
</template>
<script>
/* global bus */
import { mapGetters } from 'vuex';
import NewWebhook from './New';
import alertMixin from 'shared/mixins/alertMixin';
import globalConfigMixin from 'shared/mixins/globalConfigMixin';
export default {
components: {
NewWebhook,
},
mixins: [globalConfigMixin],
mixins: [alertMixin, globalConfigMixin],
data() {
return {
loading: {},
@@ -111,9 +111,6 @@ export default {
this.$store.dispatch('webhooks/get');
},
methods: {
showAlert(message) {
bus.$emit('newToastMessage', message);
},
openAddPopup() {
this.showAddPopup = true;
},

View File

@@ -1,6 +1,7 @@
import Index from './Index';
import SettingsContent from '../Wrapper';
import Webhook from './Webhook';
import ShowIntegration from './ShowIntegration';
import { frontendURL } from '../../../../helper/URLHelper';
export default {
@@ -10,10 +11,15 @@ export default {
component: SettingsContent,
props: params => {
const showBackButton = params.name !== 'settings_integrations';
const backUrl =
params.name === 'settings_integrations_integration'
? { name: 'settings_integrations' }
: '';
return {
headerTitle: 'INTEGRATION_SETTINGS.HEADER',
icon: 'ion-flash',
showBackButton,
backUrl,
};
},
children: [
@@ -29,6 +35,18 @@ export default {
name: 'settings_integrations_webhook',
roles: ['administrator'],
},
{
path: ':integration_id',
name: 'settings_integrations_integration',
component: ShowIntegration,
roles: ['administrator'],
props: route => {
return {
integrationId: route.params.integration_id,
code: route.query.code,
};
},
},
],
},
],