selfcompile

package module
v0.0.0-...-1c1bc9e Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Oct 3, 2015 License: MIT Imports: 10 Imported by: 0

README

GoDoc License Build Status

go-selfcompile

Build self-recompiling Go binaries for embedding new plugins at runtime.

Status: v0 (no stability guarantee); this is a proof of concept, if you'd like to depend on go-selfcompile then please open an issue with your API requirements.

Check the project's upcoming milestones to get a feel for what's prioritized.

Why?

If you ship a Go-built binary to a user and want to make it easy to install third-party plugins, what do you do?

Until now, the user would need to install the Go compiler and runtime, make a stub to import the plugin, re-build the binary with the new dependency and use that.

go-selfcompile facilitates bundling the Go compiler and runtime, creating the plugin import stub, recompiling, and replacing the original binary with just a call to SelfCompile.Compile()!

How does it work?

Plugins

Let's start with plugins: We define a plugin as a package which does something inside init() { ... }. Your system would provide some way for plugins to register themselves on init, then all you'll need to do is import them and off you go.

Example of a plugin: example/aplugin

Self-compiling Binary

Next, to use go-selfcompile in your binary you'll need to do two things:

  1. Generate the bundled asset container for the Go compiler and runtime. You'll need our handy go-selfcompile binary that you can install with go get github.com/shazow/go-selfcompile/....

    Somewhere near your func main() { ... }, add a go generate stanza:

    //go:generate go-selfcompile --skip-source
    

    Now run go generate to build the bundle container.

  2. Add the SelfCompile handler in your command line flow. Check the documentation for all the options, but a bare minimum would look something like this:

     c := selfcompile.SelfCompile{
         Install:       "github.com/shazow/go-selfcompile/example/abinary",
         RestoreAssets: RestoreAssets,
     }
     // Add a plugin from the CLI call
     c.Plugin(plugin)
     // Initiate the compiling with the plugin stubs
     if err := c.Compile(); err != nil { ... }
     // Delete the temporary directory used for compiling
     if err := c.Cleanup(); err != nil { ... }
    

Example of a self-compiling binary: example/abinary

Examples

If you're trying out the built-in examples, it will look something like this:

$ example-abinary
Just doing binary things

$ example-abinary --plugin "github.com/shazow/go-selfcompile/example/aplugin"
Installing plugin: github.com/shazow/go-selfcompile/example/aplugin
[selfcompile] 2015/10/03 15:10:08 Initializing workdir: /tmp/go-selfcompile690079187
[selfcompile] 2015/10/03 15:10:21 Compiling workdir: /tmp/go-selfcompile690079187
[selfcompile] 2015/10/03 15:10:43 Replacing binary: /usr/local/bin/example-abinary
[selfcompile] 2015/10/03 15:10:44 Cleaning up: /tmp/go-selfcompile690079187
Success.

$ example-abinary
aplugin activated.
Just doing binary things

Fancy, right?

Developing

There's an end-to-end integration flow setup in the Makefile. You can run it with make example-aplugin.

Sponsors

This project was made possible thanks to Glider Labs.

License

MIT

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func SetLogger

func SetLogger(w io.Writer)

SetLogger replaces the package's log writer

Types

type RestoreAssets

type RestoreAssets func(dir, name string) error

type SelfCompile

type SelfCompile struct {

	// Main package source URL to install on recompile (if not bundled).
	Install string

	// Automatically call SelfCompile.Cleanup() after Compile() is done.
	AutoCleanup bool

	// Parameters used to setup the temporary workdir.
	Prefix string // Prefix for TempDir, used to stage recompiling assets.
	Root   string // Root of TempDir (empty will use OS default).

	// RestoreAssets is the function generated by bindata to restore the assets
	// recursively within a given directory.
	RestoreAssets RestoreAssets
	// contains filtered or unexported fields
}

SelfCompile provides controls for registering new plugins and re-compiling the binary.

func (*SelfCompile) Cleanup

func (c *SelfCompile) Cleanup() error

Cleanup will delete any temporary files created for the workdir, good idea to call this as a defer after calling setup().

func (*SelfCompile) Compile

func (c *SelfCompile) Compile() (err error)

Compile the program's source with the registered plugins.

func (*SelfCompile) Plugin

func (c *SelfCompile) Plugin(p string)

Plugin registers a plugin to self-compile. Make sure to register the full set of plugins that need to be enabled during the compile, not just new plugins.

Directories

Path Synopsis
example
go-selfcompile binary is a helper wrapper around go-bindata for embedding the necessary assets to use SelfCompile.
go-selfcompile binary is a helper wrapper around go-bindata for embedding the necessary assets to use SelfCompile.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL