added on local at 2026-07-01 15:02:38
| 1 | #!/usr/bin/perl | |
| 2 | use strict; use warnings; | |
| 3 | use lib '/var/www/vhosts/3dshawn.com/crm.3dshawn.com'; | |
| 4 | use CGI; use MODS::DBConnect; use MODS::Login; | |
| 5 | use MODS::ContactForge::Config; use MODS::ContactForge::Wrapper; | |
| 6 | my $auth = MODS::Login->new; my $wrap = MODS::ContactForge::Wrapper->new; | |
| 7 | my $db = MODS::DBConnect->new; my $cfg = MODS::ContactForge::Config->new; | |
| 8 | my $DB = $cfg->settings('database_name'); | |
| 9 | my $userinfo = $auth->login_verify(); | |
| 10 | if (!$userinfo) { print "Status: 302 Found\nLocation: /login.cgi\n\n"; exit; } | |
| 11 | my $uid = $userinfo->{user_id}; $uid =~ s/[^0-9]//g; | |
| 12 | my $dbh = $db->db_connect(); | |
| 13 | my @rows = $db->db_readwrite_multiple($dbh, qq~ | |
| 14 | SELECT id, name, trigger_type, is_active, runs_total, last_run_at, created_at | |
| 15 | FROM `${DB}`.automations | |
| 16 | WHERE owner_user_id='$uid' ORDER BY id DESC LIMIT 200 | |
| 17 | ~, $ENV{SCRIPT_NAME}, __LINE__); | |
| 18 | $db->db_disconnect($dbh); | |
| 19 | ||
| 20 | my $body = qq~ | |
| 21 | <div class="page-header" style="display:flex;align-items:center;justify-content:space-between;margin-bottom:18px"> | |
| 22 | <div> | |
| 23 | <h1 style="margin:0;font-size:28px">Automations</h1> | |
| 24 | <p class="text-secondary" style="margin:6px 0 0;font-size:14px">Trigger-based workflows. When something happens (contact created, deal moved, tag added), run an action (email, task, tag, webhook).</p> | |
| 25 | </div> | |
| 26 | <a class="btn btn-primary" href="/automation_action.cgi?new=1">+ New automation</a> | |
| 27 | </div> | |
| 28 | ~; | |
| 29 | ||
| 30 | if (!@rows) { | |
| 31 | $body .= q~<div class="card" style="padding:48px;text-align:center;color:var(--col-text-2)"> | |
| 32 | <div style="font-size:48px;margin-bottom:14px">⚙</div> | |
| 33 | <h3 style="margin:0 0 6px;color:#fff">No automations yet</h3> | |
| 34 | <p style="margin:0 0 18px">Save your team hours per week. Examples:</p> | |
| 35 | <ul style="text-align:left;max-width:520px;margin:0 auto 22px;color:var(--col-text-2)"> | |
| 36 | <li>When a contact is created from the website form → assign to round-robin rep + send welcome email</li> | |
| 37 | <li>When a deal moves to "Demo Scheduled" → create a follow-up task for 1 hour after the demo</li> | |
| 38 | <li>When a deal is marked Won → create onboarding tasks + send Slack notification</li> | |
| 39 | <li>When a contact hasn't been touched in 14 days → create reminder task</li> | |
| 40 | </ul> | |
| 41 | <a class="btn btn-primary" href="/automation_action.cgi?new=1">Build your first automation</a> | |
| 42 | </div>~; | |
| 43 | } else { | |
| 44 | $body .= q~<div class="card" style="padding:0;overflow:hidden"><table class="table" style="width:100%"><thead><tr><th style="text-align:left;padding:12px 16px">Name</th><th style="text-align:left;padding:12px 16px">Trigger</th><th style="text-align:left;padding:12px 16px">Status</th><th style="text-align:right;padding:12px 16px">Runs</th><th style="text-align:left;padding:12px 16px">Last run</th></tr></thead><tbody>~; | |
| 45 | foreach my $r (@rows) { | |
| 46 | my $status = $r->{is_active} ? '<span style="color:#10b981">active</span>' : '<span style="color:#94a3b8">paused</span>'; | |
| 47 | $body .= qq~<tr><td style="padding:12px 16px"><a href="/automation_action.cgi?edit_id=$r->{id}" style="color:#67e8f9">$r->{name}</a></td><td style="padding:12px 16px">$r->{trigger_type}</td><td style="padding:12px 16px">$status</td><td style="padding:12px 16px;text-align:right">$r->{runs_total}</td><td style="padding:12px 16px">~ . ($r->{last_run_at} || 'never') . qq~</td></tr>~; | |
| 48 | } | |
| 49 | $body .= '</tbody></table></div>'; | |
| 50 | } | |
| 51 | print qq~Content-Type: text/html; charset=utf-8\nCache-Control: no-store, no-cache, must-revalidate, max-age=0\nPragma: no-cache\nExpires: 0\n\n~; | |
| 52 | $wrap->render({userinfo=>$userinfo, page_key=>'automations', title=>'Automations', body=>$body}); |