diff --git a/api/handler/s3reader_test.go b/api/handler/s3reader_test.go new file mode 100644 index 0000000..7ecb824 --- /dev/null +++ b/api/handler/s3reader_test.go @@ -0,0 +1,57 @@ +package handler + +import ( + "bytes" + "io" + "net/http" + "testing" + "time" + + "git.frostfs.info/TrueCloudLab/frostfs-s3-gw/api/middleware" + "github.com/nspcc-dev/neo-go/pkg/crypto/keys" + "github.com/stretchr/testify/require" +) + +func TestSigV4AStreaming(t *testing.T) { + accessKeyID := "2XEbqH4M3ym7a3E3esxfZ2gRLnMwDXrCN4y1SkQg5fHa09sThVmVL3EE6xeKsyMzaqu5jPi41YCaVbnwbwCTF3bx1" + secretKey := "00637f53f842573aaa06c2164c598973cd986880987111416cf71f1619def537" + + chunk1 := "Testing with the {sdk-java}" + reqBody := bytes.NewBufferString("1b;chunk-signature=3045022100b63692a1b20759bdabd342011823427a8952df75c93174d98ad043abca8052e002201695228a91ba986171b8d0ad20856d3d94ca3614d0a90a50a531ba8e52447b9b**\r\n") + _, err := reqBody.WriteString(chunk1) + require.NoError(t, err) + _, err = reqBody.WriteString("\r\n0;chunk-signature=30440220455885a2d4e9f705256ca6b0a5a22f7f784780ccbd1c0a371e5db3059c91745b022073259dd44746cbd63261d628a04d25be5a32a974c077c5c2d83c8157fb323b9f****\r\n\r\n") + require.NoError(t, err) + + req, err := http.NewRequest("PUT", "http://localhost:8084/test/tmp", reqBody) + require.NoError(t, err) + + signature := "30440220574244c5ff5deba388c4e3b0541a42113179b6839b3e6b4212d255a118fa9089022056f7b9b72c93f67dbcd25fe9ca67950b5913fc00bb7a62bc276c21e828c0b6c7" + signingTime, err := time.Parse("20060102T150405Z", "20240904T133253Z") + require.NoError(t, err) + + key, err := keys.NewPrivateKey() + require.NoError(t, err) + + accessBox, err := newTestAccessBox(key) + require.NoError(t, err) + accessBox.Gate.SecretKey = secretKey + + ctx := middleware.SetBox(req.Context(), &middleware.Box{ + AccessBox: accessBox, + AuthHeaders: &middleware.AuthHeader{ + AccessKeyID: accessKeyID, + SignatureV4: signature, + }, + ClientTime: signingTime, + }) + req = req.WithContext(ctx) + + r, err := newSignV4aChunkedReader(req) + require.NoError(t, err) + + data, err := io.ReadAll(r) + require.NoError(t, err) + + require.Equal(t, chunk1, string(data)) +} diff --git a/api/handler/s3v4aReader.go b/api/handler/s3v4aReader.go index 75d3491..5fb189c 100644 --- a/api/handler/s3v4aReader.go +++ b/api/handler/s3v4aReader.go @@ -136,7 +136,7 @@ func (c *s3v4aChunkReader) Read(buf []byte) (num int, err error) { // Once we have read the entire chunk successfully, we verify // that the received signature is valid. - n, err := hex.Decode(signature[:], bytes.TrimSuffix(signature[:], []byte("**"))[16:]) + n, err := hex.Decode(signature[:], bytes.TrimRight(signature[:], "*")[16:]) if err != nil { c.err = errMalformedChunkedEncoding return num, c.err