feat(proto): update RelayInfo leases to use structured Lease objects
- Changed leases field in RelayInfo from repeated string to repeated Lease in protobuf definition - Regenerated Go protobuf code to reflect the new structure - Fixed link generation in view.go to use lease.Name instead of identityID for proper URL construction with structured lease data
lemon-mint committed
Nov 4, 2025 at 00:17 UTC
cdd0fd6806cab50911eb6feacfeff77cb944c2fd
7 files changed
+103
-54
cmd/relay-server/view.go
+1
-1
@@ -348,7 +348,7 @@ func convertLeaseEntriesToRows(serv *portal.RelayServer) []leaseRow {
348
dnsLabel = dnsLabel[:8] + "..."
349
}
350
351
- link := fmt.Sprintf("https://%s.portal.gosuda.org/", identityID)
351
+ link := fmt.Sprintf("https://%s.portal.gosuda.org/", lease.Name)
352
353
row := leaseRow{
354
Peer: identityID,
cmd/webclient/main_js.go
+5
@@ -33,6 +33,11 @@ var (
33
)
34
35
var rdDialer = func(ctx context.Context, network, address string) (net.Conn, error) {
36
+ lease, err := rdClient.LookUpName(address)
37
+ if err == nil && lease != nil {
38
+ address = lease.Identity.Id
39
+ }
40
+
41
address = strings.TrimSuffix(address, ":80")
42
address = strings.TrimSuffix(address, ":443")
43
cred := sdk.NewCredential()
portal/core/proto/rdverb/rdverb.pb.go
+19
-18
@@ -203,7 +203,7 @@ type RelayInfo struct {
203
state protoimpl.MessageState `protogen:"open.v1"`
204
Identity *rdsec.Identity `protobuf:"bytes,1,opt,name=identity,proto3" json:"identity,omitempty"`
205
Address []string `protobuf:"bytes,2,rep,name=address,proto3" json:"address,omitempty"`
206
- Leases []string `protobuf:"bytes,3,rep,name=leases,proto3" json:"leases,omitempty"`
206
+ Leases []*Lease `protobuf:"bytes,3,rep,name=leases,proto3" json:"leases,omitempty"`
207
unknownFields protoimpl.UnknownFields
208
sizeCache protoimpl.SizeCache
209
}
@@ -252,7 +252,7 @@ func (x *RelayInfo) GetAddress() []string {
252
return nil
253
}
254
255
-func (x *RelayInfo) GetLeases() []string {
255
+func (x *RelayInfo) GetLeases() []*Lease {
256
if x != nil {
257
return x.Leases
258
}
@@ -718,11 +718,11 @@ const file_portal_core_proto_rdverb_rdverb_proto_rawDesc = "" +
718
"%portal/core/proto/rdverb/rdverb.proto\x12\x06rdverb\x1a#portal/core/proto/rdsec/rdsec.proto\"J\n" +
719
"\x06Packet\x12&\n" +
720
"\x04type\x18\x01 \x01(\x0e2\x12.rdverb.PacketTypeR\x04type\x12\x18\n" +
721
- "\apayload\x18\x02 \x01(\fR\apayload\"j\n" +
721
+ "\apayload\x18\x02 \x01(\fR\apayload\"y\n" +
722
"\tRelayInfo\x12+\n" +
723
"\bidentity\x18\x01 \x01(\v2\x0f.rdsec.IdentityR\bidentity\x12\x18\n" +
724
- "\aaddress\x18\x02 \x03(\tR\aaddress\x12\x16\n" +
725
- "\x06leases\x18\x03 \x03(\tR\x06leases\"\x12\n" +
724
+ "\aaddress\x18\x02 \x03(\tR\aaddress\x12%\n" +
725
+ "\x06leases\x18\x03 \x03(\v2\r.rdverb.LeaseR\x06leases\"\x12\n" +
726
"\x10RelayInfoRequest\"E\n" +
727
"\x11RelayInfoResponse\x120\n" +
728
"\n" +
@@ -803,19 +803,20 @@ var file_portal_core_proto_rdverb_rdverb_proto_goTypes = []any{
803
var file_portal_core_proto_rdverb_rdverb_proto_depIdxs = []int32{
804
0, // 0: rdverb.Packet.type:type_name -> rdverb.PacketType
805
13, // 1: rdverb.RelayInfo.identity:type_name -> rdsec.Identity
806
- 3, // 2: rdverb.RelayInfoResponse.relay_info:type_name -> rdverb.RelayInfo
807
- 13, // 3: rdverb.Lease.identity:type_name -> rdsec.Identity
808
- 6, // 4: rdverb.LeaseUpdateRequest.lease:type_name -> rdverb.Lease
809
- 1, // 5: rdverb.LeaseUpdateResponse.code:type_name -> rdverb.ResponseCode
810
- 13, // 6: rdverb.LeaseDeleteRequest.identity:type_name -> rdsec.Identity
811
- 1, // 7: rdverb.LeaseDeleteResponse.code:type_name -> rdverb.ResponseCode
812
- 13, // 8: rdverb.ConnectionRequest.client_identity:type_name -> rdsec.Identity
813
- 1, // 9: rdverb.ConnectionResponse.code:type_name -> rdverb.ResponseCode
814
- 10, // [10:10] is the sub-list for method output_type
815
- 10, // [10:10] is the sub-list for method input_type
816
- 10, // [10:10] is the sub-list for extension type_name
817
- 10, // [10:10] is the sub-list for extension extendee
818
- 0, // [0:10] is the sub-list for field type_name
806
+ 6, // 2: rdverb.RelayInfo.leases:type_name -> rdverb.Lease
807
+ 3, // 3: rdverb.RelayInfoResponse.relay_info:type_name -> rdverb.RelayInfo
808
+ 13, // 4: rdverb.Lease.identity:type_name -> rdsec.Identity
809
+ 6, // 5: rdverb.LeaseUpdateRequest.lease:type_name -> rdverb.Lease
810
+ 1, // 6: rdverb.LeaseUpdateResponse.code:type_name -> rdverb.ResponseCode
811
+ 13, // 7: rdverb.LeaseDeleteRequest.identity:type_name -> rdsec.Identity
812
+ 1, // 8: rdverb.LeaseDeleteResponse.code:type_name -> rdverb.ResponseCode
813
+ 13, // 9: rdverb.ConnectionRequest.client_identity:type_name -> rdsec.Identity
814
+ 1, // 10: rdverb.ConnectionResponse.code:type_name -> rdverb.ResponseCode
815
+ 11, // [11:11] is the sub-list for method output_type
816
+ 11, // [11:11] is the sub-list for method input_type
817
+ 11, // [11:11] is the sub-list for extension type_name
818
+ 11, // [11:11] is the sub-list for extension extendee
819
+ 0, // [0:11] is the sub-list for field type_name
820
}
821
822
func init() { file_portal_core_proto_rdverb_rdverb_proto_init() }
portal/core/proto/rdverb/rdverb.proto
+1
-1
@@ -40,7 +40,7 @@ message Packet {
40
message RelayInfo {
41
rdsec.Identity identity = 1;
42
repeated string address = 2;
43
- repeated string leases = 3;
43
+ repeated Lease leases = 3;
44
}
45
46
message RelayInfoRequest {}
portal/core/proto/rdverb/rdverb_vtproto.pb.go
+43
-27
@@ -61,8 +61,10 @@ func (m *RelayInfo) CloneVT() *RelayInfo {
61
r.Address = tmpContainer
62
}
63
if rhs := m.Leases; rhs != nil {
64
- tmpContainer := make([]string, len(rhs))
65
- copy(tmpContainer, rhs)
64
+ tmpContainer := make([]*Lease, len(rhs))
65
+ for k, v := range rhs {
66
+ tmpContainer[k] = v.CloneVT()
67
+ }
68
r.Leases = tmpContainer
69
}
70
if len(m.unknownFields) > 0 {
@@ -315,8 +317,16 @@ func (this *RelayInfo) EqualVT(that *RelayInfo) bool {
317
}
318
for i, vx := range this.Leases {
319
vy := that.Leases[i]
318
- if vx != vy {
319
- return false
320
+ if p, q := vx, vy; p != q {
321
+ if p == nil {
322
+ p = &Lease{}
323
+ }
324
+ if q == nil {
325
+ q = &Lease{}
326
+ }
327
+ if !p.EqualVT(q) {
328
+ return false
329
+ }
330
}
331
}
332
return string(this.unknownFields) == string(that.unknownFields)
@@ -616,9 +626,12 @@ func (m *RelayInfo) MarshalToSizedBufferVT(dAtA []byte) (int, error) {
626
}
627
if len(m.Leases) > 0 {
628
for iNdEx := len(m.Leases) - 1; iNdEx >= 0; iNdEx-- {
619
- i -= len(m.Leases[iNdEx])
620
- copy(dAtA[i:], m.Leases[iNdEx])
621
- i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Leases[iNdEx])))
629
+ size, err := m.Leases[iNdEx].MarshalToSizedBufferVT(dAtA[:i])
630
+ if err != nil {
631
+ return 0, err
632
+ }
633
+ i -= size
634
+ i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
635
i--
636
dAtA[i] = 0x1a
637
}
@@ -1184,9 +1197,12 @@ func (m *RelayInfo) MarshalToSizedBufferVTStrict(dAtA []byte) (int, error) {
1197
}
1198
if len(m.Leases) > 0 {
1199
for iNdEx := len(m.Leases) - 1; iNdEx >= 0; iNdEx-- {
1187
- i -= len(m.Leases[iNdEx])
1188
- copy(dAtA[i:], m.Leases[iNdEx])
1189
- i = protohelpers.EncodeVarint(dAtA, i, uint64(len(m.Leases[iNdEx])))
1200
+ size, err := m.Leases[iNdEx].MarshalToSizedBufferVTStrict(dAtA[:i])
1201
+ if err != nil {
1202
+ return 0, err
1203
+ }
1204
+ i -= size
1205
+ i = protohelpers.EncodeVarint(dAtA, i, uint64(size))
1206
i--
1207
dAtA[i] = 0x1a
1208
}
@@ -1715,8 +1731,8 @@ func (m *RelayInfo) SizeVT() (n int) {
1731
}
1732
}
1733
if len(m.Leases) > 0 {
1718
- for _, s := range m.Leases {
1719
- l = len(s)
1734
+ for _, e := range m.Leases {
1735
+ l = e.SizeVT()
1736
n += 1 + l + protohelpers.SizeOfVarint(uint64(l))
1737
}
1738
}
@@ -2105,7 +2121,7 @@ func (m *RelayInfo) UnmarshalVT(dAtA []byte) error {
2121
if wireType != 2 {
2122
return fmt.Errorf("proto: wrong wireType = %d for field Leases", wireType)
2123
}
2108
- var stringLen uint64
2124
+ var msglen int
2125
for shift := uint(0); ; shift += 7 {
2126
if shift >= 64 {
2127
return protohelpers.ErrIntOverflow
@@ -2115,23 +2131,25 @@ func (m *RelayInfo) UnmarshalVT(dAtA []byte) error {
2131
}
2132
b := dAtA[iNdEx]
2133
iNdEx++
2118
- stringLen |= uint64(b&0x7F) << shift
2134
+ msglen |= int(b&0x7F) << shift
2135
if b < 0x80 {
2136
break
2137
}
2138
}
2123
- intStringLen := int(stringLen)
2124
- if intStringLen < 0 {
2139
+ if msglen < 0 {
2140
return protohelpers.ErrInvalidLength
2141
}
2127
- postIndex := iNdEx + intStringLen
2142
+ postIndex := iNdEx + msglen
2143
if postIndex < 0 {
2144
return protohelpers.ErrInvalidLength
2145
}
2146
if postIndex > l {
2147
return io.ErrUnexpectedEOF
2148
}
2134
- m.Leases = append(m.Leases, string(dAtA[iNdEx:postIndex]))
2149
+ m.Leases = append(m.Leases, &Lease{})
2150
+ if err := m.Leases[len(m.Leases)-1].UnmarshalVT(dAtA[iNdEx:postIndex]); err != nil {
2151
+ return err
2152
+ }
2153
iNdEx = postIndex
2154
default:
2155
iNdEx = preIndex
@@ -3310,7 +3328,7 @@ func (m *RelayInfo) UnmarshalVTUnsafe(dAtA []byte) error {
3328
if wireType != 2 {
3329
return fmt.Errorf("proto: wrong wireType = %d for field Leases", wireType)
3330
}
3313
- var stringLen uint64
3331
+ var msglen int
3332
for shift := uint(0); ; shift += 7 {
3333
if shift >= 64 {
3334
return protohelpers.ErrIntOverflow
@@ -3320,27 +3338,25 @@ func (m *RelayInfo) UnmarshalVTUnsafe(dAtA []byte) error {
3338
}
3339
b := dAtA[iNdEx]
3340
iNdEx++
3323
- stringLen |= uint64(b&0x7F) << shift
3341
+ msglen |= int(b&0x7F) << shift
3342
if b < 0x80 {
3343
break
3344
}
3345
}
3328
- intStringLen := int(stringLen)
3329
- if intStringLen < 0 {
3346
+ if msglen < 0 {
3347
return protohelpers.ErrInvalidLength
3348
}
3332
- postIndex := iNdEx + intStringLen
3349
+ postIndex := iNdEx + msglen
3350
if postIndex < 0 {
3351
return protohelpers.ErrInvalidLength
3352
}
3353
if postIndex > l {
3354
return io.ErrUnexpectedEOF
3355
}
3339
- var stringValue string
3340
- if intStringLen > 0 {
3341
- stringValue = unsafe.String(&dAtA[iNdEx], intStringLen)
3356
+ m.Leases = append(m.Leases, &Lease{})
3357
+ if err := m.Leases[len(m.Leases)-1].UnmarshalVTUnsafe(dAtA[iNdEx:postIndex]); err != nil {
3358
+ return err
3359
}
3343
- m.Leases = append(m.Leases, stringValue)
3360
iNdEx = postIndex
3361
default:
3362
iNdEx = preIndex
portal/relay.go
+1
-1
@@ -250,7 +250,7 @@ func (g *RelayServer) relayInfo() *rdverb.RelayInfo {
250
return &rdverb.RelayInfo{
251
Identity: g.identity,
252
Address: g.address,
253
- Leases: leaseIds,
253
+ Leases: g.leaseManager.GetAllLeases(),
254
}
255
}
256
sdk/sdk.go
+33
-6
@@ -7,7 +7,7 @@ import (
7
"io"
8
"net"
9
"regexp"
10
- "slices"
10
+ "strings"
11
"sync"
12
"time"
13
@@ -262,11 +262,14 @@ func (g *RDClient) Dial(cred *cryptoops.Credential, leaseID string, alpn string)
262
return
263
}
264
265
- if slices.Contains(info.Leases, leaseID) {
266
- log.Debug().Str("relay", relay.addr).Str("lease_id", leaseID).Msg("[SDK] Found lease on relay")
267
- availableRelaysMu.Lock()
268
- availableRelays = append(availableRelays, relay)
269
- availableRelaysMu.Unlock()
265
+ for _, lease := range info.Leases {
266
+ if lease.Identity.Id == leaseID {
267
+ log.Debug().Str("relay", relay.addr).Str("lease_id", leaseID).Msg("[SDK] Found lease on relay")
268
+ availableRelaysMu.Lock()
269
+ availableRelays = append(availableRelays, relay)
270
+ availableRelaysMu.Unlock()
271
+ break
272
+ }
273
}
274
}(relay)
275
}
@@ -780,3 +783,27 @@ func (g *RDClient) GetRelays() []string {
783
784
return relays
785
}
786
+
787
+func (g *RDClient) LookUpName(name string) (*rdverb.Lease, error) {
788
+ var relays []*rdRelay
789
+
790
+ g.mu.Lock()
791
+ for _, server := range g.relays {
792
+ relays = append(relays, server)
793
+ }
794
+ g.mu.Unlock()
795
+
796
+ for _, relay := range relays {
797
+ info, err := relay.client.GetRelayInfo()
798
+ if err != nil {
799
+ continue
800
+ }
801
+
802
+ for _, lease := range info.Leases {
803
+ if strings.EqualFold(lease.Name, name) {
804
+ return lease, nil
805
+ }
806
+ }
807
+ }
808
+ return nil, ErrNoAvailableRelay
809
+}