fix(psa): fix time entry AttributeError and show all users in member mapping
- Fix create_time_entry() using self._client instead of self.client - GET /member-mappings now returns all active account users, not just mapped ones — allows manual assignment when auto-match by email doesn't work - PsaMemberMappingResponse mapping fields are now Optional (id, external_member_id, external_member_name, matched_by) to represent unmapped users - Frontend MemberMappingTab skips null external_member_id when building localMappings, and derives user list from all returned entries - Add docs/connectwise-psa-testing-checklist.md Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
158
docs/connectwise-psa-testing-checklist.md
Normal file
158
docs/connectwise-psa-testing-checklist.md
Normal file
@@ -0,0 +1,158 @@
|
||||
# ConnectWise PSA Integration — Testing Checklist
|
||||
|
||||
> **Purpose:** Step-by-step guide to connect ResolutionFlow to a ConnectWise developer sandbox and validate each integration feature end-to-end.
|
||||
>
|
||||
> **Date created:** 2026-04-14
|
||||
> **Branch:** main
|
||||
|
||||
---
|
||||
|
||||
## Prerequisites
|
||||
|
||||
Before starting, make sure you have:
|
||||
|
||||
- [ ] ResolutionFlow backend running (`uvicorn app.main:app --reload` from `backend/`)
|
||||
- [ ] ResolutionFlow frontend running (`npm run dev` from `frontend/`)
|
||||
- [ ] A ConnectWise developer sandbox account
|
||||
|
||||
---
|
||||
|
||||
## Step 1 — Get Your ConnectWise Developer Credentials
|
||||
|
||||
You need four pieces of information from your ConnectWise sandbox.
|
||||
|
||||
**Company ID**
|
||||
- This is the company name you log in with on the CW login screen (e.g. if your URL is `na.myconnectwise.net` and your login company is `resolutionflow`, the Company ID is `resolutionflow`)
|
||||
|
||||
**Site URL**
|
||||
- Developer sandboxes are typically `na.myconnectwise.net` or `aus.connectwisedev.com`
|
||||
- Do **not** include `https://` — enter just the hostname (e.g. `na.myconnectwise.net`)
|
||||
|
||||
**API Public Key + Private Key**
|
||||
1. Log into your CW sandbox
|
||||
2. Go to **System → Members** → open your own member record
|
||||
3. Click the **API Keys** tab
|
||||
4. Click **New** → give it a name (e.g. "ResolutionFlow Dev")
|
||||
5. Save — the **Private Key** is shown only once, copy it now
|
||||
6. Note both the **Public Key** (shown on the list) and **Private Key**
|
||||
|
||||
**Client ID** (already configured server-side)
|
||||
- The `CW_CLIENT_ID` is set in `backend/app/core/config.py` — this identifies the ResolutionFlow app to ConnectWise and is shared across all tenants. You do not need to enter this in the UI.
|
||||
|
||||
---
|
||||
|
||||
## Step 2 — Connect ResolutionFlow to ConnectWise
|
||||
|
||||
- [ ] Log into ResolutionFlow as a **Team Admin or Super Admin** user
|
||||
- [ ] Navigate to **Account → Integrations**
|
||||
- [ ] On the **Connection** tab, fill in the form:
|
||||
- Display Name: anything (e.g. `CW Dev Sandbox`)
|
||||
- Site URL: your sandbox hostname (e.g. `na.myconnectwise.net`)
|
||||
- Company ID: your CW company ID
|
||||
- Public Key: from Step 1
|
||||
- Private Key: from Step 1
|
||||
- [ ] Click **Connect** — the backend tests the credentials before saving
|
||||
- [ ] Verify: "Connected" status appears with a green dot
|
||||
- [ ] Click **Test Connection** button and confirm it returns a success message + server version
|
||||
|
||||
---
|
||||
|
||||
## Step 3 — Member Mapping
|
||||
|
||||
Maps ResolutionFlow users to ConnectWise members so that PSA posts are attributed to the right technician.
|
||||
|
||||
- [ ] Click the **Member Mapping** tab
|
||||
- [ ] Click **Auto-Match by Email** — ResolutionFlow matches users to CW members with the same email address
|
||||
- [ ] Verify the matched count in the toast notification
|
||||
- [ ] If any users are unmatched, manually assign them via the dropdown
|
||||
- [ ] Click **Save Mappings** if you made manual changes
|
||||
|
||||
---
|
||||
|
||||
## Step 4 — Ticket Search (via FlowPilot session)
|
||||
|
||||
- [ ] Start a new FlowPilot session (from the Dashboard)
|
||||
- [ ] Look for the **Link Ticket** button in the session header
|
||||
- [ ] Search for a ticket by keyword or ticket number
|
||||
- [ ] Verify: ticket results appear showing summary, board, status, priority
|
||||
- [ ] Select a ticket and confirm it links to the session
|
||||
|
||||
---
|
||||
|
||||
## Step 5 — Ticket Context Injection
|
||||
|
||||
Once a ticket is linked, FlowPilot should enrich its context with CW data.
|
||||
|
||||
- [ ] With a ticket linked, send a message to FlowPilot
|
||||
- [ ] Verify: FlowPilot's response references ticket details (company name, status, configurations, etc.)
|
||||
- [ ] Check backend logs to confirm `GET /integrations/psa/tickets/{id}/context` is being called
|
||||
|
||||
---
|
||||
|
||||
## Step 6 — PSA Post (push session notes to ticket)
|
||||
|
||||
This is the core feature — pushing session documentation back to the ConnectWise ticket.
|
||||
|
||||
- [ ] In the linked session, click **Update** (or the PSA post button in the session header)
|
||||
- [ ] Review the **Preview** — confirm the generated content looks correct
|
||||
- [ ] Select a **Note Type**:
|
||||
- `Internal Analysis` — internal-only note (visible to techs, not clients)
|
||||
- `Resolution` — marks as resolved, notifies client
|
||||
- `Description` — main ticket description note
|
||||
- [ ] Optionally select a **Status** to update the ticket to (e.g. "In Progress" → "Resolved")
|
||||
- [ ] Click **Post to Ticket**
|
||||
- [ ] Verify: success toast appears
|
||||
- [ ] Verify in ConnectWise: open the ticket and confirm the note was posted with correct content and attribution (your member name)
|
||||
|
||||
---
|
||||
|
||||
## Step 7 — FlowPilot Settings
|
||||
|
||||
Configure how FlowPilot behaves with PSA automation.
|
||||
|
||||
- [ ] Go to **Account → Integrations → FlowPilot** tab
|
||||
- [ ] Review each setting:
|
||||
- **Auto Push** — automatically post session doc on session close
|
||||
- **Auto Time Entry** — automatically log hours from session duration
|
||||
- **Time Rounding** — 15min / 30min / exact / none
|
||||
- **Note Visibility** — internal only vs. internal + external
|
||||
- **Include Diagnostic Steps** — whether to include step-by-step notes
|
||||
- **Prompt Status on Resolution** — ask to update CW status when resolving
|
||||
- **Prompt Status on Escalation** — ask to update CW status when escalating
|
||||
- [ ] Adjust to your preference and save
|
||||
|
||||
---
|
||||
|
||||
## Step 8 — End-to-End Smoke Test
|
||||
|
||||
Run a complete session to confirm the full flow works together.
|
||||
|
||||
- [ ] Start a new FlowPilot session with a test ticket in CW
|
||||
- [ ] Link the ticket at session start
|
||||
- [ ] Work through a troubleshooting flow (even a simple one)
|
||||
- [ ] Resolve or escalate the session
|
||||
- [ ] Post the session documentation to the CW ticket
|
||||
- [ ] Open the ticket in ConnectWise and confirm:
|
||||
- [ ] Note content is correct and well-formatted
|
||||
- [ ] Note is attributed to the correct CW member
|
||||
- [ ] Ticket status was updated (if you chose to update)
|
||||
- [ ] Duration / time entry was logged (if auto-time-entry is on)
|
||||
|
||||
---
|
||||
|
||||
## Known Issues / Bugs Fixed
|
||||
|
||||
| Bug | Status | Location |
|
||||
|-----|--------|----------|
|
||||
| `create_time_entry()` used `self._client` instead of `self.client` | Fixed 2026-04-14 | `services/psa/connectwise/provider.py:539` |
|
||||
|
||||
---
|
||||
|
||||
## What's NOT Yet Implemented
|
||||
|
||||
| Feature | Notes |
|
||||
|---------|-------|
|
||||
| Autotask PSA | Schema accepts `autotask` as provider but no implementation exists |
|
||||
| Retry queue for failed posts | `retry_count` / `next_retry_at` columns exist in DB but no background job |
|
||||
| `psa_activity_log` population | Table exists, no endpoints write to it yet |
|
||||
| Post History tab | Currently a placeholder — post history is viewable per-session only |
|
||||
Reference in New Issue
Block a user