M cenaly.ru
🧩 Widgets for Your Website

🧩 My Website

One tag on your site: chat, popups, cookie banner, booking, appointments, ordering, help and legal pages

Documentation

My Website: widgets on your own site

The My Website section is for those who already have a site. There's nothing to migrate to our storefront: you paste one line of code into your existing site, and after that you switch the products you need on with toggles in the admin panel.

Where to find it: Admin panel → Marketing → "My Website" (admin.cenaly.ru).

It works on any platform where you can paste a <script>: WordPress, Tilda, Wix, Shopify, Webflow, Bitrix, InSales, OpenCart, a custom-built site, or a landing page builder.


Site address and install code#

The first field in the section is your site address (for example, example.com). We use it to check the installation and to build the correct links inside the widgets.

Next comes the install code — a single line:

<script src="https://cdn.cenaly.ru/site/v1.js" data-domain="YOUR-DOMAIN" async></script>

Paste it once — into <head> or right before </body>. You won't need to touch the site's code again: which widgets run is set by toggles in the admin panel, not by tags on the page. Turn a widget on, and it appears on the site within a few minutes; turn it off, and it disappears.

If you previously pasted individual widget tags by hand, they'll keep working: the single loader sees them and won't start the same widget a second time.


The "Install code" window has a tab for each platform, with exact steps. Below are the same steps in brief.

HTML code#

Paste the line into <head> or right before </body> of any template page. If there are several pages and no shared template, paste it into each one.

Google Tag Manager#

Tags → New → Custom HTML → paste the code → "All Pages" trigger → Save → Publish. ⚠️ Our "Check installation" won't see a tag inserted through GTM (see "Troubleshooting").

WordPress#

Appearance → Theme File Editor → footer.php, before </body>. Or — more reliable across theme updates — any header/footer code-insertion plugin.

Tilda#

Site settings → More (in some accounts the section is called "Insert Code") → "HTML code for the HEAD section". After pasting it, republish all pages — otherwise the code stays in the draft.

Wix#

Settings → Development & integrations → Custom Code → "+ Add Custom Code" → Head placement, all pages. Wix allows custom code on a published site with a connected domain; a snippet is bound to the domain, so paste it again after a domain change.

Shopify#

Admin → Online Store → Themes → ⋯ → Edit code → layout/theme.liquid → before </body>.

Webflow#

Site settings → Custom code → Footer code → Save → Publish.

Squarespace#

Website → Website Tools → Code Injection → the Header field → Save. The Code Injection panel is available on the Core, Plus, Advanced and some legacy Squarespace plans.


Twelve widgets#

Each widget is a card with a toggle and a settings gear icon. Whatever the widgets collect lands in the regular sections of your admin panel — there's no separate "website inbox" to watch.

Widget What the visitor sees Where the data goes Documentation
🍪 Cookies & Consent Consent banner with categories and a preferences screen Consent log, cookie declaration Cookies & Consent
💬 Chat: AI assistant and agents Chat bubble on the page The "Chat" section — together with WhatsApp, Telegram, email, Messenger/Instagram Chat with guests
💡 Popups & Forms Promos, exit-intent offers, email capture, timers Campaigns and their statistics Engagement campaigns
📅 Table Reservation "Book a table" button The "Tables" section — bookings and floor plan Table reservations
🗓️ Online Booking "Book now" button: service → specialist → time The "Appointments" section Appointment book
🛒 Online Ordering "Order" button, cart and checkout on top of your site The "Orders" section Online ordering on your own site
📚 Help Center A "?" button with your published help articles Articles live in "Articles & Pages" (the "Help" group); help analytics live in the Knowledge Base Help Center
⚖️ Legal Documents Links to — or the text of — your privacy policy, terms, and other legal pages Pages hosted by us; republishing updates your site automatically; configured right in the widget panel, with no wizard Legal documents
📞 Call from website A "Call" button — talking straight from the browser, no dialing The "Calls" section: a recording and a breakdown, like a regular call Call from website
☎️ Callback A "Call me back" form with a choice of convenient time Callback queue: the system dials the manager and the guest itself; requests land in "Requests" and in the "Callbacks" tab of the "Customers" section Callback
Multibutton One floating button behind which all your contact channels sit at once Wherever the chosen channel leads; click statistics by channel live in your admin panel Multibutton
📈 Live Showcase Unobtrusive "just booked a table" pop-ups Collects nothing — it only shows your own events Live Showcase

The load order is deliberate: the cookie banner starts first, so that the other widgets and any third-party analytics on your site see the visitor's cookie decision already applied. For the same reason, multibutton loads second-to-last: it gathers the already-enabled widgets under itself and mutes their own buttons, so the corner doesn't end up with five buttons jostling for space. "Live Showcase" loads last — its cards step aside if another button is already sitting in the same corner.

Multibutton is not just a list of links: it has an invitation bubble ("Have a question?"), display conditions (which pages, after how many seconds, mobile-only or everywhere), a first-message draft for messengers, and its own click statistics by channel.

"Live Showcase" shows social proof built on your own data — orders, table reservations, and bookings — and does it honestly: there are no names or phone numbers in the cards, events are aggregated, and stale ones stop showing according to the location's calendar (a location that was closed yesterday doesn't "sell" yesterday's orders).

The "Popups & Forms" card has a "✨ Create from a template" button next to the toggle and the gear icon: it opens the same widget settings window, but straight on a gallery of ready-made scenarios — and it saves nothing until you click "Done".

The "Legal Documents" panel no longer sends you into a five-step wizard: the country, the set of documents, questions about your business, your company details, and the language all sit on one screen, with auto-fill and the preview collapsed, and a "Publish N documents" counter at the bottom. An option that contradicts answers you've already given is locked, with an explanation of exactly why.

The hub's open windows live in the page address: a widget's gear icon writes ?widget=<widget>, and the install-code window writes ?panel=install. That means a link to a specific widget's settings can be sent to a colleague, and it will survive F5 and the browser's Back button.

For one widget the toggle alone is not enough — it also needs content:

  • Online Booking appears on the site once your menu has at least one item of type "Service" and booking is enabled (the same switch used for table reservations);
  • Help Center switches on with the toggle right away, but without published articles it opens an empty help page — the widget's settings show how many articles are published.

The online booking widget in detail#

Settings live in the "Online Booking" card → gear icon: button color, its text, the screen corner, and the language. Right below the settings there's a ready-made code line just for this widget, in case you're installing only this one.

Language. The default is auto: the widget speaks the language of the page it sits on and knows 45 languages. Only the dictionary that's actually needed gets loaded, so this doesn't affect your site's speed. You can also pin one language in the list — for example, if the site is bilingual but you want bookings taken in just one language.

Links to a specific service or specialist. You can add attributes to the widget tag so the guest lands right on the step you need:

Attribute What it does
data-service="service id" the service is pre-selected — a "Book" button next to the service's description on your site. The id is shown next to the item in the "Menu" section
data-master="specialist id" the specialist is pre-selected — for a page about a specific specialist; the specialist's id is the same as the employee's id
data-open="true" the booking panel opens on its own, with no click on the button — for a dedicated "Book now" page

A stale id (the service was renamed, the specialist left) doesn't break the widget: it quietly shows the usual choice starting from the first step.

Fewer steps to a booking:

  • a single service or a single suitable specialist — the extra screen isn't shown;
  • the "⚡ Nearest: today 17:30" chip books in one tap, and the calendar opens on its own on the first day with free time;
  • the name, phone, and email are remembered on the guest's device: on a repeat booking the fields are already filled in, and the "Not you?" link clears them;
  • on a phone the panel opens full screen, and the booking button doesn't hide under the keyboard;
  • the widget can be used from the keyboard and reads correctly with a screen reader.

Email. The email field is optional; if the guest leaves an address, they get a letter with the visit details and a "Manage booking" link that lets them move or cancel the visit themselves. Details — in Appointment book.

What the widget brought in. In the appointment book, the "🌐 Website widget" button shows the funnel for 7, 30, or 90 days: how many times the button was seen, how many guests opened the panel, reached the contact step, and booked, and how many bookings were lost to a slot taken meanwhile. Bookings that came from the site carry a "From website" badge.


Installation check#

The "Check installation" button opens your site and reads the page's source HTML. Possible answers:

  • "Widget code found on the site" — the single tag is in place;
  • "Only individual widget tags found" — old individual snippets are working, there's no single tag;
  • "The code on the site belongs to a different location" — the tag carries someone else's data-domain (a common mistake with several venues);
  • "No widget code on this page" — no tag is visible.

⚠️ The check reads the source HTML. If the tag is inserted in the browser by Google Tag Manager or another script, the check won't see it — that's not an error. Open the site and look with your own eyes: the widget is either there or not.

Below the widget cards, the section has two more blocks: "Storefront on your own code (Headless)" — data, an API, and webhooks for when your own developer builds the site and doesn't need our widgets — and "Advanced: a separate tag per widget" with ready-made individual tags. So an individual tag isn't only something you "carry over from the past" — you can also take one right here.


Troubleshooting#

A general list for all twelve widgets — from the most common cause to the rarest. Specifics of a particular widget are covered in its own article.

1. "Check installation" says there's no code. The tag isn't inserted, it isn't inserted on every template page, or the site hasn't been republished after inserting it (Tilda, Wix, Webflow require republishing). Also check the site address in the section header: the check runs against exactly that address.

2. The code on the site belongs to a different location. The tag carries someone else's data-domain — a common mistake when there are several venues and the code was copied from a neighboring card. Take the code with the right location selected.

3. The check doesn't see a tag inserted through Google Tag Manager. That's not an error. The check reads the page's source HTML — what the server actually returned — while GTM inserts the tag only in the browser. Open the site and look with your own eyes: the widget is either there or not.

4. Changes haven't shown up on the site. Widget files are served through a CDN with a 5-minute cache. After flipping the toggle or changing the settings, wait a few minutes and reload the page with the cache cleared (Ctrl+F5). If the browser keeps showing the old version, check in an incognito window.

5. The widget is on, but it's not visible on the page. Go through the list:

  • the widget is a paid add-on and hasn't been paid for — an unpaid add-on is stripped from the site's data on the server, so it will not reach the page even with the toggle on;
  • the widget has display conditions (multibutton, callback, "Live Showcase"): a page mask, a delay, a device filter, or a schedule may have filtered out exactly this page and this moment;
  • the widget is missing content: online booking appears once the menu has at least one service item and booking is enabled; the help center opens an empty panel without published articles; multibutton isn't drawn at all without a single channel; "Live Showcase" stays silent while the numbers are below the threshold;
  • multibutton has absorbed a neighboring button: if its fan menu has an "Open chat" or "Callback" item, those widgets' own buttons are deliberately muted — they're now inside the fan menu.

6. Several buttons are crowding the corner of the screen. Turn on multibutton and add the actions of the widgets you need to its fan menu — their separate buttons will go dark on their own.

7. There are no widgets on a site built with our website builder. There, the install code is baked into the template, and the code block doesn't appear in the admin panel — that's normal. Check the widget toggles instead: a freshly generated site arrives with the cookie banner, legal documents, and chat already on; everything else needs to be switched on manually. Also note the difference between surfaces: on our storefront, multibutton shows only via a separate "Also show on our storefront" toggle (it absorbs the page's native buttons there), while "Live Showcase" works off the same single toggle as on someone else's site.


A site with a Content-Security-Policy#

If your server sends a Content-Security-Policy header, the browser — not us — decides what our install tag may load. The tag itself runs (you allowed it), but everything it pulls in can be blocked silently: from the outside that looks like "the widgets are gone". The browser console shows lines such as Refused to load the script.

The gap appears in exactly one mode: the policy allows scripts by per-response nonce only, without 'strict-dynamic' and without our CDN host in the list. Three ways to close it, simplest first.

Option 1 — a nonce on our tag#

Your server generates a fresh random value for every response and puts it in both the header and the tag:

Content-Security-Policy: script-src 'nonce-r4nd0m...'
<script nonce="r4nd0m..." src="https://cdn.<your brand>/site/v1.js" data-domain="YOUR-LOCATION" async></script>

The single tag reads the nonce of its own tag and passes it to every widget bundle it inserts, so they pass the same check. Nothing else has to be allowed.

⚠️ A fixed value that is the same on every response is not a nonce: anyone who manages to inject code into the page can copy it into their own script. Generate it per response, on the server.

Option 2 — 'strict-dynamic'#

Content-Security-Policy: script-src 'nonce-r4nd0m...' 'strict-dynamic'

With 'strict-dynamic', the trust granted to our tag extends to the scripts it inserts, and nothing else has to be listed. This is the shortest policy that keeps every widget working, including the lazy parts of "Smart popups".

Option 3 — a host allow-list#

If a nonce is not available to you (typical on site builders), allow our hosts explicitly:

Content-Security-Policy: script-src https://cdn.<your brand>;
  connect-src https://cdn.<your brand> https://api.<your brand> wss://ws.<your brand> https://o.<your brand>;
  img-src https://cdn.<your brand> https://i.<your brand>;
  frame-src https://cdn.<your brand> https://your-location.<your brand>;
  style-src 'unsafe-inline'

A ready snippet with your brand's and your location's hosts already filled in is in the admin panel: Marketing → My site, the "Does your site send a Content-Security-Policy?" block under the install code — with a "Copy" button and a note on which widget needs each host.

What needs what:

Directive Who needs it
script-src Every widget: the bundles from our CDN
connect-src Every widget: leads, reservations, bookings, orders, telemetry; chat also needs the websocket and the signals bucket
img-src Ordering: product and dish photos
frame-src Ordering, help center and legal documents: they open your storefront in an <iframe>
style-src Every widget: their windows insert a <style> element into their Shadow DOM

What this does not cover — honestly#

  • Styles. Widget chrome is an inline <style> inside Shadow DOM, so style-src 'unsafe-inline' is required. It does not affect script-src: we never ask for 'unsafe-inline' or 'unsafe-eval' for scripts.
  • The lazy parts of "Smart popups" (engage/rich-v1.js, engage/slots-v1.js) load through their own loader and do not carry the nonce yet: under a nonce-only policy without our CDN host, rich popups and slots stay down. The parts of the consent banner, the multibutton mobile bar and form capture do get it.
  • Site builders (Tilda, Wix and the like) send the header themselves, and you cannot issue a per-response nonce for your own tag there. Only the host allow-list option remains — if the platform lets you edit the policy at all.
  • Call from website streams audio over WebRTC and loads no media files, so it needs no media-src; the microphone is governed by Permissions-Policy and HTTPS, not by CSP.

Move a widget to its own section#

If one of the widgets is your main product (say, you only use popups or only the cookie banner), the path "Marketing → My Website → card → gear icon" is too long. Each card has a "Move to sidebar" button — the widget gets its own menu item and opens in one click.

This is a setting for your interface: it only controls the section's visibility, not how the widget runs on your site.


What is included and what is a paid add-on#

Some widgets are part of the subscription, others connect as an add-on in the "Extensions" section: Table Reservation, Popups & Forms, Help Center, and Legal Documents are marked as paid — their card carries a "💳 Paid add-on" chip.

A paid widget turns on after purchase. Clicking the toggle on an unpaid widget doesn't turn it on — it opens the checkout window right in the section; the widget switches itself on after payment. The "💳 Paid add-on" chip on an unpaid widget is also a checkout button, while on an already-paid one it leads to the catalog to review the subscription. A widget that's already running won't switch itself off. The limit isn't only in the interface: an unpaid widget is stripped out of the location's published data, so it won't appear on the site in any case.

On a site built with our website builder, "Legal Documents" and the cookie banner are free. Their cards carry a "🎁 Included with the site" chip instead of "paid," and no checkout window is shown at all: this isn't an upsell, it's the condition under which the site can be used lawfully. A freshly generated site arrives with the cookie banner, legal documents, and chat already switched on. On someone else's site, both widgets remain paid add-ons.

Pricing and payment — in App Store and Subscription.



FAQ#

Do I have to give up my own site? No. The widgets live on top of your site; you don't change your layout or hosting.

How many tags do I paste if I have several widgets? One. The set of widgets is toggles in the admin panel.

Will a widget slow down my site? The loader connects asynchronously (async) and doesn't block page rendering; each widget loads as its own small file, and only if it's enabled. A disabled widget isn't downloaded at all.

Will a widget break my layout? No. Every widget is drawn in an isolated container (Shadow DOM): your site's styles don't leak into the widget, and the widget's styles don't leak out. The one deliberate exception is the online ordering widget: it intentionally places "Add to cart" buttons in your own markup, and this is configured with a preview (see Online ordering on your own site).

What language will a widget speak? It looks at the page's language: first the data-lang attribute in the tag, if you've set one, then the lang of your HTML page, then the guest's browser language, and English as the last resort. Dictionaries vary in size: the cookie banner and the online booking widget know 45 languages, chat knows 35, and the rest ship with English, Russian, Georgian, and Turkish, falling back to English. You set the button labels and invitation text yourself — a separate line for each language of your site.

Where is the data the widgets collect stored? In your brand's cloud: AWS for cenaly.com, Yandex Cloud for cenaly.ru; data from Russian venues stays in Russia. Requests, orders, table reservations, and conversations land in your admin panel, while only the widgets' settings and things that are public anyway (the menu, opening hours, published documents, Live Showcase's anonymized numbers) go out to the public CDN.

I have several venues — how does that work? Widgets are configured per location: pick it in the list at the top of the section and take that location's install code. Each site has its own data-domain.

Can I put the widgets on several different sites? Yes, one location's tag can be pasted on several pages or sites — the data will arrive in that one location.