diff --git a/dev/local/docker-compose.yml b/dev/local/docker-compose.yml
index 9418154ba..da60baac1 100644
--- a/dev/local/docker-compose.yml
+++ b/dev/local/docker-compose.yml
@@ -22,6 +22,16 @@ services:
validation:
image: ghcr.io/xmtp/mls-validation-service:main
platform: linux/amd64
+ environment:
+ ANVIL_URL: "http://anvil:8545"
+
+ anvil:
+ image: ghcr.io/foundry-rs/foundry
+ platform: linux/amd64
+ entrypoint: ["anvil", "--host", "0.0.0.0"]
+ working_dir: /anvil
+ ports:
+ - 8545:8545
db:
image: postgres:13
diff --git a/library/build.gradle b/library/build.gradle
index a7c2573c3..886ffba89 100644
--- a/library/build.gradle
+++ b/library/build.gradle
@@ -86,16 +86,18 @@ dependencies {
implementation 'io.grpc:grpc-okhttp:1.62.2'
implementation 'io.grpc:grpc-protobuf-lite:1.62.2'
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-core:1.8.0'
- implementation 'org.web3j:crypto:5.0.0'
+ implementation 'org.web3j:crypto:4.9.4'
implementation "net.java.dev.jna:jna:5.14.0@aar"
api 'com.google.protobuf:protobuf-kotlin-lite:3.22.3'
- api 'org.xmtp:proto-kotlin:3.62.1'
+ api 'org.xmtp:proto-kotlin:3.71.0'
testImplementation 'junit:junit:4.13.2'
androidTestImplementation 'app.cash.turbine:turbine:1.1.0'
androidTestImplementation 'org.jetbrains.kotlinx:kotlinx-coroutines-test:1.8.0'
androidTestImplementation 'androidx.test.ext:junit:1.1.5'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.5.1'
+ androidTestImplementation 'org.web3j:core:4.9.4'
+ androidTestImplementation 'org.web3j:contracts:4.9.4'
}
afterEvaluate {
diff --git a/library/src/androidTest/AndroidManifest.xml b/library/src/androidTest/AndroidManifest.xml
new file mode 100644
index 000000000..d3204757e
--- /dev/null
+++ b/library/src/androidTest/AndroidManifest.xml
@@ -0,0 +1,5 @@
+
+
+
+
diff --git a/library/src/androidTest/java/org/xmtp/android/library/ClientTest.kt b/library/src/androidTest/java/org/xmtp/android/library/ClientTest.kt
index a1c7655f6..7696b4d92 100644
--- a/library/src/androidTest/java/org/xmtp/android/library/ClientTest.kt
+++ b/library/src/androidTest/java/org/xmtp/android/library/ClientTest.kt
@@ -159,7 +159,7 @@ class ClientTest {
)
val inboxId = runBlocking { Client.getOrCreateInboxId(options, fakeWallet.address) }
val client = runBlocking {
- Client().createOrBuild(
+ Client().createV3(
account = fakeWallet,
options = options
)
@@ -169,6 +169,18 @@ class ClientTest {
}
assert(client.installationId.isNotEmpty())
assertEquals(inboxId, client.inboxId)
+
+ val sameClient = runBlocking {
+ Client().buildV3(
+ address = fakeWallet.address,
+ options = options
+ )
+ }
+ runBlocking {
+ client.canMessageV3(listOf(sameClient.address))[sameClient.address]?.let { assert(it) }
+ }
+ assert(sameClient.installationId.isNotEmpty())
+ assertEquals(client.inboxId, sameClient.inboxId)
}
@Test
diff --git a/library/src/androidTest/java/org/xmtp/android/library/SmartContractWalletTest.kt b/library/src/androidTest/java/org/xmtp/android/library/SmartContractWalletTest.kt
new file mode 100644
index 000000000..a65d38108
--- /dev/null
+++ b/library/src/androidTest/java/org/xmtp/android/library/SmartContractWalletTest.kt
@@ -0,0 +1,44 @@
+package org.xmtp.android.library
+
+import androidx.test.ext.junit.runners.AndroidJUnit4
+import androidx.test.platform.app.InstrumentationRegistry
+import kotlinx.coroutines.runBlocking
+import org.junit.Assert.assertEquals
+import org.junit.Test
+import org.junit.runner.RunWith
+
+@RunWith(AndroidJUnit4::class)
+class SmartContractWalletTest {
+ @Test
+ fun testCanCreateASCW() {
+ val key = byteArrayOf(
+ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
+ 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
+ 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
+ 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F
+ )
+ val context = InstrumentationRegistry.getInstrumentation().targetContext
+ val davonSCW = FakeSCWWallet.generate()
+ val options = ClientOptions(
+ ClientOptions.Api(XMTPEnvironment.LOCAL, false),
+ enableV3 = true,
+ appContext = context,
+ dbEncryptionKey = key
+ )
+ val davonSCWClient = runBlocking {
+ Client().createV3(
+ account = davonSCW,
+ options = options
+ )
+ }
+ val davonSCWClient2 = runBlocking {
+ Client().buildV3(
+ address = davonSCW.address,
+ chainId = davonSCW.chainId,
+ options = options
+ )
+ }
+
+ assertEquals(davonSCWClient.inboxId, davonSCWClient2.inboxId)
+ }
+}
diff --git a/library/src/androidTest/java/org/xmtp/android/library/TestHelpers.kt b/library/src/androidTest/java/org/xmtp/android/library/TestHelpers.kt
index 2542e543a..b9915d0a8 100644
--- a/library/src/androidTest/java/org/xmtp/android/library/TestHelpers.kt
+++ b/library/src/androidTest/java/org/xmtp/android/library/TestHelpers.kt
@@ -1,14 +1,27 @@
package org.xmtp.android.library
import kotlinx.coroutines.runBlocking
+import org.web3j.abi.FunctionEncoder
+import org.web3j.abi.datatypes.DynamicBytes
+import org.web3j.abi.datatypes.Uint
+import org.web3j.crypto.Credentials
+import org.web3j.crypto.Sign
+import org.web3j.protocol.Web3j
+import org.web3j.protocol.http.HttpService
+import org.web3j.tx.gas.DefaultGasProvider
+import org.web3j.utils.Numeric
+import org.xmtp.android.library.artifact.CoinbaseSmartWallet
+import org.xmtp.android.library.artifact.CoinbaseSmartWalletFactory
import org.xmtp.android.library.messages.ContactBundle
import org.xmtp.android.library.messages.Envelope
import org.xmtp.android.library.messages.PrivateKey
import org.xmtp.android.library.messages.PrivateKeyBuilder
import org.xmtp.android.library.messages.Signature
import org.xmtp.android.library.messages.Topic
+import org.xmtp.android.library.messages.ethHash
import org.xmtp.android.library.messages.toPublicKeyBundle
import org.xmtp.android.library.messages.walletAddress
+import java.math.BigInteger
import java.util.Date
class FakeWallet : SigningKey {
@@ -41,6 +54,87 @@ class FakeWallet : SigningKey {
get() = privateKey.walletAddress
}
+private const val ANVIL_TEST_PRIVATE_KEY =
+ "ac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80"
+private const val ANVIL_TEST_PORT = "http://10.0.2.2:8545"
+
+class FakeSCWWallet : SigningKey {
+ private var web3j: Web3j = Web3j.build(HttpService(ANVIL_TEST_PORT))
+ private val contractDeployerCredentials: Credentials =
+ Credentials.create(ANVIL_TEST_PRIVATE_KEY)
+ var walletAddress: String = ""
+
+ override val address: String
+ get() = walletAddress
+
+ override val type: WalletType
+ get() = WalletType.SCW
+
+ override var chainId: Long? = 31337L
+
+ companion object {
+ fun generate(): FakeSCWWallet {
+ return FakeSCWWallet().apply {
+ createSmartContractWallet()
+ }
+ }
+ }
+
+ override suspend fun signSCW(message: String): ByteArray {
+ val smartWallet = CoinbaseSmartWallet.load(
+ walletAddress,
+ web3j,
+ contractDeployerCredentials,
+ DefaultGasProvider()
+ )
+ val digest = Signature.newBuilder().build().ethHash(message)
+ val replaySafeHash = smartWallet.replaySafeHash(digest).send()
+
+ val signature =
+ Sign.signMessage(replaySafeHash, contractDeployerCredentials.ecKeyPair, false)
+ val signatureBytes = signature.r + signature.s + signature.v
+ val tokens = listOf(
+ Uint(BigInteger.ZERO),
+ DynamicBytes(signatureBytes)
+ )
+ val encoded = FunctionEncoder.encodeConstructor(tokens)
+ val encodedBytes = Numeric.hexStringToByteArray(encoded)
+
+ return encodedBytes
+ }
+
+ private fun createSmartContractWallet() {
+ val smartWalletContract = CoinbaseSmartWallet.deploy(
+ web3j,
+ contractDeployerCredentials,
+ DefaultGasProvider()
+ ).send()
+
+ val factory = CoinbaseSmartWalletFactory.deploy(
+ web3j,
+ contractDeployerCredentials,
+ DefaultGasProvider(),
+ BigInteger.ZERO,
+ smartWalletContract.contractAddress
+ ).send()
+
+ val ownerAddress = ByteArray(32) { 0 }.apply {
+ System.arraycopy(contractDeployerCredentials.address.hexToByteArray(), 0, this, 12, 20)
+ }
+ val owners = listOf(ownerAddress)
+ val nonce = BigInteger.ZERO
+
+ val transactionReceipt = factory.createAccount(owners, nonce, BigInteger.ZERO).send()
+ val smartWalletAddress = factory.getAddress(owners, nonce).send()
+
+ if (transactionReceipt.isStatusOK) {
+ walletAddress = smartWalletAddress
+ } else {
+ throw Exception("Transaction failed: ${transactionReceipt.status}")
+ }
+ }
+}
+
data class Fixtures(
val clientOptions: ClientOptions? = ClientOptions(
ClientOptions.Api(XMTPEnvironment.LOCAL, isSecure = false)
diff --git a/library/src/androidTest/java/org/xmtp/android/library/V3ClientTest.kt b/library/src/androidTest/java/org/xmtp/android/library/V3ClientTest.kt
index f260d4968..a30d9751e 100644
--- a/library/src/androidTest/java/org/xmtp/android/library/V3ClientTest.kt
+++ b/library/src/androidTest/java/org/xmtp/android/library/V3ClientTest.kt
@@ -50,7 +50,7 @@ class V3ClientTest {
boV3Wallet = PrivateKeyBuilder()
boV3 = boV3Wallet.getPrivateKey()
boV3Client = runBlocking {
- Client().createOrBuild(
+ Client().createV3(
account = boV3Wallet,
options = ClientOptions(
ClientOptions.Api(XMTPEnvironment.LOCAL, false),
diff --git a/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWallet.java b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWallet.java
new file mode 100644
index 000000000..6a58dcd40
--- /dev/null
+++ b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWallet.java
@@ -0,0 +1,634 @@
+package org.xmtp.android.library.artifact;
+
+import io.reactivex.Flowable;
+
+import java.math.BigInteger;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
+import java.util.concurrent.Callable;
+
+import org.web3j.abi.EventEncoder;
+import org.web3j.abi.TypeReference;
+import org.web3j.abi.datatypes.Address;
+import org.web3j.abi.datatypes.Bool;
+import org.web3j.abi.datatypes.DynamicArray;
+import org.web3j.abi.datatypes.DynamicBytes;
+import org.web3j.abi.datatypes.DynamicStruct;
+import org.web3j.abi.datatypes.Event;
+import org.web3j.abi.datatypes.Function;
+import org.web3j.abi.datatypes.Type;
+import org.web3j.abi.datatypes.Utf8String;
+import org.web3j.abi.datatypes.generated.Bytes1;
+import org.web3j.abi.datatypes.generated.Bytes32;
+import org.web3j.abi.datatypes.generated.Bytes4;
+import org.web3j.abi.datatypes.generated.Uint256;
+import org.web3j.crypto.Credentials;
+import org.web3j.protocol.Web3j;
+import org.web3j.protocol.core.DefaultBlockParameter;
+import org.web3j.protocol.core.RemoteCall;
+import org.web3j.protocol.core.RemoteFunctionCall;
+import org.web3j.protocol.core.methods.request.EthFilter;
+import org.web3j.protocol.core.methods.response.BaseEventResponse;
+import org.web3j.protocol.core.methods.response.Log;
+import org.web3j.protocol.core.methods.response.TransactionReceipt;
+import org.web3j.tuples.generated.Tuple7;
+import org.web3j.tx.Contract;
+import org.web3j.tx.TransactionManager;
+import org.web3j.tx.gas.ContractGasProvider;
+
+/**
+ *
Auto generated code.
+ *
Do not modify!
+ *
Please use the web3j command line tools,
+ * or the org.web3j.codegen.SolidityFunctionWrapperGenerator in the
+ * codegen module to update.
+ *
+ *
Generated with web3j version 1.6.1.
+ */
+@SuppressWarnings("rawtypes")
+public class CoinbaseSmartWallet extends Contract {
+ public static final String BINARY = "0x60a0604052306080523480156200001557600080fd5b50604080516001808252818301909252600091816020015b60608152602001906001900390816200002d57905050604080516000602082015291925001604051602081830303815290604052816000815181106200007757620000776200037a565b60209081029190910101526200008d8162000094565b50620005b0565b60005b81518110156200022657818181518110620000b657620000b66200037a565b602002602001015151602014158015620000ee5750818181518110620000e057620000e06200037a565b602002602001015151604014155b1562000136578181815181106200010957620001096200037a565b60200260200101516040516327755b9160e11b81526004016200012d9190620003b6565b60405180910390fd5b8181815181106200014b576200014b6200037a565b60200260200101515160201480156200019357506001600160a01b0380168282815181106200017e576200017e6200037a565b60200260200101516200019190620003eb565b115b15620001d257818181518110620001ae57620001ae6200037a565b602002602001015160405163bff1ac6560e01b81526004016200012d9190620003b6565b6200021d828281518110620001eb57620001eb6200037a565b6020026020010151620002036200022a60201b60201c565b8054906000620002138362000413565b909155506200023d565b60010162000097565b5050565b6000805160206200383783398151915290565b620002488262000326565b156200026b578160405163468b12ad60e11b81526004016200012d9190620003b6565b600160008051602062003837833981519152600201836040516200029091906200043b565b908152604051908190036020019020805491151560ff1990921691909117905581620002c86000805160206200383783398151915290565b60008381526001919091016020526040902090620002e79082620004e4565b50807f38109edc26e166b5579352ce56a50813177eb25208fd90d61f2f378386220220836040516200031a9190620003b6565b60405180910390a25050565b600060008051602062003837833981519152600201826040516200034b91906200043b565b9081526040519081900360200190205460ff1692915050565b634e487b7160e01b600052604160045260246000fd5b634e487b7160e01b600052603260045260246000fd5b60005b83811015620003ad57818101518382015260200162000393565b50506000910152565b6020815260008251806020840152620003d781604085016020870162000390565b601f01601f19169190910160400192915050565b805160208083015191908110156200040d576000198160200360031b1b821691505b50919050565b6000600182016200043457634e487b7160e01b600052601160045260246000fd5b5060010190565b600082516200044f81846020870162000390565b9190910192915050565b600181811c908216806200046e57607f821691505b6020821081036200040d57634e487b7160e01b600052602260045260246000fd5b601f821115620004df576000816000526020600020601f850160051c81016020861015620004ba5750805b601f850160051c820191505b81811015620004db57828155600101620004c6565b5050505b505050565b81516001600160401b0381111562000500576200050062000364565b620005188162000511845462000459565b846200048f565b602080601f831160018114620005505760008415620005375750858301515b600019600386901b1c1916600185901b178555620004db565b600085815260208120601f198616915b82811015620005815788860151825594840194600190910190840162000560565b5085821015620005a05787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b608051613264620005d36000396000818161081e015261095501526132646000f3fe60806040526004361061014f5760003560e01c806372de3b5a116100b6578063b0d691fe1161006f578063b0d691fe146103f4578063b61d27f61461041b578063bf6ba1fc1461042e578063ce1506be14610441578063d948fd2e14610461578063f698da251461048357610156565b806372de3b5a1461032957806384b0196e1461034957806388ce4c7c146103715780638ea69029146103875780639f9bcb34146103b4578063a2e1a8d8146103d457610156565b80633a871cdd116101085780633a871cdd146102655780634f1ef286146102865780634f6e7f221461029957806352d1902d146102b95780635c60da1b146102ce5780636f2de70e1461031657610156565b8063066a1eb7146101845780630f0f3f24146101b95780631626ba7e146101d95780631ca5393f1461021257806329565e3b1461023257806334fcd5be1461025257610156565b3661015657005b60003560e01c63bc197c81811463f23a6e6182141763150b7a028214171561018257806020526020603cf35b005b34801561019057600080fd5b506101a461019f366004612769565b610498565b60405190151581526020015b60405180910390f35b3480156101c557600080fd5b506101826101d43660046127a7565b610507565b3480156101e557600080fd5b506101f96101f436600461280a565b61053f565b6040516001600160e01b031990911681526020016101b0565b34801561021e57600080fd5b506101a461022d366004612940565b610579565b34801561023e57600080fd5b5061018261024d366004612769565b6105b4565b6101826102603660046129b8565b6105dd565b610278610273366004612a12565b6106e1565b6040519081526020016101b0565b610182610294366004612a5f565b61081c565b3480156102a557600080fd5b506102786102b4366004612a98565b610900565b3480156102c557600080fd5b50610278610951565b3480156102da57600080fd5b507f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc545b6040516001600160a01b0390911681526020016101b0565b6101826103243660046129b8565b6109b1565b34801561033557600080fd5b50610182610344366004612acc565b6109f1565b34801561035557600080fd5b5061035e610ade565b6040516101b09796959493929190612b35565b34801561037d57600080fd5b5061027861210581565b34801561039357600080fd5b506103a76103a2366004612acc565b610b05565b6040516101b09190612bce565b3480156103c057600080fd5b506101a46103cf366004612be1565b610bc6565b3480156103e057600080fd5b506101a46103ef3660046127a7565b610c42565b34801561040057600080fd5b50735ff137d4b0fdcd49dca30c7cf57e578a026d27896102fe565b610182610429366004612c0b565b610c88565b61018261043c366004612c64565b610cec565b34801561044d57600080fd5b5061027861045c366004612acc565b610dad565b34801561046d57600080fd5b5060008051602061320f83398151915254610278565b34801561048f57600080fd5b50610278610db8565b60408051602081018490529081018290526000907f97e2c6aad4ce5d562ebfaa00db6b9e0fb66ea5d8162ed5b243f51a2e03086f029060600160408051601f19818403018152908290526104eb91612c99565b9081526040519081900360200190205460ff1690505b92915050565b61050f610e3e565b604080516001600160a01b038316602082015261053c91015b604051602081830303815290604052610e70565b50565b600061055461054d85610dad565b8484610e9b565b156105675750630b135d3f60e11b610572565b506001600160e01b03195b9392505050565b600060008051602061320f8339815191526002018260405161059b9190612c99565b9081526040519081900360200190205460ff1692915050565b6105bc610e3e565b60408051602081018490529081018290526105d990606001610528565b5050565b33735ff137d4b0fdcd49dca30c7cf57e578a026d27891461060057610600610e3e565b60005b818110156106dc576106d483838381811061062057610620612cb5565b90506020028101906106329190612ccb565b6106409060208101906127a7565b84848481811061065257610652612cb5565b90506020028101906106649190612ccb565b6020013585858581811061067a5761067a612cb5565b905060200281019061068c9190612ccb565b61069a906040810190612ce1565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250610fb092505050565b600101610603565b505050565b600033735ff137d4b0fdcd49dca30c7cf57e578a026d278914610716576040516282b42960e81b815260040160405180910390fd5b81602085013560401c600461072e6060880188612ce1565b90501015801561077257506107466060870187612ce1565b61075591600491600091612d27565b61075e91612d51565b6001600160e01b03191663bf6ba1fc60e01b145b156107b15761078086610900565b945061210581146107ac57604051632ef3781360e01b8152600481018290526024015b60405180910390fd5b6107d6565b61210581036107d657604051632ef3781360e01b8152600481018290526024016107a3565b6107ed856107e8610140890189612ce1565b610e9b565b156107fc576000925050610802565b60019250505b80156108145760003860003884335af1505b509392505050565b7f000000000000000000000000000000000000000000000000000000000000000030810361085257639f03a0266000526004601cfd5b61085b84611020565b8360601b60601c93506352d1902d6001527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc80602060016004601d895afa51146108ad576355299b496001526004601dfd5b847fbc7cd75a20ee27fd9adebab32041f755214dbc6bffa90cc0225b39da2e5c2d3b600038a284905581156108fa57604051828482376000388483885af46108f8573d6000823e3d81fd5b505b50505050565b600061090b82611028565b604080516020810192909252735ff137d4b0fdcd49dca30c7cf57e578a026d2789908201526060015b604051602081830303815290604052805190602001209050919050565b60007f000000000000000000000000000000000000000000000000000000000000000030811461098957639f03a0266000526004601cfd5b7f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc91505b5090565b60008051602061320f83398151915254156109df576040516302ed543d60e51b815260040160405180910390fd5b6105d96109ec8284612d81565b611041565b6109f9610e3e565b6000610a0482610b05565b90508051600003610a2b5760405163340c473d60e11b8152600481018390526024016107a3565b6040517f97e2c6aad4ce5d562ebfaa00db6b9e0fb66ea5d8162ed5b243f51a2e03086f0290610a5b908390612c99565b908152604051908190036020019020805460ff19169055610a8760008051602061320f83398151915290565b600083815260019190910160205260408120610aa29161271f565b817fcf95bbfe6f870f8cc40482dc3dccdafd268f0e9ce0a4f24ea1bea9be64e505ff82604051610ad29190612bce565b60405180910390a25050565b600f60f81b6060806000808083610af3611193565b97989097965046955030945091925090565b60008181527f97e2c6aad4ce5d562ebfaa00db6b9e0fb66ea5d8162ed5b243f51a2e03086f0160205260409020805460609190610b4190612e06565b80601f0160208091040260200160405190810160405280929190818152602001828054610b6d90612e06565b8015610bba5780601f10610b8f57610100808354040283529160200191610bba565b820191906000526020600020905b815481529060010190602001808311610b9d57829003601f168201915b50505050509050919050565b60006001600160e01b031982166329565e3b60e01b1480610bf757506001600160e01b031982166303c3cfc960e21b145b80610c1257506001600160e01b0319821663396f1dad60e11b145b80610c2d57506001600160e01b0319821663278f794360e11b145b15610c3a57506001919050565b506000919050565b600060008051602061320f833981519152604080516001600160a01b0385166020820152600292909201910160408051601f198184030181529082905261059b91612c99565b33735ff137d4b0fdcd49dca30c7cf57e578a026d278914610cab57610cab610e3e565b6108fa848484848080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250610fb092505050565b33735ff137d4b0fdcd49dca30c7cf57e578a026d278914610d1f576040516282b42960e81b815260040160405180910390fd5b6000610d2e6004828486612d27565b610d3791612d51565b9050610d4281610bc6565b610d6b57604051631d8370a360e11b81526001600160e01b0319821660048201526024016107a3565b6106dc30600085858080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250610fb092505050565b6000610501826111da565b6000806000610dc5611193565b8151602080840191909120825182840120604080517f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f9481019490945283019190915260608201524660808201523060a0820152919350915060c001604051602081830303815290604052805190602001209250505090565b610e4733610c42565b80610e5157503330145b15610e5857565b6040516282b42960e81b815260040160405180910390fd5b61053c8160008051602061320f8339815191525b8054906000610e9283612e50565b91905055611210565b600080610eaa83850185612e69565b90506000610ebb8260000151610b05565b90508051602003610f1a576001600160a01b03610ed782612ef5565b1115610ef8578060405163bff1ac6560e01b81526004016107a39190612bce565b600060208201519050610f10818885602001516112df565b9350505050610572565b8051604003610f955760008082806020019051810190610f3a9190612f19565b9150915060008460200151806020019051810190610f589190612f82565b9050610f8989604051602001610f7091815260200190565b60405160208183030381529060405260008386866113e4565b95505050505050610572565b806040516327755b9160e11b81526004016107a39190612bce565b600080846001600160a01b03168484604051610fcc9190612c99565b60006040518083038185875af1925050503d8060008114611009576040519150601f19603f3d011682016040523d82523d6000602084013e61100e565b606091505b5091509150816108f857805160208201fd5b61053c610e3e565b600061103382611754565b805190602001209050919050565b60005b81518110156105d95781818151811061105f5761105f612cb5565b602002602001015151602014158015611093575081818151811061108557611085612cb5565b602002602001015151604014155b156110cc578181815181106110aa576110aa612cb5565b60200260200101516040516327755b9160e11b81526004016107a39190612bce565b8181815181106110de576110de612cb5565b602002602001015151602014801561112057506001600160a01b03801682828151811061110d5761110d612cb5565b602002602001015161111e90612ef5565b115b156111595781818151811061113757611137612cb5565b602002602001015160405163bff1ac6560e01b81526004016107a39190612bce565b61118b82828151811061116e5761116e612cb5565b6020026020010151610e8460008051602061320f83398151915290565b600101611044565b604080518082018252601581527410dbda5b98985cd94814db585c9d0815d85b1b195d605a1b602080830191909152825180840190935260018352603160f81b9083015291565b60006111e4610db8565b6111ed83611827565b60405161190160f01b602082015260228101929092526042820152606201610934565b61121982610579565b15611239578160405163468b12ad60e11b81526004016107a39190612bce565b600160008051602061320f8339815191526002018360405161125b9190612c99565b908152604051908190036020019020805491151560ff199092169190911790558161129160008051602061320f83398151915290565b600083815260019190910160205260409020906112ae908261308d565b50807f38109edc26e166b5579352ce56a50813177eb25208fd90d61f2f37838622022083604051610ad29190612bce565b6001600160a01b03909216916000831561057257604051836000526020830151604052604083510361134f576040830151601b8160ff1c016020528060011b60011c60605250602060016080600060015afa805186183d151761134d57506000606052604052506001610572565b505b604183510361139557606083015160001a6020526040830151606052602060016080600060015afa805186183d151761139357506000606052604052506001610572565b505b600060605280604052631626ba7e60e01b808252846004830152602482016040815284516020018060448501828860045afa505060208160443d01858a5afa9051909114169150509392505050565b60007f7fffffff800000007fffffffffffffffde737d56d38bcf4279dce5617e3192a88460a00151111561141a5750600061174b565b606084015160009061143d9061143181601561314c565b60208801519190611862565b90507fff1a2a9176d650e4a99dedb58f1793003935130579fe17b5a3f698ac5b00e63481805190602001201461147757600091505061174b565b6000611485886001806118c8565b604051602001611495919061315f565b604051602081830303815290604052905060006114cd8760400151835189604001516114c1919061314c565b60208a01519190611862565b905081805190602001208180519060200120146114f0576000935050505061174b565b86518051600160f81b918291602090811061150d5761150d612cb5565b0160200151166001600160f81b0319161461152e576000935050505061174b565b878015611566575086518051600160fa1b918291602090811061155357611553612cb5565b0160200151166001600160f81b03191614155b15611577576000935050505061174b565b60006002886020015160405161158d9190612c99565b602060405180830381855afa1580156115aa573d6000803e3d6000fd5b5050506040513d601f19601f820116820180604052508101906115cd91906131a0565b9050600060028960000151836040516020016115ea9291906131b9565b60408051601f198184030181529082905261160491612c99565b602060405180830381855afa158015611621573d6000803e3d6000fd5b5050506040513d601f19601f8201168201806040525081019061164491906131a0565b6080808b015160a0808d015160408051602081018790529081019390935260608301529181018b905290810189905290915060009060c00160405160208183030381529060405290506000806101006001600160a01b0316836040516116aa9190612c99565b600060405180830381855afa9150503d80600081146116e5576040519150601f19603f3d011682016040523d82523d6000602084013e6116ea565b606091505b508051919350915015158280156116fe5750805b1561172a578180602001905181019061171791906131a0565b600114995050505050505050505061174b565b61173f858e608001518f60a001518f8f6119bd565b99505050505050505050505b95945050505050565b606081356020830135600061177461176f6040870187612ce1565b611aa0565b9050600061178861176f6060880188612ce1565b9050608086013560a087013560c088013560e08901356101008a013560006117b761176f6101208e018e612ce1565b604080516001600160a01b039c909c1660208d01528b81019a909a5260608b019890985250608089019590955260a088019390935260c087019190915260e08601526101008501526101208401526101408084019190915281518084039091018152610160909201905292915050565b604080517f9b493d222105fee7df163ab5d57f0bf1ffd2da04dd5fafbe10b54c41c1adc6576020820152908101829052600090606001610934565b60608351828111611871578092505b83811161187c578093505b5081831015610572575060405182820380825293830193601f19601f820181165b868101518482015281018061189d5750600083830160200152603f9091011681016040529392505050565b606083518015610814576003600282010460021b60405192507f4142434445464748494a4b4c4d4e4f505152535455565758595a616263646566601f526106708515027f6768696a6b6c6d6e6f707172737475767778797a303132333435363738392d5f18603f52602083018181018388602001018051600082525b60038a0199508951603f8160121c1651600053603f81600c1c1651600153603f8160061c1651600253603f811651600353506000518452600484019350828410611944579052602001604052613d3d60f01b60038406600204808303919091526000861515909102918290035290038252509392505050565b60008415806119da57506000805160206131ef8339815191528510155b806119e3575083155b806119fc57506000805160206131ef8339815191528410155b15611a095750600061174b565b611a138383611ab3565b611a1f5750600061174b565b6000611a2a85611bad565b905060006000805160206131ef833981519152828909905060006000805160206131ef83398151915283890990506000611a6687878585611c1f565b90506000805160206131ef833981519152611a8f8a6000805160206131ef8339815191526131db565b8208159a9950505050505050505050565b6000604051828085833790209392505050565b600082158015611ac1575081155b80611ad95750600160601b63ffffffff60c01b031983145b80611af15750600160601b63ffffffff60c01b031982145b15611afe57506000610501565b6000600160601b63ffffffff60c01b031983840990506000600160601b63ffffffff60c01b0319807fffffffff00000001000000000000000000000000fffffffffffffffffffffffc8709600160601b63ffffffff60c01b031987600160601b63ffffffff60c01b0319898a0909089050600160601b63ffffffff60c01b03197f5ac635d8aa3a93e7b3ebbd55769886bc651d06b0cc53b0f63bce3c3e27d2604b820891909114949350505050565b600060405160208152602080820152602060408201528260608201527fffffffff00000000ffffffffffffffffbce6faada7179e84f3b9cac2fc63254f60808201526000805160206131ef83398151915260a082015260208160c0836005600019fa611c1857600080fd5b5192915050565b600080808060ff818088158015611c34575087155b15611c4857600096505050505050506122e1565b611c947f6b17d1f2e12c4247f8bce6e563a440f277037d812deb33a0f4a13945d898c2967f4fe342e2fe1a7f9b8ee7eb4a7c0f9e162bce33576b315ececbb6406837bf51f58d8d6122e9565b909250905081158015611ca5575080155b15611cd3576000805160206131ef833981519152886000805160206131ef833981519152038a089850600097505b600189841c16600189851c1660011b015b80611d065760018403935060018a851c1660018a861c1660011b019050611ce4565b50600189841c16600189851c1660011b01955060018603611d68577f6b17d1f2e12c4247f8bce6e563a440f277037d812deb33a0f4a13945d898c29696507f4fe342e2fe1a7f9b8ee7eb4a7c0f9e162bce33576b315ececbb6406837bf51f593505b60028603611d77578a96508993505b60038603611d86578196508093505b60018303925060019550600194505b82600019111561226a57600160601b63ffffffff60c01b031984600209600160601b63ffffffff60c01b0319818209600160601b63ffffffff60c01b0319818a09600160601b63ffffffff60c01b03198284099250600160601b63ffffffff60c01b031980600160601b63ffffffff60c01b03198b8d08600160601b63ffffffff60c01b03198c600160601b63ffffffff60c01b0319038e0809600309600160601b63ffffffff60c01b03198985099850600160601b63ffffffff60c01b03198a84099950600160601b63ffffffff60c01b031980836002600160601b0363ffffffff60c01b031909600160601b63ffffffff60c01b0319838409089a50600160601b63ffffffff60c01b03198083600160601b63ffffffff60c01b0319038d0882099250600160601b63ffffffff60c01b031983600160601b63ffffffff60c01b03198a870908975060018d881c1660018d891c1660011b01905080611f125787600160601b63ffffffff60c01b03190397505050505061225f565b60018103611f61577f6b17d1f2e12c4247f8bce6e563a440f277037d812deb33a0f4a13945d898c29693507f4fe342e2fe1a7f9b8ee7eb4a7c0f9e162bce33576b315ececbb6406837bf51f592505b60028103611f70578e93508d92505b60038103611f7f578593508492505b89611f98575091985060019750879650945061225f9050565b600160601b63ffffffff60c01b031988600160601b63ffffffff60c01b03198b860908600160601b63ffffffff60c01b03198c600160601b63ffffffff60c01b031903600160601b63ffffffff60c01b03198d880908935080612151578361215157600160601b63ffffffff60c01b0319896002600160601b0363ffffffff60c01b0319099450600160601b63ffffffff60c01b03198586099350600160601b63ffffffff60c01b0319848d099250600160601b63ffffffff60c01b03198486099450600160601b63ffffffff60c01b0319808c600160601b63ffffffff60c01b0319038e08600160601b63ffffffff60c01b03198d8f08099050600160601b63ffffffff60c01b0319816003099150600160601b63ffffffff60c01b03198a86099950600160601b63ffffffff60c01b03198b85099a50600160601b63ffffffff60c01b031980846002600160601b0363ffffffff60c01b031909600160601b63ffffffff60c01b0319848509089b50600160601b63ffffffff60c01b0319808d600160601b63ffffffff60c01b031903850883099350600160601b63ffffffff60c01b0319808a870985089850505050505061225f565b600160601b63ffffffff60c01b03198485099150600160601b63ffffffff60c01b0319848309600160601b63ffffffff60c01b0319838d099b50600160601b63ffffffff60c01b0319818c099a50600160601b63ffffffff60c01b0319838e09600160601b63ffffffff60c01b031980826002600160601b0363ffffffff60c01b031909600160601b63ffffffff60c01b031984600160601b63ffffffff60c01b031903600160601b63ffffffff60c01b031987880908089350600160601b63ffffffff60c01b031980838d09600160601b63ffffffff60c01b031985600160601b63ffffffff60c01b031988600160601b63ffffffff60c01b031903860809089a50505050809a50505050505b600183039250611d95565b60405186606082015260208152602080820152602060408201526002600160601b0363ffffffff60c01b03196080820152600160601b63ffffffff60c01b031960a082015260208160c0836005600019fa6122c457600080fd5b600160601b63ffffffff60c01b0319815189099750505050505050505b949350505050565b60008080808661230057858593509350505061236e565b8461231257878793509350505061236e565b858814801561232057508487145b15612341576123328888600180612377565b929a509098509250905061235b565b61235088886001808a8a6124d2565b929a50909850925090505b61236788888484612656565b9350935050505b94509492505050565b600080600080600160601b63ffffffff60c01b0319876002099350600160601b63ffffffff60c01b03198485099150600160601b63ffffffff60c01b03198289099050600160601b63ffffffff60c01b03198285099250600160601b63ffffffff60c01b03198683099150600160601b63ffffffff60c01b031980600160601b63ffffffff60c01b0319888b08600160601b63ffffffff60c01b031989600160601b63ffffffff60c01b0319038c08096003099550600160601b63ffffffff60c01b031980826002600160601b0363ffffffff60c01b031909600160601b63ffffffff60c01b0319888909089350600160601b63ffffffff60c01b03198085600160601b63ffffffff60c01b031903830887099750600160601b63ffffffff60c01b03198584099050600160601b63ffffffff60c01b031980888509600160601b63ffffffff60c01b03190389089250945094509450949050565b600080600080886000036124f157508492508391506001905080612649565b600160601b63ffffffff60c01b0319988903988981898809089450600160601b63ffffffff60c01b03198a600160601b63ffffffff60c01b031903600160601b63ffffffff60c01b03198a8909089550600160601b63ffffffff60c01b03198687099350600160601b63ffffffff60c01b03198685099250600160601b63ffffffff60c01b03198489099150600160601b63ffffffff60c01b03198388099050600160601b63ffffffff60c01b0319848b099750600160601b63ffffffff60c01b031980896002600160601b0363ffffffff60c01b031909600160601b63ffffffff60c01b031985600160601b63ffffffff60c01b031903600160601b63ffffffff60c01b0319898a0908089350600160601b63ffffffff60c01b031980848b09600160601b63ffffffff60c01b031987600160601b63ffffffff60c01b031988600160601b63ffffffff60c01b0319038d08090892505b9650965096509692505050565b6000806000612664846126c3565b9050600160601b63ffffffff60c01b031981870991506000600160601b63ffffffff60c01b03198287099050600160601b63ffffffff60c01b03198182099150600160601b63ffffffff60c01b03198289099350505094509492505050565b600060405160208152602080820152602060408201528260608201526002600160601b0363ffffffff60c01b03196080820152600160601b63ffffffff60c01b031960a082015260208160c0836005600019fa611c1857600080fd5b50805461272b90612e06565b6000825580601f1061273b575050565b601f01602090049060005260206000209081019061053c91905b808211156109ad5760008155600101612755565b6000806040838503121561277c57600080fd5b50508035926020909101359150565b80356001600160a01b03811681146127a257600080fd5b919050565b6000602082840312156127b957600080fd5b6105728261278b565b60008083601f8401126127d457600080fd5b5081356001600160401b038111156127eb57600080fd5b60208301915083602082850101111561280357600080fd5b9250929050565b60008060006040848603121561281f57600080fd5b8335925060208401356001600160401b0381111561283c57600080fd5b612848868287016127c2565b9497909650939450505050565b634e487b7160e01b600052604160045260246000fd5b60405160c081016001600160401b038111828210171561288d5761288d612855565b60405290565b604051601f8201601f191681016001600160401b03811182821017156128bb576128bb612855565b604052919050565b60006001600160401b038211156128dc576128dc612855565b50601f01601f191660200190565b600082601f8301126128fb57600080fd5b813561290e612909826128c3565b612893565b81815284602083860101111561292357600080fd5b816020850160208301376000918101602001919091529392505050565b60006020828403121561295257600080fd5b81356001600160401b0381111561296857600080fd5b6122e1848285016128ea565b60008083601f84011261298657600080fd5b5081356001600160401b0381111561299d57600080fd5b6020830191508360208260051b850101111561280357600080fd5b600080602083850312156129cb57600080fd5b82356001600160401b038111156129e157600080fd5b6129ed85828601612974565b90969095509350505050565b60006101608284031215612a0c57600080fd5b50919050565b600080600060608486031215612a2757600080fd5b83356001600160401b03811115612a3d57600080fd5b612a49868287016129f9565b9660208601359650604090950135949350505050565b600080600060408486031215612a7457600080fd5b612a7d8461278b565b925060208401356001600160401b0381111561283c57600080fd5b600060208284031215612aaa57600080fd5b81356001600160401b03811115612ac057600080fd5b6122e1848285016129f9565b600060208284031215612ade57600080fd5b5035919050565b60005b83811015612b00578181015183820152602001612ae8565b50506000910152565b60008151808452612b21816020860160208601612ae5565b601f01601f19169290920160200192915050565b60ff60f81b881681526000602060e06020840152612b5660e084018a612b09565b8381036040850152612b68818a612b09565b606085018990526001600160a01b038816608086015260a0850187905284810360c08601528551808252602080880193509091019060005b81811015612bbc57835183529284019291840191600101612ba0565b50909c9b505050505050505050505050565b6020815260006105726020830184612b09565b600060208284031215612bf357600080fd5b81356001600160e01b03198116811461057257600080fd5b60008060008060608587031215612c2157600080fd5b612c2a8561278b565b93506020850135925060408501356001600160401b03811115612c4c57600080fd5b612c58878288016127c2565b95989497509550505050565b60008060208385031215612c7757600080fd5b82356001600160401b03811115612c8d57600080fd5b6129ed858286016127c2565b60008251612cab818460208701612ae5565b9190910192915050565b634e487b7160e01b600052603260045260246000fd5b60008235605e19833603018112612cab57600080fd5b6000808335601e19843603018112612cf857600080fd5b8301803591506001600160401b03821115612d1257600080fd5b60200191503681900382131561280357600080fd5b60008085851115612d3757600080fd5b83861115612d4457600080fd5b5050820193919092039150565b6001600160e01b03198135818116916004851015612d795780818660040360031b1b83161692505b505092915050565b60006001600160401b0380841115612d9b57612d9b612855565b8360051b6020612dad60208301612893565b86815291850191602081019036841115612dc657600080fd5b865b84811015612dfa57803586811115612de05760008081fd5b612dec36828b016128ea565b845250918301918301612dc8565b50979650505050505050565b600181811c90821680612e1a57607f821691505b602082108103612a0c57634e487b7160e01b600052602260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b600060018201612e6257612e62612e3a565b5060010190565b600060208284031215612e7b57600080fd5b81356001600160401b0380821115612e9257600080fd5b9083019060408286031215612ea657600080fd5b604051604081018181108382111715612ec157612ec1612855565b60405282358152602083013582811115612eda57600080fd5b612ee6878286016128ea565b60208301525095945050505050565b80516020808301519190811015612a0c5760001960209190910360031b1b16919050565b60008060408385031215612f2c57600080fd5b505080516020909101519092909150565b600082601f830112612f4e57600080fd5b8151612f5c612909826128c3565b818152846020838601011115612f7157600080fd5b6122e1826020830160208701612ae5565b600060208284031215612f9457600080fd5b81516001600160401b0380821115612fab57600080fd5b9083019060c08286031215612fbf57600080fd5b612fc761286b565b825182811115612fd657600080fd5b612fe287828601612f3d565b825250602083015182811115612ff757600080fd5b61300387828601612f3d565b60208301525060408301516040820152606083015160608201526080830151608082015260a083015160a082015280935050505092915050565b601f8211156106dc576000816000526020600020601f850160051c810160208610156130665750805b601f850160051c820191505b8181101561308557828155600101613072565b505050505050565b81516001600160401b038111156130a6576130a6612855565b6130ba816130b48454612e06565b8461303d565b602080601f8311600181146130ef57600084156130d75750858301515b600019600386901b1c1916600185901b178555613085565b600085815260208120601f198616915b8281101561311e578886015182559484019460019091019084016130ff565b508582101561313c5787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b8082018082111561050157610501612e3a565b6c1131b430b63632b733b2911d1160991b8152815160009061318881600d850160208701612ae5565b601160f91b600d939091019283015250600e01919050565b6000602082840312156131b257600080fd5b5051919050565b600083516131cb818460208801612ae5565b9190910191825250602001919050565b8181038181111561050157610501612e3a56feffffffff00000000ffffffffffffffffbce6faada7179e84f3b9cac2fc63255197e2c6aad4ce5d562ebfaa00db6b9e0fb66ea5d8162ed5b243f51a2e03086f00a26469706673582212206267bdd6ae13c948b83275fcdafdc1366dd287cbf41ef689e1d49904a10ea33e64736f6c6343000817003397e2c6aad4ce5d562ebfaa00db6b9e0fb66ea5d8162ed5b243f51a2e03086f00";
+
+ private static String librariesLinkedBinary;
+
+ public static final String FUNC_REPLAYABLE_NONCE_KEY = "REPLAYABLE_NONCE_KEY";
+
+ public static final String FUNC_ADDOWNERADDRESS = "addOwnerAddress";
+
+ public static final String FUNC_ADDOWNERPUBLICKEY = "addOwnerPublicKey";
+
+ public static final String FUNC_CANSKIPCHAINIDVALIDATION = "canSkipChainIdValidation";
+
+ public static final String FUNC_DOMAINSEPARATOR = "domainSeparator";
+
+ public static final String FUNC_EIP712DOMAIN = "eip712Domain";
+
+ public static final String FUNC_ENTRYPOINT = "entryPoint";
+
+ public static final String FUNC_EXECUTE = "execute";
+
+ public static final String FUNC_EXECUTEBATCH = "executeBatch";
+
+ public static final String FUNC_EXECUTEWITHOUTCHAINIDVALIDATION = "executeWithoutChainIdValidation";
+
+ public static final String FUNC_GETUSEROPHASHWITHOUTCHAINID = "getUserOpHashWithoutChainId";
+
+ public static final String FUNC_IMPLEMENTATION = "implementation";
+
+ public static final String FUNC_INITIALIZE = "initialize";
+
+ public static final String FUNC_ISOWNERADDRESS = "isOwnerAddress";
+
+ public static final String FUNC_ISOWNERBYTES = "isOwnerBytes";
+
+ public static final String FUNC_ISOWNERPUBLICKEY = "isOwnerPublicKey";
+
+ public static final String FUNC_ISVALIDSIGNATURE = "isValidSignature";
+
+ public static final String FUNC_NEXTOWNERINDEX = "nextOwnerIndex";
+
+ public static final String FUNC_OWNERATINDEX = "ownerAtIndex";
+
+ public static final String FUNC_PROXIABLEUUID = "proxiableUUID";
+
+ public static final String FUNC_REMOVEOWNERATINDEX = "removeOwnerAtIndex";
+
+ public static final String FUNC_REPLAYSAFEHASH = "replaySafeHash";
+
+ public static final String FUNC_UPGRADETOANDCALL = "upgradeToAndCall";
+
+ public static final String FUNC_VALIDATEUSEROP = "validateUserOp";
+
+ public static final Event ADDOWNER_EVENT = new Event("AddOwner",
+ Arrays.>asList(new TypeReference(true) {
+ }, new TypeReference() {
+ }));
+ ;
+
+ public static final Event REMOVEOWNER_EVENT = new Event("RemoveOwner",
+ Arrays.>asList(new TypeReference(true) {
+ }, new TypeReference() {
+ }));
+ ;
+
+ public static final Event UPGRADED_EVENT = new Event("Upgraded",
+ Arrays.>asList(new TypeReference(true) {
+ }));
+ ;
+
+ @Deprecated
+ protected CoinbaseSmartWallet(String contractAddress, Web3j web3j, Credentials credentials,
+ BigInteger gasPrice, BigInteger gasLimit) {
+ super(BINARY, contractAddress, web3j, credentials, gasPrice, gasLimit);
+ }
+
+ protected CoinbaseSmartWallet(String contractAddress, Web3j web3j, Credentials credentials,
+ ContractGasProvider contractGasProvider) {
+ super(BINARY, contractAddress, web3j, credentials, contractGasProvider);
+ }
+
+ @Deprecated
+ protected CoinbaseSmartWallet(String contractAddress, Web3j web3j,
+ TransactionManager transactionManager, BigInteger gasPrice, BigInteger gasLimit) {
+ super(BINARY, contractAddress, web3j, transactionManager, gasPrice, gasLimit);
+ }
+
+ protected CoinbaseSmartWallet(String contractAddress, Web3j web3j,
+ TransactionManager transactionManager, ContractGasProvider contractGasProvider) {
+ super(BINARY, contractAddress, web3j, transactionManager, contractGasProvider);
+ }
+
+ public RemoteFunctionCall REPLAYABLE_NONCE_KEY() {
+ final Function function = new Function(FUNC_REPLAYABLE_NONCE_KEY,
+ Arrays.asList(),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, BigInteger.class);
+ }
+
+ public RemoteFunctionCall addOwnerAddress(String owner) {
+ final Function function = new Function(
+ FUNC_ADDOWNERADDRESS,
+ Arrays.asList(new org.web3j.abi.datatypes.Address(160, owner)),
+ Collections.>emptyList());
+ return executeRemoteCallTransaction(function);
+ }
+
+ public RemoteFunctionCall addOwnerPublicKey(byte[] x, byte[] y) {
+ final Function function = new Function(
+ FUNC_ADDOWNERPUBLICKEY,
+ Arrays.asList(new org.web3j.abi.datatypes.generated.Bytes32(x),
+ new org.web3j.abi.datatypes.generated.Bytes32(y)),
+ Collections.>emptyList());
+ return executeRemoteCallTransaction(function);
+ }
+
+ public RemoteFunctionCall canSkipChainIdValidation(byte[] functionSelector) {
+ final Function function = new Function(FUNC_CANSKIPCHAINIDVALIDATION,
+ Arrays.asList(new org.web3j.abi.datatypes.generated.Bytes4(functionSelector)),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, Boolean.class);
+ }
+
+ public RemoteFunctionCall domainSeparator() {
+ final Function function = new Function(FUNC_DOMAINSEPARATOR,
+ Arrays.asList(),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, byte[].class);
+ }
+
+ public RemoteFunctionCall>> eip712Domain(
+ ) {
+ final Function function = new Function(FUNC_EIP712DOMAIN,
+ Arrays.asList(),
+ Arrays.>asList(new TypeReference() {
+ }, new TypeReference() {
+ }, new TypeReference() {
+ }, new TypeReference() {
+ }, new TypeReference() {
+ }, new TypeReference() {
+ }, new TypeReference>() {
+ }));
+ return new RemoteFunctionCall>>(function,
+ new Callable>>() {
+ @Override
+ public Tuple7> call(
+ ) throws Exception {
+ List results = executeCallMultipleValueReturn(function);
+ return new Tuple7>(
+ (byte[]) results.get(0).getValue(),
+ (String) results.get(1).getValue(),
+ (String) results.get(2).getValue(),
+ (BigInteger) results.get(3).getValue(),
+ (String) results.get(4).getValue(),
+ (byte[]) results.get(5).getValue(),
+ convertToNative((List) results.get(6).getValue()));
+ }
+ });
+ }
+
+ public RemoteFunctionCall entryPoint() {
+ final Function function = new Function(FUNC_ENTRYPOINT,
+ Arrays.asList(),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, String.class);
+ }
+
+ public RemoteFunctionCall execute(String target, BigInteger value,
+ byte[] data, BigInteger weiValue) {
+ final Function function = new Function(
+ FUNC_EXECUTE,
+ Arrays.asList(new org.web3j.abi.datatypes.Address(160, target),
+ new org.web3j.abi.datatypes.generated.Uint256(value),
+ new org.web3j.abi.datatypes.DynamicBytes(data)),
+ Collections.>emptyList());
+ return executeRemoteCallTransaction(function, weiValue);
+ }
+
+ public RemoteFunctionCall executeBatch(List calls,
+ BigInteger weiValue) {
+ final Function function = new Function(
+ FUNC_EXECUTEBATCH,
+ Arrays.asList(new org.web3j.abi.datatypes.DynamicArray(Call.class, calls)),
+ Collections.>emptyList());
+ return executeRemoteCallTransaction(function, weiValue);
+ }
+
+ public RemoteFunctionCall executeWithoutChainIdValidation(byte[] data,
+ BigInteger weiValue) {
+ final Function function = new Function(
+ FUNC_EXECUTEWITHOUTCHAINIDVALIDATION,
+ Arrays.asList(new org.web3j.abi.datatypes.DynamicBytes(data)),
+ Collections.>emptyList());
+ return executeRemoteCallTransaction(function, weiValue);
+ }
+
+ public RemoteFunctionCall getUserOpHashWithoutChainId(UserOperation userOp) {
+ final Function function = new Function(FUNC_GETUSEROPHASHWITHOUTCHAINID,
+ Arrays.asList(userOp),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, byte[].class);
+ }
+
+ public RemoteFunctionCall implementation() {
+ final Function function = new Function(FUNC_IMPLEMENTATION,
+ Arrays.asList(),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, String.class);
+ }
+
+ public RemoteFunctionCall initialize(List owners,
+ BigInteger weiValue) {
+ final Function function = new Function(
+ FUNC_INITIALIZE,
+ Arrays.asList(new org.web3j.abi.datatypes.DynamicArray(
+ org.web3j.abi.datatypes.DynamicBytes.class,
+ org.web3j.abi.Utils.typeMap(owners, org.web3j.abi.datatypes.DynamicBytes.class))),
+ Collections.>emptyList());
+ return executeRemoteCallTransaction(function, weiValue);
+ }
+
+ public RemoteFunctionCall isOwnerAddress(String account) {
+ final Function function = new Function(FUNC_ISOWNERADDRESS,
+ Arrays.asList(new org.web3j.abi.datatypes.Address(160, account)),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, Boolean.class);
+ }
+
+ public RemoteFunctionCall isOwnerBytes(byte[] account) {
+ final Function function = new Function(FUNC_ISOWNERBYTES,
+ Arrays.asList(new org.web3j.abi.datatypes.DynamicBytes(account)),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, Boolean.class);
+ }
+
+ public RemoteFunctionCall isOwnerPublicKey(byte[] x, byte[] y) {
+ final Function function = new Function(FUNC_ISOWNERPUBLICKEY,
+ Arrays.asList(new org.web3j.abi.datatypes.generated.Bytes32(x),
+ new org.web3j.abi.datatypes.generated.Bytes32(y)),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, Boolean.class);
+ }
+
+ public RemoteFunctionCall isValidSignature(byte[] hash, byte[] signature) {
+ final Function function = new Function(FUNC_ISVALIDSIGNATURE,
+ Arrays.asList(new org.web3j.abi.datatypes.generated.Bytes32(hash),
+ new org.web3j.abi.datatypes.DynamicBytes(signature)),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, byte[].class);
+ }
+
+ public RemoteFunctionCall nextOwnerIndex() {
+ final Function function = new Function(FUNC_NEXTOWNERINDEX,
+ Arrays.asList(),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, BigInteger.class);
+ }
+
+ public RemoteFunctionCall ownerAtIndex(BigInteger index) {
+ final Function function = new Function(FUNC_OWNERATINDEX,
+ Arrays.asList(new org.web3j.abi.datatypes.generated.Uint256(index)),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, byte[].class);
+ }
+
+ public RemoteFunctionCall proxiableUUID() {
+ final Function function = new Function(FUNC_PROXIABLEUUID,
+ Arrays.asList(),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, byte[].class);
+ }
+
+ public RemoteFunctionCall removeOwnerAtIndex(BigInteger index) {
+ final Function function = new Function(
+ FUNC_REMOVEOWNERATINDEX,
+ Arrays.asList(new org.web3j.abi.datatypes.generated.Uint256(index)),
+ Collections.>emptyList());
+ return executeRemoteCallTransaction(function);
+ }
+
+ public RemoteFunctionCall replaySafeHash(byte[] hash) {
+ final Function function = new Function(FUNC_REPLAYSAFEHASH,
+ Arrays.asList(new org.web3j.abi.datatypes.generated.Bytes32(hash)),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, byte[].class);
+ }
+
+ public RemoteFunctionCall upgradeToAndCall(String newImplementation,
+ byte[] data, BigInteger weiValue) {
+ final Function function = new Function(
+ FUNC_UPGRADETOANDCALL,
+ Arrays.asList(new org.web3j.abi.datatypes.Address(160, newImplementation),
+ new org.web3j.abi.datatypes.DynamicBytes(data)),
+ Collections.>emptyList());
+ return executeRemoteCallTransaction(function, weiValue);
+ }
+
+ public RemoteFunctionCall validateUserOp(UserOperation userOp,
+ byte[] userOpHash, BigInteger missingAccountFunds, BigInteger weiValue) {
+ final Function function = new Function(
+ FUNC_VALIDATEUSEROP,
+ Arrays.asList(userOp,
+ new org.web3j.abi.datatypes.generated.Bytes32(userOpHash),
+ new org.web3j.abi.datatypes.generated.Uint256(missingAccountFunds)),
+ Collections.>emptyList());
+ return executeRemoteCallTransaction(function, weiValue);
+ }
+
+ public static List getAddOwnerEvents(
+ TransactionReceipt transactionReceipt) {
+ List valueList = staticExtractEventParametersWithLog(ADDOWNER_EVENT, transactionReceipt);
+ ArrayList responses = new ArrayList(valueList.size());
+ for (Contract.EventValuesWithLog eventValues : valueList) {
+ AddOwnerEventResponse typedResponse = new AddOwnerEventResponse();
+ typedResponse.log = eventValues.getLog();
+ typedResponse.index = (BigInteger) eventValues.getIndexedValues().get(0).getValue();
+ typedResponse.owner = (byte[]) eventValues.getNonIndexedValues().get(0).getValue();
+ responses.add(typedResponse);
+ }
+ return responses;
+ }
+
+ public static AddOwnerEventResponse getAddOwnerEventFromLog(Log log) {
+ Contract.EventValuesWithLog eventValues = staticExtractEventParametersWithLog(ADDOWNER_EVENT, log);
+ AddOwnerEventResponse typedResponse = new AddOwnerEventResponse();
+ typedResponse.log = log;
+ typedResponse.index = (BigInteger) eventValues.getIndexedValues().get(0).getValue();
+ typedResponse.owner = (byte[]) eventValues.getNonIndexedValues().get(0).getValue();
+ return typedResponse;
+ }
+
+ public Flowable addOwnerEventFlowable(EthFilter filter) {
+ return web3j.ethLogFlowable(filter).map(log -> getAddOwnerEventFromLog(log));
+ }
+
+ public Flowable addOwnerEventFlowable(DefaultBlockParameter startBlock,
+ DefaultBlockParameter endBlock) {
+ EthFilter filter = new EthFilter(startBlock, endBlock, getContractAddress());
+ filter.addSingleTopic(EventEncoder.encode(ADDOWNER_EVENT));
+ return addOwnerEventFlowable(filter);
+ }
+
+ public static List getRemoveOwnerEvents(
+ TransactionReceipt transactionReceipt) {
+ List valueList = staticExtractEventParametersWithLog(REMOVEOWNER_EVENT, transactionReceipt);
+ ArrayList responses = new ArrayList(valueList.size());
+ for (Contract.EventValuesWithLog eventValues : valueList) {
+ RemoveOwnerEventResponse typedResponse = new RemoveOwnerEventResponse();
+ typedResponse.log = eventValues.getLog();
+ typedResponse.index = (BigInteger) eventValues.getIndexedValues().get(0).getValue();
+ typedResponse.owner = (byte[]) eventValues.getNonIndexedValues().get(0).getValue();
+ responses.add(typedResponse);
+ }
+ return responses;
+ }
+
+ public static RemoveOwnerEventResponse getRemoveOwnerEventFromLog(Log log) {
+ Contract.EventValuesWithLog eventValues = staticExtractEventParametersWithLog(REMOVEOWNER_EVENT, log);
+ RemoveOwnerEventResponse typedResponse = new RemoveOwnerEventResponse();
+ typedResponse.log = log;
+ typedResponse.index = (BigInteger) eventValues.getIndexedValues().get(0).getValue();
+ typedResponse.owner = (byte[]) eventValues.getNonIndexedValues().get(0).getValue();
+ return typedResponse;
+ }
+
+ public Flowable removeOwnerEventFlowable(EthFilter filter) {
+ return web3j.ethLogFlowable(filter).map(log -> getRemoveOwnerEventFromLog(log));
+ }
+
+ public Flowable removeOwnerEventFlowable(
+ DefaultBlockParameter startBlock, DefaultBlockParameter endBlock) {
+ EthFilter filter = new EthFilter(startBlock, endBlock, getContractAddress());
+ filter.addSingleTopic(EventEncoder.encode(REMOVEOWNER_EVENT));
+ return removeOwnerEventFlowable(filter);
+ }
+
+ public static List getUpgradedEvents(
+ TransactionReceipt transactionReceipt) {
+ List valueList = staticExtractEventParametersWithLog(UPGRADED_EVENT, transactionReceipt);
+ ArrayList responses = new ArrayList(valueList.size());
+ for (Contract.EventValuesWithLog eventValues : valueList) {
+ UpgradedEventResponse typedResponse = new UpgradedEventResponse();
+ typedResponse.log = eventValues.getLog();
+ typedResponse.implementation = (String) eventValues.getIndexedValues().get(0).getValue();
+ responses.add(typedResponse);
+ }
+ return responses;
+ }
+
+ public static UpgradedEventResponse getUpgradedEventFromLog(Log log) {
+ Contract.EventValuesWithLog eventValues = staticExtractEventParametersWithLog(UPGRADED_EVENT, log);
+ UpgradedEventResponse typedResponse = new UpgradedEventResponse();
+ typedResponse.log = log;
+ typedResponse.implementation = (String) eventValues.getIndexedValues().get(0).getValue();
+ return typedResponse;
+ }
+
+ public Flowable upgradedEventFlowable(EthFilter filter) {
+ return web3j.ethLogFlowable(filter).map(log -> getUpgradedEventFromLog(log));
+ }
+
+ public Flowable upgradedEventFlowable(DefaultBlockParameter startBlock,
+ DefaultBlockParameter endBlock) {
+ EthFilter filter = new EthFilter(startBlock, endBlock, getContractAddress());
+ filter.addSingleTopic(EventEncoder.encode(UPGRADED_EVENT));
+ return upgradedEventFlowable(filter);
+ }
+
+ @Deprecated
+ public static CoinbaseSmartWallet load(String contractAddress, Web3j web3j,
+ Credentials credentials, BigInteger gasPrice, BigInteger gasLimit) {
+ return new CoinbaseSmartWallet(contractAddress, web3j, credentials, gasPrice, gasLimit);
+ }
+
+ @Deprecated
+ public static CoinbaseSmartWallet load(String contractAddress, Web3j web3j,
+ TransactionManager transactionManager, BigInteger gasPrice, BigInteger gasLimit) {
+ return new CoinbaseSmartWallet(contractAddress, web3j, transactionManager, gasPrice, gasLimit);
+ }
+
+ public static CoinbaseSmartWallet load(String contractAddress, Web3j web3j,
+ Credentials credentials, ContractGasProvider contractGasProvider) {
+ return new CoinbaseSmartWallet(contractAddress, web3j, credentials, contractGasProvider);
+ }
+
+ public static CoinbaseSmartWallet load(String contractAddress, Web3j web3j,
+ TransactionManager transactionManager, ContractGasProvider contractGasProvider) {
+ return new CoinbaseSmartWallet(contractAddress, web3j, transactionManager, contractGasProvider);
+ }
+
+ public static RemoteCall deploy(Web3j web3j, Credentials credentials,
+ ContractGasProvider contractGasProvider) {
+ return deployRemoteCall(CoinbaseSmartWallet.class, web3j, credentials, contractGasProvider, getDeploymentBinary(), "");
+ }
+
+ public static RemoteCall deploy(Web3j web3j,
+ TransactionManager transactionManager, ContractGasProvider contractGasProvider) {
+ return deployRemoteCall(CoinbaseSmartWallet.class, web3j, transactionManager, contractGasProvider, getDeploymentBinary(), "");
+ }
+
+ @Deprecated
+ public static RemoteCall deploy(Web3j web3j, Credentials credentials,
+ BigInteger gasPrice, BigInteger gasLimit) {
+ return deployRemoteCall(CoinbaseSmartWallet.class, web3j, credentials, gasPrice, gasLimit, getDeploymentBinary(), "");
+ }
+
+ @Deprecated
+ public static RemoteCall deploy(Web3j web3j,
+ TransactionManager transactionManager, BigInteger gasPrice, BigInteger gasLimit) {
+ return deployRemoteCall(CoinbaseSmartWallet.class, web3j, transactionManager, gasPrice, gasLimit, getDeploymentBinary(), "");
+ }
+
+ private static String getDeploymentBinary() {
+ if (librariesLinkedBinary != null) {
+ return librariesLinkedBinary;
+ } else {
+ return BINARY;
+ }
+ }
+
+ public static class Call extends DynamicStruct {
+ public String target;
+
+ public BigInteger value;
+
+ public byte[] data;
+
+ public Call(String target, BigInteger value, byte[] data) {
+ super(new org.web3j.abi.datatypes.Address(160, target),
+ new org.web3j.abi.datatypes.generated.Uint256(value),
+ new org.web3j.abi.datatypes.DynamicBytes(data));
+ this.target = target;
+ this.value = value;
+ this.data = data;
+ }
+
+ public Call(Address target, Uint256 value, DynamicBytes data) {
+ super(target, value, data);
+ this.target = target.getValue();
+ this.value = value.getValue();
+ this.data = data.getValue();
+ }
+ }
+
+ public static class UserOperation extends DynamicStruct {
+ public String sender;
+
+ public BigInteger nonce;
+
+ public byte[] initCode;
+
+ public byte[] callData;
+
+ public BigInteger callGasLimit;
+
+ public BigInteger verificationGasLimit;
+
+ public BigInteger preVerificationGas;
+
+ public BigInteger maxFeePerGas;
+
+ public BigInteger maxPriorityFeePerGas;
+
+ public byte[] paymasterAndData;
+
+ public byte[] signature;
+
+ public UserOperation(String sender, BigInteger nonce, byte[] initCode, byte[] callData,
+ BigInteger callGasLimit, BigInteger verificationGasLimit,
+ BigInteger preVerificationGas, BigInteger maxFeePerGas,
+ BigInteger maxPriorityFeePerGas, byte[] paymasterAndData, byte[] signature) {
+ super(new org.web3j.abi.datatypes.Address(160, sender),
+ new org.web3j.abi.datatypes.generated.Uint256(nonce),
+ new org.web3j.abi.datatypes.DynamicBytes(initCode),
+ new org.web3j.abi.datatypes.DynamicBytes(callData),
+ new org.web3j.abi.datatypes.generated.Uint256(callGasLimit),
+ new org.web3j.abi.datatypes.generated.Uint256(verificationGasLimit),
+ new org.web3j.abi.datatypes.generated.Uint256(preVerificationGas),
+ new org.web3j.abi.datatypes.generated.Uint256(maxFeePerGas),
+ new org.web3j.abi.datatypes.generated.Uint256(maxPriorityFeePerGas),
+ new org.web3j.abi.datatypes.DynamicBytes(paymasterAndData),
+ new org.web3j.abi.datatypes.DynamicBytes(signature));
+ this.sender = sender;
+ this.nonce = nonce;
+ this.initCode = initCode;
+ this.callData = callData;
+ this.callGasLimit = callGasLimit;
+ this.verificationGasLimit = verificationGasLimit;
+ this.preVerificationGas = preVerificationGas;
+ this.maxFeePerGas = maxFeePerGas;
+ this.maxPriorityFeePerGas = maxPriorityFeePerGas;
+ this.paymasterAndData = paymasterAndData;
+ this.signature = signature;
+ }
+
+ public UserOperation(Address sender, Uint256 nonce, DynamicBytes initCode,
+ DynamicBytes callData, Uint256 callGasLimit, Uint256 verificationGasLimit,
+ Uint256 preVerificationGas, Uint256 maxFeePerGas, Uint256 maxPriorityFeePerGas,
+ DynamicBytes paymasterAndData, DynamicBytes signature) {
+ super(sender, nonce, initCode, callData, callGasLimit, verificationGasLimit, preVerificationGas, maxFeePerGas, maxPriorityFeePerGas, paymasterAndData, signature);
+ this.sender = sender.getValue();
+ this.nonce = nonce.getValue();
+ this.initCode = initCode.getValue();
+ this.callData = callData.getValue();
+ this.callGasLimit = callGasLimit.getValue();
+ this.verificationGasLimit = verificationGasLimit.getValue();
+ this.preVerificationGas = preVerificationGas.getValue();
+ this.maxFeePerGas = maxFeePerGas.getValue();
+ this.maxPriorityFeePerGas = maxPriorityFeePerGas.getValue();
+ this.paymasterAndData = paymasterAndData.getValue();
+ this.signature = signature.getValue();
+ }
+ }
+
+ public static class AddOwnerEventResponse extends BaseEventResponse {
+ public BigInteger index;
+
+ public byte[] owner;
+ }
+
+ public static class RemoveOwnerEventResponse extends BaseEventResponse {
+ public BigInteger index;
+
+ public byte[] owner;
+ }
+
+ public static class UpgradedEventResponse extends BaseEventResponse {
+ public String implementation;
+ }
+}
diff --git a/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWallet.json b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWallet.json
new file mode 100644
index 000000000..fc051eeab
--- /dev/null
+++ b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWallet.json
@@ -0,0 +1,719 @@
+[
+ {
+ "type": "constructor",
+ "inputs": [],
+ "stateMutability": "nonpayable"
+ },
+ {
+ "type": "fallback",
+ "stateMutability": "payable"
+ },
+ {
+ "type": "receive",
+ "stateMutability": "payable"
+ },
+ {
+ "type": "function",
+ "name": "REPLAYABLE_NONCE_KEY",
+ "inputs": [],
+ "outputs": [
+ {
+ "name": "",
+ "type": "uint256",
+ "internalType": "uint256"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "addOwnerAddress",
+ "inputs": [
+ {
+ "name": "owner",
+ "type": "address",
+ "internalType": "address"
+ }
+ ],
+ "outputs": [],
+ "stateMutability": "nonpayable"
+ },
+ {
+ "type": "function",
+ "name": "addOwnerPublicKey",
+ "inputs": [
+ {
+ "name": "x",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ },
+ {
+ "name": "y",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ }
+ ],
+ "outputs": [],
+ "stateMutability": "nonpayable"
+ },
+ {
+ "type": "function",
+ "name": "canSkipChainIdValidation",
+ "inputs": [
+ {
+ "name": "functionSelector",
+ "type": "bytes4",
+ "internalType": "bytes4"
+ }
+ ],
+ "outputs": [
+ {
+ "name": "",
+ "type": "bool",
+ "internalType": "bool"
+ }
+ ],
+ "stateMutability": "pure"
+ },
+ {
+ "type": "function",
+ "name": "domainSeparator",
+ "inputs": [],
+ "outputs": [
+ {
+ "name": "",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "eip712Domain",
+ "inputs": [],
+ "outputs": [
+ {
+ "name": "fields",
+ "type": "bytes1",
+ "internalType": "bytes1"
+ },
+ {
+ "name": "name",
+ "type": "string",
+ "internalType": "string"
+ },
+ {
+ "name": "version",
+ "type": "string",
+ "internalType": "string"
+ },
+ {
+ "name": "chainId",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "verifyingContract",
+ "type": "address",
+ "internalType": "address"
+ },
+ {
+ "name": "salt",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ },
+ {
+ "name": "extensions",
+ "type": "uint256[]",
+ "internalType": "uint256[]"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "entryPoint",
+ "inputs": [],
+ "outputs": [
+ {
+ "name": "",
+ "type": "address",
+ "internalType": "address"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "execute",
+ "inputs": [
+ {
+ "name": "target",
+ "type": "address",
+ "internalType": "address"
+ },
+ {
+ "name": "value",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "data",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ],
+ "outputs": [],
+ "stateMutability": "payable"
+ },
+ {
+ "type": "function",
+ "name": "executeBatch",
+ "inputs": [
+ {
+ "name": "calls",
+ "type": "tuple[]",
+ "internalType": "struct CoinbaseSmartWallet.Call[]",
+ "components": [
+ {
+ "name": "target",
+ "type": "address",
+ "internalType": "address"
+ },
+ {
+ "name": "value",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "data",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ]
+ }
+ ],
+ "outputs": [],
+ "stateMutability": "payable"
+ },
+ {
+ "type": "function",
+ "name": "executeWithoutChainIdValidation",
+ "inputs": [
+ {
+ "name": "data",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ],
+ "outputs": [],
+ "stateMutability": "payable"
+ },
+ {
+ "type": "function",
+ "name": "getUserOpHashWithoutChainId",
+ "inputs": [
+ {
+ "name": "userOp",
+ "type": "tuple",
+ "internalType": "struct UserOperation",
+ "components": [
+ {
+ "name": "sender",
+ "type": "address",
+ "internalType": "address"
+ },
+ {
+ "name": "nonce",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "initCode",
+ "type": "bytes",
+ "internalType": "bytes"
+ },
+ {
+ "name": "callData",
+ "type": "bytes",
+ "internalType": "bytes"
+ },
+ {
+ "name": "callGasLimit",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "verificationGasLimit",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "preVerificationGas",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "maxFeePerGas",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "maxPriorityFeePerGas",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "paymasterAndData",
+ "type": "bytes",
+ "internalType": "bytes"
+ },
+ {
+ "name": "signature",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ]
+ }
+ ],
+ "outputs": [
+ {
+ "name": "userOpHash",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "implementation",
+ "inputs": [],
+ "outputs": [
+ {
+ "name": "addr",
+ "type": "address",
+ "internalType": "address"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "initialize",
+ "inputs": [
+ {
+ "name": "owners",
+ "type": "bytes[]",
+ "internalType": "bytes[]"
+ }
+ ],
+ "outputs": [],
+ "stateMutability": "payable"
+ },
+ {
+ "type": "function",
+ "name": "isOwnerAddress",
+ "inputs": [
+ {
+ "name": "account",
+ "type": "address",
+ "internalType": "address"
+ }
+ ],
+ "outputs": [
+ {
+ "name": "",
+ "type": "bool",
+ "internalType": "bool"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "isOwnerBytes",
+ "inputs": [
+ {
+ "name": "account",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ],
+ "outputs": [
+ {
+ "name": "",
+ "type": "bool",
+ "internalType": "bool"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "isOwnerPublicKey",
+ "inputs": [
+ {
+ "name": "x",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ },
+ {
+ "name": "y",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ }
+ ],
+ "outputs": [
+ {
+ "name": "",
+ "type": "bool",
+ "internalType": "bool"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "isValidSignature",
+ "inputs": [
+ {
+ "name": "hash",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ },
+ {
+ "name": "signature",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ],
+ "outputs": [
+ {
+ "name": "result",
+ "type": "bytes4",
+ "internalType": "bytes4"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "nextOwnerIndex",
+ "inputs": [],
+ "outputs": [
+ {
+ "name": "",
+ "type": "uint256",
+ "internalType": "uint256"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "ownerAtIndex",
+ "inputs": [
+ {
+ "name": "index",
+ "type": "uint256",
+ "internalType": "uint256"
+ }
+ ],
+ "outputs": [
+ {
+ "name": "",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "proxiableUUID",
+ "inputs": [],
+ "outputs": [
+ {
+ "name": "",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "removeOwnerAtIndex",
+ "inputs": [
+ {
+ "name": "index",
+ "type": "uint256",
+ "internalType": "uint256"
+ }
+ ],
+ "outputs": [],
+ "stateMutability": "nonpayable"
+ },
+ {
+ "type": "function",
+ "name": "replaySafeHash",
+ "inputs": [
+ {
+ "name": "hash",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ }
+ ],
+ "outputs": [
+ {
+ "name": "",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "upgradeToAndCall",
+ "inputs": [
+ {
+ "name": "newImplementation",
+ "type": "address",
+ "internalType": "address"
+ },
+ {
+ "name": "data",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ],
+ "outputs": [],
+ "stateMutability": "payable"
+ },
+ {
+ "type": "function",
+ "name": "validateUserOp",
+ "inputs": [
+ {
+ "name": "userOp",
+ "type": "tuple",
+ "internalType": "struct UserOperation",
+ "components": [
+ {
+ "name": "sender",
+ "type": "address",
+ "internalType": "address"
+ },
+ {
+ "name": "nonce",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "initCode",
+ "type": "bytes",
+ "internalType": "bytes"
+ },
+ {
+ "name": "callData",
+ "type": "bytes",
+ "internalType": "bytes"
+ },
+ {
+ "name": "callGasLimit",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "verificationGasLimit",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "preVerificationGas",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "maxFeePerGas",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "maxPriorityFeePerGas",
+ "type": "uint256",
+ "internalType": "uint256"
+ },
+ {
+ "name": "paymasterAndData",
+ "type": "bytes",
+ "internalType": "bytes"
+ },
+ {
+ "name": "signature",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ]
+ },
+ {
+ "name": "userOpHash",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ },
+ {
+ "name": "missingAccountFunds",
+ "type": "uint256",
+ "internalType": "uint256"
+ }
+ ],
+ "outputs": [
+ {
+ "name": "validationData",
+ "type": "uint256",
+ "internalType": "uint256"
+ }
+ ],
+ "stateMutability": "payable"
+ },
+ {
+ "type": "event",
+ "name": "AddOwner",
+ "inputs": [
+ {
+ "name": "index",
+ "type": "uint256",
+ "indexed": true,
+ "internalType": "uint256"
+ },
+ {
+ "name": "owner",
+ "type": "bytes",
+ "indexed": false,
+ "internalType": "bytes"
+ }
+ ],
+ "anonymous": false
+ },
+ {
+ "type": "event",
+ "name": "RemoveOwner",
+ "inputs": [
+ {
+ "name": "index",
+ "type": "uint256",
+ "indexed": true,
+ "internalType": "uint256"
+ },
+ {
+ "name": "owner",
+ "type": "bytes",
+ "indexed": false,
+ "internalType": "bytes"
+ }
+ ],
+ "anonymous": false
+ },
+ {
+ "type": "event",
+ "name": "Upgraded",
+ "inputs": [
+ {
+ "name": "implementation",
+ "type": "address",
+ "indexed": true,
+ "internalType": "address"
+ }
+ ],
+ "anonymous": false
+ },
+ {
+ "type": "error",
+ "name": "AlreadyOwner",
+ "inputs": [
+ {
+ "name": "owner",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ]
+ },
+ {
+ "type": "error",
+ "name": "Initialized",
+ "inputs": []
+ },
+ {
+ "type": "error",
+ "name": "InvalidEthereumAddressOwner",
+ "inputs": [
+ {
+ "name": "owner",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ]
+ },
+ {
+ "type": "error",
+ "name": "InvalidNonceKey",
+ "inputs": [
+ {
+ "name": "key",
+ "type": "uint256",
+ "internalType": "uint256"
+ }
+ ]
+ },
+ {
+ "type": "error",
+ "name": "InvalidOwnerBytesLength",
+ "inputs": [
+ {
+ "name": "owner",
+ "type": "bytes",
+ "internalType": "bytes"
+ }
+ ]
+ },
+ {
+ "type": "error",
+ "name": "NoOwnerAtIndex",
+ "inputs": [
+ {
+ "name": "index",
+ "type": "uint256",
+ "internalType": "uint256"
+ }
+ ]
+ },
+ {
+ "type": "error",
+ "name": "SelectorNotAllowed",
+ "inputs": [
+ {
+ "name": "selector",
+ "type": "bytes4",
+ "internalType": "bytes4"
+ }
+ ]
+ },
+ {
+ "type": "error",
+ "name": "Unauthorized",
+ "inputs": []
+ },
+ {
+ "type": "error",
+ "name": "UnauthorizedCallContext",
+ "inputs": []
+ },
+ {
+ "type": "error",
+ "name": "UpgradeFailed",
+ "inputs": []
+ }
+]
\ No newline at end of file
diff --git a/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletBinary.txt b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletBinary.txt
new file mode 100644
index 000000000..aa416366f
--- /dev/null
+++ b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletBinary.txt
@@ -0,0 +1 @@
+0x60a0604052306080523480156200001557600080fd5b50604080516001808252818301909252600091816020015b60608152602001906001900390816200002d57905050604080516000602082015291925001604051602081830303815290604052816000815181106200007757620000776200037a565b60209081029190910101526200008d8162000094565b50620005b0565b60005b81518110156200022657818181518110620000b657620000b66200037a565b602002602001015151602014158015620000ee5750818181518110620000e057620000e06200037a565b602002602001015151604014155b1562000136578181815181106200010957620001096200037a565b60200260200101516040516327755b9160e11b81526004016200012d9190620003b6565b60405180910390fd5b8181815181106200014b576200014b6200037a565b60200260200101515160201480156200019357506001600160a01b0380168282815181106200017e576200017e6200037a565b60200260200101516200019190620003eb565b115b15620001d257818181518110620001ae57620001ae6200037a565b602002602001015160405163bff1ac6560e01b81526004016200012d9190620003b6565b6200021d828281518110620001eb57620001eb6200037a565b6020026020010151620002036200022a60201b60201c565b8054906000620002138362000413565b909155506200023d565b60010162000097565b5050565b6000805160206200383783398151915290565b620002488262000326565b156200026b578160405163468b12ad60e11b81526004016200012d9190620003b6565b600160008051602062003837833981519152600201836040516200029091906200043b565b908152604051908190036020019020805491151560ff1990921691909117905581620002c86000805160206200383783398151915290565b60008381526001919091016020526040902090620002e79082620004e4565b50807f38109edc26e166b5579352ce56a50813177eb25208fd90d61f2f378386220220836040516200031a9190620003b6565b60405180910390a25050565b600060008051602062003837833981519152600201826040516200034b91906200043b565b9081526040519081900360200190205460ff1692915050565b634e487b7160e01b600052604160045260246000fd5b634e487b7160e01b600052603260045260246000fd5b60005b83811015620003ad57818101518382015260200162000393565b50506000910152565b6020815260008251806020840152620003d781604085016020870162000390565b601f01601f19169190910160400192915050565b805160208083015191908110156200040d576000198160200360031b1b821691505b50919050565b6000600182016200043457634e487b7160e01b600052601160045260246000fd5b5060010190565b600082516200044f81846020870162000390565b9190910192915050565b600181811c908216806200046e57607f821691505b6020821081036200040d57634e487b7160e01b600052602260045260246000fd5b601f821115620004df576000816000526020600020601f850160051c81016020861015620004ba5750805b601f850160051c820191505b81811015620004db57828155600101620004c6565b5050505b505050565b81516001600160401b0381111562000500576200050062000364565b620005188162000511845462000459565b846200048f565b602080601f831160018114620005505760008415620005375750858301515b600019600386901b1c1916600185901b178555620004db565b600085815260208120601f198616915b82811015620005815788860151825594840194600190910190840162000560565b5085821015620005a05787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b608051613264620005d36000396000818161081e015261095501526132646000f3fe60806040526004361061014f5760003560e01c806372de3b5a116100b6578063b0d691fe1161006f578063b0d691fe146103f4578063b61d27f61461041b578063bf6ba1fc1461042e578063ce1506be14610441578063d948fd2e14610461578063f698da251461048357610156565b806372de3b5a1461032957806384b0196e1461034957806388ce4c7c146103715780638ea69029146103875780639f9bcb34146103b4578063a2e1a8d8146103d457610156565b80633a871cdd116101085780633a871cdd146102655780634f1ef286146102865780634f6e7f221461029957806352d1902d146102b95780635c60da1b146102ce5780636f2de70e1461031657610156565b8063066a1eb7146101845780630f0f3f24146101b95780631626ba7e146101d95780631ca5393f1461021257806329565e3b1461023257806334fcd5be1461025257610156565b3661015657005b60003560e01c63bc197c81811463f23a6e6182141763150b7a028214171561018257806020526020603cf35b005b34801561019057600080fd5b506101a461019f366004612769565b610498565b60405190151581526020015b60405180910390f35b3480156101c557600080fd5b506101826101d43660046127a7565b610507565b3480156101e557600080fd5b506101f96101f436600461280a565b61053f565b6040516001600160e01b031990911681526020016101b0565b34801561021e57600080fd5b506101a461022d366004612940565b610579565b34801561023e57600080fd5b5061018261024d366004612769565b6105b4565b6101826102603660046129b8565b6105dd565b610278610273366004612a12565b6106e1565b6040519081526020016101b0565b610182610294366004612a5f565b61081c565b3480156102a557600080fd5b506102786102b4366004612a98565b610900565b3480156102c557600080fd5b50610278610951565b3480156102da57600080fd5b507f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc545b6040516001600160a01b0390911681526020016101b0565b6101826103243660046129b8565b6109b1565b34801561033557600080fd5b50610182610344366004612acc565b6109f1565b34801561035557600080fd5b5061035e610ade565b6040516101b09796959493929190612b35565b34801561037d57600080fd5b5061027861210581565b34801561039357600080fd5b506103a76103a2366004612acc565b610b05565b6040516101b09190612bce565b3480156103c057600080fd5b506101a46103cf366004612be1565b610bc6565b3480156103e057600080fd5b506101a46103ef3660046127a7565b610c42565b34801561040057600080fd5b50735ff137d4b0fdcd49dca30c7cf57e578a026d27896102fe565b610182610429366004612c0b565b610c88565b61018261043c366004612c64565b610cec565b34801561044d57600080fd5b5061027861045c366004612acc565b610dad565b34801561046d57600080fd5b5060008051602061320f83398151915254610278565b34801561048f57600080fd5b50610278610db8565b60408051602081018490529081018290526000907f97e2c6aad4ce5d562ebfaa00db6b9e0fb66ea5d8162ed5b243f51a2e03086f029060600160408051601f19818403018152908290526104eb91612c99565b9081526040519081900360200190205460ff1690505b92915050565b61050f610e3e565b604080516001600160a01b038316602082015261053c91015b604051602081830303815290604052610e70565b50565b600061055461054d85610dad565b8484610e9b565b156105675750630b135d3f60e11b610572565b506001600160e01b03195b9392505050565b600060008051602061320f8339815191526002018260405161059b9190612c99565b9081526040519081900360200190205460ff1692915050565b6105bc610e3e565b60408051602081018490529081018290526105d990606001610528565b5050565b33735ff137d4b0fdcd49dca30c7cf57e578a026d27891461060057610600610e3e565b60005b818110156106dc576106d483838381811061062057610620612cb5565b90506020028101906106329190612ccb565b6106409060208101906127a7565b84848481811061065257610652612cb5565b90506020028101906106649190612ccb565b6020013585858581811061067a5761067a612cb5565b905060200281019061068c9190612ccb565b61069a906040810190612ce1565b8080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250610fb092505050565b600101610603565b505050565b600033735ff137d4b0fdcd49dca30c7cf57e578a026d278914610716576040516282b42960e81b815260040160405180910390fd5b81602085013560401c600461072e6060880188612ce1565b90501015801561077257506107466060870187612ce1565b61075591600491600091612d27565b61075e91612d51565b6001600160e01b03191663bf6ba1fc60e01b145b156107b15761078086610900565b945061210581146107ac57604051632ef3781360e01b8152600481018290526024015b60405180910390fd5b6107d6565b61210581036107d657604051632ef3781360e01b8152600481018290526024016107a3565b6107ed856107e8610140890189612ce1565b610e9b565b156107fc576000925050610802565b60019250505b80156108145760003860003884335af1505b509392505050565b7f000000000000000000000000000000000000000000000000000000000000000030810361085257639f03a0266000526004601cfd5b61085b84611020565b8360601b60601c93506352d1902d6001527f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc80602060016004601d895afa51146108ad576355299b496001526004601dfd5b847fbc7cd75a20ee27fd9adebab32041f755214dbc6bffa90cc0225b39da2e5c2d3b600038a284905581156108fa57604051828482376000388483885af46108f8573d6000823e3d81fd5b505b50505050565b600061090b82611028565b604080516020810192909252735ff137d4b0fdcd49dca30c7cf57e578a026d2789908201526060015b604051602081830303815290604052805190602001209050919050565b60007f000000000000000000000000000000000000000000000000000000000000000030811461098957639f03a0266000526004601cfd5b7f360894a13ba1a3210667c828492db98dca3e2076cc3735a920a3ca505d382bbc91505b5090565b60008051602061320f83398151915254156109df576040516302ed543d60e51b815260040160405180910390fd5b6105d96109ec8284612d81565b611041565b6109f9610e3e565b6000610a0482610b05565b90508051600003610a2b5760405163340c473d60e11b8152600481018390526024016107a3565b6040517f97e2c6aad4ce5d562ebfaa00db6b9e0fb66ea5d8162ed5b243f51a2e03086f0290610a5b908390612c99565b908152604051908190036020019020805460ff19169055610a8760008051602061320f83398151915290565b600083815260019190910160205260408120610aa29161271f565b817fcf95bbfe6f870f8cc40482dc3dccdafd268f0e9ce0a4f24ea1bea9be64e505ff82604051610ad29190612bce565b60405180910390a25050565b600f60f81b6060806000808083610af3611193565b97989097965046955030945091925090565b60008181527f97e2c6aad4ce5d562ebfaa00db6b9e0fb66ea5d8162ed5b243f51a2e03086f0160205260409020805460609190610b4190612e06565b80601f0160208091040260200160405190810160405280929190818152602001828054610b6d90612e06565b8015610bba5780601f10610b8f57610100808354040283529160200191610bba565b820191906000526020600020905b815481529060010190602001808311610b9d57829003601f168201915b50505050509050919050565b60006001600160e01b031982166329565e3b60e01b1480610bf757506001600160e01b031982166303c3cfc960e21b145b80610c1257506001600160e01b0319821663396f1dad60e11b145b80610c2d57506001600160e01b0319821663278f794360e11b145b15610c3a57506001919050565b506000919050565b600060008051602061320f833981519152604080516001600160a01b0385166020820152600292909201910160408051601f198184030181529082905261059b91612c99565b33735ff137d4b0fdcd49dca30c7cf57e578a026d278914610cab57610cab610e3e565b6108fa848484848080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250610fb092505050565b33735ff137d4b0fdcd49dca30c7cf57e578a026d278914610d1f576040516282b42960e81b815260040160405180910390fd5b6000610d2e6004828486612d27565b610d3791612d51565b9050610d4281610bc6565b610d6b57604051631d8370a360e11b81526001600160e01b0319821660048201526024016107a3565b6106dc30600085858080601f016020809104026020016040519081016040528093929190818152602001838380828437600092019190915250610fb092505050565b6000610501826111da565b6000806000610dc5611193565b8151602080840191909120825182840120604080517f8b73c3c69bb8fe3d512ecc4cf759cc79239f7b179b0ffacaa9a75d522b39400f9481019490945283019190915260608201524660808201523060a0820152919350915060c001604051602081830303815290604052805190602001209250505090565b610e4733610c42565b80610e5157503330145b15610e5857565b6040516282b42960e81b815260040160405180910390fd5b61053c8160008051602061320f8339815191525b8054906000610e9283612e50565b91905055611210565b600080610eaa83850185612e69565b90506000610ebb8260000151610b05565b90508051602003610f1a576001600160a01b03610ed782612ef5565b1115610ef8578060405163bff1ac6560e01b81526004016107a39190612bce565b600060208201519050610f10818885602001516112df565b9350505050610572565b8051604003610f955760008082806020019051810190610f3a9190612f19565b9150915060008460200151806020019051810190610f589190612f82565b9050610f8989604051602001610f7091815260200190565b60405160208183030381529060405260008386866113e4565b95505050505050610572565b806040516327755b9160e11b81526004016107a39190612bce565b600080846001600160a01b03168484604051610fcc9190612c99565b60006040518083038185875af1925050503d8060008114611009576040519150601f19603f3d011682016040523d82523d6000602084013e61100e565b606091505b5091509150816108f857805160208201fd5b61053c610e3e565b600061103382611754565b805190602001209050919050565b60005b81518110156105d95781818151811061105f5761105f612cb5565b602002602001015151602014158015611093575081818151811061108557611085612cb5565b602002602001015151604014155b156110cc578181815181106110aa576110aa612cb5565b60200260200101516040516327755b9160e11b81526004016107a39190612bce565b8181815181106110de576110de612cb5565b602002602001015151602014801561112057506001600160a01b03801682828151811061110d5761110d612cb5565b602002602001015161111e90612ef5565b115b156111595781818151811061113757611137612cb5565b602002602001015160405163bff1ac6560e01b81526004016107a39190612bce565b61118b82828151811061116e5761116e612cb5565b6020026020010151610e8460008051602061320f83398151915290565b600101611044565b604080518082018252601581527410dbda5b98985cd94814db585c9d0815d85b1b195d605a1b602080830191909152825180840190935260018352603160f81b9083015291565b60006111e4610db8565b6111ed83611827565b60405161190160f01b602082015260228101929092526042820152606201610934565b61121982610579565b15611239578160405163468b12ad60e11b81526004016107a39190612bce565b600160008051602061320f8339815191526002018360405161125b9190612c99565b908152604051908190036020019020805491151560ff199092169190911790558161129160008051602061320f83398151915290565b600083815260019190910160205260409020906112ae908261308d565b50807f38109edc26e166b5579352ce56a50813177eb25208fd90d61f2f37838622022083604051610ad29190612bce565b6001600160a01b03909216916000831561057257604051836000526020830151604052604083510361134f576040830151601b8160ff1c016020528060011b60011c60605250602060016080600060015afa805186183d151761134d57506000606052604052506001610572565b505b604183510361139557606083015160001a6020526040830151606052602060016080600060015afa805186183d151761139357506000606052604052506001610572565b505b600060605280604052631626ba7e60e01b808252846004830152602482016040815284516020018060448501828860045afa505060208160443d01858a5afa9051909114169150509392505050565b60007f7fffffff800000007fffffffffffffffde737d56d38bcf4279dce5617e3192a88460a00151111561141a5750600061174b565b606084015160009061143d9061143181601561314c565b60208801519190611862565b90507fff1a2a9176d650e4a99dedb58f1793003935130579fe17b5a3f698ac5b00e63481805190602001201461147757600091505061174b565b6000611485886001806118c8565b604051602001611495919061315f565b604051602081830303815290604052905060006114cd8760400151835189604001516114c1919061314c565b60208a01519190611862565b905081805190602001208180519060200120146114f0576000935050505061174b565b86518051600160f81b918291602090811061150d5761150d612cb5565b0160200151166001600160f81b0319161461152e576000935050505061174b565b878015611566575086518051600160fa1b918291602090811061155357611553612cb5565b0160200151166001600160f81b03191614155b15611577576000935050505061174b565b60006002886020015160405161158d9190612c99565b602060405180830381855afa1580156115aa573d6000803e3d6000fd5b5050506040513d601f19601f820116820180604052508101906115cd91906131a0565b9050600060028960000151836040516020016115ea9291906131b9565b60408051601f198184030181529082905261160491612c99565b602060405180830381855afa158015611621573d6000803e3d6000fd5b5050506040513d601f19601f8201168201806040525081019061164491906131a0565b6080808b015160a0808d015160408051602081018790529081019390935260608301529181018b905290810189905290915060009060c00160405160208183030381529060405290506000806101006001600160a01b0316836040516116aa9190612c99565b600060405180830381855afa9150503d80600081146116e5576040519150601f19603f3d011682016040523d82523d6000602084013e6116ea565b606091505b508051919350915015158280156116fe5750805b1561172a578180602001905181019061171791906131a0565b600114995050505050505050505061174b565b61173f858e608001518f60a001518f8f6119bd565b99505050505050505050505b95945050505050565b606081356020830135600061177461176f6040870187612ce1565b611aa0565b9050600061178861176f6060880188612ce1565b9050608086013560a087013560c088013560e08901356101008a013560006117b761176f6101208e018e612ce1565b604080516001600160a01b039c909c1660208d01528b81019a909a5260608b019890985250608089019590955260a088019390935260c087019190915260e08601526101008501526101208401526101408084019190915281518084039091018152610160909201905292915050565b604080517f9b493d222105fee7df163ab5d57f0bf1ffd2da04dd5fafbe10b54c41c1adc6576020820152908101829052600090606001610934565b60608351828111611871578092505b83811161187c578093505b5081831015610572575060405182820380825293830193601f19601f820181165b868101518482015281018061189d5750600083830160200152603f9091011681016040529392505050565b606083518015610814576003600282010460021b60405192507f4142434445464748494a4b4c4d4e4f505152535455565758595a616263646566601f526106708515027f6768696a6b6c6d6e6f707172737475767778797a303132333435363738392d5f18603f52602083018181018388602001018051600082525b60038a0199508951603f8160121c1651600053603f81600c1c1651600153603f8160061c1651600253603f811651600353506000518452600484019350828410611944579052602001604052613d3d60f01b60038406600204808303919091526000861515909102918290035290038252509392505050565b60008415806119da57506000805160206131ef8339815191528510155b806119e3575083155b806119fc57506000805160206131ef8339815191528410155b15611a095750600061174b565b611a138383611ab3565b611a1f5750600061174b565b6000611a2a85611bad565b905060006000805160206131ef833981519152828909905060006000805160206131ef83398151915283890990506000611a6687878585611c1f565b90506000805160206131ef833981519152611a8f8a6000805160206131ef8339815191526131db565b8208159a9950505050505050505050565b6000604051828085833790209392505050565b600082158015611ac1575081155b80611ad95750600160601b63ffffffff60c01b031983145b80611af15750600160601b63ffffffff60c01b031982145b15611afe57506000610501565b6000600160601b63ffffffff60c01b031983840990506000600160601b63ffffffff60c01b0319807fffffffff00000001000000000000000000000000fffffffffffffffffffffffc8709600160601b63ffffffff60c01b031987600160601b63ffffffff60c01b0319898a0909089050600160601b63ffffffff60c01b03197f5ac635d8aa3a93e7b3ebbd55769886bc651d06b0cc53b0f63bce3c3e27d2604b820891909114949350505050565b600060405160208152602080820152602060408201528260608201527fffffffff00000000ffffffffffffffffbce6faada7179e84f3b9cac2fc63254f60808201526000805160206131ef83398151915260a082015260208160c0836005600019fa611c1857600080fd5b5192915050565b600080808060ff818088158015611c34575087155b15611c4857600096505050505050506122e1565b611c947f6b17d1f2e12c4247f8bce6e563a440f277037d812deb33a0f4a13945d898c2967f4fe342e2fe1a7f9b8ee7eb4a7c0f9e162bce33576b315ececbb6406837bf51f58d8d6122e9565b909250905081158015611ca5575080155b15611cd3576000805160206131ef833981519152886000805160206131ef833981519152038a089850600097505b600189841c16600189851c1660011b015b80611d065760018403935060018a851c1660018a861c1660011b019050611ce4565b50600189841c16600189851c1660011b01955060018603611d68577f6b17d1f2e12c4247f8bce6e563a440f277037d812deb33a0f4a13945d898c29696507f4fe342e2fe1a7f9b8ee7eb4a7c0f9e162bce33576b315ececbb6406837bf51f593505b60028603611d77578a96508993505b60038603611d86578196508093505b60018303925060019550600194505b82600019111561226a57600160601b63ffffffff60c01b031984600209600160601b63ffffffff60c01b0319818209600160601b63ffffffff60c01b0319818a09600160601b63ffffffff60c01b03198284099250600160601b63ffffffff60c01b031980600160601b63ffffffff60c01b03198b8d08600160601b63ffffffff60c01b03198c600160601b63ffffffff60c01b0319038e0809600309600160601b63ffffffff60c01b03198985099850600160601b63ffffffff60c01b03198a84099950600160601b63ffffffff60c01b031980836002600160601b0363ffffffff60c01b031909600160601b63ffffffff60c01b0319838409089a50600160601b63ffffffff60c01b03198083600160601b63ffffffff60c01b0319038d0882099250600160601b63ffffffff60c01b031983600160601b63ffffffff60c01b03198a870908975060018d881c1660018d891c1660011b01905080611f125787600160601b63ffffffff60c01b03190397505050505061225f565b60018103611f61577f6b17d1f2e12c4247f8bce6e563a440f277037d812deb33a0f4a13945d898c29693507f4fe342e2fe1a7f9b8ee7eb4a7c0f9e162bce33576b315ececbb6406837bf51f592505b60028103611f70578e93508d92505b60038103611f7f578593508492505b89611f98575091985060019750879650945061225f9050565b600160601b63ffffffff60c01b031988600160601b63ffffffff60c01b03198b860908600160601b63ffffffff60c01b03198c600160601b63ffffffff60c01b031903600160601b63ffffffff60c01b03198d880908935080612151578361215157600160601b63ffffffff60c01b0319896002600160601b0363ffffffff60c01b0319099450600160601b63ffffffff60c01b03198586099350600160601b63ffffffff60c01b0319848d099250600160601b63ffffffff60c01b03198486099450600160601b63ffffffff60c01b0319808c600160601b63ffffffff60c01b0319038e08600160601b63ffffffff60c01b03198d8f08099050600160601b63ffffffff60c01b0319816003099150600160601b63ffffffff60c01b03198a86099950600160601b63ffffffff60c01b03198b85099a50600160601b63ffffffff60c01b031980846002600160601b0363ffffffff60c01b031909600160601b63ffffffff60c01b0319848509089b50600160601b63ffffffff60c01b0319808d600160601b63ffffffff60c01b031903850883099350600160601b63ffffffff60c01b0319808a870985089850505050505061225f565b600160601b63ffffffff60c01b03198485099150600160601b63ffffffff60c01b0319848309600160601b63ffffffff60c01b0319838d099b50600160601b63ffffffff60c01b0319818c099a50600160601b63ffffffff60c01b0319838e09600160601b63ffffffff60c01b031980826002600160601b0363ffffffff60c01b031909600160601b63ffffffff60c01b031984600160601b63ffffffff60c01b031903600160601b63ffffffff60c01b031987880908089350600160601b63ffffffff60c01b031980838d09600160601b63ffffffff60c01b031985600160601b63ffffffff60c01b031988600160601b63ffffffff60c01b031903860809089a50505050809a50505050505b600183039250611d95565b60405186606082015260208152602080820152602060408201526002600160601b0363ffffffff60c01b03196080820152600160601b63ffffffff60c01b031960a082015260208160c0836005600019fa6122c457600080fd5b600160601b63ffffffff60c01b0319815189099750505050505050505b949350505050565b60008080808661230057858593509350505061236e565b8461231257878793509350505061236e565b858814801561232057508487145b15612341576123328888600180612377565b929a509098509250905061235b565b61235088886001808a8a6124d2565b929a50909850925090505b61236788888484612656565b9350935050505b94509492505050565b600080600080600160601b63ffffffff60c01b0319876002099350600160601b63ffffffff60c01b03198485099150600160601b63ffffffff60c01b03198289099050600160601b63ffffffff60c01b03198285099250600160601b63ffffffff60c01b03198683099150600160601b63ffffffff60c01b031980600160601b63ffffffff60c01b0319888b08600160601b63ffffffff60c01b031989600160601b63ffffffff60c01b0319038c08096003099550600160601b63ffffffff60c01b031980826002600160601b0363ffffffff60c01b031909600160601b63ffffffff60c01b0319888909089350600160601b63ffffffff60c01b03198085600160601b63ffffffff60c01b031903830887099750600160601b63ffffffff60c01b03198584099050600160601b63ffffffff60c01b031980888509600160601b63ffffffff60c01b03190389089250945094509450949050565b600080600080886000036124f157508492508391506001905080612649565b600160601b63ffffffff60c01b0319988903988981898809089450600160601b63ffffffff60c01b03198a600160601b63ffffffff60c01b031903600160601b63ffffffff60c01b03198a8909089550600160601b63ffffffff60c01b03198687099350600160601b63ffffffff60c01b03198685099250600160601b63ffffffff60c01b03198489099150600160601b63ffffffff60c01b03198388099050600160601b63ffffffff60c01b0319848b099750600160601b63ffffffff60c01b031980896002600160601b0363ffffffff60c01b031909600160601b63ffffffff60c01b031985600160601b63ffffffff60c01b031903600160601b63ffffffff60c01b0319898a0908089350600160601b63ffffffff60c01b031980848b09600160601b63ffffffff60c01b031987600160601b63ffffffff60c01b031988600160601b63ffffffff60c01b0319038d08090892505b9650965096509692505050565b6000806000612664846126c3565b9050600160601b63ffffffff60c01b031981870991506000600160601b63ffffffff60c01b03198287099050600160601b63ffffffff60c01b03198182099150600160601b63ffffffff60c01b03198289099350505094509492505050565b600060405160208152602080820152602060408201528260608201526002600160601b0363ffffffff60c01b03196080820152600160601b63ffffffff60c01b031960a082015260208160c0836005600019fa611c1857600080fd5b50805461272b90612e06565b6000825580601f1061273b575050565b601f01602090049060005260206000209081019061053c91905b808211156109ad5760008155600101612755565b6000806040838503121561277c57600080fd5b50508035926020909101359150565b80356001600160a01b03811681146127a257600080fd5b919050565b6000602082840312156127b957600080fd5b6105728261278b565b60008083601f8401126127d457600080fd5b5081356001600160401b038111156127eb57600080fd5b60208301915083602082850101111561280357600080fd5b9250929050565b60008060006040848603121561281f57600080fd5b8335925060208401356001600160401b0381111561283c57600080fd5b612848868287016127c2565b9497909650939450505050565b634e487b7160e01b600052604160045260246000fd5b60405160c081016001600160401b038111828210171561288d5761288d612855565b60405290565b604051601f8201601f191681016001600160401b03811182821017156128bb576128bb612855565b604052919050565b60006001600160401b038211156128dc576128dc612855565b50601f01601f191660200190565b600082601f8301126128fb57600080fd5b813561290e612909826128c3565b612893565b81815284602083860101111561292357600080fd5b816020850160208301376000918101602001919091529392505050565b60006020828403121561295257600080fd5b81356001600160401b0381111561296857600080fd5b6122e1848285016128ea565b60008083601f84011261298657600080fd5b5081356001600160401b0381111561299d57600080fd5b6020830191508360208260051b850101111561280357600080fd5b600080602083850312156129cb57600080fd5b82356001600160401b038111156129e157600080fd5b6129ed85828601612974565b90969095509350505050565b60006101608284031215612a0c57600080fd5b50919050565b600080600060608486031215612a2757600080fd5b83356001600160401b03811115612a3d57600080fd5b612a49868287016129f9565b9660208601359650604090950135949350505050565b600080600060408486031215612a7457600080fd5b612a7d8461278b565b925060208401356001600160401b0381111561283c57600080fd5b600060208284031215612aaa57600080fd5b81356001600160401b03811115612ac057600080fd5b6122e1848285016129f9565b600060208284031215612ade57600080fd5b5035919050565b60005b83811015612b00578181015183820152602001612ae8565b50506000910152565b60008151808452612b21816020860160208601612ae5565b601f01601f19169290920160200192915050565b60ff60f81b881681526000602060e06020840152612b5660e084018a612b09565b8381036040850152612b68818a612b09565b606085018990526001600160a01b038816608086015260a0850187905284810360c08601528551808252602080880193509091019060005b81811015612bbc57835183529284019291840191600101612ba0565b50909c9b505050505050505050505050565b6020815260006105726020830184612b09565b600060208284031215612bf357600080fd5b81356001600160e01b03198116811461057257600080fd5b60008060008060608587031215612c2157600080fd5b612c2a8561278b565b93506020850135925060408501356001600160401b03811115612c4c57600080fd5b612c58878288016127c2565b95989497509550505050565b60008060208385031215612c7757600080fd5b82356001600160401b03811115612c8d57600080fd5b6129ed858286016127c2565b60008251612cab818460208701612ae5565b9190910192915050565b634e487b7160e01b600052603260045260246000fd5b60008235605e19833603018112612cab57600080fd5b6000808335601e19843603018112612cf857600080fd5b8301803591506001600160401b03821115612d1257600080fd5b60200191503681900382131561280357600080fd5b60008085851115612d3757600080fd5b83861115612d4457600080fd5b5050820193919092039150565b6001600160e01b03198135818116916004851015612d795780818660040360031b1b83161692505b505092915050565b60006001600160401b0380841115612d9b57612d9b612855565b8360051b6020612dad60208301612893565b86815291850191602081019036841115612dc657600080fd5b865b84811015612dfa57803586811115612de05760008081fd5b612dec36828b016128ea565b845250918301918301612dc8565b50979650505050505050565b600181811c90821680612e1a57607f821691505b602082108103612a0c57634e487b7160e01b600052602260045260246000fd5b634e487b7160e01b600052601160045260246000fd5b600060018201612e6257612e62612e3a565b5060010190565b600060208284031215612e7b57600080fd5b81356001600160401b0380821115612e9257600080fd5b9083019060408286031215612ea657600080fd5b604051604081018181108382111715612ec157612ec1612855565b60405282358152602083013582811115612eda57600080fd5b612ee6878286016128ea565b60208301525095945050505050565b80516020808301519190811015612a0c5760001960209190910360031b1b16919050565b60008060408385031215612f2c57600080fd5b505080516020909101519092909150565b600082601f830112612f4e57600080fd5b8151612f5c612909826128c3565b818152846020838601011115612f7157600080fd5b6122e1826020830160208701612ae5565b600060208284031215612f9457600080fd5b81516001600160401b0380821115612fab57600080fd5b9083019060c08286031215612fbf57600080fd5b612fc761286b565b825182811115612fd657600080fd5b612fe287828601612f3d565b825250602083015182811115612ff757600080fd5b61300387828601612f3d565b60208301525060408301516040820152606083015160608201526080830151608082015260a083015160a082015280935050505092915050565b601f8211156106dc576000816000526020600020601f850160051c810160208610156130665750805b601f850160051c820191505b8181101561308557828155600101613072565b505050505050565b81516001600160401b038111156130a6576130a6612855565b6130ba816130b48454612e06565b8461303d565b602080601f8311600181146130ef57600084156130d75750858301515b600019600386901b1c1916600185901b178555613085565b600085815260208120601f198616915b8281101561311e578886015182559484019460019091019084016130ff565b508582101561313c5787850151600019600388901b60f8161c191681555b5050505050600190811b01905550565b8082018082111561050157610501612e3a565b6c1131b430b63632b733b2911d1160991b8152815160009061318881600d850160208701612ae5565b601160f91b600d939091019283015250600e01919050565b6000602082840312156131b257600080fd5b5051919050565b600083516131cb818460208801612ae5565b9190910191825250602001919050565b8181038181111561050157610501612e3a56feffffffff00000000ffffffffffffffffbce6faada7179e84f3b9cac2fc63255197e2c6aad4ce5d562ebfaa00db6b9e0fb66ea5d8162ed5b243f51a2e03086f00a26469706673582212206267bdd6ae13c948b83275fcdafdc1366dd287cbf41ef689e1d49904a10ea33e64736f6c6343000817003397e2c6aad4ce5d562ebfaa00db6b9e0fb66ea5d8162ed5b243f51a2e03086f00
\ No newline at end of file
diff --git a/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletFactory.java b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletFactory.java
new file mode 100644
index 000000000..ffb496d3e
--- /dev/null
+++ b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletFactory.java
@@ -0,0 +1,166 @@
+package org.xmtp.android.library.artifact;
+
+import java.math.BigInteger;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
+
+import org.web3j.abi.FunctionEncoder;
+import org.web3j.abi.TypeReference;
+import org.web3j.abi.datatypes.Address;
+import org.web3j.abi.datatypes.Function;
+import org.web3j.abi.datatypes.Type;
+import org.web3j.abi.datatypes.generated.Bytes32;
+import org.web3j.crypto.Credentials;
+import org.web3j.protocol.Web3j;
+import org.web3j.protocol.core.RemoteCall;
+import org.web3j.protocol.core.RemoteFunctionCall;
+import org.web3j.protocol.core.methods.response.TransactionReceipt;
+import org.web3j.tx.Contract;
+import org.web3j.tx.TransactionManager;
+import org.web3j.tx.gas.ContractGasProvider;
+
+/**
+ * Auto generated code.
+ *
Do not modify!
+ *
Please use the web3j command line tools,
+ * or the org.web3j.codegen.SolidityFunctionWrapperGenerator in the
+ * codegen module to update.
+ *
+ *
Generated with web3j version 1.6.1.
+ */
+@SuppressWarnings("rawtypes")
+public class CoinbaseSmartWalletFactory extends Contract {
+ public static final String BINARY = "0x60a06040526040516105eb3803806105eb83398101604081905261002291610033565b6001600160a01b0316608052610063565b60006020828403121561004557600080fd5b81516001600160a01b038116811461005c57600080fd5b9392505050565b60805161056061008b6000396000818160a60152818161013c015261023b01526105606000f3fe60806040526004361061003f5760003560e01c8063250b1b41146100445780633ffba36f146100815780635c60da1b14610094578063db4c545e146100c8575b600080fd5b34801561005057600080fd5b5061006461005f3660046103b7565b6100eb565b6040516001600160a01b0390911681526020015b60405180910390f35b61006461008f3660046103b7565b610111565b3480156100a057600080fd5b506100647f000000000000000000000000000000000000000000000000000000000000000081565b3480156100d457600080fd5b506100dd6101e6565b604051908152602001610078565b60006101096100f86101e6565b61010386868661027b565b306102b1565b949350505050565b600082810361013357604051633c776be160e01b815260040160405180910390fd5b60008061016b347f000000000000000000000000000000000000000000000000000000000000000061016689898961027b565b6102d3565b935091508290508115156000036101dd57604051633796f38760e11b81526001600160a01b03841690636f2de70e906101aa90899089906004016104f2565b600060405180830381600087803b1580156101c457600080fd5b505af11580156101d8573d6000803e3d6000fd5b505050505b50509392505050565b604080517fcc3735a920a3ca505d382bbc545af43d6000803e6038573d6000fd5b3d6000f360609081527f5155f3363d3d373d3d363d7f360894a13ba1a3210667c828492db98dca3e207683526160096020527f0000000000000000000000000000000000000000000000000000000000000000601e5268603d3d8160223d3973600a52605f60212091909252600090915290565b600083838360405160200161029293929190610506565b6040516020818303038152906040528051906020012090509392505050565b600060ff60005350603592835260601b60015260155260556000908120915290565b6000806040517fcc3735a920a3ca505d382bbc545af43d6000803e6038573d6000fd5b3d6000f36060527f5155f3363d3d373d3d363d7f360894a13ba1a3210667c828492db98dca3e207660405261600960205284601e5268603d3d8160223d3973600a52605f60212060358201523060581b815260ff8153836015820152605581209150813b61037f5783605f602188f591508161037a5763301164256000526004601cfd5b6103a5565b6001925085156103a55760003860003889865af16103a55763b12d13eb6000526004601cfd5b80604052506000606052935093915050565b6000806000604084860312156103cc57600080fd5b833567ffffffffffffffff808211156103e457600080fd5b818601915086601f8301126103f857600080fd5b81358181111561040757600080fd5b8760208260051b850101111561041c57600080fd5b6020928301989097509590910135949350505050565b81835281816020850137506000828201602090810191909152601f909101601f19169091010190565b6000838385526020808601955060208560051b8301018460005b878110156104e557848303601f19018952813536889003601e1901811261049b57600080fd5b8701848101903567ffffffffffffffff8111156104b757600080fd5b8036038213156104c657600080fd5b6104d1858284610432565b9a86019a9450505090830190600101610475565b5090979650505050505050565b60208152600061010960208301848661045b565b60408152600061051a60408301858761045b565b905082602083015294935050505056fea264697066735822122098bae64e62859ac8d5ed01c4927e5fce406f632b517c86f038f06fef8355dba164736f6c63430008170033";
+
+ private static String librariesLinkedBinary;
+
+ public static final String FUNC_CREATEACCOUNT = "createAccount";
+
+ public static final String FUNC_GETADDRESS = "getAddress";
+
+ public static final String FUNC_IMPLEMENTATION = "implementation";
+
+ public static final String FUNC_INITCODEHASH = "initCodeHash";
+
+ @Deprecated
+ protected CoinbaseSmartWalletFactory(String contractAddress, Web3j web3j,
+ Credentials credentials, BigInteger gasPrice, BigInteger gasLimit) {
+ super(BINARY, contractAddress, web3j, credentials, gasPrice, gasLimit);
+ }
+
+ protected CoinbaseSmartWalletFactory(String contractAddress, Web3j web3j,
+ Credentials credentials, ContractGasProvider contractGasProvider) {
+ super(BINARY, contractAddress, web3j, credentials, contractGasProvider);
+ }
+
+ @Deprecated
+ protected CoinbaseSmartWalletFactory(String contractAddress, Web3j web3j,
+ TransactionManager transactionManager, BigInteger gasPrice, BigInteger gasLimit) {
+ super(BINARY, contractAddress, web3j, transactionManager, gasPrice, gasLimit);
+ }
+
+ protected CoinbaseSmartWalletFactory(String contractAddress, Web3j web3j,
+ TransactionManager transactionManager, ContractGasProvider contractGasProvider) {
+ super(BINARY, contractAddress, web3j, transactionManager, contractGasProvider);
+ }
+
+ public RemoteFunctionCall createAccount(List owners,
+ BigInteger nonce, BigInteger weiValue) {
+ final Function function = new Function(
+ FUNC_CREATEACCOUNT,
+ Arrays.asList(new org.web3j.abi.datatypes.DynamicArray(
+ org.web3j.abi.datatypes.DynamicBytes.class,
+ org.web3j.abi.Utils.typeMap(owners, org.web3j.abi.datatypes.DynamicBytes.class)),
+ new org.web3j.abi.datatypes.generated.Uint256(nonce)),
+ Collections.>emptyList());
+ return executeRemoteCallTransaction(function, weiValue);
+ }
+
+ public RemoteFunctionCall getAddress(List owners, BigInteger nonce) {
+ final Function function = new Function(FUNC_GETADDRESS,
+ Arrays.asList(new org.web3j.abi.datatypes.DynamicArray(
+ org.web3j.abi.datatypes.DynamicBytes.class,
+ org.web3j.abi.Utils.typeMap(owners, org.web3j.abi.datatypes.DynamicBytes.class)),
+ new org.web3j.abi.datatypes.generated.Uint256(nonce)),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, String.class);
+ }
+
+ public RemoteFunctionCall implementation() {
+ final Function function = new Function(FUNC_IMPLEMENTATION,
+ Arrays.asList(),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, String.class);
+ }
+
+ public RemoteFunctionCall initCodeHash() {
+ final Function function = new Function(FUNC_INITCODEHASH,
+ Arrays.asList(),
+ Arrays.>asList(new TypeReference() {
+ }));
+ return executeRemoteCallSingleValueReturn(function, byte[].class);
+ }
+
+ @Deprecated
+ public static CoinbaseSmartWalletFactory load(String contractAddress, Web3j web3j,
+ Credentials credentials, BigInteger gasPrice, BigInteger gasLimit) {
+ return new CoinbaseSmartWalletFactory(contractAddress, web3j, credentials, gasPrice, gasLimit);
+ }
+
+ @Deprecated
+ public static CoinbaseSmartWalletFactory load(String contractAddress, Web3j web3j,
+ TransactionManager transactionManager, BigInteger gasPrice, BigInteger gasLimit) {
+ return new CoinbaseSmartWalletFactory(contractAddress, web3j, transactionManager, gasPrice, gasLimit);
+ }
+
+ public static CoinbaseSmartWalletFactory load(String contractAddress, Web3j web3j,
+ Credentials credentials, ContractGasProvider contractGasProvider) {
+ return new CoinbaseSmartWalletFactory(contractAddress, web3j, credentials, contractGasProvider);
+ }
+
+ public static CoinbaseSmartWalletFactory load(String contractAddress, Web3j web3j,
+ TransactionManager transactionManager, ContractGasProvider contractGasProvider) {
+ return new CoinbaseSmartWalletFactory(contractAddress, web3j, transactionManager, contractGasProvider);
+ }
+
+ public static RemoteCall deploy(Web3j web3j,
+ Credentials credentials, ContractGasProvider contractGasProvider,
+ BigInteger initialWeiValue, String erc4337) {
+ String encodedConstructor = FunctionEncoder.encodeConstructor(Arrays.asList(new org.web3j.abi.datatypes.Address(160, erc4337)));
+ return deployRemoteCall(CoinbaseSmartWalletFactory.class, web3j, credentials, contractGasProvider, getDeploymentBinary(), encodedConstructor, initialWeiValue);
+ }
+
+ public static RemoteCall deploy(Web3j web3j,
+ TransactionManager transactionManager, ContractGasProvider contractGasProvider,
+ BigInteger initialWeiValue, String erc4337) {
+ String encodedConstructor = FunctionEncoder.encodeConstructor(Arrays.asList(new org.web3j.abi.datatypes.Address(160, erc4337)));
+ return deployRemoteCall(CoinbaseSmartWalletFactory.class, web3j, transactionManager, contractGasProvider, getDeploymentBinary(), encodedConstructor, initialWeiValue);
+ }
+
+ @Deprecated
+ public static RemoteCall deploy(Web3j web3j,
+ Credentials credentials, BigInteger gasPrice, BigInteger gasLimit,
+ BigInteger initialWeiValue, String erc4337) {
+ String encodedConstructor = FunctionEncoder.encodeConstructor(Arrays.asList(new org.web3j.abi.datatypes.Address(160, erc4337)));
+ return deployRemoteCall(CoinbaseSmartWalletFactory.class, web3j, credentials, gasPrice, gasLimit, getDeploymentBinary(), encodedConstructor, initialWeiValue);
+ }
+
+ @Deprecated
+ public static RemoteCall deploy(Web3j web3j,
+ TransactionManager transactionManager, BigInteger gasPrice, BigInteger gasLimit,
+ BigInteger initialWeiValue, String erc4337) {
+ String encodedConstructor = FunctionEncoder.encodeConstructor(Arrays.asList(new org.web3j.abi.datatypes.Address(160, erc4337)));
+ return deployRemoteCall(CoinbaseSmartWalletFactory.class, web3j, transactionManager, gasPrice, gasLimit, getDeploymentBinary(), encodedConstructor, initialWeiValue);
+ }
+
+ private static String getDeploymentBinary() {
+ if (librariesLinkedBinary != null) {
+ return librariesLinkedBinary;
+ } else {
+ return BINARY;
+ }
+ }
+}
diff --git a/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletFactory.json b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletFactory.json
new file mode 100644
index 000000000..eca83520b
--- /dev/null
+++ b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletFactory.json
@@ -0,0 +1,92 @@
+ [
+ {
+ "type": "constructor",
+ "inputs": [
+ {
+ "name": "erc4337",
+ "type": "address",
+ "internalType": "address"
+ }
+ ],
+ "stateMutability": "payable"
+ },
+ {
+ "type": "function",
+ "name": "createAccount",
+ "inputs": [
+ {
+ "name": "owners",
+ "type": "bytes[]",
+ "internalType": "bytes[]"
+ },
+ {
+ "name": "nonce",
+ "type": "uint256",
+ "internalType": "uint256"
+ }
+ ],
+ "outputs": [
+ {
+ "name": "account",
+ "type": "address",
+ "internalType": "contract CoinbaseSmartWallet"
+ }
+ ],
+ "stateMutability": "payable"
+ },
+ {
+ "type": "function",
+ "name": "getAddress",
+ "inputs": [
+ {
+ "name": "owners",
+ "type": "bytes[]",
+ "internalType": "bytes[]"
+ },
+ {
+ "name": "nonce",
+ "type": "uint256",
+ "internalType": "uint256"
+ }
+ ],
+ "outputs": [
+ {
+ "name": "predicted",
+ "type": "address",
+ "internalType": "address"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "implementation",
+ "inputs": [],
+ "outputs": [
+ {
+ "name": "",
+ "type": "address",
+ "internalType": "address"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "function",
+ "name": "initCodeHash",
+ "inputs": [],
+ "outputs": [
+ {
+ "name": "result",
+ "type": "bytes32",
+ "internalType": "bytes32"
+ }
+ ],
+ "stateMutability": "view"
+ },
+ {
+ "type": "error",
+ "name": "OwnerRequired",
+ "inputs": []
+ }
+ ]
\ No newline at end of file
diff --git a/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletFactoryBinary.txt b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletFactoryBinary.txt
new file mode 100644
index 000000000..fb4d22ac9
--- /dev/null
+++ b/library/src/androidTest/java/org/xmtp/android/library/artifact/CoinbaseSmartWalletFactoryBinary.txt
@@ -0,0 +1 @@
+0x60a06040526040516105eb3803806105eb83398101604081905261002291610033565b6001600160a01b0316608052610063565b60006020828403121561004557600080fd5b81516001600160a01b038116811461005c57600080fd5b9392505050565b60805161056061008b6000396000818160a60152818161013c015261023b01526105606000f3fe60806040526004361061003f5760003560e01c8063250b1b41146100445780633ffba36f146100815780635c60da1b14610094578063db4c545e146100c8575b600080fd5b34801561005057600080fd5b5061006461005f3660046103b7565b6100eb565b6040516001600160a01b0390911681526020015b60405180910390f35b61006461008f3660046103b7565b610111565b3480156100a057600080fd5b506100647f000000000000000000000000000000000000000000000000000000000000000081565b3480156100d457600080fd5b506100dd6101e6565b604051908152602001610078565b60006101096100f86101e6565b61010386868661027b565b306102b1565b949350505050565b600082810361013357604051633c776be160e01b815260040160405180910390fd5b60008061016b347f000000000000000000000000000000000000000000000000000000000000000061016689898961027b565b6102d3565b935091508290508115156000036101dd57604051633796f38760e11b81526001600160a01b03841690636f2de70e906101aa90899089906004016104f2565b600060405180830381600087803b1580156101c457600080fd5b505af11580156101d8573d6000803e3d6000fd5b505050505b50509392505050565b604080517fcc3735a920a3ca505d382bbc545af43d6000803e6038573d6000fd5b3d6000f360609081527f5155f3363d3d373d3d363d7f360894a13ba1a3210667c828492db98dca3e207683526160096020527f0000000000000000000000000000000000000000000000000000000000000000601e5268603d3d8160223d3973600a52605f60212091909252600090915290565b600083838360405160200161029293929190610506565b6040516020818303038152906040528051906020012090509392505050565b600060ff60005350603592835260601b60015260155260556000908120915290565b6000806040517fcc3735a920a3ca505d382bbc545af43d6000803e6038573d6000fd5b3d6000f36060527f5155f3363d3d373d3d363d7f360894a13ba1a3210667c828492db98dca3e207660405261600960205284601e5268603d3d8160223d3973600a52605f60212060358201523060581b815260ff8153836015820152605581209150813b61037f5783605f602188f591508161037a5763301164256000526004601cfd5b6103a5565b6001925085156103a55760003860003889865af16103a55763b12d13eb6000526004601cfd5b80604052506000606052935093915050565b6000806000604084860312156103cc57600080fd5b833567ffffffffffffffff808211156103e457600080fd5b818601915086601f8301126103f857600080fd5b81358181111561040757600080fd5b8760208260051b850101111561041c57600080fd5b6020928301989097509590910135949350505050565b81835281816020850137506000828201602090810191909152601f909101601f19169091010190565b6000838385526020808601955060208560051b8301018460005b878110156104e557848303601f19018952813536889003601e1901811261049b57600080fd5b8701848101903567ffffffffffffffff8111156104b757600080fd5b8036038213156104c657600080fd5b6104d1858284610432565b9a86019a9450505090830190600101610475565b5090979650505050505050565b60208152600061010960208301848661045b565b60408152600061051a60408301858761045b565b905082602083015294935050505056fea264697066735822122098bae64e62859ac8d5ed01c4927e5fce406f632b517c86f038f06fef8355dba164736f6c63430008170033
\ No newline at end of file
diff --git a/library/src/androidTest/res/xml/network_security_config.xml b/library/src/androidTest/res/xml/network_security_config.xml
new file mode 100644
index 000000000..ef218b2ba
--- /dev/null
+++ b/library/src/androidTest/res/xml/network_security_config.xml
@@ -0,0 +1,8 @@
+
+
+
+ 10.0.2.2
+ 127.0.0.1
+ localhost
+
+
\ No newline at end of file
diff --git a/library/src/main/java/libxmtp-version.txt b/library/src/main/java/libxmtp-version.txt
index 8e2ce39b5..f78cf02bd 100644
--- a/library/src/main/java/libxmtp-version.txt
+++ b/library/src/main/java/libxmtp-version.txt
@@ -1,3 +1,3 @@
-Version: 137062e8
-Branch: main
-Date: 2024-10-08 19:58:58 +0000
+Version: 6937f233
+Branch: np/fix-ffi-bindings
+Date: 2024-10-16 17:50:35 +0000
diff --git a/library/src/main/java/org/xmtp/android/library/Client.kt b/library/src/main/java/org/xmtp/android/library/Client.kt
index f45146a68..6d641b9d4 100644
--- a/library/src/main/java/org/xmtp/android/library/Client.kt
+++ b/library/src/main/java/org/xmtp/android/library/Client.kt
@@ -289,34 +289,62 @@ class Client() {
}
}
- // This is a V3 only feature
- suspend fun createOrBuild(
+ private suspend fun initializeV3Client(
+ accountAddress: String,
+ clientOptions: ClientOptions,
+ signingKey: SigningKey? = null,
+ ): Client {
+ val inboxId = getOrCreateInboxId(clientOptions, accountAddress)
+
+ val (libXMTPClient, dbPath) = ffiXmtpClient(
+ clientOptions,
+ signingKey,
+ clientOptions.appContext,
+ null,
+ accountAddress,
+ inboxId
+ )
+
+ libXMTPClient?.let { client ->
+ return Client(
+ accountAddress,
+ client,
+ dbPath,
+ client.installationId().toHex(),
+ client.inboxId(),
+ clientOptions.api.env
+ )
+ } ?: throw XMTPException("Error creating V3 client: libXMTPClient is null")
+ }
+
+ // Function to create a V3 client with a signing key
+ suspend fun createV3(
account: SigningKey,
- options: ClientOptions,
+ options: ClientOptions? = null,
): Client {
this.hasV2Client = false
- val inboxId = getOrCreateInboxId(options, account.address)
-
+ val clientOptions = options ?: ClientOptions(enableV3 = true)
+ val accountAddress =
+ if (account.chainId != null) "eip155:${account.chainId}:${account.address.lowercase()}" else account.address.lowercase()
return try {
- val (libXMTPClient, dbPath) = ffiXmtpClient(
- options,
- account,
- options.appContext,
- null,
- account.address,
- inboxId
- )
+ initializeV3Client(accountAddress, clientOptions, account)
+ } catch (e: Exception) {
+ throw XMTPException("Error creating V3 client: ${e.message}", e)
+ }
+ }
- libXMTPClient?.let { client ->
- Client(
- account.address,
- client,
- dbPath,
- client.installationId().toHex(),
- client.inboxId(),
- options.api.env
- )
- } ?: throw XMTPException("Error creating V3 client: libXMTPClient is null")
+ // Function to build a V3 client without a signing key (using only address (& chainId for SCW))
+ suspend fun buildV3(
+ address: String,
+ chainId: Long? = null,
+ options: ClientOptions? = null,
+ ): Client {
+ this.hasV2Client = false
+ val clientOptions = options ?: ClientOptions(enableV3 = true)
+ val accountAddress =
+ if (chainId != null) "eip155:$chainId:${address.lowercase()}" else address.lowercase()
+ return try {
+ initializeV3Client(accountAddress, clientOptions)
} catch (e: Exception) {
throw XMTPException("Error creating V3 client: ${e.message}", e)
}
@@ -420,9 +448,20 @@ class Client() {
}
v3Client.signatureRequest()?.let { signatureRequest ->
if (account != null) {
- account.sign(signatureRequest.signatureText())?.let {
- signatureRequest.addEcdsaSignature(it.rawData)
+ if (account.type == WalletType.SCW) {
+ val chainId = account.chainId ?: throw XMTPException("ChainId is required for smart contract wallets")
+ signatureRequest.addScwSignature(
+ account.signSCW(signatureRequest.signatureText()),
+ account.address.lowercase(),
+ chainId.toULong(),
+ account.blockNumber?.toULong()
+ )
+ } else {
+ account.sign(signatureRequest.signatureText())?.let {
+ signatureRequest.addEcdsaSignature(it.rawData)
+ }
}
+
v3Client.registerIdentity(signatureRequest)
} else {
throw XMTPException("No signer passed but signer was required.")
@@ -570,7 +609,7 @@ class Client() {
fun findGroup(groupId: String): Group? {
val client = v3Client ?: throw XMTPException("Error no V3 client initialized")
try {
- return Group(this, client.group(groupId.hexToByteArray()))
+ return Group(this, client.conversation(groupId.hexToByteArray()))
} catch (e: Exception) {
return null
}
diff --git a/library/src/main/java/org/xmtp/android/library/Contacts.kt b/library/src/main/java/org/xmtp/android/library/Contacts.kt
index 05df91cee..c0d0b544a 100644
--- a/library/src/main/java/org/xmtp/android/library/Contacts.kt
+++ b/library/src/main/java/org/xmtp/android/library/Contacts.kt
@@ -47,7 +47,7 @@ enum class EntryType {
fun toFfiConsentEntityType(option: EntryType): FfiConsentEntityType {
return when (option) {
EntryType.ADDRESS -> FfiConsentEntityType.ADDRESS
- EntryType.GROUP_ID -> FfiConsentEntityType.GROUP_ID
+ EntryType.GROUP_ID -> FfiConsentEntityType.CONVERSATION_ID
EntryType.INBOX_ID -> FfiConsentEntityType.INBOX_ID
}
}
@@ -55,7 +55,7 @@ enum class EntryType {
fun fromFfiConsentEntityType(option: FfiConsentEntityType): EntryType {
return when (option) {
FfiConsentEntityType.ADDRESS -> EntryType.ADDRESS
- FfiConsentEntityType.GROUP_ID -> EntryType.GROUP_ID
+ FfiConsentEntityType.CONVERSATION_ID -> EntryType.GROUP_ID
FfiConsentEntityType.INBOX_ID -> EntryType.INBOX_ID
}
}
@@ -301,7 +301,7 @@ class ConsentList(
client.v3Client?.let {
return ConsentState.fromFfiConsentState(
it.getConsentState(
- FfiConsentEntityType.GROUP_ID,
+ FfiConsentEntityType.CONVERSATION_ID,
groupId
)
)
diff --git a/library/src/main/java/org/xmtp/android/library/Conversations.kt b/library/src/main/java/org/xmtp/android/library/Conversations.kt
index b213f8d1c..ea7038309 100644
--- a/library/src/main/java/org/xmtp/android/library/Conversations.kt
+++ b/library/src/main/java/org/xmtp/android/library/Conversations.kt
@@ -40,7 +40,7 @@ import uniffi.xmtpv3.FfiConversationCallback
import uniffi.xmtpv3.FfiConversations
import uniffi.xmtpv3.FfiCreateGroupOptions
import uniffi.xmtpv3.FfiEnvelope
-import uniffi.xmtpv3.FfiGroup
+import uniffi.xmtpv3.FfiConversation
import uniffi.xmtpv3.FfiListConversationsOptions
import uniffi.xmtpv3.FfiMessage
import uniffi.xmtpv3.FfiMessageCallback
@@ -193,7 +193,7 @@ data class Conversations(
// Sync all existing local groups data from the network (Note: call syncGroups() first to get the latest list of groups)
suspend fun syncAllGroups(): UInt? {
- return libXMTPConversations?.syncAllGroups()
+ return libXMTPConversations?.syncAllConversations()
}
suspend fun listGroups(
@@ -201,7 +201,7 @@ data class Conversations(
before: Date? = null,
limit: Int? = null,
): List {
- return libXMTPConversations?.list(
+ return libXMTPConversations?.listGroups(
opts = FfiListConversationsOptions(
after?.time?.nanoseconds?.toLong(DurationUnit.NANOSECONDS),
before?.time?.nanoseconds?.toLong(DurationUnit.NANOSECONDS),
@@ -655,22 +655,22 @@ data class Conversations(
private fun streamGroupConversations(): Flow = callbackFlow {
val groupCallback = object : FfiConversationCallback {
- override fun onConversation(conversation: FfiGroup) {
+ override fun onConversation(conversation: FfiConversation) {
trySend(Conversation.Group(Group(client, conversation)))
}
}
- val stream = libXMTPConversations?.stream(groupCallback)
+ val stream = libXMTPConversations?.streamGroups(groupCallback)
?: throw XMTPException("Client does not support Groups")
awaitClose { stream.end() }
}
fun streamGroups(): Flow = callbackFlow {
val groupCallback = object : FfiConversationCallback {
- override fun onConversation(conversation: FfiGroup) {
+ override fun onConversation(conversation: FfiConversation) {
trySend(Group(client, conversation))
}
}
- val stream = libXMTPConversations?.stream(groupCallback)
+ val stream = libXMTPConversations?.streamGroups(groupCallback)
?: throw XMTPException("Client does not support Groups")
awaitClose { stream.end() }
}
@@ -684,7 +684,7 @@ data class Conversations(
}
}
}
- val stream = libXMTPConversations?.streamAllMessages(messageCallback)
+ val stream = libXMTPConversations?.streamAllGroupMessages(messageCallback)
?: throw XMTPException("Client does not support Groups")
awaitClose { stream.end() }
}
@@ -698,7 +698,7 @@ data class Conversations(
}
}
}
- val stream = libXMTPConversations?.streamAllMessages(messageCallback)
+ val stream = libXMTPConversations?.streamAllGroupMessages(messageCallback)
?: throw XMTPException("Client does not support Groups")
awaitClose { stream.end() }
}
diff --git a/library/src/main/java/org/xmtp/android/library/Group.kt b/library/src/main/java/org/xmtp/android/library/Group.kt
index 176a25f8f..0fa3bfb35 100644
--- a/library/src/main/java/org/xmtp/android/library/Group.kt
+++ b/library/src/main/java/org/xmtp/android/library/Group.kt
@@ -14,8 +14,8 @@ import org.xmtp.android.library.messages.PagingInfoSortDirection
import org.xmtp.android.library.messages.Topic
import org.xmtp.proto.message.api.v1.MessageApiOuterClass
import uniffi.xmtpv3.FfiDeliveryStatus
-import uniffi.xmtpv3.FfiGroup
-import uniffi.xmtpv3.FfiGroupMetadata
+import uniffi.xmtpv3.FfiConversation
+import uniffi.xmtpv3.FfiConversationMetadata
import uniffi.xmtpv3.FfiGroupPermissions
import uniffi.xmtpv3.FfiListMessagesOptions
import uniffi.xmtpv3.FfiMessage
@@ -28,7 +28,7 @@ import java.util.Date
import kotlin.time.Duration.Companion.nanoseconds
import kotlin.time.DurationUnit
-class Group(val client: Client, private val libXMTPGroup: FfiGroup) {
+class Group(val client: Client, private val libXMTPGroup: FfiConversation) {
val id: String
get() = libXMTPGroup.id().toHex()
@@ -38,7 +38,7 @@ class Group(val client: Client, private val libXMTPGroup: FfiGroup) {
val createdAt: Date
get() = Date(libXMTPGroup.createdAtNs() / 1_000_000)
- private val metadata: FfiGroupMetadata
+ private val metadata: FfiConversationMetadata
get() = libXMTPGroup.groupMetadata()
private val permissions: FfiGroupPermissions
@@ -174,7 +174,7 @@ class Group(val client: Client, private val libXMTPGroup: FfiGroup) {
}
suspend fun processMessage(envelopeBytes: ByteArray): MessageV3 {
- val message = libXMTPGroup.processStreamedGroupMessage(envelopeBytes)
+ val message = libXMTPGroup.processStreamedConversationMessage(envelopeBytes)
return MessageV3(client, message)
}
diff --git a/library/src/main/java/org/xmtp/android/library/SigningKey.kt b/library/src/main/java/org/xmtp/android/library/SigningKey.kt
index 34bd986dd..f1a10a395 100644
--- a/library/src/main/java/org/xmtp/android/library/SigningKey.kt
+++ b/library/src/main/java/org/xmtp/android/library/SigningKey.kt
@@ -19,9 +19,36 @@ import java.util.Date
interface SigningKey {
val address: String
- suspend fun sign(data: ByteArray): SignatureOuterClass.Signature?
+ // The wallet type if Smart Contract Wallet this should be type SCW.
+ val type: WalletType
+ get() = WalletType.EOA
- suspend fun sign(message: String): SignatureOuterClass.Signature?
+ // The chainId of the Smart Contract Wallet value should be null if not SCW
+ var chainId: Long?
+ get() = null
+ set(_) {}
+
+ // Default blockNumber value set to null
+ var blockNumber: Long?
+ get() = null
+ set(_) {}
+
+ suspend fun sign(data: ByteArray): SignatureOuterClass.Signature? {
+ throw NotImplementedError("sign(ByteArray) is not implemented.")
+ }
+
+ suspend fun sign(message: String): SignatureOuterClass.Signature? {
+ throw NotImplementedError("sign(String) is not implemented.")
+ }
+
+ suspend fun signSCW(message: String): ByteArray {
+ throw NotImplementedError("signSCW(String) is not implemented.")
+ }
+}
+
+enum class WalletType {
+ SCW, // Smart Contract Wallet
+ EOA // Externally Owned Account *Default
}
/**
@@ -36,10 +63,13 @@ fun SigningKey.createIdentity(
identity: PrivateKeyOuterClass.PrivateKey,
preCreateIdentityCallback: PreEventCallback? = null,
): AuthorizedIdentity {
- val slimKey = PublicKeyOuterClass.PublicKey.newBuilder().apply {
- timestamp = Date().time
- secp256K1Uncompressed = identity.publicKey.secp256K1Uncompressed
- }.build()
+ val slimKey =
+ PublicKeyOuterClass.PublicKey
+ .newBuilder()
+ .apply {
+ timestamp = Date().time
+ secp256K1Uncompressed = identity.publicKey.secp256K1Uncompressed
+ }.build()
preCreateIdentityCallback?.let {
runBlocking {
@@ -53,17 +83,19 @@ fun SigningKey.createIdentity(
val signature = runBlocking { sign(signatureText) } ?: throw XMTPException("Illegal signature")
val signatureData = KeyUtil.getSignatureData(signature.rawData.toByteString().toByteArray())
- val publicKey = Sign.recoverFromSignature(
- BigInteger(1, signatureData.v).toInt(),
- ECDSASignature(BigInteger(1, signatureData.r), BigInteger(1, signatureData.s)),
- digest,
- )
+ val publicKey =
+ Sign.recoverFromSignature(
+ BigInteger(1, signatureData.v).toInt(),
+ ECDSASignature(BigInteger(1, signatureData.r), BigInteger(1, signatureData.s)),
+ digest,
+ )
- val authorized = PublicKey.newBuilder().also {
- it.secp256K1Uncompressed = slimKey.secp256K1Uncompressed
- it.timestamp = slimKey.timestamp
- it.signature = signature
- }
+ val authorized =
+ PublicKey.newBuilder().also {
+ it.secp256K1Uncompressed = slimKey.secp256K1Uncompressed
+ it.timestamp = slimKey.timestamp
+ it.signature = signature
+ }
return AuthorizedIdentity(
address = Keys.toChecksumAddress(Keys.getAddress(publicKey)),
authorized = authorized.build(),
diff --git a/library/src/main/java/org/xmtp/android/library/libxmtp/Member.kt b/library/src/main/java/org/xmtp/android/library/libxmtp/Member.kt
index c502247a6..c8ca6c85e 100644
--- a/library/src/main/java/org/xmtp/android/library/libxmtp/Member.kt
+++ b/library/src/main/java/org/xmtp/android/library/libxmtp/Member.kt
@@ -1,13 +1,13 @@
package org.xmtp.android.library.libxmtp
import org.xmtp.android.library.ConsentState
-import uniffi.xmtpv3.FfiGroupMember
+import uniffi.xmtpv3.FfiConversationMember
import uniffi.xmtpv3.FfiPermissionLevel
enum class PermissionLevel {
MEMBER, ADMIN, SUPER_ADMIN
}
-class Member(private val ffiMember: FfiGroupMember) {
+class Member(private val ffiMember: FfiConversationMember) {
val inboxId: String
get() = ffiMember.inboxId
diff --git a/library/src/main/java/org/xmtp/android/library/libxmtp/MessageV3.kt b/library/src/main/java/org/xmtp/android/library/libxmtp/MessageV3.kt
index fc1302b7a..631fd2e5f 100644
--- a/library/src/main/java/org/xmtp/android/library/libxmtp/MessageV3.kt
+++ b/library/src/main/java/org/xmtp/android/library/libxmtp/MessageV3.kt
@@ -11,7 +11,7 @@ import org.xmtp.android.library.messages.MessageDeliveryStatus
import org.xmtp.android.library.messages.Topic
import org.xmtp.android.library.toHex
import uniffi.xmtpv3.FfiDeliveryStatus
-import uniffi.xmtpv3.FfiGroupMessageKind
+import uniffi.xmtpv3.FfiConversationMessageKind
import uniffi.xmtpv3.FfiMessage
import java.util.Date
@@ -47,7 +47,7 @@ data class MessageV3(val client: Client, private val libXMTPMessage: FfiMessage)
sent = sentAt,
deliveryStatus = deliveryStatus
)
- if (decodedMessage.encodedContent.type == ContentTypeGroupUpdated && libXMTPMessage.kind != FfiGroupMessageKind.MEMBERSHIP_CHANGE) {
+ if (decodedMessage.encodedContent.type == ContentTypeGroupUpdated && libXMTPMessage.kind != FfiConversationMessageKind.MEMBERSHIP_CHANGE) {
throw XMTPException("Error decoding group membership change")
}
return decodedMessage
diff --git a/library/src/main/java/xmtpv3.kt b/library/src/main/java/xmtpv3.kt
index 7e7f10b10..9d67779b1 100644
--- a/library/src/main/java/xmtpv3.kt
+++ b/library/src/main/java/xmtpv3.kt
@@ -860,221 +860,245 @@ internal interface UniffiLib : Library {
}
}
- fun uniffi_xmtpv3_fn_clone_fficonversations(
- `ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
- ): Pointer
-
- fun uniffi_xmtpv3_fn_free_fficonversations(
- `ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
- ): Unit
-
- fun uniffi_xmtpv3_fn_method_fficonversations_create_dm(
- `ptr`: Pointer, `accountAddress`: RustBuffer.ByValue,
- ): Long
-
- fun uniffi_xmtpv3_fn_method_fficonversations_create_group(
- `ptr`: Pointer, `accountAddresses`: RustBuffer.ByValue, `opts`: RustBuffer.ByValue,
- ): Long
-
- fun uniffi_xmtpv3_fn_method_fficonversations_list(
- `ptr`: Pointer, `opts`: RustBuffer.ByValue,
- ): Long
-
- fun uniffi_xmtpv3_fn_method_fficonversations_process_streamed_welcome_message(
- `ptr`: Pointer, `envelopeBytes`: RustBuffer.ByValue,
- ): Long
-
- fun uniffi_xmtpv3_fn_method_fficonversations_stream(
- `ptr`: Pointer, `callback`: Long,
- ): Long
-
- fun uniffi_xmtpv3_fn_method_fficonversations_stream_all_messages(
- `ptr`: Pointer, `messageCallback`: Long,
- ): Long
-
- fun uniffi_xmtpv3_fn_method_fficonversations_sync(
- `ptr`: Pointer,
- ): Long
-
- fun uniffi_xmtpv3_fn_method_fficonversations_sync_all_groups(
- `ptr`: Pointer,
- ): Long
-
- fun uniffi_xmtpv3_fn_clone_ffigroup(
+ fun uniffi_xmtpv3_fn_clone_fficonversation(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): Pointer
- fun uniffi_xmtpv3_fn_free_ffigroup(
+ fun uniffi_xmtpv3_fn_free_fficonversation(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): Unit
- fun uniffi_xmtpv3_fn_method_ffigroup_add_admin(
+ fun uniffi_xmtpv3_fn_method_fficonversation_add_admin(
`ptr`: Pointer, `inboxId`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_add_members(
+ fun uniffi_xmtpv3_fn_method_fficonversation_add_members(
`ptr`: Pointer, `accountAddresses`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_add_members_by_inbox_id(
+ fun uniffi_xmtpv3_fn_method_fficonversation_add_members_by_inbox_id(
`ptr`: Pointer, `inboxIds`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_add_super_admin(
+ fun uniffi_xmtpv3_fn_method_fficonversation_add_super_admin(
`ptr`: Pointer, `inboxId`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_added_by_inbox_id(
+ fun uniffi_xmtpv3_fn_method_fficonversation_added_by_inbox_id(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_admin_list(
+ fun uniffi_xmtpv3_fn_method_fficonversation_admin_list(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_consent_state(
+ fun uniffi_xmtpv3_fn_method_fficonversation_consent_state(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_created_at_ns(
+ fun uniffi_xmtpv3_fn_method_fficonversation_created_at_ns(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_find_messages(
+ fun uniffi_xmtpv3_fn_method_fficonversation_find_messages(
`ptr`: Pointer, `opts`: RustBuffer.ByValue, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_group_description(
+ fun uniffi_xmtpv3_fn_method_fficonversation_group_description(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_group_image_url_square(
+ fun uniffi_xmtpv3_fn_method_fficonversation_group_image_url_square(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_group_metadata(
+ fun uniffi_xmtpv3_fn_method_fficonversation_group_metadata(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): Pointer
- fun uniffi_xmtpv3_fn_method_ffigroup_group_name(
+ fun uniffi_xmtpv3_fn_method_fficonversation_group_name(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_group_permissions(
+ fun uniffi_xmtpv3_fn_method_fficonversation_group_permissions(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): Pointer
- fun uniffi_xmtpv3_fn_method_ffigroup_group_pinned_frame_url(
+ fun uniffi_xmtpv3_fn_method_fficonversation_group_pinned_frame_url(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_id(
+ fun uniffi_xmtpv3_fn_method_fficonversation_id(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_is_active(
+ fun uniffi_xmtpv3_fn_method_fficonversation_is_active(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): Byte
- fun uniffi_xmtpv3_fn_method_ffigroup_is_admin(
+ fun uniffi_xmtpv3_fn_method_fficonversation_is_admin(
`ptr`: Pointer, `inboxId`: RustBuffer.ByValue, uniffi_out_err: UniffiRustCallStatus,
): Byte
- fun uniffi_xmtpv3_fn_method_ffigroup_is_super_admin(
+ fun uniffi_xmtpv3_fn_method_fficonversation_is_super_admin(
`ptr`: Pointer, `inboxId`: RustBuffer.ByValue, uniffi_out_err: UniffiRustCallStatus,
): Byte
- fun uniffi_xmtpv3_fn_method_ffigroup_list_members(
+ fun uniffi_xmtpv3_fn_method_fficonversation_list_members(
`ptr`: Pointer,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_process_streamed_group_message(
+ fun uniffi_xmtpv3_fn_method_fficonversation_process_streamed_conversation_message(
`ptr`: Pointer, `envelopeBytes`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_publish_messages(
+ fun uniffi_xmtpv3_fn_method_fficonversation_publish_messages(
`ptr`: Pointer,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_remove_admin(
+ fun uniffi_xmtpv3_fn_method_fficonversation_remove_admin(
`ptr`: Pointer, `inboxId`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_remove_members(
+ fun uniffi_xmtpv3_fn_method_fficonversation_remove_members(
`ptr`: Pointer, `accountAddresses`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_remove_members_by_inbox_id(
+ fun uniffi_xmtpv3_fn_method_fficonversation_remove_members_by_inbox_id(
`ptr`: Pointer, `inboxIds`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_remove_super_admin(
+ fun uniffi_xmtpv3_fn_method_fficonversation_remove_super_admin(
`ptr`: Pointer, `inboxId`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_send(
+ fun uniffi_xmtpv3_fn_method_fficonversation_send(
`ptr`: Pointer, `contentBytes`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_send_optimistic(
+ fun uniffi_xmtpv3_fn_method_fficonversation_send_optimistic(
`ptr`: Pointer, `contentBytes`: RustBuffer.ByValue, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_stream(
+ fun uniffi_xmtpv3_fn_method_fficonversation_stream(
`ptr`: Pointer, `messageCallback`: Long,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_super_admin_list(
+ fun uniffi_xmtpv3_fn_method_fficonversation_super_admin_list(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroup_sync(
+ fun uniffi_xmtpv3_fn_method_fficonversation_sync(
`ptr`: Pointer,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_update_consent_state(
+ fun uniffi_xmtpv3_fn_method_fficonversation_update_consent_state(
`ptr`: Pointer, `state`: RustBuffer.ByValue, uniffi_out_err: UniffiRustCallStatus,
): Unit
- fun uniffi_xmtpv3_fn_method_ffigroup_update_group_description(
+ fun uniffi_xmtpv3_fn_method_fficonversation_update_group_description(
`ptr`: Pointer, `groupDescription`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_update_group_image_url_square(
+ fun uniffi_xmtpv3_fn_method_fficonversation_update_group_image_url_square(
`ptr`: Pointer, `groupImageUrlSquare`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_update_group_name(
+ fun uniffi_xmtpv3_fn_method_fficonversation_update_group_name(
`ptr`: Pointer, `groupName`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_update_group_pinned_frame_url(
+ fun uniffi_xmtpv3_fn_method_fficonversation_update_group_pinned_frame_url(
`ptr`: Pointer, `pinnedFrameUrl`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffigroup_update_permission_policy(
+ fun uniffi_xmtpv3_fn_method_fficonversation_update_permission_policy(
`ptr`: Pointer,
`permissionUpdateType`: RustBuffer.ByValue,
`permissionPolicyOption`: RustBuffer.ByValue,
`metadataField`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_clone_ffigroupmetadata(
+ fun uniffi_xmtpv3_fn_clone_fficonversationmetadata(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): Pointer
- fun uniffi_xmtpv3_fn_free_ffigroupmetadata(
+ fun uniffi_xmtpv3_fn_free_fficonversationmetadata(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): Unit
- fun uniffi_xmtpv3_fn_method_ffigroupmetadata_conversation_type(
+ fun uniffi_xmtpv3_fn_method_fficonversationmetadata_conversation_type(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
- fun uniffi_xmtpv3_fn_method_ffigroupmetadata_creator_inbox_id(
+ fun uniffi_xmtpv3_fn_method_fficonversationmetadata_creator_inbox_id(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
+ fun uniffi_xmtpv3_fn_clone_fficonversations(
+ `ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
+ ): Pointer
+
+ fun uniffi_xmtpv3_fn_free_fficonversations(
+ `ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
+ ): Unit
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_create_dm(
+ `ptr`: Pointer, `accountAddress`: RustBuffer.ByValue,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_create_group(
+ `ptr`: Pointer, `accountAddresses`: RustBuffer.ByValue, `opts`: RustBuffer.ByValue,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_list(
+ `ptr`: Pointer, `opts`: RustBuffer.ByValue,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_list_dms(
+ `ptr`: Pointer, `opts`: RustBuffer.ByValue,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_list_groups(
+ `ptr`: Pointer, `opts`: RustBuffer.ByValue,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_process_streamed_welcome_message(
+ `ptr`: Pointer, `envelopeBytes`: RustBuffer.ByValue,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_stream(
+ `ptr`: Pointer, `callback`: Long,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_stream_all_dm_messages(
+ `ptr`: Pointer, `messageCallback`: Long,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_stream_all_group_messages(
+ `ptr`: Pointer, `messageCallback`: Long,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_stream_all_messages(
+ `ptr`: Pointer, `messageCallback`: Long,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_stream_dms(
+ `ptr`: Pointer, `callback`: Long,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_stream_groups(
+ `ptr`: Pointer, `callback`: Long,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_sync(
+ `ptr`: Pointer,
+ ): Long
+
+ fun uniffi_xmtpv3_fn_method_fficonversations_sync_all_conversations(
+ `ptr`: Pointer,
+ ): Long
+
fun uniffi_xmtpv3_fn_clone_ffigrouppermissions(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): Pointer
@@ -1205,6 +1229,10 @@ internal interface UniffiLib : Library {
`newWalletAddress`: RustBuffer.ByValue,
): Long
+ fun uniffi_xmtpv3_fn_method_ffixmtpclient_addresses_from_inbox_id(
+ `ptr`: Pointer, `refreshFromNetwork`: Byte, `inboxIds`: RustBuffer.ByValue,
+ ): Long
+
fun uniffi_xmtpv3_fn_method_ffixmtpclient_apply_signature_request(
`ptr`: Pointer, `signatureRequest`: Pointer,
): Long
@@ -1213,6 +1241,10 @@ internal interface UniffiLib : Library {
`ptr`: Pointer, `accountAddresses`: RustBuffer.ByValue,
): Long
+ fun uniffi_xmtpv3_fn_method_ffixmtpclient_conversation(
+ `ptr`: Pointer, `conversationId`: RustBuffer.ByValue, uniffi_out_err: UniffiRustCallStatus,
+ ): Pointer
+
fun uniffi_xmtpv3_fn_method_ffixmtpclient_conversations(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): Pointer
@@ -1221,6 +1253,10 @@ internal interface UniffiLib : Library {
`ptr`: Pointer,
): Long
+ fun uniffi_xmtpv3_fn_method_ffixmtpclient_dm_conversation(
+ `ptr`: Pointer, `targetInboxId`: RustBuffer.ByValue, uniffi_out_err: UniffiRustCallStatus,
+ ): Pointer
+
fun uniffi_xmtpv3_fn_method_ffixmtpclient_find_inbox_id(
`ptr`: Pointer, `address`: RustBuffer.ByValue,
): Long
@@ -1233,10 +1269,6 @@ internal interface UniffiLib : Library {
`ptr`: Pointer, `inboxId`: RustBuffer.ByValue,
): Long
- fun uniffi_xmtpv3_fn_method_ffixmtpclient_group(
- `ptr`: Pointer, `groupId`: RustBuffer.ByValue, uniffi_out_err: UniffiRustCallStatus,
- ): Pointer
-
fun uniffi_xmtpv3_fn_method_ffixmtpclient_inbox_id(
`ptr`: Pointer, uniffi_out_err: UniffiRustCallStatus,
): RustBuffer.ByValue
@@ -1667,145 +1699,163 @@ internal interface UniffiLib : Library {
fun uniffi_xmtpv3_checksum_func_verify_k256_sha256(
): Short
- fun uniffi_xmtpv3_checksum_method_fficonversations_create_dm(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_add_admin(
): Short
- fun uniffi_xmtpv3_checksum_method_fficonversations_create_group(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_add_members(
): Short
- fun uniffi_xmtpv3_checksum_method_fficonversations_list(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_add_members_by_inbox_id(
): Short
- fun uniffi_xmtpv3_checksum_method_fficonversations_process_streamed_welcome_message(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_add_super_admin(
): Short
- fun uniffi_xmtpv3_checksum_method_fficonversations_stream(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_added_by_inbox_id(
): Short
- fun uniffi_xmtpv3_checksum_method_fficonversations_stream_all_messages(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_admin_list(
): Short
- fun uniffi_xmtpv3_checksum_method_fficonversations_sync(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_consent_state(
+ ): Short
+
+ fun uniffi_xmtpv3_checksum_method_fficonversation_created_at_ns(
+ ): Short
+
+ fun uniffi_xmtpv3_checksum_method_fficonversation_find_messages(
+ ): Short
+
+ fun uniffi_xmtpv3_checksum_method_fficonversation_group_description(
+ ): Short
+
+ fun uniffi_xmtpv3_checksum_method_fficonversation_group_image_url_square(
+ ): Short
+
+ fun uniffi_xmtpv3_checksum_method_fficonversation_group_metadata(
+ ): Short
+
+ fun uniffi_xmtpv3_checksum_method_fficonversation_group_name(
): Short
- fun uniffi_xmtpv3_checksum_method_fficonversations_sync_all_groups(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_group_permissions(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_add_admin(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_group_pinned_frame_url(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_add_members(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_id(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_add_members_by_inbox_id(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_is_active(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_add_super_admin(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_is_admin(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_added_by_inbox_id(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_is_super_admin(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_admin_list(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_list_members(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_consent_state(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_process_streamed_conversation_message(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_created_at_ns(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_publish_messages(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_find_messages(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_remove_admin(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_group_description(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_remove_members(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_group_image_url_square(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_remove_members_by_inbox_id(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_group_metadata(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_remove_super_admin(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_group_name(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_send(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_group_permissions(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_send_optimistic(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_group_pinned_frame_url(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_stream(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_id(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_super_admin_list(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_is_active(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_sync(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_is_admin(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_update_consent_state(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_is_super_admin(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_update_group_description(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_list_members(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_update_group_image_url_square(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_process_streamed_group_message(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_update_group_name(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_publish_messages(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_update_group_pinned_frame_url(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_remove_admin(
+ fun uniffi_xmtpv3_checksum_method_fficonversation_update_permission_policy(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_remove_members(
+ fun uniffi_xmtpv3_checksum_method_fficonversationmetadata_conversation_type(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_remove_members_by_inbox_id(
+ fun uniffi_xmtpv3_checksum_method_fficonversationmetadata_creator_inbox_id(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_remove_super_admin(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_create_dm(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_send(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_create_group(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_send_optimistic(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_list(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_stream(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_list_dms(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_super_admin_list(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_list_groups(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_sync(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_process_streamed_welcome_message(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_update_consent_state(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_stream(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_update_group_description(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_stream_all_dm_messages(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_update_group_image_url_square(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_stream_all_group_messages(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_update_group_name(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_stream_all_messages(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_update_group_pinned_frame_url(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_stream_dms(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroup_update_permission_policy(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_stream_groups(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroupmetadata_conversation_type(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_sync(
): Short
- fun uniffi_xmtpv3_checksum_method_ffigroupmetadata_creator_inbox_id(
+ fun uniffi_xmtpv3_checksum_method_fficonversations_sync_all_conversations(
): Short
fun uniffi_xmtpv3_checksum_method_ffigrouppermissions_policy_set(
@@ -1865,18 +1915,27 @@ internal interface UniffiLib : Library {
fun uniffi_xmtpv3_checksum_method_ffixmtpclient_add_wallet(
): Short
+ fun uniffi_xmtpv3_checksum_method_ffixmtpclient_addresses_from_inbox_id(
+ ): Short
+
fun uniffi_xmtpv3_checksum_method_ffixmtpclient_apply_signature_request(
): Short
fun uniffi_xmtpv3_checksum_method_ffixmtpclient_can_message(
): Short
+ fun uniffi_xmtpv3_checksum_method_ffixmtpclient_conversation(
+ ): Short
+
fun uniffi_xmtpv3_checksum_method_ffixmtpclient_conversations(
): Short
fun uniffi_xmtpv3_checksum_method_ffixmtpclient_db_reconnect(
): Short
+ fun uniffi_xmtpv3_checksum_method_ffixmtpclient_dm_conversation(
+ ): Short
+
fun uniffi_xmtpv3_checksum_method_ffixmtpclient_find_inbox_id(
): Short
@@ -1886,9 +1945,6 @@ internal interface UniffiLib : Library {
fun uniffi_xmtpv3_checksum_method_ffixmtpclient_get_latest_inbox_state(
): Short
- fun uniffi_xmtpv3_checksum_method_ffixmtpclient_group(
- ): Short
-
fun uniffi_xmtpv3_checksum_method_ffixmtpclient_inbox_id(
): Short
@@ -2005,145 +2061,163 @@ private fun uniffiCheckApiChecksums(lib: UniffiLib) {
if (lib.uniffi_xmtpv3_checksum_func_verify_k256_sha256() != 25521.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_fficonversations_create_dm() != 61687.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_add_admin() != 52417.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_fficonversations_create_group() != 62996.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_add_members() != 3260.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_fficonversations_list() != 10804.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_add_members_by_inbox_id() != 28069.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_fficonversations_process_streamed_welcome_message() != 15283.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_add_super_admin() != 62984.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_fficonversations_stream() != 3079.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_added_by_inbox_id() != 12748.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_fficonversations_stream_all_messages() != 13204.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_admin_list() != 26668.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_fficonversations_sync() != 9054.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_consent_state() != 25033.toShort()) {
+ throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
+ }
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_created_at_ns() != 17973.toShort()) {
+ throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
+ }
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_find_messages() != 58508.toShort()) {
+ throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
+ }
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_group_description() != 53570.toShort()) {
+ throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
+ }
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_group_image_url_square() != 3200.toShort()) {
+ throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
+ }
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_group_metadata() != 21111.toShort()) {
+ throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
+ }
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_group_name() != 9344.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_fficonversations_sync_all_groups() != 3433.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_group_permissions() != 61947.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_add_admin() != 4600.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_group_pinned_frame_url() != 40964.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_add_members() != 27666.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_id() != 5542.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_add_members_by_inbox_id() != 23290.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_is_active() != 49581.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_add_super_admin() != 40681.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_is_admin() != 12325.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_added_by_inbox_id() != 37220.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_is_super_admin() != 25811.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_admin_list() != 51010.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_list_members() != 21260.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_consent_state() != 11630.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_process_streamed_conversation_message() != 1417.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_created_at_ns() != 4894.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_publish_messages() != 15643.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_find_messages() != 14930.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_remove_admin() != 7973.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_group_description() != 37045.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_remove_members() != 49452.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_group_image_url_square() != 16754.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_remove_members_by_inbox_id() != 53192.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_group_metadata() != 13139.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_remove_super_admin() != 46017.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_group_name() != 61525.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_send() != 7954.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_group_permissions() != 15980.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_send_optimistic() != 5885.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_group_pinned_frame_url() != 29388.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_stream() != 52815.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_id() != 36764.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_super_admin_list() != 50610.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_is_active() != 33848.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_sync() != 17206.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_is_admin() != 26672.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_update_consent_state() != 27721.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_is_super_admin() != 61614.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_update_group_description() != 14549.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_list_members() != 3945.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_update_group_image_url_square() != 36900.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_process_streamed_group_message() != 19069.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_update_group_name() != 62600.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_publish_messages() != 52808.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_update_group_pinned_frame_url() != 21997.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_remove_admin() != 57094.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversation_update_permission_policy() != 3743.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_remove_members() != 24336.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversationmetadata_conversation_type() != 48024.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_remove_members_by_inbox_id() != 45424.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversationmetadata_creator_inbox_id() != 61067.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_remove_super_admin() != 35336.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_create_dm() != 63785.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_send() != 37701.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_create_group() != 7282.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_send_optimistic() != 13872.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_list() != 42790.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_stream() != 34669.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_list_dms() != 41576.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_super_admin_list() != 5323.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_list_groups() != 2386.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_sync() != 24219.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_process_streamed_welcome_message() != 57376.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_update_consent_state() != 48124.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_stream() != 3079.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_update_group_description() != 34006.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_stream_all_dm_messages() != 37950.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_update_group_image_url_square() != 18878.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_stream_all_group_messages() != 50601.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_update_group_name() != 550.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_stream_all_messages() != 13204.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_update_group_pinned_frame_url() != 37434.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_stream_dms() != 4319.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroup_update_permission_policy() != 51936.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_stream_groups() != 10208.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroupmetadata_conversation_type() != 30827.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_sync() != 9054.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffigroupmetadata_creator_inbox_id() != 26872.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversations_sync_all_conversations() != 1140.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
if (lib.uniffi_xmtpv3_checksum_method_ffigrouppermissions_policy_set() != 24928.toShort()) {
@@ -2203,18 +2277,27 @@ private fun uniffiCheckApiChecksums(lib: UniffiLib) {
if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_add_wallet() != 23786.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
+ if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_addresses_from_inbox_id() != 29264.toShort()) {
+ throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
+ }
if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_apply_signature_request() != 32172.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_can_message() != 53502.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
+ if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_conversation() != 60290.toShort()) {
+ throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
+ }
if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_conversations() != 47463.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_db_reconnect() != 6707.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
+ if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_dm_conversation() != 23917.toShort()) {
+ throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
+ }
if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_find_inbox_id() != 59020.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
@@ -2224,9 +2307,6 @@ private fun uniffiCheckApiChecksums(lib: UniffiLib) {
if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_get_latest_inbox_state() != 3165.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_group() != 64533.toShort()) {
- throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
- }
if (lib.uniffi_xmtpv3_checksum_method_ffixmtpclient_inbox_id() != 25128.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
@@ -2269,7 +2349,7 @@ private fun uniffiCheckApiChecksums(lib: UniffiLib) {
if (lib.uniffi_xmtpv3_checksum_method_ffilogger_log() != 56011.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
- if (lib.uniffi_xmtpv3_checksum_method_fficonversationcallback_on_conversation() != 42.toShort()) {
+ if (lib.uniffi_xmtpv3_checksum_method_fficonversationcallback_on_conversation() != 25316.toShort()) {
throw RuntimeException("UniFFI API checksum mismatch: try cleaning and rebuilding your project")
}
if (lib.uniffi_xmtpv3_checksum_method_ffimessagecallback_on_message() != 5286.toShort()) {
@@ -2690,31 +2770,96 @@ private class JavaLangRefCleanable(
override fun clean() = cleanable.clean()
}
-public interface FfiConversationsInterface {
+public interface FfiConversationInterface {
- suspend fun `createDm`(`accountAddress`: kotlin.String): FfiGroup
+ suspend fun `addAdmin`(`inboxId`: kotlin.String)
- suspend fun `createGroup`(
- `accountAddresses`: List,
- `opts`: FfiCreateGroupOptions,
- ): FfiGroup
+ suspend fun `addMembers`(`accountAddresses`: List)
- suspend fun `list`(`opts`: FfiListConversationsOptions): List
+ suspend fun `addMembersByInboxId`(`inboxIds`: List)
- suspend fun `processStreamedWelcomeMessage`(`envelopeBytes`: kotlin.ByteArray): FfiGroup
+ suspend fun `addSuperAdmin`(`inboxId`: kotlin.String)
- suspend fun `stream`(`callback`: FfiConversationCallback): FfiStreamCloser
+ fun `addedByInboxId`(): kotlin.String
- suspend fun `streamAllMessages`(`messageCallback`: FfiMessageCallback): FfiStreamCloser
+ fun `adminList`(): List
+
+ fun `consentState`(): FfiConsentState
+
+ fun `createdAtNs`(): kotlin.Long
+
+ fun `findMessages`(`opts`: FfiListMessagesOptions): List
+
+ fun `groupDescription`(): kotlin.String
+
+ fun `groupImageUrlSquare`(): kotlin.String
+
+ fun `groupMetadata`(): FfiConversationMetadata
+
+ fun `groupName`(): kotlin.String
+
+ fun `groupPermissions`(): FfiGroupPermissions
+
+ fun `groupPinnedFrameUrl`(): kotlin.String
+
+ fun `id`(): kotlin.ByteArray
+
+ fun `isActive`(): kotlin.Boolean
+
+ fun `isAdmin`(`inboxId`: kotlin.String): kotlin.Boolean
+
+ fun `isSuperAdmin`(`inboxId`: kotlin.String): kotlin.Boolean
+
+ suspend fun `listMembers`(): List
+
+ suspend fun `processStreamedConversationMessage`(`envelopeBytes`: kotlin.ByteArray): FfiMessage
+
+ /**
+ * Publish all unpublished messages
+ */
+ suspend fun `publishMessages`()
+
+ suspend fun `removeAdmin`(`inboxId`: kotlin.String)
+
+ suspend fun `removeMembers`(`accountAddresses`: List)
+
+ suspend fun `removeMembersByInboxId`(`inboxIds`: List)
+
+ suspend fun `removeSuperAdmin`(`inboxId`: kotlin.String)
+
+ suspend fun `send`(`contentBytes`: kotlin.ByteArray): kotlin.ByteArray
+
+ /**
+ * send a message without immediately publishing to the delivery service.
+ */
+ fun `sendOptimistic`(`contentBytes`: kotlin.ByteArray): kotlin.ByteArray
+
+ suspend fun `stream`(`messageCallback`: FfiMessageCallback): FfiStreamCloser
+
+ fun `superAdminList`(): List
suspend fun `sync`()
- suspend fun `syncAllGroups`(): kotlin.UInt
+ fun `updateConsentState`(`state`: FfiConsentState)
+
+ suspend fun `updateGroupDescription`(`groupDescription`: kotlin.String)
+
+ suspend fun `updateGroupImageUrlSquare`(`groupImageUrlSquare`: kotlin.String)
+
+ suspend fun `updateGroupName`(`groupName`: kotlin.String)
+
+ suspend fun `updateGroupPinnedFrameUrl`(`pinnedFrameUrl`: kotlin.String)
+
+ suspend fun `updatePermissionPolicy`(
+ `permissionUpdateType`: FfiPermissionUpdateType,
+ `permissionPolicyOption`: FfiPermissionPolicy,
+ `metadataField`: FfiMetadataField?,
+ )
companion object
}
-open class FfiConversations : Disposable, AutoCloseable, FfiConversationsInterface {
+open class FfiConversation : Disposable, AutoCloseable, FfiConversationInterface {
constructor(pointer: Pointer) {
this.pointer = pointer
@@ -2783,7 +2928,7 @@ open class FfiConversations : Disposable, AutoCloseable, FfiConversationsInterfa
override fun run() {
pointer?.let { ptr ->
uniffiRustCall { status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_free_fficonversations(ptr, status)
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_free_fficonversation(ptr, status)
}
}
}
@@ -2791,38 +2936,39 @@ open class FfiConversations : Disposable, AutoCloseable, FfiConversationsInterfa
fun uniffiClonePointer(): Pointer {
return uniffiRustCall() { status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_clone_fficonversations(pointer!!, status)
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_clone_fficonversation(pointer!!, status)
}
}
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `createDm`(`accountAddress`: kotlin.String): FfiGroup {
+ override suspend fun `addAdmin`(`inboxId`: kotlin.String) {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_create_dm(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_add_admin(
thisPtr,
- FfiConverterString.lower(`accountAddress`),
+ FfiConverterString.lower(`inboxId`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
// lift function
- { FfiConverterTypeFfiGroup.lift(it) },
- // Error FFI converter
+ { Unit },
+
+ // Error FFI converter
GenericException.ErrorHandler,
)
}
@@ -2830,34 +2976,31 @@ open class FfiConversations : Disposable, AutoCloseable, FfiConversationsInterfa
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `createGroup`(
- `accountAddresses`: List,
- `opts`: FfiCreateGroupOptions,
- ): FfiGroup {
+ override suspend fun `addMembers`(`accountAddresses`: List) {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_create_group(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_add_members(
thisPtr,
FfiConverterSequenceString.lower(`accountAddresses`),
- FfiConverterTypeFfiCreateGroupOptions.lower(`opts`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
// lift function
- { FfiConverterTypeFfiGroup.lift(it) },
+ { Unit },
+
// Error FFI converter
GenericException.ErrorHandler,
)
@@ -2866,30 +3009,31 @@ open class FfiConversations : Disposable, AutoCloseable, FfiConversationsInterfa
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `list`(`opts`: FfiListConversationsOptions): List {
+ override suspend fun `addMembersByInboxId`(`inboxIds`: List) {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_list(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_add_members_by_inbox_id(
thisPtr,
- FfiConverterTypeFfiListConversationsOptions.lower(`opts`),
+ FfiConverterSequenceString.lower(`inboxIds`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_rust_buffer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_rust_buffer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_rust_buffer(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
// lift function
- { FfiConverterSequenceTypeFfiGroup.lift(it) },
+ { Unit },
+
// Error FFI converter
GenericException.ErrorHandler,
)
@@ -2898,104 +3042,318 @@ open class FfiConversations : Disposable, AutoCloseable, FfiConversationsInterfa
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `processStreamedWelcomeMessage`(`envelopeBytes`: kotlin.ByteArray): FfiGroup {
+ override suspend fun `addSuperAdmin`(`inboxId`: kotlin.String) {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_process_streamed_welcome_message(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_add_super_admin(
thisPtr,
- FfiConverterByteArray.lower(`envelopeBytes`),
+ FfiConverterString.lower(`inboxId`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
// lift function
- { FfiConverterTypeFfiGroup.lift(it) },
+ { Unit },
+
// Error FFI converter
GenericException.ErrorHandler,
)
}
+ @Throws(GenericException::class)
+ override fun `addedByInboxId`(): kotlin.String {
+ return FfiConverterString.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_added_by_inbox_id(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `adminList`(): List {
+ return FfiConverterSequenceString.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_admin_list(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `consentState`(): FfiConsentState {
+ return FfiConverterTypeFfiConsentState.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_consent_state(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ override fun `createdAtNs`(): kotlin.Long {
+ return FfiConverterLong.lift(
+ callWithPointer {
+ uniffiRustCall() { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_created_at_ns(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `findMessages`(`opts`: FfiListMessagesOptions): List {
+ return FfiConverterSequenceTypeFfiMessage.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_find_messages(
+ it, FfiConverterTypeFfiListMessagesOptions.lower(`opts`), _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `groupDescription`(): kotlin.String {
+ return FfiConverterString.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_group_description(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `groupImageUrlSquare`(): kotlin.String {
+ return FfiConverterString.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_group_image_url_square(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `groupMetadata`(): FfiConversationMetadata {
+ return FfiConverterTypeFfiConversationMetadata.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_group_metadata(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `groupName`(): kotlin.String {
+ return FfiConverterString.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_group_name(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `groupPermissions`(): FfiGroupPermissions {
+ return FfiConverterTypeFfiGroupPermissions.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_group_permissions(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `groupPinnedFrameUrl`(): kotlin.String {
+ return FfiConverterString.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_group_pinned_frame_url(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ override fun `id`(): kotlin.ByteArray {
+ return FfiConverterByteArray.lift(
+ callWithPointer {
+ uniffiRustCall() { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_id(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `isActive`(): kotlin.Boolean {
+ return FfiConverterBoolean.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_is_active(
+ it, _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `isAdmin`(`inboxId`: kotlin.String): kotlin.Boolean {
+ return FfiConverterBoolean.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_is_admin(
+ it, FfiConverterString.lower(`inboxId`), _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ override fun `isSuperAdmin`(`inboxId`: kotlin.String): kotlin.Boolean {
+ return FfiConverterBoolean.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_is_super_admin(
+ it, FfiConverterString.lower(`inboxId`), _status
+ )
+ }
+ }
+ )
+ }
+
+
+ @Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `stream`(`callback`: FfiConversationCallback): FfiStreamCloser {
+ override suspend fun `listMembers`(): List {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_stream(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_list_members(
thisPtr,
- FfiConverterTypeFfiConversationCallback.lower(`callback`),
- )
+
+ )
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_rust_buffer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_rust_buffer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_rust_buffer(future) },
// lift function
- { FfiConverterTypeFfiStreamCloser.lift(it) },
+ { FfiConverterSequenceTypeFfiConversationMember.lift(it) },
// Error FFI converter
- UniffiNullRustCallStatusErrorHandler,
+ GenericException.ErrorHandler,
)
}
+ @Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `streamAllMessages`(`messageCallback`: FfiMessageCallback): FfiStreamCloser {
+ override suspend fun `processStreamedConversationMessage`(`envelopeBytes`: kotlin.ByteArray): FfiMessage {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_stream_all_messages(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_process_streamed_conversation_message(
thisPtr,
- FfiConverterTypeFfiMessageCallback.lower(`messageCallback`),
+ FfiConverterByteArray.lower(`envelopeBytes`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_rust_buffer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_rust_buffer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_rust_buffer(future) },
// lift function
- { FfiConverterTypeFfiStreamCloser.lift(it) },
+ { FfiConverterTypeFfiMessage.lift(it) },
// Error FFI converter
- UniffiNullRustCallStatusErrorHandler,
+ GenericException.ErrorHandler,
)
}
+ /**
+ * Publish all unpublished messages
+ */
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `sync`() {
+ override suspend fun `publishMessages`() {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_sync(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_publish_messages(
thisPtr,
)
@@ -3025,343 +3383,282 @@ open class FfiConversations : Disposable, AutoCloseable, FfiConversationsInterfa
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `syncAllGroups`(): kotlin.UInt {
+ override suspend fun `removeAdmin`(`inboxId`: kotlin.String) {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_sync_all_groups(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_remove_admin(
thisPtr,
+ FfiConverterString.lower(`inboxId`),
+ )
+ },
+ { future, callback, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ future,
+ callback,
+ continuation
+ )
+ },
+ { future, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ future,
+ continuation
+ )
+ },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ // lift function
+ { Unit },
- )
+ // Error FFI converter
+ GenericException.ErrorHandler,
+ )
+ }
+
+
+ @Throws(GenericException::class)
+ @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
+ override suspend fun `removeMembers`(`accountAddresses`: List) {
+ return uniffiRustCallAsync(
+ callWithPointer { thisPtr ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_remove_members(
+ thisPtr,
+ FfiConverterSequenceString.lower(`accountAddresses`),
+ )
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_u32(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_u32(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_u32(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
// lift function
- { FfiConverterUInt.lift(it) },
+ { Unit },
+
// Error FFI converter
GenericException.ErrorHandler,
)
}
- companion object
+ @Throws(GenericException::class)
+ @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
+ override suspend fun `removeMembersByInboxId`(`inboxIds`: List) {
+ return uniffiRustCallAsync(
+ callWithPointer { thisPtr ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_remove_members_by_inbox_id(
+ thisPtr,
+ FfiConverterSequenceString.lower(`inboxIds`),
+ )
+ },
+ { future, callback, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ future,
+ callback,
+ continuation
+ )
+ },
+ { future, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ future,
+ continuation
+ )
+ },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ // lift function
+ { Unit },
-}
+ // Error FFI converter
+ GenericException.ErrorHandler,
+ )
+ }
-public object FfiConverterTypeFfiConversations : FfiConverter {
- override fun lower(value: FfiConversations): Pointer {
- return value.uniffiClonePointer()
+ @Throws(GenericException::class)
+ @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
+ override suspend fun `removeSuperAdmin`(`inboxId`: kotlin.String) {
+ return uniffiRustCallAsync(
+ callWithPointer { thisPtr ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_remove_super_admin(
+ thisPtr,
+ FfiConverterString.lower(`inboxId`),
+ )
+ },
+ { future, callback, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ future,
+ callback,
+ continuation
+ )
+ },
+ { future, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ future,
+ continuation
+ )
+ },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ // lift function
+ { Unit },
+
+ // Error FFI converter
+ GenericException.ErrorHandler,
+ )
}
- override fun lift(value: Pointer): FfiConversations {
- return FfiConversations(value)
+
+ @Throws(GenericException::class)
+ @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
+ override suspend fun `send`(`contentBytes`: kotlin.ByteArray): kotlin.ByteArray {
+ return uniffiRustCallAsync(
+ callWithPointer { thisPtr ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_send(
+ thisPtr,
+ FfiConverterByteArray.lower(`contentBytes`),
+ )
+ },
+ { future, callback, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_rust_buffer(
+ future,
+ callback,
+ continuation
+ )
+ },
+ { future, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_rust_buffer(
+ future,
+ continuation
+ )
+ },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_rust_buffer(future) },
+ // lift function
+ { FfiConverterByteArray.lift(it) },
+ // Error FFI converter
+ GenericException.ErrorHandler,
+ )
}
- override fun read(buf: ByteBuffer): FfiConversations {
- // The Rust code always writes pointers as 8 bytes, and will
- // fail to compile if they don't fit.
- return lift(Pointer(buf.getLong()))
+
+ /**
+ * send a message without immediately publishing to the delivery service.
+ */
+ @Throws(GenericException::class)
+ override fun `sendOptimistic`(`contentBytes`: kotlin.ByteArray): kotlin.ByteArray {
+ return FfiConverterByteArray.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_send_optimistic(
+ it, FfiConverterByteArray.lower(`contentBytes`), _status
+ )
+ }
+ }
+ )
}
- override fun allocationSize(value: FfiConversations) = 8UL
- override fun write(value: FfiConversations, buf: ByteBuffer) {
- // The Rust code always expects pointers written as 8 bytes,
- // and will fail to compile if they don't fit.
- buf.putLong(Pointer.nativeValue(lower(value)))
+ @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
+ override suspend fun `stream`(`messageCallback`: FfiMessageCallback): FfiStreamCloser {
+ return uniffiRustCallAsync(
+ callWithPointer { thisPtr ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_stream(
+ thisPtr,
+ FfiConverterTypeFfiMessageCallback.lower(`messageCallback`),
+ )
+ },
+ { future, callback, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
+ future,
+ callback,
+ continuation
+ )
+ },
+ { future, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
+ future,
+ continuation
+ )
+ },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
+ // lift function
+ { FfiConverterTypeFfiStreamCloser.lift(it) },
+ // Error FFI converter
+ UniffiNullRustCallStatusErrorHandler,
+ )
}
-}
-// This template implements a class for working with a Rust struct via a Pointer/Arc
-// to the live Rust struct on the other side of the FFI.
-//
-// Each instance implements core operations for working with the Rust `Arc` and the
-// Kotlin Pointer to work with the live Rust struct on the other side of the FFI.
-//
-// There's some subtlety here, because we have to be careful not to operate on a Rust
-// struct after it has been dropped, and because we must expose a public API for freeing
-// theq Kotlin wrapper object in lieu of reliable finalizers. The core requirements are:
-//
-// * Each instance holds an opaque pointer to the underlying Rust struct.
-// Method calls need to read this pointer from the object's state and pass it in to
-// the Rust FFI.
-//
-// * When an instance is no longer needed, its pointer should be passed to a
-// special destructor function provided by the Rust FFI, which will drop the
-// underlying Rust struct.
-//
-// * Given an instance, calling code is expected to call the special
-// `destroy` method in order to free it after use, either by calling it explicitly
-// or by using a higher-level helper like the `use` method. Failing to do so risks
-// leaking the underlying Rust struct.
-//
-// * We can't assume that calling code will do the right thing, and must be prepared
-// to handle Kotlin method calls executing concurrently with or even after a call to
-// `destroy`, and to handle multiple (possibly concurrent!) calls to `destroy`.
-//
-// * We must never allow Rust code to operate on the underlying Rust struct after
-// the destructor has been called, and must never call the destructor more than once.
-// Doing so may trigger memory unsafety.
-//
-// * To mitigate many of the risks of leaking memory and use-after-free unsafety, a `Cleaner`
-// is implemented to call the destructor when the Kotlin object becomes unreachable.
-// This is done in a background thread. This is not a panacea, and client code should be aware that
-// 1. the thread may starve if some there are objects that have poorly performing
-// `drop` methods or do significant work in their `drop` methods.
-// 2. the thread is shared across the whole library. This can be tuned by using `android_cleaner = true`,
-// or `android = true` in the [`kotlin` section of the `uniffi.toml` file](https://mozilla.github.io/uniffi-rs/kotlin/configuration.html).
-//
-// If we try to implement this with mutual exclusion on access to the pointer, there is the
-// possibility of a race between a method call and a concurrent call to `destroy`:
-//
-// * Thread A starts a method call, reads the value of the pointer, but is interrupted
-// before it can pass the pointer over the FFI to Rust.
-// * Thread B calls `destroy` and frees the underlying Rust struct.
-// * Thread A resumes, passing the already-read pointer value to Rust and triggering
-// a use-after-free.
-//
-// One possible solution would be to use a `ReadWriteLock`, with each method call taking
-// a read lock (and thus allowed to run concurrently) and the special `destroy` method
-// taking a write lock (and thus blocking on live method calls). However, we aim not to
-// generate methods with any hidden blocking semantics, and a `destroy` method that might
-// block if called incorrectly seems to meet that bar.
-//
-// So, we achieve our goals by giving each instance an associated `AtomicLong` counter to track
-// the number of in-flight method calls, and an `AtomicBoolean` flag to indicate whether `destroy`
-// has been called. These are updated according to the following rules:
-//
-// * The initial value of the counter is 1, indicating a live object with no in-flight calls.
-// The initial value for the flag is false.
-//
-// * At the start of each method call, we atomically check the counter.
-// If it is 0 then the underlying Rust struct has already been destroyed and the call is aborted.
-// If it is nonzero them we atomically increment it by 1 and proceed with the method call.
-//
-// * At the end of each method call, we atomically decrement and check the counter.
-// If it has reached zero then we destroy the underlying Rust struct.
-//
-// * When `destroy` is called, we atomically flip the flag from false to true.
-// If the flag was already true we silently fail.
-// Otherwise we atomically decrement and check the counter.
-// If it has reached zero then we destroy the underlying Rust struct.
-//
-// Astute readers may observe that this all sounds very similar to the way that Rust's `Arc` works,
-// and indeed it is, with the addition of a flag to guard against multiple calls to `destroy`.
-//
-// The overall effect is that the underlying Rust struct is destroyed only when `destroy` has been
-// called *and* all in-flight method calls have completed, avoiding violating any of the expectations
-// of the underlying Rust code.
-//
-// This makes a cleaner a better alternative to _not_ calling `destroy()` as
-// and when the object is finished with, but the abstraction is not perfect: if the Rust object's `drop`
-// method is slow, and/or there are many objects to cleanup, and it's on a low end Android device, then the cleaner
-// thread may be starved, and the app will leak memory.
-//
-// In this case, `destroy`ing manually may be a better solution.
-//
-// The cleaner can live side by side with the manual calling of `destroy`. In the order of responsiveness, uniffi objects
-// with Rust peers are reclaimed:
-//
-// 1. By calling the `destroy` method of the object, which calls `rustObject.free()`. If that doesn't happen:
-// 2. When the object becomes unreachable, AND the Cleaner thread gets to call `rustObject.free()`. If the thread is starved then:
-// 3. The memory is reclaimed when the process terminates.
-//
-// [1] https://stackoverflow.com/questions/24376768/can-java-finalize-an-object-when-it-is-still-in-scope/24380219
-//
-
-
-public interface FfiGroupInterface {
-
- suspend fun `addAdmin`(`inboxId`: kotlin.String)
-
- suspend fun `addMembers`(`accountAddresses`: List)
-
- suspend fun `addMembersByInboxId`(`inboxIds`: List)
-
- suspend fun `addSuperAdmin`(`inboxId`: kotlin.String)
-
- fun `addedByInboxId`(): kotlin.String
-
- fun `adminList`(): List
-
- fun `consentState`(): FfiConsentState
-
- fun `createdAtNs`(): kotlin.Long
-
- fun `findMessages`(`opts`: FfiListMessagesOptions): List
-
- fun `groupDescription`(): kotlin.String
-
- fun `groupImageUrlSquare`(): kotlin.String
-
- fun `groupMetadata`(): FfiGroupMetadata
-
- fun `groupName`(): kotlin.String
-
- fun `groupPermissions`(): FfiGroupPermissions
-
- fun `groupPinnedFrameUrl`(): kotlin.String
-
- fun `id`(): kotlin.ByteArray
-
- fun `isActive`(): kotlin.Boolean
-
- fun `isAdmin`(`inboxId`: kotlin.String): kotlin.Boolean
-
- fun `isSuperAdmin`(`inboxId`: kotlin.String): kotlin.Boolean
-
- suspend fun `listMembers`(): List
-
- suspend fun `processStreamedGroupMessage`(`envelopeBytes`: kotlin.ByteArray): FfiMessage
-
- /**
- * Publish all unpublished messages
- */
- suspend fun `publishMessages`()
-
- suspend fun `removeAdmin`(`inboxId`: kotlin.String)
-
- suspend fun `removeMembers`(`accountAddresses`: List)
-
- suspend fun `removeMembersByInboxId`(`inboxIds`: List)
-
- suspend fun `removeSuperAdmin`(`inboxId`: kotlin.String)
-
- suspend fun `send`(`contentBytes`: kotlin.ByteArray): kotlin.ByteArray
-
- /**
- * send a message without immediately publishing to the delivery service.
- */
- fun `sendOptimistic`(`contentBytes`: kotlin.ByteArray): kotlin.ByteArray
-
- suspend fun `stream`(`messageCallback`: FfiMessageCallback): FfiStreamCloser
-
- fun `superAdminList`(): List
-
- suspend fun `sync`()
-
- fun `updateConsentState`(`state`: FfiConsentState)
-
- suspend fun `updateGroupDescription`(`groupDescription`: kotlin.String)
-
- suspend fun `updateGroupImageUrlSquare`(`groupImageUrlSquare`: kotlin.String)
-
- suspend fun `updateGroupName`(`groupName`: kotlin.String)
-
- suspend fun `updateGroupPinnedFrameUrl`(`pinnedFrameUrl`: kotlin.String)
-
- suspend fun `updatePermissionPolicy`(
- `permissionUpdateType`: FfiPermissionUpdateType,
- `permissionPolicyOption`: FfiPermissionPolicy,
- `metadataField`: FfiMetadataField?,
- )
-
- companion object
-}
-
-open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
-
- constructor(pointer: Pointer) {
- this.pointer = pointer
- this.cleanable = UniffiLib.CLEANER.register(this, UniffiCleanAction(pointer))
- }
-
- /**
- * This constructor can be used to instantiate a fake object. Only used for tests. Any
- * attempt to actually use an object constructed this way will fail as there is no
- * connected Rust object.
- */
- @Suppress("UNUSED_PARAMETER")
- constructor(noPointer: NoPointer) {
- this.pointer = null
- this.cleanable = UniffiLib.CLEANER.register(this, UniffiCleanAction(pointer))
+ @Throws(GenericException::class)
+ override fun `superAdminList`(): List {
+ return FfiConverterSequenceString.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_super_admin_list(
+ it, _status
+ )
+ }
+ }
+ )
}
- protected val pointer: Pointer?
- protected val cleanable: UniffiCleaner.Cleanable
- private val wasDestroyed = AtomicBoolean(false)
- private val callCounter = AtomicLong(1)
+ @Throws(GenericException::class)
+ @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
+ override suspend fun `sync`() {
+ return uniffiRustCallAsync(
+ callWithPointer { thisPtr ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_sync(
+ thisPtr,
- override fun destroy() {
- // Only allow a single call to this method.
- // TODO: maybe we should log a warning if called more than once?
- if (this.wasDestroyed.compareAndSet(false, true)) {
- // This decrement always matches the initial count of 1 given at creation time.
- if (this.callCounter.decrementAndGet() == 0L) {
- cleanable.clean()
- }
- }
- }
+ )
+ },
+ { future, callback, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ future,
+ callback,
+ continuation
+ )
+ },
+ { future, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ future,
+ continuation
+ )
+ },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ // lift function
+ { Unit },
- @Synchronized
- override fun close() {
- this.destroy()
+ // Error FFI converter
+ GenericException.ErrorHandler,
+ )
}
- internal inline fun callWithPointer(block: (ptr: Pointer) -> R): R {
- // Check and increment the call counter, to keep the object alive.
- // This needs a compare-and-set retry loop in case of concurrent updates.
- do {
- val c = this.callCounter.get()
- if (c == 0L) {
- throw IllegalStateException("${this.javaClass.simpleName} object has already been destroyed")
- }
- if (c == Long.MAX_VALUE) {
- throw IllegalStateException("${this.javaClass.simpleName} call counter would overflow")
- }
- } while (!this.callCounter.compareAndSet(c, c + 1L))
- // Now we can safely do the method call without the pointer being freed concurrently.
- try {
- return block(this.uniffiClonePointer())
- } finally {
- // This decrement always matches the increment we performed above.
- if (this.callCounter.decrementAndGet() == 0L) {
- cleanable.clean()
- }
- }
- }
- // Use a static inner class instead of a closure so as not to accidentally
- // capture `this` as part of the cleanable's action.
- private class UniffiCleanAction(private val pointer: Pointer?) : Runnable {
- override fun run() {
- pointer?.let { ptr ->
- uniffiRustCall { status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_free_ffigroup(ptr, status)
- }
+ @Throws(GenericException::class)
+ override fun `updateConsentState`(`state`: FfiConsentState) =
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_update_consent_state(
+ it, FfiConverterTypeFfiConsentState.lower(`state`), _status
+ )
}
}
- }
-
- fun uniffiClonePointer(): Pointer {
- return uniffiRustCall() { status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_clone_ffigroup(pointer!!, status)
- }
- }
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `addAdmin`(`inboxId`: kotlin.String) {
+ override suspend fun `updateGroupDescription`(`groupDescription`: kotlin.String) {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_add_admin(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_update_group_description(
thisPtr,
- FfiConverterString.lower(`inboxId`),
+ FfiConverterString.lower(`groupDescription`),
)
},
{ future, callback, continuation ->
@@ -3389,12 +3686,12 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `addMembers`(`accountAddresses`: List) {
+ override suspend fun `updateGroupImageUrlSquare`(`groupImageUrlSquare`: kotlin.String) {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_add_members(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_update_group_image_url_square(
thisPtr,
- FfiConverterSequenceString.lower(`accountAddresses`),
+ FfiConverterString.lower(`groupImageUrlSquare`),
)
},
{ future, callback, continuation ->
@@ -3422,12 +3719,12 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `addMembersByInboxId`(`inboxIds`: List) {
+ override suspend fun `updateGroupName`(`groupName`: kotlin.String) {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_add_members_by_inbox_id(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_update_group_name(
thisPtr,
- FfiConverterSequenceString.lower(`inboxIds`),
+ FfiConverterString.lower(`groupName`),
)
},
{ future, callback, continuation ->
@@ -3455,12 +3752,12 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `addSuperAdmin`(`inboxId`: kotlin.String) {
+ override suspend fun `updateGroupPinnedFrameUrl`(`pinnedFrameUrl`: kotlin.String) {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_add_super_admin(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_update_group_pinned_frame_url(
thisPtr,
- FfiConverterString.lower(`inboxId`),
+ FfiConverterString.lower(`pinnedFrameUrl`),
)
},
{ future, callback, continuation ->
@@ -3487,150 +3784,267 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
@Throws(GenericException::class)
- override fun `addedByInboxId`(): kotlin.String {
- return FfiConverterString.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_added_by_inbox_id(
- it, _status
- )
- }
- }
+ @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
+ override suspend fun `updatePermissionPolicy`(
+ `permissionUpdateType`: FfiPermissionUpdateType,
+ `permissionPolicyOption`: FfiPermissionPolicy,
+ `metadataField`: FfiMetadataField?,
+ ) {
+ return uniffiRustCallAsync(
+ callWithPointer { thisPtr ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversation_update_permission_policy(
+ thisPtr,
+ FfiConverterTypeFfiPermissionUpdateType.lower(`permissionUpdateType`),
+ FfiConverterTypeFfiPermissionPolicy.lower(`permissionPolicyOption`),
+ FfiConverterOptionalTypeFfiMetadataField.lower(`metadataField`),
+ )
+ },
+ { future, callback, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ future,
+ callback,
+ continuation
+ )
+ },
+ { future, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ future,
+ continuation
+ )
+ },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ // lift function
+ { Unit },
+
+ // Error FFI converter
+ GenericException.ErrorHandler,
)
}
- @Throws(GenericException::class)
- override fun `adminList`(): List {
- return FfiConverterSequenceString.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_admin_list(
- it, _status
- )
- }
- }
- )
- }
+ companion object
+}
- @Throws(GenericException::class)
- override fun `consentState`(): FfiConsentState {
- return FfiConverterTypeFfiConsentState.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_consent_state(
- it, _status
- )
- }
- }
- )
+public object FfiConverterTypeFfiConversation : FfiConverter {
+
+ override fun lower(value: FfiConversation): Pointer {
+ return value.uniffiClonePointer()
}
+ override fun lift(value: Pointer): FfiConversation {
+ return FfiConversation(value)
+ }
- override fun `createdAtNs`(): kotlin.Long {
- return FfiConverterLong.lift(
- callWithPointer {
- uniffiRustCall() { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_created_at_ns(
- it, _status
- )
- }
- }
- )
+ override fun read(buf: ByteBuffer): FfiConversation {
+ // The Rust code always writes pointers as 8 bytes, and will
+ // fail to compile if they don't fit.
+ return lift(Pointer(buf.getLong()))
}
+ override fun allocationSize(value: FfiConversation) = 8UL
- @Throws(GenericException::class)
- override fun `findMessages`(`opts`: FfiListMessagesOptions): List {
- return FfiConverterSequenceTypeFfiMessage.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_find_messages(
- it, FfiConverterTypeFfiListMessagesOptions.lower(`opts`), _status
- )
- }
- }
- )
+ override fun write(value: FfiConversation, buf: ByteBuffer) {
+ // The Rust code always expects pointers written as 8 bytes,
+ // and will fail to compile if they don't fit.
+ buf.putLong(Pointer.nativeValue(lower(value)))
}
+}
- @Throws(GenericException::class)
- override fun `groupDescription`(): kotlin.String {
- return FfiConverterString.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_group_description(
- it, _status
- )
- }
- }
- )
- }
+// This template implements a class for working with a Rust struct via a Pointer/Arc
+// to the live Rust struct on the other side of the FFI.
+//
+// Each instance implements core operations for working with the Rust `Arc` and the
+// Kotlin Pointer to work with the live Rust struct on the other side of the FFI.
+//
+// There's some subtlety here, because we have to be careful not to operate on a Rust
+// struct after it has been dropped, and because we must expose a public API for freeing
+// theq Kotlin wrapper object in lieu of reliable finalizers. The core requirements are:
+//
+// * Each instance holds an opaque pointer to the underlying Rust struct.
+// Method calls need to read this pointer from the object's state and pass it in to
+// the Rust FFI.
+//
+// * When an instance is no longer needed, its pointer should be passed to a
+// special destructor function provided by the Rust FFI, which will drop the
+// underlying Rust struct.
+//
+// * Given an instance, calling code is expected to call the special
+// `destroy` method in order to free it after use, either by calling it explicitly
+// or by using a higher-level helper like the `use` method. Failing to do so risks
+// leaking the underlying Rust struct.
+//
+// * We can't assume that calling code will do the right thing, and must be prepared
+// to handle Kotlin method calls executing concurrently with or even after a call to
+// `destroy`, and to handle multiple (possibly concurrent!) calls to `destroy`.
+//
+// * We must never allow Rust code to operate on the underlying Rust struct after
+// the destructor has been called, and must never call the destructor more than once.
+// Doing so may trigger memory unsafety.
+//
+// * To mitigate many of the risks of leaking memory and use-after-free unsafety, a `Cleaner`
+// is implemented to call the destructor when the Kotlin object becomes unreachable.
+// This is done in a background thread. This is not a panacea, and client code should be aware that
+// 1. the thread may starve if some there are objects that have poorly performing
+// `drop` methods or do significant work in their `drop` methods.
+// 2. the thread is shared across the whole library. This can be tuned by using `android_cleaner = true`,
+// or `android = true` in the [`kotlin` section of the `uniffi.toml` file](https://mozilla.github.io/uniffi-rs/kotlin/configuration.html).
+//
+// If we try to implement this with mutual exclusion on access to the pointer, there is the
+// possibility of a race between a method call and a concurrent call to `destroy`:
+//
+// * Thread A starts a method call, reads the value of the pointer, but is interrupted
+// before it can pass the pointer over the FFI to Rust.
+// * Thread B calls `destroy` and frees the underlying Rust struct.
+// * Thread A resumes, passing the already-read pointer value to Rust and triggering
+// a use-after-free.
+//
+// One possible solution would be to use a `ReadWriteLock`, with each method call taking
+// a read lock (and thus allowed to run concurrently) and the special `destroy` method
+// taking a write lock (and thus blocking on live method calls). However, we aim not to
+// generate methods with any hidden blocking semantics, and a `destroy` method that might
+// block if called incorrectly seems to meet that bar.
+//
+// So, we achieve our goals by giving each instance an associated `AtomicLong` counter to track
+// the number of in-flight method calls, and an `AtomicBoolean` flag to indicate whether `destroy`
+// has been called. These are updated according to the following rules:
+//
+// * The initial value of the counter is 1, indicating a live object with no in-flight calls.
+// The initial value for the flag is false.
+//
+// * At the start of each method call, we atomically check the counter.
+// If it is 0 then the underlying Rust struct has already been destroyed and the call is aborted.
+// If it is nonzero them we atomically increment it by 1 and proceed with the method call.
+//
+// * At the end of each method call, we atomically decrement and check the counter.
+// If it has reached zero then we destroy the underlying Rust struct.
+//
+// * When `destroy` is called, we atomically flip the flag from false to true.
+// If the flag was already true we silently fail.
+// Otherwise we atomically decrement and check the counter.
+// If it has reached zero then we destroy the underlying Rust struct.
+//
+// Astute readers may observe that this all sounds very similar to the way that Rust's `Arc` works,
+// and indeed it is, with the addition of a flag to guard against multiple calls to `destroy`.
+//
+// The overall effect is that the underlying Rust struct is destroyed only when `destroy` has been
+// called *and* all in-flight method calls have completed, avoiding violating any of the expectations
+// of the underlying Rust code.
+//
+// This makes a cleaner a better alternative to _not_ calling `destroy()` as
+// and when the object is finished with, but the abstraction is not perfect: if the Rust object's `drop`
+// method is slow, and/or there are many objects to cleanup, and it's on a low end Android device, then the cleaner
+// thread may be starved, and the app will leak memory.
+//
+// In this case, `destroy`ing manually may be a better solution.
+//
+// The cleaner can live side by side with the manual calling of `destroy`. In the order of responsiveness, uniffi objects
+// with Rust peers are reclaimed:
+//
+// 1. By calling the `destroy` method of the object, which calls `rustObject.free()`. If that doesn't happen:
+// 2. When the object becomes unreachable, AND the Cleaner thread gets to call `rustObject.free()`. If the thread is starved then:
+// 3. The memory is reclaimed when the process terminates.
+//
+// [1] https://stackoverflow.com/questions/24376768/can-java-finalize-an-object-when-it-is-still-in-scope/24380219
+//
- @Throws(GenericException::class)
- override fun `groupImageUrlSquare`(): kotlin.String {
- return FfiConverterString.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_group_image_url_square(
- it, _status
- )
- }
- }
- )
+public interface FfiConversationMetadataInterface {
+
+ fun `conversationType`(): kotlin.String
+
+ fun `creatorInboxId`(): kotlin.String
+
+ companion object
+}
+
+open class FfiConversationMetadata : Disposable, AutoCloseable, FfiConversationMetadataInterface {
+
+ constructor(pointer: Pointer) {
+ this.pointer = pointer
+ this.cleanable = UniffiLib.CLEANER.register(this, UniffiCleanAction(pointer))
}
+ /**
+ * This constructor can be used to instantiate a fake object. Only used for tests. Any
+ * attempt to actually use an object constructed this way will fail as there is no
+ * connected Rust object.
+ */
+ @Suppress("UNUSED_PARAMETER")
+ constructor(noPointer: NoPointer) {
+ this.pointer = null
+ this.cleanable = UniffiLib.CLEANER.register(this, UniffiCleanAction(pointer))
+ }
- @Throws(GenericException::class)
- override fun `groupMetadata`(): FfiGroupMetadata {
- return FfiConverterTypeFfiGroupMetadata.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_group_metadata(
- it, _status
- )
- }
+ protected val pointer: Pointer?
+ protected val cleanable: UniffiCleaner.Cleanable
+
+ private val wasDestroyed = AtomicBoolean(false)
+ private val callCounter = AtomicLong(1)
+
+ override fun destroy() {
+ // Only allow a single call to this method.
+ // TODO: maybe we should log a warning if called more than once?
+ if (this.wasDestroyed.compareAndSet(false, true)) {
+ // This decrement always matches the initial count of 1 given at creation time.
+ if (this.callCounter.decrementAndGet() == 0L) {
+ cleanable.clean()
}
- )
+ }
}
+ @Synchronized
+ override fun close() {
+ this.destroy()
+ }
- @Throws(GenericException::class)
- override fun `groupName`(): kotlin.String {
- return FfiConverterString.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_group_name(
- it, _status
- )
- }
+ internal inline fun callWithPointer(block: (ptr: Pointer) -> R): R {
+ // Check and increment the call counter, to keep the object alive.
+ // This needs a compare-and-set retry loop in case of concurrent updates.
+ do {
+ val c = this.callCounter.get()
+ if (c == 0L) {
+ throw IllegalStateException("${this.javaClass.simpleName} object has already been destroyed")
+ }
+ if (c == Long.MAX_VALUE) {
+ throw IllegalStateException("${this.javaClass.simpleName} call counter would overflow")
}
- )
+ } while (!this.callCounter.compareAndSet(c, c + 1L))
+ // Now we can safely do the method call without the pointer being freed concurrently.
+ try {
+ return block(this.uniffiClonePointer())
+ } finally {
+ // This decrement always matches the increment we performed above.
+ if (this.callCounter.decrementAndGet() == 0L) {
+ cleanable.clean()
+ }
+ }
}
-
- @Throws(GenericException::class)
- override fun `groupPermissions`(): FfiGroupPermissions {
- return FfiConverterTypeFfiGroupPermissions.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_group_permissions(
- it, _status
- )
+ // Use a static inner class instead of a closure so as not to accidentally
+ // capture `this` as part of the cleanable's action.
+ private class UniffiCleanAction(private val pointer: Pointer?) : Runnable {
+ override fun run() {
+ pointer?.let { ptr ->
+ uniffiRustCall { status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_free_fficonversationmetadata(ptr, status)
}
}
- )
+ }
}
+ fun uniffiClonePointer(): Pointer {
+ return uniffiRustCall() { status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_clone_fficonversationmetadata(pointer!!, status)
+ }
+ }
- @Throws(GenericException::class)
- override fun `groupPinnedFrameUrl`(): kotlin.String {
+ override fun `conversationType`(): kotlin.String {
return FfiConverterString.lift(
callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_group_pinned_frame_url(
+ uniffiRustCall() { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversationmetadata_conversation_type(
it, _status
)
}
@@ -3639,11 +4053,11 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
}
- override fun `id`(): kotlin.ByteArray {
- return FfiConverterByteArray.lift(
+ override fun `creatorInboxId`(): kotlin.String {
+ return FfiConverterString.lift(
callWithPointer {
uniffiRustCall() { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_id(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversationmetadata_creator_inbox_id(
it, _status
)
}
@@ -3652,175 +4066,279 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
}
- @Throws(GenericException::class)
- override fun `isActive`(): kotlin.Boolean {
- return FfiConverterBoolean.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_is_active(
- it, _status
- )
- }
- }
- )
+ companion object
+
+}
+
+public object FfiConverterTypeFfiConversationMetadata :
+ FfiConverter {
+
+ override fun lower(value: FfiConversationMetadata): Pointer {
+ return value.uniffiClonePointer()
}
+ override fun lift(value: Pointer): FfiConversationMetadata {
+ return FfiConversationMetadata(value)
+ }
- @Throws(GenericException::class)
- override fun `isAdmin`(`inboxId`: kotlin.String): kotlin.Boolean {
- return FfiConverterBoolean.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_is_admin(
- it, FfiConverterString.lower(`inboxId`), _status
- )
- }
- }
- )
+ override fun read(buf: ByteBuffer): FfiConversationMetadata {
+ // The Rust code always writes pointers as 8 bytes, and will
+ // fail to compile if they don't fit.
+ return lift(Pointer(buf.getLong()))
}
+ override fun allocationSize(value: FfiConversationMetadata) = 8UL
- @Throws(GenericException::class)
- override fun `isSuperAdmin`(`inboxId`: kotlin.String): kotlin.Boolean {
- return FfiConverterBoolean.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_is_super_admin(
- it, FfiConverterString.lower(`inboxId`), _status
- )
- }
- }
- )
+ override fun write(value: FfiConversationMetadata, buf: ByteBuffer) {
+ // The Rust code always expects pointers written as 8 bytes,
+ // and will fail to compile if they don't fit.
+ buf.putLong(Pointer.nativeValue(lower(value)))
}
+}
- @Throws(GenericException::class)
- @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `listMembers`(): List {
- return uniffiRustCallAsync(
- callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_list_members(
- thisPtr,
+// This template implements a class for working with a Rust struct via a Pointer/Arc
+// to the live Rust struct on the other side of the FFI.
+//
+// Each instance implements core operations for working with the Rust `Arc` and the
+// Kotlin Pointer to work with the live Rust struct on the other side of the FFI.
+//
+// There's some subtlety here, because we have to be careful not to operate on a Rust
+// struct after it has been dropped, and because we must expose a public API for freeing
+// theq Kotlin wrapper object in lieu of reliable finalizers. The core requirements are:
+//
+// * Each instance holds an opaque pointer to the underlying Rust struct.
+// Method calls need to read this pointer from the object's state and pass it in to
+// the Rust FFI.
+//
+// * When an instance is no longer needed, its pointer should be passed to a
+// special destructor function provided by the Rust FFI, which will drop the
+// underlying Rust struct.
+//
+// * Given an instance, calling code is expected to call the special
+// `destroy` method in order to free it after use, either by calling it explicitly
+// or by using a higher-level helper like the `use` method. Failing to do so risks
+// leaking the underlying Rust struct.
+//
+// * We can't assume that calling code will do the right thing, and must be prepared
+// to handle Kotlin method calls executing concurrently with or even after a call to
+// `destroy`, and to handle multiple (possibly concurrent!) calls to `destroy`.
+//
+// * We must never allow Rust code to operate on the underlying Rust struct after
+// the destructor has been called, and must never call the destructor more than once.
+// Doing so may trigger memory unsafety.
+//
+// * To mitigate many of the risks of leaking memory and use-after-free unsafety, a `Cleaner`
+// is implemented to call the destructor when the Kotlin object becomes unreachable.
+// This is done in a background thread. This is not a panacea, and client code should be aware that
+// 1. the thread may starve if some there are objects that have poorly performing
+// `drop` methods or do significant work in their `drop` methods.
+// 2. the thread is shared across the whole library. This can be tuned by using `android_cleaner = true`,
+// or `android = true` in the [`kotlin` section of the `uniffi.toml` file](https://mozilla.github.io/uniffi-rs/kotlin/configuration.html).
+//
+// If we try to implement this with mutual exclusion on access to the pointer, there is the
+// possibility of a race between a method call and a concurrent call to `destroy`:
+//
+// * Thread A starts a method call, reads the value of the pointer, but is interrupted
+// before it can pass the pointer over the FFI to Rust.
+// * Thread B calls `destroy` and frees the underlying Rust struct.
+// * Thread A resumes, passing the already-read pointer value to Rust and triggering
+// a use-after-free.
+//
+// One possible solution would be to use a `ReadWriteLock`, with each method call taking
+// a read lock (and thus allowed to run concurrently) and the special `destroy` method
+// taking a write lock (and thus blocking on live method calls). However, we aim not to
+// generate methods with any hidden blocking semantics, and a `destroy` method that might
+// block if called incorrectly seems to meet that bar.
+//
+// So, we achieve our goals by giving each instance an associated `AtomicLong` counter to track
+// the number of in-flight method calls, and an `AtomicBoolean` flag to indicate whether `destroy`
+// has been called. These are updated according to the following rules:
+//
+// * The initial value of the counter is 1, indicating a live object with no in-flight calls.
+// The initial value for the flag is false.
+//
+// * At the start of each method call, we atomically check the counter.
+// If it is 0 then the underlying Rust struct has already been destroyed and the call is aborted.
+// If it is nonzero them we atomically increment it by 1 and proceed with the method call.
+//
+// * At the end of each method call, we atomically decrement and check the counter.
+// If it has reached zero then we destroy the underlying Rust struct.
+//
+// * When `destroy` is called, we atomically flip the flag from false to true.
+// If the flag was already true we silently fail.
+// Otherwise we atomically decrement and check the counter.
+// If it has reached zero then we destroy the underlying Rust struct.
+//
+// Astute readers may observe that this all sounds very similar to the way that Rust's `Arc` works,
+// and indeed it is, with the addition of a flag to guard against multiple calls to `destroy`.
+//
+// The overall effect is that the underlying Rust struct is destroyed only when `destroy` has been
+// called *and* all in-flight method calls have completed, avoiding violating any of the expectations
+// of the underlying Rust code.
+//
+// This makes a cleaner a better alternative to _not_ calling `destroy()` as
+// and when the object is finished with, but the abstraction is not perfect: if the Rust object's `drop`
+// method is slow, and/or there are many objects to cleanup, and it's on a low end Android device, then the cleaner
+// thread may be starved, and the app will leak memory.
+//
+// In this case, `destroy`ing manually may be a better solution.
+//
+// The cleaner can live side by side with the manual calling of `destroy`. In the order of responsiveness, uniffi objects
+// with Rust peers are reclaimed:
+//
+// 1. By calling the `destroy` method of the object, which calls `rustObject.free()`. If that doesn't happen:
+// 2. When the object becomes unreachable, AND the Cleaner thread gets to call `rustObject.free()`. If the thread is starved then:
+// 3. The memory is reclaimed when the process terminates.
+//
+// [1] https://stackoverflow.com/questions/24376768/can-java-finalize-an-object-when-it-is-still-in-scope/24380219
+//
- )
- },
- { future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_rust_buffer(
- future,
- callback,
- continuation
- )
- },
- { future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_rust_buffer(
- future,
- continuation
- )
- },
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_rust_buffer(future) },
- // lift function
- { FfiConverterSequenceTypeFfiGroupMember.lift(it) },
- // Error FFI converter
- GenericException.ErrorHandler,
- )
- }
+public interface FfiConversationsInterface {
- @Throws(GenericException::class)
- @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `processStreamedGroupMessage`(`envelopeBytes`: kotlin.ByteArray): FfiMessage {
- return uniffiRustCallAsync(
- callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_process_streamed_group_message(
- thisPtr,
- FfiConverterByteArray.lower(`envelopeBytes`),
- )
- },
- { future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_rust_buffer(
- future,
- callback,
- continuation
- )
- },
- { future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_rust_buffer(
- future,
- continuation
- )
- },
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_rust_buffer(future) },
- // lift function
- { FfiConverterTypeFfiMessage.lift(it) },
- // Error FFI converter
- GenericException.ErrorHandler,
- )
- }
+ suspend fun `createDm`(`accountAddress`: kotlin.String): FfiConversation
+
+ suspend fun `createGroup`(
+ `accountAddresses`: List,
+ `opts`: FfiCreateGroupOptions,
+ ): FfiConversation
+
+ suspend fun `list`(`opts`: FfiListConversationsOptions): List
+
+ suspend fun `listDms`(`opts`: FfiListConversationsOptions): List
+
+ suspend fun `listGroups`(`opts`: FfiListConversationsOptions): List
+
+ suspend fun `processStreamedWelcomeMessage`(`envelopeBytes`: kotlin.ByteArray): FfiConversation
+
+ suspend fun `stream`(`callback`: FfiConversationCallback): FfiStreamCloser
+
+ suspend fun `streamAllDmMessages`(`messageCallback`: FfiMessageCallback): FfiStreamCloser
+
+ suspend fun `streamAllGroupMessages`(`messageCallback`: FfiMessageCallback): FfiStreamCloser
+
+ suspend fun `streamAllMessages`(`messageCallback`: FfiMessageCallback): FfiStreamCloser
+
+ suspend fun `streamDms`(`callback`: FfiConversationCallback): FfiStreamCloser
+
+ suspend fun `streamGroups`(`callback`: FfiConversationCallback): FfiStreamCloser
+
+ suspend fun `sync`()
+
+ suspend fun `syncAllConversations`(): kotlin.UInt
+
+ companion object
+}
+
+open class FfiConversations : Disposable, AutoCloseable, FfiConversationsInterface {
+ constructor(pointer: Pointer) {
+ this.pointer = pointer
+ this.cleanable = UniffiLib.CLEANER.register(this, UniffiCleanAction(pointer))
+ }
/**
- * Publish all unpublished messages
+ * This constructor can be used to instantiate a fake object. Only used for tests. Any
+ * attempt to actually use an object constructed this way will fail as there is no
+ * connected Rust object.
*/
- @Throws(GenericException::class)
- @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `publishMessages`() {
- return uniffiRustCallAsync(
- callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_publish_messages(
- thisPtr,
+ @Suppress("UNUSED_PARAMETER")
+ constructor(noPointer: NoPointer) {
+ this.pointer = null
+ this.cleanable = UniffiLib.CLEANER.register(this, UniffiCleanAction(pointer))
+ }
- )
- },
- { future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
- future,
- callback,
- continuation
- )
- },
- { future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
- future,
- continuation
- )
- },
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
- // lift function
- { Unit },
+ protected val pointer: Pointer?
+ protected val cleanable: UniffiCleaner.Cleanable
- // Error FFI converter
- GenericException.ErrorHandler,
- )
+ private val wasDestroyed = AtomicBoolean(false)
+ private val callCounter = AtomicLong(1)
+
+ override fun destroy() {
+ // Only allow a single call to this method.
+ // TODO: maybe we should log a warning if called more than once?
+ if (this.wasDestroyed.compareAndSet(false, true)) {
+ // This decrement always matches the initial count of 1 given at creation time.
+ if (this.callCounter.decrementAndGet() == 0L) {
+ cleanable.clean()
+ }
+ }
+ }
+
+ @Synchronized
+ override fun close() {
+ this.destroy()
+ }
+
+ internal inline fun callWithPointer(block: (ptr: Pointer) -> R): R {
+ // Check and increment the call counter, to keep the object alive.
+ // This needs a compare-and-set retry loop in case of concurrent updates.
+ do {
+ val c = this.callCounter.get()
+ if (c == 0L) {
+ throw IllegalStateException("${this.javaClass.simpleName} object has already been destroyed")
+ }
+ if (c == Long.MAX_VALUE) {
+ throw IllegalStateException("${this.javaClass.simpleName} call counter would overflow")
+ }
+ } while (!this.callCounter.compareAndSet(c, c + 1L))
+ // Now we can safely do the method call without the pointer being freed concurrently.
+ try {
+ return block(this.uniffiClonePointer())
+ } finally {
+ // This decrement always matches the increment we performed above.
+ if (this.callCounter.decrementAndGet() == 0L) {
+ cleanable.clean()
+ }
+ }
+ }
+
+ // Use a static inner class instead of a closure so as not to accidentally
+ // capture `this` as part of the cleanable's action.
+ private class UniffiCleanAction(private val pointer: Pointer?) : Runnable {
+ override fun run() {
+ pointer?.let { ptr ->
+ uniffiRustCall { status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_free_fficonversations(ptr, status)
+ }
+ }
+ }
+ }
+
+ fun uniffiClonePointer(): Pointer {
+ return uniffiRustCall() { status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_clone_fficonversations(pointer!!, status)
+ }
}
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `removeAdmin`(`inboxId`: kotlin.String) {
+ override suspend fun `createDm`(`accountAddress`: kotlin.String): FfiConversation {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_remove_admin(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_create_dm(
thisPtr,
- FfiConverterString.lower(`inboxId`),
+ FfiConverterString.lower(`accountAddress`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
// lift function
- { Unit },
-
+ { FfiConverterTypeFfiConversation.lift(it) },
// Error FFI converter
GenericException.ErrorHandler,
)
@@ -3829,31 +4347,34 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `removeMembers`(`accountAddresses`: List) {
+ override suspend fun `createGroup`(
+ `accountAddresses`: List,
+ `opts`: FfiCreateGroupOptions,
+ ): FfiConversation {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_remove_members(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_create_group(
thisPtr,
FfiConverterSequenceString.lower(`accountAddresses`),
+ FfiConverterTypeFfiCreateGroupOptions.lower(`opts`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
// lift function
- { Unit },
-
+ { FfiConverterTypeFfiConversation.lift(it) },
// Error FFI converter
GenericException.ErrorHandler,
)
@@ -3862,31 +4383,30 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `removeMembersByInboxId`(`inboxIds`: List) {
+ override suspend fun `list`(`opts`: FfiListConversationsOptions): List {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_remove_members_by_inbox_id(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_list(
thisPtr,
- FfiConverterSequenceString.lower(`inboxIds`),
+ FfiConverterTypeFfiListConversationsOptions.lower(`opts`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_rust_buffer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_rust_buffer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_rust_buffer(future) },
// lift function
- { Unit },
-
+ { FfiConverterSequenceTypeFfiConversation.lift(it) },
// Error FFI converter
GenericException.ErrorHandler,
)
@@ -3895,31 +4415,30 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `removeSuperAdmin`(`inboxId`: kotlin.String) {
+ override suspend fun `listDms`(`opts`: FfiListConversationsOptions): List {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_remove_super_admin(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_list_dms(
thisPtr,
- FfiConverterString.lower(`inboxId`),
+ FfiConverterTypeFfiListConversationsOptions.lower(`opts`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_rust_buffer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_rust_buffer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_rust_buffer(future) },
// lift function
- { Unit },
-
+ { FfiConverterSequenceTypeFfiConversation.lift(it) },
// Error FFI converter
GenericException.ErrorHandler,
)
@@ -3928,12 +4447,12 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `send`(`contentBytes`: kotlin.ByteArray): kotlin.ByteArray {
+ override suspend fun `listGroups`(`opts`: FfiListConversationsOptions): List {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_send(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_list_groups(
thisPtr,
- FfiConverterByteArray.lower(`contentBytes`),
+ FfiConverterTypeFfiListConversationsOptions.lower(`opts`),
)
},
{ future, callback, continuation ->
@@ -3951,37 +4470,21 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
},
{ future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_rust_buffer(future) },
// lift function
- { FfiConverterByteArray.lift(it) },
+ { FfiConverterSequenceTypeFfiConversation.lift(it) },
// Error FFI converter
GenericException.ErrorHandler,
)
}
- /**
- * send a message without immediately publishing to the delivery service.
- */
@Throws(GenericException::class)
- override fun `sendOptimistic`(`contentBytes`: kotlin.ByteArray): kotlin.ByteArray {
- return FfiConverterByteArray.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_send_optimistic(
- it, FfiConverterByteArray.lower(`contentBytes`), _status
- )
- }
- }
- )
- }
-
-
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `stream`(`messageCallback`: FfiMessageCallback): FfiStreamCloser {
+ override suspend fun `processStreamedWelcomeMessage`(`envelopeBytes`: kotlin.ByteArray): FfiConversation {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_stream(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_process_streamed_welcome_message(
thisPtr,
- FfiConverterTypeFfiMessageCallback.lower(`messageCallback`),
+ FfiConverterByteArray.lower(`envelopeBytes`),
)
},
{ future, callback, continuation ->
@@ -3999,482 +4502,260 @@ open class FfiGroup : Disposable, AutoCloseable, FfiGroupInterface {
},
{ future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
// lift function
- { FfiConverterTypeFfiStreamCloser.lift(it) },
+ { FfiConverterTypeFfiConversation.lift(it) },
// Error FFI converter
- UniffiNullRustCallStatusErrorHandler,
- )
- }
-
-
- @Throws(GenericException::class)
- override fun `superAdminList`(): List {
- return FfiConverterSequenceString.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_super_admin_list(
- it, _status
- )
- }
- }
+ GenericException.ErrorHandler,
)
}
- @Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `sync`() {
+ override suspend fun `stream`(`callback`: FfiConversationCallback): FfiStreamCloser {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_sync(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_stream(
thisPtr,
-
- )
+ FfiConverterTypeFfiConversationCallback.lower(`callback`),
+ )
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
// lift function
- { Unit },
-
+ { FfiConverterTypeFfiStreamCloser.lift(it) },
// Error FFI converter
- GenericException.ErrorHandler,
+ UniffiNullRustCallStatusErrorHandler,
)
}
- @Throws(GenericException::class)
- override fun `updateConsentState`(`state`: FfiConsentState) =
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_update_consent_state(
- it, FfiConverterTypeFfiConsentState.lower(`state`), _status
- )
- }
- }
-
-
- @Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `updateGroupDescription`(`groupDescription`: kotlin.String) {
+ override suspend fun `streamAllDmMessages`(`messageCallback`: FfiMessageCallback): FfiStreamCloser {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_update_group_description(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_stream_all_dm_messages(
thisPtr,
- FfiConverterString.lower(`groupDescription`),
+ FfiConverterTypeFfiMessageCallback.lower(`messageCallback`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
// lift function
- { Unit },
-
+ { FfiConverterTypeFfiStreamCloser.lift(it) },
// Error FFI converter
- GenericException.ErrorHandler,
+ UniffiNullRustCallStatusErrorHandler,
)
}
- @Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `updateGroupImageUrlSquare`(`groupImageUrlSquare`: kotlin.String) {
+ override suspend fun `streamAllGroupMessages`(`messageCallback`: FfiMessageCallback): FfiStreamCloser {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_update_group_image_url_square(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_stream_all_group_messages(
thisPtr,
- FfiConverterString.lower(`groupImageUrlSquare`),
+ FfiConverterTypeFfiMessageCallback.lower(`messageCallback`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
// lift function
- { Unit },
-
+ { FfiConverterTypeFfiStreamCloser.lift(it) },
// Error FFI converter
- GenericException.ErrorHandler,
+ UniffiNullRustCallStatusErrorHandler,
)
}
- @Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `updateGroupName`(`groupName`: kotlin.String) {
+ override suspend fun `streamAllMessages`(`messageCallback`: FfiMessageCallback): FfiStreamCloser {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_update_group_name(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_stream_all_messages(
thisPtr,
- FfiConverterString.lower(`groupName`),
+ FfiConverterTypeFfiMessageCallback.lower(`messageCallback`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
// lift function
- { Unit },
-
+ { FfiConverterTypeFfiStreamCloser.lift(it) },
// Error FFI converter
- GenericException.ErrorHandler,
+ UniffiNullRustCallStatusErrorHandler,
)
}
- @Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `updateGroupPinnedFrameUrl`(`pinnedFrameUrl`: kotlin.String) {
+ override suspend fun `streamDms`(`callback`: FfiConversationCallback): FfiStreamCloser {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_update_group_pinned_frame_url(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_stream_dms(
thisPtr,
- FfiConverterString.lower(`pinnedFrameUrl`),
+ FfiConverterTypeFfiConversationCallback.lower(`callback`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
// lift function
- { Unit },
-
+ { FfiConverterTypeFfiStreamCloser.lift(it) },
// Error FFI converter
- GenericException.ErrorHandler,
+ UniffiNullRustCallStatusErrorHandler,
)
}
- @Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
- override suspend fun `updatePermissionPolicy`(
- `permissionUpdateType`: FfiPermissionUpdateType,
- `permissionPolicyOption`: FfiPermissionPolicy,
- `metadataField`: FfiMetadataField?,
- ) {
+ override suspend fun `streamGroups`(`callback`: FfiConversationCallback): FfiStreamCloser {
return uniffiRustCallAsync(
callWithPointer { thisPtr ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroup_update_permission_policy(
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_stream_groups(
thisPtr,
- FfiConverterTypeFfiPermissionUpdateType.lower(`permissionUpdateType`),
- FfiConverterTypeFfiPermissionPolicy.lower(`permissionPolicyOption`),
- FfiConverterOptionalTypeFfiMetadataField.lower(`metadataField`),
+ FfiConverterTypeFfiConversationCallback.lower(`callback`),
)
},
{ future, callback, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_pointer(
future,
callback,
continuation
)
},
{ future, continuation ->
- UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_pointer(
future,
continuation
)
},
- { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_pointer(future) },
// lift function
- { Unit },
-
+ { FfiConverterTypeFfiStreamCloser.lift(it) },
// Error FFI converter
- GenericException.ErrorHandler,
- )
- }
-
-
- companion object
-
-}
-
-public object FfiConverterTypeFfiGroup : FfiConverter {
-
- override fun lower(value: FfiGroup): Pointer {
- return value.uniffiClonePointer()
- }
-
- override fun lift(value: Pointer): FfiGroup {
- return FfiGroup(value)
- }
-
- override fun read(buf: ByteBuffer): FfiGroup {
- // The Rust code always writes pointers as 8 bytes, and will
- // fail to compile if they don't fit.
- return lift(Pointer(buf.getLong()))
- }
-
- override fun allocationSize(value: FfiGroup) = 8UL
-
- override fun write(value: FfiGroup, buf: ByteBuffer) {
- // The Rust code always expects pointers written as 8 bytes,
- // and will fail to compile if they don't fit.
- buf.putLong(Pointer.nativeValue(lower(value)))
- }
-}
-
-
-// This template implements a class for working with a Rust struct via a Pointer/Arc
-// to the live Rust struct on the other side of the FFI.
-//
-// Each instance implements core operations for working with the Rust `Arc` and the
-// Kotlin Pointer to work with the live Rust struct on the other side of the FFI.
-//
-// There's some subtlety here, because we have to be careful not to operate on a Rust
-// struct after it has been dropped, and because we must expose a public API for freeing
-// theq Kotlin wrapper object in lieu of reliable finalizers. The core requirements are:
-//
-// * Each instance holds an opaque pointer to the underlying Rust struct.
-// Method calls need to read this pointer from the object's state and pass it in to
-// the Rust FFI.
-//
-// * When an instance is no longer needed, its pointer should be passed to a
-// special destructor function provided by the Rust FFI, which will drop the
-// underlying Rust struct.
-//
-// * Given an instance, calling code is expected to call the special
-// `destroy` method in order to free it after use, either by calling it explicitly
-// or by using a higher-level helper like the `use` method. Failing to do so risks
-// leaking the underlying Rust struct.
-//
-// * We can't assume that calling code will do the right thing, and must be prepared
-// to handle Kotlin method calls executing concurrently with or even after a call to
-// `destroy`, and to handle multiple (possibly concurrent!) calls to `destroy`.
-//
-// * We must never allow Rust code to operate on the underlying Rust struct after
-// the destructor has been called, and must never call the destructor more than once.
-// Doing so may trigger memory unsafety.
-//
-// * To mitigate many of the risks of leaking memory and use-after-free unsafety, a `Cleaner`
-// is implemented to call the destructor when the Kotlin object becomes unreachable.
-// This is done in a background thread. This is not a panacea, and client code should be aware that
-// 1. the thread may starve if some there are objects that have poorly performing
-// `drop` methods or do significant work in their `drop` methods.
-// 2. the thread is shared across the whole library. This can be tuned by using `android_cleaner = true`,
-// or `android = true` in the [`kotlin` section of the `uniffi.toml` file](https://mozilla.github.io/uniffi-rs/kotlin/configuration.html).
-//
-// If we try to implement this with mutual exclusion on access to the pointer, there is the
-// possibility of a race between a method call and a concurrent call to `destroy`:
-//
-// * Thread A starts a method call, reads the value of the pointer, but is interrupted
-// before it can pass the pointer over the FFI to Rust.
-// * Thread B calls `destroy` and frees the underlying Rust struct.
-// * Thread A resumes, passing the already-read pointer value to Rust and triggering
-// a use-after-free.
-//
-// One possible solution would be to use a `ReadWriteLock`, with each method call taking
-// a read lock (and thus allowed to run concurrently) and the special `destroy` method
-// taking a write lock (and thus blocking on live method calls). However, we aim not to
-// generate methods with any hidden blocking semantics, and a `destroy` method that might
-// block if called incorrectly seems to meet that bar.
-//
-// So, we achieve our goals by giving each instance an associated `AtomicLong` counter to track
-// the number of in-flight method calls, and an `AtomicBoolean` flag to indicate whether `destroy`
-// has been called. These are updated according to the following rules:
-//
-// * The initial value of the counter is 1, indicating a live object with no in-flight calls.
-// The initial value for the flag is false.
-//
-// * At the start of each method call, we atomically check the counter.
-// If it is 0 then the underlying Rust struct has already been destroyed and the call is aborted.
-// If it is nonzero them we atomically increment it by 1 and proceed with the method call.
-//
-// * At the end of each method call, we atomically decrement and check the counter.
-// If it has reached zero then we destroy the underlying Rust struct.
-//
-// * When `destroy` is called, we atomically flip the flag from false to true.
-// If the flag was already true we silently fail.
-// Otherwise we atomically decrement and check the counter.
-// If it has reached zero then we destroy the underlying Rust struct.
-//
-// Astute readers may observe that this all sounds very similar to the way that Rust's `Arc` works,
-// and indeed it is, with the addition of a flag to guard against multiple calls to `destroy`.
-//
-// The overall effect is that the underlying Rust struct is destroyed only when `destroy` has been
-// called *and* all in-flight method calls have completed, avoiding violating any of the expectations
-// of the underlying Rust code.
-//
-// This makes a cleaner a better alternative to _not_ calling `destroy()` as
-// and when the object is finished with, but the abstraction is not perfect: if the Rust object's `drop`
-// method is slow, and/or there are many objects to cleanup, and it's on a low end Android device, then the cleaner
-// thread may be starved, and the app will leak memory.
-//
-// In this case, `destroy`ing manually may be a better solution.
-//
-// The cleaner can live side by side with the manual calling of `destroy`. In the order of responsiveness, uniffi objects
-// with Rust peers are reclaimed:
-//
-// 1. By calling the `destroy` method of the object, which calls `rustObject.free()`. If that doesn't happen:
-// 2. When the object becomes unreachable, AND the Cleaner thread gets to call `rustObject.free()`. If the thread is starved then:
-// 3. The memory is reclaimed when the process terminates.
-//
-// [1] https://stackoverflow.com/questions/24376768/can-java-finalize-an-object-when-it-is-still-in-scope/24380219
-//
-
-
-public interface FfiGroupMetadataInterface {
-
- fun `conversationType`(): kotlin.String
-
- fun `creatorInboxId`(): kotlin.String
-
- companion object
-}
-
-open class FfiGroupMetadata : Disposable, AutoCloseable, FfiGroupMetadataInterface {
-
- constructor(pointer: Pointer) {
- this.pointer = pointer
- this.cleanable = UniffiLib.CLEANER.register(this, UniffiCleanAction(pointer))
- }
-
- /**
- * This constructor can be used to instantiate a fake object. Only used for tests. Any
- * attempt to actually use an object constructed this way will fail as there is no
- * connected Rust object.
- */
- @Suppress("UNUSED_PARAMETER")
- constructor(noPointer: NoPointer) {
- this.pointer = null
- this.cleanable = UniffiLib.CLEANER.register(this, UniffiCleanAction(pointer))
- }
-
- protected val pointer: Pointer?
- protected val cleanable: UniffiCleaner.Cleanable
-
- private val wasDestroyed = AtomicBoolean(false)
- private val callCounter = AtomicLong(1)
-
- override fun destroy() {
- // Only allow a single call to this method.
- // TODO: maybe we should log a warning if called more than once?
- if (this.wasDestroyed.compareAndSet(false, true)) {
- // This decrement always matches the initial count of 1 given at creation time.
- if (this.callCounter.decrementAndGet() == 0L) {
- cleanable.clean()
- }
- }
- }
-
- @Synchronized
- override fun close() {
- this.destroy()
- }
-
- internal inline fun callWithPointer(block: (ptr: Pointer) -> R): R {
- // Check and increment the call counter, to keep the object alive.
- // This needs a compare-and-set retry loop in case of concurrent updates.
- do {
- val c = this.callCounter.get()
- if (c == 0L) {
- throw IllegalStateException("${this.javaClass.simpleName} object has already been destroyed")
- }
- if (c == Long.MAX_VALUE) {
- throw IllegalStateException("${this.javaClass.simpleName} call counter would overflow")
- }
- } while (!this.callCounter.compareAndSet(c, c + 1L))
- // Now we can safely do the method call without the pointer being freed concurrently.
- try {
- return block(this.uniffiClonePointer())
- } finally {
- // This decrement always matches the increment we performed above.
- if (this.callCounter.decrementAndGet() == 0L) {
- cleanable.clean()
- }
- }
- }
-
- // Use a static inner class instead of a closure so as not to accidentally
- // capture `this` as part of the cleanable's action.
- private class UniffiCleanAction(private val pointer: Pointer?) : Runnable {
- override fun run() {
- pointer?.let { ptr ->
- uniffiRustCall { status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_free_ffigroupmetadata(ptr, status)
- }
- }
- }
- }
-
- fun uniffiClonePointer(): Pointer {
- return uniffiRustCall() { status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_clone_ffigroupmetadata(pointer!!, status)
- }
+ UniffiNullRustCallStatusErrorHandler,
+ )
}
- override fun `conversationType`(): kotlin.String {
- return FfiConverterString.lift(
- callWithPointer {
- uniffiRustCall() { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroupmetadata_conversation_type(
- it, _status
+
+ @Throws(GenericException::class)
+ @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
+ override suspend fun `sync`() {
+ return uniffiRustCallAsync(
+ callWithPointer { thisPtr ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_sync(
+ thisPtr,
+
)
- }
- }
+ },
+ { future, callback, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_void(
+ future,
+ callback,
+ continuation
+ )
+ },
+ { future, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_void(
+ future,
+ continuation
+ )
+ },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_void(future) },
+ // lift function
+ { Unit },
+
+ // Error FFI converter
+ GenericException.ErrorHandler,
)
}
- override fun `creatorInboxId`(): kotlin.String {
- return FfiConverterString.lift(
- callWithPointer {
- uniffiRustCall() { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffigroupmetadata_creator_inbox_id(
- it, _status
+ @Throws(GenericException::class)
+ @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
+ override suspend fun `syncAllConversations`(): kotlin.UInt {
+ return uniffiRustCallAsync(
+ callWithPointer { thisPtr ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_fficonversations_sync_all_conversations(
+ thisPtr,
+
)
- }
- }
+ },
+ { future, callback, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_u32(
+ future,
+ callback,
+ continuation
+ )
+ },
+ { future, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_u32(
+ future,
+ continuation
+ )
+ },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_u32(future) },
+ // lift function
+ { FfiConverterUInt.lift(it) },
+ // Error FFI converter
+ GenericException.ErrorHandler,
)
}
@@ -4483,25 +4764,25 @@ open class FfiGroupMetadata : Disposable, AutoCloseable, FfiGroupMetadataInterfa
}
-public object FfiConverterTypeFfiGroupMetadata : FfiConverter {
+public object FfiConverterTypeFfiConversations : FfiConverter {
- override fun lower(value: FfiGroupMetadata): Pointer {
+ override fun lower(value: FfiConversations): Pointer {
return value.uniffiClonePointer()
}
- override fun lift(value: Pointer): FfiGroupMetadata {
- return FfiGroupMetadata(value)
+ override fun lift(value: Pointer): FfiConversations {
+ return FfiConversations(value)
}
- override fun read(buf: ByteBuffer): FfiGroupMetadata {
+ override fun read(buf: ByteBuffer): FfiConversations {
// The Rust code always writes pointers as 8 bytes, and will
// fail to compile if they don't fit.
return lift(Pointer(buf.getLong()))
}
- override fun allocationSize(value: FfiGroupMetadata) = 8UL
+ override fun allocationSize(value: FfiConversations) = 8UL
- override fun write(value: FfiGroupMetadata, buf: ByteBuffer) {
+ override fun write(value: FfiConversations, buf: ByteBuffer) {
// The Rust code always expects pointers written as 8 bytes,
// and will fail to compile if they don't fit.
buf.putLong(Pointer.nativeValue(lower(value)))
@@ -6258,14 +6539,29 @@ public interface FfiXmtpClientInterface {
`newWalletAddress`: kotlin.String,
): FfiSignatureRequest
+ /**
+ * * Get the inbox state for each `inbox_id`.
+ * *
+ * * If `refresh_from_network` is true, the client will go to the network first to refresh the state.
+ * * Otherwise, the state will be read from the local database.
+ */
+ suspend fun `addressesFromInboxId`(
+ `refreshFromNetwork`: kotlin.Boolean,
+ `inboxIds`: List,
+ ): List
+
suspend fun `applySignatureRequest`(`signatureRequest`: FfiSignatureRequest)
suspend fun `canMessage`(`accountAddresses`: List): Map
+ fun `conversation`(`conversationId`: kotlin.ByteArray): FfiConversation
+
fun `conversations`(): FfiConversations
suspend fun `dbReconnect`()
+ fun `dmConversation`(`targetInboxId`: kotlin.String): FfiConversation
+
suspend fun `findInboxId`(`address`: kotlin.String): kotlin.String?
suspend fun `getConsentState`(
@@ -6275,8 +6571,6 @@ public interface FfiXmtpClientInterface {
suspend fun `getLatestInboxState`(`inboxId`: kotlin.String): FfiInboxState
- fun `group`(`groupId`: kotlin.ByteArray): FfiGroup
-
fun `inboxId`(): kotlin.String
/**
@@ -6435,6 +6729,48 @@ open class FfiXmtpClient : Disposable, AutoCloseable, FfiXmtpClientInterface {
}
+ /**
+ * * Get the inbox state for each `inbox_id`.
+ * *
+ * * If `refresh_from_network` is true, the client will go to the network first to refresh the state.
+ * * Otherwise, the state will be read from the local database.
+ */
+ @Throws(GenericException::class)
+ @Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
+ override suspend fun `addressesFromInboxId`(
+ `refreshFromNetwork`: kotlin.Boolean,
+ `inboxIds`: List,
+ ): List {
+ return uniffiRustCallAsync(
+ callWithPointer { thisPtr ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffixmtpclient_addresses_from_inbox_id(
+ thisPtr,
+ FfiConverterBoolean.lower(`refreshFromNetwork`),
+ FfiConverterSequenceString.lower(`inboxIds`),
+ )
+ },
+ { future, callback, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_poll_rust_buffer(
+ future,
+ callback,
+ continuation
+ )
+ },
+ { future, continuation ->
+ UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_complete_rust_buffer(
+ future,
+ continuation
+ )
+ },
+ { future -> UniffiLib.INSTANCE.ffi_xmtpv3_rust_future_free_rust_buffer(future) },
+ // lift function
+ { FfiConverterSequenceTypeFfiInboxState.lift(it) },
+ // Error FFI converter
+ GenericException.ErrorHandler,
+ )
+ }
+
+
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
override suspend fun `applySignatureRequest`(`signatureRequest`: FfiSignatureRequest) {
@@ -6499,6 +6835,21 @@ open class FfiXmtpClient : Disposable, AutoCloseable, FfiXmtpClientInterface {
)
}
+
+ @Throws(GenericException::class)
+ override fun `conversation`(`conversationId`: kotlin.ByteArray): FfiConversation {
+ return FfiConverterTypeFfiConversation.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffixmtpclient_conversation(
+ it, FfiConverterByteArray.lower(`conversationId`), _status
+ )
+ }
+ }
+ )
+ }
+
+
override fun `conversations`(): FfiConversations {
return FfiConverterTypeFfiConversations.lift(
callWithPointer {
@@ -6545,6 +6896,20 @@ open class FfiXmtpClient : Disposable, AutoCloseable, FfiXmtpClientInterface {
}
+ @Throws(GenericException::class)
+ override fun `dmConversation`(`targetInboxId`: kotlin.String): FfiConversation {
+ return FfiConverterTypeFfiConversation.lift(
+ callWithPointer {
+ uniffiRustCallWithError(GenericException) { _status ->
+ UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffixmtpclient_dm_conversation(
+ it, FfiConverterString.lower(`targetInboxId`), _status
+ )
+ }
+ }
+ )
+ }
+
+
@Throws(GenericException::class)
@Suppress("ASSIGNED_BUT_NEVER_ACCESSED_VARIABLE")
override suspend fun `findInboxId`(`address`: kotlin.String): kotlin.String? {
@@ -6644,21 +7009,6 @@ open class FfiXmtpClient : Disposable, AutoCloseable, FfiXmtpClientInterface {
)
}
-
- @Throws(GenericException::class)
- override fun `group`(`groupId`: kotlin.ByteArray): FfiGroup {
- return FfiConverterTypeFfiGroup.lift(
- callWithPointer {
- uniffiRustCallWithError(GenericException) { _status ->
- UniffiLib.INSTANCE.uniffi_xmtpv3_fn_method_ffixmtpclient_group(
- it, FfiConverterByteArray.lower(`groupId`), _status
- )
- }
- }
- )
- }
-
-
override fun `inboxId`(): kotlin.String {
return FfiConverterString.lift(
callWithPointer {
@@ -6990,6 +7340,47 @@ public object FfiConverterTypeFfiConsent : FfiConverterRustBuffer {
}
+data class FfiConversationMember(
+ var `inboxId`: kotlin.String,
+ var `accountAddresses`: List,
+ var `installationIds`: List,
+ var `permissionLevel`: FfiPermissionLevel,
+ var `consentState`: FfiConsentState,
+) {
+
+ companion object
+}
+
+public object FfiConverterTypeFfiConversationMember :
+ FfiConverterRustBuffer {
+ override fun read(buf: ByteBuffer): FfiConversationMember {
+ return FfiConversationMember(
+ FfiConverterString.read(buf),
+ FfiConverterSequenceString.read(buf),
+ FfiConverterSequenceByteArray.read(buf),
+ FfiConverterTypeFfiPermissionLevel.read(buf),
+ FfiConverterTypeFfiConsentState.read(buf),
+ )
+ }
+
+ override fun allocationSize(value: FfiConversationMember) = (
+ FfiConverterString.allocationSize(value.`inboxId`) +
+ FfiConverterSequenceString.allocationSize(value.`accountAddresses`) +
+ FfiConverterSequenceByteArray.allocationSize(value.`installationIds`) +
+ FfiConverterTypeFfiPermissionLevel.allocationSize(value.`permissionLevel`) +
+ FfiConverterTypeFfiConsentState.allocationSize(value.`consentState`)
+ )
+
+ override fun write(value: FfiConversationMember, buf: ByteBuffer) {
+ FfiConverterString.write(value.`inboxId`, buf)
+ FfiConverterSequenceString.write(value.`accountAddresses`, buf)
+ FfiConverterSequenceByteArray.write(value.`installationIds`, buf)
+ FfiConverterTypeFfiPermissionLevel.write(value.`permissionLevel`, buf)
+ FfiConverterTypeFfiConsentState.write(value.`consentState`, buf)
+ }
+}
+
+
data class FfiCreateGroupOptions(
var `permissions`: FfiGroupPermissionsOptions?,
var `groupName`: kotlin.String?,
@@ -7095,46 +7486,6 @@ public object FfiConverterTypeFfiEnvelope : FfiConverterRustBuffer
}
-data class FfiGroupMember(
- var `inboxId`: kotlin.String,
- var `accountAddresses`: List,
- var `installationIds`: List,
- var `permissionLevel`: FfiPermissionLevel,
- var `consentState`: FfiConsentState,
-) {
-
- companion object
-}
-
-public object FfiConverterTypeFfiGroupMember : FfiConverterRustBuffer {
- override fun read(buf: ByteBuffer): FfiGroupMember {
- return FfiGroupMember(
- FfiConverterString.read(buf),
- FfiConverterSequenceString.read(buf),
- FfiConverterSequenceByteArray.read(buf),
- FfiConverterTypeFfiPermissionLevel.read(buf),
- FfiConverterTypeFfiConsentState.read(buf),
- )
- }
-
- override fun allocationSize(value: FfiGroupMember) = (
- FfiConverterString.allocationSize(value.`inboxId`) +
- FfiConverterSequenceString.allocationSize(value.`accountAddresses`) +
- FfiConverterSequenceByteArray.allocationSize(value.`installationIds`) +
- FfiConverterTypeFfiPermissionLevel.allocationSize(value.`permissionLevel`) +
- FfiConverterTypeFfiConsentState.allocationSize(value.`consentState`)
- )
-
- override fun write(value: FfiGroupMember, buf: ByteBuffer) {
- FfiConverterString.write(value.`inboxId`, buf)
- FfiConverterSequenceString.write(value.`accountAddresses`, buf)
- FfiConverterSequenceByteArray.write(value.`installationIds`, buf)
- FfiConverterTypeFfiPermissionLevel.write(value.`permissionLevel`, buf)
- FfiConverterTypeFfiConsentState.write(value.`consentState`, buf)
- }
-}
-
-
data class FfiInboxState(
var `inboxId`: kotlin.String,
var `recoveryAddress`: kotlin.String,
@@ -7275,7 +7626,7 @@ data class FfiMessage(
var `convoId`: kotlin.ByteArray,
var `senderInboxId`: kotlin.String,
var `content`: kotlin.ByteArray,
- var `kind`: FfiGroupMessageKind,
+ var `kind`: FfiConversationMessageKind,
var `deliveryStatus`: FfiDeliveryStatus,
) {
@@ -7290,7 +7641,7 @@ public object FfiConverterTypeFfiMessage : FfiConverterRustBuffer {
FfiConverterByteArray.read(buf),
FfiConverterString.read(buf),
FfiConverterByteArray.read(buf),
- FfiConverterTypeFfiGroupMessageKind.read(buf),
+ FfiConverterTypeFfiConversationMessageKind.read(buf),
FfiConverterTypeFfiDeliveryStatus.read(buf),
)
}
@@ -7301,7 +7652,7 @@ public object FfiConverterTypeFfiMessage : FfiConverterRustBuffer {
FfiConverterByteArray.allocationSize(value.`convoId`) +
FfiConverterString.allocationSize(value.`senderInboxId`) +
FfiConverterByteArray.allocationSize(value.`content`) +
- FfiConverterTypeFfiGroupMessageKind.allocationSize(value.`kind`) +
+ FfiConverterTypeFfiConversationMessageKind.allocationSize(value.`kind`) +
FfiConverterTypeFfiDeliveryStatus.allocationSize(value.`deliveryStatus`)
)
@@ -7311,7 +7662,7 @@ public object FfiConverterTypeFfiMessage : FfiConverterRustBuffer {
FfiConverterByteArray.write(value.`convoId`, buf)
FfiConverterString.write(value.`senderInboxId`, buf)
FfiConverterByteArray.write(value.`content`, buf)
- FfiConverterTypeFfiGroupMessageKind.write(value.`kind`, buf)
+ FfiConverterTypeFfiConversationMessageKind.write(value.`kind`, buf)
FfiConverterTypeFfiDeliveryStatus.write(value.`deliveryStatus`, buf)
}
}
@@ -7567,7 +7918,7 @@ public object FfiConverterTypeFfiV2SubscribeRequest :
enum class FfiConsentEntityType {
- GROUP_ID,
+ CONVERSATION_ID,
INBOX_ID,
ADDRESS;
@@ -7615,50 +7966,51 @@ public object FfiConverterTypeFfiConsentState : FfiConverterRustBuffer {
+public object FfiConverterTypeFfiConversationMessageKind :
+ FfiConverterRustBuffer {
override fun read(buf: ByteBuffer) = try {
- FfiDeliveryStatus.values()[buf.getInt() - 1]
+ FfiConversationMessageKind.values()[buf.getInt() - 1]
} catch (e: IndexOutOfBoundsException) {
throw RuntimeException("invalid enum value, something is very wrong!!", e)
}
- override fun allocationSize(value: FfiDeliveryStatus) = 4UL
+ override fun allocationSize(value: FfiConversationMessageKind) = 4UL
- override fun write(value: FfiDeliveryStatus, buf: ByteBuffer) {
+ override fun write(value: FfiConversationMessageKind, buf: ByteBuffer) {
buf.putInt(value.ordinal + 1)
}
}
-enum class FfiGroupMessageKind {
+enum class FfiDeliveryStatus {
- APPLICATION,
- MEMBERSHIP_CHANGE;
+ UNPUBLISHED,
+ PUBLISHED,
+ FAILED;
companion object
}
-public object FfiConverterTypeFfiGroupMessageKind : FfiConverterRustBuffer {
+public object FfiConverterTypeFfiDeliveryStatus : FfiConverterRustBuffer {
override fun read(buf: ByteBuffer) = try {
- FfiGroupMessageKind.values()[buf.getInt() - 1]
+ FfiDeliveryStatus.values()[buf.getInt() - 1]
} catch (e: IndexOutOfBoundsException) {
throw RuntimeException("invalid enum value, something is very wrong!!", e)
}
- override fun allocationSize(value: FfiGroupMessageKind) = 4UL
+ override fun allocationSize(value: FfiDeliveryStatus) = 4UL
- override fun write(value: FfiGroupMessageKind, buf: ByteBuffer) {
+ override fun write(value: FfiDeliveryStatus, buf: ByteBuffer) {
buf.putInt(value.ordinal + 1)
}
}
@@ -7986,7 +8338,7 @@ public object FfiConverterTypeSigningError : FfiConverterRustBuffer
uniffiObj.`onConversation`(
- FfiConverterTypeFfiGroup.lift(`conversation`),
+ FfiConverterTypeFfiConversation.lift(`conversation`),
)
}
val writeReturn = { _: Unit -> Unit }
@@ -8648,24 +9000,25 @@ public object FfiConverterSequenceByteArray : FfiConverterRustBuffer