OtiumWork manual β Employee edition
A single-page reference of every help topic relevant to employees. This page is always live β when help docs change, this page updates automatically.
Contents (22 topics)
- Getting started with OtiumWork β The 5-minute overview β what OtiumWork does, what's captured, how to get tracking.
- Ask Oti β the in-app copilot β The in-app copilot β ask "how do Iβ¦" in plain English and get the answer plus the help page it came from.
- My Day β The single page every employee lands on β project tiles, tap to focus, everything captured rolls up under the active tile.
- My Tasks β One inbox for everything assigned to you β personal to-dos, project tasks, IT tickets, marketing requests.
- My activity β Audit drawer β raw events, corrections, fine-grained project linking. My Day is now the daily surface.
- Projects and clients β Create projects, assign people, track budgets, link to clients.
- Vacation (PTO) β Request vacation, track your balance, get manager approval β and feed approved time-off into capacity planning.
- AI-drafted weekly timesheet β Click β¨ on any week in /timesheets β Claude writes a professional weekly summary from your captured events.
- Connect your Outlook calendar β Pull your Microsoft 365 / Outlook meetings into your timeline so meeting time lands as events without manual logging.
- Expenses β Submit a reimbursement with a photo of the receipt, follow it through manager approval to payment.
- Partner portal β Reseller-facing help β sign in, submit deals, ask technical questions, take certifications.
- Categories, work types, and departments β Editable per-company taxonomy used to classify every event β categories, work types, departments.
- Sending a document for signature β Send any document for electronic signature β magic link for the signer, UETA / ESIGN-aligned evidence trail, certificate at the end.
- IT helpdesk β IT helpdesk module β anyone submits, IT triages with priority/due-dates, screenshot uploads, daily morning digest.
- Tags β Free-form labels that supplement the fixed category enum β for cross-cutting classifications.
- Competitor tracking (your company's) β Track competitor product releases, subscribe to what you care about, feed a dev roadmap.
- Engineering AI β How customer-facing engineers use OtiumWork's tech-support flavor of Peter β drafts tuned for resolution, customer-meeting notes that mirror to Salesforce.
- Feedback + OtiumWork roadmap β How feature requests flow into the product roadmap, how to vote on what ships next, and how the bug pipeline turns into Claude-Code-fixed issues reviewed on staging before release.
- Meeting Coach β Meeting Coach β scorecards for sales calls, engineer demos, customer training and tech support calls, from the call's transcript.
- Account recovery β what to do when you can't log in β How to get back into your account if you've lost your password, 2FA device, backup codes, or even your email.
- 2FA β I lost my device β You lost your phone (or your authenticator app got wiped). Here's how to get back in.
- I think my account is compromised β You suspect your account is compromised. Here's what to do, in order.
1. Getting started with OtiumWork
Getting started with OtiumWork
OtiumWork is one AI-native platform for B2B software and services companies. It covers four areas: Revenue (sales and marketing), People (recruiting and HR), Work (time, projects and capacity) and Money (finance across entities). Your admin decides which modules are switched on.
This page covers the Work side: how time gets captured. Instead of typing timesheets by hand, the desktop client records your foreground app and window title, and AI classifies it into billable categories for you to review.
What gets captured
- Active application name (e.g.
chrome.exe,excel.exe) - Active window title (the text in the title bar)
- Duration β in 5-minute flush buckets
- Your idle state β so we don't log anything while you're away
Explicitly not captured: screenshots, keystrokes, clipboard, file contents, camera, microphone, URLs beyond what's in the title bar, emails, chat contents.
The two sides of OtiumWork
- Desktop client β a small Windows tray app that captures the above and sends it to your company's OtiumWork server every 5 minutes.
- Web app β where you review + correct your events, see reports, track projects, and manage your team.
First steps
- Install the desktop client. Takes ~2 minutes.
- Open My Day and tap a project tile to start a focus session β everything captured rolls up under that project until you switch tiles.
- At the end of your first day, scroll to Today's captured activity at the bottom of My Day β review what was captured, link events to projects, correct any misclassifications. Every field edits inline and saves itself. Anything older than today lives in the activity drawer, linked from that same section.
- Managers + admins: set up Projects and clients so billable work gets attributed.
When you're stuck
- Ask Oti β the copilot at the top of the sidebar. Ask "how do I β¦" in plain English; it answers from these help docs and links the page it used.
- Help & FAQ β every topic, browsable.
- Your manual at /help/manual β everything that applies to your role and module access on one printable page. Worth reading end to end on day one.
- Tooltips β hover any sidebar item for a one-line description of what's behind it.
Who sees what
- Employees: your own captured events (no one else's), your own timesheet, projects you're on, your own Clockify history.
- Managers: everything above + events/reports for your direct reports + the team-aggregate view.
- Admins: everything company-wide. Plus settings, billing, AI budget, client management.
Privacy + transparency
Every event we captured on your machine shows up under Today's captured activity on My Day (and in the activity drawer for earlier days), editable. You can pause tracking at any time from the system tray icon (right-click β Pause 30 min / 1 hour / 4 hours). Tracking never resumes on its own β you decide.
More on privacy: see Privacy & data.
2. Ask Oti β the in-app copilot
Ask Oti β the in-app copilot
Ask Oti is the first item in the sidebar (π¦¦). It's a chat window that answers two kinds of questions:
- How do I use this? β "how do I request vacation", "where do I edit a work type", "how does approval work". Oti searches the same help docs you can read at /help and answers with the relevant passage plus a link to the full page, so you can always check the source.
- What's going on with my work? β "what's on my plate", "where did my time go last week", "how much PTO do I have left". These read your live data.
What it can see
Oti runs on skills β small tools it's allowed to call. Which skills exist for you depends on your role and module access, exactly like the rest of the app:
- Everyone gets the help search, their own tasks, their own tracked hours, their own PTO balance.
- Managers and admins additionally get rollups over the people they're responsible for.
- Sales-team members get the Salesforce / pipeline skills.
Ask "what can you do?" and Oti lists every skill you currently have. If a skill isn't listed, it isn't available to you β asking again won't unlock it, and Oti can't read another employee's data on your behalf.
Tips
- Ask in plain English; you don't need to know the feature's name.
- If your question is ambiguous, Oti asks a short clarifying question instead of guessing.
- Conversations are saved per person in the sidebar β reopen an old one or delete it any time.
- Oti never invents product behaviour. If the help docs don't cover something, it says so β that's your cue to file feedback so the doc gets written.
The other ways to get help
- Help & FAQ β every topic as a browsable card grid.
- Your manual at /help/manual β every topic that applies to your role and module access, stitched into one printable page. Good for a new hire's first day.
- Hover any sidebar item β each one has a one-line tooltip explaining what lives there.
- Admins get a setup checklist on the admin dashboard that tracks first-run configuration.
3. My Day
My Day
/my-day is your daily home in OtiumWork: tap a project tile β everything your desktop client captures until the next tap gets attributed to that project. For retrospective fixes use /events/mine.
How it works
- You open
/my-day. You see tiles for every project your manager has assigned to you, ordered by urgency (tasks due in 48h β over-budget β logged-today β recent β everything else). - You tap a tile. A focus session opens:
project_id = that tile. - The desktop client polls
/api/focus/currentevery 30 seconds and stampsX-Session-Idon every captured event it uploads. - On the server side, each
work_eventis tagged withsession_idand itsproject_idis set to the tile's project (the tile-press is explicit user intent β it overrides any auto-guessed project_id from rules / LLM). - When you tap a different tile, the current session closes (
ended_at = now) and a new one opens. - Tap "Stop & go idle" to close the session without opening a new one (lunch, end of day, etc.).
Capture modes β Auto / Hybrid / Manual
At the top of /my-day there's a small capture-mode chip. Click it to cycle AUTO β HYBRID β MANUAL β AUTO. It sets how the server treats events your desktop client uploads β it does not change the desktop client itself, only what the server keeps:
| Mode | What the server does | Use it when |
|---|---|---|
| Auto (default) | Every desktop-client event becomes its own work_event row. Tapping a tile sets the project_id. This is the classic "tap a tile, everything rolls up under it" behavior. |
You want full automatic tracking with the least effort. |
| Hybrid | While a block is open, the captures during that block are collapsed into one session-level row instead of one row per window-switch β so a 1-hour block is a single tidy line, not 40 fragments. While no block is open, it behaves exactly like Auto. | You like auto-capture but want clean, block-sized entries instead of granular fragments. |
| Manual | The server drops every desktop-ingest event. Nothing is recorded unless you create it β by tapping a tile or starting a manual block. Your hours come only from time you explicitly log. | You'd rather punch in your own time blocks and not have passive capture at all. |
Why this matters for your totals: in Hybrid and Auto, a project can show hours from two sources at once β the manual block you opened and the desktop activity captured underneath it. That's expected; the block and its rolled-up captures are the same time, not double-counted. In Manual, the only hours are the blocks you key in.
If a project shows hours you don't recognize, check your capture mode first β Hybrid/Auto are folding in real desktop captures, not just what you typed.
What doesn't change
- Category, work type, department β still set by the existing three-layer classifier (admin rules β past corrections β Claude Haiku). My Day only owns
project_id. - Desktop client capture β nothing changed. Window titles still get captured every few seconds, grouped into per-minute buckets, flushed every 5 minutes.
- Your manual corrections β still override everything. Edit any event at
/events/mineand your edit wins.
Precedence for project_id / task_id on each event
From highest to lowest priority:
- Manual correction in
/events/mine - My Day active tile + task (manually chosen via the tile grid / task dropdown)
- Outlook auto-focus session (opened because a calendar meeting's subject matched a project)
- Classification rule match on window title
- LLM (Haiku) guess
NULLβ shows up in the "needs classifying" queue
Note: if you manually tap a tile, the Outlook auto-focus will not override your choice. It only acts when you're idle (no open session) or when the currently-open session was itself auto-opened by Outlook.
Times are shown in your time zone
Block start/end times on My Day and My Week are rendered β and read back when you edit them β in the time zone on your profile, not the browser's. Travelling with a laptop set to a different zone no longer shifts your blocks. If times look off by a fixed number of hours, check the time zone on your profile first. Adjusting a block's time keeps its caption/task as-is.
The timeline below the tiles
Once you've started using tiles, "Today's sessions" appears below the grid β a chronological list of what you focused on today with duration per session. Each session is expandable to see the underlying captures.
Logging time against tasks (not just the project)
Hours can attach to a project alone, or to a task within that project. If you want per-task breakdowns β and you usually do, since that's what makes the project's task list and burn-down meaningful β you have to point your time at a task. Here's the full flow:
- Give the project tasks. A project with no tasks can only collect project-level hours. Add tasks from the project's detail page (
/projectsβ the project β per-task table), from My Tasks, or inline while editing a block (the + next to the Task dropdown β manager/admin role). - When you work, pick the task. Tap the project tile, then choose the task in the Task: dropdown on the active banner. From then on every captured event stamps both
project_idandtask_id, so the hours land on that task. The soonest-due task is auto-selected; switch anytime. - Check it landed. The project detail page breaks hours down per task and per person. If a task reads zero, no time was stamped to it.
The common trap: if you open a manual block (or tap a tile) and don't select a task, the hours attach to the project only β the project shows time but every task reads zero. This is the #1 reason "the project has 14 hours but the tasks are empty."
Fixing it after the fact: you don't have to re-log anything. Click the block on the My Day timeline β Edit block β set the Task β save. The underlying work_event rows are re-stamped onto the task. For older entries, use the activity drawer at /events/mine (edit inline, or shift-click a range and bulk-assign).
Overlap warnings β when a manual block fights a calendar meeting
If you start a manual focus session (project tile) at, say, 2-3pm AND your Outlook calendar has a meeting at 2:30-3pm, both blocks render side-by-side on the timeline strip β and both contribute minutes to your totals. That's 1.5h on the books when you really only worked 1h.
To avoid the double-count, an amber banner appears at the top of /my-day with two quick-resolve buttons per overlap:
- Keep meeting Β· drop session β deletes the manual
focus_sessionplus anywork_eventrows that rolled under it. - Keep session Β· drop meeting β deletes the calendar-imported
work_eventrow(s) for that meeting.
A pair is flagged when they overlap by β₯50% of the shorter block. Up to 5 conflicts surface at a time. Desktop-tracker fragments inside a meeting window get absorbed silently β those never trigger this warning.
Stale focus-session warning
If your current focus session was started more than 24h ago, a separate amber banner shows up offering a one-click "Stop the stale session" button. Common case: you tapped a tile on Monday morning and forgot to tap Stop. Until you close it, every desktop capture gets stamped with that session's project, and the calendar strip stretches across the whole stale window.
What "My Activity" is for now
/events/mine is still there. It's the audit / fix-it drawer: use it when you forgot to tap a tile in the morning, when you want to fine-tune per-event categorization, or when a manager asks "what were these 3 hours on Tuesday?" It's no longer the daily destination β My Day is.
Urgency ordering (tile sort)
Top-to-bottom:
- Due soon (red): project has an assigned task with
end_dateβ€ today + 48h - Over budget (orange): project has
budget_hoursand logged hours exceed it - Today (blue): you've already logged any time to this project today β stay in context
- Recent (gray): you've logged time to it in the last 7 days
- Assigned (faint): everything else you're assigned to
Phase 2 (live as of 2026-04-24)
- Task-level granularity. When you tap a tile, the active banner shows a Task: dropdown with that project's open tasks. The soonest-due task is auto-selected; switch to a different one anytime. Every event captured during the session stamps both
project_idandtask_id, so timesheets and reports can break down hours per task. - "Switch tile?" nudge. If the last 15 minutes of captured window titles mention a different project more than the tile you're currently on, a yellow banner appears at the top of
/my-daywith a one-click Switch to X button. Safety-net for the "oh, I forgot to tap" moment. - Outlook-meeting auto-focus. If you've connected Outlook (Admin β Settings β Microsoft 365), a server cron checks every 2 minutes whether a meeting is happening right now. If the meeting subject contains the name of one of your assigned projects, a focus session opens automatically β same as if you'd tapped the tile. Manually-opened sessions are never overridden. When the meeting ends, the auto-opened session closes and you return to idle.
Editing a calendar block β inline task creation
Click any block on the calendar timeline to open the Edit block modal. You can change the label, project, task, and start/end times.
If the project you pick doesn't yet have the task you want (e.g. you just realised this meeting was a reseller meeting and that task doesn't exist), hit the + button next to the Task dropdown. A small inline row appears β type the task name, hit Add (or Enter), and the task is created on that project and pre-selected for you. Manager/admin role required.
Phase 3 (not yet)
- Cross-device tile sync via websocket (today it's 30s polling, which is fine)
- AI suggesting the right tile from capture signals without even needing the nudge
- Manager live view: see who on your team is focused on what right now
4. My Tasks
My Tasks
/my-tasks is your personal work inbox. It sits next to My Day in the sidebar (with a badge showing how many tasks are open) and pulls everything that's yours into one triage list.
What shows up here
- Personal β standalone to-dos that aren't tied to any project. These are private to you; no one else can see them.
- Each project β tasks on real projects where you're the assignee or a collaborator.
- IT tickets β helpdesk tickets assigned to you (they already mirror in as tasks). The row links back to the ticket.
- Marketing requests β requests assigned to you, linking back to the request.
Each task shows its priority (high / normal / low) and due date, and overdue dates are highlighted in red. Tasks handed to you by a colleague are tagged "from ".
Adding a task
Use the bar at the top:
- Name β what needs doing.
- For β leave as Myself for a personal to-do, or pick a colleague to assign it to them (see below).
- Due and Priority β optional.
Working your list
- β Done β marks a personal or project task complete and drops it off the list.
- Edit β (personal tasks) change the name, due date, or priority inline.
- β β (personal tasks) delete it.
- Open β β for IT tickets and marketing requests, jump to the source to update them there. (Their status is owned by that module, so close them at the source to keep things in sync β not from here.)
Assigning a task to someone else
Pick a colleague in the For dropdown when adding a task. It becomes their personal task, shows up in their My Tasks marked "from you", bumps their sidebar badge, and emails them a heads-up. Use it for quick hand-offs without spinning up a whole project.
My Day integration
Tasks that are due today or overdue also appear in an "On your plate today" strip at the top of My Day, so your daily planning sees them without leaving the page.
5. My activity
My activity
As of 2026-04-24, My Day (/my-day) is where you start your day. My activity (/events/mine) is now the audit drawer β the place to go when you forgot to tap a tile, when you want to re-categorize a specific event, or when a manager asks about a particular hour block.
Everything below still works identically β it just isn't your daily home anymore.
The review page
/events/mine is your personal review page β every event captured on your machine (or entered via Timer) shows up here. Review it when My Day's auto-attribution needs correcting.
Filters
The page defaults to your last 7 days. Use the filter bar at the top to narrow further:
- From / To β pick any date range. To-date is inclusive ("To = Friday" includes all of Friday).
- Project β show only events linked to one project, or All for everything.
- Only unclassified β toggle to see just the rows still tagged
category=unclassified. Best filter when you want to triage quickly. - Reset β clears all filters and snaps back to the last-7-days default.
Results are paginated 100 per page; if you have more matches, page links appear under the table. The result count is shown at the right side of the filter bar.
What you can edit
Every row is inline-editable:
- Category β the type of work (see Categories)
- Work type β billable / internal / training / off-time
- Project β which project this event is for
- Department requested β which team requested this work (cross-team support)
- Note β any free-text explanation
- Tags β labels you or your admin set up
Bulk-link to a project
If you worked on the same project for several captured events:
- Check the β box at the left of each relevant row.
- Scroll to the top; the "N selected" banner lights up.
- Pick a project from the dropdown (or "(unlink)" to clear).
- Click Apply. All checked events are updated in one shot.
Or hit + New project in the same banner if the project doesn't exist yet β it'll be created with you auto-assigned as a team member.
What "corrected" means
When you edit any classification field, OtiumWork records your edit as an employee correction. This has two effects:
- Future identical events get classified the same way automatically. If you change all
chrome.exe / Gmailevents tocategory=communication, the classification engine will use that pattern on future events without calling the AI. - Your manager can see the correction count on the Team page β high correction rates hint that either the AI is misclassifying you specifically or your work is ambiguous.
Categories can come from multiple sources
Each event's classification_source field tells you how it was classified:
ruleβ an admin-defined pattern matched (fastest, free)past_eventβ someone previously classified the same (app, title) and we reused itemployee_correctionβ you manually corrected itmanager_overrideβ your manager changed itllmβ AI classified it (Claude)timerβ legacy: logged via the old Timer page (removed; old events still carry this source)clockify_importβ imported from a Clockify historical export
Getting more classified
If too many events show as "unclassified", try:
- Writing admin rules (admins only): /admin/rules β deterministic patterns that fire instantly and cost nothing.
- Correcting a few events β future similar ones inherit automatically.
- Turn AI classification on (admins): /admin/settings β AI billing β Metered mode with a cap. Haiku is cheap.
6. Projects and clients
Projects and clients
OtiumWork uses two first-class entities for billable work attribution:
- Client β a billing entity (e.g., "Acme Corp"). Has a stage (prospect / active / archived), billing email, notes. Lives at
/admin/clients. - Project β work done for a client (e.g., "Acme Q3 feasibility study"). Has status, budget, start/end dates, team assignments. Lives at
/projects.
Every work event can be linked to a project; every project belongs to a client; reports aggregate up the chain.
Who can do what
| Employee | Employee who is the project's PM | Manager | Admin | |
|---|---|---|---|---|
| Create project | β (auto-assigned as member) | β | β | β |
| Edit project | Only if you created it | β for the projects you manage | β for your team's | β |
| Assign people to project | β | β for the projects you manage | β for your direct reports | β |
| View project detail | Only if you're assigned or created it | β | β for your team's | β |
| Plan on the Gantt (add tasks, drag dates, set assignee / status / %) | β | β for the projects you manage | β | β |
| Create client | β | β | β | β |
| Change client stage | β | β | β | β |
Project managers with the plain "employee" role
Running a project doesn't require the manager role. Someone counts as a project's PM β and gets the rights in the column above, on that project only β if either:
- they're named in the project's Project manager field (project edit), or
- their role on project in the team list is
PM,Project Manager,Program Manager, orLead(case-insensitive).
A PM-employee sees the projects they manage on /projects with the planning
(Gantt) strip, and can assign work to anyone staffed on those projects. They
still don't get the company-wide capacity grid, the KPI strip, profitability,
or any dollar figures β those stay manager/admin (and Finance-flag) territory.
Salesperson on a project
The Salesperson field (project create/edit) names who sold the project. That person can open the project and follow its hours β on the project page and on the time report for any period β to decide when to bill and when to call the customer. It's read-only: they aren't added to the team, can't edit the project or its tasks, and see no dollar figures unless they already have Finance access.
Client stages
- Prospect β you're doing pre-sales work, not yet a paying customer. Hours here count as pre-sales investment (
/reports/presales). - Active β paying customer. Hours on active-stage clients count as billable.
- Archived β dormant or lost deal. Hours stay in history but are ignored by active reports.
When a prospect signs, flip their stage to active from /admin/clients β pre-sales hours retroactively count as converted investment.
Project status
plannedβ not started yet (shows on Gantt but not in active views)activeβ in progresson_holdβ pausedcompletedβ done and billedcanceledβ shut down before completionarchivedβ historical / imported (hidden from/projectsby default; click + Show N archived to reveal)
Jumping to a specific project
The filter bar on /projects and /projects/gantt has a Jump to β dropdown listing every non-archived project alphabetically. Picking one navigates straight to that project's detail page (per-task table + per-person time-spent breakdown). On the unified Gantt at /projects, project name labels are also clickable.
Budgets + alerts
Projects can have: - Budget hours β e.g., "200 hours allocated" - Budget dollars β hard spend ceiling - Alert threshold β default 80%; when logged hours Γ hourly_rate crosses this fraction of budget, admins get an email alert
The Hours logged and Cost logged cards on the project page are labelled with the period they cover: the headline figure is the whole project, and the small line under it is the last 30 days. Budget alerts and burn-down use the whole-project figure.
Linking events to projects
Three ways:
- Desktop client correction β right-click tray icon β Review recent events β pick project from dropdown.
- Web review page β
/events/mine, edit inline or use bulk-link. - Rules β admins create pattern-based rules at
/admin/rulesthat auto-link matching events.
Meetings: notes, transcripts and attachments
Each project has a Meetings list. Open a meeting to record attendees, action items and a transcript, and click Extract summary + action items with AI to turn the transcript into a summary.
Under Attachments you can add up to 5 files at a time, 20 MB each: PDFs, images, Word, Excel, PowerPoint, and text or caption files. A transcript file (.txt, .vtt, .srt, .md or a Word .docx, such as a Teams transcript export) also fills the meeting's Transcript if it's empty, so you can run the AI extract straight away. Anyone on the team can open the files. The person who attached a file, or a manager or admin, can remove it.
Projects that need a customer (Tech Support, Sales Support)
Some projects are company-wide buckets where the useful question is which customer the time was for, such as Tech Support. On a project's Edit page, tick Customer required on time entries. After that:
- adding time to the project, or moving a block onto it, asks you to pick the Customer;
- if you're running a focus session on it without a customer, My Day shows a reminder on the live tile, and picking one there tags everything in the session.
Support hours per customer: open the Time report, set Project to Tech Support (or Sales Support), and set Group by to Customer. Time logged without a customer shows up as "(no client)", so you can see what's still missing.
7. Vacation (PTO)
Vacation (PTO)
/pto is the employee surface for requesting time off and seeing your balance. Approved vacation automatically reduces your weekly capacity on Team β Capacity, so managers see realistic availability.
How the balance works
Each year:
remaining = annual_vacation_days β approved_days_this_year β pending_days_this_year
- Entitled β your contract entitlement (default 20 days/year; admin/finance set per-employee).
- Used β sum of approved vacation days in the current calendar year.
- Pending β requests still awaiting a decision, whether that's a manager or an executive after escalation (held against your balance until decided).
- Remaining β what you can still request.
Workdays only β MonβFri. Weekends in your range don't count against the balance.
Request flow
- Employee opens
/pto, picks dates, optionally adds a reason, submits. - Manager sees the pending request at Team β Vacation approvals. Approves or rejects with a comment.
- Approved vacation immediately reduces capacity in the affected weeks. Rejected requests go back to "Rejected" with the manager's comment visible to the employee.
- Cancel β employees can cancel their own request for as long as it's still awaiting a decision, including after a manager escalated it to an executive. Once it's approved or rejected they can't.
Manager view
/team/pto-approvals (Team β Vacation approvals) β pending requests from your direct reports float to the top with employee, dept, dates, days, reason, and Approve/Reject buttons. Admins see the full company.
Capacity impact
Each cell on Team β Capacity now shows allocated / capacity where:
capacity = max(0, 40 β company_holiday_hours β approved_PTO_hours)
Approved PTO uses 8h/workday for the days that fall in that week. Tooltip on the cell breaks down the math.
Setting entitlement (admin or finance-flag holders)
/admin/employees/<id>/edit β the Annual vacation entitlement (days) field. Defaults to 20. Set:
- 0 for contractors (typically no PTO)
- 25 for senior staff
- Custom per contract
Existing approved/pending days roll forward β only new requests use the updated cap.
Limits
- Tier 1 only β company-wide holidays + per-employee approved vacation.
- No carryover-from-prior-year accounting yet.
- No accrual rate (e.g., "1.67 days per month") β just a yearly cap.
- No outlook-OOO sync yet (Tier 2, future).
8. AI-drafted weekly timesheet
AI-drafted weekly timesheet
On /timesheets every week with captured activity has a β¨ AI draft button. Click it and Claude reads your week's events and produces a professional summary β executive-line, per-project bullets, and a Notes section for anything noteworthy (long meetings, unusual off-time, etc.).
What it's good for
- Weekly status emails to your manager β copy the draft, paste into Outlook, edit if needed, send.
- Monthly performance docs β string together four weeks to get a month-end narrative.
- Client retainer reports β filter to billable work, paste as the "this week's delivery" block.
- Memory aid β if you can't remember what you did on Tuesday, the draft reminds you.
How it works
- Your week's captured events (desktop client + Timer + any Clockify-imported rows) are grouped by project and category.
- A compact JSON payload (not your raw window titles β just aggregates + sample notes) is sent to Claude Haiku with a "draft a professional timesheet" prompt.
- Result stored on your timesheet row β regenerating overwrites. Can draft as many weeks as you want.
Uses AI credits from your company's metered allocation (or your BYOK key if admin picked that). One draft β $0.005 at Haiku pricing.
Privacy
- Per-user scope β only you see your own drafts. Even your manager can't see them (they live on your timesheet row).
- Events not in your captured work (e.g., someone else's) are never fed to the model.
- Drafts are never auto-submitted β you always review before sending anywhere.
9. Connect your Outlook calendar
Connect your Outlook calendar
OtiumWork can automatically pull your Microsoft 365 / Outlook meetings into your timeline so the time you spend in meetings shows up as events without you having to log them manually.
How to connect
- Open My Day (or any page where your events list is visible).
- Click Connect Outlook (button appears in the integrations strip if you don't already have a connection).
- You'll be redirected to Microsoft's sign-in page. Use the same Microsoft account that hosts your work calendar.
- Approve the requested permissions (read your calendar, read your profile so we know which mailbox you connected).
- Microsoft redirects you back to OtiumWork. You'll see a green "Outlook connected for your.email@company.com" banner.
What gets imported
After connecting, click Sync in the integrations strip to pull the last 7 days of meetings. After the first manual sync, OtiumWork runs a background sync nightly so future meetings appear automatically.
Each meeting becomes an event with:
- Start + end time from the Outlook entry
- Title from the meeting subject
- Category / work-type auto-suggested (you can recategorise later)
- Marked as source = outlook so you can tell auto-imported events apart
What does NOT get imported
- Cancelled meetings
- All-day events without a specific time range
- Meetings older than the sync window (default 7 days back)
- Meeting body / attendee list / attachments β we only read the time + title
Disconnect
Same integrations strip β Disconnect Outlook. This deletes the stored refresh token and stops future syncs. Previously-imported events stay in your timeline (they're just normal events at that point).
Troubleshooting
"Your admin hasn't configured Microsoft credentials yet"
Your company hasn't set up the Microsoft 365 app registration. An admin needs to go to Admin β Settings β Microsoft credentials and enter the tenant ID + client ID + client secret. After that you can re-try Connect.
"approval request sent" / scopes need admin consent
Some Microsoft tenants require an admin to pre-approve the OtiumWork app's permissions. Ask a tenant admin to: 1. Open Azure Portal β App registrations β OtiumWork 2. Go to API permissions 3. Click Grant admin consent for [your tenant]
After admin consent is granted, you can click Connect again and it'll go through.
"Microsoft did not return a refresh_token"
Means the offline_access scope wasn't granted. Disconnect, then connect
again and make sure you don't uncheck any scope on the consent screen.
"Your sign-in session expired before Microsoft redirected back"
You opened the Microsoft sign-in in a different tab or browser. Click Connect again and complete the prompts in the same tab.
"Last sync failed: β¦" banner on the connection card
The background sync has nowhere to show an error, so when Microsoft refuses a sync the reason is recorded and shown on the Outlook card (with the time it happened) instead of the page silently saying "Connected". The two cases:
- Consent revoked / refresh token aged out (
invalid_grant,interaction_required,consent_required) β only you can fix this: click Reconnect Outlook on the card and approve the prompts again. Previously-imported events are untouched. - Company client secret expired β this stops the sync for everyone at once. An admin needs to rotate the secret at Admin β Settings β Microsoft 365; nobody has to reconnect afterwards.
The banner clears on the next successful sync.
Events imported but in wrong time zone
OtiumWork uses your profile's time zone. Check My Day β settings β Time zone. If it's set to UTC, switch to your actual zone and re-sync.
Privacy
OtiumWork only requests two Microsoft Graph scopes:
- Calendars.Read β read your calendar entries (start/end/title only)
- User.Read β read your basic profile so we display which account is connected
- offline_access β allows nightly background sync without you having to
re-sign in every time
We never request mailbox / email contents, contact list, or write access to your calendar.
For admins setting this up the first time
See Admin Settings β Microsoft credentials for the one-time tenant
config. You'll need:
- Microsoft Entra ID tenant
- App registration with redirect URI: https://otiumwork.com/admin/integrations/outlook/callback
- Client ID + Client secret
- Above three Graph permissions added + admin-consented
After that, every employee can self-serve Connect without your involvement.
10. Expenses
Expenses
Expenses in the sidebar is where you claim money back β a taxi to a client, a conference ticket, a software subscription you paid for personally. You submit, your manager approves, finance pays. Everyone has this page; what you see on it depends on your role.
Submitting one
New expense needs three things: what it was for, how much, and when you incurred it (today by default). Everything else helps whoever approves and books it:
- Category β travel, meals, accommodation, software, office supplies, professional services, mileage, conference, client entertainment, or other.
- Currency β defaults to USD, change it if you paid in something else. The amount is not converted for you; it's recorded as spent.
- Project and Entity β which work, and which legal entity, the cost belongs to. Both show on the claim so your approver and finance can see what they're paying for without asking. Note that a claim tagged to a project does not flow into that project's profitability figures β those are built from tracked hours and invoices, not expenses.
- Receipt β a photo or PDF. Optional, but almost always what your approver asks for next if it's missing.
Attach the receipt first. OtiumWork reads it with AI and pre-fills the amount, currency, date, merchant and category for you, so most claims become a glance-and-submit. It only fills fields you haven't typed in yet, so it can't overwrite your own wording. If the scan can't make sense of the image, nothing breaks β you'll see a note saying so and you fill it in yourself. Either way, check the numbers before submitting: what's on the receipt and what you're claiming are your responsibility, not the scanner's.
Once you submit, your manager is notified automatically. You don't need to chase anyone or send a separate message.
What happens next
| Status | Meaning |
|---|---|
| submitted | Waiting on your manager. |
| pending_admin | Your manager approved, but the amount is over your company's threshold, so it also needs executive sign-off. |
| approved | Cleared for payment; sitting in finance's payable queue. |
| rejected | Turned down β the reason your approver typed is shown on the expense. |
| paid | Money sent. You're notified, and the payment method and reference are recorded. |
The threshold that triggers the extra sign-off is set per company by an admin, so a $40 taxi and a $4,000 flight can follow different paths without you having to know which is which.
Fixing or withdrawing a claim
You can delete your own expense while it's still submitted or after it's been rejected β so a claim sent in error, or one you need to resubmit properly, is yours to clean up. Once it's approved or paid it stays on the record.
If a rejection was a misunderstanding, submit a corrected claim rather than arguing on the old one; the reason text stays attached to the original for the audit trail.
Claiming for someone else
Finance and admins can submit an expense on behalf of another employee β useful when someone's out, or when a shared card payment needs to sit against the right person. Everyone else can only submit for themselves.
For approvers and finance
The approval side β the queue, the two-step escalation, and where the threshold is configured β is covered in Team and approvals. Finance's payable and paid views live on the same Expenses page, visible to anyone with finance access.
Related
- Team and approvals β the manager's side of this flow.
11. Partner portal
Partner portal
This page describes what your resellers / partners see at /partners/*. They reach the portal via an invite email containing a magic link β no password is set up for them.
Sign-in flow
- Partner contact receives an invite email the first time you add them as a contact (admin:
/admin/partners/<id>/contacts/new). Link valid 7 days. - They click β land at
/partners/dashboard. A 30-day session cookie is set. - After the first invite expires, they go to
/partners/login, enter their email, and a fresh 30-minute sign-in link is sent. Same flow as the customer portal.
If they can't find the invite, resend from /admin/partners/<id> β contacts table β "Resend invite."
What each role sees
The dashboard, navigation, and per-page content are gated by the contact's role. See the admin help for the full role table.
The top nav shows: Dashboard Β· Deals Β· Performance Β· Commissions Β· Resources Β· Ask Otium Β· Questions Β· Training Β· Profile. Items they can't act on are still visible read-only or hidden depending on role.
Submitting a deal (salesperson, principal)
/partners/deals/new β they fill in customer name, deal title, expected USD amount, optional close date, and free-text description. Submit creates a quote row with kind='partner_intent'. They see "Pending approval" in their portal until you decide.
Deals, performance and commissions
Deals has two views: the Overview (leads waiting, pending approval, pipeline, lost, won, not approved) and All deals β one table with filters for status, stage, product, a customer search and date ranges, sortable columns, totals and a CSV download. Performance and the Dashboard have a period picker (this quarter, last quarter, year to date, last 12 months, all time, custom) showing win rate, average deal size, days to close and the open pipeline by stage. Commissions filters by close date and by whether the customer has paid, with a CSV. Everything is limited to the reseller's own deals.
Resources
/partners/resources groups the files shared with them by category (Price list, Brochures, Presentations, Case studies, Datasheets, Other) with search, a folder filter, View for PDFs and Download, and a new since your last visit badge; the price list is pinned at the top and on the dashboard. Your channel team decides which files each reseller and role sees, and resellers get one daily email when new files arrive. It lists every document_space marked visible to their partner_id with their role in the allowed-roles CSV. Downloads route through the same authenticated app/storage.py path that internal employees use β full audit, no separate storage backend.
Ask Otium
/partners/ask β type a question. AxSTREAM technical questions are answered from the AxSTREAM wiki with the pages linked (every role); principals and salespeople can also ask for sales advice on a situation. Prices, discounts, delivery and contract terms always come from the channel team. If an answer isn't enough, Send to the channel team turns it into a question under Questions. 50 questions per person per day.
Questions (every role)
/partners/questions/new β submit subject + body, optionally link to a deal_id. Posts to partner_question table. Admins answer at /admin/partners/questions. Threading is single-level for v1 β one question, one answer (admin can update the answer).
Training
/partners/training lists modules where required_for_role matches their role (or is both). Each module shows their cert status:
- Not started β no passed cert exists for this contact + module.
- Certified β passed cert exists. Expiry date shown if
valid_for_dayswas set.
/partners/training/<id> shows the module description and the quiz. They submit; auto-grading writes a certification row. Pass = score β₯ module's pass_threshold (admin sets per-module, default 80%).
Footer
Every partner-portal page renders the tenant's brand (logo + primary color from company.brand_*), with a small "Powered by OtiumWork" footer link. Per-reseller white-label (where ABC Mexico shows their OWN brand instead of the tenant's) is a separate v2 build.
Limits / gotchas
- Sessions are tied to one browser. Sign-in from a new device β another magic link.
- The invite token in the URL is single-use. If they click twice, the second click hits "Link already used."
salespersonrole currently sees ALL of their partner's deals, not just deals they personally submitted. Tighter per-contact scoping is a follow-up.- Deal collisions (two partners registering the same end-customer) currently surface only at admin review time β no automatic territory rules in v1.
12. Categories, work types, and departments
Categories, work types, and departments
Each event gets two orthogonal classifications plus an optional department attribution. The starting values are below; admins can customize them per-company at /admin/taxonomy (sidebar: Categories & depts).
Editing the lists
- Add β type a new value, click Add. Available immediately in every dropdown.
- Deactivate β hides from new entries; existing events keep showing it (no rewrite).
- Reactivate β re-enables a previously deactivated value.
To rename a value, add the new one and deactivate the old. Bulk-correct existing events from the team admin page if you need historical consistency. Changes affect My Day, /events/mine, reports, manager review, classification rules, and the AI auto-classifier β all read your current company list.
Category β what kind of work was it?
Fixed enum:
| Category | Meaning | Example |
|---|---|---|
analysis |
Deep thinking, modeling, calculations | CFD simulations, financial modeling |
design |
Creating or editing deliverables | CAD drawings, slide decks, proposals |
documentation |
Writing docs, reports, wikis | Tech docs, SOPs, knowledge base |
meeting |
Scheduled or ad-hoc calls/meetings | Teams, Zoom, phone calls |
communication |
Email, chat, messaging | Outlook, Slack, Teams chat |
admin |
Internal operations | Expenses, HR, IT tickets, billing |
research |
Exploration without clear deliverable | Reading papers, competitor research |
content |
Marketing / content creation | Blog posts, social media, graphics |
prospecting |
Pre-sales, lead gen | Demos for prospects, outreach |
pipeline |
Active deal management | Proposals, scoping calls |
training |
Learning, courses, onboarding | Certifications, company training |
off_time |
Not actively working | PTO, sick leave, holidays |
unclassified |
Not yet categorized | Pending review |
Limiting a category to some departments
Some categories only make sense for one team, such as solver_development for
engineering or Social Media for marketing. On /admin/taxonomy, click
all departments under a category and tick the departments that should see
it. Everyone else stops being offered it in My Day and on their events page,
and the AI classifier stops putting their activity into it. Tick nothing to
offer it to everyone again.
It's matched against each person's Department on their profile. Events that already carry the category keep it, and admins and reports still see every category.
Work type β how does this affect billing?
Starting values:
| Work type | Meaning | Counts as |
|---|---|---|
billable |
Time the client pays for | billable |
internal |
Internal work, not billable | internal |
revenue |
Revenue-generating but not client-billable (e.g., commission work) | internal |
off |
Off-time (vacation, holiday, sick) | off |
training |
Paid training time | internal |
unclassified |
Not yet categorized | internal |
"Counts as" β the name is yours, the arithmetic is fixed
Work types are free-text labels you can rename or extend, so the reports can't rely on the name to know what to add up. Each work type therefore carries a counts as class β set from the dropdown beside it on /admin/taxonomy β and that class is what the reports, utilization and capacity actually total:
| Counts as | Effect |
|---|---|
| billable | Goes into the Billable column and billable-hours KPIs |
| internal | In the total hours, out of the billable column |
| off | Not work β excluded from hours totals and utilization |
If you add a work type such as client-support or retainer, set its class to billable or it will be treated as internal by default. Existing work types were classified automatically on upgrade (billable β billable, off β off, everything else β internal), which matches how the reports already treated them.
How they combine
A single event has one category and one work type. Examples:
- "Building a client slide deck" β
category=design,work_type=billable - "Team standup" β
category=meeting,work_type=internal - "Attending a conference" β
category=training,work_type=training - "Doctor's appointment" β
category=off_time,work_type=off
Who decides these values
- Admin rules (instant, deterministic) β patterns like "app=Outlook.exe β category=communication"
- Past event lookup β if someone corrected
chrome.exe / Gmailbefore, new events inherit - AI classification β Claude Haiku classifies when nothing else matches
- You correcting on My events β always wins; propagates forward
Adding your own dimensions
OtiumWork's categories are fixed (changing the enum requires a schema change). For project-specific or team-specific labels that don't fit the enum, use tags β see Tags.
13. Sending a document for signature
Sending a document for signature
Any document in OtiumWork can be sent out for signature. The signer needs no account and nothing installed: they get a link, read the document in their browser, type their name, and sign. What comes back is bound to the exact file they saw, so it holds up later.
Sending one
Signing starts from the document, not from a separate app. Upload the file under Documents, open it, and scroll to Send for signature:
- Title shown to the signer β what they'll see in the email subject and above the document, e.g. "NDA for Acme Corp".
- Signer email β where the link goes. Required.
- Signer name β a suggestion that pre-fills their name field. They can correct it.
- Message β optional, shown above the document.
- Expires in (days) β up to 90. After that the link stops working.
The link is emailed to the signer immediately, and also shown to you on screen β copy it if you'd rather send it through your own mail or a chat thread.
What the signer does
They open the link, read the document in the browser, and either sign or decline. Signing means typing their full name, optionally drawing a signature, and ticking the electronic-signature consent β the consent text is the standard UETA / U.S. ESIGN wording and is stored with the signature, not just displayed.
Declining is one click and doesn't require a reason.
The evidence trail
Every completed signature records the document's SHA-256 hash, the exact consent text that was shown, the signer's name and email, their IP address, and the timestamp β combined into an audit hash. That's what makes the signature meaningful: the file that was signed can be proven byte-for-byte later, even if you upload a new version afterwards.
Every completed request gets a permanent certificate page laying all of that out. It's linked from the Signing list for your side, and the URL itself is the evidence β anyone you hand it to can open it without an account, which is the point when a counterparty later asks for proof.
Tracking what's out
Signing in the sidebar lists the requests in flight, with how many parties have signed out of how many. The Finance, Legal and HR sections each link to the same list filtered to their own kinds of document β quotes, invoices and expenses under Finance, contracts under Legal, employee paperwork under HR.
Worth knowing: that list is company-wide, not personal. Anyone who can open it sees every signing request in the workspace, including who it went to. Sensitive paperwork belongs in a document with restricted access rather than being kept private by obscurity.
Cancel stops a request that's still outstanding.
Multi-party signing
Flows that need more than one signature β some HR and legal paperwork β issue a separate link per party, either all at once or in a set order. Each person signs their own link, and the request completes when the last one is in. The manual form on a document page creates a single-signer request; multi-party requests come from the flows that need them.
Elsewhere in the product
The same machinery signs things you may not think of as "documents": accepting a quote records a customer e-signature against a snapshot of that quote. So a signed quote and a signed NDA leave the same kind of trail.
If the module is turned off
An admin can disable E-signature per workspace under Modules. New requests then can't be created β but links already sent keep working, so nobody is left holding a dead link mid-signature.
14. IT helpdesk
IT helpdesk
A simple in-app ticketing system. Any employee can submit, IT staff triage from a shared queue. Tickets support screenshot/PDF attachments, deadlines, priority queue, and a morning digest email.
Turning it on
Per-tenant module flag: admin β /admin/settings/modules β toggle
IT helpdesk ON. Default is OFF for new and existing tenants
(it doesn't show up in anyone's sidebar until you enable it).
To make someone an IT-staff member, set their department field to
IT at /admin/employees/<id>/edit. They'll start seeing the IT
queue automatically.
What employees see
A single sidebar link in Your work:
- π οΈ IT tickets β opens
/it/minewhich has both: - The list of their own tickets with current status + due date
- A prominent "+ Report an issue" button at the top
Click the button β fill in title + category (Hardware / Software /
Network / Account / Other) + description β submit. Attach up to 5
screenshots or PDFs (β€ 5 MB each, image/* or application/pdf)
on the form or on any follow-up comment. The IT team is emailed
immediately.
When IT updates the ticket β comments, status changes β the reporter gets an email with a direct link.
What IT-staff and admins see
A dedicated IT sidebar section with three items:
- π οΈ Report IT issue β same form as above
- β My tickets β tickets they've personally submitted
- β‘ IT queue β the shared triage queue
The queue shows every ticket sorted by priority (Urgent β High β Medium β Low), then by due date (overdue surfaces first), then last-update time. Overdue dates render in red. Filter by status (Open / In progress / Resolved / Closed / All) and by category. A πN badge in the title column shows attachment count.
Triaging a ticket
Open a ticket from the queue. As IT-staff you get an "IT actions" panel:
- Claim this ticket β one-click; sets you as assignee, status flips to In progress
- Status dropdown β Open β In progress β Resolved β Closed
- Priority dropdown β Low / Medium / High / Urgent
- Due date picker β sets a deadline; overdue tickets surface in red
- Assignee dropdown β reassign to another IT-staff member
- Comment box β visible to the reporter; firing a comment also emails them. Supports attachments.
Logging time on a ticket
Every ticket gets a matching task, IT-<id>: <title>, under the
IT Department project, and the ticket's status carries over to the task
(resolved or closed β done). Time is not logged automatically. The
assignee is added to IT Department so the task shows in their My Day
picker.
The quickest way is the β± Log time form on the ticket page: enter the
minutes you spent (plus an optional note), and an entry ending now is added
to the ticket's task. The page shows the running total next to the linked
task. You can still log it from My Day by picking the IT-<id> task.
Logging time doesn't close the ticket; set the status to Resolved or Closed as before.
Manager priority/deadline overrides
Anyone with role manager (or admin) gets a Manager actions
panel on a ticket they can view, with just two controls:
- Priority β promote/demote so urgent items surface
- Due date β set a deadline to commit to
Managers can't change status or reassign β those stay with IT-staff β but they can flag importance and ETA from any ticket they have access to (their own team's submissions, or all of them if they're admin).
Status semantics
- Open β fresh ticket, not yet picked up
- In progress β someone's working on it
- Resolved β IT thinks it's fixed; reporter gets emailed and can reply if wrong
- Closed β done, no further activity expected
Morning digest
Every morning at 07:00 UTC, every IT-staff member (and admin) gets one email per company listing all open + in_progress tickets, grouped by priority and sorted by due date. Overdue tickets are flagged inline. The digest is skipped for companies with zero open tickets.
If you want a different time, that's a single line in the prod
crontab (/api/cron/it-morning-digest).
Email notifications
| When | Who gets emailed |
|---|---|
| Ticket submitted | Every IT-staff member + admins (broadcast) |
| Status change | The reporter |
| Comment added | The "other party" |
| Daily 07:00 UTC | All IT-staff for any tenant with open tickets |
Attachment policy
- Allowed types:
image/png,image/jpeg,image/gif,image/webp,image/heic,application/pdf - Max size: 5 MB per file, 5 files per upload (per submit/comment)
- Storage: content-addressed via
app/storage.py(deduped by sha256) - Access: only the reporter, IT-staff, and admins can fetch via
/it/attachment/<id>
Out of scope for v1: SLA timers, internal-only comments, asset register,
knowledge base, escalation rules. Add as needed via /feedback.
15. Tags
Tags
Tags are free-form labels you apply on top of the fixed category + work type enums. Use them for things that span projects, departments, or quarters β any label that doesn't fit a single existing dimension.
When to use a tag vs a category
Use a category when the work is intrinsic (analysis, meeting, adminβ¦) β these are cross-company standards.
Use a tag when:
- The label is temporary: Q3-push, year-end-close
- The label cross-cuts existing dimensions: R&D, compliance-audit
- The label is project-specific but you don't want a separate project: prospect-X-research
Managing tags (managers + admins)
/admin/tags β add, edit, archive, set colors. Each tag has:
- Name (short)
- Color (color picker)
- Active flag
Applying tags to events
- Desktop client tray β Review β picker (once shipped in a future client release)
- Web:
/events/mineβ tags appear on each row (future enhancement) - Manager overrides on the team view can set tags too
Filtering by tag
On /reports/time there's a Tag filter dropdown. Pick a tag to scope the report to only tagged events.
Honest take
Tags are table-stakes feature-parity with Clockify, but in practice most OtiumWork customers use categories + projects + clients and rarely need tags. If you never reach for them, that's fine β delete them later.
16. Competitor tracking (your company's)
Competitor tracking (your company's)
This is where your company tracks your own competitors β the ones in your market, that threaten your product. For SoftInWay that's Aspen Technology, Concepts NREC, etc. for the AxSTREAM engineering software.
Not to be confused with OtiumWork's roadmap at /roadmap β that's for voting on features you want OtiumWork to build. This page is for your product's competitive landscape.
Three surfaces:
/admin/competitors β source list
A curated list of competitor URLs (product blogs, changelogs, release notes, etc.). Every Monday at 10 UTC, Claude fetches each URL and surfaces feature announcements from the last 14 days.
Editing a competitor: expand the Edit disclosure on any row. Change name, URL, category, notes. Employees, managers, and admins all have edit access.
Deep scan a competitor: expensive one-shot β Claude reads their product pages and enumerates their full feature set, tagged SHIP / CONSIDER / AVOID / NOOP vs your offering. Takes ~30-60 seconds per competitor. Managers + admins only.
/admin/competitors/features β feature board
Every finding across competitors, tagged with:
- SHIP β build this, high priority
- CONSIDER β debate it
- AVOID β intentionally different from them
- NOOP β you already do it / not relevant
Inline edit of tag, status (new / backlog / building / shipped / skipped), priority 1-5, and notes. Use the status workflow to push SHIP items through your dev pipeline: new β backlog β building β shipped.
Dev roadmap view: /admin/competitors/features?tag=SHIP&status=backlog gives you the fastest next-steps list.
Voting: Every feature row has a β² vote button. Any employee can vote (one per user per feature). Vote counts sort rows within each tag β popular items float up, so the roadmap reflects what the team actually wants to see shipped. Includes features auto-promoted from user feature requests.
/admin/competitors/mine β personal feed
Per-user subscriptions. Click the β on any competitor or feature to star it β now it shows up in your feed.
Two subscription scopes: 1. Personal β just you. Click β on a row. 2. Team (managers + admins only) β expand the "teamβ¦" disclosure, pick a department, click Toggle team. Everyone in that department now gets the subscription.
Two subscription targets: 1. Full competitor β any signal from the competitor hits your feed. 2. Specific feature β only that one feature is tracked.
Email digest
Weekly digest runs automatically; recipients are all active admins. Shows SHIP / CONSIDER findings from the last 14 days across all tracked competitors.
17. Engineering AI
Engineering AI
OtiumWork's Engineering section is the tech-support flavor of the Peter AI assistant. Sales reps use Peter to nurture prospects through the Challenger sale; engineers use the same plumbing but with a different prompt scaffold β one that's tuned to resolve technical questions, reference internal docs, and stay clear of sales moves.
Eligibility: anyone with employee.persona_mode = 'engineering' (or admins). Set by an admin from the employee record. Developer accounts (the is_developer "dev user type") also get the TPOC View β it's a technical team dashboard β but not the sales-tuned surfaces (Drafts, Customer meetings, Engineering AI config).
Four surfaces
TPOC View (/engineering/tpoc-view)
The shared team dashboard for tech-point-of-contact assignments. Each engineer's accounts are grouped together with at-a-glance health columns:
- Last touch (resource-center activity of the first listed contact) plus a separate Real last touch column you fill in by hand for the actual customer touch β meeting, call, on-site. Both are colour-coded green (β€30d) / amber (31-89d) / red (β₯90d).
- Next meeting is auto-joined from your Outlook calendar β any future external-attendee meeting whose attendee matches the row's POC email or domain.
- Tech support expires with days-to-expiration pill.
- Filter pills at the top: Tech support (Active / Expiring β€90d / Expired) and SF match (No SF match / Loose match) for quick triage.
Per-row buttons:
- π§ β Set or clear the SF Account override. Use this when the auto-matcher gets the wrong Account (or none).
- β β Edit any field. Salesperson / Tech support expiration / Comments push through to Salesforce. Real last touch / priority / POC name stay local.
- β¨ β AI-generated 5-bullet account briefing. Pulls row data + extra contacts + last 5 SF Tasks, asks Claude Haiku for a tight summary. Cached on the row; click Regenerate to refresh.
- π₯ β Manage all contacts at the account beyond the primary POC. SF Contact ID auto-resolves from email where possible. The number shows how many extra contacts are tracked.
- β β Compose and send an email from your connected Outlook mailbox (saved to your Sent Items).
- π β View the last 10 SF Tasks on the account and add a new "TPOC note" Task inline. Single source of truth: notes live in Salesforce, not in OtiumWork.
- π β Remove the TPOC row (doesn't touch Salesforce).
Customer meetings (/engineering/meetings)
Customer-attended meetings synced from your Outlook calendar β past 30 days and next 14 days. The list is split into Past (most recent first) and Upcoming (soonest first). Any meeting with at least one external attendee (non-@<company>.com address) shows up.
- Add notes per meeting in the inline text box. Saved locally so you keep a personal resolution log.
- Save & sync to SF mirrors the notes to Salesforce as a Task on the matched record:
- First we try exact email match β SF Lead/Contact (Task on Contact + Account).
- If no Contact exists, we fall back to domain match β SF Account (Task attaches to the Account directly). Common case: SoftInWay has the Account in SF but the specific engineer the customer sent isn't yet a Contact.
- Re-saving updates the same Task (idempotent via
work_event.sf_activity_id). - Hide filters personal reminders that aren't real customer meetings (e.g. "pick up the kids" with a single external attendee). Click "Show hidden" to recover.
Salesforce sync uses the company-level SF connection β engineers don't need to connect their own SF. All engineering meeting Tasks attribute to the shared tenant SF token.
Drafts (/engineering/drafts)
Peter watches your inbox and drafts tech-support replies in your voice (see Voice tuning below). Drafts land in your Outlook Drafts folder β you review, edit, send.
Connect once at the top of the page (separate OAuth from the calendar Outlook β needs Mail.ReadWrite + Mail.Send scopes so Peter can write drafts on your behalf).
- Autonomy controls under the disclosure:
- 0 β Drafts only. Peter never sends. Everything goes to your Drafts.
- 1 β Drafts + ask. Same as 0 today; reserved for an approval queue later.
- 2 β Auto-send routine replies. Peter sends low-stakes replies automatically; novel or higher-stakes stays in Drafts.
- Auto-draft toggle: turn off if you want the connection live (for sent-items scraping + command answering) but no inbound-reply drafts.
The drafts you see in Recent activity are status snapshots β drafted, auto-sent, skipped, not a lead. "View in Outlook" opens the actual draft for editing.
Engineering AI config (/engineering/config)
Two fields, both tune what Peter writes for you:
- Engineering knowledge base (company-wide) β product docs, FAQs, version gotchas, escalation paths. Visible to every engineering rep on the tenant. Lives in
sales_ai_company_config.engineering_kb. - Personal style notes β your voice, tone, escalation preferences. Same column as the sales-side per-rep style (
employee.personal_style_notes).
Voice tuning
A new engineer can generate a draft of their personal_style_notes from their last 6 months of customer-facing sent mail. Pattern (one-shot, admin-run):
- Connect Sales-AI Outlook.
- Admin runs
scripts/seed_<rep>_demo_drafts.py(or the voice-analysis script). Pulls ~30-50 external sent emails, asks Claude to extract tone / structural patterns / recurring phrases / tech-support reflexes, returns a ready-to-paste markdown block. - Paste into
/engineering/configβ Personal style notes β Save. - Optional: seed a handful of
[Demo]-prefixed drafts in the engineer's Outlook Drafts so they can preview what Peter-in-their-voice produces before a real inbound arrives.
Differences from sales Peter
| Sales (default) | Engineering | |
|---|---|---|
| System prompt | Challenger framework, qualifying questions, next-step propose | Resolve technical question, reference KB, escalate when needed |
| Calendar link | Push when prospect signals interest | Never push (no "grab time on my calendar") |
| Sales-shaped inbounds | Engage / qualify | Punt to Sales team gracefully |
| KB source | sales_ai_company_config.knowledge_base |
sales_ai_company_config.engineering_kb |
| Pricing / commercial | Engage (Sales rep follow-up) | Never quote; route to peter@ or Sales |
Operating notes
- The same desktop client / calendar sync / Outlook OAuth infrastructure powers both modes β no separate setup beyond connecting one extra Outlook scope for the drafts pipeline.
- Engineering meeting Tasks created in Salesforce attribute to the company SF user, not the individual engineer. Engineers are named in the Task description for traceability.
- The Peter poll runs every ~5 min; drafts for new inbound external emails appear within minutes.
SoftInWay Services API + VPN
Configure tenant access at Network β Network & VPN (sidebar). This page is developer-gated: anyone with the is_developer flag can manage it without holding the full admin role (admins can reach it too). It deliberately lives off the finance-gated Admin β Settings page so an engineer who configures IP/tunnels doesn't need broad admin rights. To grant it, an admin sets a person's developer flag in Admin β Employees β Edit (the dev flag also removes them from people-analytics and finance β it's meant for technical/tooling access).
- API URL + key β what OtiumWork uses when making calls (e.g. for tech-support date sync).
- VPN tunnels β add one tunnel per network you need to reach (prod, dev, staging, β¦). Each row needs:
- Slug β short id used in the systemd unit name (e.g.
prodβwg-quick@wg-svc-prod) - Label β human-friendly name shown in the admin table
- Type β WireGuard or OpenVPN
- Config β full
.conf/.ovpnbody - Enabled β uncheck to keep the row but stop bringing it up
- Slug β short id used in the systemd unit name (e.g.
Saving a tunnel doesn't immediately apply it on the VPS β it's stored in the DB. The next bash deploy/auto-deploy.sh reconciles: it walks the table, writes configs to /etc/wireguard/ and /etc/openvpn/client/, and brings the matching systemd units up. Tunnels deleted in the UI are torn down on the next deploy. No manual SSH required.
If you need the tunnel up right now (without waiting for the next deploy), just run bash deploy/auto-deploy.sh from your local box β it's the same script that ships code, and it includes the VPN reconcile step at the end.
18. Feedback + OtiumWork roadmap
Feedback + OtiumWork roadmap
Every employee can suggest a feature, report a bug, or ask a question. There are three places to start:
- Topbar "Feedback βΎ" dropdown (every page) β β¦ Suggest a feature / π Report a bug
- Sidebar footer β same two links
/feedbackdirectly β kind defaults to "feature" but is set by?kind=query param, so the dropdown links route to the right form
What happens next depends on the kind.
Three separate boards β don't confuse them
/roadmapβ OtiumWork's product roadmap. Visible to all users at all tenants. Vote on what OtiumWork should build next. This is where your/feedbackfeature requests land./admin/competitors/featuresβ your company's internal tracker of your company's competitors (e.g., SoftInWay tracking Aspen's and NREC's feature sets for their AxSTREAM engineering product). Has nothing to do with OtiumWork as a tool. Scoped to your tenant./admin/feedbackβ raw feedback list, admin-only. For triaging bugs and questions.
Kind = feature
When you pick "feature request" and submit:
- Entry saved to
feedback_requesttable. - Auto-acknowledgment email confirms receipt, linking you to
/roadmap. - Notification email to OtiumWork's product team.
- Auto-promoted to OtiumWork's roadmap β a matching row with
competitor=[User Request], tagCONSIDER, priority 3. - You (and every authenticated user at any tenant) can vote on it from
/roadmap.
Voting to prioritize
On /roadmap (and also on your tenant's /admin/competitors/features for your own company's competitor features):
- β² N button next to every feature β click to cast your vote, click again to remove it. One vote per user per feature.
- Vote counts show live and sort order lifts high-vote items to the top within each tag β so a CONSIDER with 12 votes surfaces above a CONSIDER with 0 votes.
The OtiumWork product team uses /roadmap vote counts to sequence what gets built next.
Kind = bug / question
Bugs and questions go through the same pipeline (notification + auto-reply) but aren't auto-promoted to the roadmap β they're for the OtiumWork team to act on, not for voting.
Bug-triage workflow (Claude Code agent)
Bugs flow into a dedicated workflow that uses Valentine's Claude Code session as the fix-it loop β not an autonomous cron, not an API agent.
- User submits at
/feedback?kind=bugβ row infeedback_request(kind='bug', status='open', triage_status=NULL). - Email pings the product owner.
- Valentine opens Claude Code and asks "any new bugs?" or runs
/triageβ the agent (this is documented inCLAUDE.mdat the repo root) callsscripts/triage_bugs.py listover SSH to surface open bugs. - Working through them in conversation: agent reads each bug, identifies the file, proposes a fix, Valentine says "go" or "skip".
- On "go": agent applies, commits, deploys, and runs
triage_bugs.py fix <id> <commit_sha> '<short note>'β that marks the row resolved AND emails the reporter automatically (idempotent viareporter_emailed_at). - For non-bugs:
reject <id> 'reason'(not reproducible) orwontfix <id> 'reason'(by design). Both email the reporter.
Much of step 3β5 also runs autonomously through staging via the fix-it runner (see below); production always stays a human gate.
Staged-for-review + approvals (staging β prod)
Fixes are reviewed on the staging site before they reach production. The bug view (/admin/feedback) shows where each item is:
| Status | Meaning |
|---|---|
| β§ On staging | Fixed on the internal staging site otiumdevelopment.softinway.com (VPN-only; branch + commit shown). Awaiting developer review. |
| β Dev-approved | A developer verified it on staging and signed off. Waiting for the weekly prod go. |
| βΆ Prod-approved | The owner approved release; the promoter will ship it. |
| β Live | Shipped to production; reporter emailed. |
Who does what:
- Developers (accounts with the developer flag) see the staging branch/commit + a "Review on staging β" link, and a β Dev-approve button to confirm the fix is correct.
- The owner gets a weekly Telegram digest of dev-approved items and clicks βΆ Approve for prod. Running
deploy/promote-approved.shthen promotes just those fixes (isolated cherry-pick) and closes them.
Emails: the whole dev team (owner + developers) is auto-emailed on every new report and every status change. The person who filed the item is emailed twice: once when it's fixed on staging (pending release) and again when it goes live.
Schema on feedback_request: triage_status (triaged β staged β dev_approved β prod_approved β fixed), triage_notes, fixed_branch, fixed_commit_sha, staged_at, staged_emailed_at, dev_approved_by/at, prod_approved_by/at, resolved_at, reporter_emailed_at.
Admin view
/admin/feedback lists every submission with status. Developers additionally see the staging branch/commit, a review link, and the approve buttons described above.
Closing the loop manually
Admins can also manually close a feedback item at /admin/feedback. Submitter gets an email saying it was marked resolved, with an optional note (e.g., "Shipped in v1.6.5" or "See /help/reports β this already works"). Submitter can reply to the email or re-submit if they disagree.
19. Meeting Coach
Meeting Coach
Sales Coach and Engineering Coach
There are two coaches, one for each side of the company, and each person sees only their own:
- Sales Coach, for sales and marketing (department, or the salesperson flag): sales calls, the six stages of the sale, objections and the rebuttal bank, competitor drills, and preparing for a real call.
- Engineering Coach, for everyone else on customer calls: software demos, tech support calls and customer training sessions.
A call, scorecard, recording, practice run, lesson or lesson video belongs to one side by its type. Someone from the other side can't list it, open it or start it, even with a direct link (it shows as not found), and the API and the Claude tools return only your side. The objection bank, the rebuttal bank, competitor drills and call preparation are sales only. Admins see both coaches and switch between them (Sales, Engineering or Both) at the top of each page.
Each coach has the same areas, in the sidebar under My Day:
- Train: two-minute lessons for your side, quiz modules and your certifications.
- Practice: role-plays with an AI customer, practice assigned to you and your practice scorecards.
- Live meetings: coach a call live or in person, upload a transcript, your calls and their scorecards.
- Team (managers and admins): how the team is doing, and assigning a role-play.
The old addresses (/sales/training and /coach/practice) still work.
SoftInWay basics (everyone)
One item belongs to both sides: SoftInWay basics, who SoftInWay is and what we do, so anyone can give a short, accurate pitch. It is a two-minute lesson, a short quiz, and a role-play, Give the 60-second pitch, scored on clarity, accuracy against the published facts, one relevant example, and ending with a question. It's in Train and Practice on both sides, and it's required for everyone on customer calls.
It starts as a draft that only admins see: the Train page lists every fact in it with its source on softinway.com. An admin checks them and presses Publish to everyone; Back to draft hides it again.
Team
Managers see their own reports on their own side; admins see everyone. For each person, across the three areas:
- Train: SoftInWay basics done, lessons passed, quiz modules certified.
- Practice: open, done and average score in the last 30 days, and the trend against the 30 days before.
- Live: calls in the last 30 and 90 days, the average score, the weakest skill, and how often a call ended with an agreed next step.
The team view adds the average for each scorecard item, the most common objections (sales), and everyone with no activity at all, so nobody drops off the list. Your own to-dos (practice waiting, SoftInWay basics not done, your last scorecard) show in a Coaching card on My Day.
Meeting Coach reads the transcript of a call and tells you how it went, scored for the kind of call it was:
| Call type | Scored on |
|---|---|
| Sales call | Teach, Tailor, Take control, Discovery, Technical credibility (the Challenger method), with our Sales AI rules (BANT, first call-to-action, product names) as background |
| Engineer demo | Discovery before demoing, Relevance to their use case, Clarity and pace, Technical accuracy, Handling technical questions, Value link, Next step |
| Customer training | Structure, Clarity, Checking understanding, Hands-on practice, Technical accuracy, Handling questions, Next step |
| Tech support call | Diagnosis, Technical accuracy, Clear fix or workaround, Expectations and empathy, Ownership and follow-up, Knowledge capture, Account signals |
Every scorecard has:
- Scores (0β5) for each item above, each backed by quotes from the call.
- Questions that were missed, with the moment in the call that opened the door.
- What the customer pushed back on (objections, concerns, where trainees struggled, or frustrations) and whether it was handled.
- Next steps that were actually agreed (or a flag that none were).
- Talk metrics: how much of the call SoftInWay talked (flagged when it's high for that kind of call), the longest monologue, and how many questions were asked.
It's built into Otium. No outside recording service is used.
Scoring a call
After every call or meeting, the scorecard page also lists the key information that was said (people and roles, needs, requirements and technical details, budget, timeline, how they decide, current tools, competitors, risks), each with a short quote, and the action items: who committed to what, and by when. Both go into the Salesforce Task too.
- After a Teams meeting, open it in Teams β Recap β Transcript β Download (.vtt or .docx). Transcription must have been turned on during the meeting.
- In Otium, go to Sales β Meeting Coach β + Score a call.
- Pick the call type, give it a title, upload the file (or paste the text), and optionally add the Salesforce account id and attendee emails.
- Scoring takes a minute or two. The scorecard appears on the call's page.
SoftInWay people in the transcript are recognised by name; everyone else counts as the customer.
Who sees what
You see your own calls. Managers also see their direct reports' calls on their own side (a sales manager never sees an engineer's demo, and the other way round); admins see everyone's. Only the rep (or an admin) can delete a call.
Export control
Never upload an ITAR or EAR call. Admins keep a blocklist of export-controlled Salesforce accounts and email domains under Meeting Coach β Policy; a call that matches is refused before anything is stored or sent to the AI.
Disagreeing with the coach
Every scorecard has a Disagree with this scorecard? box. Notes there are kept on the card and used to improve the rubric. They never change scores automatically. Re-score runs the call again.
Retention
Raw transcripts are deleted after the retention period set in the policy (180 days by default). Scorecards are kept.
Live coaching during a call
From the browser (no desktop client). On the Meeting Coach page press Coach a call (Chrome or Edge on a computer). It fills in the meeting from your calendar; pick the call type and confirm that everyone knows an AI note-taker is listening. Join the Teams call, then press Start listening, allow the microphone, and share the Entire screen (or the Teams browser tab) with Share system audio ticked: your microphone is you, the shared audio is them. Use headphones so the microphone doesn't hear the customer through your speakers. Keep the Otium tab open until the call ends. This needs cloud transcription (Deepgram) in the policy. With recording on, the shared screen and both voices are recorded in the browser and saved to your OneDrive when you end the call; if that fails, the page offers the file to download.
Tips on your phone or iPad. While you share your screen, open π± Tips on your phone or iPad on the live panel and scan the QR code. The phone shows the current tip in large type, the last few lines, and the Used it / Skip / Wrong buttons, and keeps its screen on. No login is needed: the link works for that one call and stops when it ends, so don't share it. A phone or iPad can't listen to the Teams app itself (Apple doesn't allow a web page to hear other apps), so the laptop does the listening.
In-person meetings (phone or iPad). On the Meeting Coach page press In person (or open Coach a call and pick In person). Put the phone face up on the table. Listening starts on its own when the page opens (allow the microphone; an iPhone may ask for one tap on Tap to start listening), and say hello first: the first voice to speak a full sentence is taken as yours, and the others are labelled Speaker 1, Speaker 2. If it gets that wrong, tap That last line was me. Tips appear on the same screen. Keep Otium open with the screen on (it asks the phone to stay awake): iPhones and iPads stop the microphone for a web page when the screen locks or you switch apps. Adding Otium to your Home Screen (Share β Add to Home Screen) makes it open full screen. The audio is recorded to your OneDrive when recording is on. This uses Deepgram's live service, which needs a Deepgram key with the Member role.
Just record, no tips. Untick Live tips when you start (calls or in person) to only record and transcribe. Nothing is shown during the meeting and no tips are worked out; you still get the transcript, notes and scorecard afterwards.
From the desktop client. Choose Coach this call⦠from the Otium tray menu, pick the call type, and confirm that everyone on the call knows an AI note-taker is listening. Nothing joins the meeting: the client listens to your microphone (you) and your speakers (them), transcribes on your own computer, and opens a live panel in Otium.
- Live transcript. Words appear greyed while someone is still talking, then turn into the final line.
- Nudges. One short tip at a time (12 words or fewer), usually a question you can say as-is. Mark it Used it, Ignored or Wrong so the coach improves.
- Sales calls are coached with our Champion Playbook: Challenger (teach, tailor, take control), BANT, discovery questions, objection and stall handling, and catching our own slips (talking price too early, offering brochures instead of a next step). A checklist on the panel lights up as you cover why they took the meeting, pain, impact, current tools, need, budget, decision process, timeline and the next step.
- Sales calls also get negotiation nudges from the playbook: "compared to what scope?" against a cheaper quote, trading instead of giving, checking whether a deadline is real, staying silent after a price, and Voss questions ("How would you take this to your team?").
- Engineer demos are coached with the demo playbook: discovery before demoing, showing their case instead of a tour, tying features to what they save, clarifying technical questions before answering, admitting what you don't know and following up in writing, and catching overclaims. The demo checklist covers their goal, machine and duty, current tools, success criteria, showing their case, checking understanding, who else decides and the next step.
- The coach never suggests prices, discounts, trials or commitments, and never claims what AxSTREAM can or cannot do.
- How fast. The coach looks at what the customer just said within about 2 seconds. While you are talking, it waits until the customer answers (or 8 seconds) and then looks at everything you said together, which keeps tips just as timely at about half the cost. Around 30 to 40 calls can be coached at the same time.
Who transcribes. An admin picks it under Meeting Coach β Policy β Live transcription: our own Whisper server on the office GPU box (laptops transcribe on their own when it can't be reached), or Deepgram, a cloud service, until the GPU box is ready. With Deepgram, the desktop client sends each spoken line to Otium, which passes it on and returns the text; the Deepgram key stays on the server, and the policy page shows the last 30 days' hours and estimated cost. Calls on the export-control blocklist are never recorded at all. Two lists on the same page improve accuracy with any transcriber: our words (products, competitor tools, customer names, jargon) are sent with every line, and spelling fixes ("axe stream => AxSTREAM") are applied to every transcript. Test checks the chosen service with a short sample.
The coach sees your screen on real calls
When you coach a Teams call from the browser (Coach a call), the coach can also see the screen you share, so its tips fit what the customer is looking at: if they asked about part-load behaviour and you are showing the design point, it nudges you to show part load; if a demo turns into a generic tour, it nudges you to tie it to their machine.
With Teams in front of Chrome, the coach still sees your screen: the picture comes from what you shared, not from the Otium tab. A slide that stays up is re-confirmed every 30 seconds, so the coach keeps seeing it.
- What is sent. While your share is live, the page looks at it every 5 seconds and sends a picture (at most 1280 pixels wide, JPEG) only when the screen changed, never more than one every 5 seconds. Nothing is sent while the Otium tab is hidden or after you stop sharing. The live coach looks at the newest picture when it is less than 90 seconds old. At the end the scorer looks at up to six of them, each with what was being said at that moment, and the scorecard mentions whether what you showed matched what the customer needed. Key facts and next steps still come only from what was said, never from what was on screen.
- Turning it off. On the Coach a call page, untick The coach sees my shared screen before you start. During the call, untick Coach sees your screen in the capture panel; nothing more is sent for that call. Do this for calls that show confidential customer content.
- The policy switch. An admin can turn it off for everyone under Meeting Coach β Policy β Shared screens β Screen-aware live coaching (on by default). Calls on the export-control blocklist never send a picture.
- Where the pictures go. Only to Anthropic's AI, for coaching and scoring this call. They are never sent to Salesforce and never shown on any page; Otium keeps up to 120 per call and deletes them with the call, or after the coach retention period, like the transcript.
- Cost. About 1 to 2 cents each time the coach looks at a picture. To keep that down it only looks again when the screen changed, or every third moment when it didn't.
- The desktop client doesn't send your screen (yet): this works only when you coach the call from the browser.
Recordings and Salesforce
When an admin ticks Record coached calls in Meeting Coach β Policy, the desktop client (v1.7 or later) also records while it coaches: the Teams meeting window (never the rest of your screen) and the call audio, in one small MP4 (about 200 MB an hour). When the call ends it uploads the file to your own OneDrive, folder "Otium Call Recordings"; Otium keeps only the link, shown on the call's scorecard. If Otium can't reach your OneDrive (Outlook not connected, or OneDrive access not granted yet), the file stays on your laptop and uploads after your next coached call; the scorecard says so.
Teams' own recordings of meetings you organised (saved by Teams in your OneDrive "Recordings" folder) are found after the call and linked on the scorecard too.
With Log each scored call in Salesforce ticked (the default), every scored call becomes a completed Task on the customer's Contact or Account, matched from the attendee emails: the summary, scores, next steps, and links to the scorecard, transcript and recordings. When a recording arrives later, the same Task is updated.
Practice with an AI buyer
Train and Practice (in your coach in the sidebar) are where you learn and practise before it counts. What you see depends on your side; only admins switch between the two.
Sales people practise the six stages of a SoftInWay sale, as the Sales Guide lays them out:
- Prospecting: qualify before you call, and disqualify a lead that isn't a fit, politely.
- Introduction: cold calls, the first 30 seconds, hostile openers.
- Discovery: finding the real problem, happy-with-the-incumbent, stalls, reframing.
- Demo (solution sale): evaluations on our terms (success criteria, paid test case), no free trials or unpaid studies, a champion who went quiet, doubts about a small vendor.
- Proposal: "show us results first" turned into paid scoping, a proposal priced on value, and trading (not giving) when they want a bigger scope for the same price.
- Closing: price is a message, trade never give (procurement wants 20% off), the cheaper competitor, and the objection gauntlet drill.
Engineers practise the calls they run:
- Software demos: discovery before the demo, showing their case, keeping a newcomer with you, the expert asking what you can't answer, ending with a next step instead of a trial. Two are written for sharing your screen: a customer who wants to see her own impeller, and an expert who asks you to show one specific result.
- Tech support calls: diagnosing before answering (an angry customer with a Friday deadline), calming a call when a whole team is blocked by licensing, and "your results are wrong". Two are written for sharing your screen: a customer who can't find where to change the inlet conditions, and a licence error on a new laptop you walk them through.
- Customer training sessions: checking understanding instead of asking "any questions?", the expert in the room who derails the session, and getting a trainee to do it instead of watching.
Each lesson is a two-minute read from the Champion Playbook (including Exact Words phrases and Voss), then a role-play: an AI buyer, customer or trainee with a real situation, hidden facts that good questions uncover, and objections at natural moments. Type or press the mic and talk (Chrome or Edge); tick Buyer speaks out loud to hear the answers in the most natural voice your browser has, or Hands-free to talk it through like a phone call: you speak, pause, the buyer answers out loud, and it listens again. Tick Camera feedback to see, at the end, how much of the time you were in frame and facing the camera, and how often you looked away (useful practice for Teams demos). That is measured inside your browser: no video or pictures leave the page, and nothing about expressions or feelings is measured. The live coach gives hints while you practise, as on a real call (untick Live coach hints to practise without them). In a demo, support or training role-play you can share your screen (below); otherwise describe what you would show.
A voice call, hands-free. When cloud transcription (Deepgram) is on, a role-play is a voice call that starts by itself when you open it: the buyer speaks out loud (including the opening line when they pick up a cold call), the microphone listens all the time, and when you pause, your words go to the buyer and they answer. Nothing is sent while the buyer is talking, so it never hears itself. If your phone asks for a tap first (iPhones sometimes do before the microphone or sound can start), a π Tap to start the call button appears; tap the screen once more if it says so, to keep it awake. The call pauses by itself after 4 minutes of silence. If a reply is ever blocked, a Tap to hear the reply button appears. You can still type instead.
Natural voice and a face. The buyer speaks in a natural voice from Otium's own voice service (free, nothing leaves our server), or from Azure Speech if an admin saves a key. If neither is available, the browser's built-in voice is used. With a Simli key and faces saved as well, tick Show the buyer's face: the buyer appears as a talking face on video, speaking Claude's lines. Role-plays are fictional, so nothing real is sent.
Lesson videos. An admin can give any lesson a video: upload one (e.g. you reading the lesson on camera), or Record it with the avatar: the coach face reads the lesson while your browser records it, and the result is saved as the lesson video for everyone.
End and score it scores the role-play like a real call. A lesson's role-play with an average of 3.5 / 5 or better appears in My certifications for a year.
Practice from your own calls. When a real sales call or demo scores 3 or lower on something, Otium assigns you a replay of that call aimed at that point ("Replay: Priya intro (Take control)"); the scorecard links to it. Admins can turn this off in the policy. Managers can assign any role-play to their reports and see who practised, their practice scores and their real-call scores side by side.
Demo and support practice with your screen
How. In a demo, tech support or training role-play on a computer (Chrome or Edge), press π₯ Share my screen next to the call controls and pick the window you'd show the customer (AxSTREAM, a results file, a slide). It works with the voice call and when you type. The button doesn't appear on phones and tablets, or in browsers that can't share a screen. Press βΉ Stop sharing (or the browser's own Stop button) to go back to describing.
What the customer sees. About every 4 seconds, and right before each thing you say goes to the customer, the page takes a picture of the shared window (at most 1280 pixels wide); it skips pictures where nothing changed. Each turn sends the newest picture once, so the customer reacts to what is actually on your screen: in a demo they ask about what they see and say so when it isn't their case, they're lost, or it's too generic; on a support call they say whether they can follow the steps you show and whether they fix their problem. Pictures go only to Anthropic's AI (the customer and, at the end, the scorer), never anywhere else. Otium keeps up to 40 of them with the practice for the scorecard and deletes them when the practice's call is deleted or after the coach retention period. Share a window with practice material, not customer data.
Scoring. The scorer looks at up to six of the pictures, each with what you said while it was on screen, and judges whether the screens matched what you said and the customer's case: a demo of their machine, or a generic tour; on a support call, steps that match the fix you described. It uses the usual scorecard dimensions and mentions the screens in the evidence and the summary.
Recording. Record this session is ticked when you start sharing (untick it to skip). The recording holds the shared window, your microphone and the customer's voice (when it's Otium's natural voice; the browser's built-in voice can't be recorded), as a WebM video of about 7 MB a minute. When you press End and score it, it is saved to your own OneDrive, folder "Otium Call Recordings", before the scoring starts (keep the tab open while it uploads), and the practice page links it. If Otium can't reach your OneDrive (Outlook not connected, or OneDrive access not granted yet), the page offers the file to download instead, then Continue to the scorecard. Practice recordings are yours: they are never logged to Salesforce.
Prepare for a real call
Before a real call, give Otium the person's email and the stage of the call (the six stages above: prospecting, introduction, discovery, demo, proposal, closing). You get a briefing and can rehearse the call with an AI playing that person. There are two ways to do it.
The Prepare button. Prepare for a real call in Training, or Prepare for a call on the Meeting Coach page (/coach/prepare). Type the email (or pick someone from an upcoming meeting in your calendar), pick the stage and press Prepare the briefing. Otium researches in the background, usually within two minutes; the page updates by itself. It reads:
- Salesforce, with your own Salesforce login (you see what Salesforce lets you see): the contact or lead with that email, their account and its owner, open and closed deals, and the dates and subjects of the last activities (not the notes), plus any warnings such as an opt-out or an old "don't call us".
- Your own mailbox: threads with that address (subject, date and a short snippet).
- Apollo (sales team only): free people search first; a paid lookup only when Salesforce doesn't know the person or their company, counted against the same monthly caps as the rest of the Sales AI.
- Recent news about their company from a web search. Only news whose link the search really returned is kept.
One AI pass then writes the briefing: who they are, what we know (each fact with its source and link), what they build and whether it honestly fits AxSTREAM, likely needs and objections (marked as guesses), the tools they use today (with the Sales Guide's approved answers when a competitor is named), the goal for this stage, a suggested opening, five questions to ask, risks (for example another rep owns the account) and unknowns. A fact the sources don't support is never shown as known: it goes to unknowns. You can prepare up to 10 calls a day.
Rehearse this call starts a voice role-play (the same practice page as Training). The AI plays the real person by first name, role and company, from the briefing: what is known it keeps to, what isn't it improvises plausibly. The scorecard judges the rehearsal against your plan: the stage goal and which of the planned questions you didn't ask.
From your own Claude. If your Claude is connected to Otium (the OtiumWork connector), ask it, for example, "prepare me for my discovery call with ana@acme.com". Your Claude reads what Otium knows (coach_prepare_sources: Salesforce and your mail snippets, no Apollo credits), does the web research itself, and hands Otium the briefing (coach_prepare_practice). Otium checks it (news and web facts need their link, everything else unsourced goes to unknowns), stores it without spending Otium's own AI on research, and gives you the link to the briefing with the Rehearse this call button.
Private. Only you can open your briefings and rehearse them (Otium admins can read them). The rehearsal is a simulation: nothing is sent to the person and nothing is written to Salesforce, and like all practice it never feeds the objection library or the competitor board. Like your other practice runs, it appears in your practice history, where your manager sees its title and score. Companies and accounts on the export-control blocklist can't be prepared: Otium refuses before reading anything, and if Salesforce shows the account is blocked, nothing that was found is kept.
Objections and competitors from real calls
Every scored sales call (uploaded, coached live or in person) also saves, for training. Demos, support and training sessions keep their concerns on their own scorecards and don't feed the objection bank:
- Each objection the customer raised, sorted into a category (price and budget; timing; happy with what they have; someone else decides; no need; trust in us; technical doubts; other), with the customer's own words, how we answered and whether it was handled, partly handled or missed. The scorecard shows the category and the quote too.
- Each tool the customer said they use, are evaluating or considering, or dropped (CFturbo, Ansys CFX, an in-house code, Excel, AxSTREAM itself), with what they said about it: features they like or miss, price, support. Names are matched to the company's competitor list (CFX and Fluent count as Ansys; something ambiguous like "Vista" on its own is left unmatched).
Practice role-plays and calls on the export-control blocklist never feed any of this. That includes a call whose account or domain is added to the blocklist after it was scored: saving the policy removes what it saved (its objections, its tools and its FIELD notes), it can no longer be re-scored, and the backfill skips it before anything is sent to the AI. Re-score replaces the call's saved objections and tools instead of adding to them; deleting a call deletes them.
Customer names. When a call is saved, Otium also writes a copy of each objection and tool detail with the customer's names taken out: the Salesforce account's name (without Inc, AG, Company..., with its abbreviations such as MHI or GE), every customer attendee's email domain (an EPC and the end user on the same call), and the names of the customer's people on the call. When the AI is available, one quick AI pass then takes out names Otium could not know (a company or person only mentioned, the customer side of a live call). Everyone who doesn't see customer names reads this copy, so it stays clean after the transcript is deleted. If Otium could not tell who the customer was and the AI pass did not run, that call's objections are shown only to sales people, managers and admins, can't be practised, and never reach the gauntlet or the competitor board.
In Training β From real calls:
- Objections we hear: the last 12 months of objections by category, with counts, the customer's words, our answer and the verdict (answers that worked are listed first). Filter by category, and by sales calls or engineer calls (demos, support, training). Everyone sees the whole company's objections; customer names are shown only to sales people, managers and admins, and everyone else reads "a customer" and [customer] / [name] in the quotes. Practise this starts a role-play where a fictional buyer (made-up person and company, never the real customer) raises that objection; managers can assign it to someone on their team instead. The buyer is made once per objection (the first click takes a few seconds) and reused for everyone after that; clicking again within a few minutes opens the practice you already have. Managers pick who to assign it to once, at the top of the page.
- Who uses what (sales people, managers and admins only): by competitor, how many accounts and calls named it, stance and sentiment, and the latest details with a link to the call; and by account, which tools each customer uses or weighs.
The objection gauntlet drill uses the team's five most frequent real sales objections (customer names removed) once at least three have been recorded; until then it uses the playbook's list.
Competitor board. When a call names a competitor with a concrete detail (a feature they like or miss, price, support), a FIELD note is added to Market intel β Feature board ("Field: β¦", filter From calls), linked to the call, once per competitor per call. Notes on other tags are never changed. The live coach still never criticises a competitor.
Calls scored before this existed can be filled in once by an admin with scripts/backfill_coach_intel.py --company <id> (--dry-run first shows what it would save, without writing or calling the AI). For those older calls the tools come from the scorecard's key information; a plain "they use X" is saved as a tool but only something they said about it (liked, missing, price, speed, support) becomes a FIELD note. --force redoes calls that already have intel, but always keeps the tools the scorer itself found on a call.
The Sales Guide in the coach
The coach reads the company's own Sales Guide from Sales AI β documents (the sales-process overview, the objection-handling scripts and the competitive positioning). Nothing from the guide is built into Otium: replace a document and the coach uses the new one within minutes.
Rebuttal bank (Training β Rebuttal bank, or /coach/rebuttals; managers and admins). Ready answers to objections and competitors: what the prospect says, a short line of at most 12 words for a live tip, and the guide's full answer. Seed from Sales Guide (admins) proposes answers from the objection scripts and the competitive positioning; every answer must be the guide's own words (anything the AI rewrote or invented is dropped), and triggers already in the bank are skipped, so it is safe to run again. It runs in the background and takes a minute or two. Seeded answers start as proposed: review them, edit the short line if needed, and Approve the ones the coach may use; Retire removes one from live use. You can also add your own, or click Add rebuttal next to an objection in Objections we hear or a competitor in Who uses what to start one prefilled. A short line that sounds like a price, discount, trial or promise is flagged: the live coach would hold it back.
Live tips quote approved rebuttals word for word. On sales calls and demos, when a competitor from the guide is named in the last three minutes (Ansys, CFX, Agile...), the coach reads that competitor's guide section as background for a good discovery question. When the customer raises an objection or names a competitor that has approved rebuttals, the coach may pick one: the tip is then its short line exactly as approved (the guide's full answer is under it), never words the AI made up. Without an approved rebuttal the usual rules stay: no AxSTREAM capability claims, no prices.
Phrases we never say. When one of our people says a phrase from the guide's "dangerous phrases" list, the live panel shows Avoid saying "β¦" (once per phrase per call), and the scorecard lists every such phrase our side said, with the line, under the summary. This is a word match on the transcript, not an AI judgement; the customer saying the same words never counts.
Competitor drills. Training β Competitor drills has a Practise vs β¦ button for each competitor in the guide (the ones customers named on our calls first; the rest under more). The AI buyer is a fictional person and company who uses that competitor and raises its typical objections, built from the guide's section on it, its honest loss patterns and its discovery questions. The buyer is made once per competitor and reused for a week, so later clicks start at once. The scorecard judges your answers against the approved rebuttals for that competitor.
Coming next
Automatic transcripts from Teams (no download needed).
20. Account recovery β what to do when you can't log in
Account recovery β what to do when you can't log in
Use the matrix below. Each row is independent β combine them as needed.
| What you lost | What to do |
|---|---|
| Password (still have email) | Click Forgot password? on /login. Set a fresh one via the email link. Link expires in 1 hour. |
| TOTP device (still have backup codes) | At the 2FA prompt, paste one of your backup codes instead of the 6-digit code. Each code works once. |
| TOTP device + backup codes | Email your company admin. They can disable 2FA on your account from /admin/employees β your row β Reset 2FA. You'll re-enroll on next login. |
| Email account (you can no longer receive mail) | Email your admin from any other channel (chat, phone). They can change your account's email at /admin/employees β your row β Edit. |
| Platform-owner account, lost everything | SSH to the VPS and run python scripts/owner_emergency_unlock.py --email <owner@β¦> --reset-2fa --reset-password --confirm. Dry-runs without --confirm. |
How backup codes work
When you enable 2FA at /me/security, OtiumWork generates 8 single-use recovery codes. They're shown once β print them or store them in your password manager. Each code lets you log in without your TOTP device. After 6 of the 8 are used, regenerate at /me/security.
Why platform-owner recovery needs SSH
The owner account has 3-factor sign-in (password + TOTP + emailed magic link) on top of 2FA enforcement. That's deliberate β but it also means there's no in-app "reset everything" button, because it would be the most valuable credential on the platform. SSH access to the VPS is treated as the root-of-trust; if you have that, you can run the break-glass script.
Related
21. 2FA β I lost my device
2FA β I lost my device
Three paths back in, in order of preference:
1. Use a backup code (fastest)
At the 2FA prompt, paste any one of the 8 backup codes OtiumWork showed you when you enabled 2FA. Each code works once. Format: ABCDE-FGHIJ.
If you kept the codes in a password manager or printed them: great, you're 30 seconds from logged in.
After you're back in: - Go to /me/security and regenerate a fresh set of backup codes - Set up TOTP on your new device while you're there
2. Ask your admin to reset 2FA
If you've used up all backup codes (or never saved them), email your company admin. They can clear your 2FA at /admin/employees β your row β Reset 2FA.
You'll then log in with just your password, and OtiumWork will walk you through fresh enrollment.
3. Platform-owner: SSH break-glass
For the platform-owner account (whoever's on OPS_ACCESS_EMAILS), neither path 1 nor 2 applies β the admin who'd reset 2FA is you. SSH to the VPS and:
cd /opt/timeopt
.venv/bin/python scripts/owner_emergency_unlock.py \
--email <your-owner-email> --reset-2fa --confirm
Dry-runs without --confirm. After running, log in with your existing password. The owner-2FA enforcement middleware will immediately redirect you to /me/security to re-enroll.
Preventing the next time
- Save backup codes in 2 places: password manager + printed copy in a locked drawer.
- Enable TOTP on your password manager (1Password, Bitwarden, etc.) β that way "device loss" only happens if you lose your manager too.
- Tell at least one trusted person (co-founder, spouse) where the backup codes live.
Related
22. I think my account is compromised
I think my account is compromised
Move fast. The faster you act, the less anyone can do under your identity.
Right now (under 60 seconds)
- Open /me/sessions (if you can still log in). You'll see every active session, with device + IP hint + last-seen time.
- "Revoke all" the sessions you don't recognize. If you're not 100% sure which is yours, revoke everything β you'll be logged out and can log back in fresh.
- Change your password at /me/security (or via /forgot-password if you've been kicked out). Use something you've never used elsewhere β 16+ characters, mixed.
Next 5 minutes
- Enable 2FA at /me/security if you hadn't already. Pick TOTP (Google Authenticator, Authy, 1Password, Bitwarden). Save the 8 backup codes somewhere offline.
- Email your admin (or, if you ARE the admin, the platform owner) β tell them what happened. They can check audit logs for activity under your account.
- Tell anyone who got messages from you in the last 24-48 hours that the messages may not have been you.
If you got the "new sign-in detected" email
That email always includes a one-click revoke link for that exact session. Click it β even before doing anything else. You can investigate after.
If you can't log in at all
You're locked out: someone changed your password. Go straight to /forgot-password and recover via email link. If the attacker also changed your email, contact your admin (they can change it back).
If you ARE the platform owner and the attacker reached even your owner-protected account: SSH to the VPS and run scripts/owner_emergency_unlock.py --email <you> --reset-password --reset-2fa --confirm. See account recovery.
What admins should do when a user reports compromise
- Pull the user's recent activity from /admin/audit (filter on actor_email).
- Look for unexpected: data exports, employee record edits, project edits, integration token re-bindings, role changes.
- If anything looks wrong, revoke the user's API tokens (if any) and inform any affected third parties.
- File the incident in /admin/legal β Incidents so there's a paper trail.
What we've already done for you
- Every new sign-in from a device we haven't seen for your account triggers a "new sign-in detected" email with a revoke link.
- Failed logins are rate-limited: 5 wrong passwords within 15 minutes locks the account for 15 minutes.
- Audit log captures every privileged action with timestamp + actor + IP hash.
- For the platform-owner account, sign-in requires password + TOTP + an emailed magic link.
- Inactivity timeout: sessions auto-revoke after 8 hours of no activity.