Completed
Push — master ( f84666...e52fc0 )
by Evan
01:46
created

src/Term/Model.php (2 issues)

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
3
namespace Silk\Term;
4
5
use stdClass;
6
use WP_Term;
7
use Silk\Taxonomy\Taxonomy;
8
use Silk\Type\Model as BaseModel;
9
use Silk\Support\Collection;
10
use Silk\Exception\WP_ErrorException;
11
use Silk\Term\Exception\TermNotFoundException;
12
use Silk\Term\Exception\TaxonomyMismatchException;
13
14
/**
15
 * @property-read WP_Term $term
16
 * @property int    $term_id
17
 * @property string $name
18
 * @property string $slug
19
 * @property string $term_group
20
 * @property int    $term_taxonomy_id
21
 * @property string $taxonomy
22
 * @property string $description
23
 * @property int    $parent
24
 * @property int    $count
25
 */
26
abstract class Model extends BaseModel
27
{
28
    /**
29
     * The term's taxonomy
30
     * @var string
31
     */
32
    const TAXONOMY = '';
33
34
    /**
35
     * The object type in WordPress
36
     * @var string
37
     */
38
    const OBJECT_TYPE = 'term';
39
40
    /**
41
     * The primary ID property on the object
42
     */
43
    const ID_PROPERTY = 'term_id';
44
45
    /**
46
     * Model Constructor.
47
     *
48
     * @param array|WP_Term $term  WP_Term
49
     *
50
     * @throws TaxonomyMismatchException
51
     */
52 View Code Duplication
    public function __construct($term = [])
1 ignored issue
show
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
53
    {
54
        $attributes = is_array($term) ? $term : [];
55
56
        if (! $term instanceof WP_Term) {
0 ignored issues
show
The class WP_Term does not exist. Is this class maybe located in a folder that is not analyzed, or in a newer version of your dependencies than listed in your composer.lock/composer.json?
Loading history...
57
            $term = new WP_Term(new stdClass);
58
            $term->taxonomy = static::TAXONOMY;
59
        } elseif ($term->taxonomy != static::TAXONOMY) {
60
            throw new TaxonomyMismatchException();
61
        }
62
63
        $this->setObject($term);
64
65
        $this->fill($attributes);
66
    }
67
68
    /**
69
     * Create a new instance from a term ID.
70
     *
71
     * @param  int|string $id  Term ID
72
     *
73
     * @throws TermNotFoundException
74
     *
75
     * @return static
76
     */
77
    public static function fromID($id)
78
    {
79
        if (! $term = WP_Term::get_instance($id, static::TAXONOMY)) {
80
            throw new TermNotFoundException("No term found with ID $id.");
81
        }
82
83
        return new static($term);
84
    }
85
86
    /**
87
     * Create a new instance from a slug.
88
     *
89
     * @param  string $slug  Term slug
90
     *
91
     * @throws TermNotFoundException
92
     *
93
     * @return static
94
     */
95
    public static function fromSlug($slug)
96
    {
97
        if (! $term = get_term_by('slug', $slug, static::TAXONOMY)) {
98
            throw new TermNotFoundException("No term found with slug '$slug'.");
99
        }
100
101
        return new static($term);
102
    }
103
104
    /**
105
     * Check if this term exists in the database.
106
     *
107
     * @return boolean
108
     */
109
    public function exists()
110
    {
111
        return $this->id && ((bool) term_exists((int) $this->id, static::TAXONOMY));
112
    }
113
114
    /**
115
     * Check if this term exists in the database as the child of the given parent.
116
     *
117
     * @param  int|string|object  $parent  integer Parent term ID
118
     *                                     string  Parent term slug or name
119
     *                                     object  The parent term object/model.
120
     *
121
     * @return boolean                     True if the this term and the parent
122
     *                                     exist in the database, and the instance
123
     *                                     is a child of the given parent;
124
     *                                     otherwise false
125
     */
126
    public function isChildOf($parent)
127
    {
128
        if (isset($parent->term_id)) {
129
            $parent = $parent->term_id;
130
        }
131
132
        return (bool) term_exists((int) $this->id, static::TAXONOMY, $parent);
133
    }
134
135
    /**
136
     * Get the parent term instance.
137
     *
138
     * @return static
139
     */
140
    public function parent()
141
    {
142
        return static::fromID($this->object->parent);
143
    }
144
145
    /**
146
     * Get all ancestors of this term as a collection.
147
     *
148
     * @return Collection
149
     */
150
    public function ancestors()
151
    {
152
        return Collection::make(get_ancestors($this->id, static::TAXONOMY, 'taxonomy'))
153
            ->map([static::class, 'fromID']);
154
    }
155
156
    /**
157
     * Get all children of this term as a collection.
158
     *
159
     * @return Collection
160
     */
161
    public function children()
162
    {
163
        return Collection::make(get_term_children($this->id, static::TAXONOMY))
164
             ->map([static::class, 'fromID']);
165
    }
166
167
    /**
168
     * Get the Taxonomy model.
169
     *
170
     * @return Taxonomy|\Silk\Taxonomy\Builder
171
     */
172
    public static function taxonomy()
173
    {
174
        return Taxonomy::make(static::TAXONOMY);
175
    }
176
177
    /**
178
     * Get the URL for this term.
179
     *
180
     * @return string|bool
181
     */
182
    public function url()
183
    {
184
        $url = get_term_link($this->id, $this->taxonomy);
185
186
        if (is_wp_error($url)) {
187
            throw new WP_ErrorException($url);
188
        }
189
190
        return $url;
191
    }
192
193
    /**
194
     * Start a new query for terms of this type.
195
     *
196
     * @return QueryBuilder
197
     */
198
    public function newQuery()
199
    {
200
        return QueryBuilder::make()->setModel($this);
201
    }
202
203
    /**
204
     * Save the term to the database.
205
     *
206
     * @throws WP_ErrorException
207
     *
208
     * @return $this
209
     */
210
    public function save()
211
    {
212
        if ($this->id) {
213
            $ids = wp_update_term($this->id, $this->taxonomy, $this->object->to_array());
214
        } else {
215
            $ids = wp_insert_term($this->name, $this->taxonomy, $this->object->to_array());
216
        }
217
218
        if (is_wp_error($ids)) {
219
            throw new WP_ErrorException($ids);
220
        }
221
222
        $this->setId($ids['term_id'])->refresh();
223
224
        return $this;
225
    }
226
227
    /**
228
     * Delete the term from the database.
229
     *
230
     * @return $this
231
     */
232
    public function delete()
233
    {
234
        if (wp_delete_term($this->id, $this->taxonomy)) {
235
            $this->setObject(new WP_Term(new stdClass));
236
        }
237
238
        return $this;
239
    }
240
241
    /**
242
     * Reload the term object from the database.
243
     *
244
     * @return $this
245
     */
246
    public function refresh()
247
    {
248
        $this->setObject(WP_Term::get_instance($this->id, $this->taxonomy));
249
250
        return $this;
251
    }
252
}
253