Integration Steps

String Direct SDK for Web Integrations

Here are the steps on how you can integrate String Direct into your game environment. If you haven't gone through the setup steps first, see the Setup steps.

User Creation and Authentication

Now that that the SDK has been initialized, you'll need to connect the user to String prior to initiating a transaction.

Authorizing the User

Call AuthorizeUser() to handle user validating the user's wallet address, and connecting the user to String.

const user = await stringPay.authorizeUser();

Updating User Details

In order to execute transactions on behalf of the user, String will need certain identifying information from the user. Specifically Name and Email. If these have not yet been associated with the user's wallet, you'll need to send this user information to String. You can check the user returned by authorizeUser to see if String requires more information. In order for the card payments to be processed properly, it is important that the information provided by the user be accurate.

Update User Name

If String does not yet have the user's name, you'll need to provide it here. In the example code below, getUserName() is a stand-in for whatever process by which you intend to retrieve the user's name. Once you have the user's name, you can simply pass it through to String with updateUserName().

if (user.firstName == "" || user.lastName == "") {
  // Get user's name through a UI prompt or your database
  const firstName, lastName = getUserName();
  await stringPay.updateUserName(user.id, firstName, lastName);
}

Update User Email

If String does not yet have the user's email, you'll also need to provide it at this point in the flow. Here getUserEmail() is a stand in for your process for gathering the user's email. Once you have the user's email, you can simply pass this to String with the verifyEmail() method. String will send a user to the email to verify that the address is in the user's possession. On subsequent login attempts, if the user has not yet verified their email, you can prompt them to check their email, change the address to send it to, or resend the email.

if (user.status != "email_verified") {
  // If the user has not yet verified their email
  if (user.email == "") {
    // no email is associated with the user
    // get user's email and send verification
    const email = getUserEmail();
    await stringPay.verifyEmail(user.id, email);
  } else {
    // prompt user to check email. allow user to resend or update their email
    if (resend) {
      await stringPay.verifyEmail(user.id, user.email);
    } else if (new_email) {
      await stringPay.verifyEmail(user.id, new_email);
    }
  }
}

Executing a Transaction

Once the user is connected to String and fully verified you can use String to execute a transaction with a card payment.

Define a Payload

The payload defines what action String will take on behalf of the user, for example, minting an NFT. This defines the smart contract to call, as well as all relevant parameters including the name of the asset being purchased. More details on the payload struct can be found in Appendices.

const payload = {
  assetName: "String Test NFT [AVAX]",
  collection: "String Demo",
  price: "0.08",
  currency: "AVAX",
  chainID: 43113,
  userAddress,
  contractAddress: "0xea1ffe2cf6630a20e1ba397e95358daf362c8781",
  contractFunction: "mintTo(address)",
  contractReturn: "uint256",
  contractParameters: [userAddress],
  txValue: `0.08 eth`,
};

Getting Quotes

A quote allows the user to know how much a transaction will cost them. Quotes are valid for 15 seconds before expiring, so they should be regularly created on an interval.

Using the Quote Service

We've provided a quote service that allows you to subscribe to a feed of quotes. It automatically updates on a regular interval so that you don't have to manage the quote exipration. You can create a new quote service by calling subscribeToQuote(). You'll need to define a callback function that handles the quotes provided by the feed.

const cb = (_quote: any) => {
  //
  quote = _quote // assuming _quote is defined elsewhere
};
stringPay.subscribeToQuote(payload, cb);

Manually generating quotes

Alternatively, you can can generate new quotes manually for your payload with the getQuote() function. If you take this approach, be sure to get the quotes regularly enough that you don't inadvertently use a stale quote in a transaction call.

const quote = await stringPay.getQuote(payload);

Display the Quote to users

Each quote should be displayed to the user so they have an understanding of what they will pay for the asset. It includes the total price as well as a breakdown of the components of the price. More information on the quote can be found in Appendices.

Get Card Payment Info

String requires that you gather and provide the user's card payment information in order to execute a transaction. There are two paths the user can take here. They can provide a new card, or, if they've used String before, they can select a saved card payment method.

Use a New Card

You can get new card payment info from the user via the payment iframe. This gathers the users card data in a PCI compliant way without exposing your application to any regulatory burden.

Loading the payment iframe

You can load the payment field iframe by calling stringPay.loadIframe(payload) with a payload object containing the necessary transaction details.

await stringPay.loadIframe(payload);
Customizing payment frame styles (Optional)

Use the setStyle() function if you want to apply specific styles to your iframe. This step is optional. For further details on the setStyle function and the style object structure, please see the Style subsection.

stringPay.setStyle(style);

Creating a payment token

The iframe emits events to convey if the card data provided by the user is valid and sufficient. If so, the data can be submitted. Once the user clicks the button to submit, you can call submitCard() to generate a card token.

stringPay.subscribeTo("card_validation_changed", (data: any) => {
  if (data.isValid) {
    // set card submit button to active
  } else {
    // set card submit button to inactive
  }
});

// on card submit button click
const token = await stringPay.submitCard();

Getting card save preferences

You should provide a means in your UI for the user to express their desire for the card payment method to be saved for future use or not. This preference will be passed as part of the transaction payload.

Create Saved Payment variable

Once you've created a new card token and gathered the user's card save preference you can create a PaymentInfo object to be passed into the transaction payload later.

const paymentInfo = {
    cardToken: token,
    saveCard: savePreference,
};

Use a Saved Card

If the user has previously saved a card with String, they can use that payment option again without providing their whole card number. In order to use a saved card payment, you'll need to gather all saved cards, have the user select one, and provide the CVV for that card. Both the card ID and the CVV can then be provided as part of the transaction payload.

Gathering Saved Payment Info

You can get the user's saved payments using the getSavedPayments() function. This function returns a SavedCardResponse array. This data can be used to display to the user so that they can select which saved payment that they would like to use.

const cards = await stringPay.getSavedCards()

Create Saved Payment variable

Once you've selected a previously saved card and gathered that card's CVV you can create a PaymentInfo object to be passed into the transaction payload later.

const paymentInfo = {
    cardId: cardId,
    cvv: cvv,
};

Transacting

Once you have an up-to-date quote and the user's card payment information, you can execute a transaction with the submitTransaction() function. This function returns a TransactionResponse object, which includes a block explorer link to the executed transaction which you can display to the user for their verification. The transaction will execute the smart contract call and charge the user's provided card.

const tx = await stringPay.submitTransaction({
  quote,
  paymentInfo
});

Unsubscribe from the Quote service

Once the transaction has been executed or if the user abandons the transaction, you should unsubscribe from the quote service with unsubscribeFromQuote().

stringPay.unsubscribeFromQuote(cb);