Completed
Push — master ( 1857e6...d96bec )
by Joao
03:02
created

src/Database/DBPgsqlFunctions.php (3 issues)

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
3
namespace ByJG\AnyDataset\Database;
4
5
class DBPGSqlFunctions extends DBBaseFunctions
6
{
7
8 View Code Duplication
    function concat($s1, $s2 = null)
9
    {
10
        for ($i = 0, $numArgs = func_num_args(); $i < $numArgs; $i++) {
11
            $var = func_get_arg($i);
12
            $sql .= ($i == 0 ? "" : " || ") . $var;
0 ignored issues
show
The variable $sql 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...
13
        }
14
15
        return $sql;
16
    }
17
18
    /**
19
     * Given a SQL returns it with the proper LIMIT or equivalent method included
20
     * @param string $sql
21
     * @param int $start
22
     * @param int $qty
23
     * @return string
24
     */
25 View Code Duplication
    function limit($sql, $start, $qty)
26
    {
27
        if (strpos($sql, ' LIMIT ') === false) {
28
            return $sql .= " LIMIT $qty OFFSET $start ";
29
        } else {
30
            return $sql;
31
        }
32
    }
33
34
    /**
35
     * Given a SQL returns it with the proper TOP or equivalent method included
36
     * @param string $sql
37
     * @param int $qty
38
     * @return string
39
     */
40
    function top($sql, $qty)
41
    {
42
        return $this->limit($sql, 0, $qty);
43
    }
44
45
    /**
46
     * Return if the database provider have a top or similar function
47
     * @return unknown_type
48
     */
49
    function hasTop()
50
    {
51
        return true;
0 ignored issues
show
Bug Best Practice introduced by
The return type of return true; (boolean) is incompatible with the return type declared by the interface ByJG\AnyDataset\Database...ctionsInterface::hasTop of type ByJG\AnyDataset\Database\unknown_type.

If you return a value from a function or method, it should be a sub-type of the type that is given by the parent type f.e. an interface, or abstract method. This is more formally defined by the Lizkov substitution principle, and guarantees that classes that depend on the parent type can use any instance of a child type interchangably. This principle also belongs to the SOLID principles for object oriented design.

Let’s take a look at an example:

class Author {
    private $name;

    public function __construct($name) {
        $this->name = $name;
    }

    public function getName() {
        return $this->name;
    }
}

abstract class Post {
    public function getAuthor() {
        return 'Johannes';
    }
}

class BlogPost extends Post {
    public function getAuthor() {
        return new Author('Johannes');
    }
}

class ForumPost extends Post { /* ... */ }

function my_function(Post $post) {
    echo strtoupper($post->getAuthor());
}

Our function my_function expects a Post object, and outputs the author of the post. The base class Post returns a simple string and outputting a simple string will work just fine. However, the child class BlogPost which is a sub-type of Post instead decided to return an object, and is therefore violating the SOLID principles. If a BlogPost were passed to my_function, PHP would not complain, but ultimately fail when executing the strtoupper call in its body.

Loading history...
52
    }
53
54
    /**
55
     * Return if the database provider have a limit function
56
     * @return bool
57
     */
58
    function hasLimit()
59
    {
60
        return true;
61
    }
62
63
    /**
64
     * Format date column in sql string given an input format that understands Y M D
65
     * @param string $fmt
66
     * @param string $col
67
     * @return string
68
     * @example $db->getDbFunctions()->SQLDate("d/m/Y H:i", "dtcriacao")
69
     */
70
    function sqlDate($fmt, $col = false)
71
    {
72
        if (!$col) $col = $this->sysTimeStamp;
0 ignored issues
show
Bug Best Practice introduced by
The expression $col of type false|string is loosely compared to false; this is ambiguous if the string can be empty. You might want to explicitly use === false instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For string values, the empty string '' is a special case, in particular the following results might be unexpected:

''   == false // true
''   == null  // true
'ab' == false // false
'ab' == null  // false

// It is often better to use strict comparison
'' === false // false
'' === null  // false
Loading history...
73
        $s = 'TO_CHAR(' . $col . ",'";
74
75
        $len = strlen($fmt);
76
        for ($i = 0; $i < $len; $i++) {
77
            $ch = $fmt[$i];
78
            switch ($ch) {
79
                case 'Y':
80
                case 'y':
81
                    $s .= 'YYYY';
82
                    break;
83
                case 'Q':
84
                case 'q':
85
                    $s .= 'Q';
86
                    break;
87
88
                case 'M':
89
                    $s .= 'Mon';
90
                    break;
91
92
                case 'm':
93
                    $s .= 'MM';
94
                    break;
95
                case 'D':
96
                case 'd':
97
                    $s .= 'DD';
98
                    break;
99
100
                case 'H':
101
                    $s.= 'HH24';
102
                    break;
103
104
                case 'h':
105
                    $s .= 'HH';
106
                    break;
107
108
                case 'i':
109
                    $s .= 'MI';
110
                    break;
111
112
                case 's':
113
                    $s .= 'SS';
114
                    break;
115
116
                case 'a':
117
                case 'A':
118
                    $s .= 'AM';
119
                    break;
120
121
                default:
122
                    // handle escape characters...
123
                    if ($ch == '\\') {
124
                        $i++;
125
                        $ch = substr($fmt, $i, 1);
126
                    }
127
                    if (strpos('-/.:;, ', $ch) !== false) {
128
                        $s .= $ch;
129
                    } else {
130
                        $s .= '"' . $ch . '"';
131
                    }
132
            }
133
        }
134
        return $s . "')";
135
    }
136
137
    /**
138
     * Format a string date to a string database readable format.
139
     *
140
     * @param string $date
141
     * @param string $dateFormat
142
     * @return string
143
     */
144
    function toDate($date, $dateFormat)
145
    {
146
        return parent::toDate($date, $dateFormat);
147
    }
148
149
    /**
150
     * Format a string database readable format to a string date in a free format.
151
     *
152
     * @param string $date
153
     * @param string $dateFormat
154
     * @return string
155
     */
156
    function fromDate($date, $dateFormat)
157
    {
158
        return parent::fromDate($date, $dateFormat);
159
    }
160
161
    function executeAndGetInsertedId($dbdataset, $sql, $param, $sequence = null)
162
    {
163
        $id = parent::executeAndGetInsertedId($dbdataset, $sql, $param);
164
        $it = $dbdataset->getIterator(SQLHelper::createSafeSQL("select currval(':sequence') id",
165
                array(':sequence' => $sequence)));
166
        if ($it->hasNext()) {
167
            $sr = $it->moveNext();
168
            $id = $sr->getField("id");
169
        }
170
171
        return $id;
172
    }
173
}
174