Passed
Branch feature/cropping (2bd0b6)
by Philippe
05:59
created

AssetTrait::addFiles()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 9
Code Lines 5

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 6
CRAP Score 1

Importance

Changes 0
Metric Value
c 0
b 0
f 0
dl 0
loc 9
ccs 6
cts 6
cp 1
rs 9.6666
cc 1
eloc 5
nc 1
nop 3
crap 1
1
<?php
2
3
namespace Thinktomorrow\AssetLibrary\Traits;
4
5
use Illuminate\Support\Collection;
6
use Thinktomorrow\AssetLibrary\Models\Asset;
7
use Thinktomorrow\AssetLibrary\Models\AssetUploader;
8
use Thinktomorrow\Locale\Locale;
9
10
trait AssetTrait
11
{
12
    /**
13
     * @return mixed
14
     */
15 19
    public function assets()
16
    {
17 19
        return $this->morphToMany(Asset::class, 'entity', 'asset_pivots')->withPivot('type', 'locale');
0 ignored issues
show
Bug introduced by
It seems like morphToMany() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
18
    }
19
20
    /**
21
     * @param string $type
22
     * @param string $locale
0 ignored issues
show
Documentation introduced by
Should the type for parameter $locale not be string|null?

This check looks for @param annotations where the type inferred by our type inference engine differs from the declared type.

It makes a suggestion as to what type it considers more descriptive.

Most often this is a case of a parameter that can be null in addition to its declared types.

Loading history...
23
     * @return bool
24
     */
25 4
    public function hasFile($type = '', $locale = null): bool
26
    {
27 4
        $filename = $this->getFilename($type, $locale);
28
29 4
        return (bool) $filename && basename($filename) != 'other.png';
30
    }
31
32
    /**
33
     * @param string $type
34
     * @param string $locale
0 ignored issues
show
Documentation introduced by
Should the type for parameter $locale not be string|null?

This check looks for @param annotations where the type inferred by our type inference engine differs from the declared type.

It makes a suggestion as to what type it considers more descriptive.

Most often this is a case of a parameter that can be null in addition to its declared types.

Loading history...
35
     * @return string
36
     */
37 6
    public function getFilename($type = '', $locale = null): string
38
    {
39 6
        return basename($this->getFileUrl($type, '', $locale));
40
    }
41
42
    /**
43
     * @param string $type
44
     * @param string $size
45
     * @param string $locale
0 ignored issues
show
Documentation introduced by
Should the type for parameter $locale not be string|null?

This check looks for @param annotations where the type inferred by our type inference engine differs from the declared type.

It makes a suggestion as to what type it considers more descriptive.

Most often this is a case of a parameter that can be null in addition to its declared types.

Loading history...
46
     * @return string
47
     */
48 16
    public function getFileUrl($type = '', $size = '', $locale = null): ?string
49
    {
50 16
        if ($this->assets->first() === null || $this->assets->first()->pivot === null) {
0 ignored issues
show
Bug introduced by
The property assets does not exist. Did you maybe forget to declare it?

In PHP it is possible to write to properties without declaring them. For example, the following is perfectly valid PHP code:

class MyClass { }

$x = new MyClass();
$x->foo = true;

Generally, it is a good practice to explictly declare properties to avoid accidental typos and provide IDE auto-completion:

class MyClass {
    public $foo;
}

$x = new MyClass();
$x->foo = true;
Loading history...
51 2
            return null;
52
        }
53
54 16
        $locale = $this->normalizeLocale($locale);
55
56 16
        $assets = $this->assets->where('pivot.type', $type);
57 16
        if ($assets->count() > 1) {
58 5
            $assets = $assets->where('pivot.locale', $locale);
59
        }
60
61 16
        if ($assets->isEmpty()) {
62 1
            return null;
63
        }
64
65 16
        return $assets->first()->getFileUrl($size);
66
    }
67
68
    /**
69
     * Adds a file to this model, accepts a type and locale to be saved with the file.
70
     *
71
     * @param $file
72
     * @param $type
73
     * @param string $locale
0 ignored issues
show
Documentation introduced by
Should the type for parameter $locale not be string|null?

This check looks for @param annotations where the type inferred by our type inference engine differs from the declared type.

It makes a suggestion as to what type it considers more descriptive.

Most often this is a case of a parameter that can be null in addition to its declared types.

Loading history...
74
     */
75 7
    public function addFile($file, $type = '', $locale = null): void
76
    {
77 7
        $locale = $this->normalizeLocale($locale);
78
79 7
        $asset = AssetUploader::upload($file);
80 7
        $asset->attachToModel($this, $type, $locale);
0 ignored issues
show
Bug introduced by
The method attachToModel does only exist in Thinktomorrow\AssetLibrary\Models\Asset, but not in Illuminate\Support\Collection.

It seems like the method you are trying to call exists only in some of the possible types.

Let’s take a look at an example:

class A
{
    public function foo() { }
}

class B extends A
{
    public function bar() { }
}

/**
 * @param A|B $x
 */
function someFunction($x)
{
    $x->foo(); // This call is fine as the method exists in A and B.
    $x->bar(); // This method only exists in B and might cause an error.
}

Available Fixes

  1. Add an additional type-check:

    /**
     * @param A|B $x
     */
    function someFunction($x)
    {
        $x->foo();
    
        if ($x instanceof B) {
            $x->bar();
        }
    }
    
  2. Only allow a single type to be passed if the variable comes from a parameter:

    function someFunction(B $x) { /** ... */ }
    
Loading history...
81 7
    }
82
83
    /**
84
     * Adds multiple files to this model, accepts a type and locale to be saved with the file.
85
     *
86
     * @param $files
87
     * @param $type
88
     * @param string $locale
0 ignored issues
show
Documentation introduced by
Should the type for parameter $locale not be string|null?

This check looks for @param annotations where the type inferred by our type inference engine differs from the declared type.

It makes a suggestion as to what type it considers more descriptive.

Most often this is a case of a parameter that can be null in addition to its declared types.

Loading history...
89
     */
90 3
    public function addFiles($files, $type = '', $locale = null): void
91
    {
92 3
        $files = (array) $files;
93 3
        $locale = $this->normalizeLocale($locale);
94
95 3
        $asset = AssetUploader::upload($files);
96
97 3
        collect($asset)->each->attachToModel($this, $type, $locale);
98 3
    }
99
100
    /**
101
     * @return mixed
102
     */
103
    public function getAllImages()
104
    {
105 1
        $images = $this->assets->filter(function ($asset) {
106 1
            return $asset->getExtensionForFilter() == 'image';
107 1
        });
108
109 1
        return $images;
110
    }
111
112
    /**
113
     * @param null $type
114
     * @param string $locale
0 ignored issues
show
Documentation introduced by
Should the type for parameter $locale not be string|null?

This check looks for @param annotations where the type inferred by our type inference engine differs from the declared type.

It makes a suggestion as to what type it considers more descriptive.

Most often this is a case of a parameter that can be null in addition to its declared types.

Loading history...
115
     * @return mixed
116
     */
117 2
    public function getAllFiles($type = null, $locale = null)
118
    {
119 2
        $locale = $this->normalizeLocale($locale);
120
121 2
        $files = $this->assets->where('pivot.type', $type)->where('pivot.locale', $locale);
122
123 2
        return $files;
124
    }
125
126
    /**
127
     * @param string|null $locale
128
     * @return string
0 ignored issues
show
Documentation introduced by
Should the return type not be null|string?

This check compares the return type specified in the @return annotation of a function or method doc comment with the types returned by the function and raises an issue if they mismatch.

Loading history...
129
     */
130 18
    private function normalizeLocale($locale = null): ?string
131
    {
132 18
        $locale = $locale ?? Locale::getDefault();
133
134 18
        return $locale;
135
    }
136
}
137