Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature/handle geopatch updates in notifier #1620

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
44 changes: 36 additions & 8 deletions lib/archethic/p2p/mem_table_loader.ex
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ defmodule Archethic.P2P.MemTableLoader do

alias Archethic.DB

alias Archethic.P2P
alias Archethic.P2P.GeoPatch
alias Archethic.P2P.MemTable
alias Archethic.P2P.Node
Expand Down Expand Up @@ -86,7 +87,7 @@ defmodule Archethic.P2P.MemTableLoader do
end

@doc """
Load the transaction and update the P2P view
Load the transaction and update the P2P view.
"""
@spec load_transaction(Transaction.t()) :: :ok
def load_transaction(%Transaction{
Expand All @@ -112,7 +113,8 @@ defmodule Archethic.P2P.MemTableLoader do
reward_address: reward_address,
origin_public_key: origin_public_key,
mining_public_key: mining_public_key,
geo_patch: geo_patch
geo_patch: geo_patch,
geo_patch_update: geo_patch_update
}} = Node.decode_transaction_content(content)

geo_patch = if geo_patch == nil, do: GeoPatch.from_ip(ip), else: geo_patch
Expand All @@ -133,13 +135,12 @@ defmodule Archethic.P2P.MemTableLoader do
mining_public_key: mining_public_key
}

node
|> Node.enroll(timestamp)
|> MemTable.add_node()
node = Node.enroll(node, timestamp)
MemTable.add_node(node)
else
{:ok, node} = MemTable.get_node(first_public_key)

MemTable.add_node(%{
updated_node = %Node{
node
| ip: ip,
port: port,
Expand All @@ -152,10 +153,14 @@ defmodule Archethic.P2P.MemTableLoader do
origin_public_key: origin_public_key,
last_update_date: timestamp,
mining_public_key: mining_public_key
})
}

MemTable.add_node(updated_node)

handle_geo_patch_update(node, updated_node, geo_patch_update)
end

Logger.info("Node loaded into in memory p2p tables", node: Base.encode16(first_public_key))
Logger.info("Node loaded into in-memory P2P tables", node: Base.encode16(first_public_key))
end

def load_transaction(%Transaction{
Expand Down Expand Up @@ -201,4 +206,27 @@ defmodule Archethic.P2P.MemTableLoader do
MemTable.set_node_unavailable(node_public_key, availability_update)
end
end

defp handle_geo_patch_update(
%Node{first_public_key: first_public_key, geo_patch: prev_geo_patch},
%Node{geo_patch: new_geo_patch},
geo_patch_update
)
when prev_geo_patch != new_geo_patch do
Logger.info("GeoPatch changed for node", node: Base.encode16(first_public_key))
Logger.info("Starting Notifier for GeoPatch change")

new_nodes = P2P.authorized_and_available_nodes(geo_patch_update)

previous_nodes =
Enum.map(new_nodes, fn
node = %Node{first_public_key: ^first_public_key} ->
%Node{node | geo_patch: prev_geo_patch}

node ->
node
end)

SelfRepair.start_notifier(previous_nodes, new_nodes, geo_patch_update)
end
end
39 changes: 13 additions & 26 deletions lib/archethic/self_repair.ex
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@ defmodule Archethic.SelfRepair do
alias Archethic.P2P.Node
alias Archethic.Replication
alias Archethic.TransactionChain
alias Archethic.Utils

require Logger

Expand Down Expand Up @@ -164,33 +163,21 @@ defmodule Archethic.SelfRepair do
@doc """
Start a new notifier process if there is new unavailable nodes after the self repair
"""
@spec start_notifier(list(Node.t()), list(Node.t()), DateTime.t()) :: :ok
def start_notifier(prev_available_nodes, new_available_nodes, availability_update) do
diff_node =
prev_available_nodes
|> Enum.reject(
&(Utils.key_in_node_list?(new_available_nodes, &1.first_public_key) or
&1.first_public_key == Crypto.first_node_public_key())
)

case diff_node do
[] ->
:ok

nodes ->
unavailable_nodes = Enum.map(nodes, & &1.first_public_key)
@spec start_notifier(
previous_nodes :: list(Node.t()),
new_nodes :: list(Node.t()),
availability_update :: DateTime.t()
) :: :ok
def start_notifier(previous_nodes, new_nodes, availability_update) do
args = [
previous_nodes: previous_nodes,
new_nodes: new_nodes,
availability_update: availability_update
]

DynamicSupervisor.start_child(
NotifierSupervisor,
{Notifier,
unavailable_nodes: unavailable_nodes,
prev_available_nodes: prev_available_nodes,
new_available_nodes: new_available_nodes,
availability_update: availability_update}
)
DynamicSupervisor.start_child(NotifierSupervisor, {Notifier, args})

:ok
end
:ok
end

@doc """
Expand Down
Loading
Loading