diff --git a/CHANGELOG.md b/CHANGELOG.md
index f2be354..7eeb382 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,5 +1,10 @@
# Versions
+## 1.5.8
+
+- Ignore forwards < 1000 sats in statistics and autofees
+- Show 7 day Fee Log for individual channels
+
## 1.5.7
- AutoFee: Fix enable/disable all individual channels
diff --git a/cmd/psweb/handlers.go b/cmd/psweb/handlers.go
index db3db68..26225f6 100644
--- a/cmd/psweb/handlers.go
+++ b/cmd/psweb/handlers.go
@@ -893,8 +893,13 @@ func afHandler(w http.ResponseWriter, r *http.Request) {
var feeLog []FeeLog
- // load the last 24 hours of fee changes
- startTS := time.Now().Add(-24 * time.Hour).Unix()
+ // 24 hours fee log for all channels
+ days := 1
+ if channelId > 0 {
+ // or 7 days for a single one
+ days = 7
+ }
+ startTS := time.Now().AddDate(0, 0, -days).Unix()
for id := range ln.AutoFeeLog {
for _, event := range ln.AutoFeeLog[id] {
@@ -1147,8 +1152,11 @@ func updateHandler(w http.ResponseWriter, r *http.Request) {
swapData += `
Swap Cost: | `
swapData += formatSigned(cost) + " sats"
- swapData += ` |
Cost PPM: | `
- swapData += formatSigned(ppm)
+
+ if swap.State == "State_ClaimedPreimage" {
+ swapData += ` |
Cost PPM: | `
+ swapData += formatSigned(ppm)
+ }
}
swapData += ` |
diff --git a/cmd/psweb/ln/cln.go b/cmd/psweb/ln/cln.go
index 52fe9ab..e005893 100644
--- a/cmd/psweb/ln/cln.go
+++ b/cmd/psweb/ln/cln.go
@@ -416,7 +416,7 @@ func CacheForwards() {
forwardsLastIndex = newForwards.Forwards[n-1].CreatedIndex + 1
for _, f := range newForwards.Forwards {
chOut := ConvertClnToLndChannelId(f.OutChannel)
- if f.Status == "settled" {
+ if f.Status == "settled" && f.OutMsat > ignoreForwardsMsat {
chIn := ConvertClnToLndChannelId(f.InChannel)
forwardsIn[chIn] = append(forwardsIn[chIn], f)
forwardsOut[chOut] = append(forwardsOut[chOut], f)
@@ -465,7 +465,7 @@ func GetForwardingStats(lndChannelId uint64) *ForwardingStats {
timestamp6m := float64(now.AddDate(0, -6, 0).Unix())
for _, e := range forwardsOut[lndChannelId] {
- if e.ResolvedTime > timestamp6m {
+ if e.ResolvedTime > timestamp6m && e.OutMsat > ignoreForwardsMsat {
amountOut6m += e.OutMsat
feeMsat6m += e.FeeMsat
if e.ResolvedTime > timestamp30d {
@@ -479,7 +479,7 @@ func GetForwardingStats(lndChannelId uint64) *ForwardingStats {
}
}
for _, e := range forwardsIn[lndChannelId] {
- if e.ResolvedTime > timestamp6m {
+ if e.ResolvedTime > timestamp6m && e.OutMsat > ignoreForwardsMsat {
amountIn6m += e.OutMsat
assistedMsat6m += e.FeeMsat
if e.ResolvedTime > timestamp30d {
@@ -620,13 +620,13 @@ func GetChannelStats(lndChannelId uint64, timeStamp uint64) *ChannelStats {
timeStampF := float64(timeStamp)
for _, e := range forwardsOut[lndChannelId] {
- if e.ResolvedTime > timeStampF {
+ if e.ResolvedTime > timeStampF && e.OutMsat > ignoreForwardsMsat {
amountOut += e.OutMsat
feeMsat += e.FeeMsat
}
}
for _, e := range forwardsIn[lndChannelId] {
- if e.ResolvedTime > timeStampF {
+ if e.ResolvedTime > timeStampF && e.OutMsat > ignoreForwardsMsat {
amountIn += e.OutMsat
assistedMsat += e.FeeMsat
}
@@ -1216,7 +1216,7 @@ func PlotPPM(channelId uint64) *[]DataPoint {
for _, e := range forwardsOut[channelId] {
// ignore small forwards
- if e.OutMsat > 1000000 {
+ if e.OutMsat > ignoreForwardsMsat {
plot = append(plot, DataPoint{
TS: uint64(e.ResolvedTime),
Amount: e.OutMsat / 1000,
diff --git a/cmd/psweb/ln/common.go b/cmd/psweb/ln/common.go
index 798d679..ed7c665 100644
--- a/cmd/psweb/ln/common.go
+++ b/cmd/psweb/ln/common.go
@@ -132,6 +132,9 @@ type DataPoint struct {
Label string
}
+// ignore small forwards
+const ignoreForwardsMsat = 1_000_000
+
var (
// lightning payments from swap out initiator to receiver
SwapRebates = make(map[string]int64)
@@ -270,15 +273,16 @@ func LoadDB() {
func calculateAutoFee(channelId uint64, params *AutoFeeParams, liqPct int, oldFee int) int {
newFee := oldFee
- if liqPct > params.LowLiqPct {
+ if liqPct >= params.LowLiqPct {
// normal or high liquidity regime, check if fee can be dropped
lastUpdate := int64(0)
lastLog := LastAutoFeeLog(channelId, false)
if lastLog != nil {
lastUpdate = lastLog.TimeStamp
}
+ // see if cool-off period has passed
if lastUpdate < time.Now().Add(-time.Duration(params.CoolOffHours)*time.Hour).Unix() {
- // check the last outbound timestamp
+ // check the inactivity period
if lastForwardTS[channelId] < time.Now().AddDate(0, 0, -params.InactivityDays).Unix() {
// decrease the fee
newFee -= params.InactivityDropPPM
@@ -345,7 +349,7 @@ func moveLowLiqThreshold(channelId uint64, bump int) {
*AutoFee[channelId] = AutoFeeDefaults
}
- // do not alow exeeding high liquidity threshold
+ // do not allow reaching high liquidity threshold
if AutoFee[channelId].LowLiqPct+bump < AutoFee[channelId].ExcessPct {
AutoFee[channelId].LowLiqPct += bump
// persist to db
@@ -357,6 +361,4 @@ func moveLowLiqThreshold(channelId uint64, bump int) {
func saveSwapRabate(swapId string, rebate int64) {
// save rebate payment
SwapRebates[swapId] = rebate
- // save to db
- db.Save("Swaps", "SwapRebates", SwapRebates)
}
diff --git a/cmd/psweb/ln/lnd.go b/cmd/psweb/ln/lnd.go
index 6f83b2b..3252bb0 100644
--- a/cmd/psweb/ln/lnd.go
+++ b/cmd/psweb/ln/lnd.go
@@ -45,9 +45,6 @@ const (
// https://github.com/ElementsProject/peerswap/blob/master/peerswaprpc/server.go#L234
SwapFeeReserveLBTC = uint64(1000)
SwapFeeReserveBTC = uint64(2000)
-
- // used in outbound forwards tracking for auto fees
- forwardAmountThreshold = uint64(1000)
)
type InflightHTLC struct {
@@ -774,10 +771,9 @@ func downloadForwards(client lnrpc.LightningClient) {
// sort by in and out channels
for _, event := range res.ForwardingEvents {
- forwardsIn[event.ChanIdIn] = append(forwardsIn[event.ChanIdIn], event)
- forwardsOut[event.ChanIdOut] = append(forwardsOut[event.ChanIdOut], event)
- // record for autofees
- if event.AmtOut >= forwardAmountThreshold {
+ if event.AmtOutMsat > ignoreForwardsMsat {
+ forwardsIn[event.ChanIdIn] = append(forwardsIn[event.ChanIdIn], event)
+ forwardsOut[event.ChanIdOut] = append(forwardsOut[event.ChanIdOut], event)
lastForwardTS[event.ChanIdOut] = int64(event.TimestampNs / 1_000_000_000)
}
}
@@ -980,30 +976,31 @@ func subscribeForwards(ctx context.Context, client routerrpc.RouterClient) error
// find HTLC in queue
for _, htlc := range inflightHTLCs[htlcEvent.IncomingChannelId] {
if htlc.IncomingHtlcId == htlcEvent.IncomingHtlcId {
- // add our stored forwards
- forwardsIn[htlcEvent.IncomingChannelId] = append(forwardsIn[htlcEvent.IncomingChannelId], htlc.forwardingEvent)
- // settled htlcEvent has no Outgoing info, take from queue
- forwardsOut[htlc.OutgoingChannelId] = append(forwardsOut[htlc.OutgoingChannelId], htlc.forwardingEvent)
// store the last timestamp
lastForwardCreationTs = htlc.forwardingEvent.TimestampNs / 1_000_000_000
// delete from queue
removeInflightHTLC(htlcEvent.IncomingChannelId, htlcEvent.IncomingHtlcId)
- // record for autofees
- if htlc.forwardingEvent.AmtOut >= forwardAmountThreshold {
+ // ignore dust
+ if htlc.forwardingEvent.AmtOutMsat > ignoreForwardsMsat {
+ // add our stored forwards
+ forwardsIn[htlcEvent.IncomingChannelId] = append(forwardsIn[htlcEvent.IncomingChannelId], htlc.forwardingEvent)
+ // settled htlcEvent has no Outgoing info, take from queue
+ forwardsOut[htlc.OutgoingChannelId] = append(forwardsOut[htlc.OutgoingChannelId], htlc.forwardingEvent)
+ // TS for autofee
lastForwardTS[htlc.forwardingEvent.ChanIdOut] = int64(htlc.forwardingEvent.TimestampNs / 1_000_000_000)
- }
- // execute autofee
- client, cleanup, err := GetClient()
- if err != nil {
- return err
- }
- defer cleanup()
+ // execute autofee
+ client, cleanup, err := GetClient()
+ if err != nil {
+ return err
+ }
+ defer cleanup()
- // calculate with new balance
- applyAutoFee(client, htlc.forwardingEvent.ChanIdOut, false)
- break
+ // calculate with new balance
+ applyAutoFee(client, htlc.forwardingEvent.ChanIdOut, false)
+ break
+ }
}
}
}
@@ -1170,7 +1167,7 @@ func GetForwardingStats(channelId uint64) *ForwardingStats {
timestamp6m := uint64(now.AddDate(0, -6, 0).Unix()) * 1_000_000_000
for _, e := range forwardsOut[channelId] {
- if e.TimestampNs > timestamp6m {
+ if e.TimestampNs > timestamp6m && e.AmtOutMsat > ignoreForwardsMsat {
result.AmountOut6m += e.AmtOut
feeMsat6m += e.FeeMsat
if e.TimestampNs > timestamp30d {
@@ -1185,7 +1182,7 @@ func GetForwardingStats(channelId uint64) *ForwardingStats {
}
for _, e := range forwardsIn[channelId] {
- if e.TimestampNs > timestamp6m {
+ if e.TimestampNs > timestamp6m && e.AmtOutMsat > ignoreForwardsMsat {
result.AmountIn6m += e.AmtIn
assistedMsat6m += e.FeeMsat
if e.TimestampNs > timestamp30d {
@@ -1285,13 +1282,13 @@ func GetChannelStats(channelId uint64, timeStamp uint64) *ChannelStats {
timestampNs := timeStamp * 1_000_000_000
for _, e := range forwardsOut[channelId] {
- if e.TimestampNs > timestampNs {
+ if e.TimestampNs > timestampNs && e.AmtOutMsat > ignoreForwardsMsat {
routedOutMsat += e.AmtOutMsat
feeMsat += e.FeeMsat
}
}
for _, e := range forwardsIn[channelId] {
- if e.TimestampNs > timestampNs {
+ if e.TimestampNs > timestampNs && e.AmtOutMsat > ignoreForwardsMsat {
routedInMsat += e.AmtInMsat
assistedMsat += e.FeeMsat
}
@@ -1751,7 +1748,7 @@ func applyAutoFee(client lnrpc.LightningClient, channelId uint64, htlcFail bool)
liqPct := int(localBalance * 100 / r.Capacity)
if htlcFail {
- if liqPct <= params.LowLiqPct {
+ if liqPct < params.LowLiqPct {
// increase fee to help prevent further failed HTLCs
newFee += params.FailedBumpPPM
} else {
@@ -1888,7 +1885,7 @@ func PlotPPM(channelId uint64) *[]DataPoint {
for _, e := range forwardsOut[channelId] {
// ignore small forwards
- if e.AmtOut > 1000 {
+ if e.AmtOutMsat > ignoreForwardsMsat {
plot = append(plot, DataPoint{
TS: e.TimestampNs / 1_000_000_000,
Amount: e.AmtOut,
diff --git a/cmd/psweb/main.go b/cmd/psweb/main.go
index f714cc5..d0628c4 100644
--- a/cmd/psweb/main.go
+++ b/cmd/psweb/main.go
@@ -35,7 +35,7 @@ import (
const (
// App version tag
- version = "v1.5.7"
+ version = "v1.5.8"
)
type SwapParams struct {
@@ -220,6 +220,15 @@ func main() {
sig := <-signalChan
log.Printf("Received termination signal: %s\n", sig)
+ // persist to db
+ if db.Save("Swaps", "txFee", txFee) != nil {
+ log.Printf("Failed to persist txFee to db")
+ }
+
+ if db.Save("Swaps", "SwapRebates", ln.SwapRebates) != nil {
+ log.Printf("Failed to persist SwapRebates to db")
+ }
+
// Exit the program gracefully
os.Exit(0)
}
@@ -656,7 +665,11 @@ func convertPeersToHTMLTable(
peerTable += "" + formatWithThousandSeparators(totalFees) + ""
if totalCost > 0 {
- peerTable += " -" + formatWithThousandSeparators(totalCost) + ""
+ color := "red"
+ if config.Config.ColorScheme == "dark" {
+ color = "pink"
+ }
+ peerTable += " -" + formatWithThousandSeparators(totalCost) + ""
}
peerTable += ""
@@ -865,7 +878,11 @@ func convertOtherPeersToHTMLTable(peers []*peerswaprpc.PeerSwapPeer,
ppmCost = totalCost * 1_000_000 / totalPayments
}
if totalCost > 0 {
- peerTable += " -" + formatWithThousandSeparators(totalCost) + ""
+ color := "red"
+ if config.Config.ColorScheme == "dark" {
+ color = "pink"
+ }
+ peerTable += " -" + formatWithThousandSeparators(totalCost) + ""
}
peerTable += " | "
@@ -1237,17 +1254,6 @@ func executeAutoSwap() {
}
defer cleanup()
- res, err := ps.LiquidGetBalance(client)
- if err != nil {
- return
- }
-
- satAmount := res.GetSatAmount()
-
- if satAmount < config.Config.AutoSwapThresholdAmount {
- return
- }
-
res2, err := ps.ListActiveSwaps(client)
if err != nil {
return
@@ -1255,27 +1261,33 @@ func executeAutoSwap() {
activeSwaps := res2.GetSwaps()
- // cannot have active swaps pending
if len(activeSwaps) > 0 {
if autoSwapPending {
// save the Id
autoSwapId = activeSwaps[0].Id
}
+ // cannot have active swaps pending to initiate auto swap
return
}
- if autoSwapPending && autoSwapId != "" {
- autoSwapPending = false
+ if autoSwapPending {
disable := false
- // check the state
- res, err := ps.GetSwap(client, autoSwapId)
- if err != nil {
- log.Println("GetSwap:", err)
- disable = true
- }
-
- if res.GetSwap().State != "State_ClaimedPreimage" {
+ // no active swaps means completed
+ if autoSwapId != "" {
+ // check the state
+ res, err := ps.GetSwap(client, autoSwapId)
+ if err != nil {
+ log.Println("GetSwap:", err)
+ disable = true
+ }
+ if res.GetSwap().State != "State_ClaimedPreimage" {
+ log.Println("The last auto swap failed")
+ disable = true
+ }
+ } else {
+ // did not catch an Id is an exception
disable = true
+ log.Println("Unable to check the status of the last auto swap")
}
if disable {
@@ -1283,8 +1295,23 @@ func executeAutoSwap() {
config.Config.AutoSwapEnabled = false
config.Save()
log.Println("Automatic swap-ins Disabled")
- return
}
+
+ // stop following
+ autoSwapPending = false
+ autoSwapId = ""
+ return
+ }
+
+ res, err := ps.LiquidGetBalance(client)
+ if err != nil {
+ return
+ }
+
+ satAmount := res.GetSatAmount()
+
+ if satAmount < config.Config.AutoSwapThresholdAmount {
+ return
}
var candidate SwapParams
@@ -1378,8 +1405,6 @@ func onchainTxFee(asset, txId string) int64 {
// save to cache
if fee > 0 {
txFee[txId] = fee
- // persist to db
- db.Save("Swaps", "txFee", txFee)
}
return fee
}
diff --git a/cmd/psweb/templates/af.gohtml b/cmd/psweb/templates/af.gohtml
index a3980fd..3dd79ab 100644
--- a/cmd/psweb/templates/af.gohtml
+++ b/cmd/psweb/templates/af.gohtml
@@ -228,7 +228,7 @@
{{end}}
- 24h Fee Log
+ Fee Log
diff --git a/cmd/psweb/templates/config.gohtml b/cmd/psweb/templates/config.gohtml
index 540f2a3..115c009 100644
--- a/cmd/psweb/templates/config.gohtml
+++ b/cmd/psweb/templates/config.gohtml
@@ -246,12 +246,14 @@
- * Changing these values will restart {{if eq .Implementation "CLN"}}
+ * Changing these values will restart {{if eq .Implementation "CLN"}}
lightningd
{{else}}
peerswapd
{{end}}
- ** Changing these values will restart PSWeb
+ {{if .IsPossibleHTTPS}}
+ ** Changing these values will restart PSWeb
+ {{end}}
|