mirror of
https://github.com/qodo-ai/pr-agent.git
synced 2025-07-04 04:40:38 +08:00
feat: Improved server, security and commands
Signed-off-by: Luca Simone <info@lucasimone.info>
This commit is contained in:
@ -1,4 +1,5 @@
|
|||||||
import json
|
import json
|
||||||
|
import os
|
||||||
|
|
||||||
import uvicorn
|
import uvicorn
|
||||||
from fastapi import APIRouter, FastAPI
|
from fastapi import APIRouter, FastAPI
|
||||||
@ -13,35 +14,55 @@ from starlette_context.middleware import RawContextMiddleware
|
|||||||
from pr_agent.agent.pr_agent import PRAgent
|
from pr_agent.agent.pr_agent import PRAgent
|
||||||
from pr_agent.config_loader import get_settings
|
from pr_agent.config_loader import get_settings
|
||||||
from pr_agent.log import get_logger
|
from pr_agent.log import get_logger
|
||||||
|
from pr_agent.servers.utils import verify_signature
|
||||||
|
|
||||||
router = APIRouter()
|
router = APIRouter()
|
||||||
|
|
||||||
|
|
||||||
def handle_request(background_tasks: BackgroundTasks, url: str, body: str, log_context: dict):
|
def handle_request(
|
||||||
|
background_tasks: BackgroundTasks, url: str, body: str, log_context: dict
|
||||||
|
):
|
||||||
log_context["action"] = body
|
log_context["action"] = body
|
||||||
log_context["event"] = "pull_request" if body == "review" else "comment"
|
|
||||||
log_context["api_url"] = url
|
log_context["api_url"] = url
|
||||||
with get_logger().contextualize(**log_context):
|
with get_logger().contextualize(**log_context):
|
||||||
background_tasks.add_task(PRAgent().handle_request, url, body)
|
background_tasks.add_task(PRAgent().handle_request, url, body)
|
||||||
|
|
||||||
|
|
||||||
@router.post("/webhook")
|
@router.post("/")
|
||||||
async def handle_webhook(background_tasks: BackgroundTasks, request: Request):
|
async def handle_webhook(background_tasks: BackgroundTasks, request: Request):
|
||||||
log_context = {"server_type": "bitbucket_server"}
|
log_context = {"server_type": "bitbucket_server"}
|
||||||
data = await request.json()
|
data = await request.json()
|
||||||
get_logger().info(json.dumps(data))
|
get_logger().info(json.dumps(data))
|
||||||
|
|
||||||
pr_id = data['pullRequest']['id']
|
webhook_secret = getattr(get_settings().bitbucket_server, "webhook_secret", None)
|
||||||
repository_name = data['pullRequest']['toRef']['repository']['slug']
|
if webhook_secret:
|
||||||
project_name = data['pullRequest']['toRef']['repository']['project']['key']
|
body_bytes = await request.body()
|
||||||
|
signature_header = request.headers.get("x-hub-signature", None)
|
||||||
|
verify_signature(body_bytes, webhook_secret, signature_header)
|
||||||
|
|
||||||
|
pr_id = data["pullRequest"]["id"]
|
||||||
|
repository_name = data["pullRequest"]["toRef"]["repository"]["slug"]
|
||||||
|
project_name = data["pullRequest"]["toRef"]["repository"]["project"]["key"]
|
||||||
bitbucket_server = get_settings().get("BITBUCKET_SERVER.URL")
|
bitbucket_server = get_settings().get("BITBUCKET_SERVER.URL")
|
||||||
pr_url = f"{bitbucket_server}/projects/{project_name}/repos/{repository_name}/pull-requests/{pr_id}"
|
pr_url = f"{bitbucket_server}/projects/{project_name}/repos/{repository_name}/pull-requests/{pr_id}"
|
||||||
|
|
||||||
log_context["api_url"] = pr_url
|
log_context["api_url"] = pr_url
|
||||||
log_context["event"] = "pull_request"
|
log_context["event"] = "pull_request"
|
||||||
|
|
||||||
handle_request(background_tasks, pr_url, "review", log_context)
|
if data["eventKey"] == "pr:opened":
|
||||||
return JSONResponse(status_code=status.HTTP_200_OK, content=jsonable_encoder({"message": "success"}))
|
body = "review"
|
||||||
|
elif data["eventKey"] == "pr:comment:added":
|
||||||
|
body = data["comment"]["text"]
|
||||||
|
else:
|
||||||
|
return JSONResponse(
|
||||||
|
status_code=status.HTTP_400_BAD_REQUEST,
|
||||||
|
content=json.dumps({"message": "Unsupported event"}),
|
||||||
|
)
|
||||||
|
|
||||||
|
handle_request(background_tasks, pr_url, body, log_context)
|
||||||
|
return JSONResponse(
|
||||||
|
status_code=status.HTTP_200_OK, content=jsonable_encoder({"message": "success"})
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
@router.get("/")
|
@router.get("/")
|
||||||
@ -50,15 +71,10 @@ async def root():
|
|||||||
|
|
||||||
|
|
||||||
def start():
|
def start():
|
||||||
bitbucket_server_url = get_settings().get("BITBUCKET_SERVER.URL", None)
|
app = FastAPI(middleware=[Middleware(RawContextMiddleware)])
|
||||||
if not bitbucket_server_url:
|
|
||||||
raise ValueError("BITBUCKET_SERVER.URL is not set")
|
|
||||||
get_settings().config.git_provider = "bitbucket_server"
|
|
||||||
middleware = [Middleware(RawContextMiddleware)]
|
|
||||||
app = FastAPI(middleware=middleware)
|
|
||||||
app.include_router(router)
|
app.include_router(router)
|
||||||
uvicorn.run(app, host="0.0.0.0", port=3000)
|
uvicorn.run(app, host="0.0.0.0", port=int(os.environ.get("PORT", "3000")))
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == "__main__":
|
||||||
start()
|
start()
|
||||||
|
@ -65,6 +65,11 @@ personal_access_token = ""
|
|||||||
# For Bitbucket personal/repository bearer token
|
# For Bitbucket personal/repository bearer token
|
||||||
bearer_token = ""
|
bearer_token = ""
|
||||||
|
|
||||||
|
[bitbucket_server]
|
||||||
|
# For Bitbucket Server bearer token
|
||||||
|
auth_token = ""
|
||||||
|
webhook_secret = ""
|
||||||
|
|
||||||
# For Bitbucket app
|
# For Bitbucket app
|
||||||
app_key = ""
|
app_key = ""
|
||||||
base_url = ""
|
base_url = ""
|
||||||
|
@ -158,6 +158,11 @@ polling_interval_seconds = 30
|
|||||||
# token to authenticate in the patch server
|
# token to authenticate in the patch server
|
||||||
# patch_server_token = ""
|
# patch_server_token = ""
|
||||||
|
|
||||||
|
[bitbucket_server]
|
||||||
|
# URL to the BitBucket Server instance
|
||||||
|
# url = "https://git.bitbucket.com"
|
||||||
|
url = ""
|
||||||
|
|
||||||
[litellm]
|
[litellm]
|
||||||
#use_client = false
|
#use_client = false
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user