sec(core): implementasi modul security headers, cloaking versi wp, sanitasi ketat settings api, dan direct access guard

This commit is contained in:
Mas Budi Kusuma
2026-09-16 00:37:59 +07:00
parent ada95fdea3
commit 0f4a8511ca
16 changed files with 163 additions and 34 deletions
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* Template untuk Halaman Tidak Ditemukan (Error 404) * Template untuk Halaman Tidak Ditemukan (Error 404)
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* Template Footer EduKarsa Modern 4-Kolom * Template Footer EduKarsa Modern 4-Kolom
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php get_header(); ?> <?php get_header(); ?>
<main id="primary" class="site-main edukarsa-home"> <main id="primary" class="site-main edukarsa-home">
+10 -5
View File
@@ -4,17 +4,22 @@
* Seluruh logika modular ditempatkan di folder inc/ * Seluruh logika modular ditempatkan di folder inc/
*/ */
// 1. Memuat Modul Kamus Dinamis Dashboard (i18n) defined( 'ABSPATH' ) || exit;
// 1. Memuat Modul Keamanan & Hardening Native
require_once get_template_directory() . '/inc/security.php';
// 2. Memuat Modul Kamus Dinamis Dashboard (i18n)
require_once get_template_directory() . '/inc/i18n.php'; require_once get_template_directory() . '/inc/i18n.php';
// 2. Memuat Pengaturan Dasar Tema & Aset // 3. Memuat Pengaturan Dasar Tema & Aset
require_once get_template_directory() . '/inc/setup.php'; require_once get_template_directory() . '/inc/setup.php';
// 3. Memuat Custom Post Type Native // 4. Memuat Custom Post Type Native
require_once get_template_directory() . '/inc/cpt-slider.php'; require_once get_template_directory() . '/inc/cpt-slider.php';
// 4. Memuat Panel Menu EduKarsa & Settings API // 5. Memuat Panel Menu EduKarsa & Settings API
require_once get_template_directory() . '/inc/admin-menu.php'; require_once get_template_directory() . '/inc/admin-menu.php';
// 5. Memuat Native SEO & Structured Data (JSON-LD) // 6. Memuat Native SEO & Structured Data (JSON-LD)
require_once get_template_directory() . '/inc/seo.php'; require_once get_template_directory() . '/inc/seo.php';
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<!DOCTYPE html> <!DOCTYPE html>
<html <?php language_attributes(); ?>> <html <?php language_attributes(); ?>>
<head> <head>
+67 -29
View File
@@ -3,6 +3,8 @@
* Modul Pengaturan Menu Admin, Toolbar, dan Settings API EduKarsa * Modul Pengaturan Menu Admin, Toolbar, dan Settings API EduKarsa
*/ */
defined( 'ABSPATH' ) || exit;
function edukarsa_admin_menu() { function edukarsa_admin_menu() {
add_menu_page( add_menu_page(
'EduKarsa', 'EduKarsa',
@@ -43,36 +45,77 @@ function edukarsa_admin_bar_shortcut( $wp_admin_bar ) {
} }
add_action( 'admin_bar_menu', 'edukarsa_admin_bar_shortcut', 80 ); add_action( 'admin_bar_menu', 'edukarsa_admin_bar_shortcut', 80 );
// SANITASI CHECKBOX (BOOLEAN ENFORCEMENT)
function edukarsa_sanitize_checkbox( $val ) {
return ( ! empty( $val ) && ( $val === 1 || $val === '1' || $val === true ) ) ? 1 : 0;
}
// REGISTRASI SELURUH PENGATURAN DENGAN SANITASI KETAT
function edukarsa_register_settings() { function edukarsa_register_settings() {
$options = array( // 1. Toggles & Checkboxes
'edukarsa_font_choice', 'edukarsa_primary_color', 'edukarsa_secondary_color', 'edukarsa_heading_color', $checkboxes = array(
'edukarsa_tampil_bilingual', 'edukarsa_lang_en', 'edukarsa_lang_ar', 'edukarsa_lang_zh', 'edukarsa_lang_ja', 'edukarsa_tampil_bilingual', 'edukarsa_lang_en', 'edukarsa_lang_ar', 'edukarsa_lang_zh', 'edukarsa_lang_ja',
'edukarsa_tampil_accessibility', 'edukarsa_tampil_accessibility', 'edukarsa_tampil_slider', 'edukarsa_tampil_stats', 'edukarsa_tampil_about',
'edukarsa_tampil_slider', 'edukarsa_tampil_stats', 'edukarsa_tampil_about', 'edukarsa_tampil_milestone', 'edukarsa_tampil_program', 'edukarsa_tampil_video', 'edukarsa_tampil_keunggulan', 'edukarsa_tampil_cta', 'edukarsa_tampil_faq', 'edukarsa_tampil_news', 'edukarsa_tampil_milestone', 'edukarsa_tampil_program', 'edukarsa_tampil_video', 'edukarsa_tampil_keunggulan',
'edukarsa_header_logo', 'edukarsa_tampil_cta', 'edukarsa_tampil_faq', 'edukarsa_tampil_news', 'edukarsa_sidebar_tampil_search',
'edukarsa_milestone_subtitle', 'edukarsa_milestone_title', 'edukarsa_sidebar_tampil_cta', 'edukarsa_sidebar_tampil_html', 'edukarsa_sidebar_tampil_recent',
'edukarsa_program_subtitle', 'edukarsa_program_title', 'edukarsa_sidebar_tampil_cats', 'edukarsa_tampil_fb', 'edukarsa_tampil_ig', 'edukarsa_tampil_yt',
'edukarsa_keunggulan_subtitle', 'edukarsa_keunggulan_title', 'edukarsa_tampil_tiktok', 'edukarsa_tampil_x'
'edukarsa_faq_subtitle', 'edukarsa_faq_title', );
'edukarsa_news_title', foreach ( $checkboxes as $cb ) {
register_setting( 'edukarsa_settings_group', $cb, array( 'sanitize_callback' => 'edukarsa_sanitize_checkbox' ) );
}
// 2. Colors
$colors = array( 'edukarsa_primary_color', 'edukarsa_secondary_color', 'edukarsa_heading_color', 'edukarsa_mid_bg_color' );
foreach ( $colors as $col ) {
register_setting( 'edukarsa_settings_group', $col, array( 'sanitize_callback' => 'sanitize_hex_color' ) );
}
// 3. URLs
$urls = array(
'edukarsa_header_logo', 'edukarsa_foto_kepsek', 'edukarsa_link_about', 'edukarsa_mid_bg_image',
'edukarsa_video1_thumb', 'edukarsa_video1_url', 'edukarsa_video2_thumb', 'edukarsa_video2_url',
'edukarsa_cta_bg', 'edukarsa_cta_btn_url', 'edukarsa_sidebar_cta_btn_url', 'edukarsa_sidebar_banner_img',
'edukarsa_sidebar_banner_url', 'edukarsa_footer_logo', 'edukarsa_footer_fb', 'edukarsa_footer_ig',
'edukarsa_footer_yt', 'edukarsa_footer_tiktok', 'edukarsa_footer_x'
);
foreach ( $urls as $url ) {
register_setting( 'edukarsa_settings_group', $url, array( 'sanitize_callback' => 'esc_url_raw' ) );
}
// 4. Numbers & Integers
register_setting( 'edukarsa_settings_group', 'edukarsa_sidebar_recent_count', array( 'sanitize_callback' => 'absint' ) );
// 5. Emails
register_setting( 'edukarsa_settings_group', 'edukarsa_footer_email', array( 'sanitize_callback' => 'sanitize_email' ) );
// 6. Safe HTML Textareas
$safe_html = array(
'edukarsa_teks_sambutan', 'edukarsa_sidebar_html_content', 'edukarsa_footer_alamat',
'edukarsa_footer_jam', 'edukarsa_footer_desc'
);
foreach ( $safe_html as $html ) {
register_setting( 'edukarsa_settings_group', $html, array( 'sanitize_callback' => 'wp_kses_post' ) );
}
// 7. General Text Inputs
$text_inputs = array(
'edukarsa_font_choice', 'edukarsa_milestone_subtitle', 'edukarsa_milestone_title',
'edukarsa_program_subtitle', 'edukarsa_program_title', 'edukarsa_keunggulan_subtitle',
'edukarsa_keunggulan_title', 'edukarsa_faq_subtitle', 'edukarsa_faq_title', 'edukarsa_news_title',
'edukarsa_stat1_angka', 'edukarsa_stat1_label', 'edukarsa_stat1_desc', 'edukarsa_stat1_icon', 'edukarsa_stat1_angka', 'edukarsa_stat1_label', 'edukarsa_stat1_desc', 'edukarsa_stat1_icon',
'edukarsa_stat2_angka', 'edukarsa_stat2_label', 'edukarsa_stat2_desc', 'edukarsa_stat2_icon', 'edukarsa_stat2_angka', 'edukarsa_stat2_label', 'edukarsa_stat2_desc', 'edukarsa_stat2_icon',
'edukarsa_stat3_angka', 'edukarsa_stat3_label', 'edukarsa_stat3_desc', 'edukarsa_stat3_icon', 'edukarsa_stat3_angka', 'edukarsa_stat3_label', 'edukarsa_stat3_desc', 'edukarsa_stat3_icon',
'edukarsa_foto_kepsek', 'edukarsa_nama_kepsek', 'edukarsa_subtitle_about', 'edukarsa_teks_sambutan', 'edukarsa_link_about', 'edukarsa_nama_kepsek', 'edukarsa_subtitle_about', 'edukarsa_cta_title', 'edukarsa_cta_btn_teks',
'edukarsa_video1_thumb', 'edukarsa_video1_url', 'edukarsa_video2_thumb', 'edukarsa_video2_url', 'edukarsa_sidebar_cta_badge', 'edukarsa_sidebar_cta_title', 'edukarsa_sidebar_cta_desc',
'edukarsa_mid_bg_image', 'edukarsa_mid_bg_color', 'edukarsa_sidebar_cta_btn_text', 'edukarsa_sidebar_html_title', 'edukarsa_sidebar_recent_title',
'edukarsa_cta_bg', 'edukarsa_cta_title', 'edukarsa_cta_btn_teks', 'edukarsa_cta_btn_url', 'edukarsa_sidebar_cats_title', 'edukarsa_footer_telp', 'edukarsa_wa_btn_text',
'edukarsa_sidebar_tampil_search', 'edukarsa_sidebar_tampil_cta', 'edukarsa_sidebar_cta_badge', 'edukarsa_sidebar_cta_title', 'edukarsa_sidebar_cta_desc', 'edukarsa_sidebar_cta_btn_text', 'edukarsa_sidebar_cta_btn_url', 'edukarsa_wa_default_msg', 'edukarsa_footer_copyright'
'edukarsa_sidebar_tampil_html', 'edukarsa_sidebar_html_title', 'edukarsa_sidebar_html_content',
'edukarsa_sidebar_tampil_recent', 'edukarsa_sidebar_recent_title', 'edukarsa_sidebar_recent_count',
'edukarsa_sidebar_tampil_cats', 'edukarsa_sidebar_cats_title',
'edukarsa_sidebar_banner_img', 'edukarsa_sidebar_banner_url',
'edukarsa_footer_logo', 'edukarsa_footer_desc', 'edukarsa_footer_alamat', 'edukarsa_footer_telp', 'edukarsa_footer_email', 'edukarsa_footer_jam',
'edukarsa_wa_btn_text', 'edukarsa_wa_default_msg',
'edukarsa_tampil_fb', 'edukarsa_footer_fb', 'edukarsa_tampil_ig', 'edukarsa_footer_ig', 'edukarsa_tampil_yt', 'edukarsa_footer_yt', 'edukarsa_tampil_tiktok', 'edukarsa_footer_tiktok', 'edukarsa_tampil_x', 'edukarsa_footer_x',
'edukarsa_footer_copyright', 'edukarsa_custom_css'
); );
foreach ( $options as $opt ) { register_setting( 'edukarsa_settings_group', $opt ); } foreach ( $text_inputs as $txt ) {
register_setting( 'edukarsa_settings_group', $txt, array( 'sanitize_callback' => 'sanitize_text_field' ) );
}
} }
add_action( 'admin_init', 'edukarsa_register_settings' ); add_action( 'admin_init', 'edukarsa_register_settings' );
@@ -169,8 +212,6 @@ function edukarsa_settings_page_html() {
</style> </style>
<div class="wrap edukarsa-admin-wrap"> <div class="wrap edukarsa-admin-wrap">
<!-- HEADER TOPBAR: JUDUL + INSTANT DASHBOARD LANGUAGE SWITCHER -->
<div class="edukarsa-top-toolbar"> <div class="edukarsa-top-toolbar">
<h1 style="font-weight: 800; font-size: 24px; margin: 0;"> <h1 style="font-weight: 800; font-size: 24px; margin: 0;">
<?php echo esc_html( edukarsa_t( 'Pengaturan Tema EduKarsa', 'EduKarsa Theme Settings' ) ); ?> <?php echo esc_html( edukarsa_t( 'Pengaturan Tema EduKarsa', 'EduKarsa Theme Settings' ) ); ?>
@@ -190,7 +231,6 @@ function edukarsa_settings_page_html() {
<?php settings_fields( 'edukarsa_settings_group' ); ?> <?php settings_fields( 'edukarsa_settings_group' ); ?>
<div class="edukarsa-admin-layout"> <div class="edukarsa-admin-layout">
<div class="edukarsa-admin-main"> <div class="edukarsa-admin-main">
<div class="edukarsa-top-toolbar" style="justify-content: flex-end; margin-bottom: 12px;"> <div class="edukarsa-top-toolbar" style="justify-content: flex-end; margin-bottom: 12px;">
<div class="edukarsa-accordion-actions"> <div class="edukarsa-accordion-actions">
@@ -771,7 +811,6 @@ function edukarsa_about_page_html() {
if ( ! current_user_can( 'manage_options' ) ) return; if ( ! current_user_can( 'manage_options' ) ) return;
?> ?>
<div class="wrap edukarsa-admin-wrap" style="max-width: 1000px; margin-top: 20px;"> <div class="wrap edukarsa-admin-wrap" style="max-width: 1000px; margin-top: 20px;">
<div style="background: linear-gradient(135deg, #0f2b5c 0%, #1a73e8 100%); color: #ffffff; padding: 45px 40px; border-radius: 16px; box-shadow: 0 15px 35px rgba(15,43,92,0.18); margin-bottom: 30px; position: relative; overflow: hidden;"> <div style="background: linear-gradient(135deg, #0f2b5c 0%, #1a73e8 100%); color: #ffffff; padding: 45px 40px; border-radius: 16px; box-shadow: 0 15px 35px rgba(15,43,92,0.18); margin-bottom: 30px; position: relative; overflow: hidden;">
<div style="position: absolute; top: -20px; right: -20px; font-size: 140px; opacity: 0.08; font-weight: 900; user-select: none;">🎓</div> <div style="position: absolute; top: -20px; right: -20px; font-size: 140px; opacity: 0.08; font-weight: 900; user-select: none;">🎓</div>
<span style="display: inline-block; background: rgba(255,255,255,0.2); padding: 4px 14px; border-radius: 20px; font-size: 11px; font-weight: 800; letter-spacing: 1px; text-transform: uppercase; margin-bottom: 15px;"><?php echo esc_html( edukarsa_t( 'WordPress Theme Khusus Sekolah & Kampus', 'Dedicated WordPress Theme for Schools & Universities' ) ); ?></span> <span style="display: inline-block; background: rgba(255,255,255,0.2); padding: 4px 14px; border-radius: 20px; font-size: 11px; font-weight: 800; letter-spacing: 1px; text-transform: uppercase; margin-bottom: 15px;"><?php echo esc_html( edukarsa_t( 'WordPress Theme Khusus Sekolah & Kampus', 'Dedicated WordPress Theme for Schools & Universities' ) ); ?></span>
@@ -862,7 +901,6 @@ function edukarsa_about_page_html() {
</div> </div>
</div> </div>
</div> </div>
</div> </div>
<?php <?php
} }
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* Registrasi Seluruh Custom Post Type (CPT) Native EduKarsa * Registrasi Seluruh Custom Post Type (CPT) Native EduKarsa
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* Modul Native Internationalization (i18n) Dashboard EduKarsa * Modul Native Internationalization (i18n) Dashboard EduKarsa
+73
View File
@@ -0,0 +1,73 @@
<?php
/**
* Modul Pengamanan Native Tema EduKarsa
* Mencegah XSS, SQLi, Clickjacking, User Harvesting, dan Information Leakage
*/
defined( 'ABSPATH' ) || exit;
// 1. INJEKSI NATIVE HTTP SECURITY HEADERS
function edukarsa_security_headers() {
if ( ! is_admin() ) {
header( 'X-Content-Type-Options: nosniff' );
header( 'X-Frame-Options: SAMEORIGIN' );
header( 'X-XSS-Protection: 1; mode=block' );
header( 'Referrer-Policy: strict-origin-when-cross-origin' );
}
}
add_action( 'send_headers', 'edukarsa_security_headers' );
// 2. INFORMATION DISCLOSURE CLOAKING (SEMBUNYIKAN GENERATOR VERSI CMS)
function edukarsa_clean_header_fingerprints() {
remove_action( 'wp_head', 'wp_generator' );
remove_action( 'wp_head', 'wlwmanifest_link' );
remove_action( 'wp_head', 'rsd_link' );
remove_action( 'wp_head', 'wp_shortlink_wp_head' );
remove_action( 'wp_head', 'adjacent_posts_rel_link_wp_head', 10 );
}
add_action( 'init', 'edukarsa_clean_header_fingerprints' );
// Hapus query string versi WordPress dari aset agar tidak terbaca bot scanner
function edukarsa_hide_wp_version_from_assets( $src ) {
global $wp_version;
parse_str( (string) wp_parse_url( $src, PHP_URL_QUERY ), $query );
if ( ! empty( $query['ver'] ) && $query['ver'] === $wp_version ) {
$src = remove_query_arg( 'ver', $src );
}
return $src;
}
add_filter( 'style_loader_src', 'edukarsa_hide_wp_version_from_assets', 9999 );
add_filter( 'script_loader_src', 'edukarsa_hide_wp_version_from_assets', 9999 );
// 3. BLOKIR PROBING USERNAME / ENUMERASI AUTHOR (?author=N)
function edukarsa_block_author_enumeration() {
if ( ! is_admin() && isset( $_REQUEST['author'] ) ) {
wp_safe_redirect( home_url( '/' ), 301 );
exit;
}
}
add_action( 'template_redirect', 'edukarsa_block_author_enumeration' );
// 4. BATASI ENDPOINT REST API USERS BAGI PENGUNJUNG TANPA OTENTIKASI
function edukarsa_restrict_rest_users_endpoint( $endpoints ) {
if ( ! is_user_logged_in() ) {
if ( isset( $endpoints['/wp/v2/users'] ) ) {
unset( $endpoints['/wp/v2/users'] );
}
if ( isset( $endpoints['/wp/v2/users/(?P<id>[\d]+)'] ) ) {
unset( $endpoints['/wp/v2/users/(?P<id>[\d]+)'] );
}
}
return $endpoints;
}
add_filter( 'rest_endpoints', 'edukarsa_restrict_rest_users_endpoint' );
// 5. SANITASI INPUT PENCARIAN (ANTI-REFLECTED XSS)
function edukarsa_sanitize_search_query( $query ) {
if ( ! is_admin() && $query->is_main_query() && $query->is_search() ) {
$s = $query->get( 's' );
$query->set( 's', sanitize_text_field( $s ) );
}
return $query;
}
add_action( 'pre_get_posts', 'edukarsa_sanitize_search_query' );
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* Modul Native SEO & Structured Data Schema EduKarsa * Modul Native SEO & Structured Data Schema EduKarsa
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* File ini menangani dukungan tema (Theme Support) dan antrean aset (CSS/JS). * File ini menangani dukungan tema (Theme Support) dan antrean aset (CSS/JS).
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* File template fallback dan daftar arsip berita/artikel. * File template fallback dan daftar arsip berita/artikel.
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* Template Halaman Statis (Page) EduKarsa * Template Halaman Statis (Page) EduKarsa
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* Template Sidebar Native EduKarsa * Template Sidebar Native EduKarsa
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* Template untuk Detail Program Akademik / Unggulan * Template untuk Detail Program Akademik / Unggulan
+1
View File
@@ -1,3 +1,4 @@
<?php defined( 'ABSPATH' ) || exit; ?>
<?php <?php
/** /**
* Template Baca Artikel Penuh (Single Post) EduKarsa * Template Baca Artikel Penuh (Single Post) EduKarsa