diff --git a/agent/app/service/ai/vllm_upgrade.go b/agent/app/service/ai/vllm_upgrade.go new file mode 100644 index 000000000..b13775af9 --- /dev/null +++ b/agent/app/service/ai/vllm_upgrade.go @@ -0,0 +1,139 @@ +package service + +import ( + "encoding/json" + "strings" + + "github.com/1Panel-dev/1Panel/agent/utils/common" +) + +const ( + vllmAppKeyForUpgrade = "vllm" + vllmImageEnvKey = "IMAGE" + vllmImageTypeNvidia = "nvidia" + vllmImageTypeIntel = "intel" + vllmImageTypeAscend = "ascend" +) + +func resolveVllmVersionFamily(version, image string) string { + normalizedVersion := strings.ToLower(strings.TrimSpace(version)) + if strings.HasPrefix(normalizedVersion, vllmImageTypeIntel+"-") { + return vllmImageTypeIntel + } + if strings.HasPrefix(normalizedVersion, vllmImageTypeAscend+"-") { + return vllmImageTypeAscend + } + if strings.HasPrefix(normalizedVersion, vllmImageTypeNvidia+"-") { + return vllmImageTypeNvidia + } + normalizedImage := strings.ToLower(strings.TrimSpace(image)) + if strings.Contains(normalizedImage, "intel/") || strings.Contains(normalizedImage, "llm-scaler-vllm") { + return vllmImageTypeIntel + } + if strings.Contains(normalizedImage, "ascend/") || strings.Contains(normalizedImage, "vllm-ascend") { + return vllmImageTypeAscend + } + return vllmImageTypeNvidia +} + +func trimVllmVersionFamily(version string) string { + trimmed := strings.TrimSpace(version) + normalized := strings.ToLower(trimmed) + for _, family := range []string{vllmImageTypeNvidia, vllmImageTypeIntel, vllmImageTypeAscend} { + prefix := family + "-" + if strings.HasPrefix(normalized, prefix) { + return strings.TrimSpace(trimmed[len(prefix):]) + } + } + return trimmed +} + +func buildDefaultVllmImageByVersion(version string) string { + tag := trimVllmVersionFamily(version) + family := resolveVllmVersionFamily(version, "") + if family == vllmImageTypeIntel { + return "intel/llm-scaler-vllm:" + tag + } + if tag != "" && !strings.HasPrefix(strings.ToLower(tag), "v") { + tag = "v" + tag + } + if family == vllmImageTypeAscend { + return "quay.io/ascend/vllm-ascend:" + tag + } + return "vllm/vllm-openai:" + tag +} + +func isVllmUpgradeVersionAllowed(currentVersion, targetVersion, currentImage string) bool { + currentFamily := resolveVllmVersionFamily(currentVersion, currentImage) + targetFamily := resolveVllmVersionFamily(targetVersion, "") + return currentFamily == targetFamily +} + +func hasVllmVersionFamilyPrefix(version string) bool { + normalized := strings.ToLower(strings.TrimSpace(version)) + return strings.HasPrefix(normalized, vllmImageTypeNvidia+"-") || + strings.HasPrefix(normalized, vllmImageTypeIntel+"-") || + strings.HasPrefix(normalized, vllmImageTypeAscend+"-") +} + +func isVllmUpgradeCandidate(currentVersion, targetVersion, currentImage string) bool { + if strings.TrimSpace(currentVersion) == strings.TrimSpace(targetVersion) { + return false + } + if !isVllmUpgradeVersionAllowed(currentVersion, targetVersion, currentImage) { + return false + } + if common.CompareVersion(targetVersion, currentVersion) { + return true + } + return !hasVllmVersionFamilyPrefix(currentVersion) && + resolveVllmVersionFamily(targetVersion, "") == vllmImageTypeNvidia && + trimVllmVersionFamily(currentVersion) == trimVllmVersionFamily(targetVersion) +} + +func buildVllmUpgradeImage(currentImage, currentVersion, targetVersion string) string { + trimmedImage := strings.TrimSpace(currentImage) + if trimmedImage == "" || trimmedImage == buildDefaultVllmImageByVersion(currentVersion) { + return buildDefaultVllmImageByVersion(targetVersion) + } + return trimmedImage +} + +func loadVllmImageFromEnv(raw string) string { + envs := make(map[string]interface{}) + if strings.TrimSpace(raw) == "" { + return "" + } + if err := json.Unmarshal([]byte(raw), &envs); err != nil { + return "" + } + if image, ok := envs[vllmImageEnvKey].(string); ok { + return strings.TrimSpace(image) + } + return "" +} + +func setVllmImageInEnvContent(content []byte, image string) []byte { + normalizedImage := strings.TrimSpace(image) + if normalizedImage == "" { + return content + } + lines := strings.Split(string(content), "\n") + replaced := false + for index, line := range lines { + if strings.HasPrefix(line, vllmImageEnvKey+"=") { + lines[index] = vllmImageEnvKey + "=" + normalizedImage + replaced = true + break + } + } + if !replaced { + if len(lines) > 0 && lines[len(lines)-1] == "" { + lines[len(lines)-1] = vllmImageEnvKey + "=" + normalizedImage + lines = append(lines, "") + } else { + lines = append(lines, vllmImageEnvKey+"="+normalizedImage) + } + } + return []byte(strings.Join(lines, "\n")) +} diff --git a/agent/go.mod b/agent/go.mod index 8da9c5fab..0b37df184 100644 --- a/agent/go.mod +++ b/agent/go.mod @@ -8,7 +8,7 @@ require ( github.com/aliyun/aliyun-oss-go-sdk v3.0.2+incompatible github.com/compose-spec/compose-go/v2 v2.13.0 github.com/creack/pty v1.1.24 - github.com/docker/cli v29.6.1+incompatible + github.com/docker/cli v29.6.2+incompatible github.com/docker/docker v28.5.2+incompatible github.com/docker/go-connections v0.7.0 github.com/fsnotify/fsnotify v1.10.1 @@ -36,8 +36,8 @@ require ( github.com/oschwald/maxminddb-golang v1.13.1 github.com/patrickmn/go-cache v2.1.0+incompatible github.com/pkg/errors v0.9.1 - github.com/pkg/sftp v1.13.10 - github.com/qiniu/go-sdk/v7 v7.26.15 + github.com/pkg/sftp v1.13.11 + github.com/qiniu/go-sdk/v7 v7.26.16 github.com/robfig/cron/v3 v3.0.1 github.com/shirou/gopsutil/v4 v4.26.6 github.com/sirupsen/logrus v1.9.4 @@ -50,10 +50,10 @@ require ( github.com/tomasen/fcgi_client v0.0.0-20180423082037-2bb3d819fd19 github.com/upyun/go-sdk v2.1.0+incompatible go.mongodb.org/mongo-driver/v2 v2.8.0 - golang.org/x/crypto v0.53.0 - golang.org/x/net v0.56.0 + golang.org/x/crypto v0.54.0 + golang.org/x/net v0.57.0 golang.org/x/sync v0.22.0 - golang.org/x/sys v0.46.0 + golang.org/x/sys v0.47.0 golang.org/x/text v0.40.0 golang.org/x/time v0.15.0 google.golang.org/genproto v0.0.0-20260414002931-afd174a4e478 @@ -113,7 +113,6 @@ require ( github.com/ebitengine/purego v0.10.0 // indirect github.com/felixge/httpsnoop v1.0.4 // indirect github.com/gabriel-vasile/mimetype v1.4.13 // indirect - github.com/gammazero/toposort v0.1.1 // indirect github.com/gin-contrib/sse v1.1.1 // indirect github.com/glebarez/go-sqlite v1.22.0 // indirect github.com/go-acme/alidns-20150109/v5 v5.4.1 // indirect diff --git a/agent/go.sum b/agent/go.sum index ea47957c8..1d3bfb98a 100644 --- a/agent/go.sum +++ b/agent/go.sum @@ -225,8 +225,8 @@ github.com/distribution/reference v0.6.0 h1:0IXCQ5g4/QMHHkarYzh5l+u8T3t73zM5Qvfr github.com/distribution/reference v0.6.0/go.mod h1:BbU0aIcezP1/5jX/8MP0YiH4SdvB5Y4f/wlDRiLyi3E= github.com/dlclark/regexp2 v1.12.0 h1:0j4c5qQmnC6XOWNjP3PIXURXN2gWx76rd3KvgdPkCz8= github.com/dlclark/regexp2 v1.12.0/go.mod h1:DHkYz0B9wPfa6wondMfaivmHpzrQ3v9q8cnmRbL6yW8= -github.com/docker/cli v29.6.1+incompatible h1:oO7F4nn3Ovr/5TlfTUWFbMwBSS/B7Xs6Epv26gBrUP8= -github.com/docker/cli v29.6.1+incompatible/go.mod h1:JLrzqnKDaYBop7H2jaqPtU4hHvMKP+vjCwu2uszcLI8= +github.com/docker/cli v29.6.2+incompatible h1:/bjePvcbbFTnRrMfWJBY7AjfICdsiLVgHn6LwTVOcqw= +github.com/docker/cli v29.6.2+incompatible/go.mod h1:JLrzqnKDaYBop7H2jaqPtU4hHvMKP+vjCwu2uszcLI8= github.com/docker/docker v28.5.2+incompatible h1:DBX0Y0zAjZbSrm1uzOkdr1onVghKaftjlSWt4AFexzM= github.com/docker/docker v28.5.2+incompatible/go.mod h1:eEKB0N0r5NX/I1kEveEz05bcu8tLC/8azJZsviup8Sk= github.com/docker/docker-credential-helpers v0.9.5 h1:EFNN8DHvaiK8zVqFA2DT6BjXE0GzfLOZ38ggPTKePkY= @@ -274,8 +274,6 @@ github.com/fsnotify/fsnotify v1.10.1 h1:b0/UzAf9yR5rhf3RPm9gf3ehBPpf0oZKIjtpKrx5 github.com/fsnotify/fsnotify v1.10.1/go.mod h1:TLheqan6HD6GBK6PrDWyDPBaEV8LspOxvPSjC+bVfgo= github.com/gabriel-vasile/mimetype v1.4.13 h1:46nXokslUBsAJE/wMsp5gtO500a4F3Nkz9Ufpk2AcUM= github.com/gabriel-vasile/mimetype v1.4.13/go.mod h1:d+9Oxyo1wTzWdyVUPMmXFvp4F9tea18J8ufA774AB3s= -github.com/gammazero/toposort v0.1.1 h1:OivGxsWxF3U3+U80VoLJ+f50HcPU1MIqE1JlKzoJ2Eg= -github.com/gammazero/toposort v0.1.1/go.mod h1:H2cozTnNpMw0hg2VHAYsAxmkHXBYroNangj2NTBQDvw= github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= github.com/gin-contrib/sse v1.1.1 h1:uGYpNwTacv5R68bSGMapo62iLTRa9l5zxGCps4hK6ko= github.com/gin-contrib/sse v1.1.1/go.mod h1:QXzuVkA0YO7o/gun03UI1Q+FTI8ZV/n5t03kIQAI89s= @@ -696,8 +694,8 @@ github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINE github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/profile v1.2.1/go.mod h1:hJw3o1OdXxsrSjjVksARp5W95eeEaEfptyVZyv6JUPA= -github.com/pkg/sftp v1.13.10 h1:+5FbKNTe5Z9aspU88DPIKJ9z2KZoaGCu6Sr6kKR/5mU= -github.com/pkg/sftp v1.13.10/go.mod h1:bJ1a7uDhrX/4OII+agvy28lzRvQrmIQuaHrcI1HbeGA= +github.com/pkg/sftp v1.13.11 h1:0N92SLTB8JqASJB14ZLHHzFnBV8mG9zw4K7jghEFWuE= +github.com/pkg/sftp v1.13.11/go.mod h1:uNkH9roSXglNJqM+glJJi+TQXQUm0fXFWqCFmT8hsN0= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 h1:Jamvg5psRIccs7FGNTlIRMkT8wgtp5eCXdBlqhYGL6U= github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= @@ -725,8 +723,8 @@ github.com/prometheus/procfs v0.0.8/go.mod h1:7Qr8sr6344vo1JqZ6HhLceV9o3AJ1Ff+Gx github.com/prometheus/procfs v0.1.3/go.mod h1:lV6e/gmhEcM9IjHGsFOCxxuZ+z1YqCvr4OA4YeYWdaU= github.com/prometheus/procfs v0.6.0/go.mod h1:cz+aTbrPOrUb4q7XlbU9ygM+/jj0fzG6c1xBZuNvfVA= github.com/prometheus/procfs v0.7.3/go.mod h1:cz+aTbrPOrUb4q7XlbU9ygM+/jj0fzG6c1xBZuNvfVA= -github.com/qiniu/go-sdk/v7 v7.26.15 h1:CaKVcP29ZnOp/pqE7U3RAZxqwL7CmtMTWlV1gAV71H0= -github.com/qiniu/go-sdk/v7 v7.26.15/go.mod h1:ri7fGwbio0pRDFr8EK5TUpx0DbnpIMJ2bMSDxGWfCbk= +github.com/qiniu/go-sdk/v7 v7.26.16 h1:WzPUb0XdBgWnjV8n9revG13vTUcUO4LMcWoacMneH2M= +github.com/qiniu/go-sdk/v7 v7.26.16/go.mod h1:pTwVR1B+8SXcPLhDzBUasiKFTD9F7jRglRDR553BW3k= github.com/quic-go/qpack v0.6.0 h1:g7W+BMYynC1LbYLSqRt8PBg5Tgwxn214ZZR34VIOjz8= github.com/quic-go/qpack v0.6.0/go.mod h1:lUpLKChi8njB4ty2bFLX2x4gzDqXwUpaO1DP9qMDZII= github.com/quic-go/quic-go v0.59.0 h1:OLJkp1Mlm/aS7dpKgTc6cnpynnD2Xg7C1pwL6vy/SAw= @@ -950,8 +948,8 @@ golang.org/x/crypto v0.19.0/go.mod h1:Iy9bg/ha4yyC70EfRS8jz+B6ybOBKMaSxLj6P6oBDf golang.org/x/crypto v0.21.0/go.mod h1:0BP7YvVV9gBbVKyeTG0Gyn+gZm94bibOW5BjDEYAOMs= golang.org/x/crypto v0.23.0/go.mod h1:CKFgDieR+mRhux2Lsu27y0fO304Db0wZe70UKqHu0v8= golang.org/x/crypto v0.24.0/go.mod h1:Z1PMYSOR5nyMcyAVAIQSKCDwalqy85Aqn1x3Ws4L5DM= -golang.org/x/crypto v0.53.0 h1:QZ4Muo8THX6CizN2vPPd5fBGHyogrdK9fG4wLPFUsto= -golang.org/x/crypto v0.53.0/go.mod h1:DNLU434OwVakk9PzuwV8w62mAJpRJL3vsgcfp4Qnsio= +golang.org/x/crypto v0.54.0 h1:YLIA59K4fiNzHzjnZt2tUJQjQtUWfWbeHBqKtk3eScw= +golang.org/x/crypto v0.54.0/go.mod h1:KWL8ny2AZdGR2cWmzeHrp2azQPGogOv+HeQaVEXC2dk= golang.org/x/exp v0.0.0-20180321215751-8460e604b9de/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20180807140117-3d87b88a115f/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= @@ -1049,8 +1047,8 @@ golang.org/x/net v0.21.0/go.mod h1:bIjVDfnllIU7BJ2DNgfnXvpSvtn8VRwhlsaeUTyUS44= golang.org/x/net v0.23.0/go.mod h1:JKghWKKOSdJwpW2GEx0Ja7fmaKnMsbu+MWVZTokSYmg= golang.org/x/net v0.25.0/go.mod h1:JkAGAh7GEvH74S6FOH42FLoXpXbE/aqXSrIQjXgsiwM= golang.org/x/net v0.26.0/go.mod h1:5YKkiSynbBIh3p6iOc/vibscux0x38BZDkn8sCUPxHE= -golang.org/x/net v0.56.0 h1:Rw8j/hFzGvJUZwNBXnAtf5sVDVt+65SK2C7IxCxZt5o= -golang.org/x/net v0.56.0/go.mod h1:D3Ku6r+V6JROoZK144D2XfMHFcMq/0zSfLelVTCFKec= +golang.org/x/net v0.57.0 h1:K5+3DljvIuDG9/Jv9rvyMywYNFCQ9RSUY6OOTTkT+tE= +golang.org/x/net v0.57.0/go.mod h1:KpXc8iv+r3XplLAG/f7Jsf9RPszJzdR0f58q9vGOuEU= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= @@ -1152,8 +1150,8 @@ golang.org/x/sys v0.17.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/sys v0.18.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/sys v0.20.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/sys v0.21.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= -golang.org/x/sys v0.46.0 h1:noSf2Fq6F8DBgS+LysIkx7rIExoNHJsxOAtPp4rthXw= -golang.org/x/sys v0.46.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= +golang.org/x/sys v0.47.0 h1:o7XGOvZQCADBQQ4Y7VNq2dRWQR7JmOUW8Kxx4ZsNgWs= +golang.org/x/sys v0.47.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= golang.org/x/telemetry v0.0.0-20240228155512-f48c80bd79b2/go.mod h1:TeRTkGYfJXctD9OcfyVLyj2J3IxLnKwHJR8f4D8a3YE= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= @@ -1167,8 +1165,8 @@ golang.org/x/term v0.17.0/go.mod h1:lLRBjIVuehSbZlaOtGMbcMncT+aqLLLmKrsjNrUguwk= golang.org/x/term v0.18.0/go.mod h1:ILwASektA3OnRv7amZ1xhE/KTR+u50pbXfZ03+6Nx58= golang.org/x/term v0.20.0/go.mod h1:8UkIAJTvZgivsXaD6/pH6U9ecQzZ45awqEOzuCvwpFY= golang.org/x/term v0.21.0/go.mod h1:ooXLefLobQVslOqselCNF4SxFAaoS6KujMbsGzSDmX0= -golang.org/x/term v0.44.0 h1:0rLvDRCtNj0gZkyIXhCyOb2OAzEhLVqc4B+hrsBhrmc= -golang.org/x/term v0.44.0/go.mod h1:7ze4MdzUzLXpSAoFP1H0bOI9aXDqveSvatT5vKcFh2Y= +golang.org/x/term v0.45.0 h1:NwWyBmoJCbfTHpxrWoZ9C6/VxOf7ic219I8xZZFdrf0= +golang.org/x/term v0.45.0/go.mod h1:9aqxs0blBcrm/n0L9QW0aRVD+ktan8ssZromtqJC43w= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= diff --git a/core/go.mod b/core/go.mod index 60f83864f..91f9b0dca 100644 --- a/core/go.mod +++ b/core/go.mod @@ -21,7 +21,7 @@ require ( github.com/oschwald/maxminddb-golang v1.13.1 github.com/patrickmn/go-cache v2.1.0+incompatible github.com/pkg/errors v0.9.1 - github.com/pkg/sftp v1.13.10 + github.com/pkg/sftp v1.13.11 github.com/robfig/cron/v3 v3.0.1 github.com/shirou/gopsutil/v4 v4.26.6 github.com/sirupsen/logrus v1.9.4 @@ -32,10 +32,10 @@ require ( github.com/swaggo/files/v2 v2.0.2 github.com/swaggo/swag v1.16.6 github.com/xlzd/gotp v0.1.0 - golang.org/x/crypto v0.53.0 - golang.org/x/net v0.56.0 - golang.org/x/sys v0.46.0 - golang.org/x/term v0.44.0 + golang.org/x/crypto v0.54.0 + golang.org/x/net v0.57.0 + golang.org/x/sys v0.47.0 + golang.org/x/term v0.45.0 golang.org/x/text v0.40.0 gopkg.in/yaml.v2 v2.4.0 gopkg.in/yaml.v3 v3.0.1 diff --git a/core/go.sum b/core/go.sum index 36ac6a7e5..2cab76981 100644 --- a/core/go.sum +++ b/core/go.sum @@ -182,8 +182,8 @@ github.com/phpdave11/gofpdi v1.0.15/go.mod h1:vBmVV0Do6hSBHC8uKUQ71JGW+ZGQq74llk github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= -github.com/pkg/sftp v1.13.10 h1:+5FbKNTe5Z9aspU88DPIKJ9z2KZoaGCu6Sr6kKR/5mU= -github.com/pkg/sftp v1.13.10/go.mod h1:bJ1a7uDhrX/4OII+agvy28lzRvQrmIQuaHrcI1HbeGA= +github.com/pkg/sftp v1.13.11 h1:0N92SLTB8JqASJB14ZLHHzFnBV8mG9zw4K7jghEFWuE= +github.com/pkg/sftp v1.13.11/go.mod h1:uNkH9roSXglNJqM+glJJi+TQXQUm0fXFWqCFmT8hsN0= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/power-devops/perfstat v0.0.0-20240221224432-82ca36839d55 h1:o4JXh1EVt9k/+g42oCprj/FisM4qX9L3sZB3upGN2ZU= @@ -267,8 +267,8 @@ golang.org/x/arch v0.26.0 h1:jZ6dpec5haP/fUv1kLCbuJy6dnRrfX6iVK08lZBFpk4= golang.org/x/arch v0.26.0/go.mod h1:0X+GdSIP+kL5wPmpK7sdkEVTt2XoYP0cSjQSbZBwOi8= golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= -golang.org/x/crypto v0.53.0 h1:QZ4Muo8THX6CizN2vPPd5fBGHyogrdK9fG4wLPFUsto= -golang.org/x/crypto v0.53.0/go.mod h1:DNLU434OwVakk9PzuwV8w62mAJpRJL3vsgcfp4Qnsio= +golang.org/x/crypto v0.54.0 h1:YLIA59K4fiNzHzjnZt2tUJQjQtUWfWbeHBqKtk3eScw= +golang.org/x/crypto v0.54.0/go.mod h1:KWL8ny2AZdGR2cWmzeHrp2azQPGogOv+HeQaVEXC2dk= golang.org/x/image v0.0.0-20190910094157-69e4b8554b2a/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0= golang.org/x/image v0.39.0 h1:skVYidAEVKgn8lZ602XO75asgXBgLj9G/FE3RbuPFww= golang.org/x/image v0.39.0/go.mod h1:sIbmppfU+xFLPIG0FoVUTvyBMmgng1/XAMhQ2ft0hpA= @@ -276,8 +276,8 @@ golang.org/x/mod v0.37.0 h1:vF1DjpVEshcIqoEaauuHebaLk1O1forxjxBaVn884JQ= golang.org/x/mod v0.37.0/go.mod h1:m8S8VeM9r4dzDwjrKO0a1sZP3YjeMamRRlD+fmR2Q/0= golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20201202161906-c7110b5ffcbb/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= -golang.org/x/net v0.56.0 h1:Rw8j/hFzGvJUZwNBXnAtf5sVDVt+65SK2C7IxCxZt5o= -golang.org/x/net v0.56.0/go.mod h1:D3Ku6r+V6JROoZK144D2XfMHFcMq/0zSfLelVTCFKec= +golang.org/x/net v0.57.0 h1:K5+3DljvIuDG9/Jv9rvyMywYNFCQ9RSUY6OOTTkT+tE= +golang.org/x/net v0.57.0/go.mod h1:KpXc8iv+r3XplLAG/f7Jsf9RPszJzdR0f58q9vGOuEU= golang.org/x/sync v0.22.0 h1:SZjpbeLmrCk4xhRSZFNZW5gFUeCeFgjekvI/+gfScek= golang.org/x/sync v0.22.0/go.mod h1:9xrNwdLfx4jkKbNva9FpL6vEN7evnE43NNNJQ2LF3+0= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= @@ -285,10 +285,10 @@ golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20190916202348-b4ddaad3f8a3/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201204225414-ed752295db88/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.46.0 h1:noSf2Fq6F8DBgS+LysIkx7rIExoNHJsxOAtPp4rthXw= -golang.org/x/sys v0.46.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= -golang.org/x/term v0.44.0 h1:0rLvDRCtNj0gZkyIXhCyOb2OAzEhLVqc4B+hrsBhrmc= -golang.org/x/term v0.44.0/go.mod h1:7ze4MdzUzLXpSAoFP1H0bOI9aXDqveSvatT5vKcFh2Y= +golang.org/x/sys v0.47.0 h1:o7XGOvZQCADBQQ4Y7VNq2dRWQR7JmOUW8Kxx4ZsNgWs= +golang.org/x/sys v0.47.0/go.mod h1:4GL1E5IUh+htKOUEOaiffhrAeqysfVGipDYzABqnCmw= +golang.org/x/term v0.45.0 h1:NwWyBmoJCbfTHpxrWoZ9C6/VxOf7ic219I8xZZFdrf0= +golang.org/x/term v0.45.0/go.mod h1:9aqxs0blBcrm/n0L9QW0aRVD+ktan8ssZromtqJC43w= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.40.0 h1:Ub2Z6/xjgF1WrYQz2nuITOEegKFtiIy+rieRJ5lHZKs= diff --git a/frontend/package-lock.json b/frontend/package-lock.json index ebe8f3a0c..a8f4c4e2b 100644 --- a/frontend/package-lock.json +++ b/frontend/package-lock.json @@ -52,12 +52,12 @@ "@tailwindcss/postcss": "^4.3.0", "@types/node": "^26.1.1", "@types/uuid": "^11.0.0", - "@typescript-eslint/eslint-plugin": "^8.63.0", - "@typescript-eslint/parser": "^8.63.0", + "@typescript-eslint/eslint-plugin": "^8.64.0", + "@typescript-eslint/parser": "^8.64.0", "@vitejs/plugin-vue": "^6.0.7", "@vitejs/plugin-vue-jsx": "^5.1.6", "@vue/compiler-sfc": "^3.5.35", - "autoprefixer": "^10.5.0", + "autoprefixer": "^10.5.4", "esbuild": "^0.28.1", "eslint": "^10.6.0", "eslint-config-prettier": "^10.1.8", @@ -66,9 +66,9 @@ "lint-staged": "^17.0.7", "postcss": "^8.5.14", "postcss-html": "^1.8.1", - "prettier": "^3.8.2", + "prettier": "^3.9.5", "rollup-plugin-visualizer": "^5.5.4", - "sass": "^1.100.0", + "sass": "^1.101.0", "standard-version": "^9.5.0", "tailwindcss": "^4.3.0", "typescript": "^6.0.3", @@ -3057,17 +3057,17 @@ "license": "MIT" }, "node_modules/@typescript-eslint/eslint-plugin": { - "version": "8.63.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.63.0.tgz", - "integrity": "sha512-rvwSgqT+DHpWdzfSzPatRLm02a0GlESt++9iy3hLCDY4BgkaLcl8LBi9Yh7XGFBpwcBE/K3024QuXWTpbz4FfQ==", + "version": "8.64.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.64.0.tgz", + "integrity": "sha512-CGvQPBxN3wZLu6Rz2kFUpZeoCm78xUic92ck39KPePkO1NPOwjCqdQnm5Q87tpWw9vcBvW8XLrDXjH9PWYtJ3Q==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/regexpp": "^4.12.2", - "@typescript-eslint/scope-manager": "8.63.0", - "@typescript-eslint/type-utils": "8.63.0", - "@typescript-eslint/utils": "8.63.0", - "@typescript-eslint/visitor-keys": "8.63.0", + "@typescript-eslint/scope-manager": "8.64.0", + "@typescript-eslint/type-utils": "8.64.0", + "@typescript-eslint/utils": "8.64.0", + "@typescript-eslint/visitor-keys": "8.64.0", "ignore": "^7.0.5", "natural-compare": "^1.4.0", "ts-api-utils": "^2.5.0" @@ -3080,7 +3080,7 @@ "url": "https://opencollective.com/typescript-eslint" }, "peerDependencies": { - "@typescript-eslint/parser": "^8.63.0", + "@typescript-eslint/parser": "^8.64.0", "eslint": "^8.57.0 || ^9.0.0 || ^10.0.0", "typescript": ">=4.8.4 <6.1.0" } @@ -3096,17 +3096,17 @@ } }, "node_modules/@typescript-eslint/parser": { - "version": "8.63.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.63.0.tgz", - "integrity": "sha512-gwh4gvvlaVDKKxyfxMG+Gnu1u9X0OQBwyGLkbwB65dIzBKnxeRiJlNFqlI3zwVhNXJIs6qV7mlFCn/BIajlVig==", + "version": "8.64.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-8.64.0.tgz", + "integrity": "sha512-KA0OshtlcCCXmbfqyZkM5pV3/WNraJf7DkJRLpyrmwPtud57H5BDX7C3k0LPSPxpprfRL+cJDGabF10mvNCoCw==", "dev": true, "license": "MIT", "peer": true, "dependencies": { - "@typescript-eslint/scope-manager": "8.63.0", - "@typescript-eslint/types": "8.63.0", - "@typescript-eslint/typescript-estree": "8.63.0", - "@typescript-eslint/visitor-keys": "8.63.0", + "@typescript-eslint/scope-manager": "8.64.0", + "@typescript-eslint/types": "8.64.0", + "@typescript-eslint/typescript-estree": "8.64.0", + "@typescript-eslint/visitor-keys": "8.64.0", "debug": "^4.4.3" }, "engines": { @@ -3122,14 +3122,14 @@ } }, "node_modules/@typescript-eslint/project-service": { - "version": "8.63.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.63.0.tgz", - "integrity": "sha512-e5dh0/UI0ok53AlZ5wRkXCB32z/f2jUZqPR/ygAw5WYaSw8j9EoJWlS7wQjr/dmOaqWjnPIn2m+HhVPCMWGZVQ==", + "version": "8.64.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/project-service/-/project-service-8.64.0.tgz", + "integrity": "sha512-tk4WpOJ6IEbGrVHaNmM0YRrwAD3exZlIK3iadQNAxh4YKk6jvUQ4ecq18n+v7+meh+cJ3j+D8nbk8sRKhlwLQg==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/tsconfig-utils": "^8.63.0", - "@typescript-eslint/types": "^8.63.0", + "@typescript-eslint/tsconfig-utils": "^8.64.0", + "@typescript-eslint/types": "^8.64.0", "debug": "^4.4.3" }, "engines": { @@ -3144,14 +3144,14 @@ } }, "node_modules/@typescript-eslint/scope-manager": { - "version": "8.63.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.63.0.tgz", - "integrity": "sha512-uUyfMWCnDSN8bCpcrY8nGP2BLkQ9Xn0GsipcONcpIDWhwhO4ZSyHvyS14U3X75mzxWxL3I2UZIrenTzdzcJO8A==", + "version": "8.64.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-8.64.0.tgz", + "integrity": "sha512-CXEaFdYXjSTgKhisNkwCcJwTP8Pl+fmRrEQrri4nm3vU743bALrxzLmq7fHG/7e6a5xO0lDYeURpZmBuhHk54w==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.63.0", - "@typescript-eslint/visitor-keys": "8.63.0" + "@typescript-eslint/types": "8.64.0", + "@typescript-eslint/visitor-keys": "8.64.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3162,9 +3162,9 @@ } }, "node_modules/@typescript-eslint/tsconfig-utils": { - "version": "8.63.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.63.0.tgz", - "integrity": "sha512-sUAbkulqBAsncKnbRP3+7CtQFRKicexnj7ZwNC6ddCR7EmrXvjvdCYMJbUIqMd6lwoEriZjwLo08aS5tSjVMHg==", + "version": "8.64.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/tsconfig-utils/-/tsconfig-utils-8.64.0.tgz", + "integrity": "sha512-2yo8rRNKuzbVWQp5kslhANqZ2uDAeROQHBRZNPu8JDsHmeFNj/XJJhX/FhNUWmkHHvoNsKa6+tHJiig87EzsQw==", "dev": true, "license": "MIT", "engines": { @@ -3179,15 +3179,15 @@ } }, "node_modules/@typescript-eslint/type-utils": { - "version": "8.63.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.63.0.tgz", - "integrity": "sha512-Nzzh/OGxVCOjObjaj1CQF2RUasyYy2Jfuh+zZ3PjLzG2fYRriAiZLib9UKtO+CpQAS3YHiAS+ckZDclwqI1TPA==", + "version": "8.64.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-8.64.0.tgz", + "integrity": "sha512-XWG4Fmmv/6SvyS9nH8jWrKs6terwJvE8cyRt1CzYYqzp9OrPhCT4cMc/f7C6RZCwG+qMmiffJS1/qJP8G1URtg==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.63.0", - "@typescript-eslint/typescript-estree": "8.63.0", - "@typescript-eslint/utils": "8.63.0", + "@typescript-eslint/types": "8.64.0", + "@typescript-eslint/typescript-estree": "8.64.0", + "@typescript-eslint/utils": "8.64.0", "debug": "^4.4.3", "ts-api-utils": "^2.5.0" }, @@ -3204,9 +3204,9 @@ } }, "node_modules/@typescript-eslint/types": { - "version": "8.63.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.63.0.tgz", - "integrity": "sha512-xyLtl9DUBBFrcJS4x2pIqGLH68/tC2uOa4Z7pUteW09D3bXnnXUom4dyPikzWgB7llmIc1zoeI3aoUdC4rPK/Q==", + "version": "8.64.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-8.64.0.tgz", + "integrity": "sha512-qjhfuTfLXjA4IOzXvz0rTjT01BqEiIgPoUeMwiEjnaHKJMTNo8rH5pYW1a2L/0Dnux2fPC85AeyJoWaGa8WxTA==", "dev": true, "license": "MIT", "engines": { @@ -3218,16 +3218,16 @@ } }, "node_modules/@typescript-eslint/typescript-estree": { - "version": "8.63.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.63.0.tgz", - "integrity": "sha512-ygBkU+B7ex5UI/gKhaqexWev79uISfIv7XQCRNYO/jmD8rGLPyWLAb3KMRT6nd8Gt9bmUBi9+iX6tBdYfOY81Q==", + "version": "8.64.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-8.64.0.tgz", + "integrity": "sha512-Pztpsn1aCE1oWDvDEfUk31nngvvF7vUB5SwHFEaZIFpvw7WJtqUHHL4plBZDA9HfWJJjL13BdG0YrJInTUvoVA==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/project-service": "8.63.0", - "@typescript-eslint/tsconfig-utils": "8.63.0", - "@typescript-eslint/types": "8.63.0", - "@typescript-eslint/visitor-keys": "8.63.0", + "@typescript-eslint/project-service": "8.64.0", + "@typescript-eslint/tsconfig-utils": "8.64.0", + "@typescript-eslint/types": "8.64.0", + "@typescript-eslint/visitor-keys": "8.64.0", "debug": "^4.4.3", "minimatch": "^10.2.2", "semver": "^7.7.3", @@ -3285,16 +3285,16 @@ } }, "node_modules/@typescript-eslint/utils": { - "version": "8.63.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.63.0.tgz", - "integrity": "sha512-fUKaeAvrTuQg/Tgt3nliAUSZHJM6DlCcfyEmxCvlX8kieWSStBX+5O5Fnidtc3i2JrH+9c/GL4RY2iasd/GPTA==", + "version": "8.64.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-8.64.0.tgz", + "integrity": "sha512-aJUGVB3+U0htrrCjoA8qukw8cm8fNCGAxK/tVoS70k8aeb7DETKeFozRiVFIwEeN9WJLsjaP3ph8I60tY2XZoQ==", "dev": true, "license": "MIT", "dependencies": { "@eslint-community/eslint-utils": "^4.9.1", - "@typescript-eslint/scope-manager": "8.63.0", - "@typescript-eslint/types": "8.63.0", - "@typescript-eslint/typescript-estree": "8.63.0" + "@typescript-eslint/scope-manager": "8.64.0", + "@typescript-eslint/types": "8.64.0", + "@typescript-eslint/typescript-estree": "8.64.0" }, "engines": { "node": "^18.18.0 || ^20.9.0 || >=21.1.0" @@ -3309,13 +3309,13 @@ } }, "node_modules/@typescript-eslint/visitor-keys": { - "version": "8.63.0", - "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.63.0.tgz", - "integrity": "sha512-UexrHGnGTpbuQHct2ExOc2ZcFbGUS9FOesCxxqdBGcpI1BxYu/LZ6U8Aq6/72XtF/qRBk9nhuGHFJIXXMhPMdw==", + "version": "8.64.0", + "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-8.64.0.tgz", + "integrity": "sha512-mrtuL8Nsn6gi2H4mo5KMTp823M+3Q19Ew/i+Zlikq20tIMm99C3Ez0dCmkWWnxut20esQvTg8aUSEhMcAOXhEw==", "dev": true, "license": "MIT", "dependencies": { - "@typescript-eslint/types": "8.63.0", + "@typescript-eslint/types": "8.64.0", "eslint-visitor-keys": "^5.0.0" }, "engines": { @@ -3920,9 +3920,9 @@ "license": "MIT" }, "node_modules/autoprefixer": { - "version": "10.5.0", - "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.5.0.tgz", - "integrity": "sha512-FMhOoZV4+qR6aTUALKX2rEqGG+oyATvwBt9IIzVR5rMa2HRWPkxf+P+PAJLD1I/H5/II+HuZcBJYEFBpq39ong==", + "version": "10.5.4", + "resolved": "https://registry.npmjs.org/autoprefixer/-/autoprefixer-10.5.4.tgz", + "integrity": "sha512-MaU0U/za7N3r6brxD4YB/l4NSrFzLPlANv6wEuQVaIPlD3L4W9rFcQPbL/EilY9BHhHvhfcz3gInDLrEtWT4EA==", "dev": true, "funding": [ { @@ -3940,8 +3940,8 @@ ], "license": "MIT", "dependencies": { - "browserslist": "^4.28.2", - "caniuse-lite": "^1.0.30001787", + "browserslist": "^4.28.6", + "caniuse-lite": "^1.0.30001806", "fraction.js": "^5.3.4", "picocolors": "^1.1.1", "postcss-value-parser": "^4.2.0" @@ -3976,9 +3976,9 @@ "license": "MIT" }, "node_modules/baseline-browser-mapping": { - "version": "2.10.35", - "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.10.35.tgz", - "integrity": "sha512-honAfLBde0HAFLdNyBEfuuENkF6zR+ozxqxa/2zJKHBe1qzLqyTSeRKpdPEHAP03rlDGyQOPnCSxnVpVqQo9Mg==", + "version": "2.10.44", + "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.10.44.tgz", + "integrity": "sha512-T3ghW+sl/ZJ8w1v/yQx3qvJ9040DWoLBz8JT/CILbAKcFyG9b2MRe75v6W5uXjv6uH1lumK2Kv46y2zSkcej0Q==", "dev": true, "license": "Apache-2.0", "bin": { @@ -4030,9 +4030,9 @@ } }, "node_modules/browserslist": { - "version": "4.28.2", - "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.28.2.tgz", - "integrity": "sha512-48xSriZYYg+8qXna9kwqjIVzuQxi+KYWp2+5nCYnYKPTr0LvD89Jqk2Or5ogxz0NUMfIjhh2lIUX/LyX9B4oIg==", + "version": "4.28.6", + "resolved": "https://registry.npmjs.org/browserslist/-/browserslist-4.28.6.tgz", + "integrity": "sha512-FQBYNK15VMslhLHpA7+n+n1GOlF1kId2xcCg7/j95f24AOF6VDYMNH4mFxF7KuaTdv627faazpOAjFzMrfJOUw==", "dev": true, "funding": [ { @@ -4051,10 +4051,10 @@ "license": "MIT", "peer": true, "dependencies": { - "baseline-browser-mapping": "^2.10.12", - "caniuse-lite": "^1.0.30001782", - "electron-to-chromium": "^1.5.328", - "node-releases": "^2.0.36", + "baseline-browser-mapping": "^2.10.42", + "caniuse-lite": "^1.0.30001803", + "electron-to-chromium": "^1.5.389", + "node-releases": "^2.0.51", "update-browserslist-db": "^1.2.3" }, "bin": { @@ -4129,9 +4129,9 @@ } }, "node_modules/caniuse-lite": { - "version": "1.0.30001797", - "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001797.tgz", - "integrity": "sha512-l8xKG+gwAIExZGl9FrF7KUwuOmk6wbEPC9Xoy/RtnWv1XG0Q4LFlagaLpUv3Kiza3W/wm27zy0yWJEieYKAP6w==", + "version": "1.0.30001806", + "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001806.tgz", + "integrity": "sha512-72Cuvd95zbSYPKq6Fhg8eDJRlzgWDf7/mtoZv6Qe/DYNCEBdNxoA3+rZAU2ZhGCpZlns3EssFavaZomckT5Uuw==", "dev": true, "funding": [ { @@ -5154,9 +5154,9 @@ } }, "node_modules/electron-to-chromium": { - "version": "1.5.376", - "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.376.tgz", - "integrity": "sha512-cUVA7/RvbFTEuw/i3obUwDTRIXojaxkResf+ibByPFxjc6XK3VNtcQXV0NSbAlJ0FMjcJGgftVVB4Qo184EXvA==", + "version": "1.5.394", + "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.394.tgz", + "integrity": "sha512-Wmt2Gm0o8JWBuGgmc4XZ0u9s1RaCRqhxP47phplmfg04+qypTUurpeJGP45A7Fhv7jdrrVH44PLlR9qXo37cVQ==", "dev": true, "license": "ISC" }, @@ -7914,9 +7914,9 @@ "optional": true }, "node_modules/node-releases": { - "version": "2.0.48", - "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.48.tgz", - "integrity": "sha512-1uz8041X6LoI6ZSdZacM9lVY28vuzDlSKitnpbSNK0RfKoIJkX29NBPVEFXhnuSuEOA9Ww0xnPJ+ILWbGAv8DA==", + "version": "2.0.51", + "resolved": "https://registry.npmjs.org/node-releases/-/node-releases-2.0.51.tgz", + "integrity": "sha512-wRNIrw4DmVLKQlbgOMdkMx27Wrpzes2hh5Jtbi2bjPd+4wJstWIqP5A+lscnqbm0xxmT5Bpg8Lec5ItEBwx6BQ==", "dev": true, "license": "MIT", "engines": { @@ -8344,9 +8344,9 @@ } }, "node_modules/prettier": { - "version": "3.8.2", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.8.2.tgz", - "integrity": "sha512-8c3mgTe0ASwWAJK+78dpviD+A8EqhndQPUBpNUIPt6+xWlIigCwfN01lWr9MAede4uqXGTEKeQWTvzb3vjia0Q==", + "version": "3.9.5", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-3.9.5.tgz", + "integrity": "sha512-/FVl766LpUfB5vXgCYOYa0MeV/441Ia99AeICQIQFTY/Nw0roZwULcXpku5i1/m5kt/baz+s4Zogspd839HSMg==", "dev": true, "license": "MIT", "peer": true, @@ -8813,9 +8813,9 @@ "license": "MIT" }, "node_modules/sass": { - "version": "1.100.0", - "resolved": "https://registry.npmjs.org/sass/-/sass-1.100.0.tgz", - "integrity": "sha512-B5j0rYMlinhhOo9tjQebMVVn0TfyXAF+wB3b2ggZUuJ/is/Y+7+JGjirAMxHZ9Z3hIP98NPfamlAkBHa1lAaXQ==", + "version": "1.101.0", + "resolved": "https://registry.npmjs.org/sass/-/sass-1.101.0.tgz", + "integrity": "sha512-OL3GoQyoUdDt843DpVmDO6y2k1sc5IhUDSpu8XucEI+35neq5QivZ1iuegnpraEVTJXlQGK1gl27zKcTLEPbQw==", "dev": true, "license": "MIT", "peer": true, diff --git a/frontend/package.json b/frontend/package.json index 480d636c5..403035ab1 100644 --- a/frontend/package.json +++ b/frontend/package.json @@ -63,12 +63,12 @@ "@tailwindcss/postcss": "^4.3.0", "@types/node": "^26.1.1", "@types/uuid": "^11.0.0", - "@typescript-eslint/eslint-plugin": "^8.63.0", - "@typescript-eslint/parser": "^8.63.0", + "@typescript-eslint/eslint-plugin": "^8.64.0", + "@typescript-eslint/parser": "^8.64.0", "@vitejs/plugin-vue": "^6.0.7", "@vitejs/plugin-vue-jsx": "^5.1.6", "@vue/compiler-sfc": "^3.5.35", - "autoprefixer": "^10.5.0", + "autoprefixer": "^10.5.4", "esbuild": "^0.28.1", "eslint": "^10.6.0", "eslint-config-prettier": "^10.1.8", @@ -77,9 +77,9 @@ "lint-staged": "^17.0.7", "postcss": "^8.5.14", "postcss-html": "^1.8.1", - "prettier": "^3.8.2", + "prettier": "^3.9.5", "rollup-plugin-visualizer": "^5.5.4", - "sass": "^1.100.0", + "sass": "^1.101.0", "standard-version": "^9.5.0", "tailwindcss": "^4.3.0", "typescript": "^6.0.3", diff --git a/frontend/src/composables/usePageState.ts b/frontend/src/composables/usePageState.ts new file mode 100644 index 000000000..659d65cab --- /dev/null +++ b/frontend/src/composables/usePageState.ts @@ -0,0 +1,11 @@ +import { reactive, type UnwrapNestedRefs } from 'vue'; +import { useRoute } from 'vue-router'; +import { useGlobalStore } from '@/composables/useGlobalStore'; +import { getPageState } from '@/utils/page-state-cache'; + +export const usePageState = (factory: () => T): UnwrapNestedRefs => { + const route = useRoute(); + const { currentNode } = useGlobalStore(); + const key = `${currentNode.value}:${String(route.name || route.path)}`; + return reactive(getPageState(key, factory)); +}; diff --git a/frontend/src/lang/modules/en.ts b/frontend/src/lang/modules/en.ts index 0beda34b2..ae6cfd285 100644 --- a/frontend/src/lang/modules/en.ts +++ b/frontend/src/lang/modules/en.ts @@ -4835,6 +4835,7 @@ const message = { provinceRuleLabel: 'Province', openRestyFeatureVersionAlert: 'OpenResty must be newer than 1.31.1.1-0 for {0} to take effect.', ipLocation: 'IP Location', + ipLocationSearchHelper: 'Enter an IP location, fuzzy search supported', action: 'Action', ruleType: 'Attack Type', ipHelper: 'Enter the IP address', @@ -5042,6 +5043,9 @@ const message = { observationModeConfirm: 'In observation mode, all WAF matches are logged without blocking requests. Continue?', globalStrictRequired: 'Enable strict mode in global settings first', + websiteSearchHelper: 'Enter a website domain, alias, or remark', + configReadFailed: 'Failed to load configuration', + detailSetting: 'Detailed settings', observe: 'Observe', saveLog: 'Save Log', remoteURLHelper: 'The remote URL needs to ensure one IP per line and no other characters', diff --git a/frontend/src/lang/modules/es-es.ts b/frontend/src/lang/modules/es-es.ts index 5ff0f8ae2..a137af8dd 100644 --- a/frontend/src/lang/modules/es-es.ts +++ b/frontend/src/lang/modules/es-es.ts @@ -4885,6 +4885,7 @@ const message = { provinceRuleLabel: 'Provincia', openRestyFeatureVersionAlert: 'OpenResty debe ser posterior a la versión 1.31.1.1-0 para que {0} funcione.', ipLocation: 'Ubicación IP', + ipLocationSearchHelper: 'Introduzca la ubicación de la IP; se admite búsqueda aproximada', action: 'Acción', ruleType: 'Tipo de ataque', ipHelper: 'Introduce la dirección IP', @@ -5086,6 +5087,9 @@ const message = { observationModeConfirm: 'En el modo de observación, todas las coincidencias del WAF se registran sin bloquear solicitudes. ¿Continuar?', globalStrictRequired: 'Primero habilite el modo estricto en la configuración global', + websiteSearchHelper: 'Introduzca el dominio, alias o comentario del sitio web', + configReadFailed: 'No se pudo cargar la configuración', + detailSetting: 'Configuración detallada', observe: 'Observar', saveLog: 'Guardar log', remoteURLHelper: 'La URL remota debe tener solo una IP por línea y sin otros caracteres', diff --git a/frontend/src/lang/modules/fa.ts b/frontend/src/lang/modules/fa.ts index ed7a24853..8d82478c5 100644 --- a/frontend/src/lang/modules/fa.ts +++ b/frontend/src/lang/modules/fa.ts @@ -4796,6 +4796,7 @@ const message = { provincePolicy: 'سیاست استان', openRestyFeatureVersionAlert: 'برای فعال شدن {0}، نسخه OpenResty باید جدیدتر از 1.31.1.1-0 باشد.', ipLocation: 'مکان IP', + ipLocationSearchHelper: 'موقعیت IP را وارد کنید؛ جست‌وجوی تقریبی پشتیبانی می‌شود', action: 'اقدام', ruleType: 'نوع حمله', ipHelper: 'آدرس IP را وارد کنید', @@ -4991,6 +4992,17 @@ const message = { crlf: 'تزریق CRLF', strict: 'حالت سخت‌گیرانه', strictHelper: 'از قوانین سخت‌گیرانه‌تر برای تأیید درخواست‌ها استفاده کنید', + executionStrategy: 'راهبرد اجرا', + detectionStrength: 'شدت تشخیص', + protectionMode: 'حالت محافظت', + observationMode: 'حالت مشاهده', + standardMode: 'حالت استاندارد', + observationModeConfirm: + 'در حالت مشاهده، تمام موارد منطبق WAF فقط ثبت می‌شوند و درخواست‌ها مسدود نمی‌شوند. ادامه می‌دهید؟', + globalStrictRequired: 'ابتدا حالت سخت‌گیرانه را در تنظیمات سراسری فعال کنید', + websiteSearchHelper: 'دامنه، نام مستعار یا توضیحات وب‌سایت را وارد کنید', + configReadFailed: 'بارگذاری پیکربندی ناموفق بود', + detailSetting: 'تنظیمات دقیق', saveLog: 'ذخیره لاگ', remoteURLHelper: 'URL از راه دور باید تضمین کند که هر خط یک IP است و هیچ کاراکتر دیگری ندارد', notFound: 'یافت نشد (۴۰۴)', diff --git a/frontend/src/lang/modules/ja.ts b/frontend/src/lang/modules/ja.ts index fab4698ff..91c643b20 100644 --- a/frontend/src/lang/modules/ja.ts +++ b/frontend/src/lang/modules/ja.ts @@ -4849,6 +4849,7 @@ const message = { openRestyFeatureVersionAlert: '{0} を有効にするには、OpenResty のバージョンが 1.31.1.1-0 より新しい必要があります。', ipLocation: 'IP位置', + ipLocationSearchHelper: 'IP の所在地を入力してください(あいまい検索対応)', action: 'アクション', ruleType: '攻撃タイプ', ipHelper: 'IPアドレスを入力してください', @@ -5053,6 +5054,9 @@ const message = { observationModeConfirm: '監視モードでは、すべての WAF 検出をログに記録し、リクエストをブロックしません。続行しますか?', globalStrictRequired: '先にグローバル設定で厳格モードを有効にしてください', + websiteSearchHelper: 'サイトのドメイン、エイリアス、または備考を入力してください', + configReadFailed: '設定の読み込みに失敗しました', + detailSetting: '詳細設定', observe: '監視', saveLog: 'ログを保存', remoteURLHelper: 'リモート URL は、1行に1つのIPで、他の文字がないことを保証する必要があります', diff --git a/frontend/src/lang/modules/ko.ts b/frontend/src/lang/modules/ko.ts index 5f9426dea..45aef8836 100644 --- a/frontend/src/lang/modules/ko.ts +++ b/frontend/src/lang/modules/ko.ts @@ -4753,6 +4753,7 @@ const message = { provinceRuleLabel: '성', openRestyFeatureVersionAlert: '{0}을(를) 적용하려면 OpenResty 버전이 1.31.1.1-0보다 높아야 합니다.', ipLocation: 'IP 위치', + ipLocationSearchHelper: 'IP 위치를 입력하세요. 부분 검색을 지원합니다', action: '동작', ruleType: '공격 유형', ipHelper: 'IP 주소를 입력하세요', @@ -4953,6 +4954,9 @@ const message = { observationModeConfirm: '관찰 모드에서는 모든 WAF 탐지를 기록하지만 요청을 차단하지 않습니다. 계속하시겠습니까?', globalStrictRequired: '먼저 전역 설정에서 엄격 모드를 활성화하세요', + websiteSearchHelper: '웹사이트 도메인, 별칭 또는 비고를 입력하세요', + configReadFailed: '설정을 불러오지 못했습니다', + detailSetting: '상세 설정', observe: '관찰', saveLog: '로그 저장', remoteURLHelper: '원격 URL은 한 줄에 하나의 IP만 포함하고 다른 문자는 포함하지 않아야 합니다', diff --git a/frontend/src/lang/modules/ms.ts b/frontend/src/lang/modules/ms.ts index 913ee5e51..a78997fe3 100644 --- a/frontend/src/lang/modules/ms.ts +++ b/frontend/src/lang/modules/ms.ts @@ -4912,6 +4912,7 @@ const message = { provinceRuleLabel: 'Wilayah pentadbiran', openRestyFeatureVersionAlert: 'OpenResty mesti lebih baharu daripada 1.31.1.1-0 agar {0} berfungsi.', ipLocation: 'Lokasi IP', + ipLocationSearchHelper: 'Masukkan lokasi IP; carian kabur disokong', action: 'Tindakan', ruleType: 'Jenis Serangan', ipHelper: 'Masukkan alamat IP', @@ -5118,6 +5119,9 @@ const message = { observationModeConfirm: 'Dalam mod pemerhatian, semua padanan WAF direkod tanpa menyekat permintaan. Teruskan?', globalStrictRequired: 'Dayakan mod strict dalam tetapan global terlebih dahulu', + websiteSearchHelper: 'Masukkan domain, alias atau catatan laman web', + configReadFailed: 'Gagal memuatkan konfigurasi', + detailSetting: 'Tetapan terperinci', observe: 'Perhati', saveLog: 'Simpan Log', remoteURLHelper: 'URL jauh perlu memastikan satu IP setiap baris dan tiada aksara lain', diff --git a/frontend/src/lang/modules/pt-br.ts b/frontend/src/lang/modules/pt-br.ts index d361526f3..ea7ec09d0 100644 --- a/frontend/src/lang/modules/pt-br.ts +++ b/frontend/src/lang/modules/pt-br.ts @@ -5054,6 +5054,7 @@ const message = { provinceRuleLabel: 'Província', openRestyFeatureVersionAlert: 'A versão do OpenResty deve ser superior a 1.31.1.1-0 para que {0} funcione.', ipLocation: 'Localização do IP', + ipLocationSearchHelper: 'Insira a localização do IP; pesquisa aproximada é suportada', action: 'Ação', ruleType: 'Tipo de ataque', ipHelper: 'Digite o endereço IP', @@ -5262,6 +5263,9 @@ const message = { observationModeConfirm: 'No modo de observação, todas as correspondências do WAF são registradas sem bloquear solicitações. Continuar?', globalStrictRequired: 'Primeiro habilite o modo estrito nas configurações globais', + websiteSearchHelper: 'Digite o domínio, alias ou observação do site', + configReadFailed: 'Falha ao carregar a configuração', + detailSetting: 'Configurações detalhadas', observe: 'Observar', saveLog: 'Salvar log', remoteURLHelper: 'O URL remoto precisa garantir um IP por linha e nenhum outro caractere', diff --git a/frontend/src/lang/modules/ru.ts b/frontend/src/lang/modules/ru.ts index bdeaf1f35..ca990b14e 100644 --- a/frontend/src/lang/modules/ru.ts +++ b/frontend/src/lang/modules/ru.ts @@ -4900,6 +4900,7 @@ const message = { provinceRuleLabel: 'Провинция', openRestyFeatureVersionAlert: 'Для работы функции «{0}» требуется версия OpenResty новее 1.31.1.1-0.', ipLocation: 'Местоположение IP', + ipLocationSearchHelper: 'Введите местоположение IP; поддерживается нечеткий поиск', action: 'Действие', ruleType: 'Тип атаки', ipHelper: 'Введите IP-адрес', @@ -5108,6 +5109,9 @@ const message = { observationModeConfirm: 'В режиме наблюдения все срабатывания WAF записываются без блокировки запросов. Продолжить?', globalStrictRequired: 'Сначала включите строгий режим в глобальных настройках', + websiteSearchHelper: 'Введите домен, псевдоним или примечание сайта', + configReadFailed: 'Не удалось загрузить конфигурацию', + detailSetting: 'Подробные настройки', observe: 'Наблюдение', saveLog: 'Сохранить лог', remoteURLHelper: 'Удаленный URL должен содержать один IP на строку и не содержать других символов', diff --git a/frontend/src/lang/modules/tr.ts b/frontend/src/lang/modules/tr.ts index b744a4059..a168ea4ca 100644 --- a/frontend/src/lang/modules/tr.ts +++ b/frontend/src/lang/modules/tr.ts @@ -4897,6 +4897,7 @@ const message = { openRestyFeatureVersionAlert: '{0} özelliğinin çalışması için OpenResty sürümü 1.31.1.1-0 sürümünden daha yeni olmalıdır.', ipLocation: 'IP Konumu', + ipLocationSearchHelper: 'IP konumunu girin; bulanık arama desteklenir', action: 'Eylem', ruleType: 'Saldırı Türü', ipHelper: 'IP adresini girin', @@ -5103,6 +5104,9 @@ const message = { observationModeConfirm: 'Gözlem modunda tüm WAF eşleşmeleri istekler engellenmeden kaydedilir. Devam edilsin mi?', globalStrictRequired: 'Önce genel ayarlarda katı modu etkinleştirin', + websiteSearchHelper: 'Web sitesi alan adı, takma adı veya açıklaması girin', + configReadFailed: 'Yapılandırma yüklenemedi', + detailSetting: 'Ayrıntılı ayarlar', observe: 'Gözlem', saveLog: 'Günlüğü Kaydet', remoteURLHelper: 'Uzak URL, her satırda bir IP içermeli ve başka karakter olmamalıdır', diff --git a/frontend/src/lang/modules/zh-Hant.ts b/frontend/src/lang/modules/zh-Hant.ts index e61c670d7..8c54e916b 100644 --- a/frontend/src/lang/modules/zh-Hant.ts +++ b/frontend/src/lang/modules/zh-Hant.ts @@ -4498,6 +4498,7 @@ const message = { provinceRuleLabel: '省份', openRestyFeatureVersionAlert: 'OpenResty 版本需高於 1.31.1.1-0,{0}才會生效。', ipLocation: 'IP 歸屬地', + ipLocationSearchHelper: '請輸入 IP 歸屬地,支援模糊搜尋', action: '動作', ruleType: '攻擊類型', ipHelper: '請輸入 IP', @@ -4691,6 +4692,9 @@ const message = { observationModeHelper: '僅檢測並記錄日誌,不會攔截請求', observationModeConfirm: '開啟觀察模式後,所有 WAF 命中都只記錄日誌,不會攔截請求,是否繼續?', globalStrictRequired: '需要先在全域設定中開啟嚴格模式', + websiteSearchHelper: '請輸入網站網域、別名或備註', + configReadFailed: '設定讀取失敗', + detailSetting: '詳細設定', observe: '觀察', saveLog: '儲存日誌', remoteURLHelper: '遠端 URL 需要保證每行一個 IP 並且沒有其他字元', diff --git a/frontend/src/lang/modules/zh.ts b/frontend/src/lang/modules/zh.ts index b620fa4bd..24262c904 100644 --- a/frontend/src/lang/modules/zh.ts +++ b/frontend/src/lang/modules/zh.ts @@ -3956,6 +3956,7 @@ const message = { provinceRuleLabel: '省份', openRestyFeatureVersionAlert: 'OpenResty 版本需高于 1.31.1.1-0,{0}才会生效。', ipLocation: 'IP 归属地', + ipLocationSearchHelper: '请输入 IP 归属地,支持模糊搜索', action: '动作', ruleType: '攻击类型', ipHelper: '请输入 IP', @@ -4149,6 +4150,9 @@ const message = { observationModeHelper: '仅检测并记录日志,不会拦截请求', observationModeConfirm: '开启观察模式后,所有 WAF 命中都只记录日志,不会拦截请求,是否继续?', globalStrictRequired: '需要先在全局设置中开启严格模式', + websiteSearchHelper: '请输入网站域名、别名或备注', + configReadFailed: '配置读取失败', + detailSetting: '详细设置', observe: '观察', saveLog: '保存日志', remoteURLHelper: '远程 URL 需要保证每行一个 IP 并且没有其他字符', diff --git a/frontend/src/store/modules/global.ts b/frontend/src/store/modules/global.ts index a27ab79d4..8003d8255 100644 --- a/frontend/src/store/modules/global.ts +++ b/frontend/src/store/modules/global.ts @@ -5,6 +5,7 @@ import { GlobalState } from '../interface'; import { DeviceType } from '@/enums/app'; import i18n, { setActiveLocale } from '@/lang'; import { isMasterOnlyPermissionCode, setMasterOnlyPermissionCodes, toManageCode } from '@/utils/permission-codes'; +import { clearPageStateCache } from '@/utils/page-state-cache'; const CN_DOCS_URL = 'https://1panel.cn/docs/v2'; const INTL_DOCS_URL = 'https://docs.1panel.pro/v2'; @@ -121,6 +122,7 @@ const GlobalStore = defineStore('GlobalState', { setMasterOnlyPermissionCodes(this.masterOnlyPermissions); }, clearAuthInfo() { + clearPageStateCache(); this.permissions = []; this.masterOnlyPermissions = []; this.nodeRoles = []; diff --git a/frontend/src/utils/page-state-cache.ts b/frontend/src/utils/page-state-cache.ts new file mode 100644 index 000000000..64863fe23 --- /dev/null +++ b/frontend/src/utils/page-state-cache.ts @@ -0,0 +1,15 @@ +const pageStateCache = new Map(); + +export const getPageState = (key: string, factory: () => T): T => { + const cached = pageStateCache.get(key) as T | undefined; + if (cached) { + return cached; + } + const state = factory(); + pageStateCache.set(key, state); + return state; +}; + +export const clearPageStateCache = () => { + pageStateCache.clear(); +}; diff --git a/frontend/src/views/cronjob/cronjob/index.vue b/frontend/src/views/cronjob/cronjob/index.vue index 180efeee8..d8bbbd5ac 100644 --- a/frontend/src/views/cronjob/cronjob/index.vue +++ b/frontend/src/views/cronjob/cronjob/index.vue @@ -61,6 +61,11 @@