While you might have already implemented your Project 4 Play Trivia script, it is good to see and consider alternative implementations.
In this lab, we will...
Download the following starter code and use it to complete all the tasks
Later, if you choose, you can use this code for your own Project 4 implementation.
Read the following carefully as it explains key concepts to complete the remaining tasks.
While there are many ways to implement the trivia game for Project 4, any good PHP approach must keep track of at least three variables:
$_SESSION['username']
), which is established at login$_SESSION['question_num']
), which is set to 1 when the
user requests play_trivia.php
and
is incremented each time a question is answered.
$_SESSION['points']
), which is set to 0 when the user
user requests play_trivia.php
and then
is incremented each time a question is answered correctly.
The play_trivia.php
script can be viewed as a recursive function that
is called when the game begins. The script calls itself each time the user selects a choice for a question.
By clicking the form's submit button, an HTTP request is made where all the form data is transmitted to the server. We need to implement a form that transmits the user's choice $_POST['answer'] and the value of the button the user clicked $_POST['action'].
Clicking the reload button on the browser will trigger the same HTTP request as the user's last click. Thus, a reload could submit the user's previous choice as their choice for the current question. We can prevent reload issues by alternating between two states:
Thus, when a question is displayed, a reload will not trigger a "Submit" action because the previous action was clicking the "Next Question" button. Similarly, when a feedback message is displayed, a reload will not trigger a "Next Question" action because the previous action was clicking the "Submit" button.
The trivia application actually has four distinct states that we can detect by looking at the session-stored question number and the value of the button the user clicked to submit the form. Here is a summary of the states (please read carefully):
play_trivia.php
script.
We can detect this by checking if $_SESSION['question_num'] is null, zero or undefined,
or if the $_POST variable is null or undefined.
In this state, we need to set $_SESSION['question_num'] = 1, set _SESSION['points'] = 0,
execute a query to fetch 10 random questions, and store the questions in a session variable, i.e., $_SESSION['questions'].
See below for details on how to store the 10 questions as a 2D array.
Finally, we can print the "Start" button to move us to the Display state.
In your starter code folder, create a file called play_trivia.php
and add the following code. This code illustrates how to detect the first two state from the
posted action of the submitted form. You will have to implement the other two states.
Write the code to detect the Feedback state and then echo a form with a "Next Question" button. Then, write the code to detect the Stop state and then echo a form with a "Play Again" button. In this task, you just want to display messages indicating what state you are in to make sure you can move correctly through the 4 states.
<? session_start(); require_once("functions.php"); if ($_SESSION['authenticated'] != true) { die("Access denied"); } print_html_header("Play Trivia"); // Start State if (!$_SESSION['question_num'] || !$_POST || $_POST['action']=="Play Again") { $_SESSION['question_num'] = 1; $_SESSION['points'] = 0; echo ' <p>Get 10 question from database</p> <form method="post" action="play_trivia.php"> <input type="submit" name="action" value="Start"> </form>'; } // Display State else if ($_POST['action']=="Start" || $_POST['action']=="Next Question") { echo ' <p>Display question '.$_SESSION['question_num'].'</p> <form method="post" action="play_trivia.php"> <input type="submit" name="action" value="Submit"> </form>'; } // Add Feedback State // Add Stop State } print_html_footer(); ?>
While you should have been able to implement the four states on your own, here is some solution code to help you move forward if you get stuck.
Finish implementing the play_trivia.php. Please read all the text below because it contain implementation help and details.
Each state has a core operation that we can implement and test incrementally.
$mysqli = db_connect(); $result = $mysqli->query("SELECT question, choice1, choice2, choice3, choice4, answer FROM Questions ORDER BY RAND() LIMIT 10"); echo $mysqli->error; $questions_array = array(); while ($row = $result->fetch_row()) { array_push($questions_array, $row); } $result->close(); $mysqli->close(); var_dump($questions_array); $_SESSION['questions'] = $questions_array;Be sure to change the table name to your questions table. Note that for debugging, we print $mysqli->error in case there is an error. If you do not have 10 questions, you can set the LIMIT to a smaller value, i.e., 3. And, you can enter the Stop state after 3 questions. Also, we use
var_dump
to make sure the array is full of questions
before copying it to $_SESSION['questions'].
$question_index = $_SESSION['question_num'] - 1; $current_question = $_SESSION['questions'][ $question_index ];Then, we need to remember that the query fetched the question (index 0), then the four choices (index 1 to 4), and finally then answer (index 5). To make things clearer, we can copy these values to more compact and meaningful variable names.
$q = $current_question[0]; $c1 = $current_question[1]; $c2 = $current_question[2]; $c3 = $current_question[3]; $c4 = $current_question[4];Then, we can also store the answer to help process the submission.
$_SESSION['answer'] = $current_question[5];Finally, we can use the compact variables to print the question as a simple HTML form
echo ' <h3>Question '.$_SESSION['question_num'].'</h3> <p>'.$q.'</p> <form method="post" action="play_trivia.php"> <label> <input type="radio" name="answer" value="1"> '.$c1.' </label><br> <label> <input type="radio" name="answer" value="2"> '.$c2.' </label><br> <label> <input type="radio" name="answer" value="3"> '.$c3.' </label><br> <label> <input type="radio" name="answer" value="4"> '.$c4.' </label><br> <input type="submit" name="action" value="Submit"> </form>';
$username = $_SESSION['username']; $sql = "SELECT games, points FROM Users WHERE username='$username'"; $result = $mysqli->query($sql); $row = $result->fetch_row(); $games = $row[0]; $points = $row[1];Notice that $username must have single quotes because it is a string.
UPDATE Users SET games=$games, points=$points WHERE username='$username'Note that you can connect to the database once perform the select query, update the values of $games and $points, and then run the update query before closing the $result and $mysqli connections.
Notice that we are calling print_html_header("Play Trivia")
and print_html_footer()
, which includes Bootstrap's CSS and JavaScript.
Add CSS classes to the basic forms for answering each question. Read below for some helpful hints and documentation links.
<fieldset class="form-group">
and <div class="form-check">
just like the example:The game play of a trivia application can be almost entirely implemented in JavaScript. Only two core operations (getting the questions and updating the user's games and points) require server/database support. And, as we have learned in past labs, AJAX can be used to run server-side scripts in the background.
To help support application development in JavaScript, developers often impelment APIs (Application Program Interfaces). Here is an example to illustrate the concept:Imagine working for a company call Trivoogle, which is the world-class leader in providing trivia questions to other companies that wish to make trivia applications.
As a Trivoogle developer, your job is to create
JavaScript programs that reside on a Trivoogle server that
other developers could link
to in order to help build applications.
Since the URLs of your JavaScript code originate from a Trivoogle server,
other developers can call your functions in order
to get trivia questions via AJAX from Trivoogle's servers.
You, as the API developer, would create functions that have
lots of parameters so that other developers could specify
things like:
An API is just a collection of objects and functions that are highly parameterized to help implement applications. Good API's should have good documentation to describe the parameters and the output. Companies like Google provides many API's so developers can build applications using these companies' tools.
Many API's will return data in JSON format.
In the past, XML was the standard format.
However, it is very common for API's to output chunks
of HTML that developers can simply append into
div
tags.
Some API's will allow developers to specify the id
of an HTML element that the API can then manipulate.
Thus, developers do not even have to
write the JavaScript to append the API's output
to an HTML element; The API function can do
it directly. The key concept is that
developers are including
Trivoogle's JavaScript as if it were their own code.
This allows Trivoogle to deliver content
to many paying clients without having to
do a lot of customized programming. The developers
have to implement their application to work
with Trivoogle's API.
JavaScript code cannot be hidden on a server like PHP code. While the code can be compressed and minified, anyone with a web server could use Trivoogle's API. Since Trivoogle wishes to charge for access to their API, they must figure out a way to control access.
The most popular approach is to require an authentication key. Thus, Trivoogle's server will not respond to AJAX requests unless the request includes a valid key. The problem is that this API key would be present in the code of other developer's web scripts. Anyone could then copy this key and use it.
Thus, Trivoogle must build a server to server authentication system that other developers must use to get dynamic keys. The idea is that when a user logs in, the developer must also use Trivoogle's authentication systems to get a dynamic key for that user. This key is sent back to the client and it get's stored on Trivoogle's API server.
When the application needs to get a trivia question, the key would be sent to verify that the request is coming from a paying client. The key is stored on Trivoogle server using sessions. The session can be set to expire or it can be destroyed when a user logs out. Thus, even if a hacker intercepted the key, they would only be able to use if for a limited time.
In general, there is no fail safe way to secure API's, so "pure" server-side applications are still very common for many applications where the code needs to remain hidden.
While some API's allow developers to directly call defined JavaScript functions, other API's are "main programs" that can be customized by URL parameters. Consider this URL:
get_trivia_question.php?difficulty=hard&targetid=questiondiv
This PHP script would output the JavaScript code to insert "hard"
questions in the questiondiv
of the web page that linked to the code.
The developer would have to define the questiondiv
in
their application's web page. Once loaded, this custom JavaScript program
could completely implement a trivia application by making AJAX calls
to Trivoogle's server. In other words, another developer could
completely embed a trivia application on their web pages just
by linking and customizing one link URL.
Think about the insanity that a server side scripting language like PHP (language #1) can execute an SQL query (language #2) to get content from a database and then output JavaScript (language #3) which can then dynamically modify the HTML (language #4) and CSS (language #5) of a web page hosted on a completely different server. While this seems insane, it allows web applications to be developed and deployed with ultimate flexibility. It also allows applications to be built using the best languages for key task. JavaScript, HTML and CSS are the best languages for creating user interfaces because these languages are standardized and are the foundation of the World Wide Web, so they represent the most accessible and widely used languages that exist in the world. SQL is certainly the leading language for selecting data from a database. The server side language is the only language where there is a debate on which one is the best. But, this general framework allows developers to use whatever server-side language they want. For this task, you only need to consider the awesomeness of this general framework and then smile because you now know the fundamentals of the most powerful application framework ever developed.
None. This lab is attendance only.