diff --git a/docs/01-getting-started/02-quick-start-guide.md b/docs/01-getting-started/02-quick-start-guide.md index 079460d..523d472 100644 --- a/docs/01-getting-started/02-quick-start-guide.md +++ b/docs/01-getting-started/02-quick-start-guide.md @@ -123,11 +123,6 @@ Once this association (or "link") is established, you can: ### Implementation A native wallet linking flow is currently in development. Once it ships, this section will document the end-to-end implementation. In the meantime, you can have users share their wallet address directly (for example, by pasting it into a form) and use that address in the steps below. - -:::info Reference -The [Sending Wallet Requests](/02-guides/01-platform/02-managing-users/01-connecting-user-wallets/01-sending-wallet-requests.md) page will become the full in-depth guide once the flow ships. -::: - ## 5. Send a Token to a User ### Why Send Tokens? diff --git a/docs/02-guides/01-platform/01-managing-tokens/01-creating-collections.md b/docs/02-guides/01-platform/01-managing-tokens/01-creating-collections.md index e7e6774..6cf81e2 100644 --- a/docs/02-guides/01-platform/01-managing-tokens/01-creating-collections.md +++ b/docs/02-guides/01-platform/01-managing-tokens/01-creating-collections.md @@ -50,8 +50,8 @@ Once you've created a collection you're ready to start [creating tokens](/02-gui Every on-chain action goes through the single `CreateTransaction` mutation. The action itself is selected by which field you set on the `transaction` input — for collections, that's `createCollection`. -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: @@ -84,32 +84,30 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Setup the mutation -var createCollection = new CreateCollection() - .SetMintPolicy(new MintPolicy().SetForceCollapsingSupply(false)); //Set to true to enforce collapsing supply mint policy - -// Define and assign the return data fragment to the mutation -var transactionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -createCollection.Fragment(transactionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendCreateCollection(createCollection); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation, selecting createCollection as the action +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + CreateCollection = new CreateCollectionInput + { + ForceCollapsingSupply = false, // set to true to enforce collapsing supply + }, + }); + +// Send the mutation; poll GetTransaction by uuid to track its on-chain state +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/01-managing-tokens/010-transfer-accept-collection.md b/docs/02-guides/01-platform/01-managing-tokens/010-transfer-accept-collection.md index d6d6e18..827f15e 100644 --- a/docs/02-guides/01-platform/01-managing-tokens/010-transfer-accept-collection.md +++ b/docs/02-guides/01-platform/01-managing-tokens/010-transfer-accept-collection.md @@ -17,8 +17,8 @@ The collection owner is the only account authorized to make changes to the colle Transferring collection ownership is a two-step process: the current owner submits a transfer request, and the new owner accepts it. -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: ## Step #1: Sending a transfer ownership request with the [Enjin API](/01-getting-started/05-using-enjin-api/05-using-enjin-api.md) @@ -56,37 +56,32 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Set up the collection mutation input. -var collectionMutationInput = new CollectionMutationInput() - .SetOwner("cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f"); // Set the new owner account of the collection. - -// Set up the mutation -var mutateCollection = new MutateCollection() - .SetCollectionId(36105) // Specify the collection ID. - .SetMutation(collectionMutationInput); // Specify the mutation input. - -// Define and assign the return data fragment to the mutation -var transactionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -mutateCollection.Fragment(transactionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendMutateCollection(mutateCollection); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (one action set on TransactionInput) +// Initiating a collection-ownership transfer is done via the mutateCollection +// action by setting the new owner's address on the Owner field. +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + MutateCollection = new MutateCollectionInput + { + CollectionId = 36105, + Owner = "cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f", // the new owner + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` @@ -253,32 +248,29 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Set up the mutation -var acceptCollectionTransfer = new AcceptCollectionTransfer() - .SetCollectionId(36105); // Specify the collection ID. - -// Define and assign the return data fragment to the mutation -var transactionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -acceptCollectionTransfer.Fragment(transactionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendAcceptCollectionTransfer(acceptCollectionTransfer); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (one action set on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + AcceptCollectionTransfer = new AcceptCollectionTransferInput + { + Id = 36105, // the collection id + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/01-managing-tokens/02-creating-tokens/02-creating-a-currency-token.md b/docs/02-guides/01-platform/01-managing-tokens/02-creating-tokens/02-creating-a-currency-token.md index 66aef4b..9742275 100644 --- a/docs/02-guides/01-platform/01-managing-tokens/02-creating-tokens/02-creating-a-currency-token.md +++ b/docs/02-guides/01-platform/01-managing-tokens/02-creating-tokens/02-creating-a-currency-token.md @@ -68,8 +68,8 @@ Once your token is created, lets give it a new look by [Adding Metadata](/02-gui To create a currency token, use the standard `createToken` action with the `behavior` field set to `{ type: IS_CURRENCY, name, symbol, decimalCount }`. The rest of the input (recipient, collectionId, tokenId, initialSupply, etc.) follows the same shape as a regular [token create](/02-guides/01-platform/01-managing-tokens/02-creating-tokens/02-creating-tokens.md#option-b-using-the-enjin-api--sdks). -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: @@ -114,47 +114,43 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Define the token metadata input -var tokenMetadata = new TokenMetadataInput() - .SetName("Token Name") // Set the token name - .SetSymbol("TKN") // Set the token symbol - .SetDecimalCount(18); // Set the decimal count - -// Define the token parameters -var tokenParams = new CreateTokenParams() - .SetTokenId(new EncodableTokenIdInput().SetInteger(1)) //Set the token ID - .SetInitialSupply(1) //Mint initial supply - .SetCap(new TokenMintCap().SetType(TokenMintCapType.Infinite)) //Define supply type - .SetMetadata(tokenMetadata); //Set the token metadata - -// Set up the mutation -var createToken = new CreateToken() - .SetRecipient("cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f") //The recipient of the initial supply - .SetCollectionId(2406) //Set the collection ID - .SetParams(tokenParams); //Set the previously defined token params - -// Define and assign the return data fragment to the mutation -var createTokenFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -createToken.Fragment(createTokenFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendCreateToken(createToken); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation, selecting createToken as the action +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + CreateToken = new CreateTokenInput + { + Recipient = "cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f", // recipient of the initial supply + CollectionId = 2406, // collection to mint into + TokenId = 1, // the new token ID + InitialSupply = 1, // initial supply to mint + ListingForbidden = false, + Infusion = 0, + AnyoneCanInfuse = false, + Behavior = new TokenBehaviorInput // makes this token a currency + { + Type = TokenBehaviorType.IsCurrency, + Name = "Gold Coins", + Symbol = "GOLD", + DecimalCount = 2, + }, + }, + }); + +// Send the mutation; poll GetTransaction by uuid to track its on-chain state +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/01-managing-tokens/02-creating-tokens/02-creating-tokens.md b/docs/02-guides/01-platform/01-managing-tokens/02-creating-tokens/02-creating-tokens.md index fb67413..20a8a4a 100644 --- a/docs/02-guides/01-platform/01-managing-tokens/02-creating-tokens/02-creating-tokens.md +++ b/docs/02-guides/01-platform/01-managing-tokens/02-creating-tokens/02-creating-tokens.md @@ -63,8 +63,8 @@ Once your token is created, lets give it a new look by [Adding Metadata](/02-gui All on-chain actions go through the single `CreateTransaction` mutation. For creating a token, set the `createToken` field on the `transaction` input. `tokenId` is a flat `BigInt` scalar, and `cap` is optional — omit it to create a token with unlimited supply. -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: @@ -105,40 +105,38 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Define the token parameters -var tokenParams = new CreateTokenParams() - .SetTokenId(new EncodableTokenIdInput().SetInteger(1)) //Set the token ID - .SetInitialSupply(1) //Mint initial supply - .SetCap(new TokenMintCap().SetType(TokenMintCapType.Infinite)); //Define supply type - -// Setup the mutation -var createToken = new CreateToken() - .SetRecipient("cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f") //The recipient of the initial supply - .SetCollectionId(2406) //Set the collection ID - .SetParams(tokenParams); //Set the previously defined token params - -// Define and assign the return data fragment to the mutation -var createTokenFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -createToken.Fragment(createTokenFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendCreateToken(createToken); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation, selecting createToken as the action +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + CreateToken = new CreateTokenInput + { + Recipient = "cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f", // recipient of the initial supply + CollectionId = 2406, // collection to mint into + TokenId = 1, // the new token ID + InitialSupply = 1, // initial supply to mint + ListingForbidden = false, // set true to disallow marketplace listings + Infusion = 0, // ENJ infused per unit (base units) + AnyoneCanInfuse = false, + // Cap omitted for unlimited supply. + // For a finite cap: Cap = new TokenCapInput { Type = TokenCapType.Supply, Supply = 100 } + }, + }); + +// Send the mutation; poll GetTransaction by uuid to track its on-chain state +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/01-managing-tokens/03-adding-metadata.md b/docs/02-guides/01-platform/01-managing-tokens/03-adding-metadata.md index 71bf234..253b910 100644 --- a/docs/02-guides/01-platform/01-managing-tokens/03-adding-metadata.md +++ b/docs/02-guides/01-platform/01-managing-tokens/03-adding-metadata.md @@ -101,8 +101,8 @@ Batched attributes are split into two discriminator actions on `CreateTransactio The example below sets three attributes on a token. To target the collection itself, swap `batchSetTokenAttribute` for `batchSetCollectionAttribute` and replace the `collectionId` / `tokenId` pair with a single `id` field equal to the collection ID. -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: @@ -144,48 +144,44 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; +using System.Collections.Generic; using Enjin.Platform.Sdk; -//Define attributes to set -var attributes = new List -{ - new AttributeInput() - .SetKey("name") //Provide an attribute name - .SetValue("Chronicles of the Celestium"), //Provide an attribute value - new AttributeInput() - .SetKey("description") //Provide an attribute name - .SetValue("An epic saga where players assume the roles of intrepid tradesmiths, shaping destinies with fire and will across the star-woven expanses of the multiverse."), //Provide an attribute value - new AttributeInput() - .SetKey("uri") //Provide an attribute name - .SetValue("https://yourhost/metadata.json") //Provide an attribute value -}; - -// Setup the mutation -var batchSetAttribute = new BatchSetAttribute() - .SetCollectionId(36105) //Specify the collection ID - .SetTokenId(new EncodableTokenIdInput().SetInteger(0)) //Specify the token ID. If you wish to add collection metadata, omit this line entirely. - .SetAttributes(attributes.ToArray()); //Set the previously defined attributes as an array - -// Define and assign the return data fragment to the mutation -var batchSetAttributeFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -batchSetAttribute.Fragment(batchSetAttributeFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendBatchSetAttribute(batchSetAttribute); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (one action set on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet — match the GraphQL tab + chain: Chain.Matrix, + transaction: new TransactionInput + { + // To target the collection itself, use BatchSetCollectionAttribute + // with an Id instead (omit TokenId). + BatchSetTokenAttribute = new BatchSetTokenAttributeInput + { + CollectionId = 36105, + TokenId = 0, + Attributes = new List + { + new AttributeInput { Key = "name", Value = "Chronicles of the Celestium" }, + new AttributeInput + { + Key = "description", + Value = "An epic saga where players assume the roles of intrepid tradesmiths, shaping destinies with fire and will across the star-woven expanses of the multiverse.", + }, + new AttributeInput { Key = "uri", Value = "https://yourhost/metadata.json" }, + }, + }, + }); + +// Send the mutation; poll GetTransaction by uuid to track its on-chain state +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/01-managing-tokens/04-minting-a-token.md b/docs/02-guides/01-platform/01-managing-tokens/04-minting-a-token.md index 3a53e28..cd7f049 100644 --- a/docs/02-guides/01-platform/01-managing-tokens/04-minting-a-token.md +++ b/docs/02-guides/01-platform/01-managing-tokens/04-minting-a-token.md @@ -46,8 +46,8 @@ Minting is split into two discriminator actions on `CreateTransaction`: The example below uses `mintTokens` so it scales naturally if you add more recipients to the array. -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: @@ -87,44 +87,41 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; +using System.Collections.Generic; using Enjin.Platform.Sdk; -// Define the list of recipients and their mint parameters -var recipients = new List -{ - new MintRecipient() - .SetAccount("0xaa89f9099742a928051c41eadba188ad4e863539ff96f16722ae7850271c2921") - .SetMintParams(new MintTokenParams() - .SetAmount(1) - .SetTokenId(new EncodableTokenIdInput().SetInteger(6533)) - ) -}; - -// Setup the mutation -var batchMint = new BatchMint() - .SetCollectionId(7154) - .SetRecipients(recipients.ToArray()); - -// Define and assign the return data fragment to the mutation -var batchMintFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -batchMint.Fragment(batchMintFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendBatchMint(batchMint); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (one action set on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet — match the GraphQL tab + chain: Chain.Matrix, + transaction: new TransactionInput + { + // mintTokens scales to multiple recipients — add more entries to the list + MintTokens = new MintTokensInput + { + CollectionId = 7154, + Tokens = new List + { + new MintTokenEntryInput + { + Recipient = "0xaa89f9099742a928051c41eadba188ad4e863539ff96f16722ae7850271c2921", + TokenId = 6533, + Amount = 1, + }, + }, + }, + }); + +// Send the mutation; poll GetTransaction by uuid to track its on-chain state +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/01-managing-tokens/05-transferring-tokens.md b/docs/02-guides/01-platform/01-managing-tokens/05-transferring-tokens.md index cc29e59..f51519c 100644 --- a/docs/02-guides/01-platform/01-managing-tokens/05-transferring-tokens.md +++ b/docs/02-guides/01-platform/01-managing-tokens/05-transferring-tokens.md @@ -53,8 +53,8 @@ Transfers are split into three discriminator actions on `CreateTransaction`: - `transferEnj` — transfer ENJ (or cENJ on Canary) between accounts. - `batchTransfer` — transfer multiple tokens from one collection to multiple recipients in a single transaction. -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: ### Transferring an asset @@ -94,40 +94,32 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Define the simple transfer parameters -var simpleTransferParams = new SimpleTransferParams() - .SetTokenId(new EncodableTokenIdInput().SetInteger(0)) - .SetAmount(1); - - -// Setup the mutation -var simpleTransferToken = new SimpleTransferToken() - .SetRecipient("cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f") - .SetCollectionId(36105) - .SetParams(simpleTransferParams); - -// Define and assign the return data fragment to the mutation -var simpleTransferTokenFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -simpleTransferToken.Fragment(simpleTransferTokenFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendSimpleTransferToken(simpleTransferToken); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (transferToken action on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + TransferToken = new TransferTokenInput + { + Recipient = "cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f", + CollectionId = 36105, + TokenId = 0, + Amount = 1, + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` @@ -358,33 +350,31 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; +using System.Numerics; using Enjin.Platform.Sdk; -// Set up the mutation -var transferKeepAlive = new TransferKeepAlive() - .SetRecipient("cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f") //The recipient of the initial supply - .SetAmount(5000000000000000000); //The amount of tokens to transfer - -// Define and assign the return data fragment to the mutation -var transferKeepAliveFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -transferKeepAlive.Fragment(transferKeepAliveFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendTransferKeepAlive(transferKeepAlive); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (transferEnj action on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + TransferEnj = new TransferEnjInput + { + Recipient = "cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f", + Amount = BigInteger.Parse("5000000000000000000"), // 5 ENJ in base units (5 * 10^18) + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` @@ -538,50 +528,46 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; +using System.Collections.Generic; +using System.Numerics; using Enjin.Platform.Sdk; -// Set up the transfers for the batch -var transferBalanceParams1 = new TransferBalanceParams() - .SetValue(5000000000000000000); //The amount of tokens to transfer +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); -var transferBalanceParams2 = new TransferBalanceParams() - .SetValue(5000000000000000000) //The amount of tokens to transfer - .SetKeepAlive(true); //Whether the transaction will be kept from failing if the balance drops below the minimum requirement - -var transferRecipients = new[] +// One TransactionInput per recipient, each with a transferEnj action +var transactions = new List { - new TransferRecipient() - .SetAccount("cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f") - .SetTransferBalanceParams(transferBalanceParams1), - new TransferRecipient() - .SetAccount("cxKy7aqhQTtoJYUjpebxFK2ooKhcvQ2FQj3FePrXhDhd9nLfu") - .SetTransferBalanceParams(transferBalanceParams2) + new TransactionInput + { + TransferEnj = new TransferEnjInput + { + Recipient = "cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f", + Amount = BigInteger.Parse("5000000000000000000"), // 5 ENJ + }, + }, + new TransactionInput + { + TransferEnj = new TransferEnjInput + { + Recipient = "cxKy7aqhQTtoJYUjpebxFK2ooKhcvQ2FQj3FePrXhDhd9nLfu", + Amount = BigInteger.Parse("15250000000000000000"), // 15.25 ENJ + }, + }, }; -// Set up the mutation -var batchTransferBalance = new BatchTransferBalance() - .SetRecipients(transferRecipients); - -// Define and assign the return data fragment to the mutation -var transferBalanceFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -batchTransferBalance.Fragment(transferBalanceFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendBatchTransferBalance(batchTransferBalance); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Build the CreateBatchTransaction mutation +var mutation = new MutationQueryBuilder() + .WithCreateBatchTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transactions: transactions); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateBatchTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/01-managing-tokens/07-freezing-thawing.md b/docs/02-guides/01-platform/01-managing-tokens/07-freezing-thawing.md index c402002..a9db373 100644 --- a/docs/02-guides/01-platform/01-managing-tokens/07-freezing-thawing.md +++ b/docs/02-guides/01-platform/01-managing-tokens/07-freezing-thawing.md @@ -73,8 +73,8 @@ Freeze and thaw are split into four discriminator actions on `CreateTransaction` - `thawCollection: { collectionId }` - `thawToken: { collectionId, tokenId, state }` -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: ### Freezing an entire collection @@ -109,33 +109,29 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Setup the mutation -var freezeCollection = new Freeze() - .SetCollectionId(36105) - .SetFreezeType(FreezeType.Collection); - -// Define and assign the return data fragment to the mutation -var transactionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -freezeCollection.Fragment(transactionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendFreeze(freezeCollection); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (freezeCollection action on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + FreezeCollection = new FreezeCollectionInput + { + CollectionId = 36105, + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` @@ -321,35 +317,31 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Setup the mutation -var freezeToken = new Freeze() - .SetCollectionId(36105) - .SetTokenId(new EncodableTokenIdInput().SetInteger(0)) - .SetFreezeType(FreezeType.Token) - .SetFreezeState(FreezeState.Temporary); - -// Define and assign the return data fragment to the mutation -var transactionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -freezeToken.Fragment(transactionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendFreeze(freezeToken); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (freezeToken action on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + FreezeToken = new FreezeTokenInput + { + CollectionId = 36105, + TokenId = 0, + State = FreezeState.Temporary, // or FreezeState.Permanent for a soulbound freeze + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` @@ -543,33 +535,29 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Setup the mutation -var thawCollection = new Thaw() - .SetCollectionId(36105) - .SetFreezeType(FreezeType.Collection); - -// Define and assign the return data fragment to the mutation -var transactionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -thawCollection.Fragment(transactionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendThaw(thawCollection); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (thawCollection action on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + ThawCollection = new ThawCollectionInput + { + CollectionId = 36105, + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` @@ -755,34 +743,31 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Setup the mutation -var thawToken = new Thaw() - .SetCollectionId(36105) - .SetTokenId(new EncodableTokenIdInput().SetInteger(0)) - .SetFreezeType(FreezeType.Token); - -// Define and assign the return data fragment to the mutation -var transactionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -thawToken.Fragment(transactionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendThaw(thawToken); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (thawToken action on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + ThawToken = new ThawTokenInput + { + CollectionId = 36105, + TokenId = 0, + State = FreezeState.Temporary, + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/01-managing-tokens/08-burning-destroying-tokens.md b/docs/02-guides/01-platform/01-managing-tokens/08-burning-destroying-tokens.md index 10567ec..71cf868 100644 --- a/docs/02-guides/01-platform/01-managing-tokens/08-burning-destroying-tokens.md +++ b/docs/02-guides/01-platform/01-managing-tokens/08-burning-destroying-tokens.md @@ -82,8 +82,8 @@ Since this request requires a , it must be sign Burning is the `burnToken` discriminator action on `CreateTransaction`. The same action handles both "melt some supply" and "destroy the token entirely" — set `removeTokenStorage: true` to destroy. -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: ### Melting token's supply @@ -121,38 +121,32 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Set up the burn params -var burnParams = new BurnParamsInput() - .SetTokenId(new EncodableTokenIdInput().SetInteger(0)) // Set the token id. - .SetAmount(1); // Set the amount to burn. - -// Set up the mutation -var burn = new Burn() - .SetCollectionId(68844) // Set the collection id. - .SetParams(burnParams); // Set the burn params. - -// Define and assign the return data fragment to the mutation -var burnFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -burn.Fragment(burnFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendBurn(burn); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (one action set on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + BurnToken = new BurnTokenInput + { + CollectionId = 68844, + TokenId = 0, + Amount = 1, + RemoveTokenStorage = false, // set true to also destroy the token (see below) + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` @@ -309,39 +303,32 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Set up the burn params -var burnParams = new BurnParamsInput() - .SetTokenId(new EncodableTokenIdInput().SetInteger(0)) // Set the token id. - .SetAmount(1) // Set the amount to burn. - .SetRemoveTokenStorage(true); // Set whether the token storage will be removed if no tokens are left. - -// Set up the mutation -var burn = new Burn() - .SetCollectionId(68844) // Set the collection id. - .SetParams(burnParams); // Set the burn params. - -// Define and assign the return data fragment to the mutation -var burnFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -burn.Fragment(burnFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendBurn(burn); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (one action set on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + BurnToken = new BurnTokenInput + { + CollectionId = 68844, + TokenId = 0, + Amount = 1, + RemoveTokenStorage = true, // also destroy the token + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` @@ -495,32 +482,29 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Set up the mutation -var destroyCollection = new DestroyCollection() - .SetCollectionId(68844); // Set the collection id. - -// Define and assign the return data fragment to the mutation -var destrotCollectionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -destroyCollection.Fragment(destrotCollectionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendDestroyCollection(destroyCollection); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (one action set on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + transaction: new TransactionInput + { + DestroyCollection = new DestroyCollectionInput + { + Id = 68844, // the collection id + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/02-managing-users/01-connecting-user-wallets/01-sending-wallet-requests.md b/docs/02-guides/01-platform/02-managing-users/01-connecting-user-wallets/_01-sending-wallet-requests.md similarity index 100% rename from docs/02-guides/01-platform/02-managing-users/01-connecting-user-wallets/01-sending-wallet-requests.md rename to docs/02-guides/01-platform/02-managing-users/01-connecting-user-wallets/_01-sending-wallet-requests.md diff --git a/docs/02-guides/01-platform/02-managing-users/02-reading-user-wallets.md b/docs/02-guides/01-platform/02-managing-users/02-reading-user-wallets.md index 35c0ba0..a5d5b73 100644 --- a/docs/02-guides/01-platform/02-managing-users/02-reading-user-wallets.md +++ b/docs/02-guides/01-platform/02-managing-users/02-reading-user-wallets.md @@ -26,8 +26,8 @@ For example, if a user has a particular token in their wallet, they might gain a Wallet data is read with the `GetAccount` query. It takes the `network` and `chain` to look up, along with the wallet's `address`. -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: ### Fetching a wallet's Enjin Coin balance @@ -56,33 +56,24 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Setup the query -var getWallet = new GetWallet() - .SetAccount("cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f"); - -// Define and assign the return data fragment to the query -var walletFragment = new WalletFragment() - .WithBalances(new BalancesFragment() - .WithFree() - .WithReserved() - ); - -getWallet.Fragment(walletFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendGetWallet(getWallet); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the GetAccount query, selecting the wallet's ENJ balance +var query = new QueryQueryBuilder() + .WithGetAccount( + new AccountQueryBuilder().WithBalance(), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + address: "efQh8FzLm6oH3dmTU3HWqGrtm6Xcuu1WG33N2Ka9fzo5MFFAr"); + +// Send the query and read the result +var response = await client.SendQuery(query); +Console.WriteLine(response.Result.Data?.GetAccount?.Balance); ``` @@ -273,46 +264,34 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Setup the query -var getWallet = new GetWallet() - .SetAccount("cxLU94nRz1en6gHnXnYPyTdtcZZ9dqBasexvexjArj4V1Qr8f"); - -// Define and assign the return data fragment to the query -var walletFragment = new WalletFragment() - .WithTokenAccounts(new ConnectionFragment() - .WithEdges(new EdgeFragment() - .WithNode(new TokenAccountFragment() - .WithBalance() - .WithToken(new TokenFragment() - .WithTokenId() - .WithCollection(new CollectionFragment() - .WithCollectionId() - ) - .WithAttributes(new AttributeFragment() - .WithKey() - .WithValue() - ) - ) - ) - ) - ); - -getWallet.Fragment(walletFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendGetWallet(getWallet); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the GetAccount query, selecting the tokens the wallet holds. +// Each held token is an AccountToken (its balance) wrapping the Token itself. +var query = new QueryQueryBuilder() + .WithGetAccount( + new AccountQueryBuilder() + .WithTokens( + new AccountTokenQueryBuilder() + .WithBalance() + .WithToken(new TokenQueryBuilder() + .WithId() + .WithTokenId() + .WithCollection(new CollectionQueryBuilder().WithId()) + .WithAttributes(new AttributeQueryBuilder().WithKey().WithValue())), + limit: 100), + network: Network.Enjin, // or Network.Canary for testnet + chain: Chain.Matrix, + address: "efQh8FzLm6oH3dmTU3HWqGrtm6Xcuu1WG33N2Ka9fzo5MFFAr"); + +// Send the query; the wallet's current holdings are on the returned account +var response = await client.SendQuery(query); +var account = response.Result.Data?.GetAccount; ``` diff --git a/docs/02-guides/01-platform/02-managing-users/03-using-managed-wallets.md b/docs/02-guides/01-platform/02-managing-users/03-using-managed-wallets.md index 3a168c6..172daf9 100644 --- a/docs/02-guides/01-platform/02-managing-users/03-using-managed-wallets.md +++ b/docs/02-guides/01-platform/02-managing-users/03-using-managed-wallets.md @@ -34,8 +34,8 @@ You can obtain cENJ (Canary ENJ) for testing from the [built-in Canary faucet](/ --- -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: ## Creating a Managed Wallet {#creating-a-managed-wallet} @@ -64,24 +64,20 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Setup the mutation -var createWallet = new CreateWallet() - .SetExternalId("player_1_id"); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); +// Provision a managed wallet keyed by your own unique externalId +var mutation = new MutationQueryBuilder() + .WithCreateManagedWallet(externalId: "docs-example-player"); -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendCreateWallet(createWallet); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Send the mutation; the result is true once the wallet is being provisioned +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateManagedWallet); ``` @@ -236,31 +232,24 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Setup the query -var getWallet = new GetWallet() - .SetExternalId("player_1_id"); - -// Define and assign the return data fragment to the query -var walletFragment = new WalletFragment() - .WithAccount(new AccountFragment() - .WithAddress() - .WithPublicKey() - ); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendGetWallet(getWallet); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Look the managed wallet up by its externalId and read its on-chain public key +var query = new QueryQueryBuilder() + .WithGetManagedWallet( + new ManagedWalletQueryBuilder().WithPublicKey().WithExternalId(), + network: Network.Canary, + chain: Chain.Matrix, + externalId: "docs-example-player"); + +var response = await client.SendQuery(query); +var wallet = response.Result.Data?.GetManagedWallet; +Console.WriteLine(wallet?.PublicKey); ``` @@ -449,45 +438,32 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Create the list of recipients for the batch mint -var recipients = new List() -{ - new MintRecipient() - .SetAccount("cxMkGKAmD73fGoFVaKj5HNmeLRHpTFDf5oQMp2dsqKJ8uZ3tT") - .SetMintParams(new MintTokenParams() - .SetAmount(1) - .SetTokenId(new EncodableTokenIdInput().SetInteger(6533) - ) - ) -}; - -// Setup the mutation -var batchMint = new BatchMint() - .SetCollectionId(7154) - .SetRecipients(recipients.ToArray()); - -// Define and assign the return data fragment to the mutation -var transactionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -batchMint.Fragment(transactionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendBatchMint(batchMint); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Mint a token straight into the managed wallet by setting it as the recipient +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Canary, + chain: Chain.Matrix, + transaction: new TransactionInput + { + MintToken = new MintTokenInput + { + Recipient = "0xded3c8f0296f5ee023f07aa5617fc261bd5991c4474ee775a16ec35c1d1a1e3a", // the managed wallet's public key + CollectionId = 36105, + TokenId = 1, + Amount = 1, + }, + }); + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` @@ -715,45 +691,34 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; using Enjin.Platform.Sdk; -// Create the array of recipients for the batch transfer -var recipients = new List() -{ - new TransferRecipient() - .SetAccount("cxLf6yvvtscKrHRfKDphnzsT3eoRY45VbJvqXKub5pmj5mdbQ") // The recipient of the transfer - .SetSimpleParams(new SimpleTransferParams() - .SetTokenId(new EncodableTokenIdInput().SetInteger(6533)) - .SetAmount(1) - ) -}; - -// Setup the mutation -var batchTransfer = new BatchTransfer() - .SetCollectionId(7154) - .SetSigningAccount("cxMkGKAmD73fGoFVaKj5HNmeLRHpTFDf5oQMp2dsqKJ8uZ3tT") // Add your signing account address (the Managed wallet account address from the GetWallet query) - .SetRecipients(recipients.ToArray()); - -// Define and assign the return data fragment to the mutation -var transactionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -batchTransfer.Fragment(transactionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendBatchTransfer(batchTransfer); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Transfer a token out of the managed wallet. signerExternalId makes the +// platform sign with that managed wallet instead of the Wallet Daemon. +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Canary, + chain: Chain.Matrix, + transaction: new TransactionInput + { + TransferToken = new TransferTokenInput + { + Recipient = "cxLf6yvvtscKrHRfKDphnzsT3eoRY45VbJvqXKub5pmj5mdbQ", // the recipient of the transfer + CollectionId = 36105, + TokenId = 1, + Amount = 1, + }, + }, + signerExternalId: "docs-example-player"); // the managed wallet that signs + +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/03-advanced-mechanics/05-enj-infusion.md b/docs/02-guides/01-platform/03-advanced-mechanics/05-enj-infusion.md index b228cc1..6d292e9 100644 --- a/docs/02-guides/01-platform/03-advanced-mechanics/05-enj-infusion.md +++ b/docs/02-guides/01-platform/03-advanced-mechanics/05-enj-infusion.md @@ -97,8 +97,8 @@ The Platform accepts infusion values in the **base unit** (integers), not decima - **Example:** To infuse a token with **5 ENJ**, input `5000000000000000000`. ::: -:::warning SDKs are not yet available -The C# and C++ SDK examples below are out of date and **will not work against the current Enjin Platform API**. This section will be updated once new SDKs are published. Until then, use the GraphQL, cURL, Javascript, Node.js, or Python examples. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: @@ -133,34 +133,33 @@ curl --location 'https://platform.beta.enjin.io/graphql' \ ```csharp -using System.Text.Json; +using System; +using System.Numerics; using Enjin.Platform.Sdk; -// Set up the mutation -var infuse = new Infuse() - .SetCollectionId(3298) // Specify the collection ID. - .SetTokenId(new EncodableTokenIdInput().SetInteger(1)) // Specify the token ID. - .SetAmount(5000000000000000000); // Specify the amount of ENJ to infuse. - -// Define and assign the return data fragment to the mutation -var transactionFragment = new TransactionFragment() - .WithId() - .WithMethod() - .WithState(); - -infuse.Fragment(transactionFragment); - -// Create and auth a client to send the request to the platform -var client = PlatformClient.Builder() - .SetBaseAddress("https://platform.beta.enjin.io") - .Build(); -client.Auth("Your_Platform_Token_Here"); - -// Send the request and write the output to the console. -// Only the fields that were requested in the fragment will be filled in, -// other fields which weren't requested in the fragment will be set to null. -var response = await client.SendInfuse(infuse); -Console.WriteLine(JsonSerializer.Serialize(response.Result.Data)); +// Create and authenticate the client +using var client = new PlatformClient(); +client.Auth(""); + +// Build the CreateTransaction mutation (one action set on TransactionInput) +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithUuid().WithState(), + network: Network.Enjin, // or Network.Canary for testnet — match the GraphQL tab + chain: Chain.Matrix, + transaction: new TransactionInput + { + InfuseToken = new InfuseTokenInput + { + CollectionId = 3298, + TokenId = 1, + Amount = BigInteger.Parse("5000000000000000000"), // 5 ENJ in base units + }, + }); + +// Send the mutation; poll GetTransaction by uuid to track its on-chain state +var response = await client.SendMutation(mutation); +Console.WriteLine(response.Result.Data?.CreateTransaction?.Uuid); ``` diff --git a/docs/02-guides/01-platform/03-advanced-mechanics/06-the-multiverse.md b/docs/02-guides/01-platform/03-advanced-mechanics/06-the-multiverse.md index cc6e0ec..a32af5b 100644 --- a/docs/02-guides/01-platform/03-advanced-mechanics/06-the-multiverse.md +++ b/docs/02-guides/01-platform/03-advanced-mechanics/06-the-multiverse.md @@ -53,7 +53,7 @@ You are also welcome to design your own 3D or 2D models to better suit your game To add utility to Multiverse Items, your game will need to: -1. [Link player wallets to your game](/02-guides/01-platform/02-managing-users/01-connecting-user-wallets/01-sending-wallet-requests.md). +1. Link player wallets to your game. 2. [Read the inventory from player wallets](/02-guides/01-platform/02-managing-users/02-reading-user-wallets.md). 3. Validate ownership of the [Multiverse Items](#the-multiverse-collection). 4. Provide an in-game benefit for each Multiverse Item. diff --git a/docs/02-guides/01-platform/03-advanced-mechanics/07-hot-cold-inventories.md b/docs/02-guides/01-platform/03-advanced-mechanics/07-hot-cold-inventories.md index b5658ba..a5a0a6d 100644 --- a/docs/02-guides/01-platform/03-advanced-mechanics/07-hot-cold-inventories.md +++ b/docs/02-guides/01-platform/03-advanced-mechanics/07-hot-cold-inventories.md @@ -79,7 +79,7 @@ This guide calls it "moving" an item between inventories. In your game's UI, cal ### Cold inventory: the player's wallet -Each player gets an on-chain wallet that acts as their cold inventory — either a [managed wallet](/02-guides/01-platform/02-managing-users/03-using-managed-wallets.md) you create for them (`CreateManagedWallet(externalId: "player-115")`), or a self-custodial wallet they [link to your application](/02-guides/01-platform/02-managing-users/01-connecting-user-wallets/01-sending-wallet-requests.md#step-1--linking-a-players-wallet). +Each player gets an on-chain wallet that acts as their cold inventory — either a [managed wallet](/02-guides/01-platform/02-managing-users/03-using-managed-wallets.md) you create for them (`CreateManagedWallet(externalId: "player-115")`), or a self-custodial wallet they link to your application. ### Hot inventory: your database @@ -123,7 +123,7 @@ query ConfirmMove { See [Working with Events](/05-enjin-platform/03-working-with-events.md) for the full finalization-and-events workflow. (Real-time push events that remove the need to poll are [planned](/03-api-reference/03-websocket-events.md).) -For a **self-custodial** cold wallet, your server can't sign the melt — instead, the player approves it in their own Enjin Wallet app via a [wallet request](/02-guides/01-platform/02-managing-users/01-connecting-user-wallets/01-sending-wallet-requests.md). +For a **self-custodial** cold wallet, your server can't sign the melt — instead, the player approves it in their own Enjin Wallet app via a wallet request. ### Move to cold — mint to the cold wallet diff --git a/docs/02-guides/01-platform/04-software-development-kit/01-getting-started.md b/docs/02-guides/01-platform/04-software-development-kit/01-getting-started.md index c2d16cf..aea3fe9 100644 --- a/docs/02-guides/01-platform/04-software-development-kit/01-getting-started.md +++ b/docs/02-guides/01-platform/04-software-development-kit/01-getting-started.md @@ -1,212 +1,136 @@ --- title: "Getting Started" slug: "getting-started" -description: "Learn how to get started with the Enjin SDK, your first step toward building powerful blockchain-based applications and games." +description: "Learn how to get started with the Enjin Platform C# SDK, your first step toward building powerful blockchain-based applications and games." --- import Tabs from '@theme/Tabs'; import TabItem from '@theme/TabItem'; -:::warning SDKs are not yet available -The C# and C++ SDK content on this page is out of date and **will not work against the current Enjin Platform API**. This page will be updated once new SDKs are published. Until then, see [How to Use GraphQL](/01-getting-started/05-using-enjin-api/01-how-to-use-graphql.md) and the [API Reference](/03-api-reference/03-api-reference.md) for the current API shapes. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: -To have the SDK connect with the Enjin Platform we must use its platform clients and event services. As a starter, we will look over how to set up these clients. +To communicate with the Enjin Platform from C#, you use the SDK's `PlatformClient`. This page covers installing the SDK and setting up an authenticated client. :::warning Please always make sure to integrate authentication endpoints via secure backend servers. -Direct integration of the SDKs into game clients, which can be decompiled, is strictly not recommended due to potential security risks and exposure of your keys. +Direct integration of the SDK into game clients, which can be decompiled, is strictly not recommended due to potential security risks and exposure of your keys. ::: -## Platform Clients +## Installing the SDK -For communicating with the platform's GraphQL API, the SDK defines an `IPlatformClient` interface that works with GraphQL objects for sending requests and receiving responses from the platform. +### C# -### Creating the Client - -The built-in `PlatformClient` class, which implements `IPlatformClient`, utilizes a builder pattern for instantiating new instances. When using this builder, one of the essential inputs we must set is the base address of the platform we will be using. - - - -```csharp -using Enjin.Platform.Sdk; - -IPlatformClient client = PlatformClient - .Builder() - .SetBaseAddress("https://") - .Build(); -``` - - -```cpp -#include "EnjinPlatformSdk/PlatformClient.hpp" -#include - -using namespace enjin::platform::sdk; -using namespace std; - -unique_ptr client = PlatformClient::Builder() - .SetBaseAddress("https://") - .Build(); -``` - - +The C# SDK is published to NuGet as a single package, [`Enjin.Platform.Sdk`](https://www.nuget.org/packages/Enjin.Platform.Sdk). It targets .NET Standard 2.1 (compatible with .NET 5.0+, Unity 2021.3 LTS+, and Godot 4.0+). -### Authenticating the Client - -Once we have our client instance we may now authenticate it using an authentication token for our platform. +Install it with the .NET CLI: - - -```csharp -client.Auth(""); +```bash +dotnet add package Enjin.Platform.Sdk ``` - - -```cpp -client->Auth(""); -``` - - - -### Disposing of the Client -When we no longer need our platform client, we may dispose of it to free up any system resources it may be using with the appropriate method as shown: - - - -```csharp -client.Dispose(); -``` - - -```cpp -// We may reset the pointer or allow the class destructor to handle -// this when our client goes out-of-scope. +Or add it to your project file: -client.reset(); +```xml + ``` - - -## Event Services - -The platform broadcasts events that we may respond to or gather information from. For interfacing with an event broadcasting service the SDK offers the `IEventService` interface. Whether we decide to use a free, paid, self-hosted, or any such framework as the driver for broadcasting platform events, the `IEventService` interface defines what operations we may use for working with it. +:::note +In v3 the SDK is a single package. The old v2 sub-packages (`Enjin.Platform.Sdk.Beam`, `.FuelTanks`, `.Marketplace`) have been consolidated into `Enjin.Platform.Sdk`, and everything lives under the single `Enjin.Platform.Sdk` namespace. +::: -### Creating the Service +### C++ -The default framework used by the Enjin Platform Cloud and platforms using the Enjin Platform - Starter Template for broadcasting cloud events is [Pusher Channels](https://pusher.com/channels). To work with this framework the SDK has its own `PusherEventService` which implements `IEventService` and serves as an abstraction between us and Pusher for subscribing and listening for events and is a useful tool for those just getting started. +An updated C++ SDK for the current Enjin Platform is on the way. Installation instructions will be added here once it's released — in the meantime, you can track the [C++ SDK repository](https://github.com/enjin/platform-cpp-sdk). -Our builder for the `PusherEventService` typically expects two attributes to be set before building with a third optional attribute for encryption. The two essential attributes are: +## Platform Client -- The application key -- The hostname of our platform +For communicating with the platform's GraphQL API, the SDK defines an `IPlatformClient` interface. The built-in `PlatformClient` class implements it and handles building, sending, and deserializing requests for you. -:::info -If our application key is not valid, then we may expect a 404 error when connecting our event service. -::: - -The other optional attribute we may set is the encryption status. This will determine which protocol our service will connect with (`wss` or `ws`). If we do not set this attribute, then our builder will default to the `WebSocket Secured` protocol on building. +### Creating the Client -An example of building this event service can be seen below: +Constructing a `PlatformClient` with no arguments connects to the Enjin Platform using the SDK's built-in endpoint — you don't need to specify a URL. You choose which network to work against (Enjin Mainnet or the Canary testnet) per request via the `network` argument, covered in [GraphQL Requests](/02-guides/01-platform/04-software-development-kit/02-graphql-requests.md), so the same client serves both. ```csharp using Enjin.Platform.Sdk; -IEventService service = PusherEventService - .Builder() - .SetKey("websocket") - .SetHost("") - .SetEncrypted(true) // Defaults to true if not set - .Build(); +using var client = new PlatformClient(); ``` ```cpp -#include "EnjinPlatformSdk/PusherEventService.hpp" +#include "EnjinPlatformSdk/PlatformClient.hpp" #include using namespace enjin::platform::sdk; using namespace std; -unique_ptr service = PusherEventService::Builder() - .SetKey("websocket") - .SetHost("") - .SetEncrypted(true) // Defaults to true if not set +unique_ptr client = PlatformClient::Builder() + .SetBaseAddress("https://") .Build(); ``` -:::tip -If you wish to change the key (websocket), you can do so in the platform config files. -::: - -::: note -For developers who opt to utilize Pusher's own Channels service for broadcasting events, then instead of `SetHost()` we may use the builder's `SetCluster()` method to connect our event service to the appropriate Pusher cluster. -::: - -### Managing the Connection - -Before we can use our event service, we must connect it to the designated server host through its ConnectAsync method as shown below: +The constructor also accepts optional parameters — including a custom base-address `Uri` (only needed for a self-hosted platform instance), a user agent, an `ILogger` implementation, and an `HttpLogLevel` for logging HTTP traffic: ```csharp -using System.Threading.Tasks; - -Task task = service.ConnectAsync(); -``` - - -```cpp -#include +using Enjin.Platform.Sdk; -using namespace std; +ILogger logger = /* your ILogger implementation */; -future fut = service->ConnectAsync(); +using var client = new PlatformClient( + logger: logger, + httpLogLevel: HttpLogLevel.Body); ``` -To disconnect the service from the server, we make a call to its DisconnectAsync method. +### Authenticating the Client + +Once you have a client instance, authenticate it with your platform authentication token: ```csharp -using System.Threading.Tasks; - -Task task = service.DisconnectAsync(); +client.Auth(""); ``` ```cpp -#include - -using namespace std; - -future fut = service->DisconnectAsync(); +client->Auth(""); ``` -## Disposing of the Service +### Disposing of the Client -When we no longer need our event service, we may dispose of it to free up any system resources it may be using with the appropriate method as shown: +`PlatformClient` implements `IDisposable`. When you no longer need it, dispose of it to free up its underlying resources. The `using var` declaration above does this automatically when the client goes out of scope; you can also dispose of it explicitly: ```csharp -service.Dispose(); +client.Dispose(); ``` ```cpp // We may reset the pointer or allow the class destructor to handle -// this when our event service goes out-of-scope. +// this when our client goes out-of-scope. -service.reset(); +client.reset(); ``` + +## Next Steps + +With an authenticated client you can start sending requests. See [GraphQL Requests](/02-guides/01-platform/04-software-development-kit/02-graphql-requests.md) to learn how to build queries and mutations, select the fields you want back, and handle responses. + +:::tip Real-time events +The Enjin Platform doesn't yet expose real-time WebSocket events. Until it does, the pattern for tracking a submitted transaction is to poll the `GetTransaction` query by its UUID until it reaches a final state — see the [Enjin Farmer implementation breakdown](/02-guides/01-platform/05-enjin-farmer-sample-game/03-implementation-breakdown.md) for a worked example. +::: diff --git a/docs/02-guides/01-platform/04-software-development-kit/02-graphql-requests.md b/docs/02-guides/01-platform/04-software-development-kit/02-graphql-requests.md index 4e94666..a081564 100644 --- a/docs/02-guides/01-platform/04-software-development-kit/02-graphql-requests.md +++ b/docs/02-guides/01-platform/04-software-development-kit/02-graphql-requests.md @@ -1,67 +1,71 @@ --- title: "GraphQL Requests" slug: "graphql-requests" -description: "Learn how to use GraphQL requests to interact with the Enjin platform, allowing you to query and mutate blockchain data efficiently." +description: "Learn how to build GraphQL requests with the Enjin Platform C# SDK to query and mutate blockchain data efficiently." --- import Tabs from '@theme/Tabs'; import TabItem from '@theme/TabItem'; -:::warning SDKs are not yet available -The C# and C++ SDK content on this page is out of date and **will not work against the current Enjin Platform API**. This page will be updated once new SDKs are published. Until then, see [How to Use GraphQL](/01-getting-started/05-using-enjin-api/01-how-to-use-graphql.md) and the [API Reference](/03-api-reference/03-api-reference.md) for the current API shapes. +:::info C++ SDK coming soon +The C++ examples on this page target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: -## Creating the Request +The SDK builds GraphQL requests for you through a set of fluent query builders, so you never have to write a query string by hand. Every request follows the same shape: build a query or mutation with a builder, choose the fields you want back, send it with the client, then read the result. -The most important step in sending a request is to first create said request. The SDK provides us with two ways to create a request. The first way is to utilize a predefined, dynamic request class to programmatically compile our request at runtime. The second way is to provide our own query string to be sent along with any relevant information, however, this method of going about creating a request places a greater demand on us to validate that our queries and mutations are indeed correct. +## Building a Request -### Dynamic Requests +There are two root builders, one for each GraphQL operation type: -Dynamic requests represent the different queries and mutations we may make in the platform's GraphQL schemas and offer a built-in, programmatic method of arranging requests at runtime. +- `QueryQueryBuilder` — for reading data (e.g. `GetCollection`, `GetToken`, `GetAccount`). +- `MutationQueryBuilder` — for changing state (e.g. `CreateTransaction`, `CreateManagedWallet`). -### Setting Result Fields - -Requests which produce non-scalar types in the response will have an associated fragment class that may be passed to its aptly named `Fragment` method. For predefined type models in the SDK, there will be corresponding fragment classes that allow us to specify the fields we want to be returned in the response. - -As an example, the `GetCollection` request accepts a `CollectionFragment` instance as its and through the fragment we may specify that we want the `collectId` field to be returned in the data of the response by using a predefined method as shown below: +You add an operation by calling the matching `WithXxx` method. Each operation takes a **field-selection builder** (which fields you want returned) followed by its arguments. Every root query and mutation requires the target `network` and `chain`: ```csharp using Enjin.Platform.Sdk; -CollectionFragment fragment = new CollectionFragment() - .WithCollectionId(); - -req.Fragment(fragment); +var query = new QueryQueryBuilder() + .WithGetCollection( + new CollectionQueryBuilder().WithId(), + network: Network.Canary, + chain: Chain.Matrix, + id: 2000); ``` ```cpp -#include "EnjinPlatformSdk/CollectionFragment.hpp" +#include "EnjinPlatformSdk/GetCollection.hpp" +#include "EnjinPlatformSdk/SerializableString.hpp" #include using namespace enjin::platform::sdk; using namespace std; -CollectionFragmentPtr fragment = make_shared(); -fragment->WithCollectionId(); +SerializableStringPtr value = make_shared("2000"); -req.SetFragment(fragment); +GetCollection req = GetCollection() + .SetCollectionId(value); ``` -We may also set the fragment to include fields not specified by the SDK if needed by using the general `WithField` method. For this method, we must pass a string as the first parameter containing the name of the field we would like to request and for the second parameter we may either pass a Boolean when requesting a scalar field or an instance of a class implementing which `IGraphQlFragment` for a non-scalar field. An example of this can be seen below: +Note that `tokenId` and `collectionId` are plain numeric values (`System.Numerics.BigInteger`) in v3 — there is no token-id wrapper object. You can pass an `int` or `long` literal directly and it will be converted for you. + +## Selecting Result Fields + +For any operation that returns an object, you pass a field-selection builder for that type (for example, `CollectionQueryBuilder`, `TokenQueryBuilder`, `AccountQueryBuilder`). Call a `WithXxx` method for each field you want returned. Scalar fields take no builder; object fields take a nested builder so you can select their sub-fields: ```csharp using Enjin.Platform.Sdk; -CollectionFragment fragment = new CollectionFragment() - .WithField("collectionId", true) - .WithField("owner", new WalletFragment().WithId()); +var fragment = new CollectionQueryBuilder() + .WithId() + .WithOwner(new AccountQueryBuilder().WithAddress()); ``` @@ -83,49 +87,29 @@ fragment->WithField("collectionId", true) -:::warning -For requests which accept fragments, a fragment with at least one field requested must be passed or the SDK will throw an exception. +:::tip Convenience selectors +Builders inherit helpers from their base class: `WithAllScalarFields()` selects every scalar field at once, `WithAllFields()` selects all fields, and `ExceptField("name")` removes a field you don't want. These are handy while prototyping, but selecting only the fields you need keeps responses small. ::: -### Setting Request Variables - -GraphQL requests that have settable variables will have methods prefixed with "set" for setting predefined parameters for the given type. An example of this for the `GetCollection` the query can be seen below: - - - -```csharp -using Enjin.Platform.Sdk; - -GetCollection req = new GetCollection() - .SetCollectionId(2000) -``` - - -```cpp -#include "EnjinPlatformSdk/GetCollection.hpp" -#include "EnjinPlatformSdk/SerializableString.hpp" -#include - -using namespace enjin::platform::sdk; -using namespace std; +:::warning +A request that returns an object must have at least one field selected on its builder, or the platform will reject the query. +::: -SerializableStringPtr value = make_shared("2000"); +## Setting Arguments -GetCollection req = GetCollection() - .SetCollectionId(value); -``` - - - -Such classes also have a general `SetVariable` method which accepts a string for the parameter name, a string for the variable's type, and a value. This can be used to set variables that are not predefined by the SDK. An example of what this may look like for the `GetCollection` can be seen below: +Operation arguments are passed by name directly to the `WithXxx` method. You can pass plain C# values — enums, numbers, and strings are accepted as-is (the builder wraps them internally). The required `network` and `chain` arguments are the `Network` and `Chain` enums: ```csharp using Enjin.Platform.Sdk; -GetCollection req = new GetCollection() - .SetVariable("collectionId", "BigInt!", 2000); +var query = new QueryQueryBuilder() + .WithGetCollection( + new CollectionQueryBuilder().WithId(), + network: Network.Canary, // or Network.Enjin for Mainnet + chain: Chain.Matrix, // or Chain.Relay + id: 2000); ``` @@ -145,122 +129,21 @@ GetCollection req = GetCollection() -Each component of the SDK also comes with a static class containing string fields representing the types present for that component's GraphQL schema and offer a more programmatic option for setting the type of a variable, as shown below: - - - -```csharp -#include "EnjinPlatformSdk/GetCollection.hpp" -#include "EnjinPlatformSdk/SerializableString.hpp" -#include - -using namespace enjin::platform::sdk; -using namespace std; - -SerializableStringPtr value = make_shared("2000"); - -GetCollection req = GetCollection() - .SetVariable("collectionId", CoreTypes::BigInt, value); -``` - - -```cpp -#include "EnjinPlatformSdk/GetCollection.hpp" -#include "EnjinPlatformSdk/SerializableString.hpp" -#include - -using namespace enjin::platform::sdk; -using namespace std; - -SerializableStringPtr value = make_shared("2000"); - -GetCollection req = GetCollection() - .SetVariable("collectionId", CoreTypes::BigInt, value); -``` - - - -### Setting Input Parameters - -Classes, such as fragments and those modeling a GraphQL input may have settable parameters to be used as part of a request. An example of one of these parameter holders is shown below: - - - -```csharp -using System.Numerics; -using Enjin.Platform.Sdk; - -BigInteger integer = BigInteger.Parse(""); +## Sending the Request -EncodableTokenIdInput tokenId = new EncodableTokenIdInput() - .SetInteger(integer); -``` - - -```cpp -#include "EnjinPlatformSdk/EncodableTokenIdInput.hpp" -#include "EnjinPlatformSdk/SerializableString.hpp" -#include +The client provides two extension methods that build the request body and POST it for you: -using namespace enjin::platform::sdk; -using namespace std; +- `SendQuery(QueryQueryBuilder)` returns an `IPlatformResponse`. +- `SendMutation(MutationQueryBuilder)` returns an `IPlatformResponse`. -SerializableStringPtr integer = - make_shared(""); - -EncodableTokenIdInputPtr tokenId = make_shared(); -tokenId->SetInteger(integer); -``` - - - -These classes also have a general `SetParameter` method for setting parameters not already defined by the SDK. These parameters may be of a type that implements `IGraphQlParameter` which itself may be a parameter holder, a list of types implementing the aforementioned interface, or a general value representing parameters that do not support nesting such as a scalar. Usage of this method can be seen below: +Both are asynchronous: ```csharp -using System.Numerics; using Enjin.Platform.Sdk; -BigInteger integer = BigInteger.Parse(""); - -EncodableTokenIdInput tokenId = new EncodableTokenIdInput() - .SetParameter("integer", integer); -``` - - -```cpp -#include "EnjinPlatformSdk/EncodableTokenIdInput.hpp" -#include "EnjinPlatformSdk/SerializableString.hpp" -#include - -using namespace enjin::platform::sdk; -using namespace std; - -SerializableStringPtr integer = - make_shared(""); - -EncodableTokenIdInputPtr tokenId = make_shared(); -tokenId->SetParameter("integer", integer); -``` - - - -:::tip -Parameters on the root fragment of a request will be treated as if they are parameters for the request itself, such is the case for the after and first parameters of the ConnectionFragment class. -::: - -### Sending the Request - -When sending requests the SDK offers built-in methods that complement the predefined requests. The methods will be prefixed with "Send" followed by the name of the request. An example of what this may look like for the `GetCollection` the request is shown below: - - - -```csharp -using Enjin.Platform.Sdk; // Namespace of extension method - -// Returns a Task containing the response -client.SendGetCollection(req); +IPlatformResponse response = await client.SendQuery(query); ``` @@ -275,197 +158,91 @@ SendGetCollection(*client, req); -### Static Requests - -Aside from the dynamic queries and mutations built into the SDK, we may pass static query strings and variable mappings to the platform client in cases where speed is valued more than dynamic request creation. - -To facilitate static requests, the platform client implements a method that takes a string for the query body, a nullable mapping for any variables, and a relative path for the request's schema in the API. - -:::warning -The type for the data in the GraphQL query string must be aliased as result to ensure that the returned data may be properly deserialized for the response. -::: - -### Without Variables - -When creating a static request without passing a mapping of variables we need only set the values for such variables in the query string we will be using. After creating our query string we then pass it and the schema path to the `SendRequest` method while leaving the variables argument as `null`, as shown below: - - - -```csharp -using Enjin.Platform.Sdk; - -string query = @"query { - result: GetCollection(collectionId: 2000) { - collectionId - } -}"; -IPlatformRequest req = PlatformRequest - .Builder() - .SetPath("") - .AddOperation(query, null) - .Build(); - -// Returns a Task containing the response -client.SendRequest>(req); -``` - - -```cpp -#include "EnjinPlatformSdk/Collection.hpp" -#include "EnjinPlatformSdk/GraphQlResponse.hpp" -#include "EnjinPlatformSdk/PlatformRequest.hpp" -#include - -using namespace enjin::platform::sdk; -using namespace std; - -string query = R"(query { - result: GetCollection(collectionId: 2000) { - collectionId - } -})"; - -PlatformRequestPtr req = PlatformRequest::Builder() - .SetPath("") - .AddOperation(query, {}) - .Build(); - -// Returns a Future containing the response -client->SendRequest>(req); -``` - - - -:::warning -For the C++ SDK, if the request contains an Upload variable then an additional map containing the names and values of the uploads will need to be passed to the AddOperation method. -::: - -### Handling the Response +## Handling the Response -Once we have sent our request to the platform we should expect to get a response back with information that we intended to retrieve in the first place or with information that we may act on if we so choose. +The returned `IPlatformResponse` wraps the HTTP layer (`IsSuccessStatusCode`, `StatusCode`, `Headers`) and exposes the GraphQL payload on its `Result` property. From there: -### Getting the Response +- `response.Result.Data` holds the typed result — each operation appears as a property matching its name (`Data.GetCollection`, `Data.CreateTransaction`, …). +- `response.Result.Errors` holds any GraphQL errors returned by the platform. -The send methods of a platform client return asynchronous handlers which contain the result of our operation. At the first level of the result, is a platform response of type, which generally holds the HTTP information of the response from the platform. Within this platform response, there is also a `GraphQlResponse` property, which contains the result data of our GraphQL request and any errors that may have been returned with it. +Always check for errors before reading the data: ```csharp -using System.Threading.Tasks; +using System; using Enjin.Platform.Sdk; -GetCollection req = /* Creating the request... */ +IPlatformResponse response = await client.SendQuery(query); -// Send the request and get the Task containing the response -Task>> task = - client.SendGetCollection(req); - -// Get the platform response holding the HTTP data -IPlatformResponse> platformRes = task.Result; +// GraphQL-level errors (malformed request, failed validation, etc.) +if (response.Result.Errors is { Count: > 0 }) +{ + foreach (var error in response.Result.Errors) + Console.WriteLine(error.Message); + return; +} -// Get the result, a GraphQL response, holding the GraphQL data -GraphQlResponse gqlRes = platformRes.GqlResponse; +// Read the typed result +Collection? collection = response.Result.Data.GetCollection; +Console.WriteLine(collection?.Id); ``` ```cpp #include "EnjinPlatformSdk/Collection.hpp" -#include "EnjinPlatformSdk/CoreQueries.hpp" -#include "EnjinPlatformSdk/GraphQlResponse.hpp" -#include "EnjinPlatformSdk/IPlatformResponse.hpp" -#include #include using namespace enjin::platform::sdk; using namespace std; -GetCollection req = /* Creating the request... */ - -// Send the request and get the Future containing the response -future>> fut = - SendGetCollection(*client, req); - -// Get the platform response holding the HTTP data -PlatformResponsePtr> platformRes = fut.get(); - -// Get the result, a GraphQL response, holding the GraphQL data -const optional>& gqlRes = platformRes->GetResult(); -``` - - - -### Processing the Result - -To process the result we must first get the `GraphQlData` property within the `GraphQlResponse`, then we will get the result property from the data. The type of result will be either one of the predefined type models or a scalar value depending on our request. - -The response also has a property indicating whether the request was successful, indicating that a result is present, and we ought to consider checking if this property is `true` before retrieving the result. - - - -```csharp -using Enjin.Platform.Sdk; - -if (gqlRes.IsSuccess) +if (gqlRes.has_value() && gqlRes->IsSuccess()) { - Collection collection = gqlRes.Data.Result; + const optional& collection = gqlRes->GetData()->GetResult(); /* Handle the result */ } -``` - - -```cpp -#include "EnjinPlatformSdk/Collection.hpp" -#include -using namespace enjin::platform::sdk; -using namespace std; - -if (gqlRes.has_value() && gqlRes->IsSuccess()) +if (gqlRes.has_value() && gqlRes->HasErrors()) { - const optional& collection = gqlRes->GetData()->GetResult(); + const optional>& errors = gqlRes->GetErrors(); - /* Handle the result */ + /* Handle the errors */ } ``` -### Processing Errors +## Sending Mutations -The response may also contain errors that the platform may return in situations where our request was malformed, had incorrect arguments, or failed some other validation. To retrieve any such errors we make a call to the response's Errors property as shown below: +Mutations work the same way, built with `MutationQueryBuilder` and sent with `SendMutation`. In v3, almost every on-chain action (creating a collection, minting, transferring, burning, …) is submitted through a single `CreateTransaction` mutation: you populate a `TransactionInput` with exactly one action field and submit it. ```csharp -using System.Collections.Generic; using Enjin.Platform.Sdk; -if (gqlRes.HasErrors) +var transaction = new TransactionInput { - IEnumerable errors = gqlRes.Errors; - - /* Handle the errors */ -} -``` - - -```cpp -#include "EnjinPlatformSdk/GraphQlError.hpp" -#include -#include - -using namespace enjin::platform::sdk; -using namespace std; + MintToken = new MintTokenInput + { + Recipient = "", + CollectionId = 2000, + TokenId = 1, + Amount = 1, + }, +}; -if (gqlRes.has_value() && gqlRes->HasErrors()) -{ - const optional>& errors = gqlRes->GetErrors(); +var mutation = new MutationQueryBuilder() + .WithCreateTransaction( + new TransactionQueryBuilder().WithId().WithState(), + network: Network.Canary, + chain: Chain.Matrix, + transaction: transaction); - /* Handle the errors */ -} +IPlatformResponse response = await client.SendMutation(mutation); ``` -The response also has a `HasErrors` property, which indicates whether there are in fact any errors at all and is a property we should check before making an attempt to retrieve them. +See the [Managing Tokens](/02-guides/01-platform/01-managing-tokens/01-creating-collections.md) guides for the full set of `TransactionInput` actions and worked examples for each operation. diff --git a/docs/02-guides/01-platform/04-software-development-kit/03-platform-events.md b/docs/02-guides/01-platform/04-software-development-kit/03-platform-events.md deleted file mode 100644 index 7c52d04..0000000 --- a/docs/02-guides/01-platform/04-software-development-kit/03-platform-events.md +++ /dev/null @@ -1,396 +0,0 @@ ---- -title: "Platform Events" -slug: "platform-events" -description: "Explore how to monitor and handle platform events in the Enjin SDK, ensuring real-time updates for your blockchain applications." ---- - -import Tabs from '@theme/Tabs'; -import TabItem from '@theme/TabItem'; - -:::warning SDKs are not yet available -The C# and C++ SDK content on this page is out of date and **will not work against the current Enjin Platform API**. This page will be updated once new SDKs are published. Until then, see [How to Use GraphQL](/01-getting-started/05-using-enjin-api/01-how-to-use-graphql.md) and the [API Reference](/03-api-reference/03-api-reference.md) for the current API shapes. -::: - -## Event Listeners - -To allow our application to receive events from the platform the SDK comes with an `IEventListener` interface for us to use to receive events for processing. - -### Creating a Listener - -To use the `IEventListener` interface on a listener class we create we must implement its `OnEvent` method. This method accepts a `PlatformEvent`, which contains the name of the event, the channel it was broadcasted on, the raw event message, and the parsed JSON data representing the message. A generic listener implementing this interface is shown in the code block below: - - - -```csharp -using System.Text.Json; -using Enjin.Platform.Sdk; - -class EventListener : IEventListener -{ - public void OnEvent(PlatformEvent evt) - { - string eventName = evt.EventName; - string channelName = evt.ChannelName; - string message = evt.Message; - JsonElement data = evt.Data; - - /* Handle event */ - } -} -``` - - -```cpp -#include "EnjinPlatformSdk/IEventListener.hpp" -#include "EnjinPlatformSdk/PlatformEvent.hpp" -#include - -using namespace enjin::platform::sdk; -using namespace std; - -class EventListener : public virtual IEventListener -{ -public: - void OnEvent(const PlatformEvent& evt) override - { - const string& eventName = evt.GetEventName(); - const string& channelName = evt.GetChannelName(); - const string& message = evt.GetMessage(); - - /* Handle event */ - } -}; -``` - - - -### Registering a Listener - -To make use of the event listener we have created, we will need to register it with the event service so that the service may pass any cloud events it receives to the listener. To do so, we may make a call to the registration method, passing our listener as an argument as can be seen below: - - - -```csharp -IEventListener listener = /* Create event listener */ - -IEventListenerRegistration reg = service.RegisterListener(listener); -``` - - -```cpp -#include "EnjinPlatformSdk/IEventListener.hpp" -#include "EnjinPlatformSdk/IEventListenerRegistration.hpp" - -using namespace enjin::platform::sdk; - -EventListenerPtr listener = /* Make pointer containing event listener */ - -EventListenerRegistrationPtr reg = service->RegisterListener(listener); -``` - - - -By registering our listener this way, the service will pass along any event it receives from the cloud to our listener for handling. - -We may also use the registration the service returned to a way to monitor or validate our listener's state within the service. The registration comes with a getter for the matcher used by the service to filter events, as well as a property indicating whether the listener's registration with the service is still active or not. - -#### Filter Events with Registration - -The event service also provides means for registering listeners while filter out events for the given registration. This may help in the creation of listeners with narrower scopes, such as a dedicated wallet listener. Without using one of the follow methods of registration, a given listener will be notified of all events the service receives. - -One method for registering a listener with event filtering is to pass an event matcher. For any event to be passed along to the listener, the service expects the matcher to return `true` for it. Aside from this requirement the matcher may be configured however we want. - - - -```csharp -using System; -using Enjin.Platform.Sdk; - -IEventListener listener = /* Create event listener */ -Func matcher = evtName => -{ - return /* Return boolean */ -}; - -// Returns a registration -service.RegisterListenerWithMatcher(listener, matcher); -``` - - -```cpp -#include "EnjinPlatformSdk/IEventListener.hpp" -#include "EnjinPlatformSdk/IEventListenerRegistration.hpp" -#include - -using namespace enjin::platform::sdk; -using namespace std; - -EventListenerPtr listener = /* Make pointer containing event listener */ -EventMatcher matcher = [](const string& evtName) { - return /* Return boolean */ -}; - -// Returns a registration -service->RegisterListenerWithMatcher(listener, matcher); -``` - - - -Alternatively, we may pass our listener with an array of events to filter for or exclude using one of two methods as shown below: - - - -```csharp -using System; -using Enjin.Platform.Sdk; - -IEventListener listener = /* Create event listener */ -string[] events = { "", "", "" }; - -// Pass only the listed events to the listener -service.RegisterListenerIncludingEvents(listener, events); - -// Pass events other than the ones listed to the listener -service.RegisterListenerExcludingEvents(listener, events); -``` - - -```cpp -#include "EnjinPlatformSdk/IEventListener.hpp" -#include -#include - -using namespace enjin::platform::sdk; -using namespace std; - -EventListenerPtr listener = /* Make pointer containing event listener */ -std::set events = { "", "", "" }; - -// Pass only the listed events to the listener -service->RegisterListenerIncludingEvents(listener, events); - -// Pass events other than the ones listed to the listener -service->RegisterListenerExcludingEvents(listener, events); -``` - - - -#### Filter Events with Attribute - -Event listeners may also have an attribute attached to them that the service may refer to for filtering. The attribute takes two arguments: a Boolean stating whether the events are allowed and a list of the event names. - - - -```csharp -using Enjin.Platform.Sdk; - -[EventFilter(isAllowed: true, "", "", "")] -class EventListener : IEventListener -{ - /* ... */ -} -``` - - - ```cpp - Work in progress. - ``` - - - -Once the class has been instantiated, we may then register it using the standard `RegisterListener` method that accepts only the listener as an argument. - -:::warning -If a listener with the filter attribute is registered using any of the registration methods that accept filter arguments, then the event service may throw an exception. -::: - -#### The Events to Filter - -The SDK contains utility classes which have constants representing the names of events broadcasted by the platform. These classes allow us to programmatically set which events we want to filter or even act as a simple reference when making branch statements for the different events we receive. An example of usage for one of these utility classes, `SubstrateEvents` can be seen below: - - - -```csharp -using Enjin.Platform.Sdk; - -IEventListener listener = /* Create event listener */ -string[] events = { SubstrateEvents.CollectionCreated }; - -service.RegisterListenerIncludingEvents(listener, events); -``` - - -```cpp -#include "EnjinPlatformSdk/IEventListener.hpp" -#include "EnjinPlatformSdk/SubstrateEvents.hpp" -#include -#include - -using namespace enjin::platform::sdk; -using namespace std; - -EventListenerPtr listener = /* Make pointer containing event listener */ -std::set events = { SubstrateEvents::CollectionCreated }; - -service->RegisterListenerIncludingEvents(listener, events); -``` - - - -#### Unregistering a Listener - -To unregister a listener from the event service, we need only pass the listener instance to the service's unregister method as shown below: - - - -```csharp -// Passing an event listener instance -service.UnregisterListener(listener); -``` - - -```cpp -// Passing an event listener reference -service->UnregisterListener(*listener); // Reference from pointer -``` - - - -We may also unregister all listeners from the service by calling the unregister all method as so: - - - -```csharp -service.UnregisterAllListeners(); -``` - - -```cpp -service->UnregisterAllListeners(); -``` - - - -After a listener is unregistered, the service will also update the `IEventRegistration` we received while registering our listener, so that the registration now returns `false` for its `IsRegistered` getter. - -### Event Subscription - -After setting up our event listener we now need to manage which event channels we want our service to listen to for it to pull events from. This enables us to have our service only listen in on channels necessary for our application's current needs, such as the wallet channel for a connected user, updates to a particular collection, or the progression of a transaction. - -#### Subscribing - -To subscribe to an event channel, we need to pass the channel name to the subscribe method, as shown below: - - - -```csharp -using System.Threading.Tasks; - -string channelName = ""; -Task task = service.SubscribeAsync(channelName); -``` - - -```cpp -#include -#include - -using namespace std; - -string channelName = ""; -future fut = service->SubscribeAsync(channelName); -``` - - - -Once subscribed, the event service will pass along any event broadcasted on the given channel to our registered listeners, so long as said listeners do not exclude the events. - -#### Unsubscribing - -To unsubscribe from an event channel, we may pass the same channel name we used to subscribe, as shown below: - - - -```csharp -using System.Threading.Tasks; - -string channelName = ""; -Task task = service.UnsubscribeAsync(channelName);; -``` - - -```cpp -#include -#include - -using namespace std; - -string channelName = ""; -future fut = service->UnsubscribeAsync(channelName); -``` - - - -We may also unsubscribe from all channels by calling the relevant method. - - - -```csharp -using System.Threading.Tasks; - -Task task = service.UnsubscribeAllAsync(); -``` - - -```cpp -#include - -using namespace std; - -future fut = service->UnsubscribeAllAsync(); -``` - - - -#### Monitoring the Service - -The event service also provides means to monitor its state through events. The following code shows the different events that may be used to receive notifications regarding state changes within the service. - - - -```csharp -// Notifies that the service has connected to a server -service.OnConnected += (sender, _) => { /* ... */ }; - -// Notifies that the service has disconnected froma server -service.OnDisconnected += (sender, _) => { /* ... */ }; - -// Notifies that the service's connection state has updated -service.OnConnectionStateChanged += (sender, state) => { /* ... */ }; - -// Notifies that the service has subscribed to an event channel -service.OnSubscribed += (sender, channelName) => { /* ... */ }; -``` - - -```cpp -PusherEventService::Builder() - // Notifies that the service has connected to a server - .SetOnConnectedHandler([]() { - /* ... */ - }) - // Notifies that the service has disconnected froma server - .SetOnDisconnectedHandler([]() { - /* ... */ - }) - // Notifies that the service's connection state has updated - .SetOnConnectionStateChangedHandler([](ConnectionState state) { - /* ... */ - }) - // Notifies that the service has subscribed to an event channel - .SetOnSubscribedHandler([](const string& channelName) { - /* ... */ - }); -``` - - diff --git a/docs/02-guides/01-platform/04-software-development-kit/04-software-development-kit.md b/docs/02-guides/01-platform/04-software-development-kit/04-software-development-kit.md index 72a809e..13190ed 100644 --- a/docs/02-guides/01-platform/04-software-development-kit/04-software-development-kit.md +++ b/docs/02-guides/01-platform/04-software-development-kit/04-software-development-kit.md @@ -4,17 +4,17 @@ slug: "../software-development-kit" description: "Get started with the Enjin SDK, offering comprehensive developer tools to integrate blockchain technology into your apps and games with ease." --- -:::warning SDKs are not yet available -The C# and C++ SDK content on this page is out of date and **will not work against the current Enjin Platform API**. This page will be updated once new SDKs are published. Until then, see [How to Use GraphQL](/01-getting-started/05-using-enjin-api/01-how-to-use-graphql.md) and the [API Reference](/03-api-reference/03-api-reference.md) for the current API shapes. +:::info C++ SDK coming soon +The C++ examples throughout this section target an older version of the Enjin Platform and won't work against the current API. An updated C++ SDK is on the way — for now, use the C# SDK or the GraphQL examples. ::: The Enjin Platform SDKs provide an API for communicating with the Enjin Platform. -The Enjin Platform SDKs provide a framework that developers can use on their desired programming language as it allows games and apps to interact with the Enjin API without the need of building a bridge between your application and our API requests, the Enjin SDKs facilitate the usage of listening and processing of events emitted by the Enjin Platform, which helps us deliver a better user experience in our application and eliminate unnecessary API requests we would otherwise make to the Enjin Platform. +The Enjin Platform SDKs give developers a native, strongly-typed way to interact with the Enjin Platform's GraphQL API in their language of choice, without having to hand-write queries or build a bridge between your application and our API. This lets games and apps query on-chain data and submit transactions directly, with the request building, sending, and response handling all handled for you. ## SDK Libraries -| Library | Link | -| :------ | :------------------------------------------------------------------------- | -| C# | [/enjin/platform-csharp-sdk](https://github.com/enjin/platform-csharp-sdk) | -| C++ | [/enjin/platform-cpp-sdk](https://github.com/enjin/platform-cpp-sdk) | +| Library | Package | Source | +| :------ | :----------------------------------------------------------------------------------------------------- | :------------------------------------------------------------------------- | +| C# | [Enjin.Platform.Sdk on NuGet](https://www.nuget.org/packages/Enjin.Platform.Sdk) | [/enjin/platform-csharp-sdk](https://github.com/enjin/platform-csharp-sdk) | +| C++ | _Coming soon_ | [/enjin/platform-cpp-sdk](https://github.com/enjin/platform-cpp-sdk) | diff --git a/docs/02-guides/01-platform/04-software-development-kit/_logger.md b/docs/02-guides/01-platform/04-software-development-kit/_logger.md index d756953..59b6f72 100644 --- a/docs/02-guides/01-platform/04-software-development-kit/_logger.md +++ b/docs/02-guides/01-platform/04-software-development-kit/_logger.md @@ -70,7 +70,7 @@ The `ILogger` interface uses log levels to communicate the type of message being ## Platform Client Logging -To setup logging for the `PlatformClient` we may pass an `ILogger` instance to its builder as shown below: +To set up logging for the `PlatformClient`, pass an `ILogger` instance to its constructor as shown below: @@ -79,8 +79,7 @@ using Enjin.Platform.Sdk; ILogger logger = /* Instantiate class implementing ILogger */ -// Using a PlatformClient builder -builder.SetLogger(logger); +using var client = new PlatformClient(logger: logger); ``` @@ -108,7 +107,7 @@ The SDK also offers HTTP logging options for its built-in platform client. There | Headers | Logs HTTP headers in addition to topical information. | | Body | Logs the full request/response. | -To enable HTTP traffic logging, we must provide an `ILogger` instance and our desired HTTP log level when building the client as shown below: +To enable HTTP traffic logging, provide an `ILogger` instance and your desired HTTP log level when constructing the client as shown below: @@ -116,11 +115,9 @@ To enable HTTP traffic logging, we must provide an `ILogger` instance and our de using Enjin.Platform.Sdk; ILogger logger = /* Instantiate class implementing ILogger */ -HttpLogLevel level = /* Choose a HTTP log level */ +HttpLogLevel level = HttpLogLevel.Body; // Choose a HTTP log level -// Using a PlatformClient builder -builder.SetLogger(logger) - .SetHttpLogLevel(level); +using var client = new PlatformClient(logger: logger, httpLogLevel: level); ``` @@ -139,32 +136,3 @@ builder.SetLogger(logger) ``` - -### Event Service Logging - -To setup logging for the `PusherEventService` we may pass an `ILogger` instance to its builder as shown below: - - - -```csharp -using Enjin.Platform.Sdk; - -ILogger logger = /* Instantiate class implementing ILogger */ - -// Using a PusherEventService builder -builder.SetLogger(logger); -``` - - -```cpp -#include "EnjinPlatformSdk/ILogger.hpp" - -using namespace enjin::platform::sdk; - -LoggerPtr logger = /* Make pointer containing ILogger implementation */ - -// Using a PusherEventService builder -builder.SetLogger(logger); -``` - - diff --git a/docs/05-enjin-platform/05-enjin-platform.md b/docs/05-enjin-platform/05-enjin-platform.md index 3cefd13..057e7ca 100644 --- a/docs/05-enjin-platform/05-enjin-platform.md +++ b/docs/05-enjin-platform/05-enjin-platform.md @@ -44,7 +44,7 @@ The Enjin Platform is packed with features designed to make your life as a devel - **Single endpoint, multi-chain routing** — reach both Enjin Mainnet and Canary Testnet, and target either the Matrixchain or the Relaychain, through one URL by changing a single argument on the request. - **Managed wallet creation** — create platform-side wallets for your end users with [`CreateManagedWallet`](/02-guides/01-platform/02-managing-users/03-using-managed-wallets.md), and have your project's Wallet Daemon sign on their behalf. -- **Wallet linking and transaction requests** — [link a player's Enjin Wallet](/02-guides/01-platform/02-managing-users/01-connecting-user-wallets/01-sending-wallet-requests.md) to your application and send transaction-signing prompts directly to it. Use it for ownership verification, in-app authentication, or approving in-game actions like consuming items, listing on the marketplace, or staking ENJ. +- **Wallet linking and transaction requests** — link a player's Enjin Wallet to your application and send transaction-signing prompts directly to it. Use it for ownership verification, in-app authentication, or approving in-game actions like consuming items, listing on the marketplace, or staking ENJ. - **Asset transfer and management** — transfer, mint, freeze, burn, and infuse tokens through the API. Bundle multiple actions into a single `CreateBatchTransaction` to commit them atomically. - **Marketplace** — create [fixed-price, auction, and offer listings](/03-api-reference/02-mutations/06-marketplace-mutations.md), place bids, and answer counter-offers. - **Fuel Tank dispatching** — dispatch transactions through an existing [Fuel Tank](/04-enjin-blockchain/03-enjin-matrixchain/02-fuel-tank-pallet.md) to subsidize transaction fees for your users.