Configuração da marca da empresa#
Configurando branding.json no Sherpa AI Server#
Finalidade#
O arquivo branding.json permite alterar a aparência e parte do comportamento da interface do Sherpa AI Server sem recompilar o frontend:
- nome e logotipos;
- cores principais, raio dos cantos e fonte;
- plano de fundo das mensagens do usuário e do Assistente;
- idioma padrão e idiomas disponíveis;
- exibição do botão de login com OpenID;
- links adicionais no menu lateral;
- um botão de informação na página de login.
As configurações são aplicadas no navegador quando a aplicação é carregada. Não existe uma tela separada de administração de branding no Sherpa AI Server.
Onde o arquivo fica#
No código-fonte#
Arquivo principal:
frontend/src/assets/branding/branding.json
Ele faz parte da build do frontend e é usado como o conjunto padrão de configurações para a distribuição.
Na distribuição do cliente#
Ao preparar o pacote do cliente, o arquivo é copiado para este local:
frontend/config/branding.json
Para que o nginx use este arquivo, é necessário habilitar um bind mount no docker-compose.yml no serviço aiserver-nginx:
services:
aiserver-nginx:
volumes:
- ./frontend/config/branding.json:/opt/SherpaAIServer/frontend/dist/assets/branding/branding.json:ro
No docker-compose.yml distribuído, essa linha pode estar comentada. Depois de habilitar o mount pela primeira vez, recrie o contêiner:
docker compose up -d --force-recreate aiserver-nginx
Se o mount já estiver habilitado, as alterações no arquivo do host ficam visíveis imediatamente dentro do contêiner. Para aplicá-las na interface, basta recarregar a página.
Como a configuração é carregada#
Quando o frontend inicia, ele solicita:
/assets/branding/branding.json
A configuração é carregada antes da inicialização do aplicativo Angular. Por isso, o idioma, os logotipos e as variáveis CSS de branding já estão disponíveis durante a renderização inicial da interface.
Regras de carregamento:
- Os valores embutidos do Sherpa AI Server são usados como base.
- Os campos de
branding.jsonsubstituem os valores embutidos correspondentes. - Se o arquivo não estiver disponível ou contiver JSON inválido, a aplicação continua funcionando com os valores embutidos.
- Os campos de nível superior ausentes não precisam ser informados: os valores embutidos são mantidos para eles.
- Objetos aninhados e itens de arrays não são preenchidos automaticamente — eles devem ser definidos por completo.
O campo _comments dentro do branding.json padrão contém descrições de referência. É um campo auxiliar normal de JSON; a interface não o utiliza.
Início rápido#
Copie ou edite
frontend/config/branding.json.Verifique se o bind mount está habilitado em
docker-compose.yml.Confira a sintaxe do JSON:
jq empty frontend/config/branding.jsonAo conectar o arquivo pela primeira vez, recrie o
aiserver-nginx:docker compose up -d --force-recreate aiserver-nginxVerifique qual arquivo o servidor está fornecendo:
curl -fsS https://<server-address>/assets/branding/branding.json | jq .Recarregue a página do Sherpa AI Server. Se o navegador mostrar recursos antigos, faça um hard refresh.
Exemplo completo#
{
"app_name": "Корпоративный AI",
"logo_url": "assets/branding/logo-light-v1.svg",
"logo_url_light": "assets/branding/logo-light-v1.svg",
"logo_url_dark": "assets/branding/logo-dark-v1.svg",
"disable_openid": false,
"default_language": "ru",
"available_languages": ["ru", "en"],
"additional_menu_items": [
{
"button_name": {
"ru": "Поддержка",
"en": "Support"
},
"url": "https://support.example.org",
"icon": "question-mark-circle-outline"
},
{
"button_name": {
"ru": "Инструкции",
"en": "Documentation"
},
"url": "/main/documents",
"icon": "book-open-outline"
}
],
"additional_login_button": {
"button_name": {
"ru": "Как получить доступ?",
"en": "How do I get access?"
},
"message": {
"ru": "Для получения доступа обратитесь в службу поддержки.",
"en": "Contact the support team to request access."
}
},
"primary_color": "#2563eb",
"primary_dark_color": "#1d4ed8",
"primary_light_color": "#60a5fa",
"primary_rgb": "37, 99, 235",
"secondary_color": "#1f2937",
"border_radius": "8px",
"font_family": "Inter, sans-serif",
"font_url": "https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&display=swap",
"chat_user_bg": "#eff6ff",
"chat_assistant_bg": "#ffffff"
}
Descrição dos parâmetros#
| Parâmetro | Formato | Finalidade |
|---|---|---|
app_name |
string | Nome ao lado do logotipo no menu lateral e texto alt do logotipo. Não altera o título do cartão de login nem o <title> da página — atualmente Sherpa AI Server é usado ali. |
logo_url |
string de URL | Logotipo de fallback por compatibilidade. Usado se um logotipo separado para o tema necessário não estiver definido. |
logo_url_light |
string de URL | Logotipo para o tema claro. |
logo_url_dark |
string de URL | Logotipo para o tema escuro. |
disable_openid |
true ou false |
Quando true, oculta o botão Entrar com OpenID na página de login. O parâmetro controla a interface e, por si só, não desativa o OpenID no backend. |
default_language |
ru ou en |
Idioma padrão. O valor deve estar presente em available_languages. |
available_languages |
array de ru e/ou en |
Idiomas disponíveis para o usuário. Outros valores são descartados. |
additional_menu_items |
array de objetos | Itens permanentes adicionais no menu lateral antes da seção Chat. |
additional_login_button |
objeto ou null |
Botão de informação na página de login. Ao clicar, abre uma caixa de diálogo com texto localizado. null oculta o botão. |
primary_color |
#RRGGBB |
Cor principal para botões, links, elementos ativos, tabelas e controles de formulário. |
primary_dark_color |
#RRGGBB |
Tom mais escuro da cor principal para estados de hover e pressionado e alguns seletores. |
primary_light_color |
#RRGGBB |
Tom mais claro para realces e estados secundários. |
primary_rgb |
string R, G, B |
Componentes RGB de primary_color para fundos translúcidos, sombras e realces. |
secondary_color |
cor CSS | Cor secundária. Também é usada nas superfícies dos cartões no tema escuro e na tela de abertura. |
border_radius |
tamanho CSS | Arredondamento dos elementos, por exemplo 0px, 6px ou 16px. |
font_family |
font-family CSS |
Família de fonte aplicada à interface. |
font_url |
URL de arquivo CSS | Folha de estilo da qual o navegador carrega a fonte. Uma string vazia desativa o download adicional. |
chat_user_bg |
cor CSS | Fundo das mensagens do usuário na tela Chat. |
chat_assistant_bg |
cor CSS | Fundo das respostas do Assistente na tela Chat. |
Configuração dos logotipos#
Prioridade de seleção do logotipo para cada tema:
logo_url_light or logo_url_dark → logo_url → built-in logo
É possível usar:
- um caminho relativo dentro do frontend, por exemplo
assets/branding/logo-light-v1.svg; - um caminho absoluto a partir da raiz do site, por exemplo
/assets/branding/logo-light-v1.svg; - uma URL absoluta, por exemplo
https://static.example.org/logo-light-v1.svg.
Se o logotipo estiver armazenado junto com a configuração do cliente, monte-o separadamente em docker-compose.yml:
services:
aiserver-nginx:
volumes:
- ./frontend/config/branding.json:/opt/SherpaAIServer/frontend/dist/assets/branding/branding.json:ro
- ./frontend/config/logo-light-v1.svg:/opt/SherpaAIServer/frontend/dist/assets/branding/logo-light-v1.svg:ro
- ./frontend/config/logo-dark-v1.svg:/opt/SherpaAIServer/frontend/dist/assets/branding/logo-dark-v1.svg:ro
Em produção, imagens, fontes e outros arquivos estáticos podem ser armazenados em cache pelo navegador por até um ano. Quando o conteúdo do logotipo mudar, use um novo nome, por exemplo logo-light-v2.svg, e atualize o caminho em branding.json.
Configuração das cores#
primary_color e primary_rgb descrevem a mesma cor em formatos diferentes. Eles não são sincronizados automaticamente.
Exemplo:
{
"primary_color": "#2563eb",
"primary_rgb": "37, 99, 235"
}
Para primary_color, primary_dark_color e primary_light_color, use o formato HEX completo #RRGGBB. O serviço calcula o contraste da cor principal para o texto e os ícones, portanto não se deve usar HEX abreviado nem valores rgb(...) ou rgba(...) para esses três campos.
Para secondary_color, chat_user_bg e chat_assistant_bg, cores CSS normais, como HEX ou rgba(...), são permitidas.
Depois de alterar as cores, verifique os dois temas, tabelas, campos de formulário, botões e a legibilidade das mensagens no chat.
Configuração da fonte#
font_url deve apontar para um arquivo CSS com a fonte, e font_family deve apontar para o nome da família nesse arquivo CSS:
{
"font_family": "Inter, sans-serif",
"font_url": "https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&display=swap"
}
Para uma fonte personalizada, é possível montar o CSS e os arquivos da fonte no diretório frontend e usar uma URL relativa. Certifique-se de que a URL esteja acessível nos navegadores dos usuários, e não apenas no backend do Sherpa AI Server.
Para não carregar um arquivo CSS adicional, deixe font_url vazio:
{
"font_family": "Roboto, 'Helvetica Neue', sans-serif",
"font_url": ""
}
Idiomas da interface#
Somente os valores ru e en são suportados.
Se available_languages estiver vazio, tiver um formato inválido ou não contiver valores suportados, o Sherpa AI Server habilita os dois idiomas. Se default_language não estiver presente na lista de idiomas disponíveis, o primeiro item de available_languages se torna o idioma padrão.
Exemplo de uma interface somente em russo:
{
"default_language": "ru",
"available_languages": ["ru"]
}
O botão do idioma atual continua visível, mas o menu de troca não é aberto.
O idioma real é selecionado na seguinte ordem:
- o parâmetro
langoulocalena URL; - o idioma escolhido anteriormente no navegador;
default_languagedebranding.json.
O valor da URL ou do navegador só é aplicado quando o idioma está presente em available_languages.
Itens adicionais do menu#
Cada item de additional_menu_items deve conter:
{
"button_name": {
"ru": "Поддержка",
"en": "Support"
},
"url": "https://support.example.org",
"icon": "question-mark-circle-outline"
}
Regras:
- pelo menos uma tradução não vazia do nome é necessária;
urldeve ser um caminho interno com apenas uma/inicial ou uma URL com o protocolohttpouhttps;- valores com outros protocolos e URLs inválidas são ignorados;
- links internos são abertos pelo roteador do Sherpa AI Server;
- links externos são abertos na aba atual;
- os itens são exibidos na mesma ordem em que aparecem no array;
- para um ícone padrão, informe um nome de Eva Icons, por exemplo
book-open-outline; - uma string que termine em
/ou.svgé interpretada como um caminho para um ícone SVG personalizado.
Se faltar uma tradução, primeiro é usado o russo e depois o inglês.
Botão de informação na página de login#
Exemplo:
{
"additional_login_button": {
"button_name": {
"ru": "Forgot your password?",
"en": "Forgot your password?"
},
"message": {
"ru": "Contact the support team.",
"en": "Contact the support team."
}
}
}
O botão é exibido se houver pelo menos um nome e pelo menos um texto de mensagem preenchidos. O texto é exibido como texto simples, não como HTML. Se faltar uma tradução, primeiro é usado o russo e depois o inglês.
Para ocultar o botão:
{
"additional_login_button": null
}