chore: Use get app helper to get application data

This commit is contained in:
Faruk AYDIN
2022-10-06 15:49:05 +03:00
parent a58a59788d
commit 0825eb36e4
52 changed files with 139 additions and 1761 deletions

View File

@@ -1,15 +0,0 @@
import SendMessageToChannel from './actions/send-message-to-channel';
import FindMessage from './actions/find-message';
import SlackClient from './client';
export default class Actions {
client: SlackClient;
sendMessageToChannel: SendMessageToChannel;
findMessage: FindMessage;
constructor(client: SlackClient) {
this.client = client;
this.sendMessageToChannel = new SendMessageToChannel(client);
this.findMessage = new FindMessage(client);
}
}

View File

@@ -1,26 +0,0 @@
import SlackClient from '../client';
export default class FindMessage {
client: SlackClient;
constructor(client: SlackClient) {
this.client = client;
}
async run() {
const parameters = this.client.step.parameters;
const query = parameters.query as string;
const sortBy = parameters.sortBy as string;
const sortDirection = parameters.sortDirection as string;
const count = 1;
const messages = await this.client.findMessages.run(
query,
sortBy,
sortDirection,
count,
);
return messages;
}
}

View File

@@ -1,18 +0,0 @@
import SlackClient from '../client';
export default class SendMessageToChannel {
client: SlackClient;
constructor(client: SlackClient) {
this.client = client;
}
async run() {
const channelId = this.client.step.parameters.channel as string;
const text = this.client.step.parameters.message as string;
const message = await this.client.postMessageToChannel.run(channelId, text);
return message;
}
}

View File

@@ -1,7 +0,0 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"
aria-label="Slack" role="img"
viewBox="0 0 512 512"><rect
width="512" height="512"
rx="15%"
fill="#fff"/><g fill="#e01e5a"><path id="a" d="M149 305a39 39 0 01-78 0c0-22 17 -39 39 -39h39zM168 305a39 39 0 0178 0v97a39 39 0 01-78 0z"/></g><use xlink:href="#a" fill="#36c5f0" transform="rotate(90,256,256)"/><use xlink:href="#a" fill="#2eb67d" transform="rotate(180,256,256)"/><use xlink:href="#a" fill="#ecb22e" transform="rotate(270,256,256)"/></svg>

Before

Width:  |  Height:  |  Size: 533 B

View File

@@ -1,36 +0,0 @@
import type { IAuthentication, IJSONObject } from '@automatisch/types';
import SlackClient from './client';
export default class Authentication implements IAuthentication {
client: SlackClient;
static requestOptions: IJSONObject = {
headers: {
'Content-Type': 'application/x-www-form-urlencoded',
},
};
constructor(client: SlackClient) {
this.client = client;
}
async verifyCredentials() {
const { bot_id: botId, user: screenName } =
await this.client.verifyAccessToken.run();
return {
botId,
screenName,
token: this.client.connection.formattedData.accessToken,
};
}
async isStillVerified() {
try {
await this.client.verifyAccessToken.run();
return true;
} catch (error) {
return false;
}
}
}

View File

@@ -1,44 +0,0 @@
import SlackClient from '../index';
export default class FindMessages {
client: SlackClient;
constructor(client: SlackClient) {
this.client = client;
}
async run(query: string, sortBy: string, sortDirection: string, count = 1) {
const headers = {
Authorization: `Bearer ${this.client.connection.formattedData.accessToken}`,
};
const params = {
query,
sort: sortBy,
sort_dir: sortDirection,
count,
};
const response = await this.client.httpClient.get('/search.messages', {
headers,
params,
});
const data = response.data;
if (!data.ok) {
if (data.error === 'missing_scope') {
throw new Error(
`Error occured while finding messages; ${data.error}: ${data.needed}`
);
}
throw new Error(`Error occured while finding messages; ${data.error}`);
}
const messages = data.messages.matches;
const message = messages?.[0];
return message;
}
}

View File

@@ -1,44 +0,0 @@
import SlackClient from '../index';
import { IJSONObject } from '@automatisch/types';
export default class PostMessageToChannel {
client: SlackClient;
constructor(client: SlackClient) {
this.client = client;
}
async run(channelId: string, text: string) {
const message: {
data: IJSONObject | null;
error: IJSONObject | null;
} = {
data: null,
error: null,
};
const headers = {
Authorization: `Bearer ${this.client.connection.formattedData.accessToken}`,
};
const params = {
channel: channelId,
text,
};
const response = await this.client.httpClient.post(
'/chat.postMessage',
params,
{ headers }
);
message.error = response?.integrationError;
message.data = response?.data?.message;
if (response.data.ok === false) {
message.error = response.data;
}
return message;
}
}

View File

@@ -1,35 +0,0 @@
import { IJSONObject } from '@automatisch/types';
import qs from 'qs';
import SlackClient from '../index';
export default class VerifyAccessToken {
client: SlackClient;
static requestOptions: IJSONObject = {
headers: {
'Content-Type': 'application/x-www-form-urlencoded',
},
};
constructor(client: SlackClient) {
this.client = client;
}
async run() {
const response = await this.client.httpClient.post(
'/auth.test',
qs.stringify({
token: this.client.connection.formattedData.accessToken,
}),
VerifyAccessToken.requestOptions
);
if (response.data.ok === false) {
throw new Error(
`Error occured while verifying credentials: ${response.data.error}.(More info: https://api.slack.com/methods/auth.test#errors)`
);
}
return response.data;
}
}

View File

@@ -1,29 +0,0 @@
import { IFlow, IStep, IConnection } from '@automatisch/types';
import createHttpClient, { IHttpClient } from '../../../helpers/http-client';
import VerifyAccessToken from './endpoints/verify-access-token';
import PostMessageToChannel from './endpoints/post-message-to-channel';
import FindMessages from './endpoints/find-messages';
export default class SlackClient {
flow: IFlow;
step: IStep;
connection: IConnection;
httpClient: IHttpClient;
verifyAccessToken: VerifyAccessToken;
postMessageToChannel: PostMessageToChannel;
findMessages: FindMessages;
static baseUrl = 'https://slack.com/api';
constructor(connection: IConnection, flow?: IFlow, step?: IStep) {
this.connection = connection;
this.flow = flow;
this.step = step;
this.httpClient = createHttpClient({ baseURL: SlackClient.baseUrl });
this.verifyAccessToken = new VerifyAccessToken(this);
this.postMessageToChannel = new PostMessageToChannel(this);
this.findMessages = new FindMessages(this);
}
}

View File

@@ -1,12 +0,0 @@
import ListChannels from './data/list-channels';
import SlackClient from './client';
export default class Data {
client: SlackClient;
listChannels: ListChannels;
constructor(client: SlackClient) {
this.client = client;
this.listChannels = new ListChannels(client);
}
}

View File

@@ -1,31 +0,0 @@
import { IJSONObject } from '@automatisch/types';
import SlackClient from '../client';
export default class ListChannels {
client: SlackClient;
constructor(client: SlackClient) {
this.client = client;
}
async run() {
const response = await this.client.httpClient.get('/conversations.list', {
headers: {
Authorization: `Bearer ${this.client.connection.formattedData.accessToken}`,
},
});
if (response.data.ok === 'false') {
throw new Error(
`Error occured while fetching slack channels: ${response.data.error}`
);
}
return response.data.channels.map((channel: IJSONObject) => {
return {
value: channel.id,
name: channel.name,
};
});
}
}

View File

@@ -1,30 +0,0 @@
import {
IService,
IAuthentication,
IConnection,
IFlow,
IStep,
} from '@automatisch/types';
import Authentication from './authentication';
import Triggers from './triggers';
import Actions from './actions';
import Data from './data';
import SlackClient from './client';
export default class Slack implements IService {
client: SlackClient;
authenticationClient: IAuthentication;
triggers: Triggers;
actions: Actions;
data: Data;
constructor(connection: IConnection, flow?: IFlow, step?: IStep) {
this.client = new SlackClient(connection, flow, step);
this.authenticationClient = new Authentication(this.client);
// this.triggers = new Triggers(this.client);
this.actions = new Actions(this.client);
this.data = new Data(this.client);
}
}

View File

@@ -1,278 +0,0 @@
{
"name": "Slack",
"key": "slack",
"iconUrl": "{BASE_URL}/apps/slack/assets/favicon.svg",
"docUrl": "https://automatisch.io/docs/slack",
"authDocUrl": "https://automatisch.io/docs/connections/slack",
"primaryColor": "2DAAE1",
"supportsConnections": true,
"baseUrl": "https://slack.com/api",
"fields": [
{
"key": "accessToken",
"label": "Access Token",
"type": "string",
"required": true,
"readOnly": false,
"value": null,
"placeholder": null,
"description": "Access token of slack that Automatisch will connect to.",
"clickToCopy": false
}
],
"authenticationSteps": [
{
"step": 1,
"type": "mutation",
"name": "createConnection",
"arguments": [
{
"name": "key",
"value": "{key}"
},
{
"name": "formattedData",
"value": null,
"properties": [
{
"name": "accessToken",
"value": "{fields.accessToken}"
}
]
}
]
},
{
"step": 2,
"type": "mutation",
"name": "verifyConnection",
"arguments": [
{
"name": "id",
"value": "{createConnection.id}"
}
]
}
],
"reconnectionSteps": [
{
"step": 1,
"type": "mutation",
"name": "resetConnection",
"arguments": [
{
"name": "id",
"value": "{connection.id}"
}
]
},
{
"step": 2,
"type": "mutation",
"name": "updateConnection",
"arguments": [
{
"name": "id",
"value": "{connection.id}"
},
{
"name": "formattedData",
"value": null,
"properties": [
{
"name": "accessToken",
"value": "{fields.accessToken}"
}
]
}
]
},
{
"step": 3,
"type": "mutation",
"name": "verifyConnection",
"arguments": [
{
"name": "id",
"value": "{connection.id}"
}
]
}
],
"triggers": [
{
"name": "New message posted to a channel",
"key": "newMessageToChannel",
"pollInterval": 15,
"description": "Triggers when a new message is posted to a channel",
"substeps": [
{
"key": "chooseConnection",
"name": "Choose connection"
},
{
"key": "chooseTrigger",
"name": "Set up a trigger",
"arguments": [
{
"label": "Channel",
"key": "channel",
"type": "dropdown",
"required": true,
"variables": false,
"source": {
"type": "query",
"name": "getData",
"arguments": [
{
"name": "key",
"value": "listChannels"
}
]
}
},
{
"label": "Trigger for Bot Messages?",
"key": "triggerForBotMessages",
"type": "dropdown",
"description": "Should this flow trigger for bot messages?",
"required": true,
"value": true,
"variables": false,
"options": [
{
"label": "Yes",
"value": true
},
{
"label": "No",
"value": false
}
]
}
]
},
{
"key": "testStep",
"name": "Test trigger"
}
]
}
],
"actions": [
{
"name": "Send a message to channel",
"key": "sendMessageToChannel",
"description": "Send a message to a specific channel you specify.",
"substeps": [
{
"key": "chooseConnection",
"name": "Choose connection"
},
{
"key": "setupAction",
"name": "Set up action",
"arguments": [
{
"label": "Channel",
"key": "channel",
"type": "dropdown",
"required": true,
"description": "Pick a channel to send the message to.",
"variables": false,
"source": {
"type": "query",
"name": "getData",
"arguments": [
{
"name": "key",
"value": "listChannels"
}
]
}
},
{
"label": "Message text",
"key": "message",
"type": "string",
"required": true,
"description": "The content of your new message.",
"variables": true
}
]
},
{
"key": "testStep",
"name": "Test action"
}
]
},
{
"name": "Find message",
"key": "findMessage",
"description": "Find a Slack message using the Slack Search feature.",
"substeps": [
{
"key": "chooseConnection",
"name": "Choose connection"
},
{
"key": "setupAction",
"name": "Set up action",
"arguments": [
{
"label": "Search Query",
"key": "query",
"type": "string",
"required": true,
"description": "Search query to use for finding matching messages. See the Slack Search Documentation for more information on constructing a query.",
"variables": true
},
{
"label": "Sort by",
"key": "sortBy",
"type": "dropdown",
"description": "Sort messages by their match strength or by their date. Default is score.",
"required": true,
"value": "score",
"variables": false,
"options": [
{
"label": "Match strength",
"value": "score"
},
{
"label": "Message date time",
"value": "timestamp"
}
]
},
{
"label": "Sort direction",
"key": "sortDirection",
"type": "dropdown",
"description": "Sort matching messages in ascending or descending order. Default is descending.",
"required": true,
"value": "desc",
"variables": false,
"options": [
{
"label": "Descending (newest or best match first)",
"value": "desc"
},
{
"label": "Ascending (oldest or worst match first)",
"value": "asc"
}
]
}
]
},
{
"key": "testStep",
"name": "Test action"
}
]
}
]
}

View File

@@ -1,13 +0,0 @@
import { IJSONObject } from '@automatisch/types';
import NewMessageToChannel from './triggers/new-message-to-channel';
export default class Triggers {
newMessageToChannel: NewMessageToChannel;
constructor(connectionData: IJSONObject, parameters: IJSONObject) {
this.newMessageToChannel = new NewMessageToChannel(
connectionData,
parameters
);
}
}

View File

@@ -1,47 +0,0 @@
import { IJSONObject } from '@automatisch/types';
import axios, { AxiosInstance } from 'axios';
export default class NewMessageToChannel {
httpClient: AxiosInstance;
parameters: IJSONObject;
connectionData: IJSONObject;
BASE_URL = 'https://slack.com/api';
constructor(connectionData: IJSONObject, parameters: IJSONObject) {
this.httpClient = axios.create({ baseURL: this.BASE_URL });
this.connectionData = connectionData;
this.parameters = parameters;
}
async run() {
// TODO: Fix after webhook implementation.
}
async testRun() {
const headers = {
Authorization: `Bearer ${this.connectionData.accessToken}`,
};
const params = {
channel: this.parameters.channel,
};
const response = await this.httpClient.get('/conversations.history', {
headers,
params,
});
let lastMessage;
if (this.parameters.triggerForBotMessages) {
lastMessage = response.data.messages[0];
} else {
lastMessage = response.data.messages.find(
(message: IJSONObject) =>
!Object.prototype.hasOwnProperty.call(message, 'bot_id')
);
}
return [lastMessage];
}
}