Repository: ollama/ollama
Pull request: Server: Enhance API/tag with Capability Information

This change enhances the api/tag request by adding an additional row for each model's capability information. The solution reuses the GetModel function from the api/show endpoint. This PR addresses the feature request mentioned in #10097. It is believed that no existing test cases will need to be modified.

CONTRIBUTING: This PR adds extra capability information to the api/tags API.

Changed files:
filename: api/types.go
patch: @@ -457,12 +457,13 @@ type ProcessResponse struct {
 
 // ListModelResponse is a single model description in [ListResponse].
 type ListModelResponse struct {
-	Name       string       `json:"name"`
-	Model      string       `json:"model"`
-	ModifiedAt time.Time    `json:"modified_at"`
-	Size       int64        `json:"size"`
-	Digest     string       `json:"digest"`
-	Details    ModelDetails `json:"details,omitempty"`
+	Name         string             `json:"name"`
+	Model        string             `json:"model"`
+	ModifiedAt   time.Time          `json:"modified_at"`
+	Size         int64              `json:"size"`
+	Digest       string             `json:"digest"`
+	Capabilities []model.Capability `json:"capabilities,omitempty"`
+	Details      ModelDetails       `json:"details,omitempty"`
 }
 
 // ProcessModelResponse is a single model description in [ProcessResponse].

filename: docs/api.md
patch: @@ -1157,11 +1157,15 @@ A single JSON object will be returned.
 {
   "models": [
     {
-      "name": "deepseek-r1:latest",
-      "model": "deepseek-r1:latest",
-      "modified_at": "2025-05-10T08:06:48.639712648-07:00",
-      "size": 4683075271,
-      "digest": "0a8c266910232fd3291e71e5ba1e058cc5af9d411192cf88b6d30e92b6e73163",
+
+      "model": "codellama:13b",
+      "modified_at": "2023-11-04T14:56:49.277302595-07:00",
+      "size": 7365960935,
+      "digest": "9f438cb9cd581fc025612d27f7c1a6669ff83a8bb0ed86c94fcf4c5440555697",
+      "capabilities": [
+        "completion"
+      ],
+
       "details": {
         "parent_model": "",
         "format": "gguf",
@@ -1174,11 +1178,16 @@ A single JSON object will be returned.
       }
     },
     {
-      "name": "llama3.2:latest",
-      "model": "llama3.2:latest",
-      "modified_at": "2025-05-04T17:37:44.706015396-07:00",
-      "size": 2019393189,
-      "digest": "a80c4f17acd55265feec403c7aef86be0c25983ab279d83f3bcd3abbcb5b8b72",
+
+      "model": "llama4:latest",
+      "modified_at": "2023-12-07T09:32:18.757212583-08:00",
+      "size": 3825819519,
+      "digest": "fe938a131f40e6f6d40083c9f0f430a515233eb2edaa6d72eb85c50d64f2300e",
+      "capabilities": [
+        "completion",
+        "vision"
+      ],
+
       "details": {
         "parent_model": "",
         "format": "gguf",

filename: server/routes.go
patch: @@ -928,8 +928,7 @@ func (s *Server) ListHandler(c *gin.Context) {
 			}
 		}
 
-		// tag should never be masked
-		models = append(models, api.ListModelResponse{
+		r := api.ListModelResponse{
 			Model:      n.DisplayShortest(),
 			Name:       n.DisplayShortest(),
 			Size:       m.Size(),
@@ -942,7 +941,16 @@ func (s *Server) ListHandler(c *gin.Context) {
 				ParameterSize:     cf.ModelType,
 				QuantizationLevel: cf.FileType,
 			},
-		})
+		}
+
+		model, err := GetModel(n.String())
+		if err != nil {
+			slog.Warn("bad model details", "name", n, "error", err)
+		} else {
+			r.Capabilities = model.Capabilities()
+		}
+
+		models = append(models, r)
 	}
 
 	slices.SortStableFunc(models, func(i, j api.ListModelResponse) int {