Просмотр исходного кода

Update: 更改唯一主键的支持方式

zjh 4 месяцев назад
Родитель
Сommit
7bceb7fe0e

+ 58 - 17
src/Driver/Entity/Base.php

@@ -5,6 +5,7 @@ namespace Qii\Driver\Entity;
 
 use Qii\Driver\Model;
 use Qii\Driver\Response;
+use Qii\Exceptions\InvalidParams;
 
 class Base {
     /**
@@ -1017,10 +1018,44 @@ class Base {
         }
         return (bool) $this->db()->where($where)->selectOne($this->prepareTable());
     }
+
+    /**
+     * replace into database
+     *
+     * @return mixed|Response
+     * @throws InvalidParams
+     */
+    final public function replace(){
+        $valid = $this->validFieldsForAdd();
+        if($valid->isError()) {
+            return $valid;
+        }
+        //如果设置了 unique 就先验证唯一性
+        list($uniqueWhere, $uniqueOr, $exclude, $primary) = $this->condition();
+        unset($uniqueWhere, $uniqueOr, $exclude, $exclude);
+        if(count($primary) == 0) {
+            throw new InvalidParams('DB::replace需要设置主键');
+        }
+        $values = array_merge($this->getDefaultValue(), $this->properties());
+        $this->lastInsertID = $res = $this->db()->replaceObject($this->prepareTable(), $values);
+
+        if($this->db()->isError()) {
+            return Response::FailSave(static::class .'::'. __FUNCTION__,
+                [
+                    '_result' => ['code' => Response::FAIL_FOR_SAVE, 'msg' => $this->db()->getMessage(), 'body' => []],
+                    'message' => $this->db()->getMessage()
+                ]);
+        }
+        return Response::Success(static::class .'::'. __FUNCTION__,
+            [
+                '_result' => ['code' => Response::DO_SUCCESS, 'msg' => '添加成功', 'body' => $res]
+            ]
+        );
+    }
     /**
      * 保存数据
      *
-     * @return mixed|Qii\Driver\Response
+     * @return mixed|Response
      * @throws \Exception
      */
     final public function add() {
@@ -1747,28 +1782,34 @@ class Base {
      * @throws \Exception
      */
     protected function uniqueCondition() {
-        $uniqueWhere = [];
-        $uniqueOr = [];
         $unique = $this->uniqueKey();
-        $useWhere = true;
-
         if(!is_array($unique)) {
-            $unique = $this->explode(',', $unique);
-            $useWhere = false;
-            if(count($unique) == 1) {
-                $useWhere  = true;
+            if(strpos($unique, ',') !== false) {
+                $unique = explode(',', $unique);
+            }else{
+                $unique = array($unique);
             }
         }
-        foreach ($unique as $key) {
-            $key = $this->entity()->convertToField($key);
-            $property = $this->entity()->convertToProperty($key);
-            if($useWhere) {
-                $uniqueWhere[$key] = $this->$property;
+        $where = ['and' => [], 'or' => []];
+        $a1 = array_reduce($unique, function ($where, $item){
+            if(strpos($item, ',') !== false) {
+                $item = explode(',', $item);
+                foreach($item as $k){
+                    $key = $this->entity()->convertToField($k);
+                    $property = $this->entity()->convertToProperty($k);
+                    $where['and'][$key] = $this->$property;
+                }
             }else{
-                $uniqueOr[$key] = $this->$property;
+                $key = $this->entity()->convertToField($item);
+                $property = $this->entity()->convertToProperty($item);
+                $where['or'][$key] = $this->$property;
+                $where['or'][] = 'or';
             }
-        }
-        return [$uniqueWhere, $uniqueOr];
+            return $where;
+        }, $where);
+        //弹出or的最后一个or操作符
+        array_pop($a1['or']);
+        return [$a1['and'], $a1['or']];
     }
 
     /**

+ 14 - 5
src/Driver/Entity/Entity.php

@@ -294,6 +294,14 @@ DOC;
         if(isset($tableInfo['rules']['extra']['auto_increment'])) {
             $primaryKey = $tableInfo['rules']['extra']['auto_increment'];
             $autoIncrement = $tableInfo['rules']['extra']['auto_increment'][0];
+        }else if(isset($tableInfo['rules']['pri'])) {
+            $primaryKey = $tableInfo['rules']['pri'];
+        }
+        $uniqueKey = [];
+        if(isset($tableInfo['rules']['uniq'])) {
+            $uniqueKey = $tableInfo['rules']['uniq'];
+        }else{
+            $uniqueKey = $primaryKey;
         }
         $next[] = "\t\treturn ". '$rules;';
         $next[] = "\t". '}';
@@ -311,16 +319,17 @@ DOC;
 
         $next [] = <<<DOC
     /**
-     * unique (unique 如果是 array 则表示 联合唯一,如果是string则是任意唯一,多个单独唯一使用字符串以逗号隔开, 主键除外)
-     *
+     * unique (unique 如果是 array('a,b') 则表示 a,b联合唯一,array('a,b', 'b,c') 表示a,b唯一 或 b,c唯一
+     * 'a,b' 字符串则表示任意唯一 类似于array ('a','b')
      * @return mixed
      * @throws \Exception
      */
     public function uniqueKey(){
         if(\$this->uniqKeys !== null) return \$this->uniqKeys;
 DOC;
-        if($primaryKey) {
-            $next[] = "\t\treturn array('". join("','", $primaryKey). "');";
+
+        if($uniqueKey) {
+            $next[] = "\t\treturn array('". join("','", $uniqueKey). "');";
         }else {
 
             $next[] = <<<DOC
@@ -534,7 +543,7 @@ DOC;
      */
     public function convertToProperty($field) {
         $field = $this->ucFirst ? ucfirst($field) : $field;
-        return preg_replace_callback("/\_([a-z]|[A-Z]|[0-9])/", function($match){
+        return preg_replace_callback("/\_([a-z]|[A-Z])/", function($match){
             return ucfirst($match[1]);
         }, $field);
     }

+ 2 - 1
src/Driver/TraitDatabase.php

@@ -206,7 +206,8 @@ trait TraitDatabase
         if(count($matches) == 3) {
             foreach ($matches[2] as $key => $match) {
                 //$uniqKeys[$matches[1][$key]] = explode("`,`", $match);
-                $uniqKeys[] = explode("`,`", $match);
+                $arr = explode("`,`", $match);
+                if(count($arr) > 0)  $uniqKeys[] = join(',', $arr);
             }
         }
         if(count($uniqKeys) > 0) {

+ 2 - 2
src/Exceptions/InvalidParams.php

@@ -8,8 +8,8 @@ class InvalidParams extends Errors
 {
     const VERSION = '1.2';
 
-    public function __construct($code = 200, \Exception $previous = null) {
-        parent::__construct("Invalid params", $code, $previous);
+    public function __construct($msg = 'Invalid params', $code = 200, \Exception $previous = null) {
+        parent::__construct($msg, $code, $previous);
     }
     /**
      * 显示错误