Limit user on CoursePress Pro.

Is it possible or any workaround on this:

Once they finish the online training and get their certificate or if 6 months have passed since first registered (whichever comes first) you should be locked out and not be able to log back into the training center again or be able to see other website content from trying to log in to the training center.
This is a continues course with no start and end date. but we need to be able to give lockouts for individual students after this time frame based on when they signed up.

  • Panos

    Hi carl ,

    You could try the following snippet for that :

    add_action( 'coursepress_student_enrolled', function( $student_id, $course_id ){
    
    	$_student_enrollments = get_user_meta( $student_id, '_cp_student_enrollments', true );
    	if ( ! is_array( $_student_enrollments ) ) {
    		$_student_enrollments = array();
    	}
    
    	$_student_enrollments[$course_id] = time();
    	update_user_meta( $student_id, '_cp_student_enrollments', $_student_enrollments );
    
    }, 20, 2 );
    
    // Set the cron by visiting : http://site.com/wp-admin/tools.php?_cp_schedule_enrollment_expire=yes
    add_action( 'load-tools.php', function(){
    
    	if ( ! isset( $_GET['_cp_schedule_enrollment_expire'] ) || 'yes' != $_GET['_cp_schedule_enrollment_expire'] ) {
    		return;
    	}
    
    	if (! wp_next_scheduled ( '_cp_schedule_enrollment_expire' )) {
    		wp_schedule_event( time(), 'daily', '_cp_schedule_enrollment_expire' );
        }
    
    } );
    
    add_action ( '_cp_schedule_enrollment_expire', function(){
    
    	$allowed_diff = 6; // Months
    	$course_id = 122;
    
    	$student_ids = CoursePress_Data_Course::get_student_ids( $course_id );
    
    	foreach ( $student_ids as $student_id ) {
    
    		$_student_enrollments = get_user_meta( $student_id, '_cp_student_enrollments', true );
    
    		 if ( empty( $_student_enrollments ) || ! isset( $_student_enrollments[$course_id] ) ) {
    		 	continue;
    		 }
    
    		$date_current 	= new DateTime( date( 'Y-m-d' ) );
    		$date_enrolled 	= new DateTime( date( 'Y-m-d', (int) $_student_enrollments[$course_id] ) );
    
    		$diff = $date_current->diff( $date_enrolled );
    
    		if ( ( ( $diff->format('%y') * 12 ) + $diff->format('%m') ) >= $allowed_diff ) {
    			CoursePress_Data_Course::withdraw_student( $student_id, $course_id );
    		}
    	}
    
    } );

    You can add the above snippet in a mu-plugin. In case you are not familiar with them, they are simple php files which are located in your wp-content/mu-plugins folder. If that folder doesn't exist you can simply create it. You can read more about mu-plugins here :
    https://premium.wpmudev.org/manuals/wpmu-manual-2/using-mu-plugins/

    The snippet uses a WP daily schedule that checks the enrollment date of the students on the course, once each day. If 6 months have past since enrollment day, it would remove them from the course.

    I would strongly recommend to first test this snippet in a mu-plugin and then move it to your production site.

    In order to test, first you need to activate the cron job. You can simply go to:
    http://site.com/wp-admin/tools.php?_cp_schedule_enrollment_expire=yes
    and the cron will be activated. You can also install a plugin to manage cron jobs, like WP Crontrol

    If you install Crontrol plugin, you should see the _cp_schedule_enrollment_expire in the Hook Name in admin > Tools > Cron Events

    Then you need to confirm that the dates are working fine on your site too. For that, you can add /enroll a few test users (even from admin > Course > Students page) with different enrollment dates. To use different dates, before enrolling the user, change the line :
    $_student_enrollments[$course_id] = time();
    to
    $_student_enrollments[$course_id] = strtotime("10 August 2017");
    etc

    Make sure you have various date and that you note which date is for which user.

    Now that you have a list of students with different enrollment dates, you can trigger that cron job (so you don't have to wait) with the help of the Crontrol plugin from
    admin > Tools > Cron Events
    Search for _cp_schedule_enrollment_expire using browser search (ctrl + f)
    Then click "Run" as in the following screenshot:

    Once page has refreshed check if the proper students have been removed from course.

    I hope I explained those steps clearly but please let us know if you have any difficulties there as I might be unclear in some parts :slight_smile:

    Kind regards!

  • Emanaku

    Thank you, Panos, for this explanation!
    We have basically the same problem. But we have some details different:
    - For all courses all users can be active a maximum of 6 months.
    - Some courses have another timing in the title (e.g. "Labor Law - 3 months")
    So my questions about your snippet are:
    1. How can I loop through all courses (not only examining the students of course 122, as in your snippet)?
    2. How can I read the title of the course (so I can use the title of the course to determine how much time the user is allowed in the course)?
    Thank you for all your support!

  • Emanaku

    Ok, answering my own questions :wink:
    1. Loop through all courses:

    $courses = get_posts( 'post_type=' . CoursePress_Data_Course::get_post_type_name() );
    			foreach ( $courses as $course ) {
    
    				$course_id = (int) $course->ID;
    ....

    2. Read the title of a course:
    $course_title = $course->post_title;

    In our case course titles begin with sth like xx3M, xx is a code for the type of course, and the 3M means "for 3 months" (or 1M or 6M etc.). With this information I adjust the "$allowed_diff", instead of using one time span for all courses.

    Still I am searching for an easy way to tell the student, how many days are left for him/her.

    The solution in this thread: https://premium.wpmudev.org/forums/topic/coursepress-pro-coursepress-subscriptions (also aimed at general subscriptions) could also be used, but seems to create a gigantic overhead, if you only want time restrict your users and nothing else.

    • Panos

      Great Emanaku ,

      I would suggest to use a custom meta field for each course, which would contain the number of months. You could use that in both, the script for withdrawing and for notifying about the time left for each student.

      If you agree with that I could provide some snippet for that. Not sure where you would like to inform user about days remaining, perhaps the dashboard would be a good place.

      Kind regards!

      • Emanaku

        Hi Panos,
        thank you for your kind offer.
        Basically two fields would be needed, because we have also courses with a time span of some days (e.g. 3 days, 7 days).
        So e.g. tunit (is "m" for month or "d" for days) and
        tamount (number of months or days the course should be accessible.)
        Alternatively one field would be enough, when used for a notation like "3D", "1M", "6M" etc.
        The dashboard is a good starting point. This is the original dashboard in our system (sorry, all in German):

        And this is how it could be (I used an english headline):

        Any support is greatly welcome!

  • Panos

    Hey carl and Emanaku !

    In order to add the expire date in the Dashboard column, I had to repeat two functions and the code got pretty long. So instead of pasting it here I added it in gist, so you can download it from here :
    https://gist.github.com/wpmudev-sls/c37112707bb3003ffb0f12dfe2ff1fbf

    For each course you should see 2 new meta fields. One to select days or months, and the second one to choose the amount.

    As the above, it adds a daily cron. You need to visit the same url again to register:
    http://site.com/wp-admin/tools.php?_cp_schedule_enrollment_expire=yes
    It will loop through courses and withdraw any expired student

    It adds the expiration date in a new column in the dashboard.

    It has a shortcode to show the expiration date in any page:
    [cp_enrollment_expire course_id="122" student_id="56" format="d M Y"]
    If format is not set it will use the date and time format used in WordPress settings.
    If course id is not used, it will try to use the current post id
    if student is not set, it will try use the current user id

    Again please do some good testing before adding this to your production site. Please keep in mind that this exceeds the scope of our support, so it can't be supported. If it something quick and simple then we would love to help out, but for further customization you would need to hire a developer.

    Hope this helps :slight_smile:

    Kind regards!

Thank NAME, for their help.

Let NAME know exactly why they deserved these points.

Gift a custom amount of points.