Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
31 commits
Select commit Hold shift + click to select a range
a5a3754
Track flows data
truongwp Sep 27, 2024
a0fcbad
Add flows and payments data to usage snapshot
truongwp Oct 3, 2024
b76fdee
Track style name
truongwp Oct 3, 2024
ec8e5d9
Change to test endpoint
truongwp Oct 8, 2024
c507b5e
Track subscriptions
truongwp Oct 11, 2024
f3edd81
Fix subscriptions tracking
truongwp Oct 12, 2024
0ab3962
Add usage tracking request timeout
truongwp Oct 12, 2024
e4b40b4
Update usage test URL
truongwp Oct 14, 2024
c303edd
Fix PHPStan
truongwp Oct 14, 2024
a964813
Temporary update version
truongwp Oct 14, 2024
5a72df4
Merge branch 'master' into usage-tracking-v2
truongwp Oct 14, 2024
a68e5a3
Log usage tracking error
truongwp Oct 15, 2024
f400c8b
Update the usage snapshot URL
truongwp Oct 16, 2024
8df9c02
Fix hello-world style in usage data
truongwp Oct 16, 2024
a26bf3d
Add payment time to usage data
truongwp Oct 16, 2024
114fd2f
Add missing page check and doc comments
truongwp Oct 23, 2024
c84e329
Skip some onboarding wizard usage data
truongwp Oct 29, 2024
2862d78
Coderabbit suggestion
truongwp Oct 29, 2024
2d6fadf
Add permission check and support AI addon code
truongwp Nov 2, 2024
55039da
Move add_action call
truongwp Nov 2, 2024
0ad800f
Remove time limit when sending usage data
truongwp Nov 2, 2024
3530ac0
Improve JS code
truongwp Nov 3, 2024
2061e6c
Reduce add_action call
truongwp Nov 5, 2024
e3e66e8
Track disabled style
truongwp Nov 6, 2024
5c67a7b
Merge branch 'master' into usage-tracking-v2
Crabcyborg Nov 7, 2024
c411f6e
Fix phpcs
truongwp Nov 9, 2024
91a3ea8
Merge branch 'usage-tracking-v2' of github.com:Strategy11/formidable-…
truongwp Nov 9, 2024
635477a
Merge branch 'master' into usage-tracking-v2
truongwp Nov 9, 2024
ea91f45
Fix wpdb prepare
truongwp Nov 12, 2024
0b84172
Fix phpcs
truongwp Nov 12, 2024
d0dfd16
Do not log failed usage tracking requests
truongwp Nov 12, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions classes/controllers/FrmAppController.php
Original file line number Diff line number Diff line change
Expand Up @@ -888,6 +888,7 @@ private static function should_show_floating_links() {
public static function admin_enqueue_scripts() {
self::load_wp_admin_style();
self::maybe_force_formidable_block_on_gutenberg_page();
FrmUsageController::load_scripts();
}

/**
Expand Down
3 changes: 3 additions & 0 deletions classes/controllers/FrmHooksController.php
Original file line number Diff line number Diff line change
Expand Up @@ -290,6 +290,9 @@ public static function load_ajax_hooks() {
// Trigger before process_entry.
add_action( 'wp_loaded', 'FrmEntriesAJAXSubmitController::ajax_create', 5 );

// Track the flows usage data.
add_action( 'wp_ajax_frm_track_flows', 'FrmUsageController::ajax_track_flows' );

// Applications.
add_action( 'wp_ajax_frm_get_applications_data', 'FrmApplicationsController::get_applications_data' );

Expand Down
99 changes: 99 additions & 0 deletions classes/controllers/FrmUsageController.php
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,15 @@
*/
class FrmUsageController {

/**
* Option name of flows data.
*
* @since x.x
*
* @var string
*/
const FLOWS_ACTION_NAME = 'frm_usage_tracking_flows';
Comment thread
Crabcyborg marked this conversation as resolved.

/**
* Randomize the first send to prevent our servers from crashing.
*
Expand Down Expand Up @@ -56,4 +65,94 @@ public static function send_snapshot() {
$usage = new FrmUsage();
$usage->send_snapshot();
}

/**
* Loads scripts.
*
* @since x.x
*/
public static function load_scripts() {
if ( self::is_forms_list_page() || FrmAppHelper::is_admin_page( 'formidable-form-templates' ) ) {
wp_enqueue_script( 'frm-usage-tracking', FrmAppHelper::plugin_url() . '/js/admin/usage-tracking.js', array( 'formidable_dom' ), FrmAppHelper::$plug_version, true );
}
}

/**
* Checks if is forms list page.
*
* @since x.x
*
* @return bool
*/
private static function is_forms_list_page() {
if ( ! FrmAppHelper::is_admin_page() ) {
return false;
}

// Check Trash page.
$form_type = FrmAppHelper::simple_get( 'form_type' );
if ( $form_type && 'published' !== $form_type ) {
return false;
}

// Check edit or settings page.
return ! FrmAppHelper::simple_get( 'frm_action' );
}

/**
* AJAX handler to track flows.
*
* @since x.x
*/
public static function ajax_track_flows() {
FrmAppHelper::permission_check( 'frm_view_forms' );
check_ajax_referer( 'frm_ajax', 'nonce' );

Comment thread
truongwp marked this conversation as resolved.
$key = FrmAppHelper::get_post_param( 'key', '', 'sanitize_text_field' );
$value = FrmAppHelper::get_post_param( 'value', '', 'sanitize_text_field' );

self::update_flows_data( $key, $value );

wp_send_json_success();
}

/**
* Updates flows data.
*
* @since x.x
*
* @param string $key Flow key.
* @param string $value Flow value.
*
* @return void
*/
public static function update_flows_data( $key, $value ) {
$flows_data = self::get_flows_data();

if ( '' === $key || '' === $value ) {
return;
}

if ( ! isset( $flows_data[ $key ] ) ) {
$flows_data[ $key ] = array();
}

if ( ! isset( $flows_data[ $key ][ $value ] ) ) {
$flows_data[ $key ][ $value ] = 0;
}

$flows_data[ $key ][ $value ]++;
update_option( self::FLOWS_ACTION_NAME, $flows_data );
}

/**
* Get flows data.
*
* @since x.x
*
* @return array
*/
public static function get_flows_data() {
return get_option( self::FLOWS_ACTION_NAME, array() );
}
}
93 changes: 89 additions & 4 deletions classes/models/FrmUsage.php
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ public function send_snapshot() {
return;
}

$ep = 'aHR0cHM6Ly91c2FnZS5mb3JtaWRhYmxlZm9ybXMuY29tL2FwcC9zbmFwc2hvdAo=';
$ep = 'aHR0cHM6Ly91c2FnZTIuZm9ybWlkYWJsZWZvcm1zLmNvbS9zbmFwc2hvdA==';
// $ep = base64_encode( 'http://localhost:4567/snapshot' ); // Uncomment for testing
$body = json_encode( $this->snapshot() );

Expand All @@ -31,8 +31,15 @@ public function send_snapshot() {
'Content-Length' => strlen( $body ),
),
'body' => $body,
// Without this, Debug Log catches the `http_request_failed` error.
'timeout' => 45,
);

// Remove time limit to execute this function.
if ( function_exists( 'set_time_limit' ) ) {
set_time_limit( 0 );
}

wp_remote_request( base64_decode( $ep ), $post );
}

Expand Down Expand Up @@ -88,12 +95,74 @@ public function snapshot() {
'fields' => $this->fields(),
'actions' => $this->actions(),

'onboarding-wizard' => FrmOnboardingWizardController::get_usage_data(),
'onboarding-wizard' => $this->onboarding_wizard(),
'flows' => FrmUsageController::get_flows_data(),
'payments' => $this->payments(),
'subscriptions' => $this->payments( 'frm_subscriptions' ),
);

return apply_filters( 'frm_usage_snapshot', $snap );
}

/**
* Gets onboarding wizard data.
*
* @since x.x
*
* @return array
*/
private function onboarding_wizard() {
$data = FrmOnboardingWizardController::get_usage_data();
$skipped_keys = array(
'default_email',
'is_subscribed',
'allows_tracking',
'summary_emails',
'installed_addons',
);

foreach ( $skipped_keys as $skipped_key ) {
unset( $data[ $skipped_key ] );
}
Comment thread
Crabcyborg marked this conversation as resolved.

return $data;
}

/**
* Gets payments data.
*
* @since x.x
*
* @param string $table Database table name.
* @return array
*/
private function payments( $table = 'frm_payments' ) {
$allowed_tables = array( 'frm_payments', 'frm_subscriptions' );
if ( ! in_array( $table, $allowed_tables, true ) ) {
return array();
}

global $wpdb;
$rows = $wpdb->get_results(
$wpdb->prepare(
'SELECT amount, status, paysys, created_at FROM %1$s',
$wpdb->prefix . $table
)
);

$payments = array();
foreach ( $rows as $row ) {
$payments[] = array(
'amount' => (float) $row->amount,
'status' => $row->status,
'gateway' => $row->paysys,
'created_at' => $row->created_at,
);
}

return $payments;
}

/**
* @since 3.06.04
* @return array
Expand Down Expand Up @@ -255,6 +324,7 @@ private function forms() {
'submit_conditions',
);

$style = new FrmStyle();
foreach ( $saved_forms as $form ) {
$new_form = array(
'form_id' => $form->id,
Expand All @@ -269,12 +339,27 @@ private function forms() {

foreach ( $settings as $setting ) {
if ( isset( $form->options[ $setting ] ) ) {
$new_form[ $setting ] = $this->maybe_json( $form->options[ $setting ] );
if ( 'custom_style' === $setting ) {
$style->id = $form->options[ $setting ];

if ( ! $style->id ) {
$style_name = 0;
} elseif ( 1 === intval( $style->id ) ) {
$style_name = 'formidable-style';
} else {
$style_post = $style->get_one();
$style_name = $style_post ? $style_post->post_name : 'formidable-style';
Comment thread
Crabcyborg marked this conversation as resolved.
}

$new_form[ $setting ] = $style_name;
} else {
$new_form[ $setting ] = $this->maybe_json( $form->options[ $setting ] );
}
}
}

$forms[] = apply_filters( 'frm_usage_form', $new_form, compact( 'form' ) );
}
}//end foreach

// If the array uses numeric keys, reset them.
return $forms;
Expand Down
20 changes: 20 additions & 0 deletions js/admin/usage-tracking.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
( function() {
'use strict';

// Track edit form clicked link.
frmDom.util.documentOn( 'click', '.toplevel_page_formidable #the-list .column-primary .row-actions a', function( event ) {
sendData( 'edit_form_clicked_link', event.target.parentNode.className );
});

// Track form templates.
frmDom.util.documentOn( 'click', '.frm-form-templates-use-template-button', function( event ) {
sendData( 'form_templates', event.target.closest( 'li' ).dataset.slug );
});

const sendData = ( key, value ) => {
const formData = new FormData();
formData.append( 'key', key );
formData.append( 'value', value );
frmDom.ajax.doJsonPost( 'track_flows', formData );
};
}() );
9 changes: 9 additions & 0 deletions stubs.php
Original file line number Diff line number Diff line change
Expand Up @@ -379,6 +379,15 @@ class WPO_Page_Cache {
public function purge() {
}
}
class FrmLog {
/**
* @param array<string> $values values.
*
* @return void
*/
public function add( $values ) {
}
}
/**
* @return WP_Optimize
*/
Expand Down