feat: enforce hard test-tier requirement across all DevPlace workflow agents and feature-builder docs

Update the feature-builder agent prompt, test-maintainer agent, and all four workflow JS files (devii-tool, endpoint, feature, job-service) to codify the DevPlace test standard as a non-optional project requirement: one test file per endpoint, directory tree mirroring the URL/source path, split into three tiers (unit, api, e2e). Add explicit Test phases to devii-tool, endpoint, feature, and job-service workflows, and embed tier-specific test instructions (path mapping, fixture choice, coverage scope) directly in each workflow's meta description and TESTS constant.
This commit is contained in:
2026-06-15 12:10:14 +00:00
parent 3c7527988e
commit e1874f9b6a
71 changed files with 2198 additions and 145 deletions
+29 -9
View File
@@ -15,8 +15,7 @@ logger = logging.getLogger(__name__)
TOKEN_PATTERN = re.compile(r"[a-z0-9]+")
BM25_K1 = 1.5
BM25_B = 0.75
HYBRID_VECTOR_WEIGHT = 0.6
HYBRID_KEYWORD_WEIGHT = 0.4
RRF_K = 60.0
DEFAULT_TOP_K = 8
CANDIDATE_MULTIPLIER = 4
@@ -182,18 +181,39 @@ class VectorStore:
)
if not candidates:
return []
vector_rank = sorted(
candidates, key=lambda chunk: chunk.score, reverse=True
)
keyword = self.keyword_scores(query, candidates)
vec_max = max((chunk.score for chunk in candidates), default=0.0) or 1.0
kw_max = max(keyword.values(), default=0.0) or 1.0
keyword_rank = sorted(
candidates, key=lambda chunk: keyword.get(chunk.uid, 0.0), reverse=True
)
fused: dict[str, float] = {}
for rank, chunk in enumerate(vector_rank, start=1):
fused[chunk.uid] = fused.get(chunk.uid, 0.0) + 1.0 / (RRF_K + rank)
for rank, chunk in enumerate(keyword_rank, start=1):
fused[chunk.uid] = fused.get(chunk.uid, 0.0) + 1.0 / (RRF_K + rank)
for chunk in candidates:
vec_norm = max(0.0, chunk.score) / vec_max
kw_norm = keyword.get(chunk.uid, 0.0) / kw_max
chunk.score = (
HYBRID_VECTOR_WEIGHT * vec_norm + HYBRID_KEYWORD_WEIGHT * kw_norm
)
chunk.score = fused.get(chunk.uid, 0.0)
candidates.sort(key=lambda chunk: chunk.score, reverse=True)
return candidates[:top_k]
def coverage_analytics(self) -> dict:
chunks = self.all_chunks()
if not chunks:
return {"chunks": 0, "domains": 0, "sources": 0, "avg_chunk_chars": 0}
domains = {chunk.metadata.get("url", "") for chunk in chunks}
domains.discard("")
sources = {chunk.source for chunk in chunks}
sources.discard("")
avg_chars = int(sum(len(chunk.text) for chunk in chunks) / len(chunks))
return {
"chunks": len(chunks),
"domains": len(domains),
"sources": len(sources),
"avg_chunk_chars": avg_chars,
}
def drop(self) -> None:
try:
import chromadb