From 380f2067fd43338c740fd06f45c3e26d236778a6 Mon Sep 17 00:00:00 2001 From: Gabriel Moise Date: Mon, 3 Mar 2025 15:35:46 +0000 Subject: [PATCH 1/6] Agnostic_baker: Add agnostic baker profiler module --- manifest/product_octez.ml | 4 ++++ opam/octez-experimental-agnostic-baker-lib.opam | 2 +- src/bin_agnostic_baker/main_agnostic_baker.ml | 8 ++++++++ .../agnostic_baker_profiler.ml | 17 +++++++++++++++++ .../agnostic_baker_profiler.mli | 16 ++++++++++++++++ src/lib_agnostic_baker/daemon.ml | 8 ++++++++ src/lib_agnostic_baker/dune | 8 ++++++-- 7 files changed, 60 insertions(+), 3 deletions(-) create mode 100644 src/lib_agnostic_baker/agnostic_baker_profiler.ml create mode 100644 src/lib_agnostic_baker/agnostic_baker_profiler.mli diff --git a/manifest/product_octez.ml b/manifest/product_octez.ml index d1d286db12ae..e3e5e6641269 100644 --- a/manifest/product_octez.ml +++ b/manifest/product_octez.ml @@ -5343,11 +5343,14 @@ let _octez_scoru_wasm_fast_tests = ~preprocess:(staged_pps [ppx_import; ppx_deriving_show]) let octez_experimental_agnostic_baker_lib = + let (PPX {preprocess; preprocessor_deps}) = ppx_profiler in public_lib "octez-experimental-agnostic-baker-lib" ~path:"src/lib_agnostic_baker" ~internal_name:"octez_experimental_agnostic_baker" ~synopsis:"Octez: library for Agnostic Baker" + ~preprocess + ~preprocessor_deps ~deps: [ octez_rustzcash_deps; @@ -5358,6 +5361,7 @@ let octez_experimental_agnostic_baker_lib = octez_client_base_unix |> open_; octez_node_config; octez_client_commands |> open_; + octez_profiler |> open_; ] (* PROTOCOL PACKAGES *) diff --git a/opam/octez-experimental-agnostic-baker-lib.opam b/opam/octez-experimental-agnostic-baker-lib.opam index ee8a3184911c..5ecb396d33b3 100644 --- a/opam/octez-experimental-agnostic-baker-lib.opam +++ b/opam/octez-experimental-agnostic-baker-lib.opam @@ -10,9 +10,9 @@ license: "MIT" depends: [ "dune" { >= "3.11.1" } "ocaml" { >= "4.14" } + "octez-libs" { = version } "octez-rustzcash-deps" { = version } "bls12-381" { = version } - "octez-libs" { = version } "octez-shell-libs" { = version } "octez-node-config" { = version } ] diff --git a/src/bin_agnostic_baker/main_agnostic_baker.ml b/src/bin_agnostic_baker/main_agnostic_baker.ml index a1c5132671f8..012833f1d3e0 100644 --- a/src/bin_agnostic_baker/main_agnostic_baker.ml +++ b/src/bin_agnostic_baker/main_agnostic_baker.ml @@ -6,6 +6,13 @@ (* *) (*****************************************************************************) +let[@warning "-32"] may_start_profiler baking_dir = + match Tezos_profiler_unix.Profiler_instance.selected_backend () with + | Some {instance_maker; _} -> + let profiler_maker = instance_maker ~directory:baking_dir in + Agnostic_baker_profiler.init profiler_maker + | None -> () + let run () = let open Lwt_result_syntax in let Run_args.{node_endpoint; base_dir; baker_args} = @@ -16,6 +23,7 @@ let run () = ~config:(Parameters.log_config ~base_dir) () in + () [@profiler.overwrite may_start_profiler base_dir] ; let daemon = Daemon.create ~node_endpoint ~baker_args in let* (_ : unit) = Daemon.run daemon in let*! () = Lwt_utils.never_ending () in diff --git a/src/lib_agnostic_baker/agnostic_baker_profiler.ml b/src/lib_agnostic_baker/agnostic_baker_profiler.ml new file mode 100644 index 000000000000..9b93ffd25bef --- /dev/null +++ b/src/lib_agnostic_baker/agnostic_baker_profiler.ml @@ -0,0 +1,17 @@ +(*****************************************************************************) +(* *) +(* SPDX-License-Identifier: MIT *) +(* Copyright (c) 2025 Trilitech *) +(* *) +(*****************************************************************************) +open Profiler + +let agnostic_baker_profiler = unplugged () + +let init profiler_maker = + match profiler_maker ~name:"agnostic_baker" with + | Some instance -> plug agnostic_baker_profiler instance + | None -> () + +let create_reset_block_section = + section_maker Block_hash.equal Block_hash.to_b58check diff --git a/src/lib_agnostic_baker/agnostic_baker_profiler.mli b/src/lib_agnostic_baker/agnostic_baker_profiler.mli new file mode 100644 index 000000000000..3e9e56176b2b --- /dev/null +++ b/src/lib_agnostic_baker/agnostic_baker_profiler.mli @@ -0,0 +1,16 @@ +(*****************************************************************************) +(* *) +(* SPDX-License-Identifier: MIT *) +(* Copyright (c) 2025 Trilitech *) +(* *) +(*****************************************************************************) + +(** Unplugged agnostic baker profiler. *) +val agnostic_baker_profiler : Profiler.profiler + +(** Plug the agnostic baker profiler given its name and Profiler instance option. *) +val init : (name:string -> Profiler.instance option) -> unit + +(** Creates a function to reset the block section *) +val create_reset_block_section : + Profiler.profiler -> Block_hash.t * Profiler.metadata -> unit diff --git a/src/lib_agnostic_baker/daemon.ml b/src/lib_agnostic_baker/daemon.ml index f396b39727e8..675eaaf0f43b 100644 --- a/src/lib_agnostic_baker/daemon.ml +++ b/src/lib_agnostic_baker/daemon.ml @@ -6,6 +6,14 @@ (* *) (*****************************************************************************) +module Profiler = struct + include (val Profiler.wrap Agnostic_baker_profiler.agnostic_baker_profiler) + + let[@warning "-32"] reset_block_section = + Agnostic_baker_profiler.create_reset_block_section + Agnostic_baker_profiler.agnostic_baker_profiler +end + open Agnostic_baker_errors (* Number of extra levels to keep the old baker alive before shutting it down. diff --git a/src/lib_agnostic_baker/dune b/src/lib_agnostic_baker/dune index ba71b4b59cab..266070c8d71e 100644 --- a/src/lib_agnostic_baker/dune +++ b/src/lib_agnostic_baker/dune @@ -13,7 +13,10 @@ octez-libs.base.unix octez-shell-libs.client-base-unix octez-node-config - octez-shell-libs.client-commands) + octez-shell-libs.client-commands + octez-libs.octez-profiler) + (preprocess (pps octez-libs.ppx_profiler)) + (preprocessor_deps (env_var TEZOS_PPX_PROFILER)) (flags (:standard) -open Data_encoding @@ -21,4 +24,5 @@ -open Tezos_base -open Tezos_base_unix -open Tezos_client_base_unix - -open Tezos_client_commands)) + -open Tezos_client_commands + -open Tezos_profiler)) -- GitLab From 9ee50eed341990ba4025718572862e52f12286e1 Mon Sep 17 00:00:00 2001 From: Gabriel Moise Date: Fri, 21 Mar 2025 12:23:20 +0000 Subject: [PATCH 2/6] Agnostic_baker: Initialise agnostic baker profiler --- manifest/product_octez.ml | 4 ++++ opam/octez-experimental-agnostic-baker.opam | 2 +- src/bin_agnostic_baker/dune | 6 +++++- src/bin_agnostic_baker/main_agnostic_baker.ml | 5 +++++ src/lib_agnostic_baker/daemon.ml | 9 +++++++++ src/lib_agnostic_baker/parameters.ml | 5 ----- src/lib_agnostic_baker/parameters.mli | 2 +- 7 files changed, 25 insertions(+), 8 deletions(-) diff --git a/manifest/product_octez.ml b/manifest/product_octez.ml index e3e5e6641269..cff4e1dfa733 100644 --- a/manifest/product_octez.ml +++ b/manifest/product_octez.ml @@ -8284,6 +8284,7 @@ let _octez_node = ] let _octez_experimental_agnostic_baker = + let (PPX {preprocess; preprocessor_deps}) = ppx_profiler in let protocol_deps = let deps_for_protocol protocol = let is_optional = @@ -8301,6 +8302,8 @@ let _octez_experimental_agnostic_baker = ~path:"src/bin_agnostic_baker" ~internal_name:"main_agnostic_baker" ~synopsis:"Tezos: `octez-experimental-agnostic-baker` binary for baking" + ~preprocess + ~preprocessor_deps ~release_status:Released ~with_macos_security_framework:true ~deps: @@ -8310,6 +8313,7 @@ let _octez_experimental_agnostic_baker = octez_base |> open_ ~m:"TzPervasives" |> open_; octez_base_unix |> open_; octez_experimental_agnostic_baker_lib |> open_; + octez_profiler |> open_; ] @ protocol_deps) ~linkall:true diff --git a/opam/octez-experimental-agnostic-baker.opam b/opam/octez-experimental-agnostic-baker.opam index bc418220acd1..eab07475ebd5 100644 --- a/opam/octez-experimental-agnostic-baker.opam +++ b/opam/octez-experimental-agnostic-baker.opam @@ -10,9 +10,9 @@ license: "MIT" depends: [ "dune" { >= "3.11.1" } "ocaml" { >= "4.14" } + "octez-libs" { = version } "octez-rust-deps" { = version } "bls12-381" { = version } - "octez-libs" { = version } "octez-experimental-agnostic-baker-lib" { = version } "octez-protocol-021-PsQuebec-libs" { = version } "octez-protocol-022-PsRiotum-libs" { = version } diff --git a/src/bin_agnostic_baker/dune b/src/bin_agnostic_baker/dune index d836df1c327c..d184c7a2c707 100644 --- a/src/bin_agnostic_baker/dune +++ b/src/bin_agnostic_baker/dune @@ -12,11 +12,14 @@ octez-libs.base octez-libs.base.unix octez-experimental-agnostic-baker-lib + octez-libs.octez-profiler octez-protocol-021-PsQuebec-libs.agnostic-baker octez-protocol-022-PsRiotum-libs.agnostic-baker (select void_for_linking-octez-protocol-alpha-libs-agnostic-baker from (octez-protocol-alpha-libs.agnostic-baker -> void_for_linking-octez-protocol-alpha-libs-agnostic-baker.empty) (-> void_for_linking-octez-protocol-alpha-libs-agnostic-baker.empty))) + (preprocess (pps octez-libs.ppx_profiler)) + (preprocessor_deps (env_var TEZOS_PPX_PROFILER)) (link_flags (:standard) (:include %{workspace_root}/static-link-flags.sexp) @@ -27,7 +30,8 @@ -open Tezos_base.TzPervasives -open Tezos_base -open Tezos_base_unix - -open Octez_experimental_agnostic_baker)) + -open Octez_experimental_agnostic_baker + -open Tezos_profiler)) (rule (action diff --git a/src/bin_agnostic_baker/main_agnostic_baker.ml b/src/bin_agnostic_baker/main_agnostic_baker.ml index 012833f1d3e0..5dbaafca021b 100644 --- a/src/bin_agnostic_baker/main_agnostic_baker.ml +++ b/src/bin_agnostic_baker/main_agnostic_baker.ml @@ -18,6 +18,11 @@ let run () = let Run_args.{node_endpoint; base_dir; baker_args} = Run_args.parse_args Sys.argv in + let base_dir = + Option.value + ~default:Tezos_client_base_unix.Client_config.Cfg_file.default.base_dir + base_dir + in let*! () = Tezos_base_unix.Internal_event_unix.init ~config:(Parameters.log_config ~base_dir) diff --git a/src/lib_agnostic_baker/daemon.ml b/src/lib_agnostic_baker/daemon.ml index 675eaaf0f43b..b693d1d79148 100644 --- a/src/lib_agnostic_baker/daemon.ml +++ b/src/lib_agnostic_baker/daemon.ml @@ -171,6 +171,12 @@ let parse_level head_info = let json = Ezjsonm.from_string head_info in Ezjsonm.find json ["level"] |> Ezjsonm.get_int +(** [parse_block_hash head_info] retrieves the ["hash"] field information from the + json information of the chain from [head_info]. *) +let[@warning "-32"] parse_block_hash head_info = + let json = Ezjsonm.from_string head_info in + Ezjsonm.find json ["hash"] |> Ezjsonm.get_string |> Block_hash.of_b58check_exn + (** [maybe_kill_old_baker state head_info] checks whether the [old_baker] process from the [state] of the agnostic baker has surpassed its lifetime and it stops it if that is the case. *) @@ -201,6 +207,9 @@ let monitor_voting_periods ~state head_stream = match head_info_opt with | None -> tzfail Lost_node_connection | Some head_info -> + () + [@profiler.reset_block_section + {profiler_module = Profiler} (parse_block_hash head_info)] ; let* period_kind, remaining = Rpc_services.get_current_period ~node_addr in diff --git a/src/lib_agnostic_baker/parameters.ml b/src/lib_agnostic_baker/parameters.ml index e273beaa109b..7e67520deb12 100644 --- a/src/lib_agnostic_baker/parameters.ml +++ b/src/lib_agnostic_baker/parameters.ml @@ -14,11 +14,6 @@ let default_node_endpoint = let default_daily_logs_path = Some "octez-experimental-agnostic-baker" let log_config ~base_dir = - let base_dir : string = - match base_dir with - | Some p -> p - | None -> Tezos_client_base_unix.Client_config.Cfg_file.default.base_dir - in let daily_logs_path = default_daily_logs_path |> Option.map Filename.Infix.(fun logdir -> base_dir // "logs" // logdir) diff --git a/src/lib_agnostic_baker/parameters.mli b/src/lib_agnostic_baker/parameters.mli index df009a953ce5..79f7c870b154 100644 --- a/src/lib_agnostic_baker/parameters.mli +++ b/src/lib_agnostic_baker/parameters.mli @@ -13,7 +13,7 @@ val default_node_endpoint : string (** Default logs path for the agnostic baker. *) val default_daily_logs_path : string option -val log_config : base_dir:string option -> Tezos_base.Internal_event_config.t +val log_config : base_dir:string -> Tezos_base.Internal_event_config.t (** Status of a protocol, based on Manifest/Product_octez/Protocol. A protocol is considered as [Active] while it is running on a network, -- GitLab From 495e4bec6520b6c660c8312a13c8da76047b0b4e Mon Sep 17 00:00:00 2001 From: Gabriel Moise Date: Fri, 21 Mar 2025 12:30:20 +0000 Subject: [PATCH 3/6] Agnostic_baker: Profile RPC calls and baker process --- src/lib_agnostic_baker/daemon.ml | 26 +++++++++++++++++++++----- 1 file changed, 21 insertions(+), 5 deletions(-) diff --git a/src/lib_agnostic_baker/daemon.ml b/src/lib_agnostic_baker/daemon.ml index b693d1d79148..a486bdaeb90a 100644 --- a/src/lib_agnostic_baker/daemon.ml +++ b/src/lib_agnostic_baker/daemon.ml @@ -85,7 +85,11 @@ let spawn_baker protocol_hash ~baker_args = let baker_args = "./mock-binary" :: baker_args in let cancel_promise, canceller = Lwt.wait () in let* thread = - let*? plugin = Protocol_plugins.proto_plugin_for_protocol protocol_hash in + let*? plugin = + (Protocol_plugins.proto_plugin_for_protocol + protocol_hash + [@profiler.record_f {verbosity = Notice} "proto_plugin_for_protocol"]) + in let baker_commands = Commands.baker_commands plugin in return @@ run_thread @@ -190,7 +194,9 @@ let maybe_kill_old_baker state head_info = let* () = Agnostic_baker_events.(emit stopping_baker) baker.protocol_hash in - Lwt.wakeup baker.process.canceller 0 ; + Lwt.wakeup + baker.process.canceller + 0 [@profiler.record_f {verbosity = Notice} "kill old baker"] ; state.old_baker <- None ; return_unit) else return_unit @@ -211,14 +217,23 @@ let monitor_voting_periods ~state head_stream = [@profiler.reset_block_section {profiler_module = Profiler} (parse_block_hash head_info)] ; let* period_kind, remaining = - Rpc_services.get_current_period ~node_addr + (Rpc_services.get_current_period + ~node_addr + [@profiler.record_s {verbosity = Notice} "get_current_period"]) in let*! () = Agnostic_baker_events.(emit period_status) (period_kind, remaining) in - let*! () = maybe_kill_old_baker state head_info in + let*! () = + (maybe_kill_old_baker + state + head_info + [@profiler.record_s {verbosity = Notice} "maybe_kill_old_baker"]) + in let* next_protocol_hash = - Rpc_services.get_next_protocol_hash ~node_addr + (Rpc_services.get_next_protocol_hash + ~node_addr + [@profiler.record_s {verbosity = Notice} "get_next_protocol_hash"]) in let* current_protocol_hash = match state.current_baker with @@ -234,6 +249,7 @@ let monitor_voting_periods ~state head_stream = ~next_protocol_hash ~level_to_kill_old_baker: (parse_level head_info + extra_levels_for_old_baker) + [@profiler.record_s {verbosity = Notice} "hot_swap_baker"] else return_unit in loop () -- GitLab From 9efaae182595ca231cf8183747a6e42309fdcd88 Mon Sep 17 00:00:00 2001 From: Gabriel Moise Date: Mon, 3 Mar 2025 16:47:17 +0000 Subject: [PATCH 4/6] Agnostic_baker: Make printing of longer messages work properly --- src/lib_agnostic_baker/agnostic_baker_events.ml | 1 + 1 file changed, 1 insertion(+) diff --git a/src/lib_agnostic_baker/agnostic_baker_events.ml b/src/lib_agnostic_baker/agnostic_baker_events.ml index 4a591d8ffb79..c58e8db584cc 100644 --- a/src/lib_agnostic_baker/agnostic_baker_events.ml +++ b/src/lib_agnostic_baker/agnostic_baker_events.ml @@ -22,6 +22,7 @@ let starting_baker = ("proto", Protocol_hash.encoding) ("args", string) ~pp1:Protocol_hash.pp_short + ~pp2:Format.pp_print_string let baker_running = declare_1 -- GitLab From dda37062f7172f4a858eed316a08cc0f007f5a2a Mon Sep 17 00:00:00 2001 From: Gabriel Moise Date: Fri, 21 Mar 2025 12:32:18 +0000 Subject: [PATCH 5/6] Agnostic_baker: Improve documentation --- src/lib_agnostic_baker/daemon.ml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/lib_agnostic_baker/daemon.ml b/src/lib_agnostic_baker/daemon.ml index a486bdaeb90a..5ac613b5d1bd 100644 --- a/src/lib_agnostic_baker/daemon.ml +++ b/src/lib_agnostic_baker/daemon.ml @@ -204,7 +204,8 @@ let maybe_kill_old_baker state head_info = (** [monitor_voting_periods ~state head_stream] continuously monitors [heads_stream] to detect protocol changes. It will: - Shut down an old baker it its time has come; - - Spawn and "hot-swap" to a new baker if the next protocol hash is different. *) + - Spawn and "hot-swap" to a new baker if the next protocol hash is different. + The voting period information is used for logging purposes. *) let monitor_voting_periods ~state head_stream = let open Lwt_result_syntax in let node_addr = state.node_endpoint in -- GitLab From ec99e7c90a6c8b48b7ef592ac82562ace2f280d2 Mon Sep 17 00:00:00 2001 From: Gabriel Moise Date: Fri, 21 Mar 2025 13:48:33 +0000 Subject: [PATCH 6/6] Agnostic_baker: Use Rpc_services functions for level and block hash --- .../agnostic_baker_events.ml | 7 +- src/lib_agnostic_baker/daemon.ml | 64 +++++++++---------- src/lib_agnostic_baker/rpc_services.ml | 19 ++++++ src/lib_agnostic_baker/rpc_services.mli | 4 ++ 4 files changed, 60 insertions(+), 34 deletions(-) diff --git a/src/lib_agnostic_baker/agnostic_baker_events.ml b/src/lib_agnostic_baker/agnostic_baker_events.ml index c58e8db584cc..ce6a651baadc 100644 --- a/src/lib_agnostic_baker/agnostic_baker_events.ml +++ b/src/lib_agnostic_baker/agnostic_baker_events.ml @@ -93,12 +93,15 @@ let waiting_for_active_protocol = () let period_status = - declare_2 + declare_3 ~section ~alternative_color ~level:Notice ~name:"period_status" - ~msg:"new block on {period} period (remaining period duration {remaining})" + ~msg: + "new block ({block}) on {period} period (remaining period duration \ + {remaining})" + ("block", Block_hash.encoding) ("period", string) ("remaining", int31) diff --git a/src/lib_agnostic_baker/daemon.ml b/src/lib_agnostic_baker/daemon.ml index 5ac613b5d1bd..0dfe075731dc 100644 --- a/src/lib_agnostic_baker/daemon.ml +++ b/src/lib_agnostic_baker/daemon.ml @@ -169,29 +169,20 @@ let hot_swap_baker ~state ~current_protocol_hash ~next_protocol_hash state.current_baker <- Some new_baker ; return_unit -(** [parse_level head_info] retrieves the ["level"] field information from the - json information of the chain from [head_info]. *) -let parse_level head_info = - let json = Ezjsonm.from_string head_info in - Ezjsonm.find json ["level"] |> Ezjsonm.get_int - -(** [parse_block_hash head_info] retrieves the ["hash"] field information from the - json information of the chain from [head_info]. *) -let[@warning "-32"] parse_block_hash head_info = - let json = Ezjsonm.from_string head_info in - Ezjsonm.find json ["hash"] |> Ezjsonm.get_string |> Block_hash.of_b58check_exn - -(** [maybe_kill_old_baker state head_info] checks whether the [old_baker] process +(** [maybe_kill_old_baker state node_addr] checks whether the [old_baker] process from the [state] of the agnostic baker has surpassed its lifetime and it stops it if that is the case. *) -let maybe_kill_old_baker state head_info = - let open Lwt_syntax in +let maybe_kill_old_baker state node_addr = + let open Lwt_result_syntax in match state.old_baker with | None -> return_unit | Some {baker; level_to_kill} -> - let head_level = parse_level head_info in + let* head_level = + (Rpc_services.get_level + ~node_addr [@profiler.record_s {verbosity = Notice} "get_level"]) + in if head_level >= level_to_kill then ( - let* () = + let*! () = Agnostic_baker_events.(emit stopping_baker) baker.protocol_hash in Lwt.wakeup @@ -210,25 +201,30 @@ let monitor_voting_periods ~state head_stream = let open Lwt_result_syntax in let node_addr = state.node_endpoint in let rec loop () = - let*! head_info_opt = Lwt_stream.get head_stream in - match head_info_opt with + let*! v = Lwt_stream.get head_stream in + match v with | None -> tzfail Lost_node_connection - | Some head_info -> + | Some _tick -> + let* block_hash = + (Rpc_services.get_block_hash + ~node_addr + [@profiler.record_s {verbosity = Notice} "get_block_hash"]) + in () - [@profiler.reset_block_section - {profiler_module = Profiler} (parse_block_hash head_info)] ; + [@profiler.reset_block_section {profiler_module = Profiler} block_hash] ; let* period_kind, remaining = (Rpc_services.get_current_period ~node_addr [@profiler.record_s {verbosity = Notice} "get_current_period"]) in let*! () = - Agnostic_baker_events.(emit period_status) (period_kind, remaining) + Agnostic_baker_events.(emit period_status) + (block_hash, period_kind, remaining) in - let*! () = + let* () = (maybe_kill_old_baker state - head_info + node_addr [@profiler.record_s {verbosity = Notice} "maybe_kill_old_baker"]) in let* next_protocol_hash = @@ -244,13 +240,17 @@ let monitor_voting_periods ~state head_stream = let* () = if not (Protocol_hash.equal current_protocol_hash next_protocol_hash) then - hot_swap_baker - ~state - ~current_protocol_hash - ~next_protocol_hash - ~level_to_kill_old_baker: - (parse_level head_info + extra_levels_for_old_baker) - [@profiler.record_s {verbosity = Notice} "hot_swap_baker"] + let* head_level = + (Rpc_services.get_level + ~node_addr + [@profiler.record_s {verbosity = Notice} "get_level"]) + in + (hot_swap_baker + ~state + ~current_protocol_hash + ~next_protocol_hash + ~level_to_kill_old_baker:(head_level + extra_levels_for_old_baker) + [@profiler.record_s {verbosity = Notice} "hot_swap_baker"]) else return_unit in loop () diff --git a/src/lib_agnostic_baker/rpc_services.ml b/src/lib_agnostic_baker/rpc_services.ml index bde5622bb778..c2415fc5cbc1 100644 --- a/src/lib_agnostic_baker/rpc_services.ml +++ b/src/lib_agnostic_baker/rpc_services.ml @@ -64,6 +64,25 @@ let get_level ~node_addr = in call_and_wrap_rpc ~node_addr ~uri ~f +let get_block_hash ~node_addr = + let open Lwt_result_syntax in + let f json = + (* Hash field in the RPC result *) + let name = "hash" in + let* v = + match json with + | `O fields -> ( + match List.assoc_opt ~equal:( = ) name fields with + | None -> tzfail (Cannot_decode_node_data ("missing field " ^ name)) + | Some node -> return node) + | _ -> tzfail (Cannot_decode_node_data "not an object") + in + let block_hash = Block_hash.of_b58check_exn @@ Ezjsonm.get_string v in + return block_hash + in + let uri = Format.sprintf "%s/chains/main/blocks/head/header" node_addr in + call_and_wrap_rpc ~node_addr ~uri ~f + let get_next_protocol_hash ~node_addr = let open Lwt_result_syntax in let f json = diff --git a/src/lib_agnostic_baker/rpc_services.mli b/src/lib_agnostic_baker/rpc_services.mli index 063adf0e11f0..904ac48456d9 100644 --- a/src/lib_agnostic_baker/rpc_services.mli +++ b/src/lib_agnostic_baker/rpc_services.mli @@ -16,6 +16,10 @@ val request_uri : (** [get_level ~node_addr] returns the level of the block. *) val get_level : node_addr:string -> (int, error trace) result Lwt.t +(** [get_level ~node_addr] returns the hash of the block. *) +val get_block_hash : + node_addr:string -> (Block_hash.t, error trace) result Lwt.t + (** [get_next_protocol_hash ~node_addr] returns the protocol hash contained in the [next_protocol] field of the metadata of a block. *) -- GitLab