start a help system for forge
This commit is contained in:
commit
8d8c0b6ceb
|
@ -0,0 +1,15 @@
|
||||||
|
# A simple, generic help repo for forge
|
||||||
|
|
||||||
|
all: goimports vet
|
||||||
|
|
||||||
|
vet:
|
||||||
|
@GO111MODULE=off go vet
|
||||||
|
@echo this go library package builds okay
|
||||||
|
|
||||||
|
# autofixes your import headers in your golang files
|
||||||
|
goimports:
|
||||||
|
goimports -w *.go
|
||||||
|
|
||||||
|
clean:
|
||||||
|
rm -f *.pb.go
|
||||||
|
-rm -f go.*
|
|
@ -0,0 +1,67 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"os"
|
||||||
|
"os/exec"
|
||||||
|
|
||||||
|
"go.wit.com/log"
|
||||||
|
)
|
||||||
|
|
||||||
|
func CheckProtoc() bool {
|
||||||
|
if checkCmdSimple("protoc") {
|
||||||
|
userInstructions()
|
||||||
|
log.Sleep(2)
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
if checkCmdSimple("protoc-gen-go") {
|
||||||
|
userInstructions()
|
||||||
|
log.Sleep(2)
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
func checkCmdSimple(cmd string) bool {
|
||||||
|
path, err := exec.LookPath(cmd)
|
||||||
|
if err != nil {
|
||||||
|
fmt.Printf("\n%s is not in the PATH\n", cmd)
|
||||||
|
return false
|
||||||
|
} else {
|
||||||
|
fmt.Printf("%s is available at %s\n", cmd, path)
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
func checkCmd(cmd string) (string, error) {
|
||||||
|
path, err := exec.LookPath(cmd)
|
||||||
|
if err != nil {
|
||||||
|
fmt.Printf("\n%s is not in the PATH\n", cmd)
|
||||||
|
} else {
|
||||||
|
fmt.Printf("%s is available at %s\n", cmd, path)
|
||||||
|
}
|
||||||
|
return path, err
|
||||||
|
}
|
||||||
|
|
||||||
|
func oldcheckCmd(cmd string) {
|
||||||
|
// path, err := exec.LookPath(cmd)
|
||||||
|
_, err := exec.LookPath(cmd)
|
||||||
|
if err != nil {
|
||||||
|
// fmt.Printf("\n%s is not in the PATH\n", cmd)
|
||||||
|
userInstructions()
|
||||||
|
log.Sleep(2)
|
||||||
|
} else {
|
||||||
|
// fmt.Printf("%s is available at %s\n", cmd, path)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// todo: figure out how to determine, in a package, what the program name is
|
||||||
|
func okExit(s string) {
|
||||||
|
log.Info("<program> ok", s)
|
||||||
|
os.Exit(0)
|
||||||
|
}
|
||||||
|
|
||||||
|
func badExit(err error) {
|
||||||
|
log.Info("<program> error:", err)
|
||||||
|
os.Exit(-1)
|
||||||
|
}
|
|
@ -0,0 +1,139 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
// auto run protoc with the correct args
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bufio"
|
||||||
|
"fmt"
|
||||||
|
"os"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/google/uuid"
|
||||||
|
"go.wit.com/log"
|
||||||
|
"golang.org/x/text/cases"
|
||||||
|
"golang.org/x/text/language"
|
||||||
|
)
|
||||||
|
|
||||||
|
/*
|
||||||
|
This verifies a .proto file conforms to the autogenpb standard
|
||||||
|
|
||||||
|
That means, for "toy.proto", there MUST exist:
|
||||||
|
|
||||||
|
message toy {
|
||||||
|
}
|
||||||
|
message toys {
|
||||||
|
}
|
||||||
|
|
||||||
|
this parses the .proto file and handles anything with `autogenpb: `
|
||||||
|
does the fruit.proto file have "message Fruits"
|
||||||
|
does it have a Uuid & valid version ?
|
||||||
|
|
||||||
|
This returns (UUID, Version, error on failure)
|
||||||
|
*/
|
||||||
|
func ValidProtobuf(filename string) (string, string, error) {
|
||||||
|
filebase := strings.TrimSuffix(filename, ".proto")
|
||||||
|
base := cases.Title(language.English, cases.NoLower).String(filebase)
|
||||||
|
pluralBase := base + "s" // to conform to autogenpb, it must have an added 's'
|
||||||
|
|
||||||
|
file, err := os.Open(filename)
|
||||||
|
if err != nil {
|
||||||
|
return "", "", err
|
||||||
|
}
|
||||||
|
defer file.Close()
|
||||||
|
scanner := bufio.NewScanner(file)
|
||||||
|
for scanner.Scan() {
|
||||||
|
line := scanner.Text()
|
||||||
|
|
||||||
|
prefix := "message " + pluralBase + " {"
|
||||||
|
if !strings.HasPrefix(line, prefix) {
|
||||||
|
// log.Info("nope", prefix, "line", line)
|
||||||
|
// nope, not this line
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
scanner.Scan()
|
||||||
|
line = scanner.Text()
|
||||||
|
fields := strings.Fields(line)
|
||||||
|
// log.Info("GOT LINE", line)
|
||||||
|
if fields[0] == "string" && fields[1] != "uuid" {
|
||||||
|
noUuid(filename)
|
||||||
|
return "", "", fmt.Errorf("proto file does not have a UUID")
|
||||||
|
}
|
||||||
|
// ok, uuid is here
|
||||||
|
UUID := line
|
||||||
|
log.Info("found UUID:", line)
|
||||||
|
|
||||||
|
scanner.Scan()
|
||||||
|
line = scanner.Text()
|
||||||
|
fields = strings.Fields(line)
|
||||||
|
// log.Info("GOT LINE", line)
|
||||||
|
if fields[0] == "string" && fields[1] != "version" {
|
||||||
|
noUuid(filename)
|
||||||
|
return "", "", fmt.Errorf("proto file does not have a version")
|
||||||
|
}
|
||||||
|
// found "version", the .proto file conforms
|
||||||
|
version := line
|
||||||
|
log.Info("found Version:", line)
|
||||||
|
return UUID, version, nil
|
||||||
|
}
|
||||||
|
// right now, noPluralMessage does os.Exit(-1)
|
||||||
|
// return "", "", noPluralMessage(filename)
|
||||||
|
return "", "", fmt.Errorf("proto file does not have message %s", pluralBase)
|
||||||
|
}
|
||||||
|
|
||||||
|
func noPluralMessage(filename string) {
|
||||||
|
filebase := strings.TrimSuffix(filename, ".proto")
|
||||||
|
base := cases.Title(language.English, cases.NoLower).String(filebase)
|
||||||
|
|
||||||
|
log.Info("")
|
||||||
|
log.Info("###########################################################################")
|
||||||
|
log.Info("Your proto file", filename, "does not contain the correct 'message' definitions")
|
||||||
|
log.Info("")
|
||||||
|
log.Info("For autogenpb to work on your file", filename, ", you must have both names exactly:")
|
||||||
|
log.Info("")
|
||||||
|
log.Printf("message %s {\n", base)
|
||||||
|
log.Info("}")
|
||||||
|
log.Printf("message %s {\n", base+"s")
|
||||||
|
log.Info("}")
|
||||||
|
log.Info("")
|
||||||
|
log.Info("###########################################################################")
|
||||||
|
badExit(fmt.Errorf("proto file error %s", filename))
|
||||||
|
}
|
||||||
|
|
||||||
|
// message Fruits { // `autogenpb:marshal` `autogenpb:mutex`
|
||||||
|
// string uuid = 1; // `autogenpb:uuid:be926ad9-f07f-484c-adf2-d96eeabf3079`
|
||||||
|
// string version = 2; // `autogenpb:version:v0.0.1`
|
||||||
|
// repeated Fruit Fruits = 3; // THIS MUST BE "Fruit" and then "Fruit" + "s"
|
||||||
|
// }
|
||||||
|
|
||||||
|
func noUuid(filename string) {
|
||||||
|
filebase := strings.TrimSuffix(filename, ".proto")
|
||||||
|
base := cases.Title(language.English, cases.NoLower).String(filebase)
|
||||||
|
id := uuid.New()
|
||||||
|
|
||||||
|
log.Info("")
|
||||||
|
log.Info("###########################################################################")
|
||||||
|
log.Info("Your proto file", filename, "is incorrect for 'message' ", base+"s")
|
||||||
|
log.Info("")
|
||||||
|
log.Info("For autogenpb to work on your file", filename, ",", base+"s must be exactly:")
|
||||||
|
log.Info("")
|
||||||
|
log.Info("message", base+"s", "{ // `autogenpb:marshal` `autogenpb:mutex`")
|
||||||
|
log.Info(" string uuid = 1; // `autogenpb:uuid:" + id.String() + "`")
|
||||||
|
log.Info(" string version = 2; // `autogenpb:version:v0.0.1`")
|
||||||
|
log.Info(" repeated", base, base+"s", " = 3; // THIS MUST BE ", base, " and then ", base+"s")
|
||||||
|
log.Info("}")
|
||||||
|
log.Info("")
|
||||||
|
log.Info("If you don't have a UUID, you can use the randomly generated one here")
|
||||||
|
log.Info("")
|
||||||
|
log.Info("###########################################################################")
|
||||||
|
badExit(fmt.Errorf("proto file error %s", filename))
|
||||||
|
}
|
||||||
|
|
||||||
|
func userInstructions() {
|
||||||
|
log.Info("This is likely because you don't have protoc and protoc-gen-go installed")
|
||||||
|
log.Info("")
|
||||||
|
log.Info("On debian, you can:")
|
||||||
|
log.Info(" apt install protobuf-compiler # for protoc")
|
||||||
|
log.Info(" apt install protoc-gen-go # for protoc-gen-go")
|
||||||
|
log.Info("")
|
||||||
|
}
|
Loading…
Reference in New Issue