mirror of https://github.com/go-python/gopy.git
gopy: proper handling of lang option
This CL introduces a split in handling of {py|py2|py3}{thon,}. It also lifts up the bind.Package creation so the processing is done only once. Change-Id: I946605fb24885df986baa77088f76df90ff4d168
This commit is contained in:
parent
2f34f14535
commit
63c5bca8e1
35
cmd_bind.go
35
cmd_bind.go
|
@ -6,7 +6,6 @@ package main
|
|||
|
||||
import (
|
||||
"fmt"
|
||||
"go/build"
|
||||
"io/ioutil"
|
||||
"log"
|
||||
"os"
|
||||
|
@ -32,6 +31,7 @@ ex:
|
|||
Flag: *flag.NewFlagSet("gopy-bind", flag.ExitOnError),
|
||||
}
|
||||
|
||||
cmd.Flag.String("lang", "py2", "python version to use for bindings (python2|py2|python3|py3)")
|
||||
cmd.Flag.String("output", "", "output directory for bindings")
|
||||
return cmd
|
||||
}
|
||||
|
@ -47,6 +47,7 @@ func gopyRunCmdBind(cmdr *commander.Command, args []string) error {
|
|||
}
|
||||
|
||||
odir := cmdr.Flag.Lookup("output").Value.Get().(string)
|
||||
lang := cmdr.Flag.Lookup("lang").Value.Get().(string)
|
||||
|
||||
cwd, err := os.Getwd()
|
||||
if err != nil {
|
||||
|
@ -69,7 +70,7 @@ func gopyRunCmdBind(cmdr *commander.Command, args []string) error {
|
|||
}
|
||||
|
||||
path := args[0]
|
||||
pkg, err := build.Import(path, cwd, 0)
|
||||
pkg, err := newPackage(path)
|
||||
if err != nil {
|
||||
return fmt.Errorf(
|
||||
"gopy-bind: go/build.Inport failed with path=%q: %v\n",
|
||||
|
@ -90,30 +91,12 @@ func gopyRunCmdBind(cmdr *commander.Command, args []string) error {
|
|||
}
|
||||
//defer os.RemoveAll(work)
|
||||
|
||||
cmd := exec.Command(
|
||||
"gopy", "gen",
|
||||
"-output", work,
|
||||
"-lang=python", pkg.ImportPath,
|
||||
)
|
||||
cmd.Stdin = os.Stdin
|
||||
cmd.Stdout = os.Stdout
|
||||
cmd.Stderr = os.Stderr
|
||||
|
||||
err = cmd.Run()
|
||||
err = genPkg(work, pkg, lang)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
cmd = exec.Command(
|
||||
"gopy", "gen",
|
||||
"-output", work,
|
||||
"-lang=go", pkg.ImportPath,
|
||||
)
|
||||
cmd.Stdin = os.Stdin
|
||||
cmd.Stdout = os.Stdout
|
||||
cmd.Stderr = os.Stderr
|
||||
|
||||
err = cmd.Run()
|
||||
err = genPkg(work, pkg, "go")
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
@ -129,9 +112,9 @@ func gopyRunCmdBind(cmdr *commander.Command, args []string) error {
|
|||
}
|
||||
defer os.RemoveAll(wbind)
|
||||
|
||||
cmd = exec.Command(
|
||||
cmd := exec.Command(
|
||||
"go", "build", "-v", "-buildmode=c-shared",
|
||||
"-o", filepath.Join(wbind, pkg.Name)+".so",
|
||||
"-o", filepath.Join(wbind, pkg.Name())+".so",
|
||||
// pkg.ImportPath,
|
||||
".",
|
||||
)
|
||||
|
@ -146,8 +129,8 @@ func gopyRunCmdBind(cmdr *commander.Command, args []string) error {
|
|||
|
||||
cmd = exec.Command(
|
||||
"/bin/cp",
|
||||
filepath.Join(wbind, pkg.Name)+".so",
|
||||
filepath.Join(odir, pkg.Name)+".so",
|
||||
filepath.Join(wbind, pkg.Name())+".so",
|
||||
filepath.Join(odir, pkg.Name())+".so",
|
||||
)
|
||||
cmd.Stdin = os.Stdin
|
||||
cmd.Stdout = os.Stdout
|
||||
|
|
|
@ -6,7 +6,6 @@ package main
|
|||
|
||||
import (
|
||||
"fmt"
|
||||
"go/build"
|
||||
"log"
|
||||
"os"
|
||||
"path/filepath"
|
||||
|
@ -73,7 +72,7 @@ func gopyRunCmdGen(cmdr *commander.Command, args []string) error {
|
|||
}
|
||||
|
||||
path := args[0]
|
||||
pkg, err := build.Import(path, cwd, 0)
|
||||
pkg, err := newPackage(path)
|
||||
if err != nil {
|
||||
return fmt.Errorf(
|
||||
"gopy-gen: go/build.Inport failed with path=%q: %v\n",
|
||||
|
|
63
gen.go
63
gen.go
|
@ -26,31 +26,22 @@ var (
|
|||
fset = token.NewFileSet()
|
||||
)
|
||||
|
||||
func genPkg(odir string, pkg *build.Package, lang string) error {
|
||||
func genPkg(odir string, p *bind.Package, lang string) error {
|
||||
var err error
|
||||
var o *os.File
|
||||
|
||||
files, err := parseFiles(pkg.Dir, pkg.GoFiles)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
conf := loader.Config{
|
||||
Fset: fset,
|
||||
}
|
||||
conf.TypeChecker.Error = func(e error) {
|
||||
log.Printf("%v\n", e)
|
||||
err = e
|
||||
}
|
||||
|
||||
p, err := newPackage(files, &conf, pkg)
|
||||
if err != nil {
|
||||
log.Printf("%v\n", err)
|
||||
return err
|
||||
switch lang {
|
||||
case "python", "py":
|
||||
lang, err = getPythonVersion()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
default:
|
||||
// no-op
|
||||
}
|
||||
|
||||
switch lang {
|
||||
case "python", "py":
|
||||
case "python2", "py2":
|
||||
o, err = os.Create(filepath.Join(odir, p.Name()+".c"))
|
||||
if err != nil {
|
||||
return err
|
||||
|
@ -61,6 +52,9 @@ func genPkg(odir string, pkg *build.Package, lang string) error {
|
|||
return err
|
||||
}
|
||||
|
||||
case "python3", "py3":
|
||||
return fmt.Errorf("gopy: python-3 support not yet implemented")
|
||||
|
||||
case "go":
|
||||
o, err = os.Create(filepath.Join(odir, p.Name()+".go"))
|
||||
if err != nil {
|
||||
|
@ -147,7 +141,36 @@ func parseFiles(dir string, fnames []string) ([]*ast.File, error) {
|
|||
return files, err
|
||||
}
|
||||
|
||||
func newPackage(files []*ast.File, conf *loader.Config, pkg *build.Package) (*bind.Package, error) {
|
||||
func newPackage(path string) (*bind.Package, error) {
|
||||
cwd, err := os.Getwd()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
pkg, err := build.Import(path, cwd, 0)
|
||||
files, err := parseFiles(pkg.Dir, pkg.GoFiles)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
conf := loader.Config{
|
||||
Fset: fset,
|
||||
}
|
||||
conf.TypeChecker.Error = func(e error) {
|
||||
log.Printf("%v\n", e)
|
||||
err = e
|
||||
}
|
||||
|
||||
p, err := newPackageFrom(files, &conf, pkg)
|
||||
if err != nil {
|
||||
log.Printf("%v\n", err)
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return p, err
|
||||
}
|
||||
|
||||
func newPackageFrom(files []*ast.File, conf *loader.Config, pkg *build.Package) (*bind.Package, error) {
|
||||
|
||||
conf.CreateFromFiles(pkg.ImportPath, files...)
|
||||
program, err := conf.Load()
|
||||
|
|
|
@ -0,0 +1,45 @@
|
|||
// Copyright 2015 The go-python Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
package main
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
"os/exec"
|
||||
)
|
||||
|
||||
// getPythonVersion returns the python version available on this machine
|
||||
func getPythonVersion() (string, error) {
|
||||
py, err := exec.LookPath("python")
|
||||
if err != nil {
|
||||
return "", fmt.Errorf(
|
||||
"gopy: could not locate 'python' executable (err: %v)",
|
||||
err,
|
||||
)
|
||||
}
|
||||
|
||||
out, err := exec.Command(py, "--version").Output()
|
||||
if err != nil {
|
||||
return "", fmt.Errorf(
|
||||
"gopy: error retrieving python version (err: %v)",
|
||||
err,
|
||||
)
|
||||
}
|
||||
|
||||
vers := ""
|
||||
switch {
|
||||
case bytes.HasPrefix(out, []byte("Python 2")):
|
||||
vers = "py2"
|
||||
case bytes.HasPrefix(out, []byte("Python 3")):
|
||||
vers = "py3"
|
||||
default:
|
||||
return "", fmt.Errorf(
|
||||
"gopy: invalid python version (%s)",
|
||||
string(out),
|
||||
)
|
||||
}
|
||||
|
||||
return vers, nil
|
||||
}
|
Loading…
Reference in New Issue