Skip to content

Commit

Permalink
Merge pull request #26 from omnisend/contact-sync
Browse files Browse the repository at this point in the history
Contact sync
  • Loading branch information
nerijuszaniauskas authored Feb 21, 2024
2 parents 377d978 + 8006f01 commit c086fde
Show file tree
Hide file tree
Showing 8 changed files with 194 additions and 10 deletions.
10 changes: 5 additions & 5 deletions composer.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

24 changes: 22 additions & 2 deletions omnisend/class-omnisend-core-bootstrap.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
*
* Plugin Name: Omnisend
* Description: Omnisend main plugin that enables integration with Omnisend.
* Version: 1.2.1
* Version: 1.3.0
* Author: Omnisend
* Author URI: https://www.omnisend.com
* Developer: Omnisend
Expand All @@ -22,10 +22,14 @@

defined( 'ABSPATH' ) || die( 'no direct access' );

const OMNISEND_CORE_PLUGIN_VERSION = '1.2.1';
const OMNISEND_CORE_PLUGIN_VERSION = '1.3.0';
const OMNISEND_CORE_SETTINGS_PAGE = 'omnisend';
const OMNISEND_CORE_PLUGIN_NAME = 'Email Marketing by Omnisend';

const OMNISEND_CORE_CRON_SCHEDULE_EVERY_MINUTE = 'omni_send_core_every_minute';

const OMNISEND_CORE_CRON_SYNC_CONTACT = 'omni_send_cron_sync_contacts';

// Change for different environment.
const OMNISEND_CORE_API_V3 = 'https://api.omnisend.com/v3';
const OMNISEND_CORE_SNIPPET_URL = 'https://omnisnippet1.com/inshop/launcher-v2.js';
Expand All @@ -40,6 +44,9 @@
class Omnisend_Core_Bootstrap {

public static function load(): void {
// phpcs:ignore because linter could not detect internal, but it is fine
add_filter( 'cron_schedules', 'Omnisend_Core_Bootstrap::cron_schedules' ); // phpcs:ignore

add_action( 'admin_notices', 'Omnisend_Core_Bootstrap::admin_notices' );
add_action( 'admin_menu', 'Omnisend_Core_Bootstrap::add_admin_menu' );
add_action( 'admin_enqueue_scripts', 'Omnisend_Core_Bootstrap::load_omnisend_admin_styles' );
Expand All @@ -49,6 +56,10 @@ public static function load(): void {
if ( ! self::is_omnisend_woocommerce_plugin_active() || ! self::is_omnisend_woocommerce_plugin_connected() ) {
add_action( 'wp_footer', 'Omnisend\Internal\Snippet::add' );
}

add_action( OMNISEND_CORE_CRON_SYNC_CONTACT, 'Omnisend\Internal\Sync::sync_contacts' );
add_action( 'user_register', 'Omnisend\Internal\Sync::hook_user_register' );
add_action( 'profile_update', 'Omnisend\Internal\Sync::hook_profile_update' );
}

public static function add_admin_menu() {
Expand All @@ -63,6 +74,15 @@ public static function add_admin_menu() {
add_menu_page( $page_title, $menu_title, $capability, $menu_slug, $function, $omnisend_icon, $position );
}

public static function cron_schedules( $schedules ) {
$schedules[ OMNISEND_CORE_CRON_SCHEDULE_EVERY_MINUTE ] = array(
'interval' => 60,
'display' => __( 'Every minute', 'omnisend' ),
);

return $schedules;
}

public static function load_omnisend_admin_styles(): void {
// phpcs:disable WordPress.Security.NonceVerification
if ( isset( $_GET['page'] ) ) {
Expand Down
6 changes: 5 additions & 1 deletion omnisend/includes/Internal/class-connection.php
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ public static function display(): void {
check_admin_referer( 'connect' );
$api_key = sanitize_text_field( wp_unslash( $_POST['api_key'] ) );
$response = self::get_account_data( $api_key );
$brand_id = $response['brandID'];
$brand_id = ! empty( $response['brandID'] ) ? $response['brandID'] : '';

if ( ! $brand_id ) {
echo '<div class="notice notice-error"><p>The connection didn’t go through. Check if the API key is correct.</p></div>';
Expand Down Expand Up @@ -50,6 +50,10 @@ public static function display(): void {
Options::set_api_key( $api_key );
Options::set_brand_id( $brand_id );
Options::set_store_connected();

if ( ! wp_next_scheduled( OMNISEND_CORE_CRON_SYNC_CONTACT ) && ! Omnisend_Core_Bootstrap::is_omnisend_woocommerce_plugin_connected() ) {
wp_schedule_event( time(), OMNISEND_CORE_CRON_SCHEDULE_EVERY_MINUTE, OMNISEND_CORE_CRON_SYNC_CONTACT );
}
}

if ( ! $connected ) {
Expand Down
1 change: 1 addition & 0 deletions omnisend/includes/Internal/class-options.php
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,7 @@ public static function disconnect(): void {
delete_option( self::OPTION_API_KEY );
delete_option( self::OPTION_BRAND_ID );
delete_option( self::OPTION_STORE_CONNECTED );
delete_metadata( 'user', '0', UserMetaData::LAST_SYNC, '', true );
}

public static function delete_all(): void {
Expand Down
126 changes: 126 additions & 0 deletions omnisend/includes/Internal/class-sync.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,126 @@
<?php
/**
* Omnisend Contact Utils
*
* @package OmnisendClient
*/

namespace Omnisend\Internal;

use Omnisend\SDK\V1\Contact;
use Omnisend\SDK\V1\Omnisend;

! defined( 'ABSPATH' ) && die( 'no direct access' );

class Sync {

/**
* Listens for 'user_register' hook https://developer.wordpress.org/reference/hooks/user_register/
*
* @param $user_id
* @return void
*/
public static function hook_user_register( $user_id ): void {
if ( \Omnisend_Core_Bootstrap::is_omnisend_woocommerce_plugin_connected() ) {
return; // do not sync if omni woo plugin is active.
}

$user = get_userdata( $user_id );
if ( $user ) {
self::sync_contact( $user );
}
}

/**
* Listens for 'profile_update' hook https://developer.wordpress.org/reference/hooks/profile_update/
*
* @param $user_id
* @return void
*/
public static function hook_profile_update( $user_id ): void {
if ( \Omnisend_Core_Bootstrap::is_omnisend_woocommerce_plugin_connected() ) {
return; // do not sync if omni woo plugin is active.
}

$user = get_userdata( $user_id );
if ( $user ) {
self::sync_contact( $user );
}
}

/**
* @param int $limit number of users to sync
*/
public static function sync_contacts( int $limit = 100 ): void {
$wp_user_query = new \WP_User_Query(
array(
'number' => $limit,
'meta_query' => array( // phpcs:ignore WordPress.DB.SlowDBQuery.slow_db_query_meta_query
'relation' => 'OR',
array(
'key' => UserMetaData::LAST_SYNC,
'compare' => 'NOT EXISTS',
'value' => '',
),
),
)
);
$users = $wp_user_query->get_results();

if ( empty( $users ) ) {
wp_clear_scheduled_hook( OMNISEND_CORE_CRON_SYNC_CONTACT );
return;
}

foreach ( $users as $user ) {
self::sync_contact( $user );
}
}

/**
* @param \WP_User $user
* @return void
*/
private static function sync_contact( $user ): void {
$contact = new Contact();
$contact->add_tag( 'WordPress' );

if ( ! filter_var( $user->user_email, FILTER_VALIDATE_EMAIL ) ) {
UserMetaData::mark_sync_skipped( $user->ID );
return;
}

$contact->set_email( $user->user_email );

$first_name = get_user_meta( $user->ID, 'first_name', true );
if ( $first_name ) {
$contact->set_first_name( $first_name );
}

$last_name = get_user_meta( $user->ID, 'last_name', true );
if ( $last_name ) {
$contact->set_last_name( $last_name );
}

$roles = get_user_meta( $user->ID, 'wp_capabilities', true );
$parsed_roles = array();
if ( is_array( $roles ) ) {
foreach ( $roles as $role => $active ) {
if ( $active ) {
$parsed_roles[] = $role;
}
}

if ( ! empty( $parsed_roles ) ) {
$contact->add_custom_property( 'wordpress_roles', array_unique( $parsed_roles ) );
}
}

$response = Omnisend::get_client( OMNISEND_CORE_PLUGIN_NAME, OMNISEND_CORE_PLUGIN_VERSION )->create_contact( $contact );
if ( $response->get_contact_id() ) {
UserMetaData::mark_synced( $user->ID );
} else {
UserMetaData::mark_sync_error( $user->ID );
}
}
}
26 changes: 26 additions & 0 deletions omnisend/includes/Internal/class-usermetadata.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
<?php
/**
* Omnisend plugin
*
* @package OmnisendPlugin
*/

namespace Omnisend\Internal;

defined( 'ABSPATH' ) || die( 'no direct access' );

class UserMetaData {
public const LAST_SYNC = 'omni_send_core_last_sync';

public static function mark_synced( $user_id ) {
update_user_meta( $user_id, self::LAST_SYNC, gmdate( DATE_ATOM, time() ) );
}

public static function mark_sync_error( $user_id ) {
update_user_meta( $user_id, self::LAST_SYNC, 'ERROR' );
}

public static function mark_sync_skipped( $user_id ) {
update_user_meta( $user_id, self::LAST_SYNC, 'SKIPPED' );
}
}
8 changes: 6 additions & 2 deletions omnisend/readme.txt
Original file line number Diff line number Diff line change
Expand Up @@ -5,15 +5,15 @@ Tags: email marketing, marketing, newsletter, sms, form
Requires at least: 4.7.0
Tested up to: 6.4
Requires PHP: 7.1
Stable tag: 1.2.1
Stable tag: 1.3.0
License: GPLv3 or later
URI: http://www.gnu.org/licenses/gpl-3.0.html

Email Marketing, Newsletter, Email Automation, Forms, Pop Up, SMS by Omnisend

== DESCRIPTION ==

The Omnisend plugin connects to Omnisend email marketing tool, allows other plugins automatically sending form data and contact information to Omnisend. This makes it simple to segment your contacts and send them personalized emails.
The Omnisend plugin connects to Omnisend email marketing tool, automatically import all your WordPress users to Omnisend, allows other plugins automatically sending form data and contact information to Omnisend. This makes it simple to segment your contacts and send them personalized emails.

You are also able to:

Expand Down Expand Up @@ -54,6 +54,10 @@ Read Omnisend [Terms of Use](https://www.omnisend.com/terms)

== Changelog ==

= 1.3.0 =

* Sync WordPress users as contacts to Omnisend.

= 1.2.1 =

* Improve SDK client.
Expand Down
3 changes: 3 additions & 0 deletions omnisend/view/connection-form.html
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,9 @@ <h2 class="omnisend-h2">Connect Omnisend Plugin</h2>
</p>
<div class="omnisend-spacing-mt-4">
<ul class="omnisend-bullet-list">
<li>
<span> Automatically import all your WordPress users to Omnisend </span>
</li>
<li>
<span> Collect subscribers through Forms </span>
</li>
Expand Down

0 comments on commit c086fde

Please sign in to comment.