update the modal deployment logic
All checks were successful
Triton Modal Trigger / deploy-to-modal (push) Successful in 11s
All checks were successful
Triton Modal Trigger / deploy-to-modal (push) Successful in 11s
This commit is contained in:
@@ -7,7 +7,7 @@ jobs:
|
|||||||
deploy-to-modal:
|
deploy-to-modal:
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
container:
|
container:
|
||||||
image: gitea-modal-runner:latest
|
image: gitea-modal-runner:latest # where build the code
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- name: Checkout code
|
- name: Checkout code
|
||||||
|
|||||||
@@ -25,16 +25,36 @@ triton_image = (
|
|||||||
)
|
)
|
||||||
|
|
||||||
app = modal.App("triton-s3-service", image=triton_image)
|
app = modal.App("triton-s3-service", image=triton_image)
|
||||||
from fastapi import FastAPI, Response, Request,HTTPException
|
|
||||||
from fastapi.responses import StreamingResponse # 👈 ADD THIS IMPORT
|
|
||||||
import httpx
|
|
||||||
web_app = FastAPI()
|
|
||||||
# -------------------------------------------------------------
|
# -------------------------------------------------------------
|
||||||
# FASTAPI PROXY ROUTING (Living inside the container)
|
# THE UNIFIED SERVICE FUNCTION (1 Container, 1 GPU, 1 Triton Process)
|
||||||
# -------------------------------------------------------------
|
# -------------------------------------------------------------
|
||||||
|
|
||||||
@web_app.get("/v2/health/ready")
|
@app.function(
|
||||||
async def forward_health():
|
gpu="T4", # for the expense
|
||||||
|
timeout=3600,
|
||||||
|
max_containers=3, # Strict production capping
|
||||||
|
min_containers=1, # for keeping warm and prevention,
|
||||||
|
buffer_containers=2, # Number of additional idle containers to maintain under active load.
|
||||||
|
scaledown_window=30, # Max time (in seconds) a container can remain idle while scaling down.
|
||||||
|
volumes= {
|
||||||
|
'/mnt/vkist-ml-model' : modal.CloudBucketMount(bucket_name="vkist-ml-model", secret=modal.Secret.from_name("aws-secrets"))
|
||||||
|
},
|
||||||
|
secrets=[modal.Secret.from_name("aws-secrets")]
|
||||||
|
)
|
||||||
|
@modal.asgi_app()
|
||||||
|
def unified_triton_server():
|
||||||
|
|
||||||
|
from fastapi import FastAPI, Response, Request,HTTPException
|
||||||
|
from fastapi.responses import StreamingResponse # 👈 ADD THIS IMPORT
|
||||||
|
import httpx
|
||||||
|
web_app = FastAPI()
|
||||||
|
# -------------------------------------------------------------
|
||||||
|
# FASTAPI PROXY ROUTING (Living inside the container)
|
||||||
|
# -------------------------------------------------------------
|
||||||
|
|
||||||
|
@web_app.get("/v2/health/ready")
|
||||||
|
async def forward_health():
|
||||||
"""Proxies external HTTP REST calls straight to Triton's internal inference engine"""
|
"""Proxies external HTTP REST calls straight to Triton's internal inference engine"""
|
||||||
async with httpx.AsyncClient() as client:
|
async with httpx.AsyncClient() as client:
|
||||||
try:
|
try:
|
||||||
@@ -43,9 +63,9 @@ async def forward_health():
|
|||||||
except Exception as e:
|
except Exception as e:
|
||||||
return Response(content=f"Triton booting models from S3... Error: {str(e)}", status_code=503)
|
return Response(content=f"Triton booting models from S3... Error: {str(e)}", status_code=503)
|
||||||
|
|
||||||
@web_app.get("/metrics")
|
@web_app.get("/metrics")
|
||||||
@web_app.get("/")
|
@web_app.get("/")
|
||||||
async def forward_metrics():
|
async def forward_metrics():
|
||||||
"""Proxies external metric calls straight to Triton's internal metrics engine"""
|
"""Proxies external metric calls straight to Triton's internal metrics engine"""
|
||||||
async with httpx.AsyncClient() as client:
|
async with httpx.AsyncClient() as client:
|
||||||
try:
|
try:
|
||||||
@@ -54,9 +74,9 @@ async def forward_metrics():
|
|||||||
except Exception as e:
|
except Exception as e:
|
||||||
return Response(content=f"Waiting for metrics channel... Error: {str(e)}", status_code=503)
|
return Response(content=f"Waiting for metrics channel... Error: {str(e)}", status_code=503)
|
||||||
|
|
||||||
# 👇 ADD THIS CATCH-ALL ROUTE HERE 👇
|
# 👇 ADD THIS CATCH-ALL ROUTE HERE 👇
|
||||||
@web_app.api_route("/v2/{path:path}", methods=["GET", "POST"])
|
@web_app.api_route("/v2/{path:path}", methods=["GET", "POST"])
|
||||||
async def proxy_all_triton_request(path: str, request: Request):
|
async def proxy_all_triton_request(path: str, request: Request):
|
||||||
import tritonclient.grpc.aio as grpcclient
|
import tritonclient.grpc.aio as grpcclient
|
||||||
from tritonclient.grpc import service_pb2, service_pb2_grpc
|
from tritonclient.grpc import service_pb2, service_pb2_grpc
|
||||||
from tritonclient.grpc import _utils as grpc_utils #InferenceServerClient
|
from tritonclient.grpc import _utils as grpc_utils #InferenceServerClient
|
||||||
@@ -188,30 +208,12 @@ async def proxy_all_triton_request(path: str, request: Request):
|
|||||||
status_code=502
|
status_code=502
|
||||||
)
|
)
|
||||||
|
|
||||||
@web_app.get("/v2/models")
|
@web_app.get("/v2/models")
|
||||||
async def forward_list_models():
|
async def forward_list_models():
|
||||||
async with httpx.AsyncClient() as client:
|
async with httpx.AsyncClient() as client:
|
||||||
r = await client.get("http://127.0.0.1:8000/v2/models")
|
r = await client.get("http://127.0.0.1:8000/v2/models")
|
||||||
return Response(content=r.content, status_code=r.status_code, media_type=r.headers.get("content-type"))
|
return Response(content=r.content, status_code=r.status_code, media_type=r.headers.get("content-type"))
|
||||||
|
|
||||||
# -------------------------------------------------------------
|
|
||||||
# THE UNIFIED SERVICE FUNCTION (1 Container, 1 GPU, 1 Triton Process)
|
|
||||||
# -------------------------------------------------------------
|
|
||||||
|
|
||||||
@app.function(
|
|
||||||
gpu="T4", # for the expense
|
|
||||||
timeout=3600,
|
|
||||||
max_containers=3, # Strict production capping
|
|
||||||
min_containers=1, # for keeping warm and prevention,
|
|
||||||
buffer_containers=2, # Number of additional idle containers to maintain under active load.
|
|
||||||
scaledown_window=30, # Max time (in seconds) a container can remain idle while scaling down.
|
|
||||||
volumes= {
|
|
||||||
'/mnt/vkist-ml-model' : modal.CloudBucketMount(bucket_name="vkist-ml-model", secret=modal.Secret.from_name("aws-secrets"))
|
|
||||||
},
|
|
||||||
secrets=[modal.Secret.from_name("aws-secrets")]
|
|
||||||
)
|
|
||||||
@modal.asgi_app()
|
|
||||||
def unified_triton_server():
|
|
||||||
print("🚀 Booting ONE Triton Instance inside ONE A100 Container...")
|
print("🚀 Booting ONE Triton Instance inside ONE A100 Container...")
|
||||||
|
|
||||||
# Spawns Triton in the background. It will automatically read
|
# Spawns Triton in the background. It will automatically read
|
||||||
|
|||||||
Reference in New Issue
Block a user