package cache import ( "github.com/TeaOSLab/EdgeCommon/pkg/configutils" "github.com/TeaOSLab/EdgeCommon/pkg/langs/codes" "github.com/TeaOSLab/EdgeCommon/pkg/rpc/pb" "github.com/TeaOSLab/EdgeCommon/pkg/userconfigs" "github.com/TeaOSLab/EdgeUser/internal/configloaders" "github.com/TeaOSLab/EdgeUser/internal/web/actions/actionutils" "github.com/TeaOSLab/EdgeUser/internal/web/actions/default/servers/cache/cacheutils" "github.com/iwind/TeaGo/actions" "github.com/iwind/TeaGo/lists" "github.com/iwind/TeaGo/maps" "github.com/iwind/TeaGo/types" timeutil "github.com/iwind/TeaGo/utils/time" "net" "net/url" "strings" ) type IndexAction struct { actionutils.ParentAction } func (this *IndexAction) Init() { this.Nav("", "", "purge") } func (this *IndexAction) RunGet(params struct{}) { // 初始化菜单数据 err := InitMenu(this.Parent()) if err != nil { this.ErrorPage(err) return } // 后台配置 var maxKeysPerTask = userconfigs.MaxCacheKeysPerTask var maxKeysPerDay = userconfigs.MaxCacheKeysPerDay serverConfig, err := configloaders.LoadServerConfig() if err != nil { this.ErrorPage(err) return } if serverConfig != nil && serverConfig.HTTPCacheTaskPurgeConfig != nil { if serverConfig.HTTPCacheTaskPurgeConfig.MaxKeysPerTask > 0 { maxKeysPerTask = serverConfig.HTTPCacheTaskPurgeConfig.MaxKeysPerTask } if serverConfig.HTTPCacheTaskPurgeConfig.MaxKeysPerDay > 0 { maxKeysPerDay = serverConfig.HTTPCacheTaskPurgeConfig.MaxKeysPerDay } } this.Data["maxKeysPerTask"] = maxKeysPerTask this.Data["maxKeysPerDay"] = maxKeysPerDay // 剩余配额 this.Data["quotaKeysToday"] = 0 if maxKeysPerDay > 0 { countKeysResp, err := this.RPC().HTTPCacheTaskKeyRPC().CountHTTPCacheTaskKeysWithDay(this.UserContext(), &pb.CountHTTPCacheTaskKeysWithDayRequest{ KeyType: "purge", Day: timeutil.Format("Ymd"), }) if err != nil { this.ErrorPage(err) return } var quota = maxKeysPerDay - types.Int32(countKeysResp.Count) if quota < 0 { quota = 0 } this.Data["quotaKeysToday"] = quota } this.Show() } func (this *IndexAction) RunPost(params struct { KeyType string UrlList string Must *actions.Must CSRF *actionutils.CSRF }) { defer this.CreateLogInfo(codes.HTTPCacheTask_LogCreateHTTPCacheTaskPurge) switch params.KeyType { case "key", "prefix": default: this.Fail("请选择正确的刷新类型") } // 查找当前用户的所有域名 serverNamesResp, err := this.RPC().ServerRPC().FindAllEnabledServerNamesWithUserId(this.UserContext(), &pb.FindAllEnabledServerNamesWithUserIdRequest{UserId: this.UserId()}) if err != nil { this.ErrorPage(err) return } var serverNames = serverNamesResp.ServerNames var keys = []string{} for _, key := range strings.Split(params.UrlList, "\n") { key = strings.TrimSpace(key) if len(key) == 0 { continue } if lists.ContainsString(keys, key) { continue } // 检查域名 u, err := url.Parse(key) if err != nil || len(u.Host) == 0 || (u.Scheme != "http" && u.Scheme != "https") { this.Fail("'" + key + "'不是正确的URL格式") } var host = u.Host // 去掉端口 hostString, _, err := net.SplitHostPort(host) if err == nil { host = hostString } if !configutils.MatchDomains(serverNames, host) { this.Fail("'" + key + "'中域名'" + u.Host + "'没有绑定") } if params.KeyType == "prefix" && !strings.HasSuffix(key, "/") { key += "/" } keys = append(keys, key) } if len(keys) == 0 { if params.KeyType == "key" { this.Fail("请输入要刷新的URL列表") } else if params.KeyType == "prefix" { this.Fail("请输入要刷新的目录列表") } } // 校验Key validateResp, err := this.RPC().HTTPCacheTaskKeyRPC().ValidateHTTPCacheTaskKeys(this.UserContext(), &pb.ValidateHTTPCacheTaskKeysRequest{Keys: keys}) if err != nil { this.ErrorPage(err) return } var failKeyMaps = []maps.Map{} if len(validateResp.FailKeys) > 0 { for _, key := range validateResp.FailKeys { failKeyMaps = append(failKeyMaps, maps.Map{ "key": key.Key, "reason": cacheutils.KeyFailReason(key.ReasonCode), }) } } this.Data["failKeys"] = failKeyMaps if len(failKeyMaps) > 0 { this.Fail("有" + types.String(len(failKeyMaps)) + "个Key无法完成操作,请删除后重试") } // 提交任务 _, err = this.RPC().HTTPCacheTaskRPC().CreateHTTPCacheTask(this.UserContext(), &pb.CreateHTTPCacheTaskRequest{ Type: "purge", KeyType: params.KeyType, Keys: keys, }) if err != nil { this.ErrorPage(err) return } this.Success() }