cli/internal/cmd/sdk/generators/python.go

83 lines
2.1 KiB
Go
Raw Normal View History

package generators
import (
"context"
"fmt"
"os"
"os/exec"
"path/filepath"
feat: Batch implementation of Gemini issues (#176) * feat(help): Add CLI help command Fixes #136 * chore: remove binary * feat(mcp): Add TCP transport Fixes #126 * feat(io): Migrate pkg/mcp to use Medium abstraction Fixes #103 * chore(io): Migrate internal/cmd/docs/* to Medium abstraction Fixes #113 * chore(io): Migrate internal/cmd/dev/* to Medium abstraction Fixes #114 * chore(io): Migrate internal/cmd/setup/* to Medium abstraction * chore(io): Complete migration of internal/cmd/dev/* to Medium abstraction * chore(io): Migrate internal/cmd/sdk, pkgcmd, and workspace to Medium abstraction * style: fix formatting in internal/variants Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> * refactor(io): simplify local Medium implementation Rewrote to match the simpler TypeScript pattern: - path() sanitizes and returns string directly - Each method calls path() once - No complex symlink validation - Less code, less attack surface Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> * test(mcp): update sandboxing tests for simplified Medium The simplified io/local.Medium implementation: - Sanitizes .. to . (no error, path is cleaned) - Allows absolute paths through (caller validates if needed) - Follows symlinks (no traversal blocking) Update tests to match this simplified behavior. Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> * fix(updater): resolve PkgVersion duplicate declaration Remove var PkgVersion from updater.go since go generate creates const PkgVersion in version.go. Track version.go in git to ensure builds work without running go generate first. Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.5 <noreply@anthropic.com>
2026-02-02 04:20:18 +00:00
coreio "forge.lthn.ai/core/cli/pkg/io"
)
// PythonGenerator generates Python SDKs from OpenAPI specs.
type PythonGenerator struct{}
// NewPythonGenerator creates a new Python generator.
func NewPythonGenerator() *PythonGenerator {
return &PythonGenerator{}
}
// Language returns the generator's target language identifier.
func (g *PythonGenerator) Language() string {
return "python"
}
// Available checks if generator dependencies are installed.
func (g *PythonGenerator) Available() bool {
_, err := exec.LookPath("openapi-python-client")
return err == nil
}
// Install returns instructions for installing the generator.
func (g *PythonGenerator) Install() string {
return "pip install openapi-python-client"
}
// Generate creates SDK from OpenAPI spec.
func (g *PythonGenerator) Generate(ctx context.Context, opts Options) error {
feat: Batch implementation of Gemini issues (#176) * feat(help): Add CLI help command Fixes #136 * chore: remove binary * feat(mcp): Add TCP transport Fixes #126 * feat(io): Migrate pkg/mcp to use Medium abstraction Fixes #103 * chore(io): Migrate internal/cmd/docs/* to Medium abstraction Fixes #113 * chore(io): Migrate internal/cmd/dev/* to Medium abstraction Fixes #114 * chore(io): Migrate internal/cmd/setup/* to Medium abstraction * chore(io): Complete migration of internal/cmd/dev/* to Medium abstraction * chore(io): Migrate internal/cmd/sdk, pkgcmd, and workspace to Medium abstraction * style: fix formatting in internal/variants Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> * refactor(io): simplify local Medium implementation Rewrote to match the simpler TypeScript pattern: - path() sanitizes and returns string directly - Each method calls path() once - No complex symlink validation - Less code, less attack surface Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> * test(mcp): update sandboxing tests for simplified Medium The simplified io/local.Medium implementation: - Sanitizes .. to . (no error, path is cleaned) - Allows absolute paths through (caller validates if needed) - Follows symlinks (no traversal blocking) Update tests to match this simplified behavior. Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> * fix(updater): resolve PkgVersion duplicate declaration Remove var PkgVersion from updater.go since go generate creates const PkgVersion in version.go. Track version.go in git to ensure builds work without running go generate first. Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.5 <noreply@anthropic.com>
2026-02-02 04:20:18 +00:00
if err := coreio.Local.EnsureDir(opts.OutputDir); err != nil {
return fmt.Errorf("python.Generate: failed to create output dir: %w", err)
}
if g.Available() {
return g.generateNative(ctx, opts)
}
return g.generateDocker(ctx, opts)
}
func (g *PythonGenerator) generateNative(ctx context.Context, opts Options) error {
parentDir := filepath.Dir(opts.OutputDir)
cmd := exec.CommandContext(ctx, "openapi-python-client", "generate",
"--path", opts.SpecPath,
"--output-path", opts.OutputDir,
)
cmd.Dir = parentDir
cmd.Stdout = os.Stdout
cmd.Stderr = os.Stderr
return cmd.Run()
}
func (g *PythonGenerator) generateDocker(ctx context.Context, opts Options) error {
specDir := filepath.Dir(opts.SpecPath)
specName := filepath.Base(opts.SpecPath)
args := []string{"run", "--rm"}
args = append(args, dockerUserArgs()...)
args = append(args,
"-v", specDir+":/spec",
"-v", opts.OutputDir+":/out",
"openapitools/openapi-generator-cli", "generate",
"-i", "/spec/"+specName,
"-g", "python",
"-o", "/out",
"--additional-properties=packageName="+opts.PackageName,
)
cmd := exec.CommandContext(ctx, "docker", args...)
cmd.Stdout = os.Stdout
cmd.Stderr = os.Stderr
return cmd.Run()
}