diff --git a/.golangci.yaml b/.golangci.yaml index 2adeee613..f7284e10a 100644 --- a/.golangci.yaml +++ b/.golangci.yaml @@ -38,6 +38,7 @@ linters: - unused - misspell - whitespace + - errorlint #- gosec #- revive @@ -121,4 +122,4 @@ issues: # Default: 50 max-issues-per-linter: 0 # Maximum count of issues with the same text. Set to 0 to disable. Default is 3. - max-same-issues: 0 \ No newline at end of file + max-same-issues: 0 diff --git a/cli/kthena/cmd/create.go b/cli/kthena/cmd/create.go index 7c16da7f3..a85e21164 100644 --- a/cli/kthena/cmd/create.go +++ b/cli/kthena/cmd/create.go @@ -97,13 +97,13 @@ func runCreateManifest(cmd *cobra.Command, args []string) error { // Load template values values, err := loadTemplateValues() if err != nil { - return fmt.Errorf("failed to load template values: %v", err) + return fmt.Errorf("failed to load template values: %w", err) } // Render template renderedYAML, err := renderTemplate(templateName, values) if err != nil { - return fmt.Errorf("failed to render template: %v", err) + return fmt.Errorf("failed to render template: %w", err) } // Show rendered YAML @@ -134,11 +134,11 @@ func loadTemplateValues() (map[string]interface{}, error) { if valuesFile != "" { data, err := os.ReadFile(valuesFile) if err != nil { - return nil, fmt.Errorf("failed to read values file: %v", err) + return nil, fmt.Errorf("failed to read values file: %w", err) } if err := yaml.Unmarshal(data, &values); err != nil { - return nil, fmt.Errorf("failed to parse values file: %v", err) + return nil, fmt.Errorf("failed to parse values file: %w", err) } } @@ -169,7 +169,7 @@ func renderTemplate(templateName string, values map[string]interface{}) (string, // Get template content from embedded files templateData, err := GetTemplateContent(templateName) if err != nil { - return "", fmt.Errorf("failed to read template: %v", err) + return "", fmt.Errorf("failed to read template: %w", err) } // Create Helm template engine @@ -199,7 +199,7 @@ func renderTemplate(templateName string, values map[string]interface{}) (string, // Render template using Helm engine rendered, err := helmEngine.Render(helmChart, helmValues) if err != nil { - return "", fmt.Errorf("failed to render template: %v", err) + return "", fmt.Errorf("failed to render template: %w", err) } // Get rendered content for our template @@ -228,13 +228,13 @@ func applyResources(yamlContent string) error { // Load kubeconfig config, err := clientcmd.BuildConfigFromFlags("", clientcmd.RecommendedHomeFile) if err != nil { - return fmt.Errorf("failed to load kubeconfig: %v", err) + return fmt.Errorf("failed to load kubeconfig: %w", err) } // Create kthena client client, err := versioned.NewForConfig(config) if err != nil { - return fmt.Errorf("failed to create kthena client: %v", err) + return fmt.Errorf("failed to create kthena client: %w", err) } ctx := context.Background() @@ -248,7 +248,7 @@ func applyResources(yamlContent string) error { if err.Error() == "EOF" { break } - return fmt.Errorf("failed to decode YAML: %v", err) + return fmt.Errorf("failed to decode YAML: %w", err) } if rawObj == nil { @@ -270,7 +270,7 @@ func applyResources(yamlContent string) error { // Apply based on resource type if err := applyKthenaResource(ctx, client, obj); err != nil { - return fmt.Errorf("failed to apply %s %s: %v", gvk.Kind, resourceName, err) + return fmt.Errorf("failed to apply %s %s: %w", gvk.Kind, resourceName, err) } fmt.Printf(" ✓ Applied successfully\n") @@ -292,12 +292,12 @@ func applyKthenaResource(ctx context.Context, client versioned.Interface, obj *u modelServing := &workloadv1alpha1.ModelServing{} err := runtime.DefaultUnstructuredConverter.FromUnstructured(obj.Object, modelServing) if err != nil { - return fmt.Errorf("failed to convert unstructured object to ModelServing: %v", err) + return fmt.Errorf("failed to convert unstructured object to ModelServing: %w", err) } _, err = client.WorkloadV1alpha1().ModelServings(resourceNamespace).Create(ctx, modelServing, metav1.CreateOptions{}) if err != nil { - return fmt.Errorf("failed to create ModelServing: %v", err) + return fmt.Errorf("failed to create ModelServing: %w", err) } case "ModelBooster": @@ -305,12 +305,12 @@ func applyKthenaResource(ctx context.Context, client versioned.Interface, obj *u model := &workloadv1alpha1.ModelBooster{} err := runtime.DefaultUnstructuredConverter.FromUnstructured(obj.Object, model) if err != nil { - return fmt.Errorf("failed to convert unstructured object to ModelBooster: %v", err) + return fmt.Errorf("failed to convert unstructured object to ModelBooster: %w", err) } _, err = client.WorkloadV1alpha1().ModelBoosters(resourceNamespace).Create(ctx, model, metav1.CreateOptions{}) if err != nil { - return fmt.Errorf("failed to create ModelBooster: %v", err) + return fmt.Errorf("failed to create ModelBooster: %w", err) } case "AutoscalingPolicy": @@ -318,12 +318,12 @@ func applyKthenaResource(ctx context.Context, client versioned.Interface, obj *u policy := &workloadv1alpha1.AutoscalingPolicy{} err := runtime.DefaultUnstructuredConverter.FromUnstructured(obj.Object, policy) if err != nil { - return fmt.Errorf("failed to convert unstructured object to AutoscalingPolicy: %v", err) + return fmt.Errorf("failed to convert unstructured object to AutoscalingPolicy: %w", err) } _, err = client.WorkloadV1alpha1().AutoscalingPolicies(resourceNamespace).Create(ctx, policy, metav1.CreateOptions{}) if err != nil { - return fmt.Errorf("failed to create AutoscalingPolicy: %v", err) + return fmt.Errorf("failed to create AutoscalingPolicy: %w", err) } case "ModelRoute": @@ -331,12 +331,12 @@ func applyKthenaResource(ctx context.Context, client versioned.Interface, obj *u modelRoute := &networkingv1alpha1.ModelRoute{} err := runtime.DefaultUnstructuredConverter.FromUnstructured(obj.Object, modelRoute) if err != nil { - return fmt.Errorf("failed to convert unstructured object to ModelRoute: %v", err) + return fmt.Errorf("failed to convert unstructured object to ModelRoute: %w", err) } _, err = client.NetworkingV1alpha1().ModelRoutes(resourceNamespace).Create(ctx, modelRoute, metav1.CreateOptions{}) if err != nil { - return fmt.Errorf("failed to create ModelRoute: %v", err) + return fmt.Errorf("failed to create ModelRoute: %w", err) } case "ModelServer": @@ -344,12 +344,12 @@ func applyKthenaResource(ctx context.Context, client versioned.Interface, obj *u modelServer := &networkingv1alpha1.ModelServer{} err := runtime.DefaultUnstructuredConverter.FromUnstructured(obj.Object, modelServer) if err != nil { - return fmt.Errorf("failed to convert unstructured object to ModelServer: %v", err) + return fmt.Errorf("failed to convert unstructured object to ModelServer: %w", err) } _, err = client.NetworkingV1alpha1().ModelServers(resourceNamespace).Create(ctx, modelServer, metav1.CreateOptions{}) if err != nil { - return fmt.Errorf("failed to create ModelServer: %v", err) + return fmt.Errorf("failed to create ModelServer: %w", err) } default: diff --git a/cli/kthena/cmd/describe.go b/cli/kthena/cmd/describe.go index ef2a41e5e..cf93f4eef 100644 --- a/cli/kthena/cmd/describe.go +++ b/cli/kthena/cmd/describe.go @@ -133,7 +133,7 @@ func runDescribeTemplate(cmd *cobra.Command, args []string) error { // Read template content from embedded files content, err := GetTemplateContent(templateName) if err != nil { - return fmt.Errorf("failed to read template: %v", err) + return fmt.Errorf("failed to read template: %w", err) } fmt.Println("=================") fmt.Println("Template Content:") @@ -159,7 +159,7 @@ func runDescribeModelBooster(cmd *cobra.Command, args []string) error { model, err := client.WorkloadV1alpha1().ModelBoosters(namespace).Get(ctx, modelName, metav1.GetOptions{}) if err != nil { - return fmt.Errorf("failed to get Model '%s': %v", modelName, err) + return fmt.Errorf("failed to get Model '%s': %w", modelName, err) } fmt.Printf("Model: %s\n", model.Name) @@ -171,7 +171,7 @@ func runDescribeModelBooster(cmd *cobra.Command, args []string) error { // Output the full resource as YAML data, err := yaml.Marshal(model) if err != nil { - return fmt.Errorf("failed to marshal Model to YAML: %v", err) + return fmt.Errorf("failed to marshal Model to YAML: %w", err) } fmt.Println("Resource Details:") @@ -197,7 +197,7 @@ func runDescribeModelServing(cmd *cobra.Command, args []string) error { modelServing, err := client.WorkloadV1alpha1().ModelServings(namespace).Get(ctx, modelServingName, metav1.GetOptions{}) if err != nil { - return fmt.Errorf("failed to get ModelServing '%s': %v", modelServingName, err) + return fmt.Errorf("failed to get ModelServing '%s': %w", modelServingName, err) } fmt.Printf("ModelServing: %s\n", modelServing.Name) @@ -209,7 +209,7 @@ func runDescribeModelServing(cmd *cobra.Command, args []string) error { // Output the full resource as YAML data, err := yaml.Marshal(modelServing) if err != nil { - return fmt.Errorf("failed to marshal ModelServing to YAML: %v", err) + return fmt.Errorf("failed to marshal ModelServing to YAML: %w", err) } fmt.Println("Resource Details:") @@ -235,7 +235,7 @@ func runDescribeAutoscalingPolicy(cmd *cobra.Command, args []string) error { policy, err := client.WorkloadV1alpha1().AutoscalingPolicies(namespace).Get(ctx, policyName, metav1.GetOptions{}) if err != nil { - return fmt.Errorf("failed to get AutoscalingPolicy '%s': %v", policyName, err) + return fmt.Errorf("failed to get AutoscalingPolicy '%s': %w", policyName, err) } fmt.Printf("AutoscalingPolicy: %s\n", policy.Name) @@ -247,7 +247,7 @@ func runDescribeAutoscalingPolicy(cmd *cobra.Command, args []string) error { // Output the full resource as YAML data, err := yaml.Marshal(policy) if err != nil { - return fmt.Errorf("failed to marshal AutoscalingPolicy to YAML: %v", err) + return fmt.Errorf("failed to marshal AutoscalingPolicy to YAML: %w", err) } fmt.Println("Resource Details:") @@ -272,7 +272,7 @@ func runDescribeModelRoute(cmd *cobra.Command, args []string) error { route, err := client.NetworkingV1alpha1().ModelRoutes(namespace).Get(ctx, routeName, metav1.GetOptions{}) if err != nil { - return fmt.Errorf("failed to get ModelRoute '%s': %v", routeName, err) + return fmt.Errorf("failed to get ModelRoute '%s': %w", routeName, err) } fmt.Printf("ModelRoute: %s\n", route.Name) @@ -283,7 +283,7 @@ func runDescribeModelRoute(cmd *cobra.Command, args []string) error { data, err := yaml.Marshal(route) if err != nil { - return fmt.Errorf("failed to marshal ModelRoute to YAML: %v", err) + return fmt.Errorf("failed to marshal ModelRoute to YAML: %w", err) } fmt.Println("Resource Details:") @@ -309,7 +309,7 @@ func runDescribeModelServer(cmd *cobra.Command, args []string) error { server, err := client.NetworkingV1alpha1().ModelServers(namespace).Get(ctx, serverName, metav1.GetOptions{}) if err != nil { - return fmt.Errorf("failed to get ModelServer '%s': %v", serverName, err) + return fmt.Errorf("failed to get ModelServer '%s': %w", serverName, err) } fmt.Printf("ModelServer: %s\n", server.Name) @@ -320,7 +320,7 @@ func runDescribeModelServer(cmd *cobra.Command, args []string) error { data, err := yaml.Marshal(server) if err != nil { - return fmt.Errorf("failed to marshal ModelServer to YAML: %v", err) + return fmt.Errorf("failed to marshal ModelServer to YAML: %w", err) } fmt.Println("Resource Details:") diff --git a/cli/kthena/cmd/get.go b/cli/kthena/cmd/get.go index 31cbef09b..911444737 100644 --- a/cli/kthena/cmd/get.go +++ b/cli/kthena/cmd/get.go @@ -128,7 +128,7 @@ func init() { func runGetTemplates(cmd *cobra.Command, args []string) error { templateNames, err := ListTemplates() if err != nil { - return fmt.Errorf("failed to read templates: %v", err) + return fmt.Errorf("failed to read templates: %w", err) } if len(templateNames) == 0 { @@ -152,7 +152,7 @@ func runGetTemplates(cmd *cobra.Command, args []string) error { data, err := yaml.Marshal(templates) if err != nil { - return fmt.Errorf("failed to marshal to YAML: %v", err) + return fmt.Errorf("failed to marshal to YAML: %w", err) } fmt.Print(string(data)) return nil @@ -192,7 +192,7 @@ func runGetTemplate(cmd *cobra.Command, args []string) error { if outputFormat == "yaml" || outputFormat == "" { content, err := GetTemplateContent(templateName) if err != nil { - return fmt.Errorf("failed to read template: %v", err) + return fmt.Errorf("failed to read template: %w", err) } fmt.Print(content) return nil @@ -201,7 +201,7 @@ func runGetTemplate(cmd *cobra.Command, args []string) error { // For other output formats, show template info manifestInfo, err := GetTemplateInfo(templateName) if err != nil { - return fmt.Errorf("failed to get template info: %v", err) + return fmt.Errorf("failed to get template info: %w", err) } w := tabwriter.NewWriter(os.Stdout, 0, 0, 3, ' ', 0) @@ -213,12 +213,12 @@ func runGetTemplate(cmd *cobra.Command, args []string) error { func getKthenaClient() (*versioned.Clientset, error) { config, err := clientcmd.BuildConfigFromFlags("", clientcmd.RecommendedHomeFile) if err != nil { - return nil, fmt.Errorf("failed to load kubeconfig: %v", err) + return nil, fmt.Errorf("failed to load kubeconfig: %w", err) } client, err := versioned.NewForConfig(config) if err != nil { - return nil, fmt.Errorf("failed to create kthena client: %v", err) + return nil, fmt.Errorf("failed to create kthena client: %w", err) } return client, nil @@ -285,7 +285,7 @@ func runGetModelBoosters(cmd *cobra.Command, args []string) error { models, err := client.WorkloadV1alpha1().ModelBoosters(namespace).List(ctx, metav1.ListOptions{}) if err != nil { - return fmt.Errorf("failed to list Models: %v", err) + return fmt.Errorf("failed to list Models: %w", err) } // Get name filter if provided @@ -350,7 +350,7 @@ func runGetModelServings(cmd *cobra.Command, args []string) error { modelServingList, err := client.WorkloadV1alpha1().ModelServings(namespace).List(ctx, metav1.ListOptions{}) if err != nil { - return fmt.Errorf("failed to list ModelServings: %v", err) + return fmt.Errorf("failed to list ModelServings: %w", err) } if len(modelServingList.Items) == 0 { @@ -395,7 +395,7 @@ func runGetAutoscalingPolicies(cmd *cobra.Command, args []string) error { policies, err := client.WorkloadV1alpha1().AutoscalingPolicies(namespace).List(ctx, metav1.ListOptions{}) if err != nil { - return fmt.Errorf("failed to list AutoscalingPolicies: %v", err) + return fmt.Errorf("failed to list AutoscalingPolicies: %w", err) } if len(policies.Items) == 0 { @@ -455,7 +455,7 @@ func runGetModelRoutes(cmd *cobra.Command, args []string) error { routes, err := client.NetworkingV1alpha1().ModelRoutes(namespace).List(ctx, metav1.ListOptions{}) if err != nil { - return fmt.Errorf("failed to list ModelRoutes: %v", err) + return fmt.Errorf("failed to list ModelRoutes: %w", err) } if len(routes.Items) == 0 { @@ -506,7 +506,7 @@ func runGetModelServers(cmd *cobra.Command, args []string) error { servers, err := client.NetworkingV1alpha1().ModelServers(namespace).List(ctx, metav1.ListOptions{}) if err != nil { - return fmt.Errorf("failed to list ModelServers: %v", err) + return fmt.Errorf("failed to list ModelServers: %w", err) } if len(servers.Items) == 0 { diff --git a/cli/kthena/cmd/templates.go b/cli/kthena/cmd/templates.go index badfe5fcc..7b01ebf35 100644 --- a/cli/kthena/cmd/templates.go +++ b/cli/kthena/cmd/templates.go @@ -50,7 +50,7 @@ func findTemplatePath(templateName string) (string, error) { // Fallback: search through all vendor directories (for backward compatibility) vendors, err := templatesFS.ReadDir("helm/templates") if err != nil { - return "", fmt.Errorf("failed to read templates directory: %v", err) + return "", fmt.Errorf("failed to read templates directory: %w", err) } for _, vendor := range vendors { @@ -75,7 +75,7 @@ func GetTemplateContent(templateName string) (string, error) { content, err := templatesFS.ReadFile(templatePath) if err != nil { - return "", fmt.Errorf("failed to read template '%s': %v", templateName, err) + return "", fmt.Errorf("failed to read template '%s': %w", templateName, err) } return string(content), nil @@ -85,7 +85,7 @@ func GetTemplateContent(templateName string) (string, error) { func ListTemplates() ([]string, error) { vendors, err := templatesFS.ReadDir("helm/templates") if err != nil { - return nil, fmt.Errorf("failed to read templates directory: %v", err) + return nil, fmt.Errorf("failed to read templates directory: %w", err) } var templates []string diff --git a/pkg/autoscaler/webhook/autoscalingpolicy_mutator.go b/pkg/autoscaler/webhook/autoscalingpolicy_mutator.go index 29c73e45c..6b266dda3 100644 --- a/pkg/autoscaler/webhook/autoscalingpolicy_mutator.go +++ b/pkg/autoscaler/webhook/autoscalingpolicy_mutator.go @@ -146,7 +146,7 @@ func createPolicyBatch(policy *registryv1.AutoscalingPolicy) []jsonpatch.Operati func createPolicyPatchBytes(patch []jsonpatch.Operation) ([]byte, error) { patchBytes, err := json.Marshal(patch) if err != nil { - return nil, fmt.Errorf("failed to marshal patch: %v", err) + return nil, fmt.Errorf("failed to marshal patch: %w", err) } return patchBytes, nil diff --git a/pkg/autoscaler/webhook/common.go b/pkg/autoscaler/webhook/common.go index 23519cfb0..9da327988 100644 --- a/pkg/autoscaler/webhook/common.go +++ b/pkg/autoscaler/webhook/common.go @@ -30,7 +30,7 @@ import ( func parseAdmissionRequest[T any](r *http.Request) (*admissionv1.AdmissionReview, *T, error) { body, err := io.ReadAll(r.Body) if err != nil { - return nil, nil, fmt.Errorf("failed to read request body: %v", err) + return nil, nil, fmt.Errorf("failed to read request body: %w", err) } // Verify the content type is accurate @@ -41,7 +41,7 @@ func parseAdmissionRequest[T any](r *http.Request) (*admissionv1.AdmissionReview // Parse the AdmissionReview request var admissionReview admissionv1.AdmissionReview if err := json.Unmarshal(body, &admissionReview); err != nil { - return nil, nil, fmt.Errorf("failed to decode body: %v", err) + return nil, nil, fmt.Errorf("failed to decode body: %w", err) } if admissionReview.Request == nil { @@ -54,7 +54,7 @@ func parseAdmissionRequest[T any](r *http.Request) (*admissionv1.AdmissionReview // Get the object from the request var obj T if err := json.Unmarshal(admissionReview.Request.Object.Raw, &obj); err != nil { - return nil, nil, fmt.Errorf("failed to decode object: %v", err) + return nil, nil, fmt.Errorf("failed to decode object: %w", err) } return &admissionReview, &obj, nil @@ -65,13 +65,13 @@ func sendAdmissionResponse(w http.ResponseWriter, admissionReview *admissionv1.A // Send the response resp, err := json.Marshal(admissionReview) if err != nil { - return fmt.Errorf("failed to encode response: %v", err) + return fmt.Errorf("failed to encode response: %w", err) } klog.V(4).Infof("Sending response: %s", string(resp)) w.Header().Set("Content-Type", "application/json") if _, err := w.Write(resp); err != nil { - return fmt.Errorf("failed to write response: %v", err) + return fmt.Errorf("failed to write response: %w", err) } return nil diff --git a/pkg/kthena-router/backend/metrics/metrics.go b/pkg/kthena-router/backend/metrics/metrics.go index a27b7d6fc..82939969d 100644 --- a/pkg/kthena-router/backend/metrics/metrics.go +++ b/pkg/kthena-router/backend/metrics/metrics.go @@ -45,7 +45,7 @@ func PodEndpointURL(podIP string, port uint32, path string) string { func ParseMetricsURL(url string) (map[string]*dto.MetricFamily, error) { resp, err := httpClient.Get(url) if err != nil { - return nil, fmt.Errorf("failed to fetch metrics from %s: %v", url, err) + return nil, fmt.Errorf("failed to fetch metrics from %s: %w", url, err) } defer func() { if err := resp.Body.Close(); err != nil { @@ -60,7 +60,7 @@ func ParseMetricsURL(url string) (map[string]*dto.MetricFamily, error) { parser := expfmt.NewTextParser(model.UTF8Validation) allMetrics, err := parser.TextToMetricFamilies(resp.Body) if err != nil { - return nil, fmt.Errorf("error parsing metric families: %v", err) + return nil, fmt.Errorf("error parsing metric families: %w", err) } return allMetrics, nil } diff --git a/pkg/kthena-router/controller/modelserver_controller.go b/pkg/kthena-router/controller/modelserver_controller.go index 75f4e3807..22c950743 100644 --- a/pkg/kthena-router/controller/modelserver_controller.go +++ b/pkg/kthena-router/controller/modelserver_controller.go @@ -185,7 +185,7 @@ func (c *ModelServerController) syncModelServerHandler(key string) error { selector, err := metav1.LabelSelectorAsSelector(&metav1.LabelSelector{MatchLabels: ms.Spec.WorkloadSelector.MatchLabels}) if err != nil { - return fmt.Errorf("invalid selector: %v", err) + return fmt.Errorf("invalid selector: %w", err) } podList, err := c.podLister.Pods(ms.Namespace).List(selector) @@ -260,7 +260,7 @@ func (c *ModelServerController) syncPodHandler(key string) error { func (c *ModelServerController) addOrUpdatePod(pod *corev1.Pod) error { modelServers, err := c.modelServerLister.ModelServers(pod.Namespace).List(labels.Everything()) if err != nil { - return fmt.Errorf("failed to list ModelServers for pod %s/%s: %v", pod.Namespace, pod.Name, err) + return fmt.Errorf("failed to list ModelServers for pod %s/%s: %w", pod.Namespace, pod.Name, err) } servers := []*aiv1alpha1.ModelServer{} @@ -274,7 +274,7 @@ func (c *ModelServerController) addOrUpdatePod(pod *corev1.Pod) error { if len(servers) > 0 { if err := c.store.AddOrUpdatePod(pod, servers); err != nil { - return fmt.Errorf("failed to add or update pod %s/%s in data store: %v", pod.Namespace, pod.Name, err) + return fmt.Errorf("failed to add or update pod %s/%s in data store: %w", pod.Namespace, pod.Name, err) } } diff --git a/pkg/kthena-router/router/router.go b/pkg/kthena-router/router/router.go index 14604d750..c2e6899f3 100644 --- a/pkg/kthena-router/router/router.go +++ b/pkg/kthena-router/router/router.go @@ -600,7 +600,7 @@ func (r *Router) doLoadbalance(c *gin.Context, modelRequest ModelRequest) error if err != nil { accesslog.SetError(c, "scheduling", fmt.Sprintf("can't schedule to target pod: %v", err)) c.AbortWithStatusJSON(http.StatusBadRequest, fmt.Sprintf("can't schedule to target pod: %v", err)) - return fmt.Errorf("can't schedule to target pod: %v", err) + return fmt.Errorf("can't schedule to target pod: %w", err) } // Set complete request routing information in access log @@ -1446,7 +1446,7 @@ func (r *Router) handleFairnessScheduling(c *gin.Context, modelRequest ModelRequ klog.Errorf("%s failed to enqueue: reqID=%s sessionID=%s user=%s model=%s err=%v", logPrefix, requestID, sessionID, userId, modelName, err) c.AbortWithStatusJSON(http.StatusInternalServerError, fmt.Sprintf("failed to enqueue request: %v", err)) - return fmt.Errorf("failed to enqueue request: %v", err) + return fmt.Errorf("failed to enqueue request: %w", err) } select { diff --git a/pkg/kthena-router/scheduler/plugins/conf/conf.go b/pkg/kthena-router/scheduler/plugins/conf/conf.go index f09f83c2b..2154006b2 100644 --- a/pkg/kthena-router/scheduler/plugins/conf/conf.go +++ b/pkg/kthena-router/scheduler/plugins/conf/conf.go @@ -104,7 +104,7 @@ func ParseRouterConfig(configMapPath string) (*RouterConfiguration, error) { var routerConfig RouterConfiguration if err := yaml.Unmarshal(data, &routerConfig); err != nil { klog.Errorf("failed to Unmarshal routerConfiguration: %v", err) - return nil, fmt.Errorf("failed to Unmarshal routerConfiguration: %v", err) + return nil, fmt.Errorf("failed to Unmarshal routerConfiguration: %w", err) } return &routerConfig, nil } @@ -117,7 +117,7 @@ func LoadSchedulerConfig(schedulerConfig *SchedulerConfiguration) (map[string]in scorePluginMap, filterPlugins, err := unmarshalPlugins(schedulerConfig) if err != nil { klog.Errorf("failed to Unmarshal Plugins: %v", err) - return nil, nil, nil, fmt.Errorf("failed to Unmarshal Plugins: %v", err) + return nil, nil, nil, fmt.Errorf("failed to Unmarshal Plugins: %w", err) } // Check for random plugin conflicts and remove random plugin if needed @@ -126,7 +126,7 @@ func LoadSchedulerConfig(schedulerConfig *SchedulerConfiguration) (map[string]in pluginsArgMap, err := unmarshalPluginsConfig(schedulerConfig) if err != nil { klog.Errorf("failed to Unmarshal PluginsConfig: %v", err) - return nil, nil, nil, fmt.Errorf("failed to Unmarshal PluginsConfig: %v", err) + return nil, nil, nil, fmt.Errorf("failed to Unmarshal PluginsConfig: %w", err) } return scorePluginMap, filterPlugins, pluginsArgMap, nil diff --git a/pkg/kthena-router/scheduler/scheduler_impl.go b/pkg/kthena-router/scheduler/scheduler_impl.go index c1ce1dfa7..5dc5a2eff 100644 --- a/pkg/kthena-router/scheduler/scheduler_impl.go +++ b/pkg/kthena-router/scheduler/scheduler_impl.go @@ -130,7 +130,7 @@ func (s *SchedulerImpl) Schedule(ctx *framework.Context, pods []*datastore.PodIn // Get decode pods directly from store (O(1) lookup) decodePods, err := s.store.GetDecodePods(ctx.ModelServerName) if err != nil { - return fmt.Errorf("failed to get decode pods: %v", err) + return fmt.Errorf("failed to get decode pods: %w", err) } if len(decodePods) == 0 { diff --git a/pkg/kthena-router/webhook/utils.go b/pkg/kthena-router/webhook/utils.go index 24aff3d4e..432f0cf09 100644 --- a/pkg/kthena-router/webhook/utils.go +++ b/pkg/kthena-router/webhook/utils.go @@ -40,7 +40,7 @@ func parseAdmissionReviewFromRequest(r *http.Request) (*admissionv1.AdmissionRev defer r.Body.Close() data, err := io.ReadAll(r.Body) if err != nil { - return nil, fmt.Errorf("failed to read request body: %v", err) + return nil, fmt.Errorf("failed to read request body: %w", err) } body = data } @@ -48,7 +48,7 @@ func parseAdmissionReviewFromRequest(r *http.Request) (*admissionv1.AdmissionRev // Parse the AdmissionReview request var admissionReview admissionv1.AdmissionReview if err := json.Unmarshal(body, &admissionReview); err != nil { - return nil, fmt.Errorf("failed to decode body: %v", err) + return nil, fmt.Errorf("failed to decode body: %w", err) } return &admissionReview, nil @@ -63,7 +63,7 @@ func ParseModelRouteFromRequest(r *http.Request) (*admissionv1.AdmissionReview, var mr networkingv1alpha1.ModelRoute if err := json.Unmarshal(admissionReview.Request.Object.Raw, &mr); err != nil { - return nil, nil, fmt.Errorf("failed to decode modelRoute: %v", err) + return nil, nil, fmt.Errorf("failed to decode modelRoute: %w", err) } return admissionReview, &mr, nil @@ -78,7 +78,7 @@ func ParseModelServerFromRequest(r *http.Request) (*admissionv1.AdmissionReview, var ms networkingv1alpha1.ModelServer if err := json.Unmarshal(admissionReview.Request.Object.Raw, &ms); err != nil { - return nil, nil, fmt.Errorf("failed to decode modelServer: %v", err) + return nil, nil, fmt.Errorf("failed to decode modelServer: %w", err) } return admissionReview, &ms, nil @@ -93,7 +93,7 @@ func ParseExternalModelProviderFromRequest(r *http.Request) (*admissionv1.Admiss var provider networkingv1alpha1.ExternalModelProvider if err := json.Unmarshal(admissionReview.Request.Object.Raw, &provider); err != nil { - return nil, nil, fmt.Errorf("failed to decode externalModelProvider: %v", err) + return nil, nil, fmt.Errorf("failed to decode externalModelProvider: %w", err) } return admissionReview, &provider, nil @@ -104,13 +104,13 @@ func SendAdmissionResponse(w http.ResponseWriter, admissionReview *admissionv1.A // Send the response resp, err := json.Marshal(admissionReview) if err != nil { - return fmt.Errorf("failed to encode response: %v", err) + return fmt.Errorf("failed to encode response: %w", err) } klog.V(4).Infof("Sending response: %s", string(resp)) w.Header().Set("Content-Type", "application/json") if _, err := w.Write(resp); err != nil { - return fmt.Errorf("failed to write response: %v", err) + return fmt.Errorf("failed to write response: %w", err) } return nil diff --git a/pkg/model-booster-controller/controller/model_booster_controller.go b/pkg/model-booster-controller/controller/model_booster_controller.go index 9e0d9d956..c72bbf4b0 100644 --- a/pkg/model-booster-controller/controller/model_booster_controller.go +++ b/pkg/model-booster-controller/controller/model_booster_controller.go @@ -125,7 +125,7 @@ func (mc *ModelBoosterController) processNextWorkItem(ctx context.Context) bool mc.workQueue.Forget(key) return true } - utilruntime.HandleError(fmt.Errorf("sync %q failed with %v", key, err)) + utilruntime.HandleError(fmt.Errorf("sync %q failed with %w", key, err)) mc.workQueue.AddRateLimited(key) return true } diff --git a/pkg/model-booster-controller/convert/model_serving.go b/pkg/model-booster-controller/convert/model_serving.go index ace9f560a..a6b532c2c 100644 --- a/pkg/model-booster-controller/convert/model_serving.go +++ b/pkg/model-booster-controller/convert/model_serving.go @@ -528,7 +528,7 @@ func loadModelServingTemplate(templatePath string, data *map[string]interface{}) return nil, fmt.Errorf("YAML template parse failed: %w", err) } if err = utils.ReplacePlaceholders(&jsonObj, data); err != nil { - return nil, fmt.Errorf("replace placeholders failed: %v", err) + return nil, fmt.Errorf("replace placeholders failed: %w", err) } replacedJsonBytes, err := json.Marshal(jsonObj) diff --git a/pkg/model-booster-controller/utils/common.go b/pkg/model-booster-controller/utils/common.go index 383564ffd..fcc735682 100644 --- a/pkg/model-booster-controller/utils/common.go +++ b/pkg/model-booster-controller/utils/common.go @@ -142,12 +142,12 @@ func GetInClusterNameSpace() (string, error) { if _, err := os.Stat(inClusterNamespacePath); os.IsNotExist(err) { return "", fmt.Errorf("not running in-cluster, please specify namespace") } else if err != nil { - return "", fmt.Errorf("error checking namespace file: %v", err) + return "", fmt.Errorf("error checking namespace file: %w", err) } // Load the namespace file and return its content namespace, err := os.ReadFile(inClusterNamespacePath) if err != nil { - return "", fmt.Errorf("error reading namespace file: %v", err) + return "", fmt.Errorf("error reading namespace file: %w", err) } return string(namespace), nil } diff --git a/pkg/model-booster-controller/webhook/common.go b/pkg/model-booster-controller/webhook/common.go index 669a5ac14..afea3ccc6 100644 --- a/pkg/model-booster-controller/webhook/common.go +++ b/pkg/model-booster-controller/webhook/common.go @@ -30,7 +30,7 @@ import ( func parseAdmissionRequest[T any](r *http.Request) (*admissionv1.AdmissionReview, *T, error) { body, err := io.ReadAll(r.Body) if err != nil { - return nil, nil, fmt.Errorf("failed to read request body: %v", err) + return nil, nil, fmt.Errorf("failed to read request body: %w", err) } // Verify the content type is accurate @@ -41,7 +41,7 @@ func parseAdmissionRequest[T any](r *http.Request) (*admissionv1.AdmissionReview // Parse the AdmissionReview request var admissionReview admissionv1.AdmissionReview if err := json.Unmarshal(body, &admissionReview); err != nil { - return nil, nil, fmt.Errorf("failed to decode body: %v", err) + return nil, nil, fmt.Errorf("failed to decode body: %w", err) } if admissionReview.Request == nil { @@ -54,7 +54,7 @@ func parseAdmissionRequest[T any](r *http.Request) (*admissionv1.AdmissionReview // Get the Model from the request var obj T if err := json.Unmarshal(admissionReview.Request.Object.Raw, &obj); err != nil { - return nil, nil, fmt.Errorf("failed to decode object: %v", err) + return nil, nil, fmt.Errorf("failed to decode object: %w", err) } return &admissionReview, &obj, nil @@ -65,13 +65,13 @@ func sendAdmissionResponse(w http.ResponseWriter, admissionReview *admissionv1.A // Send the response resp, err := json.Marshal(admissionReview) if err != nil { - return fmt.Errorf("failed to encode response: %v", err) + return fmt.Errorf("failed to encode response: %w", err) } klog.V(4).Infof("Sending response: %s", string(resp)) w.Header().Set("Content-Type", "application/json") if _, err := w.Write(resp); err != nil { - return fmt.Errorf("failed to write response: %v", err) + return fmt.Errorf("failed to write response: %w", err) } return nil diff --git a/pkg/model-booster-controller/webhook/model_mutator.go b/pkg/model-booster-controller/webhook/model_mutator.go index eec172cb6..1e8c2b2cb 100644 --- a/pkg/model-booster-controller/webhook/model_mutator.go +++ b/pkg/model-booster-controller/webhook/model_mutator.go @@ -90,24 +90,24 @@ func createPatch(original, mutated *registryv1alpha1.ModelBooster) ([]byte, erro // Convert both objects to JSON originalJSON, err := json.Marshal(original) if err != nil { - return nil, fmt.Errorf("failed to marshal original: %v", err) + return nil, fmt.Errorf("failed to marshal original: %w", err) } mutatedJSON, err := json.Marshal(mutated) if err != nil { - return nil, fmt.Errorf("failed to marshal mutated: %v", err) + return nil, fmt.Errorf("failed to marshal mutated: %w", err) } // Create a JSON patch using the jsonpatch library patch, err := jsonpatch.CreatePatch(originalJSON, mutatedJSON) if err != nil { - return nil, fmt.Errorf("failed to create patch: %v", err) + return nil, fmt.Errorf("failed to create patch: %w", err) } // Marshal the patch patchBytes, err := json.Marshal(patch) if err != nil { - return nil, fmt.Errorf("failed to marshal patch: %v", err) + return nil, fmt.Errorf("failed to marshal patch: %w", err) } return patchBytes, nil diff --git a/pkg/model-serving-controller/controller/lws_controller.go b/pkg/model-serving-controller/controller/lws_controller.go index d6e878c30..88656e1c9 100644 --- a/pkg/model-serving-controller/controller/lws_controller.go +++ b/pkg/model-serving-controller/controller/lws_controller.go @@ -51,7 +51,7 @@ func InitializeLWSController( ) (*LWSController, error) { exists, err := ResourceExists(kubeClient, "leaderworkerset.x-k8s.io/v1", "LeaderWorkerSet") if err != nil { - return nil, fmt.Errorf("failed to check LWS CRD existence: %v", err) + return nil, fmt.Errorf("failed to check LWS CRD existence: %w", err) } if !exists { return nil, nil @@ -59,7 +59,7 @@ func InitializeLWSController( lwsClient, err := lwsclientset.NewForConfig(cfg) if err != nil { - return nil, fmt.Errorf("failed to create lws client: %v", err) + return nil, fmt.Errorf("failed to create lws client: %w", err) } lwsInformerFactory := lwsinformers.NewSharedInformerFactory(lwsClient, 0) @@ -67,7 +67,7 @@ func InitializeLWSController( controller, err := NewLWSController(kubeClient, kthenaClient, lwsClient, lwsInformerFactory, kthenaInformerFactory) if err != nil { - return nil, fmt.Errorf("failed to create LWS controller: %v", err) + return nil, fmt.Errorf("failed to create LWS controller: %w", err) } return controller, nil diff --git a/pkg/model-serving-controller/controller/model_serving_controller.go b/pkg/model-serving-controller/controller/model_serving_controller.go index 7b4ef5a69..67cdeb764 100644 --- a/pkg/model-serving-controller/controller/model_serving_controller.go +++ b/pkg/model-serving-controller/controller/model_serving_controller.go @@ -118,12 +118,12 @@ type ModelServingController struct { func NewModelServingController(kubeClientSet kubernetes.Interface, modelServingClient clientset.Interface, volcanoClient volcano.Interface, apiextClient apiextClientSet.Interface) (*ModelServingController, error) { selector, err := labels.NewRequirement(workloadv1alpha1.GroupNameLabelKey, selection.Exists, nil) if err != nil { - return nil, fmt.Errorf("cannot create label selector, err: %v", err) + return nil, fmt.Errorf("cannot create label selector, err: %w", err) } // Register ModelServing types in the global scheme for event recording. if err := workloadv1alpha1.Install(scheme.Scheme); err != nil { - return nil, fmt.Errorf("failed to register ModelServing API scheme: %v", err) + return nil, fmt.Errorf("failed to register ModelServing API scheme: %w", err) } kubeInformerFactory := informers.NewSharedInformerFactoryWithOptions( @@ -143,7 +143,7 @@ func NewModelServingController(kubeClientSet kubernetes.Interface, modelServingC RoleIDKey: utils.RoleIDIndexFunc, }) if err != nil { - return nil, fmt.Errorf("cannot create pod Informer Index, err: %v", err) + return nil, fmt.Errorf("cannot create pod Informer Index, err: %w", err) } err = servicesInformer.Informer().AddIndexers(cache.Indexers{ @@ -151,7 +151,7 @@ func NewModelServingController(kubeClientSet kubernetes.Interface, modelServingC RoleIDKey: utils.RoleIDIndexFunc, }) if err != nil { - return nil, fmt.Errorf("cannot create service Informer Index, err: %v", err) + return nil, fmt.Errorf("cannot create service Informer Index, err: %w", err) } store := datastore.New() @@ -536,7 +536,7 @@ func (c *ModelServingController) processNextWorkItem(ctx context.Context) bool { return true } - utilruntime.HandleError(fmt.Errorf("sync %q failed with %v", key, err)) + utilruntime.HandleError(fmt.Errorf("sync %q failed with %w", key, err)) c.workqueue.AddRateLimited(key) return true @@ -562,27 +562,27 @@ func (c *ModelServingController) syncModelServing(ctx context.Context, key strin // 1. Sync the number of ServingGroups to match the expected replicas defined in spec. if err := c.syncServingGroupReplicas(ctx, ms, revision); err != nil { - return fmt.Errorf("failed to sync ServingGroup replicas: %v", err) + return fmt.Errorf("failed to sync ServingGroup replicas: %w", err) } // 2. Sync the roles and their replicas within each ServingGroup, handling partitioned scaling and revisions. if err := c.syncRoleReplicas(ctx, ms, revision); err != nil { - return fmt.Errorf("failed to sync role replicas: %v", err) + return fmt.Errorf("failed to sync role replicas: %w", err) } // 3. Handle the rolling update process, deleting outdated ServingGroups/Roles to trigger updates. if err := c.manageRollingUpdate(ctx, ms, revision); err != nil { - return fmt.Errorf("failed to handle rollingUpdate: %v", err) + return fmt.Errorf("failed to handle rollingUpdate: %w", err) } // 4. Create and update Headless Services for internal networking between entry and worker pods. if err := c.syncHeadlessServices(ctx, ms); err != nil { - return fmt.Errorf("failed to sync headless services: %v", err) + return fmt.Errorf("failed to sync headless services: %w", err) } // 5. Calculate and update the overall condition and replica status fields of the ModelServing. if err := c.UpdateModelServingStatus(ms, revision); err != nil { - return fmt.Errorf("failed to update status of ms %s/%s: %v", namespace, name, err) + return fmt.Errorf("failed to update status of ms %s/%s: %w", namespace, name, err) } return nil @@ -650,7 +650,7 @@ func (c *ModelServingController) syncAll() { func (c *ModelServingController) syncServingGroupReplicas(ctx context.Context, ms *workloadv1alpha1.ModelServing, newRevision string) error { servingGroupList, err := c.store.GetServingGroupByModelServing(utils.GetNamespaceName(ms)) if err != nil && !errors.Is(err, datastore.ErrServingGroupNotFound) { - return fmt.Errorf("cannot get servingGroup of modelServing: %s from map: %v", ms.GetName(), err) + return fmt.Errorf("cannot get servingGroup of modelServing: %s from map: %w", ms.GetName(), err) } expectedCount := int(*ms.Spec.Replicas) curReplicas := len(servingGroupList) @@ -662,18 +662,18 @@ func (c *ModelServingController) syncServingGroupReplicas(ctx context.Context, m for _, servingGroup := range servingGroupList { if servingGroup.Status != datastore.ServingGroupDeleting { if err := c.createOrUpdatePodGroupByServingGroup(ctx, ms, servingGroup.Name); err != nil { - return fmt.Errorf("failed to update PodGroup for ServingGroup %s: %v", servingGroup.Name, err) + return fmt.Errorf("failed to update PodGroup for ServingGroup %s: %w", servingGroup.Name, err) } } } if err := c.scaleUpServingGroups(ctx, ms, servingGroupList, expectedCount, newRevision); err != nil { - return fmt.Errorf("failed to scale up ServingGroups: %v", err) + return fmt.Errorf("failed to scale up ServingGroups: %w", err) } } else { if curReplicas > expectedCount { klog.V(2).Infof("manageServingGroupReplicas: scaling down modelServing=%s (%d -> %d)", utils.GetNamespaceName(ms), curReplicas, expectedCount) if err := c.scaleDownServingGroups(ctx, ms, servingGroupList, expectedCount); err != nil { - return fmt.Errorf("failed to scale down ServingGroups: %v", err) + return fmt.Errorf("failed to scale down ServingGroups: %w", err) } } @@ -682,12 +682,12 @@ func (c *ModelServingController) syncServingGroupReplicas(ctx context.Context, m // Moreover, it is also possible to reconstruct accidentally deleted podGroups here. servingGroupList, err := c.store.GetServingGroupByModelServing(utils.GetNamespaceName(ms)) if err != nil && !errors.Is(err, datastore.ErrServingGroupNotFound) { - return fmt.Errorf("cannot get servingGroup of modelServing: %s from map: %v", ms.GetName(), err) + return fmt.Errorf("cannot get servingGroup of modelServing: %s from map: %w", ms.GetName(), err) } for _, servingGroup := range servingGroupList { if servingGroup.Status != datastore.ServingGroupDeleting { if err := c.createOrUpdatePodGroupByServingGroup(ctx, ms, servingGroup.Name); err != nil { - return fmt.Errorf("failed to update PodGroup for ServingGroup %s: %v", servingGroup.Name, err) + return fmt.Errorf("failed to update PodGroup for ServingGroup %s: %w", servingGroup.Name, err) } } } @@ -727,7 +727,7 @@ func (c *ModelServingController) scaleUpServingGroups(ctx context.Context, ms *w klog.V(4).Infof("Creating ServingGroup %s at ordinal %d with revision %s", groupName, ordinal, revision) // Create pods for ServingGroup using the provided roles template if err := c.CreatePodsForServingGroup(ctx, ms, ordinal, revision, roles); err != nil { - return fmt.Errorf("create Serving group failed: %v", err) + return fmt.Errorf("create Serving group failed: %w", err) } // Insert new ServingGroup to global storage c.store.AddServingGroup(utils.GetNamespaceName(ms), ordinal, revision) @@ -817,7 +817,7 @@ func (c *ModelServingController) scaleUpServingGroups(ctx context.Context, ms *w func (c *ModelServingController) syncRoleReplicas(ctx context.Context, ms *workloadv1alpha1.ModelServing, newRevision string) error { servingGroupList, err := c.store.GetServingGroupByModelServing(utils.GetNamespaceName(ms)) if err != nil && !errors.Is(err, datastore.ErrServingGroupNotFound) { - return fmt.Errorf("cannot get ServingGroup of modelServing: %s from map: %v", ms.GetName(), err) + return fmt.Errorf("cannot get ServingGroup of modelServing: %s from map: %w", ms.GetName(), err) } partition, _, _ := c.getPartition(modelServingPartition(ms), modelServingReplicas(ms)) for index, servingGroup := range servingGroupList { @@ -997,7 +997,7 @@ func (c *ModelServingController) scaleUpRoles(ctx context.Context, ms *workloadv // Create pods for role err := c.CreatePodsByRole(ctx, *roleToApply.DeepCopy(), ms, ordinal, servingGroupOrdinal, revision, roleTemplateHash) if err != nil { - return fmt.Errorf("create role %s for ServingGroup %s failed: %v", utils.GenerateRoleID(targetRole.Name, ordinal), groupName, err) + return fmt.Errorf("create role %s for ServingGroup %s failed: %w", utils.GenerateRoleID(targetRole.Name, ordinal), groupName, err) } // Insert new Role to global storage roleID := utils.GenerateRoleID(targetRole.Name, ordinal) @@ -1300,7 +1300,7 @@ func (c *ModelServingController) DeleteRole(ctx context.Context, ms *workloadv1a func (c *ModelServingController) manageRollingUpdate(ctx context.Context, ms *workloadv1alpha1.ModelServing, revision string) error { servingGroupList, err := c.store.GetServingGroupByModelServing(utils.GetNamespaceName(ms)) if err != nil { - return fmt.Errorf("cannot get ServingGroupList from store, err:%v", err) + return fmt.Errorf("cannot get ServingGroupList from store, err:%w", err) } partition, _, _ := c.getPartition(modelServingPartition(ms), modelServingReplicas(ms)) @@ -1331,7 +1331,7 @@ func (c *ModelServingController) manageRollingUpdate(ctx context.Context, ms *wo if ms.Spec.RolloutStrategy == nil || ms.Spec.RolloutStrategy.Type == workloadv1alpha1.ServingGroupRollingUpdate { maxUnavailable, err := utils.GetMaxUnavailable(ms) if err != nil { - return fmt.Errorf("failed to calculate maxUnavailable: %v", err) + return fmt.Errorf("failed to calculate maxUnavailable: %w", err) } // TODO(hzxuzhonghu): reuse calMaxScaleDown @@ -1468,7 +1468,7 @@ func (c *ModelServingController) rolesToDeleteForRoleRollingUpdate(ms *workloadv allRoles, err := c.store.GetRolesByGroup(utils.GetNamespaceName(ms), sg.Name) if err != nil { - return nil, false, fmt.Errorf("failed to get roles for ServingGroup %s: %v", sg.Name, err) + return nil, false, fmt.Errorf("failed to get roles for ServingGroup %s: %w", sg.Name, err) } var rolesToDelete []roleToDelete @@ -1476,7 +1476,7 @@ func (c *ModelServingController) rolesToDeleteForRoleRollingUpdate(ms *workloadv for _, roleSpec := range ms.Spec.Template.Roles { roleList, err := c.store.GetRoleList(utils.GetNamespaceName(ms), sg.Name, roleSpec.Name) if err != nil { - return nil, false, fmt.Errorf("failed to get roles for ServingGroup %s, role %s: %v", sg.Name, roleSpec.Name, err) + return nil, false, fmt.Errorf("failed to get roles for ServingGroup %s, role %s: %w", sg.Name, roleSpec.Name, err) } outdatedRoles, newUnavailable := c.outdatedRoles(ms, sg, roleSpec, roleList) @@ -1644,14 +1644,14 @@ func (c *ModelServingController) handleReadyPod(ms *workloadv1alpha1.ModelServin ready, err := c.checkServingGroupReady(ms, servingGroupName) if err != nil { - return fmt.Errorf("failed to check ServingGroup status, err: %v", err) + return fmt.Errorf("failed to check ServingGroup status, err: %w", err) } if ready { // All pods in the ServingGroup are running, so the ServingGroup status also needs to be set to running err = c.store.UpdateServingGroupStatus(utils.GetNamespaceName(ms), servingGroupName, datastore.ServingGroupRunning) klog.V(4).Infof("ServingGroup: %s/%s status updated to Running", ms.GetName(), servingGroupName) if err != nil { - return fmt.Errorf("failed to set ServingGroup %s status: %v", servingGroupName, err) + return fmt.Errorf("failed to set ServingGroup %s status: %w", servingGroupName, err) } klog.V(2).Infof("Update ServingGroup %s status to Running", servingGroupName) c.enqueueModelServing(ms) @@ -1696,7 +1696,7 @@ func (c *ModelServingController) handleErrorPod(ms *workloadv1alpha1.ModelServin err := c.store.UpdateServingGroupStatus(utils.GetNamespaceName(ms), servingGroupName, datastore.ServingGroupCreating) klog.V(4).Infof("Setting ServingGroup %s/%s status to Creating when pod fails", ms.GetName(), servingGroupName) if err != nil { - return fmt.Errorf("update ServingGroup status failed, err:%v", err) + return fmt.Errorf("update ServingGroup status failed, err:%w", err) } klog.V(2).Infof("update ServingGroup %s to processing when pod fails", servingGroupName) } @@ -1771,7 +1771,7 @@ func (c *ModelServingController) handleDeletedPod(ms *workloadv1alpha1.ModelServ err := c.store.UpdateServingGroupStatus(utils.GetNamespaceName(ms), servingGroupName, datastore.ServingGroupCreating) klog.V(4).Infof("Setting ServingGroup %s/%s status to Creating when pod deleted for recreating", ms.GetName(), servingGroupName) if err != nil { - return fmt.Errorf("failed to set ServingGroup %s status: %v", servingGroupName, err) + return fmt.Errorf("failed to set ServingGroup %s status: %w", servingGroupName, err) } } c.DeleteRole(context.Background(), ms, servingGroupName, utils.GetRoleName(pod), utils.GetRoleID(pod)) @@ -1809,7 +1809,7 @@ func (c *ModelServingController) checkRoleReady(ms *workloadv1alpha1.ModelServin roleIDValue := fmt.Sprintf("%s/%s/%s/%s", ms.Namespace, servingGroupName, roleName, roleID) pods, err := c.getPodsByIndex(RoleIDKey, roleIDValue) if err != nil { - return false, fmt.Errorf("failed to get pods for role %s/%s: %v", roleName, roleID, err) + return false, fmt.Errorf("failed to get pods for role %s/%s: %w", roleName, roleID, err) } // Find the role specification to get expected pod count var targetRole *workloadv1alpha1.Role @@ -2131,7 +2131,7 @@ func (c *ModelServingController) UpdateModelServingStatus(ms *workloadv1alpha1.M // some scenarios, pod events may not trigger group status updates, such as role scaling down. err = c.store.UpdateServingGroupStatus(utils.GetNamespaceName(latestMS), groups[index].Name, datastore.ServingGroupRunning) if err != nil { - return fmt.Errorf("failed to set servingGroup %s status: %v", groups[index].Name, err) + return fmt.Errorf("failed to set servingGroup %s status: %w", groups[index].Name, err) } available = available + 1 klog.V(2).Infof("Update servingGroup %s status to Running", groups[index].Name) @@ -2436,7 +2436,7 @@ func (c *ModelServingController) scaleDownServingGroups(ctx context.Context, ms func (c *ModelServingController) syncHeadlessServices(ctx context.Context, ms *workloadv1alpha1.ModelServing) error { servingGroups, err := c.store.GetServingGroupByModelServing(utils.GetNamespaceName(ms)) if err != nil && !errors.Is(err, datastore.ErrServingGroupNotFound) { - return fmt.Errorf("cannot get servingGroups: %v", err) + return fmt.Errorf("cannot get servingGroups: %w", err) } for _, sg := range servingGroups { @@ -2480,7 +2480,7 @@ func (c *ModelServingController) syncHeadlessServices(ctx context.Context, ms *w if role.WorkerTemplate != nil { _, roleIndex := utils.GetParentNameAndOrdinal(roleObj.Name) if err := utils.CreateHeadlessService(ctx, c.kubeClientSet, ms, serviceSelector, sg.Name, role.Name, roleIndex); err != nil { - return fmt.Errorf("failed to create service for role %s in serving group %s: %v", roleObj.Name, sg.Name, err) + return fmt.Errorf("failed to create service for role %s in serving group %s: %w", roleObj.Name, sg.Name, err) } } } @@ -2570,7 +2570,7 @@ func (c *ModelServingController) createPod( Pod: pod, } if err := chain.OnPodCreate(ctx, req); err != nil { - return fmt.Errorf("execute OnPodCreate failed for %s pod %s: %v", roleKind, pod.Name, err) + return fmt.Errorf("execute OnPodCreate failed for %s pod %s: %w", roleKind, pod.Name, err) } } @@ -2585,7 +2585,7 @@ func (c *ModelServingController) createPod( return nil } } else { - return fmt.Errorf("failed to create %s pod %s: %v", roleKind, pod.Name, err) + return fmt.Errorf("failed to create %s pod %s: %w", roleKind, pod.Name, err) } } @@ -2619,7 +2619,7 @@ func (c *ModelServingController) deleteServingGroup(ctx context.Context, ms *wor err = c.podGroupManager.DeletePodGroup(ctx, ms, servingGroupName) if err != nil { - return fmt.Errorf("failed to delete PodGroup for ServingGroup %s: %v", servingGroupName, err) + return fmt.Errorf("failed to delete PodGroup for ServingGroup %s: %w", servingGroupName, err) } selector := labels.SelectorFromSet(map[string]string{ @@ -2629,13 +2629,13 @@ func (c *ModelServingController) deleteServingGroup(ctx context.Context, ms *wor LabelSelector: selector.String(), }) if err != nil { - return fmt.Errorf("failed to delete pods of ServingGroup %s: %v", servingGroupName, err) + return fmt.Errorf("failed to delete pods of ServingGroup %s: %w", servingGroupName, err) } // Delete services services, err := c.getServicesByIndex(GroupNameKey, fmt.Sprintf("%s/%s", ms.Namespace, servingGroupName)) if err != nil { - return fmt.Errorf("failed to get services for ServingGroup %s: %v", servingGroupName, err) + return fmt.Errorf("failed to get services for ServingGroup %s: %w", servingGroupName, err) } for _, svc := range services { @@ -2667,7 +2667,7 @@ func (c *ModelServingController) createOrUpdatePodGroupByServingGroup(ctx contex c.enqueueModelServingAfter(ms, retryAfter) return nil } - return fmt.Errorf("failed to update PodGroup for ServingGroup %s: %v", servingGroupName, err) + return fmt.Errorf("failed to update PodGroup for ServingGroup %s: %w", servingGroupName, err) } return nil } @@ -2865,7 +2865,7 @@ func calMaxScaleDown(role workloadv1alpha1.Role, outdatedRoles []datastore.Role, // ModelServing-level maxUnavailable is intentionally not consulted here. maxUnavailable, configured, err := utils.GetMaxUnavailableForRole(role) if err != nil { - return 0, fmt.Errorf("failed to calculate maxUnavailable for role %s: %v", role.Name, err) + return 0, fmt.Errorf("failed to calculate maxUnavailable for role %s: %w", role.Name, err) } if !configured { return len(outdatedRoles), nil diff --git a/pkg/model-serving-controller/podgroupmanager/manager.go b/pkg/model-serving-controller/podgroupmanager/manager.go index bef62db7d..d4ff50ca1 100644 --- a/pkg/model-serving-controller/podgroupmanager/manager.go +++ b/pkg/model-serving-controller/podgroupmanager/manager.go @@ -206,7 +206,7 @@ func (m *Manager) initPodGroupInformer() error { if err := pgInformer.Informer().AddIndexers(cache.Indexers{ groupNameKey: utils.GroupNameIndexFunc, }); err != nil { - return fmt.Errorf("cannot create podGroup Informer Index, err: %v", err) + return fmt.Errorf("cannot create podGroup Informer Index, err: %w", err) } m.PodGroupInformer = pgInformer.Informer() m.PodGroupLister = pgInformer.Lister() @@ -252,7 +252,7 @@ func (m *Manager) CreateOrUpdatePodGroup(ctx context.Context, ms *workloadv1alph podGroup, err := podGroupLister.PodGroups(ms.Namespace).Get(pgName) if err != nil { if !apierrors.IsNotFound(err) { - return fmt.Errorf("failed to get PodGroup %s: %v", pgName, err), 0 + return fmt.Errorf("failed to get PodGroup %s: %w", pgName, err), 0 } return m.createPodGroup(ctx, ms, pgName), 0 } @@ -502,13 +502,13 @@ func (m *Manager) DeletePodGroup(ctx context.Context, ms *workloadv1alpha1.Model func (m *Manager) CleanupPodGroups(ctx context.Context, ms *workloadv1alpha1.ModelServing) error { existingPodGroups, err := m.getExistingPodGroups(ctx, ms) if err != nil { - return fmt.Errorf("failed to get existing PodGroups for cleanup: %v", err) + return fmt.Errorf("failed to get existing PodGroups for cleanup: %w", err) } for _, podGroup := range existingPodGroups { err := m.volcanoClient.SchedulingV1beta1().PodGroups(ms.Namespace).Delete(ctx, podGroup.Name, metav1.DeleteOptions{}) if err != nil && !apierrors.IsNotFound(err) { - return fmt.Errorf("failed to delete PodGroup %s: %v", podGroup.Name, err) + return fmt.Errorf("failed to delete PodGroup %s: %w", podGroup.Name, err) } klog.V(2).Infof("Deleted PodGroup %s (gang scheduling disabled)", podGroup.Name) } diff --git a/pkg/model-serving-controller/utils/controller_revision.go b/pkg/model-serving-controller/utils/controller_revision.go index 4362ad1f6..33fedd121 100644 --- a/pkg/model-serving-controller/utils/controller_revision.go +++ b/pkg/model-serving-controller/utils/controller_revision.go @@ -49,7 +49,7 @@ func CreateControllerRevision(ctx context.Context, client kubernetes.Interface, } data, err := json.Marshal(wrappedData) if err != nil { - return nil, fmt.Errorf("failed to marshal template data: %v", err) + return nil, fmt.Errorf("failed to marshal template data: %w", err) } // Check if ControllerRevision already exists @@ -71,7 +71,7 @@ func CreateControllerRevision(ctx context.Context, client kubernetes.Interface, } return existing, nil } else if !apierrors.IsNotFound(err) { - return nil, fmt.Errorf("failed to get ControllerRevision: %v", err) + return nil, fmt.Errorf("failed to get ControllerRevision: %w", err) } // Create ControllerRevision @@ -96,7 +96,7 @@ func CreateControllerRevision(ctx context.Context, client kubernetes.Interface, // Create ControllerRevision created, err := client.AppsV1().ControllerRevisions(ms.Namespace).Create(ctx, cr, metav1.CreateOptions{}) if err != nil { - return nil, fmt.Errorf("failed to create ControllerRevision: %v", err) + return nil, fmt.Errorf("failed to create ControllerRevision: %w", err) } klog.V(4).Infof("Created ControllerRevision %s/%s with revision %s", ms.Namespace, controllerRevisionName, revision) @@ -134,7 +134,7 @@ func GetRolesFromControllerRevision(cr *appsv1.ControllerRevision) ([]workloadv1 if rawData, ok := wrapper["data"]; ok { var roles []workloadv1alpha1.Role if err := json.Unmarshal(rawData, &roles); err != nil { - return nil, fmt.Errorf("failed to unmarshal roles from wrapped data: %v", err) + return nil, fmt.Errorf("failed to unmarshal roles from wrapped data: %w", err) } return roles, nil } @@ -143,7 +143,7 @@ func GetRolesFromControllerRevision(cr *appsv1.ControllerRevision) ([]workloadv1 // Fallback: try to unmarshal directly (for backward compatibility or if not wrapped) var roles []workloadv1alpha1.Role if err := json.Unmarshal(cr.Data.Raw, &roles); err != nil { - return nil, fmt.Errorf("failed to unmarshal roles from ControllerRevision: %v", err) + return nil, fmt.Errorf("failed to unmarshal roles from ControllerRevision: %w", err) } return roles, nil @@ -166,7 +166,7 @@ func CleanupOldControllerRevisions( LabelSelector: selector.String(), }) if err != nil { - return fmt.Errorf("failed to list ControllerRevisions: %v", err) + return fmt.Errorf("failed to list ControllerRevisions: %w", err) } // Get the revision names that must be preserved (CurrentRevision and UpdateRevision) diff --git a/pkg/model-serving-controller/utils/utils.go b/pkg/model-serving-controller/utils/utils.go index 492afe628..001b20bb1 100644 --- a/pkg/model-serving-controller/utils/utils.go +++ b/pkg/model-serving-controller/utils/utils.go @@ -263,7 +263,7 @@ func CreateHeadlessService(ctx context.Context, k8sClient kubernetes.Interface, if err != nil { if !apierrors.IsAlreadyExists(err) { - return fmt.Errorf("create headless service failed: %v", err) + return fmt.Errorf("create headless service failed: %w", err) } } return nil @@ -507,7 +507,7 @@ func ParseModelServingFromRequest(r *http.Request) (*admissionv1.AdmissionReview defer r.Body.Close() data, err := io.ReadAll(r.Body) if err != nil { - return nil, nil, fmt.Errorf("failed to read request body: %v", err) + return nil, nil, fmt.Errorf("failed to read request body: %w", err) } body = data } @@ -515,12 +515,12 @@ func ParseModelServingFromRequest(r *http.Request) (*admissionv1.AdmissionReview // Parse the AdmissionReview request var admissionReview admissionv1.AdmissionReview if err := json.Unmarshal(body, &admissionReview); err != nil { - return nil, nil, fmt.Errorf("failed to decode body: %v", err) + return nil, nil, fmt.Errorf("failed to decode body: %w", err) } var ms workloadv1alpha1.ModelServing if err := json.Unmarshal(admissionReview.Request.Object.Raw, &ms); err != nil { - return nil, nil, fmt.Errorf("failed to decode modelServing: %v", err) + return nil, nil, fmt.Errorf("failed to decode modelServing: %w", err) } return &admissionReview, &ms, nil @@ -531,13 +531,13 @@ func SendAdmissionResponse(w http.ResponseWriter, admissionReview *admissionv1.A // Send the response resp, err := json.Marshal(admissionReview) if err != nil { - return fmt.Errorf("failed to encode response: %v", err) + return fmt.Errorf("failed to encode response: %w", err) } klog.V(4).Infof("Sending response: %s", string(resp)) w.Header().Set("Content-Type", "application/json") if _, err := w.Write(resp); err != nil { - return fmt.Errorf("failed to write response: %v", err) + return fmt.Errorf("failed to write response: %w", err) } return nil diff --git a/test/e2e/framework/framework.go b/test/e2e/framework/framework.go index f19070935..97f30f805 100644 --- a/test/e2e/framework/framework.go +++ b/test/e2e/framework/framework.go @@ -90,7 +90,7 @@ func InstallKthena(cfg *KthenaConfig) error { cmd.Stderr = os.Stderr fmt.Printf("Installing kthena: %s\n", strings.Join(cmd.Args, " ")) if err := cmd.Run(); err != nil { - return fmt.Errorf("failed to install kthena: %v", err) + return fmt.Errorf("failed to install kthena: %w", err) } // Wait for pods to be ready @@ -99,7 +99,7 @@ func InstallKthena(cfg *KthenaConfig) error { waitCmd.Stdout = os.Stdout waitCmd.Stderr = os.Stderr if err := waitCmd.Run(); err != nil { - return fmt.Errorf("failed to wait for kthena pods: %v", err) + return fmt.Errorf("failed to wait for kthena pods: %w", err) } // Wait for auto-generated Gateway if Gateway API is enabled @@ -127,13 +127,13 @@ func InstallKthena(cfg *KthenaConfig) error { var err error pfForwarder, err = utils.SetupPortForward(cfg.Namespace, "kthena-router", "8080", "80") if err != nil { - return fmt.Errorf("failed to setup port-forward: %v", err) + return fmt.Errorf("failed to setup port-forward: %w", err) } metricsPFForwarder, err = utils.SetupPortForward(cfg.Namespace, utils.RouterMetricsService, utils.RouterMetricsPort, utils.RouterMetricsPort) if err != nil { pfForwarder.Close() pfForwarder = nil - return fmt.Errorf("failed to setup metrics port-forward: %v", err) + return fmt.Errorf("failed to setup metrics port-forward: %w", err) } // Note: SetupPortForward already waits for the port-forward to be ready. // Cleanup is handled by UninstallKthena via the global pfForwarder. diff --git a/test/e2e/utils/portforward.go b/test/e2e/utils/portforward.go index 3349abd31..734e6d52c 100644 --- a/test/e2e/utils/portforward.go +++ b/test/e2e/utils/portforward.go @@ -77,11 +77,11 @@ func (f *forwarder) Start() error { // Build a new port forwarder. fw, err = f.buildK8sPortForwarder(readyCh) if err != nil { - f.errCh <- fmt.Errorf("building port forwarder: %v", err) + f.errCh <- fmt.Errorf("building port forwarder: %w", err) return } if err = fw.ForwardPorts(); err != nil { - f.errCh <- fmt.Errorf("port forward: %v", err) + f.errCh <- fmt.Errorf("port forward: %w", err) return } f.errCh <- nil @@ -96,11 +96,11 @@ func (f *forwarder) Start() error { // We may later get an error, but that is handled async. select { case err := <-f.errCh: - return fmt.Errorf("failure running port forward process: %v", err) + return fmt.Errorf("failure running port forward process: %w", err) case <-readyCh: p, err := fw.GetPorts() if err != nil { - return fmt.Errorf("failed to get ports: %v", err) + return fmt.Errorf("failed to get ports: %w", err) } if len(p) == 0 { return fmt.Errorf("got no ports") @@ -179,13 +179,13 @@ func SetupPortForward(namespace, service, localPort, remotePort string) (PortFor // Get Kubernetes config config, err := GetKubeConfig() if err != nil { - return nil, fmt.Errorf("failed to get kubeconfig: %v", err) + return nil, fmt.Errorf("failed to get kubeconfig: %w", err) } // Create Kubernetes client clientset, err := kubernetes.NewForConfig(config) if err != nil { - return nil, fmt.Errorf("failed to create kubernetes client: %v", err) + return nil, fmt.Errorf("failed to create kubernetes client: %w", err) } // Parse remote port (service port) @@ -194,13 +194,13 @@ func SetupPortForward(namespace, service, localPort, remotePort string) (PortFor // Find a pod for the service and get the targetPort from service configuration podName, targetPort, err := findPodForService(clientset, namespace, service, remotePortIntOrStr) if err != nil { - return nil, fmt.Errorf("failed to find pod for service %s/%s: %v", namespace, service, err) + return nil, fmt.Errorf("failed to find pod for service %s/%s: %w", namespace, service, err) } // Parse local port localPortInt, err := strconv.Atoi(localPort) if err != nil { - return nil, fmt.Errorf("invalid local port %q: %v", localPort, err) + return nil, fmt.Errorf("invalid local port %q: %w", localPort, err) } return startForwarder(namespace, podName, localPortInt, targetPort) @@ -214,13 +214,13 @@ func SetupPortForwardToPod(namespace, podName, localPort, podPort string) (PortF // Parse local port localPortInt, err := strconv.Atoi(localPort) if err != nil { - return nil, fmt.Errorf("invalid local port %q: %v", localPort, err) + return nil, fmt.Errorf("invalid local port %q: %w", localPort, err) } // Parse pod port podPortInt, err := strconv.Atoi(podPort) if err != nil { - return nil, fmt.Errorf("invalid pod port %q: %v", podPort, err) + return nil, fmt.Errorf("invalid pod port %q: %w", podPort, err) } return startForwarder(namespace, podName, localPortInt, podPortInt) @@ -234,7 +234,7 @@ func findPodForService(clientset *kubernetes.Clientset, namespace, serviceName s // Get the service svc, err := clientset.CoreV1().Services(namespace).Get(ctx, serviceName, metav1.GetOptions{}) if err != nil { - return "", 0, fmt.Errorf("failed to get service: %v", err) + return "", 0, fmt.Errorf("failed to get service: %w", err) } // Find the targetPort from service port configuration @@ -270,7 +270,7 @@ func findPodForService(clientset *kubernetes.Clientset, namespace, serviceName s LabelSelector: selector, }) if err != nil { - return "", 0, fmt.Errorf("failed to list pods: %v", err) + return "", 0, fmt.Errorf("failed to list pods: %w", err) } // Find the first running pod and resolve the targetPort @@ -315,13 +315,13 @@ func (f *forwarder) buildK8sPortForwarder(readyCh chan struct{}) (*portforward.P // Get Kubernetes config restConfig, err := GetKubeConfig() if err != nil { - return nil, fmt.Errorf("failed to get kubeconfig: %v", err) + return nil, fmt.Errorf("failed to get kubeconfig: %w", err) } // Create Kubernetes clientset to get REST client clientset, err := kubernetes.NewForConfig(restConfig) if err != nil { - return nil, fmt.Errorf("failed to create kubernetes client: %v", err) + return nil, fmt.Errorf("failed to create kubernetes client: %w", err) } // Use the REST client from CoreV1() which is already configured for core/v1 API @@ -332,7 +332,7 @@ func (f *forwarder) buildK8sPortForwarder(readyCh chan struct{}) (*portforward.P roundTripper, upgrader, err := spdy.RoundTripperFor(restConfig) if err != nil { - return nil, fmt.Errorf("failure creating roundtripper: %v", err) + return nil, fmt.Errorf("failure creating roundtripper: %w", err) } dialer := spdy.NewDialer(upgrader, &http.Client{Transport: roundTripper}, http.MethodPost, serverURL) @@ -345,7 +345,7 @@ func (f *forwarder) buildK8sPortForwarder(readyCh chan struct{}) (*portforward.P io.Discard, os.Stderr) if err != nil { - return nil, fmt.Errorf("failed establishing port-forward: %v", err) + return nil, fmt.Errorf("failed establishing port-forward: %w", err) } // Run the same check as k8s.io/kubectl/pkg/cmd/portforward/portforward.go