Adds method to create subscriber

This commit is contained in:
Vlad
2017-05-14 14:46:53 -04:00
parent 3a1bf88c22
commit a1b3aaf1f8
2 changed files with 172 additions and 0 deletions

View File

@ -5,6 +5,7 @@ use MailPoet\Models\CustomField;
use MailPoet\Models\Segment; use MailPoet\Models\Segment;
use MailPoet\Models\Subscriber; use MailPoet\Models\Subscriber;
use MailPoet\Models\SubscriberSegment; use MailPoet\Models\SubscriberSegment;
use MailPoet\Newsletter\Scheduler\Scheduler;
if(!defined('ABSPATH')) exit; if(!defined('ABSPATH')) exit;
@ -74,4 +75,54 @@ class API {
function getLists() { function getLists() {
return Segment::whereNotEqual('type', Segment::TYPE_WP_USERS)->findArray(); return Segment::whereNotEqual('type', Segment::TYPE_WP_USERS)->findArray();
} }
function addSubscriber(array $subscriber, $segments = array(), $options = array()) {
// throw exception when subscriber email is missing
if(empty($subscriber['email'])) {
throw new \Exception(
__('Subscriber email address is required.', 'mailpoet')
);
}
// throw exception when subscriber already exists
if(Subscriber::findOne($subscriber['email'])) {
throw new \Exception(
__('This subscriber already exists.', 'mailpoet')
);
}
// separate data into default and custom fields
list($default_fields, $custom_fields) = CustomField::extractCustomFieldsFromFromObject($subscriber);
// if some required default fields are missing, set their values
$default_fields = Subscriber::setRequiredFieldsDefaultValues($default_fields);
// add subscriber
$new_subscriber = Subscriber::create();
$new_subscriber->hydrate($default_fields);
$new_subscriber->save();
if($new_subscriber->getErrors() !== false) {
throw new \Exception(
__(sprintf('Failed to add subscriber: %s', strtolower(implode(', ', $new_subscriber->getErrors()))), 'mailpoet')
);
}
if(!empty($custom_fields)) {
$new_subscriber->saveCustomFields($custom_fields);
}
// subscribe to segments and optionally: 1) send confirmation email, 2) schedule welcome email(s)
if(!empty($segments)) {
$this->subscribeToLists($new_subscriber->id, $segments);
// send confirmation email
if(!empty($options['send_confirmation_email']) && $new_subscriber->status === Subscriber::STATUS_UNCONFIRMED) {
$this->sendConfirmationEmail($new_subscriber);
}
// schedule welcome email(s)
if(!empty($options['schedule_welcome_email'])) {
Scheduler::scheduleSubscriberWelcomeNotification($new_subscriber->id, $segments);
}
}
return $new_subscriber->withCustomFields()->withSubscriptions()->asArray();
}
} }

View File

@ -3,12 +3,18 @@
use Codeception\Util\Fixtures; use Codeception\Util\Fixtures;
use MailPoet\API\API; use MailPoet\API\API;
use MailPoet\Models\CustomField; use MailPoet\Models\CustomField;
use MailPoet\Models\Newsletter;
use MailPoet\Models\NewsletterOption;
use MailPoet\Models\NewsletterOptionField;
use MailPoet\Models\Segment; use MailPoet\Models\Segment;
use MailPoet\Models\SendingQueue;
use MailPoet\Models\Subscriber; use MailPoet\Models\Subscriber;
use MailPoet\Models\SubscriberCustomField;
use MailPoet\Models\SubscriberSegment; use MailPoet\Models\SubscriberSegment;
class MPAPITest extends MailPoetTest { class MPAPITest extends MailPoetTest {
const VERSION = 'v1'; const VERSION = 'v1';
function testItReturnsSubscriberFields() { function testItReturnsSubscriberFields() {
$custom_field = CustomField::create(); $custom_field = CustomField::create();
$custom_field->name = 'test custom field'; $custom_field->name = 'test custom field';
@ -162,10 +168,125 @@ class MPAPITest extends MailPoetTest {
expect($result[0]['id'])->equals($default_segment->id); expect($result[0]['id'])->equals($default_segment->id);
} }
function testItRequiresEmailAddressToAddSubscriber() {
try {
API::MP(self::VERSION)->addSubscriber(array());
$this->fail('Subscriber email address required exception should have been thrown.');
} catch(\Exception $e) {
expect($e->getMessage())->equals('Subscriber email address is required.');
}
}
function testItDoesNotAddExistingSubscriber() {
$subscriber = Subscriber::create();
$subscriber->hydrate(Fixtures::get('subscriber_template'));
$subscriber->save();
try {
API::MP(self::VERSION)->addSubscriber(array('email' => $subscriber->email));
$this->fail('Subscriber exists exception should have been thrown.');
} catch(\Exception $e) {
expect($e->getMessage())->equals('This subscriber already exists.');
}
}
function testItThrowsExceptionWhenSubscriberCannotBeAdded() {
$subscriber = array(
'email' => 'test' // invalid email
);
try {
API::MP(self::VERSION)->addSubscriber($subscriber);
$this->fail('Failed to add subscriber exception should have been thrown.');
} catch(\Exception $e) {
expect($e->getMessage())->contains('Failed to add subscriber:');
// error message (converted to lowercase) returned by the model
expect($e->getMessage())->contains('your email address is invalid!');
}
}
function testItAddsSubscriber() {
$custom_field = CustomField::create();
$custom_field->name = 'test custom field';
$custom_field->type = CustomField::TYPE_TEXT;
$custom_field->save();
$subscriber = array(
'email' => 'test@example.com',
'cf_' . $custom_field->id => 'test'
);
$result = API::MP(self::VERSION)->addSubscriber($subscriber);
expect($result['id'])->greaterThan(0);
expect($result['email'])->equals($subscriber['email']);
expect($result['cf_' . $custom_field->id])->equals('test');
}
function testItSubscribesToSegmentsWhenAddingSubscriber() {
$segment = Segment::createOrUpdate(
array(
'name' => 'Default',
'type' => Segment::TYPE_DEFAULT
)
);
$subscriber = array(
'email' => 'test@example.com'
);
$result = API::MP(self::VERSION)->addSubscriber($subscriber, array($segment->id));
expect($result['id'])->greaterThan(0);
expect($result['email'])->equals($subscriber['email']);
expect($result['subscriptions'][0]['id'])->equals($segment->id);
}
function testItSendsConfirmationEmailAfterAddingSubscriber() {
$segment = Segment::createOrUpdate(
array(
'name' => 'Default',
'type' => Segment::TYPE_DEFAULT
)
);
$subscriber = array(
'email' => 'test@example.com'
);
$options = array('schedule_welcome_email' => true);
// create newsletter with associated options to send welcome email one day after subscription to segment
$newsletter = Newsletter::create();
$newsletter->type = Newsletter::TYPE_WELCOME;
$newsletter->status = Newsletter::STATUS_ACTIVE;
$newsletter->save();
$newsletter_options = array(
'event' => 'segment',
'segment' => $segment->id,
'afterTimeType' => 'days',
'afterTimeNumber' => 1
);
foreach($newsletter_options as $option => $value) {
$newsletter_option_field = NewsletterOptionField::create();
$newsletter_option_field->name = $option;
$newsletter_option_field->newsletter_type = $newsletter->type;
$newsletter_option_field->save();
expect($newsletter_option_field->getErrors())->false();
$newsletter_option = NewsletterOption::create();
$newsletter_option->option_field_id = $newsletter_option_field->id;
$newsletter_option->newsletter_id = $newsletter->id;
$newsletter_option->value = $value;
$newsletter_option->save();
expect($newsletter_option->getErrors())->false();
}
expect(SendingQueue::findArray())->count(0);
API::MP(self::VERSION)->addSubscriber($subscriber, array($segment->id), $options);
expect(SendingQueue::findArray())->count(1);
}
function _after() { function _after() {
ORM::raw_execute('TRUNCATE ' . Subscriber::$_table); ORM::raw_execute('TRUNCATE ' . Subscriber::$_table);
ORM::raw_execute('TRUNCATE ' . CustomField::$_table); ORM::raw_execute('TRUNCATE ' . CustomField::$_table);
ORM::raw_execute('TRUNCATE ' . Segment::$_table); ORM::raw_execute('TRUNCATE ' . Segment::$_table);
ORM::raw_execute('TRUNCATE ' . SubscriberSegment::$_table); ORM::raw_execute('TRUNCATE ' . SubscriberSegment::$_table);
ORM::raw_execute('TRUNCATE ' . SubscriberCustomField::$_table);
ORM::raw_execute('TRUNCATE ' . NewsletterOption::$_table);
ORM::raw_execute('TRUNCATE ' . NewsletterOptionField::$_table);
ORM::raw_execute('TRUNCATE ' . SendingQueue::$_table);
} }
} }