Skip to main content

recoco_core/setup/
auth_registry.rs

1// ReCoco is a Rust-only fork of CocoIndex, by [CocoIndex](https://CocoIndex)
2// Original code from CocoIndex is copyrighted by CocoIndex
3// SPDX-FileCopyrightText: 2025-2026 CocoIndex (upstream)
4// SPDX-FileContributor: CocoIndex Contributors
5//
6// All modifications from the upstream for ReCoco are copyrighted by Knitli Inc.
7// SPDX-FileCopyrightText: 2026 Knitli Inc. (ReCoco)
8// SPDX-FileContributor: Adam Poulemanos <adam@knit.li>
9//
10// Both the upstream CocoIndex code and the ReCoco modifications are licensed under the Apache-2.0 License.
11// SPDX-License-Identifier: Apache-2.0
12
13use std::collections::hash_map;
14
15use crate::prelude::*;
16
17pub struct AuthRegistry {
18    entries: RwLock<HashMap<String, serde_json::Value>>,
19}
20
21impl Default for AuthRegistry {
22    fn default() -> Self {
23        Self::new()
24    }
25}
26
27impl AuthRegistry {
28    pub fn new() -> Self {
29        Self {
30            entries: RwLock::new(HashMap::new()),
31        }
32    }
33
34    pub fn add(&self, key: String, value: serde_json::Value) -> Result<()> {
35        let mut entries = self.entries.write().unwrap();
36        match entries.entry(key) {
37            hash_map::Entry::Occupied(entry) => {
38                api_bail!("Auth entry already exists: {}", entry.key());
39            }
40            hash_map::Entry::Vacant(entry) => {
41                entry.insert(value);
42            }
43        }
44        Ok(())
45    }
46
47    pub fn add_transient(&self, value: serde_json::Value) -> Result<String> {
48        let key = format!(
49            "__transient_{}",
50            utils::fingerprint::Fingerprinter::default()
51                .with("cocoindex_auth")? // salt
52                .with(&value)?
53                .into_fingerprint()
54                .to_base64()
55        );
56        self.entries
57            .write()
58            .unwrap()
59            .entry(key.clone())
60            .or_insert(value);
61        Ok(key)
62    }
63
64    pub fn get<T: DeserializeOwned>(&self, entry_ref: &spec::AuthEntryReference<T>) -> Result<T> {
65        let entries = self.entries.read().unwrap();
66        match entries.get(&entry_ref.key) {
67            Some(value) => Ok(utils::deser::from_json_value(value.clone())?),
68            None => api_bail!(
69                "Auth entry `{key}` not found.\n\
70                Hint: If you're not referencing `{key}` in your flow, it will likely be caused by a previously persisted target using it. \
71                You need to bring back the definition for the auth entry `{key}`, so that CocoIndex will be able to do a cleanup in the next `setup` run. \
72                See https://CocoIndex/docs/core/flow_def#auth-registry for more details.",
73                key = entry_ref.key
74            ),
75        }
76    }
77}