This commit is contained in:
parent
e3a97170a9
commit
f4e876a4b1
10 changed files with 191 additions and 20 deletions
|
@ -28,6 +28,7 @@ func New(addr string) *Server {
|
|||
handler.HandleFunc("POST /post-as", postAs)
|
||||
handler.HandleFunc("GET /notes-for", notesFrom)
|
||||
handler.HandleFunc("GET /import", issueUserImport)
|
||||
handler.HandleFunc("GET /keys-for", returnKeypair)
|
||||
web := http.Server{
|
||||
Addr: addr,
|
||||
Handler: webutils.ChainMiddlewares(
|
||||
|
|
|
@ -4,6 +4,8 @@ import (
|
|||
"crypto/rand"
|
||||
"database/sql"
|
||||
"encoding/json"
|
||||
"encoding/pem"
|
||||
"fmt"
|
||||
"net/http"
|
||||
"strconv"
|
||||
"time"
|
||||
|
@ -173,6 +175,33 @@ func deleteUser(w http.ResponseWriter, r *http.Request) {
|
|||
w.WriteHeader(http.StatusOK)
|
||||
}
|
||||
|
||||
func returnKeypair(w http.ResponseWriter, r *http.Request) {
|
||||
id := r.FormValue("id")
|
||||
user, err := dbgen.User.Where(dbgen.User.ID.Eq(id)).First()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
err = shared.SanityCheckX509dRsaKeys(user.PublicKeyRsa, user.PrivateKeyRsa)
|
||||
if err != nil {
|
||||
hlog.FromRequest(r).Error().Err(err).Msg("Sanity check failed")
|
||||
}
|
||||
privKeyBlock := pem.Block{
|
||||
Type: "RSA PRIVATE KEY",
|
||||
Bytes: user.PrivateKeyRsa,
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
hlog.FromRequest(r).Error().Err(err).Msg("Sanity check failed")
|
||||
}
|
||||
privKeyPem := pem.EncodeToMemory(&privKeyBlock)
|
||||
pubKeyPen := []byte(shared.KeyBytesToPem(user.PublicKeyRsa))
|
||||
err = shared.SanityCheckPemdRsaKeys(pubKeyPen, privKeyPem)
|
||||
if err != nil {
|
||||
hlog.FromRequest(r).Error().Err(err).Msg("Pem Sanity check failed")
|
||||
}
|
||||
fmt.Fprintf(w, "%s\n\n%s", privKeyPem, pubKeyPen)
|
||||
}
|
||||
|
||||
func issueUserImport(w http.ResponseWriter, r *http.Request) {
|
||||
target := r.FormValue("target")
|
||||
_, err := activitypub.ImportRemoteAccount(target)
|
||||
|
|
|
@ -14,6 +14,7 @@ import (
|
|||
|
||||
"git.mstar.dev/mstar/linstrom/activitypub"
|
||||
"git.mstar.dev/mstar/linstrom/config"
|
||||
"git.mstar.dev/mstar/linstrom/shared"
|
||||
"git.mstar.dev/mstar/linstrom/storage-new"
|
||||
"git.mstar.dev/mstar/linstrom/storage-new/dbgen"
|
||||
"git.mstar.dev/mstar/linstrom/storage-new/models"
|
||||
|
@ -71,9 +72,9 @@ func users(w http.ResponseWriter, r *http.Request) {
|
|||
apUrl := userIdToApUrl(user.ID)
|
||||
var keyBytes string
|
||||
if config.GlobalConfig.Experimental.UseEd25519Keys {
|
||||
keyBytes = keyBytesToPem(user.PublicKeyEd)
|
||||
keyBytes = shared.KeyBytesToPem(user.PublicKeyEd)
|
||||
} else {
|
||||
keyBytes = keyBytesToPem(user.PublicKeyRsa)
|
||||
keyBytes = shared.KeyBytesToPem(user.PublicKeyRsa)
|
||||
}
|
||||
data := Outbound{
|
||||
Context: activitypub.BaseLdContext,
|
||||
|
|
|
@ -1,7 +1,6 @@
|
|||
package activitypub
|
||||
|
||||
import (
|
||||
"encoding/pem"
|
||||
"fmt"
|
||||
|
||||
"git.mstar.dev/mstar/linstrom/config"
|
||||
|
@ -14,12 +13,3 @@ func userIdToApUrl(id string) string {
|
|||
id,
|
||||
)
|
||||
}
|
||||
|
||||
func keyBytesToPem(bytes []byte) string {
|
||||
block := pem.Block{
|
||||
Type: "PUBLIC KEY",
|
||||
Headers: nil,
|
||||
Bytes: bytes,
|
||||
}
|
||||
return string(pem.EncodeToMemory(&block))
|
||||
}
|
||||
|
|
|
@ -1,13 +1,17 @@
|
|||
package webshared
|
||||
|
||||
import (
|
||||
"crypto"
|
||||
"crypto/ed25519"
|
||||
"crypto/sha256"
|
||||
"crypto/x509"
|
||||
"io"
|
||||
"net/http"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"git.mstar.dev/mstar/goutils/maputils"
|
||||
"github.com/go-fed/httpsig"
|
||||
"github.com/rs/zerolog/log"
|
||||
|
||||
"git.mstar.dev/mstar/linstrom/config"
|
||||
|
@ -66,7 +70,6 @@ func SignRequest(r *http.Request, keyId string, privateKeyBytes, postBody []byte
|
|||
signedString = tmp
|
||||
usedHeaders = tmp2
|
||||
}
|
||||
log.Debug().Str("string-to-sign", signedString).Any("headers", mappedHeaders).Send()
|
||||
signature := CreateSignatureHeaderContent(
|
||||
keyId,
|
||||
signedString,
|
||||
|
@ -77,6 +80,46 @@ 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
|
||||
if config.GlobalConfig.Experimental.UseEd25519Keys {
|
||||
log.Debug().Msg("Using ed25519")
|
||||
preferredAlgorithm = []httpsig.Algorithm{httpsig.ED25519}
|
||||
privateKey = ed25519.PrivateKey(privateKeyBytes)
|
||||
digestMethod = httpsig.DigestSha512
|
||||
} 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
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func applyBodyHash(headers http.Header, body []byte) error {
|
||||
if body == nil {
|
||||
return nil
|
||||
|
|
|
@ -46,13 +46,14 @@ func genPreSignatureString(method, target string, headers map[string]string) (st
|
|||
dataBuilder.WriteString("(request-target): ")
|
||||
dataBuilder.WriteString(strings.ToLower(method) + " ")
|
||||
dataBuilder.WriteString(target + "\n")
|
||||
dataBuilder.WriteString("algorithm: rsa-sha256\n")
|
||||
usedHeaders := []string{"(request-target)", "algorithm"}
|
||||
// dataBuilder.WriteString("algorithm: rsa-sha256\n")
|
||||
// usedHeaders := []string{"(request-target)", "algorithm"}
|
||||
usedHeaders := []string{"(request-target)"}
|
||||
for k, v := range headers {
|
||||
dataBuilder.WriteString(k + ": " + v + "\n")
|
||||
usedHeaders = append(usedHeaders, k)
|
||||
}
|
||||
tmp := dataBuilder.String()
|
||||
tmp := strings.TrimSuffix(dataBuilder.String(), "\n")
|
||||
log.Debug().Str("Raw signature string", tmp).Send()
|
||||
return tmp, usedHeaders
|
||||
}
|
||||
|
@ -73,7 +74,11 @@ func CreateSignatureHeaderContent(userId string, hash string, headerNames ...str
|
|||
builder.WriteRune(' ')
|
||||
}
|
||||
}
|
||||
builder.WriteString("\",algorithm=\"rsa-sha256\",signature=\"")
|
||||
if config.GlobalConfig.Experimental.UseEd25519Keys {
|
||||
builder.WriteString("\",algorithm=\"ed-sha512\",signature=\"")
|
||||
} else {
|
||||
builder.WriteString("\",algorithm=\"rsa-sha256\",signature=\"")
|
||||
}
|
||||
builder.WriteString(hash)
|
||||
builder.WriteRune('"')
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue