Skip to content

Commit

Permalink
feat: add campaign report
Browse files Browse the repository at this point in the history
  • Loading branch information
clairton committed Aug 1, 2024
1 parent 8c6cc80 commit 61cd55c
Show file tree
Hide file tree
Showing 6 changed files with 78 additions and 18 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,12 @@
>
{{ messageStamp(new Date(campaign.scheduled_at), 'LLL d, h:mm a') }}
</div>
<div
v-if="campaign.inbox.channel_type == 'Channel::Whatsapp'"
class="mb-1 text-xs text-slate-700 dark:text-slate-500"
>
{{ campaignReport }}
</div>
</div>
</div>
</template>
Expand Down Expand Up @@ -101,6 +107,22 @@ export default {
? this.$t('CAMPAIGN.LIST.STATUS.COMPLETED')
: this.$t('CAMPAIGN.LIST.STATUS.ACTIVE');
},
campaignReport() {
const audience = this.campaign.audience;
const reports = {
total: 0,
};
// eslint-disable-next-line no-plusplus
for (let i = 0; i < audience.length; i++) {
const a = audience[i];
if (!reports[a.status]) {
reports[a.status] = 0;
}
reports.total += 1;
reports[a.status] += 1;
}
return reports;
},
colorScheme() {
if (this.isOngoingType) {
return this.campaign.enabled ? 'success' : 'secondary';
Expand Down
2 changes: 1 addition & 1 deletion app/jobs/campaign_message_job.rb
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ def perform(account_id, inbox_id, campaign_id, content, audience)
content: m, account_id: account_id,
content_type: :text, inbox_id: inbox_id,
message_type: :outgoing, status: :progress,
additional_attributes: { campaign_id: campaign_id }
additional_attributes: { campaign_id: campaign_id, audience_id: audience[:audience_id] }
)
end
end
22 changes: 22 additions & 0 deletions app/jobs/campaign_message_update_job.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
class CampaignMessageUpdateJob < ApplicationJob
queue_as :low

def perform(campaign_id, audience_id, status)
campaign = Campaign.find(campaign_id)
new_audience = campaign.audience.map do |a|
if a['audience_id'] == audience_id && (!a['status'] || a['status'] == :failed || (statuses(status) > statuses(a['status'])))
a['status'] = status
end
a
end
# rubocop:disable Rails/SkipsModelValidations
campaign.update_column(:audience, new_audience)
# rubocop:enable Rails/SkipsModelValidations
end

private

def statuses(status)
[:scheduled, :progress, :sent, :delivered, :read, :failed].find_index(status.to_sym)
end
end
8 changes: 0 additions & 8 deletions app/jobs/oneoff_unoapi_campaign_job.rb

This file was deleted.

8 changes: 8 additions & 0 deletions app/models/message.rb
Original file line number Diff line number Diff line change
Expand Up @@ -328,6 +328,14 @@ def dispatch_update_event

Rails.configuration.dispatcher.dispatch(MESSAGE_UPDATED, Time.zone.now, message: self, performed_by: Current.executed_by,
previous_changes: previous_changes)

if additional_attributes['campaign_id'].present?
CampaignMessageUpdateJob.perform_later(
additional_attributes['campaign_id'],
additional_attributes['audience_id'],
status
)
end
end

def send_reply
Expand Down
34 changes: 25 additions & 9 deletions app/services/whatsapp/oneoff_unoapi_campaign_service.rb
Original file line number Diff line number Diff line change
Expand Up @@ -19,15 +19,31 @@ def perform
def process_audience(audience)
Rails.logger.debug { "Process campaign #{campaign.id} and #{audience.length} audience record(s)" }
interval = 0.seconds
audience.each do |a|
interval += rand(1..10).seconds
CampaignMessageJob.set(wait_until: DateTime.current + interval.seconds).perform_later(
campaign.account_id,
campaign.inbox_id,
campaign.id,
campaign.message,
a.symbolize_keys
)
new_audience = audience.map do |a|
aa = update_audience(a)
interval = schedule_job(campaign, aa, interval)
aa
end
# rubocop:disable Rails/SkipsModelValidations
campaign.update_column(:audience, new_audience)
# rubocop:enable Rails/SkipsModelValidations
end

def update_audience(audience)
audience[:status] = 'scheduled'
audience[:audience_id] = SecureRandom.uuid
audience
end

def schedule_job(campaign, audience, interval)
interval += rand(1..10).seconds
CampaignMessageJob.set(wait_until: DateTime.current + interval.seconds).perform_later(
campaign.account_id,
campaign.inbox_id,
campaign.id,
campaign.message,
audience.symbolize_keys
)
interval
end
end

0 comments on commit 61cd55c

Please sign in to comment.