<?php
session_start();
require_once("../config/database.php");
require_once("lib.php");
require_once("lti.php");
require 'vendor/autoload.php'; // Include the JWT library

$lti = new LTI();

$scope = $_REQUEST['scope'];
$responsetype = $_REQUEST['response_type'];
$clientid = $_REQUEST['client_id'];
$redirecturi = $_REQUEST['redirect_uri'];
$loginhint = $_REQUEST['login_hint'];
$ltimessagehintenc = $_REQUEST['lti_message_hint'];
$state = $_REQUEST['state'];
$responsemode = $_REQUEST['response_mode'];
$nonce = $_REQUEST['nonce'];
$prompt = $_REQUEST['prompt'];

$config = array();
$user = new \stdClass();
$company = new \stdClass();
$type = new \stdClass();

$ok = !empty($scope) && !empty($responsetype) && !empty($clientid) &&
        !empty($redirecturi) && !empty($loginhint) &&
        !empty($nonce);

if (!$ok) {
    $error = 'invalid_request';
}
$ltimessagehint = json_decode($ltimessagehintenc);

$ok = $ok && isset($ltimessagehint->launchid);

if (!$ok) {
    $error = 'invalid_request';
    $desc = 'No launch id in LTI hint';
}
if ($ok && ($scope !== 'openid')) {
    $ok = false;
    $error = 'invalid_scope';
}
if ($ok && ($responsetype !== 'id_token')) {
    $ok = false;
    $error = 'unsupported_response_type';
}
$uid = 0;
if ($ok) {
    $launchid = $ltimessagehint->launchid;
    $SESSION = $_SESSION[$launchid];
    list($uid, $courseid, $comp_id, $typeid, $contentdtl_id, $offering_id, $messagetype, $foruserid, $titleb64, $textb64) = explode(',', $SESSION->$launchid, 10);
    unset($_SESSION[$launchid]);
    try {
        //Fetch User details
        $user_data = $lti->get_user_details($uid);
        if ($result = $user_data->fetch(PDO::FETCH_ASSOC)) {
            $user->user_id = $result['user_id'];
            $user->first_name = $result['first_name'];
            $user->last_name = $result['last_name'];
            $user->mobile_no = $result['mobile_no'];
            $user->email_id = $result['email_id'];
            $user->username = $result['login_id'];
        }

        //Fetch company details
        $lti_company_data = $lti->get_company_details($comp_id);
        if ($result = $lti_company_data->fetch(PDO::FETCH_ASSOC)) {
            $company->company_id = $result['company_id'];
            $company->company_code = $result['company_code'];
            $company->company_name = $result['name'];
            $company->private_key = $result['private_key'];
            $company->kid = $result['kid'];
        }

        //Fetch LTI Types
        $stmt = $lti->get_lti_types_from_clientId($clientid);
        if ($result = $stmt->fetch(PDO::FETCH_ASSOC)) {
            $type->lti_typename = $result['tool_name'];
            $type->typeid = $result['lti_types_id'];
            $type->lti_toolurl = $result['tool_url'];
            $type->lti_ltiversion = $result['lti_version'];
            $type->lti_clientid = $result['client_id'];
            $type->toolproxyid = $result['tool_proxy_id'];
            $type->lti_parameters = $result['parameter'];
        }

        //Fetch LTI Types Config
        $stmt = $lti->get_lti_types_config($type->typeid);
        // fetch values
        while ($result = $stmt->fetch(PDO::FETCH_ASSOC)) {
            $config[$result['name']] = $result['value'];
        }

        if (isset($config['publickeyset'])) {
            $type->lti_publickeyset = $config['publickeyset'];
        }
        if (isset($config['keytype'])) {
            $type->lti_keytype = $config['keytype'];
        }
        if (isset($config['initiatelogin'])) {
            $type->lti_initiatelogin = $config['initiatelogin'];
        }
        if (isset($config['sendname'])) {
            $type->lti_sendname = $config['sendname'];
        }
        if (isset($config['send_email_id'])) {
            $type->lti_sendemailaddr = $config['send_email_id'];
        }
        if (isset($config['accept_grades'])) {
            $type->lti_acceptgrades = $config['accept_grades'];
        }
        if (isset($config['customparameters'])) {
            $type->lti_customparameters = $config['customparameters'];
        }
        if (isset($config['launchcontainer'])) {
            $type->lti_launchcontainer = $config['launchcontainer'];
        }
        if (isset($config['content_item_selection_request'])) {
            $type->lti_toolurl_ContentItemSelectionRequest = $config['content_item_selection_request'];
        }
        if (isset($config['lti_service_grade_synchronization'])) {
            $type->ltiservice_gradesynchronization = $config['lti_service_grade_synchronization'];
        }
        // Get the parameters from the LTI services.
        foreach ($config as $name => $value) {
            if (strpos($name, 'ltiservice_') === 0) {
                $type->{$name} = $config[$name];
            }
        }
    } catch (PDOException $e) {
        error_log("Caught $e");
    }

    $ok = ($clientid === $type->lti_clientid);
    if (!$ok) {
        $error = 'unauthorized_client';
    }
}
if ($ok && ($loginhint !== $uid)) {
    $ok = false;
    $error = 'access_denied';
}
// If we're unable to load up config; we cannot trust the redirect uri for POSTing to.
if (empty($config)) {
    $error = 'invalidrequest';
}
if ($ok) {
    if (isset($responsemode)) {
        $ok = ($responsemode === 'form_post');
        if (!$ok) {
            $error = 'invalid_request';
            $desc = 'Invalid response_mode';
        }
    } else {
        $ok = false;
        $error = 'invalid_request';
        $desc = 'Missing response_mode';
    }
}
if ($ok && !empty($prompt) && ($prompt !== 'none')) {
    $ok = false;
    $error = 'invalid_request';
    $desc = 'Invalid prompt';
}
if ($ok) {

    if (!empty($contentdtl_id)) {
        $content_details = new stdClass();
        $offering_details = new stdClass();
        $lti_class = new stdClass();
        $grade_items = new stdClass();
        //Fetch offering details
        $offering_details_data = $lti->get_offering_details($offering_id);
        if ($result = $offering_details_data->fetch(PDO::FETCH_ASSOC)) {
            $offering_details->offering_id = $result['offering_id'];
            $offering_details->course_name = $result['course_name'];
        }
        // Fetch content details
        $content_details_record = $lti->get_content_details($contentdtl_id); //Tip: Fetch lti table
        if ($result = $content_details_record->fetch(PDO::FETCH_ASSOC)) {
            $lti_class->contentdtl_id = $result['contentdtl_id'];
            $lti_class->course_id = $result['course_id'];
            $lti_class->content_name = $result['content_name'];
            $lti_class->content_desc = $result['content_desc'];
        }
        //Fetch LTI
        $lti_class_record = $lti->get_lti($contentdtl_id);
        if ($result = $lti_class_record->fetch(PDO::FETCH_ASSOC)) {
            $lti_class->lti_id = $result['lti_id'];
            $lti_class->name = $result['name'];
            $lti_class->lti_types_id = $result['lti_types_id'];
            $lti_class->tool_url = $result['tool_url'];
            $lti_class->text = $result['text'];
            $lti_class->launch_container = $result['launch_container'];
            $lti_class->custom_id = $result['custom_id'];
            $lti_class->grade_max = $result['grade_max'];
        }
        //Fetch Grade Items
        $grade_items_record = $lti->get_grade_items($contentdtl_id, $lti_class->lti_id);
        if ($result = $grade_items_record->fetch(PDO::FETCH_ASSOC)) {
            $grade_items->grade_items_id = $result['grade_items_id'];
            $grade_items->name = $result['name'];
            $grade_items->lti_id = $result['lti_id'];
            $grade_items->grade_type = $result['grade_type'];
            $grade_items->grade_max = $result['grade_max'];
            $grade_items->grade_min = $result['grade_min'];
            $grade_items->grade_pass = $result['grade_pass'];
        }

        list($endpoint, $params) = lti_get_launch_data($user, $company, $offering_details, $contentdtl_id, $lti_class, $grade_items, $type, $nonce, $messagetype, $foruserid);
    } else {
        $lti_class = new stdClass();
        //Tip: sesskey() will implement in next version
        //$returnurl = CLIENT_HTTP_PATH . 'tool/contentitem_return.php?course=' . $courseid . '&id=' . $typeid . '&sesskey=' . sesskey();
        $returnurl = CLIENT_HTTP_PATH . 'tool/contentitem_return.php?course=' . $courseid . '&id=' . $typeid;
        // Prepare the request.
        $title = base64_decode($titleb64);
        $text = base64_decode($textb64);
        $course = new stdClass();
        $course_data = $lti->get_course_details($courseid);
        if ($result = $course_data->fetch(PDO::FETCH_ASSOC)) {
            $course->course_id = $result['course_id'];
            $course->course_name = $result['course_name'];
        }
        $request = lti_build_content_item_selection_request(
                $user, $company, $lti_class, $type, $course, $returnurl, $title, $text, [], [], false, false, false, false, false, $nonce
        );
        $params = $request->params;
    }
} else {
    $params['error'] = $error;
    if (!empty($desc)) {
        $params['error_description'] = $desc;
    }
}
if (isset($state)) {
    $params['state'] = $state;
}
unset($SESSION->lti_message_hint);

$r = '<form action="' . $redirecturi . "\" name=\"ltiAuthForm\" id=\"ltiAuthForm\" " .
        "method=\"post\" enctype=\"application/x-www-form-urlencoded\">\n";
if (!empty($params)) {
    foreach ($params as $key => $value) {
        $key = htmlspecialchars($key, ENT_COMPAT);
        $value = htmlspecialchars($value, ENT_COMPAT);
        $r .= "  <input type=\"hidden\" name=\"{$key}\" value=\"{$value}\"/>\n";
    }
}
$r .= "</form>\n";
$r .= "<script type=\"text/javascript\">\n" .
        "//<![CDATA[\n" .
        "document.ltiAuthForm.submit();\n" .
        "//]]>\n" .
        "</script>\n";
echo $r;
