Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/eighty-phones-fly.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"chainlink-deployments-framework": minor
---

feat(engine): load catalog into datastore
10 changes: 10 additions & 0 deletions .mockery.yml
Original file line number Diff line number Diff line change
Expand Up @@ -81,3 +81,13 @@ packages:
filename: "mock_{{.InterfaceName | snakecase}}.go"
interfaces:
NodeServiceClient:
github.com/smartcontractkit/chainlink-deployments-framework/datastore:
config:
all: false
filename: "mock_{{.InterfaceName | snakecase}}_test.go"
structname: "{{.Mock}}{{.InterfaceName | firstUpper }}"
interfaces:
CatalogStore:
MutableRefStoreV2:
MutableStoreV2:
MutableUnaryStoreV2:
84 changes: 84 additions & 0 deletions datastore/catalog_loader.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
package datastore

import (
"context"
"errors"
"fmt"
)

// LoadDataStoreFromCatalog fetches all data from a remote CatalogStore and creates a local
// in-memory DataStore populated with that data. After loading, all operations are performed
// on the local DataStore without any remote calls.
func LoadDataStoreFromCatalog(ctx context.Context, catalog CatalogStore) (DataStore, error) {
// Create a new mutable in-memory datastore
memoryDS := NewMemoryDataStore()

// Fetch all address references from the catalog
addressRefs, err := catalog.Addresses().Fetch(ctx)
if err != nil {
// If no address refs found, treat as empty catalog (valid state)
if !errors.Is(err, ErrAddressRefNotFound) {
return nil, fmt.Errorf("failed to fetch address references from catalog: %w", err)
}
addressRefs = []AddressRef{} // Empty catalog is valid
}

// Populate the address ref store
for _, ref := range addressRefs {
if addErr := memoryDS.Addresses().Add(ref); addErr != nil {
return nil, fmt.Errorf("failed to add address reference to local store: %w", addErr)
}
}

// Fetch all chain metadata from the catalog
chainMetadata, err := catalog.ChainMetadata().Fetch(ctx)
if err != nil {
// If no chain metadata found, treat as empty catalog (valid state)
if !errors.Is(err, ErrChainMetadataNotFound) {
return nil, fmt.Errorf("failed to fetch chain metadata from catalog: %w", err)
}
chainMetadata = []ChainMetadata{} // Empty catalog is valid
}

// Populate the chain metadata store
for _, metadata := range chainMetadata {
if addErr := memoryDS.ChainMetadata().Add(metadata); addErr != nil {
return nil, fmt.Errorf("failed to add chain metadata to local store: %w", addErr)
}
}

// Fetch all contract metadata from the catalog
contractMetadata, err := catalog.ContractMetadata().Fetch(ctx)
if err != nil {
// If no contract metadata found, treat as empty catalog (valid state)
if !errors.Is(err, ErrContractMetadataNotFound) {
return nil, fmt.Errorf("failed to fetch contract metadata from catalog: %w", err)
}
contractMetadata = []ContractMetadata{} // Empty catalog is valid
}

// Populate the contract metadata store
for _, metadata := range contractMetadata {
if addErr := memoryDS.ContractMetadata().Add(metadata); addErr != nil {
return nil, fmt.Errorf("failed to add contract metadata to local store: %w", addErr)
}
}

// Fetch environment metadata from the catalog
envMetadata, err := catalog.EnvMetadata().Get(ctx)
if err != nil {
// EnvMetadata might not exist, which is okay - ignore ErrEnvMetadataNotSet
if !errors.Is(err, ErrEnvMetadataNotSet) {
return nil, fmt.Errorf("failed to fetch environment metadata from catalog: %w", err)
}
// If it's ErrEnvMetadataNotSet, continue without error
} else {
// Populate the environment metadata store
if setErr := memoryDS.EnvMetadata().Set(envMetadata); setErr != nil {
return nil, fmt.Errorf("failed to set environment metadata in local store: %w", setErr)
}
}

// Seal the datastore to make it read-only and return
return memoryDS.Seal(), nil
}
Loading