Completed
Pull Request — master (#10)
by ARCANEDEV
06:56
created

Category::createMany()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 6
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 3
CRAP Score 1

Importance

Changes 0
Metric Value
dl 0
loc 6
rs 9.4285
c 0
b 0
f 0
ccs 3
cts 3
cp 1
cc 1
eloc 3
nc 1
nop 1
crap 1
1
<?php namespace Arcanesoft\Blog\Models;
2
3
use Arcanedev\Localization\Traits\HasTranslations;
4
use Arcanesoft\Blog\Blog;
5
use Illuminate\Database\Eloquent\SoftDeletes;
6
use Illuminate\Support\Arr;
7
use Illuminate\Support\Str;
8
use Arcanesoft\Blog\Events\Categories as CategoryEvents;
9
10
/**
11
 * Class     Category
12
 *
13
 * @package  Arcanesoft\Blog\Models
14
 * @author   ARCANEDEV <[email protected]>
15
 *
16
 * @property  int             id
17
 * @property  string          name
18
 * @property  string          slug
19
 * @property  \Carbon\Carbon  created_at
20
 * @property  \Carbon\Carbon  updated_at
21
 * @property  \Carbon\Carbon  deleted_at
22
 *
23
 * @property  \Illuminate\Database\Eloquent\Collection  posts
24
 */
25
class Category extends AbstractModel
26
{
27
    /* -----------------------------------------------------------------
28
     |  Constants
29
     | -----------------------------------------------------------------
30
     */
31
32
    const SELECT_CACHE_NAME = 'blog::categories.select-data';
33
34
    /* -----------------------------------------------------------------
35
     |  Traits
36
     | -----------------------------------------------------------------
37
     */
38
39
    use SoftDeletes,
40
        HasTranslations;
41
42
    /* -----------------------------------------------------------------
43
     |  Properties
44
     | -----------------------------------------------------------------
45
     */
46
47
    /**
48
     * The database table used by the model
49
     *
50
     * @var string
51
     */
52
    protected $table = 'categories';
53
54
    /**
55
     * The attributes that are mass assignable
56
     *
57
     * @var array
58
     */
59
    protected $fillable = ['name', 'slug'];
60
61
    /**
62
     * The attributes that should be mutated to dates.
63
     *
64
     * @var array
65
     */
66
    protected $dates = ['deleted_at'];
67
68
    /**
69
     * The attributes that should be cast to native types.
70
     *
71
     * @var array
72
     */
73
    protected $casts = [
74
        'id' => 'integer',
75
    ];
76
77
    /**
78
     * The event map for the model.
79
     *
80
     * @var array
81
     */
82
    protected $dispatchesEvents = [
83
        'creating'  => CategoryEvents\CategoryCreating::class,
84
        'created'   => CategoryEvents\CategoryCreated::class,
85
        'updating'  => CategoryEvents\CategoryUpdating::class,
86
        'updated'   => CategoryEvents\CategoryUpdated::class,
87
        'saving'    => CategoryEvents\CategorySaving::class,
88
        'saved'     => CategoryEvents\CategorySaved::class,
89
        'deleting'  => CategoryEvents\CategoryDeleting::class,
90
        'deleted'   => CategoryEvents\CategoryDeleted::class,
91
        'restoring' => CategoryEvents\CategoryRestoring::class,
92
        'restored'  => CategoryEvents\CategoryRestored::class,
93
    ];
94
95
    /* -----------------------------------------------------------------
96
     |  Relationships
97
     | -----------------------------------------------------------------
98
     */
99
100
    /**
101
     * Relationship with posts.
102
     *
103
     * @return \Illuminate\Database\Eloquent\Relations\HasMany
104
     */
105 2
    public function posts()
106
    {
107 2
        return $this->hasMany(Post::class);
108
    }
109
110
    /* -----------------------------------------------------------------
111
     |  Getters & Setters
112
     | -----------------------------------------------------------------
113
     */
114
115
    /**
116
     * Set the name attribute.
117
     *
118
     * @param  string  $name
119
     *
120
     * @return string
121
     */
122 12
    public function setNameAttribute($name)
123
    {
124 12
        return $this->attributes['name'] = $name;
125
    }
126
127
    /**
128
     * Set the slug attribute.
129
     *
130
     * @param  string  $name
131
     *
132
     * @return string
133
     */
134 12
    public function setSlugAttribute($name)
135
    {
136 12
        return $this->attributes['slug'] = Str::slug($name);
137
    }
138
139
    /**
140
     * Get the translatable attributes.
141
     *
142
     * @return array
143
     */
144 12
    public function getTranslatableAttributes()
145
    {
146 12
        return Blog::instance()->isTranslatable() ? ['name', 'slug'] : [];
147
    }
148
149
    /* -----------------------------------------------------------------
150
     |  Main Methods
151
     | -----------------------------------------------------------------
152
     */
153
154
    /**
155
     * Create a new category.
156
     *
157
     * @param  array  $attributes
158
     *
159
     * @return self
160
     */
161
    public static function createOne(array $attributes)
162
    {
163 12
        return tap(new self, function (self $category) use ($attributes) {
164 12
            $attributes['slug'] = $attributes['slug'] ?? $attributes['name'];
165
166 12
            $category->populate($attributes)->save();
167 12
        });
168
    }
169
170
    /**
171
     * Create many categories.
172
     *
173
     * @param  array  $categories
174
     *
175
     * @return \Illuminate\Support\Collection
176
     */
177
    public static function createMany(array $categories)
178
    {
179 2
        return collect($categories)->transform(function ($attributes) {
180 2
            return static::createOne($attributes);
181 2
        });
182
    }
183
184
    /**
185
     * Update the current category.
186
     *
187
     * @param  array  $attributes
188
     *
189
     * @return self
190
     */
191 4
    public function updateOne(array $attributes)
192
    {
193 4
        $this->populate($attributes)->save();
194
195 4
        return $this;
196
    }
197
198
    /**
199
     * Get the categories options for select input.
200
     *
201
     * @param  bool  $placeholder
202
     *
203
     * @return \Illuminate\Support\Collection
204
     */
205 2
    public static function getSelectData($placeholder = true)
206
    {
207 2
        $minutes = config('arcanesoft.blog.cache.categories.select-data', 5);
208
209
        /** @var  \Illuminate\Database\Eloquent\Collection  $categories */
210 2
        return cache()->remember(self::SELECT_CACHE_NAME, $minutes, function () {
211 2
                $withTranslations = Blog::instance()->isTranslatable();
212
213 2
                return self::all()->mapWithKeys(function (Category $category) use ($withTranslations) {
214
                    return [
215 2
                        $category->id => $withTranslations
216
                            ? implode(' / ', $category->getTranslations('name'))
217 2
                            : $category->name
218
                    ];
219 2
                });
220 2
            })
221 2
            ->toBase()->when($placeholder, function ($categories) {
222
                /** @var  \Illuminate\Support\Collection  $categories */
223 2
                return $categories->prepend(trans('blog::categories.select-category'), 0);
224 2
            });
225
    }
226
227
    /* -----------------------------------------------------------------
228
     |  Check Methods
229
     | -----------------------------------------------------------------
230
     */
231
232
    /**
233
     * Check if category has posts.
234
     *
235
     * @return bool
236
     */
237 2
    public function hasPosts()
238
    {
239 2
        return ! $this->posts->isEmpty();
240
    }
241
242
    /**
243
     * Check if the category is deletable.
244
     *
245
     * @return bool
246
     */
247 2
    public function isDeletable()
248
    {
249 2
        return ! $this->hasPosts();
250
    }
251
252
    /* -----------------------------------------------------------------
253
     |  Other Methods
254
     | -----------------------------------------------------------------
255
     */
256
257
    /**
258
     * Fill the model with an array of attributes.
259
     *
260
     * @param  array  $attributes
261
     *
262
     * @return self
263
     */
264 12
    protected function populate(array $attributes)
265
    {
266 12
        if ( ! Blog::instance()->isTranslatable())
267 8
            return $this->fill($attributes);
268
269 4
        $keys = ['name', 'slug'];
270
271 4
        foreach ($keys as $key) {
272 4
            $this->setTranslations($key, $attributes[$key] ?? []);
273
        }
274
275 4
        return $this->fill(Arr::except($attributes, $keys));
276
    }
277
}
278