Files
llmgw/internal/router/audio.go
T

63 lines
1.8 KiB
Go

package router
import (
"bytes"
"errors"
"mime"
"mime/multipart"
"net/http"
"strings"
"gitea.mynodes.xyz/ilker/llmgw/internal/auth"
)
// parseForm reads a multipart request — audio sent for transcription — for
// what routing needs, the model, and keeps the body to send on unchanged.
func (r *Router) parseForm(req *http.Request, path, ct string, body []byte) (*parsedRequest, error) {
_, params, err := mime.ParseMediaType(ct)
if err != nil || params["boundary"] == "" {
return nil, errors.New("a multipart form needs its boundary")
}
mr := multipart.NewReader(bytes.NewReader(body), params["boundary"])
model, stream := "", false
for {
part, err := mr.NextPart()
if err != nil {
break
}
switch part.FormName() {
case "model":
var b bytes.Buffer
_, _ = b.ReadFrom(part)
model = strings.TrimSpace(b.String())
case "stream":
var b bytes.Buffer
_, _ = b.ReadFrom(part)
stream = strings.TrimSpace(b.String()) == "true"
}
part.Close()
}
if model == "" {
return nil, errors.New("model is required")
}
tags, err := requestTags(nil, req.Header.Get(tagsHeader))
if err != nil {
return nil, err
}
p := &parsedRequest{
Path: path, ContentType: ct, Model: model, RequestedModel: model, Stream: stream,
UpstreamBody: body, Header: req.Header, Tags: tags,
SessionID: sessionID(req, r.cfg.SessionHeader, ""),
Band: req.Header.Get(r.cfg.Admission.BandHeader),
ProfileOverride: req.Header.Get("x-llmgw-profile"),
}
if principal, ok := auth.FromContext(req.Context()); ok {
p.Band = principal.Band
p.ProfileOverride = principal.RoutingProfile
p.KeyID, p.UserID, p.ProjectID = principal.KeyID, principal.UserID, principal.ProjectID
p.TeamID, p.OrgID = principal.TeamID, principal.OrgID
p.Tenant = principal.KeyID
}
return p, nil
}