Script 'mail_helper' called by obssrc
Hello community,

here is the log from the commit of package rdap for openSUSE:Factory checked in 
at 2026-09-08 16:54:07
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/rdap (Old)
 and      /work/SRC/openSUSE:Factory/.rdap.new.1265 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "rdap"

Tue Sep  8 16:54:07 2026 rev:3 rq:1376087 version:0.10.2

Changes:
--------
--- /work/SRC/openSUSE:Factory/rdap/rdap.changes        2026-07-18 
22:25:22.874872545 +0200
+++ /work/SRC/openSUSE:Factory/.rdap.new.1265/rdap.changes      2026-09-08 
16:55:09.671587714 +0200
@@ -1,0 +2,6 @@
+Fri Sep  4 11:42:05 UTC 2026 - Martin Hauke <[email protected]>
+
+- Update to version 0.10.2
+  * fix: use cached bootstrap registry files instead of downloading
+
+-------------------------------------------------------------------

Old:
----
  rdap-0.10.1.tar.gz

New:
----
  rdap-0.10.2.tar.gz

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ rdap.spec ++++++
--- /var/tmp/diff_new_pack.moVJWV/_old  2026-09-08 16:55:11.079645779 +0200
+++ /var/tmp/diff_new_pack.moVJWV/_new  2026-09-08 16:55:11.085646026 +0200
@@ -19,7 +19,7 @@
 %global provider_prefix github.com/openrdap/rdap
 %global import_path     %{provider_prefix}
 Name:           rdap
-Version:        0.10.1
+Version:        0.10.2
 Release:        0
 Summary:        RDAP command line client
 License:        MIT

++++++ rdap-0.10.1.tar.gz -> rdap-0.10.2.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/rdap-0.10.1/.github/workflows/tests.yml 
new/rdap-0.10.2/.github/workflows/tests.yml
--- old/rdap-0.10.1/.github/workflows/tests.yml 2026-07-16 23:42:12.000000000 
+0200
+++ new/rdap-0.10.2/.github/workflows/tests.yml 2026-09-04 02:59:42.000000000 
+0200
@@ -20,10 +20,9 @@
     strategy:
       fail-fast: false
       matrix:
-        # 1.25.x is the floor declared in go.mod; 1.26.x is the latest release.
-        # Testing both ensures the declared minimum stays buildable while the
-        # latest toolchain is exercised.
-        go-version: ['1.25.x', '1.26.x']
+        # 1.26.x is both the floor declared in go.mod and the latest release.
+        # Add older versions here if go.mod ever lowers its floor.
+        go-version: ['1.26.x']
 
     steps:
       - name: Checkout
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/rdap-0.10.1/bootstrap/client.go 
new/rdap-0.10.2/bootstrap/client.go
--- old/rdap-0.10.1/bootstrap/client.go 2026-07-16 23:42:12.000000000 +0200
+++ new/rdap-0.10.2/bootstrap/client.go 2026-09-04 02:59:42.000000000 +0200
@@ -81,6 +81,19 @@
 //
 //     dsr2 := b.DNS()  // Loads dns.json from disk cache.
 //
+// You can pre-populate the cache with your own copy of a Service Registry file
+// (e.g. one embedded with //go:embed), to avoid downloading it:
+//
+//     c := cache.NewMemoryCache()
+//     c.Save(bootstrap.DNS.Filename(), embeddedDNSJSON)
+//
+//     b := &bootstrap.Client{Cache: c}  // Lookup() uses the cached file.
+//
+// The file is still refreshed once it expires (see SetTimeout), falling back 
to
+// the cached copy if the download fails. Note this only works with the default
+// BaseURL: files cached for a custom bootstrap service are stored under a
+// different, unexported filename.
+//
 // This package also implements the experimental Service Provider registry. Due
 // to the experimental nature, no Service Registry file exists on data.iana.org
 // yet, additionally the filename isn't known. The current filename used is
@@ -250,8 +263,10 @@
        return json, s, nil
 }
 
+// freshenFromCache attempts to refresh the specified registry from the cache
+// if it is outdated or missing in memory.
 func (c *Client) freshenFromCache(registry RegistryType) {
-       if c.Cache.State(c.filenameFor(registry)) == cache.ShouldReload {
+       if c.shouldLoadFromCache(registry, 
c.Cache.State(c.filenameFor(registry))) {
                // Best-effort refresh; on failure the existing in-memory 
registry is kept.
                _ = c.reloadFromCache(registry)
        }
@@ -274,6 +289,13 @@
        return nil
 }
 
+// shouldLoadFromCache reports whether the cached registry file should be 
parsed
+// into memory: either the cache holds a newer copy, or nothing is in memory 
yet
+// and the cache holds an unexpired one (e.g., a caller pre-populated the 
cache).
+func (c *Client) shouldLoadFromCache(registry RegistryType, state 
cache.FileState) bool {
+       return state == cache.ShouldReload || (state == cache.Good && 
c.registries[registry] == nil)
+}
+
 func newRegistry(registry RegistryType, json []byte) (Registry, error) {
        var s Registry
        var err error
@@ -312,8 +334,10 @@
        state := c.Cache.State(c.filenameFor(registry))
        c.Verbose(fmt.Sprintf("  bootstrap: Cache state: %s: %s", 
c.filenameFor(registry), state))
 
-       var forceDownload bool
-       if state == cache.ShouldReload {
+       // An expired file is refreshed even if it's already parsed into memory.
+       forceDownload := state == cache.Expired
+
+       if c.shouldLoadFromCache(registry, state) {
                if err := c.reloadFromCache(registry); err != nil {
                        forceDownload = true
 
@@ -324,9 +348,16 @@
        if c.registries[registry] == nil || forceDownload {
                c.Verbose(fmt.Sprintf("  bootstrap: Downloading %s", 
registry.Filename()))
 
-               err := c.DownloadWithContext(question.Context(), registry)
-               if err != nil {
-                       return nil, err
+               if err := c.DownloadWithContext(question.Context(), registry); 
err != nil {
+                       // Service Registry files change rarely, so an expired 
copy still
+                       // answers most queries. Prefer one to failing the 
lookup.
+                       if c.registries[registry] == nil {
+                               if cacheErr := c.reloadFromCache(registry); 
cacheErr != nil {
+                                       return nil, err
+                               }
+                       }
+
+                       c.Verbose(fmt.Sprintf("  bootstrap: Download failed 
(%s), using expired Service Registry file", err))
                }
        } else {
                c.Verbose("  bootstrap: Using cached Service Registry file")
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/rdap-0.10.1/bootstrap/client_test.go 
new/rdap-0.10.2/bootstrap/client_test.go
--- old/rdap-0.10.1/bootstrap/client_test.go    2026-07-16 23:42:12.000000000 
+0200
+++ new/rdap-0.10.2/bootstrap/client_test.go    2026-09-04 02:59:42.000000000 
+0200
@@ -6,7 +6,10 @@
 
 import (
        "testing"
+       "time"
 
+       "github.com/jarcoal/httpmock"
+       "github.com/openrdap/rdap/bootstrap/cache"
        "github.com/openrdap/rdap/test"
 )
 
@@ -105,6 +108,116 @@
        }
 }
 
+// A pre-populated cache should be used instead of downloading. The HTTP
+// responders here all return 404, so a download attempt fails the test.
+func TestLookupUsesPrePopulatedCache(t *testing.T) {
+       test.Start(test.BootstrapHTTPError)
+       defer test.Finish()
+
+       memCache := cache.NewMemoryCache()
+       if err := memCache.Save("dns.json", 
test.LoadFile("bootstrap/dns.json")); err != nil {
+               t.Fatalf("Save() error: %s", err)
+       }
+
+       c := &Client{Cache: memCache}
+
+       downloads := httpmock.GetTotalCallCount()
+
+       answer, err := c.Lookup(&Question{RegistryType: DNS, Query: 
"example.br"})
+       if err != nil {
+               t.Fatalf("Lookup() error: %s", err)
+       }
+
+       if got := httpmock.GetTotalCallCount() - downloads; got != 0 {
+               t.Errorf("pre-populated cache triggered %d downloads, want 0", 
got)
+       }
+
+       if len(answer.URLs) != 1 || answer.URLs[0].String() != 
"https://rdap.registro.br/"; {
+               t.Errorf("Lookup() got %v, want [https://rdap.registro.br/]";, 
answer.URLs)
+       }
+
+       if c.DNS() == nil {
+               t.Error("DNS() returned nil after loading the registry from the 
cache")
+       }
+}
+
+// An expired cached file is used when the refresh download fails, rather than
+// failing the lookup.
+func TestLookupFallsBackToExpiredCache(t *testing.T) {
+       test.Start(test.BootstrapHTTPError)
+       defer test.Finish()
+
+       memCache := cache.NewMemoryCache()
+       if err := memCache.Save("dns.json", 
test.LoadFile("bootstrap/dns.json")); err != nil {
+               t.Fatalf("Save() error: %s", err)
+       }
+
+       memCache.SetTimeout(-1 * time.Second)
+
+       if got := memCache.State("dns.json"); got != cache.Expired {
+               t.Fatalf("cache state = %v, want Expired", got)
+       }
+
+       c := &Client{Cache: memCache}
+
+       downloads := httpmock.GetTotalCallCount()
+
+       answer, err := c.Lookup(&Question{RegistryType: DNS, Query: 
"example.br"})
+       if err != nil {
+               t.Fatalf("Lookup() error: %s", err)
+       }
+
+       if got := httpmock.GetTotalCallCount() - downloads; got != 1 {
+               t.Errorf("expired cache triggered %d refresh attempts, want 1", 
got)
+       }
+
+       if len(answer.URLs) != 1 || answer.URLs[0].String() != 
"https://rdap.registro.br/"; {
+               t.Errorf("Lookup() got %v, want [https://rdap.registro.br/]";, 
answer.URLs)
+       }
+}
+
+// An expired file is re-downloaded even though it's already parsed into 
memory.
+func TestLookupRefreshesExpiredCache(t *testing.T) {
+       test.Start(test.Bootstrap)
+       defer test.Finish()
+
+       c := &Client{}
+
+       if _, err := c.Lookup(&Question{RegistryType: DNS, Query: 
"example.br"}); err != nil {
+               t.Fatalf("Lookup() error: %s", err)
+       }
+
+       downloads := httpmock.GetTotalCallCount()
+
+       c.Cache.SetTimeout(-1 * time.Second)
+
+       if _, err := c.Lookup(&Question{RegistryType: DNS, Query: 
"example.br"}); err != nil {
+               t.Fatalf("Lookup() error: %s", err)
+       }
+
+       if got := httpmock.GetTotalCallCount() - downloads; got != 1 {
+               t.Errorf("expired registry triggered %d downloads, want 1", got)
+       }
+}
+
+// An unparseable cached file plus a failed download reports the download 
error,
+// rather than panicking on the unpopulated registry.
+func TestLookupWithCorruptCacheAndDownloadError(t *testing.T) {
+       test.Start(test.BootstrapHTTPError)
+       defer test.Finish()
+
+       memCache := cache.NewMemoryCache()
+       if err := memCache.Save("dns.json", []byte("{{{ not json")); err != nil 
{
+               t.Fatalf("Save() error: %s", err)
+       }
+
+       c := &Client{Cache: memCache}
+
+       if _, err := c.Lookup(&Question{RegistryType: DNS, Query: 
"example.br"}); err == nil {
+               t.Error("Lookup() unexpectedly succeeded")
+       }
+}
+
 func TestLookupWithDownloadError(t *testing.T) {
        test.Start(test.BootstrapHTTPError)
        defer test.Finish()
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/rdap-0.10.1/go.mod new/rdap-0.10.2/go.mod
--- old/rdap-0.10.1/go.mod      2026-07-16 23:42:12.000000000 +0200
+++ new/rdap-0.10.2/go.mod      2026-09-04 02:59:42.000000000 +0200
@@ -1,13 +1,13 @@
 module github.com/openrdap/rdap
 
-go 1.25.0
+go 1.26.0
 
 require (
        github.com/alecthomas/kingpin/v2 v2.4.0
        github.com/davecgh/go-spew v1.1.1
-       github.com/jarcoal/httpmock v1.4.1
+       github.com/jarcoal/httpmock v1.4.2
        github.com/mitchellh/go-homedir v1.1.0
-       golang.org/x/crypto v0.54.0
+       golang.org/x/crypto v0.56.0
 )
 
 require (
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/rdap-0.10.1/go.sum new/rdap-0.10.2/go.sum
--- old/rdap-0.10.1/go.sum      2026-07-16 23:42:12.000000000 +0200
+++ new/rdap-0.10.2/go.sum      2026-09-04 02:59:42.000000000 +0200
@@ -5,8 +5,8 @@
 github.com/davecgh/go-spew v1.1.0/go.mod 
h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
 github.com/davecgh/go-spew v1.1.1 
h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
 github.com/davecgh/go-spew v1.1.1/go.mod 
h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
-github.com/jarcoal/httpmock v1.4.1 
h1:0Ju+VCFuARfFlhVXFc2HxlcQkfB+Xq12/EotHko+x2A=
-github.com/jarcoal/httpmock v1.4.1/go.mod 
h1:ftW1xULwo+j0R0JJkJIIi7UKigZUXCLLanykgjwBXL0=
+github.com/jarcoal/httpmock v1.4.2 
h1:dKwiP/9zITCPfBLsDn3kchbSOu16JrnxtVEmL0fPRcI=
+github.com/jarcoal/httpmock v1.4.2/go.mod 
h1:ftW1xULwo+j0R0JJkJIIi7UKigZUXCLLanykgjwBXL0=
 github.com/maxatome/go-testdeep v1.14.0 
h1:rRlLv1+kI8eOI3OaBXZwb3O7xY3exRzdW5QyX48g9wI=
 github.com/maxatome/go-testdeep v1.14.0/go.mod 
h1:lPZc/HAcJMP92l7yI6TRz1aZN5URwUBUAfUNvrclaNM=
 github.com/mitchellh/go-homedir v1.1.0 
h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG+4E0Y=
@@ -24,8 +24,8 @@
 github.com/stretchr/testify v1.9.0/go.mod 
h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY=
 github.com/xhit/go-str2duration/v2 v2.1.0 
h1:lxklc02Drh6ynqX+DdPyp5pCKLUQpRT8bp8Ydu2Bstc=
 github.com/xhit/go-str2duration/v2 v2.1.0/go.mod 
h1:ohY8p+0f07DiV6Em5LKB0s2YpLtXVyJfNt1+BlmyAsU=
-golang.org/x/crypto v0.54.0 h1:YLIA59K4fiNzHzjnZt2tUJQjQtUWfWbeHBqKtk3eScw=
-golang.org/x/crypto v0.54.0/go.mod 
h1:KWL8ny2AZdGR2cWmzeHrp2azQPGogOv+HeQaVEXC2dk=
+golang.org/x/crypto v0.56.0 h1:GUh5Ii4J5jtcseSMiRqr1jXCNHoxjeV9Fmekc2oLy6Y=
+golang.org/x/crypto v0.56.0/go.mod 
h1:OMW5y6CY9l38uPLmxU6l6pwcXp1obtLo3e6gT7gQR2I=
 gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod 
h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
 gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod 
h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
 gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=

++++++ vendor.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/vendor/github.com/jarcoal/httpmock/README.md 
new/vendor/github.com/jarcoal/httpmock/README.md
--- old/vendor/github.com/jarcoal/httpmock/README.md    2026-07-16 
23:42:12.000000000 +0200
+++ new/vendor/github.com/jarcoal/httpmock/README.md    2026-09-04 
02:59:42.000000000 +0200
@@ -4,7 +4,7 @@
 
 ## Install
 
-Currently supports Go 1.16 to 1.24 and is regularly tested against tip.
+Currently supports Go 1.16 to 1.26 and is regularly tested against tip.
 
 `v1` branch has to be used instead of `master`.
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/vendor/github.com/jarcoal/httpmock/response.go 
new/vendor/github.com/jarcoal/httpmock/response.go
--- old/vendor/github.com/jarcoal/httpmock/response.go  2026-07-16 
23:42:12.000000000 +0200
+++ new/vendor/github.com/jarcoal/httpmock/response.go  2026-09-04 
02:59:42.000000000 +0200
@@ -139,8 +139,12 @@
 //       )
 func (r Responder) Delay(d time.Duration) Responder {
        return func(req *http.Request) (*http.Response, error) {
-               time.Sleep(d)
-               return r(req)
+               select {
+               case <-time.After(d):
+                       return r(req)
+               case <-req.Context().Done():
+                       return nil, req.Context().Err()
+               }
        }
 }
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/vendor/modules.txt new/vendor/modules.txt
--- old/vendor/modules.txt      2026-07-16 23:42:12.000000000 +0200
+++ new/vendor/modules.txt      2026-09-04 02:59:42.000000000 +0200
@@ -7,7 +7,7 @@
 # github.com/davecgh/go-spew v1.1.1
 ## explicit
 github.com/davecgh/go-spew/spew
-# github.com/jarcoal/httpmock v1.4.1
+# github.com/jarcoal/httpmock v1.4.2
 ## explicit; go 1.18
 github.com/jarcoal/httpmock
 github.com/jarcoal/httpmock/internal
@@ -17,7 +17,7 @@
 # github.com/xhit/go-str2duration/v2 v2.1.0
 ## explicit; go 1.13
 github.com/xhit/go-str2duration/v2
-# golang.org/x/crypto v0.54.0
-## explicit; go 1.25.0
+# golang.org/x/crypto v0.56.0
+## explicit; go 1.26.0
 golang.org/x/crypto/pkcs12
 golang.org/x/crypto/pkcs12/internal/rc2

Reply via email to