From ce9fc3516acb9fcc72dc63469c66d59da681b5bc Mon Sep 17 00:00:00 2001 From: Asara Date: Sun, 31 Dec 2023 20:08:48 -0500 Subject: [PATCH] feat: first pass at lnurlp --- lnurlp/lnurlp.go | 62 ++++++++++++++++++++++++++++++++++++++++++++++++ main.go | 14 +++++++++-- redis/redis.go | 10 ++++---- 3 files changed, 80 insertions(+), 6 deletions(-) create mode 100644 lnurlp/lnurlp.go diff --git a/lnurlp/lnurlp.go b/lnurlp/lnurlp.go new file mode 100644 index 0000000..b8abab6 --- /dev/null +++ b/lnurlp/lnurlp.go @@ -0,0 +1,62 @@ +package lnurlp + +import ( + "context" + b64 "encoding/base64" + "encoding/json" + "fmt" + "net/http" + "strings" + + "git.minhas.io/asara/well-goknown/logger" + "git.minhas.io/asara/well-goknown/redis" +) + +type ErrorMessage struct { + Error string `json:"error"` +} + +type Response struct { + Payload string `json:"request_key"` +} + +func GetLnurlpUser(w http.ResponseWriter, r *http.Request) { + ctx := context.TODO() + l := logger.Get() + + // connect to redis + redisCli := redis.LnurlpRedisConn.Client + + // search for user@domain + search := getRkey("lnurlp", "asara", r.Host) + addr, err := redisCli.Get(ctx, search).Result() + if err != nil { + l.Info().Msg(fmt.Sprintf("get %s: not found", search)) + w.WriteHeader(http.StatusNotFound) + json.NewEncoder(w).Encode(&ErrorMessage{ + Error: "username not registered", + }) + return + } + dec, err := b64.StdEncoding.DecodeString(addr) + if err != nil { + l.Error().Msg(fmt.Sprintf("get %s: unable to decode key", search)) + w.WriteHeader(http.StatusInternalServerError) + json.NewEncoder(w).Encode(&ErrorMessage{ + Error: "internal server error", + }) + return + } + + l.Info().Msg(fmt.Sprintf("get %s: found and returned", search)) + w.Header().Set("Content-Type", "application/json") + w.WriteHeader(http.StatusOK) + w.Write(dec) +} + +func getRkey(prefix string, user string, hostname string) string { + if strings.Contains(hostname, ":") { + hostname = strings.Split(hostname, ":")[0] + } + return fmt.Sprintf("%s:%s@%s", prefix, user, hostname) +} diff --git a/main.go b/main.go index 2c71dfa..ef256d3 100644 --- a/main.go +++ b/main.go @@ -4,6 +4,7 @@ import ( "net/http" "git.minhas.io/asara/well-goknown/config" + "git.minhas.io/asara/well-goknown/lnurlp" "git.minhas.io/asara/well-goknown/logger" "git.minhas.io/asara/well-goknown/matrix" "git.minhas.io/asara/well-goknown/nostr" @@ -22,6 +23,10 @@ func main() { if err != nil { l.Fatal().Msg("unable to connect to redis") } + redis.LnurlpRedisConn, err = redis.New("localhost:6379", "", redis.LnurlpKeyspace) + if err != nil { + l.Fatal().Msg("unable to connect to redis") + } // matrix endpoints l.Debug().Msg("enabling matrix server endpoint") @@ -33,12 +38,17 @@ func main() { l.Debug().Msg("enabling nostr user endpoint") http.HandleFunc("/.well-known/nostr.json", nostr.GetNostrAddr) - addr := config.GetConfig().LndAddr - if addr != "" { + // enable requesting of nostr addresses + lndAddr := config.GetConfig().LndAddr + if lndAddr != "" { l.Debug().Msg("enabling nostr request endpoint") http.HandleFunc("/request/nostr", nostr.RequestNostrAddr) } + //lnurlp endpoints + l.Debug().Msg("enabling lnurlp endpoint") + http.HandleFunc("/.well-known/lnurlp/", lnurlp.GetLnurlpUser) + // start server port := config.GetConfig().ListenAddr l.Info().Msgf("starting server on %s", port) diff --git a/redis/redis.go b/redis/redis.go index e892e60..ae474bf 100644 --- a/redis/redis.go +++ b/redis/redis.go @@ -7,8 +7,9 @@ import ( ) const ( - NostrKeyspace = iota - LndKeyspace = iota + NostrKeyspace = iota + LndKeyspace = iota + LnurlpKeyspace = iota ) type Redis struct { @@ -16,8 +17,9 @@ type Redis struct { } var ( - NostrRedisConn *Redis - LndRedisConn *Redis + NostrRedisConn *Redis + LndRedisConn *Redis + LnurlpRedisConn *Redis ) func New(address string, password string, database int) (*Redis, error) {