passkey

package module
v1.0.4 Latest Latest
Warning

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

Go to latest
Published: Jun 24, 2024 License: MIT Imports: 12 Imported by: 1

README

passkey authentication

A simple authentication system for machine-to-machine communication utilizing a rolling interval based authentication code derived from a shared secret using the concept of RFC 4226 OTP standards.

The passkey/cmd and passkey/example folders have working examples.

For a working client-server example go run example/server/main.go and then go run example/client/main.go in a different terminal.


  • CMD wrapper provides:
    • secret generation
    • code generation passkey generator for manual testing
      • go build cmd/pkgen.go is provided to obtain the current interval passkey
      • token can be drived and utilized with curl from the shell via curl -H token:$(pkgen AW6TJVTYMAYJXLWFW2WWJ6D3Q5B2AY25) http://localhost:1455/demo
    • install pkgen command line utility with sudo go build cmd/main.go -o /usr/local/bin/pkgen
func main() {

	// configure secret
	var secret = os.Getenv("SECRET")
	if len(secret) == 0 && len(os.Args) > 1 {
		secret = os.Args[1]
	}

	// configure interval
	var interval time.Duration
	if n := os.Getenv("INTERVAL"); len(n) > 0 {
		i, _ := strconv.Atoi(n)
		interval = time.Duration(i) * time.Second
	}
	if interval == 0 && len(os.Args) > 2 {
		i, _ := strconv.Atoi(os.Args[2])
		interval = time.Duration(i) * time.Second
	}

	// configure passkey.CMD using the secret and interval and when
	// none are supplied a random secret will be generated
	pk := new(passkey.CMD)
	pk.Interval(&interval)
	current := pk.Current(secret)
	if len(secret) == 0 {
		fmt.Fprintln(os.Stdout, pk.Show())
		return
	}

	fmt.Fprintln(os.Stdout, current)
}

  • Server wrapper provides:
    • HKey setting
    • IsValid middleware
func getRoot(w http.ResponseWriter, r *http.Request) {
	log.Println("got / request")
	w.Write([]byte("try /hello"))
}

func getHello(w http.ResponseWriter, r *http.Request) {
	log.Println("got /hello request")
	w.Write([]byte("Hello!"))
}

func main() {

	var pk passkey.NewServer((context.Background(),"PASSKEYXXBASE32XXSECRETXXEXAMPLE")

	router := http.NewServeMux()
	router.Handle("/", http.HandlerFunc(getRoot))
	router.Handle("/hello", pk.IsValid(http.HandlerFunc(getHello)))

	http.ListenAndServe(":8080", router)

}



  • Client wrapper provides:
    • Token generation
func main() {

	var timeout = time.Second * 15
	var pk passkey.NewClient(context.Background(),"PASSKEYXXBASE32XXSECRETXXEXAMPLE")

    client := &http.Client{Timeout: timeout}
    req, _ := http.NewRequest("GET", "http://localhost:8080/hello", nil)
    pk.SetHeader(req)
    resp, err := client.Do(req)
    if err != nil {
        log.Println(err)
        return
    }
    if resp.StatusCode != 200 {
        log.Println("http:", resp.StatusCode)
        return
    }

    var buf bytes.Buffer
    buf.ReadFrom(resp.Body)
    log.Println(buf.String())

}

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type CMD

type CMD struct {
	PassKey
}

CMD methods

func (*CMD) Current

func (pk *CMD) Current(secret string) string

Current returns a current valid token based on the shared secret

func (*CMD) Show

func (pk *CMD) Show() string

Show returns the base32 encoded shared secret

type Client

type Client struct {
	PassKey
}

Client methods

func NewClient

func NewClient(ctx context.Context, secret string) *Client

NewClient configurator takea a shared secret; applies defaults and will generate and emit a new secret on os.Stdout when required, and starts the interval generator

func (*Client) SetHeader

func (pk *Client) SetHeader(req *http.Request)

SetHeader sets the req.Header hKey:{current} value

type PassKey

type PassKey struct {
	// contains filtered or unexported fields
}

PassKey generats a time based authentication token set based using a shared secret and a defined interval rolling authentication code generation ttl

func (*PassKey) Interval

func (pk *PassKey) Interval(interval *time.Duration) *PassKey

Interval sets the PassKey generation interval; default time.Minute

pass nil for default

func (*PassKey) Secret

func (pk *PassKey) Secret(secret interface{}) *PassKey

Secret sets the PassKey secret; accepts

[20]byte secret
32-character base32 encoded string secret; [A..Z,2..7]

func (*PassKey) SetHeaderKey added in v1.0.4

func (pk *PassKey) SetHeaderKey(hkey *string) *PassKey

SetHeaderKey sets the http.Request header passkey name for use by the server to authenticate the clients access credential; default token

pass nil for default

func (*PassKey) Start

func (pk *PassKey) Start(ctx context.Context)

Start token generator using the secret and interval or apply default values when neither are configured; when a secret is generated the secret in use will be emited on os.Stdout

type Server

type Server struct {
	PassKey
}

Server methods

func NewServer

func NewServer(ctx context.Context, secret string) *Server
SERVER
wrapper for PassKey with addition server methods

NewServer configurator takes a shared secret; applies defaults and will generate and emit a new secret on os.Stdout when required, and starts the interval generator

func (*Server) IsValid

func (pk *Server) IsValid(next http.Handler) http.Handler

IsValid returns a http.Handler middleware for authentication; the default hKey {token} is set when necessary

Directories

Path Synopsis
example
client command
server command

Jump to

Keyboard shortcuts

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