> For the complete documentation index, see [llms.txt](https://ai-os-and-trend-finder.gitbook.io/ai-os-and-trend-finder-docs/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://ai-os-and-trend-finder.gitbook.io/ai-os-and-trend-finder-docs/.spec_system/archive/sessions/phase27-session04-daily-time-series-persistence-and-sparklines/spec.md).

# Session Specification

**Session ID**: `phase27-session04-daily-time-series-persistence-and-sparklines` **Phase**: 27 - Trend Finder Alpha Radar Adoption **Status**: Not Started **Created**: 2026-06-12

***

## 1. Session Overview

This session starts the Tier 2 Alpha Radar adoption path by giving Trend Finder a real daily time-series foundation. The current runtime already keeps 12-week historical summaries from private snapshots, but it does not publish day-bucketed evidence counts for topic trajectory visuals. This work persists daily evidence counts by canonical topic ID in the private snapshot archive, then publishes only a capped 14-day browser-safe sparkline per topic.

The session also tracks Hugging Face model download counts across runs without adding a new source. Hugging Face model evidence already carries public `downloads` metrics, so the collector can compare the current model count to the prior private snapshot and expose a bounded delta context only when a real baseline exists. First-seen models must show an explicit no-baseline state instead of an invented delta.

The result is a reusable runtime layer for later velocity, burst, convergence, and demand growth sessions. The implementation stays additive: legacy payloads must continue to parse, private archives stay out of browser output, and the UI renders dense sparklines with explicit empty states instead of pretending missing history exists.

***

## 2. Objectives

1. Persist per-canonical-topic daily evidence counts and per-model Hugging Face download observations in the private Trend Finder snapshot archive.
2. Assemble a deterministic, UTC-bucketed, capped 14-day sparkline for each topic and publish only that bounded browser-safe projection.
3. Emit Hugging Face download delta context on model evidence only when a previous public download count exists.
4. Render compact sparklines on trend cards and in the Signal Workbench with accessible labels, stable sizing, and explicit missing-history states.

***

## 3. Prerequisites

### Required Sessions

* [x] `phase27-session01-brief-movement-groups-and-calibration-metrics` - establishes Phase 27 additive browser payload and calibration patterns.
* [x] `phase27-session02-deterministic-derived-signals-and-risk-flags` - establishes derived signal defaults, Workbench fields, and validation discipline.
* [x] `phase27-session03-data-driven-radar-aliases-and-watching-state` - establishes current card, Workbench, alias, watching, and outlier UI patterns.

### Required Tools/Knowledge

* Bun 1.3.14 for package scripts and Vitest.
* TypeScript, Zod, React, Tailwind CSS 4, and existing Trend Finder component conventions.
* Existing private snapshot flow in `scripts/lib/ai-runtime/snapshots.ts`.
* Existing historical summary flow in `scripts/lib/ai-runtime/historical-context.ts`.
* Hugging Face model evidence normalization and public `downloads` metrics.

### Environment Requirements

* Repository rooted at `/home/aiwithapex/projects/aios`.
* Phase 27 PRD stubs present under `.spec_system/PRD/phase_27/`.
* No new source credentials are required; fixtures and unit/component tests should cover persistence, assembly, UI, and no-baseline states.

***

## 4. Scope

### In Scope (MVP)

* Trend Finder operator can see a 14-day sparkline on each topic card when private snapshot history has daily evidence counts for the canonical topic.
* Trend Finder operator can see an explicit missing-history or no-baseline state when a topic or Hugging Face model does not yet have enough prior private snapshot data.
* Trend Finder runtime persists private daily evidence counts keyed by canonical topic ID under `.cache/extensions/trend-finder/snapshots/`.
* Trend Finder runtime persists private Hugging Face model download observations by public model entity ID and compares them across runs.
* Browser payload exposes only bounded sparkline points and bounded download delta context; it does not expose raw snapshot paths, raw archives, or private cache internals.
* Signal Workbench renders a compact sparkline column and keeps row ordering, filtering, and pagination deterministic.
* Tests cover UTC day bucketing, 14-entry bounds, missing-history states, delta math, first-run no-baseline behavior, and legacy payload defaults.

### Out of Scope (Deferred)

* Velocity acceleration, statistical significance, and burst math - Reason: planned for Session 05 after this daily series foundation lands.
* SQLite migration - Reason: the current session keeps the snapshot-file derivation replaceable by the ongoing SQLite observation-store plan.
* New sources, new Apify actors, or new Hugging Face API calls - Reason: this session consumes already-collected public metrics only.
* Score trajectory forecasts and convergence timelines - Reason: planned for Session 07 after lifecycle and velocity work lands.
* Documentation closeout - Reason: Phase 27 docs are finalized in Session 12 after all behavior is shipped.

***

## 5. Technical Approach

### Architecture

Keep the time-series layer script-owned and publish only bounded projections:

* `scripts/lib/ai-runtime/trend-series.ts` owns pure helpers for UTC day bucket normalization, zero-filled 14-day sparkline assembly, bounded counts, and Hugging Face model download delta math.
* `scripts/lib/ai-runtime/snapshots.ts` extends the private snapshot schema with optional series branches while preserving legacy snapshot reads and path-confined atomic writes.
* `scripts/lib/ai-runtime/historical-context.ts` reads dated snapshots and returns topic sparkline context plus model download baseline lookup data inside the existing 84-day history window.
* `scripts/extensions/trend-finder/collector.ts` attaches browser-safe sparkline arrays to topics and download delta context to Hugging Face model evidence before `TrendFinderDataSchema` validation and snapshot writing.
* `src/extensions/trend-finder/schema.ts` adds additive, bounded fields for topic sparklines and evidence download delta context so old payloads still parse.
* `src/extensions/trend-finder/view-model.ts` projects sparkline labels, SVG points, empty-state copy, Workbench fields, and delta metric chips before React components render them.
* `src/extensions/trend-finder/components/trend-sparkline.tsx` renders a small SVG sparkline with stable dimensions and accessible labels, reused by trend cards and the Signal Workbench.

Daily buckets use UTC dates derived from evidence `publishedAt` values. Invalid or missing timestamps are excluded from bucket counts and should produce warnings or unavailable states only where useful; they must not create guessed dates. The 14-day browser array should be capped by schema validation, while the private snapshot branch can keep enough bounded context for future sessions to compute velocity and burst.

Download delta comparison should identify Hugging Face models through the public model entity already normalized by source-local signals. A delta is available only when the same model has a previous finite `downloads` value in the private history. First-seen, missing-metric, malformed, and decreased counts must remain explicit states, with no invented positive growth.

### Design Patterns

* Script-only runtime boundary: Private snapshot and delta assembly stay under `scripts/lib/` and collector code, away from browser state.
* Project before rendering: React components consume bounded view models and labels, not raw archive data.
* Additive schema defaults: New topic and evidence branches use defaults or optional fields so old generated payloads and fixtures continue to parse.
* Explicit unavailable states: Missing history, invalid timestamps, and no-baseline Hugging Face models render as known states.
* Deterministic ordering: Buckets, topics, Workbench rows, and deltas use stable tie-breakers and UTC date ordering.
* Behavioral quality by design: Interactive and visual elements keep stable dimensions, accessible labels, empty states, and no layout overflow.

### Technology Stack

* TypeScript 6.0.3
* React 19.2.0
* Zod 4.4.3
* Vitest 4.1.6
* Bun 1.3.14

***

## 6. Deliverables

### Files to Create

| File                                                                        | Purpose                                                                                  | Est. Lines |
| --------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------- | ---------- |
| `scripts/lib/ai-runtime/trend-series.ts`                                    | Pure daily bucket, sparkline, and Hugging Face download delta helpers.                   | \~220      |
| `scripts/lib/ai-runtime/__tests__/trend-series.test.ts`                     | Unit tests for UTC buckets, bounds, zero-fill, deltas, no-baseline, and malformed dates. | \~180      |
| `src/extensions/trend-finder/components/trend-sparkline.tsx`                | Reusable compact SVG sparkline with stable dimensions and accessible labels.             | \~120      |
| `src/extensions/trend-finder/components/__tests__/trend-sparkline.test.tsx` | Component tests for sparkline rendering, empty states, and labels.                       | \~120      |

### Files to Modify

| File                                                                   | Changes                                                                                                           | Est. Lines |
| ---------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------- | ---------- |
| `scripts/lib/ai-runtime/snapshots.ts`                                  | Add optional private series branches, legacy defaults, and validation for snapshot read/write.                    | \~180      |
| `scripts/lib/ai-runtime/historical-context.ts`                         | Assemble topic sparkline context and Hugging Face download baseline lookup from dated snapshots.                  | \~180      |
| `scripts/extensions/trend-finder/collector.ts`                         | Build daily counts, attach sparkline and delta context, validate browser payload, and persist enriched snapshots. | \~220      |
| `src/extensions/trend-finder/schema.ts`                                | Add bounded topic sparkline and evidence download delta schemas with additive defaults.                           | \~160      |
| `src/extensions/trend-finder/view-model.ts`                            | Add sparkline projection, labels, Workbench fields, and download delta chip view models.                          | \~180      |
| `src/extensions/trend-finder/components/trend-card.tsx`                | Render compact topic sparkline and unavailable state on cards.                                                    | \~90       |
| `src/extensions/trend-finder/signal-workbench-model.ts`                | Add sparkline row fields, sort keys, labels, and deterministic ordering support.                                  | \~130      |
| `src/extensions/trend-finder/components/signal-workbench-table.tsx`    | Render sparkline column and Hugging Face delta evidence context with fixed table sizing.                          | \~110      |
| `src/extensions/trend-finder/fixtures.ts`                              | Add fixture topics/evidence for sparkline, missing-history, download-delta, and no-baseline states.               | \~100      |
| `scripts/lib/ai-runtime/__tests__/snapshots.test.ts`                   | Extend snapshot compatibility and private series persistence coverage.                                            | \~100      |
| `scripts/lib/ai-runtime/__tests__/historical-context.test.ts`          | Extend historical assembly coverage for bounded series and baselines.                                             | \~120      |
| `src/lib/__tests__/trend-finder-schema.test.ts`                        | Cover additive schema defaults, caps, malformed values, and legacy parsing.                                       | \~100      |
| `src/lib/__tests__/trend-finder-dashboard.test.tsx`                    | Cover view-model chips, labels, and browser-safe render output.                                                   | \~120      |
| `src/extensions/trend-finder/__tests__/signal-workbench-model.test.ts` | Cover Workbench sparkline fields, sorting, and empty states.                                                      | \~100      |

***

## 7. Success Criteria

### Functional Requirements

* [ ] Topic sparkline arrays are capped at 14 UTC day buckets and parse through the browser schema.
* [ ] Topics with missing history render explicit unavailable or empty states.
* [ ] Day bucketing is deterministic across timezone edges and invalid timestamps are not guessed.
* [ ] Hugging Face download deltas appear only when a prior finite download count exists for the same public model entity.
* [ ] First-seen Hugging Face models show no-baseline context rather than a numeric delta.
* [ ] Private snapshot archives and paths do not appear in browser payload, UI, static export projections, or logs.
* [ ] Trend cards and Signal Workbench render sparklines without layout overflow on dense dashboard surfaces.

### Testing Requirements

* [ ] Unit tests cover bucket math, bounds, zero-fill, malformed dates, and download delta states.
* [ ] Snapshot and historical-context tests cover legacy snapshots, path confinement, missing archives, and bounded output.
* [ ] Schema and view-model tests cover additive defaults and browser-safe labels.
* [ ] Component tests cover card/Workbench sparkline empty states and accessible labels.
* [ ] Focused Trend Finder test suites run successfully.

### Non-Functional Requirements

* [ ] Browser payload stays within the shared 1 MB extension payload budget.
* [ ] No new public source collection path, credential, or third-party transfer path is introduced.
* [ ] Private generated data remains gitignored and local-only.
* [ ] Existing legacy payloads and fixtures without new fields remain valid.

### Quality Gates

* [ ] All files ASCII-encoded.
* [ ] Unix LF line endings.
* [ ] Code follows project conventions.
* [ ] TypeScript typechecks pass for app and scripts as feasible.
* [ ] Relevant Vitest suites pass.

***

## 8. Implementation Notes

### Key Considerations

* Use canonical topic IDs for daily counts; fall back to topic ID only when canonical ID is absent.
* Treat evidence `publishedAt` as UTC input. Missing or invalid dates should not be coerced into the run date for sparkline purposes.
* Keep private series data in snapshots so future Session 05 burst and significance math can consume it without widening the browser contract.
* Bound browser arrays in both helper code and Zod schema to prevent payload growth.
* Prefer source-local Hugging Face model entity IDs over parsing URLs again in collector code.

### Potential Challenges

* Legacy snapshots have no series branch: Mitigate with additive defaults and derivation from existing topics/evidence where possible.
* Download counts can decrease or reset upstream: Mitigate with an explicit decreased or unavailable state rather than a misleading positive delta.
* Dense UI can overflow with new visuals: Mitigate with fixed sparkline dimensions, compact labels, table column widths, and component tests.
* Snapshot history can be missing on first run: Mitigate with no-history labels and no warnings for the normal first-run path.

### Relevant Considerations

* \[P02] **Extension payloads and demo labels stay bounded**: Sparkline arrays and delta context must be capped before they reach browser state.
* \[P05] **Script-only runtime boundary**: Snapshot archives and delta assembly remain under script/runtime code, not React components.
* \[P24] **Browser-safe export and triage boundaries**: Private paths, raw evidence archives, and local triage state must not leak into exports or UI.
* \[P21] **Additive live-data changes stay safest when the scanner, validator, example payload, and transforms move together**: Schema, collector, fixtures, and view-models should land in one coordinated change.
* \[P24] **Project before rendering**: Components should render bounded view-model rows rather than deriving from raw payload branches inline.
* \[P02] **Zod schemas with `.default()` for safe parsing**: New schema branches should preserve legacy payload compatibility.

### Behavioral Quality Focus

Checklist active: Yes

Top behavioral risks for this session:

* Missing history or first-run data could render as false precision instead of an explicit unavailable state.
* Private snapshot details could accidentally leak into browser payloads, labels, logs, or static exports.
* Sparkline UI could destabilize dense cards or Workbench rows if dimensions and overflow behavior are not fixed.
* Download delta math could mislead users if first-seen, missing, decreased, or malformed counts are collapsed into a single numeric state.

***

## 9. Testing Strategy

### Unit Tests

* Test UTC day bucket extraction for boundary timestamps around midnight.
* Test zero-filled 14-day output, cap enforcement, deterministic ordering, and missing/invalid timestamp handling.
* Test Hugging Face download delta states: available, no-baseline, missing-current, missing-previous, decreased, and malformed.
* Test snapshot read/write compatibility with legacy snapshots that lack private series branches.

### Integration Tests

* Test `readHistoricalTrendContext` returns bounded series and baselines while keeping malformed snapshot issues recoverable.
* Test collector output validates with new schema fields and writes enriched snapshots after browser payload validation.
* Test Workbench model rows include sparkline summaries without mutating topic payloads.

### Manual Testing

* Run Trend Finder with fixture data and confirm trend cards show sparklines where history exists and explicit empty states where it does not.
* Inspect Signal Workbench in compact and comfortable density to confirm the sparkline column does not resize rows unexpectedly.
* Confirm Hugging Face model evidence shows download deltas only when a prior baseline exists.

### Edge Cases

* First run with no snapshot directory.
* Legacy snapshot with topics/evidence but no private series branch.
* Evidence with missing, empty, or invalid `publishedAt`.
* Topic with no evidence in the last 14 days.
* Hugging Face model with missing `downloads`, missing source-local entity, changed model ID, decreased downloads, or previous zero downloads.

***

## 10. Dependencies

### External Libraries

* None. Use plain SVG for sparklines; do not add a charting dependency.

### Other Sessions

* **Depends on**: `phase27-session01-brief-movement-groups-and-calibration-metrics`, `phase27-session02-deterministic-derived-signals-and-risk-flags`, `phase27-session03-data-driven-radar-aliases-and-watching-state`.
* **Depended by**: `phase27-session05-velocity-dynamics-upgrade`, `phase27-session07-convergence-detection-and-trajectory-visuals`, `phase27-session10-demand-centers`.

***

## Next Steps

Run the implement workflow step to begin AI-led implementation.


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter, and the optional `goal` query parameter:

```
GET https://ai-os-and-trend-finder.gitbook.io/ai-os-and-trend-finder-docs/.spec_system/archive/sessions/phase27-session04-daily-time-series-persistence-and-sparklines/spec.md?ask=<question>&goal=<endgoal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is optional and describes the broader end goal you are ultimately trying to accomplish on behalf of the user. GitBook uses it to tailor the answer towards what is most useful for that goal.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
