From ba97af9a3def1d357274e2d7623ac453d60d9924 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=AE=B5=E4=BB=AA?= Date: Thu, 9 Oct 2025 19:39:39 +0800 Subject: [PATCH 1/3] feat: support dynamic version --- version.go | 27 +++++++++++++++++++++++++-- 1 file changed, 25 insertions(+), 2 deletions(-) diff --git a/version.go b/version.go index af5561e1..727480a6 100644 --- a/version.go +++ b/version.go @@ -16,6 +16,29 @@ package main -const ( - Version = "0.2.1" +import ( + "debug/buildinfo" + "fmt" + "os" ) + +var Version = "0.0.0" + +func init() { + path, err := os.Executable() + if err != nil { + fmt.Fprintf(os.Stderr, "fail to get executable path: %v\n", err) + return + } + data, err := os.Open(path) + if err != nil { + fmt.Fprintf(os.Stderr, "fail to read executable file: %v\n", err) + return + } + info, err := buildinfo.Read(data) + if err != nil { + fmt.Fprintf(os.Stderr, "fail to read build info: %v\n", err) + return + } + Version = info.Main.Version +} From 244f14956e7d8f4f4b5f2fa4959cf16521d15e9d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=AE=B5=E4=BB=AA?= Date: Thu, 9 Oct 2025 20:03:37 +0800 Subject: [PATCH 2/3] update UniAST field `ToolVersion` --- docs/uniast-en.md | 12 +++++++++--- docs/uniast-zh.md | 11 ++++++++--- lang/parse.go | 2 ++ lang/uniast/ast.go | 11 ++++++----- lang/uniast/version.go | 2 +- main.go | 7 +++++-- version.go => version/version.go | 4 ++-- 7 files changed, 33 insertions(+), 16 deletions(-) rename version.go => version/version.go (96%) diff --git a/docs/uniast-en.md b/docs/uniast-en.md index 48ff999a..58237414 100644 --- a/docs/uniast-en.md +++ b/docs/uniast-en.md @@ -81,7 +81,10 @@ A repository consists of entity Modules and relationship Graph ```json { - "Identity": "/Users/bytedance/golang/work/abcoder/tmp/localsession", + "id": "/Users/bytedance/golang/work/abcoder/tmp/localsession", + "ASTVersion": "xx", + "ToolVersion": "yy", + "Path": "/a/b/localsession", "Modules": { "github.com/bytedance/gopkg@v0.0.0-20230728082804-614d0af6619b": {}, "github.com/cloudwego/localsession": {} @@ -90,7 +93,7 @@ A repository consists of entity Modules and relationship Graph } ``` -- Identity: The unique name of the repo. Since the abcoder parser does not currently retrieve repository git information, the absolute path where it is currently located is generally used as the Identity +- id: The unique name of the repo. Since the abcoder parser does not currently retrieve repository git information, the absolute path where it is currently located is generally used as the Identity - Modules: Contains submodules, a dictionary of {ModPath}: {Module AST}. Both repository modules and external dependency modules can appear in Modules, but need to be distinguished by ModulePath. @@ -104,7 +107,10 @@ A repository consists of entity Modules and relationship Graph - Path: The file directory of the repository, usually should be an absolute path -- ASTVersion: The UniAST version used to parse +- ASTVersion: The UniAST version spefication when the repository is parsed + +- ToolVersion: The abcoder version used to parse + ### Module diff --git a/docs/uniast-zh.md b/docs/uniast-zh.md index 2a7d6448..7a826ebd 100644 --- a/docs/uniast-zh.md +++ b/docs/uniast-zh.md @@ -81,7 +81,10 @@ Universal Abstract-Syntax-Tree 是 ABCoder 建立的一种 LLM 亲和、语言 ```json { - "Identity": "/Users/bytedance/golang/work/abcoder/tmp/localsession", + "id": "/Users/bytedance/golang/work/abcoder/tmp/localsession", + "ASTVersion": "xx", + "ToolVersion": "yy", + "Path": "/a/b/localsession", "Modules": { "github.com/bytedance/gopkg@v0.0.0-20230728082804-614d0af6619b": {}, "github.com/cloudwego/localsession": {} @@ -90,7 +93,7 @@ Universal Abstract-Syntax-Tree 是 ABCoder 建立的一种 LLM 亲和、语言 } ``` -- Identity: repo 的唯一名称。由于 abcoder parser 目前不获取仓库 git 信息,因此一般使用当前所处的绝对路径作为 Identity +- id: repo 的唯一名称。由于 abcoder parser 目前不获取仓库 git 信息,因此一般使用当前所处的绝对路径作为 Identity - Modules: 包含的子模块,{ModPath} : {Module AST} 的字典,本仓库模块和外部依赖模块都可以出现在 Modules 中,但是需要通过 ModulePath 来区分。 @@ -104,7 +107,9 @@ Universal Abstract-Syntax-Tree 是 ABCoder 建立的一种 LLM 亲和、语言 - Path: 仓库的文件目录,通常应该为绝对路径 -- ASTVersion: 解析时使用的 UniAST 版本 +- ASTVersion: 解析时对应的 UniAST 版本 + +- ToolVersion: 解析时使用的 abcoder 版本 ### Module diff --git a/lang/parse.go b/lang/parse.go index 2c3ac204..98e46381 100644 --- a/lang/parse.go +++ b/lang/parse.go @@ -35,6 +35,7 @@ import ( "github.com/cloudwego/abcoder/lang/register" "github.com/cloudwego/abcoder/lang/rust" "github.com/cloudwego/abcoder/lang/uniast" + "github.com/cloudwego/abcoder/version" ) // ParseOptions is the options for parsing the repo. @@ -105,6 +106,7 @@ func Parse(ctx context.Context, uri string, args ParseOptions) ([]byte, error) { } repo.ASTVersion = uniast.Version + repo.ToolVersion = version.Version out, err := json.Marshal(repo) if err != nil { diff --git a/lang/uniast/ast.go b/lang/uniast/ast.go index 12afedae..50490eee 100644 --- a/lang/uniast/ast.go +++ b/lang/uniast/ast.go @@ -83,11 +83,12 @@ type NodeGraph map[string]*Node // Repository type Repository struct { - ASTVersion string - Name string `json:"id"` // module name - Path string // repo path - Modules map[string]*Module // module name => module - Graph NodeGraph // node id => node + Name string `json:"id"` // module name + ASTVersion string // uniast version + ToolVersion string // abcoder version + Path string // repo absolute path + Modules map[string]*Module // module name => module + Graph NodeGraph // node id => node } func (r Repository) ID() string { diff --git a/lang/uniast/version.go b/lang/uniast/version.go index 5d84a052..99a9f558 100644 --- a/lang/uniast/version.go +++ b/lang/uniast/version.go @@ -16,4 +16,4 @@ package uniast -const Version = "v0.1.3" +const Version = "v0.1.4" diff --git a/main.go b/main.go index 762aa38b..1e65d050 100644 --- a/main.go +++ b/main.go @@ -47,6 +47,7 @@ import ( "github.com/cloudwego/abcoder/llm/agent" "github.com/cloudwego/abcoder/llm/mcp" "github.com/cloudwego/abcoder/llm/tool" + "github.com/cloudwego/abcoder/version" ) const Usage = `abcoder [Language] [Flags] @@ -106,7 +107,7 @@ func main() { switch action { case "version": - fmt.Fprintf(os.Stdout, "%s\n", Version) + fmt.Fprintf(os.Stdout, "%s\n", version.Version) case "parse": language, uri := parseArgsAndFlags(flags, true, flagHelp, flagVerbose) @@ -183,7 +184,7 @@ func main() { svr := mcp.NewServer(mcp.ServerOptions{ ServerName: "abcoder", - ServerVersion: Version, + ServerVersion: version.Version, Verbose: *flagVerbose, ASTReadToolsOptions: tool.ASTReadToolsOptions{ RepoASTsDir: uri, @@ -308,6 +309,8 @@ func parseTSProject(ctx context.Context, repoPath string, opts lang.ParseOptions cmd := exec.CommandContext(ctx, parserPath, args...) cmd.Env = append(os.Environ(), "NODE_OPTIONS=--max-old-space-size=65536") + cmd.Env = append(cmd.Env, "ABCODER_TOOL_VERSION="+version.Version) + cmd.Env = append(cmd.Env, "ABCODER_AST_VERSION="+uniast.Version) cmd.Stdout = os.Stdout cmd.Stderr = os.Stderr diff --git a/version.go b/version/version.go similarity index 96% rename from version.go rename to version/version.go index 727480a6..32142296 100644 --- a/version.go +++ b/version/version.go @@ -14,7 +14,7 @@ * limitations under the License. */ -package main +package version import ( "debug/buildinfo" @@ -22,7 +22,7 @@ import ( "os" ) -var Version = "0.0.0" +var Version = "unknown" func init() { path, err := os.Executable() From 222493d7187f68ddb3ea201562580b93d39ca455 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=AE=B5=E4=BB=AA?= Date: Thu, 9 Oct 2025 20:27:17 +0800 Subject: [PATCH 3/3] feat:(ts) update uniast --- ts-parser/package-lock.json | 9 ++++++--- ts-parser/package.json | 4 ++-- ts-parser/src/index.ts | 10 +++++----- ts-parser/src/types/uniast.ts | 8 ++++++-- ts-parser/src/utils/package-processor.ts | 13 ++++++++++--- 5 files changed, 29 insertions(+), 15 deletions(-) diff --git a/ts-parser/package-lock.json b/ts-parser/package-lock.json index 0fb367b6..19428107 100644 --- a/ts-parser/package-lock.json +++ b/ts-parser/package-lock.json @@ -1,18 +1,21 @@ { "name": "abcoder-ts-parser", - "version": "1.0.0", + "version": "0.0.4", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "abcoder-ts-parser", - "version": "1.0.0", - "license": "MIT", + "version": "0.0.4", + "license": "ALv2", "dependencies": { "commander": "^11.0.0", "json5": "^2.2.3", "ts-morph": "^23.0.0" }, + "bin": { + "abcoder-ts-parser": "dist/index.js" + }, "devDependencies": { "@types/jest": "^29.0.0", "@types/json5": "^2.2.0", diff --git a/ts-parser/package.json b/ts-parser/package.json index 3d19986e..b1658fd8 100644 --- a/ts-parser/package.json +++ b/ts-parser/package.json @@ -1,6 +1,6 @@ { "name": "abcoder-ts-parser", - "version": "0.0.3", + "version": "0.0.4", "description": "TypeScript AST parser for UNIAST v0.1.3 specification", "main": "dist/index.js", "types": "dist/index.d.ts", @@ -43,4 +43,4 @@ "ts-node": "^10.9.0", "typescript": "^5.0.0" } -} +} \ No newline at end of file diff --git a/ts-parser/src/index.ts b/ts-parser/src/index.ts index 23096543..87f02dc3 100644 --- a/ts-parser/src/index.ts +++ b/ts-parser/src/index.ts @@ -10,7 +10,7 @@ const program = new Command(); program .name('abcoder-ts-parser') .description('TypeScript AST parser for UNIAST v0.1.3 specification') - .version('1.0.0'); + .version('0.0.4'); program .command('parse') @@ -25,14 +25,14 @@ program .action(async (directory, options) => { try { const repoPath = path.resolve(directory); - + if (!fs.existsSync(repoPath)) { console.error(`Error: Directory ${repoPath} does not exist`); process.exit(1); } console.log(`Parsing TypeScript repository: ${repoPath}`); - + const parser = new RepositoryParser(repoPath, options.tsconfig); const repository = await parser.parseRepository(repoPath, { loadExternalSymbols: false, @@ -43,12 +43,12 @@ program // Output the repository JSON file const outputPath = path.resolve(options.output); - const jsonOutput = options.pretty + const jsonOutput = options.pretty ? JSON.stringify(repository, null, 2) : JSON.stringify(repository); fs.writeFileSync(outputPath, jsonOutput); - + console.log(`Successfully parsed repository`); console.log(`Output written to: ${outputPath}`); console.log(`Total modules: ${Object.keys(repository.Modules).length}`); diff --git a/ts-parser/src/types/uniast.ts b/ts-parser/src/types/uniast.ts index fe2f10b7..2d28fb90 100644 --- a/ts-parser/src/types/uniast.ts +++ b/ts-parser/src/types/uniast.ts @@ -9,10 +9,14 @@ * Root object representing an entire code repository. */ export interface Repository { - /** UNIAST specification version. Fixed to "v0.1.3". */ - ASTVersion: string; /** Unique identifier for the repository. Field name in JSON is "id". */ id: string; + /** UNIAST specification version. Fixed to "v0.1.3". */ + ASTVersion: string; + /** abcoder version used to parse the repository. Field name in JSON is "ToolVersion". */ + ToolVersion: string; + /** File directory of the repository, usually should be an absolute path. */ + Path: string; /** Map of all modules in the repository. Keys are unique path identifiers. */ Modules: Record; /** diff --git a/ts-parser/src/utils/package-processor.ts b/ts-parser/src/utils/package-processor.ts index 679758d8..54390226 100644 --- a/ts-parser/src/utils/package-processor.ts +++ b/ts-parser/src/utils/package-processor.ts @@ -371,7 +371,7 @@ export class ProjectFactory { * Handles tsconfig.json resolution and project references */ static createProjectForSingleRepo( - projectRoot: string, + projectRoot: string, tsConfigPath?: string, tsConfigCache?: TsConfigCache ): Project { @@ -492,7 +492,7 @@ export class ProjectFactory { return false; } }); - + if (existingFiles.length > 0) { try { project.addSourceFilesAtPaths(existingFiles); @@ -523,7 +523,8 @@ export class ProjectFactory { * Repository Factory - Centralized creation of Repository objects */ export class RepositoryFactory { - private static readonly AST_VERSION = 'v0.1.3'; + private static AST_VERSION = process.env.ABCODER_AST_VERSION || 'unknown'; + private static TOOL_VERSION = process.env.ABCODER_TOOL_VERSION || 'unknown'; /** * Create a repository for a single project/repository @@ -532,7 +533,9 @@ export class RepositoryFactory { const absolutePath = path.resolve(repoPath); return { ASTVersion: RepositoryFactory.AST_VERSION, + ToolVersion: RepositoryFactory.TOOL_VERSION, id: path.basename(absolutePath), + Path: absolutePath, Modules: {}, Graph: {}, }; @@ -544,6 +547,8 @@ export class RepositoryFactory { static createPackageRepository(pkg: MonorepoPackage, module: Module): Repository { return { ASTVersion: RepositoryFactory.AST_VERSION, + ToolVersion: RepositoryFactory.TOOL_VERSION, + Path: pkg.absolutePath, id: pkg.name || path.basename(pkg.absolutePath), Modules: { [module.Name]: module }, Graph: {}, @@ -556,6 +561,8 @@ export class RepositoryFactory { static createEmptyRepository(id: string): Repository { return { ASTVersion: RepositoryFactory.AST_VERSION, + ToolVersion: RepositoryFactory.TOOL_VERSION, + Path: '', id, Modules: {}, Graph: {},