Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use logRangesFlag in API, route reads based on TreeID #671

Merged
merged 5 commits into from
Mar 5, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 10 additions & 4 deletions cmd/rekor-cli/app/get.go
Original file line number Diff line number Diff line change
Expand Up @@ -112,22 +112,28 @@ var getCmd = &cobra.Command{
}
}

// Note: this UUID may be an EntryID
if uuid != "" {
params := entries.NewGetLogEntryByUUIDParams()
params.SetTimeout(viper.GetDuration("timeout"))

params.EntryUUID, err = sharding.GetUUIDFromIDString(uuid)
// NOTE: This undoes the change that let people pass in longer UUIDs without
// trouble even if their client is old, a.k.a. it will be able to use the TreeID
// (if present) for routing in the GetLogEntryByUUIDHandler
params.EntryUUID = uuid

resp, err := rekorClient.Entries.GetLogEntryByUUID(params)
if err != nil {
return nil, fmt.Errorf("unable to parse uuid: %w", err)
return nil, err
}

resp, err := rekorClient.Entries.GetLogEntryByUUID(params)
u, err := sharding.GetUUIDFromIDString(params.EntryUUID)
if err != nil {
return nil, err
}

for k, entry := range resp.Payload {
if k != params.EntryUUID {
if k != u {
continue
}

Expand Down
5 changes: 4 additions & 1 deletion cmd/rekor-cli/app/log_info.go
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ type logInfoCmdOutput struct {
TreeSize int64
RootHash string
TimestampNanos uint64
TreeID int64
}

func (l *logInfoCmdOutput) String() string {
Expand All @@ -52,7 +53,8 @@ func (l *logInfoCmdOutput) String() string {
Tree Size: %v
Root Hash: %s
Timestamp: %s
`, l.TreeSize, l.RootHash, ts)
TreeID: %v
`, l.TreeSize, l.RootHash, ts, l.TreeID)
}

// logInfoCmd represents the current information about the transparency log
Expand Down Expand Up @@ -114,6 +116,7 @@ var logInfoCmd = &cobra.Command{
TreeSize: *logInfo.TreeSize,
RootHash: *logInfo.RootHash,
TimestampNanos: sth.GetTimestamp(),
TreeID: *logInfo.TreeID,
}

oldState := state.Load(serverURL)
Expand Down
8 changes: 4 additions & 4 deletions cmd/rekor-server/app/flags.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,11 +41,11 @@ func (l *LogRangesFlag) Set(s string) error {
return fmt.Errorf("invalid range flag, expected two parts separated by an =, got %s", r)
}
lr := sharding.LogRange{}
lr.TreeID, err = strconv.ParseUint(split[0], 10, 64)
lr.TreeID, err = strconv.ParseInt(split[0], 10, 64)
if err != nil {
return err
}
lr.TreeLength, err = strconv.ParseUint(split[1], 10, 64)
lr.TreeLength, err = strconv.ParseInt(split[1], 10, 64)
if err != nil {
return err
}
Expand All @@ -55,7 +55,7 @@ func (l *LogRangesFlag) Set(s string) error {

// The last entry is special and should not have a terminating range, because this is active.
lastRangeStr := ranges[len(ranges)-1]
lastTreeID, err := strconv.ParseUint(lastRangeStr, 10, 64)
lastTreeID, err := strconv.ParseInt(lastRangeStr, 10, 64)
if err != nil {
return err
}
Expand All @@ -65,7 +65,7 @@ func (l *LogRangesFlag) Set(s string) error {
})

// Look for duplicate tree ids
TreeIDs := map[uint64]struct{}{}
TreeIDs := map[int64]struct{}{}
for _, lr := range inputRanges {
if _, ok := TreeIDs[lr.TreeID]; ok {
return fmt.Errorf("duplicate tree id: %d", lr.TreeID)
Expand Down
2 changes: 1 addition & 1 deletion cmd/rekor-server/app/flags_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ func TestLogRanges_Set(t *testing.T) {
name string
arg string
want []sharding.LogRange
active uint64
active int64
}{
{
name: "one, no length",
Expand Down
2 changes: 1 addition & 1 deletion cmd/rekor-server/app/root.go
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ func init() {
rootCmd.PersistentFlags().String("trillian_log_server.address", "127.0.0.1", "Trillian log server address")
rootCmd.PersistentFlags().Uint16("trillian_log_server.port", 8090, "Trillian log server port")
rootCmd.PersistentFlags().Uint("trillian_log_server.tlog_id", 0, "Trillian tree id")
rootCmd.PersistentFlags().Var(&logRangeMap, "trillian_log_server.log_id_ranges", "ordered list of tree ids and ranges")
rootCmd.PersistentFlags().String("trillian_log_server.log_id_ranges", "", "ordered list of tree ids and ranges")

rootCmd.PersistentFlags().String("rekor_server.hostname", "rekor.sigstore.dev", "public hostname of instance")
rootCmd.PersistentFlags().String("rekor_server.address", "127.0.0.1", "Address to bind to")
Expand Down
8 changes: 8 additions & 0 deletions cmd/rekor-server/app/serve.go
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,14 @@ var serveCmd = &cobra.Command{
server.Port = int(viper.GetUint("port"))
server.EnabledListeners = []string{"http"}

// Update logRangeMap if flag was passed in
rangeMap := viper.GetString("trillian_log_server.log_id_ranges")
if rangeMap != "" {
if err := logRangeMap.Set(rangeMap); err != nil {
log.Logger.Fatal("unable to set logRangeMap from flag: %v", err)
}
}

api.ConfigureAPI(logRangeMap.Ranges)
server.ConfigureAPI()

Expand Down
4 changes: 4 additions & 0 deletions openapi.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -581,10 +581,14 @@ definitions:
type: string
format: signedCheckpoint
description: The current signed tree head
treeID:
type: integer
description: The current treeID
required:
- rootHash
- treeSize
- signedTreeHead
- treeID

ConsistencyProof:
type: object
Expand Down
3 changes: 3 additions & 0 deletions pkg/api/api.go
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,10 @@ func NewAPI(ranges sharding.LogRanges) (*API, error) {
return nil, errors.Wrap(err, "create and init tree")
}
tLogID = t.TreeId
log.Logger.Infof("Creating new tree with ID: %v", t.TreeId)
}
// append the active treeID to the API's logRangeMap for lookups
ranges.Ranges = append(ranges.Ranges, sharding.LogRange{TreeID: tLogID})

rekorSigner, err := signer.New(ctx, viper.GetString("rekor_server.signer"))
if err != nil {
Expand Down
31 changes: 26 additions & 5 deletions pkg/api/entries.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import (
"fmt"
"net/http"
"net/url"
"strconv"

"github.com/cyberphone/json-canonicalization/go/src/webpki.org/jsoncanonicalizer"
"github.com/go-openapi/runtime/middleware"
Expand Down Expand Up @@ -117,9 +118,11 @@ func logEntryFromLeaf(ctx context.Context, signer signature.Signer, tc TrillianC
// GetLogEntryAndProofByIndexHandler returns the entry and inclusion proof for a specified log index
func GetLogEntryByIndexHandler(params entries.GetLogEntryByIndexParams) middleware.Responder {
ctx := params.HTTPRequest.Context()
tc := NewTrillianClient(ctx)
tid, resolvedIndex := api.logRanges.ResolveVirtualIndex(int(params.LogIndex))
tc := NewTrillianClientFromTreeID(ctx, tid)
log.RequestIDLogger(params.HTTPRequest).Debugf("Retrieving resolved index %v from TreeID %v", resolvedIndex, tid)

resp := tc.getLeafAndProofByIndex(params.LogIndex)
resp := tc.getLeafAndProofByIndex(resolvedIndex)
switch resp.status {
case codes.OK:
case codes.NotFound, codes.OutOfRange, codes.InvalidArgument:
Expand Down Expand Up @@ -268,12 +271,30 @@ func getEntryURL(locationURL url.URL, uuid string) strfmt.URI {
func GetLogEntryByUUIDHandler(params entries.GetLogEntryByUUIDParams) middleware.Responder {
ctx := params.HTTPRequest.Context()

entryUUID, err := sharding.GetUUIDFromIDString(params.EntryUUID)
uuid, err := sharding.GetUUIDFromIDString(params.EntryUUID)
if err != nil {
return handleRekorAPIError(params, http.StatusBadRequest, err, "")
}
hashValue, _ := hex.DecodeString(entryUUID)
tc := NewTrillianClient(params.HTTPRequest.Context())
var tid int64
tidString, err := sharding.GetTreeIDFromIDString(params.EntryUUID)
if err != nil {
// If EntryID is plain UUID, assume no sharding and use ActiveIndex. The ActiveIndex
// will == the tlog_id if a tlog_id is passed in at server startup.
if err.Error() == "cannot get treeID from plain UUID" {
tid = api.logRanges.ActiveIndex()
} else {
return handleRekorAPIError(params, http.StatusBadRequest, err, "")
}
} else {
tid, err = strconv.ParseInt(tidString, 16, 64)
if err != nil {
return handleRekorAPIError(params, http.StatusBadRequest, err, "")
}
}
hashValue, _ := hex.DecodeString(uuid)

tc := NewTrillianClientFromTreeID(params.HTTPRequest.Context(), tid)
log.RequestIDLogger(params.HTTPRequest).Debugf("Retrieving UUID %v from TreeID %v", uuid, tid)

resp := tc.getLeafAndProofByHash(hashValue)
switch resp.status {
Expand Down
2 changes: 2 additions & 0 deletions pkg/api/tlog.go
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,9 @@ func GetLogInfoHandler(params tlog.GetLogInfoParams) middleware.Responder {
RootHash: &hashString,
TreeSize: &treeSize,
SignedTreeHead: &scString,
TreeID: &tc.logID,
}

return tlog.NewGetLogInfoOK().WithPayload(&logInfo)
}

Expand Down
8 changes: 8 additions & 0 deletions pkg/api/trillian_client.go
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,14 @@ func NewTrillianClient(ctx context.Context) TrillianClient {
}
}

func NewTrillianClientFromTreeID(ctx context.Context, tid int64) TrillianClient {
return TrillianClient{
client: api.logClient,
logID: tid,
context: ctx,
}
}

type Response struct {
status codes.Code
err error
Expand Down
17 changes: 17 additions & 0 deletions pkg/generated/models/log_info.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

12 changes: 6 additions & 6 deletions pkg/sharding/ranges.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,24 +20,24 @@ type LogRanges struct {
}

type LogRange struct {
TreeID uint64
TreeLength uint64
TreeID int64
TreeLength int64
}

func (l *LogRanges) ResolveVirtualIndex(index int) (uint64, uint64) {
func (l *LogRanges) ResolveVirtualIndex(index int) (int64, int64) {
indexLeft := index
for _, l := range l.Ranges {
if indexLeft < int(l.TreeLength) {
return l.TreeID, uint64(indexLeft)
return l.TreeID, int64(indexLeft)
}
indexLeft -= int(l.TreeLength)
}

// Return the last one!
return l.Ranges[len(l.Ranges)-1].TreeID, uint64(indexLeft)
return l.Ranges[len(l.Ranges)-1].TreeID, int64(indexLeft)
}

// ActiveIndex returns the active shard index, always the last shard in the range
func (l *LogRanges) ActiveIndex() uint64 {
func (l *LogRanges) ActiveIndex() int64 {
return l.Ranges[len(l.Ranges)-1].TreeID
}
4 changes: 2 additions & 2 deletions pkg/sharding/ranges_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,8 @@ func TestLogRanges_ResolveVirtualIndex(t *testing.T) {

for _, tt := range []struct {
Index int
WantTreeID uint64
WantIndex uint64
WantTreeID int64
WantIndex int64
}{
{
Index: 3,
Expand Down
Loading