Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
50.00% covered (danger)
50.00%
1 / 2
50.00% covered (danger)
50.00%
1 / 2
CRAP
0.00% covered (danger)
0.00%
0 / 1
InAppNotificationCampaign
50.00% covered (danger)
50.00%
1 / 2
50.00% covered (danger)
50.00%
1 / 2
2.50
0.00% covered (danger)
0.00%
0 / 1
 notifications
0.00% covered (danger)
0.00%
0 / 1
0.00% covered (danger)
0.00%
0 / 1
2
 newFactory
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
1<?php
2
3namespace App\Http\Models;
4
5use Database\Factories\Http\Models\InAppNotificationCampaignFactory;
6use Illuminate\Database\Eloquent\Factories\HasFactory;
7use Illuminate\Database\Eloquent\Relations\HasMany;
8
9/**
10 * InAppNotificationCampaign model - admin-managed notification templates.
11 *
12 * Stores the campaign configuration that determines what notification
13 * to show, to whom, and when. Per-user records are created via assignment.
14 *
15 * @property string $_id
16 * @property string $id_slug Human-readable slug (e.g. "grammar-reengage-2026-q1")
17 * @property int $priority Display priority (lower = higher priority)
18 * @property string $title Notification title
19 * @property string $body Notification body text
20 * @property string|null $icon_url URL for the notification icon
21 * @property string|null $image_url URL for the notification image
22 * @property string|null $iframe_url URL for embedded iframe content
23 * @property int|null $iframe_width Width of embedded iframe in pixels
24 * @property int|null $iframe_height Height of embedded iframe in pixels
25 * @property string|null $cta_text Primary call-to-action button text
26 * @property string|null $cta_url Primary call-to-action URL
27 * @property string|null $cta_action Primary CTA action type
28 * @property string|null $secondary_cta_text Secondary CTA button text
29 * @property string|null $secondary_cta_url Secondary CTA URL
30 * @property string|null $accent_color Accent color hex code
31 * @property string $display_mode Display mode (banner, modal, toast, etc.)
32 * @property string|null $position Display position on screen
33 * @property array|null $target_urls URL patterns where notification should appear
34 * @property bool $requires_auth Whether user must be authenticated
35 * @property array|null $target_plans Plan identifiers to target
36 * @property int|null $max_impressions Maximum number of impressions per user
37 * @property int|null $cooldown_hours Hours between re-showing to same user
38 * @property \Carbon\Carbon|null $start_date Campaign start date
39 * @property \Carbon\Carbon|null $end_date Campaign end date
40 * @property int|null $auto_dismiss_seconds Auto-dismiss after N seconds
41 * @property string|null $tracking_event Analytics tracking event name
42 * @property bool $is_active Whether campaign is active
43 * @property \Carbon\Carbon|null $created_at
44 * @property \Carbon\Carbon|null $updated_at
45 */
46class InAppNotificationCampaign extends Moloquent
47{
48    use HasFactory;
49
50    /**
51     * The collection name.
52     *
53     * @var string
54     */
55    protected $table = 'in_app_notification_campaigns';
56
57    /**
58     * The attributes that are mass assignable.
59     *
60     * @var array<int, string>
61     */
62    protected $fillable = [
63        'id_slug',
64        'priority',
65        'title',
66        'body',
67        'icon_url',
68        'image_url',
69        'iframe_url',
70        'iframe_width',
71        'iframe_height',
72        'cta_text',
73        'cta_url',
74        'cta_action',
75        'secondary_cta_text',
76        'secondary_cta_url',
77        'accent_color',
78        'display_mode',
79        'position',
80        'target_urls',
81        'requires_auth',
82        'target_plans',
83        'max_impressions',
84        'cooldown_hours',
85        'start_date',
86        'end_date',
87        'auto_dismiss_seconds',
88        'tracking_event',
89        'is_active',
90    ];
91
92    /**
93     * The attributes that should be cast.
94     *
95     * @var array<string, string>
96     */
97    protected $casts = [
98        'priority' => 'integer',
99        'iframe_width' => 'integer',
100        'iframe_height' => 'integer',
101        'requires_auth' => 'boolean',
102        'is_active' => 'boolean',
103        'max_impressions' => 'integer',
104        'cooldown_hours' => 'integer',
105        'auto_dismiss_seconds' => 'integer',
106        'target_urls' => 'array',
107        'target_plans' => 'array',
108        'start_date' => 'datetime',
109        'end_date' => 'datetime',
110    ];
111
112    /**
113     * Get the per-user notification records for this campaign.
114     */
115    public function notifications(): HasMany
116    {
117        return $this->hasMany(InAppNotification::class, 'campaign_id');
118    }
119
120    /**
121     * Create a new factory instance for the model.
122     */
123    protected static function newFactory(): InAppNotificationCampaignFactory
124    {
125        return InAppNotificationCampaignFactory::new();
126    }
127}