Discovery Nano the light version.

This commit is contained in:
mr
2026-04-29 07:41:00 +02:00
parent fa341494d9
commit 7f951afd41
34 changed files with 2961 additions and 1501 deletions

View File

@@ -3,6 +3,7 @@ package indexer
import (
"context"
"encoding/json"
"fmt"
"strings"
"time"
@@ -10,8 +11,8 @@ import (
"oc-discovery/daemons/node/common"
oclib "cloud.o-forge.io/core/oc-lib"
pp "github.com/libp2p/go-libp2p/core/peer"
"github.com/libp2p/go-libp2p/core/network"
pp "github.com/libp2p/go-libp2p/core/peer"
)
const TopicSearchPeer = "oc-search-peer"
@@ -46,31 +47,34 @@ func (ix *IndexerService) updateReferent(pid pp.ID, rec PeerRecord, referent boo
// searchReferenced looks up nodes in referencedNodes matching the query.
// Matches on peerID (exact), DID (exact), or name (case-insensitive contains).
func (ix *IndexerService) searchReferenced(peerID, did, name string) []common.SearchHit {
func (ix *IndexerService) searchReferenced(peerID, did, name string) []PeerRecord {
ix.referencedNodesMu.RLock()
defer ix.referencedNodesMu.RUnlock()
nameLow := strings.ToLower(name)
var hits []common.SearchHit
var hits []PeerRecord
for pid, rec := range ix.referencedNodes {
pidStr := pid.String()
matchPeerID := peerID != "" && pidStr == peerID
matchDID := did != "" && rec.DID == did
matchName := name != "" && strings.Contains(strings.ToLower(rec.Name), nameLow)
if matchPeerID || matchDID || matchName {
hits = append(hits, common.SearchHit{
PeerID: pidStr,
DID: rec.DID,
Name: rec.Name,
})
rec.ID = rec.DID
hits = append(hits, rec)
}
}
return hits
}
type SearchPeerResult struct {
QueryID string `json:"query_id"`
Records []PeerRecord `json:"records"`
}
// handleSearchPeer is the ProtocolSearchPeer handler.
// The node opens this stream, sends a SearchPeerRequest, and reads results
// as they stream in. The stream stays open until timeout or node closes it.
func (ix *IndexerService) handleSearchPeer(s network.Stream) {
fmt.Println("handleSearchPeer")
logger := oclib.GetLogger()
defer s.Reset()
@@ -78,7 +82,7 @@ func (ix *IndexerService) handleSearchPeer(s network.Stream) {
logger.Warn().Str("peer", s.Conn().RemotePeer().String()).Msg("[search] unknown peer, rejecting stream")
return
}
fmt.Println("SearchPeerRequest")
var req common.SearchPeerRequest
if err := json.NewDecoder(s).Decode(&req); err != nil || req.QueryID == "" {
return
@@ -94,7 +98,7 @@ func (ix *IndexerService) handleSearchPeer(s network.Stream) {
}()
defer streamCancel()
resultCh := make(chan []common.SearchHit, 16)
resultCh := make(chan []PeerRecord, 16)
ix.pendingSearchesMu.Lock()
ix.pendingSearches[req.QueryID] = resultCh
ix.pendingSearchesMu.Unlock()
@@ -106,9 +110,10 @@ func (ix *IndexerService) handleSearchPeer(s network.Stream) {
// Check own referencedNodes immediately.
if hits := ix.searchReferenced(req.PeerID, req.DID, req.Name); len(hits) > 0 {
fmt.Println("hits", hits)
resultCh <- hits
}
fmt.Println("publishSearchQuery")
// Broadcast search on GossipSub so other indexers can respond.
ix.publishSearchQuery(req.QueryID, req.PeerID, req.DID, req.Name)
@@ -119,7 +124,8 @@ func (ix *IndexerService) handleSearchPeer(s network.Stream) {
for {
select {
case hits := <-resultCh:
if err := enc.Encode(common.SearchPeerResult{QueryID: req.QueryID, Records: hits}); err != nil {
fmt.Println("resultCh hits", hits)
if err := enc.Encode(SearchPeerResult{QueryID: req.QueryID, Records: hits}); err != nil {
logger.Debug().Err(err).Msg("[search] stream write failed")
return
}
@@ -145,13 +151,15 @@ func (ix *IndexerService) handleSearchPeer(s network.Stream) {
// Another indexer opens this stream to deliver hits for a pending queryID.
func (ix *IndexerService) handleSearchPeerResponse(s network.Stream) {
defer s.Reset()
var result common.SearchPeerResult
fmt.Println("RECEIVED SEARCH")
var result SearchPeerResult
if err := json.NewDecoder(s).Decode(&result); err != nil || result.QueryID == "" {
return
}
ix.pendingSearchesMu.Lock()
ch := ix.pendingSearches[result.QueryID]
ix.pendingSearchesMu.Unlock()
fmt.Println("RECEIVED", result.QueryID, ix.pendingSearches[result.QueryID])
if ch != nil {
select {
case ch <- result.Records:
@@ -213,21 +221,28 @@ func (ix *IndexerService) onSearchQuery(q common.SearchQuery) {
if q.EmitterID == ix.Host.ID().String() {
return
}
fmt.Println("ON SEARCH QUERY")
hits := ix.searchReferenced(q.PeerID, q.DID, q.Name)
fmt.Println("ON SEARCH QUERY HITS", hits)
if len(hits) == 0 {
return
}
emitterID, err := pp.Decode(q.EmitterID)
if err != nil {
fmt.Println("ON SEARCH QUERY err DECODE", err)
return
}
ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
defer cancel()
s, err := ix.Host.NewStream(ctx, emitterID, common.ProtocolSearchPeerResponse)
if err != nil {
fmt.Println("ON SEARCH QUERY err NewStream", emitterID, err)
return
}
defer s.Reset()
fmt.Println("ON ", emitterID)
defer s.Close()
s.SetDeadline(time.Now().Add(5 * time.Second))
json.NewEncoder(s).Encode(common.SearchPeerResult{QueryID: q.QueryID, Records: hits})
err = json.NewEncoder(s).Encode(SearchPeerResult{QueryID: q.QueryID, Records: hits})
fmt.Println("SEARCH ERR", err)
s.CloseWrite()
}