@polymorphism-tech/morph-spec 4.3.0 → 4.3.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CLAUDE.md +155 -0
- package/bin/morph-spec.js +3 -3
- package/bin/task-manager.cjs +102 -14
- package/package.json +2 -1
- package/src/commands/agents/agents-fuse.js +2 -1
- package/src/commands/project/detect-agents.js +31 -1
- package/src/commands/project/detect.js +11 -1
- package/src/commands/project/doctor.js +76 -70
- package/src/commands/project/init.js +9 -2
- package/src/commands/project/update.js +12 -2
- package/src/commands/state/advance-phase.js +19 -4
- package/src/commands/state/state.js +38 -14
- package/src/commands/tasks/task.js +1 -1
- package/src/commands/threads/thread-template.js +1 -1
- package/src/core/state/state-manager.js +19 -15
- package/src/core/templates/template-registry.js +1 -1
- package/src/core/workflows/workflow-detector.js +16 -3
- package/src/lib/checkpoints/checkpoint-hooks.js +8 -3
- package/src/lib/detectors/index.js +1 -1
- package/src/lib/detectors/standards-generator.js +77 -17
- package/src/lib/detectors/structure-detector.js +67 -39
- package/src/lib/generators/recap-generator.js +30 -10
- package/src/lib/validators/validation-runner.js +8 -24
- package/src/utils/hooks-installer.js +69 -0
- package/stacks/blazor-azure/.claude/commands/morph-apply.md +221 -0
- package/stacks/blazor-azure/.claude/commands/morph-archive.md +79 -0
- package/stacks/blazor-azure/.claude/commands/morph-deploy.md +529 -0
- package/stacks/blazor-azure/.claude/commands/morph-infra.md +209 -0
- package/stacks/blazor-azure/.claude/commands/morph-preflight.md +227 -0
- package/stacks/blazor-azure/.claude/commands/morph-proposal.md +122 -0
- package/stacks/blazor-azure/.claude/commands/morph-status.md +86 -0
- package/stacks/blazor-azure/.claude/commands/morph-troubleshoot.md +122 -0
- package/stacks/blazor-azure/.morph/.morphversion +5 -5
- package/stacks/blazor-azure/.morph/archive/.gitkeep +25 -0
- package/stacks/blazor-azure/.morph/config/config.json +9 -0
- package/stacks/blazor-azure/.morph/features/.gitkeep +25 -0
- package/stacks/blazor-azure/.morph/project/context/README.md +17 -0
- package/stacks/blazor-azure/.morph/schemas/agent.schema.json +296 -0
- package/stacks/blazor-azure/.morph/schemas/tasks.schema.json +220 -0
- package/stacks/blazor-azure/.morph/specs/.gitkeep +20 -0
- package/stacks/blazor-azure/.morph/standards/ai-agents/blazor-ui.md +364 -0
- package/stacks/blazor-azure/.morph/standards/ai-agents/production.md +415 -0
- package/stacks/blazor-azure/.morph/standards/ai-agents/setup.md +418 -0
- package/stacks/blazor-azure/.morph/standards/ai-agents/team-orchestration.md +479 -0
- package/stacks/blazor-azure/.morph/standards/ai-agents/workflows.md +354 -0
- package/stacks/blazor-azure/.morph/standards/architecture/ddd/aggregates.md +120 -0
- package/stacks/blazor-azure/.morph/standards/architecture/ddd/entities.md +99 -0
- package/stacks/blazor-azure/.morph/standards/architecture/ddd/value-objects.md +124 -0
- package/stacks/blazor-azure/.morph/standards/backend/api/minimal-api.md +494 -0
- package/stacks/blazor-azure/.morph/standards/backend/api/rest.md +492 -0
- package/stacks/blazor-azure/.morph/standards/backend/api/validation.md +88 -0
- package/stacks/blazor-azure/.morph/standards/backend/authentication/passkeys.md +428 -0
- package/stacks/blazor-azure/.morph/standards/backend/database/ef-core.md +199 -0
- package/stacks/blazor-azure/.morph/standards/backend/database/migrations.md +393 -0
- package/stacks/blazor-azure/.morph/standards/backend/database/postgresql/database.md +352 -0
- package/stacks/blazor-azure/.morph/standards/backend/database/repository-patterns.md +528 -0
- package/stacks/blazor-azure/.morph/standards/backend/database/vector-search-rag.md +541 -0
- package/stacks/blazor-azure/.morph/standards/backend/dotnet/async.md +366 -0
- package/stacks/blazor-azure/.morph/standards/backend/dotnet/core.md +117 -0
- package/stacks/blazor-azure/.morph/standards/backend/dotnet/di.md +439 -0
- package/stacks/blazor-azure/.morph/standards/backend/dotnet/program-cs-checklist.md +92 -0
- package/stacks/blazor-azure/.morph/standards/backend/integrations/asaas/asaas-api.md +216 -0
- package/stacks/blazor-azure/.morph/standards/backend/integrations/clerk/clerk-auth.md +290 -0
- package/stacks/blazor-azure/.morph/standards/backend/integrations/hangfire/hangfire-jobs.md +350 -0
- package/stacks/blazor-azure/.morph/standards/backend/integrations/resend/resend-email.md +385 -0
- package/stacks/blazor-azure/.morph/standards/context/analytics.md +96 -0
- package/stacks/blazor-azure/.morph/standards/context/bundles.md +110 -0
- package/stacks/blazor-azure/.morph/standards/context/priming.md +78 -0
- package/stacks/blazor-azure/.morph/standards/core/architecture.md +185 -0
- package/stacks/blazor-azure/.morph/standards/core/coding.md +214 -0
- package/stacks/blazor-azure/.morph/standards/core/git-branching-strategy.md +403 -0
- package/stacks/blazor-azure/.morph/standards/core/git.md +185 -0
- package/stacks/blazor-azure/.morph/standards/core/testing.md +295 -0
- package/stacks/blazor-azure/.morph/standards/data/nosql/blob-storage.md +102 -0
- package/stacks/blazor-azure/.morph/standards/data/nosql/cache/redis.md +97 -0
- package/stacks/blazor-azure/.morph/standards/data/nosql/cosmos-db.md +118 -0
- package/stacks/blazor-azure/.morph/standards/data/vector-search/azure-ai-search.md +121 -0
- package/stacks/blazor-azure/.morph/standards/data/vector-search/rag-chunking.md +104 -0
- package/stacks/blazor-azure/.morph/standards/frontend/blazor/design-checklist.md +222 -0
- package/stacks/blazor-azure/.morph/standards/frontend/blazor/fluent-ui-setup.md +595 -0
- package/stacks/blazor-azure/.morph/standards/frontend/blazor/fluent-ui.md +137 -0
- package/stacks/blazor-azure/.morph/standards/frontend/blazor/html-conversion.md +184 -0
- package/stacks/blazor-azure/.morph/standards/frontend/blazor/lifecycle.md +195 -0
- package/stacks/blazor-azure/.morph/standards/frontend/blazor/pitfalls.md +198 -0
- package/stacks/blazor-azure/.morph/standards/frontend/blazor/state.md +191 -0
- package/stacks/blazor-azure/.morph/standards/frontend/design-system/animations.md +151 -0
- package/stacks/blazor-azure/.morph/standards/frontend/design-system/naming.md +64 -0
- package/stacks/blazor-azure/.morph/standards/frontend/nextjs/nextjs-patterns.md +198 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/azure/azure.md +624 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/azure/bicep/bicep-patterns.md +422 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/azure/devops/azure-devops-setup.md +516 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/azure/devops/local-development.md +520 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/azure/services/functions.md +486 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/azure/services/service-bus.md +459 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/azure/services/storage.md +407 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/docker/easypanel-deploy.md +196 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/supabase/mcp-setup.md +252 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/supabase/supabase-auth.md +176 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/supabase/supabase-pgvector.md +169 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/supabase/supabase-rls.md +184 -0
- package/stacks/blazor-azure/.morph/standards/infrastructure/supabase/supabase-storage.md +153 -0
- package/stacks/blazor-azure/.morph/standards/integration/api/graphql.md +91 -0
- package/stacks/blazor-azure/.morph/standards/integration/api/grpc.md +114 -0
- package/stacks/blazor-azure/.morph/standards/integration/api/rest-design.md +95 -0
- package/stacks/blazor-azure/.morph/standards/integration/event-driven/cqrs.md +101 -0
- package/stacks/blazor-azure/.morph/standards/integration/event-driven/event-sourcing.md +124 -0
- package/stacks/blazor-azure/.morph/standards/integration/event-driven/service-bus.md +95 -0
- package/stacks/blazor-azure/.morph/standards/observability/logging.md +131 -0
- package/stacks/blazor-azure/.morph/standards/observability/metrics.md +121 -0
- package/stacks/blazor-azure/.morph/standards/observability/monitoring.md +114 -0
- package/stacks/blazor-azure/.morph/standards/observability/tracing.md +132 -0
- package/stacks/blazor-azure/.morph/standards/workflows/parallel-execution.md +112 -0
- package/stacks/blazor-azure/.morph/standards/workflows/thread-management.md +113 -0
- package/stacks/blazor-azure/.morph/test-infra/example.bicep +59 -0
- package/stacks/blazor-azure/CLAUDE.md +106 -101
- package/stacks/nextjs-supabase/.claude/commands/morph-apply.md +221 -0
- package/stacks/nextjs-supabase/.claude/commands/morph-archive.md +79 -0
- package/stacks/nextjs-supabase/.claude/commands/morph-deploy.md +529 -0
- package/stacks/nextjs-supabase/.claude/commands/morph-infra.md +209 -0
- package/stacks/nextjs-supabase/.claude/commands/morph-preflight.md +227 -0
- package/stacks/nextjs-supabase/.claude/commands/morph-proposal.md +122 -0
- package/stacks/nextjs-supabase/.claude/commands/morph-status.md +86 -0
- package/stacks/nextjs-supabase/.claude/commands/morph-troubleshoot.md +122 -0
- package/stacks/nextjs-supabase/.morph/.morphversion +5 -0
- package/stacks/nextjs-supabase/.morph/config/agents.json +730 -127
- package/stacks/nextjs-supabase/.morph/config/config.json +9 -0
- package/stacks/nextjs-supabase/.morph/project/context/README.md +17 -0
- package/stacks/nextjs-supabase/.morph/standards/ai-agents/blazor-ui.md +364 -0
- package/stacks/nextjs-supabase/.morph/standards/ai-agents/production.md +415 -0
- package/stacks/nextjs-supabase/.morph/standards/ai-agents/setup.md +418 -0
- package/stacks/nextjs-supabase/.morph/standards/ai-agents/team-orchestration.md +479 -0
- package/stacks/nextjs-supabase/.morph/standards/ai-agents/workflows.md +354 -0
- package/stacks/nextjs-supabase/.morph/standards/architecture/ddd/aggregates.md +120 -0
- package/stacks/nextjs-supabase/.morph/standards/architecture/ddd/entities.md +99 -0
- package/stacks/nextjs-supabase/.morph/standards/architecture/ddd/value-objects.md +124 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/api/minimal-api.md +494 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/api/rest.md +492 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/api/validation.md +88 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/authentication/passkeys.md +428 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/database/ef-core.md +199 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/database/migrations.md +393 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/database/postgresql/database.md +352 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/database/repository-patterns.md +528 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/database/vector-search-rag.md +541 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/dotnet/async.md +366 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/dotnet/core.md +117 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/dotnet/di.md +439 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/dotnet/program-cs-checklist.md +92 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/integrations/asaas/asaas-api.md +216 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/integrations/clerk/clerk-auth.md +290 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/integrations/hangfire/hangfire-jobs.md +350 -0
- package/stacks/nextjs-supabase/.morph/standards/backend/integrations/resend/resend-email.md +385 -0
- package/stacks/nextjs-supabase/.morph/standards/context/analytics.md +96 -0
- package/stacks/nextjs-supabase/.morph/standards/context/bundles.md +110 -0
- package/stacks/nextjs-supabase/.morph/standards/context/priming.md +78 -0
- package/stacks/nextjs-supabase/.morph/standards/core/architecture.md +185 -0
- package/stacks/nextjs-supabase/.morph/standards/core/coding.md +214 -0
- package/stacks/nextjs-supabase/.morph/standards/core/git-branching-strategy.md +403 -0
- package/stacks/nextjs-supabase/.morph/standards/core/git.md +185 -0
- package/stacks/nextjs-supabase/.morph/standards/core/testing.md +295 -0
- package/stacks/nextjs-supabase/.morph/standards/data/nosql/blob-storage.md +102 -0
- package/stacks/nextjs-supabase/.morph/standards/data/nosql/cache/redis.md +97 -0
- package/stacks/nextjs-supabase/.morph/standards/data/nosql/cosmos-db.md +118 -0
- package/stacks/nextjs-supabase/.morph/standards/data/vector-search/azure-ai-search.md +121 -0
- package/stacks/nextjs-supabase/.morph/standards/data/vector-search/rag-chunking.md +104 -0
- package/stacks/nextjs-supabase/.morph/standards/frontend/blazor/design-checklist.md +222 -0
- package/stacks/nextjs-supabase/.morph/standards/frontend/blazor/fluent-ui-setup.md +595 -0
- package/stacks/nextjs-supabase/.morph/standards/frontend/blazor/fluent-ui.md +137 -0
- package/stacks/nextjs-supabase/.morph/standards/frontend/blazor/html-conversion.md +184 -0
- package/stacks/nextjs-supabase/.morph/standards/frontend/blazor/lifecycle.md +195 -0
- package/stacks/nextjs-supabase/.morph/standards/frontend/blazor/pitfalls.md +198 -0
- package/stacks/nextjs-supabase/.morph/standards/frontend/blazor/state.md +191 -0
- package/stacks/nextjs-supabase/.morph/standards/frontend/design-system/animations.md +151 -0
- package/stacks/nextjs-supabase/.morph/standards/frontend/design-system/naming.md +64 -0
- package/stacks/nextjs-supabase/.morph/standards/frontend/nextjs/nextjs-patterns.md +198 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/azure/azure.md +624 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/azure/bicep/bicep-patterns.md +422 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/azure/devops/azure-devops-setup.md +516 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/azure/devops/local-development.md +520 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/azure/services/functions.md +486 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/azure/services/service-bus.md +459 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/azure/services/storage.md +407 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/docker/easypanel-deploy.md +196 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/supabase/mcp-setup.md +252 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/supabase/supabase-auth.md +176 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/supabase/supabase-pgvector.md +169 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/supabase/supabase-rls.md +184 -0
- package/stacks/nextjs-supabase/.morph/standards/infrastructure/supabase/supabase-storage.md +153 -0
- package/stacks/nextjs-supabase/.morph/standards/integration/api/graphql.md +91 -0
- package/stacks/nextjs-supabase/.morph/standards/integration/api/grpc.md +114 -0
- package/stacks/nextjs-supabase/.morph/standards/integration/api/rest-design.md +95 -0
- package/stacks/nextjs-supabase/.morph/standards/integration/event-driven/cqrs.md +101 -0
- package/stacks/nextjs-supabase/.morph/standards/integration/event-driven/event-sourcing.md +124 -0
- package/stacks/nextjs-supabase/.morph/standards/integration/event-driven/service-bus.md +95 -0
- package/stacks/nextjs-supabase/.morph/standards/observability/logging.md +131 -0
- package/stacks/nextjs-supabase/.morph/standards/observability/metrics.md +121 -0
- package/stacks/nextjs-supabase/.morph/standards/observability/monitoring.md +114 -0
- package/stacks/nextjs-supabase/.morph/standards/observability/tracing.md +132 -0
- package/stacks/nextjs-supabase/.morph/standards/workflows/parallel-execution.md +112 -0
- package/stacks/nextjs-supabase/.morph/standards/workflows/thread-management.md +113 -0
- package/stacks/nextjs-supabase/CLAUDE.md +69 -63
- package/stacks/blazor-azure/.morph/templates/.gitkeep +0 -0
- package/stacks/blazor-azure/.morph/templates/infrastructure/github/workflows/cd-prod.yml.hbs +0 -41
- package/stacks/blazor-azure/.morph/templates/infrastructure/github/workflows/cd-staging.yml.hbs +0 -24
- package/stacks/blazor-azure/.morph/templates/infrastructure/github/workflows/ci-build.yml.hbs +0 -23
- package/stacks/nextjs-supabase/.morph/templates/.gitkeep +0 -0
- package/stacks/nextjs-supabase/.morph/templates/infrastructure/github/workflows/cd-prod.yml.hbs +0 -22
- package/stacks/nextjs-supabase/.morph/templates/infrastructure/github/workflows/cd-staging.yml.hbs +0 -22
- package/stacks/nextjs-supabase/.morph/templates/infrastructure/github/workflows/ci-build.yml.hbs +0 -35
|
@@ -0,0 +1,121 @@
|
|
|
1
|
+
# Data Standard: Azure AI Search (Vector Search)
|
|
2
|
+
|
|
3
|
+
## Overview
|
|
4
|
+
Azure AI Search provides vector and hybrid search for RAG (Retrieval-Augmented Generation) patterns.
|
|
5
|
+
|
|
6
|
+
## Index Design
|
|
7
|
+
```csharp
|
|
8
|
+
// Define index with vector field
|
|
9
|
+
var index = new SearchIndex("documents-index")
|
|
10
|
+
{
|
|
11
|
+
Fields =
|
|
12
|
+
[
|
|
13
|
+
new SimpleField("id", SearchFieldDataType.String) { IsKey = true },
|
|
14
|
+
new SearchableField("content") { AnalyzerName = "pt.microsoft" },
|
|
15
|
+
new SearchableField("title") { AnalyzerName = "pt.microsoft" },
|
|
16
|
+
new SimpleField("sourceUrl", SearchFieldDataType.String) { IsFilterable = true },
|
|
17
|
+
new SimpleField("category", SearchFieldDataType.String) { IsFilterable = true, IsFacetable = true },
|
|
18
|
+
new VectorSearchField("contentVector", dimensions: 1536, vectorSearchProfileName: "hnsw-profile")
|
|
19
|
+
],
|
|
20
|
+
VectorSearch = new VectorSearch
|
|
21
|
+
{
|
|
22
|
+
Profiles = { new VectorSearchProfile("hnsw-profile", "hnsw-config") },
|
|
23
|
+
Algorithms = { new HnswAlgorithmConfiguration("hnsw-config") }
|
|
24
|
+
}
|
|
25
|
+
};
|
|
26
|
+
await indexClient.CreateOrUpdateIndexAsync(index);
|
|
27
|
+
```
|
|
28
|
+
|
|
29
|
+
## Embedding Generation
|
|
30
|
+
```csharp
|
|
31
|
+
public class EmbeddingService : IEmbeddingService
|
|
32
|
+
{
|
|
33
|
+
private readonly OpenAIClient _client;
|
|
34
|
+
private const string EmbeddingModel = "text-embedding-ada-002"; // 1536 dimensions
|
|
35
|
+
|
|
36
|
+
public async Task<float[]> GenerateEmbeddingAsync(string text)
|
|
37
|
+
{
|
|
38
|
+
// Truncate to model limit
|
|
39
|
+
var truncated = text.Length > 8192 ? text[..8192] : text;
|
|
40
|
+
|
|
41
|
+
var response = await _client.GetEmbeddingsAsync(
|
|
42
|
+
new EmbeddingsOptions(EmbeddingModel, [truncated]));
|
|
43
|
+
|
|
44
|
+
return response.Value.Data[0].Embedding.ToArray();
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
public async Task<IReadOnlyList<float[]>> GenerateBatchEmbeddingsAsync(IReadOnlyList<string> texts)
|
|
48
|
+
{
|
|
49
|
+
var response = await _client.GetEmbeddingsAsync(
|
|
50
|
+
new EmbeddingsOptions(EmbeddingModel, texts));
|
|
51
|
+
return response.Value.Data.Select(d => d.Embedding.ToArray()).ToList();
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
```
|
|
55
|
+
|
|
56
|
+
## Document Indexing
|
|
57
|
+
```csharp
|
|
58
|
+
public class DocumentIndexer
|
|
59
|
+
{
|
|
60
|
+
public async Task IndexDocumentAsync(Document doc)
|
|
61
|
+
{
|
|
62
|
+
var embedding = await _embeddingService.GenerateEmbeddingAsync(doc.Content);
|
|
63
|
+
|
|
64
|
+
var searchDoc = new SearchDocument
|
|
65
|
+
{
|
|
66
|
+
["id"] = doc.Id.ToString(),
|
|
67
|
+
["content"] = doc.Content,
|
|
68
|
+
["title"] = doc.Title,
|
|
69
|
+
["sourceUrl"] = doc.SourceUrl,
|
|
70
|
+
["category"] = doc.Category,
|
|
71
|
+
["contentVector"] = embedding
|
|
72
|
+
};
|
|
73
|
+
|
|
74
|
+
await _searchClient.MergeOrUploadDocumentsAsync([searchDoc]);
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
## Hybrid Search (Vector + Keyword)
|
|
80
|
+
```csharp
|
|
81
|
+
public async Task<IReadOnlyList<SearchResult>> SearchAsync(string query, string? category = null)
|
|
82
|
+
{
|
|
83
|
+
var queryEmbedding = await _embeddingService.GenerateEmbeddingAsync(query);
|
|
84
|
+
|
|
85
|
+
var options = new SearchOptions
|
|
86
|
+
{
|
|
87
|
+
Filter = category != null ? $"category eq '{category}'" : null,
|
|
88
|
+
Size = 10,
|
|
89
|
+
VectorSearch = new VectorSearchOptions
|
|
90
|
+
{
|
|
91
|
+
Queries =
|
|
92
|
+
{
|
|
93
|
+
new VectorizedQuery(queryEmbedding)
|
|
94
|
+
{
|
|
95
|
+
Fields = { "contentVector" },
|
|
96
|
+
KNearestNeighborsCount = 50
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
},
|
|
100
|
+
QueryType = SearchQueryType.Semantic,
|
|
101
|
+
SemanticSearch = new SemanticSearchOptions
|
|
102
|
+
{
|
|
103
|
+
SemanticConfigurationName = "my-semantic-config",
|
|
104
|
+
QueryCaption = new QueryCaption(QueryCaptionType.Extractive)
|
|
105
|
+
}
|
|
106
|
+
};
|
|
107
|
+
|
|
108
|
+
var response = await _searchClient.SearchAsync<SearchDocument>(query, options);
|
|
109
|
+
return await response.Value.GetResultsAsync().Select(r => new SearchResult(
|
|
110
|
+
r.Document["id"].ToString()!,
|
|
111
|
+
r.Document["content"].ToString()!,
|
|
112
|
+
r.Score ?? 0
|
|
113
|
+
)).ToListAsync();
|
|
114
|
+
}
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
## Cost Optimization
|
|
118
|
+
- Index only necessary fields (cost per GB/month)
|
|
119
|
+
- Use semantic ranking sparingly (higher cost per query)
|
|
120
|
+
- Cache frequent query embeddings (embeddings are stable for same text)
|
|
121
|
+
- Batch indexing for large document sets (avoid per-document API calls)
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
# Data Standard: RAG Chunking Strategies
|
|
2
|
+
|
|
3
|
+
## Overview
|
|
4
|
+
Chunking splits documents into segments for embedding. Chunk quality directly impacts RAG answer quality.
|
|
5
|
+
|
|
6
|
+
## Chunking Strategies
|
|
7
|
+
|
|
8
|
+
### 1. Fixed-Size (Baseline)
|
|
9
|
+
```csharp
|
|
10
|
+
public IEnumerable<Chunk> FixedSizeChunk(string text, int size = 512, int overlap = 50)
|
|
11
|
+
{
|
|
12
|
+
for (int i = 0; i < text.Length; i += size - overlap)
|
|
13
|
+
{
|
|
14
|
+
yield return new Chunk
|
|
15
|
+
{
|
|
16
|
+
Content = text[i..Math.Min(i + size, text.Length)],
|
|
17
|
+
StartIndex = i,
|
|
18
|
+
EndIndex = Math.Min(i + size, text.Length)
|
|
19
|
+
};
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
```
|
|
23
|
+
|
|
24
|
+
### 2. Sentence-Aware (Recommended for prose)
|
|
25
|
+
```csharp
|
|
26
|
+
public IEnumerable<Chunk> SentenceChunk(string text, int maxTokens = 256)
|
|
27
|
+
{
|
|
28
|
+
var sentences = SplitSentences(text);
|
|
29
|
+
var current = new StringBuilder();
|
|
30
|
+
var tokenCount = 0;
|
|
31
|
+
|
|
32
|
+
foreach (var sentence in sentences)
|
|
33
|
+
{
|
|
34
|
+
var sentenceTokens = EstimateTokens(sentence);
|
|
35
|
+
if (tokenCount + sentenceTokens > maxTokens && current.Length > 0)
|
|
36
|
+
{
|
|
37
|
+
yield return new Chunk { Content = current.ToString().Trim() };
|
|
38
|
+
current.Clear();
|
|
39
|
+
tokenCount = 0;
|
|
40
|
+
}
|
|
41
|
+
current.Append(sentence).Append(' ');
|
|
42
|
+
tokenCount += sentenceTokens;
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
if (current.Length > 0)
|
|
46
|
+
yield return new Chunk { Content = current.ToString().Trim() };
|
|
47
|
+
}
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
### 3. Semantic (Best quality, higher cost)
|
|
51
|
+
Split at semantic boundaries (paragraphs, headers, sections) rather than character count.
|
|
52
|
+
|
|
53
|
+
```csharp
|
|
54
|
+
public IEnumerable<Chunk> SemanticChunk(string markdown)
|
|
55
|
+
{
|
|
56
|
+
// Split at markdown headers
|
|
57
|
+
var sections = Regex.Split(markdown, @"(?=^#{1,3} )", RegexOptions.Multiline);
|
|
58
|
+
foreach (var section in sections.Where(s => s.Trim().Length > 0))
|
|
59
|
+
yield return new Chunk { Content = section.Trim() };
|
|
60
|
+
}
|
|
61
|
+
```
|
|
62
|
+
|
|
63
|
+
## Token Estimation
|
|
64
|
+
```csharp
|
|
65
|
+
// Rough estimate: 1 token ≈ 4 characters (English), ≈ 3 characters (Portuguese)
|
|
66
|
+
private static int EstimateTokens(string text) => text.Length / 4;
|
|
67
|
+
|
|
68
|
+
// More accurate: use tiktoken (if available)
|
|
69
|
+
// var encoder = TiktokenSharp.TikToken.EncodingForModel("gpt-4");
|
|
70
|
+
// return encoder.Encode(text).Count;
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
## Chunk Metadata
|
|
74
|
+
Always store metadata with chunks for filtering and citation:
|
|
75
|
+
```csharp
|
|
76
|
+
public record Chunk
|
|
77
|
+
{
|
|
78
|
+
public string Content { get; init; } = "";
|
|
79
|
+
public string DocumentId { get; init; } = "";
|
|
80
|
+
public string DocumentTitle { get; init; } = "";
|
|
81
|
+
public string SourceUrl { get; init; } = "";
|
|
82
|
+
public int ChunkIndex { get; init; }
|
|
83
|
+
public int StartCharIndex { get; init; }
|
|
84
|
+
public string Section { get; init; } = ""; // H1/H2 header this belongs to
|
|
85
|
+
public DateTime IndexedAt { get; init; } = DateTime.UtcNow;
|
|
86
|
+
}
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
## Strategy Selection Guide
|
|
90
|
+
| Document Type | Strategy | Chunk Size |
|
|
91
|
+
|---------------|----------|------------|
|
|
92
|
+
| Legal documents | Sentence-aware | 256 tokens |
|
|
93
|
+
| Technical docs | Semantic (headers) | Variable |
|
|
94
|
+
| Q&A pairs | Keep as-is | Whole Q+A |
|
|
95
|
+
| Code files | Function-boundary | Whole function |
|
|
96
|
+
| News articles | Paragraph | 512 tokens |
|
|
97
|
+
|
|
98
|
+
## Quality Checklist
|
|
99
|
+
- [ ] Chunks overlap by 10-20% to avoid cutting context at boundaries
|
|
100
|
+
- [ ] Minimum chunk size: 50 tokens (avoid noisy small chunks)
|
|
101
|
+
- [ ] Maximum chunk size: 512 tokens for ada-002 (8192 token model limit)
|
|
102
|
+
- [ ] Metadata preserved and searchable
|
|
103
|
+
- [ ] Source URL included for citation
|
|
104
|
+
- [ ] Re-index when document changes (detect via content hash)
|
|
@@ -0,0 +1,222 @@
|
|
|
1
|
+
# Blazor Design Phase Checklist
|
|
2
|
+
|
|
3
|
+
> **Scope:** blazor-azure
|
|
4
|
+
> **Layer:** 2 (on keyword)
|
|
5
|
+
> **Keywords:** blazor, design, checklist, phase, architecture
|
|
6
|
+
> **Load When:** design phase for blazor features
|
|
7
|
+
|
|
8
|
+
Use this checklist during FASE 2 (DESIGN) for features involving Blazor Server
|
|
9
|
+
|
|
10
|
+
---
|
|
11
|
+
|
|
12
|
+
## 1. State and Session Management
|
|
13
|
+
|
|
14
|
+
### State Persistence
|
|
15
|
+
|
|
16
|
+
- [ ] **How will critical state be persisted?**
|
|
17
|
+
- [ ] Database (recommended for important data)
|
|
18
|
+
- [ ] Distributed cache (Redis, SQL Distributed Cache)
|
|
19
|
+
- [ ] Cookie (only for identification, not data)
|
|
20
|
+
- [ ] LocalStorage via JS Interop (only for non-critical preferences)
|
|
21
|
+
|
|
22
|
+
- [ ] **SessionState has `LoadFrom(entity)` method?**
|
|
23
|
+
- Allows reloading state from persisted source
|
|
24
|
+
- See [state.md](./state.md)
|
|
25
|
+
|
|
26
|
+
- [ ] **`IsLoaded` property exists to avoid unnecessary reloads?**
|
|
27
|
+
|
|
28
|
+
- [ ] **SessionId middleware is configured?**
|
|
29
|
+
- HttpOnly cookie with session identifier
|
|
30
|
+
- Injected into HttpContext.Items for component access
|
|
31
|
+
|
|
32
|
+
### Page Validation
|
|
33
|
+
|
|
34
|
+
- [ ] **All pages in flow reload state in `OnInitializedAsync`?**
|
|
35
|
+
```csharp
|
|
36
|
+
if (!Session.IsLoaded)
|
|
37
|
+
{
|
|
38
|
+
var entity = await Repository.GetBySessionIdAsync(sessionId);
|
|
39
|
+
Session.LoadFrom(entity);
|
|
40
|
+
}
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
- [ ] **What happens if user accesses middle page directly?**
|
|
44
|
+
- Redirect to start?
|
|
45
|
+
- Load partial state?
|
|
46
|
+
- Show friendly error?
|
|
47
|
+
|
|
48
|
+
---
|
|
49
|
+
|
|
50
|
+
## 2. EF Core Concurrency
|
|
51
|
+
|
|
52
|
+
### Background Operations
|
|
53
|
+
|
|
54
|
+
- [ ] **Will any service be called via `Task.Run`?**
|
|
55
|
+
- If YES: Use `IDbContextFactory<T>`
|
|
56
|
+
- See [ef-core.md](../../backend/database/ef-core.md)
|
|
57
|
+
|
|
58
|
+
- [ ] **Will any service be called in background job (Hangfire, Timer)?**
|
|
59
|
+
- If YES: Use `IDbContextFactory<T>` or Repository Factory pattern
|
|
60
|
+
|
|
61
|
+
- [ ] **Will multiple operations happen concurrently in same component?**
|
|
62
|
+
- If YES: Each operation needs isolated DbContext
|
|
63
|
+
|
|
64
|
+
---
|
|
65
|
+
|
|
66
|
+
## 3. File Upload
|
|
67
|
+
|
|
68
|
+
- [ ] **Will feature handle file uploads?**
|
|
69
|
+
- [ ] Max file size defined?
|
|
70
|
+
- [ ] Allowed file types/extensions specified?
|
|
71
|
+
- [ ] Files read once and bytes stored?
|
|
72
|
+
- [ ] Upload progress indicator planned?
|
|
73
|
+
|
|
74
|
+
- [ ] **Where will files be stored?**
|
|
75
|
+
- [ ] Azure Blob Storage (recommended)
|
|
76
|
+
- [ ] Local file system (not scalable)
|
|
77
|
+
- [ ] Database as byte[] (only for small files < 1MB)
|
|
78
|
+
|
|
79
|
+
---
|
|
80
|
+
|
|
81
|
+
## 4. JavaScript Interop
|
|
82
|
+
|
|
83
|
+
- [ ] **Will feature use JavaScript?**
|
|
84
|
+
- [ ] JS calls in `OnAfterRenderAsync`, not `OnInitializedAsync`?
|
|
85
|
+
- [ ] `firstRender` check to prevent duplicate calls?
|
|
86
|
+
- [ ] JS file location planned (wwwroot/js/)?
|
|
87
|
+
|
|
88
|
+
- [ ] **Will feature need external JS libraries?**
|
|
89
|
+
- [ ] Library loaded via CDN or npm?
|
|
90
|
+
- [ ] Initialization strategy planned?
|
|
91
|
+
|
|
92
|
+
---
|
|
93
|
+
|
|
94
|
+
## 5. Navigation and Routing
|
|
95
|
+
|
|
96
|
+
- [ ] **How many pages in the feature?**
|
|
97
|
+
- Single page?
|
|
98
|
+
- Multi-page flow?
|
|
99
|
+
- Modal/dialog-based?
|
|
100
|
+
|
|
101
|
+
- [ ] **Will users need to navigate back/forward?**
|
|
102
|
+
- [ ] State persisted before navigation?
|
|
103
|
+
- [ ] Browser back button handled correctly?
|
|
104
|
+
|
|
105
|
+
- [ ] **Are there deep links?**
|
|
106
|
+
- [ ] Each page can load state from URL/DB?
|
|
107
|
+
- [ ] Invalid state handled gracefully?
|
|
108
|
+
|
|
109
|
+
---
|
|
110
|
+
|
|
111
|
+
## 6. Real-time Updates
|
|
112
|
+
|
|
113
|
+
- [ ] **Will feature need real-time updates?**
|
|
114
|
+
- SignalR circuit is already available
|
|
115
|
+
- Update strategy planned?
|
|
116
|
+
|
|
117
|
+
- [ ] **Will updates come from background jobs?**
|
|
118
|
+
- [ ] Notification mechanism planned?
|
|
119
|
+
- [ ] UI refresh strategy defined?
|
|
120
|
+
|
|
121
|
+
---
|
|
122
|
+
|
|
123
|
+
## 7. Performance
|
|
124
|
+
|
|
125
|
+
- [ ] **Expected data volume?**
|
|
126
|
+
- Pagination needed for lists > 100 items?
|
|
127
|
+
- Lazy loading for large datasets?
|
|
128
|
+
|
|
129
|
+
- [ ] **Heavy computations planned?**
|
|
130
|
+
- [ ] Run in background (Task.Run with factory)?
|
|
131
|
+
- [ ] Cache results?
|
|
132
|
+
|
|
133
|
+
- [ ] **Large components/forms?**
|
|
134
|
+
- [ ] Split into smaller components?
|
|
135
|
+
- [ ] Lazy rendering planned?
|
|
136
|
+
|
|
137
|
+
---
|
|
138
|
+
|
|
139
|
+
## 8. Error Handling
|
|
140
|
+
|
|
141
|
+
- [ ] **What errors might occur?**
|
|
142
|
+
- Database errors?
|
|
143
|
+
- Network errors?
|
|
144
|
+
- Validation errors?
|
|
145
|
+
- Permission errors?
|
|
146
|
+
|
|
147
|
+
- [ ] **Error display strategy?**
|
|
148
|
+
- [ ] Toast notifications?
|
|
149
|
+
- [ ] Inline validation messages?
|
|
150
|
+
- [ ] Error page redirect?
|
|
151
|
+
|
|
152
|
+
- [ ] **Retry strategy for transient errors?**
|
|
153
|
+
|
|
154
|
+
---
|
|
155
|
+
|
|
156
|
+
## 9. Security
|
|
157
|
+
|
|
158
|
+
- [ ] **Authentication required?**
|
|
159
|
+
- [ ] `[Authorize]` attribute on pages?
|
|
160
|
+
- [ ] Login redirect configured?
|
|
161
|
+
|
|
162
|
+
- [ ] **Authorization rules?**
|
|
163
|
+
- Role-based?
|
|
164
|
+
- Policy-based?
|
|
165
|
+
- Resource-based?
|
|
166
|
+
|
|
167
|
+
- [ ] **Input validation?**
|
|
168
|
+
- [ ] Client-side (Blazor validation)?
|
|
169
|
+
- [ ] Server-side (service layer)?
|
|
170
|
+
- [ ] Both?
|
|
171
|
+
|
|
172
|
+
- [ ] **Sensitive data?**
|
|
173
|
+
- [ ] Not stored in SessionState?
|
|
174
|
+
- [ ] Not logged?
|
|
175
|
+
- [ ] Encrypted in database?
|
|
176
|
+
|
|
177
|
+
---
|
|
178
|
+
|
|
179
|
+
## 10. UI/UX
|
|
180
|
+
|
|
181
|
+
- [ ] **Loading states?**
|
|
182
|
+
- Spinners for async operations?
|
|
183
|
+
- Skeleton loaders for data?
|
|
184
|
+
- Disabled buttons during saves?
|
|
185
|
+
|
|
186
|
+
- [ ] **Success feedback?**
|
|
187
|
+
- Toast messages?
|
|
188
|
+
- Inline success indicators?
|
|
189
|
+
- Redirect to confirmation page?
|
|
190
|
+
|
|
191
|
+
- [ ] **Responsive design?**
|
|
192
|
+
- Mobile layout planned?
|
|
193
|
+
- Breakpoints defined?
|
|
194
|
+
|
|
195
|
+
---
|
|
196
|
+
|
|
197
|
+
## Quick Design Decisions
|
|
198
|
+
|
|
199
|
+
Before implementing, answer these:
|
|
200
|
+
|
|
201
|
+
| Question | Answer Required |
|
|
202
|
+
|----------|----------------|
|
|
203
|
+
| **State:** Where is critical state stored? | Database / Cache / Cookie |
|
|
204
|
+
| **Files:** Where are uploads stored? | Azure Blob / Database / FileSystem |
|
|
205
|
+
| **Navigation:** Single page or multi-page? | Single / Multi / Modal |
|
|
206
|
+
| **JS:** Is JavaScript needed? | Yes / No |
|
|
207
|
+
| **Auth:** Authentication required? | Yes / No |
|
|
208
|
+
| **Background:** Any background operations? | Yes (use factory) / No |
|
|
209
|
+
| **Real-time:** Real-time updates needed? | Yes / No |
|
|
210
|
+
|
|
211
|
+
---
|
|
212
|
+
|
|
213
|
+
## Related Standards
|
|
214
|
+
|
|
215
|
+
- [state.md](./state.md) - Session state patterns
|
|
216
|
+
- [lifecycle.md](./lifecycle.md) - Component lifecycle
|
|
217
|
+
- [pitfalls.md](./pitfalls.md) - Common mistakes
|
|
218
|
+
- [ef-core.md](../../backend/database/ef-core.md) - DbContext concurrency
|
|
219
|
+
|
|
220
|
+
---
|
|
221
|
+
|
|
222
|
+
*MORPH-SPEC by Polymorphism Tech*
|