Функции mysql* для php7+

mysql_*

  • Использует глобальную переменную для хранения PDO соединения, как это делали оригинальные mysql_* функции.
  • Функция mysql_query:
    – Автоматически определяет тип запроса
    – Для INSERT/UPDATE/DELETE использует exec() и сохраняет affected rows
    – Для SELECT возвращает обёртку MySQLResult для совместимости
  • Класс MySQLResult это обёртка над PDOStatement для поддержки функций вроде mysql_num_rows()
  • Реализованы все основные функции:
    mysql_connect(), mysql_select_db()
    mysql_fetch_array(), mysql_fetch_assoc(), mysql_fetch_row(), mysql_fetch_object()
    mysql_real_escape_string(), mysql_escape_string()
    mysql_insert_id(), mysql_affected_rows(), mysql_num_rows()
    mysql_error(), mysql_errno()
    mysql_close(), mysql_free_result()
  • Определены константы MYSQL_ASSOC, MYSQL_NUM, MYSQL_BOTH для совместимости

Просто подключите этот файл в начале вашего старого кода, и все mysql_* функции будут работать через PDO без изменения остального кода. Это позволит быстро мигрировать старые проекты на PHP7+, где расширение mysql было удалено.

<?php

/**
 * Глобальная переменная для хранения соединения PDO
 */
$GLOBALS['_mysql_pdo_connection'] = null;
$GLOBALS['_mysql_last_insert_id'] = 0;
$GLOBALS['_mysql_affected_rows'] = 0;

/**
 * Замена функции mysql_connect
 * 
 * @param string $server
 * @param string $username
 * @param string $password
 * @return PDO|false
 */
function mysql_connect($server = 'localhost', $username = 'root', $password = '') {
    try {
        // Разбираем хост и порт
        $host = $server;
        $port = 3306;
        
        if (strpos($server, ':') !== false) {
            list($host, $port) = explode(':', $server, 2);
        }
        
        $dsn = "mysql:host={$host};port={$port};charset=utf8mb4";
        
        $options = [
            PDO::ATTR_ERRMODE => PDO::ERRMODE_SILENT,
            PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_BOTH,
            PDO::MYSQL_ATTR_USE_BUFFERED_QUERY => true,
            PDO::ATTR_EMULATE_PREPARES => true
        ];
        
        $GLOBALS['_mysql_pdo_connection'] = new PDO($dsn, $username, $password, $options);
        return $GLOBALS['_mysql_pdo_connection'];
        
    } catch (PDOException $e) {
        trigger_error("MySQL Connection Failed: " . $e->getMessage(), E_USER_WARNING);
        return false;
    }
}

/**
 * Замена функции mysql_select_db
 * 
 * @param string $database
 * @param PDO $link_identifier
 * @return bool
 */
function mysql_select_db($database, $link_identifier = null) {
    $pdo = $link_identifier ?: $GLOBALS['_mysql_pdo_connection'];
    
    if (!$pdo) {
        trigger_error("No database connection", E_USER_WARNING);
        return false;
    }
    
    try {
        $pdo->exec("USE `{$database}`");
        return true;
    } catch (PDOException $e) {
        return false;
    }
}

/**
 * Замена функции mysql_query
 * 
 * @param string $query
 * @param PDO $link_identifier
 * @return PDOStatement|bool
 */
function mysql_query($query, $link_identifier = null) {
    $pdo = $link_identifier ?: $GLOBALS['_mysql_pdo_connection'];
    
    if (!$pdo) {
        trigger_error("No database connection", E_USER_WARNING);
        return false;
    }
    
    try {
        // Определяем тип запроса
        $queryType = strtoupper(substr(trim($query), 0, 6));
        
        if (in_array($queryType, ['INSERT', 'UPDATE', 'DELETE', 'REPLAC'])) {
            // Для запросов изменения данных
            $result = $pdo->exec($query);
            
            if ($result === false) {
                return false;
            }
            
            // Сохраняем affected rows
            $GLOBALS['_mysql_affected_rows'] = $result;
            
            // Для INSERT сохраняем last insert id
            if ($queryType === 'INSERT') {
                $GLOBALS['_mysql_last_insert_id'] = $pdo->lastInsertId();
            }
            
            return true;
            
        } else {
            // Для SELECT и других запросов возвращающих результат
            $stmt = $pdo->query($query);
            
            if ($stmt === false) {
                return false;
            }
            
            // Оборачиваем PDOStatement в класс для совместимости
            return new MySQLResult($stmt);
        }
        
    } catch (PDOException $e) {
        trigger_error("MySQL Query Failed: " . $e->getMessage(), E_USER_WARNING);
        return false;
    }
}

/**
 * Класс-обертка для PDOStatement для совместимости с mysql_* функциями
 */
class MySQLResult {
    private $stmt;
    private $currentRow = 0;
    private $data = null;
    
    public function __construct(PDOStatement $stmt) {
        $this->stmt = $stmt;
    }
    
    public function getStatement() {
        return $this->stmt;
    }
    
    public function fetchAll() {
        if ($this->data === null) {
            $this->data = $this->stmt->fetchAll(PDO::FETCH_BOTH);
        }
        return $this->data;
    }
    
    public function rowCount() {
        return $this->stmt->rowCount();
    }
}

/**
 * Замена функции mysql_fetch_array
 * 
 * @param MySQLResult|PDOStatement $result
 * @param int $result_type
 * @return array|false
 */
function mysql_fetch_array($result, $result_type = MYSQL_BOTH) {
    if (!$result) {
        return false;
    }
    
    $stmt = ($result instanceof MySQLResult) ? $result->getStatement() : $result;
    
    $fetch_style = PDO::FETCH_BOTH;
    if (defined('MYSQL_ASSOC') && $result_type === MYSQL_ASSOC) {
        $fetch_style = PDO::FETCH_ASSOC;
    } elseif (defined('MYSQL_NUM') && $result_type === MYSQL_NUM) {
        $fetch_style = PDO::FETCH_NUM;
    }
    
    return $stmt->fetch($fetch_style);
}

/**
 * Замена функции mysql_fetch_assoc
 * 
 * @param MySQLResult|PDOStatement $result
 * @return array|false
 */
function mysql_fetch_assoc($result) {
    if (!$result) {
        return false;
    }
    
    $stmt = ($result instanceof MySQLResult) ? $result->getStatement() : $result;
    return $stmt->fetch(PDO::FETCH_ASSOC);
}

/**
 * Замена функции mysql_fetch_row
 * 
 * @param MySQLResult|PDOStatement $result
 * @return array|false
 */
function mysql_fetch_row($result) {
    if (!$result) {
        return false;
    }
    
    $stmt = ($result instanceof MySQLResult) ? $result->getStatement() : $result;
    return $stmt->fetch(PDO::FETCH_NUM);
}

/**
 * Замена функции mysql_fetch_object
 * 
 * @param MySQLResult|PDOStatement $result
 * @param string $class_name
 * @param array $params
 * @return object|false
 */
function mysql_fetch_object($result, $class_name = 'stdClass', $params = []) {
    if (!$result) {
        return false;
    }
    
    $stmt = ($result instanceof MySQLResult) ? $result->getStatement() : $result;
    
    if ($class_name === 'stdClass') {
        return $stmt->fetch(PDO::FETCH_OBJ);
    } else {
        return $stmt->fetchObject($class_name, $params);
    }
}

/**
 * Замена функции mysql_num_rows
 * 
 * @param MySQLResult|PDOStatement $result
 * @return int|false
 */
function mysql_num_rows($result) {
    if (!$result) {
        return false;
    }
    
    if ($result instanceof MySQLResult) {
        // Для SELECT запросов нужно получить все данные
        $data = $result->fetchAll();
        return count($data);
    }
    
    return $result->rowCount();
}

/**
 * Замена функции mysql_affected_rows
 * 
 * @param PDO $link_identifier
 * @return int
 */
function mysql_affected_rows($link_identifier = null) {
    return $GLOBALS['_mysql_affected_rows'] ?? 0;
}

/**
 * Замена функции mysql_insert_id
 * 
 * @param PDO $link_identifier
 * @return int
 */
function mysql_insert_id($link_identifier = null) {
    $pdo = $link_identifier ?: $GLOBALS['_mysql_pdo_connection'];
    
    if (!$pdo) {
        return 0;
    }
    
    return $GLOBALS['_mysql_last_insert_id'] ?? $pdo->lastInsertId();
}

/**
 * Замена функции mysql_real_escape_string
 * 
 * @param string $string
 * @param PDO $link_identifier
 * @return string|false
 */
function mysql_real_escape_string($string, $link_identifier = null) {
    $pdo = $link_identifier ?: $GLOBALS['_mysql_pdo_connection'];
    
    if (!$pdo) {
        trigger_error("No database connection", E_USER_WARNING);
        return false;
    }
    
    // Убираем кавычки, т.к. PDO::quote добавляет их
    return trim($pdo->quote($string), "'");
}

/**
 * Замена функции mysql_escape_string (deprecated версия)
 * 
 * @param string $string
 * @return string
 */
function mysql_escape_string($string) {
    return mysql_real_escape_string($string);
}

/**
 * Замена функции mysql_error
 * 
 * @param PDO $link_identifier
 * @return string
 */
function mysql_error($link_identifier = null) {
    $pdo = $link_identifier ?: $GLOBALS['_mysql_pdo_connection'];
    
    if (!$pdo) {
        return '';
    }
    
    $errorInfo = $pdo->errorInfo();
    return isset($errorInfo[2]) ? $errorInfo[2] : '';
}

/**
 * Замена функции mysql_errno
 * 
 * @param PDO $link_identifier
 * @return int
 */
function mysql_errno($link_identifier = null) {
    $pdo = $link_identifier ?: $GLOBALS['_mysql_pdo_connection'];
    
    if (!$pdo) {
        return 0;
    }
    
    $errorInfo = $pdo->errorInfo();
    return isset($errorInfo[1]) ? (int)$errorInfo[1] : 0;
}

/**
 * Замена функции mysql_close
 * 
 * @param PDO $link_identifier
 * @return bool
 */
function mysql_close($link_identifier = null) {
    if ($link_identifier) {
        $link_identifier = null;
    } else {
        $GLOBALS['_mysql_pdo_connection'] = null;
    }
    return true;
}

/**
 * Замена функции mysql_free_result
 * 
 * @param MySQLResult|PDOStatement $result
 * @return bool
 */
function mysql_free_result($result) {
    if ($result instanceof MySQLResult || $result instanceof PDOStatement) {
        $result = null;
        return true;
    }
    return false;
}

/**
 * Определяем константы для совместимости
 */
if (!defined('MYSQL_ASSOC')) {
    define('MYSQL_ASSOC', 1);
}
if (!defined('MYSQL_NUM')) {
    define('MYSQL_NUM', 2);
}
if (!defined('MYSQL_BOTH')) {
    define('MYSQL_BOTH', 3);
}

// Пример использования:
/*
// Подключение к БД
mysql_connect('localhost', 'username', 'password');
mysql_select_db('database_name');

// Выполнение запроса
$result = mysql_query("SELECT * FROM users WHERE active = 1");

// Обработка результатов
while ($row = mysql_fetch_assoc($result)) {
    echo $row['name'] . "\n";
}

// Вставка данных
$name = mysql_real_escape_string($_POST['name']);
mysql_query("INSERT INTO users (name) VALUES ('{$name}')");
echo "Inserted ID: " . mysql_insert_id();
echo "Affected rows: " . mysql_affected_rows();

// Проверка ошибок
if (!$result) {
    echo "Error: " . mysql_error();
}

// Закрытие соединения
mysql_close();
*/

Ибо нефиг такие базовые штуки по приватам прятать. :wink: