trucking wrap-up: close-out becomes a paid order + workflow
- Checker closing mode now pitches a done-for-you 'Trucking Wrap-Up' ($199) with a buy button to /order/dot-compliance?services=carrier-closeout, instead of a lead form. DIY checklist replaced by what's-included list. - Entity dissolution offered as a paid add-on with the lawsuits/liens/judgments warning before dissolving. - New catalog services: carrier-closeout ($199), entity-dissolution ($199). - CarrierCloseoutHandler orchestrates the sequential shutdown workflow (final MCS-150 out-of-business, MC revoke, UCR cancel, IFTA/IRP + state closures; dissolution branch for the add-on) as admin-tracked tasks. - Sell-your-trucks: single shared form with quick-cash / marketplace / both; name field is now a real first+last name (no corp-name prefill). - tickets categories: add truck_sale_both, drop business_closeout (now an order). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
1e34707258
commit
b25d1f5fd3
6 changed files with 202 additions and 105 deletions
|
|
@ -53,6 +53,8 @@ from .state_trucking import StateTruckingHandler
|
|||
# EIN application + virtual mailbox
|
||||
from .ein_application import EINApplicationHandler
|
||||
from .mailbox_setup import MailboxSetupHandler
|
||||
# Carrier close-out / trucking wrap-up (shutdown) + entity dissolution
|
||||
from .carrier_closeout import CarrierCloseoutHandler
|
||||
|
||||
SERVICE_HANDLERS: dict[str, type] = {
|
||||
"flsa-audit": FLSAAuditHandler,
|
||||
|
|
@ -112,6 +114,8 @@ SERVICE_HANDLERS: dict[str, type] = {
|
|||
"emergency-temporary-authority": MCS150UpdateHandler, # ask.fmcsa.dot.gov type 308
|
||||
"ein-application": EINApplicationHandler,
|
||||
"virtual-mailbox": MailboxSetupHandler,
|
||||
"carrier-closeout": CarrierCloseoutHandler, # trucking wrap-up / USDOT shutdown
|
||||
"entity-dissolution": CarrierCloseoutHandler, # add-on, same handler (dissolution branch)
|
||||
"annual-report-filing": MCS150UpdateHandler, # admin-assisted
|
||||
"registered-agent": MCS150UpdateHandler, # admin-assisted (NWRA/CorpTools)
|
||||
"entity-reinstatement": MCS150UpdateHandler, # admin-assisted
|
||||
|
|
|
|||
89
scripts/workers/services/carrier_closeout.py
Normal file
89
scripts/workers/services/carrier_closeout.py
Normal file
|
|
@ -0,0 +1,89 @@
|
|||
"""Carrier Close-Out — Trucking Wrap-Up workflow.
|
||||
|
||||
Done-for-you shutdown of a motor carrier. Orchestrates the sequential
|
||||
wind-down as an admin-tracked workflow:
|
||||
final MCS-150 (Out of Business) -> revoke MC authority -> cancel UCR ->
|
||||
close IFTA/IRP + state accounts -> advise on insurance timing.
|
||||
|
||||
The `entity-dissolution` add-on (separate slug, same handler) dissolves the
|
||||
LLC/Corp and files the final report — gated on a no-outstanding-liabilities
|
||||
attestation.
|
||||
|
||||
Intake data:
|
||||
- entity_name / legal_name, dot_number, mc_number
|
||||
- phy_state / state, operating_states
|
||||
"""
|
||||
from __future__ import annotations
|
||||
|
||||
import json
|
||||
import logging
|
||||
import os
|
||||
|
||||
LOG = logging.getLogger("workers.services.carrier_closeout")
|
||||
|
||||
|
||||
class CarrierCloseoutHandler:
|
||||
SERVICE_SLUG = "carrier-closeout"
|
||||
|
||||
async def process(self, order_data: dict) -> list[str]:
|
||||
order_number = order_data.get("order_number", order_data.get("name", ""))
|
||||
return self.handle(order_data, order_number)
|
||||
|
||||
def handle(self, order_data: dict, order_number: str) -> list[str]:
|
||||
intake = order_data.get("intake_data") or {}
|
||||
if isinstance(intake, str):
|
||||
intake = json.loads(intake)
|
||||
|
||||
slug = order_data.get("service_slug", self.SERVICE_SLUG)
|
||||
name = intake.get("entity_name") or intake.get("legal_name") or "Unknown carrier"
|
||||
dot = intake.get("dot_number") or intake.get("usdot") or "N/A"
|
||||
state = intake.get("phy_state") or intake.get("state") or "N/A"
|
||||
LOG.info("[%s] Carrier close-out (%s) for %s (DOT %s)", order_number, slug, name, dot)
|
||||
|
||||
if slug == "entity-dissolution":
|
||||
steps = [
|
||||
"Confirm NO outstanding lawsuits, liens, or judgments before dissolving (client attestation).",
|
||||
f"File Articles of Dissolution for {name} with the {state} Secretary of State.",
|
||||
"File final state report / franchise tax return; close state tax accounts.",
|
||||
"Notify IRS (final return, check the 'final' box); close the EIN if requested.",
|
||||
]
|
||||
title = f"Entity Dissolution — {name} ({state})"
|
||||
else:
|
||||
steps = [
|
||||
f"File final MCS-150 marking carrier OUT OF BUSINESS — deactivate USDOT {dot}.",
|
||||
"Submit voluntary revocation of operating authority (MC) to FMCSA.",
|
||||
"Cancel UCR registration; confirm marked inactive (no next-year bill).",
|
||||
"Close IFTA account, file final quarterly return, retire decals.",
|
||||
f"Return IRP apportioned plates to base state ({state}); close the account.",
|
||||
"Close state-level accounts/permits (CA MCP/CARB, OR weight-mile, NY HUT, KY KYU, etc.) per operating states.",
|
||||
"Advise client on insurance cancellation timing (only AFTER authority is revoked).",
|
||||
]
|
||||
title = f"Trucking Wrap-Up (Shutdown) — {name} (DOT {dot})"
|
||||
|
||||
description = (
|
||||
f"Carrier: {name}\nUSDOT: {dot}\nMC: {intake.get('mc_number', 'N/A')}\n"
|
||||
f"Base state: {state}\nOperating states: {intake.get('operating_states', 'N/A')}\n\n"
|
||||
"Sequential wind-down steps:\n"
|
||||
+ "\n".join(f" {i + 1}. {s}" for i, s in enumerate(steps))
|
||||
)
|
||||
self._create_todo(order_number, intake, title, description, slug, priority="high")
|
||||
return [f"Close-out workflow queued: {title}"]
|
||||
|
||||
def _create_todo(self, order_number, intake, title, description, slug, priority="normal"):
|
||||
try:
|
||||
import psycopg2
|
||||
conn = psycopg2.connect(os.environ.get("DATABASE_URL", ""))
|
||||
with conn.cursor() as cur:
|
||||
cur.execute(
|
||||
"""
|
||||
INSERT INTO admin_todos (
|
||||
title, category, priority, order_number, service_slug,
|
||||
description, data, status
|
||||
) VALUES (%s, %s, %s, %s, %s, %s, %s, 'pending')
|
||||
""",
|
||||
(title, "filing", priority, order_number, slug, description, json.dumps(intake)),
|
||||
)
|
||||
conn.commit()
|
||||
conn.close()
|
||||
except Exception as exc:
|
||||
LOG.error("[%s] Failed to create close-out todo: %s", order_number, exc)
|
||||
Loading…
Add table
Add a link
Reference in a new issue