Submitting a Deal via Slack
Slack is the fastest way to hand Memosa a new deal. You upload your documents into a channel where the bot lives, tell it the deal name, and run a single command to generate the memo. The bot keeps each deal in its own Slack thread, so you can run several deals in parallel without crossing wires.
If you would rather work entirely in the browser, the Canvas web app offers the same intake flow — see Submitting a Deal via Web Chat.
Where the bot listens
Section titled “Where the bot listens”The bot only responds in an explicit allow-list of channels. Every incoming mention and file upload is checked against the channel name before anything else happens; events in any other channel are ignored silently (you will not get a reply, and no work is queued).
| Environment | Bot handle | Live channels |
|---|---|---|
| Production | @memobot | #memosa-main, #initiative-memosa |
| Staging | @memosa-staging | #memosa-dev |
If you mention the bot in a channel it is not configured for, it sends you a private (ephemeral) note listing the channels where it is available, so only you see it and the channel stays quiet.
The intake flow, step by step
Section titled “The intake flow, step by step”1. Upload your files
Section titled “1. Upload your files”Drag your deal documents into a channel message, or attach them the usual Slack way. You can upload one file or many at once. The three input types Memosa understands are:
- PDF — the offering memorandum / deal summary (the sponsor’s narrative).
- Excel — the underwriting model (
.xlsx,.xls,.xlsm). - CoStar — CoStar market or comparables exports (these arrive as PDFs and are auto-detected as CoStar even when the filename never says “CoStar”).
A PDF and an Excel model are the two required inputs; CoStar exports are optional extras that sharpen the market analysis. For the full breakdown of what each file type contributes, see What to Upload.
2. The 3-second batch window
Section titled “2. The 3-second batch window”Slack fires a separate upload event for every file, even when you select several and drop them together. To avoid the bot reacting to each one individually (and posting a wall of “got your file” messages), the file handler buffers incoming uploads for a short window and then processes them as one batch.
The debounce window is 3 seconds . Every new file you add inside that window resets the timer, so a quick multi-file drop is always collected into a single batch. Once the window closes with no new files, the bot fetches all the buffered files from Slack in parallel, validates each one, and hands the valid set to the intake pipeline together.
3. The bot confirms what it received
Section titled “3. The bot confirms what it received”After the batch is processed, the bot replies in the thread with a single message listing every file it accepted, for example:
✅ Received 3 files:
OM - 151 Avenue A.pdf,Underwriting Model.xlsx,Sales Comp Report.pdf
Each file is validated on the way in. If a file’s content does not match its extension (a renamed file, a corrupt upload), or if it is empty, an unsupported type, or still mid-classification on Slack’s side, the bot calls it out by name with the reason and the rest of the batch still proceeds. A typical rejection reads:
⚠️ Some uploads were rejected because the file content does not match its extension: •
notes.pdf— …
4. Name the deal
Section titled “4. Name the deal”If you have not already named the deal, the bot prompts you for a deal name and any context you want to add. The deal name matters: it is what your namespace and the eventual memo are keyed to, so use the name you want to see on the finished document.
You set the name simply by replying in the thread. An empty or whitespace-only name is refused — a deal must have a real name before generation can run.
5. Generate the memo
Section titled “5. Generate the memo”Once both required files (PDF + Excel) and a deal name are present, the bot tells you it is ready:
✅ All required documents and information are now present. You can now generate your Memosa memo by saying
@memobot generate
Run the command in the thread:
@memobot generate(On staging, use @memosa-staging generate.) The bot validates readiness one more time, enqueues the analysis job, and the deal moves into processing. From here, watch the thread for progress and the final memo link.
If you run generate before the deal is ready, the bot tells you exactly what is missing — upload the remaining files, set the deal name, or wait for an in-flight run to finish — rather than starting an incomplete memo.
What happens behind the confirmation
Section titled “What happens behind the confirmation”A few details are worth knowing because they explain the bot’s behavior:
- Each deal is one thread. When you upload a file that is not already part of an active memo thread, the bot maps it to the most recent active thread in the channel, or — as a last resort — opens a fresh thread and tells you to continue there. Keep a deal’s files and your
generatecommand in the same thread. - Large files are handled patiently. The bot downloads each file from Slack with progressive timeouts and automatic retries, so a big underwriting workbook that takes a while to transfer will still come through.
- Duplicate uploads are deduplicated. Re-uploading the same file (same Slack file ID) will not create a second copy; the most recent PDF or Excel replaces the prior one of that type, and duplicate CoStar reports are skipped.
Common situations
Section titled “Common situations”| You see / do | What it means |
|---|---|
| No reply at all after an upload | You are in a channel the bot does not watch. Move to a live channel (see the table above). |
| ”I couldn’t find an active memo thread for this upload” | The upload could not be tied to a thread. Upload inside an existing memo thread, or mention the bot with your files to start one. |
| A single file was rejected but others went through | That file failed validation (wrong content for its extension, empty, or unsupported). Fix and re-upload just that file. |
generate says the deal is not ready | A required file or the deal name is missing, or a run is already in progress. The error message names the gap. |
Sources
Section titled “Sources”src/slack/handlers/file_handler.py— file_shared event handling, the 3-second debounce buffer (FILE_BATCH_DEBOUNCE_SECS), per-file validation, batch assembly, and thread/auto-thread resolution.src/slack/handlers/base_handler.py—is_channel_allowed()(channel-name allow-list check) and the ephemeral “wrong channel” notice.src/slack/handlers/mention_handler.py— app_mention handling and the allowed-channel guard on mentions.src/slack/handlers/command_handlers.py— thegeneratecommand handler and its readiness checks / error codes.src/services/intake_coordinator.py— batch collection, file classification, deal-name setting, readiness gating, and the consolidated “Received N files” / “ready to generate” replies.src/utils/file_classifier.py— classification of uploads intopdf/excel/costar.CLAUDE.md— production vs staging Slack apps and channel isolation (#memosa-main+#initiative-memosavs#memosa-dev).