General tab add_action( 'woocommerce_product_options_general_product_data', array( $self, 'academy_courses_linked_with_woo_product' ), 10, 2 ); // Save product with courses add_action( 'woocommerce_admin_process_product_object', array( $self, 'save_academy_courses_meta' ) ); } public function add_store_dashboard_menu( $menu ) { if ( function_exists( 'wc_get_page_permalink' ) && \Academy\Helper::get_settings( 'store_link_inside_frontend_dashboard', true ) ) { $menu['store-dashboard'] = array( 'label' => \Academy\Helper::get_settings( 'store_link_label_inside_frontend_dashboard', __( 'Store Dashboard', 'academy' ) ), 'area' => 'learning', 'icon' => 'academy-icon academy-icon--calender', 'permalink' => wc_get_page_permalink( 'myaccount' ), 'public' => true, 'priority' => 27, ); } return $menu; } public function create_course_order_from_admin( $order_id ) { if ( ! is_admin() ) { return; } $order = wc_get_order( $order_id ); if ( ! $order ) { return; } $customer_id = $order->get_customer_id(); if ( ! $customer_id ) { $customer_id = $this->create_user_by_order_details( $order ); } foreach ( $order->get_items() as $item ) { $product_id = $item->get_product_id(); $if_has_course = \Academy\Helper::product_belongs_with_course( $product_id ); if ( $if_has_course ) { $course_id = $if_has_course->post_id; \Academy\Helper::do_enroll( $course_id, $customer_id, $order_id ); } } } public function enrolled_courses_status_change( $order_id, $status_from, $status_to ) { global $wpdb; $order = wc_get_order( $order_id ); /* Group PLUS : ignore if purchase mode: team */ foreach ( $order->get_items() as $item_id => $item ) { // check if academy group info present as line item meta if ( ! empty( $item->get_meta( 'academy_group' ) ) ) { return; } } /* Group PLUS : END */ $course_enrolled_by_order = \Academy\Helper::get_course_enrolled_ids_by_order_id( $order_id ); if ( $course_enrolled_by_order && is_array( $course_enrolled_by_order ) && count( $course_enrolled_by_order ) ) { foreach ( $course_enrolled_by_order as $enrolled_info ) { if ( ! is_admin() && self::is_order_will_be_automatically_completed( $order_id ) ) { $status_to = 'completed'; self::order_mark_as_completed( $order_id ); } // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching $wpdb->update( $wpdb->posts, array( 'post_status' => $status_to ), array( 'ID' => $enrolled_info['enrolled_id'] ) ); if ( 'completed' === $status_to ) { $enrolled_user_id = get_post_field( 'post_author', $enrolled_info['enrolled_id'] ); do_action( 'academy/course/after_enroll', $enrolled_info['course_id'], $enrolled_info['enrolled_id'], $enrolled_user_id ); } } } elseif ( $order ) { $order_status = \Academy\Helper::get_settings( 'woo_order_auto_complete_status' ) ?? [ 'on-hold', 'pending', 'processing', 'completed' ]; $items = $order->get_items(); foreach ( $items as $item ) { $product_id = $item->get_product_id(); $has_course = \Academy\Helper::product_belongs_with_course( $product_id ); if ( $has_course ) { if ( $order && in_array( $order->get_status(), $order_status, true ) ) { $customer_id = $order->get_customer_id(); if ( ! $customer_id ) { $customer_id = $this->create_user_by_order_details( $order ); } $course_id = $has_course->post_id; $course_attach_product_id = $has_course->meta_value; if ( $course_id && $course_attach_product_id ) { $enroll_id = \Academy\Helper::do_enroll( $course_id, $customer_id, $order_id ); // make order auto complete if ( ! is_admin() && self::is_order_will_be_automatically_completed( $order_id ) ) { $status_to = 'completed'; self::order_mark_as_completed( $order_id ); } // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching $wpdb->update( $wpdb->posts, array( 'post_status' => $status_to ), array( 'ID' => $enroll_id ) ); if ( 'completed' === $status_to ) { $enrolled_user_id = get_post_field( 'post_author', $enroll_id ); do_action( 'academy/course/after_enroll', $course_id, $enroll_id, $enrolled_user_id ); } } }//end if }//end if }//end foreach }//end if } public function add_academy_type_in_wc_product( $types ) { $types['academy_product'] = array( 'id' => '_academy_product', 'wrapper_class' => 'show_if_simple', 'label' => __( 'For Academy LMS', 'academy' ), 'description' => __( 'This checkmark ensure that you will sell a specific course via this product.', 'academy' ), 'default' => 'no', ); return $types; } public function save_wc_product_meta( $post_ID ) { // Only the product edit screen posts this checkbox. Any other save (quick edit, // REST, bulk edit) must leave the flag alone rather than read "unchecked". if ( ! isset( $_POST['woocommerce_meta_nonce'] ) || ! wp_verify_nonce( sanitize_key( wp_unslash( $_POST['woocommerce_meta_nonce'] ) ), 'woocommerce_save_data' ) ) { return; } $is_academy_product = isset( $_POST['_academy_product'] ) ? sanitize_text_field( wp_unslash( $_POST['_academy_product'] ) ) : ''; if ( 'on' === $is_academy_product ) { update_post_meta( $post_ID, '_academy_product', 'yes' ); } else { delete_post_meta( $post_ID, '_academy_product' ); } } public function update_product_meta( $post ) { $product_id = (int) get_post_meta( $post->ID, 'academy_course_product_id', true ); if ( $product_id ) { update_post_meta( $product_id, '_virtual', 'yes' ); update_post_meta( $product_id, '_academy_product', 'yes' ); } } public function remove_course_product_from_shop( $wp_query ) { $wp_query->set( 'meta_query', array( array( 'key' => '_academy_product', 'compare' => 'NOT EXISTS', ), ) ); return $wp_query; } public function save_earning_data( $item_id, $item, $order_id ) { $is_enabled_earning = (bool) \Academy\Helper::get_settings( 'is_enabled_earning' ); if ( ! \Academy\Helper::get_addon_active_status( 'multi_instructor' ) || ! $is_enabled_earning ) { return; } $item = new \WC_Order_Item_Product( $item ); $product_id = $item->get_product_id(); $course = \Academy\Helper::product_belongs_with_course( $product_id ); if ( $course ) { \Academy\Helper::save_instructor_earnings( $course->post_id, $item, $order_id ); }//end if } public function save_earning_data_status_change( $order_id, $status_from, $status_to ) { $is_enabled_earning = (bool) \Academy\Helper::get_settings( 'is_enabled_earning' ); if ( ! \Academy\Helper::get_addon_active_status( 'multi_instructor' ) || ! $is_enabled_earning ) { return; } if ( ! get_post_meta( $order_id, 'is_academy_order_for_course', true ) ) { return; } if ( ! is_admin() && self::is_order_will_be_automatically_completed( $order_id ) ) { $status_to = 'completed'; self::order_mark_as_completed( $order_id ); } if ( count( self::get_earning_by_order_id( $order_id ) ) ) { self::update_earning_status_by_order_id( $order_id, $status_to ); } } public function add_frontend_dashboard_menu_item( $menu_links ) { $allow_fontend_dashbaord = (bool) \Academy\Helper::get_settings( 'is_enabled_fd_link_inside_woo_dashboard' ); $fontend_dashbaord_label = (string) \Academy\Helper::get_settings( 'store_link_label_inside_frontend_dashboard' ); if ( ! $allow_fontend_dashbaord || empty( $fontend_dashbaord_label ) ) { return $menu_links; } $menu = []; foreach ( $menu_links as $key => $value ) { $menu[ $key ] = $value; if ( 'dashboard' === $key ) { $menu['academy_frontend_dashboard'] = esc_html( $fontend_dashbaord_label ); } } return $menu; } public function set_frontend_dashboard_menu_item_url( $url, $endpoint ) { if ( 'academy_frontend_dashboard' === $endpoint ) { return esc_url( \Academy\Helper::get_page_permalink( 'frontend_dashboard_page' ) ); } return $url; } public function add_frontend_dashboard_menu_link( $order_id ) { $allow_fontend_dashbaord = (bool) \Academy\Helper::get_settings( 'is_enabled_fd_link_inside_woo_order_page' ); $fontend_dashbaord_label = (string) \Academy\Helper::get_settings( 'woo_order_page_fd_link_label' ); if ( ! $allow_fontend_dashbaord || empty( $fontend_dashbaord_label ) ) { return; } $product_id = 0; $order = new \WC_Order( $order_id ); $items = $order->get_items(); foreach ( $items as $item ) { if ( isset( $item['product_id'] ) && ! empty( $item['product_id'] ) ) { $product_id = $item['product_id']; break; } } if ( 'yes' === get_post_meta( $product_id, '_academy_product', true ) ) { ?>
get_data() : array(); $payment_method = isset( $order_data['payment_method'] ) ? $order_data['payment_method'] : ''; if ( $enable_woo_order_auto_complete ) { return true; } return false; } public static function order_mark_as_completed( $order_id ) { global $wpdb; if ( 'yes' === get_option( 'woocommerce_custom_orders_table_enabled' ) ) { // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching $is_update = $wpdb->update( "{$wpdb->prefix}wc_orders", array( 'status' => 'wc-completed' ), array( 'ID' => $order_id ) ); } else { // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching $is_update = $wpdb->update( $wpdb->posts, array( 'post_status' => 'wc-completed' ), array( 'ID' => $order_id ) ); } return $is_update; } public static function create_user_by_order_details( $order ) { // Create a new user $billing_address = $order->get_address( 'billing' ); $password = wp_generate_password(); $email = $billing_address['email']; $username = strstr( $email, '@', true ); // Generate a unique username $user_id = wp_create_user( $username, $password, $email ); // Send the new user notification email wp_new_user_notification( $user_id, null, 'both' ); // Log in the user $user = get_user_by( 'id', $user_id ); if ( $user ) { wp_set_current_user( $user_id, $user->user_login ); wp_set_auth_cookie( $user_id ); } // Set the created user ID as the customer ID in the order object $order->set_customer_id( $user_id ); $order->save(); return $user_id; } public function add_course_price( $response, $post, $request ) { if ( 'paid' === \Academy\Helper::get_course_type( $post->ID ) ) { $product_id = get_post_meta( $post->ID, 'academy_course_product_id', true ); if ( ! $product_id ) { return $response; } $symbol = function_exists( 'get_woocommerce_currency_symbol' ) ? html_entity_decode( get_woocommerce_currency_symbol(), ENT_HTML5, 'UTF-8' ) : ''; $prices = []; $regular_price = get_post_meta( $product_id, '_regular_price', true ); $sale_price = get_post_meta( $product_id, '_sale_price', true ); if ( $regular_price ) { $prices[] = $symbol . number_format( $regular_price, 2 ); } if ( $sale_price ) { $prices[] = $symbol . number_format( $sale_price, 2 ); } if ( count( $prices ) ) { $response->data['academy_course_price'] = implode( '|', $prices ); $response->data['meta']['academy_ecommerce_engine'] = 'woocommerce'; } }//end if return $response; } public function academy_woo_order_delete( $order_id, $order ) { // Check if the order is an academy order if ( empty( get_post_meta( $order_id, 'is_academy_order_for_course', true ) ) ) { return; } if ( ! $order_id ) { return; } // Retrieve enrollment info $enrolled_info = \Academy\Helper::get_course_enrolled_ids_by_order_id( $order_id ); if ( empty( $enrolled_info ) ) { return; } $info = reset( $enrolled_info ); $enrolled_post = get_post( $info['enrolled_id'] ); if ( ! $enrolled_post ) { return; } // Cancel course enrollment wp_delete_post( $info['enrolled_id'] ); delete_post_meta( $order_id, 'is_academy_order_for_course' ); delete_post_meta( $order_id, 'academy_order_for_course_id_' . $info['course_id'] ); delete_user_meta( $enrolled_post->post_author, 'academy_course_' . $info['course_id'] . '_completed_topics' ); } public function academy_courses_linked_with_woo_product() { // phpcs:disable WordPressVIPMinimum.Performance.NoPaging.posts_per_page_posts_per_page -- needs the complete (small, bounded) set $courses = get_posts( [ 'post_type' => 'academy_courses', 'posts_per_page' => -1, 'post_status' => 'publish' ] ); // phpcs:enable WordPressVIPMinimum.Performance.NoPaging.posts_per_page_posts_per_page if ( $courses ) { woocommerce_wp_select( [ 'id' => '_linked_academy_courses', 'label' => __( 'Linked Academy Courses', 'academy' ), 'options' => wp_list_pluck( $courses, 'post_title', 'ID' ), 'desc_tip' => true, 'description' => __( 'Select a course to link with this product.', 'academy' ), ] ); } } public function save_academy_courses_meta( $product ) { if ( empty( $_POST['_linked_academy_courses'] ) ) {// phpcs:ignore WordPress.Security.NonceVerification.Missing return; } $course_id = absint( wp_unslash( $_POST['_linked_academy_courses'] ) );// phpcs:ignore WordPress.Security.NonceVerification.Missing $product_id = absint( $product->get_id() ); if ( ! empty( $_POST['_academy_product'] ) ) {// phpcs:ignore WordPress.Security.NonceVerification.Missing // Paid course $product->update_meta_data( '_linked_academy_courses', $course_id ); update_post_meta( $course_id, 'academy_course_product_id', $product_id ); update_post_meta( $course_id, 'academy_course_type', 'paid' ); } else { // Free course update_post_meta( $course_id, 'academy_course_product_id', 0 ); update_post_meta( $course_id, 'academy_course_type', 'free' ); } } }