@proca/cli 3.4.5 → 3.8.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1991 -61
- package/package.json +88 -72
- package/proca-cli +8 -0
- package/src/commands/action/add.mjs +192 -0
- package/src/commands/action/confirm.mjs +93 -0
- package/src/commands/action/count.mjs +61 -0
- package/src/commands/action/list.mjs +204 -0
- package/src/commands/action/replay.mjs +56 -0
- package/src/commands/action/requeue.mjs +156 -0
- package/src/commands/campaign/add.mjs +113 -0
- package/src/commands/campaign/copy.mjs +91 -0
- package/src/commands/campaign/delete.mjs +41 -0
- package/src/commands/campaign/get.mjs +132 -0
- package/src/commands/campaign/list.mjs +161 -0
- package/src/commands/campaign/mtt.mjs +131 -0
- package/src/commands/campaign/queries.graphql +19 -0
- package/src/commands/campaign/status.mjs +63 -0
- package/src/commands/campaign/widget/archive.mjs +124 -0
- package/src/commands/campaign/widget/copy.mjs +175 -0
- package/src/commands/campaign/widget/get.mjs +19 -0
- package/src/commands/campaign/widget/index.mjs +17 -0
- package/src/commands/campaign/widget/rebuild.mjs +50 -0
- package/src/commands/config/add.mjs +97 -0
- package/src/commands/config/folder.mjs +42 -0
- package/src/commands/config/server.mjs +33 -0
- package/src/commands/config/set.mjs +103 -0
- package/src/commands/config/user.mjs +79 -0
- package/src/commands/contact/count.mjs +41 -0
- package/src/commands/contact/list.mjs +207 -0
- package/src/commands/org/add.mjs +75 -0
- package/src/commands/org/crm.mjs +88 -0
- package/src/commands/org/delete.mjs +48 -0
- package/src/commands/org/email.mjs +111 -0
- package/src/commands/org/get.mjs +152 -0
- package/src/commands/service/add.mjs +78 -0
- package/src/commands/service/list.mjs +24 -0
- package/src/commands/target/add.mjs +94 -0
- package/src/commands/template/add.mjs +97 -0
- package/src/commands/template/list.mjs +61 -0
- package/src/commands/user/get.mjs +91 -0
- package/src/commands/user/invite.mjs +56 -0
- package/src/commands/user/join.mjs +81 -0
- package/src/commands/user/leave.mjs +57 -0
- package/src/commands/user/list.mjs +80 -0
- package/src/commands/user/reset.mjs +83 -0
- package/src/commands/widget/add.mjs +116 -0
- package/src/commands/widget/delete.mjs +45 -0
- package/src/commands/widget/get.mjs +60 -0
- package/src/commands/widget/list.mjs +135 -0
- package/src/commands/widget/rebuild.mjs +64 -0
- package/src/commands/widget/update.mjs +174 -0
- package/src/config.mjs +49 -0
- package/src/generated/schema.json +10677 -0
- package/src/hooks/help.mjs +14 -0
- package/src/hooks/init.mjs +41 -0
- package/src/index.mjs +1 -0
- package/src/procaCommand.mjs +316 -0
- package/src/queries/campaign.mjs +35 -0
- package/src/queries/widget.mjs +25 -0
- package/src/urql.mjs +60 -0
- package/src/util/twitter.mjs +23 -0
- package/theme.json +29 -0
- package/bin/proca-cli +0 -4
- package/dist/browser.d.ts +0 -1
- package/dist/browser.js +0 -28
- package/dist/browser.js.map +0 -1
- package/dist/campaign.d.ts +0 -156
- package/dist/campaign.js +0 -192
- package/dist/campaign.js.map +0 -1
- package/dist/cli.d.ts +0 -40
- package/dist/cli.js +0 -416
- package/dist/cli.js.map +0 -1
- package/dist/client.d.ts +0 -2
- package/dist/client.js +0 -18
- package/dist/client.js.map +0 -1
- package/dist/config.d.ts +0 -35
- package/dist/config.js +0 -71
- package/dist/config.js.map +0 -1
- package/dist/crypto.d.ts +0 -40
- package/dist/crypto.js +0 -53
- package/dist/crypto.js.map +0 -1
- package/dist/export.d.ts +0 -15
- package/dist/export.js +0 -145
- package/dist/export.js.map +0 -1
- package/dist/format.d.ts +0 -37
- package/dist/format.js +0 -200
- package/dist/format.js.map +0 -1
- package/dist/index.d.ts +0 -8
- package/dist/index.js +0 -39
- package/dist/index.js.map +0 -1
- package/dist/keys.d.ts +0 -4
- package/dist/keys.js +0 -38
- package/dist/keys.js.map +0 -1
- package/dist/org.d.ts +0 -11
- package/dist/org.js +0 -97
- package/dist/org.js.map +0 -1
- package/dist/proca.d.ts +0 -2095
- package/dist/proca.js +0 -398
- package/dist/proca.js.map +0 -1
- package/dist/queue.d.ts +0 -8
- package/dist/queue.js +0 -126
- package/dist/queue.js.map +0 -1
- package/dist/queueMessage.d.ts +0 -102
- package/dist/queueMessage.js +0 -109
- package/dist/queueMessage.js.map +0 -1
- package/dist/service/actionnetwork.d.ts +0 -10
- package/dist/service/actionnetwork.js +0 -302
- package/dist/service/actionnetwork.js.map +0 -1
- package/dist/service/distance.d.ts +0 -3
- package/dist/service/distance.js +0 -96
- package/dist/service/distance.js.map +0 -1
- package/dist/service/echo.d.ts +0 -4
- package/dist/service/echo.js +0 -19
- package/dist/service/echo.js.map +0 -1
- package/dist/service/email.d.ts +0 -14
- package/dist/service/email.js +0 -67
- package/dist/service/email.js.map +0 -1
- package/dist/service/identity.d.ts +0 -58
- package/dist/service/identity.js +0 -190
- package/dist/service/identity.js.map +0 -1
- package/dist/service/index.d.ts +0 -14
- package/dist/service/index.js +0 -61
- package/dist/service/index.js.map +0 -1
- package/dist/setup.d.ts +0 -2
- package/dist/setup.js +0 -291
- package/dist/setup.js.map +0 -1
- package/dist/util.d.ts +0 -5
- package/dist/util.js +0 -30
- package/dist/util.js.map +0 -1
- package/dist/watch.d.ts +0 -9
- package/dist/watch.js +0 -80
- package/dist/watch.js.map +0 -1
|
@@ -0,0 +1,132 @@
|
|
|
1
|
+
import { Args, Flags } from "@oclif/core";
|
|
2
|
+
import { error, stdout, ux } from "@oclif/core/ux";
|
|
3
|
+
import Command from "#src/procaCommand.mjs";
|
|
4
|
+
import {
|
|
5
|
+
FragmentMtt,
|
|
6
|
+
FragmentOrg,
|
|
7
|
+
FragmentStats,
|
|
8
|
+
FragmentSummary,
|
|
9
|
+
} from "#src/queries/campaign.mjs";
|
|
10
|
+
import { gql, query } from "#src/urql.mjs";
|
|
11
|
+
|
|
12
|
+
export const getCampaign = (params) => {
|
|
13
|
+
const d = new CampaignGet([]);
|
|
14
|
+
return d.fetch(params);
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
export default class CampaignGet extends Command {
|
|
18
|
+
actionTypes = new Set();
|
|
19
|
+
|
|
20
|
+
static args = this.multiid();
|
|
21
|
+
|
|
22
|
+
static description = "view a campaign";
|
|
23
|
+
|
|
24
|
+
static examples = ["<%= config.bin %> <%= command.id %> -i 42"];
|
|
25
|
+
|
|
26
|
+
static flags = {
|
|
27
|
+
// flag with no value (-f, --force)
|
|
28
|
+
...this.flagify({ multiid: true }),
|
|
29
|
+
config: Flags.boolean({
|
|
30
|
+
description: "display the config",
|
|
31
|
+
default: false,
|
|
32
|
+
allowNo: true,
|
|
33
|
+
}),
|
|
34
|
+
stats: Flags.boolean({
|
|
35
|
+
description: "display the stats",
|
|
36
|
+
default: true,
|
|
37
|
+
allowNo: true,
|
|
38
|
+
}),
|
|
39
|
+
locale: Flags.string({
|
|
40
|
+
description: "display a locale",
|
|
41
|
+
}),
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
fetch = async ({ id, name }) => {
|
|
45
|
+
const GetCampaignDocument = gql`
|
|
46
|
+
query GetCampaign($id: Int, $name: String, $withStats: Boolean = false) {
|
|
47
|
+
campaign (name: $name, id: $id) {
|
|
48
|
+
...Summary
|
|
49
|
+
...Org
|
|
50
|
+
config
|
|
51
|
+
...Stats @include(if: $withStats)
|
|
52
|
+
...Mtt
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
${FragmentStats}
|
|
56
|
+
${FragmentSummary}
|
|
57
|
+
${FragmentOrg}
|
|
58
|
+
${FragmentMtt}
|
|
59
|
+
`;
|
|
60
|
+
const result = await query(GetCampaignDocument, {
|
|
61
|
+
id: id,
|
|
62
|
+
name: name,
|
|
63
|
+
withStats: this.flags.stats,
|
|
64
|
+
});
|
|
65
|
+
return result.campaign;
|
|
66
|
+
};
|
|
67
|
+
|
|
68
|
+
simplify = (d) => {
|
|
69
|
+
const result = {
|
|
70
|
+
id: d.id,
|
|
71
|
+
Name: d.name,
|
|
72
|
+
Title: d.title,
|
|
73
|
+
Org: d.org.name,
|
|
74
|
+
Status: d.status,
|
|
75
|
+
locales: d.config.locales && Object.keys(d.config.locales).join(" "),
|
|
76
|
+
journey: d.config.journey?.join(" → "),
|
|
77
|
+
};
|
|
78
|
+
if (d.mtt) {
|
|
79
|
+
// we have an mtt
|
|
80
|
+
const hhmm = (date) =>
|
|
81
|
+
new Date(date).toLocaleTimeString(undefined, {
|
|
82
|
+
hour: "2-digit",
|
|
83
|
+
minute: "2-digit",
|
|
84
|
+
hour12: false,
|
|
85
|
+
});
|
|
86
|
+
result.from = d.mtt.startAt.substring(0, 10);
|
|
87
|
+
result.to = d.mtt.endAt.substring(0, 10);
|
|
88
|
+
result.period = `${hhmm(d.mtt.startAt)}↔${hhmm(d.mtt.endAt)}`;
|
|
89
|
+
result["test email"] = d.mtt.testEmail;
|
|
90
|
+
result["mtt template"] = d.mtt.template;
|
|
91
|
+
result["cc contacts"] = d.mtt.ccContacts?.join(", ");
|
|
92
|
+
result["cc sender"] = d.mtt.ccSender;
|
|
93
|
+
result["drip delivery"] = d.mtt.dripDelivery;
|
|
94
|
+
}
|
|
95
|
+
if (this.flags.stats) {
|
|
96
|
+
result["#Supporters"] = d.stats.supporterCount;
|
|
97
|
+
|
|
98
|
+
this.actionTypes.forEach((type) => {
|
|
99
|
+
const action = d.stats.actionCount.find(
|
|
100
|
+
(action) => action.actionType === type,
|
|
101
|
+
);
|
|
102
|
+
if (action) result[`#${type}`] = action.count;
|
|
103
|
+
});
|
|
104
|
+
}
|
|
105
|
+
return result;
|
|
106
|
+
};
|
|
107
|
+
|
|
108
|
+
table = (r) => {
|
|
109
|
+
r.config = JSON.parse(r.config);
|
|
110
|
+
super.table(r, null, null);
|
|
111
|
+
if (this.flags.locale) {
|
|
112
|
+
this.prettyJson(r.config?.locales[this.flags.locale]);
|
|
113
|
+
}
|
|
114
|
+
if (this.flags.config) {
|
|
115
|
+
r.config.locales = undefined;
|
|
116
|
+
this.prettyJson(r.config);
|
|
117
|
+
}
|
|
118
|
+
};
|
|
119
|
+
|
|
120
|
+
async run() {
|
|
121
|
+
const { args, flags } = await this.parse();
|
|
122
|
+
|
|
123
|
+
const data = await this.fetch({ id: flags.id, name: flags.name });
|
|
124
|
+
if (this.flags.stats) {
|
|
125
|
+
data.stats.actionCount.forEach((d) => {
|
|
126
|
+
//skip share_confirmed?
|
|
127
|
+
this.actionTypes.add(d.actionType);
|
|
128
|
+
});
|
|
129
|
+
}
|
|
130
|
+
return this.output(data);
|
|
131
|
+
}
|
|
132
|
+
}
|
|
@@ -0,0 +1,161 @@
|
|
|
1
|
+
import { Args, Flags } from "@oclif/core";
|
|
2
|
+
import { error, stdout, ux } from "@oclif/core/ux";
|
|
3
|
+
import Command from "#src/procaCommand.mjs";
|
|
4
|
+
import {
|
|
5
|
+
FragmentOrg,
|
|
6
|
+
FragmentStats,
|
|
7
|
+
FragmentSummary,
|
|
8
|
+
} from "#src/queries/campaign.mjs";
|
|
9
|
+
import { gql, query } from "#src/urql.mjs";
|
|
10
|
+
|
|
11
|
+
export const getCampaignList = (params) => {
|
|
12
|
+
const d = new CampaignList([]);
|
|
13
|
+
return d.fetch(params);
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
export default class CampaignList extends Command {
|
|
17
|
+
actionTypes = new Set();
|
|
18
|
+
|
|
19
|
+
static args = {
|
|
20
|
+
title: Args.string({ description: "name of the campaign, % for wildchar" }),
|
|
21
|
+
};
|
|
22
|
+
|
|
23
|
+
static description = "list all the campaigns";
|
|
24
|
+
|
|
25
|
+
static examples = ["<%= config.bin %> <%= command.id %> %pizza%"];
|
|
26
|
+
|
|
27
|
+
static flags = {
|
|
28
|
+
// flag with no value (-f, --force)
|
|
29
|
+
...super.globalFlags,
|
|
30
|
+
org: Flags.string({
|
|
31
|
+
char: "o",
|
|
32
|
+
description: "campaigns of the organisation (coordinator or partner)",
|
|
33
|
+
exactlyOne: ["org", "title"],
|
|
34
|
+
helpValue: "<organisation name>",
|
|
35
|
+
}),
|
|
36
|
+
title: Flags.string({
|
|
37
|
+
char: "t",
|
|
38
|
+
description: "name of the campaign, % for wildchar",
|
|
39
|
+
helpValue: "<campaign title>",
|
|
40
|
+
}),
|
|
41
|
+
stats: Flags.boolean({
|
|
42
|
+
description: "display the stats",
|
|
43
|
+
default: true,
|
|
44
|
+
allowNo: true,
|
|
45
|
+
}),
|
|
46
|
+
};
|
|
47
|
+
|
|
48
|
+
OrgSearch = async (name) => {
|
|
49
|
+
const SearchCampaignsDocument = gql`
|
|
50
|
+
query SearchCampaigns($org: String!, $withStats: Boolean = false) {
|
|
51
|
+
org (name:$org) {
|
|
52
|
+
campaigns {
|
|
53
|
+
...Summary
|
|
54
|
+
...Org
|
|
55
|
+
...Stats @include(if: $withStats)
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
${FragmentStats}
|
|
60
|
+
${FragmentOrg}
|
|
61
|
+
${FragmentSummary}
|
|
62
|
+
`;
|
|
63
|
+
const result = await query(SearchCampaignsDocument, {
|
|
64
|
+
org: name,
|
|
65
|
+
withStats: this.flags.stats,
|
|
66
|
+
});
|
|
67
|
+
return result.org.campaigns;
|
|
68
|
+
//return result.campaigns.map (d => {d.config = JSON.parse(d.config); return d});
|
|
69
|
+
};
|
|
70
|
+
|
|
71
|
+
Search = async (title) => {
|
|
72
|
+
const SearchCampaignsDocument = gql`
|
|
73
|
+
query SearchCampaigns($title: String!, $withStats: Boolean = false) {
|
|
74
|
+
campaigns(title: $title) {
|
|
75
|
+
...Summary
|
|
76
|
+
...Org
|
|
77
|
+
...Stats @include(if: $withStats)
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
${FragmentStats}
|
|
81
|
+
${FragmentOrg}
|
|
82
|
+
${FragmentSummary}
|
|
83
|
+
`;
|
|
84
|
+
const result = await query(SearchCampaignsDocument, {
|
|
85
|
+
title: title,
|
|
86
|
+
withStats: this.flags.stats,
|
|
87
|
+
});
|
|
88
|
+
return result.campaigns;
|
|
89
|
+
//return result.campaigns.map (d => {d.config = JSON.parse(d.config); return d});
|
|
90
|
+
};
|
|
91
|
+
|
|
92
|
+
simplify = (d) => {
|
|
93
|
+
const result = {
|
|
94
|
+
id: d.id,
|
|
95
|
+
Name: d.name,
|
|
96
|
+
Title: d.title,
|
|
97
|
+
Org: d.org.name,
|
|
98
|
+
Status: d.status,
|
|
99
|
+
};
|
|
100
|
+
if (this.flags.stats) {
|
|
101
|
+
result["#Supporters"] = d.stats.supporterCount;
|
|
102
|
+
|
|
103
|
+
this.actionTypes.forEach((type) => {
|
|
104
|
+
const action = d.stats.actionCount.find(
|
|
105
|
+
(action) => action.actionType === type,
|
|
106
|
+
);
|
|
107
|
+
if (action) result[`#${type}`] = action.count;
|
|
108
|
+
});
|
|
109
|
+
}
|
|
110
|
+
return result;
|
|
111
|
+
};
|
|
112
|
+
|
|
113
|
+
table = (r) => {
|
|
114
|
+
super.table(r, null, (table) => table.sort(["id|des"]).toString());
|
|
115
|
+
};
|
|
116
|
+
|
|
117
|
+
async run() {
|
|
118
|
+
const { args, flags } = await this.parse(CampaignList);
|
|
119
|
+
let data = [];
|
|
120
|
+
|
|
121
|
+
if (args.title && flags.title) {
|
|
122
|
+
throw new Error(
|
|
123
|
+
`${this.id} EITHER [title of the campaign] OR --title [title of the campaign]`,
|
|
124
|
+
);
|
|
125
|
+
}
|
|
126
|
+
if (args.title) {
|
|
127
|
+
flags.title = args.title;
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
if (!flags.title && !flags.org) {
|
|
131
|
+
throw new Error(
|
|
132
|
+
`${this.id} -t [title of the campaign] or -o [organisation]`,
|
|
133
|
+
);
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
if (flags.title) {
|
|
137
|
+
data = await this.Search(flags.title);
|
|
138
|
+
if (this.flags.stats) {
|
|
139
|
+
data.forEach((d) => {
|
|
140
|
+
d.stats.actionCount.forEach((d) => {
|
|
141
|
+
//skip share_confirmed?
|
|
142
|
+
this.actionTypes.add(d.actionType);
|
|
143
|
+
});
|
|
144
|
+
});
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
if (flags.org) {
|
|
149
|
+
data = await this.OrgSearch(flags.org);
|
|
150
|
+
if (this.flags.stats) {
|
|
151
|
+
data.forEach((d) => {
|
|
152
|
+
d.stats.actionCount.forEach((d) => {
|
|
153
|
+
//skip share_confirmed?
|
|
154
|
+
this.actionTypes.add(d.actionType);
|
|
155
|
+
});
|
|
156
|
+
});
|
|
157
|
+
}
|
|
158
|
+
}
|
|
159
|
+
return this.output(data);
|
|
160
|
+
}
|
|
161
|
+
}
|
|
@@ -0,0 +1,131 @@
|
|
|
1
|
+
import { Flags } from "@oclif/core";
|
|
2
|
+
import Command from "#src/procaCommand.mjs";
|
|
3
|
+
import { FragmentMtt } from "#src/queries/campaign.mjs";
|
|
4
|
+
import { gql, mutation } from "#src/urql.mjs";
|
|
5
|
+
|
|
6
|
+
export default class CampaignMtt extends Command {
|
|
7
|
+
static args = this.multiid();
|
|
8
|
+
|
|
9
|
+
static description = "set the mail to target (mtt) params";
|
|
10
|
+
|
|
11
|
+
static examples = [
|
|
12
|
+
"<%= config.bin %> <%= command.id %> -n <test-mtt-campaign>",
|
|
13
|
+
];
|
|
14
|
+
|
|
15
|
+
static flags = {
|
|
16
|
+
...this.flagify({ multiid: true }),
|
|
17
|
+
from: Flags.string({
|
|
18
|
+
description: "start date (yyyy-mm-dd)",
|
|
19
|
+
required: false,
|
|
20
|
+
}),
|
|
21
|
+
to: Flags.string({
|
|
22
|
+
description: "end date (yyyy-mm-dd)",
|
|
23
|
+
required: false,
|
|
24
|
+
}),
|
|
25
|
+
template: Flags.string({
|
|
26
|
+
description: "mtt template to use",
|
|
27
|
+
}),
|
|
28
|
+
period: Flags.string({
|
|
29
|
+
description: "period of the day (HH:HH-HH:HH)",
|
|
30
|
+
default: "09:09-18:18",
|
|
31
|
+
}),
|
|
32
|
+
email: Flags.string({
|
|
33
|
+
description: "test email address",
|
|
34
|
+
}),
|
|
35
|
+
cc: Flags.string({
|
|
36
|
+
description: "comma-separated list of CC email addresses",
|
|
37
|
+
}),
|
|
38
|
+
sender: Flags.boolean({
|
|
39
|
+
description: "add sender to CC",
|
|
40
|
+
default: false,
|
|
41
|
+
}),
|
|
42
|
+
drip: Flags.boolean({
|
|
43
|
+
description: "drip delivery or deliver as fast as possible",
|
|
44
|
+
default: false,
|
|
45
|
+
}),
|
|
46
|
+
};
|
|
47
|
+
|
|
48
|
+
updateMtt = async (flags) => {
|
|
49
|
+
const Query = gql`
|
|
50
|
+
mutation (
|
|
51
|
+
$id: Int,
|
|
52
|
+
$name: String
|
|
53
|
+
$mtt: CampaignMttInput!
|
|
54
|
+
) {
|
|
55
|
+
updateCampaign (id:$id, name: $name, input: { mtt: $mtt }) {
|
|
56
|
+
id, name
|
|
57
|
+
...Mtt
|
|
58
|
+
}
|
|
59
|
+
${FragmentMtt}
|
|
60
|
+
}
|
|
61
|
+
`;
|
|
62
|
+
|
|
63
|
+
const testEmail = flags.email || `campaign+${flags.name}@proca.app`;
|
|
64
|
+
|
|
65
|
+
const [startPeriod, endPeriod] = flags.period.split("-");
|
|
66
|
+
const [startHour, startMinute] = startPeriod.split(":");
|
|
67
|
+
const [endHour, endMinute] = endPeriod.split(":");
|
|
68
|
+
|
|
69
|
+
const mtt = {
|
|
70
|
+
testEmail,
|
|
71
|
+
};
|
|
72
|
+
|
|
73
|
+
if (flags.template) mtt.messageTemplate = flags.template;
|
|
74
|
+
if (flags.email) mtt.testEmail = testEmail;
|
|
75
|
+
if (flags.cc) mtt.ccContacts = flags.cc.split(",").map((e) => e.trim());
|
|
76
|
+
if (flags.sender) mtt.ccSender = flags.sender;
|
|
77
|
+
|
|
78
|
+
if (flags.from) {
|
|
79
|
+
const startAt = new Date(flags.from);
|
|
80
|
+
startAt.setHours(startHour, startMinute, 0, 0);
|
|
81
|
+
mtt.startAt = startAt.toISOString();
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
if (flags.to) {
|
|
85
|
+
const endAt = new Date(flags.to);
|
|
86
|
+
endAt.setHours(endHour, endMinute, 0, 0);
|
|
87
|
+
mtt.endAt = endAt.toISOString();
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
const result = await mutation(Query, {
|
|
91
|
+
id: flags.id,
|
|
92
|
+
name: flags.name,
|
|
93
|
+
mtt,
|
|
94
|
+
});
|
|
95
|
+
return result.updateCampaign;
|
|
96
|
+
};
|
|
97
|
+
|
|
98
|
+
simplify = (d) => {
|
|
99
|
+
const result = { id: d.id, Name: d.name };
|
|
100
|
+
const hhmm = (date) =>
|
|
101
|
+
new Date(date).toLocaleTimeString(undefined, {
|
|
102
|
+
hour: "2-digit",
|
|
103
|
+
minute: "2-digit",
|
|
104
|
+
hour12: false,
|
|
105
|
+
});
|
|
106
|
+
if (d.mtt.startAt && d.mtt.endAt) {
|
|
107
|
+
result.from = d.mtt.startAt.substring(0, 10);
|
|
108
|
+
result.to = d.mtt.endAt.substring(0, 10);
|
|
109
|
+
result.period = `${hhmm(d.mtt.startAt)}↔${hhmm(d.mtt.endAt)}`;
|
|
110
|
+
}
|
|
111
|
+
result["test email"] = d.mtt.testEmail;
|
|
112
|
+
result["mtt template"] = d.mtt.messageTemplate;
|
|
113
|
+
if (d.mtt.ccContacts?.length)
|
|
114
|
+
result["cc contacts"] = d.mtt.ccContacts.join(", ");
|
|
115
|
+
if (typeof d.mtt.ccSender !== "undefined") {
|
|
116
|
+
result["cc sender"] = d.mtt.ccSender ? "yes" : "no";
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
return result;
|
|
120
|
+
};
|
|
121
|
+
|
|
122
|
+
table = (r) => {
|
|
123
|
+
super.table(r, null, null);
|
|
124
|
+
};
|
|
125
|
+
|
|
126
|
+
async run() {
|
|
127
|
+
const { args, flags } = await this.parse();
|
|
128
|
+
const result = await this.updateMtt(flags);
|
|
129
|
+
this.output(result);
|
|
130
|
+
}
|
|
131
|
+
}
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
import { Args, Flags } from "@oclif/core";
|
|
2
|
+
import { error, stdout, ux } from "@oclif/core/ux";
|
|
3
|
+
import Command from "#src/procaCommand.mjs";
|
|
4
|
+
import { gql, mutation } from "#src/urql.mjs";
|
|
5
|
+
|
|
6
|
+
export default class CampaignStatus extends Command {
|
|
7
|
+
static args = this.multiid();
|
|
8
|
+
static aliases = ["campaign:close"];
|
|
9
|
+
|
|
10
|
+
static examples = [
|
|
11
|
+
"<%= config.bin %> <%= command.id %> -name <campaign>",
|
|
12
|
+
"<%= config.bin %> <%= command.id %> -i <campaign_id>",
|
|
13
|
+
];
|
|
14
|
+
|
|
15
|
+
static isCloseCommand =
|
|
16
|
+
process.argv.includes("close") ||
|
|
17
|
+
this.commandPath?.includes("close") ||
|
|
18
|
+
this.id?.includes("close");
|
|
19
|
+
|
|
20
|
+
static flags = {
|
|
21
|
+
status: Flags.string({
|
|
22
|
+
...this.flagify({ multiid: true }),
|
|
23
|
+
description: "Status to set",
|
|
24
|
+
required: true,
|
|
25
|
+
default: this.isCloseCommand ? "close" : undefined,
|
|
26
|
+
options: ["draft", "live", "closed", "ignored"],
|
|
27
|
+
}),
|
|
28
|
+
};
|
|
29
|
+
|
|
30
|
+
updateStatus = async (props) => {
|
|
31
|
+
const Query = gql`
|
|
32
|
+
mutation (
|
|
33
|
+
$id: Int,
|
|
34
|
+
$name: String
|
|
35
|
+
$status: String!
|
|
36
|
+
) {
|
|
37
|
+
updateCampaign (id:$id, input: { name: $name,status: $status }) {
|
|
38
|
+
name
|
|
39
|
+
org {name}
|
|
40
|
+
status
|
|
41
|
+
title
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
`;
|
|
45
|
+
|
|
46
|
+
const result = await mutation(Query, {
|
|
47
|
+
// org: props.org,
|
|
48
|
+
id: props.id,
|
|
49
|
+
name: props.name,
|
|
50
|
+
status: props.status.toUpperCase(),
|
|
51
|
+
});
|
|
52
|
+
|
|
53
|
+
console.log("result", result);
|
|
54
|
+
return result.updateCampaign;
|
|
55
|
+
};
|
|
56
|
+
|
|
57
|
+
async run() {
|
|
58
|
+
const { args, flags } = await this.parse();
|
|
59
|
+
|
|
60
|
+
const data = await this.updateStatus(flags);
|
|
61
|
+
return this.output(data);
|
|
62
|
+
}
|
|
63
|
+
}
|
|
@@ -0,0 +1,124 @@
|
|
|
1
|
+
import { Flags } from "@oclif/core";
|
|
2
|
+
import prompts from "prompts";
|
|
3
|
+
import CampaignGet from "#src/commands/campaign/get.mjs";
|
|
4
|
+
import WidgetList from "#src/commands/widget/list.mjs";
|
|
5
|
+
import WidgetUpdate from "#src/commands/widget/update.mjs";
|
|
6
|
+
import Command from "#src/procaCommand.mjs";
|
|
7
|
+
|
|
8
|
+
export default class CampaignWidgetArchive extends Command {
|
|
9
|
+
static args = this.multiid(); // Add this!
|
|
10
|
+
|
|
11
|
+
static description = "Archive all widgets in the campaign by adding suffix";
|
|
12
|
+
|
|
13
|
+
static examples = [
|
|
14
|
+
"<%= config.bin %> <%= command.id %> old_campaign",
|
|
15
|
+
"<%= config.bin %> <%= command.id %> -n old_campaign --suffix _backup",
|
|
16
|
+
"<%= config.bin %> <%= command.id %> old_campaign --dry-run",
|
|
17
|
+
];
|
|
18
|
+
|
|
19
|
+
static flags = {
|
|
20
|
+
...this.flagify({ multiid: true }),
|
|
21
|
+
suffix: Flags.string({
|
|
22
|
+
char: "s",
|
|
23
|
+
description: "custom suffix to append (default: _archive)",
|
|
24
|
+
helpValue: "<suffix>",
|
|
25
|
+
default: "_archive",
|
|
26
|
+
}),
|
|
27
|
+
"dry-run": Flags.boolean({
|
|
28
|
+
description: "preview changes without executing",
|
|
29
|
+
default: false,
|
|
30
|
+
}),
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
fetchCampaign = async ({ id, name }) => {
|
|
34
|
+
const campaignGet = new CampaignGet([], this.config);
|
|
35
|
+
return await campaignGet.fetch({ id, name });
|
|
36
|
+
};
|
|
37
|
+
|
|
38
|
+
fetchWidgets = async (campaignName) => {
|
|
39
|
+
const widgetList = new WidgetList([], this.config);
|
|
40
|
+
widgetList.flags = { campaign: campaignName, config: true };
|
|
41
|
+
return await widgetList.fetchCampaign(campaignName);
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
async run() {
|
|
45
|
+
const { flags } = await this.parse();
|
|
46
|
+
const { id, name, suffix, "dry-run": dryRun } = flags;
|
|
47
|
+
|
|
48
|
+
this.log(`Fetching source campaign: ${name || id}`);
|
|
49
|
+
const campaign = await this.fetchCampaign({ id, name });
|
|
50
|
+
|
|
51
|
+
if (!campaign) {
|
|
52
|
+
this.error("Campaign not found");
|
|
53
|
+
return;
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
this.log(`Fetching widgets for campaign: ${campaign.name}`);
|
|
57
|
+
const widgets = await this.fetchWidgets(campaign.name);
|
|
58
|
+
|
|
59
|
+
if (!widgets || widgets.length === 0) {
|
|
60
|
+
this.warn("No widgets found for this campaign");
|
|
61
|
+
return;
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
this.log(`Found ${widgets.length} widgets`);
|
|
65
|
+
|
|
66
|
+
const renameList = widgets.map((widget) => ({
|
|
67
|
+
id: widget.id,
|
|
68
|
+
oldName: widget.name,
|
|
69
|
+
newName: `${widget.name}${suffix}`,
|
|
70
|
+
locale: widget.locale,
|
|
71
|
+
}));
|
|
72
|
+
|
|
73
|
+
this.log("\nArchive plan:");
|
|
74
|
+
this.table(renameList);
|
|
75
|
+
|
|
76
|
+
if (dryRun) {
|
|
77
|
+
this.log("\n[DRY RUN] No changes made");
|
|
78
|
+
return renameList;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
// Confirm before proceeding
|
|
82
|
+
const response = await prompts({
|
|
83
|
+
type: "confirm",
|
|
84
|
+
name: "proceed",
|
|
85
|
+
message: `Archive ${renameList.length} widgets by adding suffix "${suffix}"?`,
|
|
86
|
+
initial: false,
|
|
87
|
+
});
|
|
88
|
+
|
|
89
|
+
if (!response.proceed) {
|
|
90
|
+
this.log("Cancelled");
|
|
91
|
+
return;
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
const widgetUpdate = new WidgetUpdate([], this.config);
|
|
95
|
+
const results = [];
|
|
96
|
+
|
|
97
|
+
for (const item of renameList) {
|
|
98
|
+
try {
|
|
99
|
+
this.log(`Archiving: ${item.oldName} → ${item.newName}`);
|
|
100
|
+
const input = {
|
|
101
|
+
name: item.newName,
|
|
102
|
+
locale: item.locale,
|
|
103
|
+
};
|
|
104
|
+
const result = await widgetUpdate.update(item.id, input);
|
|
105
|
+
results.push({
|
|
106
|
+
id: result.id,
|
|
107
|
+
name: result.name,
|
|
108
|
+
status: "success",
|
|
109
|
+
});
|
|
110
|
+
} catch (error) {
|
|
111
|
+
this.error(`Failed to archive ${item.oldName}: ${error.message}`);
|
|
112
|
+
results.push({
|
|
113
|
+
id: item.id,
|
|
114
|
+
name: item.oldName,
|
|
115
|
+
status: "failed",
|
|
116
|
+
error: error.message,
|
|
117
|
+
});
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
this.log("\nArchive complete!");
|
|
122
|
+
return this.output(results);
|
|
123
|
+
}
|
|
124
|
+
}
|