Passed
Push — master ( 329e83...2ea8eb )
by Andre
13:17 queued 10:08
created

Provider::canView()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 1
c 0
b 0
f 0
nc 1
nop 1
dl 0
loc 3
rs 10
1
<?php
2
/**
3
 * Socializer plugin for Craft CMS 3.x
4
 *
5
 * @link      https://enupal.com/
6
 * @copyright Copyright (c) 2019 Enupal LLC
7
 */
8
9
namespace enupal\socializer\elements;
10
11
use Craft;
12
use craft\base\Element;
13
use craft\behaviors\FieldLayoutBehavior;
14
use craft\elements\actions\Restore;
15
use craft\elements\db\ElementQueryInterface;
16
use craft\elements\User;
17
use craft\helpers\UrlHelper;
18
19
use enupal\socializer\elements\actions\Delete;
20
use enupal\socializer\records\Provider as ProviderRecord;
21
use craft\validators\UniqueValidator;
22
use enupal\socializer\elements\db\ProvidersQuery;
23
use enupal\socializer\Socializer;
24
use enupal\socializer\validators\EnabledValidator;
25
use Hybridauth\Adapter\AdapterInterface;
26
use Hybridauth\Provider\Apple;
27
use yii\base\Model;
28
29
/**
30
 * Provider represents a provider element.
31
 *
32
 */
33
class Provider extends Element
34
{
35
    /**
36
     * @var string Name.
37
     */
38
    public $name;
39
40
    /**
41
     * @var string Handle.
42
     */
43
    public $handle;
44
45
    /**
46
     * @var string Type.
47
     */
48
    public $type;
49
50
    /**
51
     * @var string Client ID.
52
     */
53
    public $clientId;
54
55
    /**
56
     * @var string Client Secret.
57
     */
58
    public $clientSecret;
59
60
    /**
61
     * @var string Field Mapping
62
     */
63
    public $fieldMapping;
64
65
    /**
66
     * @inheritdoc
67
     */
68
    public function canView(User $user): bool
69
    {
70
        return true;
71
    }
72
73
    /**
74
     * @inheritdoc
75
     */
76
    public function behaviors(): array
77
    {
78
        return array_merge(parent::behaviors(), [
79
            'fieldLayout' => [
80
                'class' => FieldLayoutBehavior::class,
81
                'elementType' => self::class
82
            ],
83
        ]);
84
    }
85
86
    public function init(): void
87
    {
88
        parent::init();
89
90
        $this->setScenario(Model::SCENARIO_DEFAULT);
91
92
        if ($this->fieldMapping && is_string($this->fieldMapping)) {
93
            $this->fieldMapping = json_decode($this->fieldMapping, true);
94
        }
95
    }
96
97
    /**
98
     * Returns the field context this element's content uses.
99
     *
100
     * @access protected
101
     * @return string
102
     */
103
    public function getFieldContext(): string
104
    {
105
        return 'enupalSocializer:' . $this->id;
106
    }
107
108
    /**
109
     * Returns the element type name.
110
     *
111
     * @return string
112
     */
113
    public static function displayName(): string
114
    {
115
        return Craft::t('enupal-socializer','Socializer');
116
    }
117
118
    /**
119
     * @inheritdoc
120
     */
121
    public static function refHandle(): ?string
122
    {
123
        return 'socializer-providers';
124
    }
125
126
    /**
127
     * @inheritdoc
128
     */
129
    public static function hasContent(): bool
130
    {
131
        return true;
132
    }
133
134
    /**
135
     * @inheritdoc
136
     */
137
    public static function hasTitles(): bool
138
    {
139
        return false;
140
    }
141
142
    /**
143
     * @inheritdoc
144
     */
145
    public static function isLocalized(): bool
146
    {
147
        return false;
148
    }
149
150
    /**
151
     * @inheritdoc
152
     */
153
    public static function hasStatuses(): bool
154
    {
155
        return true;
156
    }
157
158
    /**
159
     * @inheritdoc
160
     */
161
    public function getFieldLayout(): ?\craft\models\FieldLayout
162
    {
163
        $behaviors = $this->getBehaviors();
164
        $fieldLayout = $behaviors['fieldLayout'];
165
166
        return $fieldLayout->getFieldLayout();
167
    }
168
169
    /**
170
     * @inheritdoc
171
     */
172
    public function getCpEditUrl(): ?string
173
    {
174
        return UrlHelper::cpUrl(
175
            'enupal-socializer/providers/edit/' . $this->id
176
        );
177
    }
178
179
    /**
180
     * Use the name as the string representation.
181
     *
182
     * @return string
183
     */
184
    public function __toString(): string
185
    {
186
        return $this->name;
187
    }
188
189
    /**
190
     * @inheritdoc
191
     *
192
     * @return ProvidersQuery The newly created [[ProvidersQuery]] instance.
193
     */
194
    public static function find(): ElementQueryInterface
195
    {
196
        return new ProvidersQuery(get_called_class());
197
    }
198
199
    /**
200
     * @inheritdoc
201
     */
202
    protected static function defineSources(string $context = null): array
203
    {
204
        $sources = [
205
            [
206
                'key' => '*',
207
                'label' => Craft::t('enupal-socializer','All Providers'),
208
            ]
209
        ];
210
211
        // @todo add groups
212
213
        return $sources;
214
    }
215
216
    /**
217
     * @inheritdoc
218
     */
219
    protected static function defineActions(string $source = null): array
220
    {
221
        $actions = [];
222
223
        // Delete
224
        $actions[] = Craft::$app->getElements()->createAction([
225
            'type' => Delete::class
226
        ]);
227
228
        $actions[] = Craft::$app->getElements()->createAction([
229
            'type' => Restore::class,
230
            'successMessage' => 'Providers restored'
231
        ]);
232
233
        return $actions;
234
    }
235
236
    /**
237
     * @inheritdoc
238
     */
239
    protected static function defineSearchableAttributes(): array
240
    {
241
        return ['name', 'type'];
242
    }
243
244
    /**
245
     * @inheritdoc
246
     */
247
    protected static function defineSortOptions(): array
248
    {
249
        $attributes = [
250
            'elements.dateCreated' => Craft::t('enupal-socializer','Date Created'),
251
            'name' => Craft::t('enupal-socializer','Name')
252
        ];
253
254
        return $attributes;
255
    }
256
257
    /**
258
     * @inheritdoc
259
     */
260
    protected static function defineTableAttributes(): array
261
    {
262
        $attributes = [];
263
        $attributes['name'] = ['label' => Craft::t('enupal-socializer','Name')];
264
        $attributes['handle'] = ['label' => Craft::t('enupal-socializer','Handle')];
265
        $attributes['dateCreated'] = ['label' => Craft::t('enupal-socializer','Date Created')];
266
267
        return $attributes;
268
    }
269
270
    /**
271
     * @inheritdoc
272
     */
273
    protected static function defineDefaultTableAttributes(string $source): array
274
    {
275
        $attributes = ['name', 'handle' , 'dateCreated'];
276
277
        return $attributes;
278
    }
279
280
    /**
281
     * @inheritdoc
282
     * @throws \yii\base\InvalidConfigException
283
     * @throws \yii\base\InvalidConfigException
284
     */
285
    protected function tableAttributeHtml(string $attribute): string
286
    {
287
        switch ($attribute) {
288
            case 'dateCreated':
289
                {
290
                    return $this->dateCreated->/** @scrutinizer ignore-call */ format("Y-m-d H:i");
291
                }
292
        }
293
294
        return parent::tableAttributeHtml($attribute);
295
    }
296
297
    /**
298
     * @inheritdoc
299
     */
300
    public function datetimeAttributes(): array
301
    {
302
        $attributes = parent::datetimeAttributes();
303
        $attributes[] = 'dateCreated';
304
        return $attributes;
305
    }
306
307
    /**
308
     * @inheritdoc
309
     * @param bool $isNew
310
     * @throws \Exception
311
     */
312
    public function afterSave(bool $isNew): void
313
    {
314
        $record = new ProviderRecord();
315
316
        if (!$isNew) {
317
            $record = ProviderRecord::findOne($this->id);
318
319
            if (!$record) {
0 ignored issues
show
introduced by
$record is of type yii\db\ActiveRecord, thus it always evaluated to true.
Loading history...
320
                throw new \Exception('Invalid Provider ID: ' . $this->id);
321
            }
322
        } else {
323
            $record->id = $this->id;
324
        }
325
326
        $record->name = $this->name;
0 ignored issues
show
Bug Best Practice introduced by
The property name does not exist. Although not strictly required by PHP, it is generally a best practice to declare properties explicitly.
Loading history...
327
        $record->type = $this->type;
328
        $record->handle = $this->handle;
329
330
        $record->clientId = $this->clientId;
331
        $record->clientSecret = $this->clientSecret;
332
        $record->fieldMapping = $this->fieldMapping;
333
334
        if (is_array($record->fieldMapping)){
0 ignored issues
show
introduced by
The condition is_array($record->fieldMapping) is always false.
Loading history...
335
            $record->fieldMapping = json_encode($record->fieldMapping);
336
        };
337
338
        $record->save(false);
339
340
        parent::afterSave($isNew);
341
    }
342
343
    /**
344
     * @return AdapterInterface
345
     */
346
    public function getAdapter()
347
    {
348
        return new $this->type($this->getProviderConfig());
349
    }
350
351
    /**
352
     * @return array
353
     */
354
    private function getProviderConfig()
355
    {
356
        // @todo add event to give a chance to update default config
357
        $config = [
358
            'callback' => Socializer::$app->settings->getCallbackUrl(),
359
            'keys' => [
360
                'id' => $this->getClientId(),
361
                'secret' => $this->getClientSecret()
362
            ],
363
            'includeEmail' => true
364
        ];
365
366
        if ($this->type === Apple::class && Socializer::$app->settings->validateAppleSettings()) {
367
            $configSettings = Socializer::$app->settings->getConfigSettings();
368
369
            if (isset($configSettings['apple'])) {
370
                $config = $configSettings['apple'];
371
                $config['callback'] = Socializer::$app->settings->getCallbackUrl();
372
            }
373
        }
374
375
        return $config;
376
    }
377
378
    /**
379
     * @return string
380
     */
381
    public function getClientId()
382
    {
383
        return Craft::parseEnv($this->clientId);
0 ignored issues
show
Deprecated Code introduced by
The function Craft::parseEnv() has been deprecated: in 3.7.29. [[App::parseEnv()]] should be used instead. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

383
        return /** @scrutinizer ignore-deprecated */ Craft::parseEnv($this->clientId);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
384
    }
385
386
    /**
387
     * @return string
388
     */
389
    public function getClientSecret()
390
    {
391
        return Craft::parseEnv($this->clientSecret);
0 ignored issues
show
Deprecated Code introduced by
The function Craft::parseEnv() has been deprecated: in 3.7.29. [[App::parseEnv()]] should be used instead. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

391
        return /** @scrutinizer ignore-deprecated */ Craft::parseEnv($this->clientSecret);

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
392
    }
393
394
    /**
395
     * @return array|null
396
     */
397
    public function getCurrentUserToken()
398
    {
399
        return Socializer::$app->tokens->getCurrentUserToken($this->id);
0 ignored issues
show
Bug Best Practice introduced by
The expression return enupal\socializer...entUserToken($this->id) also could return the type craft\base\ElementInterface which is incompatible with the documented return type array|null.
Loading history...
400
    }
401
402
    /**
403
     * @inheritdoc
404
     */
405
    public function rules(): array
406
    {
407
        $rules = parent::rules();
408
        $rules[] = [['name', 'type'], 'required'];
409
        $rules[] = [['name', 'type'], 'string', 'max' => 255];
410
        $rules[] = [['name', 'type'], UniqueValidator::class, 'targetClass' => ProviderRecord::class];
411
        $rules[] = [['name', 'type'], 'required'];
412
        $rules[] = [['clientId'], EnabledValidator::class];
413
414
        return $rules;
415
    }
416
417
    public function isAppleProvider()
418
    {
419
        return $this->type === Apple::class;
420
    }
421
}