mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-08-19 10:22:23 +00:00
swarm/storage/mru: Add version / header for future use
This commit is contained in:
parent
c3897268cc
commit
2d212ed246
6 changed files with 60 additions and 31 deletions
|
|
@ -33,7 +33,7 @@ Structure Summary:
|
|||
|
||||
Request: Resource update with signature
|
||||
ResourceUpdate: headers + data
|
||||
UpdateHeader: (placeholder, to be deleted)
|
||||
Header: Protocol version and reserved for future use placeholders
|
||||
ID: Information about how to locate a specific update
|
||||
View: Author of the update and what is updating
|
||||
Topic: Item that the updates are about
|
||||
|
|
|
|||
|
|
@ -123,13 +123,13 @@ func (h *Handler) GetContent(view *View) (storage.Address, []byte, error) {
|
|||
// just add the desired data and sign it.
|
||||
// The resulting structure can then be signed and passed to Handler.Update to be verified and sent
|
||||
func (h *Handler) NewRequest(ctx context.Context, view *View) (request *Request, err error) {
|
||||
|
||||
if view == nil {
|
||||
return nil, NewError(ErrInvalidValue, "view cannot be nil")
|
||||
}
|
||||
|
||||
now := TimestampProvider.Now().Time
|
||||
request = new(Request)
|
||||
request.Header.Version = ProtocolVersion
|
||||
|
||||
query := NewQueryLatest(view, lookup.NoClue)
|
||||
|
||||
|
|
|
|||
|
|
@ -38,6 +38,7 @@ type Request struct {
|
|||
// updateRequestJSON represents a JSON-serialized UpdateRequest
|
||||
type updateRequestJSON struct {
|
||||
ID
|
||||
ProtocolVersion uint8 `json:"protocolVersion"`
|
||||
Data string `json:"data,omitempty"`
|
||||
Signature string `json:"signature,omitempty"`
|
||||
}
|
||||
|
|
@ -58,6 +59,7 @@ func NewFirstRequest(topic Topic) *Request {
|
|||
now := TimestampProvider.Now().Time
|
||||
request.Epoch = lookup.GetFirstEpoch(now)
|
||||
request.View.Topic = topic
|
||||
request.Header.Version = ProtocolVersion
|
||||
|
||||
return request
|
||||
}
|
||||
|
|
@ -230,6 +232,7 @@ func (r *Request) AppendValues(values Values) []byte {
|
|||
func (r *Request) fromJSON(j *updateRequestJSON) error {
|
||||
|
||||
r.ID = j.ID
|
||||
r.Header.Version = j.ProtocolVersion
|
||||
|
||||
var err error
|
||||
if j.Data != "" {
|
||||
|
|
@ -274,6 +277,7 @@ func (r *Request) MarshalJSON() (rawData []byte, err error) {
|
|||
|
||||
requestJSON := &updateRequestJSON{
|
||||
ID: r.ID,
|
||||
ProtocolVersion: r.Header.Version,
|
||||
Data: dataString,
|
||||
Signature: signatureString,
|
||||
}
|
||||
|
|
|
|||
|
|
@ -79,8 +79,8 @@ func TestEncodingDecodingUpdateRequests(t *testing.T) {
|
|||
// and recover the information above. To sign an update, we need the rootAddr and the metaHash to construct
|
||||
// proof of ownership
|
||||
|
||||
const expectedSignature = "0x1cbdad7702b7d43ca983dc9f2ed87e73984288cdae6a8844e44688ee22c72080516fcd65a894b894b7b41ac780d5ce5d9fb527dc7126ea876501948d2bb6880d00"
|
||||
const expectedJSON = `{"view":{"topic":"0x6120676f6f64207265736f75726365206e616d65000000000000000000000000","user":"0x876a8936a7cd0b79ef0735ad0896c1afe278781c"},"epoch":{"level":1,"time":1000},"data":"0x5468697320686f75722773207570646174653a20537761726d2039392e3020686173206265656e2072656c656173656421"}`
|
||||
const expectedSignature = "0x32c2d2c7224e24e4d3ae6a10595fc6e945f1b3ecdf548a04d8247c240a50c9240076aa7730abad6c8a46dfea00cfb8f43b6211f02db5c4cc5ed8584cb0212a4d00"
|
||||
const expectedJSON = `{"view":{"topic":"0x6120676f6f64207265736f75726365206e616d65000000000000000000000000","user":"0x876a8936a7cd0b79ef0735ad0896c1afe278781c"},"epoch":{"time":1000,"level":1},"protocolVersion":0,"data":"0x5468697320686f75722773207570646174653a20537761726d2039392e3020686173206265656e2072656c656173656421"}`
|
||||
|
||||
//Put together an unsigned update request that we will serialize to send it to the signer.
|
||||
data := []byte("This hour's update: Swarm 99.0 has been released!")
|
||||
|
|
@ -225,7 +225,7 @@ func TestUpdateChunkSerializationErrorChecking(t *testing.T) {
|
|||
t.Fatalf("error creating update chunk:%s", err)
|
||||
}
|
||||
|
||||
compareByteSliceToExpectedHex(t, "chunk", chunk.Data(), "0x776f726c64206e657773207265706f72742c20657665727920686f7572000000876a8936a7cd0b79ef0735ad0896c1afe278781ce803000000000019416c206269656e206861636572206a616dc3a173206c652066616c7461207072656d696f376972cfb8bba6ad0c0f15e17f28bf03b6829649fddfc6b66d9de79a67f85c990982b513b09e8fd5365bde6920c8c73582ebf6f7fc85938b6d0dd285a3f18e2201")
|
||||
compareByteSliceToExpectedHex(t, "chunk", chunk.Data(), "0x0000000000000000776f726c64206e657773207265706f72742c20657665727920686f7572000000876a8936a7cd0b79ef0735ad0896c1afe278781ce803000000000019416c206269656e206861636572206a616dc3a173206c652066616c7461207072656d696f5a0ffe0bc27f207cd5b00944c8b9cee93e08b89b5ada777f123ac535189333f174a6a4ca2f43a92c4a477a49d774813c36ce8288552c58e6205b0ac35d0507eb00")
|
||||
|
||||
var recovered Request
|
||||
recovered.fromChunk(chunk.Address(), chunk.Data())
|
||||
|
|
|
|||
|
|
@ -17,22 +17,32 @@
|
|||
package mru
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"strconv"
|
||||
|
||||
"github.com/ethereum/go-ethereum/swarm/chunk"
|
||||
)
|
||||
|
||||
// ProtocolVersion defines the current version of the protocol that will be included in each update message
|
||||
const ProtocolVersion uint8 = 0
|
||||
|
||||
const headerLength = 8
|
||||
|
||||
// Header defines a update message header including a protocol version byte
|
||||
type Header struct {
|
||||
Version uint8 // Protocol version
|
||||
Padding [headerLength - 1]uint8 // reserved for future use
|
||||
}
|
||||
|
||||
// ResourceUpdate encapsulates the information sent as part of a resource update
|
||||
type ResourceUpdate struct {
|
||||
ID // metainformation about this resource update
|
||||
Header Header //
|
||||
ID // Resource update identifying information
|
||||
data []byte // actual data payload
|
||||
}
|
||||
|
||||
// Header: (see updateHeader)
|
||||
// Data:
|
||||
// data (datalength bytes)
|
||||
//
|
||||
// Minimum size is Header + 1 (minimum data length, enforced)
|
||||
const minimumUpdateDataLength = idLength + 1
|
||||
const maxUpdateDataLength = chunk.DefaultSize - signatureLength - idLength
|
||||
const minimumUpdateDataLength = idLength + headerLength + 1
|
||||
const maxUpdateDataLength = chunk.DefaultSize - signatureLength - idLength - headerLength
|
||||
|
||||
// binaryPut serializes the resource update information into the given slice
|
||||
func (r *ResourceUpdate) binaryPut(serializedData []byte) error {
|
||||
|
|
@ -50,7 +60,12 @@ func (r *ResourceUpdate) binaryPut(serializedData []byte) error {
|
|||
}
|
||||
|
||||
var cursor int
|
||||
// serialize header (see updateHeader)
|
||||
// serialize Header
|
||||
serializedData[cursor] = r.Header.Version
|
||||
copy(serializedData[cursor+1:headerLength], r.Header.Padding[:headerLength-1])
|
||||
cursor += headerLength
|
||||
|
||||
// serialize ID
|
||||
if err := r.ID.binaryPut(serializedData[cursor : cursor+idLength]); err != nil {
|
||||
return err
|
||||
}
|
||||
|
|
@ -65,7 +80,7 @@ func (r *ResourceUpdate) binaryPut(serializedData []byte) error {
|
|||
|
||||
// binaryLength returns the expected number of bytes this structure will take to encode
|
||||
func (r *ResourceUpdate) binaryLength() int {
|
||||
return idLength + len(r.data)
|
||||
return idLength + headerLength + len(r.data)
|
||||
}
|
||||
|
||||
// binaryGet populates this instance from the information contained in the passed byte slice
|
||||
|
|
@ -73,9 +88,16 @@ func (r *ResourceUpdate) binaryGet(serializedData []byte) error {
|
|||
if len(serializedData) < minimumUpdateDataLength {
|
||||
return NewErrorf(ErrNothingToReturn, "chunk less than %d bytes cannot be a resource update chunk", minimumUpdateDataLength)
|
||||
}
|
||||
dataLength := len(serializedData) - idLength
|
||||
var cursor int
|
||||
dataLength := len(serializedData) - idLength - headerLength
|
||||
// at this point we can be satisfied that we have the correct data length to read
|
||||
|
||||
var cursor int
|
||||
|
||||
// deserialize Header
|
||||
r.Header.Version = serializedData[cursor] // extract the protocol version
|
||||
copy(r.Header.Padding[:headerLength-1], serializedData[cursor+1:headerLength]) // extract the padding
|
||||
cursor += headerLength
|
||||
|
||||
if err := r.ID.binaryGet(serializedData[cursor : cursor+idLength]); err != nil {
|
||||
return err
|
||||
}
|
||||
|
|
@ -96,6 +118,8 @@ func (r *ResourceUpdate) binaryGet(serializedData []byte) error {
|
|||
// useful to parse query strings
|
||||
func (r *ResourceUpdate) FromValues(values Values, data []byte) error {
|
||||
r.data = data
|
||||
version, _ := strconv.ParseUint(values.Get("protocolVersion"), 10, 32)
|
||||
r.Header.Version = uint8(version)
|
||||
return r.ID.FromValues(values)
|
||||
}
|
||||
|
||||
|
|
@ -103,5 +127,6 @@ func (r *ResourceUpdate) FromValues(values Values, data []byte) error {
|
|||
// useful to build query strings
|
||||
func (r *ResourceUpdate) AppendValues(values Values) []byte {
|
||||
r.ID.AppendValues(values)
|
||||
values.Set("protocolVersion", fmt.Sprintf("%d", r.Header.Version))
|
||||
return r.data
|
||||
}
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ func getTestResourceUpdate() *ResourceUpdate {
|
|||
}
|
||||
|
||||
func TestResourceUpdateSerializer(t *testing.T) {
|
||||
testBinarySerializerRecovery(t, getTestResourceUpdate(), "0x776f726c64206e657773207265706f72742c20657665727920686f7572000000876a8936a7cd0b79ef0735ad0896c1afe278781ce803000000000019456c20717565206c6565206d7563686f207920616e6461206d7563686f2c207665206d7563686f20792073616265206d7563686f")
|
||||
testBinarySerializerRecovery(t, getTestResourceUpdate(), "0x0000000000000000776f726c64206e657773207265706f72742c20657665727920686f7572000000876a8936a7cd0b79ef0735ad0896c1afe278781ce803000000000019456c20717565206c6565206d7563686f207920616e6461206d7563686f2c207665206d7563686f20792073616265206d7563686f")
|
||||
}
|
||||
|
||||
func TestResourceUpdateLengthCheck(t *testing.T) {
|
||||
|
|
|
|||
Loading…
Reference in a new issue