Conditional display of statistics column (for standard)
- improved duplicate action (for standard) - moved STATUS_COMPLETED constant from worker to SendingQueue model where it belongs
This commit is contained in:
@ -676,6 +676,12 @@ define(
|
||||
sort_by = this.state.sort_by,
|
||||
sort_order = this.state.sort_order;
|
||||
|
||||
// columns
|
||||
var columns = this.props.columns || [];
|
||||
columns = columns.filter(function(column) {
|
||||
return (column.display === undefined || !!(column.display) === true);
|
||||
});
|
||||
|
||||
// bulk actions
|
||||
var bulk_actions = this.props.bulk_actions || [];
|
||||
|
||||
@ -761,7 +767,7 @@ define(
|
||||
selection={ this.state.selection }
|
||||
sort_by={ sort_by }
|
||||
sort_order={ sort_order }
|
||||
columns={ this.props.columns }
|
||||
columns={ columns }
|
||||
is_selectable={ bulk_actions.length > 0 } />
|
||||
</thead>
|
||||
|
||||
@ -771,7 +777,7 @@ define(
|
||||
onRestoreItem={ this.handleRestoreItem }
|
||||
onTrashItem={ this.handleTrashItem }
|
||||
onRefreshItems={ this.handleRefreshItems }
|
||||
columns={ this.props.columns }
|
||||
columns={ columns }
|
||||
is_selectable={ bulk_actions.length > 0 }
|
||||
onSelectItem={ this.handleSelectItem }
|
||||
onSelectAll={ this.handleSelectAll }
|
||||
@ -791,7 +797,7 @@ define(
|
||||
selection={ this.state.selection }
|
||||
sort_by={ sort_by }
|
||||
sort_order={ sort_order }
|
||||
columns={ this.props.columns }
|
||||
columns={ columns }
|
||||
is_selectable={ bulk_actions.length > 0 } />
|
||||
</tfoot>
|
||||
|
||||
|
@ -68,17 +68,12 @@ var columns = [
|
||||
label: MailPoet.I18n.t('status')
|
||||
},
|
||||
{
|
||||
name: 'segments',
|
||||
label: MailPoet.I18n.t('lists')
|
||||
name: 'settings',
|
||||
label: MailPoet.I18n.t('settings')
|
||||
},
|
||||
{
|
||||
name: 'statistics',
|
||||
label: MailPoet.I18n.t('statistics')
|
||||
},
|
||||
{
|
||||
name: 'created_at',
|
||||
label: MailPoet.I18n.t('createdOn'),
|
||||
sortable: true
|
||||
name: 'history',
|
||||
label: MailPoet.I18n.t('history')
|
||||
},
|
||||
{
|
||||
name: 'updated_at',
|
||||
@ -96,6 +91,16 @@ var bulk_actions = [
|
||||
];
|
||||
|
||||
var newsletter_actions = [
|
||||
{
|
||||
name: 'view',
|
||||
link: function(newsletter) {
|
||||
return (
|
||||
<a href={ newsletter.preview_url } target="_blank">
|
||||
{MailPoet.I18n.t('preview')}
|
||||
</a>
|
||||
);
|
||||
}
|
||||
},
|
||||
{
|
||||
name: 'edit',
|
||||
link: function(newsletter) {
|
||||
@ -106,6 +111,26 @@ var newsletter_actions = [
|
||||
);
|
||||
}
|
||||
},
|
||||
{
|
||||
name: 'duplicate',
|
||||
label: MailPoet.I18n.t('duplicate'),
|
||||
onClick: function(newsletter, refresh) {
|
||||
return MailPoet.Ajax.post({
|
||||
endpoint: 'newsletters',
|
||||
action: 'duplicate',
|
||||
data: newsletter.id
|
||||
}).done(function(response) {
|
||||
if (response !== false && response.subject !== undefined) {
|
||||
MailPoet.Notice.success(
|
||||
(MailPoet.I18n.t('newsletterDuplicated')).replace(
|
||||
'%$1s', response.subject
|
||||
)
|
||||
);
|
||||
}
|
||||
refresh();
|
||||
});
|
||||
}
|
||||
},
|
||||
{
|
||||
name: 'trash'
|
||||
}
|
||||
@ -158,31 +183,6 @@ const NewsletterListNotification = React.createClass({
|
||||
</span>
|
||||
);
|
||||
},
|
||||
renderStatistics: function(newsletter) {
|
||||
if (!newsletter.statistics || !newsletter.queue || newsletter.queue.count_processed == 0 || newsletter.queue.status === 'scheduled') {
|
||||
return (
|
||||
<span>
|
||||
{MailPoet.I18n.t('notSentYet')}
|
||||
</span>
|
||||
);
|
||||
}
|
||||
|
||||
var percentage_clicked = Math.round(
|
||||
(newsletter.statistics.clicked * 100) / (newsletter.queue.count_processed)
|
||||
);
|
||||
var percentage_opened = Math.round(
|
||||
(newsletter.statistics.opened * 100) / (newsletter.queue.count_processed)
|
||||
);
|
||||
var percentage_unsubscribed = Math.round(
|
||||
(newsletter.statistics.unsubscribed * 100) / (newsletter.queue.count_processed)
|
||||
);
|
||||
|
||||
return (
|
||||
<span>
|
||||
{ percentage_opened }%, { percentage_clicked }%, { percentage_unsubscribed }%
|
||||
</span>
|
||||
);
|
||||
},
|
||||
renderItem: function(newsletter, actions) {
|
||||
var rowClasses = classNames(
|
||||
'manage-column',
|
||||
@ -190,10 +190,6 @@ const NewsletterListNotification = React.createClass({
|
||||
'has-row-actions'
|
||||
);
|
||||
|
||||
var segments = newsletter.segments.map(function(segment) {
|
||||
return segment.name
|
||||
}).join(', ');
|
||||
|
||||
return (
|
||||
<div>
|
||||
<td className={ rowClasses }>
|
||||
@ -207,14 +203,11 @@ const NewsletterListNotification = React.createClass({
|
||||
<td className="column" data-colname={ MailPoet.I18n.t('status') }>
|
||||
{ this.renderStatus(newsletter) }
|
||||
</td>
|
||||
<td className="column" data-colname={ MailPoet.I18n.t('lists') }>
|
||||
{ segments }
|
||||
<td className="column" data-colname={ MailPoet.I18n.t('settings') }>
|
||||
{ this.renderSettings(newsletter) }
|
||||
</td>
|
||||
<td className="column" data-colname={ MailPoet.I18n.t('statistics') }>
|
||||
{ this.renderStatistics(newsletter) }
|
||||
</td>
|
||||
<td className="column-date" data-colname={ MailPoet.I18n.t('createdOn') }>
|
||||
<abbr>{ MailPoet.Date.format(newsletter.created_at) }</abbr>
|
||||
<td className="column" data-colname={ MailPoet.I18n.t('history') }>
|
||||
<a href="#TODO">{ MailPoet.I18n.t('viewHistory') }</a>
|
||||
</td>
|
||||
<td className="column-date" data-colname={ MailPoet.I18n.t('lastModifiedOn') }>
|
||||
<abbr>{ MailPoet.Date.format(newsletter.updated_at) }</abbr>
|
||||
|
@ -9,6 +9,8 @@ import classNames from 'classnames'
|
||||
import jQuery from 'jquery'
|
||||
import MailPoet from 'mailpoet'
|
||||
|
||||
const mailpoet_tracking_enabled = (!!(window['mailpoet_tracking_enabled']));
|
||||
|
||||
const messages = {
|
||||
onTrash(response) {
|
||||
const count = ~~response;
|
||||
@ -73,7 +75,8 @@ var columns = [
|
||||
},
|
||||
{
|
||||
name: 'statistics',
|
||||
label: MailPoet.I18n.t('statistics')
|
||||
label: MailPoet.I18n.t('statistics'),
|
||||
display: mailpoet_tracking_enabled
|
||||
},
|
||||
{
|
||||
name: 'updated_at',
|
||||
@ -82,6 +85,7 @@ var columns = [
|
||||
}
|
||||
];
|
||||
|
||||
|
||||
var bulk_actions = [
|
||||
{
|
||||
name: 'trash',
|
||||
@ -231,30 +235,33 @@ const NewsletterListStandard = React.createClass({
|
||||
);
|
||||
}
|
||||
},
|
||||
renderStatistics: function(item) {
|
||||
if(!item.statistics || !item.queue || item.queue.count_processed == 0 || item.queue.status === 'scheduled') {
|
||||
return (
|
||||
<span>
|
||||
{MailPoet.I18n.t('notSentYet')}
|
||||
</span>
|
||||
);
|
||||
renderStatistics: function(newsletter) {
|
||||
if (mailpoet_tracking_enabled === false) {
|
||||
return;
|
||||
}
|
||||
|
||||
var percentage_clicked = Math.round(
|
||||
(item.statistics.clicked * 100) / (item.queue.count_processed)
|
||||
);
|
||||
var percentage_opened = Math.round(
|
||||
(item.statistics.opened * 100) / (item.queue.count_processed)
|
||||
);
|
||||
var percentage_unsubscribed = Math.round(
|
||||
(item.statistics.unsubscribed * 100) / (item.queue.count_processed)
|
||||
);
|
||||
if(newsletter.statistics && newsletter.queue && newsletter.queue.status !== 'scheduled') {
|
||||
const total_sent = ~~(newsletter.queue.count_processed);
|
||||
const percentage_clicked = Math.round(
|
||||
(~~(newsletter.statistics.clicked) * 100) / total_sent
|
||||
);
|
||||
const percentage_opened = Math.round(
|
||||
(~~(newsletter.statistics.opened) * 100) / total_sent
|
||||
);
|
||||
const percentage_unsubscribed = Math.round(
|
||||
(~~(newsletter.statistics.unsubscribed) * 100) / total_sent
|
||||
);
|
||||
|
||||
return (
|
||||
<span>
|
||||
{ percentage_opened }%, { percentage_clicked }%, { percentage_unsubscribed }%
|
||||
</span>
|
||||
);
|
||||
return (
|
||||
<span>
|
||||
{ percentage_opened }%, { percentage_clicked }%, { percentage_unsubscribed }%
|
||||
</span>
|
||||
);
|
||||
} else {
|
||||
return (
|
||||
<span>{MailPoet.I18n.t('notSentYet')}</span>
|
||||
);
|
||||
}
|
||||
},
|
||||
renderItem: function(newsletter, actions) {
|
||||
var rowClasses = classNames(
|
||||
@ -283,9 +290,11 @@ const NewsletterListStandard = React.createClass({
|
||||
<td className="column" data-colname={ MailPoet.I18n.t('lists') }>
|
||||
{ segments }
|
||||
</td>
|
||||
<td className="column" data-colname={ MailPoet.I18n.t('statistics') }>
|
||||
{ this.renderStatistics(newsletter) }
|
||||
</td>
|
||||
{(mailpoet_tracking_enabled === true) ? (
|
||||
<td className="column" data-colname={ MailPoet.I18n.t('statistics') }>
|
||||
{ this.renderStatistics(newsletter) }
|
||||
</td>
|
||||
) : null }
|
||||
<td className="column-date" data-colname={ MailPoet.I18n.t('lastModifiedOn') }>
|
||||
<abbr>{ MailPoet.Date.format(newsletter.updated_at) }</abbr>
|
||||
</td>
|
||||
|
@ -8,6 +8,7 @@ import ListingTabs from 'newsletters/listings/tabs.jsx'
|
||||
import classNames from 'classnames'
|
||||
import jQuery from 'jquery'
|
||||
import MailPoet from 'mailpoet'
|
||||
import _ from 'underscore'
|
||||
|
||||
const messages = {
|
||||
onTrash(response) {
|
||||
@ -165,21 +166,48 @@ const NewsletterListWelcome = React.createClass({
|
||||
}.bind(this));
|
||||
},
|
||||
renderStatus: function(newsletter) {
|
||||
let total_sent;
|
||||
total_sent = (
|
||||
MailPoet.I18n.t('sentToXSubscribers')
|
||||
.replace('%$1d', newsletter.total_sent)
|
||||
);
|
||||
|
||||
return (
|
||||
<select
|
||||
data-id={ newsletter.id }
|
||||
defaultValue={ newsletter.status }
|
||||
onChange={ this.updateStatus }
|
||||
>
|
||||
<option value="active">{ MailPoet.I18n.t('active') }</option>
|
||||
<option value="draft">{ MailPoet.I18n.t('inactive') }</option>
|
||||
</select>
|
||||
<div>
|
||||
<select
|
||||
data-id={ newsletter.id }
|
||||
defaultValue={ newsletter.status }
|
||||
onChange={ this.updateStatus }
|
||||
>
|
||||
<option value="active">{ MailPoet.I18n.t('active') }</option>
|
||||
<option value="draft">{ MailPoet.I18n.t('inactive') }</option>
|
||||
</select>
|
||||
<p>{ total_sent }</p>
|
||||
</div>
|
||||
);
|
||||
},
|
||||
renderSettings: function(newsletter) {
|
||||
let settings;
|
||||
|
||||
switch (newsletter.options.event) {
|
||||
case 'user':
|
||||
// WP User
|
||||
settings = MailPoet.I18n.t('onWordpressUserRegistration');
|
||||
break;
|
||||
|
||||
case 'segment':
|
||||
// get segment
|
||||
const segment = _.find(mailpoet_segments, function(segment) {
|
||||
return (~~(segment.id) === ~~(newsletter.options.segment));
|
||||
});
|
||||
|
||||
settings = MailPoet.I18n.t('onSubscriptionToList') + ' ' +segment.name;
|
||||
break;
|
||||
}
|
||||
|
||||
return (
|
||||
<span>
|
||||
Settings...
|
||||
{ settings }
|
||||
</span>
|
||||
);
|
||||
},
|
||||
|
@ -413,6 +413,8 @@ class Menu {
|
||||
24
|
||||
);
|
||||
|
||||
$data['tracking_enabled'] = Setting::getValue('tracking.enabled');
|
||||
|
||||
wp_enqueue_script('jquery-ui');
|
||||
wp_enqueue_script('jquery-ui-datepicker');
|
||||
|
||||
|
@ -4,6 +4,7 @@ namespace MailPoet\Cron\Workers;
|
||||
use MailPoet\Cron\CronHelper;
|
||||
use MailPoet\Mailer\Mailer;
|
||||
use MailPoet\Models\Newsletter;
|
||||
use MailPoet\Models\SendingQueue as SendingQueueModel;
|
||||
use MailPoet\Models\NewsletterPost;
|
||||
use MailPoet\Models\Setting;
|
||||
use MailPoet\Models\StatisticsNewsletters;
|
||||
@ -23,7 +24,6 @@ class SendingQueue {
|
||||
private $timer;
|
||||
const BATCH_SIZE = 50;
|
||||
const DIVIDER = '***MailPoet***';
|
||||
const STATUS_COMPLETED = 'completed';
|
||||
|
||||
function __construct($timer = false) {
|
||||
$this->mta_config = $this->getMailerConfig();
|
||||
@ -295,7 +295,7 @@ class SendingQueue {
|
||||
}
|
||||
|
||||
function getQueues() {
|
||||
return \MailPoet\Models\SendingQueue::orderByDesc('priority')
|
||||
return SendingQueueModel::orderByDesc('priority')
|
||||
->whereNull('deleted_at')
|
||||
->whereNull('status')
|
||||
->findResultSet();
|
||||
@ -321,7 +321,7 @@ class SendingQueue {
|
||||
$queue->count_processed + $queue->count_to_process;
|
||||
if(!$queue->count_to_process) {
|
||||
$queue->processed_at = current_time('mysql');
|
||||
$queue->status = self::STATUS_COMPLETED;
|
||||
$queue->status = SendingQueueModel::STATUS_COMPLETED;
|
||||
}
|
||||
$queue->subscribers = serialize((array) $queue->subscribers);
|
||||
$queue->save();
|
||||
|
@ -1,5 +1,6 @@
|
||||
<?php
|
||||
namespace MailPoet\Models;
|
||||
use MailPoet\Util\Helpers;
|
||||
|
||||
if(!defined('ABSPATH')) exit;
|
||||
|
||||
@ -55,11 +56,19 @@ class Newsletter extends Model {
|
||||
}
|
||||
|
||||
function duplicate($data = array()) {
|
||||
$data = $this->asArray();
|
||||
unset($data['id']);
|
||||
// get current newsletter's data as an array
|
||||
$newsletter_data = $this->asArray();
|
||||
|
||||
$duplicate = self::create();
|
||||
// remove id so that it creates a new record
|
||||
unset($newsletter_data['id']);
|
||||
|
||||
// merge data with newsletter data (allows override)
|
||||
$data = array_merge($newsletter_data, $data);
|
||||
|
||||
$duplicate = self::create();
|
||||
$duplicate->hydrate($data);
|
||||
|
||||
// reset timestamps
|
||||
$duplicate->set_expr('created_at', 'NOW()');
|
||||
$duplicate->set_expr('updated_at', 'NOW()');
|
||||
$duplicate->set_expr('deleted_at', 'NULL');
|
||||
@ -67,15 +76,25 @@ class Newsletter extends Model {
|
||||
// reset status
|
||||
$duplicate->set('status', self::STATUS_DRAFT);
|
||||
|
||||
// TODO: duplicate segments linked (if need be)
|
||||
$duplicate->save();
|
||||
|
||||
// TODO: duplicate options (if need be)
|
||||
if($duplicate->getErrors() === false) {
|
||||
// create relationships between duplicate and segments
|
||||
$segments = $this->segments()->findArray();
|
||||
|
||||
if($duplicate->save()) {
|
||||
return $duplicate;
|
||||
} else {
|
||||
return false;
|
||||
if(!empty($segments)) {
|
||||
foreach($segments as $segment) {
|
||||
$relation = NewsletterSegment::create();
|
||||
$relation->segment_id = $segment['id'];
|
||||
$relation->newsletter_id = $duplicate->id();
|
||||
$result = $relation->save();
|
||||
}
|
||||
}
|
||||
|
||||
// TODO: duplicate options (if need be)
|
||||
}
|
||||
|
||||
return $duplicate;
|
||||
}
|
||||
|
||||
function asArray() {
|
||||
@ -133,6 +152,24 @@ class Newsletter extends Model {
|
||||
return $this;
|
||||
}
|
||||
|
||||
function withOptions() {
|
||||
$options = $this->options()->findArray();
|
||||
if(empty($options)) {
|
||||
$this->options = array();
|
||||
} else {
|
||||
$this->options = Helpers::arrayColumn($options, 'value', 'name');
|
||||
}
|
||||
return $this;
|
||||
}
|
||||
|
||||
function withTotalSent() {
|
||||
// total of subscribers who received the email
|
||||
$this->total_sent = (int)SendingQueue::where('newsletter_id', $this->id)
|
||||
->where('status', SendingQueue::STATUS_COMPLETED)
|
||||
->sum('count_processed');
|
||||
return $this;
|
||||
}
|
||||
|
||||
function withStatistics() {
|
||||
$statistics = $this->getStatistics();
|
||||
if($statistics === false) {
|
||||
@ -140,6 +177,7 @@ class Newsletter extends Model {
|
||||
} else {
|
||||
$this->statistics = $statistics->asArray();
|
||||
}
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
@ -149,9 +187,9 @@ class Newsletter extends Model {
|
||||
}
|
||||
return SendingQueue::tableAlias('queues')
|
||||
->selectExpr(
|
||||
'count(DISTINCT(clicks.subscriber_id)) as clicked, ' .
|
||||
'count(DISTINCT(opens.subscriber_id)) as opened, ' .
|
||||
'count(DISTINCT(unsubscribes.subscriber_id)) as unsubscribed '
|
||||
'COUNT(DISTINCT(clicks.subscriber_id)) as clicked, ' .
|
||||
'COUNT(DISTINCT(opens.subscriber_id)) as opened, ' .
|
||||
'COUNT(DISTINCT(unsubscribes.subscriber_id)) as unsubscribed '
|
||||
)
|
||||
->leftOuterJoin(
|
||||
MP_STATISTICS_CLICKS_TABLE,
|
||||
@ -299,14 +337,6 @@ class Newsletter extends Model {
|
||||
case self::TYPE_WELCOME:
|
||||
case self::TYPE_NOTIFICATION:
|
||||
$groups = array_merge($groups, array(
|
||||
array(
|
||||
'name' => self::STATUS_DRAFT,
|
||||
'label' => __('Not active'),
|
||||
'count' => Newsletter::getPublished()
|
||||
->filter('filterType', $type)
|
||||
->filter('filterStatus', self::STATUS_DRAFT)
|
||||
->count()
|
||||
),
|
||||
array(
|
||||
'name' => self::STATUS_ACTIVE,
|
||||
'label' => __('Active'),
|
||||
@ -314,6 +344,14 @@ class Newsletter extends Model {
|
||||
->filter('filterType', $type)
|
||||
->filter('filterStatus', self::STATUS_ACTIVE)
|
||||
->count()
|
||||
),
|
||||
array(
|
||||
'name' => self::STATUS_DRAFT,
|
||||
'label' => __('Not active'),
|
||||
'count' => Newsletter::getPublished()
|
||||
->filter('filterType', $type)
|
||||
->filter('filterStatus', self::STATUS_DRAFT)
|
||||
->count()
|
||||
)
|
||||
));
|
||||
break;
|
||||
@ -379,7 +417,15 @@ class Newsletter extends Model {
|
||||
}
|
||||
|
||||
static function listingQuery($data = array()) {
|
||||
return self::filter('filterType', $data['tab'])
|
||||
return self::select(array(
|
||||
'id',
|
||||
'subject',
|
||||
'type',
|
||||
'status',
|
||||
'updated_at',
|
||||
'deleted_at'
|
||||
))
|
||||
->filter('filterType', $data['tab'])
|
||||
->filter('filterBy', $data)
|
||||
->filter('groupBy', $data)
|
||||
->filter('search', $data['search']);
|
||||
|
@ -6,6 +6,8 @@ if(!defined('ABSPATH')) exit;
|
||||
class SendingQueue extends Model {
|
||||
public static $_table = MP_SENDING_QUEUES_TABLE;
|
||||
|
||||
const STATUS_COMPLETED = 'completed';
|
||||
|
||||
function __construct() {
|
||||
parent::__construct();
|
||||
}
|
||||
|
@ -150,9 +150,13 @@ class Newsletters {
|
||||
|
||||
$newsletter = Newsletter::findOne($id);
|
||||
if($newsletter !== false) {
|
||||
$result = $newsletter->duplicate(array(
|
||||
$duplicate = $newsletter->duplicate(array(
|
||||
'subject' => sprintf(__('Copy of %s'), $newsletter->subject)
|
||||
))->asArray();
|
||||
));
|
||||
|
||||
if($duplicate !== false && $duplicate->getErrors() === false) {
|
||||
$result = $newsletter->asArray();
|
||||
}
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
@ -256,7 +260,13 @@ class Newsletters {
|
||||
->withStatistics();
|
||||
} else if($newsletter->type === Newsletter::TYPE_WELCOME) {
|
||||
$newsletter
|
||||
->withOptions()
|
||||
->withTotalSent()
|
||||
->withStatistics();
|
||||
|
||||
$options = $newsletter->options()->findArray();
|
||||
$newsletter->options = Helpers::arrayColumn($options, 'value', 'name');
|
||||
|
||||
} else if($newsletter->type === Newsletter::TYPE_NOTIFICATION) {
|
||||
$newsletter
|
||||
->withSegments()
|
||||
|
@ -14,6 +14,7 @@
|
||||
var mailpoet_schedule_time_of_day = <%= json_encode(schedule_time_of_day) %>;
|
||||
var mailpoet_date_display_format = "<%= wp_date_format() %>";
|
||||
var mailpoet_date_storage_format = "Y-m-d";
|
||||
var mailpoet_tracking_enabled = <%= json_encode(tracking_enabled) %>;
|
||||
</script>
|
||||
<% endblock %>
|
||||
|
||||
@ -61,6 +62,8 @@
|
||||
'statistics': __('Opened, Clicked, Unsubscribed'),
|
||||
'lists': __('Lists'),
|
||||
'settings': __('Settings'),
|
||||
'history': __('History'),
|
||||
'viewHistory': __('View history'),
|
||||
'createdOn': __('Created on'),
|
||||
'lastModifiedOn': __('Last modified on'),
|
||||
'oneNewsletterTrashed': __('1 newsletter was moved to the trash.'),
|
||||
@ -79,6 +82,7 @@
|
||||
'active': __('Active'),
|
||||
'inactive': __('Not Active'),
|
||||
'newsletterQueueCompleted': __('Sent to %$1d of %$2d.'),
|
||||
'sentToXSubscribers': __('Sent to %$1d subscribers.'),
|
||||
'resume': __('Resume'),
|
||||
'pause': __('Pause'),
|
||||
'new': __('New'),
|
||||
@ -133,7 +137,7 @@
|
||||
'selectEventToSendWelcomeEmail': __('Select an event to send this welcome email'),
|
||||
|
||||
'onSubscriptionToList': __('When someone subscribes to the list...'),
|
||||
'onWordpressUserRegistration': __('When a new Wordrpess user is added to your site...'),
|
||||
'onWordpressUserRegistration': __('When a new WordPress user is added to your site...'),
|
||||
'delayImmediately': __('immediately'),
|
||||
'delayHoursAfter': __('hour(s) after'),
|
||||
'delayDaysAfter': __('day(s) after'),
|
||||
|
Reference in New Issue
Block a user