Passed
Push — feature/manager_poster_index ( 747099...a9970e )
by Xander
06:33
created

JobPoster::job_poster_questions()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
eloc 1
dl 0
loc 3
rs 10
c 0
b 0
f 0
ccs 0
cts 0
cp 0
cc 1
nc 1
nop 0
crap 2
1
<?php
2
3
/**
4
 * Created by Reliese Model.
5
 * Date: Thu, 12 Jul 2018 22:39:27 +0000.
6
 */
0 ignored issues
show
Coding Style introduced by
Missing @link tag in file comment
Loading history...
Coding Style introduced by
Missing @category tag in file comment
Loading history...
Coding Style introduced by
Missing @author tag in file comment
Loading history...
Coding Style introduced by
PHP version not specified
Loading history...
Coding Style introduced by
Missing @package tag in file comment
Loading history...
Coding Style introduced by
Missing @license tag in file comment
Loading history...
7
8
namespace App\Models;
9
10
use App\Events\JobSaved;
11
use App\Models\JobApplication;
12
use Illuminate\Notifications\Notifiable;
13
use Illuminate\Support\Facades\App;
14
use Illuminate\Support\Facades\Lang;
15
use Jenssegers\Date\Date;
16
17
/**
18
 * Class JobPoster
19
 *
20
 * @property int $id
21
 * @property int $job_term_id
22
 * @property int $term_qty
23
 * @property \Jenssegers\Date\Date $open_date_time
24
 * @property \Jenssegers\Date\Date $close_date_time
25
 * @property \Jenssegers\Date\Date $start_date_time
26
 * @property \Jenssegers\Date\Date $review_requested_at
27
 * @property \Jessengers\Date\Date $published_at
28
 * @property int $department_id
29
 * @property int $province_id
30
 * @property int $salary_min
31
 * @property int $salary_max
32
 * @property int $noc
33
 * @property string $classification
34
 * @property int $security_clearance_id
35
 * @property int $language_requirement_id
36
 * @property boolean $remote_work_allowed
37
 * @property int $manager_id
38
 * @property boolean $published
39
 * @property \Jenssegers\Date\Date $created_at
40
 * @property \Jenssegers\Date\Date $updated_at
41
 *
42
 * @property int $submitted_applications_count
43
 *
44
 * @property \App\Models\Lookup\Department $department
45
 * @property \App\Models\Lookup\JobTerm $job_term
46
 * @property \App\Models\Lookup\LanguageRequirement $language_requirement
47
 * @property \App\Models\Manager $manager
48
 * @property \App\Models\Lookup\Province $province
49
 * @property \App\Models\Lookup\SecurityClearance $security_clearance
50
 * @property \Illuminate\Database\Eloquent\Collection $criteria
51
 * @property \Illuminate\Database\Eloquent\Collection $job_applications
52
 * @property \Illuminate\Database\Eloquent\Collection $job_poster_key_tasks
53
 * @property \Illuminate\Database\Eloquent\Collection $job_poster_questions
54
 * @property \Illuminate\Database\Eloquent\Collection $job_poster_translations
55
 * @property \Illuminate\Database\Eloquent\Collection $submitted_applications
56
 * @property \Illuminate\Database\Eloquent\Collection[ScreeningPlan] $screening_plans
57
 *
58
 * Localized Properties:
59
 * @property string $city
60
 * @property string $title
61
 * @property string $impact
62
 * @property string $branch
63
 * @property string $division
64
 * @property string $education
65
 *
66
 * Methods
67
 * @method boolean isOpen()
0 ignored issues
show
Coding Style introduced by
Tag value indented incorrectly; expected 3 spaces but found 1
Loading history...
68
 * @method string timeRemaining()
0 ignored issues
show
Coding Style introduced by
Tag value indented incorrectly; expected 3 spaces but found 1
Loading history...
69
 */
0 ignored issues
show
Documentation Bug introduced by
The doc comment \Illuminate\Database\Elo...llection[ScreeningPlan] at position 1 could not be parsed: Expected ']' at position 1, but found '['.
Loading history...
Coding Style introduced by
Missing @category tag in class comment
Loading history...
Coding Style introduced by
Missing @package tag in class comment
Loading history...
Coding Style introduced by
Missing @author tag in class comment
Loading history...
Coding Style introduced by
Missing @license tag in class comment
Loading history...
Coding Style introduced by
Missing @link tag in class comment
Loading history...
70
class JobPoster extends BaseModel
71
{
72
73
    use \Dimsav\Translatable\Translatable;
0 ignored issues
show
introduced by
The trait Dimsav\Translatable\Translatable requires some properties which are not provided by App\Models\JobPoster: $translations, $useTranslationFallback, $translationModel, $localeKey, $translationForeignKey
Loading history...
74
    use Notifiable;
0 ignored issues
show
introduced by
The trait Illuminate\Notifications\Notifiable requires some properties which are not provided by App\Models\JobPoster: $email, $phone_number
Loading history...
75
76
    const DATE_FORMAT = [
77
        'en' => 'M jS, Y',
78
        'fr' => 'd M Y',
79
    ];
80
    const TIME_FORMAT = [
81
        'en' => 'h:i A T',
82
        'fr' => 'H \h i T',
83
    ];
84
    const TIMEZONE = 'America/Toronto';
85
86
    /**
0 ignored issues
show
Coding Style introduced by
Missing short description in doc comment
Loading history...
87
     * @var string[] $translatedAttributes
88
     */
89
    public $translatedAttributes = [
90
        'city',
91
        'title',
92
        'impact',
93
        'branch',
94
        'division',
95
        'education'
96
    ];
97
98
    /**
0 ignored issues
show
Coding Style introduced by
Missing short description in doc comment
Loading history...
99
     * @var string[] $casts
100
     */
101
    protected $casts = [
102
        'job_term_id' => 'int',
103
        'department_id' => 'int',
104
        'province_id' => 'int',
105
        'salary_min' => 'int',
106
        'salary_max' => 'int',
107
        'noc' => 'int',
108
        'security_clearance_id' => 'int',
109
        'language_requirement_id' => 'int',
110
        'remote_work_allowed' => 'boolean',
111
        'manager_id' => 'int',
112
        'published' => 'boolean'
113
    ];
114
115
    /**
0 ignored issues
show
Coding Style introduced by
Missing short description in doc comment
Loading history...
116
     * @var string[] $dates
117
     */
118
    protected $dates = [
119
        'open_date_time',
120
        'close_date_time',
121
        'start_date_time',
122
        'review_requested_at',
123
        'published_at'
124
    ];
125
126
    /**
0 ignored issues
show
Coding Style introduced by
Missing short description in doc comment
Loading history...
127
     * @var string[] $fillable
128
     */
129
    protected $fillable = [
130
        'job_term_id',
131
        'term_qty',
132
        'open_date_time',
133
        'close_date_time',
134
        'start_date_time',
135
        'department_id',
136
        'province_id',
137
        'salary_min',
138
        'salary_max',
139
        'noc',
140
        'classification',
141
        'security_clearance_id',
142
        'language_requirement_id',
143
        'remote_work_allowed',
144
        'published'
145
    ];
146
147
    /**
0 ignored issues
show
Coding Style introduced by
Missing short description in doc comment
Loading history...
148
     * @var string[] $withCount
149
     */
150
    protected $withCount = ['submitted_applications'];
151
152
    /**
0 ignored issues
show
Coding Style introduced by
Missing short description in doc comment
Loading history...
153
     * @var mixed[] $dispatchesEvents
154
     */
155
    protected $dispatchesEvents = [
156
        'saved' => JobSaved::class,
157
    ];
158
159
    // @codeCoverageIgnoreStart
160
161
    public function department() // phpcs:ignore
162
    {
163
        return $this->belongsTo(\App\Models\Lookup\Department::class);
164
    }
165
166
    public function job_term() // phpcs:ignore
167
    {
168
        return $this->belongsTo(\App\Models\Lookup\JobTerm::class);
169
    }
170
171
    public function language_requirement() // phpcs:ignore
172
    {
173
        return $this->belongsTo(\App\Models\Lookup\LanguageRequirement::class);
174
    }
175
176
    public function manager() // phpcs:ignore
177
    {
178
        return $this->belongsTo(\App\Models\Manager::class);
179
    }
180
181
    public function province() // phpcs:ignore
182
    {
183
        return $this->belongsTo(\App\Models\Lookup\Province::class);
184
    }
185
186
    public function security_clearance() // phpcs:ignore
187
    {
188
        return $this->belongsTo(\App\Models\Lookup\SecurityClearance::class);
189
    }
190
191
    public function criteria() // phpcs:ignore
192
    {
193
        return $this->hasMany(\App\Models\Criteria::class);
194
    }
195
196
    public function job_applications() // phpcs:ignore
197
    {
198
        return $this->hasMany(\App\Models\JobApplication::class);
199
    }
200
201
    public function job_poster_key_tasks() // phpcs:ignore
202
    {
203
        return $this->hasMany(\App\Models\JobPosterKeyTask::class);
204
    }
205
206
    public function job_poster_questions() // phpcs:ignore
207
    {
208
        return $this->hasMany(\App\Models\JobPosterQuestion::class);
209
    }
210
211
    public function job_poster_translations() // phpcs:ignore
212
    {
213
        return $this->hasMany(\App\Models\JobPosterTranslation::class);
214
    }
215
216
    public function screening_plans() // phpcs:ignore
217
    {
218
        return $this->hasMany(\App\Models\ScreeningPlan::class);
219
    }
220
221
    // Artificial Relations
222
223
    public function submitted_applications() // phpcs:ignore
224
    {
225
        return $this->hasMany(\App\Models\JobApplication::class)->whereHas('application_status', function ($query) : void {
0 ignored issues
show
Coding Style introduced by
The opening parenthesis of a multi-line function call should be the last content on the line.
Loading history...
226
            $query->where('name', '!=', 'draft');
227
        });
0 ignored issues
show
Coding Style introduced by
For multi-line function calls, the closing parenthesis should be on a new line.

If a function call spawns multiple lines, the coding standard suggests to move the closing parenthesis to a new line:

someFunctionCall(
    $firstArgument,
    $secondArgument,
    $thirdArgument
); // Closing parenthesis on a new line.
Loading history...
228
    }
229
230
    // @codeCoverageIgnoreEnd
231
232
    // Accessors
233
234
    // Mutators
235
236
    /**
237
     * Intercept setting the "published" attribute, and set the
238
     * "published_at" timestamp if true.
239
     *
240
     * @param mixed $value Incoming value for the 'published' attribute.
241
     *
242
     * @return void
243
     */
244 34
    public function setPublishedAttribute($value) : void
245
    {
246 34
        if ($value && $this->open_date_time->isPast()) {
247 28
            $this->attributes['published_at'] = new Date();
248 26
        } elseif ($value && $this->open_date_time->isFuture()) {
249 2
            $this->attributes['published_at'] = $this->open_date_time;
250
        }
251 34
        $this->attributes['published'] = $value;
252 34
    }
253
254
    // Methods
255
256
    /**
257
     * Formatted and localized date and time the Job Poster closes.
258
     *
259
     * @return string[]
260
     */
261 6
    public function applyBy() : array
262
    {
263 6
        $localCloseDate = new Date($this->close_date_time); // This initializes the date object in UTC time
264 6
        $localCloseDate->setTimezone(new \DateTimeZone(self::TIMEZONE)); // Then set the time zone for display
265
        $displayDate = [
266 6
            'date' => $localCloseDate->format(self::DATE_FORMAT[App::getLocale()]),
267 6
            'time' => $localCloseDate->format(self::TIME_FORMAT[App::getLocale()])
268
        ];
269
270 6
        if (App::isLocale('fr')) {
271
            $displayDate['time'] = str_replace(['EST', 'EDT'], ['HNE', 'HAE'], $displayDate['time']);
272
        }
273
274 6
        return $displayDate;
275
    }
276
277
    /**
278
     * Check if a Job Poster is open for applications.
279
     *
280
     * @return boolean
281
     */
282 12
    public function isOpen() : bool
283
    {
284 12
        return $this->published
285 12
            && $this->open_date_time->isPast()
286 12
            && $this->close_date_time->isFuture();
287
    }
288
289
    /**
290
     * Check if a Job Poster is closed for applications.
291
     *
292
     * @return boolean
293
     */
294 8
    public function isClosed() : bool
295
    {
296 8
        return $this->published
297 8
            && $this->open_date_time->isPast()
298 8
            && $this->close_date_time->isPast();
299
    }
300
301
    /**
302
     * Calculate the remaining time a Job Poster is open.
303
     *
304
     * @return string
305
     */
306 2
    public function timeRemaining() : string
307
    {
308 2
        $interval = $this->close_date_time->diff(Date::now());
309
310 2
        $d = $interval->d;
311 2
        $h = $interval->h;
312 2
        $m = $interval->i;
313 2
        $s = $interval->s;
314
315 2
        if ($d > 0) {
316 2
            $unit = 'day';
317 2
            $count = $d;
318 2
        } elseif ($h > 0) {
319 2
            $unit = 'hour';
320 2
            $count = $h;
321 2
        } elseif ($m > 0) {
322 2
            $unit = 'minute';
323 2
            $count = $m;
324
        } else {
325 2
            $unit = 'second';
326 2
            $count = $s;
327
        }
328
329 2
        $key = "common/time.$unit";
330
331 2
        return Lang::choice($key, $count);
332
    }
333
334
    /**
335
     * Return the current status for the Job Poster.
336
     * Possible values are "draft", "submitted", "published" and "closed".
337
     *
338
     * @return string
339
     */
340 6
    public function status() : string
341
    {
342 6
        $status = 'draft';
343 6
        if ($this->isOpen()) {
344 2
            $status = 'published';
345 6
        } elseif ($this->isClosed()) {
346 2
            $status = 'closed';
347 6
        } elseif ($this->review_requested_at !== null) {
348 4
            $status = 'submitted';
349
        } else {
350 4
            $status = 'draft';
351
        }
352
353 6
        return $status;
354
    }
355
}
356