PluginProbe
LearnPress – WordPress LMS Plugin for Create and Sell Online Courses / 4.4.0
LearnPress – WordPress LMS Plugin for Create and Sell Online Courses v4.4.0
4.4.6 4.4.5 4.4.4 4.4.3 4.4.2 4.4.1 4.4.0 4.3.9.1 4.3.9 4.3.8 4.3.7 4.1.6.9 4.1.6.9.1 4.1.6.9.2 4.1.6.9.3 4.1.6.9.4 4.1.7 4.1.7.1 4.1.7.2 4.1.7.3 4.1.7.3.1 4.1.7.3.2 4.2.0 4.2.1 4.2.1.1 All 137 releases
learnpress / learnpress.php

learnpress.php in LearnPress – WordPress LMS Plugin for Create and Sell Online Courses 4.4.0, at learnpress.php

1,100 lines 33.9 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Plugin Name: LearnPress
4 * Plugin URI: https://thimpress.com/learnpress
5 * Description: LearnPress is a WordPress complete solution for creating a Learning Management System (LMS). It can help you to create courses, lessons and quizzes.
6 * Author: ThimPress
7 * Version: 4.4.0
8 * Author URI: http://thimpress.com
9 * Requires at least: 6.0
10 * Requires PHP: 7.4
11 * Text Domain: learnpress
12 * Domain Path: /languages/
13 *
14 * @package LearnPress
15 */
16
17 use LearnPress\TemplateHooks\CourseBuilder\Course\BuilderListCoursesTemplate;
18 use LearnPress\TemplateHooks\CourseBuilder\Course\BuilderCourseTemplate;
19 use LearnPress\TemplateHooks\CourseBuilder\Course\BuilderEditCourseTemplate;
20 use LearnPress\Ajax\AI\OpenAiAjax;
21 use LearnPress\Ajax\BuilderDashboardAjax;
22 use LearnPress\Ajax\CourseBuilder\CourseBuilderAjax;
23 use LearnPress\Ajax\EditCurriculumAjax;
24 use LearnPress\Ajax\EditQuestionAjax;
25 use LearnPress\Ajax\EditQuizAjax;
26 use LearnPress\Ajax\Order\ExportOrderCSVAjax;
27 use LearnPress\Ajax\LessonAjax;
28 use LearnPress\Ajax\LoadContentViaAjax;
29 use LearnPress\Ajax\AI\AIAssistantAjax;
30 use LearnPress\Ajax\MCP\McpApiKeysAjax;
31 use LearnPress\Ajax\CourseBuilder\CBEditCourseAjax;
32 use LearnPress\Ajax\SendEmailAjax;
33 use LearnPress\Background\LPBackgroundTrigger;
34 use LearnPress\ExternalPlugin\Elementor\LPElementor;
35 use LearnPress\ExternalPlugin\RankMath\LPRankMath;
36 use LearnPress\ExternalPlugin\YoastSeo\LPYoastSeo;
37 use LearnPress\Gutenberg\GutenbergHandleMain;
38 use LearnPress\Ajax\Order\RefundOrderAjax;
39 use LearnPress\MCP\Abilities;
40 use LearnPress\MCP\Auth\ApiKeyAuthenticator;
41 use LearnPress\Models\CourseModel;
42 use LearnPress\Models\UserModel;
43 use LearnPress\Shortcodes\Course\FilterCourseShortcode;
44 use LearnPress\Shortcodes\CourseButtonShortcode;
45 use LearnPress\Shortcodes\CourseMaterialShortcode;
46 use LearnPress\Shortcodes\Courses\ListCoursesShortcode;
47 use LearnPress\Shortcodes\ListInstructorsShortcode;
48 use LearnPress\Shortcodes\SingleInstructorShortcode;
49 use LearnPress\TemplateHooks\Admin\AdminEditQizTemplate;
50 use LearnPress\TemplateHooks\Admin\AdminEditQuestionTemplate;
51 use LearnPress\TemplateHooks\Admin\AdminListStudentsEnrolled;
52 use LearnPress\TemplateHooks\Admin\AI\AdminCreateCourseAITemplate;
53 use LearnPress\TemplateHooks\Admin\AI\AdminEditCourseCurriculumWithAITemplate;
54 use LearnPress\TemplateHooks\Admin\AI\AdminEditWithAITemplate;
55 use LearnPress\TemplateHooks\Course\AdminEditCurriculumTemplate;
56 use LearnPress\TemplateHooks\Course\AdminEditSettingTemplate;
57 use LearnPress\TemplateHooks\Course\CourseMaterialTemplate;
58 use LearnPress\TemplateHooks\Course\FilterCourseTemplate;
59 use LearnPress\TemplateHooks\Course\ListCoursesRelatedTemplate;
60 use LearnPress\TemplateHooks\Course\ListCoursesTemplate;
61 use LearnPress\TemplateHooks\Course\SingleCourseClassicTemplate;
62 use LearnPress\TemplateHooks\Course\SingleCourseModernLayout;
63 use LearnPress\TemplateHooks\Course\SingleCourseOfflineTemplate;
64 use LearnPress\TemplateHooks\Course\SingleCourseTemplate;
65 use LearnPress\TemplateHooks\CourseBuilder\BuilderPopupTemplate;
66 use LearnPress\TemplateHooks\CourseBuilder\CourseBuilderTemplate;
67 use LearnPress\TemplateHooks\CourseBuilder\Dashboard\BuilderDashboardTemplate;
68 use LearnPress\TemplateHooks\CourseBuilder\Lesson\BuilderEditLessonTemplate;
69 use LearnPress\TemplateHooks\CourseBuilder\Lesson\BuilderLessonTemplate;
70 use LearnPress\TemplateHooks\CourseBuilder\Lesson\BuilderListLessonsTemplate;
71 use LearnPress\TemplateHooks\CourseBuilder\Question\BuilderEditQuestionTemplate;
72 use LearnPress\TemplateHooks\CourseBuilder\Question\BuilderListQuestionsTemplate;
73 use LearnPress\TemplateHooks\CourseBuilder\Question\BuilderQuestionTemplate;
74 use LearnPress\TemplateHooks\CourseBuilder\Quiz\BuilderEditQuizTemplate;
75 use LearnPress\TemplateHooks\CourseBuilder\Quiz\BuilderListQuizzesTemplate;
76 use LearnPress\TemplateHooks\CourseBuilder\Quiz\BuilderQuizTemplate;
77 use LearnPress\TemplateHooks\CourseBuilder\Settings\BuilderSettingsTemplate;
78 use LearnPress\TemplateHooks\Instructor\ListInstructorsTemplate;
79 use LearnPress\TemplateHooks\Instructor\SingleInstructorTemplate;
80 use LearnPress\TemplateHooks\Order\AdminOrderItemsTemplate;
81 use LearnPress\TemplateHooks\Order\AdminOrderListTemplate;
82 use LearnPress\TemplateHooks\Profile\ProfileCoursesTemplate;
83 use LearnPress\TemplateHooks\Profile\ProfileGeneralInfoTemplate;
84 use LearnPress\TemplateHooks\Profile\ProfileInstructorStatisticsTemplate;
85 use LearnPress\TemplateHooks\Profile\ProfileOrdersTemplate;
86 use LearnPress\TemplateHooks\Profile\ProfileOrderTemplate;
87 use LearnPress\TemplateHooks\Profile\ProfileQuizzesTemplate;
88 use LearnPress\TemplateHooks\Profile\ProfileStudentEnrolledTemplate;
89 use LearnPress\TemplateHooks\Profile\ProfileStudentStatisticsTemplate;
90 use LearnPress\TemplateHooks\Course\CourseAIAssistantTemplate;
91 use LearnPress\Widgets\LPRegisterWidget;
92 use LearnPress\WPGDPR\ErasePersonalData;
93 use LearnPress\WPGDPR\ExportPersonalData;
94
95 defined( 'ABSPATH' ) || exit();
96
97 if ( ! class_exists( 'LearnPress' ) ) {
98 /**
99 * Class LearnPress
100 *
101 * Version 3.0.1
102 */
103 class LearnPress {
104 /**
105 * Current version of the plugin
106 *
107 * @var string
108 */
109 public $version = '';
110 /**
111 * Version database require, use for this LP source
112 *
113 * @var int
114 */
115 public $db_version = 5;
116
117 /**
118 * The single instance of the class
119 *
120 * @var LearnPress object
121 */
122 private static $_instance = null;
123
124 /**
125 * Store the session class
126 *
127 * @var LP_Session_Handler
128 */
129 public $session = null;
130
131 /**
132 * @var LP_Cart object
133 */
134 public $cart = false;
135
136 /**
137 * @var LP_Settings
138 */
139 public $settings = null;
140
141 /**
142 * @var array
143 */
144 public $query_vars = array();
145
146 /**
147 * @var array
148 */
149 public $global = array();
150
151 /**
152 * @var LP_Template
153 */
154 public $template = null;
155
156 /**
157 * @var LP_Core_API
158 */
159 public $api = null;
160
161 /**
162 * @var LP_Admin_Core_API
163 */
164 public $admin_api = null;
165
166 /**
167 * @var string
168 */
169 public $thim_core_version_require = '2.0.0';
170
171 public static $time_limit_default_of_sever = 0;
172
173 public static $doc_link = 'https://learnpresslms.com/docs/';
174
175 /**
176 * LearnPress constructor.
177 */
178 private function __construct() {
179 /*if ( isset( $_POST['action'] ) && 'heartbeat' === $_POST['action'] ) {
180 return;
181 }*/
182
183 try {
184 $this->prepare_before_handle();
185
186 if ( ! LP_Install::instance()->tables_install_done() ) {
187 return;
188 }
189
190 // Must handle in hook init of WordPress, when loaded plugins, theme, user.
191 add_action( 'init', [ $this, 'lp_main_handle' ], - 1000 );
192
193 // hooks .
194 $this->hooks();
195 } catch ( Throwable $e ) {
196 error_log( __METHOD__ . ': ' . $e->getMessage() );
197 }
198 }
199
200 /**
201 * Prepare before handle.
202 * 1.Load constants and includes files.
203 * 2.Get default time limit of server.
204 * 3.Update version of LP undefined.
205 *
206 * @return void
207 * @since 4.2.7.6
208 * @version 1.0.0
209 */
210 public function prepare_before_handle() {
211 // Define constant .
212 $this->plugin_defines();
213
214 self::$time_limit_default_of_sever = ini_get( 'max_execution_time' );
215
216 // Update for case compare version of LP if LEARNPRESS_VERSION undefined
217 $this->version = LEARNPRESS_VERSION;
218 if ( is_admin() ) {
219 $learn_press_version = get_option( 'learnpress_version', '' );
220 if ( $learn_press_version !== $this->version ) {
221 if ( empty( $learn_press_version ) ) { // Case user install new
222 // Set using modern layout for new installation.
223 update_option( 'learn_press_layout_single_course', 'modern' );
224 }
225
226 update_option( 'learnpress_version', $this->version );
227 }
228 }
229
230 // define table prefixes .
231 $this->define_tables();
232
233 // Include files .
234 $this->includes();
235 }
236
237 /**
238 * Define constant.
239 */
240 protected function plugin_defines() {
241 if ( ! defined( 'LP_PLUGIN_FILE' ) ) {
242 define( 'LP_PLUGIN_FILE', __FILE__ );
243 include_once 'inc/lp-constants.php';
244 }
245 }
246
247 /**
248 * Defines database table names.
249 */
250 public function define_tables() {
251 global $wpdb;
252
253 $tables = array(
254 'sessions',
255 'sections',
256 'section_items',
257 'user_items',
258 'user_itemmeta',
259 'user_item_results',
260 'order_items',
261 'order_itemmeta',
262 'quiz_questions',
263 'question_answers',
264 'question_answermeta',
265 );
266
267 foreach ( $tables as $short_name ) {
268 $table_name = $wpdb->prefix . LP_TABLE_PREFIX . $short_name;
269 $backward_key = 'learnpress_' . $short_name;
270 $wpdb->{$backward_key} = $table_name;
271 }
272 }
273
274 /**
275 * Includes needed files.
276 */
277 public function includes() {
278 include_once LP_PLUGIN_PATH . 'vendor/autoload.php';
279
280 // Include required files load anywhere, both frontend and backend.
281 $this->include_files_global();
282
283 // include files when LP ready run - after setup success .
284 if ( ! LP_Install::instance()->tables_install_done() ) {
285 return;
286 }
287
288 // Include required files Backend.
289 $this->include_files_admin();
290
291 // Include required files Frontend.
292 $this->include_files_frontend();
293
294 new LP_Query();
295 }
296
297 /**
298 * load files anywhere, both frontend and backend
299 *
300 * @return void
301 */
302 private function include_files_global() {
303
304 // Filter query .
305 include_once 'inc/Filters/class-lp-filter.php';
306 include_once 'inc/Filters/class-lp-post-type-filter.php';
307 include_once 'inc/Filters/class-lp-post-meta-filter.php';
308 include_once 'inc/Filters/class-lp-user-filter.php';
309 include_once 'inc/Filters/class-lp-course-filter.php';
310 include_once 'inc/Filters/class-lp-course-json-filter.php';
311 include_once 'inc/Filters/class-lp-order-filter.php';
312 include_once 'inc/Filters/class-lp-session-filter.php';
313 include_once 'inc/Filters/class-lp-section-filter.php';
314 include_once 'inc/Filters/class-lp-section-items-filter.php';
315 include_once 'inc/Filters/class-lp-question-filter.php';
316 include_once 'inc/Filters/class-lp-quiz-filter.php';
317 include_once 'inc/Filters/class-lp-user-items-filter.php';
318 include_once 'inc/Filters/class-lp-user-item-meta-filter.php';
319 include_once 'inc/Filters/class-lp-quiz-filter.php';
320 include_once 'inc/Filters/class-lp-quiz-questions-filter.php';
321 include_once 'inc/Filters/class-lp-question-answers-filter.php';
322 include_once 'inc/Filters/class-lp-question-answermeta-filter.php';
323
324 // Query Database .
325 include_once 'inc/Databases/class-lp-db.php';
326 include_once 'inc/Databases/class-lp-course-json-db.php';
327 include_once 'inc/Databases/class-lp-order-db.php';
328 include_once 'inc/Databases/class-lp-post-db.php';
329 include_once 'inc/Databases/class-lp-post-meta-db.php';
330 include_once 'inc/Databases/class-lp-user-db.php';
331 include_once 'inc/Databases/class-lp-course-db.php';
332 include_once 'inc/Databases/class-lp-lesson-db.php';
333 include_once 'inc/Databases/class-lp-section-db.php';
334 include_once 'inc/Databases/class-lp-section-items-db.php';
335 include_once 'inc/Databases/class-lp-quiz-db.php';
336 include_once 'inc/Databases/class-lp-quiz-questions-db.php';
337 include_once 'inc/Databases/class-lp-question-answers-db.php';
338 include_once 'inc/Databases/class-lp-sessions-db.php';
339 include_once 'inc/Databases/class-lp-question-db.php';
340 include_once 'inc/Databases/class-lp-user-items-db.php';
341 include_once 'inc/Databases/class-lp-user-item-meta-db.php';
342 include_once 'inc/Databases/class-lp-user-item-results-db.php';
343 include_once 'inc/Databases/class-thim-cache-db.php';
344 include_once 'inc/Databases/class-lp-material-db.php';
345 include_once 'inc/Databases/class-lp-statistics-db.php';
346
347 // File system .
348 include_once 'inc/class-lp-file-system.php';
349
350 // File helper
351 include_once 'inc/class-lp-helper.php';
352
353 // Template Hooks.
354 ListCoursesTemplate::instance();
355 ListCoursesRelatedTemplate::instance();
356 ListInstructorsTemplate::instance();
357 SingleCourseTemplate::instance();
358 SingleCourseOfflineTemplate::instance();
359 SingleCourseModernLayout::instance();
360 SingleCourseClassicTemplate::instance();
361 SingleInstructorTemplate::instance();
362 ProfileInstructorStatisticsTemplate::instance();
363 ProfileStudentStatisticsTemplate::instance();
364 ProfileOrdersTemplate::instance();
365 ProfileOrderTemplate::instance();
366 ProfileGeneralInfoTemplate::instance();
367 FilterCourseTemplate::instance();
368 ProfileQuizzesTemplate::instance();
369 CourseBuilderTemplate::instance();
370 BuilderCourseTemplate::instance();
371 BuilderListCoursesTemplate::instance();
372 BuilderDashboardTemplate::instance();
373 BuilderSettingsTemplate::instance();
374 BuilderDashboardAjax::instance();
375 BuilderEditCourseTemplate::instance();
376 BuilderLessonTemplate::instance();
377 BuilderListLessonsTemplate::instance();
378 BuilderEditLessonTemplate::instance();
379 BuilderQuizTemplate::instance();
380 BuilderListQuizzesTemplate::instance();
381 BuilderEditQuizTemplate::instance();
382 BuilderQuestionTemplate::instance();
383 BuilderListQuestionsTemplate::instance();
384 BuilderEditQuestionTemplate::instance();
385 BuilderPopupTemplate::instance();
386 ProfileCoursesTemplate::instance();
387 ProfileStudentEnrolledTemplate::instance();
388
389 // Admin template hooks.
390 AdminEditCurriculumTemplate::instance();
391 AdminEditSettingTemplate::instance();
392 AdminEditQizTemplate::instance();
393 AdminEditQuestionTemplate::instance();
394 CourseMaterialTemplate::instance();
395 CourseAIAssistantTemplate::instance();
396 AdminOrderItemsTemplate::instance();
397 AdminOrderListTemplate::instance();
398 AdminCreateCourseAITemplate::instance();
399 AdminEditWithAITemplate::instance();
400 AdminEditCourseCurriculumWithAITemplate::instance();
401 AdminListStudentsEnrolled::instance();
402 // WP GDPR
403 ErasePersonalData::instance();
404 ExportPersonalData::instance();
405
406 // Models
407 include_once 'inc/Models/class-lp-rest-response.php';
408 include_once 'inc/Models/steps/class-lp-group-step.php';
409 include_once 'inc/Models/steps/class-lp-step.php';
410 include_once 'inc/Models/class-lp-course-extra-info-fast-query-model.php';
411
412 // Handle steps.
413 include_once 'inc/handle-steps/class-lp-handle-steps.php';
414 include_once 'inc/handle-steps/class-lp-handle-upgrade-db-steps.php';
415
416 // LP Cache
417 include_once 'inc/cache/class-lp-cache.php';
418 include_once 'inc/cache/class-lp-courses-cache.php';
419 include_once 'inc/cache/class-lp-course-cache.php';
420 include_once 'inc/cache/class-lp-quiz-cache.php';
421 include_once 'inc/cache/class-lp-question-cache.php';
422 include_once 'inc/cache/class-lp-session-cache.php';
423 include_once 'inc/cache/class-lp-settings-cache.php';
424 include_once 'inc/cache/class-lp-user-items-cache.php';
425
426 // Background processes.
427 LPBackgroundTrigger::instance();
428 include_once 'inc/libraries/wp-background-process/wp-background-processing.php';
429 include_once 'inc/background-process/abstract-lp-async-request.php';
430 //include_once 'inc/background-process/abstract-lp-async-task.php';
431 include_once 'inc/background-process/class-lp-background-single-course.php';
432 include_once 'inc/background-process/class-lp-background-single-email.php';
433
434 // Assets object
435 include_once 'inc/class-lp-asset-key.php';
436 include_once 'inc/abstracts/abstract-assets.php';
437
438 // Debug class
439 include_once 'inc/class-lp-debug.php';
440
441 include_once 'inc/class-lp-settings.php';
442 include_once 'inc/abstract-settings.php';
443 include_once 'inc/settings/abstract-settings-page.php';
444 include_once 'inc/settings/class-lp-settings-courses.php';
445 include_once 'inc/class-lp-global.php';
446 include_once 'inc/class-lp-datetime.php';
447
448 // Register custom-post-type and taxonomies .
449 /*include_once 'inc/custom-post-types/abstract.php';
450 include_once 'inc/custom-post-types/course.php';
451 include_once 'inc/custom-post-types/lesson.php';
452 include_once 'inc/custom-post-types/quiz.php';
453 include_once 'inc/custom-post-types/question.php';
454 include_once 'inc/custom-post-types/order.php';*/
455
456 include_once 'inc/interfaces/interface-curd.php';
457 include_once 'inc/abstracts/abstract-array-access.php';
458 include_once 'inc/abstracts/abstract-object-data.php';
459 include_once 'inc/abstracts/abstract-post-data.php';
460
461 include_once 'inc/curds/class-lp-course-curd.php';
462 include_once 'inc/curds/class-lp-section-curd.php';
463 include_once 'inc/curds/class-lp-lesson-curd.php';
464 include_once 'inc/curds/class-lp-quiz-curd.php';
465 include_once 'inc/curds/class-lp-question-curd.php';
466 include_once 'inc/curds/class-lp-order-curd.php';
467 include_once 'inc/curds/class-lp-user-curd.php';
468 include_once 'inc/curds/class-lp-user-item-curd.php';
469
470 include_once 'inc/course/class-lp-course-item.php';
471 include_once 'inc/question/class-lp-question.php';
472 include_once 'inc/course/class-lp-course-section.php';
473 include_once 'inc/course/class-lp-course-no-required-enroll.php';
474 include_once 'inc/user-item/class-lp-user-item.php';
475 include_once 'inc/user-item/class-lp-user-item-course.php';
476
477 include_once 'inc/lp-deprecated.php'; // Will remove if Eduma and guest update all 4.0.0
478 include_once 'inc/lp-core-functions.php';
479 include_once 'inc/class-lp-autoloader.php';
480
481 include_once 'inc/lp-webhooks.php'; // Addon learnpress-2checkout-payment v4.0.1 is using, when update v4.0.2 don't need load it.
482 include_once 'inc/class-lp-request-handler.php';
483
484 include_once 'inc/admin/helpers/class-lp-plugins-helper.php';
485
486 // Todo: tungnx check those files.
487 include_once 'inc/abstracts/abstract-object-query.php';
488 include_once 'inc/class-lp-course-query.php';
489 include_once 'inc/abstracts/abstract-addon.php';
490 include_once 'inc/class-lp-thumbnail-helper.php';
491 include_once 'inc/cache.php';
492
493 // Class handle check db of LP need to upgrade?
494 include_once 'inc/admin/class-lp-updater.php';
495
496 include_once 'inc/course/lp-course-functions.php';
497 include_once 'inc/course/abstract-course.php';
498 include_once 'inc/course/class-lp-course.php';
499 include_once 'inc/quiz/lp-quiz-functions.php';
500 include_once 'inc/quiz/class-lp-quiz.php';
501 //include_once 'inc/lesson/lp-lesson-functions.php';
502 include_once 'inc/order/lp-order-functions.php';
503 include_once 'inc/order/class-lp-order.php';
504
505 include_once 'inc/user/lp-user-functions.php';
506 include_once 'inc/user/class-lp-user-factory.php';
507 include_once 'inc/user/abstract-lp-user.php';
508 include_once 'inc/user/class-lp-user.php';
509 include_once 'inc/user/class-lp-profile.php';
510 include_once 'inc/user-item/class-lp-user-item.php';
511 include_once 'inc/user-item/class-lp-user-item-course.php';
512 include_once 'inc/user-item/class-lp-user-item-quiz.php';
513 include_once 'inc/user-item/class-lp-quiz-results.php';
514
515 // Shortcodes.
516 SingleInstructorShortcode::instance();
517 ListInstructorsShortcode::instance();
518 CourseMaterialShortcode::instance();
519 CourseButtonShortcode::instance();
520 FilterCourseShortcode::instance();
521 ListCoursesShortcode::instance();
522 //ListCourseRecentShortcode::instance();
523 include_once 'inc/class-lp-shortcodes.php';
524
525 // include template functions .
526 include_once 'inc/lp-template-functions.php';
527 include_once 'inc/templates/abstract-template.php';
528 //include_once 'inc/class-lp-template.php';
529
530 // Cart
531 include_once 'inc/cart/class-lp-cart.php';
532 include_once 'inc/cart/lp-cart-functions.php';
533
534 // Block Templates
535 //include_once 'inc/block-template/class-abstract-block-template.php';
536 //include_once 'inc/block-template/class-block-template-handle.php';
537 GutenbergHandleMain::instance();
538
539 // API
540 include_once 'inc/abstracts/abstract-rest-api.php';
541 include_once 'inc/abstracts/abstract-rest-controller.php';
542 include_once 'inc/rest-api/class-lp-core-api.php';
543 include_once 'inc/rest-api/class-lp-admin-core-api.php';
544
545 /** Jwt */
546 include_once 'inc/jwt/class-jwt-auth.php';
547
548 LPRegisterWidget::instance();
549 include_once 'inc/class-lp-widget.php';
550 include_once 'inc/lp-widget-functions.php';
551
552 // TODO: update frontend editor before move to function include_files_admin.
553 include_once 'inc/admin/views/meta-boxes/class-lp-meta-box.php';
554
555 include_once 'inc/class-lp-page-controller.php';
556 LP_Page_Controller::instance();
557
558 include_once 'inc/gateways/class-lp-gateway-abstract.php';
559 include_once 'inc/gateways/subscriptions/class-lp-subscription-manager.php';
560 include_once 'inc/gateways/class-lp-gateways.php';
561 }
562
563 /**
564 * Include file run on backend
565 */
566 private function include_files_admin() {
567 if ( ! is_admin() ) {
568 return;
569 }
570
571 include_once 'inc/admin/class-lp-admin-ajax.php';
572
573 include_once 'inc/admin/class-lp-admin-notice.php';
574
575 // File handle install LP
576 include_once 'inc/class-lp-install.php';
577
578 // Meta box helper
579 include_once 'inc/admin/meta-box/class-lp-meta-box-helper.php';
580
581 // include_once 'inc/admin/class-lp-admin.php';
582 // include_once 'inc/admin/settings/abstract-settings-page.php';
583 }
584
585 /**
586 * Include file run on frontend
587 */
588 private function include_files_frontend() {
589 if ( is_admin() ) {
590 return;
591 }
592
593 include_once 'inc/class-lp-assets.php';
594
595 include_once 'inc/course/class-model-user-can-view-course-item.php';
596
597 include_once 'inc/class-lp-ajax.php';
598
599 include_once 'inc/class-lp-session-handler.php';
600 }
601
602 /**
603 * Main instance of LearnPress.
604 * Must load on "init" hook of WordPress.
605 * 1. Load text domain.
606 * 2. Handle lp ajax.
607 *
608 * @return void
609 * @version 4.2.7.6
610 * @version 1.0.2
611 */
612 public function lp_main_handle() {
613 try {
614 // Load text domain.
615 $this->load_plugin_text_domain();
616
617 // Register custom post type and taxonomies .
618 include_once 'inc/custom-post-types/abstract.php';
619 include_once 'inc/custom-post-types/course.php';
620 include_once 'inc/custom-post-types/lesson.php';
621 include_once 'inc/custom-post-types/quiz.php';
622 include_once 'inc/custom-post-types/question.php';
623 include_once 'inc/custom-post-types/order.php';
624
625 // Polylang
626 if ( defined( 'POLYLANG_VERSION' ) ) {
627 include_once 'inc/ExternalPlugin/Polylang/class-lp-polylang.php';
628 LP_Polylang::instance();
629 }
630
631 // For plugin Elementor
632 if ( defined( 'ELEMENTOR_VERSION' ) ) {
633 LPElementor::instance();
634 }
635
636 // For plugin WPSEO
637 if ( defined( 'WPSEO_FILE' ) ) {
638 LPYoastSeo::instance();
639 }
640
641 // For plugin RankMath
642 if ( defined( 'RANK_MATH_VERSION' ) ) {
643 LPRankMath::instance();
644 }
645
646 $this->api = new LP_Core_API();
647 $this->admin_api = new LP_Admin_Core_API();
648 $this->get_session();
649 $this->settings = $this->settings();
650 $this->get_cart();
651
652 // Init emails
653 LP_Emails::instance();
654 // Email hook notify
655 include_once 'inc/emails/class-lp-email-hooks.php';
656
657 if ( is_admin() ) {
658 $this->check_addons_version_valid();
659
660 include_once 'inc/admin/class-lp-admin.php';
661 }
662
663 // let third parties know that we're ready .
664 do_action( 'learn-press/ready' );
665
666 // For addon sorting choice old <= v4.0.1
667 /*if ( class_exists( 'LP_Addon_Sorting_Choice_Preload' ) ) {
668 if ( version_compare( LP_ADDON_SORTING_CHOICE_VER, '4.0.1', '<=' ) ) {
669 $lp_addon_sorting_choice = new LP_Addon_Sorting_Choice();
670 $lp_addon_sorting_choice->init();
671 }
672 }*/
673
674 /**
675 * Init gateways, to load all payment gateways, catch callback.
676 * Must be call after learn-press/ready to register hook of addon.
677 */
678 LP_Gateways::instance();
679
680 /**
681 * Fixed temporary for emails of Announcement v4.0.6, Assignment v4.1.1 addons.
682 * @since 4.2.7.4
683 * When 2 addons update to new version, will remove this code.
684 */
685 /*if ( class_exists( 'LP_Addon_Announcements_Preload' ) ) {
686 if ( version_compare( LP_ADDON_ANNOUNCEMENTS_VER, '4.0.6', '<=' ) ) {
687 $addon_announcement = LP_Addon_Announcements_Preload::$addon;
688 $addon_announcement->emails_setting();
689 }
690 }*/
691 /*if ( class_exists( 'LP_Addon_Assignment_Preload' ) ) {
692 if ( version_compare( LP_ADDON_ASSIGNMENT_VER, '4.1.1', '<=' ) ) {
693 $addon_assignment = LP_Addon_Assignment_Preload::$addon;
694 $addon_assignment->emails_setting();
695 }
696 }*/
697 } catch ( Throwable $e ) {
698 LP_Debug::error_log( $e );
699 }
700 }
701
702 /**
703 * Check version addons valid version require.
704 * If not valid will be to deactivate.
705 * Reload page, so not affect to hook "learn-press/ready"
706 */
707 public function check_addons_version_valid() {
708 $addons_valid = true;
709 $plugins = get_option( 'active_plugins' );
710
711 $list_lp_addon_activated = preg_grep( '/^learnpress-.*/i', $plugins );
712 foreach ( $list_lp_addon_activated as $lp_addon ) {
713 $lp_addon_info = get_file_data(
714 WP_PLUGIN_DIR . '/' . $lp_addon,
715 array(
716 'Require_LP_Version' => 'Require_LP_Version',
717 'Version' => 'Version',
718 )
719 );
720
721 $lp_addon_version = $lp_addon_info['Version'];
722
723 $addon = new LP_Addon();
724 $addon->version = $lp_addon_version;
725 $addon->plugin_base = $lp_addon;
726 $addon->require_version = $lp_addon_info['Require_LP_Version'];
727 $addon_valid = $addon->check_require_version_addon();
728
729 if ( $addons_valid ) {
730 //$addon_valid = $addon->check_require_version_lp();
731 }
732
733 if ( ! $addon_valid ) {
734 $addons_valid = false;
735 }
736 }
737 }
738
739 /**
740 * Initial common hooks
741 */
742 public function hooks() {
743 add_action( 'init', array( $this, 'maybe_init_mcp_abilities' ), 20 );
744
745 /**
746 * Handle lp ajax.
747 * Set priority after register_post_type to register capabilities for post type of LP.
748 */
749 add_action(
750 'init',
751 function () {
752 LoadContentViaAjax::catch_lp_ajax();
753 LessonAjax::catch_lp_ajax();
754 EditCurriculumAjax::catch_lp_ajax();
755 EditQuizAjax::catch_lp_ajax();
756 EditQuestionAjax::catch_lp_ajax();
757 SendEmailAjax::catch_lp_ajax();
758 RefundOrderAjax::catch_lp_ajax();
759 CourseBuilderAjax::catch_lp_ajax();
760 OpenAiAjax::catch_lp_ajax();
761 AIAssistantAjax::catch_lp_ajax();
762 ExportOrderCSVAjax::catch_lp_ajax();
763 McpApiKeysAjax::catch_lp_ajax();
764 CBEditCourseAjax::catch_lp_ajax();
765
766 do_action( 'learn-press/register-ajax-handlers' );
767 },
768 11
769 );
770
771 // Add links setting|document|addon on plugins page.
772 add_filter( 'plugin_action_links_' . LP_PLUGIN_BASENAME, array( $this, 'plugin_links' ) );
773
774 register_activation_hook( LP_PLUGIN_FILE, array( $this, 'on_activate' ) );
775 register_deactivation_hook( LP_PLUGIN_FILE, array( $this, 'on_deactivate' ) );
776
777 add_action(
778 'plugin_loaded',
779 function ( $plugin ) {
780 // For check wp_remote call normally of WP
781 if ( ! empty( LP_Request::get_param( 'lp_test_wp_remote' ) ) ) {
782 echo '[TEST_REMOTE]';
783 die;
784 }
785 }
786 );
787
788 // Check require version thim-core on Backend.
789 if ( is_admin() ) {
790 add_action( 'before_thim_core_init', array( $this, 'check_thim_core_version_require' ) );
791 }
792
793 // Save key purchase addon when install via file download from Thimpress.
794 add_action(
795 'upgrader_process_complete',
796 function ( $plugin_upgrader ) {
797 if ( ! empty( $plugin_upgrader->result ) ) {
798 $res = $plugin_upgrader->result;
799 $path_source = $res['destination'] ?? '';
800 if ( empty( $path_source ) ) {
801 return;
802 }
803
804 $key_purchase_path = realpath( $path_source . '/purchase-code.txt' );
805 if ( file_exists( $key_purchase_path ) ) {
806 $purchase_code_content = file_get_contents( $key_purchase_path );
807 if ( empty( $purchase_code_content ) ) {
808 return;
809 }
810
811 $addon_slug = $res['destination_name'] ?? '';
812 if ( empty( $addon_slug ) ) {
813 return;
814 }
815
816 // Call active purchase code for site.
817 LP_Manager_Addons::instance()->active_site( $addon_slug, $purchase_code_content );
818 }
819 }
820 }
821 );
822
823 // Clear cache UserModel when save user.
824 add_action(
825 'wp_update_user',
826 function ( $user_id ) {
827 $user = UserModel::find( $user_id, true );
828 $user->clean_caches();
829 }
830 );
831
832 // For temporary fix issue security of wp comments. Is it error of WP, not LP, LP only call to comments_template function.
833 add_filter(
834 'comments_array',
835 function ( $comments_flat, $post_id ) {
836 // Check if post type is course or item's course (lesson, quiz...)
837 $post_type = get_post_type( $post_id );
838 $course_item_types = CourseModel::item_types_support();
839 $course_item_types[] = LP_COURSE_CPT;
840 if ( ! in_array( $post_type, $course_item_types ) ) {
841 return $comments_flat;
842 }
843
844 foreach ( $comments_flat as $key => $comment ) {
845 $comment->comment_content = wp_kses_post( $comment->comment_content );
846 $comments_flat[ $key ] = $comment;
847 }
848
849 return $comments_flat;
850 },
851 10,
852 2
853 );
854 }
855
856 /**
857 * Add links to Documentation and Extensions in plugin's list of action links
858 *
859 * @param array $links Array of action links
860 *
861 * @return array
862 * @since 4.3.11
863 *
864 */
865 public function plugin_links( array $links ): array {
866 $links[] = sprintf( '<a href="%s">%s</a>', admin_url( 'admin.php?page=learn-press-settings' ), __( 'Settings', 'learnpress' ) );
867 $links[] = sprintf( '<a href="%s" target="_blank">%s</a>', LearnPress::$doc_link, __( 'Documentation', 'learnpress' ) );
868 $links[] = sprintf( '<a href="%s" target="_blank">%s</a>', get_admin_url() . '/admin.php?page=learn-press-addons', __( 'Add-ons', 'learnpress' ) );
869
870 return $links;
871 }
872
873 /**
874 * Trigger this function while activating Learnpress.
875 *
876 * @since 3.0.0
877 * @version 4.1.4.1
878 */
879 public function on_activate() {
880 LP_Install::instance()->on_activate();
881 }
882
883 /**
884 * Trigger this function while deactivating Learnpress.
885 *
886 * $since 3.0.0
887 *
888 * @hook learn_press_deactivate
889 */
890 public function on_deactivate() {
891 do_action( 'learn-press/deactivate', $this );
892 }
893
894 /**
895 * Conditionally bootstrap MCP abilities.
896 *
897 * @return void
898 */
899 public function maybe_init_mcp_abilities() {
900 if ( LP_Settings::get_option( 'enable_mcp_integration', 'no' ) !== 'yes' ) {
901 return;
902 }
903
904 ApiKeyAuthenticator::init();
905 Abilities::init();
906 }
907
908 /**
909 * Handle load text domain for LearnPress.
910 *
911 * @since 4.2.7.4
912 * @version 1.0.1
913 */
914 public function load_plugin_text_domain() {
915 /*$locale = determine_locale();
916 $locale = apply_filters( 'plugin_locale', $locale, 'learnpress' );
917
918 $plugin_translation_path = WP_LANG_DIR . '/plugins/learnpress-' . $locale . '.mo';
919 $custom_translation_path = WP_LANG_DIR . '/learnpress/learnpress-' . $locale . '.mo';
920 if ( is_readable( $custom_translation_path ) ) {
921 unload_textdomain( LP_TEXT_DOMAIN );
922 load_textdomain( LP_TEXT_DOMAIN, $custom_translation_path );
923 load_textdomain( LP_TEXT_DOMAIN, $plugin_translation_path );
924 }*/
925
926 load_plugin_textdomain( LP_TEXT_DOMAIN, false, LP_PLUGIN_FOLDER_NAME . '/languages' );
927 }
928
929 /**
930 * Get instance of class LP_Template.
931 *
932 * @param string $type
933 *
934 * @return LP_Template_Course|LP_Template_Profile|LP_Template_General|LP_Abstract_Template|LP_Template
935 *
936 * @throws Exception
937 * @since 3.3.0
938 */
939 public function template( $type = '' ) {
940 $this->template = LP_Template::instance();
941 $templates = (array) $this->template->get_templates();
942
943 return $templates[ $type ] ?? $this->template;
944 }
945
946 /**
947 * Get session object instance.
948 *
949 * @return mixed
950 */
951 public function get_session() {
952 if ( ! $this->session ) {
953 $this->session = LP_Session_Handler::instance();
954 }
955
956 return $this->session;
957 }
958
959 /**
960 * Get settings object instance.
961 *
962 * @return bool|LP_Settings
963 */
964 public function settings() {
965 return LP_Settings::instance();
966 }
967
968 /**
969 * Get cart object instance for online learning market.
970 *
971 * @return LP_Cart
972 */
973 public function get_cart(): LP_Cart {
974 if ( ! $this->cart ) {
975 $this->cart = LP_Cart::instance();
976 }
977
978 return $this->cart;
979 }
980
981 /**
982 * Get the plugin url.
983 *
984 * @param string $sub_dir
985 *
986 * @return string
987 */
988 public function plugin_url( $sub_dir = '' ) {
989 return LP_PLUGIN_URL . ( $sub_dir ? "{$sub_dir}" : '' );
990 }
991
992 /**
993 * Get the plugin path.
994 *
995 * @param string $sub_dir
996 *
997 * @return string
998 */
999 public function plugin_path( $sub_dir = '' ) {
1000 return LP_PLUGIN_PATH . ( $sub_dir ? "{$sub_dir}" : '' );
1001 }
1002
1003 /**
1004 * Get checkout object instance
1005 *
1006 * @return LP_Checkout
1007 */
1008 public function checkout() {
1009 return LP_Checkout::instance();
1010 }
1011
1012 /**
1013 * Short way to return image file is located in LearnPress directory.
1014 *
1015 * @param string
1016 *
1017 * @return string
1018 */
1019 public function image( $file ) {
1020 if ( ! preg_match( '/.(jpg|png)$/', $file ) ) {
1021 $file .= '.jpg';
1022 }
1023
1024 return $this->plugin_url( "assets/images/{$file}" );
1025 }
1026
1027 /**
1028 * Check require version thim-core
1029 */
1030 public function check_thim_core_version_require() {
1031 // Get thim-core info for LP check .
1032 include_once ABSPATH . 'wp-admin/includes/plugin.php';
1033 $thim_core_info = get_file_data(
1034 WP_PLUGIN_DIR . '/thim-core/thim-core.php',
1035 array(
1036 'Name' => 'Plugin Name',
1037 'Require_LP_Version' => 'Require_LP_Version',
1038 'Version' => 'Version',
1039 )
1040 );
1041
1042 if ( version_compare( $this->thim_core_version_require, $thim_core_info['Version'], '>' ) ) {
1043 deactivate_plugins( 'thim-core/thim-core.php' );
1044
1045 if ( isset( $_GET['activate'] ) ) {
1046 unset( $_GET['activate'] );
1047 }
1048
1049 $message = sprintf(
1050 '%s %s You can download %s. Read guide on %s',
1051 'LP4 require version Thim-core:',
1052 $this->thim_core_version_require,
1053 '<a href="https://thimpresswp.github.io/thim-core/thim-core.zip">latest version</a>',
1054 '<a href="https://docspress.thimpress.com/upgrade-database-how-to-fix-some-issue/">here</a>'
1055 );
1056 ?>
1057 <div class="notice notice-error">
1058 <p><?php echo wp_kses_post( $message ); ?></p>
1059 </div>
1060 <?php
1061 die;
1062 }
1063 }
1064
1065 /**
1066 * Main plugin instance.
1067 *
1068 * @return LearnPress
1069 */
1070 public static function instance() {
1071 if ( is_null( self::$_instance ) ) {
1072 self::$_instance = new self();
1073 }
1074
1075 return self::$_instance;
1076 }
1077 }
1078 }
1079
1080 /**
1081 * Short way to load main instance of plugin
1082 *
1083 * @return LearnPress
1084 * @since 1.0
1085 * @author thimpress
1086 */
1087 function LP() {
1088 return LearnPress::instance();
1089 }
1090
1091 /**
1092 * Done! entry point of the plugin
1093 * Create new instance of LearnPress and put it to global
1094 */
1095 $GLOBALS['LearnPress'] = LearnPress::instance();
1096
1097 // Load template hooks here, before theme add hooks remove.
1098 // Load here because this file call LearnPress::instance(), loop call.
1099 require_once 'inc/lp-template-hooks.php';
1100