Completed
Pull Request — test (#1)
by Temitope
02:52
created

DatabaseHandler::insertRecord()   A

Complexity

Conditions 3
Paths 4

Size

Total Lines 23
Code Lines 12

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 1 Features 0
Metric Value
c 1
b 1
f 0
dl 0
loc 23
rs 9.0856
cc 3
eloc 12
nc 4
nop 3
1
<?php
2
3
/**
4
 * @author   Temitope Olotin <[email protected]>
5
 * @license  <https://opensource.org/license/MIT> MIT
6
 */
7
namespace Laztopaz\PotatoORM;
8
9
use PDO;
10
class DatabaseHandler
11
{
12
    private $tableFields;
0 ignored issues
show
Unused Code introduced by
The property $tableFields is not used and could be removed.

This check marks private properties in classes that are never used. Those properties can be removed.

Loading history...
13
    private $dbHelperInstance;
0 ignored issues
show
Unused Code introduced by
The property $dbHelperInstance is not used and could be removed.

This check marks private properties in classes that are never used. Those properties can be removed.

Loading history...
14
    private $dbConnection;
15
    private $model;
16
17
    /**
18
     * This is a constructor; a default method  that will be called automatically during class instantiation.
19
     */
20
    public function __construct($modelClassName, $dbConn = null)
21
    {
22
        if (is_null($dbConn)) {
23
            $this->dbConnection = new DatabaseConnection();
24
        } else {
25
            $this->dbConnection = $dbConn;
26
        }
27
28
        $this->model = $modelClassName;
29
    }
30
31
    /**
32
     * This method create a record and store it in a table row.
33
     *
34
     * @params associative array, string tablename
35
     *
36
     * @return bool true or false
37
     */
38
    public function create($associative1DArray, $tableName, $dbConn = null)
39
    {
40
        $tableFields = $this->getColumnNames($this->model, $this->dbConnection);
41
42
        $unexpectedFields = self::filterClassAttributes($tableFields, $associative1DArray);
43
44
        if (count($unexpectedFields) > 0) {
45
            throw TableFieldUndefinedException::create($unexpectedFields, 'needs to be created as a table field');
46
        }
47
48
        unset($associative1DArray[0]);
49
50
        if (is_null($dbConn)) {
51
            $dbConn = $this->dbConnection;
52
        }
53
54
        return $this->insertRecord($dbConn, $tableName, $associative1DArray);
55
    }
56
57
    /**
58
     * This method runs the insertion query.
59
     *
60
     * @param  $dbConn
61
     * @param  $tableName
62
     * @param  $associative1DArray
63
     *
64
     * @return bool true
65
     */
66
    private function insertRecord($dbConn, $tableName, $associative1DArray)
67
    {
68
        $insertQuery = 'INSERT INTO '.$tableName;
69
70
        $TableValues = implode(',', array_keys($associative1DArray));
71
72
        foreach ($associative1DArray as $field => $value) {
73
            $FormValues[] = "'".trim(addslashes($value))."'";
0 ignored issues
show
Coding Style Comprehensibility introduced by
$FormValues was never initialized. Although not strictly required by PHP, it is generally a good practice to add $FormValues = array(); before regardless.

Adding an explicit array definition is generally preferable to implicit array definition as it guarantees a stable state of the code.

Let’s take a look at an example:

foreach ($collection as $item) {
    $myArray['foo'] = $item->getFoo();

    if ($item->hasBar()) {
        $myArray['bar'] = $item->getBar();
    }

    // do something with $myArray
}

As you can see in this example, the array $myArray is initialized the first time when the foreach loop is entered. You can also see that the value of the bar key is only written conditionally; thus, its value might result from a previous iteration.

This might or might not be intended. To make your intention clear, your code more readible and to avoid accidental bugs, we recommend to add an explicit initialization $myArray = array() either outside or inside the foreach loop.

Loading history...
74
        }
75
76
        $splittedTableValues = implode(',', $FormValues);
0 ignored issues
show
Bug introduced by
The variable $FormValues does not seem to be defined for all execution paths leading up to this point.

If you define a variable conditionally, it can happen that it is not defined for all execution paths.

Let’s take a look at an example:

function myFunction($a) {
    switch ($a) {
        case 'foo':
            $x = 1;
            break;

        case 'bar':
            $x = 2;
            break;
    }

    // $x is potentially undefined here.
    echo $x;
}

In the above example, the variable $x is defined if you pass “foo” or “bar” as argument for $a. However, since the switch statement has no default case statement, if you pass any other value, the variable $x would be undefined.

Available Fixes

  1. Check for existence of the variable explicitly:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        if (isset($x)) { // Make sure it's always set.
            echo $x;
        }
    }
    
  2. Define a default value for the variable:

    function myFunction($a) {
        $x = ''; // Set a default which gets overridden for certain paths.
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
        }
    
        echo $x;
    }
    
  3. Add a value for the missing path:

    function myFunction($a) {
        switch ($a) {
            case 'foo':
                $x = 1;
                break;
    
            case 'bar':
                $x = 2;
                break;
    
            // We add support for the missing case.
            default:
                $x = '';
                break;
        }
    
        echo $x;
    }
    
Loading history...
77
78
        $insertQuery .= ' ('.$TableValues.')';
79
        $insertQuery .= ' VALUES ('.$splittedTableValues.')';
80
81
        $executeQuery = $dbConn->exec($insertQuery);
82
83
        if ($executeQuery) {
84
            return true;
85
        }
86
87
        return false;
88
    }
89
90
    /**
91
     * This method updates any table by supplying 3 parameter.
92
     *
93
     * @params: $updateParams, $tableName, $associative1DArray
94
     *
95
     * @return bool true or false
96
     */
97
    public function update(array $updateParams, $tableName, $associative1DArray, $dbConn = null)
98
    {
99
        $sql = '';
100
101
        if (is_null($dbConn)) {
102
            $dbConn = $this->dbConnection;
103
        }
104
105
        $updateSql = "UPDATE `$tableName` SET ";
106
107
        unset($associative1DArray['id']);
108
109
        $unexpectedFields = self::filterClassAttributes($this->getColumnNames($this->model, $this->dbConnection), $associative1DArray);
110
111
        if (count($unexpectedFields) > 0) {
112
            throw TableFieldUndefinedException::create($unexpectedFields, 'needs to be created as a table field');
113
        }
114
115
        foreach ($associative1DArray as $field => $value) {
116
            $sql .= "`$field` = '$value'".',';
117
        }
118
119
        $updateSql .= $this->prepareUpdateQuery($sql);
120
121
        foreach ($updateParams as $key => $val) {
122
            $updateSql .= " WHERE $key = $val";
123
        }
124
125
        $stmt = $dbConn->prepare($updateSql);
126
127
        $boolResponse = $stmt->execute();
128
129
        if ($boolResponse) {
130
            return true;
131
        }
132
133
        return false;
134
    }
135
136
   /**
137
    * This method retrieves record from a table.
138
    *
139
    * @params int id, string tableName
140
    *
141
    * @return array
142
    */
143
   public static function read($id, $tableName, $dbConn = null)
144
   {
145
       $tableData = [];
146
147
       if (is_null($dbConn)) {
148
           $dbConn = new DatabaseConnection();
149
       }
150
151
       $sql = $id ? 'SELECT * FROM '.$tableName.' WHERE id = '.$id : 'SELECT * FROM '.$tableName;
152
153
       $stmt = $dbConn->prepare($sql);
154
       $stmt->bindValue(':table', $tableName);
155
       $stmt->bindValue(':id', $id);
156
       $stmt->execute();
157
158
       $results = $stmt->fetchAll(PDO::FETCH_ASSOC);
159
160
       foreach ($results as $result) {
161
           array_push($tableData, $result);
162
       }
163
164
       return $tableData;
165
   }
166
167
  /**
168
   * This method deletes a record  from a table row.
169
   *
170
   * @params int id, string tableName
171
   *
172
   * @return bool true or false
173
   */
174
  public static function delete($id, $tableName, $dbConn = null)
175
  {
176
      if (is_null($dbConn)) {
177
          $dbConn = new DatabaseConnection();
178
      }
179
180
      $sql = 'DELETE FROM '.$tableName.' WHERE id = '.$id;
181
182
      $boolResponse = $dbConn->exec($sql);
183
184
      if ($boolResponse) {
185
          return true;
186
      }
187
188
      throw NoRecordDeletionException::create('Record deletion unsuccessful because id does not match any record');
189
  }
190
191
  /**
192
   * This method checks if the magic setters array is the same as the table columns.
193
   *
194
   * @param array $tableColumn
195
   * @param array $userSetterArray
196
   *
197
   * @return array $unexpectedFields
198
   */
199
  public static function filterClassAttributes(array $tableColumn, array $userSetterArray)
200
  {
201
      $unexpectedFields = [];
202
203
      foreach ($userSetterArray as $key => $val) {
204
          if (!in_array($key, $tableColumn)) {
205
              $unexpectedFields[] = $key;
206
          }
207
      }
208
209
      return $unexpectedFields;
210
  }
211
212
  /**
213
   * This method returns sql query.
214
   *
215
   * @param $sql
216
   *
217
   * @return string
218
   */
219
  public function prepareUpdateQuery($sql)
220
  {
221
      $splittedQuery = explode(',', $sql);
222
223
      array_pop($splittedQuery);
224
225
      $mergeData = implode(',', $splittedQuery);
226
227
      return $mergeData;
228
  }
229
230
  /**
231
   * @param array $params
232
   * @param $tableName
233
   * @param $dbConn
234
   *
235
   * @throws EmptyArrayException
236
   *
237
   * @return bool
238
   */
239
  public function findAndWhere($params, $tableName, $dbConn = null)
240
  {
241
      if (is_null($dbConn)) {
242
          $dbConn = $this->dbConnection;
243
      }
244
245
      if (is_array($params) && !empty($params)) {
246
          $sql = 'SELECT * FROM '.$tableName;
247
248
          foreach ($params as $key => $val) {
249
              $sql .= " WHERE `$key` = '$val'";
250
          }
251
252
          $statement = $dbConn->prepare($sql);
253
          $statement->execute();
254
255
          $returnedRowNumbers = $statement->rowCount();
256
257
          return $returnedRowNumbers ? true : false;
258
      }
259
260
      throw EmptyArrayException::create('Array Expected: parameter passed to this function is not an array');
261
  }
262
263
  /**
264
   * This method returns column fields of a particular table.
265
   *
266
   * @param $table
267
   * @param $conn
268
   *
269
   * @return array
270
   */
271
  public function getColumnNames($table, $dbConn = null)
272
  {
273
      $tableFields = [];
274
275
      if (is_null($dbConn)) {
276
          $dbConn = $this->dbConnection;
277
      }
278
279
      $sql = 'SHOW COLUMNS FROM '.$table;
280
281
      $stmt = $dbConn->prepare($sql);
282
      $stmt->bindValue(':table', $table, PDO::PARAM_STR);
283
      $stmt->execute();
284
285
      $results = $stmt->fetchAll(PDO::FETCH_ASSOC);
286
287
      foreach ($results as $result) {
288
          array_push($tableFields, $result['Field']);
289
      }
290
291
      return $tableFields;
292
  }
293
}
294