Skip to main content

Documentation Index

Fetch the complete documentation index at: https://grantmaster.dev/llms.txt

Use this file to discover all available pages before exploring further.

shared/intelligence — API Reference

The shared/intelligence module provides opt-in access to cross-organisation intelligence data — sector benchmarks, funder profiles, AI predictions, and sector trends — aggregated at the platform level. A GDPR-compliant consent layer gates all reads: an organisation must explicitly opt in before any intelligence data is accessible.

Module Map

FileResponsibility
intelligenceService.tsRead-only access to benchmarks, funder profiles, and trends; org-level caching
consentService.tsConsent record CRUD; GDPR-compliant opt-in/withdrawal/deletion
All writes to the platform-level intelligence collections are handled by Cloud Functions (aggregation jobs), not by these services.

ConsentService

Manages IntelligenceConsent records stored at platform/intelligence/consent/{organizationId}.

Export

import { consentService } from '@/shared/intelligence';
// or
import { consentService } from '@/shared/intelligence/consentService';

Data Categories

type IntelligenceDataCategory =
  | 'grants'
  | 'finance'
  | 'compliance'
  | 'users'
  | 'projects';
The default full-consent grant includes all five categories.

Key Methods

// Read consent status
consentService.getConsentStatus(organizationId): Promise<IntelligenceConsent | null>

// Grant consent (GDPR Article 7 — explicit opt-in)
consentService.grantConsent(
  organizationId,
  userId,
  categories?: IntelligenceDataCategory[]   // defaults to all 5
): Promise<ServiceResult<IntelligenceConsent>>

// Withdraw consent
consentService.withdrawConsent(organizationId, userId): Promise<ServiceResult<void>>

// Delete all platform-held data (GDPR Article 17 — right to erasure)
consentService.requestDataDeletion(organizationId, userId): Promise<ServiceResult<void>>

// Update data categories without full withdrawal
consentService.updateConsentCategories(
  organizationId,
  userId,
  categories: IntelligenceDataCategory[]
): Promise<ServiceResult<IntelligenceConsent>>

IntelligenceConsent Schema

interface IntelligenceConsent {
  organizationId: string;
  isActive: boolean;
  grantedAt: string;           // ISO 8601
  grantedBy: string;           // userId
  withdrawnAt?: string;
  withdrawnBy?: string;
  dataCategories: IntelligenceDataCategory[];
  deletionRequestedAt?: string;
  version: string;             // consent policy version
}

EventBus Events

ConsentService emits the following via emitCanonicalSystemEvent:
EventWhen
INTELLIGENCE_CONSENT_GRANTEDOrganisation opts in
INTELLIGENCE_CONSENT_WITHDRAWNOrganisation opts out
INTELLIGENCE_DATA_DELETION_REQUESTEDOrganisation requests erasure

IntelligenceService

Provides read-only access to platform intelligence data. Before any read, verifyConsent() is called internally — requests from organisations that have not opted in receive an AuthorizationError.

Export

import { intelligenceService } from '@/shared/intelligence';

Caching Strategy

  1. Check organizations/{orgId}/intelligenceCache/{cacheKey} (org-scoped cache).
  2. If cache is stale (older than 24 hours), fall back to platform-level aggregate collections under platform/intelligence/.
  3. Cloud Functions refresh org caches on a nightly schedule.

Key Methods

// Sector benchmarks — how does this org compare to peers?
intelligenceService.getBenchmarks(
  organizationId,
  options?: BenchmarkQueryOptions
): Promise<OrgBenchmarkPosition>

// Funder intelligence — success rates, preferences, decision timelines
intelligenceService.getFunderProfile(
  organizationId,
  funderName: string
): Promise<FunderProfile | null>

intelligenceService.getFunderInsights(
  organizationId,
  funderName: string
): Promise<FunderInsight[]>

// Sector trends — thematic funding shifts, emerging priorities
intelligenceService.getSectorTrends(
  organizationId,
  sector?: string
): Promise<SectorTrend[]>

// Invalidate org cache (called after consent withdrawal)
intelligenceService.clearOrgCache(organizationId): Promise<void>

BenchmarkQueryOptions

interface BenchmarkQueryOptions {
  sector?: string;
  country?: string;
  subscriptionTier?: SubscriptionTier;  // compare like-for-like
  metrics?: string[];                   // subset of benchmark dimensions
}

OrgBenchmarkPosition

interface OrgBenchmarkPosition {
  organizationId: string;
  sector: string;
  peerCount: number;
  metrics: {
    [metricName: string]: {
      value: number;
      percentile: number;   // 0–100
      average: number;
      median: number;
    };
  };
  lastRefreshed: string;
}

Firestore Collections

PathContents
platform/intelligence/benchmarks/{benchmarkId}Sector-level benchmark aggregates
platform/intelligence/funderProfiles/{funderId}Per-funder intelligence summaries
platform/intelligence/trends/{trendId}Sector trend analysis
platform/intelligence/consent/{orgId}Consent records
organizations/{orgId}/intelligenceCache/{cacheKey}Org-scoped cached intelligence

Privacy Notes

  • No individual organisation’s data is exposed to another. All platform aggregates are computed from anonymous, aggregate statistics by Cloud Functions.
  • Consent records are stored at the platform level (not org-scoped) so they remain accessible even if an org’s data is deleted.
  • requestDataDeletion() sets deletionRequestedAt and triggers a Cloud Function to anonymise the org’s contribution to platform aggregates within 30 days (GDPR Article 17 compliance).

Callers

CallerUses
src/features/organizations/Consent management UI (ConsentService)
src/features/dashboard/Intelligence widgets reading benchmarks and trends
src/features/grantors/Funder profile and insight lookups
Firebase Cloud FunctionsPlatform aggregate computation; org cache refresh