From 01f7228f6f3ffb7a5816edbc96523c3e301c4d5c Mon Sep 17 00:00:00 2001 From: Rafael Bradley Date: Tue, 6 Oct 2026 23:12:12 -0300 Subject: [PATCH] Update docs --- content/guides/tune-a-protection-profile.mdx | 10 +-- content/guides/write-your-own-sdk.mdx | 24 +++--- content/quick-start.mdx | 78 ++++++++++---------- content/sdks/javascript.mdx | 18 ++--- content/sdks/python.mdx | 40 +++++----- content/sdks/react.mdx | 18 ++--- content/sdks/rust.mdx | 30 ++++---- 7 files changed, 107 insertions(+), 111 deletions(-) diff --git a/content/guides/tune-a-protection-profile.mdx b/content/guides/tune-a-protection-profile.mdx index 78ca11f..f8ce798 100644 --- a/content/guides/tune-a-protection-profile.mdx +++ b/content/guides/tune-a-protection-profile.mdx @@ -1,13 +1,13 @@ --- -title: Tune a Protection Profile +title: Tune a Policy description: - Learn how to tune your protection profiles to better protect your application while enhancing - your users' experiences. + Learn how to tune your policies to better protect your application while enhancing your users' + experiences. --- ### Throttling Windows -The first of all settings a protection profile has are the throttling windows. Throttling windows -rate-limit challenge issuance. +The first of all settings a policy has are the throttling windows. Throttling windows rate-limit +challenge issuance. ![Screenshot](/images/screenshot-dashboard-throttling-windows.png) diff --git a/content/guides/write-your-own-sdk.mdx b/content/guides/write-your-own-sdk.mdx index e75127a..b9d3209 100644 --- a/content/guides/write-your-own-sdk.mdx +++ b/content/guides/write-your-own-sdk.mdx @@ -37,11 +37,11 @@ Duckity serves challenges through the duckling API. It's separate from the manag a specialized backend. The hosted endpoint of such version is at `https://api.duckity.com/d1`. Subsequent versions of this API will be named `d2`, `d3`, and so on. -To get a challenge, you need to be able to make HTTP requests and a protection profile ID. Requests -to get challenges look like follows: +To get a challenge, you need to be able to make HTTP requests and a policy ID. Requests to get +challenges look like follows: ```http -POST /d1/challenges/{protection_profile_id}/issue HTTP/1.1 +POST /d1/challenges/{policy_id}/issue HTTP/1.1 Host: api.duckity.com Accept: application/json ``` @@ -89,8 +89,8 @@ X-RateLimit-Penalty-Resets-In: 500 } ``` -Other errors, like an invalid protection profile, will result in a response of similar body -structure and with the corresponding status code. +Other errors, like an invalid policy, will result in a response of similar body structure and with +the corresponding status code. ## Decoding the Challenge [step] @@ -109,7 +109,7 @@ type Challenge = { challenge_id: string; // The challenge's unique ID. 21-character NanoID using the default alphabet. ip: string; // The IP of the client the challenge was issued for. Only this client may submit a solution for validation. timestamp: number; // The milliseconds since UNIX epoch when the challenge was issued. - protection_profile_id: string; // The ID of the protection profile this challenge was issued for. 21-character NanoID using the default alphabet. + policy_id: string; // The ID of the policy this challenge was issued for. 21-character NanoID using the default alphabet. n: number[]; // An array of 32-bit unsigned digits, most significant digit first. The Wesolowski VDF N parameter. x: number[]; // An array of 32-bit unsigned digits, most significant digit first. The Wesolowski VDF X parameter. t: number; // The Wesolowski VDF T parameter. @@ -128,8 +128,8 @@ These code pieces implement the decoding as a reference. ip: string; // The unix timestamp, in milliseconds, in which the challenge was issued. timestamp: number; - // The ID of the protection profile this challenge was issued for. - protection_profile_id: string; + // The ID of the policy this challenge was issued for. + policy_id: string; // The unsigned 32-bit digits of the N Wesolowski VDF parameter, most significant digit first. n: number[]; // The unsigned 32-bit digits of the X Wesolowski VDF parameter, most significant digit first. @@ -172,8 +172,8 @@ These code pieces implement the decoding as a reference. """The IP of the client this challenge was issued for.""" timestamp: int """The UNIX timestamp in milliseconds at which this challenge was issued.""" - protection_profile_id: str - """The ID of the protection profile this challenge was issued for.""" + policy_id: str + """The ID of the policy this challenge was issued for.""" n: list[int] """The unsigned 32-bit digits of the N Wesolowski VDF parameter, most significant digit first.""" x: list[int] @@ -210,7 +210,7 @@ These code pieces implement the decoding as a reference. id=data["challenge_id"], ip=data["ip"], timestamp=data["timestamp"], - protection_profile_id=data["protection_profile_id"], + policy_id=data["policy_id"], n=data["n"], x=data["x"], t=data["t"] @@ -1078,7 +1078,7 @@ the Duckling API to check whether the token is valid. The request looks like follows: ```http -POST /d1/{protection_profile_id}/validate HTTP/1.1 +POST /d1/{policy_id}/validate HTTP/1.1 Host: api.duckity.com Authorization: Bearer Accept: application/json diff --git a/content/quick-start.mdx b/content/quick-start.mdx index bfeaf9a..1875961 100644 --- a/content/quick-start.mdx +++ b/content/quick-start.mdx @@ -24,21 +24,21 @@ now have your first application created. origins. If your application is not a web app, you can leave the CORS origins empty. -## Create a Protection Profile [step] +## Create a Policy [step] Applications commonly have multiple features that need to be protected. For example, you may have a -signup form and a login form with different protection needs. For each, you'll create one -**protection profile** with settings tuned to each feature's specific needs. +signup form and a login form with different protection needs. For each, you'll create one **policy** +with settings tuned to each feature's specific needs. -Each application needs at least one protection profile to work. To create your first one, press the -**+ Create Protection Profile** button. +Each application needs at least one policy to work. To create your first one, press the **+ Create +Policy** button. Set the name to the name of the feature you'll be protecting, like "Sign-up Form" or "Add Friend". This is for you to recognize it later, it won't be displayed to your users. Once you're done filling -it, press on **✓ Create Protection Profile**. +it, press on **✓ Create Policy**. -Copy your protection profile's ID using the button at the top right corner, that's all you'll need -to integrate it into your application. +Copy your policy's ID using the button at the top right corner, that's all you'll need to integrate +it into your application. Don't worry about all the settings displayed for now, you'll learn to tune them later. @@ -46,9 +46,9 @@ to integrate it into your application. ## Install a Client SDK [step] -To integrate your protection profile into your application, you'll need to install a client SDK in -your client and validate solution tokens from your server. This is very simple to do and will take -you little to no time. +To integrate your policy into your application, you'll need to install a client SDK in your client +and validate solution tokens from your server. This is very simple to do and will take you little to +no time. @@ -91,7 +91,7 @@ you little to no time. ```ts async function handleSubmit(e) { e.preventDefault(); - const solution: string = await duckity.solve(PROTECTION_PROFILE_ID); + const solution: string = await duckity.solve(POLICY_ID); // Send it to your backend. } ``` @@ -143,7 +143,7 @@ you little to no time. import { useChallenge } from "@duckity/react"; function MyComponent() { - const duckity = useChallenge(process.env.NEXT_PUBLIC_DUCKITY_PROTECTION_PROFILE_ID); + const duckity = useChallenge(process.env.NEXT_PUBLIC_DUCKITY_POLICY_ID); } ``` @@ -152,7 +152,7 @@ you little to no time. import { useChallenge } from "@duckity/react"; function MyComponent() { - const duckity = useChallenge(import.meta.env.VITE_DUCKITY_PROTECTION_PROFILE_ID); + const duckity = useChallenge(import.meta.env.VITE_DUCKITY_POLICY_ID); } ``` @@ -165,14 +165,14 @@ you little to no time. export async function loader() { return json({ ENV: { - DUCKITY_PROTECTION_PROFILE_ID: process.env.DUCKITY_PROTECTION_PROFILE_ID, + DUCKITY_POLICY_ID: process.env.DUCKITY_POLICY_ID, }, }); } function MyComponent() { const data = useLoaderData(); - const duckity = useChallenge(data.ENV.DUCKITY_PROTECTION_PROFILE_ID); + const duckity = useChallenge(data.ENV.DUCKITY_POLICY_ID); } ``` @@ -181,7 +181,7 @@ you little to no time. import { useChallenge } from "@duckity/react"; function MyComponent() { - const duckity = useChallenge(process.env.GATSBY_DUCKITY_PROTECTION_PROFILE_ID); + const duckity = useChallenge(process.env.GATSBY_DUCKITY_POLICY_ID); } ``` @@ -190,7 +190,7 @@ you little to no time. import { useChallenge } from "@duckity/react"; function MyComponent() { - const duckity = useChallenge(process.env.EXPO_PUBLIC_DUCKITY_PROTECTION_PROFILE_ID); + const duckity = useChallenge(process.env.EXPO_PUBLIC_DUCKITY_POLICY_ID); } ``` @@ -199,7 +199,7 @@ you little to no time. import { useChallenge } from "@duckity/react"; function MyComponent() { - const duckity = useChallenge(import.meta.env.PUBLIC_DUCKITY_PROTECTION_PROFILE_ID); + const duckity = useChallenge(import.meta.env.PUBLIC_DUCKITY_POLICY_ID); } ``` @@ -270,14 +270,14 @@ you little to no time. - Solving a challenge only requires your protection profile ID. + Solving a challenge only requires your policy ID. ```py import duckity - solution: str = await duckity.solve(PROTECTION_PROFILE_ID) + solution: str = await duckity.solve(POLICY_ID) ``` The CPU-intensive part of solving the challenge is done in a @@ -289,7 +289,7 @@ you little to no time. import duckity - solution: str = asyncio.run(duckity.solve(PROTECTION_PROFILE_ID)) + solution: str = asyncio.run(duckity.solve(POLICY_ID)) ``` The CPU-intensive part of solving the challenge is done in a @@ -303,7 +303,7 @@ you little to no time. ```py import requests - solution: str = asyncio.run(duckity.solve(PROTECTION_PROFILE_ID)) + solution: str = asyncio.run(duckity.solve(POLICY_ID)) requests.post( "https://api.example.com/login", @@ -338,7 +338,7 @@ you little to no time. To get and solve a challenge, use `duckity::solve()` like follows: ```rs - let solution: str = duckity::solve(PROTECTION_PROFILE_ID).await?; + let solution: str = duckity::solve(POLICY_ID).await?; ``` That's it! Once you have your solution token, you can send it over to your backend for @@ -410,7 +410,7 @@ Once you have a solution token in your server, validating it is quite easy. solution, // The solution token submitted by the client. clientIp, // The IP address of the client that submitted the solution. applicationSecret, // Your application's secret. Get it from the dashboard. - protectionProfileId, // The protection profile ID used to generate the challenge. + policyId, // The policy ID used to generate the challenge. ); ``` @@ -449,10 +449,10 @@ Once you have a solution token in your server, validating it is quite easy. solution: str # The solution token submitted by the client. client_ip: str # The IP address of the client that submitted the solution. application_secret: str # Your application's secret. Get it from the dashboard. - protection_profile_id: str # The protection profile ID used to generate the challenge. + policy_id: str # The policy ID used to generate the challenge. is_valid: bool = await duckity.validate( - solution, client_ip, application_secret, protection_profile_id + solution, client_ip, application_secret, policy_id ) ``` @@ -465,10 +465,10 @@ Once you have a solution token in your server, validating it is quite easy. solution: str # The solution token submitted by the client. client_ip: str # The IP address of the client that submitted the solution. application_secret: str # Your application's secret. Get it from the dashboard. - protection_profile_id: str # The protection profile ID used to generate the challenge. + policy_id: str # The policy ID used to generate the challenge. is_valid: bool = asyncio.run( - duckity.validate(solution, client_ip, application_secret, protection_profile_id) + duckity.validate(solution, client_ip, application_secret, policy_id) ) ``` @@ -493,7 +493,7 @@ Once you have a solution token in your server, validating it is quite easy. solution, // The solution token submitted by the client. client_ip, // The IP address of the client that submitted the solution. APPLICATION_SECRET, // Your application's secret. Get it from the dashboard. - PROTECTION_PROFILE_ID // The protection profile ID used to generate the challenge. + POLICY_ID // The policy ID used to generate the challenge. ) .await?; ``` @@ -506,7 +506,7 @@ Once you have a solution token in your server, validating it is quite easy. hand by making the HTTP request by hand instead. ```http - POST /d1/challenges/{protection_profile_id}/validate HTTP/1.1 + POST /d1/challenges/{policy_id}/validate HTTP/1.1 Host: api.duckity.com Accept: application/json Content-Type: application/json @@ -548,8 +548,8 @@ Once you have a solution token in your server, validating it is quite easy. Content-Type: application/json { - "title": "Protection Profile Not Found", - "message": "The protection profile ID you specified was not found." + "title": "Policy Not Found", + "message": "The policy ID you specified was not found." } ``` @@ -594,7 +594,7 @@ Once you have a solution token in your server, validating it is quite easy. Note that status codes are related to server actions, not to client actions. An invalid solution token submitted by the client will return `200` because the token was validated successfully (even if the result was that it was invalid), while a wrong application secret - or an incorrect protection profile ID will return `4xx` status codes. + or an incorrect policy ID will return `4xx` status codes. @@ -608,11 +608,7 @@ combine settings to produce a more powerful setup, check out the following guide configuration by configuration to teach you how to configure the parameters you need to suit your application's needs. -} -> - Learn how to tune your protection profiles to better protect your application while enhancing - your users' experiences. +}> + Learn how to tune your policies to better protect your application while enhancing your users' + experiences. diff --git a/content/sdks/javascript.mdx b/content/sdks/javascript.mdx index a9e2e68..15f94a9 100644 --- a/content/sdks/javascript.mdx +++ b/content/sdks/javascript.mdx @@ -23,8 +23,8 @@ Before you can integrate Duckity into your application, you'll need to have the 1. An application, 2. CORS origins set up pointing to your application's origin(s), -3. At least one protection profile created in that application, and -4. The ID of the protection profiles to use +3. At least one policy created in that application, and +4. The ID of the policies to use If you're missing either of those, head over to the [Duckity Dashboard](https://app.duckity.com) or read the [Quick Start](/quick-start) guide to learn how to set those up. @@ -78,7 +78,7 @@ Once you have the SDK installed, you can request a challenge whenever you need i import duckity from "@duckity/js"; /// Slow! Runs in a web worker, yet don't let it block code below unless necessary. -let solution: string = await duckity.solve(PROTECTION_PROFILE_ID); +let solution: string = await duckity.solve(POLICY_ID); ``` ### Validate a Challenge [step] @@ -86,18 +86,18 @@ let solution: string = await duckity.solve(PROTECTION_PROFILE_ID); Send the solution token to your backend server any way you want. A header or parameter in a JSON field will work. -Once in the server, you'll need the client's IP, their submitted solution token, the protection -profile's ID, and the application secret. +Once in the server, you'll need the client's IP, their submitted solution token, the policy's ID, +and the application secret. ```ts import * as duckity from "@duckity/js"; let applicationSecret: string; -let protectionProfileId: string; +let policyId: string; let clientIp: string; let solution: string; -let isValid = await duckity.validate(solution, clientIp, applicationSecret, protectionProfileId); +let isValid = await duckity.validate(solution, clientIp, applicationSecret, policyId); if (isValid) { // Keep processing the request. @@ -144,7 +144,7 @@ wait.