Back to list
ethereum

data-layer

by ethereum

Ethereum.org is a primary online resource for the Ethereum community.

5,836🍴 5,374📅 Jan 22, 2026

SKILL.md


name: data-layer description: This skill provides patterns for working with the data-layer module. Use when creating/editing files in src/data-layer/, src/lib/data/, or adding new data sources.

Data Layer

Architecture

src/data-layer/
├── fetchers/         # Fetch functions (one per data source)
├── index.ts          # Public API - typed getter functions
├── tasks.ts          # KEYS constant + Trigger.dev scheduled tasks
├── storage.ts        # get/set abstraction (Netlify Blobs or mock files)
└── mocks/            # Mock data files for local development

src/lib/data/
└── index.ts          # Next.js caching adapter (createCachedGetter)

Key Files

tasks.ts - Single Source of Truth

Defines all task keys and scheduled jobs:

export const KEYS = {
  ETH_PRICE: "fetch-eth-price",
  L2BEAT: "fetch-l2beat",
  // ...
} as const

const DAILY: Task[] = [
  [KEYS.APPS, fetchApps],
  [KEYS.EVENTS, fetchEvents],
]

const HOURLY: Task[] = [
  [KEYS.ETH_PRICE, fetchEthPrice],
  [KEYS.BEACONCHAIN, fetchBeaconChain],
]

index.ts - Simple Getters

One-liner passthrough functions:

export const getEthPrice = () => get<MetricReturnData>(KEYS.ETH_PRICE)
export const getL2beatData = () => get<L2beatData>(KEYS.L2BEAT)

storage.ts - Storage Abstraction

Simple get/set that switches between Netlify Blobs (prod) and local JSON files (dev):

export async function get<T>(key: string): Promise<T | null>
export async function set(key: string, data: unknown): Promise<void>

Uses USE_MOCK_DATA=true env var for local development.

Rules

1. Getters must be pure passthrough

No transformations in index.ts - just get<T>(KEYS.X):

// Correct
export const getEventsData = () => get<EventItem[]>(KEYS.EVENTS)

// Wrong - no transformations in getters
export const getEventsData = () => {
  const data = await get<EventItem[]>(KEYS.EVENTS)
  return data?.map(transform) ?? null
}

All transformations belong in the fetcher (src/data-layer/fetchers/).

2. KEYS is the single source of truth

All task IDs are defined in KEYS in tasks.ts. The getter in index.ts and the task tuple in DAILY/HOURLY must use the same key.

3. Expose via lib/data for caching

Add cached wrapper in src/lib/data/index.ts:

export const getEventsData = createCachedGetter(
  dataLayer.getEventsData,
  ["events-data"],
  CACHE_REVALIDATE_DAY  // or CACHE_REVALIDATE_HOUR
)

Adding a New Data Source

  1. Create fetcher in src/data-layer/fetchers/fetchNewData.ts:

    export async function fetchNewData(): Promise<YourDataType> {
      // Fetch and transform data here
    }
    
  2. Add key to KEYS in src/data-layer/tasks.ts:

    export const KEYS = {
      // ...existing keys
      NEW_DATA: "fetch-new-data",
    } as const
    
  3. Add task tuple to DAILY or HOURLY in tasks.ts:

    const DAILY: Task[] = [
      // ...existing tasks
      [KEYS.NEW_DATA, fetchNewData],
    ]
    
  4. Add getter in src/data-layer/index.ts:

    export const getNewData = () => get<YourDataType>(KEYS.NEW_DATA)
    
  5. Add mock file at src/data-layer/mocks/fetch-new-data.json for local development

  6. Add cached wrapper in src/lib/data/index.ts:

    export const getNewData = createCachedGetter(
      dataLayer.getNewData,
      ["new-data"],
      CACHE_REVALIDATE_HOUR
    )
    

Score

Total Score

80/100

Based on repository quality metrics

SKILL.md

SKILL.mdファイルが含まれている

+20
LICENSE

ライセンスが設定されている

+10
説明文

100文字以上の説明がある

0/10
人気

GitHub Stars 1000以上

+15
最近の活動

1ヶ月以内に更新

+10
フォーク

10回以上フォークされている

+5
Issue管理

オープンIssueが50未満

0/5
言語

プログラミング言語が設定されている

+5
タグ

1つ以上のタグが設定されている

+5

Reviews

💬

Reviews coming soon