Diff: STRATO-apps/wordpress_03/app/wp-content/plugins/blocksy-companion-pro/freemius/README.md

Keine Baseline-Datei – Diff nur gegen leer.
Zur Liste
1 -
1 + # Freemius SDK - Premium License Bypass
2 +
3 + **Modified by GPL Times - https://www.gpltimes.com**
4 +
5 + This is a modified version of the Freemius WordPress SDK that bypasses all licensing requirements and enables all premium features automatically. All API calls are intercepted and prevented, while mock objects simulate a premium license environment.
6 +
7 + ## ⚠️ Important Notice
8 +
9 + This modified SDK is intended for **development and testing purposes only**. Please respect the original developers' work and consider purchasing legitimate licenses for production use.
10 +
11 + ## 🚀 Features
12 +
13 + - ✅ **Complete License Bypass** - All premium features enabled automatically
14 + - ✅ **API Call Prevention** - No external API requests made to Freemius servers
15 + - ✅ **Mock Objects** - Realistic user, site, license, and plan objects created automatically
16 + - ✅ **Green Debug Status** - Shows "Connected" status in Freemius debug page
17 + - ✅ **Error Prevention** - Eliminates common PHP errors and sync issues
18 + - ✅ **Priority Loading** - Ensures this SDK loads first when multiple Freemius plugins are active
19 + - ✅ **Account Page Support** - Prevents account page errors with mock data
20 + - ✅ **Realistic Validation** - License changes show as successful validations, not "bypassed"
21 +
22 + ## 📋 Modifications Summary
23 +
24 + ### 1. SDK Version Override (`start.php`)
25 + ```php
26 + // Changed from '2.12.1' to '999.99.99'
27 + $this_sdk_version = '999.99.99';
28 + ```
29 + **Purpose**: Ensures this modified SDK is always loaded first when multiple plugins with Freemius are active.
30 +
31 + ### 2. Configuration Constants (`config.php`)
32 + ```php
33 + // Mock plan configuration constants
34 + define( 'WP_FS__MOCK_PLAN_NAME', 'professional' );
35 + define( 'WP_FS__MOCK_PLAN_TITLE', 'Professional Plan' );
36 + ```
37 + **Purpose**: Allows easy customization of the displayed plan name and title.
38 +
39 + ### 3. Core License Bypass Methods (`includes/class-freemius.php`)
40 +
41 + #### License Status Methods
42 + ```php
43 + function is_paying() { return true; }
44 + function is_free_plan() { return false; }
45 + function has_features_enabled_license() { return true; }
46 + function can_use_premium_code() { return true; }
47 + function is_trial() { return false; }
48 + function is_trial_utilized() { return false; }
49 + function is_registered() { return true; }
50 + function has_active_valid_license() { return true; }
51 + function is_active_valid_license() { return true; }
52 + ```
53 +
54 + #### Mock Object Creation
55 + ```php
56 + private function _ensure_mock_objects() {
57 + // Creates realistic mock user, site, license, and plan objects
58 + // Prevents account page errors and undefined property issues
59 +
60 + // Mock User Object
61 + if ( ! is_object( $this->_user ) ) {
62 + $this->_user = new FS_User();
63 + $this->_user->id = 1;
64 + $this->_user->email = 'noreply@gmail.com';
65 + $this->_user->first = 'Premium';
66 + $this->_user->last = 'User';
67 + $this->_user->is_verified = true;
68 + $this->_user->created = date('Y-m-d H:i:s');
69 + $this->_user->public_key = 'pk_4a7c9e2f8b3d1a6e5c8f2b9d4a7c0e3f';
70 + $this->_user->secret_key = 'sk_8f3d1a6e5c2b9d4a7c0e3f6b8a1d4e7c';
71 + }
72 +
73 + // Mock Site Object (Comprehensive)
74 + if ( ! is_object( $this->_site ) ) {
75 + $this->_site = new FS_Site();
76 + $this->_site->id = 1;
77 + $this->_site->site_id = 1;
78 + $this->_site->blog_id = get_current_blog_id();
79 + $this->_site->plugin_id = $this->_plugin->id;
80 + $this->_site->license_id = 1;
81 + $this->_site->plan_id = 1;
82 + $this->_site->user_id = 1;
83 + $this->_site->title = get_bloginfo('name');
84 + $this->_site->url = home_url();
85 + $this->_site->version = $this->_plugin->version;
86 + $this->_site->language = get_locale();
87 + $this->_site->platform_version = get_bloginfo('version');
88 + $this->_site->sdk_version = $this->version;
89 + $this->_site->programming_language_version = phpversion();
90 + $this->_site->is_premium = true;
91 + $this->_site->is_active = true;
92 + $this->_site->is_uninstalled = false;
93 + $this->_site->public_key = 'pk_f3b8c2a7e9d1f4a6c3e8b2d5a9f1c4e7';
94 + $this->_site->secret_key = 'sk_2d5a9f1c4e7b3a6c8f2e1d4a7c0e3f6b';
95 + $this->_site->created = date('Y-m-d H:i:s');
96 + }
97 +
98 + // Mock License Object
99 + if ( ! is_object( $this->_license ) ) {
100 + $this->_license = new FS_Plugin_License();
101 + $this->_license->id = 1;
102 + $this->_license->plan_id = 1;
103 + $this->_license->user_id = 1;
104 + $this->_license->secret_key = 'sk_b5e0b5f8dd8689e6aca49dd6e6e1a930';
105 + $this->_license->quota = null; // Unlimited
106 + $this->_license->expiration = null; // Lifetime
107 + $this->_license->created = date('Y-m-d H:i:s');
108 + }
109 +
110 + // Mock Plan Object
111 + if ( ! is_array( $this->_plans ) || empty( $this->_plans ) ) {
112 + $this->_plans = array();
113 + $mock_plan = new FS_Plugin_Plan();
114 + $mock_plan->id = 1;
115 + $mock_plan->name = WP_FS__MOCK_PLAN_NAME;
116 + $mock_plan->title = WP_FS__MOCK_PLAN_TITLE;
117 + $mock_plan->pricing_id = 1;
118 + $mock_plan->is_block_features = false;
119 + $mock_plan->license_type = 'paid';
120 + $mock_plan->created = date('Y-m-d H:i:s');
121 + $this->_plans[] = $mock_plan;
122 + }
123 + }
124 + ```
125 +
126 + #### API Bypass Methods
127 + ```php
128 + function has_api_connectivity() { return true; }
129 + function _sync_license() { return; } // Bypassed completely
130 + function _sync_plugin_license() { return; } // Bypassed completely
131 + function _fetch_payments() { return array(); }
132 + function _fetch_billing() { return null; }
133 + ```
134 +
135 + ### 4. License Entity Modifications (`includes/entities/class-fs-plugin-license.php`)
136 + ```php
137 + function is_features_enabled() { return true; }
138 + function is_active() { return true; }
139 + function is_expired() { return false; }
140 + ```
141 +
142 + ### 5. WordPress API Bypass (`includes/sdk/FreemiusWordPress.php`)
143 + ```php
144 + public function MakeRequest() {
145 + return (object) array(
146 + 'success' => true,
147 + 'api' => 'success'
148 + );
149 + }
150 +
151 + public static function Ping() {
152 + return (object) array(
153 + 'api' => 'pong',
154 + 'timestamp' => gmdate('Y-m-d H:i:s'),
155 + 'is_active' => true
156 + );
157 + }
158 + ```
159 +
160 + ### 6. API Manager Bypass (`includes/class-fs-api.php`)
161 + ```php
162 + private function _call( $path, $method = 'GET', $params = array(), $in_retry = false ) {
163 + // Returns realistic mock responses based on endpoint type
164 + // - Site endpoints: Return complete FS_Site object
165 + // - License endpoints: Return complete FS_Plugin_License object
166 + // - User endpoints: Return complete FS_User object
167 + // This simulates successful license validation instead of showing 'bypassed'
168 + }
169 + ```
170 +
171 + ## 🔧 Mock Data Configuration
172 +
173 + ### Default Mock Data
174 +
175 + #### User Object
176 + - **User ID**: 1
177 + - **Email**: `noreply@gmail.com`
178 + - **Name**: Premium User
179 + - **Status**: Verified
180 + - **Public Key**: `pk_4a7c9e2f8b3d1a6e5c8f2b9d4a7c0e3f`
181 + - **Secret Key**: `sk_8f3d1a6e5c2b9d4a7c0e3f6b8a1d4e7c`
182 +
183 + #### Site Object (Comprehensive)
184 + - **Site ID**: 1
185 + - **Site ID (Alternative)**: 1
186 + - **Blog ID**: Current WordPress blog ID
187 + - **Plugin ID**: Actual plugin ID from context
188 + - **Title**: WordPress site title
189 + - **URL**: WordPress home URL
190 + - **Version**: Plugin version
191 + - **Language**: WordPress locale
192 + - **Platform Version**: WordPress version
193 + - **SDK Version**: Freemius SDK version
194 + - **PHP Version**: Server PHP version
195 + - **Premium Status**: true
196 + - **Active Status**: true
197 + - **Uninstalled Status**: false
198 + - **Public Key**: `pk_f3b8c2a7e9d1f4a6c3e8b2d5a9f1c4e7`
199 + - **Secret Key**: `sk_2d5a9f1c4e7b3a6c8f2e1d4a7c0e3f6b`
200 +
201 + #### License Object
202 + - **License ID**: 1
203 + - **License Key**: `sk_b5e0b5f8dd8689e6aca49dd6e6e1a930`
204 + - **Quota**: Unlimited (null)
205 + - **Expiration**: Lifetime (null)
206 + - **Status**: Active, non-expired, features enabled
207 +
208 + #### Plan Object
209 + - **Plan ID**: 1
210 + - **Plugin ID**: Plugin ID from context (defensive)
211 + - **Plan Name**: `professional` (configurable)
212 + - **Plan Title**: `Professional Plan` (configurable)
213 + - **License Type**: Paid
214 + - **Feature Blocking**: Disabled
215 +
216 + ### Customizing Plan Information
217 + To change the displayed plan name and title, modify these constants in `config.php`:
218 + ```php
219 + define( 'WP_FS__MOCK_PLAN_NAME', 'your_plan_name' );
220 + define( 'WP_FS__MOCK_PLAN_TITLE', 'Your Plan Title' );
221 + ```
222 +
223 + ## 🐛 Issues Resolved
224 +
225 + 1. **Red Debug Status** → Green "Connected" status
226 + 2. **"Unknown" Connectivity** → "Connected"
227 + 3. **PHP foreach errors** → Fixed with null array checks
228 + 4. **Account page errors** → Fixed with comprehensive mock objects
229 + 5. **Undefined property errors** → Fixed by bypassing sync methods
230 + 6. **Plan display "FREE"** → Shows configured plan name
231 + 7. **SDK loading conflicts** → Fixed with version 999.99.99
232 + 8. **API timeout errors** → Prevented by bypassing all API calls
233 + 9. **Sync-related errors** → Eliminated by bypassing sync methods
234 + 10. **Payment/billing errors** → Prevented by returning safe values
235 + 11. **"No ID" Site ID display** → Fixed with comprehensive site object
236 + 12. **Email not verified** → Fixed with verified user object
237 + 13. **Missing site properties** → Added all required FS_Site properties
238 + 14. **"Property on false" errors** → Fixed with defensive plugin object checks
239 + 15. **Dynamic property warnings** → Fixed by removing invalid pricing_id property
240 + 16. **API scope creation errors** → Fixed with mock API fallbacks and object validation
241 + 17. **"Class FS_Billing not found" errors** → Fixed by adding missing require statement in require.php
242 + 18. **Unwanted addons tab** → Disabled by overriding has_addons() method
243 + 19. **Unwanted pricing menu** → Disabled by overriding is_pricing_page_visible() method
244 +
245 + ## 📁 Files Modified
246 +
247 + | File | Purpose |
248 + |------|---------|
249 + | `start.php` | SDK version override for priority loading |
250 + | `config.php` | Mock plan configuration constants |
251 + | `includes/class-freemius.php` | Core license bypass, mock object creation, and menu item control |
252 + | `includes/entities/class-fs-plugin-license.php` | License entity method overrides |
253 + | `includes/sdk/FreemiusWordPress.php` | WordPress API bypass |
254 + | `includes/class-fs-api.php` | API manager bypass |
255 + | `require.php` | Added missing FS_Billing class loading |
256 +
257 + ## 🔄 Reapplying Modifications
258 +
259 + If you need to reapply these modifications to a newer version of Freemius SDK:
260 +
261 + ### Step 1: SDK Version Override
262 + **File**: `start.php`
263 + ```php
264 + // Change this line:
265 + $this_sdk_version = '2.12.1';
266 + // To:
267 + $this_sdk_version = '999.99.99';
268 + ```
269 +
270 + ### Step 2: Fix Missing Class Loading
271 + **File**: `require.php`
272 + ```php
273 + // Add this line after the other entity classes (around line 47):
274 + require_once WP_FS__DIR_INCLUDES . '/entities/class-fs-billing.php';
275 + ```
276 +
277 + ### Step 3: Configuration Constants
278 + **File**: `config.php`
279 + ```php
280 + // Add these constants:
281 + define( 'WP_FS__MOCK_PLAN_NAME', 'professional' );
282 + define( 'WP_FS__MOCK_PLAN_TITLE', 'Professional Plan' );
283 + ```
284 +
285 + ### Step 4: Core License Methods
286 + **File**: `includes/class-freemius.php`
287 + ```php
288 + // Modify these methods to always return true/false:
289 + function is_paying() { return true; }
290 + function is_free_plan() { return false; }
291 + function has_features_enabled_license() { return true; }
292 + function can_use_premium_code() { return true; }
293 + function is_trial() { return false; }
294 + function is_trial_utilized() { return false; }
295 + function is_registered() { return true; }
296 + function has_active_valid_license() { return true; }
297 + function is_active_valid_license() { return true; }
298 + ```
299 +
300 + ### Step 5: Mock Objects (Critical)
301 + **File**: `includes/class-freemius.php`
302 +
303 + Add the complete `_ensure_mock_objects()` method with **all** properties:
304 + ```php
305 + private function _ensure_mock_objects() {
306 + // User Object
307 + if ( ! is_object( $this->_user ) ) {
308 + $this->_user = new FS_User();
309 + $this->_user->id = 1;
310 + $this->_user->email = 'noreply@gmail.com';
311 + $this->_user->first = 'Premium';
312 + $this->_user->last = 'User';
313 + $this->_user->is_verified = true;
314 + $this->_user->created = date('Y-m-d H:i:s');
315 + $this->_user->public_key = 'pk_4a7c9e2f8b3d1a6e5c8f2b9d4a7c0e3f';
316 + $this->_user->secret_key = 'sk_8f3d1a6e5c2b9d4a7c0e3f6b8a1d4e7c';
317 + }
318 +
319 + // Site Object (ALL properties required)
320 + if ( ! is_object( $this->_site ) ) {
321 + $this->_site = new FS_Site();
322 + $this->_site->id = 1;
323 + $this->_site->site_id = 1; // CRITICAL for Site ID display
324 + $this->_site->blog_id = get_current_blog_id(); // WordPress blog ID
325 + $this->_site->plugin_id = ( is_object( $this->_plugin ) ? $this->_plugin->id : 1 ); // Plugin ID (defensive)
326 + $this->_site->license_id = 1;
327 + $this->_site->plan_id = 1;
328 + $this->_site->user_id = 1;
329 + $this->_site->title = get_bloginfo('name'); // Site title
330 + $this->_site->url = home_url(); // Site URL
331 + $this->_site->version = ( is_object( $this->_plugin ) ? $this->_plugin->version : '1.0.0' ); // Plugin version (defensive)
332 + $this->_site->language = get_locale(); // Site language
333 + $this->_site->platform_version = get_bloginfo('version'); // WordPress version
334 + $this->_site->sdk_version = $this->version; // SDK version
335 + $this->_site->programming_language_version = phpversion(); // PHP version
336 + $this->_site->is_premium = true; // Premium status
337 + $this->_site->is_active = true; // Active status
338 + $this->_site->is_uninstalled = false; // Not uninstalled
339 + $this->_site->public_key = 'pk_f3b8c2a7e9d1f4a6c3e8b2d5a9f1c4e7';
340 + $this->_site->secret_key = 'sk_2d5a9f1c4e7b3a6c8f2e1d4a7c0e3f6b';
341 + $this->_site->created = date('Y-m-d H:i:s');
342 + }
343 +
344 + // License Object
345 + if ( ! is_object( $this->_license ) ) {
346 + $this->_license = new FS_Plugin_License();
347 + $this->_license->id = 1;
348 + $this->_license->plan_id = 1;
349 + $this->_license->user_id = 1;
350 + $this->_license->secret_key = 'sk_b5e0b5f8dd8689e6aca49dd6e6e1a930';
351 + $this->_license->quota = null;
352 + $this->_license->expiration = null;
353 + $this->_license->created = date('Y-m-d H:i:s');
354 + }
355 +
356 + // Plan Object
357 + if ( ! is_array( $this->_plans ) || empty( $this->_plans ) ) {
358 + $this->_plans = array();
359 + $mock_plan = new FS_Plugin_Plan();
360 + $mock_plan->id = 1;
361 + $mock_plan->name = WP_FS__MOCK_PLAN_NAME;
362 + $mock_plan->title = WP_FS__MOCK_PLAN_TITLE;
363 + $mock_plan->plugin_id = ( is_object( $this->_plugin ) ? $this->_plugin->id : 1 ); // Fixed: Use valid property
364 + $mock_plan->is_block_features = false;
365 + $mock_plan->license_type = 'paid';
366 + $mock_plan->created = date('Y-m-d H:i:s');
367 + $this->_plans[] = $mock_plan;
368 + }
369 + }
370 + ```
371 +
372 + ### Step 6: Update Getter Methods
373 + **File**: `includes/class-freemius.php`
374 + ```php
375 + // Modify these methods to call _ensure_mock_objects():
376 + function get_user() {
377 + $this->_ensure_mock_objects();
378 + return $this->_user;
379 + }
380 +
381 + function get_site() {
382 + $this->_ensure_mock_objects();
383 + return $this->_site;
384 + }
385 +
386 + function _get_license() {
387 + $this->_ensure_mock_objects();
388 + return $this->_license;
389 + }
390 +
391 + function get_plan() {
392 + $this->_ensure_mock_objects();
393 + return ( is_array( $this->_plans ) && ! empty( $this->_plans ) ) ? $this->_plans[0] : null;
394 + }
395 + ```
396 +
397 + ### Step 7: API Scope Protection (Critical)
398 + **File**: `includes/class-freemius.php`
399 +
400 + Add defensive checks to prevent "property on false" errors:
401 + ```php
402 + // Fix get_api_plugin_scope() method:
403 + function get_api_plugin_scope() {
404 + if ( ! isset( $this->_plugin_api ) ) {
405 + // Modified by GPL Times - https://www.gpltimes.com
406 + // Ensure plugin object exists to prevent "property on false" errors
407 + if ( ! is_object( $this->_plugin ) ) {
408 + // Return mock API object to prevent errors
409 + return (object) array(
410 + 'call' => function() { return (object) array( 'success' => true, 'api' => 'bypassed' ); },
411 + 'get' => function() { return (object) array( 'success' => true, 'api' => 'bypassed' ); },
412 + 'post' => function() { return (object) array( 'success' => true, 'api' => 'bypassed' ); }
413 + );
414 + }
415 +
416 + $this->_plugin_api = FS_Api::instance(
417 + $this->_module_id,
418 + 'plugin',
419 + $this->_plugin->id,
420 + $this->_plugin->public_key,
421 + ! $this->is_live(),
422 + false,
423 + $this->get_sdk_version()
424 + );
425 + }
426 +
427 + return $this->_plugin_api;
428 + }
429 + ```
430 +
431 + ### Step 8: Disable Addons Tab and Pricing Menu
432 + **File**: `includes/class-freemius.php`
433 +
434 + Override these methods to disable unwanted menu items:
435 + ```php
436 + // Disable addons tab
437 + function has_addons() {
438 + $this->_logger->entrance();
439 +
440 + // Modified by GPL Times - https://www.gpltimes.com
441 + // Always return false to disable addons tab
442 + return false;
443 + }
444 +
445 + // Disable pricing menu
446 + function is_pricing_page_visible() {
447 + // Modified by GPL Times - https://www.gpltimes.com
448 + // Always return false to disable pricing menu
449 + return false;
450 + }
451 + ```
452 +
453 + // Fix get_api_site_scope() method:
454 + private function get_api_site_scope( $flush = false ) {
455 + if ( ! isset( $this->_site_api ) || $flush ) {
456 + // Modified by GPL Times - https://www.gpltimes.com
457 + // Ensure site object exists to prevent "property on false" errors
458 + if ( ! is_object( $this->_site ) ) {
459 + $this->_ensure_mock_objects();
460 + }
461 +
462 + $this->_site_api = FS_Api::instance(
463 + $this->_module_id,
464 + 'install',
465 + $this->_site->id,
466 + $this->_site->public_key,
467 + ! $this->is_live(),
468 + $this->_site->secret_key,
469 + $this->get_sdk_version(),
470 + self::get_unfiltered_site_url()
471 + );
472 + }
473 +
474 + return $this->_site_api;
475 + }
476 +
477 + // Fix get_account_addons() method:
478 + function get_account_addons() {
479 + $this->_logger->entrance();
480 +
481 + $addons = self::get_all_account_addons();
482 +
483 + // Modified by GPL Times - https://www.gpltimes.com
484 + // Ensure plugin object exists to prevent "property on false" errors
485 + if ( ! is_object( $this->_plugin ) ) {
486 + return false;
487 + }
488 +
489 + if ( ! is_array( $addons ) ||
490 + ! isset( $addons[ $this->_plugin->id ] ) ||
491 + ! is_array( $addons[ $this->_plugin->id ] ) ||
492 + 0 === count( $addons[ $this->_plugin->id ] )
493 + ) {
494 + return false;
495 + }
496 +
497 + return $addons[ $this->_plugin->id ];
498 + }
499 + ```
500 +
501 + ### Step 7: API Bypass Methods
502 + **File**: `includes/class-freemius.php`
503 + ```php
504 + // Bypass these methods:
505 + function has_api_connectivity() { return true; }
506 + function _sync_license() { return; }
507 + function _sync_plugin_license() { return; }
508 + function _fetch_payments() { return array(); }
509 + function _fetch_billing() { return null; }
510 +
511 + // Add null checks:
512 + function _get_plan_by_id( $id ) {
513 + if ( ! is_array( $this->_plans ) ) return null;
514 + // ... existing code
515 + }
516 +
517 + function get_plan_by_name( $name ) {
518 + if ( ! is_array( $this->_plans ) ) return null;
519 + // ... existing code
520 + }
521 + ```
522 +
523 + ### Step 8: License Entity Methods
524 + **File**: `includes/entities/class-fs-plugin-license.php`
525 + ```php
526 + function is_features_enabled() { return true; }
527 + function is_active() { return true; }
528 + function is_expired() { return false; }
529 + ```
530 +
531 + ### Step 9: WordPress API Bypass
532 + **File**: `includes/sdk/FreemiusWordPress.php`
533 + ```php
534 + public function MakeRequest() {
535 + return (object) array( 'success' => true, 'api' => 'success' );
536 + }
537 +
538 + public static function Ping() {
539 + return (object) array( 'api' => 'pong', 'timestamp' => gmdate('Y-m-d H:i:s'), 'is_active' => true );
540 + }
541 + ```
542 +
543 + ### Step 10: API Manager Bypass
544 + **File**: `includes/class-fs-api.php`
545 + ```php
546 + private function _call( $path, $method = 'GET', $params = array(), $in_retry = false ) {
547 + // Check endpoint type and return appropriate mock response
548 + // Site endpoints: Complete FS_Site object with license data
549 + // License endpoints: Complete FS_Plugin_License object with validation data
550 + // User endpoints: Complete FS_User object
551 + // Default: Success response
552 + // This makes license changes appear as successful validations
553 + }
554 + ```
555 +
556 + ## 🎯 Technical Implementation
557 +
558 + ### Priority Loading System
559 + The SDK version is set to `999.99.99` because WordPress's Freemius loader always uses the highest version number found among all active plugins. This ensures our modified SDK takes precedence.
560 +
561 + ### Mock Object Strategy
562 + Instead of making API calls to fetch user/site/license data, the system creates realistic mock objects with:
563 + - Valid-looking keys and IDs
564 + - Professional plan configuration
565 + - Active license status
566 + - Unlimited quota and lifetime expiration
567 + - Proper API responses that simulate successful license validation
568 + - Context-aware responses based on endpoint type (site/license/user)
569 +
570 + ### Critical Site Object Properties
571 + The site object requires **ALL** these properties to prevent account page errors:
572 +
573 + | Property | Purpose | Value |
574 + |----------|---------|-------|
575 + | `id` | Primary site identifier | 1 |
576 + | `site_id` | Alternative site ID (critical for display) | 1 |
577 + | `blog_id` | WordPress blog ID | Current blog ID |
578 + | `plugin_id` | Links to plugin context | Actual plugin ID |
579 + | `title` | Site display name | WordPress site title |
580 + | `url` | Site URL | WordPress home URL |
581 + | `version` | Plugin version | Current plugin version |
582 + | `language` | Site language | WordPress locale |
583 + | `platform_version` | WordPress version | Current WP version |
584 + | `sdk_version` | SDK version | Freemius SDK version |
585 + | `programming_language_version` | PHP version | Server PHP version |
586 + | `is_premium` | Premium status flag | true |
587 + | `is_active` | Active status flag | true |
588 + | `is_uninstalled` | Uninstalled flag | false |
589 + | `public_key` | Site public key | Mock key |
590 + | `secret_key` | Site secret key | Mock key |
591 + | `created` | Creation timestamp | Current datetime |
592 +
593 + **⚠️ Warning**: Missing any of these properties may cause "No ID" displays or account page errors.
594 +
595 + ### Critical Error Prevention
596 + The modifications include defensive programming to prevent common PHP errors:
597 +
598 + | Error Type | Cause | Fix |
599 + |------------|-------|-----|
600 + | `Attempt to read property "id" on false` | `$this->_plugin` is false | Plugin object validation in API scopes |
601 + | `Attempt to read property "public_key" on false` | `$this->_plugin` is false | Mock API object fallback |
602 + | `Attempt to read property "secret_key" on false` | `$this->_plugin` is false | Defensive checks before access |
603 + | `Creation of dynamic property` | Invalid `pricing_id` property | Use valid `plugin_id` property |
604 + | API scope creation errors | Missing objects during initialization | Ensure mock objects before API calls |
605 +
606 + **🔧 Key Defensive Patterns:**
607 + - Always check `is_object( $this->_plugin )` before accessing properties
608 + - Call `$this->_ensure_mock_objects()` before API scope creation
609 + - Use fallback values: `( is_object( $this->_plugin ) ? $this->_plugin->id : 1 )`
610 + - Return mock API objects when real objects are unavailable
611 +
612 + ### API Interception
613 + All API communication is intercepted at multiple levels:
614 + - `FreemiusWordPress::MakeRequest()` - WordPress HTTP layer
615 + - `FreemiusWordPress::Ping()` - Connectivity tests
616 + - `FS_Api::_call()` - API manager layer
617 + - Sync methods - License synchronization
618 +
619 + ### Error Prevention
620 + Common error sources are eliminated by:
621 + - Bypassing sync operations that cause undefined property errors
622 + - Adding null checks before foreach loops
623 + - Returning safe default values from API methods
624 + - Creating mock objects when needed
625 +
626 + ## 📊 Debug Page Information
627 +
628 + After applying these modifications, the Freemius debug page will show:
629 + - **Status**: Connected (Green)
630 + - **API Connectivity**: Connected
631 + - **Plan**: Professional Plan (or your configured plan)
632 + - **License**: Active, Non-expired
633 + - **Features**: All enabled
634 +
635 + ## ⚙️ Compatibility
636 +
637 + This modified SDK is compatible with:
638 + - WordPress 5.0+
639 + - PHP 7.0+
640 + - All Freemius-powered plugins and themes
641 + - Single site and multisite installations
642 +
643 + ## 📝 Development Notes
644 +
645 + - All modifications are clearly marked with "Modified by GPL Times" comments
646 + - Original functionality is preserved where possible
647 + - Mock data uses realistic formats and structures
648 + - No external dependencies added
649 + - Maintains compatibility with existing Freemius integrations
650 +
651 + ## 🔗 Attribution
652 +
653 + **Original Freemius SDK**: https://github.com/Freemius/wordpress-sdk
654 + **Modified by**: GPL Times - https://www.gpltimes.com
655 + **License**: GPL v3.0
656 +
657 + ---
658 +
659 + *This modified SDK enables all premium features without requiring license activation. Use responsibly and consider supporting original developers.*