Skip to content

feat: implement PoH credential refresh function#202

Closed
gryaele wants to merge 8 commits intomainfrom
elenagryaznova-pop-3497-implement-calling-refresh-credential-code-in-oxide-from
Closed

feat: implement PoH credential refresh function#202
gryaele wants to merge 8 commits intomainfrom
elenagryaznova-pop-3497-implement-calling-refresh-credential-code-in-oxide-from

Conversation

@gryaele
Copy link
Copy Markdown
Contributor

@gryaele gryaele commented Feb 10, 2026

This pull request introduces a new credential issuer for Proof of Personhood (POP) in the walletkit-core package, adds the required dependencies, and exposes the new issuer for use.

New POP issuer and API client:

  • Added a new module tfh_pop in walletkit-core/src/issuers/, implementing the ProofOfHumanIssuer API client to interact with the POP credential refresh endpoint. This includes a method to refresh credentials, error handling, and response parsing.
  • Exposed the ProofOfHumanIssuer in the issuer module's public API, making it available for use elsewhere in the codebase.

Dependency updates:

  • Added reqwest (with json, multipart, and rustls-tls features) to both the root Cargo.toml and walletkit-core/Cargo.toml to support HTTP requests and multipart form data needed for the POP issuer. [1] [2]

@gryaele gryaele force-pushed the elenagryaznova-pop-3497-implement-calling-refresh-credential-code-in-oxide-from branch from 52c01bd to 6ffc062 Compare February 10, 2026 15:32
@thomas-waite
Copy link
Copy Markdown
Contributor

@codex review

Copy link
Copy Markdown

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 061b99681e

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread walletkit-core/src/issuers/tfh_pop.rs Outdated
Comment on lines +23 to +27
impl TfhPopIssuer {
/// Create a new TFH POP issuer with the specified base URL
#[uniffi::constructor]
#[must_use]
pub fn new(environment: &Environment) -> Self {
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Add UniFFI export on TfhPopIssuer impl

TfhPopIssuer is declared as a #[derive(uniffi::Object)], but this impl block is not annotated with #[uniffi::export]. As written, UniFFI will not generate callable bindings for new or refresh_pop_credential, so foreign-language clients cannot use the POP issuer even though it is publicly re-exported.

Useful? React with 👍 / 👎.

Comment on lines +55 to +56
let mut request = self.client.post(url).multipart(multipart_form);

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Enforce timeout/retry policy for POP refresh call

This request path uses a bare reqwest::Client request builder without any timeout or retry policy, so transient network issues can cause indefinite waits or one-shot failures. Other issuer/network paths in this crate use http_request::Request (with timeout and retry handling), so this introduces a reliability regression specifically for POP refresh in flaky network conditions.

Useful? React with 👍 / 👎.

@thomas-waite
Copy link
Copy Markdown
Contributor

@codex review

Copy link
Copy Markdown

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 061b99681e

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +34 to +37
Self {
base_url,
client: Client::new(),
}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Configure POP requests with a bounded timeout

The POP issuer builds a plain reqwest::Client and uses it for send() without any timeout configuration, so a slow or stalled /api/v1/refresh connection can hang this call indefinitely in production. This is a reliability regression versus the existing Request helper used by other issuer/network paths (which applies a 5s timeout and retries), so POP refresh can block user flows under transient network faults.

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thanks, timeout added

Copy link
Copy Markdown
Contributor

@thomas-waite thomas-waite left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seems fine to me from a mobile perspective apart from we need docs/explanation of what the headers passed to this are

Comment thread walletkit-core/src/issuers/proof_of_human.rs
Comment thread walletkit-core/src/issuers/proof_of_human.rs Outdated
Comment thread walletkit-core/src/issuers/mod.rs Outdated
//! Credential issuers for World ID.

mod tfh_nfc;
mod tfh_pop;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the pop credential isn't issued by tfh. this should just be called mod proof_of_human. generally also the credential has been renamed to Proof of Human, so naming should reflect that everywhere

/// Returns error on network failure or invalid response.
pub async fn refresh_pop_credential(
&self,
multipart_form: Form,
Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I believe we wouldn't be able to call refresh_pop_credential from other languages bindings because reqwest::multipart::Form doesn't have bindings.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@Dzejkop what'd you think?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

hmm well if the form is constructed in Rust elsewhere it may work. Likely this is compiling because Form is wrapped in an Arc internally and can pass between foreign/Rust boundaries. but this may be fragile, perhaps accepting raw bytes of the body instead?

Copy link
Copy Markdown
Contributor

@thomas-waite thomas-waite left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks fine to me. Lets wait for @Dzejkop's review before we go ahead with merging. He's the expert for the multipart-form Rust question


#[uniffi::export]
impl ProofOfHumanIssuer {
/// Create a new TFH POP issuer with the specified base URL
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's called Proof of Human everywhere now, so POP should be POH

@paolodamico paolodamico changed the title Implement iris credentials refresh function Implement PoH credential refresh function Feb 18, 2026
@paolodamico paolodamico changed the title Implement PoH credential refresh function feat: implement PoH credential refresh function Feb 18, 2026

Self {
base_url,
client: Client::new(),
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

IIRC with the introduction of NFC we introduced a module for HTTP requests, that will handle things like user agent headers, retries and timeouts

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yes, I saw that one, unfortunately it doesn't have multipart option

let refresh_credentials_response =
serde_json::from_str::<RefreshCredentialsResponse>(&response_text)
.map_err(|e| WalletKitError::SerializationError {
error: format!("Failed to parse POP refresh response: {e}"),
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This may be confusing because SerializationError is an internal error from a Rust object, but this is an error from the HTTP response. I'd still propagate a network error

@gryaele gryaele closed this Feb 20, 2026
@paolodamico paolodamico deleted the elenagryaznova-pop-3497-implement-calling-refresh-credential-code-in-oxide-from branch March 11, 2026 18:05
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants