Completed
Push — master ( c00f94...0cf580 )
by Brett
03:12
created

AuditEntry::hasRelatedData()   B

↳ Parent: AuditEntry

Complexity

Conditions 5
Paths 5

Duplication

Lines 0
Ratio 0 %

Size

Total Lines 16
Code Lines 10

Code Coverage

Tests 0
CRAP Score 30

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 5
eloc 10
nc 5
nop 0
dl 0
loc 16
rs 8.8571
c 1
b 0
f 0
ccs 0
cts 0
cp 0
crap 30
1
<?php
2
3
namespace bedezign\yii2\audit\models;
4
5
use bedezign\yii2\audit\Audit;
6
use bedezign\yii2\audit\components\db\ActiveRecord;
7
use bedezign\yii2\audit\components\Helper;
8
use Yii;
9
use yii\db\ActiveQuery;
10
use yii\db\Expression;
11
12
/**
13
 * AuditEntry
14
 * @package bedezign\yii2\audit\models
15
 *
16
 * @property int               $id
17
 * @property string            $created
18
 * @property float             $duration
19
 * @property int               $user_id        0 means anonymous
20
 * @property string            $ip
21
 * @property string            $route
22
 * @property int               $memory_max
23
 * @property string            $request_method
24
 * @property string            $ajax
25
 *
26
 * @property AuditError[]      $linkedErrors
27
 * @property AuditJavascript[] $javascripts
28
 * @property AuditTrail[]      $trails
29
 * @property AuditMail[]       $mails
30
 * @property AuditData[]       $data
31
 */
32
class AuditEntry extends ActiveRecord
33
{
34
    /**
35
     * @var bool
36
     */
37
    protected $autoSerialize = false;
38
39
    /**
40
     * @inheritdoc
41 57
     */
42
    public static function tableName()
43 57
    {
44
        return '{{%audit_entry}}';
45
    }
46
47
    /**
48
     * @param bool $initialise
49
     * @return static
50 113
     */
51
    public static function create($initialise = true)
52 39
    {
53 74
        $entry = new static;
54 39
        if ($initialise)
55
            $entry->record();
56 113
57
        return $entry;
58
    }
59
60
    /**
61
     * Returns all linked AuditError instances
62
     * (Called `linkedErrors()` to avoid confusion with the `getErrors()` method)
63
     * @return ActiveQuery
64 3
     */
65
    public function getLinkedErrors()
66 3
    {
67
        return static::hasMany(AuditError::className(), ['entry_id' => 'id']);
68
    }
69
70
    /**
71
     * Returns all linked AuditTrail instances
72
     * @return ActiveQuery
73 3
     */
74
    public function getTrails()
75 3
    {
76
        return static::hasMany(AuditTrail::className(), ['entry_id' => 'id']);
77
    }
78
79
    /**
80
     * Returns all linked AuditMail instances
81
     * @return ActiveQuery
82 3
     */
83
    public function getMails()
84 3
    {
85
        return static::hasMany(AuditMail::className(), ['entry_id' => 'id']);
86
    }
87
88
    /**
89
     * Returns all linked AuditJavascript instances
90
     * @return ActiveQuery
91 3
     */
92
    public function getJavascripts()
93 3
    {
94
        return static::hasMany(AuditJavascript::className(), ['entry_id' => 'id']);
95
    }
96
97
    /**
98
     * Returns all linked data records
99
     * @return ActiveQuery
100 1
     */
101
    public function getData()
102 1
    {
103
        return static::hasMany(AuditData::className(), ['entry_id' => 'id'])->indexBy('type');
104
    }
105
106
    /**
107
     * Writes a number of associated data records in one go.
108
     * @param      $batchData
109
     * @param bool $compact
110
     * @throws \yii\db\Exception
111 38
     */
112
    public function addBatchData($batchData, $compact = true)
113 38
    {
114 38
        $columns = ['entry_id', 'type', 'created', 'data'];
115 38
        $rows = [];
116 14
        $params = [];
117
        $date = date('Y-m-d H:i:s');
118
        // Some database like postgres depend on the data being escaped correctly.
119
        // PDO can take care of this if you define the field as a LOB (Large OBject), but unfortunately Yii does threat values
120
        // for batch inserts the same way. This code adds a number of literals instead of the actual values
121 14
        // so that they can be bound right before insert and still get escaped correctly
122 14
        foreach ($batchData as $type => $data) {
123 14
            $param = ':data_' . str_replace('/', '_', $type);
124 14
            $rows[] = [$this->id, $type, $date, new Expression($param)];
125 14
            $params[$param] = [Helper::serialize($data, $compact), \PDO::PARAM_LOB];
126 14
        }
127 38
        static::getDb()->createCommand()->batchInsert(AuditData::tableName(), $columns, $rows)->bindValues($params)->execute();
128
    }
129
130
    /**
131
     * @param $type
132
     * @param $data
133
     * @param bool|true $compact
134
     * @throws \yii\db\Exception
135 2
     */
136
    public function addData($type, $data, $compact = true)
137
    {
138
        // Make sure to mark data as a large object so it gets escaped
139 2
        $record = [
140 2
            'entry_id' => $this->id,
141 2
            'type' => $type,
142 2
            'created' => date('Y-m-d H:i:s'),
143 2
            'data' => [Helper::serialize($data, $compact), \PDO::PARAM_LOB],
144 2
        ];
145 2
        static::getDb()->createCommand()->insert(AuditData::tableName(), $record)->execute();
146
    }
147
148
    /**
149
     * Records the current application state into the instance.
150 113
     */
151
    public function record()
152 113
    {
153 39
        $app = Yii::$app;
154
        $request = $app->request;
155 39
156 113
        $this->route = $app->requestedAction ? $app->requestedAction->uniqueId : null;
157 39
        if ($request instanceof \yii\web\Request) {
158 39
            $this->user_id        = Audit::getInstance()->getUserId();
159 39
            $this->ip             = $request->userIP;
160 39
            $this->ajax           = $request->isAjax;
161 39
            $this->request_method = $request->method;
162 39
        } else if ($request instanceof \yii\console\Request) {
163
            $this->request_method = 'CLI';
164 74
        }
165
166 39
        $this->save(false);
167 113
    }
168
169
    /**
170
     * @return bool
171
     */
172 68
    public function finalize()
173
    {
174 68
        $app = Yii::$app;
175 24
        $request = $app->request;
176
177 24
        if (!$this->user_id && $request instanceof \yii\web\Request) {
178 24
            $this->user_id = Audit::getInstance()->getUserId();
179 24
        }
180 24
181
        $this->duration = microtime(true) - YII_BEGIN_TIME;
182 24
        $this->memory_max = memory_get_peak_usage();
183 24
        return $this->save(false, ['duration', 'memory_max', 'user_id']);
184 24
    }
185
186
    /**
187
     * @return array
188
     */
189
    public function attributeLabels()
190 5
    {
191
        return [
192
            'id'             => Yii::t('audit', 'Entry ID'),
193 5
            'created'        => Yii::t('audit', 'Created'),
194 5
            'ip'             => Yii::t('audit', 'IP'),
195 5
            'duration'       => Yii::t('audit', 'Duration'),
196 5
            'user_id'        => Yii::t('audit', 'User'),
197 5
            'memory_max'     => Yii::t('audit', 'Memory'),
198 5
            'request_method' => Yii::t('audit', 'Request Method'),
199 5
        ];
200 5
    }
201
202
    /**
203
     * @return bool
204
     */
205
    public function hasRelatedData()
206
    {
207
        if ($this->getLinkedErrors()->count()) {
208
            return true;
209
        }
210
        if ($this->getJavascripts()->count()) {
211
            return true;
212
        }
213
        if ($this->getMails()->count()) {
214
            return true;
215
        }
216
        if ($this->getTrails()->count()) {
217
            return true;
218
        }
219
        return false;
220
    }
221
222
}
223