1
0
Fork 0
mirror of https://code.forgejo.org/forgejo/runner.git synced 2025-08-11 17:50:58 +00:00

wip: begin implementation of new design in proxy

This commit is contained in:
Kwonunn 2024-11-22 23:36:05 +01:00 committed by Kwonunn
parent 975364553b
commit d92f9305dc
2 changed files with 47 additions and 20 deletions

View file

@ -16,7 +16,7 @@ import (
var ( var (
ErrValidation = errors.New("validation error") ErrValidation = errors.New("validation error")
cachePrefixPath = "org:/repo:/run:/ts:/mac:/" cachePrefixPath = "/:org/:repo/:run/:ts/:mac"
) )
func (h *Handler) validateMac(params httprouter.Params) (string, error) { func (h *Handler) validateMac(params httprouter.Params) (string, error) {

View file

@ -2,6 +2,7 @@ package cacheproxy
import ( import (
"crypto/hmac" "crypto/hmac"
"crypto/rand"
"crypto/sha256" "crypto/sha256"
"encoding/hex" "encoding/hex"
"errors" "errors"
@ -33,11 +34,20 @@ type Handler struct {
cacheServerHost string cacheServerHost string
repositoryName string cacheSecret string
repositorySecret string
workflows map[string]WorkflowData
} }
func StartHandler(repoName string, targetHost string, outboundIP string, port uint16, cacheSecret string, logger logrus.FieldLogger) (*Handler, error) { type WorkflowData struct {
repositoryOwner string
repositoryName string
runNumber string
timestamp string
repositoryMAC string
}
func StartHandler(targetHost string, outboundIP string, port uint16, cacheSecret string, logger logrus.FieldLogger) (*Handler, error) {
h := &Handler{} h := &Handler{}
if logger == nil { if logger == nil {
@ -48,12 +58,7 @@ func StartHandler(repoName string, targetHost string, outboundIP string, port ui
logger = logger.WithField("module", "artifactcache") logger = logger.WithField("module", "artifactcache")
h.logger = logger h.logger = logger
h.repositoryName = repoName h.cacheSecret = cacheSecret
repoSecret, err := calculateMAC(repoName, cacheSecret)
if err != nil {
return nil, fmt.Errorf("unable to decode cacheSecret")
}
h.repositorySecret = repoSecret
if outboundIP != "" { if outboundIP != "" {
h.outboundIP = outboundIP h.outboundIP = outboundIP
@ -122,7 +127,7 @@ func (h *Handler) newReverseProxy(targetHost string) (*httputil.ReverseProxy, er
} }
func (h *Handler) injectAuth(r *httputil.ProxyRequest) { func (h *Handler) injectAuth(r *httputil.ProxyRequest) {
r.Out.SetBasicAuth(h.repositoryName, h.repositorySecret) // TODO: re-implement this one
} }
func (h *Handler) ExternalURL() string { func (h *Handler) ExternalURL() string {
@ -132,6 +137,31 @@ func (h *Handler) ExternalURL() string {
h.listener.Addr().(*net.TCPAddr).Port) h.listener.Addr().(*net.TCPAddr).Port)
} }
// Informs the proxy of a workflow that can make cache requests.
// The WorkflowData contains the information about the repository.
// The function returns the 32-bit random key which the workflow will use to identify itself.
func (h *Handler) AddWorkflow(data WorkflowData) (string, error) {
keyBytes := make([]byte, 4)
_, err := rand.Read(keyBytes)
if err != nil {
return "", errors.New("Could not generate the workflow key")
}
key := hex.EncodeToString(keyBytes)
h.workflows[key] = data
return key, nil
}
func (h *Handler) RemoveWorkflow(workflowKey string) error {
_, exists := h.workflows[workflowKey]
if !exists {
return errors.New("The workflow key was not known to the proxy")
}
delete(h.workflows, workflowKey)
return nil
}
func (h *Handler) Close() error { func (h *Handler) Close() error {
if h == nil { if h == nil {
return nil return nil
@ -157,13 +187,10 @@ func (h *Handler) Close() error {
return retErr return retErr
} }
func calculateMAC(repoName string, cacheSecret string) (string, error) { func computeMac(key, repo, run, ts string) string {
sec, err := hex.DecodeString(cacheSecret) mac := hmac.New(sha256.New, []byte(key))
if err != nil { mac.Write([]byte(repo))
return "", err mac.Write([]byte(run))
} mac.Write([]byte(ts))
mac := hmac.New(sha256.New, sec) return string(mac.Sum(nil))
mac.Write([]byte(repoName))
macBytes := mac.Sum(nil)
return hex.EncodeToString(macBytes), nil
} }