Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
1145f5c
fix(shortcut): fixed global keyboard commands provider to follow `lat…
waleedlatif1 Dec 24, 2025
b1cd8d1
fix(executor): workflow abort has to send abort signal to route for c…
icecrasher321 Dec 24, 2025
cb8b9c5
fix(router): update router to handle azure creds the same way the age…
waleedlatif1 Dec 24, 2025
77521a3
fix(cancel-workflow-exec): move cancellation tracking for multi-task …
icecrasher321 Dec 24, 2025
92b2e34
feat(autolayout): add fitToView on autolayout and reduce horizontal s…
waleedlatif1 Dec 25, 2025
da7eca9
fix(change-detection): move change detection logic to client-side to …
waleedlatif1 Dec 25, 2025
40a6bf5
improvement(variables): update workflows to use deployed variables, n…
waleedlatif1 Dec 25, 2025
47a259b
feat(byok): byok for hosted model capabilities (#2574)
icecrasher321 Dec 25, 2025
66766a9
improvement(byok): remove web search block exa (#2579)
icecrasher321 Dec 25, 2025
9737253
feat(i18n): update translations (#2578)
waleedlatif1 Dec 25, 2025
26ec125
improvement(byok): updated styling for byok page (#2581)
waleedlatif1 Dec 25, 2025
f604ca3
feat(chat-otp): added db fallback for chat otp (#2582)
waleedlatif1 Dec 25, 2025
d79696b
feat(docs): added vector search (#2583)
waleedlatif1 Dec 25, 2025
3201aba
improvement(schedules): use tanstack query to fetch schedule data, cl…
waleedlatif1 Dec 25, 2025
61e7213
feat(i18n): update translations (#2585)
waleedlatif1 Dec 25, 2025
b7f6bab
feat(tests): added testing package, overhauled tests (#2586)
waleedlatif1 Dec 26, 2025
d707d18
fix(build): update dockerfile to contain testing package deps (#2591)
waleedlatif1 Dec 26, 2025
88cda3a
improvement(billing): migrate to decimaljs from number.parseFloat (#2…
waleedlatif1 Dec 26, 2025
1f0e3f2
feat: light mode (#2457)
emir-karabeg Dec 26, 2025
27ec412
fix(tools): fixed tool outputs (#2534)
aadamgough Dec 26, 2025
66b8434
fix(block-name): updating block name should update downstream var ref…
icecrasher321 Dec 26, 2025
7793a6d
feat(kb): added tags information to kb docs table (#2589)
waleedlatif1 Dec 26, 2025
b60b98e
improvement(tag-dropdown): added option to select block in tag dropdo…
waleedlatif1 Dec 27, 2025
298546d
fix(parallel): add parallel sentinel to make parallel-parallel and pa…
icecrasher321 Dec 27, 2025
a60a1fc
improvement(edges): drag edge over block (#2596)
aadamgough Dec 27, 2025
bd0eca0
fix(tag-dropdown): fix the way variables are displayed in the tag dro…
waleedlatif1 Dec 27, 2025
5add261
improvement(easyconnect): use native reactflow getIntersectingNodes i…
waleedlatif1 Dec 27, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
142 changes: 126 additions & 16 deletions apps/docs/app/api/search/route.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,126 @@
import { createFromSource } from 'fumadocs-core/search/server'
import { source } from '@/lib/source'

export const revalidate = 3600 // Revalidate every hour

export const { GET } = createFromSource(source, {
localeMap: {
en: { language: 'english' },
es: { language: 'spanish' },
fr: { language: 'french' },
de: { language: 'german' },
// ja and zh are not supported by the stemmer library, so we'll skip language config for them
ja: {},
zh: {},
},
})
import { sql } from 'drizzle-orm'
import { type NextRequest, NextResponse } from 'next/server'
import { db, docsEmbeddings } from '@/lib/db'
import { generateSearchEmbedding } from '@/lib/embeddings'

export const runtime = 'nodejs'
export const revalidate = 0

/**
* Hybrid search API endpoint
* - English: Vector embeddings + keyword search
* - Other languages: Keyword search only
*/
export async function GET(request: NextRequest) {
try {
const searchParams = request.nextUrl.searchParams
const query = searchParams.get('query') || searchParams.get('q') || ''
const locale = searchParams.get('locale') || 'en'
const limit = Number.parseInt(searchParams.get('limit') || '10', 10)

if (!query || query.trim().length === 0) {
return NextResponse.json([])
}

const candidateLimit = limit * 3
const similarityThreshold = 0.6

const localeMap: Record<string, string> = {
en: 'english',
es: 'spanish',
fr: 'french',
de: 'german',
ja: 'simple', // PostgreSQL doesn't have Japanese support, use simple
zh: 'simple', // PostgreSQL doesn't have Chinese support, use simple
}
const tsConfig = localeMap[locale] || 'simple'

const useVectorSearch = locale === 'en'
let vectorResults: Array<{
chunkId: string
chunkText: string
sourceDocument: string
sourceLink: string
headerText: string
headerLevel: number
similarity: number
searchType: string
}> = []

if (useVectorSearch) {
const queryEmbedding = await generateSearchEmbedding(query)
vectorResults = await db
.select({
chunkId: docsEmbeddings.chunkId,
chunkText: docsEmbeddings.chunkText,
sourceDocument: docsEmbeddings.sourceDocument,
sourceLink: docsEmbeddings.sourceLink,
headerText: docsEmbeddings.headerText,
headerLevel: docsEmbeddings.headerLevel,
similarity: sql<number>`1 - (${docsEmbeddings.embedding} <=> ${JSON.stringify(queryEmbedding)}::vector)`,
searchType: sql<string>`'vector'`,
})
.from(docsEmbeddings)
.where(
sql`1 - (${docsEmbeddings.embedding} <=> ${JSON.stringify(queryEmbedding)}::vector) >= ${similarityThreshold}`
)
.orderBy(sql`${docsEmbeddings.embedding} <=> ${JSON.stringify(queryEmbedding)}::vector`)
.limit(candidateLimit)
}

const keywordResults = await db
.select({
chunkId: docsEmbeddings.chunkId,
chunkText: docsEmbeddings.chunkText,
sourceDocument: docsEmbeddings.sourceDocument,
sourceLink: docsEmbeddings.sourceLink,
headerText: docsEmbeddings.headerText,
headerLevel: docsEmbeddings.headerLevel,
similarity: sql<number>`ts_rank(${docsEmbeddings.chunkTextTsv}, plainto_tsquery(${tsConfig}, ${query}))`,
searchType: sql<string>`'keyword'`,
})
.from(docsEmbeddings)
.where(sql`${docsEmbeddings.chunkTextTsv} @@ plainto_tsquery(${tsConfig}, ${query})`)
.orderBy(
sql`ts_rank(${docsEmbeddings.chunkTextTsv}, plainto_tsquery(${tsConfig}, ${query})) DESC`
)
.limit(candidateLimit)

const seenIds = new Set<string>()
const mergedResults = []

for (let i = 0; i < Math.max(vectorResults.length, keywordResults.length); i++) {
if (i < vectorResults.length && !seenIds.has(vectorResults[i].chunkId)) {
mergedResults.push(vectorResults[i])
seenIds.add(vectorResults[i].chunkId)
}
if (i < keywordResults.length && !seenIds.has(keywordResults[i].chunkId)) {
mergedResults.push(keywordResults[i])
seenIds.add(keywordResults[i].chunkId)
}
}

const filteredResults = mergedResults.slice(0, limit)
const searchResults = filteredResults.map((result) => {
const title = result.headerText || result.sourceDocument.replace('.mdx', '')
const pathParts = result.sourceDocument
.replace('.mdx', '')
.split('/')
.map((part) => part.charAt(0).toUpperCase() + part.slice(1))

return {
id: result.chunkId,
type: 'page' as const,
url: result.sourceLink,
content: title,
breadcrumbs: pathParts,
}
})

return NextResponse.json(searchResults)
} catch (error) {
console.error('Semantic search error:', error)

return NextResponse.json([])
}
}
80 changes: 42 additions & 38 deletions apps/docs/content/docs/de/execution/costs.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -105,28 +105,32 @@ Die Modellaufschlüsselung zeigt:
Die angezeigten Preise entsprechen den Tarifen vom 10. September 2025. Überprüfen Sie die Dokumentation der Anbieter für aktuelle Preise.
</Callout>

## Bring Your Own Key (BYOK)

Sie können Ihre eigenen API-Schlüssel für gehostete Modelle (OpenAI, Anthropic, Google, Mistral) unter **Einstellungen → BYOK** verwenden, um Basispreise zu zahlen. Schlüssel werden verschlüsselt und gelten arbeitsbereichsweit.

## Strategien zur Kostenoptimierung

- **Modellauswahl**: Wählen Sie Modelle basierend auf der Komplexität der Aufgabe. Einfache Aufgaben können GPT-4.1-nano verwenden, während komplexes Denken möglicherweise o1 oder Claude Opus erfordert.
- **Prompt-Engineering**: Gut strukturierte, präzise Prompts reduzieren den Token-Verbrauch ohne Qualitätseinbußen.
- **Modellauswahl**: Wählen Sie Modelle basierend auf der Aufgabenkomplexität. Einfache Aufgaben können GPT-4.1-nano verwenden, während komplexes Reasoning o1 oder Claude Opus erfordern könnte.
- **Prompt Engineering**: Gut strukturierte, prägnante Prompts reduzieren den Token-Verbrauch ohne Qualitätsverlust.
- **Lokale Modelle**: Verwenden Sie Ollama oder VLLM für unkritische Aufgaben, um API-Kosten vollständig zu eliminieren.
- **Caching und Wiederverwendung**: Speichern Sie häufig verwendete Ergebnisse in Variablen oder Dateien, um wiederholte KI-Modellaufrufe zu vermeiden.
- **Batch-Verarbeitung**: Verarbeiten Sie mehrere Elemente in einer einzigen KI-Anfrage anstatt einzelne Aufrufe zu tätigen.
- **Caching und Wiederverwendung**: Speichern Sie häufig verwendete Ergebnisse in Variablen oder Dateien, um wiederholte AI-Modellaufrufe zu vermeiden.
- **Batch-Verarbeitung**: Verarbeiten Sie mehrere Elemente in einer einzigen AI-Anfrage, anstatt einzelne Aufrufe zu tätigen.

## Nutzungsüberwachung

Überwachen Sie Ihre Nutzung und Abrechnung unter Einstellungen → Abonnement:

- **Aktuelle Nutzung**: Echtzeit-Nutzung und -Kosten für den aktuellen Zeitraum
- **Nutzungslimits**: Plangrenzen mit visuellen Fortschrittsanzeigen
- **Aktuelle Nutzung**: Echtzeit-Nutzung und Kosten für den aktuellen Zeitraum
- **Nutzungslimits**: Plan-Limits mit visuellen Fortschrittsindikatoren
- **Abrechnungsdetails**: Prognostizierte Gebühren und Mindestverpflichtungen
- **Planverwaltung**: Upgrade-Optionen und Abrechnungsverlauf
- **Plan-Verwaltung**: Upgrade-Optionen und Abrechnungsverlauf

### Programmatische Nutzungsverfolgung
### Programmatisches Nutzungs-Tracking

Sie können Ihre aktuelle Nutzung und Limits programmatisch über die API abfragen:

**Endpunkt:**
**Endpoint:**

```text
GET /api/users/me/usage-limits
Expand Down Expand Up @@ -172,69 +176,69 @@ curl -X GET -H "X-API-Key: YOUR_API_KEY" -H "Content-Type: application/json" htt
```

**Rate-Limit-Felder:**
- `requestsPerMinute`: Dauerhafte Rate-Begrenzung (Tokens werden mit dieser Rate aufgefüllt)
- `maxBurst`: Maximale Tokens, die Sie ansammeln können (Burst-Kapazität)
- `remaining`: Aktuell verfügbare Tokens (können bis zu `maxBurst` sein)
- `requestsPerMinute`: Dauerhaftes Rate-Limit (Tokens werden mit dieser Rate aufgefüllt)
- `maxBurst`: Maximale Tokens, die Sie akkumulieren können (Burst-Kapazität)
- `remaining`: Aktuell verfügbare Tokens (kann bis zu `maxBurst` betragen)

**Antwortfelder:**
- `currentPeriodCost` spiegelt die Nutzung in der aktuellen Abrechnungsperiode wider
- `limit` wird von individuellen Limits (Free/Pro) oder gepoolten Organisationslimits (Team/Enterprise) abgeleitet
- `plan` ist der aktive Plan mit der höchsten Priorität, der mit Ihrem Benutzer verknüpft ist
- `currentPeriodCost` spiegelt die Nutzung im aktuellen Abrechnungszeitraum wider
- `limit` wird aus individuellen Limits (Free/Pro) oder gepoolten Organisationslimits (Team/Enterprise) abgeleitet
- `plan` ist der Plan mit der höchsten Priorität, der Ihrem Benutzer zugeordnet ist

## Plan-Limits

Verschiedene Abonnementpläne haben unterschiedliche Nutzungslimits:
Verschiedene Abonnement-Pläne haben unterschiedliche Nutzungslimits:

| Plan | Monatliches Nutzungslimit | Ratenlimits (pro Minute) |
|------|-------------------|-------------------------|
| **Free** | 20 $ | 5 synchron, 10 asynchron |
| **Pro** | 100 $ | 10 synchron, 50 asynchron |
| **Team** | 500 $ (gepoolt) | 50 synchron, 100 asynchron |
| **Free** | 20 $ | 5 sync, 10 async |
| **Pro** | 100 $ | 10 sync, 50 async |
| **Team** | 500 $ (gemeinsam) | 50 sync, 100 async |
| **Enterprise** | Individuell | Individuell |

## Abrechnungsmodell

Sim verwendet ein **Basisabonnement + Mehrverbrauch**-Abrechnungsmodell:
Sim verwendet ein **Basis-Abonnement + Mehrverbrauch**-Abrechnungsmodell:

### Wie es funktioniert
### So funktioniert es

**Pro-Plan ($20/Monat):**
- Monatliches Abonnement beinhaltet $20 Nutzung
- Nutzung unter $20 → Keine zusätzlichen Kosten
- Nutzung über $20 → Zahlen Sie den Mehrverbrauch am Monatsende
- Beispiel: $35 Nutzung = $20 (Abonnement) + $15 (Mehrverbrauch)
**Pro-Plan (20 $/Monat):**
- Monatsabonnement beinhaltet 20 $ Nutzung
- Nutzung unter 20 $ → Keine zusätzlichen Gebühren
- Nutzung über 20 $ → Mehrverbrauch am Monatsende zahlen
- Beispiel: 35 $ Nutzung = 20 $ (Abonnement) + 15 $ (Mehrverbrauch)

**Team-Plan ($40/Benutzer/Monat):**
- Gepoolte Nutzung für alle Teammitglieder
- Mehrverbrauch wird aus der Gesamtnutzung des Teams berechnet
**Team-Plan (40 $/Platz/Monat):**
- Gemeinsame Nutzung über alle Teammitglieder
- Mehrverbrauch wird aus der gesamten Team-Nutzung berechnet
- Organisationsinhaber erhält eine Rechnung

**Enterprise-Pläne:**
- Fester monatlicher Preis, kein Mehrverbrauch
- Fester Monatspreis, kein Mehrverbrauch
- Individuelle Nutzungslimits gemäß Vereinbarung

### Schwellenwert-Abrechnung

Wenn der nicht abgerechnete Mehrverbrauch $50 erreicht, berechnet Sim automatisch den gesamten nicht abgerechneten Betrag.
Wenn der nicht abgerechnete Mehrverbrauch 50 $ erreicht, rechnet Sim automatisch den gesamten nicht abgerechneten Betrag ab.

**Beispiel:**
- Tag 10: $70 Mehrverbrauch → Sofortige Abrechnung von $70
- Tag 15: Zusätzliche $35 Nutzung ($105 insgesamt) → Bereits abgerechnet, keine Aktion
- Tag 20: Weitere $50 Nutzung ($155 insgesamt, $85 nicht abgerechnet) → Sofortige Abrechnung von $85
- Tag 10: 70 $ Mehrverbrauch → 70 $ sofort abrechnen
- Tag 15: Zusätzliche 35 $ Nutzung (105 $ gesamt) → Bereits abgerechnet, keine Aktion
- Tag 20: Weitere 50 $ Nutzung (155 $ gesamt, 85 $ nicht abgerechnet) → 85 $ sofort abrechnen

Dies verteilt große Überziehungsgebühren über den Monat, anstatt eine große Rechnung am Ende des Abrechnungszeitraums zu erhalten.
Dies verteilt große Mehrverbrauchsgebühren über den Monat, anstatt einer großen Rechnung am Periodenende.

## Best Practices für Kostenmanagement

1. **Regelmäßig überwachen**: Überprüfen Sie Ihr Nutzungs-Dashboard häufig, um Überraschungen zu vermeiden
2. **Budgets festlegen**: Nutzen Sie Planlimits als Leitplanken für Ihre Ausgaben
2. **Budgets festlegen**: Nutzen Sie Plan-Limits als Leitplanken für Ihre Ausgaben
3. **Workflows optimieren**: Überprüfen Sie kostenintensive Ausführungen und optimieren Sie Prompts oder Modellauswahl
4. **Passende Modelle verwenden**: Passen Sie die Modellkomplexität an die Aufgabenanforderungen an
5. **Ähnliche Aufgaben bündeln**: Kombinieren Sie wenn möglich mehrere Anfragen, um den Overhead zu reduzieren
5. **Ähnliche Aufgaben bündeln**: Kombinieren Sie mehrere Anfragen, wenn möglich, um Overhead zu reduzieren

## Nächste Schritte

- Überprüfen Sie Ihre aktuelle Nutzung unter [Einstellungen → Abonnement](https://sim.ai/settings/subscription)
- Erfahren Sie mehr über [Protokollierung](/execution/logging), um Ausführungsdetails zu verfolgen
- Erkunden Sie die [Externe API](/execution/api) für programmatische Kostenüberwachung
- Entdecken Sie die [externe API](/execution/api) für programmatische Kostenüberwachung
- Sehen Sie sich [Workflow-Optimierungstechniken](/blocks) an, um Kosten zu reduzieren
2 changes: 1 addition & 1 deletion apps/docs/content/docs/de/triggers/schedule.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,7 @@ Sie müssen Ihren Workflow bereitstellen, damit der Zeitplan mit der Ausführung

## Automatische Deaktivierung

Zeitpläne werden nach **10 aufeinanderfolgenden Fehlschlägen** automatisch deaktiviert, um unkontrollierte Fehler zu verhindern. Bei Deaktivierung:
Zeitpläne werden nach **100 aufeinanderfolgenden Fehlern** automatisch deaktiviert, um unkontrollierte Fehler zu verhindern. Bei Deaktivierung:

- Erscheint ein Warnhinweis auf dem Zeitplan-Block
- Die Ausführung des Zeitplans wird gestoppt
Expand Down
4 changes: 4 additions & 0 deletions apps/docs/content/docs/en/execution/costs.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,10 @@ The model breakdown shows:
Pricing shown reflects rates as of September 10, 2025. Check provider documentation for current pricing.
</Callout>

## Bring Your Own Key (BYOK)

You can use your own API keys for hosted models (OpenAI, Anthropic, Google, Mistral) in **Settings → BYOK** to pay base prices. Keys are encrypted and apply workspace-wide.

## Cost Optimization Strategies

- **Model Selection**: Choose models based on task complexity. Simple tasks can use GPT-4.1-nano while complex reasoning might need o1 or Claude Opus.
Expand Down
2 changes: 1 addition & 1 deletion apps/docs/content/docs/en/triggers/schedule.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,7 @@ You must deploy your workflow for the schedule to start running. Configure the s

## Automatic Disabling

Schedules automatically disable after **10 consecutive failures** to prevent runaway errors. When disabled:
Schedules automatically disable after **100 consecutive failures** to prevent runaway errors. When disabled:

- A warning badge appears on the schedule block
- The schedule stops executing
Expand Down
Loading
Loading