<?php
/**
 * Checks is current page belongs to the plugin
 *
 * @see WP_Awesome_Support::isPluginPage()
 * @since 2.0.0
 * @uses $wpas
 * 
 * @param (numeric) Current post ID
 * @return (boolean) True is the page belongs to the plugin
 */
function wpas_is_plugin_page( $post = false ) {

	global $wpas;

	return $wpas->isPluginPage( $post );

}

/**
 * Get the tickets post type slug
 *
 * @see WP_Awesome_Support::getPostTypeSlug()
 * @since 2.0.0
 * @uses $wpas
 * @return (string) Current slug
 */
function wpas_get_slug() {

	return WP_Awesome_Support::getPostTypeSlug();

}

/**
 * Get plugin options
 *
 * This function will return an individual option.
 * 
 * @param  (string) $option  ID of the desired option
 * @param  (mixed) 	$default Fallback that has to be returned if no option found
 * @return (string) Value of the requested option or fallback
 * @since 	1.0.0
 */
function wpas_get_option( $option, $default = false) {

	/* We check if the options have been stored in session to avoid querying the DB */
	if( isset( $_SESSION['wpas_options']['plugin'] ) && !empty( $_SESSION['wpas_options']['plugin'] ) ) {

		/* Set the options var */
		$options = $_SESSION['wpas_options']['plugin'];

	}

	/* If not we query the DB to get the latest settings */
	else {

		/* Set the options var */
		$options = get_option( WPAS_PREFIX.'plugin_options', false );

		/* Make sure it doesn't need to be unserialized */
		$options = maybe_unserialize( $options );

		/* Store the options in session for later requests */
		$_SESSION['wpas_options']['plugin'] = $options;
	}

	/* We check if the requested option is avaiable in the list */
	if( $options && isset( $options[$option] ) ) {

		/* Return the requested option value */
		return $options[$option];

	}

	/* If not we return the default value */
	else {

		return $default;

	}
}

/**
 * Write a log file
 *
 * This function is used for debug purposes and
 * will only work if the log constant is set to true
 *
 * @param (string) Content to write in the log file
 */
function wpas_write_log( $content ) {

	if( !WPAS_LOG )
		return;

	$myFile = WPAS_PATH . 'log.txt';
	$fh 	= fopen($myFile, 'a+') or die("can't open file");

	$stringData = '
	
	'.$content."\n";
	fwrite($fh, $stringData);

	fclose($fh);
}

/**
 * Checks if the user is allowed
 * to attach files to a ticket
 *
 * @return (boolean)
 */
function wpas_can_attach_files() {
	$can = wpas_get_option( 'allow_file_attachment' );
	$ext = wpas_get_option( 'allowed_filetypes' );

	if( $can && $can == 'yes' && $ext ) {
		return true;
	} else {
		return false;
	}
}

/** 
 * Get max allowed filesize for uploads
 * 
 * Get the max size allowed by the user (in the settings)
 * and compare it to the server's max allowed size. If the
 * server's max filesize is lower, then we use it as a limit.
 * If max filesize allowed by the user is higher than the
 * server's limit the plugin bugs.
 *
 * @return (integer) Filesize
 */
function wpas_get_upload_max_size() {

	/* Max allowed by the server  */
	$server_max = ini_get('upload_max_filesize');

	/* We get rid of the unit */
	$server_max = str_replace( 'M', '', $server_max );

	/* Compare max allowed by server to max allowed by user */
	if( $server_max > wpas_get_option('files_size', 2) ) {

		$max_size = wpas_get_option('files_size', 2);

	} else {

		$max_size = $server_max;
		
	}

	return $max_size;
}

/**
 * Check Envato Licence
 *
 * This function will check the validity of
 * an Envato licence. It required cURL to work.
 * 
 * @param  (integer) $pid     Post ID
 * @param  (string)  $license Licence number
 * @return (boolean)          True if the licence is valid
 */
function wpas_verify_envato_purchase( $pid = false, $license = false ) {

	/**
	 * If product ID is given we check for verification status in DB
	 */
	if( $pid ) {

		$verified = get_post_meta( $pid, WPAS_PREFIX . 'envato_purchased', true );

		if( $verified && $verified == 'yes' ) {

			return true;

		} elseif( $verified && $verified == 'no' ) {

			return false;

		}

	}

	/**
	 * Otherwise we check via the API
	 */
	else {
		/* We check if cURL is loaded before running the script */
		if( !in_array('curl', get_loaded_extensions()) )
			return false;

		if( !$license )
			$license  		= get_post_meta( $pid, WPAS_PREFIX.'envato_purchase_license', true );
		$envato_apikey 		= wpas_get_option( 'envato_api_key' );
		$envato_username 	= wpas_get_option( 'envato_username' );
		$license_to_check 	= preg_replace( '/[^a-zA-Z0-9_ -]/s', '', !empty($license) ? $license: '' );

		if( !empty($license_to_check) && !empty($envato_apikey) && !empty($envato_username) ) {

			//Initialize curl
			$ch = curl_init();
			curl_setopt($ch, CURLOPT_URL, 'http://marketplace.envato.com/api/edge/'.$envato_username.'/'.$envato_apikey.'/verify-purchase:'.$license_to_check.'.json');
			curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 5);
			curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
			$ch_data = curl_exec($ch);
			curl_close($ch);
			
			if( !empty($ch_data) ) {
				$json_data = json_decode($ch_data, true);
				if( isset($json_data['verify-purchase']) && count($json_data['verify-purchase']) > 0 ) {

					$dat = array(
						'item_name' 	=> $json_data['verify-purchase']['item_name'],
						'item_id' 		=> $json_data['verify-purchase']['item_id'],
						'item_purchase' => $json_data['verify-purchase']['created_at'],
						'item_licence' 	=> $json_data['verify-purchase']['licence'],
						'item_buyer' 	=> $json_data['verify-purchase']['buyer']
					);

					return $dat;

				} else {
					return false;
				}
			} else {
				return false;
			}
		} else { 
			return false;
		}
	}
}

/**
 * Check if current user can view the ticket
 *
 * The function takes the current user and checks
 * if he can view the ticket based on ticket status
 * and plugin settings.
 * 
 * @param  (integer) $ticket_id Requested ticket ID
 * @return (boolean)            True if user can view the ticket, false otherwise
 */
function wpas_can_view_ticket( $ticket_id ) {
	if( !$ticket_id )
		return false;

	$ticket 	= get_post( $ticket_id );
	$author_id  = $ticket->post_author;

	if( current_user_can('administrator') )
		return true;

	$read 	 = wpas_get_option('ticket_can_read');
	$status  = get_post_meta( $ticket_id, WPAS_PREFIX.'status', true );

	if( is_user_logged_in() ) {
		global $current_user;
		$usr_mail 	  = $current_user->data->user_email;
		$user_id 	  = $current_user->data->ID;

		if( $user_id == $author_id )
			return true;
	}

	switch($read):
		case 'public';
			return true;
		break;
		case 'author';
			if( isset($user_id) && $user_id == $ticket->post_author ) {
				return true;
			}
		break;
		case 'closed';
			/* Get current ticket status */
			$status  = get_the_terms( $ticket_id, 'status' );
			if( $status ) {
				foreach($status as $s) {
					$status = $s->slug;
				}
			}

			if( $status == 'wpas-close' ) {
				return true;
			} else {
				return false;
			}
		break;
		default:
			return false;
		break;
	endswitch;

	if( !$read ) {
		return false;
	}
}

/**
 * Check if current user can reply to the ticket being displayed
 *
 * @param (integer) $ticket_id
 * @return (boolean)
 */
function wpas_can_reply_ticket( $ticket_id ) {

	/* Gimme a post ID! */
	if( !$ticket_id )
		return false;

	$ticket 	= get_post( $ticket_id );
	$author_id  = $ticket->post_author;
	$reply 	 	= wpas_get_option('ticket_can_reply', 'author');

	if( is_user_logged_in() ) {

		global $current_user;

		$usr_mail 	  = $current_user->data->user_email;
		$user_id 	  = $current_user->data->ID;

		/* If the current user is the author then yes */
		if( $user_id == $author_id )
			return true;
	}

	/* Depending on how the plugin is setup */
	switch($reply):

		/* Only the author can reply */
		case 'author';
			if( isset($user_id) && $user_id == $ticket->post_author ) {
				return true;
			}
		break;

		/* Anyone can reply */
		case 'all';
			return true;
		break;

		/* In any other case, no one can reply */
		default;
			return false;
		break;

	endswitch;
}

/**
 * Automatically logs user in
 *
 * This function is triggered after a user successfully registered
 * on the support site. The user will be logged-in using the credentials
 * he just registered.
 * 
 * @param  (integer) $user_id    ID of the user to login
 * @param  (strong)  $user_login Login of user to login
 */
function wpas_user_auto_login( $user_id, $user_login ) {
	if( headers_sent() )
		return;

    if( !is_user_logged_in() ) {
		wp_set_current_user($user_id, $user_login);
		wp_set_auth_cookie($user_id);
    }
}

/**
 * We register a new user to the support.
 * The function will return the native
 * WordPress error messages in case of failure.
 */
function wpas_register_user() {

	$email 		= sanitize_email( $_POST['email'] );
	$username 	= sanitize_text_field( $_POST['username'] );
	$pwd 		= $_POST['pwd'];
	$repeat 	= $_POST['pwd-validate'];

	if( !isset($_POST['user_registration']) || !wp_verify_nonce( $_POST['user_registration'], 'register' ) ) {
		$_SESSION['register']['errors'] = __('Your submission seems to be invalid.', 'wpas');
		return false;
	}

	/**
	 * reCAPTCHA verification
	 */
	$captcha 	= wpas_get_option( 'recaptcha_enabled', 'no' );

	if( 'yes' == $captcha ) {

		/* Include reCAPTCHA lib */
		require_once( WPAS_PATH . 'vendor/recaptcha-php-1.11/recaptchalib.php' );

		$privatekey = wpas_get_option( 'recaptcha_private_key', false );

		$resp = recaptcha_check_answer ($privatekey,
			$_SERVER["REMOTE_ADDR"],
			$_POST["recaptcha_challenge_field"],
			$_POST["recaptcha_response_field"]);

		if( !$resp->is_valid ) {

			$_SESSION['register']['errors'] = sprintf( __('The reCAPTCHA wasn\'t entered correctly. Go back and try it again (reCAPTCHA said: %s).', 'wpas'), $resp->error );
			return false;

		}
	}

	if( $email == '' || $username == '' || $pwd == '' || $repeat == '' ) {
		$_SESSION['register']['errors'] = __('Sorry, it appears that you didn\'t fill all the required fields.', 'wpas');
		return false;
	}

	if( $pwd == '' || $pwd != $repeat ) {
		$_SESSION['register']['errors'] = __('Sorry, the two passwords do not match.', 'wpas');
		return false;
	}

	$usr = array(
		'user_email' => $email,
		'user_login' => $username,
		'user_pass'  => $pwd
	);

	$insert = wp_insert_user( $usr );
	$error 	= false;

	if( !is_wp_error($insert) ) {
		wpas_user_auto_login( $insert, $usr['user_login']);

		$submit = wpas_get_option('ticket_submit');

		if( !headers_sent() ) {
			wp_redirect( add_query_arg( 'message', '0', get_permalink($submit) ), 302 );
			exit;
		}

		$_SESSION['register']['succes'] = true;

		return $insert;
	} else {
		foreach( $insert->errors as $err => $args ) {
			$error = $args[0];
		}

		if( $error )
			$_SESSION['register']['errors'] = $error;

		return false;
	}
}

/**
 * We hook the user registration function early
 * in order to avoid headers issues as we use the
 * wp_redirect function. */
if( isset( $_POST['wpas_registration'] ) )
	add_action('wp_loaded', 'wpas_start_user_registration');

/**
 * Load the user registration function
 */
function wpas_start_user_registration() {
	wpas_register_user();
}

function wpas_validate_option( $options ) {
	return $options;
}

/**
 * Get the original ticket's template
 *
 * The function will look for a custom template in the theme folder and if no file is found, the default template will be loaded from the plugin directory instead
 *
 * @param (string) $base  The template base
 * @param (string) $tpl   The template name
 * @param (mixed)  $param Additional parameters
 */
function wpas_get_template_part( $base = 'part', $tpl = false, $param = false ) {

	if( !$tpl )
		return;

	/* Get theme name */
	$theme = get_stylesheet();

	/* Theme URI */
	$uri = STYLESHEETPATH;

	/* Pre-built template URI */
	$ready 	= WPAS_PATH . 'templates/' . $theme . '/' . $base . '-' . $tpl . '.php';

	/* User custom template */
	if( file_exists( "$uri/$base-$tpl.php" ) )
		include( "$uri/$base-$tpl.php" );

	/* Pre-Built template */
	elseif( file_exists( $ready ) )
		include( $ready );

	/* Default template */
	else
		include( WPAS_PATH . "templates/$base-$tpl.php" );

}

/**
 * Get file uploader markup
 *
 * @since 2.0.0
 */
function wpas_file_uploader() {

	global $wpas_submit;

	$uploader = wpas_get_option( 'upload_script', 'fineuploader' );

	switch( $uploader ):

		case 'fineuploader':

			?>
			<div class="form-group wpas_attachements">
				<div id="wpas_fileupload"></div>
				<div id="wpas_fileuploaded"></div>
			</div>
			<?php
			if( isset( $_SESSION['formtmp']['attachments'] ) && '' != $_SESSION['formtmp']['filenames'] ) {

				/* We make sure we have the same number of files and filenames */
				if( count( $_SESSION['formtmp']['attachments'] ) == count( $_SESSION['formtmp']['filenames'] ) ) {

					/* Associate file with its name */
					foreach( $_SESSION['formtmp']['attachments'] as $key => $attch ) {

						?><li class="list-group-item"><a href="<?php echo $attch; ?>" target="_blank"><?php echo $_SESSION['formtmp']['filenames'][$key]; ?></a></li><?php

					}

				}
			}

		break;

		case 'filepicker':

			$api = wpas_get_option( 'filepicker_api', false );

			if( !$api ):
				
				echo 'No API key given for Filepicker';

			else: ?>

				<div class="form-group">

					<?php
					/* Don't display the upload button if files have been uploaded before a submission failure */
					if( !isset( $_SESSION['formtmp']['attachments'] ) || '' == $_SESSION['formtmp']['attachments'] ): ?>

						<label for="wpas-attachments" class="sr-only"><?php _e( 'File Upload', 'wpas' ); ?></label>
						<button class="btn btn-default filepicker" type="button"><i class="glyphicon glyphicon-plus-sign" aria-hidden="true"></i> <?php _e( 'Browse files', 'wpas' ); ?></button>

					<?php endif; ?>

					<input id="wpas-attachments" name="attachments" type="hidden" value="<?php echo $wpas_submit->populate_fields_values( 'attachments' ); ?>">
				</div>

				<ul class="list-group wpas-attachments-list">
					<?php
					if( isset( $_SESSION['formtmp']['attachments'] ) && '' != $_SESSION['formtmp']['attachments'] ):

						$attachments = json_decode( urldecode( $_SESSION['formtmp']['attachments'] ) );

						if( !empty( $attachments ) ) {

							/* We'll save all attachments in this array */
							$files = array();

							foreach( $attachments as $key => $attachment ) {

								?><li class="list-group-item"><a href="<?php echo $attachment->url; ?>" target="_blank"><?php echo $attachment->filename; ?></a> <span class="badge"><?php echo ceil( $attachment->size/1024 ); ?> KB</span></li><?php

							}

						}

					endif;
					?>
				</ul>
				<?php
			endif;

		break;

	endswitch;

	$authorized = wpas_get_option( 'allowed_filetypes' );
	$authorized = explode( ',', $authorized );
	$allowed 	= array();

	foreach( $authorized as $auth ) {

		array_push( $allowed, "<span>$auth</span>");

	}

	if( 'yes' == wpas_get_option( 'show_upload_limitations', 'no' ) ): ?>
		<div class="wpas-attachments-meta"><?php printf( __( 'Upload max %s and only the following file types: %s', 'wpas' ), '<strong>' . wpas_get_upload_max_size() . ' Mb</strong>', implode( ', ', $allowed ) ); ?></div><?php
	endif;

}

/**
 * Get uploaded files URLs
 *
 * The function gets all files uploaded with the current ticket or reply and gets the correct URL.
 *
 * The plugin supports Fineuploader and Ink Filepicker. The first one saves uploads locally, the other remotely. Moreover,
 * if the user enables the extra security layer with Filepicker by activating the secret, we need to generate a policy and
 * a signature for uploads and viewing the images.
 * 
 * @param  (integer) $post_id IF of the post to retrieve attachments for
 * @param  (array)  $args    Additional parameters
 * @since 2.0.0
 */
function wpas_get_uploaded_files( $post_id, $args = array() ) {

	/* Default values */
	$default = array(
		'link_before' => '<li>',
		'link_after'  => '</li>',
		'link_target' => '_blank'
	);

	extract( shortcode_atts( $default, $args ) );

	/* Get the post attachments */
	$attachments = get_post_meta( $post_id, WPAS_PREFIX . 'attachments', true );

	if( $attachments != '' && is_array( $attachments ) ) {

		foreach( $attachments as $attach => $values ) {

			/* If Fineuploader is used, the attachements are stored locally. No much URL process to do */
			if( !isset( $values['uploader'] ) || 'fineuploader' == $values['uploader'] ) {

				$url = WP_CONTENT_URL . '/uploads/wpas_attachments/' . $values['file'];

			}

			/**
			 * If the user uses Ink Filepicker, we need to prepare the URL to the remote file
			 */
			elseif( 'filepicker' == $values['uploader'] ) {

				$file 		= explode( '/', $values['file'] );					// Get file handle
				$secret 	= wpas_get_option( 'filepicker_secret', false );	// Get Filepicker Secret

				/**
				 * If a secret is set, we need to generate a policy and a signature for it. We then append those 2 params to the URL
				 */
				if( $secret ) {

					$policy 	= base64_encode( json_encode( array( 'handle' => $file[count($file)-1], 'expiry' => strtotime( '+60 minutes' ), 'call' => array( 'read' ) ) ) );
					$signature  = hash_hmac( 'sha256', $policy, $secret );
					$url 		= $values['file'] . '?signature=' . $signature . '&amp;policy=' . $policy;

				} else {
					$url = $values['file'];
				}

			}

			/* Echo the final attachment URL */
			echo $link_before; ?><a href="<?php echo $url; ?>" target="<?php echo $link_target; ?>"><?php echo $values['filename']; ?></a><?php echo $link_after;
		}

	}

}

/**
 * Get reCAPTCHA challenge
 *
 * This function will call the reCAPTCHA API and display the challenge to avoid spammy registrations.
 * 
 * @return (string) HTML Markup
 * @since 2.0.0
 */
function wpas_get_captcha() {

	$captcha 	= wpas_get_option( 'recaptcha_enabled', 'no' );

	if( 'no' == $captcha )
		return;

	$publickey 	= wpas_get_option( 'recaptcha_public_key', false );

	echo '<div class="form-group">';

	if( 'disable' == wpas_get_option( 'plugin_style' ) ) {

		require_once( WPAS_PATH . 'vendor/recaptcha-php-1.11/recaptchalib.php' );

		return recaptcha_get_html( $publickey );

	} else {

		?>
		<div id="wpas-recaptcha" style="display:none"><div id="recaptcha_image"></div><div class="form-group"><span class="recaptcha_only_if_image"><?php _e( 'Enter the words above:', 'wpas' ); ?></span><span class="recaptcha_only_if_audio"><?php _e( 'Enter the numbers you hear:', 'wpas' ); ?></span><input class="form-control" type="text" id="recaptcha_response_field" name="recaptcha_response_field" /></div><div class="btn-group"><a href="javascript:Recaptcha.reload()" title="<?php _e( 'Get another CAPTCHA', 'wpas' ); ?>" class="btn btn-default btn-sm"><span aria-hidden="true" class="glyphicon glyphicon-refresh"></span></a><a href="javascript:Recaptcha.switch_type('audio')" title="<?php _e( 'Get an audio CAPTCHA', 'wpas' ); ?>" class="recaptcha_only_if_image btn btn-default btn-sm"><span aria-hidden="true" class="glyphicon glyphicon-volume-up"></span></a><a href="javascript:Recaptcha.switch_type('image')" title="<?php _e( 'Get an image CAPTCHA', 'wpas' ); ?>" class="recaptcha_only_if_audio btn btn-default btn-sm"><span aria-hidden="true" class="glyphicon glyphicon-picture"></span></a><a href="javascript:Recaptcha.showhelp()" title="<?php _e( 'Help', 'wpas' ); ?>" class="btn btn-default btn-sm"><span aria-hidden="true" class="glyphicon glyphicon-question-sign"></span></a></div></div>

		<script type="text/javascript" src="//www.google.com/recaptcha/api/challenge?k=<?php echo $publickey; ?>"></script>
		<noscript>
			<iframe src="//www.google.com/recaptcha/api/noscript?k=<?php echo $publickey; ?>"
			height="300" width="500" frameborder="0"></iframe><br>
			<textarea name="recaptcha_challenge_field" rows="3" cols="40">
			</textarea>
			<input type="hidden" name="recaptcha_response_field"
			value="manual_challenge">
		</noscript>
		<?php

	}

	echo '</div>';

}