package main import ( "context" "errors" "flag" "fmt" "io" "ipa/IPAGo/models" "ipa/IPAGo/wrapper" "net/http" "os" "path/filepath" "time" "github.com/danielgtaylor/huma/v2" "github.com/danielgtaylor/huma/v2/adapters/humago" ) const ( version = "1.0.1" ) func main() { port := flag.Int("port", 8888, "Port to listen on") flag.Parse() mux := http.NewServeMux() config := huma.DefaultConfig("IPAGo", version) config.CreateHooks = nil api := humago.New(mux, config) huma.Get( api, "/auth/login", func(ctx context.Context, input *models.AuthInput) (*models.AuthOutput, error) { output := &models.AuthOutput{} output.Body.Success = wrapper.Auth(input.User, input.Pswd, input.Code) return output, nil }) huma.Get( api, "/auth/info", func(ctx context.Context, input *models.AuthInfoInput) (*models.AuthInfoOutput, error) { output := &models.AuthInfoOutput{} output.Body.Success = wrapper.AuthInfo(input.User, input.Pswd) return output, nil }) huma.Get( api, "/search", func(ctx context.Context, input *models.SearchInput) (*models.SearchOutput, error) { output := &models.SearchOutput{} output.Body.Apps = []wrapper.App{} output.Body.Success = false if input.Limit == 0 { input.Limit = 1 } if input.Query == "" { return output, nil } apps, err := wrapper.Search(input.Query, input.Limit) if err != nil { return output, nil } output.Body.Success = true output.Body.Apps = apps return output, nil }) huma.Get( api, "/download", func(ctx context.Context, input *models.DownloadInput) (*models.DownloadOutput, error) { outputPath := filepath.Join(os.TempDir(), fmt.Sprintf("%s.ipa", time.Now().Format("20060102150405"))) output := &models.DownloadOutput{} if input.BundleID == "" { return nil, errors.New("bundleID is empty") } success := wrapper.Download(input.BundleID, outputPath) if !success { return nil, errors.New("failed to download") } output.ContentDisposition = fmt.Sprintf("attachment; filename=%s", filepath.Base(outputPath)) output.ContentType = "application/octet-stream" output.Body = func(hctx huma.Context) { file, err := os.Open(outputPath) if err != nil { return } defer func() { file.Close() os.Remove(outputPath) fmt.Println("File removed after download") }() _, _ = io.Copy(hctx.BodyWriter(), file) } return output, nil }) addr := fmt.Sprintf(":%d", *port) fmt.Printf("Server is running on %s\n", addr) http.ListenAndServe(addr, mux) }