就我个人而言,我总是倾向于将数据库操作粘在数据库类中,该类完成初始化类、打开连接等所有繁重的工作。它还有通用查询包装器,我将包含普通占位符的 SQL 语句传递给它绑定变量,加上要绑定的变量数组(或参数的可变数量方法,如果这更适合您)。如果您想单独绑定每个参数而不使用$stmt->execute(array());
您只需在您选择的数据结构中传递具有值的类型,多暗数组,字典,JSON,任何适合您的需要并且您发现易于使用的东西。
它自己的模型类(在您的情况下为博客)然后对数据库进行子类化。然后你有几个选择要做。您想使用构造函数只创建新对象吗?您是否希望它仅基于 ID 加载?还是两者兼而有之?就像是:
function __construct(id = null, title = null, ingress = null, body = null) {
if(id){
$row = $this->getRow("SELECT * FROM blog WHERE id = :id",id); // Get a single row from the result
$this->title = $row->title;
$this->ingress = $row->ingress;
$this->body = $row->body;
... etc
} else if(!empty(title,ingress,body)){
$this->title = title;
... etc
}
}
也许两者都不是?您可以跳过构造函数并使用new(title, ingress, body)
,save()
和 aload(id)
方法,如果那是您的偏好。
当然,如果您只配置一些类成员并让数据库超类根据您发送或设置为成员变量的内容进行查询构建,则查询部分可以进一步概括。例如:
class Database {
$columns = []; // Array for storing the column names, could also be a dictionary that also stores the values
$idcolumn = "id"; // Generic id column name typically used, can be overridden in subclass
...
// Function for loading the object in a generic way based on configured data
function load($id){
if(!$this->db) $this->connect(); // Make sure we are connected
$query = "SELECT "; // Init the query to base string
foreach($this->columns as $column){
if($query !== "SELECT ") $query .= ", "; // See if we need comma before column name
$query .= $column; // Add column name to query
}
$query .= " FROM " . $this->tablename . " WHERE " . $this->idcolumn . " = :" . $this->idcolumn . ";";
$arg = ["col"=>$this->idcolumn,"value"=>$id,"type"=>PDO::PARAM_INT];
$row = $this->getRow($query,[$arg]); // Do the query and get the row pass in the type of the variable along with the variable, in this case an integer based ID
foreach($row as $column => $value){
$this->$column = $value; // Assign the values from $row to $this
}
}
...
function getRow($query,$args){
$statement = $this->query($query,$args); // Use the main generic query to return the result as a PDOStatement
$result = $statement->fetch(); // Get the first row
return $result;
}
...
function query($query,$args){
...
$stmt = $this->db->prepare($query);
foreach($args as $arg){
$stmt->bindParam(":".$arg["col"],$arg["value"],$arg["type"]);
}
$stmt->execute();
return $stmt;
}
...
}
现在你看到load($id)
,getrow($query,$args)
和query($query,$args)
是完全通用的。'getrow()' 只是query()
获取第一行的包装器,您可能希望有几个不同的包装器来以不同的方式解释或解释您的语句结果。如果无法将它们设为通用,您甚至可能希望将特定于对象的包装器添加到您的模型中。现在,在您的情况下,模型Blog
可能如下所示:
class Blog extends Database {
$title;
$ingress;
$body;
...
function __construct($id = null){
$this->columns = ["title","ingress","body","id",...];
$this->idcolumn = "articleid"; // override parent id name
...
if($id) $this->load($id);
}
...
}
像这样使用它:$blog = new Blog(123);
加载特定的博客,或者$blog = new Blog(); $blog->title = "title"; ... $blog->save();
如果你想要一个新的。