diff --git a/agent/app/api/v2/model_downloader.go b/agent/app/api/v2/model_downloader.go index f0a6dffae..a6381e074 100644 --- a/agent/app/api/v2/model_downloader.go +++ b/agent/app/api/v2/model_downloader.go @@ -305,6 +305,15 @@ func (b *BaseApi) PageLocalDownloadedModels(c *gin.Context) { helper.SuccessWithData(c, dto.PageResult{Items: items, Total: total}) } +func (b *BaseApi) ListLocalModelOptions(c *gin.Context) { + items, err := modelDownloaderService.ListLocalModelOptions() + if err != nil { + handleModelDownloaderError(c, err) + return + } + helper.SuccessWithData(c, items) +} + // @Tags AI // @Summary Delete locally downloaded model // @Accept json diff --git a/agent/app/dto/model_downloader.go b/agent/app/dto/model_downloader.go index f7819f848..fd45058d5 100644 --- a/agent/app/dto/model_downloader.go +++ b/agent/app/dto/model_downloader.go @@ -92,6 +92,12 @@ type ModelDownloadTaskItem struct { CanRemoveRecord bool `json:"canRemoveRecord"` } +type LocalModelOption struct { + Name string `json:"name"` + Organization string `json:"organization"` + Path string `json:"path"` +} + type LocalModelSearch struct { DownloadType string `json:"downloadType" validate:"omitempty,oneof=all tokenizer"` PageInfo @@ -121,6 +127,7 @@ type FeaturedModel struct { Sort int `json:"sort" yaml:"sort"` Family string `json:"family" yaml:"category"` RepoID string `json:"repoID" yaml:"name"` + WeightProvider string `json:"weightProvider" yaml:"weightProvider"` Sources []string `json:"sources" yaml:"sources"` SourceModelIDs map[string]string `json:"sourceModelIds" yaml:"sourceModelIds"` Architecture string `json:"architecture" yaml:"modelType"` @@ -133,11 +140,13 @@ type FeaturedModel struct { type FeaturedModelSearch struct { PageInfo - Family string `json:"family"` - Info string `json:"info"` + Family string `json:"family"` + WeightProvider string `json:"weightProvider"` + Info string `json:"info"` } type FeaturedModelPage struct { PageResult - Families []string `json:"families"` + Families []string `json:"families"` + WeightProviders []string `json:"weightProviders"` } diff --git a/agent/app/model/featured_model.go b/agent/app/model/featured_model.go index f305d3938..37e490f89 100644 --- a/agent/app/model/featured_model.go +++ b/agent/app/model/featured_model.go @@ -6,6 +6,7 @@ type FeaturedModel struct { Sort int `json:"sort"` Family string `json:"family"` RepoID string `json:"repoID"` + WeightProvider string `json:"weightProvider"` Sources []string `json:"sources" gorm:"serializer:json"` SourceModelIDs map[string]string `json:"sourceModelIds" gorm:"serializer:json"` Architecture string `json:"architecture"` diff --git a/agent/app/repo/featured_model.go b/agent/app/repo/featured_model.go index daa6a9049..b3a476c6c 100644 --- a/agent/app/repo/featured_model.go +++ b/agent/app/repo/featured_model.go @@ -11,8 +11,9 @@ import ( type FeaturedModelRepo struct{} type IFeaturedModelRepo interface { - Page(page, size int, family, info string) (int64, []model.FeaturedModel, error) + Page(page, size int, family, weightProvider, info string) (int64, []model.FeaturedModel, error) Families() ([]string, error) + WeightProviders() ([]string, error) SyncAll(models []model.FeaturedModel, version string) error } @@ -20,13 +21,16 @@ func NewIFeaturedModelRepo() IFeaturedModelRepo { return &FeaturedModelRepo{} } -func (r *FeaturedModelRepo) Page(page, size int, family, info string) (int64, []model.FeaturedModel, error) { +func (r *FeaturedModelRepo) Page(page, size int, family, weightProvider, info string) (int64, []model.FeaturedModel, error) { var total int64 var items []model.FeaturedModel db := global.DB.Model(&model.FeaturedModel{}) if family != "" { db = db.Where("family = ?", family) } + if weightProvider != "" { + db = db.Where("weight_provider = ?", weightProvider) + } if info != "" { db = db.Where("LOWER(repo_id) LIKE ?", "%"+strings.ToLower(info)+"%") } @@ -45,6 +49,12 @@ func (r *FeaturedModelRepo) Families() ([]string, error) { return families, err } +func (r *FeaturedModelRepo) WeightProviders() ([]string, error) { + providers := make([]string, 0) + err := global.DB.Model(&model.FeaturedModel{}).Where("weight_provider <> ?", "").Distinct("weight_provider").Order("weight_provider asc").Pluck("weight_provider", &providers).Error + return providers, err +} + func (r *FeaturedModelRepo) SyncAll(models []model.FeaturedModel, version string) error { return global.DB.Transaction(func(tx *gorm.DB) error { if err := tx.Where("1 = 1").Delete(&model.FeaturedModel{}).Error; err != nil { diff --git a/agent/app/service/featured_model.go b/agent/app/service/featured_model.go index 25e28c171..4ed8b8f12 100644 --- a/agent/app/service/featured_model.go +++ b/agent/app/service/featured_model.go @@ -19,7 +19,7 @@ import ( var featuredModelsSyncMu sync.Mutex func (m *ModelDownloaderService) PageFeaturedModels(req dto.FeaturedModelSearch) (*dto.FeaturedModelPage, error) { - total, models, err := featuredModelRepo.Page(req.Page, req.PageSize, strings.TrimSpace(req.Family), strings.TrimSpace(req.Info)) + total, models, err := featuredModelRepo.Page(req.Page, req.PageSize, strings.TrimSpace(req.Family), strings.TrimSpace(req.WeightProvider), strings.TrimSpace(req.Info)) if err != nil { return nil, err } @@ -31,8 +31,8 @@ func (m *ModelDownloaderService) PageFeaturedModels(req dto.FeaturedModelSearch) } items = append(items, dto.FeaturedModel{ Key: item.Key, Sort: item.Sort, Family: item.Family, RepoID: item.RepoID, Sources: item.Sources, - SourceModelIDs: item.SourceModelIDs, - Architecture: item.Architecture, BackboneParams: item.BackboneParams, + SourceModelIDs: item.SourceModelIDs, WeightProvider: item.WeightProvider, + Architecture: item.Architecture, BackboneParams: item.BackboneParams, ActiveParams: item.ActiveParams, Engram: item.Engram, WeightGB: item.WeightGB, Description: description, }) @@ -41,7 +41,11 @@ func (m *ModelDownloaderService) PageFeaturedModels(req dto.FeaturedModelSearch) if err != nil { return nil, err } - return &dto.FeaturedModelPage{PageResult: dto.PageResult{Total: total, Items: items}, Families: families}, nil + weightProviders, err := featuredModelRepo.WeightProviders() + if err != nil { + return nil, err + } + return &dto.FeaturedModelPage{PageResult: dto.PageResult{Total: total, Items: items}, Families: families, WeightProviders: weightProviders}, nil } func (m *ModelDownloaderService) SyncFeaturedModels() error { @@ -74,6 +78,12 @@ func (m *ModelDownloaderService) SyncFeaturedModels() error { item.Key = strings.TrimSpace(item.Key) item.Family = strings.TrimSpace(item.Family) item.RepoID = strings.TrimSpace(item.RepoID) + item.WeightProvider = strings.TrimSpace(item.WeightProvider) + if item.WeightProvider == "" { + if provider, _, ok := strings.Cut(item.RepoID, "/"); ok { + item.WeightProvider = provider + } + } if item.Key == "" || item.Family == "" || item.RepoID == "" || (item.Architecture != "MoE" && item.Architecture != "Dense") || item.WeightGB < 0 { return fmt.Errorf("invalid featured model: %s", item.Key) } @@ -95,8 +105,8 @@ func (m *ModelDownloaderService) SyncFeaturedModels() error { } models = append(models, model.FeaturedModel{ Key: item.Key, Sort: item.Sort, Family: item.Family, RepoID: item.RepoID, Sources: item.Sources, - SourceModelIDs: item.SourceModelIDs, - Architecture: item.Architecture, BackboneParams: item.BackboneParams, + SourceModelIDs: item.SourceModelIDs, WeightProvider: item.WeightProvider, + Architecture: item.Architecture, BackboneParams: item.BackboneParams, ActiveParams: item.ActiveParams, Engram: item.Engram, WeightGB: item.WeightGB, Description: string(description), }) diff --git a/agent/app/service/model_downloader.go b/agent/app/service/model_downloader.go index 319fef374..0c602de2f 100644 --- a/agent/app/service/model_downloader.go +++ b/agent/app/service/model_downloader.go @@ -59,6 +59,7 @@ type IModelDownloaderService interface { RemoveTask(req dto.ModelDownloadTaskOperate) error RecoverInterruptedTasks() error ListLocalModels(req dto.LocalModelSearch) (int64, []dto.LocalModelItem, error) + ListLocalModelOptions() ([]dto.LocalModelOption, error) DeleteLocalModel(req dto.LocalModelDelete) error } @@ -393,6 +394,10 @@ func (m *ModelDownloaderService) ListLocalModels(req dto.LocalModelSearch) (int6 return int64(len(items)), pageLocalModels(items, req.Page, req.PageSize), nil } +func (m *ModelDownloaderService) ListLocalModelOptions() ([]dto.LocalModelOption, error) { + return listLocalModelOptions(loadModelDownloaderDir()) +} + func (m *ModelDownloaderService) DeleteLocalModel(req dto.LocalModelDelete) error { if req.Name != strings.TrimSpace(req.Name) { return newModelDownloaderInputError("invalid model directory") diff --git a/agent/app/service/model_downloader_options.go b/agent/app/service/model_downloader_options.go new file mode 100644 index 000000000..d8ad1ebe7 --- /dev/null +++ b/agent/app/service/model_downloader_options.go @@ -0,0 +1,63 @@ +package service + +import ( + "os" + "path/filepath" + "sort" + "strings" + + "github.com/1Panel-dev/1Panel/agent/app/dto" +) + +func listLocalModelOptions(root string) ([]dto.LocalModelOption, error) { + items := make([]dto.LocalModelOption, 0) + entries, err := os.ReadDir(root) + if os.IsNotExist(err) { + return items, nil + } + if err != nil { + return nil, err + } + var scan func(string, string) error + scan = func(path, organization string) error { + children, err := os.ReadDir(path) + if err != nil { + return err + } + for _, child := range children { + if child.IsDir() || child.Type()&os.ModeSymlink != 0 || strings.HasPrefix(child.Name(), ".") { + continue + } + name := child.Name() + if name == "config.json" || name == "params.json" { + items = append(items, dto.LocalModelOption{Name: filepath.Base(path), Organization: organization, Path: path}) + return nil + } + } + if organization == "" { + for _, child := range children { + if child.IsDir() && !strings.HasPrefix(child.Name(), ".") { + if err := scan(filepath.Join(path, child.Name()), filepath.Base(path)); err != nil { + return err + } + } + } + } + return nil + } + for _, entry := range entries { + if entry.IsDir() && !strings.HasPrefix(entry.Name(), ".") { + if err := scan(filepath.Join(root, entry.Name()), ""); err != nil { + return nil, err + } + } + } + sort.Slice(items, func(i, j int) bool { + left, right := strings.ToLower(items[i].Name), strings.ToLower(items[j].Name) + if left == right { + return items[i].Path < items[j].Path + } + return left < right + }) + return items, nil +} diff --git a/agent/init/migration/migrate.go b/agent/init/migration/migrate.go index e98515bc5..eaf47b399 100644 --- a/agent/init/migration/migrate.go +++ b/agent/init/migration/migrate.go @@ -121,6 +121,7 @@ func agentDBMigrations() []*gormigrate.Migration { migrations.AddModelQuickJump, migrations.MigrateModelDownloader, migrations.MigrateVMDatabase, + migrations.AddFeaturedModelWeightProvider, } } diff --git a/agent/init/migration/migrations/model_downloader.go b/agent/init/migration/migrations/model_downloader.go index ff9dbd649..220d07ad1 100644 --- a/agent/init/migration/migrations/model_downloader.go +++ b/agent/init/migration/migrations/model_downloader.go @@ -21,6 +21,21 @@ var MigrateModelDownloader = &gormigrate.Migration{ }, } +var AddFeaturedModelWeightProvider = &gormigrate.Migration{ + ID: "20261103-add-featured-model-weight-provider", + Migrate: func(tx *gorm.DB) error { + if err := tx.AutoMigrate(&model.FeaturedModel{}); err != nil { + return err + } + if err := tx.Model(&model.FeaturedModel{}). + Where("(weight_provider IS NULL OR weight_provider = '') AND instr(repo_id, '/') > 0"). + Update("weight_provider", gorm.Expr("substr(repo_id, 1, instr(repo_id, '/') - 1)")).Error; err != nil { + return err + } + return tx.Model(&model.Setting{}).Where("key = ?", "FeaturedModelsVersion").Update("value", "").Error + }, +} + func migrateModelDownloader(db *gorm.DB, legacyPath string) error { var legacy *gorm.DB if _, err := os.Stat(legacyPath); err == nil { diff --git a/agent/router/ro_model_downloader.go b/agent/router/ro_model_downloader.go index 87cba75d7..0942ad1a3 100644 --- a/agent/router/ro_model_downloader.go +++ b/agent/router/ro_model_downloader.go @@ -27,6 +27,7 @@ func (m *ModelDownloaderRouter) InitRouter(Router *gin.RouterGroup) { router.POST("/tasks/retry", baseApi.RetryModelDownloadTask) router.POST("/tasks/remove", baseApi.RemoveModelDownloadTask) router.POST("/local/search", baseApi.PageLocalDownloadedModels) + router.GET("/local/options", baseApi.ListLocalModelOptions) router.POST("/local/delete", baseApi.DeleteLocalDownloadedModel) } } diff --git a/core/init/migration/helper/menu.go b/core/init/migration/helper/menu.go index 55ce703ec..e558a816a 100644 --- a/core/init/migration/helper/menu.go +++ b/core/init/migration/helper/menu.go @@ -96,9 +96,10 @@ func LoadMenus() string { item := []dto.ShowMenu{ {ID: "1", Disabled: true, Title: "menu.home", IsShow: true, Label: "Home-Menu", Path: "/", Sort: 100}, {ID: "2", Disabled: true, Title: "menu.apps", IsShow: true, Label: "App-Menu", Path: "/apps/all", Sort: 200}, - {ID: "3", Disabled: false, Title: "menu.aiTools", IsShow: true, Label: "AI-Menu", Path: "/ai/model/account", Sort: 300, + {ID: "3", Disabled: false, Title: "menu.aiTools", IsShow: true, Label: "AI-Menu", Path: "/ai/model/files", Sort: 300, Children: []dto.ShowMenu{ - {ID: "41", Disabled: false, Title: "aiTools.model.model", IsShow: true, Label: "AIModel", Path: "/ai/model/account", Sort: 50}, + {ID: "48", Disabled: false, Title: "aiTools.model.ollamaManagement", IsShow: true, Label: "OllamaModels", Path: "/ai/model/local/ollama", Sort: 25}, + {ID: "41", Disabled: false, Title: "aiTools.model.vllmManagement", IsShow: true, Label: "AIModel", Path: "/ai/model/files", Sort: 50}, {ID: "44", Disabled: false, Title: "aiTools.agents.agent", IsShow: true, Label: "Agents", Path: "/ai/agents/agent", Sort: 100}, {ID: "42", Disabled: false, Title: "menu.mcp", IsShow: true, Label: "MCPServer", Path: "/ai/mcp", Sort: 200}, {ID: "43", Disabled: false, Title: "aiTools.gpu.gpu", IsShow: true, Label: "GPU", Path: "/ai/gpu", Sort: 300}, @@ -204,6 +205,7 @@ func MenuSort() []dto.MenuLabelSort { {Label: "Home-Menu", Sort: 100}, {Label: "App-Menu", Sort: 200}, {Label: "AI-Menu", Sort: 300}, + {Label: "OllamaModels", Sort: 25}, {Label: "AIModel", Sort: 50}, {Label: "Agents", Sort: 100}, {Label: "AIProxyManagement", Sort: 150}, diff --git a/core/init/migration/migrate.go b/core/init/migration/migrate.go index 69ef55528..c4122d3d4 100644 --- a/core/init/migration/migrate.go +++ b/core/init/migration/migrate.go @@ -74,5 +74,6 @@ func coreMigrations() []*gormigrate.Migration { migrations.AddPanelMCP, migrations.AddAPIKeyDeletedAt, migrations.MoveVirtualMachineMenuToTopLevel, + migrations.UpdateAiModelManagementMenus, } } diff --git a/core/init/migration/migrations/init.go b/core/init/migration/migrations/init.go index c500ddcd6..49e99d8a8 100644 --- a/core/init/migration/migrations/init.go +++ b/core/init/migration/migrations/init.go @@ -1406,6 +1406,46 @@ var UpdateAiMenuOrderV2 = &gormigrate.Migration{ }, } +var UpdateAiModelManagementMenus = &gormigrate.Migration{ + ID: "20261103-update-ai-model-management-menus", + Migrate: func(tx *gorm.DB) error { + return helper.UpdateHideMenu(tx, func(menus []dto.ShowMenu) []dto.ShowMenu { + for i := range menus { + if menus[i].Label != "AI-Menu" { + continue + } + menus[i].Path = "/ai/model/files" + children := menus[i].Children + showOllama := true + hasOllama := false + insertIndex := 0 + for j := range children { + switch children[j].Label { + case "AIModel": + children[j].Title = "aiTools.model.vllmManagement" + children[j].Path = "/ai/model/files" + showOllama = children[j].IsShow + insertIndex = j + case "OllamaModels": + hasOllama = true + } + } + if !hasOllama { + children = append(children, dto.ShowMenu{}) + copy(children[insertIndex+1:], children[insertIndex:]) + children[insertIndex] = dto.ShowMenu{ + ID: "48", Title: "aiTools.model.ollamaManagement", IsShow: showOllama, + Label: "OllamaModels", Path: "/ai/model/local/ollama", Sort: 25, + } + } + menus[i].Children = children + break + } + return menus + }) + }, +} + var UpdateFirewallMenuPath = &gormigrate.Migration{ ID: "20260819-update-firewall-menu-path", Migrate: func(tx *gorm.DB) error { diff --git a/frontend/src/api/interface/model-downloader.ts b/frontend/src/api/interface/model-downloader.ts index 91941c8f5..cf88e4167 100644 --- a/frontend/src/api/interface/model-downloader.ts +++ b/frontend/src/api/interface/model-downloader.ts @@ -3,17 +3,20 @@ import { ReqPage, ResPage } from '@/api/interface'; export namespace ModelDownloader { export interface FeaturedModelSearch extends ReqPage { family: string; + weightProvider: string; info: string; } export interface FeaturedModelPage extends ResPage { families: string[]; + weightProviders: string[]; } export interface FeaturedModel { description: Record | null; family: string; repoID: string; + weightProvider: string; sources: Source[]; sourceModelIds?: Partial> | null; architecture: 'MoE' | 'Dense'; @@ -110,6 +113,12 @@ export namespace ModelDownloader { canRemoveRecord: boolean; } + export interface LocalModelOption { + name: string; + organization: string; + path: string; + } + export interface LocalModelSearch extends ReqPage { downloadType?: DownloadType | ''; info: string; diff --git a/frontend/src/api/modules/model-downloader.ts b/frontend/src/api/modules/model-downloader.ts index fac5aaf5f..99e2b98d1 100644 --- a/frontend/src/api/modules/model-downloader.ts +++ b/frontend/src/api/modules/model-downloader.ts @@ -59,6 +59,10 @@ export const pageLocalDownloadedModels = (req: ModelDownloader.LocalModelSearch) return http.post>('/ai/model/downloader/local/search', req); }; +export const listLocalModelOptions = () => { + return http.get('/ai/model/downloader/local/options'); +}; + export const deleteLocalDownloadedModel = (req: ModelDownloader.LocalModelDelete) => { return http.post('/ai/model/downloader/local/delete', req); }; diff --git a/frontend/src/lang/modules/en.ts b/frontend/src/lang/modules/en.ts index 9ed13b34e..906369b2d 100644 --- a/frontend/src/lang/modules/en.ts +++ b/frontend/src/lang/modules/en.ts @@ -1064,6 +1064,7 @@ const message = { backboneParams: 'MoE backbone parameters', activeParams: 'Active parameters', engram: 'Engram', + weightProvider: 'Weight provider', weightFootprint: 'Weight size', undisclosed: 'Undisclosed', featuredModels: 'Featured models', @@ -1076,10 +1077,24 @@ const message = { instanceDeployment: 'Deploy by instance', engines: 'Local inference engines', modelManagement: 'Model management', + ollamaManagement: 'Ollama management', + vllmManagement: 'vLLM management', serviceDetails: 'Service details', - deployments: 'Local deployments', - files: 'Model hub', + deployments: 'Model deployment', + files: 'Model preparation', connectExternal: 'Connect external service', + recipes: 'vLLM Recipes', + createRecipe: 'Create Recipe', + recipeHelper: + 'Recipe = model + hardware + launch arguments. Import from {link} or create from a downloaded model.', + recipeFormHelper: 'Paste a command from {link}, or fill in the fields manually.', + recipeArguments: 'Launch arguments', + recipeImportCommand: 'Import command', + recipeImportPlaceholder: 'Paste Docker, pip/uv or vllm serve commands to fill in the Recipe automatically', + recipeVariablesNotSupported: + 'Variable references are not supported in commands. Use explicit values; configure environment variables in the environment field.', + recipeImportError: + 'Unable to convert. Include a Docker or vllm serve launch command with a model; paste pip/uv installation commands together with the launch command.', deploymentTemplates: 'vLLM startup command templates', engineProvider: 'Engine / Provider', endpoint: 'Endpoint', @@ -1106,8 +1121,6 @@ const message = { vllmDeployProfile: 'Deployment model', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: - 'The startup command must use port {0}; otherwise, the service will be inaccessible.', ascendVisibleDevices: 'Ascend visible devices (ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: 'Sync to model service', modelAccountAddressHelper: @@ -1115,6 +1128,8 @@ const message = { containerAddress: 'Container address', customAddress: 'Custom address', downloader: 'Downloads', + modelDirectoryPlaceholder: 'Search models or enter a full path', + selectModelDirectory: 'Select directory', modelDir: 'Model directory', modelSource: 'Model source', repoID: 'Repository ID', diff --git a/frontend/src/lang/modules/es-es.ts b/frontend/src/lang/modules/es-es.ts index 790ead4a3..41b8aecf6 100644 --- a/frontend/src/lang/modules/es-es.ts +++ b/frontend/src/lang/modules/es-es.ts @@ -1066,6 +1066,7 @@ const message = { backboneParams: 'Parámetros base de MoE', activeParams: 'Parámetros activos', engram: 'Engram', + weightProvider: 'Proveedor de pesos', weightFootprint: 'Tamaño de los pesos', undisclosed: 'No divulgado', featuredModels: 'Modelos destacados', @@ -1078,10 +1079,25 @@ const message = { instanceDeployment: 'Despliegue por instancia', engines: 'Motores de inferencia locales', modelManagement: 'Gestión de modelos', + ollamaManagement: 'Gestión de Ollama', + vllmManagement: 'Gestión de vLLM', serviceDetails: 'Detalles del servicio', - deployments: 'Despliegues locales', - files: 'Catálogo de modelos', + deployments: 'Despliegue de modelos', + files: 'Preparación de modelos', connectExternal: 'Conectar servicio externo', + recipes: 'vLLM Recipes', + createRecipe: 'Crear Recipe', + recipeHelper: + 'Recipe = modelo + hardware + argumentos de inicio. Importe desde {link} o cree una a partir de un modelo descargado.', + recipeFormHelper: 'Pegue un comando de {link} o complete los campos manualmente.', + recipeArguments: 'Argumentos de inicio', + recipeImportCommand: 'Importar comando', + recipeImportPlaceholder: + 'Pegue comandos Docker, pip/uv o vllm serve para completar la Recipe automáticamente', + recipeVariablesNotSupported: + 'No se admiten referencias a variables en los comandos. Use valores concretos; configure las variables de entorno en su campo correspondiente.', + recipeImportError: + 'No se puede convertir. Incluya un comando de inicio Docker o vllm serve con un modelo; pegue los comandos de instalación pip/uv junto con el comando de inicio.', deploymentTemplates: 'Plantillas de comandos de inicio de vLLM', engineProvider: 'Motor / Proveedor', endpoint: 'Punto de conexión', @@ -1109,8 +1125,6 @@ const message = { vllmDeployProfile: 'Modelo de despliegue', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: - 'El comando de inicio debe usar el puerto {0}; de lo contrario, no se podrá acceder al servicio.', ascendVisibleDevices: 'Dispositivos Ascend visibles (ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: 'Sincronizar con servicio de modelo', modelAccountAddressHelper: @@ -1118,6 +1132,8 @@ const message = { containerAddress: 'Dirección del contenedor', customAddress: 'Dirección personalizada', downloader: 'Gestión de descargas', + modelDirectoryPlaceholder: 'Buscar modelos o introducir una ruta completa', + selectModelDirectory: 'Seleccionar directorio', modelDir: 'Directorio del modelo', modelSource: 'Fuente del modelo', repoID: 'ID del repositorio', diff --git a/frontend/src/lang/modules/fa.ts b/frontend/src/lang/modules/fa.ts index 031552165..b6dc3a34d 100644 --- a/frontend/src/lang/modules/fa.ts +++ b/frontend/src/lang/modules/fa.ts @@ -1047,6 +1047,7 @@ const message = { backboneParams: 'پارامترهای پایه MoE', activeParams: 'پارامترهای فعال', engram: 'Engram', + weightProvider: 'ارائه‌دهنده وزن‌ها', weightFootprint: 'حجم وزن‌ها', undisclosed: 'اعلام نشده', featuredModels: 'مدل‌های برگزیده', @@ -1059,10 +1060,25 @@ const message = { instanceDeployment: 'استقرار بر اساس نمونه', engines: 'موتورهای استنتاج محلی', modelManagement: 'مدیریت مدل‌ها', + ollamaManagement: 'مدیریت Ollama', + vllmManagement: 'مدیریت vLLM', serviceDetails: 'جزئیات سرویس', - deployments: 'استقرارهای محلی', - files: 'مرکز مدل‌ها', + deployments: 'استقرار مدل', + files: 'آماده‌سازی مدل', connectExternal: 'اتصال به سرویس خارجی', + recipes: 'vLLM Recipes', + createRecipe: 'ایجاد Recipe', + recipeHelper: + 'Recipe = مدل + سخت‌افزار + آرگومان‌های راه‌اندازی. از {link} وارد کنید یا از مدل دانلودشده بسازید.', + recipeFormHelper: 'فرمان را از {link} جای‌گذاری کنید یا فیلدها را دستی پر کنید.', + recipeArguments: 'آرگومان‌های راه‌اندازی', + recipeImportCommand: 'وارد کردن فرمان', + recipeImportPlaceholder: + 'فرمان‌های Docker، pip/uv یا vllm serve را برای تکمیل خودکار Recipe جای‌گذاری کنید', + recipeVariablesNotSupported: + 'ارجاع به متغیرها در دستور پشتیبانی نمی‌شود. مقادیر مشخص وارد کنید؛ متغیرهای محیطی را در بخش مربوط به آن‌ها تنظیم کنید.', + recipeImportError: + 'تبدیل ممکن نیست. فرمان راه‌اندازی Docker یا vllm serve همراه با مدل را وارد کنید؛ فرمان‌های نصب pip/uv را همراه با فرمان راه‌اندازی جای‌گذاری کنید.', deploymentTemplates: 'الگوهای فرمان راه‌اندازی vLLM', engineProvider: 'موتور / ارائه‌دهنده', endpoint: 'نقطه پایانی', @@ -1089,8 +1105,6 @@ const message = { vllmDeployProfile: 'مدل استقرار', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: - 'فرمان راه‌اندازی باید از پورت {0} استفاده کند؛ در غیر این صورت سرویس قابل دسترسی نخواهد بود.', ascendVisibleDevices: 'دستگاه‌های قابل مشاهده Ascend (ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: 'همگام‌سازی با سرویس مدل', modelAccountAddressHelper: @@ -1098,6 +1112,8 @@ const message = { containerAddress: 'آدرس کانتینر', customAddress: 'آدرس سفارشی', downloader: 'مدیریت دانلودها', + modelDirectoryPlaceholder: 'جستجوی مدل یا وارد کردن مسیر کامل', + selectModelDirectory: 'انتخاب پوشه', modelDir: 'دایرکتوری مدل', modelSource: 'منبع مدل', repoID: 'شناسه مخزن', diff --git a/frontend/src/lang/modules/ja.ts b/frontend/src/lang/modules/ja.ts index 41c347494..10a514dd7 100644 --- a/frontend/src/lang/modules/ja.ts +++ b/frontend/src/lang/modules/ja.ts @@ -1051,6 +1051,7 @@ const message = { backboneParams: 'MoE バックボーンパラメータ数', activeParams: 'アクティブパラメータ数', engram: 'Engram', + weightProvider: '重みの提供元', weightFootprint: '重みのサイズ', undisclosed: '非公開', featuredModels: '注目のモデル', @@ -1063,10 +1064,24 @@ const message = { instanceDeployment: 'インスタンス単位でデプロイ', engines: 'ローカル推論エンジン', modelManagement: 'モデル管理', + ollamaManagement: 'Ollama 管理', + vllmManagement: 'vLLM 管理', serviceDetails: 'サービス詳細', - deployments: 'ローカルデプロイ', - files: 'モデル広場', + deployments: 'モデルデプロイ', + files: 'モデル準備', connectExternal: '外部サービスに接続', + recipes: 'vLLM Recipes', + createRecipe: 'Recipe を作成', + recipeHelper: + 'Recipe = モデル + ハードウェア + 起動引数。{link} からインポートするか、ダウンロード済みモデルから作成できます。', + recipeFormHelper: '{link} のコマンドを貼り付けるか、手動で入力してください。', + recipeArguments: '起動引数', + recipeImportCommand: 'コマンドをインポート', + recipeImportPlaceholder: 'Docker、pip/uv、または vllm serve コマンドを貼り付けて Recipe に自動入力', + recipeVariablesNotSupported: + 'コマンド内の変数参照はサポートされていません。具体的な値を入力し、環境変数は環境変数欄で設定してください。', + recipeImportError: + '変換できません。モデルを含む Docker または vllm serve の起動コマンドを入力してください。pip/uv のインストールコマンドは起動コマンドと一緒に貼り付けてください。', deploymentTemplates: 'vLLM 起動コマンドテンプレート', engineProvider: 'エンジン / プロバイダー', endpoint: 'エンドポイント', @@ -1094,8 +1109,6 @@ const message = { vllmDeployProfile: 'デプロイモデル', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: - '起動コマンドではポート {0} を使用する必要があります。使用しない場合、サービスにアクセスできません。', ascendVisibleDevices: 'Ascend 可視デバイス(ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: 'モデルサービスに同期', modelAccountAddressHelper: @@ -1103,6 +1116,8 @@ const message = { containerAddress: 'コンテナアドレス', customAddress: 'カスタムアドレス', downloader: 'ダウンロード管理', + modelDirectoryPlaceholder: 'モデルを検索するかフルパスを入力', + selectModelDirectory: 'ディレクトリを選択', modelDir: 'モデルディレクトリ', modelSource: 'モデルソース', repoID: 'リポジトリ ID', diff --git a/frontend/src/lang/modules/ko.ts b/frontend/src/lang/modules/ko.ts index cd2d2b190..128cf7cd8 100644 --- a/frontend/src/lang/modules/ko.ts +++ b/frontend/src/lang/modules/ko.ts @@ -1041,6 +1041,7 @@ const message = { backboneParams: 'MoE 백본 매개변수 수', activeParams: '활성 매개변수 수', engram: 'Engram', + weightProvider: '가중치 제공자', weightFootprint: '가중치 크기', undisclosed: '비공개', featuredModels: '추천 모델', @@ -1053,10 +1054,24 @@ const message = { instanceDeployment: '인스턴스별 배포', engines: '로컬 추론 엔진', modelManagement: '모델 관리', + ollamaManagement: 'Ollama 관리', + vllmManagement: 'vLLM 관리', serviceDetails: '서비스 상세 정보', - deployments: '로컬 배포', - files: '모델 허브', + deployments: '모델 배포', + files: '모델 준비', connectExternal: '외부 서비스 연결', + recipes: 'vLLM Recipes', + createRecipe: 'Recipe 만들기', + recipeHelper: + 'Recipe = 모델 + 하드웨어 + 시작 인수. {link}에서 가져오거나 다운로드한 모델로 만들 수 있습니다.', + recipeFormHelper: '{link}의 명령을 붙여넣거나 직접 입력하세요.', + recipeArguments: '시작 인수', + recipeImportCommand: '명령 가져오기', + recipeImportPlaceholder: 'Docker, pip/uv 또는 vllm serve 명령을 붙여넣어 Recipe 자동 입력', + recipeVariablesNotSupported: + '명령에서 변수 참조는 지원되지 않습니다. 구체적인 값을 입력하고 환경 변수는 환경 변수 필드에서 설정하세요.', + recipeImportError: + '변환할 수 없습니다. 모델이 포함된 Docker 또는 vllm serve 시작 명령을 입력하세요. pip/uv 설치 명령은 시작 명령과 함께 붙여넣으세요.', deploymentTemplates: 'vLLM 시작 명령 템플릿', engineProvider: '엔진 / 공급자', endpoint: '엔드포인트', @@ -1083,7 +1098,6 @@ const message = { vllmDeployProfile: '배포 모델', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: '시작 명령은 {0} 포트를 사용해야 하며, 그렇지 않으면 서비스에 접근할 수 없습니다.', ascendVisibleDevices: 'Ascend 표시 장치 (ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: '모델 서비스에 동기화', modelAccountAddressHelper: @@ -1091,6 +1105,8 @@ const message = { containerAddress: '컨테이너 주소', customAddress: '사용자 지정 주소', downloader: '다운로드 관리', + modelDirectoryPlaceholder: '모델 검색 또는 전체 경로 입력', + selectModelDirectory: '디렉터리 선택', modelDir: '모델 디렉토리', modelSource: '모델 소스', repoID: '저장소 ID', diff --git a/frontend/src/lang/modules/lo.ts b/frontend/src/lang/modules/lo.ts index 40915108d..5e5d3881e 100644 --- a/frontend/src/lang/modules/lo.ts +++ b/frontend/src/lang/modules/lo.ts @@ -1038,6 +1038,7 @@ const message = { backboneParams: 'ພາຣາມິເຕີຫຼັກຂອງ MoE', activeParams: 'ພາຣາມິເຕີທີ່ໃຊ້ງານ', engram: 'Engram', + weightProvider: 'ຜູ້ໃຫ້ບໍລິການນ້ຳໜັກໂມເດວ', weightFootprint: 'ຂະໜາດນ້ຳໜັກ', undisclosed: 'ບໍ່ເປີດເຜີຍ', featuredModels: 'ໂມເດວແນະນຳ', @@ -1050,10 +1051,24 @@ const message = { instanceDeployment: 'ນຳໃຊ້ຕາມອິນສະແຕນ', engines: 'ເຄື່ອງຈັກອະນຸມານພາຍໃນ', modelManagement: 'ຈັດການໂມເດວ', + ollamaManagement: 'ການຈັດການ Ollama', + vllmManagement: 'ການຈັດການ vLLM', serviceDetails: 'ລາຍລະອຽດບໍລິການ', - deployments: 'ການນຳໃຊ້ພາຍໃນເຄື່ອງ', - files: 'ສູນລວມໂມເດວ', + deployments: 'ການນຳໃຊ້ໂມເດວ', + files: 'ການກະກຽມໂມເດວ', connectExternal: 'ເຊື່ອມຕໍ່ບໍລິການພາຍນອກ', + recipes: 'vLLM Recipes', + createRecipe: 'ສ້າງ Recipe', + recipeHelper: + 'Recipe = ໂມເດວ + ຮາດແວ + ພາລາມິເຕີເລີ່ມຕົ້ນ. ນຳເຂົ້າຈາກ {link} ຫຼືສ້າງຈາກໂມເດວທີ່ດາວໂຫຼດແລ້ວ.', + recipeFormHelper: 'ວາງຄຳສັ່ງຈາກ {link} ຫຼືປ້ອນຂໍ້ມູນເອງ.', + recipeArguments: 'ພາລາມິເຕີເລີ່ມຕົ້ນ', + recipeImportCommand: 'ນຳເຂົ້າຄຳສັ່ງ', + recipeImportPlaceholder: 'ວາງຄຳສັ່ງ Docker, pip/uv ຫຼື vllm serve ເພື່ອຕື່ມ Recipe ອັດຕະໂນມັດ', + recipeVariablesNotSupported: + 'ຄຳສັ່ງບໍ່ຮອງຮັບການອ້າງອີງຕົວແປ. ກະລຸນາປ້ອນຄ່າໂດຍກົງ ແລະຕັ້ງຄ່າຕົວແປສະພາບແວດລ້ອມໃນຊ່ອງທີ່ກ່ຽວຂ້ອງ.', + recipeImportError: + 'ບໍ່ສາມາດແປງໄດ້. ກະລຸນາໃສ່ຄຳສັ່ງເລີ່ມຕົ້ນ Docker ຫຼື vllm serve ທີ່ມີໂມເດວ; ວາງຄຳສັ່ງຕິດຕັ້ງ pip/uv ພ້ອມກັບຄຳສັ່ງເລີ່ມຕົ້ນ.', deploymentTemplates: 'ແມ່ແບບຄຳສັ່ງເລີ່ມຕົ້ນ vLLM', engineProvider: 'ເຄື່ອງຈັກ / ຜູ້ໃຫ້ບໍລິການ', endpoint: 'ຈຸດເຊື່ອມຕໍ່', @@ -1080,7 +1095,6 @@ const message = { vllmDeployProfile: 'ໂມເດວສຳລັບຕິດຕັ້ງ', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: 'ຄຳສັ່ງເລີ່ມຕົ້ນຕ້ອງໃຊ້ພອດ {0}; ບໍ່ດັ່ງນັ້ນຈະບໍ່ສາມາດເຂົ້າເຖິງບໍລິການໄດ້.', ascendVisibleDevices: 'ອຸປະກອນ Ascend ທີ່ເຫັນໄດ້ (ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: 'ຊິ້ງຄ໌ໄປຍັງບໍລິການໂມເດວ', modelAccountAddressHelper: @@ -1088,6 +1102,8 @@ const message = { containerAddress: 'ທີ່ຢູ່ຄອນເທນເນີ', customAddress: 'ທີ່ຢູ່ກຳນົດເອງ', downloader: 'ຈັດການການດາວໂຫຼດ', + modelDirectoryPlaceholder: 'ຄົ້ນຫາໂມເດວ ຫຼື ປ້ອນເສັ້ນທາງເຕັມ', + selectModelDirectory: 'ເລືອກໄດເຣັກທໍຣີ', modelDir: 'ໄດເຣັກທໍຣີໂມເດວ', modelSource: 'ແຫຼ່ງທີ່ມາໂມເດວ', repoID: 'ID ຄັງເກັບ', diff --git a/frontend/src/lang/modules/ms.ts b/frontend/src/lang/modules/ms.ts index 1bd6de626..350411169 100644 --- a/frontend/src/lang/modules/ms.ts +++ b/frontend/src/lang/modules/ms.ts @@ -1074,6 +1074,7 @@ const message = { backboneParams: 'Parameter teras MoE', activeParams: 'Parameter aktif', engram: 'Engram', + weightProvider: 'Penyedia pemberat', weightFootprint: 'Saiz pemberat', undisclosed: 'Tidak didedahkan', featuredModels: 'Model pilihan', @@ -1086,10 +1087,25 @@ const message = { instanceDeployment: 'Pengerahan mengikut instans', engines: 'Enjin inferens setempat', modelManagement: 'Pengurusan model', + ollamaManagement: 'Pengurusan Ollama', + vllmManagement: 'Pengurusan vLLM', serviceDetails: 'Butiran perkhidmatan', - deployments: 'Pengerahan setempat', - files: 'Hab model', + deployments: 'Pengerahan model', + files: 'Penyediaan model', connectExternal: 'Sambungkan perkhidmatan luaran', + recipes: 'vLLM Recipes', + createRecipe: 'Cipta Recipe', + recipeHelper: + 'Recipe = model + perkakasan + argumen pelancaran. Import daripada {link} atau cipta daripada model yang dimuat turun.', + recipeFormHelper: 'Tampal arahan daripada {link} atau isi medan secara manual.', + recipeArguments: 'Argumen pelancaran', + recipeImportCommand: 'Import arahan', + recipeImportPlaceholder: + 'Tampal arahan Docker, pip/uv atau vllm serve untuk mengisi Recipe secara automatik', + recipeVariablesNotSupported: + 'Rujukan pemboleh ubah tidak disokong dalam arahan. Masukkan nilai khusus; tetapkan pemboleh ubah persekitaran dalam medan yang berkenaan.', + recipeImportError: + 'Tidak dapat menukar. Sertakan arahan pelancaran Docker atau vllm serve dengan model; tampal arahan pemasangan pip/uv bersama arahan pelancaran.', deploymentTemplates: 'Templat arahan permulaan vLLM', engineProvider: 'Enjin / Pembekal', endpoint: 'Titik akhir', @@ -1116,8 +1132,6 @@ const message = { vllmDeployProfile: 'Model penggunaan', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: - 'Perintah permulaan mesti menggunakan port {0}; jika tidak, perkhidmatan tidak dapat diakses.', ascendVisibleDevices: 'Peranti Ascend boleh dilihat (ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: 'Segerakkan ke perkhidmatan model', modelAccountAddressHelper: @@ -1125,6 +1139,8 @@ const message = { containerAddress: 'Alamat kontena', customAddress: 'Alamat tersuai', downloader: 'Pengurusan muat turun', + modelDirectoryPlaceholder: 'Cari model atau masukkan laluan penuh', + selectModelDirectory: 'Pilih direktori', modelDir: 'Direktori Model', modelSource: 'Sumber model', repoID: 'ID Repositori', diff --git a/frontend/src/lang/modules/pt-br.ts b/frontend/src/lang/modules/pt-br.ts index 38da9dd51..9a17e53b7 100644 --- a/frontend/src/lang/modules/pt-br.ts +++ b/frontend/src/lang/modules/pt-br.ts @@ -1070,6 +1070,7 @@ const message = { backboneParams: 'Parâmetros base do MoE', activeParams: 'Parâmetros ativos', engram: 'Engram', + weightProvider: 'Provedor de pesos', weightFootprint: 'Tamanho dos pesos', undisclosed: 'Não divulgado', featuredModels: 'Modelos em destaque', @@ -1082,10 +1083,25 @@ const message = { instanceDeployment: 'Implantação por instância', engines: 'Mecanismos de inferência locais', modelManagement: 'Gerenciamento de modelos', + ollamaManagement: 'Gerenciamento do Ollama', + vllmManagement: 'Gerenciamento do vLLM', serviceDetails: 'Detalhes do serviço', - deployments: 'Implantações locais', - files: 'Central de modelos', + deployments: 'Implantação de modelos', + files: 'Preparação de modelos', connectExternal: 'Conectar serviço externo', + recipes: 'vLLM Recipes', + createRecipe: 'Criar Recipe', + recipeHelper: + 'Recipe = modelo + hardware + argumentos de inicialização. Importe de {link} ou crie a partir de um modelo baixado.', + recipeFormHelper: 'Cole um comando de {link} ou preencha os campos manualmente.', + recipeArguments: 'Argumentos de inicialização', + recipeImportCommand: 'Importar comando', + recipeImportPlaceholder: + 'Cole comandos Docker, pip/uv ou vllm serve para preencher a Recipe automaticamente', + recipeVariablesNotSupported: + 'Referências a variáveis não são aceitas nos comandos. Use valores explícitos; configure as variáveis de ambiente no campo correspondente.', + recipeImportError: + 'Não foi possível converter. Inclua um comando de inicialização Docker ou vllm serve com um modelo; cole os comandos de instalação pip/uv junto com o comando de inicialização.', deploymentTemplates: 'Modelos de comandos de inicialização do vLLM', engineProvider: 'Mecanismo / Provedor', endpoint: 'Endpoint', @@ -1112,8 +1128,6 @@ const message = { vllmDeployProfile: 'Modelo de implantação', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: - 'O comando de inicialização deve usar a porta {0}; caso contrário, o serviço ficará inacessível.', ascendVisibleDevices: 'Dispositivos Ascend visíveis (ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: 'Sincronizar com serviço de modelo', modelAccountAddressHelper: @@ -1121,6 +1135,8 @@ const message = { containerAddress: 'Endereço do contêiner', customAddress: 'Endereço personalizado', downloader: 'Gerenciamento de downloads', + modelDirectoryPlaceholder: 'Buscar modelos ou inserir um caminho completo', + selectModelDirectory: 'Selecionar diretório', modelDir: 'Diretório do modelo', modelSource: 'Fonte do modelo', repoID: 'ID do repositório', diff --git a/frontend/src/lang/modules/ru.ts b/frontend/src/lang/modules/ru.ts index a204355f9..c6c358aa9 100644 --- a/frontend/src/lang/modules/ru.ts +++ b/frontend/src/lang/modules/ru.ts @@ -1063,6 +1063,7 @@ const message = { backboneParams: 'Параметры основы MoE', activeParams: 'Активные параметры', engram: 'Engram', + weightProvider: 'Поставщик весов', weightFootprint: 'Размер весов', undisclosed: 'Не раскрыто', featuredModels: 'Рекомендуемые модели', @@ -1075,10 +1076,25 @@ const message = { instanceDeployment: 'Развертывание по экземплярам', engines: 'Локальные движки инференса', modelManagement: 'Управление моделями', + ollamaManagement: 'Управление Ollama', + vllmManagement: 'Управление vLLM', serviceDetails: 'Сведения о сервисе', - deployments: 'Локальные развертывания', - files: 'Каталог моделей', + deployments: 'Развертывание моделей', + files: 'Подготовка моделей', connectExternal: 'Подключить внешний сервис', + recipes: 'vLLM Recipes', + createRecipe: 'Создать Recipe', + recipeHelper: + 'Recipe = модель + оборудование + параметры запуска. Импортируйте с {link} или создайте из загруженной модели.', + recipeFormHelper: 'Вставьте команду с {link} или заполните поля вручную.', + recipeArguments: 'Параметры запуска', + recipeImportCommand: 'Импорт команды', + recipeImportPlaceholder: + 'Вставьте команды Docker, pip/uv или vllm serve для автоматического заполнения Recipe', + recipeVariablesNotSupported: + 'Ссылки на переменные в командах не поддерживаются. Укажите конкретные значения; переменные окружения настройте в соответствующем поле.', + recipeImportError: + 'Не удалось преобразовать. Добавьте команду запуска Docker или vllm serve с моделью; вставляйте команды установки pip/uv вместе с командой запуска.', deploymentTemplates: 'Шаблоны команд запуска vLLM', engineProvider: 'Движок / Поставщик', endpoint: 'Конечная точка', @@ -1106,7 +1122,6 @@ const message = { vllmDeployProfile: 'Модель развертывания', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: 'Команда запуска должна использовать порт {0}, иначе сервис будет недоступен.', ascendVisibleDevices: 'Видимые устройства Ascend (ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: 'Синхронизировать с сервисом модели', modelAccountAddressHelper: @@ -1114,6 +1129,8 @@ const message = { containerAddress: 'Адрес контейнера', customAddress: 'Пользовательский адрес', downloader: 'Управление загрузками', + modelDirectoryPlaceholder: 'Найти модель или ввести полный путь', + selectModelDirectory: 'Выбрать каталог', modelDir: 'Каталог модели', modelSource: 'Источник модели', repoID: 'ID репозитория', diff --git a/frontend/src/lang/modules/tr.ts b/frontend/src/lang/modules/tr.ts index 9c261cb86..335b43232 100644 --- a/frontend/src/lang/modules/tr.ts +++ b/frontend/src/lang/modules/tr.ts @@ -1072,6 +1072,7 @@ const message = { backboneParams: 'MoE omurga parametreleri', activeParams: 'Etkin parametreler', engram: 'Engram', + weightProvider: 'Ağırlık sağlayıcısı', weightFootprint: 'Ağırlık boyutu', undisclosed: 'Açıklanmadı', featuredModels: 'Öne çıkan modeller', @@ -1084,10 +1085,25 @@ const message = { instanceDeployment: 'Örnek bazında dağıtım', engines: 'Yerel çıkarım motorları', modelManagement: 'Model yönetimi', + ollamaManagement: 'Ollama yönetimi', + vllmManagement: 'vLLM yönetimi', serviceDetails: 'Hizmet ayrıntıları', - deployments: 'Yerel dağıtımlar', - files: 'Model merkezi', + deployments: 'Model dağıtımı', + files: 'Model hazırlığı', connectExternal: 'Harici hizmete bağlan', + recipes: 'vLLM Recipes', + createRecipe: 'Recipe oluştur', + recipeHelper: + 'Recipe = model + donanım + başlatma parametreleri. {link} üzerinden içe aktarın veya indirilen bir modelden oluşturun.', + recipeFormHelper: '{link} üzerinden bir komut yapıştırın veya alanları elle doldurun.', + recipeArguments: 'Başlatma parametreleri', + recipeImportCommand: 'Komut içe aktar', + recipeImportPlaceholder: + 'Recipe alanlarını otomatik doldurmak için Docker, pip/uv veya vllm serve komutlarını yapıştırın', + recipeVariablesNotSupported: + 'Komutlarda değişken başvuruları desteklenmez. Açık değerler girin; ortam değişkenlerini ilgili alanda yapılandırın.', + recipeImportError: + 'Dönüştürülemedi. Model içeren bir Docker veya vllm serve başlatma komutu ekleyin; pip/uv kurulum komutlarını başlatma komutuyla birlikte yapıştırın.', deploymentTemplates: 'vLLM başlatma komutu şablonları', engineProvider: 'Motor / Sağlayıcı', endpoint: 'Uç nokta', @@ -1114,8 +1130,6 @@ const message = { vllmDeployProfile: 'Dağıtım modeli', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: - 'Başlatma komutu {0} numaralı bağlantı noktasını kullanmalıdır; aksi halde hizmete erişilemez.', ascendVisibleDevices: 'Görünür Ascend cihazları (ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: 'Model hizmetine senkronize et', modelAccountAddressHelper: @@ -1123,6 +1137,8 @@ const message = { containerAddress: 'Konteyner adresi', customAddress: 'Özel adres', downloader: 'İndirme yönetimi', + modelDirectoryPlaceholder: 'Model arayın veya tam yol girin', + selectModelDirectory: 'Dizin seç', modelDir: 'Model dizini', modelSource: 'Model kaynağı', repoID: 'Depo ID', diff --git a/frontend/src/lang/modules/zh-Hant.ts b/frontend/src/lang/modules/zh-Hant.ts index 1da913a9b..702e5dd21 100644 --- a/frontend/src/lang/modules/zh-Hant.ts +++ b/frontend/src/lang/modules/zh-Hant.ts @@ -1002,6 +1002,7 @@ const message = { backboneParams: 'MoE 骨幹參數', activeParams: '啟用參數', engram: 'Engram', + weightProvider: '權重提供商', weightFootprint: '權重體積', undisclosed: '未公開', featuredModels: '精選模型', @@ -1014,10 +1015,22 @@ const message = { instanceDeployment: '按執行個體部署', engines: '本機推理引擎', modelManagement: '模型管理', + ollamaManagement: 'Ollama 管理', + vllmManagement: 'vLLM 管理', serviceDetails: '服務詳情', - deployments: '本機部署', - files: '模型廣場', + deployments: '模型部署', + files: '模型準備', connectExternal: '接入外部服務', + recipes: 'vLLM Recipes', + createRecipe: '建立 Recipe', + recipeHelper: 'Recipe = 模型 + 硬體 + 啟動參數。支援從 {link} 匯入或從已下載模型建立。', + recipeFormHelper: '從 {link} 複製命令匯入,或手動填寫。', + recipeArguments: '啟動參數', + recipeImportCommand: '匯入命令', + recipeImportPlaceholder: '貼上 Docker、pip/uv 或 vllm serve 命令,自動填入 Recipe', + recipeVariablesNotSupported: '命令中不支援變數引用,請填寫具體值;環境變數請在環境變數欄設定。', + recipeImportError: + '無法轉換,請提供包含模型的 Docker 或 vllm serve 啟動命令;pip/uv 安裝命令需要與啟動命令一起貼上。', deploymentTemplates: 'vLLM 啟動命令範本', engineProvider: '引擎 / 供應商', endpoint: '端點', @@ -1044,7 +1057,6 @@ const message = { vllmDeployProfile: '部署模型', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: '啟動命令必須使用 {0} 連接埠,否則服務將無法存取。', ascendVisibleDevices: 'Ascend 可見裝置(ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: '同步到模型服務', modelAccountAddressHelper: @@ -1052,6 +1064,8 @@ const message = { containerAddress: '容器地址', customAddress: '自訂地址', downloader: '下載管理', + modelDirectoryPlaceholder: '搜尋模型或輸入完整路徑', + selectModelDirectory: '選擇目錄', modelDir: '模型目錄', modelSource: '模型來源', repoID: '倉庫 ID', diff --git a/frontend/src/lang/modules/zh.ts b/frontend/src/lang/modules/zh.ts index cfc4729d9..0fec8a409 100644 --- a/frontend/src/lang/modules/zh.ts +++ b/frontend/src/lang/modules/zh.ts @@ -1015,6 +1015,7 @@ const message = { backboneParams: 'MoE 骨干参数', activeParams: '激活参数', engram: 'Engram', + weightProvider: '权重提供商', weightFootprint: '权重体积', undisclosed: '未公开', featuredModels: '精选模型', @@ -1027,10 +1028,22 @@ const message = { instanceDeployment: '按实例部署', engines: '本地推理引擎', modelManagement: '模型管理', + ollamaManagement: 'Ollama 管理', + vllmManagement: 'vLLM 管理', serviceDetails: '服务详情', - deployments: '本地部署', - files: '模型广场', + deployments: '模型部署', + files: '模型准备', connectExternal: '接入外部服务', + recipes: 'vLLM Recipes', + createRecipe: '创建 Recipe', + recipeHelper: 'Recipe = 模型 + 硬件 + 启动参数。支持从 {link} 导入或从已下载模型创建。', + recipeFormHelper: '从 {link} 复制命令导入,或手动填写。', + recipeArguments: '启动参数', + recipeImportCommand: '导入命令', + recipeImportPlaceholder: '粘贴 Docker、pip/uv 或 vllm serve 命令,自动填充 Recipe', + recipeVariablesNotSupported: '命令中不支持变量引用,请填写具体值;环境变量请在环境变量栏配置。', + recipeImportError: + '无法转换,请提供包含模型的 Docker 或 vllm serve 启动命令;pip/uv 安装命令需要与启动命令一起粘贴。', deploymentTemplates: 'vLLM 启动命令模板', engineProvider: '引擎 / 供应商', endpoint: '端点', @@ -1057,7 +1070,6 @@ const message = { vllmDeployProfile: '部署模型', vllmProfileFlash0731: 'DeepSeek V4 Flash 0731', vllmProfileVisionExp: 'DeepSeek V4 Flash Vision Exp', - vllmCommandPortHelper: '启动命令必须使用 {0} 端口,否则服务将无法访问。', ascendVisibleDevices: 'Ascend 可见设备(ASCEND_RT_VISIBLE_DEVICES)', syncModelAccount: '同步到模型服务', modelAccountAddressHelper: @@ -1065,6 +1077,8 @@ const message = { containerAddress: '容器地址', customAddress: '自定义地址', downloader: '下载管理', + modelDirectoryPlaceholder: '搜索模型或输入完整路径', + selectModelDirectory: '选择目录', modelDir: '模型目录', modelSource: '模型来源', repoID: '仓库 ID', diff --git a/frontend/src/routers/modules/ai.ts b/frontend/src/routers/modules/ai.ts index 94fa4d807..6f1e8c858 100644 --- a/frontend/src/routers/modules/ai.ts +++ b/frontend/src/routers/modules/ai.ts @@ -12,13 +12,23 @@ const aiRouter = { title: 'menu.aiTools', }, children: [ + { + path: '/ai/model/local/ollama', + name: 'OllamaModels', + component: () => import('@/views/ai/model/ollama/index.vue'), + meta: { + icon: 'p-moxing-menu', + title: 'aiTools.model.ollamaManagement', + permission: 'ai_model_view', + }, + }, { path: '/ai/model', name: 'AIModel', redirect: '/ai/model/files', meta: { icon: 'p-moxing-menu', - title: 'aiTools.model.model', + title: 'aiTools.model.vllmManagement', activeMenu: '/ai/model', permission: 'ai_model_view', }, @@ -56,18 +66,6 @@ const aiRouter = { permission: 'ai_model_view', }, }, - { - path: '/ai/model/local/ollama', - hidden: true, - name: 'OllamaModels', - component: () => import('@/views/ai/model/ollama/index.vue'), - meta: { - title: 'aiTools.model.engines', - detail: 'aiTools.model.modelManagement', - activeMenu: '/ai/model', - permission: 'ai_model_view', - }, - }, { path: '/ai/agents/agent', name: 'Agents', diff --git a/frontend/src/utils/app.ts b/frontend/src/utils/app.ts index 56733b4b3..90dfeb5c5 100644 --- a/frontend/src/utils/app.ts +++ b/frontend/src/utils/app.ts @@ -38,9 +38,6 @@ export const jumpToInstall = (type: string, key: string) => { }, }); return true; - case 'ollama': - router.push({ path: '/ai/model/local', query: { engine: 'ollama', uncached: 'true', open: 'create' } }); - return true; case 'vllm': if (globalStore.isProductPro) { router.push({ diff --git a/frontend/src/views/ai/model/components/create/index.vue b/frontend/src/views/ai/model/components/create/index.vue index ac3f881c9..8eb021b58 100644 --- a/frontend/src/views/ai/model/components/create/index.vue +++ b/frontend/src/views/ai/model/components/create/index.vue @@ -1,43 +1,9 @@ - diff --git a/frontend/src/views/ai/model/components/deployment-manage/index.vue b/frontend/src/views/ai/model/components/deployment-manage/index.vue index 105ab5c70..fb5456c62 100644 --- a/frontend/src/views/ai/model/components/deployment-manage/index.vue +++ b/frontend/src/views/ai/model/components/deployment-manage/index.vue @@ -11,14 +11,9 @@