简单的MySQL / PDO表生成器

时间:2014-03-20 22:31:57

标签: php mysql oop pdo

我一直在努力学习OOP和课程,我想要对我正在编写的一个简单项目进行批评。

我编写了几个类,以便我更容易使用MySQL和PDO生成表。它仍在继续,但我想确保我没有“破碎”任何东西。

我的主要问题是我想知道我写的内容是否仍然被认为是“安全的”,主要来自SQL注入。

的index.php:

<!DOCTYPE html>
<html>
    <head>
        <meta charset="UTF-8">
        <title>Database Class</title>
    </head>
    <body>
        <?php
        include 'class.MySQL.php';
        include 'class.TableBuilder.php';

        //Check to make sure a valid connection has been made
        //If so, instantiate the object and login to the database
        $db = (new MySQLDatabase_Object)->check_login();

        //Define the columns headings
        //Can be empty, but shouldn't be
        //Example:
        //"First Name"
        //"Last Name"
        $columns = array(
            'First Name',
            'Last Name',
            'Street Address'
        );

        //Build the 'SELECT' query fields
        //Cannot be empty
        //Example:
        //"leads.fname" => "fname means"
        //"leads.fname" => "fname"
        $fields = array(
            'leads.fname' => 'fname',
            'leads.lname' => 'lname',
            'leads.addr_street' => 'addr_street'
        );

        //Builds the 'FROM' query values
        //This will be a single table name
        //Cannot be empty
        //Example:
        //"leads"
        $tables = array('leads');

        //Builds the 'WHERE' query
        //Can only use the JOIN query or the WHERE query, not both
        //Can be empty
        //Examples:
        //"WHERE leads.fname LIKE '%Walt%'"
        //"WHERE leads.fname = 'Walter'"
        $where = array(
        );

        //Builds the JOIN query
        //Can only use the JOIN query or the WHERE query, not both
        //Can be empty
        //Examples:
        //"INNER JOIN appointments" => "leads.id = appointments.lead"
        //"INNER JOIN leads_notes" => "leads.id = leads_notes.id_lead"
        $join = array(
        );

        //Builds the AND/OR/NOT query
        //Can be empty
        //Examples:
        //"AND leads.assigned = 1"
        //"OR leads.assigned != 0"
        //"NOT leads.assigned = 0"
        $and = array(
        );

        //Sets the 'ORDER BY' clause
        //Can be empty
        //Example:
        //"leads.lname ASC"
        //"leads.fname DESC"
        $order = array(
        );

        //Build and return the query
        $query = MySQLDatabase_Object::query_builder_select($fields, $tables, $where, $join, $and, $order);

        //Gather the result set from the query and
        //place them in a nested array
        $result_set = MySQLDatabase_Object::results($fields, $db, $query);

        //Build the table, based on the result set and columns
        //and print the table to the screen
        $table = new MySQLTable;
        echo $table->buildTable($columns, $result_set);
        ?>
    </body>
</html>

class.MySQL.php:

<?php

class MySQLDatabase_Object {

    //Create the database connection and attempt to login to the database
    private function login() {
        $host = "localhost"; //Host Name
        $port = '3306'; //Default MySQL Port
        $dbname = "xxxxxx"; //Database Name
        $db_username = "xxxxxx"; //MySQL Username
        $db_password = "xxxxxx"; //MySQL Password

        $dsn = "mysql:host=$host;port=$port;dbname=$dbname"; //Data Source Name = Mysql
        $db = new PDO($dsn, $db_username, $db_password); //Connect to DB
        $db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
        return $db;
    }

    //Public-facing login method to log into the database and return the $db PDO
    public function check_login() {
        $db = $this->login();
        return $db;
    }

    static function query_builder_select($fields, $tables, $where, $join, $and, $order) {
        //Process the SELECT fields
        $select_fields = self::check_fields($fields);

        //Process the FROM field
        $tables = self::check_table($tables);

        //Processes the JOIN or WHERE fields
        if (!empty($where) && !empty($join)) {
            die("You can only use one of the JOIN or WHERE clauses.  Not both.");
        } elseif (!empty($where)) {
            $where = self::check_where($where);
        } elseif (!empty($join)) {
            $where = self::check_join($join);
        } else {
            $where = null;
        }

        //Process the AND/OR/NOT fields
        $and = self::check_and($and);

        //Process the ORDER BY fields
        $order = self::check_order($order);

        //Build the SELECT query
        $query = "SELECT $select_fields ";
        $query .= "FROM $tables";
        if (!is_null($where)) {
            $query .= " $where";
        }
        if (!is_null($and)) {
            $query .= " $and";
        }
        if (!is_null($order)) {
            $query .= " ORDER BY $order";
        }
        echo $query;
        return $query;
    }

    private static function check_fields($fields) {
        //Purpose: Gathers all the values from the $fields array
        //and formats them correctly to generate a correct "SELECT" statement
        //Check for an empty array
        if (empty($fields)) {
            die("No query fields selected");
        }

        //
        $select_fields = '';
        foreach ($fields AS $key => $value) {
            $select_fields .= "$key AS $value,";
        }
        //Remove the trailing comma from the last element in the array
        $select_fields = trim($select_fields, ',');
        return $select_fields;
    }

    private static function check_table($tables) {
        //Get the table array elements and seperate them with a comma
        if (!empty($tables)) {
            $tables = implode(',', $tables);
            $tables = trim($tables, ',');
        } else {
            die('No Tables selected');
        }
        return $tables;
    }

    private static function check_where($where) {
        //Get the WHERE array elements and seperate them with a comma
        if (!empty($where)) {
            $where = implode(',', $where);
            $where = trim($where, ',');
        } else {
            $where = null;
        }
        return $where;
    }

    private static function check_join($join) {
        $join_options = '';
        if (!empty($join)) {
            foreach ($join AS $key => $value) {
                $join_options .= " $key ON $value ";
            }
        } else {
            $join_options = null;
        }
        return $join_options;
    }

    private static function check_and($and) {
        //Get the WHERE array elements and seperate them with a comma
        if (!empty($and)) {
            $and = implode(' ', $and);
            $and = trim($and, ' ');
        } else {
            $and = null;
        }
        return $and;
    }

    private static function check_order($order) {
        //Get the order array elements and seperate them with a comma
        if (!empty($order)) {
            $order = implode(',', $order);
            $order = trim($order, ',');
        } else {
            $order = null;
        }
        return $order;
    }

    static function results($fields, $db, $query) {
        //Run the prepared query
        $stmt = $db->prepare($query);
        $stmt->execute();

        $results = array();
        $field_array = array();
        foreach ($stmt->fetchAll(PDO::FETCH_OBJ) as $row) {

            //Build the nested arrays
            foreach ($fields AS $key => $value) {
                $$value = $row->$value;
                array_push($field_array, $$value);
            }

            //Add the nested arrays to the main array ($results)
            array_push($results, $field_array);
            $field_array = array();
        }

        return $results;
    }

}

class.TableBuilder.php:

<?php

class MySQLTable {

    public function buildTable($columns, $result_set) {
        //Create an empty table
        $table = '';
        $table .= '<table border="1">';

        //Build the column structure, passed in from the $columns array
        $table .= "<tr>";
        foreach ($columns as $column) {
            $table .= "<td>$column</td>";
        }
        $table .= "</tr>";

        //Build the rows from the $result_set array
        foreach ($result_set AS $array) {
            $table .= "<tr>";
            //Pass each nested array to the table as a single row
            //per nested array
            foreach ($array AS $table_cell) {
                $table .= "<td>$table_cell</td>";
            }
            //Placeholder for adding additional columns (usually button columns)
//            $table .= "<td><button type='button'>Test</button></td>";

            $table .= "</tr>";
        }

        //Complete the table
        $table .= "</table>";
        return $table;
    }

}

为了使其正常工作,您需要使用数据库信息修改class.MySQL.php。

您可以修改index.php中的$ fields和$ columns,看看它是如何工作的。理论上,您应该能够在'$ columns'数组中命名列,在$ fields数组中命名您的MySQL SELECT字段,在$ tables中命名您的表名。

如果您需要更多信息,我很乐意提供帮助。

我知道只有简单的'WHERE'和'JOIN'子句处理。我将在接下来的工作。

感谢任何批评!

0 个答案:

没有答案