This tool is basically equivalent to any of the protoc-gen-*
compilers
except it is standalone, and uses JavaScript and Go
templates to produce the generated
files.
It works in the following way:
- The protocol buffer is compiled to a FileDescriptorSet.
- CamelCase functions defined in the JavaScript file are exposed to the template (same export rules as Go).
- The
FileDescriptorSet
is passed to the Go template as the top-level context.
If you want to:
- Generate custom RPC stubs from protobuf service definitions.
- Generate documentation from your protobuf file.
- ...
First, install protoc. This varies by platform, but with Homebrew it's something like:
$ brew install protobuf
Then install prototemplate:
$ go get -ldflags "-X main.TemplateDir ${GOPATH}/src/github.com/alecthomas/prototemplate/templates" github.com/alecthomas/prototemplate
The above incantation allows prototemplate to find its builtin templates.
The following example will list all messages and fields in all files while stripping any leading package names present.
Protocol buffer definition (test.proto):
package test;
// Defines what role a user has.
enum Role {
EXECUTIVE = 1;
MANAGER = 2;
EMPLOYEE = 3;
}
message User {
required string name = 1;
optional int64 age = 2 [default=18];
repeated Role roles = 3;
}
message Group {
required User owner = 1;
repeated User users = 2;
}
Javascript helper (test.js):
function StripPackage(ref) {
return ref.replace(/^.*\./, '');
}
And this template (test.got):
{{with .FileDescriptorSet}}\
{{range .File}}\
{{range .MessageType}}\
{{.Name|StripPackage}}
{{range .Field}}\
{{.Name}} = {{.Number}}
{{end}}\
{{end}}\
{{end}}\
{{end}}\
NOTE: prototemplate uses a fork of text/template
that elides newlines when a closing delimiter is immediately followed by a \
(as seen above).
And invoke the utility like so:
$ prototemplate test.proto test.got test.js
User
name = 1
age = 2
roles = 3
Group
owner = 1
users = 2
$ prototemplate --help
usage: prototemplate [<flags>] <proto> <template> [<script>]
Flags:
--help Show help.
--templates=/Users/alec/.go/src/github.com/alecthomas/prototemplate/templates
Root path to templates.
--list List builtin generators.
--builtins List builtin functions.
-I, --include=DIR List of include paths to pass to protoc.
-o, --output=FILE File to output generated template source to.
Args:
<proto> Protocol buffer definition to compile.
<template> Template file, or name of a builtin generator.
[<script>] A JavaScript file defining template helper functions.
This generator currently includes a generator for Swift, utilising the serialisation layer from the excellent protobuf-swift. This template has two goals:
- To work around a bug in the existing generated code.
- To generate more idiomatic code utilising Swift's optional types.
Usage:
$ prototemplate test.proto swift