Files
EventHubBack/src/infra/infra_mnesia_fragmentation.erl

84 lines
3.6 KiB
Erlang
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
%% ===================================================================
%% EventHub утилита фрагментации больших таблиц Mnesia
%% ===================================================================
-module(infra_mnesia_fragmentation).
-export([
fragment_table/2,
defragment_table/1,
add_fragment/2,
info/1
]).
%% -------------------------------------------------------------------
%% @doc Включает фрагментацию для заданной таблицы.
%% Table - имя таблицы (atom)
%% FragCount - количество фрагментов (integer > 1)
%%
%% После вызова таблица будет автоматически распределена
%% по фрагментам. Новые записи будут попадать в нужный фрагмент
%% на основе хеша ключа.
%%
%% Пример:
%% infra_mnesia_fragmentation:fragment_table(event, 4).
%% -------------------------------------------------------------------
fragment_table(Table, FragCount) when FragCount > 1 ->
case mnesia:change_table_frag(Table, {activate, FragCount}) of
{atomic, ok} ->
io:format("Table ~p successfully fragmented into ~p fragments~n", [Table, FragCount]),
ok;
{aborted, Reason} ->
{error, {fragmentation_failed, Table, Reason}}
end;
fragment_table(_Table, FragCount) ->
{error, {invalid_frag_count, FragCount}}.
%% -------------------------------------------------------------------
%% @doc Отключает фрагментацию, возвращая таблицу к обычному виду.
%% Все данные остаются сохранными, но таблица перестаёт быть
%% фрагментированной. Может занять продолжительное время
%% на больших объёмах.
%% -------------------------------------------------------------------
defragment_table(Table) ->
case mnesia:change_table_frag(Table, deactivate) of
{atomic, ok} ->
io:format("Fragmentation removed for table ~p~n", [Table]),
ok;
{aborted, Reason} ->
{error, {defragmentation_failed, Table, Reason}}
end.
%% -------------------------------------------------------------------
%% @doc Добавляет новый фрагмент к уже фрагментированной таблице.
%% Полезно для постепенного масштабирования.
%% -------------------------------------------------------------------
add_fragment(Table, ExtraFrags) ->
case mnesia:add_table_fragment(Table, ExtraFrags) of
{atomic, ok} ->
io:format("Added ~p fragment(s) to table ~p~n", [ExtraFrags, Table]),
ok;
{aborted, Reason} ->
{error, {add_fragment_failed, Table, Reason}}
end.
%% -------------------------------------------------------------------
%% @doc Выводит информацию о фрагментации таблицы (если включена)
%% или о текущем состоянии.
%% -------------------------------------------------------------------
info(Table) ->
try
IsFrag = mnesia:table_info(Table, frag_property),
FragCount = case IsFrag of
[{n_fragments, N} | _] -> N;
_ -> 1
end,
io:format("Table ~p fragmentation: ~p fragments~n", [Table, FragCount]),
FragList = mnesia:table_info(Table, frag_dist),
io:format("Fragment distribution: ~p~n", [FragList]),
ok
catch
_:_ ->
io:format("Table ~p is not fragmented~n", [Table]),
ok
end.