Authenticated Chat (Intranet)

Publish the chatbot inside your intranet, customer portal or web system: the chat automatically recognizes who the logged-in user is, without asking for another login.

Intranet

What it is

The Authenticated Chat (Intranet) is a way to publish the chatbot inside a platform where users are already logged in (intranet, customer portal, web system, ERP, etc.).

The chat automatically recognizes who the user is, without asking them to log in again, and keeps each person’s conversation history separate and secure.


1. When to use it

Publication typeWhen to use
Public (Script or Link)Open websites, landing pages — any anonymous visitor can talk to the bot.
Intranet (Authenticated Access)Systems where the user has already logged in to your platform. The chat inherits their identity (name, email and ID from your system).
Login and Password AccessRestricted sites where you want to protect the chat with a shared password.

Use Intranet mode when you want:

  • Support to start already knowing who the user is (no identification form);
  • Conversation history to be tied to the user ID in your system;
  • No one to be able to impersonate another user or see third-party conversations.

2. Setting up on the platform

  1. Go to your ProjectChatbots menu → select the desired chatbot.
  2. Click the Publish tab and then the Sites sub-tab.
  3. Click Add.
  4. In the “Publish on Websites or Web Systems” modal, fill in:
    • Publication name: an internal name to identify this connection (e.g., “Customer Portal”);
    • Integration type: select “Intranet (Authenticated Access)”.
  5. Click Save Publication.

Done! The new connection appears in the Publications list.


3. What the platform shows after creation

When you expand the created publication, you will see two essential pieces of data and code examples:

3.1 Project ID

Your project’s public identifier. It can safely appear in the page code.

3.2 Secret Token (Intranet)

The integration’s secret key. It is what your platform’s server uses to authenticate users in the chat.

⚠️ Never put the Secret Token in browser code (HTML/JavaScript). It must stay only in your application’s backend. If it leaks, anyone could generate access on behalf of your users.

3.3 Code examples

The card shows a backend call example and a frontend script example. They correspond to Mode A of integration — there are two ways to place the chat in your platform, explained in section 5.


4. How everything connects

┌─────────────────────┐   1. logged-in user    ┌──────────────────────┐
│  User on your       │ ─────────────────────▶ │  Your platform's     │
│  platform           │                        │  backend             │
└─────────────────────┘                        └──────────┬───────────┘
                                                          │ 2. POST /intranet-auth
                                                          │    (Secret Token + user data)
                                                          ▼
                                               ┌──────────────────────┐
                                               │  Caramelo API        │
                                               │  → validates secret  │
                                               │  → creates/identifies│
                                               │    the contact       │
                                               │  → returns the token │
                                               └──────────┬───────────┘
                                                          │ 3. real_time_access_token (24h)
                                                          ▼
                                               ┌──────────────────────┐
                                               │  Your HTML page      │
                                               │  receives the token  │
                                               │  and loads the script│
                                               └──────────┬───────────┘
                                                          │ 4. chat opens already identified
                                                          ▼
                                               ┌──────────────────────┐
                                               │  Chatbot with that   │
                                               │  user's history      │
                                               └──────────────────────┘

In summary:

  1. The user logs in normally on your platform;
  2. Your backend calls the Caramelo API with the Secret Token and the user’s data;
  3. The API returns a temporary token exclusive to that user (real_time_access_token field);
  4. Your page receives this token and passes it to the chat script (secure_connection_token parameter);
  5. The chat opens already identified, with that person’s conversation history.

📌 Heads up: one token, two names.

Where it appearsName used
In the API response (your backend receives)real_time_access_token
In the chat script (your page sends)secure_connection_token

It is the same value: your backend receives real_time_access_token and your page forwards it to the script as secure_connection_token. Throughout this guide, whenever you see secure_connection_token, read it as: “the real_time_access_token the API returned”.

💡 Tip: the token must be generated on every page load (it expires in 24 hours). Do not reuse old tokens or share the same token between different users.


5. The two integration modes

There are two ways to place the authenticated chat in your platform. Both use the same intranet-auth call on the backend — what changes is how the token reaches the chat script:

Mode A — Injected token (SSR)Mode B — On demand (Async)
Who fetches the tokenYour backend, when rendering the pageThe chat script itself, calling an endpoint on your backend
Script usedprod/index.js (starts on its own)sdk/latest/client.js (starts when you tell it to)
When the chat opensAutomatically on page loadWhen the page calls CarameloChatbotClient.start()
Token appears in the HTML?Yes, injected into the pageNo — it only travels in your endpoint’s response
Ideal forServer-rendered sites (PHP, WordPress, templates, Next.js SSR)React/SPA apps, cached/CDN pages, opening the chat only on a button click

🤔 Not sure which to choose? If your page is generated on the server on every request, use Mode A (simpler). If your application runs in the browser (React, Vue, Angular) or you want to control when the chat opens, use Mode B.

5.1 Mode A — Token injected by the server (SSR)

Step 1 — Backend: when rendering the page, your server calls the Caramelo API with the logged-in user’s data:

curl -X POST https://api.carameloai.com/api/chatbox/project/{PROJECT_ID}/intranet-auth \
  -H "Authorization: Bearer {SECRET_TOKEN}" \
  -H "Content-Type: application/json" \
  -d '{
    "external_customer_id": "user-123",
    "name": "User Name",
    "email": "user@example.com"
  }'
FieldDescription
external_customer_idRequired. The user’s unique ID in your system. It is what links the conversation history.
nameUser’s name (shown to support agents).
emailUser’s email.

Step 2 — Frontend: your server injects the returned token into the page HTML, along with the chat script:

<script>
  var carameloaiChatbot = {
    secure_connection_token: "<realtime_access_token_goes_here>",
    project_id: "YOUR_PROJECT_ID",
    pluginVersion: "PLUGIN_VERSION"
  };
</script>
<script src="https://static.carameloai.com/prod/index.js"></script>

The script loads, reads the configuration and opens the chat automatically, already identified.

5.2 Mode B — On demand (Async)

┌──────────────────┐  1. opens the page  ┌───────────────────────────┐
│  Logged-in user  │ ──────────────────▶ │  Page loads client.js     │
└──────────────────┘                     │  (nothing appears yet)    │
                                         └────────────┬──────────────┘
                                                      │ 2. CarameloChatbotClient.start()
                                                      ▼
                                         ┌───────────────────────────┐
                                         │  SDK makes a POST to YOUR │
                                         │  endpoint (same origin)   │
                                         └────────────┬──────────────┘
                                                      │ 3. your backend calls
                                                      │    intranet-auth (with the Secret)
                                                      ▼
                                         ┌───────────────────────────┐
                                         │  Token returns to browser │
                                         │  → chat opens identified  │
                                         └───────────────────────────┘

Step 1 — Backend: create an endpoint on your domain (e.g., /api/chatbot-token). It identifies the logged-in user via the session, calls intranet-auth and returns the token:

// Node.js / Express example
app.post('/api/chatbot-token', async (req, res) => {
  const user = req.user; // user already authenticated on YOUR platform
  if (!user) {
    return res.status(401).json({ error: 'unauthenticated' });
  }

  const response = await fetch(
    'https://api.carameloai.com/api/chatbox/project/YOUR_PROJECT_ID/intranet-auth',
    {
      method: 'POST',
      headers: {
        'Authorization': 'Bearer YOUR_SECRET_TOKEN', // never exposed to the browser
        'Content-Type': 'application/json'
      },
      body: JSON.stringify({
        external_customer_id: user.id,
        name: user.name,
        email: user.email
      })
    }
  );

  const data = await response.json();
  res.json({ real_time_access_token: data.real_time_access_token });
});

Step 2 — Frontend: load client.js pointing to your endpoint and start the chat whenever you want:

<script>
  var carameloaiChatbot = {
    project_id: "YOUR_PROJECT_ID",
    auth_endpoint: "/api/chatbot-token",  // endpoint on YOUR domain
    on_error: function (err) {
      console.error("Failed to start chat", err);
    }
  };
</script>
<script src="https://static.carameloai.com/sdk/latest/client.js"></script>
<script>
  // The chat only opens when you tell it to — e.g., on a button click:
  document.getElementById("open-chat").addEventListener("click", function () {
    CarameloChatbotClient.start();
  });
</script>
DirectionDetails
SDK → your endpointPOST <auth_endpoint> (no body — the user is identified by your system’s session)
Your endpoint → Caramelo APIPOST /api/chatbox/project/{PROJECT_ID}/intranet-auth with Bearer + user data
Your endpoint → SDKJSON with at least { "real_time_access_token": "..." }

6. Chat visual settings

On the same publication screen, you can also adjust the widget’s behavior (click Save after changing):

  • Chat position on the site: screen corner where the bubble appears;
  • Start and keep the conversation box open: the chat stays always open, with no close option;
  • Compact Mode: the chat takes up the smallest possible size;
  • Attention Retention: after a period of inactivity, the browser tab draws attention and the chat glows;
  • Render in a fixed spot on the page: instead of floating, the chat is displayed inside a specific <div> in your layout.

7. Frequently asked questions

Does the user need to log in again in the chat?

No. Their identity is securely transmitted by your backend — the chat already opens knowing who they are.

My application is React/SPA. Which mode should I use?

Mode B. In the browser there is no way to hide the Secret Token, so the component calls an endpoint on your own backend, which performs the authentication securely.

Can I open the chat only when the user clicks a button?

Yes — use Mode B and call CarameloChatbotClient.start() on the click.

What happens if the token expires?

The token lasts 24 hours. Just generate a new one on the next page load (Mode A) or on the next start() call (Mode B).

Can I use the same publication across multiple systems?

Yes, but we recommend creating one publication (and one Secret Token) per environment/system, to make control and revocation easier.

What if the Secret Token leaks?

Delete the publication on the platform and create a new one — a new Secret Token will be generated automatically.