More attempt at getting this shit to work
All checks were successful
/ docker (push) Successful in 4m9s

This commit is contained in:
Melody Becker 2025-04-14 17:00:11 +02:00
parent 06e6d457da
commit 59dd8d82cf
Signed by: mstar
SSH key fingerprint: SHA256:9VAo09aaVNTWKzPW7Hq2LW+ox9OdwmTSHRoD4mlz1yI
10 changed files with 158 additions and 118 deletions

View file

@ -1,17 +1,17 @@
package webshared
import (
"crypto"
"crypto/ed25519"
"crypto/sha256"
"crypto/x509"
"encoding/base64"
"io"
"net/http"
"strings"
"time"
"git.mstar.dev/mstar/goutils/maputils"
"github.com/go-fed/httpsig"
"github.com/go-ap/httpsig"
"github.com/rs/zerolog/log"
"git.mstar.dev/mstar/linstrom/config"
@ -53,6 +53,11 @@ func SignRequest(r *http.Request, keyId string, privateKeyBytes, postBody []byte
return strings.ToLower(k), ""
}
})
// Filter for only the date, host, digest and request-target headers
mappedHeaders = maputils.FilterMap(mappedHeaders, func(k, v string) bool {
k = strings.ToLower(k)
return k == "date" || k == "host" || k == "digest" || k == "(request-target)"
})
var signedString string
var usedHeaders []string
if config.GlobalConfig.Experimental.UseEd25519Keys {
@ -80,42 +85,28 @@ func SignRequest(r *http.Request, keyId string, privateKeyBytes, postBody []byte
return nil
}
func SignWithHttpsig(r *http.Request, keyId string, privateKeyBytes, postBody []byte) error {
var privateKey crypto.PrivateKey
var preferredAlgorithm []httpsig.Algorithm
var digestMethod httpsig.DigestAlgorithm
func SignRequestWithHttpsig(
r *http.Request,
keyId string,
privateKeyBytes, postBody []byte,
) error {
keyId = config.GlobalConfig.General.GetFullPublicUrl() + "/api/activitypub/user/" + keyId
if config.GlobalConfig.Experimental.UseEd25519Keys {
log.Debug().Msg("Using ed25519")
preferredAlgorithm = []httpsig.Algorithm{httpsig.ED25519}
privateKey = ed25519.PrivateKey(privateKeyBytes)
digestMethod = httpsig.DigestSha512
key := ed25519.PrivateKey(privateKeyBytes)
signer := httpsig.NewEd25519Signer(keyId, key, nil)
if err := signer.Sign(r); err != nil {
return err
}
} else {
log.Debug().Msg("Using rsa")
preferredAlgorithm = []httpsig.Algorithm{httpsig.RSA_SHA256}
key, err := x509.ParsePKCS1PrivateKey(privateKeyBytes)
if err != nil {
return err
}
privateKey = key
digestMethod = httpsig.DigestSha256
}
headers := []string{httpsig.RequestTarget, "date", "host"}
if postBody != nil {
headers = append(headers, "digest")
}
signer, _, err := httpsig.NewSigner(
preferredAlgorithm,
digestMethod,
headers,
httpsig.Signature, time.Now().Add(time.Minute).Unix())
if err != nil {
return err
}
err = signer.SignRequest(
privateKey,
config.GlobalConfig.General.GetFullPublicUrl()+"/api/activitypub/user/"+keyId, r, postBody)
if err != nil {
return err
signer := httpsig.NewRSASHA256Signer(keyId, key, nil)
if err = signer.Sign(r); err != nil {
return err
}
// r.Header.Add("Signature", strings.TrimPrefix(r.Header.Get("Authorization"), "Signature "))
}
return nil
}
@ -125,7 +116,8 @@ func applyBodyHash(headers http.Header, body []byte) error {
return nil
}
hash := sha256.Sum256(body)
headers.Set("Digest", string(hash[:]))
based := base64.StdEncoding.EncodeToString(hash[:])
headers.Set("Digest", "SHA-256="+based)
return nil
}

View file

@ -0,0 +1,56 @@
package webshared
import (
"crypto/x509"
"io"
"net/http"
"github.com/yaronf/httpsign"
"git.mstar.dev/mstar/linstrom/config"
)
/*
Links for home:
- https://pkg.go.dev/github.com/yaronf/httpsign#Client.Do
- https://www.ietf.org/archive/id/draft-richanna-http-message-signatures-00.html
- https://github.com/mastodon/mastodon/issues/29905
- https://github.com/fedify-dev/fedify/issues/208
- https://github.com/mastodon/mastodon/issues/21429
- https://github.com/go-ap/fedbox/blob/master/httpsig.go
- https://swicg.github.io/activitypub-http-signature/
- https://datatracker.ietf.org/doc/html/rfc9421
*/
func RequestSigned(
method, target string,
body io.Reader,
keyId string,
privateKeyBytes []byte,
) (*http.Response, error) {
req, err := http.NewRequest(method, target, body)
if err != nil {
return nil, err
}
var signer *httpsign.Signer
signerFields := httpsign.Headers("@request-target", "content-digest")
if config.GlobalConfig.Experimental.UseEd25519Keys {
signer, err = httpsign.NewEd25519Signer(
privateKeyBytes,
httpsign.NewSignConfig(),
signerFields,
)
} else {
key, err := x509.ParsePKCS1PrivateKey(privateKeyBytes)
if err != nil {
return nil, err
}
signer, err = httpsign.NewRSASigner(*key, httpsign.NewSignConfig(), signerFields)
}
client := httpsign.NewClient(
RequestClient,
httpsign.NewClientConfig().SetSigner(signer).SetSignatureName("sig1"),
)
res, err := client.Do(req)
return res, err
}