edit subscription form + save

This commit is contained in:
Jonathan Labreuille
2016-03-03 15:57:42 +01:00
parent 85995bc8a6
commit 4b528549f5
13 changed files with 302 additions and 146 deletions

View File

@ -2,3 +2,13 @@
@require 'parsley' @require 'parsley'
@require 'form_validation' @require 'form_validation'
/* labels */
.mailpoet_text_label
.mailpoet_textarea_label
.mailpoet_select_label
.mailpoet_radio_label
.mailpoet_checkbox_label
.mailpoet_list_label
.mailpoet_date_label
display:block

View File

@ -1,8 +1,12 @@
<?php <?php
namespace MailPoet\Config; namespace MailPoet\Config;
use \MailPoet\Models\Setting; use \MailPoet\Models\Setting;
use \MailPoet\Util\Url;
class Changelog { class Changelog {
function __construct() {
}
function init() { function init() {
$doing_ajax = (bool)(defined('DOING_AJAX') && DOING_AJAX); $doing_ajax = (bool)(defined('DOING_AJAX') && DOING_AJAX);
@ -42,20 +46,7 @@ class Changelog {
// save version number // save version number
Setting::setValue('version', Env::$version); Setting::setValue('version', Env::$version);
global $wp; Url::redirectWithReferer($redirect_url);
$current_url = home_url(add_query_arg($wp->query_string, $wp->request));
if($redirect_url !== $current_url) {
wp_safe_redirect(
add_query_arg(
array(
'mailpoet_redirect' => urlencode($current_url)
),
$redirect_url
)
);
exit;
}
} }
} }
} }

View File

@ -20,18 +20,22 @@ class Checkbox extends Base {
foreach($options as $option) { foreach($options as $option) {
$html .= '<label class="mailpoet_checkbox_label">'; $html .= '<label class="mailpoet_checkbox_label">';
$html .= '<input type="hidden" name="'.$field_name.'" value="" />';
$html .= '<input type="checkbox" class="mailpoet_checkbox" '; $html .= '<input type="checkbox" class="mailpoet_checkbox" ';
$html .= 'name="'.$field_name.'" '; $html .= 'name="'.$field_name.'" ';
$html .= 'value="1" '; $html .= 'value="1" ';
$html .= (isset($option['is_checked']) && $option['is_checked']) $html .= (
? 'checked="checked"' : ''; (isset($option['is_checked']) && $option['is_checked'])
||
(self::getFieldValue($block))
) ? 'checked="checked"' : '';
$html .= $field_validation; $html .= $field_validation;
$html .= ' />'.$option['value']; $html .= ' /> '.$option['value'];
$html .= '</label>'; $html .= '</label>';
} }

View File

@ -33,18 +33,37 @@ class Date extends Base {
// generate an array of selectors based on date format // generate an array of selectors based on date format
$date_selectors = explode('/', $date_format); $date_selectors = explode('/', $date_format);
// format value if present
$value = self::getFieldValue($block);
$day = null;
$month = null;
$year = null;
if($value) {
$day = (int)strftime('%d', $value);
$month = (int)strftime('%m', $value);
$year = (int)strftime('%Y', $value);
} else if(!empty($block['params']['is_default_today'])) {
$day = (int)strftime('%d');
$month = (int)strftime('%m');
$year = (int)strftime('%Y');
}
foreach($date_selectors as $date_selector) { foreach($date_selectors as $date_selector) {
if($date_selector === 'dd') { if($date_selector === 'dd') {
$block['selected'] = $day;
$html .= '<select class="mailpoet_date_day" '; $html .= '<select class="mailpoet_date_day" ';
$html .= 'name="'.$field_name.'[day]" placeholder="'.__('Day').'">'; $html .= 'name="'.$field_name.'[day]" placeholder="'.__('Day').'">';
$html .= static::getDays($block); $html .= static::getDays($block);
$html .= '</select>'; $html .= '</select>';
} else if($date_selector === 'mm') { } else if($date_selector === 'mm') {
$block['selected'] = $month;
$html .= '<select class="mailpoet_date_month" '; $html .= '<select class="mailpoet_date_month" ';
$html .= 'name="'.$field_name.'[month]" placeholder="'.__('Month').'">'; $html .= 'name="'.$field_name.'[month]" placeholder="'.__('Month').'">';
$html .= static::getMonths($block); $html .= static::getMonths($block);
$html .= '</select>'; $html .= '</select>';
} else if($date_selector === 'yyyy') { } else if($date_selector === 'yyyy') {
$block['selected'] = $year;
$html .= '<select class="mailpoet_date_year" '; $html .= '<select class="mailpoet_date_year" ';
$html .= 'name="'.$field_name.'[year]" placeholder="'.__('Year').'">'; $html .= 'name="'.$field_name.'[year]" placeholder="'.__('Year').'">';
$html .= static::getYears($block); $html .= static::getYears($block);
@ -84,11 +103,6 @@ class Date extends Base {
'selected' => null 'selected' => null
); );
// is default today
if(!empty($block['params']['is_default_today'])) {
$defaults['selected'] = (int)strftime('%m');
}
// merge block with defaults // merge block with defaults
$block = array_merge($defaults, $block); $block = array_merge($defaults, $block);

View File

@ -27,8 +27,12 @@ class Radio extends Base {
$html .= 'value="'.esc_attr($option['value']).'" '; $html .= 'value="'.esc_attr($option['value']).'" ';
$html .= (isset($option['is_checked']) && $option['is_checked']) $html .= (
? 'checked="checked"' : ''; (isset($option['is_checked']) && $option['is_checked'])
||
(self::getFieldValue($block) === $option['value'])
) ? 'checked="checked"' : '';
$html .= $field_validation; $html .= $field_validation;
$html .= ' />&nbsp;'.esc_attr($option['value']); $html .= ' />&nbsp;'.esc_attr($option['value']);

View File

@ -28,7 +28,7 @@ class Segment extends Base {
$html .= 'name="'.$field_name.'[]" '; $html .= 'name="'.$field_name.'[]" ';
$html .= 'value="'.$option['id'].'" '.$is_checked.' '; $html .= 'value="'.$option['id'].'" '.$is_checked.' ';
$html .= $field_validation; $html .= $field_validation;
$html .= ' />'.$option['name']; $html .= ' /> '.$option['name'];
$html .= '</label>'; $html .= '</label>';
} }

View File

@ -10,9 +10,7 @@ class Select extends Base {
$field_validation = static::getInputValidation($block); $field_validation = static::getInputValidation($block);
$html .= '<p class="mailpoet_paragraph">'; $html .= '<p class="mailpoet_paragraph">';
$html .= static::renderLabel($block); $html .= static::renderLabel($block);
$html .= '<select class="mailpoet_select" name="'.$field_name.'">'; $html .= '<select class="mailpoet_select" name="'.$field_name.'">';
if(isset($block['params']['label_within']) if(isset($block['params']['label_within'])
@ -21,8 +19,11 @@ class Select extends Base {
} }
foreach($block['params']['values'] as $option) { foreach($block['params']['values'] as $option) {
$is_selected = (isset($option['is_checked']) && $option['is_checked']) $is_selected = (
? 'selected="selected"' : ''; (isset($option['is_checked']) && $option['is_checked'])
||
(self::getFieldValue($block) === $option['value'])
) ? 'selected="selected"' : '';
if(is_array($option['value'])) { if(is_array($option['value'])) {
$value = key($option['value']); $value = key($option['value']);

View File

@ -17,7 +17,7 @@ class Styles {
} }
/* labels */ /* labels */
.mailpoet_input_label, .mailpoet_text_label,
.mailpoet_textarea_label, .mailpoet_textarea_label,
.mailpoet_select_label, .mailpoet_select_label,
.mailpoet_radio_label, .mailpoet_radio_label,
@ -28,7 +28,7 @@ class Styles {
} }
/* inputs */ /* inputs */
.mailpoet_input, .mailpoet_text,
.mailpoet_textarea, .mailpoet_textarea,
.mailpoet_select, .mailpoet_select,
.mailpoet_date { .mailpoet_date {
@ -36,9 +36,7 @@ class Styles {
} }
.mailpoet_checkbox { .mailpoet_checkbox {
display:inline;
margin-right: 5px;
vertical-align:middle;
} }
.mailpoet_validate_success { .mailpoet_validate_success {

View File

@ -186,6 +186,6 @@ class Segment extends Model {
} }
static function getPublic() { static function getPublic() {
return self::getPublished()->where('type', 'default'); return self::getPublished()->where('type', 'default')->orderByAsc('name');
} }
} }

View File

@ -18,7 +18,7 @@ class SubscriberSegment extends Model {
SubscriberSegment::where('subscriber_id', $subscriber->id) SubscriberSegment::where('subscriber_id', $subscriber->id)
->whereNotIn('segment_id', $segment_ids) ->whereNotIn('segment_id', $segment_ids)
->findResultSet() ->findResultSet()
->set('status', 'unsubscribed') ->set('status', Subscriber::STATUS_UNSUBSCRIBED)
->save(); ->save();
// subscribe to segments // subscribe to segments
@ -26,7 +26,7 @@ class SubscriberSegment extends Model {
self::createOrUpdate(array( self::createOrUpdate(array(
'subscriber_id' => $subscriber->id, 'subscriber_id' => $subscriber->id,
'segment_id' => $segment_id, 'segment_id' => $segment_id,
'status' => 'subscribed' 'status' => Subscriber::STATUS_SUBSCRIBED
)); ));
} }
} }
@ -35,7 +35,7 @@ class SubscriberSegment extends Model {
} }
static function subscribed($orm) { static function subscribed($orm) {
return $orm->where('status', 'subscribed'); return $orm->where('status', Subscriber::STATUS_SUBSCRIBED);
} }
static function createOrUpdate($data = array()) { static function createOrUpdate($data = array()) {

View File

@ -1,11 +1,13 @@
<?php <?php
namespace MailPoet\Subscription; namespace MailPoet\Subscription;
use \MailPoet\Router\Subscribers;
use \MailPoet\Models\Subscriber; use \MailPoet\Models\Subscriber;
use \MailPoet\Models\CustomField; use \MailPoet\Models\CustomField;
use \MailPoet\Models\Setting; use \MailPoet\Models\Setting;
use \MailPoet\Models\Segment; use \MailPoet\Models\Segment;
use \MailPoet\Util\Helpers; use \MailPoet\Util\Helpers;
use \MailPoet\Util\Url;
class Pages { class Pages {
function __construct() { function __construct() {
@ -17,6 +19,27 @@ class Pages {
add_filter('the_title', array($this,'setPageTitle')); add_filter('the_title', array($this,'setPageTitle'));
add_filter('the_content', array($this,'setPageContent')); add_filter('the_content', array($this,'setPageContent'));
} }
add_action('admin_post_update', array($this, 'updateSubscriber'));
}
function updateSubscriber() {
$action = (isset($_POST['action']) ? $_POST['action'] : null);
if($action !== 'update') {
Url::redirectBack();
}
$reserved_keywords = array('action', 'mailpoet_redirect');
$subscriber_data = array_diff_key(
$_POST,
array_flip($reserved_keywords)
);
$subscriber = Subscriber::createOrUpdate($subscriber_data);
$errors = $subscriber->getErrors();
// TODO: success/error messages
Url::redirectBack();
} }
function isPreview() { function isPreview() {
@ -101,7 +124,12 @@ class Pages {
} }
private function getEditTitle($subscriber) { private function getEditTitle($subscriber) {
if($subscriber !== false) { if($this->isPreview()) {
return sprintf(
__('Edit your subscriber profile: %s'),
'demo@mailpoet.com'
);
} else if($subscriber !== false) {
return sprintf( return sprintf(
__('Edit your subscriber profile: %s'), __('Edit your subscriber profile: %s'),
$subscriber->email $subscriber->email
@ -123,124 +151,135 @@ class Pages {
} }
private function getEditContent($subscriber) { private function getEditContent($subscriber) {
if($subscriber !== false) { if($this->isPreview()) {
$subscriber = Subscriber::create();
$subscriber->hydrate(array(
'email' => 'demo@mailpoet.com'
));
} else if($subscriber !== false) {
$subscriber = $subscriber $subscriber = $subscriber
->withCustomFields() ->withCustomFields()
->withSubscriptions(); ->withSubscriptions();
} else {
return;
}
$custom_fields = array_map(function($custom_field) use($subscriber) { $custom_fields = array_map(function($custom_field) use($subscriber) {
$custom_field->id = 'cf_'.$custom_field->id; $custom_field->id = 'cf_'.$custom_field->id;
$custom_field = $custom_field->asArray(); $custom_field = $custom_field->asArray();
$custom_field['params']['value'] = $subscriber->{$custom_field['id']}; $custom_field['params']['value'] = $subscriber->{$custom_field['id']};
return $custom_field; return $custom_field;
}, CustomField::findMany()); }, CustomField::findMany());
$segment_ids = Setting::getValue('subscription.segments', array()); $segment_ids = Setting::getValue('subscription.segments', array());
if(!empty($segment_ids)) { if(!empty($segment_ids)) {
$segments = Segment::getPublic() $segments = Segment::getPublic()
->whereIn('id', $segment_ids) ->whereIn('id', $segment_ids)
->findMany(); ->findMany();
} else { } else {
$segments = Segment::getPublic()->findMany(); $segments = Segment::getPublic()
->findMany();
}
$subscribed_segment_ids = array();
if(!empty($subscriber->subscriptions)) {
foreach ($subscriber->subscriptions as $subscription) {
if($subscription['status'] === Subscriber::STATUS_SUBSCRIBED) {
$subscribed_segment_ids[] = $subscription['segment_id'];
}
} }
}
$subscribed_segment_ids = Helpers::arrayColumn( $segments = array_map(function($segment) use($subscribed_segment_ids) {
$subscriber->subscriptions, 'id' return array(
'id' => $segment->id,
'name' => $segment->name,
'is_checked' => in_array($segment->id, $subscribed_segment_ids)
); );
}, $segments);
$segments = array_map(function($segment) use($subscribed_segment_ids) { $fields = array(
return array( array(
'id' => $segment->id, 'id' => 'email',
'name' => $segment->name, 'type' => 'text',
'is_checked' => in_array($segment->id, $subscribed_segment_ids) 'params' => array(
); 'label' => __('Email'),
}, $segments); 'required' => true,
'value' => $subscriber->email
$fields = array( )
array( ),
'id' => 'email', array(
'type' => 'text', 'id' => 'first_name',
'params' => array( 'type' => 'text',
'label' => __('Email'), 'params' => array(
'required' => true, 'label' => __('First name'),
'value' => $subscriber->email 'value' => $subscriber->first_name
) )
), ),
array( array(
'id' => 'first_name', 'id' => 'last_name',
'type' => 'text', 'type' => 'text',
'params' => array( 'params' => array(
'label' => __('First name'), 'label' => __('Last name'),
'value' => $subscriber->first_name 'value' => $subscriber->last_name
) )
), ),
array( array(
'id' => 'last_name', 'id' => 'status',
'type' => 'text', 'type' => 'select',
'params' => array( 'params' => array(
'label' => __('Last name'), 'label' => __('Status'),
'value' => $subscriber->last_name 'values' => array(
) array(
), 'value' => array(
array( Subscriber::STATUS_SUBSCRIBED => __('Subscribed')
'id' => 'status',
'type' => 'select',
'params' => array(
'label' => __('Status'),
'values' => array(
array(
'value' => array(
Subscriber::STATUS_SUBSCRIBED => __('Subscribed')
),
'is_checked' => (
$subscriber->status === Subscriber::STATUS_SUBSCRIBED
)
), ),
array( 'is_checked' => (
'value' => array( $subscriber->status === Subscriber::STATUS_SUBSCRIBED
Subscriber::STATUS_UNSUBSCRIBED => __('Unsubscribed') )
), ),
'is_checked' => ( array(
$subscriber->status === Subscriber::STATUS_UNSUBSCRIBED 'value' => array(
) Subscriber::STATUS_UNSUBSCRIBED => __('Unsubscribed')
), ),
array( 'is_checked' => (
'value' => array( $subscriber->status === Subscriber::STATUS_UNSUBSCRIBED
Subscriber::STATUS_UNCONFIRMED => __('Unconfirmed') )
), ),
'is_checked' => ( array(
$subscriber->status === Subscriber::STATUS_UNCONFIRMED 'value' => array(
) Subscriber::STATUS_UNCONFIRMED => __('Unconfirmed')
),
'is_checked' => (
$subscriber->status === Subscriber::STATUS_UNCONFIRMED
) )
) )
) )
) )
); )
);
$form = array_merge( $form = array_merge(
$fields, $fields,
$custom_fields, $custom_fields,
array(
array( array(
array( 'id' => 'submit',
'id' => 'segment', 'type' => 'submit',
'type' => 'segment', 'params' => array(
'params' => array( 'label' => __('Subscribe!')
'label' => __('Your lists'),
'values' => $segments
)
),
array(
'id' => 'submit',
'type' => 'submit',
'params' => array(
'label' => __('Subscribe!')
)
) )
) )
); )
);
return \MailPoet\Form\Renderer::renderBlocks($form); $form_html = '<form method="POST" action="'.admin_url('admin-post.php').'" novalidate>';
} $form_html .= '<input type="hidden" name="action" value="update" />';
$form_html .= '<input type="hidden" name="mailpoet_redirect" value="'.Url::getCurrentUrl().'" />';
$form_html .= \MailPoet\Form\Renderer::renderBlocks($form);
$form_html .= '</form>';
return $form_html;
} }
private function getUnsubscribeContent($subscriber) { private function getUnsubscribeContent($subscriber) {

55
lib/Util/Url.php Normal file
View File

@ -0,0 +1,55 @@
<?php
namespace MailPoet\Util;
class Url {
function __construct() {
}
static function getCurrentUrl() {
global $wp;
return home_url(
add_query_arg(
$wp->query_string,
$wp->request
)
);
}
static function redirectTo($url = null) {
wp_safe_redirect($url);
exit();
}
static function redirectBack() {
$referer = (isset($_REQUEST['mailpoet_redirect'])
? $_REQUEST['mailpoet_redirect']
: null
);
if($referer === null) {
// try to get the server's referer
if(!empty($_SERVER['HTTP_REFERER'])) {
$referer = $_SERVER['HTTP_REFERER'];
}
}
if($referer !== null) {
self::redirectTo($referer);
}
exit();
}
static function redirectWithReferer($url = null) {
$current_url = self::getCurrentUrl();
$url = add_query_arg(
array(
'mailpoet_redirect' => urlencode($current_url)
),
$url
);
if($url !== $current_url) {
self::redirectTo($url);
}
exit();
}
}

View File

@ -194,14 +194,13 @@
<% endif %> <% endif %>
</td> </td>
</tr> </tr>
<!-- manage subscriptions--> <!-- edit subscription-->
<tr> <tr>
<th scope="row"> <th scope="row">
<label for="settings[subscription_edit]"> <label for="subscription_edit_page">
<%= __('Unsubscribe & Manage Subscription page') %> <%= __('Manage Subscription page') %>
<p class="description"> <p class="description">
<%= __('The page your subscribers see when they click to <%= __('The page your subscribers see when they click on "Manage your subscription" in your emails.') %>
"Unsubscribe" or "Manage your subscription" in your emails.') %>
</p> </p>
</label> </label>
</th> </th>
@ -209,14 +208,15 @@
<p> <p>
<select <select
class="mailpoet_page_selection" class="mailpoet_page_selection"
name="subscription[page]" id="subscription_edit_page"
name="subscription[edit_page]"
> >
<% for page in pages %> <% for page in pages %>
<option <option
value="<%= page.id %>" value="<%= page.id %>"
data-preview-url="<%= page.preview_url|raw %>&amp;mailpoet_action=unsubscribe" data-preview-url="<%= page.preview_url|raw %>&amp;mailpoet_action=edit"
data-edit-url="<%= page.edit_url|raw %>" data-edit-url="<%= page.edit_url|raw %>"
<% if(page.id == settings.subscription.page) %> <% if(page.id == settings.subscription.edit_page) %>
selected="selected" selected="selected"
<% endif %> <% endif %>
><%= page.title %></option> ><%= page.title %></option>
@ -254,6 +254,46 @@
</p> </p>
</td> </td>
</tr> </tr>
<!-- unsubscribe-->
<tr>
<th scope="row">
<label for="subscription_unsubscribe_page">
<%= __('Unsubscribe page') %>
<p class="description">
<%= __('The page your subscribers see when they click on "Unsubscribe" in your emails.') %>
</p>
</label>
</th>
<td>
<p>
<select
class="mailpoet_page_selection"
id="subscription_unsubscribe_page"
name="subscription[unsubscribe_page]"
>
<% for page in pages %>
<option
value="<%= page.id %>"
data-preview-url="<%= page.preview_url|raw %>&amp;mailpoet_action=unsubscribe"
data-edit-url="<%= page.edit_url|raw %>"
<% if(page.id == settings.subscription.unsubscribe_page) %>
selected="selected"
<% endif %>
><%= page.title %></option>
<% endfor %>
</select>
<a
class="mailpoet_page_preview"
href="javascript:;"
title="<%= __('Preview page') %>"
><%= __('Preview') %></a>&nbsp;|&nbsp;<a
class="mailpoet_page_edit"
href="javascript:;"
title="<%= __('Edit page') %>"
><%= __('Edit') %></a>
</p>
</td>
</tr>
<!-- shortcode: archive page --> <!-- shortcode: archive page -->
<tr> <tr>
<th scope="row"> <th scope="row">