If your knowledge base is private or restricted to specific users, you can use JWT (JSON Web Tokens) to securely control access to the embedded Document360 widget. This setup ensures that only authenticated users can view articles through the widget, without requiring them to sign in separately.
With JWT authentication, your system handles login and token generation. The widget then uses that token to fetch content based on each user's access level.
In this article, you'll learn:
How JWT authentication works for widgets
How to configure JWT settings in the Document360 portal
How to set up your backend to generate and return secure tokens
How to test your JWT configuration using Postman
How JWT authentication for widgets works
JWT is the recommended approach when your knowledge base visibility is set to Private or Mixed. In these cases, readers must be authenticated before the widget can display content. JWT handles this silently — readers never see a separate login screen.
Use JWT when:
Your knowledge base is restricted to specific users or reader groups
You want single sign-on access to the widget without a separate login prompt
You need to control which content each reader sees based on their group membership
Visual overview of the authentication process
This flow diagram shows what happens when a user loads a widget on your website. The Document360 widget communicates with your system to get a secure token before displaying content.
Sequence diagram of the authentication process

This sequence diagram outlines the technical flow between the user's browser, your backend, and Document360's identity server to generate and validate the JWT token.
The steps below explain the complete JWT authentication flow:
User visits your website, where the Document360 widget is embedded.
The widget sends a silent request to your authentication endpoint (token endpoint) configured in the widget settings.
Your backend sends a request to Document360 with the required credentials (client ID, client secret) and reader details.
Document360 validates the request and returns a signed JWT to your backend.
Your backend sends the token back to the widget.
The widget uses this token to fetch and display articles that the reader has access to.
When the token expires, the widget automatically requests a new one (if configured to do so).
NOTE
The above flow happens behind the scenes. Readers never see a login screen for the widget.
Before you begin
Before configuring JWT for the widget, ensure the following:
You have a Project Owner or Admin role in Document360.
You have at least one knowledge base widget already created. If not, create one first from Connections > Knowledge base widget.
Your knowledge base project visibility is set to Private or Mixed. JWT is not required for public projects.
You have access to your backend server to implement the authentication endpoint. The code example in this article uses C#, but the same principles apply to any server-side language.
At least one reader group is configured in your project. The widget requires at least one valid reader group ID to render content.
Enable and configure JWT for the widget
You can implement an authentication configuration for the widget using JWT, ensuring a secure environment for private and mixed projects.
Navigate to Connections (⊞) > Knowledge base widget in the left navigation bar.
The list of widgets will appear.
Hover over the desired widget you want to configure and click the Edit (✎) icon.
In the Configure & connect tab, navigate to the JWT accordion and turn on the JWT Enable toggle.

Client ID: The client ID will be your project's ID.
Widget ID: Since multiple widgets may exist, a Widget ID is provided for their unique purposes.
Token endpoint: A token endpoint is an HTTP endpoint that allows you to obtain an access token given an authorization code.
Client secret: Click Regenerate to generate the client secret. You need to save this for future purposes, and the same client secret will apply to all widgets in the future.
NOTE
The client secret is shared across all JWT-enabled widgets and chatbots in the project. If you regenerate the secret, you must update the new secret in all JWT-configured widgets and applications to prevent authentication failures.The client secret is shown only during generation and is not stored in Document360, so save it securely.
e. Authorize URL: Paste the authorized URL from your knowledge base widget webpage.
Click Save to apply changes.
Embed the authorized URL within your code and paste it into the script section on your webpage. This will implement a secure, authenticated widget that prevents unauthorized third-party access.
Implementing the auth endpoint
After configuring JWT in the portal, you'll need to set up an authentication endpoint in your backend application. This endpoint receives a request from the widget and returns a valid token in response.
The example below shows how to implement the endpoint in C#. The same logic applies to other server-side languages such as Node.js or Python — adapt the HTTP client and JSON serialization libraries as needed.
/// <summary>
/// Endpoint to authenticate a user, generate a JWT token from Document360,
/// and return it to the widget.
/// </summary>
[HttpGet]
[Route("authenticate")]
public async Task<IActionResult> WidgetAuthentication(string id)
{
// Ensure the user is authenticated in your application
if (!HttpContext.User.Identity.IsAuthenticated)
{
return Unauthorized(new { message = "User is not authenticated." });
}
// Define configuration values
var clientData = new ClientDetails
{
ClientId = "{Client ID}", // Replace with your project's client ID
Secret = "{Client secret}", // Replace with your generated client secret
TokenEndpoint = "{Token endpoint}", // Replace with the token endpoint URL from Document360
WidgetId = "{Widget ID}", // Replace with your widget ID
SecurityGroupIds = "group1,group2", // Replace with comma-separated reader group IDs
TokenValidity = 900 // Token validity in seconds (300–86400)
};
// Return 404 if configuration is missing
if (clientData == null)
{
return NotFound(new { message = "Client configuration not found." });
}
// Convert the comma-separated reader group IDs into a list
List<string> readerGroupIds = null;
if (!string.IsNullOrEmpty(clientData.SecurityGroupIds))
{
readerGroupIds = clientData.SecurityGroupIds
.Split(',')
.Select(c => c.Trim())
.ToList();
}
// Prepare the payload with user and configuration details
var payload = new
{
username = "{Username}", // Replace with actual user data if available
firstName = "{First name}",
lastName = "{Last name}",
emailId = "{Email address}",
readerGroupIds = readerGroupIds,
tokenValidity = clientData.TokenValidity,
widgetId = clientData.WidgetId,
projectId = clientData.ClientId
};
var payloadString = JsonConvert.SerializeObject(payload);
try
{
// Send request to Document360 token endpoint
var result = await client.RequestTokenAsync(new TokenRequest
{
Address = clientData.TokenEndpoint,
ClientId = clientData.ClientId,
ClientSecret = clientData.Secret,
GrantType = "Widget",
Parameters =
{
{ "payload", payloadString },
{ "id", clientData.ClientId }
}
});
// Return the access token to the widget
return Ok(new
{
accessToken = result.AccessToken,
expiresIn = result.ExpiresIn
});
}
catch (Exception ex)
{
// Handle unexpected errors (optional)
return StatusCode(500, new
{
message = "Failed to generate token.",
details = ex.Message
});
}
}
The
tokenValidityvalue is set in seconds. It must be between 300 seconds (5 minutes) and 86,400 seconds (1440 minutes). If you enter a value outside this range, the system automatically adjusts it to the nearest valid value. For example, if you settokenValidityto 60 seconds (1 minute), the system increases it to the minimum allowed value of 300 seconds (5 minutes). A value of 900 seconds (15 minutes) is a reasonable default for most use cases — shorter values improve security but increase backend load.The widget requires at least one valid reader group ID to render content. Include these as a comma-separated list in the
readerGroupIdsparameter of the JWT payload.
Test your JWT widget configuration using Postman
After setting up JWT in the Document360 portal and implementing your backend authentication endpoint, you can use Postman to confirm that your configuration works as expected.
This test simulates what the widget does: it sends a request to your backend to fetch a valid JWT.
Set up the test in Postman
Launch Postman.
Select + New tab or click New > HTTP request.
Set the method to POST.
In the request URL field, enter the full URL of your backend endpoint.
Example:
https://yourdomain.com/authenticateGo to the Authorization tab.
Under Type, select Basic Auth.
Enter the following credentials:
Username: Your Client ID from the Document360 portal.
Password: Your Client Secret (generated when you created the JWT).
Next, to set the request body, go to the Body tab.
Select raw.
Choose JSON from the dropdown on the right.
Paste the following example JSON into the body:
{ "username": "john.doe", "firstName": "John", "lastName": "Doe", "emailId": "john.doe@example.com", "readerGroupIds": ["group1", "group2"], "tokenValidity": 900, "widgetId": "your-widget-id", "projectId": "your-project-id" }Replace the values with actual data from your app and Document360 configuration.
If the request is successful, you'll receive a JSON response like the following:
{
"accessToken": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...",
"expiresIn": 900
}accessToken: This is the signed JWT that the widget will use to authorize the reader.expiresIn: Token validity in seconds (15 minutes = 900 seconds).
After sending the request, check that the response status is 200 OK, indicating a successful request. The response body should contain a valid accessToken, which is the signed JWT used by the widget. Additionally, confirm that the expiresIn value matches the expected token validity duration in seconds (for example, 900 seconds for 15 minutes).
If all these values appear correctly, your JWT setup is working as intended.
Troubleshooting
If the Postman request or the live widget fails to return a valid token, refer to the common issues below.
Symptom | Likely cause | What to do |
|---|---|---|
Response status is 401 Unauthorized | Incorrect Client ID or Client Secret in the request | Verify the credentials in the JWT section of the widget configuration. If you recently regenerated the secret, update it everywhere it is used. |
Response status is 400 Bad Request | Malformed payload or missing required fields | Check that all required fields ( |
Widget loads but displays no content | No valid reader group IDs in the token payload | Confirm that the |
Token is generated but the widget shows an error | Authorize URL mismatch | Ensure the Authorize URL in the portal matches the exact URL of the webpage where the widget is embedded. |
Authentication fails after regenerating the client secret | Old client secret still in use in one or more integrations | Update the new client secret in all JWT-configured widgets, chatbots, and backend applications that use it. |
Next steps
After your JWT configuration is verified and working, you can:
Embed the widget on your website by adding the script snippet to your webpage's script section.
Manage reader access by updating reader group assignments in Connections > Readers.
Customize the widget's appearance and behavior from the Customize tab in the widget editor.