Skip to content

Services Documentation

Last Updated: 2026-05-08

The backend contains 38 service files across 12 directories, organized by domain following a clean layered architecture.

Service Architecture

Controller → Orchestrator → Domain Services → Persistence → Repository

                              AI Provider

                            Notion Sync Service

Service Overview

DomainFilesKey Services
Orchestrator2DigestOrchestrator, KnowledgeOrchestrator
Digest10Generation, formatting, creation, distribution, scheduling, delivery tracking
Knowledge3Creation, persistence, query
Subscription3Facade + query/persistence CQRS split
Notion11Sync, 4 repositories, page builder, property extractor, markdown content
AI2Provider interface + OpenAI/OpenRouter implementation
Content2Content extraction + HTML parser
Slack1Slack DM delivery
Transport2Message transport interface + Slack implementation
Root2CategoryService + EmojiConverter

Orchestrator Layer

Thin coordination layer that orchestrates multi-step workflows without containing business logic.

DigestOrchestrator

Coordinates the 7-step digest generation pipeline:

  1. Resolve category → 2. Parse date range → 3. Query knowledge → 4. Generate AI highlights → 5. Format Markdown → 6. Create entity → 7. Persist & sync to Notion

Also handles distribution if distributeNow is set.

KnowledgeOrchestrator

Coordinates knowledge creation: resolve category, create entity, persist, sync to Notion.


Digest Services (10 files)

ServiceResponsibility
DateRangeParserParses date range strings ("7 days", "last week", "2026-01-01 to 2026-01-07") into DateRangeDto
DigestContentFormatterFormats knowledge highlights into Dutch Markdown with headers, summaries, tags, and read time
DigestCreationServiceCreates Digest entity with title, content, statistics, highlight snapshot, and knowledge links
DigestPersistenceServicePersists digests to database and syncs to Notion
DigestDistributionServiceResolves subscribers, sends via Slack DMs, logs per-user delivery
DigestDeliveryLogServiceCreates/updates DigestDelivery entities for delivery tracking
DigestDeliveryPersistenceServiceLow-level save/mark operations on DigestDelivery entities
DigestDeliveryQueryServiceQuery deliveries by digest, user, status
DigestQueryServiceFind digest by ID or category
DigestSchedulerServiceChecks digest-enabled categories and triggers generation when due
KnowledgeHighlightGeneratorGenerates 2-3 sentence Dutch AI summaries per knowledge item

AI Services (2 files)

AiProviderInterface

php
interface AiProviderInterface {
    public function generateCompletion(string $prompt, AiOptionsDto $options): AiResponseDto;
}

OpenAIService

Implements AiProviderInterface. Supports:

  • OpenAI (default) via Symfony AI Platform
  • OpenRouter (detected by API URL containing openrouter.ai)
  • Configured via OPENAI_MODEL, OPENAI_API_KEY, OPENAI_API_URL

Notion Services (11 files)

ServiceResponsibility
NotionSyncServiceCoordinates bidirectional sync for all entity types
NotionRepositoryManagerResolves correct repository by ID type (local int vs Notion UUID)
NotionKnowledgeRepositoryCRUD on Notion Knowledge database
NotionCategoryRepositoryCRUD on Notion Categories database
NotionDigestRepositoryCRUD on Notion Digests database
NotionSubscriptionRepositoryCRUD on Notion Subscriptions database
NotionPageBuilderFluent builder for constructing Notion page properties
NotionPropertyExtractorReads typed values from Notion page properties
NotionMarkdownContentServiceEmbeds full Markdown content as Notion blocks
NotionClientFactoryStatic factory for Notion SDK client
NotionPaginationTraitHandles paginated Notion API queries

Environment Variables

bash
# Notion API
NOTION_API_KEY=secret_xxx
NOTION_KNOWLEDGE_DATABASE_ID=xxx
NOTION_CATEGORIES_DATABASE_ID=xxx
NOTION_DIGESTS_DATABASE_ID=xxx
NOTION_SUBSCRIPTIONS_DATABASE_ID=xxx

# AI Provider
OPENAI_API_KEY=sk-xxx
OPENAI_MODEL=gpt-4
OPENAI_API_URL=https://api.openai.com/v1

# Slack Integration (for digest delivery)
SLACK_BOT_URL=http://localhost:4001
INTERNAL_API_SECRET=xxx