Outerfaces.Rev (Outerfaces Dependency Distribution (ODD) v0.2.8)

View Source

Manages the current revision identifier for rev-pinned asset serving.

Rev sources (in priority order):

  1. OUTERFACES_REV environment variable (for production deployments)
  2. Git SHA via git rev-parse HEAD (for dev/staging)
  3. Application config :outerfaces_odd, :rev
  4. Timestamp fallback (for local dev without git)

The rev value is cached in :persistent_term for optimal read performance.

Scoped revs

A host serving several projects can give each its own rev, so a project's rev moves only when that project changes. set_rev/2 sets the rev for a scope (any term naming a project, such as its directory name) and current_rev/1 reads it. A scope with no rev of its own falls back to current_rev/0, so the global rev keeps working where scopes aren't used.

Summary

Functions

Removes every scope's rev, so each falls back to the global rev again.

Returns the current revision identifier.

Returns the rev for scope, or the global rev when the scope has none of its own (or scope is nil).

Invalidates the cached rev value, forcing a fresh fetch on next current_rev/0 call.

Rechecks and returns the current rev by invalidating the cache and fetching fresh.

The revs set per scope, as a map of scope => rev.

Sets the revision to a specific value and caches it.

Sets the rev for scope, leaving the global rev and other scopes as they are.

Functions

clear_scoped_revs()

@spec clear_scoped_revs() :: :ok

Removes every scope's rev, so each falls back to the global rev again.

current_rev()

@spec current_rev() :: String.t()

Returns the current revision identifier.

The rev is cached in :persistent_term for performance. Once set, it persists for the lifetime of the VM (or until explicitly invalidated).

Examples

iex> Outerfaces.Rev.current_rev()
"abc123def456"

current_rev(scope)

@spec current_rev(term()) :: String.t()

Returns the rev for scope, or the global rev when the scope has none of its own (or scope is nil).

Examples

iex> Outerfaces.Rev.set_rev(:docs_site, "7-3f2a9c1d0b7e")
:ok
iex> Outerfaces.Rev.current_rev(:docs_site)
"7-3f2a9c1d0b7e"

invalidate_cache()

@spec invalidate_cache() :: :ok

Invalidates the cached rev value, forcing a fresh fetch on next current_rev/0 call.

This is primarily useful for testing or when you need to update the rev at runtime by re-detecting from environment/git/config sources.

If you want to set a specific rev value, use set_rev/1 instead.

recheck()

@spec recheck() :: String.t()

Rechecks and returns the current rev by invalidating the cache and fetching fresh.

This is a convenience method that combines invalidate_cache/0 and current_rev/0 to force a re-detection from environment/git/config sources in a single call.

Examples

iex> Outerfaces.Rev.recheck()
"abc123def456"  # Freshly fetched from OUTERFACES_REV, git, config, or timestamp

scoped_revs()

@spec scoped_revs() :: %{optional(term()) => String.t()}

The revs set per scope, as a map of scope => rev.

set_rev(new_rev)

@spec set_rev(String.t()) :: :ok

Sets the revision to a specific value and caches it.

This is useful when you want to manually update to a specific rev without relying on environment variables, git, or config.

Examples

iex> Outerfaces.Rev.set_rev("new-rev-123")
:ok
iex> Outerfaces.Rev.current_rev()
"new-rev-123"

set_rev(scope, rev)

@spec set_rev(term(), String.t()) :: :ok

Sets the rev for scope, leaving the global rev and other scopes as they are.