|
1 | 1 | // Copyright 2021-Present Datadog, Inc. https://www.datadoghq.com/
|
2 | 2 | // SPDX-License-Identifier: Apache-2.0
|
3 | 3 |
|
4 |
| -use crate::targets::TargetsList; |
| 4 | +use crate::targets::{Root, TargetsList}; |
5 | 5 | use crate::{
|
6 | 6 | RemoteConfigCapabilities, RemoteConfigPath, RemoteConfigPathRef, RemoteConfigPathType,
|
7 | 7 | RemoteConfigProduct, Target,
|
@@ -189,16 +189,29 @@ pub struct ConfigFetcher<S: FileStorage> {
|
189 | 189 | state: Arc<ConfigFetcherState<S::StoredFile>>,
|
190 | 190 | }
|
191 | 191 |
|
192 |
| -#[derive(Default)] |
193 | 192 | pub struct ConfigClientState {
|
194 | 193 | opaque_backend_state: Vec<u8>,
|
195 | 194 | last_configs: Vec<String>,
|
196 | 195 | // 'static because it actually depends on last_configs, and rust doesn't like self-referencing
|
197 | 196 | last_config_paths: HashSet<RemoteConfigPathRef<'static>>,
|
198 | 197 | targets_version: u64,
|
| 198 | + root_version: u64, |
199 | 199 | last_error: Option<String>,
|
200 | 200 | }
|
201 | 201 |
|
| 202 | +impl Default for ConfigClientState { |
| 203 | + fn default() -> Self { |
| 204 | + ConfigClientState { |
| 205 | + opaque_backend_state: vec![], |
| 206 | + last_configs: vec![], |
| 207 | + last_config_paths: Default::default(), |
| 208 | + targets_version: 0, |
| 209 | + root_version: 1, |
| 210 | + last_error: None, |
| 211 | + } |
| 212 | + } |
| 213 | +} |
| 214 | + |
202 | 215 | impl<S: FileStorage> ConfigFetcher<S> {
|
203 | 216 | pub fn new(file_storage: S, state: Arc<ConfigFetcherState<S::StoredFile>>) -> Self {
|
204 | 217 | ConfigFetcher {
|
@@ -265,7 +278,7 @@ impl<S: FileStorage> ConfigFetcher<S> {
|
265 | 278 | let config_req = ClientGetConfigsRequest {
|
266 | 279 | client: Some(datadog_trace_protobuf::remoteconfig::Client {
|
267 | 280 | state: Some(ClientState {
|
268 |
| - root_version: 1, |
| 281 | + root_version: opaque_state.root_version, |
269 | 282 | targets_version: opaque_state.targets_version,
|
270 | 283 | config_states,
|
271 | 284 | has_error: opaque_state.last_error.is_some(),
|
@@ -351,6 +364,21 @@ impl<S: FileStorage> ConfigFetcher<S> {
|
351 | 364 | ))
|
352 | 365 | })?;
|
353 | 366 |
|
| 367 | + opaque_state.root_version = response.roots.iter().try_fold( |
| 368 | + opaque_state.root_version, |
| 369 | + |max, cur| -> anyhow::Result<_> { |
| 370 | + let decoded_root = |
| 371 | + base64::engine::general_purpose::STANDARD.decode(cur.as_slice())?; |
| 372 | + let root = Root::try_parse(decoded_root.as_slice()).map_err(|e| { |
| 373 | + anyhow::Error::msg(e).context(format!( |
| 374 | + "Decoded roots reply: {}", |
| 375 | + String::from_utf8_lossy(decoded_root.as_slice()) |
| 376 | + )) |
| 377 | + })?; |
| 378 | + Ok(std::cmp::max(max, root.signed.version)) |
| 379 | + }, |
| 380 | + )?; |
| 381 | + |
354 | 382 | opaque_state.opaque_backend_state = targets_list
|
355 | 383 | .signed
|
356 | 384 | .custom
|
|
0 commit comments