Completed
Push — master ( 2b1674...071d4d )
by ARCANEDEV
05:46
created

Post::getShowUrl()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
c 0
b 0
f 0
dl 0
loc 4
ccs 0
cts 2
cp 0
rs 10
cc 1
eloc 2
nc 1
nop 0
crap 2
1
<?php namespace Arcanesoft\Blog\Models;
2
3
use Arcanedev\LaravelSeo\Traits\Seoable;
4
use Carbon\Carbon;
5
use Illuminate\Database\Eloquent\Builder;
6
use Illuminate\Database\Eloquent\SoftDeletes;
7
use Illuminate\Support\Arr;
8
use Illuminate\Support\Collection;
9
use Illuminate\Support\Facades\DB;
10
use Illuminate\Support\HtmlString;
11
use Illuminate\Support\Str;
12
13
/**
14
 * Class     Post
15
 *
16
 * @package  Arcanesoft\Blog\Models
17
 * @author   ARCANEDEV <[email protected]>
18
 *
19
 * @property  int             id
20
 * @property  int             author_id
21
 * @property  int             category_id
22
 * @property  string          title
23
 * @property  string          slug
24
 * @property  string          excerpt
25
 * @property  string          content_raw
26
 * @property  string          content_html
27
 * @property  bool            is_draft
28
 * @property  \Carbon\Carbon  published_at
29
 * @property  \Carbon\Carbon  created_at
30
 * @property  \Carbon\Carbon  updated_at
31
 * @property  \Carbon\Carbon  deleted_at
32
 *
33
 * @property  \Arcanesoft\Contracts\Auth\Models\User  user
34
 * @property  \Arcanesoft\Blog\Models\Category        category
35
 *
36
 * @method  static  \Illuminate\Database\Eloquent\Builder  published()
37
 * @method  static  \Illuminate\Database\Eloquent\Builder  publishedAt(int $year)
38
 */
39
class Post extends AbstractModel
40
{
41
    /* -----------------------------------------------------------------
42
     |  Constants
43
     | -----------------------------------------------------------------
44
     */
45
46
    const STATUS_DRAFT     = 'draft';
47
    const STATUS_PUBLISHED = 'published';
48
49
    /* -----------------------------------------------------------------
50
     |  Traits
51
     | -----------------------------------------------------------------
52
     */
53
54
    use Presenters\PostPresenter,
55
        Seoable,
56
        SoftDeletes;
57
58
    /* -----------------------------------------------------------------
59
     |  Properties
60
     | -----------------------------------------------------------------
61
     */
62
63
    /**
64
     * The database table used by the model
65
     *
66
     * @var string
67
     */
68
    protected $table = 'posts';
69
70
    /**
71
     * The attributes that are mass assignable
72
     *
73
     * @var array
74
     */
75
    protected $fillable = [
76
        'author_id', 'category_id', 'title', 'excerpt', 'content', 'published_at'
77
    ];
78
79
    /**
80
     * The attributes that should be mutated to dates.
81
     *
82
     * @var array
83
     */
84
    protected $dates = ['published_at', 'deleted_at'];
85
86
    /**
87
     * The attributes that should be casted to native types.
88
     *
89
     * @var array
90
     */
91
    protected $casts = [
92
        'author_id'   => 'integer',
93
        'category_id' => 'integer',
94
        'is_draft'    => 'boolean',
95
    ];
96
97
    /* -----------------------------------------------------------------
98
     |  Scopes
99
     | -----------------------------------------------------------------
100
     */
101
102
    /**
103
     * Scope only published posts.
104
     *
105
     * @param  \Illuminate\Database\Eloquent\Builder  $builder
106
     */
107
    public function scopePublished(Builder $builder)
108
    {
109
        $builder->where('is_draft', false)
110
                ->where('published_at', '<=', Carbon::now());
111
    }
112
113
    /**
114
     * Scope only published posts.
115
     *
116
     * @param  \Illuminate\Database\Eloquent\Builder  $builder
117
     * @param  int                                    $year
118
     */
119
    public function scopePublishedAt(Builder $builder, $year)
120
    {
121
        $this->scopePublished($builder);
122
        $builder->where(DB::raw('YEAR(published_at)'), $year);
123
    }
124
125
    /* -----------------------------------------------------------------
126
     |  Relationships
127
     | -----------------------------------------------------------------
128
     */
129
130
    /**
131
     * Author relationship.
132
     *
133
     * @return \Illuminate\Database\Eloquent\Relations\BelongsTo
134
     */
135
    public function author()
136
    {
137
        return $this->belongsTo(
138
            config('auth.providers.users.model', \App\Models\User::class),
139
            'author_id'
140
        );
141
    }
142
143
    /**
144
     * Category relationship.
145
     *
146
     * @return \Illuminate\Database\Eloquent\Relations\BelongsTo
147
     */
148
    public function category()
149
    {
150
        return $this->belongsTo(Category::class);
151
    }
152
153
    /**
154
     * Tags relationship.
155
     *
156
     * @return \Illuminate\Database\Eloquent\Relations\BelongsToMany
157
     */
158
    public function tags()
159
    {
160
        return $this->belongsToMany(Tag::class, "{$this->prefix}post_tag");
161
    }
162
163
    /* -----------------------------------------------------------------
164
     |  Getters & Setters
165
     | -----------------------------------------------------------------
166
     */
167
168
    /**
169
     * Set the title attribute.
170
     *
171
     * @param  string  $title
172
     */
173
    public function setTitleAttribute($title)
174
    {
175
        $this->attributes['title'] = $title;
176
        $this->attributes['slug']  = Str::slug($title);
177
    }
178
179
    /**
180
     * Set the content attribute.
181
     *
182
     * @param  string  $content
183
     */
184
    public function setContentAttribute($content)
185
    {
186
        $this->attributes['content_raw']  = $content;
187
        $this->attributes['content_html'] = markdown($content);
188
    }
189
190
    /**
191
     * Get the content attribute.
192
     *
193
     * @return \Illuminate\Support\HtmlString
194
     */
195
    public function getContentAttribute()
196
    {
197
        return new HtmlString($this->content_html);
198
    }
199
200
    /**
201
     * Set the status attribute.
202
     *
203
     * @param  string  $status
204
     */
205
    public function setStatusAttribute($status)
206
    {
207
        $this->attributes['is_draft'] = ($status === self::STATUS_DRAFT);
208
    }
209
210
    /**
211
     * Get the status name attribute.
212
     *
213
     * @return string|null
214
     */
215
    public function getStatusNameAttribute()
216
    {
217
        return self::getStatuses()->get(
218
            $this->isDraft() ? self::STATUS_DRAFT : self::STATUS_PUBLISHED
219
        );
220
    }
221
222
    /* -----------------------------------------------------------------
223
     |  Main Functions
224
     | -----------------------------------------------------------------
225
     */
226
227
    /**
228
     * Create a post.
229
     *
230
     * @param  array  $attributes
231
     *
232
     * @return self
233
     */
234
    public static function createOne(array $attributes)
235
    {
236
        $post = new self($attributes);
237
238
        $post->save();
239
240
        $post->tags()->sync($attributes['tags']);
241
242
        $post->createSeo(
243
            static::extractSeoAttributes($attributes)
244
        );
245
246
        return $post;
247
    }
248
249
    /**
250
     * Create a post.
251
     *
252
     * @param  array  $inputs
253
     *
254
     * @return bool|int
255
     */
256
    public function updateOne(array $inputs)
257
    {
258
        $updated = $this->update(Arr::except($inputs, ['author_id']));
259
260
        $this->tags()->sync($inputs['tags']);
261
262
        $seoAttributes = static::extractSeoAttributes($inputs);
263
264
        $this->hasSeo() ? $this->updateSeo($seoAttributes) : $this->createSeo($seoAttributes);
265
266
        return $updated;
267
    }
268
269
    /* -----------------------------------------------------------------
270
     |  Check Functions
271
     | -----------------------------------------------------------------
272
     */
273
274
    /**
275
     * Check if the post's status is "draft".
276
     *
277
     * @return bool
278
     */
279
    public function isDraft()
280
    {
281
        return $this->is_draft;
282
    }
283
284
    /**
285
     * Check if the post's status is "published".
286
     *
287
     * @return bool
288
     */
289
    public function isPublished()
290
    {
291
        return ! $this->isDraft();
292
    }
293
294
    /* -----------------------------------------------------------------
295
     |  Other Methods
296
     | -----------------------------------------------------------------
297
     */
298
299
    /**
300
     * Get the post statuses.
301
     *
302
     * @return \Illuminate\Support\Collection
303
     */
304
    public static function getStatuses()
305
    {
306
        return Collection::make(
307
            trans('blog::posts.statuses', [])
308
        );
309
    }
310
311
    /**
312
     * Extract the seo attributes.
313
     *
314
     * @param  array  $inputs
315
     *
316
     * @return array
317
     */
318
    protected static function extractSeoAttributes(array $inputs)
319
    {
320
        return [
321
            'title'       => Arr::get($inputs, 'seo_title'),
322
            'description' => Arr::get($inputs, 'seo_description'),
323
            'keywords'    => Arr::get($inputs, 'seo_keywords'),
324
            'metas'       => Arr::get($inputs, 'seo_metas'),
325
        ];
326
    }
327
328
    /**
329
     * Get the show url.
330
     *
331
     * @return string
332
     */
333
    public function getShowUrl()
334
    {
335
        return route('admin::blog.posts.show', [$this]);
336
    }
337
338
    /**
339
     * Get the edit url.
340
     *
341
     * @return string
342
     */
343
    public function getEditUrl()
344
    {
345
        return route('admin::blog.posts.edit', [$this]);
346
    }
347
}
348