Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions app/src/features/catalog/AgencyGrid.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,8 @@ const CATEGORIES: Category[] = [
"learning",
"finance",
"people",
"security",
"legal",
];

/** A fixed color per role, so the mascots tell the cards apart. */
Expand Down
6 changes: 3 additions & 3 deletions app/src/features/catalog/agency.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ describe("the Bot agency", () => {

fireEvent.click(within(invite).getByRole("button", { name: "See all bots" }));
const dialog = await screen.findByRole("dialog", { name: "Bot agency" });
expect(await within(dialog).findAllByRole("listitem")).toHaveLength(94);
expect(await within(dialog).findAllByRole("listitem")).toHaveLength(115);
});

test("a crew with only its chief invites the owner to pick bots, and a click adds one", async () => {
Expand Down Expand Up @@ -82,7 +82,7 @@ describe("the Bot agency", () => {
await openCrewWithChief();
fireEvent.click(screen.getByRole("button", { name: "Bot agency" }));
const dialog = await screen.findByRole("dialog", { name: "Bot agency" });
expect(await within(dialog).findAllByRole("listitem")).toHaveLength(94);
expect(await within(dialog).findAllByRole("listitem")).toHaveLength(115);

fireEvent.click(within(dialog).getByRole("button", { name: "Marketing & sales" }));
expect(within(dialog).getAllByRole("listitem")).toHaveLength(24);
Expand Down Expand Up @@ -129,7 +129,7 @@ describe("the Bot agency", () => {
expect(addCalls(fake)[0]).toMatchObject({ templateId: "code-reviewer" });

fireEvent.click(within(dialog).getByRole("button", { name: "Back to all bots" }));
expect(within(dialog).getAllByRole("listitem")).toHaveLength(94);
expect(within(dialog).getAllByRole("listitem")).toHaveLength(115);
});

test("the same role twice gets another name", async () => {
Expand Down
8 changes: 8 additions & 0 deletions app/src/i18n/en/catalog.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,13 @@ import { design } from "./catalogDesign";
import { engineering } from "./catalogEngineering";
import { engineeringMore } from "./catalogEngineeringMore";
import { finance } from "./catalogFinance";
import { legal } from "./catalogLegal";
import { marketing } from "./catalogMarketing";
import { paidMedia } from "./catalogPaidMedia";
import { people } from "./catalogPeople";
import { product } from "./catalogProduct";
import { sectors } from "./catalogSectors";
import { security } from "./catalogSecurity";

// The Bot agency (spec 26): ready-made bots the owner adds to a crew. The
// roles are the daemon's sheets, by id; this is what the owner reads about
Expand Down Expand Up @@ -37,6 +40,8 @@ export const catalog = {
learning: "Learning",
finance: "Finance",
people: "People & HR",
security: "Security",
legal: "Legal",
},
none: "No bot matches that.",
loading: "Loading the bots…",
Expand Down Expand Up @@ -67,5 +72,8 @@ export const catalog = {
...paidMedia,
...people,
...engineeringMore,
...security,
...sectors,
...legal,
},
};
74 changes: 74 additions & 0 deletions app/src/i18n/en/catalogLegal.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
// Legal roles (spec 26.3): what the owner reads about each. None is a
// lawyer; each says so and sends the owner to one for anything that matters.

export const legal = {
"contract-reader": {
name: "Contract Reader",
role: "Reads a contract in plain words: what each side must do, the dates and money, the risky clauses and the questions to ask a lawyer",
summary: "Reads a contract in plain words and flags the risky clauses and what to ask a lawyer",
about:
"Reads the whole contract and gives you one page: who must do what, the money, the dates and how it ends. It flags the clauses that deserve attention, such as automatic renewal, penalties or giving up rights, and marks each as common, unusual or worth negotiating. It never says a clause is valid or enforceable. It is not a lawyer, and it ends with the questions to take to one.",
when: "Before you sign a contract, or when you want to understand one you already signed.",
pairs: "Contract Dates Tracker, for the dates, and Legal Research Assistant.",
},
"terms-drafter": {
name: "Terms and Privacy Notice Drafter",
role: "Drafts the terms of use and the privacy notice of a site or app in plain words, from how the business really works, for a lawyer to check",
summary:
"Drafts your site's terms and privacy notice in plain words from how you really work, for a lawyer to check",
about:
"Asks how your business really works and what data it collects, then drafts the terms of use, the privacy notice and the refund and shipping policy in short, plain sentences. The parts that depend on the law are marked as questions for a lawyer, and it lists the promises you will have to keep. It never publishes anything on your site.",
when: "When you launch a site, an app or a shop and need the texts that go with it.",
pairs: "Privacy Engineer, for the data map, and Editor, to polish.",
},
"legal-research-assistant": {
name: "Legal Research Assistant",
role: "Finds and explains the laws, rules and decisions on a question from official sources, with exact citations, and says what it could not verify",
summary:
"Finds the laws and decisions on a question from official sources, with exact citations and honest limits",
about:
"Needs the place, the date and the facts, then looks in official sources first, opens every source before it cites it and gives you a short memo with exact references. It separates what the law says from what courts say about it and what is unsettled. It never invents a law or a case, and says when it could not verify one.",
when: "When you need to know what the law says on a question, before you talk to a lawyer.",
pairs: "Fact Checker, to verify a citation, and Editor, to polish the memo.",
},
"legal-intake-assistant": {
name: "Client Intake Assistant",
role: "Helps a small law practice or advisor collect a new client's facts: a clear questionnaire, a neat summary of the matter and the missing documents",
summary:
"Helps a small practice collect a new client's facts: a clear questionnaire, a neat summary and what is missing",
about:
"Prepares a plain intake form for the kind of matter, then turns the client's answers into a timeline and a one-page summary, with facts kept apart from opinions. It lists the missing documents and puts anything urgent on top. It never tells a client their rights or whether they have a case, and never contacts a client.",
when: "At the first step with a new client, before the lawyer reviews the matter.",
pairs: "Time and Billing Assistant, and Contract Reader.",
},
"legal-billing-assistant": {
name: "Time and Billing Assistant",
role: "Turns your work log into clear time entries and invoice drafts for a practice or consultant, and shows what is unbilled",
summary:
"Turns your work log into clear time entries and invoice drafts, and shows what is still unbilled",
about:
"Turns your notes and calendar into time entries with descriptions a client would understand and that do not reveal more than they need to. It shows what is unbilled by client, flags entries that look wrong without changing them and prepares the invoice draft from the entries you approve. It never rounds up or overstates the work.",
when: "When you bill by the hour and the time slips away before you invoice.",
pairs: "Invoicing Assistant, for payment follow-up, and Bookkeeper.",
},
"contract-deadline-tracker": {
name: "Contract Dates Tracker",
role: "Keeps track of the dates in your contracts: renewals, notice periods, payments and deadlines, and warns you well before each one",
summary:
"Keeps track of the dates in your contracts, such as renewals and notice periods, and warns you early",
about:
"Reads your contracts and lists every date and duty with the clause it comes from, working out the real date and saying in plain words how it was counted. It puts the traps first, such as automatic renewals with a notice period, and warns you early. If a clause is unclear it says so instead of guessing. It never sends a notice or ends a contract.",
when: "When you have several contracts and are afraid of missing a renewal or a notice.",
pairs: "Contract Reader, to explain a clause, and Writer, to draft a notice for you to send.",
},
"complaint-letter-drafter": {
name: "Complaint Letter Drafter",
role: "Drafts clear, firm and polite letters for a complaint or a dispute with a company or a landlord, from the facts and the papers you have",
summary:
"Drafts clear, firm and polite complaint letters for a dispute with a company or a landlord",
about:
"Gets the facts straight with you, builds a timeline checked against your papers and drafts a short, polite and firm letter: what happened, what you ask for and a reasonable date to reply. It does not threaten or exaggerate. It lists the attachments and the places to check next as questions for your country. You send the letter.",
when: "When a company, a landlord or a seller has not done right by you.",
pairs: "Contract Reader, for the terms, and Editor, to proofread.",
},
};
77 changes: 77 additions & 0 deletions app/src/i18n/en/catalogSectors.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,77 @@
// Roles for particular kinds of business (spec 26.3), listed under Business:
// what the owner reads about each. None sends, signs, buys, pays, refunds or
// publishes by itself.

export const sectors = {
"real-estate-assistant": {
name: "Real Estate Assistant",
role: "Helps you buy, sell or rent a property: compares listings, prepares questions and checklists, and drafts ads and messages",
summary:
"Helps you buy, sell or rent a property: compares listings, prepares questions and drafts the ad",
about:
"Compares places in one table with the same facts for each, including the real costs, and tells you what a listing leaves out. It prepares visit checklists and questions, and helps you write an honest ad and questions for buyers or tenants. It never states a market value as a fact, makes an offer or signs, and it is not an agent or a lawyer.",
when: "When you are looking for a place, or getting yours ready to sell or rent.",
pairs: "Researcher, for facts about an area, and Writer, to polish the ad.",
},
"hospitality-guest-assistant": {
name: "Guest Experience Assistant",
role: "Helps a hotel, guesthouse or rental host look after guests: answers, welcome messages, guides, and notes on what to improve",
summary:
"Helps a hotel or rental host look after guests: answers, welcome messages, guides and improvements",
about:
"Keeps a short sheet of facts about your place and drafts replies to guests from it, never inventing a time, a price or a promise. It writes the welcome message and guest guide, drafts calm answers to complaints and reads your reviews for what guests like and what repeats as a problem. Refunds and discounts stay your decision.",
when: "When guests ask the same things all day, or you want better reviews.",
pairs: "Translator, for guests who speak another language, and Social Media.",
},
"returns-assistant": {
name: "Returns and Refunds Assistant",
role: "Handles customer returns and refund requests by your own policy: sorts them, drafts the replies and spots patterns and abuse",
summary:
"Handles returns and refund requests by your own policy: sorts them, drafts replies and spots patterns",
about:
"Reads each request against your written policy and sorts it as inside, outside or a doubt, then drafts a clear, friendly reply. Doubts and exceptions come to you. Each week it shows what repeats, such as items with many returns, without accusing any customer. It warns you when a customer may have a legal right to a refund. It never issues a refund itself.",
when: "When returns and refund requests take too much of your day.",
pairs: "Customer Support, for tone, and E-commerce Manager, for listing fixes.",
},
"supply-chain-planner": {
name: "Supply Chain Planner",
role: "Plans what to buy and when: stock levels, reorder points, supplier comparisons and delivery risks, for a small business",
summary:
"Plans what to buy and when: stock levels, reorder points and supplier comparisons for a small business",
about:
"Works from your sales, stock, prices and lead times to propose a reorder point and an order size for each item, with the formula shown. It flags the items you cannot run out of and the slow ones that tie up money, compares suppliers on the full cost and lists the risks with a plan B. It never places an order or contacts a supplier.",
when: "When you run out of stock, or hold too much of what does not sell.",
pairs: "Bookkeeper, for costs, and Cash Flow Forecaster, for what you can afford.",
},
"grant-writer": {
name: "Grant Writer",
role: "Finds and prepares applications for grants and public calls: reads the rules, plans the answer and drafts it from your real facts",
summary:
"Prepares applications for grants and public calls: reads the rules, plans the answer and drafts it",
about:
"Reads the call in full, summarizes it with the deadline first and checks honestly whether you qualify before it writes anything. Then it plans the application against the scoring and drafts each section from your real facts, marking every gap as a question. It never invents a result, a partner or a number, and never submits for you.",
when: "When you find a grant, a public call or a funding program that could fit you.",
pairs: "Financial Analyst, for the budget, and Editor, to polish.",
},
"restaurant-manager": {
name: "Restaurant Assistant",
role: "Helps run a small restaurant or café: menu and costs, shifts, orders and supplies, and answers to guests",
summary:
"Helps run a small restaurant or café: menu costs, shifts, supplies and answers to guests",
about:
"Works out what each dish really costs and where you lose money, plans shifts around your busy hours, keeps the shopping list and a daily sheet that shows what repeats. It never says a dish is free of an allergen or safe for a diet on a guess: that comes from your own recipe sheets, and when they do not say, it tells you to check first.",
when: "When you run a small food business and the paperwork eats your time.",
pairs: "Bookkeeper, for costs, and Social Media, for posts about the menu.",
},
"course-creator": {
name: "Online Course Creator",
role: "Helps you turn what you know into an online course or workshop: the promise, the outline, the lessons, the exercises and the page that explains it",
summary:
"Helps you turn what you know into an online course: outline, lessons, exercises and the sales page",
about:
"Starts from the student and an honest promise you can deliver, builds the outline backwards from the result and drafts the lessons and exercises in your voice, with your own examples. The course page uses only real content and results: no made-up testimonials, no false deadlines, no earnings promises. You publish and set the price.",
when: "When you know something people would pay to learn and want to teach it.",
pairs:
"Presentation Designer, for slides, Video Scriptwriter, for scripts, and Editor, to proofread.",
},
};
Loading
Loading