dreinuqm992401 2018-05-11 09:58
浏览 54
已采纳

如何针对源代码和仅二进制包编译Go程序?

Background: I wrote a feature(in packageA) and don't want anyone see my code. So I installed it into .a file(packageA.a). I use it by below method:

package main  
import packageA  
func main(){  
    packageA.Run()  
}   

Then I do

go tool compile -I lib/ main.go
go tool link -o main -L main.o
It can work.

But when I do this it doesn't work.
I wrote another feature(packageB) in $GOPATH/src/project/packageB
and update main.go

// main.go
package main
import (
    "packageA"
    _ "project/packageB"
)

func main(){
    packageA.Run()
}

exec go tool compile -I lib/ main.go

but error can't find import "packageB"

my directory layout

project  
     main.go  
     lib/  
        packageA.a  
     packageB  
        xxx.go  

Wanted to know if it's good practice to do that and what would be the best way to do that? go tool compile how to import .a file and source code?

Thanks sincerely in advance.

  • 写回答

1条回答 默认 最新

  • dscdttg4389 2018-05-11 11:39
    关注

    This is a great question, and required a bit of research on my part to answer.

    I'm going to assume that your question is really just a minimal example for reproduction purposes, and that your REAL question is: "How do I compile a Go program against both source code and binary-only packages?"

    Let's walk through this step by step

    Phase 1: Generating your binary-only package.

    You probably already have the binary-only package, so you can skip this step if you want, but it's helpful for setting context.

    First, let's make sure your package names actually are correct for the folder structure. That means main.go has the following imports:

    import (
        "project/packageA"
        "project/packageB"
    )
    

    Similarly, the source code in packageB (which in your example is dependent on packageA) uses import "project/packageB"

    So what you want to have originally is a structure that looks like this:

    $GOPATH/
      src/
        project/
          main.go
          packageA
            xxx.go
          packageB
            xxx.go
    

    And you want to compile packageA so that it's just a static binary. You can do this very simply by running go install . from the packageA directory.

    You now have the following structure:

    $GOPATH/
      pkg/
        $ARCH/
          project/
            packageA.a
      src/
        project/
          main.go
          packageA
            xxx.go
          packageB
            xxx.go
    

    Phase 2: Building main.go without the Go source for packageA

    Your problem now is: how do I tell the Go compiler to look for both go source files in src and linked binaries in pkg?

    The catch here is that if you just delete packageA, the Go compiler toolchain will be confused - it assumes by default that missing Go source code means the build has failed. So what you can do as of Go 1.7 is to provide a build flag to the compiler inside packageA that says "Hey! Don't use this source code, go use the linked binary for this instead!"

    To do this, we want to replace the source code contents in packageA with a file that looks like the following:

    //go:binary-only-package
    
    package packageA
    

    Now, all we need to do to build main.go is just to use plain old go build main.go and we're all done.

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 执行 virtuoso 命令后,界面没有,cadence 启动不起来
  • ¥50 comfyui下连接animatediff节点生成视频质量非常差的原因
  • ¥20 有关区间dp的问题求解
  • ¥15 多电路系统共用电源的串扰问题
  • ¥15 slam rangenet++配置
  • ¥15 有没有研究水声通信方面的帮我改俩matlab代码
  • ¥15 ubuntu子系统密码忘记
  • ¥15 信号傅里叶变换在matlab上遇到的小问题请求帮助
  • ¥15 保护模式-系统加载-段寄存器
  • ¥15 电脑桌面设定一个区域禁止鼠标操作