PHP Interview Questions & Answers for experienced
PHP Interview Questions & Answers for experienced are provided here. TutorialsClass helps you to test your knowledge and enhance your experience.
Read PHP Interview Questions & Answers for experienced candidates to get your dream job.
How to get the browser details of a visitor in PHP?
The browser sends a text called user agent with every request. In PHP you can read it from $_SERVER["HTTP_USER_AGENT"].
<?php
echo $_SERVER["HTTP_USER_AGENT"];
?>
Output:
Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36
PHP also has the get_browser() function, which tells the browser name, version and platform in an array. But it needs a browscap.ini file configured in php.ini, which is not available on most servers.
- The user agent is sent by the browser, so a visitor can change or fake it.
- Do not use it for security. For features like JavaScript or cookies, test the feature in the browser instead of checking the browser name.
In how many ways can we fetch data from a MySQL result set in PHP?
With the MySQLi extension there are five main functions to read rows from a result set.
| Function | Returns the row as |
|---|---|
| mysqli_fetch_assoc() | Associative array (keys are column names) |
| mysqli_fetch_row() | Numeric array (keys are 0, 1, 2…) |
| mysqli_fetch_array() | Both associative and numeric array |
| mysqli_fetch_object() | Object (columns are properties) |
| mysqli_fetch_all() | All rows together in one array |
This example uses the users table from our MySQL chapters. Suppose the user with id 1 is “Ram”.
<?php
require_once('db-connection.php');
$sql = "SELECT id, name FROM users WHERE id = 1";
$row = mysqli_fetch_assoc(mysqli_query($conn, $sql));
echo $row["name"] . "<br>";
$row = mysqli_fetch_row(mysqli_query($conn, $sql));
echo $row[1] . "<br>";
$row = mysqli_fetch_object(mysqli_query($conn, $sql));
echo $row->name;
?>
Output:
Ram
Ram
Ram
fetch_assoc() is the most used, because the code is easy to read. Use fetch_all() only when the result is small, as it loads every row in memory.
How to encrypt and decrypt data stored in a MySQL table?
MySQL has two built-in functions: AES_ENCRYPT() and AES_DECRYPT(). The column that stores the encrypted data must be of type VARBINARY or BLOB.
INSERT INTO users (name, secret)
VALUES ('Robin', AES_ENCRYPT('my secret', 'strong-key'));
SELECT AES_DECRYPT(secret, 'strong-key') AS secret
FROM users WHERE name = 'Robin';
This works, but it has weak points. The key goes inside the SQL, so it can be seen in query logs. And in MySQL 8 the default mode is AES-128-ECB, which is not a strong mode.
A better way is to encrypt the data in PHP before saving it, so MySQL only stores the encrypted text. The sodium extension is built in PHP 7.2 and above.
<?php
$key = sodium_crypto_secretbox_keygen(); // save this key safely
$nonce = random_bytes(SODIUM_CRYPTO_SECRETBOX_NONCEBYTES);
$cipher = sodium_crypto_secretbox("my secret", $nonce, $key); // save $nonce and $cipher in the database
echo sodium_crypto_secretbox_open($cipher, $nonce, $key);
?>
Output:
my secret
What is SQL injection and how to prevent it in PHP?
SQL injection is an attack where a visitor types SQL code in a form or URL, and your script runs it as part of the query. The attacker can read, change or delete data of your database.
It happens when you put user input directly inside the SQL text.
<?php
// Unsafe: the email comes from the form and goes directly in SQL
$email = $_POST["email"];
$sql = "SELECT * FROM users WHERE email = '$email'";
?>
If the visitor types ' OR '1'='1, the condition is always true and the query returns every user.
How to prevent it: use prepared statements. The SQL and the data are sent separately, so the data can never become a part of the SQL.
<?php
$stmt = $conn->prepare("SELECT id, name FROM users WHERE email = ?");
$stmt->bind_param("s", $email);
$stmt->execute();
?>
- Use prepared statements with mysqli or PDO for every query that has user data.
- Never build SQL by joining strings with variables.
- Give the database user only the permissions it needs.
- Do not show database errors to visitors.
Full examples are in PHP MySQL Prepared Statements.
What is XSS and how to prevent it in PHP?
XSS (Cross Site Scripting) is an attack where a visitor puts JavaScript code in your page, for example in a comment, and that code runs in the browser of other visitors. It can steal cookies, show fake forms or change the page.
The main fix is to escape the output. Convert special characters of user data to safe HTML before you print it, using htmlspecialchars().
<?php
$comment = "<script>alert('Hacked')</script>";
echo htmlspecialchars($comment, ENT_QUOTES, 'UTF-8');
?>
Output:
<script>alert(‘Hacked’)</script>
The browser shows this as plain text and does not run it.
- Escape every user value when you print it, always with ENT_QUOTES and UTF-8.
- Validate input on the server (for example allow only numbers in an age field).
- Use the
HttpOnlyflag on cookies, so JavaScript can not read the session cookie. - Add a Content-Security-Policy header for extra protection.
More tips are in PHP Security Tips.
What is CSRF and how to prevent it in PHP?
CSRF (Cross Site Request Forgery) is an attack where another website makes the browser of a logged-in user send a request to your site, without the user knowing. Because the browser sends the login cookie automatically, your site thinks the request is real.
How to prevent it: put a secret random token in every form, and check it when the form is submitted.
<?php
session_start();
// When showing the form: create the token
if (empty($_SESSION["csrf_token"])) {
$_SESSION["csrf_token"] = bin2hex(random_bytes(32));
}
?>
<input type="hidden" name="csrf_token" value="<?php echo $_SESSION["csrf_token"]; ?>">
<?php
session_start();
// When the form is submitted: check the token
$token = $_POST["csrf_token"] ?? "";
if (!hash_equals($_SESSION["csrf_token"] ?? "", $token)) {
http_response_code(403);
exit("Invalid request.");
}
?>
- Use
hash_equals()to compare the tokens. - Set the session cookie with
SameSite=Laxor Strict. - Use POST (not GET) for actions that change data.
See the full steps in PHP Security Tips.
What is the difference between mysqli and PDO in PHP?
Both MySQLi and PDO (PHP Data Objects) are used to connect PHP with a database. Both support prepared statements, so both can protect from SQL injection.
| Feature | MySQLi | PDO |
|---|---|---|
| Databases supported | MySQL and MariaDB only | 12 different databases (MySQL, PostgreSQL, SQLite and more) |
| Style | Procedural and object oriented | Object oriented only |
| Named parameters (:email) | No, only ? | Yes, and also ? |
| Switching database later | Need to rewrite the code | Mostly change only the connection string |
| Error handling | Exceptions (default from PHP 8.1) | Exceptions (when you set the error mode) |
<?php
$pdo = new PDO("mysql:host=localhost;dbname=student;charset=utf8mb4", "root", "");
$pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$stmt = $pdo->prepare("SELECT name FROM users WHERE email = :email");
$stmt->execute(["email" => "ram@example.com"]);
echo $stmt->fetchColumn();
?>
Output:
Ram
Use PDO if you may change the database in future, or you like named parameters. Use MySQLi if you work only with MySQL and want its extra features. See MySQLi prepared statements and MySQLi procedural vs object oriented.
What is Composer in PHP?
Composer is the dependency manager of PHP. It downloads the libraries (called packages) that your project needs, and keeps them updated. Packages come from a website called Packagist.
You write the needed packages in a file named composer.json. Composer installs them in the vendor folder and also creates an autoloader, so you do not need to write require for every class.
| Command | What it does |
|---|---|
composer init | Creates a composer.json file |
composer require vendor/package | Installs a package and adds it to composer.json |
composer install | Installs all packages listed in composer.lock |
composer update | Updates packages to the latest allowed version |
composer dump-autoload | Rebuilds the autoloader |
<?php
// One line loads every installed package
require __DIR__ . "/vendor/autoload.php";
?>
Composer is used by almost all modern PHP frameworks like Laravel and Symfony. Do not upload the vendor folder to Git, only composer.json and composer.lock.
How to handle errors using try, catch and finally in PHP?
PHP uses exceptions to handle errors. You put risky code in a try block. If something goes wrong, the code throws an exception and PHP jumps to the catch block. The finally block runs always, with or without error.
<?php
function divide($a, $b) {
if ($b == 0) {
throw new Exception("Division by zero");
}
return $a / $b;
}
try {
echo divide(10, 2) . "<br>";
echo divide(5, 0) . "<br>";
} catch (Exception $e) {
echo "Error: " . $e->getMessage() . "<br>";
} finally {
echo "Done";
}
?>
Output:
5
Error: Division by zero
Done
getMessage()gives the error text, andgetLine()gives the line number.- You can use many catch blocks for different exception types.
- In PHP 7 and above, serious errors are thrown as
Errorobjects. CatchThrowableto catch both Exception and Error.
Basics of PHP errors are in PHP Errors.
How to upload a file securely in PHP?
File upload is risky, because someone can upload a PHP file and run it on your server. Follow these steps to make it safe:
- Check the upload error with
UPLOAD_ERR_OK. - Check the real type of the file, not the name or the type sent by the browser.
- Limit the file size.
- Give the file a new random name, and never use the original name.
- Save the file outside the public folder if you can, or at least block PHP execution in the upload folder.
<?php
if ($_FILES["photo"]["error"] !== UPLOAD_ERR_OK) {
exit("Upload failed.");
}
$allowed = ["image/jpeg" => "jpg", "image/png" => "png"];
$finfo = new finfo(FILEINFO_MIME_TYPE);
$mime = $finfo->file($_FILES["photo"]["tmp_name"]);
if (!isset($allowed[$mime])) {
exit("Only JPG and PNG files are allowed.");
}
if ($_FILES["photo"]["size"] > 2 * 1024 * 1024) {
exit("File is too big. Maximum 2 MB.");
}
$newName = bin2hex(random_bytes(16)) . "." . $allowed[$mime];
move_uploaded_file($_FILES["photo"]["tmp_name"], "/var/www/uploads/" . $newName);
?>
Learn the basics in PHP File Upload, and how to change the size limit in maximum upload size.
What is type juggling and strict_types in PHP?
Type juggling means PHP converts the data type of a value automatically when needed. For example, the string "10" is treated as a number when you compare or add it with a number.
<?php
var_dump("10" == 10); // string and number, values are same
var_dump("abc" == 0); // false in PHP 8 (it was true in PHP 7)
var_dump(0 == ""); // false in PHP 8 (it was true in PHP 7)
?>
Output:
bool(true)
bool(false)
bool(false)
This automatic change can create bugs. You can ask PHP to be strict with declare(strict_types=1). It must be the first statement of the file, and it affects the function calls made from that file.
<?php
declare(strict_types=1);
function add(int $a, int $b) {
return $a + $b;
}
echo add(2, 3); // 5
// echo add("2", "3"); // TypeError, because strings are not accepted
?>
Output:
5
To be safe, compare with === and use type declarations in functions. See == vs ===.
- « Previous
- 1
- 2