-
Notifications
You must be signed in to change notification settings - Fork 7
Unified Architecture Refactor - Python and C++ Packages Use Same Version Management #72
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Open
PengPengPeng717
wants to merge
46
commits into
xgo-dev:llpyg
Choose a base branch
from
PengPengPeng717:v2
base: llpyg
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from all commits
Commits
Show all changes
46 commits
Select commit
Hold shift + click to select a range
12d90af
chore: start modify xxh
9b48768
feat: Divide different cmd commands
c76b538
feat: Add the llpkgstore verfication function(python)
000e341
feat: Add the llpkgstore install function(python)
0d6554e
feat: Add the llpkgstore issueclose function(python)
fa9e456
fix: fix the generate bug
5b712ae
feat: Modify Chinese to English
052760b
feat: Add the llpkgstore demotest function(python)
cd9f126
feat: Add the llpkgstore release,label,post function(python)
22d2d53
fix: fix the llpkgstore bug
340850a
feat: Add the llpkgstore postprocessing function(python)
ceb3532
feat: Add the version information to llpkgstore.json
734da10
feat: modify post+release function(Python)
8485cc1
chore: Optimize the code
c4e60fb
chore: Optimize the code
931462c
feat: creat release if release already exists
0dd3a6d
feat: Remove llpkgstore.json from python, and the version will no lon…
1e7c5cb
feat: tag the version based on the commit information
8404f43
fix: bug_modify
3da015c
fix: bug_modify
5f467bc
feat: generate_modify
cd68035
docx: add llpkgstore.md
35dc243
feat: verrsion modify
f36243e
chore: Code improvement
6d72569
docx: modify_doc, add project.md
b215634
feat: modify generate
eccdf75
docx: add architecture.md
cc7d333
docx: modify-docs
c24ada5
feat: Improve the verification function of llpkgstored
8c6f233
fix: fix bug
09a326d
fix: fix the bug
0e3a091
feat: veify Release-as: tabulate/v0.0.25
5b1cde7
chore: Improve the code
e798886
Fix the 'actions: no artifact found' error in CI
545ed11
docx: add version-mapping-logic.md
4e642f1
feat: allow coverage
45bcf38
fix: modify bug
d0ae52e
fix: fix the bug
2da3b2e
feat: del llpkgstore.json
fe9c7fb
feat: Update Python package tag format from Python_package to py
16af0d8
feat: Give priority to using packages in the system environment and o…
f45867b
chore: Modify the Chinese annotations into English
b0249d0
feat: Move internal_cpp and internal_python under internal
f284aa4
Modify internal_cpp and internal_python to cpp and python respectively
8b91690
docx: Revise the project documentation and architecture documentation
e5fb688
Modify the project documentation and architecture documentation to En…
File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,20 @@ | ||
| { | ||
| "type": "python", | ||
| "upstream": { | ||
| "installer": { | ||
| "name": "pip", | ||
| "config": { | ||
| "options": "" | ||
| } | ||
| }, | ||
| "package": { | ||
| "name": "numpy", | ||
| "version": "1.26.4" | ||
| } | ||
| }, | ||
| "llpyg": { | ||
| "output_dir": "./generated", | ||
| "mod_name": "github.com/PengPengPeng717/llpkg/numpy", | ||
| "mod_depth": 2 | ||
| } | ||
| } | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. |
||
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,80 @@ | ||
| package internal | ||
|
|
||
| import ( | ||
| "encoding/json" | ||
| "fmt" | ||
| "os" | ||
| "os/exec" | ||
| "path/filepath" | ||
|
|
||
| "github.com/spf13/cobra" | ||
| ) | ||
|
|
||
| // demotestCmd represents the demotest command for Python packages | ||
| var demotestCmd = &cobra.Command{ | ||
| Use: "demotest", | ||
| Short: "A tool that runs all Python package demos", | ||
| Long: `A tool that runs all demo tests for Python packages to verify the generated Go bindings work correctly.`, | ||
| RunE: runPythonDemotestCmd, | ||
| } | ||
|
|
||
| func runPythonDemotestCmd(cmd *cobra.Command, args []string) error { | ||
| var paths []string | ||
| pathEnv := os.Getenv("LLPKG_PATH") | ||
| if pathEnv != "" { | ||
| json.Unmarshal([]byte(pathEnv), &paths) | ||
| } else { | ||
| // not in github action | ||
| paths = append(paths, currentDir()) | ||
| } | ||
|
|
||
| for _, path := range paths { | ||
| if err := runPythonDemo(path); err != nil { | ||
| return err | ||
| } | ||
| } | ||
| return nil | ||
| } | ||
|
|
||
| func runPythonDemo(demoRoot string) error { | ||
| demosPath := filepath.Join(demoRoot, "_demo") | ||
|
|
||
| fmt.Printf("Testing Python demos in %s\n", demosPath) | ||
|
|
||
| // Check if _demo directory exists | ||
| if _, err := os.Stat(demosPath); os.IsNotExist(err) { | ||
| return fmt.Errorf("demotest: demo directory not found: %s", demosPath) | ||
| } | ||
|
|
||
| // Read and run all demos | ||
| demos, err := os.ReadDir(demosPath) | ||
| if err != nil { | ||
| return fmt.Errorf("demotest: failed to read demo directory: %w", err) | ||
| } | ||
|
|
||
| for _, demo := range demos { | ||
| if demo.IsDir() { | ||
| fmt.Printf("Running Python demo: %s\n", demo.Name()) | ||
| if demoErr := runPythonCommand(demoRoot, filepath.Join(demosPath, demo.Name()), "llgo", "run", "."); demoErr != nil { | ||
| return fmt.Errorf("demotest: failed to run Python demo: %s: %w", demo.Name(), demoErr) | ||
| } | ||
| } | ||
| } | ||
| return nil | ||
| } | ||
|
|
||
| func runPythonCommand(pcPath, dir, command string, args ...string) error { | ||
| cmd := exec.Command(command, args...) | ||
| cmd.Dir = dir | ||
| cmd.Stdout = os.Stdout | ||
| cmd.Stderr = os.Stderr | ||
|
|
||
| // Set environment variables for Python packages | ||
| cmd.Env = append(os.Environ(), "PYTHONPATH="+pcPath) | ||
|
|
||
| return cmd.Run() | ||
| } | ||
|
|
||
| func init() { | ||
| rootCmd.AddCommand(demotestCmd) | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,171 @@ | ||
| package internal | ||
|
|
||
| import ( | ||
| "fmt" | ||
| "log" | ||
| "os" | ||
| "os/exec" | ||
| "path/filepath" | ||
| "strings" | ||
|
|
||
| "github.com/goplus/llpkgstore/config" | ||
| "github.com/goplus/llpkgstore/internal/actions/generator/llpyg" | ||
| "github.com/spf13/cobra" | ||
| ) | ||
|
|
||
| var generateCmd = &cobra.Command{ | ||
| Use: "generate", | ||
| Short: "Generate Python bindings", | ||
| Long: ``, | ||
| RunE: runLLPygGenerate, | ||
| } | ||
|
|
||
| func currentDir() string { | ||
| dir, err := os.Getwd() | ||
| if err != nil { | ||
| panic(err) | ||
| } | ||
| return dir | ||
| } | ||
|
|
||
| // isPackageInstalledInSystem checks if the specified package is already installed in the system environment | ||
| func isPackageInstalledInSystem(packageName string) bool { | ||
| // Method 1: Try to import the package directly | ||
| if canImportPackage(packageName) { | ||
| return true | ||
| } | ||
|
|
||
| // Method 2: Check pip list output | ||
| if isPackageInPipList(packageName) { | ||
| return true | ||
| } | ||
|
|
||
| return false | ||
| } | ||
|
|
||
| // canImportPackage tries to import the package to check if it's installed | ||
| func canImportPackage(packageName string) bool { | ||
| cmd := exec.Command("python3", "-c", fmt.Sprintf("import %s; print('OK')", packageName)) | ||
| output, err := cmd.CombinedOutput() | ||
| if err != nil { | ||
| log.Printf("Package %s import test failed: %v", packageName, err) | ||
| return false | ||
| } | ||
|
|
||
| // Check if output contains "OK" | ||
| result := strings.TrimSpace(string(output)) | ||
| return strings.Contains(result, "OK") | ||
| } | ||
|
|
||
| // isPackageInPipList checks if the package is in pip list | ||
| func isPackageInPipList(packageName string) bool { | ||
| cmd := exec.Command("pip3", "list") | ||
| output, err := cmd.CombinedOutput() | ||
| if err != nil { | ||
| log.Printf("Failed to run pip3 list: %v", err) | ||
| return false | ||
| } | ||
|
|
||
| // Check if package name is in the output | ||
| lines := strings.Split(string(output), "\n") | ||
| for _, line := range lines { | ||
| if strings.Contains(line, packageName) { | ||
| return true | ||
| } | ||
| } | ||
|
|
||
| return false | ||
| } | ||
|
|
||
| func runLLPygGenerateWithDir(dir string) error { | ||
| cfg, err := config.ParseLLPkgConfig(filepath.Join(dir, LLGOModuleIdentifyFile)) | ||
| if err != nil { | ||
| return fmt.Errorf("parse config error: %v", err) | ||
| } | ||
| uc, err := config.NewUpstreamFromConfig(cfg.Upstream) | ||
| if err != nil { | ||
| return err | ||
| } | ||
| log.Printf("Start to generate %s", uc.Pkg.Name) | ||
|
|
||
| // Prioritize checking if package is already installed in system environment | ||
| var pythonDir string | ||
| var tempDir string | ||
| var needCleanup bool | ||
|
|
||
| // Check if the package already exists in system environment | ||
| if isPackageInstalledInSystem(uc.Pkg.Name) { | ||
| log.Printf("Package %s found in system environment, using system installation", uc.Pkg.Name) | ||
| pythonDir = "" // Use system environment, no need to set PYTHONPATH | ||
| } else { | ||
| log.Printf("Package %s not found in system environment, installing to temporary directory", uc.Pkg.Name) | ||
| tempDir, err = os.MkdirTemp("", "llpkg-tool") | ||
| if err != nil { | ||
| return err | ||
| } | ||
| needCleanup = true | ||
| defer func() { | ||
| if needCleanup { | ||
| os.RemoveAll(tempDir) | ||
| } | ||
| }() | ||
|
|
||
| _, err = uc.Installer.Install(uc.Pkg, tempDir) | ||
| if err != nil { | ||
| return err | ||
| } | ||
| pythonDir = tempDir | ||
| } | ||
|
|
||
| // Check if this is a Python package | ||
| if cfg.Type == "python" { | ||
| // For Python packages, directly use llpyg generator | ||
| // This will call "llpyg numpy" and copy the generated files | ||
| generator := llpyg.New(dir, cfg.Upstream.Package.Name, pythonDir) | ||
| return generator.Generate(dir) | ||
| } else { | ||
| // For C/C++ packages, we need to import the C++ generator | ||
| // This is a simplified version - in practice you might want to handle this differently | ||
| return fmt.Errorf("C/C++ packages not supported in Python version") | ||
| } | ||
| } | ||
|
|
||
| func runLLPygGenerate(_ *cobra.Command, args []string) error { | ||
| // Detect environment based on the first directory | ||
| path := currentDir() | ||
| if len(args) > 0 { | ||
| if absPath, err := filepath.Abs(args[0]); err == nil { | ||
| path = absPath | ||
| } | ||
| } | ||
|
|
||
| // Check if this is a Python package by reading the config | ||
| cfg, err := config.ParseLLPkgConfig(filepath.Join(path, LLGOModuleIdentifyFile)) | ||
| if err == nil && cfg.Type == "python" { | ||
| // For Python packages, we don't need conan profile detection | ||
| log.Printf("Detected Python package: %s", cfg.Upstream.Package.Name) | ||
| } else { | ||
| // For C/C++ packages, detect conan profile | ||
| exec.Command("conan", "profile", "detect").Run() | ||
| } | ||
|
|
||
| // by default, use current dir | ||
| if len(args) == 0 { | ||
| return runLLPygGenerateWithDir(path) | ||
| } | ||
| for _, argPath := range args { | ||
| absPath, err := filepath.Abs(argPath) | ||
| if err != nil { | ||
| continue | ||
| } | ||
| err = runLLPygGenerateWithDir(absPath) | ||
| if err != nil { | ||
| return err | ||
| } | ||
| } | ||
| return nil | ||
| } | ||
|
|
||
| func init() { | ||
| rootCmd.AddCommand(generateCmd) | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,92 @@ | ||
| package internal | ||
|
|
||
| import ( | ||
| "fmt" | ||
| "log" | ||
| "os" | ||
|
|
||
| "github.com/goplus/llpkgstore/config" | ||
| "github.com/spf13/cobra" | ||
| ) | ||
|
|
||
| // installCmd represents the install command | ||
| var installCmd = &cobra.Command{ | ||
| Use: "install [LLPkgConfigFilePath]", | ||
| Short: "Manually install a Python package", | ||
| Long: `Manually install a Python package from llpkg.cfg file using pip.`, | ||
| Args: cobra.ExactArgs(1), | ||
| RunE: manuallyInstall, | ||
| } | ||
|
|
||
| func manuallyInstall(cmd *cobra.Command, args []string) error { | ||
| cfgPath := args[0] | ||
|
|
||
| // Check if configuration file exists | ||
| if _, err := os.Stat(cfgPath); os.IsNotExist(err) { | ||
| return fmt.Errorf("configuration file does not exist: %s", cfgPath) | ||
| } | ||
|
|
||
| // Parse configuration file | ||
| LLPkgConfig, err := config.ParseLLPkgConfig(cfgPath) | ||
| if err != nil { | ||
| return fmt.Errorf("failed to parse configuration file: %v", err) | ||
| } | ||
|
|
||
| // Check package type | ||
| if LLPkgConfig.Type != "python" { | ||
| return fmt.Errorf("unsupported package type: %s, currently only Python packages are supported", LLPkgConfig.Type) | ||
| } | ||
|
|
||
| // Get output directory | ||
| output, err := cmd.Flags().GetString("output") | ||
| if err != nil { | ||
| return err | ||
| } | ||
|
|
||
| // If output directory is empty, use current directory | ||
| if output == "" { | ||
| output = "." | ||
| } | ||
|
|
||
| // Ensure output directory exists | ||
| if err := os.MkdirAll(output, 0755); err != nil { | ||
| return fmt.Errorf("failed to create output directory: %v", err) | ||
| } | ||
|
|
||
| log.Printf("Starting to install Python package: %s==%s", LLPkgConfig.Upstream.Package.Name, LLPkgConfig.Upstream.Package.Version) | ||
| log.Printf("Output directory: %s", output) | ||
|
|
||
| // Create upstream instance | ||
| upstream, err := config.NewUpstreamFromConfig(LLPkgConfig.Upstream) | ||
| if err != nil { | ||
| return fmt.Errorf("failed to create upstream instance: %v", err) | ||
| } | ||
|
|
||
| // Execute installation | ||
| installedPackages, err := upstream.Installer.Install(upstream.Pkg, output) | ||
| if err != nil { | ||
| return fmt.Errorf("installation failed: %v", err) | ||
| } | ||
|
|
||
| log.Printf("Installation successful! Installed packages: %v", installedPackages) | ||
|
|
||
| // Display installation results | ||
| fmt.Printf("✓ Successfully installed Python package: %s==%s\n", LLPkgConfig.Upstream.Package.Name, LLPkgConfig.Upstream.Package.Version) | ||
| fmt.Printf(" Installation location: %s\n", output) | ||
| fmt.Printf(" Installed packages: %v\n", installedPackages) | ||
|
|
||
| // If it's a pip installer, show additional information | ||
| if LLPkgConfig.Upstream.Installer.Name == "pip" { | ||
| fmt.Println("\nNote:") | ||
| fmt.Println("- Package has been installed to the specified directory via pip3") | ||
| fmt.Println("- You can use 'generate' command to generate Go bindings") | ||
| fmt.Println("- You can use 'test' command to verify installation results") | ||
| } | ||
|
|
||
| return nil | ||
| } | ||
|
|
||
| func init() { | ||
| installCmd.Flags().StringP("output", "o", "", "Installation output directory (default: current directory)") | ||
| rootCmd.AddCommand(installCmd) | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,26 @@ | ||
| package internal | ||
|
|
||
| import ( | ||
| "github.com/goplus/llpkgstore/internal/actions" | ||
| "github.com/spf13/cobra" | ||
| ) | ||
|
|
||
| var issueCloseCmd = &cobra.Command{ | ||
| Use: "issueclose", | ||
| Short: "Clean up resources after issue closure", | ||
| Long: ``, | ||
|
|
||
| RunE: runIssueCloseCmd, | ||
| } | ||
|
|
||
| func runIssueCloseCmd(cmd *cobra.Command, args []string) error { | ||
| client, err := actions.NewDefaultClient() | ||
| if err != nil { | ||
| return err | ||
| } | ||
| return client.CleanResource() | ||
| } | ||
|
|
||
| func init() { | ||
| rootCmd.AddCommand(issueCloseCmd) | ||
| } |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Invalid file extension name, should be
llpkg.cfg