chainlit身份验证方案oauth2.0及常用社交应用账户集成
阅读原文
建议阅读原文,始终查看最新文档版本,获得最佳阅读体验:《chainlit身份验证方案oauth2.0及常用社交应用账户集成》
本文摘要
本文详细说明了如何将chainlit与Microsoft AD(LDAP)集成,以便于企业用户通过域账号登录到chainlit,另外,还简要介绍了两个功能类似的开源项目lobechat和librechat。
chainlit简介
github网址:Chainlit/chainlit: Build Conversational AI in minutes ⚡️
chainlit是一个用于快速构建AI对话式聊天机器人的开源python库,其最大的特点是,可以很方便的构建类似于chatGPT那样的前端页面
类似的开源项目
Lobe Chat
lobe-chat/README.zh-CN.md at main · lobehub/lobe-chat
LobeHub - LobeChat:个人 LLM 效能工具,超越 ChatGPT / OLLaMA 使用体验
lobechat是现代化设计的开源 ChatGPT/LLMs 聊天应用与开发框架支持语音合成、多模态、可扩展的(function call)插件系统,一键免费拥有你自己的 ChatGPT/Gemini/Claude/Ollama 应用
lobechat也是支持OAuth2.0的
lobechat的github stars数远高于librechat和chainlit,高达6万多。
LibreChat
librechat.ai/docs danny-avila/LibreChat: Enhanced ChatGPT Clone: Features Agents, DeepSeek, Anthropic, AWS, OpenAI, Assistants API, Azure, Groq, o1, GPT-4o, Mistral, OpenRouter, Vertex AI, Gemini, Artifacts, AI model switching, message search, Code Interpreter, langchain, DALL-E-3, OpenAPI Actions, Functions, Secure Multi-User Auth, Presets, open-source for self-hosting. Active project.
官方介绍视频:https://youtu.be/ilfwGQtJNlI
LibreChat 是一款面向所有人工智能对话的终极开源应用程序,它完全可定制且兼容任何AI服务提供商——所有这些功能都集成在一个时尚流畅的界面中
LibreChat原生支持LDAP,同时也支持OAuth2.0
chainlit支持的身份验证提供商
参考资料:Overview - Chainlit
chainlit支持这三种身份认证方式:
其中OAuth又包括了以下几种,可以看到,支持的OAuth providers是非常多的,几乎包含了所有的社交账号,而keycloak本身也支持很多平台。
安装chainlit
Linux系统
首先要安装python和pip,此过程省略
注意,下面几行命令是在ubuntu desktop 24.04系统上运行的,Windows系统命令有所区别
#创建虚拟环境
python3 -m venv chainlit
#激活虚拟环境
source ./chainlit/bin/activate
#用pip安装chainlit包
pip install --upgrade chainlit
Windows系统,trae(vs code)
先通过trae(用vs code或cursor也是可以的)创建一个空的app.py文件,然后通过命令面板创建虚拟环境
成功创建虚拟环境后,就可以在资源管理中看到自动生成了.env文件夹
激活虚拟环境
.venv\Scripts\activate
检查当前python解释器是不是虚拟环境中的解释器,如果不是,务必选择虚拟环境中的解释器
用pip安装chainlit包,时间会比较长,因为国内下载包会比较慢
pip install --upgrade chainlit
用github验证身份
创建一个github app
参考资料:OAuth - Chainlit
点击此链接,然后创建一个github app
下图是我已经创建好的一个github app
关键是callback url、client secret(可以直接生成)
Request user authorization (OAuth) during installation
这个一定要勾选。
webhook不用勾选
private key也是必须的,直接生成即可,网页会提示的
安装github app
注册好github app后,还要安装此github app,很简单,点击install app,然后右侧会显示待安装和已安装的github app,下图是我已经安装的github app
验证
启动chainlit app
chainlit run .\text_to_SQL.py -d -w
text_to_SQL.py代码如下:
import os
from openai import AsyncOpenAI
from chainlit.oauth_providers import OAuthProvider
import chainlit as cl
import httpx
from fastapi import HTTPException
from chainlit.user import User
import json
cl.instrument_openai()
""" import os
# 手动加载.env文件
from dotenv import load_dotenv
load_dotenv() """
# 打印环境变量
""" print(os.getenv("OAUTH_KEYCLOAK_BASE_URL"))
print(os.getenv("OAUTH_KEYCLOAK_REALM"))
print(os.getenv("OAUTH_KEYCLOAK_CLIENT_ID"))
print(os.getenv("OAUTH_KEYCLOAK_CLIENT_SECRET"))
print(os.getenv("OAUTH_KEYCLOAK_NAME")) """
#user_env = cl.user_session.get("env") #从.env文件中获取环境变量
# 从环境变量中获取API KEY
api_key = os.getenv("OPENAI_API_KEY")
api_key = "<此处替换为你的api_key>"
print(os.getenv("OPENAI_API_KEY"))
if api_key is None:
raise ValueError("OPENAI_API_KEY environment variable is not set.")
client = AsyncOpenAI(
api_key=api_key,
base_url="https://dashscope.aliyuncs.com/compatible-mode/v1"
)
# 优化后的模板,让指令更清晰
template = """SQL tables (and columns):
* Customers(customer_id, signup_date)
* Streaming(customer_id, video_id, watch_date, watch_minutes)
Generate a well - written SQL query to {input} and return the query wrapped in triple backticks (```):
```"""
settings = {
"model": "qwen-plus",
"temperature": 0,
"max_tokens": 500,
"top_p": 1,
"frequency_penalty": 0,
"presence_penalty": 0,
# 可以尝试去掉 stop 参数
# "stop": ["```"],
}
@cl.set_starters
async def starters():
return [
cl.Starter(
label=">50 minutes watched",
message="Compute the number of customers who watched more than 50 minutes of video this month."
)
]
@cl.on_message
async def main(message: cl.Message):
try:
stream = await client.chat.completions.create(
messages=[
{
"role": "user",
"content": template.format(input=message.content),
}
], stream=True, **settings
)
msg = await cl.Message(content="", language="sql").send()
async for part in stream:
if token := part.choices[0].delta.content or "":
await msg.stream_token(token)
await msg.update()
except Exception as e:
# 打印详细的错误信息
print(f"Error occurred: {e}")
error_msg = await cl.Message(content=f"An error occurred: {e}").send()
from typing import Dict, Optional
@cl.oauth_callback
def oauth_callback(
provider_id: str,
token: str,
raw_user_data: Dict[str, str],
default_user: cl.User,
) -> Optional[cl.User]:
return default_user
.env文件如下
DASHSCOPE_API_KEY=<此处替换为你的api_key>
OPENAI_API_KEY=<此处替换为你的api_key>
#下面的环境变量值,可以在github app中查到
OAUTH_GITHUB_CLIENT_ID=<此处替换为你的GITHUB_CLIENT_ID>
OAUTH_GITHUB_CLIENT_SECRET=<此处替换为你的GITHUB_CLIENT_SECRET>
会自动打开默认浏览器,自动打开网页,网址为http://localhost:8000
如下图,点击“继续使用github”,然后会跳转到github的登录界面,提示需要授权,完成授权后,网页会自动跳转回chainlit页面
可以看到,成功登录了
问聊天机器人,也输出了回答
下面是chainlit部分日志
2025-06-11 11:13:30 - HTTP Request: GET https://api.github.com/user "HTTP/1.1 200 OK"
2025-06-11 11:13:31 - HTTP Request: GET https://api.github.com/user/emails "HTTP/1.1 200 OK"
INFO: 127.0.0.1:60250 - "GET /auth/oauth/github/callback?code=c57134e83b9aa8f9411b&state=im0fiESYJ7wlUrS%24%2FpJ%40t%40%3ER03DsRQRG HTTP/1.1" 302 Found
INFO: 127.0.0.1:60250 - "GET /login/callback?success=True HTTP/1.1" 200 OK
INFO: 127.0.0.1:60250 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:60249 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60252 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
2025-06-11 11:13:31 - Translated markdown file for zh-CN not found. Defaulting to chainlit.md.
INFO: 127.0.0.1:60252 - "GET /project/settings?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60252 - "POST /set-session-cookie HTTP/1.1" 200 OK
INFO: 127.0.0.1:60252 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTS-eSY HTTP/1.1" 200 OK
INFO: 127.0.0.1:60252 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTS-eSk&sid=BhVCTPSnvJ-ahsFyAAAE HTTP/1.1" 200 OK
INFO: 127.0.0.1:60249 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTS-eSl&sid=BhVCTPSnvJ-ahsFyAAAE HTTP/1.1" 200 OK
INFO: 127.0.0.1:60249 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTS-eTB&sid=BhVCTPSnvJ-ahsFyAAAE HTTP/1.1" 200 OK
INFO: 127.0.0.1:60252 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTS-eTA&sid=BhVCTPSnvJ-ahsFyAAAE HTTP/1.1" 200 OK
INFO: 127.0.0.1:60252 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTS-eTd&sid=BhVCTPSnvJ-ahsFyAAAE HTTP/1.1" 200 OK
INFO: ('127.0.0.1', 60344) - "WebSocket /ws/socket.io/?EIO=4&transport=websocket&sid=BhVCTPSnvJ-ahsFyAAAE" [accepted]
INFO: 127.0.0.1:60252 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTS-eTm&sid=BhVCTPSnvJ-ahsFyAAAE HTTP/1.1" 200 OK
INFO: 127.0.0.1:60452 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60453 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60456 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60456 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60484 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60484 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60529 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60529 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60629 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60630 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
2025-06-11 11:14:44 - HTTP Request: POST https://dashscope.aliyuncs.com/compatible-mode/v1/chat/completions "HTTP/1.1 200 OK"
INFO: 127.0.0.1:60630 - "GET /user HTTP/1.1" 200 OK
关于https的特别说明
github的安全策略要求生产环境下,callback url必须使用https
但是开发环境下,可以使用http,不过callback url中的ip地址必须是localhost或127.0.0.1
keycloak–LDAP
部署keycloak
最简单的方法是用docker部署
docker run -p 8080:8080 -e KC_BOOTSTRAP_ADMIN_USERNAME=admin -e KC_BOOTSTRAP_ADMIN_PASSWORD=admin --dns=192.168.124.7 docker.1ms.run/keycloak/keycloak:26.2.5 start-dev
注意,这种方式,只适用于实验环境,生产环境尽量用helm部署,且必须用https
添加一个LDAP provider
访问keycloak,网址为:http://your_serverIP:8080
默认的用户名和密码都是admin
下面是一个示例:
验证ldap连接性
创建一个新的client
参考资料:OAuth - Chainlit
官方文档,对于redirect URLs的说明如下,其实关键是callback前的字符,这个是可以自定义的,我设置的是chainlit-keycloak
You have the option of changing the id of your Keycloak provider, which by default is keycloak. This is useful if you want to display a more appropriate name on your login page. Use the OAUTH_KEYCLOAK_NAME environment variable to set the name. Don’t choose an id that conflicts with any of the other Oauth providers.
The callback URL for your client should be: CHAINLIT_URL/auth/oauth/ O A U T H _ K E Y C L O A K _ N A M E / c a l l b a c k . I f y o u r C h a i n l i t a p p i s h o s t e d a t l o c a l h o s t : 8000 , y o u s h o u l d u s e [ h t t p : / / l o c a l h o s t : 8000 / a u t h / o a u t h / {OAUTH\_KEYCLOAK\_NAME}/callback. If your Chainlit app is hosted at localhost:8000, you should use[http://localhost:8000/auth/oauth/ OAUTH_KEYCLOAK_NAME/callback. If your Chainlit app is hosted at localhost:8000, you should use[http://localhost:8000/auth/oauth/{OAUTH_KEYCLOAK_NAME}/callback](http://localhost:8000/auth/oauth/${OAUTH_KEYCLOAK_NAME}/callback).
这里,redirect URLs使用ip地址也是可以的,只是运行chainlit时,需要指定–host参数,如果不指定,则默认是在localhost上监听的
chainlit.exe run .\text_to_SQL.py -d -h -w --host 192.168.124.11
设置chainlit环境变量(.env文件)
特别说明:OAUTH_KEYCLOAK_CLIENT_SECRET
这个环境变量的值可以在keycloak中直接复制:client–credentials–client secret
OAUTH_KEYCLOAK_CLIENT_SECRET和CHAINLIT_AUTH_SECRET的值要保持一致,另外千万注意,不要在=号两边加上空格,也不要对环境变量的值用双引号,这会导致实际的环境变量值发生变化,从而导致chainlit身份认证出现问题。不要在环境变量值的后面加上#号,因为这会赋值给环境变量,如果要对.env文件进行注释,请在单独的行中进行注释。
# OAUTH_KEYCLOAK_BASE_URL = "http://10.65.37.239:8080"
DASHSCOPE_API_KEY=<此处替换为你的api_key>
OPENAI_API_KEY=<此处替换为你的api_key>
OAUTH_KEYCLOAK_BASE_URL=http://10.65.37.239:8080
#OAUTH_KEYCLOAK_REALM的值就是keycloak中的REALM名,keycloak中默认的REALM是master,但是也可以再新建REALM
OAUTH_KEYCLOAK_REALM = "master"
OAUTH_KEYCLOAK_CLIENT_ID = "chainlit-client"
#下面这个环境变量的值可以在keycloak中直接复制:client--credentials--client secret
#OAUTH_KEYCLOAK_CLIENT_SECRET和CHAINLIT_AUTH_SECRET的值要保持一致,另外千万注意,不要在=号两边加上空格,也不要对环境变量的值用双引号,这会导致实际的环境变量值发生变化,从而导致chainlit身份认证出现问题。不要在环境变量值的后面加上#号,因为这会赋值给环境变量,如果要对.env文件进行注释,请在单独的行中进行注释。
OAUTH_KEYCLOAK_CLIENT_SECRET=7M7FzG7pVNe0RA84C75cgWk0VHzCCLm6
# CHAINLIT_AUTH_SECRET="F3rrs1vky1*MU9~ron_p1ntNfu2Rv1GiSWgl1p:$=>Yl0cRFubC?2=I1=$uCBLVS"
CHAINLIT_AUTH_SECRET=7M7FzG7pVNe0RA84C75cgWk0VHzCCLm6
#OAUTH_KEYCLOAK_NAME的值可以自己设置,如果不设置,默认为keycloak
OAUTH_KEYCLOAK_NAME = "chainlit-keycloak"
编写chainlit主程序逻辑代码
import os
from openai import AsyncOpenAI
from chainlit.oauth_providers import OAuthProvider
import chainlit as cl
import httpx
from fastapi import HTTPException
from chainlit.user import User
import json
cl.instrument_openai()
""" import os
# 手动加载.env文件
from dotenv import load_dotenv
load_dotenv() """
# 打印环境变量
print(os.getenv("OAUTH_KEYCLOAK_BASE_URL"))
print(os.getenv("OAUTH_KEYCLOAK_REALM"))
print(os.getenv("OAUTH_KEYCLOAK_CLIENT_ID"))
print(os.getenv("OAUTH_KEYCLOAK_CLIENT_SECRET"))
print(os.getenv("OAUTH_KEYCLOAK_NAME"))
print(os.getenv("CHAINLIT_AUTH_SECRET"))
#user_env = cl.user_session.get("env") #从.env文件中获取环境变量
# 从环境变量中获取API KEY
api_key = os.getenv("OPENAI_API_KEY")
print(os.getenv("OPENAI_API_KEY"))
if api_key is None:
raise ValueError("OPENAI_API_KEY environment variable is not set.")
client = AsyncOpenAI(
api_key=api_key,
base_url="https://dashscope.aliyuncs.com/compatible-mode/v1"
)
# 优化后的模板,让指令更清晰
template = """SQL tables (and columns):
* Customers(customer_id, signup_date)
* Streaming(customer_id, video_id, watch_date, watch_minutes)
Generate a well - written SQL query to {input} and return the query wrapped in triple backticks (```):
```"""
settings = {
"model": "qwen-plus",
"temperature": 0,
"max_tokens": 500,
"top_p": 1,
"frequency_penalty": 0,
"presence_penalty": 0,
# 可以尝试去掉 stop 参数
# "stop": ["```"],
}
@cl.set_starters
async def starters():
return [
cl.Starter(
label=">50 minutes watched",
message="Compute the number of customers who watched more than 50 minutes of video this month."
)
]
@cl.on_message
async def main(message: cl.Message):
try:
stream = await client.chat.completions.create(
messages=[
{
"role": "user",
"content": template.format(input=message.content),
}
], stream=True, **settings
)
msg = await cl.Message(content="", language="sql").send()
async for part in stream:
if token := part.choices[0].delta.content or "":
await msg.stream_token(token)
await msg.update()
except Exception as e:
# 打印详细的错误信息
print(f"Error occurred: {e}")
error_msg = await cl.Message(content=f"An error occurred: {e}").send()
from typing import Dict, Optional
# 下面部分的代码很重要,这部分代码的含义是允许所有经过身份验证的用户登录到chainlit
@cl.oauth_callback
def oauth_callback(
provider_id: str,
token: str,
raw_user_data: Dict[str, str],
default_user: cl.User,
) -> Optional[cl.User]:
return default_user
启动chainlit并验证登录
chainlit run .\text_to_SQL.py -d -w
浏览器会自动打开chainlit网站
设置了身份验证后,必须要登录才能真正使用chainlit,这里点击“继续使用chainlit-keycloak”
网页跳转到了keycloak的登录页面
这里,我先用一个合法的用户登录,就是之前添加的Microsoft AD中的用户
其实keycloak中的这些用户都是可以登录的,可以看到,其中很多用户是通过LDAP同步过来的
成功登录
与chainlit应用对话,也是正常的:
再试一下,一个不存在的用户登录,会发生什么:
无法登陆
查看keycloak的日志,可以看到提示没有找到此用户error="user_not_found"
2025-06-11 06:50:53,645 WARN [org.keycloak.events] (executor-thread-65) type="LOGIN_ERROR", realmId="c62613af-801b-459c-9302-0871e049403a", realmName="master", clientId="chainlit-client", userId="null", ipAddress="192.168.124.11", error="user_not_found", auth_method="openid-connect", auth_type="code", redirect_uri="http://localhost:8000/auth/oauth/chainlit-keycloak/callback", code_id="f6d377ce-62b1-4cd5-8326-018216b3071c", username="david"
完整的keycloak日志
仔细看下面的日志,会发现出现了几次报错:error="invalid_client_credentials"
,这是因为chainlit的.env文件中的环境变量设置有误,我之前在=号两边加上了空格,还有引号,甚至还在环境变量的值的后面用#进行了注释,这都是错误的,导致环境变量赋值错误,从而出现了这个报错。所以一定要注意.env文件的最佳实践:
不要有空格;
不要在值的两边加双引号;
决不能在值的末尾用#进行注释,应该另外加一行进行注释。
docker run -p 8080:8080 -e KC_BOOTSTRAP_ADMIN_USERNAME=admin -e KC_BOOTSTRAP_ADMIN_PASSWORD=admin --dns=192.168.124.7 docker.1ms.run/keycloak/keycloak:26.2.5 start-dev
Updating the configuration and installing your custom providers, if any. Please wait.
2025-06-11 04:54:29,743 INFO [io.quarkus.deployment.QuarkusAugmentor] (main) Quarkus augmentation completed in 61147ms
Running the server in development mode. DO NOT use this configuration in production.
2025-06-11 04:54:42,967 INFO [org.keycloak.quarkus.runtime.storage.database.liquibase.QuarkusJpaUpdaterProvider] (main) Initializing database schema. Using changelog META-INF/jpa-changelog-master.xml
2025-06-11 04:54:51,606 INFO [org.keycloak.quarkus.runtime.storage.infinispan.CacheManagerFactory] (main) Starting Infinispan embedded cache manager
2025-06-11 04:54:51,755 INFO [org.keycloak.quarkus.runtime.storage.infinispan.CacheManagerFactory] (main) JGroups JDBC_PING discovery enabled.
2025-06-11 04:54:52,043 INFO [org.infinispan.CONTAINER] (main) Virtual threads support enabled
2025-06-11 04:54:52,486 INFO [org.infinispan.CONTAINER] (main) ISPN000556: Starting user marshaller 'org.infinispan.commons.marshall.ImmutableProtoStreamMarshaller'
2025-06-11 04:54:53,452 INFO [org.keycloak.connections.infinispan.DefaultInfinispanConnectionProviderFactory] (main) Node name: node_700622, Site name: null
2025-06-11 04:54:54,049 INFO [org.keycloak.services] (main) KC-SERVICES0050: Initializing master realm
2025-06-11 04:54:58,037 INFO [org.keycloak.services] (main) KC-SERVICES0077: Created temporary admin user with username admin
2025-06-11 04:54:58,376 INFO [io.quarkus] (main) Keycloak 26.2.5 on JVM (powered by Quarkus 3.20.1) started in 28.079s. Listening on: http://0.0.0.0:8080
2025-06-11 04:54:58,377 INFO [io.quarkus] (main) Profile dev activated.
2025-06-11 04:54:58,377 INFO [io.quarkus] (main) Installed features: [agroal, cdi, hibernate-orm, jdbc-h2, keycloak, narayana-jta, opentelemetry, reactive-routes, rest, rest-jackson, smallrye-context-propagation, vertx]
2025-06-11 04:55:27,371 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-3) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 04:55:28,271 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-1) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 04:55:31,313 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-4) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:02:50,657 INFO [org.keycloak.storage.ldap.LDAPIdentityStoreRegistry] (executor-thread-15) Creating new LDAP Store for the LDAP storage provider: 'ldap', LDAP Configuration: {fullSyncPeriod=[604800], pagination=[true], connectionTrace=[false], startTls=[false], connectionPooling=[true], usersDn=[OU=myse,DC=dltornado2,DC=com], cachePolicy=[DEFAULT], useKerberosForPasswordAuthentication=[false], importEnabled=[true], enabled=[true], changedSyncPeriod=[86400], bindDn=[CN=adm,OU=myse,DC=dltornado2,DC=com], usernameLDAPAttribute=[cn], vendor=[ad], uuidLDAPAttribute=[objectGUID], allowKerberosAuthentication=[false], connectionUrl=[ldap://dc-t.dltornado2.com:389], syncRegistrations=[true], authType=[simple], krbPrincipalAttribute=[userPrincipalName], searchScope=[2], useTruststoreSpi=[always], usePasswordModifyExtendedOp=[false], trustEmail=[false], userObjectClasses=[person, organizationalPerson, user], removeInvalidUsersEnabled=[true], rdnLDAPAttribute=[cn], editMode=[WRITABLE], validatePasswordPolicy=[false]}, binaryAttributes: []
2025-06-11 05:06:38,983 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-15) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:06:48,097 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-22) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:06:49,529 WARN [org.keycloak.events] (executor-thread-22) type="CODE_TO_TOKEN_ERROR", realmId="c62613af-801b-459c-9302-0871e049403a", realmName="master", clientId="chainlit-client", userId="null", ipAddress="192.168.124.11", error="invalid_client_credentials", grant_type="authorization_code"
2025-06-11 05:09:53,486 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-22) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:10:00,019 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-24) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:10:01,581 WARN [org.keycloak.events] (executor-thread-24) type="CODE_TO_TOKEN_ERROR", realmId="c62613af-801b-459c-9302-0871e049403a", realmName="master", clientId="chainlit-client", userId="null", ipAddress="192.168.124.11", error="invalid_client_credentials", grant_type="authorization_code"
2025-06-11 05:44:49,771 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-24) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:44:59,211 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-29) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:45:00,915 WARN [org.keycloak.events] (executor-thread-29) type="CODE_TO_TOKEN_ERROR", realmId="c62613af-801b-459c-9302-0871e049403a", realmName="master", clientId="chainlit-client", userId="null", ipAddress="192.168.124.11", error="invalid_client_credentials", grant_type="authorization_code"
2025-06-11 05:45:51,892 WARN [org.keycloak.events] (executor-thread-29) type="REFRESH_TOKEN_ERROR", realmId="c62613af-801b-459c-9302-0871e049403a", realmName="master", clientId="security-admin-console", userId="null", ipAddress="192.168.124.11", error="invalid_token", reason="Token is not active", grant_type="refresh_token", client_auth_method="client-secret"
2025-06-11 05:45:51,934 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-29) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:45:54,749 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-33) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:52:04,838 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-35) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:52:23,253 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-37) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:52:24,413 WARN [org.keycloak.events] (executor-thread-37) type="CODE_TO_TOKEN_ERROR", realmId="c62613af-801b-459c-9302-0871e049403a", realmName="master", clientId="chainlit-client", userId="null", ipAddress="192.168.124.11", error="invalid_client_credentials", grant_type="authorization_code"
2025-06-11 05:57:47,864 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-37) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 05:57:54,214 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-42) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:21:30,489 WARN [org.keycloak.events] (executor-thread-42) type="REFRESH_TOKEN_ERROR", realmId="c62613af-801b-459c-9302-0871e049403a", realmName="master", clientId="security-admin-console", userId="null", ipAddress="192.168.124.11", error="invalid_token", reason="Token is not active", grant_type="refresh_token", client_auth_method="client-secret"
2025-06-11 06:21:30,545 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-42) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:21:33,628 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-42) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:24:10,345 INFO [org.keycloak.storage.ldap.LDAPStorageProviderFactory] (executor-thread-53) Sync all users from LDAP to local store: realm: c62613af-801b-459c-9302-0871e049403a, federation provider: ldap
2025-06-11 06:24:10,477 INFO [org.keycloak.storage.ldap.LDAPStorageProviderFactory] (executor-thread-53) Sync all users finished: 0 imported users, 10 updated users
2025-06-11 06:24:12,997 INFO [org.keycloak.storage.ldap.LDAPIdentityStoreRegistry] (executor-thread-53) Creating new LDAP Store for the LDAP storage provider: 'ldap', LDAP Configuration: {pagination=[true], fullSyncPeriod=[604800], connectionTrace=[false], startTls=[false], usersDn=[OU=myse,DC=dltornado2,DC=com], connectionPooling=[true], cachePolicy=[DEFAULT], useKerberosForPasswordAuthentication=[false], importEnabled=[true], enabled=[true], usernameLDAPAttribute=[cn], bindDn=[CN=adm,OU=myse,DC=dltornado2,DC=com], changedSyncPeriod=[86400], lastSync=[1749623050], vendor=[ad], uuidLDAPAttribute=[objectGUID], connectionUrl=[ldap://dc-t.dltornado2.com:389], allowKerberosAuthentication=[false], syncRegistrations=[true], authType=[simple], krbPrincipalAttribute=[userPrincipalName], searchScope=[2], useTruststoreSpi=[always], usePasswordModifyExtendedOp=[false], trustEmail=[false], userObjectClasses=[person, organizationalPerson, user], removeInvalidUsersEnabled=[true], rdnLDAPAttribute=[cn], editMode=[WRITABLE], validatePasswordPolicy=[false]}, binaryAttributes: []
2025-06-11 06:32:03,056 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-53) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:32:06,748 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-53) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:46:32,652 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-58) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:46:52,782 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-58) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:47:37,201 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-60) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:48:49,050 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-60) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:49:03,145 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-60) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:49:20,683 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-60) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:50:53,552 WARN [org.keycloak.cookie.DefaultCookieProvider] (executor-thread-65) Non-secure context detected; cookies are not secured, and will not be available in cross-origin POST requests
2025-06-11 06:50:53,645 WARN [org.keycloak.events] (executor-thread-65) type="LOGIN_ERROR", realmId="c62613af-801b-459c-9302-0871e049403a", realmName="master", clientId="chainlit-client", userId="null", ipAddress="192.168.124.11", error="user_not_found", auth_method="openid-connect", auth_type="code", redirect_uri="http://localhost:8000/auth/oauth/chainlit-keycloak/callback", code_id="f6d377ce-62b1-4cd5-8326-018216b3071c", username="david"
除了上述详细日志,还可以在keycloak的webUI上查看每个用户的登录日志:
完整的chainlit日志
chainlit.exe run .\text_to_SQL.py -d -h -w
2025-06-11 13:57:25 - Loaded .env file
http://10.65.37.239:8080
master
chainlit-client
7M7FzG7pVNe0RA84C75cgWk0VHzCCLm6
chainlit-keycloak
7M7FzG7pVNe0RA84C75cgWk0VHzCCLm6
sk-189ff68fba9d4ff884e718d8338ee075
INFO: Started server process [10032]
INFO: Waiting for application startup.
2025-06-11 13:57:29 - Your app is available at http://localhost:8000
INFO: Application startup complete.
INFO: Uvicorn running on http://127.0.0.1:8000 (Press CTRL+C to quit)
INFO: 127.0.0.1:50307 - "GET / HTTP/1.1" 200 OK
INFO: 127.0.0.1:50307 - "GET /assets/index-B28WSRhf.js HTTP/1.1" 200 OK
INFO: 127.0.0.1:50307 - "GET /assets/index-BIhgNEQJ.css HTTP/1.1" 200 OK
INFO: 127.0.0.1:50307 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:50315 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:50317 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:50317 - "GET /favicon HTTP/1.1" 200 OK
INFO: 127.0.0.1:50317 - "GET /login HTTP/1.1" 200 OK
INFO: 127.0.0.1:50317 - "GET /logo?theme=dark& HTTP/1.1" 200 OK
INFO: 127.0.0.1:50317 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:50315 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:50307 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:50307 - "GET /auth/oauth/chainlit-keycloak HTTP/1.1" 307 Temporary Redirect
2025-06-11 13:57:56 - HTTP Request: POST http://10.65.37.239:8080/realms/master/protocol/openid-connect/token "HTTP/1.1 200 OK"
2025-06-11 13:57:57 - HTTP Request: GET http://10.65.37.239:8080/realms/master/protocol/openid-connect/userinfo "HTTP/1.1 200 OK"
INFO: 127.0.0.1:50415 - "GET /auth/oauth/chainlit-keycloak/callback?state=Ybg2D%24nMym%3DZoriieZzb%3As.KhI6%24xJvZ&session_state=e18c6678-3ab1-40a7-b029-feae13ffd730&iss=http%3A%2F%2F10.65.37.239%3A8080%2Frealms%2Fmaster&code=f69f3b5b-3a47-4dbc-9582-cbdba4c74040.e18c6678-3ab1-40a7-b029-feae13ffd730.c2cb61ae-c661-4d8f-a30c-eaa54c053c70 HTTP/1.1" 302 Found
INFO: 127.0.0.1:50415 - "GET /login/callback?success=True HTTP/1.1" 200 OK
INFO: 127.0.0.1:50415 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:50418 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:50415 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
2025-06-11 13:57:57 - Translated markdown file for zh-CN not found. Defaulting to chainlit.md.
INFO: 127.0.0.1:50415 - "GET /project/settings?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:50415 - "POST /set-session-cookie HTTP/1.1" 200 OK
INFO: 127.0.0.1:50415 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTaHAw HTTP/1.1" 200 OK
INFO: 127.0.0.1:50415 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTaHB2&sid=f5Q7w8XTp-P5DNFCAAAA HTTP/1.1" 200 OK
INFO: 127.0.0.1:50418 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTaHB4&sid=f5Q7w8XTp-P5DNFCAAAA HTTP/1.1" 200 OK
INFO: 127.0.0.1:50415 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTaHBC.0&sid=f5Q7w8XTp-P5DNFCAAAA HTTP/1.1" 200 OK
INFO: 127.0.0.1:50418 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTaHBC&sid=f5Q7w8XTp-P5DNFCAAAA HTTP/1.1" 200 OK
INFO: 127.0.0.1:50418 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTaHBN&sid=f5Q7w8XTp-P5DNFCAAAA HTTP/1.1" 200 OK
INFO: ('127.0.0.1', 50457) - "WebSocket /ws/socket.io/?EIO=4&transport=websocket&sid=f5Q7w8XTp-P5DNFCAAAA" [accepted]
INFO: 127.0.0.1:50418 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTaHBR&sid=f5Q7w8XTp-P5DNFCAAAA HTTP/1.1" 200 OK
INFO: 127.0.0.1:50447 - "GET /user HTTP/1.1" 200 OK
2025-06-11 13:58:07 - HTTP Request: POST https://dashscope.aliyuncs.com/compatible-mode/v1/chat/completions "HTTP/1.1 200 OK"
INFO: 127.0.0.1:50447 - "GET /avatars/Assistant HTTP/1.1" 200 OK
INFO: 127.0.0.1:50447 - "GET /avatars/qwen-plus HTTP/1.1" 200 OK
INFO: 127.0.0.1:50447 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:50447 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:63226 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:63227 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:63227 - "POST /logout HTTP/1.1" 200 OK
INFO: 127.0.0.1:63227 - "GET / HTTP/1.1" 200 OK
INFO: 127.0.0.1:63227 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:63226 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:63229 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:63229 - "GET /login HTTP/1.1" 200 OK
INFO: 127.0.0.1:63229 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:63226 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:63227 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:63368 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:63369 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:63369 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:63852 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:51541 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:51542 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:51542 - "GET /auth/oauth/chainlit-keycloak HTTP/1.1" 307 Temporary Redirect
2025-06-11 14:32:08 - HTTP Request: POST http://10.65.37.239:8080/realms/master/protocol/openid-connect/token "HTTP/1.1 200 OK"
2025-06-11 14:32:09 - HTTP Request: GET http://10.65.37.239:8080/realms/master/protocol/openid-connect/userinfo "HTTP/1.1 200 OK"
INFO: 127.0.0.1:51542 - "GET /auth/oauth/chainlit-keycloak/callback?state=V4iDQ*AhZKYUZkhQ81RUTKLUylfRi8Sd&session_state=69b670fa-4777-49e8-984c-53f774f5f450&iss=http%3A%2F%2F10.65.37.239%3A8080%2Frealms%2Fmaster&code=5fad669e-18f6-4bf1-852e-1c4a9be86a93.69b670fa-4777-49e8-984c-53f774f5f450.c2cb61ae-c661-4d8f-a30c-eaa54c053c70 HTTP/1.1" 302 Found
INFO: 127.0.0.1:51542 - "GET /login/callback?success=True HTTP/1.1" 200 OK
INFO: 127.0.0.1:51542 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:51543 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:51542 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
2025-06-11 14:32:09 - Translated markdown file for zh-CN not found. Defaulting to chainlit.md.
INFO: 127.0.0.1:51542 - "GET /project/settings?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:51542 - "POST /set-session-cookie HTTP/1.1" 200 OK
INFO: 127.0.0.1:51542 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTi68I HTTP/1.1" 200 OK
INFO: 127.0.0.1:51542 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTi68Q&sid=wZYwx15PyFRbphgYAAAC HTTP/1.1" 200 OK
INFO: 127.0.0.1:51543 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTi68R&sid=wZYwx15PyFRbphgYAAAC HTTP/1.1" 200 OK
INFO: 127.0.0.1:51542 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTi68Z&sid=wZYwx15PyFRbphgYAAAC HTTP/1.1" 200 OK
INFO: 127.0.0.1:51543 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTi68Y&sid=wZYwx15PyFRbphgYAAAC HTTP/1.1" 200 OK
INFO: 127.0.0.1:51543 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTi68g&sid=wZYwx15PyFRbphgYAAAC HTTP/1.1" 200 OK
INFO: ('127.0.0.1', 51637) - "WebSocket /ws/socket.io/?EIO=4&transport=websocket&sid=wZYwx15PyFRbphgYAAAC" [accepted]
INFO: 127.0.0.1:51543 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTi68m&sid=wZYwx15PyFRbphgYAAAC HTTP/1.1" 200 OK
2025-06-11 14:44:53 - 1 change detected
2025-06-11 14:44:53 - File modified: text_to_SQL.py. Reloading app...
http://10.65.37.239:8080
master
chainlit-client
7M7FzG7pVNe0RA84C75cgWk0VHzCCLm6
chainlit-keycloak
7M7FzG7pVNe0RA84C75cgWk0VHzCCLm6
sk-189ff68fba9d4ff884e718d8338ee075
INFO: 127.0.0.1:58914 - "GET / HTTP/1.1" 200 OK
INFO: 127.0.0.1:58914 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:58916 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:58914 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
2025-06-11 14:44:56 - Translated markdown file for zh-CN not found. Defaulting to chainlit.md.
INFO: 127.0.0.1:58914 - "GET /project/settings?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:58914 - "POST /set-session-cookie HTTP/1.1" 200 OK
INFO: 127.0.0.1:58914 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTl1O7 HTTP/1.1" 200 OK
INFO: 127.0.0.1:58914 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTl1OP&sid=t0Y2a0u2A4dUwnWBAAAE HTTP/1.1" 200 OK
INFO: 127.0.0.1:58916 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTl1OQ&sid=t0Y2a0u2A4dUwnWBAAAE HTTP/1.1" 200 OK
INFO: 127.0.0.1:58914 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTl1Ob&sid=t0Y2a0u2A4dUwnWBAAAE HTTP/1.1" 200 OK
INFO: 127.0.0.1:58916 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTl1OZ&sid=t0Y2a0u2A4dUwnWBAAAE HTTP/1.1" 200 OK
INFO: 127.0.0.1:58916 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTl1Ot&sid=t0Y2a0u2A4dUwnWBAAAE HTTP/1.1" 200 OK
INFO: ('127.0.0.1', 58938) - "WebSocket /ws/socket.io/?EIO=4&transport=websocket&sid=t0Y2a0u2A4dUwnWBAAAE" [accepted]
INFO: 127.0.0.1:58916 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTl1Ow&sid=t0Y2a0u2A4dUwnWBAAAE HTTP/1.1" 200 OK
INFO: 127.0.0.1:58928 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:58928 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:58928 - "POST /logout HTTP/1.1" 200 OK
INFO: 127.0.0.1:58928 - "GET / HTTP/1.1" 200 OK
INFO: 127.0.0.1:58928 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:59260 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:58928 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:58928 - "GET /login HTTP/1.1" 200 OK
INFO: 127.0.0.1:58928 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:59260 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:58928 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:58928 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:59260 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:59303 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:59303 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:59304 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:59304 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:59622 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:59822 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:59824 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:59824 - "GET /auth/oauth/chainlit-keycloak HTTP/1.1" 307 Temporary Redirect
2025-06-11 14:46:34 - HTTP Request: POST http://10.65.37.239:8080/realms/master/protocol/openid-connect/token "HTTP/1.1 200 OK"
2025-06-11 14:46:35 - HTTP Request: GET http://10.65.37.239:8080/realms/master/protocol/openid-connect/userinfo "HTTP/1.1 200 OK"
INFO: 127.0.0.1:59824 - "GET /auth/oauth/chainlit-keycloak/callback?state=cCWkfkL%3Dle0F*%3DJBdhzyBPc4M5qypDZv&session_state=69b670fa-4777-49e8-984c-53f774f5f450&iss=http%3A%2F%2F10.65.37.239%3A8080%2Frealms%2Fmaster&code=bc7de006-a3e9-452e-ab20-5efad0951d93.69b670fa-4777-49e8-984c-53f774f5f450.c2cb61ae-c661-4d8f-a30c-eaa54c053c70 HTTP/1.1" 302 Found
INFO: 127.0.0.1:59824 - "GET /login/callback?success=True HTTP/1.1" 200 OK
INFO: 127.0.0.1:59824 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:59822 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:59825 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
2025-06-11 14:46:35 - Translated markdown file for zh-CN not found. Defaulting to chainlit.md.
INFO: 127.0.0.1:59825 - "GET /project/settings?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:59825 - "POST /set-session-cookie HTTP/1.1" 200 OK
INFO: 127.0.0.1:59825 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlPWk HTTP/1.1" 200 OK
INFO: 127.0.0.1:59825 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTlPWt&sid=gs65c01bGM9t5p8gAAAG HTTP/1.1" 200 OK
INFO: 127.0.0.1:59822 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlPWu&sid=gs65c01bGM9t5p8gAAAG HTTP/1.1" 200 OK
INFO: 127.0.0.1:59825 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTlPW_&sid=gs65c01bGM9t5p8gAAAG HTTP/1.1" 200 OK
INFO: 127.0.0.1:59822 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlPW-&sid=gs65c01bGM9t5p8gAAAG HTTP/1.1" 200 OK
INFO: 127.0.0.1:59822 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlPXA&sid=gs65c01bGM9t5p8gAAAG HTTP/1.1" 200 OK
INFO: ('127.0.0.1', 59850) - "WebSocket /ws/socket.io/?EIO=4&transport=websocket&sid=gs65c01bGM9t5p8gAAAG" [accepted]
INFO: 127.0.0.1:59822 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlPXF&sid=gs65c01bGM9t5p8gAAAG HTTP/1.1" 200 OK
INFO: 127.0.0.1:59919 - "GET / HTTP/1.1" 200 OK
INFO: 127.0.0.1:59919 - "GET /assets/index-B28WSRhf.js HTTP/1.1" 200 OK
INFO: 127.0.0.1:59919 - "GET /assets/index-BIhgNEQJ.css HTTP/1.1" 200 OK
INFO: 127.0.0.1:59919 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:59928 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:59929 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:59929 - "GET /favicon HTTP/1.1" 200 OK
INFO: 127.0.0.1:59929 - "GET /login HTTP/1.1" 200 OK
INFO: 127.0.0.1:59929 - "GET /logo?theme=dark& HTTP/1.1" 200 OK
INFO: 127.0.0.1:59929 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:59928 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:59919 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:59919 - "GET /auth/oauth/chainlit-keycloak HTTP/1.1" 307 Temporary Redirect
2025-06-11 14:47:39 - HTTP Request: POST http://10.65.37.239:8080/realms/master/protocol/openid-connect/token "HTTP/1.1 200 OK"
2025-06-11 14:47:40 - HTTP Request: GET http://10.65.37.239:8080/realms/master/protocol/openid-connect/userinfo "HTTP/1.1 200 OK"
INFO: 127.0.0.1:60114 - "GET /auth/oauth/chainlit-keycloak/callback?state=Rx%25Hr.uNEG~Y%24V9l%3EY7wrsVR3%3E_n1%24-F&session_state=a453c204-b018-40f2-984a-7913ca83b2c9&iss=http%3A%2F%2F10.65.37.239%3A8080%2Frealms%2Fmaster&code=e0dcca7c-1f7c-40ec-806a-f50f8aac61cd.a453c204-b018-40f2-984a-7913ca83b2c9.c2cb61ae-c661-4d8f-a30c-eaa54c053c70 HTTP/1.1" 302 Found
INFO: 127.0.0.1:60114 - "GET /login/callback?success=True HTTP/1.1" 200 OK
INFO: 127.0.0.1:60114 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:60115 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60114 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
2025-06-11 14:47:40 - Translated markdown file for zh-CN not found. Defaulting to chainlit.md.
INFO: 127.0.0.1:60114 - "GET /project/settings?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60114 - "POST /set-session-cookie HTTP/1.1" 200 OK
INFO: 127.0.0.1:60114 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlfO2 HTTP/1.1" 200 OK
INFO: 127.0.0.1:60114 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTlfOC&sid=W9MFmv3qqXgFxzDlAAAI HTTP/1.1" 200 OK
INFO: 127.0.0.1:60115 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlfOD&sid=W9MFmv3qqXgFxzDlAAAI HTTP/1.1" 200 OK
INFO: 127.0.0.1:60114 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTlfOJ&sid=W9MFmv3qqXgFxzDlAAAI HTTP/1.1" 200 OK
INFO: 127.0.0.1:60115 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlfOI&sid=W9MFmv3qqXgFxzDlAAAI HTTP/1.1" 200 OK
INFO: 127.0.0.1:60115 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlfOT&sid=W9MFmv3qqXgFxzDlAAAI HTTP/1.1" 200 OK
INFO: ('127.0.0.1', 60128) - "WebSocket /ws/socket.io/?EIO=4&transport=websocket&sid=W9MFmv3qqXgFxzDlAAAI" [accepted]
INFO: 127.0.0.1:60115 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlfOX&sid=W9MFmv3qqXgFxzDlAAAI HTTP/1.1" 200 OK
INFO: 127.0.0.1:60126 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60126 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60228 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60228 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60271 - "GET /user HTTP/1.1" 200 OK
2025-06-11 14:48:10 - Retrying request to /chat/completions in 0.487590 seconds
2025-06-11 14:48:16 - Retrying request to /chat/completions in 0.839006 seconds
2025-06-11 14:48:17 - HTTP Request: POST https://dashscope.aliyuncs.com/compatible-mode/v1/chat/completions "HTTP/1.1 200 OK"
INFO: 127.0.0.1:60357 - "GET /avatars/Assistant HTTP/1.1" 200 OK
INFO: 127.0.0.1:60357 - "GET /avatars/qwen-plus HTTP/1.1" 200 OK
INFO: 127.0.0.1:60357 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60358 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60410 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60411 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60415 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60415 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60415 - "POST /logout HTTP/1.1" 200 OK
INFO: 127.0.0.1:60415 - "GET / HTTP/1.1" 200 OK
INFO: 127.0.0.1:60415 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:60479 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:60415 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60415 - "GET /login HTTP/1.1" 200 OK
INFO: 127.0.0.1:60415 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:60479 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:60415 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60415 - "GET /auth/oauth/chainlit-keycloak HTTP/1.1" 307 Temporary Redirect
2025-06-11 14:48:50 - HTTP Request: POST http://10.65.37.239:8080/realms/master/protocol/openid-connect/token "HTTP/1.1 200 OK"
2025-06-11 14:48:51 - HTTP Request: GET http://10.65.37.239:8080/realms/master/protocol/openid-connect/userinfo "HTTP/1.1 200 OK"
INFO: 127.0.0.1:60415 - "GET /auth/oauth/chainlit-keycloak/callback?state=GRv%3DyZw2%2Fj%3EFR%3E%3A%25TLuHbPK~4u%3EHMx%25G&session_state=a453c204-b018-40f2-984a-7913ca83b2c9&iss=http%3A%2F%2F10.65.37.239%3A8080%2Frealms%2Fmaster&code=c89ad3dd-6042-4e94-9e51-d7aa962b6af7.a453c204-b018-40f2-984a-7913ca83b2c9.c2cb61ae-c661-4d8f-a30c-eaa54c053c70 HTTP/1.1" 302 Found
INFO: 127.0.0.1:60415 - "GET /login/callback?success=True HTTP/1.1" 200 OK
INFO: 127.0.0.1:60415 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:60479 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60482 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
2025-06-11 14:48:51 - Translated markdown file for zh-CN not found. Defaulting to chainlit.md.
INFO: 127.0.0.1:60482 - "GET /project/settings?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60482 - "POST /set-session-cookie HTTP/1.1" 200 OK
INFO: 127.0.0.1:60482 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlwmQ HTTP/1.1" 200 OK
INFO: 127.0.0.1:60482 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTlwmY&sid=f7_nQWRj5C-PiHVEAAAK HTTP/1.1" 200 OK
INFO: 127.0.0.1:60479 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlwmY.0&sid=f7_nQWRj5C-PiHVEAAAK HTTP/1.1" 200 OK
INFO: 127.0.0.1:60482 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTlwmf&sid=f7_nQWRj5C-PiHVEAAAK HTTP/1.1" 200 OK
INFO: 127.0.0.1:60479 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlwme&sid=f7_nQWRj5C-PiHVEAAAK HTTP/1.1" 200 OK
INFO: 127.0.0.1:60479 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlwmm&sid=f7_nQWRj5C-PiHVEAAAK HTTP/1.1" 200 OK
INFO: ('127.0.0.1', 60526) - "WebSocket /ws/socket.io/?EIO=4&transport=websocket&sid=f7_nQWRj5C-PiHVEAAAK" [accepted]
INFO: 127.0.0.1:60479 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTlwmq&sid=f7_nQWRj5C-PiHVEAAAK HTTP/1.1" 200 OK
INFO: 127.0.0.1:60491 - "POST /logout HTTP/1.1" 200 OK
INFO: 127.0.0.1:60491 - "GET / HTTP/1.1" 200 OK
INFO: 127.0.0.1:60491 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:60491 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:60491 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60491 - "GET /login HTTP/1.1" 200 OK
INFO: 127.0.0.1:60491 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:60491 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:60491 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60491 - "GET /auth/oauth/chainlit-keycloak HTTP/1.1" 307 Temporary Redirect
2025-06-11 14:49:04 - HTTP Request: POST http://10.65.37.239:8080/realms/master/protocol/openid-connect/token "HTTP/1.1 200 OK"
2025-06-11 14:49:05 - HTTP Request: GET http://10.65.37.239:8080/realms/master/protocol/openid-connect/userinfo "HTTP/1.1 200 OK"
INFO: 127.0.0.1:60491 - "GET /auth/oauth/chainlit-keycloak/callback?state=Vgz7P%5E4m%2C%3AhO6DZckA8s7z7qc*Bx%240l.&session_state=a453c204-b018-40f2-984a-7913ca83b2c9&iss=http%3A%2F%2F10.65.37.239%3A8080%2Frealms%2Fmaster&code=01eee904-48cc-44f8-a2d1-9e9b2070a6f3.a453c204-b018-40f2-984a-7913ca83b2c9.c2cb61ae-c661-4d8f-a30c-eaa54c053c70 HTTP/1.1" 302 Found
INFO: 127.0.0.1:60491 - "GET /login/callback?success=True HTTP/1.1" 200 OK
INFO: 127.0.0.1:60491 - "GET /user HTTP/1.1" 200 OK
INFO: 127.0.0.1:60567 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:60568 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
2025-06-11 14:49:05 - Translated markdown file for zh-CN not found. Defaulting to chainlit.md.
INFO: 127.0.0.1:60568 - "GET /project/settings?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60568 - "POST /set-session-cookie HTTP/1.1" 200 OK
INFO: 127.0.0.1:60568 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTl-BC HTTP/1.1" 200 OK
INFO: 127.0.0.1:60568 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTl-BH&sid=2BgXYmAwfamF-B9gAAAM HTTP/1.1" 200 OK
INFO: 127.0.0.1:60567 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTl-BI&sid=2BgXYmAwfamF-B9gAAAM HTTP/1.1" 200 OK
INFO: 127.0.0.1:60568 - "POST /ws/socket.io/?EIO=4&transport=polling&t=PTTl-BY.0&sid=2BgXYmAwfamF-B9gAAAM HTTP/1.1" 200 OK
INFO: 127.0.0.1:60567 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTl-BY&sid=2BgXYmAwfamF-B9gAAAM HTTP/1.1" 200 OK
INFO: 127.0.0.1:60567 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTl-Be&sid=2BgXYmAwfamF-B9gAAAM HTTP/1.1" 200 OK
INFO: ('127.0.0.1', 60611) - "WebSocket /ws/socket.io/?EIO=4&transport=websocket&sid=2BgXYmAwfamF-B9gAAAM" [accepted]
INFO: 127.0.0.1:60567 - "GET /ws/socket.io/?EIO=4&transport=polling&t=PTTl-Bp&sid=2BgXYmAwfamF-B9gAAAM HTTP/1.1" 200 OK
INFO: 127.0.0.1:60668 - "GET / HTTP/1.1" 200 OK
INFO: 127.0.0.1:60668 - "GET /assets/index-B28WSRhf.js HTTP/1.1" 200 OK
INFO: 127.0.0.1:60668 - "GET /assets/index-BIhgNEQJ.css HTTP/1.1" 200 OK
INFO: 127.0.0.1:60668 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:60675 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:60676 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60676 - "GET /favicon HTTP/1.1" 200 OK
INFO: 127.0.0.1:60676 - "GET /login HTTP/1.1" 200 OK
INFO: 127.0.0.1:60676 - "GET /logo?theme=dark& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60676 - "GET /user HTTP/1.1" 401 Unauthorized
INFO: 127.0.0.1:60675 - "GET /auth/config HTTP/1.1" 200 OK
INFO: 127.0.0.1:60668 - "GET /project/translations?language=zh-CN& HTTP/1.1" 200 OK
INFO: 127.0.0.1:60668 - "GET /auth/oauth/chainlit-keycloak HTTP/1.1" 307 Temporary Redirect
INFO: Shutting down
INFO: Waiting for application shutdown.
发现的问题
注销后,不会再次弹出登录页面
我单击sign out(退出登录)后,再次点击“继续使用chainlit-keycloak”,并没有弹出keycloak登录页面,而是直接自动登录了,登录的用户是上一次点击注销的用户
可能的解决方案:
我在官方文档中看到了这样一部分代码,或许可以解决此问题,没有验证过。
关于chainlit .env文件的特别说明
.env文件最佳实际
不要有空格;
不要在值的两边加双引号;
决不能在值的末尾用#进行注释,应该另外加一行进行注释。
下面这个.env文件是符合规范的:
# OAUTH_KEYCLOAK_BASE_URL = "http://10.65.37.239:8080"
DASHSCOPE_API_KEY=<此处替换为你的api_key>
OPENAI_API_KEY=<此处替换为你的api_key>
OAUTH_KEYCLOAK_BASE_URL=http://10.65.37.239:8080
#OAUTH_KEYCLOAK_REALM的值就是keycloak中的REALM名,keycloak中默认的REALM是master,但是也可以再新建REALM
OAUTH_KEYCLOAK_REALM = "master"
OAUTH_KEYCLOAK_CLIENT_ID = "chainlit-client"
#下面这个环境变量的值可以在keycloak中直接复制:client--credentials--client secret
#OAUTH_KEYCLOAK_CLIENT_SECRET和CHAINLIT_AUTH_SECRET的值要保持一致,另外千万注意,不要在=号两边加上空格,也不要对环境变量的值用双引号,这会导致实际的环境变量值发生变化,从而导致chainlit身份认证出现问题。不要在环境变量值的后面加上#号,因为这会赋值给环境变量,如果要对.env文件进行注释,请在单独的行中进行注释。
OAUTH_KEYCLOAK_CLIENT_SECRET=7M7FzG7pVNe0RA84C75cgWk0VHzCCLm6
# CHAINLIT_AUTH_SECRET="F3rrs1vky1*MU9~ron_p1ntNfu2Rv1GiSWgl1p:$=>Yl0cRFubC?2=I1=$uCBLVS"
CHAINLIT_AUTH_SECRET=7M7FzG7pVNe0RA84C75cgWk0VHzCCLm6
#OAUTH_KEYCLOAK_NAME的值可以自己设置,如果不设置,默认为keycloak
OAUTH_KEYCLOAK_NAME = "chainlit-keycloak"
下面这种做法完全错误,会导致环境变量赋值错误。
更改.env文件后,要新创建终端
我注意到,更改.env文件后,如果重新启动chainlit应用,则chainlit获取到的环境变量的值仍然是旧的,是错误的,需要再创建一个终端,再次运行chainlit,才能真正应用当前的.env文件