<?php
namespace Simply_Static;
class Admin_Settings {
/**
* Contains the number of failed tests.
*
* @var int
*/
public int $failed_tests = 0;
/**
* Contains instance or null
*
* @var object|null
*/
private static $instance = null;
/**
* Returns instance of SS_Admin_Settings.
*
* @return object
*/
public static function get_instance() {
if ( null === self::$instance ) {
self::$instance = new self();
}
return self::$instance;
}
/**
* Setting up admin fields
*
* @return void
*/
public function __construct() {
add_action( 'admin_menu', array( $this, 'add_menu' ) );
add_action( 'rest_api_init', array( $this, 'rest_api_init' ) );
$this->failed_tests = intval( get_transient( 'simply_static_failed_tests' ) );
Admin_Meta::get_instance();
}
/**
* Register submenu page.
*
* @return void
*/
public function add_menu() {
if ( apply_filters( 'ss_hide_admin_menu', false ) ) {
return;
}
// Generate settings page.
add_menu_page(
__( 'Simply Static', 'simply-static' ),
__( 'Simply Static', 'simply-static' ),
apply_filters( 'ss_user_capability', 'publish_pages', 'generate' ),
'simply-static-generate',
array( $this, 'render_settings' ),
SIMPLY_STATIC_URL . '/assets/simply-static-icon.svg',
apply_filters( 'ss_menu_position', 100 )
);
$generate_suffix = add_submenu_page(
'simply-static-generate',
__( 'Generate', 'simply-static' ),
__( 'Generate', 'simply-static' ),
apply_filters( 'ss_user_capability', 'publish_pages', 'generate' ),
'simply-static-generate',
array( $this, 'render_settings' )
);
add_action( "admin_print_scripts-{$generate_suffix}", array( $this, 'add_settings_scripts' ) );
if ( ! is_network_admin() ) {
// Add settings page.
$settings_suffix = add_submenu_page(
'simply-static-generate',
__( 'Settings', 'simply-static' ),
__( 'Settings', 'simply-static' ),
apply_filters( 'ss_user_capability', 'manage_options', 'settings' ),
'simply-static-settings',
array( $this, 'render_settings' )
);
add_action( "admin_print_scripts-{$settings_suffix}", array( $this, 'add_settings_scripts' ) );
$notifications = sprintf( '<span class="update-plugins diagnostics-error"><span class="plugin-count" aria-hidden="true">%s</span><span class="screen-reader-text">errors in diagnostics</span></span>', $this->failed_tests );
// Add diagnostics page.
$diagnostics_suffix = add_submenu_page(
'simply-static-generate',
__( 'Diagnostics', 'simply-static' ),
$this->failed_tests > 0 ? __( 'Diagnostics', 'simply-static' ) . ' ' . wp_kses_post( $notifications ) : __( 'Diagnostics', 'simply-static' ),
apply_filters( 'ss_user_capability', 'publish_pages', 'generate' ),
'simply-static-diagnostics',
array( $this, 'render_settings' )
);
add_action( "admin_print_scripts-{$diagnostics_suffix}", array( $this, 'add_settings_scripts' ) );
}
}
public function add_settings_scripts() {
$screen = get_current_screen();
$options = Options::reinstance();
wp_enqueue_script( 'simplystatic-settings', SIMPLY_STATIC_URL . '/src/admin/build/index.js', array(
'wp-api',
'wp-components',
'wp-element',
'wp-api-fetch',
'wp-data',
'wp-i18n',
'wp-block-editor'
), SIMPLY_STATIC_VERSION, true );
// Determine initial screen.
$initial = '/';
if ( 'simply-static_page_simply-static-settings' === $screen->base ) {
$initial = '/general';
}
// Maybe switch to Diagnostics.
if ( 'simply-static_page_simply-static-diagnostics' === $screen->base ) {
$initial = '/diagnostics';
}
// Check if directory exists, if not, create it.
$temp_dir = Util::get_temp_dir();
$args = apply_filters(
'ss_settings_args',
array(
'screen' => 'simplystatic-settings',
'version' => SIMPLY_STATIC_VERSION,
'logo' => SIMPLY_STATIC_URL . '/assets/simply-static-logo.svg',
'plan' => 'free',
'initial' => $initial,
'home' => home_url(),
'home_path' => get_home_path(),
'admin_email' => get_bloginfo( 'admin_email' ),
'temp_files_dir' => $temp_dir,
'blog_id' => get_current_blog_id(),
'need_upgrade' => 'no',
'builds' => array(),
'integrations' => array_map( function ( $item ) {
$object = new $item;
return $object->js_object();
}, Plugin::instance()->get_integrations() ),
)
);
if ( defined( 'SIMPLY_STATIC_PRO_VERSION' ) ) {
$args['version_pro'] = SIMPLY_STATIC_PRO_VERSION;
// Pass in additional data.
$data = get_option( 'fs_accounts' );
if ( ! empty( $data['plugin_data']['simply-static-pro'] ) ) {
if ( isset( $data['plugin_data']['simply-static-pro']['connectivity_test'] ) ) {
$args['connect'] = $data['plugin_data']['simply-static-pro']['connectivity_test'];
}
}
}
// Multisite?
if ( is_multisite() && function_exists( 'get_sites' ) ) {
$sites = [];
$selectable_sites = [];
$public_sites = get_sites( [ 'public' => true ] );
if ( $public_sites ) {
foreach ( $public_sites as $site ) {
$sites[] = [
'blog_id' => $site->blog_id,
'name' => $site->blogname,
'url' => $site->siteurl,
'settings_url' => esc_url( get_admin_url( $site->blog_id ) . 'admin.php?page=simply-static-settings' ),
'activity_log_url' => esc_url( get_admin_url( $site->blog_id ) . 'admin.php?page=simply-static-generate' )
];
if ( $site->blog_id != get_current_blog_id() ) {
$selectable_sites[] = [
'blog_id' => $site->blog_id,
'name' => $site->blogname,
];
}
}
}
$args['sites'] = $sites;
$args['selectable_sites'] = $selectable_sites;
$args['is_network'] = is_network_admin();
$args['is_multisite'] = is_multisite();
}
// Check if debug log exists.
$debug_file = Util::get_debug_log_filename();
if ( file_exists( $debug_file ) ) {
$uploads_dir = wp_upload_dir();
$simply_static_dir = $uploads_dir['baseurl'] . DIRECTORY_SEPARATOR . 'simply-static' . DIRECTORY_SEPARATOR;
$args['log_file'] = $simply_static_dir . $options->get( 'encryption_key' ) . '-debug.txt';
}
// Maybe show migration notice.
$version = $options->get( 'version' );
if ( floatval( $version ) < floatval( '3.0.4' ) ) {
$args['need_upgrade'] = 'yes';
}
// Forms enabled?
if ( ! empty( $options->get( 'use_forms' ) ) ) {
$args['form_connection_url'] = esc_url( get_admin_url() . 'post-new.php?post_type=ssp-form' );
}
wp_localize_script( 'simplystatic-settings', 'options', $args );
// Make the blocks translatable.
if ( function_exists( 'wp_set_script_translations' ) ) {
wp_set_script_translations( 'simplystatic-settings', 'simply-static', SIMPLY_STATIC_PATH . '/languages' );
}
wp_enqueue_style( 'simplystatic-settings-style', SIMPLY_STATIC_URL . '/src/admin/build/index.css', array( 'wp-components' ) );
}
public function render_settings() {
?>
<div id="simplystatic-settings"></div>
<?php
}
/**
* Setup Rest API endpoints.
*
* @return void
*/
public function rest_api_init() {
register_rest_route( 'simplystatic/v1', '/settings', array(
'methods' => 'GET',
'callback' => [ $this, 'get_settings' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'settings' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/settings', array(
'methods' => 'POST',
'callback' => [ $this, 'save_settings' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'settings' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/settings/reset', array(
'methods' => 'POST',
'callback' => [ $this, 'reset_settings' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'settings' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/settings/reset-database', array(
'methods' => 'POST',
'callback' => [ $this, 'reset_database' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'settings' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/update-from-network', array(
'methods' => 'POST',
'callback' => [ $this, 'update_from_network' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'settings' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/pages', array(
'methods' => 'GET',
'callback' => [ $this, 'get_pages' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'settings' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/pages-slugs', array(
'methods' => 'GET',
'callback' => [ $this, 'get_pages_slugs' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'settings' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/migrate', array(
'methods' => 'POST',
'callback' => [ $this, 'migrate_settings' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'settings' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/reset-diagnostics', array(
'methods' => 'POST',
'callback' => [ $this, 'reset_diagnostics' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'settings' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/system-status', array(
'methods' => 'GET',
'callback' => [ $this, 'get_system_status' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'diagnostics' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/system-status/passed', array(
'methods' => 'GET',
'callback' => [ $this, 'check_system_status_passed' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'diagnostics' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/delete-log', array(
'methods' => 'POST',
'callback' => [ $this, 'clear_log' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'activity-log' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/activity-log', array(
'methods' => 'GET',
'callback' => [ $this, 'get_activity_log' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'activity-log' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/export-log', array(
'methods' => 'GET',
'callback' => [ $this, 'get_export_log' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'manage_options', 'activity-log' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/start-export', array(
'methods' => 'POST',
'callback' => [ $this, 'start_export' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'publish_pages', 'generate' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/cancel-export', array(
'methods' => 'POST',
'callback' => [ $this, 'cancel_export' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'publish_pages', 'generate' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/pause-export', array(
'methods' => 'POST',
'callback' => [ $this, 'pause_export' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'publish_pages', 'generate' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/resume-export', array(
'methods' => 'POST',
'callback' => [ $this, 'resume_export' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'publish_pages', 'generate' ) );
},
) );
register_rest_route( 'simplystatic/v1', '/is-running', array(
'methods' => 'GET',
'callback' => [ $this, 'is_running' ],
'permission_callback' => function () {
return current_user_can( apply_filters( 'ss_user_capability', 'publish_pages', 'generate' ) );
},
) );
}
/**
* Get settings via Rest API.
*
* @return false|mixed|null
*/
public function get_settings() {
$settings = get_option( 'simply-static' );
if ( empty( $settings['integrations'] ) ) {
$integrations = Plugin::instance()->get_integrations();
$enabled_integrations = [];
foreach ( $integrations as $integration => $class ) {
$object = new $class;
if ( ! $object->is_enabled() ) {
continue;
}
$enabled_integrations[] = $integration;
}
$settings['integrations'] = $enabled_integrations;
}
return $settings;
}
/**
* Get System Status via Rest API.
*
* @return array[]
*/
public function get_system_status() {
$checks = get_transient( 'simply_static_checks' );
if ( ! $checks ) {
$diagnostics = new Diagnostic();
$checks = $diagnostics->get_checks();
}
return $checks;
}
/**
* Clear transient for diagnostics.
*
* @return string
*/
public function reset_diagnostics() {
delete_transient( 'simply_static_checks' );
delete_transient( 'simply_static_failed_tests' );
return json_encode( [ 'status' => 200 ] );
}
/**
* All diagnostics passed?
*
* @return false|string
*/
public function check_system_status_passed() {
$diagnostics = new Diagnostic();
$passed = 'yes';
$checks = $diagnostics->get_checks();
foreach ( $checks as $topics ) {
foreach ( $topics as $check ) {
if ( ! $check['test'] ) {
$passed = 'no';
break;
}
}
}
return json_encode( [ 'status' => 200, 'passed' => $passed ] );
}
/**
* Save settings via rest API.
*
* @param object $request given request.
*
* @return false|string
*/
public function save_settings( $request ) {
if ( $request->get_params() ) {
$options = sanitize_option( 'simply-static', $request->get_params() );
$multiline_fields = [
'additional_urls',
'additional_files',
'urls_to_exclude',
'search_excludable',
'iframe_urls',
'iframe_custom_css',
'whitelist_plugins'
];
$array_fields = [ 'integrations' ];
// Sanitize each key/value pair in options.
foreach ( $options as $key => $value ) {
if ( in_array( $key, $multiline_fields ) ) {
$options[ $key ] = sanitize_textarea_field( $value );
} elseif ( in_array( $key, $array_fields ) ) {
$options[ $key ] = array_map( 'sanitize_text_field', $value );
} else {
// Exclude Basic Auth fields from sanitize.
if ( $key === 'http_basic_auth_username' || $key === 'http_basic_auth_password' ) {
continue;
}
$options[ $key ] = sanitize_text_field( $value );
}
}
// Maybe update network settings.
if ( is_multisite() ) {
$blog_id = get_current_blog_id();
if ( $blog_id > 1 ) {
update_site_option( 'simply-static-' . $blog_id, $options );
}
}
// Update settings.
update_option( 'simply-static', $options );
return json_encode( [ 'status' => 200, 'message' => "Ok" ] );
}
return json_encode( [ 'status' => 400, 'message' => "No options updated." ] );
}
/**
* Save settings via rest API.
*
* @param object $request given request.
*
* @return false|string
*/
public function reset_settings( $request ) {
if ( $request->get_params() ) {
// Check table.
Page::create_or_update_table();
// Reset options.
$options = sanitize_option( 'simply-static', $request->get_params() );
// Update settings.
update_option( 'simply-static', $options );
return json_encode( [ 'status' => 200, 'message' => "Ok" ] );
}
return json_encode( [ 'status' => 400, 'message' => "No options updated." ] );
}
/**
* Reset database via rest API.
*
* @return false|string
*/
public function reset_database() {
// Drop Simply Static database table.
global $wpdb;
$table_name = $wpdb->prefix . 'simply_static_pages';
$wpdb->query( "DROP TABLE IF EXISTS $table_name" );
// Check table.
Page::create_or_update_table();
return json_encode( [ 'status' => 200, 'message' => "Ok" ] );
}
/**
* Save settings via rest API from another subsite in the network.
*
* @param object $request given request.
*
* @return false|string
*/
public function update_from_network( $request ) {
$params = $request->get_params();
if ( $request->get_params() ) {
$blog_id = intval( $params['blog_id'] );
// Get Settings from selected subsite.
$options = get_site_option( 'simply-static-' . $blog_id );
// Output notice if there are no network settings for the blog id.
if ( ! $options ) {
return json_encode(
[
'status' => 400,
'message' => "Please save the settings on the selected subsite before importing them into a new site."
]
);
}
// Update current site settings.
update_option( 'simply-static', $options );
return json_encode( [ 'status' => 200, 'message' => "Ok" ] );
}
return json_encode( [ 'status' => 400, 'message' => "No options updated." ] );
}
/**
* Get pages for settings.
* @return array
*/
public function get_pages() {
$args = array(
'post_type' => 'page',
'post_status' => 'publish',
'numberposts' => - 1,
);
$pages = get_posts( $args );
// Build selectable pages array.
$selectable_pages = array();
foreach ( $pages as $page ) {
$selectable_pages[] = array( 'label' => $page->post_title, 'value' => $page->ID );
}
return $selectable_pages;
}
/**
* Get pages slugs for settings.
* @return array
*/
public function get_pages_slugs() {
$args = array(
'post_type' => 'page',
'post_status' => 'publish',
'numberposts' => - 1,
);
$pages = get_posts( $args );
// Build selectable pages array.
$selectable_pages = array();
foreach ( $pages as $page ) {
$permalink = get_permalink( $page->ID );
$selectable_pages[] = array( 'label' => $page->post_title, 'value' => $permalink );
}
return $selectable_pages;
}
/**
* Migrate settings via rest API.
*
* @return false|string
*/
public function migrate_settings() {
Migrate_Settings::migrate();
return json_encode( [ 'status' => 200, 'message' => "Ok" ] );
}
/**
* Clear log file.
*
* @return false|string
*/
public function clear_log() {
Util::clear_debug_log();
return json_encode( [ 'status' => 200, 'message' => "Ok" ] );
}
/**
* Get Activity Log.
*
* @return false|string
*/
public function get_activity_log( $request ) {
$params = $request->get_params();
$activity_log = Plugin::instance()->get_activity_log( $params['blog_id'] );
return json_encode( [
'status' => 200,
'data' => $activity_log,
'running' => Plugin::instance()->get_archive_creation_job()->is_running(),
] );
}
/**
* Get Export Log
*
* @return false|string
*/
public function get_export_log( $request ) {
$params = $request->get_params();
$export_log = Plugin::instance()->get_export_log( $params['per_page'], $params['page'], $params['blog_id'] );
return json_encode( [
'status' => 200,
'data' => $export_log,
] );
}
/**
* Start Export
*
* @return false|string
*/
public function start_export( $request ) {
$params = $request->get_params();
$blog_id = ! empty( $params['blog_id'] ) ? $params['blog_id'] : 0;
$type = ! empty( $params['type'] ) ? $params['type'] : 'export';
do_action( 'ss_before_perform_archive_action', $blog_id, 'start', Plugin::instance()->get_archive_creation_job() );
$type = apply_filters( 'ss_export_type', $type );
Plugin::instance()->run_static_export( $blog_id, $type );
do_action( 'ss_after_perform_archive_action', $blog_id, 'start', Plugin::instance()->get_archive_creation_job() );
return json_encode( [
'status' => 200,
] );
}
/**
* Cancel Export
*
* @return false|string
*/
public function cancel_export() {
Util::debug_log( "Received request to cancel static archive generation" );
$blog_id = ! empty( $params['blog_id'] ) ? $params['blog_id'] : 0;
do_action( 'ss_before_perform_archive_action', $blog_id, 'cancel', Plugin::instance()->get_archive_creation_job() );
Plugin::instance()->cancel_static_export();
do_action( 'ss_after_perform_archive_action', $blog_id, 'cancel', Plugin::instance()->get_archive_creation_job() );
return json_encode( [ 'status' => 200 ] );
}
/**
* Is running
*
* @return false|string
*/
public function is_running( $request ) {
return json_encode( [
'status' => 200,
'running' => Plugin::instance()->get_archive_creation_job()->is_running(),
'paused' => Plugin::instance()->get_archive_creation_job()->is_paused(),
] );
}
/**
* Pause Export
*
* @return false|string
*/
public function pause_export() {
Util::debug_log( "Received request to pause static archive generation" );
$blog_id = ! empty( $params['blog_id'] ) ? $params['blog_id'] : 0;
do_action( 'ss_before_perform_archive_action', $blog_id, 'pause', Plugin::instance()->get_archive_creation_job() );
Plugin::instance()->pause_static_export();
do_action( 'ss_after_perform_archive_action', $blog_id, 'pause', Plugin::instance()->get_archive_creation_job() );
return json_encode( [ 'status' => 200 ] );
}
/**
* Resume Export
*
* @return false|string
*/
public function resume_export() {
Util::debug_log( "Received request to resume static archive generation" );
$blog_id = ! empty( $params['blog_id'] ) ? $params['blog_id'] : 0;
do_action( 'ss_before_perform_archive_action', $blog_id, 'resume', Plugin::instance()->get_archive_creation_job() );
Plugin::instance()->resume_static_export();
do_action( 'ss_after_perform_archive_action', $blog_id, 'resume', Plugin::instance()->get_archive_creation_job() );
return json_encode( [ 'status' => 200 ] );
}
}
|