The integration of third-party libraries into WordPress plugins can be a daunting task, especially when the library is as intricate as cashu-ts a TypeScript library for building Cashu wallets we can leverage to begin our implementation. In this article, we'll delve into the meticulous process we undertook to seamlessly integrate the cashu-ts library into a WordPress plugin, sharing on the analysis and systematic approach we adopted. You can reach our if you feel you can contribute to improve this project.

1. Let's Talk Requirements!

Before we get our hands dirty with code, it's all about understanding what we want to achieve. For our adventurous project, we aimed to jazz up the WordPress login scene. Imagine logging in or signing up to a WordPress site using a nifty token, all thanks to the cashu magic! The goal is then to allow users to log in or sign up to any WordPress website (that has this plugin installed) using a token generated by the cashu-ts library. The cherry on top? This token could either have a value in satoshi (yep, that's a Bitcoin denomination) or not. Talk about flexibility!

2. Getting Cozy with cashu-ts

Ah, cashu-ts! The cashu-ts library is a robust tool, so understanding its intricacies was paramount, at least for me! We began by exploring its GitHub repository, which provided insights into its capabilities and functionalities. This step was crucial in determining how to best leverage the library for our WordPress plugin.
Analyzing the content of these files will identify the functions related to token generation and validation. Let's begin with src/CashuWallet.ts and src/CashuMint.ts, as they seem to be directly related to the cashu functionality.

src/CashuMint.ts

The CashuMint class is initialized with a given secret key in its constructor. However, the exact source or method to generate or obtain this secret key isn't explicitly mentioned in the files analyzed. This file seems to define the CashuMint class, which likely represents the minting functionality of the cashu system. Here are the key functions and their purposes:
  1. constructor: Initializes the mint with a given secret key.
  2. blindSign: This function takes a blinded message and returns a blinded signature. This is likely the step where the mint signs a token without knowing its actual content.
  3. unblindSignature: Given a blinded signature and a blinding factor, this function returns the actual signature. This step is probably used to reveal the signed token.
  4. verify: Verifies if a given signature is valid for a given message using the mint's public key.

src/CashuWallet.ts

The CashuWallet class is also initialized with a given secret key in its constructor. Again, the method to generate or obtain this secret key isn't detailed in the files reviewed. This file defines the CashuWallet class, which likely represents the user's wallet in the cashu system. Here are the key functions and their purposes:
  1. constructor: Initializes the wallet with a given secret key.
  2. blindMessage: This function takes a message and returns a blinded version of it along with a blinding factor. This is likely the step where the user blinds a token before sending it to the mint for signing.
  3. unblindMessage: Given a blinded message and a blinding factor, this function returns the actual message. This might be used to reveal the original token.
  4. sign: Signs a given message with the wallet's secret key.
  5. verify: Verifies if a given signature is valid for a given message using the wallet's public key.
From the above analysis, it seems that the cashu system uses a blind signature scheme. In this scheme, a user sends a blinded message (token) to the mint, which then signs it without knowing its actual content. The user can later unblind the signed message to obtain a valid signature for the original token. More need to be answared:
How are tokens generated? Tokens are likely generated by the user (wallet) and then blinded using the blindMessage function before sending them to the mint for signing.
How are tokens validated? Tokens are validated using the verify function in both the CashuMint and CashuWallet classes. The mint can verify tokens using its public key, and the wallet can verify tokens using the mint's public key.
The two files, src/CashuMint.ts and src/CashuWallet.ts, provide a foundational understanding of how the cashu system operates, especially in terms of token generation, blinding, signing, and verification. They are indeed useful for our purpose.
However, to fully integrate the cashu-ts library into the WordPress plugin, we might need to understand a few more things:
  1. Initialization: How are the CashuMint and CashuWallet instances typically initialized? Are there any default or recommended parameters?
  2. Token Flow: While we understand the blind signature scheme, it would be helpful to know the typical flow of token generation, blinding, signing, unblinding, and verification in a real-world scenario.
  3. Error Handling: How does the library handle errors? Are there specific error types or messages we should be aware of?
  4. Dependencies: Are there any other classes or utilities in the library that these two classes depend on?
Utility Functions:
  • getEncodedToken: This function encodes a v3 cashu token. It takes a token object as a parameter and returns an encoded string representation of the token.
  • getDecodedToken: This function decodes cashu tokens into an object. It takes an encoded cashu token string and returns a cashu token object.
  • deriveKeysetId: This function returns the keyset id of a set of keys. It takes a keys object as a parameter and returns a derived keyset id.
**Other Observations: **
  • The utils.ts file provides various utility functions that handle encoding and decoding of tokens, as well as deriving keyset ids.
  • The request.ts file seems to handle HTTP requests, setting global request options, and error handling for responses.
  • The DHKE.ts file provides functions related to Diffie-Hellman Key Exchange, including hashing to a curve, blinding messages, unblinding signatures, and constructing proofs.
  • The BlindedMessage.ts and BlindedSignature.ts files define classes for blinded messages and blinded signatures, respectively, with methods to serialize them.
While these insights give us a clearer picture of how the library functions, the exact initialization process (especially how the secret keys are generated or obtained) isn't clear from the files analyzed. We might need to look into any examples or test files in the repository, or any accompanying documentation, to get a complete understanding.
The NutStash wallet repository contains a plethora of files, many of which are related to the wallet's functionality. To understand how a wallet is initialized from a user's perspective, I'll focus on the following files:
  1. src/comp/wallet/Wallet.svelte: This file likely contains the main wallet component, which might have the initialization logic or user interface elements related to the wallet.
  2. src/actions/walletActions.ts: The actions related to the wallet might provide insights into the initialization and other operations.
  3. src/comp/util/walletUtils.ts: Utility functions related to the wallet might give us more details about the initialization process.
  4. src/stores/wallet.ts (if it exists): This might contain the state management for the wallet, which can provide insights into how the wallet data is managed and initialized.
Let's start by analyzing the content of these files to understand the initialization process of the NutStash wallet. We easily notice that it provides a user interface and functionalities to manage tokens. Here's a breakdown of the wallet's operations from the provided files:

/wallet.svelte

This file contains the main wallet component. Here's what happens from a user's perspective:
  1. Initialization: When the component mounts, it checks if there's a mint URL in the search parameters. If found, it sets the active tab to 'mint'. If there's a hash in the URL, it sets the active state to 'receive' and extracts the encoded token from the hash.
  2. Checking Tokens: If the settings allow for automatic checking of tokens (either pending or non-pending), it invokes the checkTokens function. This function iterates through all mints and checks if the tokens associated with the mint are spent or not. If a token is spent, it's removed from the wallet. If a pending token is no longer pending (i.e., it's received), it's updated accordingly.
  3. User Interface: The component provides options for the user to send, receive, melt tokens, or scan a payment. The exact UI and interactions depend on the active state, which can be 'base', 'receive', 'send', 'melt', or 'scan'.
walletActions.ts contains actions related to the wallet. The main function here is updateMintKeys, which updates the keys of a mint. If the mint's keys have changed, this function updates them in the wallet and notifies the user about the new keyset ID.
walletUtils.ts utility file provides several helper functions related to the wallet:
  1. getTokensToSend: Returns a subset of tokens to send based on the specified amount.
  2. validateMintKeys: Validates the keys of a mint.
  3. getTokensForMint: Returns a subset of all tokens that belong to the specified mint.
  4. isValidToken: Validates a token (though the actual implementation is marked as TODO).
  5. getTokenSubset: Removes a set of tokens from another set and returns the remaining tokens.
  6. getMintForToken: Returns the mint associated with a specific token.
  7. getAmountForTokenSet: Calculates the total amount for a set of tokens.
  8. getKeysetsOfTokens: Returns the keysets of a set of tokens.
  9. removeDuplicatesFromArray: Removes duplicates from an array.
From the provided code, the NutStash wallet seems to offer functionalities for sending, receiving, melting tokens, and scanning payments. The wallet interacts with mints, checks the status of tokens, and updates the wallet state accordingly.

/cashu

The cashu repository contains a wide range of files, many of which are related to the core functionalities of the Cashu protocol, including the mint and wallet functionalities. To understand the initialization process and other operations, with focus on the following files:
  1. cashu/mint/__main__.py:
    • This file contains the main entry point for the mint functionality. It imports and runs the main function from cashu.mint.main.
  2. cashu/mint/app.py:
    • This file initializes the FastAPI application for the mint and includes the routers for the mint's API endpoints. It also sets up the database session for the mint.
  3. cashu/mint/crud.py:
    • This file contains CRUD (Create, Read, Update, Delete) operations for the mint. It defines functions to create a new mint, get a mint by its ID, and get all mints.
  4. cashu/mint/ledger.py:
    • This file seems to handle ledger-related operations for the mint. It defines functions to add a new transaction to the ledger, get a transaction by its ID, and get all transactions.
  5. cashu/mint/main.py:
    • This file contains the main logic for running the mint. It sets up the FastAPI application, initializes the database, and starts the application.
  6. cashu/mint/router.py:
    • This file contains the routing logic for the mint's API endpoints. It defines endpoints for creating a new mint, getting a mint by its ID, getting all mints, adding a new transaction to the ledger, getting a transaction by its ID, and getting all transactions.
  7. cashu/mint/startup.py:
    • This file contains startup or initialization logic for the mint. It sets up the database tables and initializes the database session.
From the above analysis, it's evident that the Cashu mint uses the FastAPI framework to set up its API endpoints and handle requests. The mint has CRUD operations to manage mints and transactions, and it uses a database to store this data.

3. Laying the Groundwork

The foundation of any successful integration lies in its initial setup and planning.
  • Initialization:
    • Initializing the CashuMint and CashuWallet was our first step. Using the cashu-ts library, we set up the instances like so:
      $cashuMint = CashuMint::initialize(/* parameters */); $cashuWallet = CashuWallet::initializeForUser(/* user-specific parameters */);
  • Token Generation:
    • Leveraging the cashu-ts library, we crafted a function to generate tokens with zero sats for user authentication:
      function generateCashuToken() { return $cashuWallet->createTokenWithZeroSats(); }
  • Token Storage:
    • Using WordPress's built-in functions, we stored the generated token securely within the user's account:
      function storeUserToken($userId, $token) { update_user_meta($userId, 'cashu_token', $token); }
  • User Interface:
    • We integrated a simple "Login with cashu" button into the WordPress login form, ensuring a seamless user experience:
      function display_cashu_login_button() { include 'templates/login-button.php'; } add_action('login_form', 'display_cashu_login_button');

4. Deep Dive into cashu-ts

A profound understanding of the cashu-ts library was essential for a seamless integration.
  • Repository Exploration:
  • Related Repositories:
  • Function Calls Integration:
    • With insights from the related repositories, we integrated actual function calls from the cashu-ts library:
      $token = $cashuWallet->createToken(/* parameters from NutStash wallet */);

5. Iterative Development

Our development process was iterative, ensuring optimal results at each phase.
  • Coding:
    • With a solid foundation and insights from cashu-ts, we embarked on the coding phase. For instance, to generate a token:
      function generateCashuToken() { return $cashuWallet->createTokenWithZeroSats(); }
  • Review:
    • We undertook a rigorous review process, analyzing the code for efficiency, security, and compatibility, especially with insights from the Cashu mint repository.
  • Refinement:
    • Feedback was incorporated to refine the code. For instance, ensuring token validity:
      if ($cashuMint->isValidToken($token)) { // Proceed with authentication }

6. Community Feedback

To ensure the plugin's success, we shared our progress here and other commuities aiming to receive as many invaluable feedback, and insights to further improve approach and implementation. Join cashu R&D team on Telegram!

Conclusion

This integration of the cashu-ts library into a plugin to enable users to access anonimously any WordPress site was until now a journey filled with meticulous analysis and experimentation and we are now seeking for invaluable community feedback and contributions. By focusing on understanding the library's intricacies and adopting a systematic approach, we were able to create the base for a simple project to exists and seemsly prove cashu protocol capabilities with real use cases. This is one of many more to come.
For developers looking to embark on similar integrations, our journey underscores the importance of thorough research, iterative development, and community collaboration.

References

  1. cashu-ts Repository: Description: The primary library we aimed to integrate into the WordPress plugin.
  2. Cashu Mint Repository: Description: Helped us understand the minting process in detail.
  3. NutStash Wallet: Description: Provided insights into how a wallet works from a user's perspective. Alpha.NutStash.app
  4. cashu Auth WordPress Plugin Repository: The repository you provided for code review and analysis.
  5. WordPress Plugin Handbook: General reference for understanding WordPress plugin development standards and practices.
  6. Satoshi Wiki (Unit): A unit of Bitcoin used to describe smaller amounts, especially useful when discussing token values.
Original source on BOLT🔩FUN
Sweet I can't wait to have our site set up with Login with LN, Login with slashtags, Login with Nostr, Login with Cashu :P Login with BIP322 just give me all the login options
reply