github.com/mika/distribution@v2.2.2-0.20160108133430-a75790e3d8e0+incompatible/registry/client/blob_writer_test.go (about) 1 package client 2 3 import ( 4 "bytes" 5 "fmt" 6 "net/http" 7 "testing" 8 9 "github.com/docker/distribution" 10 "github.com/docker/distribution/registry/api/errcode" 11 "github.com/docker/distribution/registry/api/v2" 12 "github.com/docker/distribution/testutil" 13 ) 14 15 // Test implements distribution.BlobWriter 16 var _ distribution.BlobWriter = &httpBlobUpload{} 17 18 func TestUploadReadFrom(t *testing.T) { 19 _, b := newRandomBlob(64) 20 repo := "test/upload/readfrom" 21 locationPath := fmt.Sprintf("/v2/%s/uploads/testid", repo) 22 23 m := testutil.RequestResponseMap([]testutil.RequestResponseMapping{ 24 { 25 Request: testutil.Request{ 26 Method: "GET", 27 Route: "/v2/", 28 }, 29 Response: testutil.Response{ 30 StatusCode: http.StatusOK, 31 Headers: http.Header(map[string][]string{ 32 "Docker-Distribution-API-Version": {"registry/2.0"}, 33 }), 34 }, 35 }, 36 // Test Valid case 37 { 38 Request: testutil.Request{ 39 Method: "PATCH", 40 Route: locationPath, 41 Body: b, 42 }, 43 Response: testutil.Response{ 44 StatusCode: http.StatusAccepted, 45 Headers: http.Header(map[string][]string{ 46 "Docker-Upload-UUID": {"46603072-7a1b-4b41-98f9-fd8a7da89f9b"}, 47 "Location": {locationPath}, 48 "Range": {"0-63"}, 49 }), 50 }, 51 }, 52 // Test invalid range 53 { 54 Request: testutil.Request{ 55 Method: "PATCH", 56 Route: locationPath, 57 Body: b, 58 }, 59 Response: testutil.Response{ 60 StatusCode: http.StatusAccepted, 61 Headers: http.Header(map[string][]string{ 62 "Docker-Upload-UUID": {"46603072-7a1b-4b41-98f9-fd8a7da89f9b"}, 63 "Location": {locationPath}, 64 "Range": {""}, 65 }), 66 }, 67 }, 68 // Test 404 69 { 70 Request: testutil.Request{ 71 Method: "PATCH", 72 Route: locationPath, 73 Body: b, 74 }, 75 Response: testutil.Response{ 76 StatusCode: http.StatusNotFound, 77 }, 78 }, 79 // Test 400 valid json 80 { 81 Request: testutil.Request{ 82 Method: "PATCH", 83 Route: locationPath, 84 Body: b, 85 }, 86 Response: testutil.Response{ 87 StatusCode: http.StatusBadRequest, 88 Body: []byte(` 89 { "errors": 90 [ 91 { 92 "code": "BLOB_UPLOAD_INVALID", 93 "message": "blob upload invalid", 94 "detail": "more detail" 95 } 96 ] 97 } `), 98 }, 99 }, 100 // Test 400 invalid json 101 { 102 Request: testutil.Request{ 103 Method: "PATCH", 104 Route: locationPath, 105 Body: b, 106 }, 107 Response: testutil.Response{ 108 StatusCode: http.StatusBadRequest, 109 Body: []byte("something bad happened"), 110 }, 111 }, 112 // Test 500 113 { 114 Request: testutil.Request{ 115 Method: "PATCH", 116 Route: locationPath, 117 Body: b, 118 }, 119 Response: testutil.Response{ 120 StatusCode: http.StatusInternalServerError, 121 }, 122 }, 123 }) 124 125 e, c := testServer(m) 126 defer c() 127 128 blobUpload := &httpBlobUpload{ 129 client: &http.Client{}, 130 } 131 132 // Valid case 133 blobUpload.location = e + locationPath 134 n, err := blobUpload.ReadFrom(bytes.NewReader(b)) 135 if err != nil { 136 t.Fatalf("Error calling ReadFrom: %s", err) 137 } 138 if n != 64 { 139 t.Fatalf("Wrong length returned from ReadFrom: %d, expected 64", n) 140 } 141 142 // Bad range 143 blobUpload.location = e + locationPath 144 _, err = blobUpload.ReadFrom(bytes.NewReader(b)) 145 if err == nil { 146 t.Fatalf("Expected error when bad range received") 147 } 148 149 // 404 150 blobUpload.location = e + locationPath 151 _, err = blobUpload.ReadFrom(bytes.NewReader(b)) 152 if err == nil { 153 t.Fatalf("Expected error when not found") 154 } 155 if err != distribution.ErrBlobUploadUnknown { 156 t.Fatalf("Wrong error thrown: %s, expected %s", err, distribution.ErrBlobUploadUnknown) 157 } 158 159 // 400 valid json 160 blobUpload.location = e + locationPath 161 _, err = blobUpload.ReadFrom(bytes.NewReader(b)) 162 if err == nil { 163 t.Fatalf("Expected error when not found") 164 } 165 if uploadErr, ok := err.(errcode.Errors); !ok { 166 t.Fatalf("Wrong error type %T: %s", err, err) 167 } else if len(uploadErr) != 1 { 168 t.Fatalf("Unexpected number of errors: %d, expected 1", len(uploadErr)) 169 } else { 170 v2Err, ok := uploadErr[0].(errcode.Error) 171 if !ok { 172 t.Fatalf("Not an 'Error' type: %#v", uploadErr[0]) 173 } 174 if v2Err.Code != v2.ErrorCodeBlobUploadInvalid { 175 t.Fatalf("Unexpected error code: %s, expected %d", v2Err.Code.String(), v2.ErrorCodeBlobUploadInvalid) 176 } 177 if expected := "blob upload invalid"; v2Err.Message != expected { 178 t.Fatalf("Unexpected error message: %q, expected %q", v2Err.Message, expected) 179 } 180 if expected := "more detail"; v2Err.Detail.(string) != expected { 181 t.Fatalf("Unexpected error message: %q, expected %q", v2Err.Detail.(string), expected) 182 } 183 } 184 185 // 400 invalid json 186 blobUpload.location = e + locationPath 187 _, err = blobUpload.ReadFrom(bytes.NewReader(b)) 188 if err == nil { 189 t.Fatalf("Expected error when not found") 190 } 191 if uploadErr, ok := err.(*UnexpectedHTTPResponseError); !ok { 192 t.Fatalf("Wrong error type %T: %s", err, err) 193 } else { 194 respStr := string(uploadErr.Response) 195 if expected := "something bad happened"; respStr != expected { 196 t.Fatalf("Unexpected response string: %s, expected: %s", respStr, expected) 197 } 198 } 199 200 // 500 201 blobUpload.location = e + locationPath 202 _, err = blobUpload.ReadFrom(bytes.NewReader(b)) 203 if err == nil { 204 t.Fatalf("Expected error when not found") 205 } 206 if uploadErr, ok := err.(*UnexpectedHTTPStatusError); !ok { 207 t.Fatalf("Wrong error type %T: %s", err, err) 208 } else if expected := "500 " + http.StatusText(http.StatusInternalServerError); uploadErr.Status != expected { 209 t.Fatalf("Unexpected response status: %s, expected %s", uploadErr.Status, expected) 210 } 211 }