SuperCache.Partition (SuperCache v1.3.0)

Copy Markdown View Source

Partition resolution and management for SuperCache.

SuperCache splits data across multiple ETS tables (partitions) to reduce contention and improve parallelism. This module handles:

  • Hashing — mapping arbitrary terms to partition indices using :erlang.phash2/2.
  • Resolution — translating partition indices to ETS table atoms.
  • Lifecycle — initialising and tearing down the partition registry.

How partitioning works

  1. A term (usually extracted from a tuple via :partition_pos) is hashed with :erlang.phash2/2 modulo the number of partitions.
  2. The resulting index is looked up in SuperCache.Partition.Holder to get the corresponding ETS table atom.
  3. All reads and writes for that term go to that table.

Example

# Start with 4 partitions
SuperCache.Partition.start(4)

# Resolve partition for a term
SuperCache.Partition.get_partition(:user_123)
# => :"SuperCache.Storage.Ets_2"

# Get partition index directly
SuperCache.Partition.get_partition_order(:user_123)
# => 2

# Clean up
SuperCache.Partition.stop()

Summary

Functions

List all registered partition ETS table atoms.

Return the configured number of partitions.

Resolve the ETS table atom for a given term.

Resolve the ETS table atom directly from a partition index.

Compute the partition index for any term.

Compute the partition index for a data tuple using the configured :partition_pos.

Return the number of online schedulers in the Erlang VM.

Initialise the partition registry.

Clear all partition registrations from the registry.

Functions

get_all_partition()

@spec get_all_partition() :: [atom()]

List all registered partition ETS table atoms.

Returns a flat list of table names, excluding internal registry entries.

Examples

SuperCache.Partition.start(3)
SuperCache.Partition.get_all_partition()
# => [:"SuperCache.Storage.Ets_0", :"SuperCache.Storage.Ets_1", :"SuperCache.Storage.Ets_2"]

get_num_partition()

@spec get_num_partition() :: pos_integer()

Return the configured number of partitions.

Reads directly from the Holder ETS table — no GenServer hop. Raises if the partition count has not been initialised.

Examples

SuperCache.Partition.start(8)
SuperCache.Partition.get_num_partition()
# => 8

get_partition(data)

@spec get_partition(any()) :: atom()

Resolve the ETS table atom for a given term.

The term is hashed to derive a partition index, which is then looked up in the Holder registry to return the corresponding ETS table name.

This is the primary entry point used by the public API when the caller has a raw key or partition value.

Examples

SuperCache.Partition.get_partition(:session_abc)
# => :"SuperCache.Storage.Ets_1"

SuperCache.Partition.get_partition({:user, 42})
# => :"SuperCache.Storage.Ets_3"

get_partition_by_idx(idx)

@spec get_partition_by_idx(non_neg_integer()) :: atom() | nil

Resolve the ETS table atom directly from a partition index.

Does not re-hash the input. Safe to call from the Replicator and Router where the index is already known.

Examples

SuperCache.Partition.get_partition_by_idx(0)
# => :"SuperCache.Storage.Ets_0"

get_partition_order(term)

@spec get_partition_order(any()) :: non_neg_integer()
@spec get_partition_order(any()) :: non_neg_integer()

Compute the partition index for any term.

Uses :erlang.phash2/2 with the configured number of partitions as the range. The result is an integer in 0..(num_partitions - 1).

Examples

SuperCache.Partition.get_partition_order(:hello)
# => 2

get_partition_order_from_data(data)

@spec get_partition_order_from_data(tuple()) :: non_neg_integer()

Compute the partition index for a data tuple using the configured :partition_pos.

Extracts the element at :partition_pos from the tuple, then hashes it to determine the partition index.

Examples

SuperCache.Config.set_config(:partition_pos, 1)
SuperCache.Partition.get_partition_order_from_data({:user, 42, "data"})
# => (hash of 42) mod num_partitions

get_schedulers()

@spec get_schedulers() :: pos_integer()

Return the number of online schedulers in the Erlang VM.

Used as the default partition count when :num_partition is not explicitly configured.

Examples

SuperCache.Partition.get_schedulers()
# => 8  (on an 8-core machine)

start(num_partition)

@spec start(pos_integer()) :: :ok

Initialise the partition registry.

Stores the total partition count and registers each index (0 to N-1) with its corresponding ETS table name.

Called by SuperCache.Bootstrap during startup.

Examples

SuperCache.Partition.start(4)
# => :ok

stop()

@spec stop() :: :ok

Clear all partition registrations from the registry.

Does not delete the ETS tables themselves — only removes the index-to-name mappings from the Holder.

Called by SuperCache.Bootstrap during shutdown.