✅ [BORA Network] Connect

1440

When your Dapp is served in BORA network, you should add a step named "BORA Connect" after login. When an user uses Dapp with Face Wallet, it is necessary to "connect" only for the first time. "BORA Connect" sends a signed message to BORA for mapping BORA user to Dapp.


IsConnected

You can know whether an user needs "Connect" or not by using IsConnected method. You can get walletAddressHash, boraPortalUsn from the response and use the values to call BoraPortal API.

public async void IsBoraConnected()
{
  ...
  string bappUsn = "YOUR_BAPP_USN";
  BoraPortalConnectStatusResponse statusResponse = await this.face.Bora().IsConnected(bappUsn);
  if(statusResponse.status == BoraPortalConnectStatusEnum.Unconnected) {
    // Do something if unconnected
  }
  Debug.Log($"BoraPortalUsn: {statusResponse.BoraPortalUsn}");
  Debug.Log($"WalletAddressHash: {statusResponse.WalletAddressHash}");
  ...
}

Connect

After the user login to Face Wallet, you should call Connect if it is the first time for the user to use the Dapp. Connect makes the user to sign a message. The signed message would be sent to BORA.

public async void Connect()
{
  ...
  string bappUsn = "YOUR_BAPP_USN";
  string signature = "YOUR_SIGNATURE_SIGNED_BY_API_SECRET";
  BoraPortalConnectRequest request = new BoraPortalConnectRequest(
    bappUsn,
    signature);
  FaceRpcResponse rseponse = await this.face.Bora().Connect(request);
  BoraPortalConnectStatusResponse statusResponse = response.CastResult<BoraPortalConnectStatusResponse>();
  Debug.Log($"BoraPortalUsn: {statusResponse.BoraPortalUsn}");
  Debug.Log($"WalletAddressHash: {statusResponse.WalletAddressHash}");
  ...
}

How to make Signature using API Secret

You can make a Signature using Face Wallet SDK API Secret.

  1. Convert your API Secret to PEM format.
  2. Create an instance of RSACryptoServiceProvider using the PEM key generated in step 1.
  3. To sign data, we need to create a message by concatenating the values of bappUsn and walletAddress and converting it to a byte array. You can obtain the walletAddress value from the Face Wallet login response.
  4. Finally, sign the message using the RSACryptoServiceProvider.SignData method with the "SHA256" algorithm, and encode the resulting signature in Base64 format.
using System.IO;
using System.Security.Cryptography;
using System.Text;
using System.Text.RegularExpressions;
using Org.BouncyCastle.Crypto;
using Org.BouncyCastle.Crypto.Parameters;
using Org.BouncyCastle.OpenSsl;
using Org.BouncyCastle.Security;

// Define Class, and put below static methods in that.
...
  
public static string CreateSignatureForBoraConnect(string apiSecret, string bappUsn, string walletAddress) {
  try
  {
    string pem = KeyToPem(apiSecret);
    RSACryptoServiceProvider rsaPrivateKey = ImportPrivateKey(pem);
    string signatureMessage = $"{bappUsn}:{walletAddress}";
    byte[] bytesPlainTextData = Encoding.UTF8.GetBytes(signatureMessage);
    byte[] signedData = rsaPrivateKey.SignData(bytesPlainTextData, "SHA256");

    return Convert.ToBase64String(signedData);
  }
  catch (Exception e)
  {
    Debug.Log($"{e.Message}:\n{e.StackTrace}");
    return null;
  }
}

private static string KeyToPem(string key)
{
  key = key.Replace('-', '+').Replace('_', '/')
  key = Regex.Replace(key, @"(\S{64}(?!$))", "$1\n");
  StringBuilder sb = new StringBuilder();
  sb.AppendLine($"-----BEGIN PRIVATE KEY-----");
  foreach (var line in key.Split("\n"))
  {
    sb.AppendLine(line);
  }

  sb.AppendLine($"-----END PRIVATE KEY-----");
  return sb.ToString();
}

private static RSACryptoServiceProvider ImportPrivateKey(string pem) {
  PemReader pr = new PemReader(new StringReader(pem));
  RsaPrivateCrtKeyParameters key = (RsaPrivateCrtKeyParameters)pr.ReadObject();
  RSAParameters rsaParams = DotNetUtilities.ToRSAParameters(key);

  RSACryptoServiceProvider rsaPrivateKey = new RSACryptoServiceProvider();
  rsaPrivateKey.ImportParameters(rsaParams);
  return rsaPrivateKey;
}

...

👍

How can I get my API Secret?

Please contact and request API Secret to Face Wallet Team.

❗️

API Secret should be careful not to leak outside. Also, a signature should be created in your backend, not frontend.

🚧

If a user without the BORA Connect attempts to perform a BORA-related function, a 4xx error occurs.