(w http.ResponseWriter, req *http.Request)
| 122 | } |
| 123 | |
| 124 | func (rs *ragServer) queryHandler(w http.ResponseWriter, req *http.Request) { |
| 125 | // Parse HTTP request from JSON. |
| 126 | type queryRequest struct { |
| 127 | Content string |
| 128 | } |
| 129 | qr := &queryRequest{} |
| 130 | err := readRequestJSON(req, qr) |
| 131 | if err != nil { |
| 132 | http.Error(w, err.Error(), http.StatusBadRequest) |
| 133 | return |
| 134 | } |
| 135 | |
| 136 | // Embed the query contents. |
| 137 | rsp, err := rs.embModel.EmbedContent(rs.ctx, genai.Text(qr.Content)) |
| 138 | if err != nil { |
| 139 | http.Error(w, err.Error(), http.StatusInternalServerError) |
| 140 | return |
| 141 | } |
| 142 | |
| 143 | // Search weaviate to find the most relevant (closest in vector space) |
| 144 | // documents to the query. |
| 145 | gql := rs.wvClient.GraphQL() |
| 146 | result, err := gql.Get(). |
| 147 | WithNearVector( |
| 148 | gql.NearVectorArgBuilder().WithVector(rsp.Embedding.Values)). |
| 149 | WithClassName("Document"). |
| 150 | WithFields(graphql.Field{Name: "text"}). |
| 151 | WithLimit(3). |
| 152 | Do(rs.ctx) |
| 153 | if werr := combinedWeaviateError(result, err); werr != nil { |
| 154 | http.Error(w, werr.Error(), http.StatusInternalServerError) |
| 155 | return |
| 156 | } |
| 157 | |
| 158 | contents, err := decodeGetResults(result) |
| 159 | if err != nil { |
| 160 | http.Error(w, fmt.Errorf("reading weaviate response: %w", err).Error(), http.StatusInternalServerError) |
| 161 | return |
| 162 | } |
| 163 | |
| 164 | // Create a RAG query for the LLM with the most relevant documents as |
| 165 | // context. |
| 166 | ragQuery := fmt.Sprintf(ragTemplateStr, qr.Content, strings.Join(contents, "\n")) |
| 167 | resp, err := rs.genModel.GenerateContent(rs.ctx, genai.Text(ragQuery)) |
| 168 | if err != nil { |
| 169 | log.Printf("calling generative model: %v", err.Error()) |
| 170 | http.Error(w, "generative model error", http.StatusInternalServerError) |
| 171 | return |
| 172 | } |
| 173 | |
| 174 | if len(resp.Candidates) != 1 { |
| 175 | log.Printf("got %v candidates, expected 1", len(resp.Candidates)) |
| 176 | http.Error(w, "generative model error", http.StatusInternalServerError) |
| 177 | return |
| 178 | } |
| 179 | |
| 180 | var respTexts []string |
| 181 | for _, part := range resp.Candidates[0].Content.Parts { |
nothing calls this directly
no test coverage detected