github.com/StarfishStorage/goofys@v0.23.2-0.20200415030923-535558486b34/internal/backend_adlv2.go (about) 1 // Copyright 2019 Databricks 2 // Copyright (c) Microsoft and contributors for generated code from azure-sdk-for-go 3 // 4 // Licensed under the Apache License, Version 2.0 (the "License"); 5 // you may not use this file except in compliance with the License. 6 // You may obtain a copy of the License at 7 // 8 // http://www.apache.org/licenses/LICENSE-2.0 9 // 10 // Unless required by applicable law or agreed to in writing, software 11 // distributed under the License is distributed on an "AS IS" BASIS, 12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 // See the License for the specific language governing permissions and 14 // limitations under the License. 15 16 package internal 17 18 import ( 19 . "github.com/kahing/goofys/api/common" 20 21 "context" 22 "encoding/base64" 23 "encoding/json" 24 "fmt" 25 "io" 26 "net/http" 27 "net/url" 28 "strconv" 29 "strings" 30 "sync/atomic" 31 "syscall" 32 "time" 33 34 "github.com/google/uuid" 35 "github.com/jacobsa/fuse" 36 "github.com/sirupsen/logrus" 37 38 adl2 "github.com/Azure/azure-sdk-for-go/services/storage/datalake/2018-11-09/storagedatalake" 39 "github.com/Azure/go-autorest/autorest" 40 "github.com/Azure/go-autorest/autorest/azure" 41 ) 42 43 type ADLv2 struct { 44 cap Capabilities 45 46 flags *FlagStorage 47 config *ADLv2Config 48 49 client adl2PathClient 50 bucket string 51 } 52 53 const ADL2_CLIENT_REQUEST_ID = "X-Ms-Client-Request-Id" 54 const ADL2_REQUEST_ID = "X-Ms-Request-Id" 55 56 var adl2Log = GetLogger("adlv2") 57 58 type ADLv2MultipartBlobCommitInput struct { 59 Size uint64 60 ContentType string 61 RenewLeaseStop chan bool 62 } 63 64 func IsADLv2Endpoint(endpoint string) bool { 65 return strings.HasPrefix(endpoint, "abfs://") 66 } 67 68 func adl2LogResp(level logrus.Level, r *http.Response) { 69 if r == nil { 70 return 71 } 72 73 if adl2Log.IsLevelEnabled(level) { 74 requestId := r.Request.Header.Get(ADL2_CLIENT_REQUEST_ID) 75 respId := r.Header.Get(ADL2_REQUEST_ID) 76 // don't log anything if this is being called twice, 77 // which it is via ResponseInspector 78 if respId != "" { 79 adl2Log.Logf(level, "%v %v %v %v %v", r.Request.Method, 80 r.Request.URL.String(), 81 requestId, r.Status, respId) 82 r.Header.Del(ADL2_REQUEST_ID) 83 } 84 } 85 } 86 87 func NewADLv2(bucket string, flags *FlagStorage, config *ADLv2Config) (*ADLv2, error) { 88 u, err := url.Parse(config.Endpoint) 89 if err != nil { 90 return nil, err 91 } 92 93 parts := strings.SplitN(u.Hostname(), ".", 2) 94 if len(parts) != 2 { 95 return nil, fmt.Errorf("Invalid endpoint: %v", config.Endpoint) 96 } 97 storageAccountName := parts[0] 98 dnsSuffix := parts[1] 99 100 LogRequest := func(p autorest.Preparer) autorest.Preparer { 101 return autorest.PreparerFunc(func(r *http.Request) (*http.Request, error) { 102 r.URL.Scheme = u.Scheme 103 date := time.Now().Format(time.RFC1123) 104 date = strings.Replace(date, "UTC", "GMT", 1) 105 106 r.Header.Set("X-Ms-Date", date) 107 r.Header.Set("X-Ms-Version", "2018-11-09") 108 r.Header.Set(ADL2_CLIENT_REQUEST_ID, uuid.New().String()) 109 r.Header.Set("Accept-Charset", "utf-8") 110 r.Header.Set("Content-Type", "") 111 r.Header.Set("Accept", "application/json, application/octet-stream") 112 // set transfer encoding and non-nil Body to 113 // ensure Content-Length: 0 is sent, seems 114 // like an idiotic golang behavior: 115 // https://github.com/golang/go/issues/20257 116 // azure server side rejects the request if 117 // Content-Length is missing 118 r.TransferEncoding = []string{"identity"} 119 if r.Header.Get("Content-Length") == "0" { 120 r.Body = http.NoBody 121 } else if r.Body == nil { 122 r.Body = http.NoBody 123 } 124 125 if adl2Log.IsLevelEnabled(logrus.DebugLevel) { 126 requestId := r.Header.Get(ADL2_CLIENT_REQUEST_ID) 127 op := r.Method 128 switch op { 129 case http.MethodPost: 130 // this is a lease 131 leaseAction := r.Header.Get("X-Ms-Lease-Action") 132 leaseId := r.Header.Get("X-Ms-Lease-Id") 133 proposeLeaseId := r.Header.Get("X-Ms-Proposed-Lease-Id") 134 op += fmt.Sprintf(" %v (%v, %v)", 135 leaseAction, leaseId, proposeLeaseId) 136 case http.MethodPatch: 137 action := r.URL.Query().Get("action") 138 op += " " + action 139 if action == "append" { 140 op += fmt.Sprintf("(%v)", r.ContentLength) 141 } 142 } 143 adl2Log.Debugf("%v %v %v", op, 144 r.URL.String(), requestId) 145 } 146 147 r, err := p.Prepare(r) 148 if err != nil { 149 adl2Log.Error(err) 150 } 151 return r, err 152 }) 153 } 154 155 LogResponse := func(p autorest.Responder) autorest.Responder { 156 return autorest.ResponderFunc(func(r *http.Response) error { 157 adl2LogResp(logrus.DebugLevel, r) 158 err := p.Respond(r) 159 if err != nil { 160 adl2Log.Error(err) 161 } 162 return err 163 }) 164 } 165 166 client := adl2.NewWithoutDefaults("", storageAccountName, dnsSuffix) 167 client.Authorizer = config.Authorizer 168 client.RequestInspector = LogRequest 169 client.ResponseInspector = LogResponse 170 client.Sender.(*http.Client).Transport = GetHTTPTransport() 171 172 b := &ADLv2{ 173 flags: flags, 174 config: config, 175 client: adl2PathClient{client}, 176 bucket: bucket, 177 cap: Capabilities{ 178 DirBlob: true, 179 Name: "adl2", 180 // tested on 2019-11-07, seems to have same 181 // limit as azblob 182 MaxMultipartSize: 100 * 1024 * 1024, 183 }, 184 } 185 186 return b, nil 187 } 188 189 func (b *ADLv2) Bucket() string { 190 return b.bucket 191 } 192 193 func (b *ADLv2) Delegate() interface{} { 194 return b 195 } 196 197 func (b *ADLv2) Init(key string) (err error) { 198 _, err = b.HeadBlob(&HeadBlobInput{Key: key}) 199 if err == fuse.ENOENT { 200 err = nil 201 } 202 return 203 } 204 205 func (b *ADLv2) Capabilities() *Capabilities { 206 return &b.cap 207 } 208 209 type ADL2Error struct { 210 adl2.DataLakeStorageError 211 } 212 213 func (e ADL2Error) Error() string { 214 return fmt.Sprintf("%v: %v", *e.DataLakeStorageError.Error.Code, 215 *e.DataLakeStorageError.Error.Message) 216 } 217 218 func decodeADLv2Error(body io.Reader) (adlErr adl2.DataLakeStorageError, err error) { 219 decoder := json.NewDecoder(body) 220 err = decoder.Decode(&adlErr) 221 return 222 } 223 224 func mapADLv2Error(resp *http.Response, err error, rawError bool) error { 225 226 if resp == nil { 227 if err != nil { 228 if detailedError, ok := err.(autorest.DetailedError); ok { 229 if urlErr, ok := detailedError.Original.(*url.Error); ok { 230 adl2Log.Errorf("url.Err: %T: %v %v %v %v %v", urlErr.Err, urlErr.Err, urlErr.Temporary(), urlErr.Timeout(), urlErr.Op, urlErr.URL) 231 } else { 232 adl2Log.Errorf("%T: %v", detailedError.Original, detailedError.Original) 233 } 234 } else { 235 adl2Log.Errorf("unknown error: %v", err) 236 } 237 return syscall.EAGAIN 238 } else { 239 return err 240 } 241 } 242 243 if resp.StatusCode < 200 || resp.StatusCode >= 300 { 244 defer resp.Body.Close() 245 if rawError { 246 adlErr, err := decodeADLv2Error(resp.Body) 247 if err == nil { 248 return ADL2Error{adlErr} 249 } else { 250 adl2Log.Errorf("cannot parse error: %v", err) 251 return syscall.EAGAIN 252 } 253 } else { 254 switch resp.StatusCode { 255 case http.StatusBadRequest: 256 if !adl2Log.IsLevelEnabled(logrus.DebugLevel) { 257 adl2LogResp(logrus.ErrorLevel, resp) 258 } 259 adlErr, err := decodeADLv2Error(resp.Body) 260 if err == nil { 261 switch *adlErr.Error.Code { 262 case "MissingRequiredHeader", "UnsupportedHeader": 263 var s strings.Builder 264 for k, _ := range resp.Request.Header { 265 s.WriteString(k) 266 s.WriteString(" ") 267 } 268 adl2Log.Errorf("%v, sent: %v", 269 *adlErr.Error.Code, 270 s.String()) 271 case "InvalidSourceUri": 272 adl2Log.Errorf("SourceUri: %v", 273 resp.Request.Header.Get("X-Ms-Rename-Source")) 274 } 275 } 276 case http.StatusPreconditionFailed: 277 return syscall.EAGAIN 278 } 279 280 err = mapHttpError(resp.StatusCode) 281 if err != nil { 282 return err 283 } else { 284 if !adl2Log.IsLevelEnabled(logrus.DebugLevel) { 285 adl2LogResp(logrus.ErrorLevel, resp) 286 } 287 adl2Log.Errorf("resp: %#v %v", resp, err) 288 return syscall.EINVAL 289 } 290 } 291 } else { 292 return err 293 } 294 } 295 296 func getHeader(resp *http.Response, key string) *string { 297 if v, set := resp.Header[http.CanonicalHeaderKey(key)]; set { 298 return &v[0] 299 } else { 300 return nil 301 } 302 } 303 304 func parseADLv2Time(v string) *time.Time { 305 t, err := time.Parse(time.RFC1123, v) 306 if err == nil { 307 return &t 308 } else { 309 return nil 310 } 311 } 312 313 func adlv2ToBlobItem(resp *http.Response, key string) BlobItemOutput { 314 return BlobItemOutput{ 315 Key: &key, 316 ETag: getHeader(resp, "ETag"), 317 Size: uint64(resp.ContentLength), 318 LastModified: parseADLv2Time(resp.Header.Get("Last-Modified")), 319 } 320 } 321 322 func (b *ADLv2) HeadBlob(param *HeadBlobInput) (*HeadBlobOutput, error) { 323 key := param.Key 324 if strings.HasSuffix(key, "/") { 325 key = key[:len(key)-1] 326 } 327 328 // GetProperties(GetStatus) does not return user defined 329 // properties, despite what the documentation says, use a 0 330 // bytes range get instead 331 res, err := b.GetBlob(&GetBlobInput{ 332 Key: key, 333 Start: 0, 334 Count: 0, 335 }) 336 if err != nil { 337 return nil, err 338 } 339 res.Body.Close() 340 341 return &res.HeadBlobOutput, nil 342 } 343 344 func (b *ADLv2) ListBlobs(param *ListBlobsInput) (*ListBlobsOutput, error) { 345 if param.Delimiter != nil && *param.Delimiter != "/" { 346 return nil, fuse.EINVAL 347 } 348 349 var maxResults *int32 350 if param.MaxKeys != nil { 351 maxResults = PInt32(int32(*param.MaxKeys)) 352 } 353 354 res, err := b.client.List(context.TODO(), param.Delimiter == nil, b.bucket, 355 nilStr(param.Prefix), nilStr(param.ContinuationToken), maxResults, 356 nil, "", nil, "") 357 if err != nil { 358 err = mapADLv2Error(res.Response.Response, err, false) 359 if err == fuse.ENOENT { 360 return &ListBlobsOutput{ 361 RequestId: res.Response.Response.Header.Get(ADL2_REQUEST_ID), 362 }, nil 363 } else { 364 return nil, err 365 } 366 } 367 368 var prefixes []BlobPrefixOutput 369 var items []BlobItemOutput 370 371 if param.Delimiter != nil && param.Prefix != nil { 372 // we didn't get 404 which means the path must 373 // exists. If the path is actually a file, adlv2 374 // returns the file itself as the result. That's 375 // already handled by the loop below 376 if len(*res.Paths) != 1 || 377 *(*res.Paths)[0].Name != strings.TrimRight(*param.Prefix, "/") { 378 // the prefix we listed is a directory 379 if strings.HasSuffix(*param.Prefix, "/") { 380 // we listed for the dir object itself 381 items = append(items, BlobItemOutput{ 382 Key: param.Prefix, 383 }) 384 } else { 385 prefixes = append(prefixes, BlobPrefixOutput{ 386 PString(*param.Prefix + "/"), 387 }) 388 } 389 } else { 390 if strings.HasSuffix(*param.Prefix, "/") { 391 // we asked for a dir and got a file 392 return &ListBlobsOutput{ 393 RequestId: res.Response.Response.Header.Get(ADL2_REQUEST_ID), 394 }, nil 395 } 396 } 397 } 398 399 for _, p := range *res.Paths { 400 if param.Delimiter != nil { 401 if p.isDirectory() { 402 prefixes = append(prefixes, BlobPrefixOutput{ 403 PString(*p.Name + "/"), 404 }) 405 continue 406 } 407 } 408 409 key := *p.Name 410 if p.isDirectory() { 411 key += "/" 412 } 413 items = append(items, BlobItemOutput{ 414 Key: &key, 415 ETag: p.ETag, 416 LastModified: parseADLv2Time(nilStr(p.LastModified)), 417 Size: uint64(p.contentLength()), 418 }) 419 } 420 421 continuationToken := getHeader(res.Response.Response, "x-ms-continuation") 422 423 return &ListBlobsOutput{ 424 Prefixes: prefixes, 425 Items: items, 426 NextContinuationToken: continuationToken, 427 IsTruncated: continuationToken != nil, 428 RequestId: res.Response.Response.Header.Get(ADL2_REQUEST_ID), 429 }, nil 430 } 431 432 func (b *ADLv2) DeleteBlob(param *DeleteBlobInput) (*DeleteBlobOutput, error) { 433 if strings.HasSuffix(param.Key, "/") { 434 return b.DeleteBlob(&DeleteBlobInput{param.Key[:len(param.Key)-1]}) 435 } 436 437 res, err := b.client.Delete(context.TODO(), b.bucket, param.Key, nil, "", "", 438 /*ifMatch=*/ "", "", "", "", "", nil, "") 439 err = mapADLv2Error(res.Response, err, false) 440 if err != nil { 441 return nil, err 442 } 443 return &DeleteBlobOutput{}, nil 444 } 445 446 func (b *ADLv2) DeleteBlobs(param *DeleteBlobsInput) (*DeleteBlobsOutput, error) { 447 return nil, syscall.ENOTSUP 448 } 449 450 func (b *ADLv2) RenameBlob(param *RenameBlobInput) (*RenameBlobOutput, error) { 451 var continuation string 452 453 renameDest := param.Destination 454 if strings.HasSuffix(renameDest, "/") { 455 renameDest = renameDest[:len(renameDest)-1] 456 } 457 renameSource := param.Source 458 if strings.HasSuffix(renameSource, "/") { 459 renameSource = renameSource[:len(renameSource)-1] 460 } 461 renameSource = "/" + b.bucket + "/" + url.PathEscape(renameSource) 462 463 var requestId string 464 for cont := true; cont; cont = continuation != "" { 465 res, err := b.client.Create(context.TODO(), b.bucket, renameDest, 466 "", continuation, "", "", "", "", "", "", "", "", "", "", 467 renameSource, "", "", "", "", "", "", "", "", "", "", "", 468 "", "", "", nil, "") 469 if err != nil { 470 return nil, mapADLv2Error(res.Response, err, false) 471 } 472 473 continuation = res.Header.Get("x-ms-continuation") 474 requestId = res.Header.Get(ADL2_REQUEST_ID) 475 } 476 477 return &RenameBlobOutput{requestId}, nil 478 } 479 480 func (b *ADLv2) CopyBlob(param *CopyBlobInput) (*CopyBlobOutput, error) { 481 if param.Source != param.Destination || param.Metadata == nil { 482 return nil, syscall.ENOTSUP 483 } 484 485 res, err := b.client.Update(context.TODO(), adl2.SetProperties, b.bucket, param.Source, nil, 486 nil, nil, nil, "", "", "", "", "", "", "", "", b.toADLProperties(param.Metadata), 487 "", "", "", "", "", "", "", "", nil, "", nil, "") 488 if err != nil { 489 return nil, mapADLv2Error(res.Response, err, false) 490 } 491 492 return &CopyBlobOutput{ 493 RequestId: res.Response.Header.Get(ADL2_REQUEST_ID), 494 }, nil 495 } 496 497 func (b *ADLv2) GetBlob(param *GetBlobInput) (*GetBlobOutput, error) { 498 var bytes string 499 if param.Start != 0 || param.Count != 0 { 500 if param.Count != 0 { 501 bytes = fmt.Sprintf("bytes=%v-%v", param.Start, param.Start+param.Count-1) 502 } else { 503 bytes = fmt.Sprintf("bytes=%v-", param.Start) 504 } 505 } 506 507 res, err := b.client.Read(context.TODO(), b.bucket, param.Key, bytes, 508 "", nil, nilStr(param.IfMatch), "", "", "", 509 "", nil, "") 510 if err != nil { 511 return nil, mapADLv2Error(res.Response.Response, err, false) 512 } 513 514 metadata := make(map[string]*string) 515 for _, p := range res.Header["X-Ms-Properties"] { 516 csv := strings.Split(p, ",") 517 for _, kv := range csv { 518 kv = strings.TrimSpace(kv) 519 if len(kv) == 0 { 520 continue 521 } 522 523 s := strings.SplitN(kv, "=", 2) 524 if len(s) != 2 { 525 adl2Log.Warnf("Dropping property: %v: %v", param.Key, kv) 526 continue 527 } 528 key := strings.TrimSpace(s[0]) 529 value := strings.TrimSpace(s[1]) 530 buf, err := base64.StdEncoding.DecodeString(value) 531 if err != nil { 532 adl2Log.Warnf("Unable to decode property: %v: %v", 533 param.Key, key) 534 continue 535 } 536 metadata[key] = PString(string(buf)) 537 } 538 } 539 540 return &GetBlobOutput{ 541 HeadBlobOutput: HeadBlobOutput{ 542 BlobItemOutput: adlv2ToBlobItem(res.Response.Response, param.Key), 543 ContentType: getHeader(res.Response.Response, "Content-Type"), 544 IsDirBlob: res.Header.Get("X-Ms-Resource-Type") == string(adl2.Directory), 545 Metadata: metadata, 546 }, 547 Body: *res.Value, 548 }, nil 549 } 550 551 func (b *ADLv2) toADLProperties(metadata map[string]*string) string { 552 var buf strings.Builder 553 for k, v := range metadata { 554 buf.WriteString(k) 555 buf.WriteString("=") 556 buf.WriteString(base64.StdEncoding.EncodeToString([]byte(*v))) 557 buf.WriteString(",") 558 } 559 var s = buf.String() 560 if len(s) != 0 { 561 // remove trailing comma 562 s = s[:len(s)-1] 563 } 564 return s 565 } 566 567 func (b *ADLv2) create(key string, pathType adl2.PathResourceType, contentType *string, 568 metadata map[string]*string, leaseId string) (resp autorest.Response, err error) { 569 resp, err = b.client.Create(context.TODO(), b.bucket, key, 570 pathType, "", "", "", "", "", "", "", nilStr(contentType), 571 "", "", "", "", leaseId, "", b.toADLProperties(metadata), "", "", "", "", "", "", 572 "", "", "", "", "", nil, "") 573 if err != nil { 574 err = mapADLv2Error(resp.Response, err, false) 575 } 576 return 577 } 578 579 func (b *ADLv2) append(key string, offset int64, size int64, body io.ReadSeeker, 580 leaseId string) (resp autorest.Response, err error) { 581 resp, err = b.client.Update(context.TODO(), adl2.Append, b.bucket, 582 key, &offset, nil, nil, &size, "", leaseId, "", 583 "", "", "", "", "", "", "", "", "", "", 584 "", "", "", "", &ReadSeekerCloser{body}, 585 "", nil, "") 586 if err != nil { 587 err = mapADLv2Error(resp.Response, err, false) 588 } 589 return 590 } 591 592 func (b *ADLv2) flush(key string, offset int64, contentType string, leaseId string) (res autorest.Response, err error) { 593 res, err = b.client.Update(context.TODO(), adl2.Flush, b.bucket, 594 key, &offset, PBool(false), PBool(true), PInt64(0), "", leaseId, "", 595 contentType, "", "", "", "", "", "", "", "", "", 596 "", "", "", "", nil, "", nil, "") 597 if err != nil { 598 err = mapADLv2Error(res.Response, err, false) 599 } 600 return 601 } 602 603 func (b *ADLv2) PutBlob(param *PutBlobInput) (*PutBlobOutput, error) { 604 if param.DirBlob { 605 res, err := b.create(param.Key, adl2.Directory, param.ContentType, 606 param.Metadata, "") 607 if err != nil { 608 return nil, err 609 } 610 return &PutBlobOutput{ 611 ETag: getHeader(res.Response, "ETag"), 612 }, nil 613 } else { 614 if param.Size == nil { 615 panic("size cannot be nil") 616 } 617 618 create, err := b.create(param.Key, adl2.File, param.ContentType, 619 param.Metadata, "") 620 if err != nil { 621 return nil, err 622 } 623 624 size := int64(*param.Size) 625 if size == 0 { 626 // nothing to write, we can return 627 // here. appending a 0-size buffer 628 // causes azure to fail with 400 bad 629 // request 630 return &PutBlobOutput{ 631 ETag: getHeader(create.Response, "ETag"), 632 }, nil 633 } 634 635 // not doing a lease for these because append to 0 636 // would guarantee that we don't have concurrent 637 // appends, and flushing is safe to do 638 _, err = b.append(param.Key, 0, size, param.Body, "") 639 if err != nil { 640 return nil, err 641 } 642 643 flush, err := b.flush(param.Key, size, nilStr(param.ContentType), "") 644 if err != nil { 645 return nil, err 646 } 647 648 return &PutBlobOutput{ 649 ETag: getHeader(flush.Response, "ETag"), 650 }, nil 651 } 652 } 653 654 // adlv2 doesn't have atomic multipart upload, instead we will hold a 655 // lease, replace the object, then release the lease 656 func (b *ADLv2) MultipartBlobBegin(param *MultipartBlobBeginInput) (*MultipartBlobCommitInput, error) { 657 leaseId := uuid.New().String() 658 err := b.lease(adl2.Acquire, param.Key, leaseId, 60, "") 659 if err == fuse.ENOENT { 660 // the file didn't exist, we will create the file 661 // first and then acquire the lease 662 create, err := b.create(param.Key, adl2.File, param.ContentType, param.Metadata, "") 663 if err != nil { 664 return nil, err 665 } 666 667 err = b.lease(adl2.Acquire, param.Key, leaseId, 60, 668 create.Response.Header.Get("ETag")) 669 if err != nil { 670 return nil, err 671 } 672 } else { 673 if err != nil { 674 return nil, err 675 } 676 677 defer func() { 678 if err != nil { 679 err2 := b.lease(adl2.Release, param.Key, leaseId, 0, "") 680 if err2 != nil { 681 adl2Log.Errorf("Unable to release lease for %v: %v", 682 param.Key, err2) 683 } 684 } 685 }() 686 687 _, err = b.create(param.Key, adl2.File, param.ContentType, param.Metadata, leaseId) 688 if err != nil { 689 return nil, err 690 } 691 692 } 693 694 commitData := &ADLv2MultipartBlobCommitInput{ 695 ContentType: nilStr(param.ContentType), 696 RenewLeaseStop: make(chan bool, 1), 697 } 698 699 go func() { 700 for { 701 select { 702 case <-commitData.RenewLeaseStop: 703 break 704 case <-time.After(30 * time.Second): 705 b.lease(adl2.Renew, param.Key, leaseId, 60, "") 706 } 707 } 708 }() 709 710 return &MultipartBlobCommitInput{ 711 Key: ¶m.Key, 712 Metadata: param.Metadata, 713 UploadId: &leaseId, 714 backendData: commitData, 715 }, nil 716 } 717 718 func (b *ADLv2) lease(action adl2.PathLeaseAction, key string, leaseId string, durationSec int32, 719 ifMatch string) error { 720 var proposeLeaseId string 721 var prevLeaseId string 722 if action == adl2.Acquire { 723 proposeLeaseId = leaseId 724 } else { 725 prevLeaseId = leaseId 726 } 727 728 var duration *int32 729 if durationSec != 0 { 730 duration = &durationSec 731 } 732 733 res, err := b.client.Lease(context.TODO(), action, b.bucket, key, 734 duration, nil, prevLeaseId, proposeLeaseId, ifMatch, "", "", "", "", nil, "") 735 if err != nil { 736 err = mapADLv2Error(res.Response, err, false) 737 } 738 return err 739 } 740 741 func (b *ADLv2) MultipartBlobAdd(param *MultipartBlobAddInput) (*MultipartBlobAddOutput, error) { 742 var commitData *ADLv2MultipartBlobCommitInput 743 var ok bool 744 if commitData, ok = param.Commit.backendData.(*ADLv2MultipartBlobCommitInput); !ok { 745 panic("Incorrect commit data type") 746 } 747 748 res, err := b.append(*param.Commit.Key, int64(param.Offset), int64(param.Size), 749 param.Body, *param.Commit.UploadId) 750 if err != nil { 751 return nil, err 752 } 753 atomic.AddUint64(&commitData.Size, param.Size) 754 755 return &MultipartBlobAddOutput{ 756 res.Response.Header.Get(ADL2_REQUEST_ID), 757 }, nil 758 } 759 760 func (b *ADLv2) MultipartBlobAbort(param *MultipartBlobCommitInput) (*MultipartBlobAbortOutput, error) { 761 if param.UploadId != nil { 762 err := b.lease(adl2.Release, *param.Key, *param.UploadId, 0, "") 763 if err != nil { 764 return nil, err 765 } 766 } 767 return &MultipartBlobAbortOutput{}, nil 768 } 769 770 func (b *ADLv2) MultipartBlobCommit(param *MultipartBlobCommitInput) (*MultipartBlobCommitOutput, error) { 771 var commitData *ADLv2MultipartBlobCommitInput 772 var ok bool 773 if commitData, ok = param.backendData.(*ADLv2MultipartBlobCommitInput); !ok { 774 panic("Incorrect commit data type") 775 } 776 777 defer func() { 778 commitData.RenewLeaseStop <- true 779 leaseId := *param.UploadId 780 // if the commit failed, we don't need to release the 781 // lease during abort 782 param.UploadId = nil 783 784 err2 := b.lease(adl2.Release, *param.Key, leaseId, 0, "") 785 if err2 != nil { 786 adl2Log.Errorf("Unable to release lease for %v: %v", 787 *param.Key, err2) 788 } 789 }() 790 791 flush, err := b.flush(*param.Key, int64(commitData.Size), commitData.ContentType, *param.UploadId) 792 if err != nil { 793 return nil, err 794 } 795 796 return &MultipartBlobCommitOutput{ 797 ETag: nil, 798 RequestId: flush.Response.Header.Get(ADL2_REQUEST_ID), 799 }, nil 800 } 801 802 func (b *ADLv2) MultipartExpire(param *MultipartExpireInput) (*MultipartExpireOutput, error) { 803 return nil, syscall.ENOTSUP 804 } 805 806 func (b *ADLv2) RemoveBucket(param *RemoveBucketInput) (*RemoveBucketOutput, error) { 807 fs := adl2.FilesystemClient{b.client.BaseClient} 808 res, err := fs.Delete(context.TODO(), b.bucket, "", "", uuid.New().String(), nil, "") 809 if err != nil { 810 return nil, mapADLv2Error(res.Response, err, false) 811 } 812 return &RemoveBucketOutput{}, nil 813 } 814 815 func (b *ADLv2) MakeBucket(param *MakeBucketInput) (*MakeBucketOutput, error) { 816 fs := adl2.FilesystemClient{b.client.BaseClient} 817 res, err := fs.Create(context.TODO(), b.bucket, "", uuid.New().String(), nil, "") 818 if err != nil { 819 return nil, mapADLv2Error(res.Response, err, false) 820 } 821 return &MakeBucketOutput{}, nil 822 } 823 824 // hacked from azure-sdk-for-go 825 // remove after these bugs are fixed: 826 // https://github.com/Azure/azure-sdk-for-go/issues/5502 827 // https://github.com/Azure/azure-sdk-for-go/issues/5550 828 // https://github.com/Azure/azure-sdk-for-go/issues/5549 829 type adl2PathClient struct { 830 adl2.BaseClient 831 } 832 833 func (client adl2PathClient) Create(ctx context.Context, filesystem string, pathParameter string, resource adl2.PathResourceType, continuation string, mode adl2.PathRenameMode, cacheControl string, contentEncoding string, contentLanguage string, contentDisposition string, xMsCacheControl string, xMsContentType string, xMsContentEncoding string, xMsContentLanguage string, xMsContentDisposition string, xMsRenameSource string, xMsLeaseID string, xMsSourceLeaseID string, xMsProperties string, xMsPermissions string, xMsUmask string, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, xMsSourceIfMatch string, xMsSourceIfNoneMatch string, xMsSourceIfModifiedSince string, xMsSourceIfUnmodifiedSince string, xMsClientRequestID string, timeout *int32, xMsDate string) (result autorest.Response, err error) { 834 req, err := client.CreatePreparer(ctx, filesystem, pathParameter, resource, continuation, mode, cacheControl, contentEncoding, contentLanguage, contentDisposition, xMsCacheControl, xMsContentType, xMsContentEncoding, xMsContentLanguage, xMsContentDisposition, xMsRenameSource, xMsLeaseID, xMsSourceLeaseID, xMsProperties, xMsPermissions, xMsUmask, ifMatch, ifNoneMatch, ifModifiedSince, ifUnmodifiedSince, xMsSourceIfMatch, xMsSourceIfNoneMatch, xMsSourceIfModifiedSince, xMsSourceIfUnmodifiedSince, xMsClientRequestID, timeout, xMsDate) 835 if err != nil { 836 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Create", nil, "Failure preparing request") 837 return 838 } 839 840 resp, err := client.CreateSender(req) 841 if err != nil { 842 result.Response = resp 843 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Create", resp, "Failure sending request") 844 return 845 } 846 847 result, err = client.CreateResponder(resp) 848 if err != nil { 849 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Create", resp, "Failure responding to request") 850 } 851 852 return 853 } 854 855 // CreatePreparer prepares the Create request. 856 func (client adl2PathClient) CreatePreparer(ctx context.Context, filesystem string, pathParameter string, resource adl2.PathResourceType, continuation string, mode adl2.PathRenameMode, cacheControl string, contentEncoding string, contentLanguage string, contentDisposition string, xMsCacheControl string, xMsContentType string, xMsContentEncoding string, xMsContentLanguage string, xMsContentDisposition string, xMsRenameSource string, xMsLeaseID string, xMsSourceLeaseID string, xMsProperties string, xMsPermissions string, xMsUmask string, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, xMsSourceIfMatch string, xMsSourceIfNoneMatch string, xMsSourceIfModifiedSince string, xMsSourceIfUnmodifiedSince string, xMsClientRequestID string, timeout *int32, xMsDate string) (*http.Request, error) { 857 urlParameters := map[string]interface{}{ 858 "accountName": client.AccountName, 859 "dnsSuffix": client.DNSSuffix, 860 } 861 862 pathParameters := map[string]interface{}{ 863 "filesystem": autorest.Encode("path", filesystem), 864 //"path": url.PathEscape(pathParameter), 865 "path": autorest.Encode("path", pathParameter), 866 } 867 868 queryParameters := map[string]interface{}{} 869 if len(string(resource)) > 0 { 870 queryParameters["resource"] = autorest.Encode("query", resource) 871 } 872 if len(continuation) > 0 { 873 queryParameters["continuation"] = autorest.Encode("query", continuation) 874 } 875 if len(string(mode)) > 0 { 876 queryParameters["mode"] = autorest.Encode("query", mode) 877 } 878 if timeout != nil { 879 queryParameters["timeout"] = autorest.Encode("query", *timeout) 880 } 881 882 preparer := autorest.CreatePreparer( 883 autorest.AsPut(), 884 autorest.WithCustomBaseURL("http://{accountName}.{dnsSuffix}", urlParameters), 885 autorest.WithPathParameters("/{filesystem}/{path}", pathParameters), 886 autorest.WithQueryParameters(queryParameters)) 887 if len(cacheControl) > 0 { 888 preparer = autorest.DecoratePreparer(preparer, 889 autorest.WithHeader("Cache-Control", autorest.String(cacheControl))) 890 } 891 if len(contentEncoding) > 0 { 892 preparer = autorest.DecoratePreparer(preparer, 893 autorest.WithHeader("Content-Encoding", autorest.String(contentEncoding))) 894 } 895 if len(contentLanguage) > 0 { 896 preparer = autorest.DecoratePreparer(preparer, 897 autorest.WithHeader("Content-Language", autorest.String(contentLanguage))) 898 } 899 if len(contentDisposition) > 0 { 900 preparer = autorest.DecoratePreparer(preparer, 901 autorest.WithHeader("Content-Disposition", autorest.String(contentDisposition))) 902 } 903 if len(xMsCacheControl) > 0 { 904 preparer = autorest.DecoratePreparer(preparer, 905 autorest.WithHeader("x-ms-cache-control", autorest.String(xMsCacheControl))) 906 } 907 if len(xMsContentType) > 0 { 908 preparer = autorest.DecoratePreparer(preparer, 909 autorest.WithHeader("x-ms-content-type", autorest.String(xMsContentType))) 910 } 911 if len(xMsContentEncoding) > 0 { 912 preparer = autorest.DecoratePreparer(preparer, 913 autorest.WithHeader("x-ms-content-encoding", autorest.String(xMsContentEncoding))) 914 } 915 if len(xMsContentLanguage) > 0 { 916 preparer = autorest.DecoratePreparer(preparer, 917 autorest.WithHeader("x-ms-content-language", autorest.String(xMsContentLanguage))) 918 } 919 if len(xMsContentDisposition) > 0 { 920 preparer = autorest.DecoratePreparer(preparer, 921 autorest.WithHeader("x-ms-content-disposition", autorest.String(xMsContentDisposition))) 922 } 923 if len(xMsRenameSource) > 0 { 924 preparer = autorest.DecoratePreparer(preparer, 925 autorest.WithHeader("x-ms-rename-source", autorest.String(xMsRenameSource))) 926 } 927 if len(xMsLeaseID) > 0 { 928 preparer = autorest.DecoratePreparer(preparer, 929 autorest.WithHeader("x-ms-lease-id", autorest.String(xMsLeaseID))) 930 } 931 if len(xMsSourceLeaseID) > 0 { 932 preparer = autorest.DecoratePreparer(preparer, 933 autorest.WithHeader("x-ms-source-lease-id", autorest.String(xMsSourceLeaseID))) 934 } 935 if len(xMsProperties) > 0 { 936 preparer = autorest.DecoratePreparer(preparer, 937 autorest.WithHeader("x-ms-properties", autorest.String(xMsProperties))) 938 } 939 if len(xMsPermissions) > 0 { 940 preparer = autorest.DecoratePreparer(preparer, 941 autorest.WithHeader("x-ms-permissions", autorest.String(xMsPermissions))) 942 } 943 if len(xMsUmask) > 0 { 944 preparer = autorest.DecoratePreparer(preparer, 945 autorest.WithHeader("x-ms-umask", autorest.String(xMsUmask))) 946 } 947 if len(ifMatch) > 0 { 948 preparer = autorest.DecoratePreparer(preparer, 949 autorest.WithHeader("If-Match", autorest.String(ifMatch))) 950 } 951 if len(ifNoneMatch) > 0 { 952 preparer = autorest.DecoratePreparer(preparer, 953 autorest.WithHeader("If-None-Match", autorest.String(ifNoneMatch))) 954 } 955 if len(ifModifiedSince) > 0 { 956 preparer = autorest.DecoratePreparer(preparer, 957 autorest.WithHeader("If-Modified-Since", autorest.String(ifModifiedSince))) 958 } 959 if len(ifUnmodifiedSince) > 0 { 960 preparer = autorest.DecoratePreparer(preparer, 961 autorest.WithHeader("If-Unmodified-Since", autorest.String(ifUnmodifiedSince))) 962 } 963 if len(xMsSourceIfMatch) > 0 { 964 preparer = autorest.DecoratePreparer(preparer, 965 autorest.WithHeader("x-ms-source-if-match", autorest.String(xMsSourceIfMatch))) 966 } 967 if len(xMsSourceIfNoneMatch) > 0 { 968 preparer = autorest.DecoratePreparer(preparer, 969 autorest.WithHeader("x-ms-source-if-none-match", autorest.String(xMsSourceIfNoneMatch))) 970 } 971 if len(xMsSourceIfModifiedSince) > 0 { 972 preparer = autorest.DecoratePreparer(preparer, 973 autorest.WithHeader("x-ms-source-if-modified-since", autorest.String(xMsSourceIfModifiedSince))) 974 } 975 if len(xMsSourceIfUnmodifiedSince) > 0 { 976 preparer = autorest.DecoratePreparer(preparer, 977 autorest.WithHeader("x-ms-source-if-unmodified-since", autorest.String(xMsSourceIfUnmodifiedSince))) 978 } 979 if len(xMsClientRequestID) > 0 { 980 preparer = autorest.DecoratePreparer(preparer, 981 autorest.WithHeader("x-ms-client-request-id", autorest.String(xMsClientRequestID))) 982 } 983 if len(xMsDate) > 0 { 984 preparer = autorest.DecoratePreparer(preparer, 985 autorest.WithHeader("x-ms-date", autorest.String(xMsDate))) 986 } 987 if len(client.XMsVersion) > 0 { 988 preparer = autorest.DecoratePreparer(preparer, 989 autorest.WithHeader("x-ms-version", autorest.String(client.XMsVersion))) 990 } 991 return preparer.Prepare((client.defaultRequest()).WithContext(ctx)) 992 } 993 994 // CreateSender sends the Create request. The method will close the 995 // http.Response Body if it receives an error. 996 func (client adl2PathClient) CreateSender(req *http.Request) (*http.Response, error) { 997 sd := autorest.GetSendDecorators(req.Context(), autorest.DoRetryForStatusCodes(client.RetryAttempts, client.RetryDuration, autorest.StatusCodesForRetry...)) 998 return autorest.SendWithSender(client, req, sd...) 999 } 1000 1001 // CreateResponder handles the response to the Create request. The method always 1002 // closes the http.Response Body. 1003 func (client adl2PathClient) CreateResponder(resp *http.Response) (result autorest.Response, err error) { 1004 err = autorest.Respond( 1005 resp, 1006 client.ByInspecting(), 1007 azure.WithErrorUnlessStatusCode(http.StatusOK, http.StatusCreated), 1008 autorest.ByClosing()) 1009 result.Response = resp 1010 return 1011 } 1012 1013 func (client adl2PathClient) Delete(ctx context.Context, filesystem string, pathParameter string, recursive *bool, continuation string, xMsLeaseID string, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, xMsClientRequestID string, timeout *int32, xMsDate string) (result autorest.Response, err error) { 1014 req, err := client.DeletePreparer(ctx, filesystem, pathParameter, recursive, continuation, xMsLeaseID, ifMatch, ifNoneMatch, ifModifiedSince, ifUnmodifiedSince, xMsClientRequestID, timeout, xMsDate) 1015 if err != nil { 1016 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Delete", nil, "Failure preparing request") 1017 return 1018 } 1019 1020 resp, err := client.DeleteSender(req) 1021 if err != nil { 1022 result.Response = resp 1023 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Delete", resp, "Failure sending request") 1024 return 1025 } 1026 1027 result, err = client.DeleteResponder(resp) 1028 if err != nil { 1029 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Delete", resp, "Failure responding to request") 1030 } 1031 1032 return 1033 } 1034 1035 // DeletePreparer prepares the Delete request. 1036 func (client adl2PathClient) DeletePreparer(ctx context.Context, filesystem string, pathParameter string, recursive *bool, continuation string, xMsLeaseID string, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, xMsClientRequestID string, timeout *int32, xMsDate string) (*http.Request, error) { 1037 urlParameters := map[string]interface{}{ 1038 "accountName": client.AccountName, 1039 "dnsSuffix": client.DNSSuffix, 1040 } 1041 1042 pathParameters := map[string]interface{}{ 1043 "filesystem": autorest.Encode("path", filesystem), 1044 "path": autorest.Encode("path", pathParameter), 1045 } 1046 1047 queryParameters := map[string]interface{}{} 1048 if recursive != nil { 1049 queryParameters["recursive"] = autorest.Encode("query", *recursive) 1050 } 1051 if len(continuation) > 0 { 1052 queryParameters["continuation"] = autorest.Encode("query", continuation) 1053 } 1054 if timeout != nil { 1055 queryParameters["timeout"] = autorest.Encode("query", *timeout) 1056 } 1057 1058 preparer := autorest.CreatePreparer( 1059 autorest.AsDelete(), 1060 autorest.WithCustomBaseURL("http://{accountName}.{dnsSuffix}", urlParameters), 1061 autorest.WithPathParameters("/{filesystem}/{path}", pathParameters), 1062 autorest.WithQueryParameters(queryParameters)) 1063 if len(xMsLeaseID) > 0 { 1064 preparer = autorest.DecoratePreparer(preparer, 1065 autorest.WithHeader("x-ms-lease-id", autorest.String(xMsLeaseID))) 1066 } 1067 if len(ifMatch) > 0 { 1068 preparer = autorest.DecoratePreparer(preparer, 1069 autorest.WithHeader("If-Match", autorest.String(ifMatch))) 1070 } 1071 if len(ifNoneMatch) > 0 { 1072 preparer = autorest.DecoratePreparer(preparer, 1073 autorest.WithHeader("If-None-Match", autorest.String(ifNoneMatch))) 1074 } 1075 if len(ifModifiedSince) > 0 { 1076 preparer = autorest.DecoratePreparer(preparer, 1077 autorest.WithHeader("If-Modified-Since", autorest.String(ifModifiedSince))) 1078 } 1079 if len(ifUnmodifiedSince) > 0 { 1080 preparer = autorest.DecoratePreparer(preparer, 1081 autorest.WithHeader("If-Unmodified-Since", autorest.String(ifUnmodifiedSince))) 1082 } 1083 if len(xMsClientRequestID) > 0 { 1084 preparer = autorest.DecoratePreparer(preparer, 1085 autorest.WithHeader("x-ms-client-request-id", autorest.String(xMsClientRequestID))) 1086 } 1087 if len(xMsDate) > 0 { 1088 preparer = autorest.DecoratePreparer(preparer, 1089 autorest.WithHeader("x-ms-date", autorest.String(xMsDate))) 1090 } 1091 if len(client.XMsVersion) > 0 { 1092 preparer = autorest.DecoratePreparer(preparer, 1093 autorest.WithHeader("x-ms-version", autorest.String(client.XMsVersion))) 1094 } 1095 return preparer.Prepare((client.defaultRequest()).WithContext(ctx)) 1096 } 1097 1098 // DeleteSender sends the Delete request. The method will close the 1099 // http.Response Body if it receives an error. 1100 func (client adl2PathClient) DeleteSender(req *http.Request) (*http.Response, error) { 1101 sd := autorest.GetSendDecorators(req.Context(), autorest.DoRetryForStatusCodes(client.RetryAttempts, client.RetryDuration, autorest.StatusCodesForRetry...)) 1102 return autorest.SendWithSender(client, req, sd...) 1103 } 1104 1105 // DeleteResponder handles the response to the Delete request. The method always 1106 // closes the http.Response Body. 1107 func (client adl2PathClient) DeleteResponder(resp *http.Response) (result autorest.Response, err error) { 1108 err = autorest.Respond( 1109 resp, 1110 client.ByInspecting(), 1111 azure.WithErrorUnlessStatusCode(http.StatusOK), 1112 autorest.ByClosing()) 1113 result.Response = resp 1114 return 1115 } 1116 1117 func (client adl2PathClient) GetProperties(ctx context.Context, filesystem string, pathParameter string, action adl2.PathGetPropertiesAction, upn *bool, xMsLeaseID string, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, xMsClientRequestID string, timeout *int32, xMsDate string) (result autorest.Response, err error) { 1118 req, err := client.GetPropertiesPreparer(ctx, filesystem, pathParameter, action, upn, xMsLeaseID, ifMatch, ifNoneMatch, ifModifiedSince, ifUnmodifiedSince, xMsClientRequestID, timeout, xMsDate) 1119 if err != nil { 1120 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "GetProperties", nil, "Failure preparing request") 1121 return 1122 } 1123 1124 resp, err := client.GetPropertiesSender(req) 1125 if err != nil { 1126 result.Response = resp 1127 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "GetProperties", resp, "Failure sending request") 1128 return 1129 } 1130 1131 result, err = client.GetPropertiesResponder(resp) 1132 if err != nil { 1133 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "GetProperties", resp, "Failure responding to request") 1134 } 1135 1136 return 1137 } 1138 1139 // GetPropertiesPreparer prepares the GetProperties request. 1140 func (client adl2PathClient) GetPropertiesPreparer(ctx context.Context, filesystem string, pathParameter string, action adl2.PathGetPropertiesAction, upn *bool, xMsLeaseID string, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, xMsClientRequestID string, timeout *int32, xMsDate string) (*http.Request, error) { 1141 urlParameters := map[string]interface{}{ 1142 "accountName": client.AccountName, 1143 "dnsSuffix": client.DNSSuffix, 1144 } 1145 1146 pathParameters := map[string]interface{}{ 1147 "filesystem": autorest.Encode("path", filesystem), 1148 "path": autorest.Encode("path", pathParameter), 1149 } 1150 1151 queryParameters := map[string]interface{}{} 1152 if len(string(action)) > 0 { 1153 queryParameters["action"] = autorest.Encode("query", action) 1154 } 1155 if upn != nil { 1156 queryParameters["upn"] = autorest.Encode("query", *upn) 1157 } 1158 if timeout != nil { 1159 queryParameters["timeout"] = autorest.Encode("query", *timeout) 1160 } 1161 1162 preparer := autorest.CreatePreparer( 1163 autorest.AsHead(), 1164 autorest.WithCustomBaseURL("http://{accountName}.{dnsSuffix}", urlParameters), 1165 autorest.WithPathParameters("/{filesystem}/{path}", pathParameters), 1166 autorest.WithQueryParameters(queryParameters)) 1167 if len(xMsLeaseID) > 0 { 1168 preparer = autorest.DecoratePreparer(preparer, 1169 autorest.WithHeader("x-ms-lease-id", autorest.String(xMsLeaseID))) 1170 } 1171 if len(ifMatch) > 0 { 1172 preparer = autorest.DecoratePreparer(preparer, 1173 autorest.WithHeader("If-Match", autorest.String(ifMatch))) 1174 } 1175 if len(ifNoneMatch) > 0 { 1176 preparer = autorest.DecoratePreparer(preparer, 1177 autorest.WithHeader("If-None-Match", autorest.String(ifNoneMatch))) 1178 } 1179 if len(ifModifiedSince) > 0 { 1180 preparer = autorest.DecoratePreparer(preparer, 1181 autorest.WithHeader("If-Modified-Since", autorest.String(ifModifiedSince))) 1182 } 1183 if len(ifUnmodifiedSince) > 0 { 1184 preparer = autorest.DecoratePreparer(preparer, 1185 autorest.WithHeader("If-Unmodified-Since", autorest.String(ifUnmodifiedSince))) 1186 } 1187 if len(xMsClientRequestID) > 0 { 1188 preparer = autorest.DecoratePreparer(preparer, 1189 autorest.WithHeader("x-ms-client-request-id", autorest.String(xMsClientRequestID))) 1190 } 1191 if len(xMsDate) > 0 { 1192 preparer = autorest.DecoratePreparer(preparer, 1193 autorest.WithHeader("x-ms-date", autorest.String(xMsDate))) 1194 } 1195 if len(client.XMsVersion) > 0 { 1196 preparer = autorest.DecoratePreparer(preparer, 1197 autorest.WithHeader("x-ms-version", autorest.String(client.XMsVersion))) 1198 } 1199 return preparer.Prepare((client.defaultRequest()).WithContext(ctx)) 1200 } 1201 1202 // GetPropertiesSender sends the GetProperties request. The method will close the 1203 // http.Response Body if it receives an error. 1204 func (client adl2PathClient) GetPropertiesSender(req *http.Request) (*http.Response, error) { 1205 sd := autorest.GetSendDecorators(req.Context(), autorest.DoRetryForStatusCodes(client.RetryAttempts, client.RetryDuration, autorest.StatusCodesForRetry...)) 1206 return autorest.SendWithSender(client, req, sd...) 1207 } 1208 1209 // GetPropertiesResponder handles the response to the GetProperties request. The method always 1210 // closes the http.Response Body. 1211 func (client adl2PathClient) GetPropertiesResponder(resp *http.Response) (result autorest.Response, err error) { 1212 err = autorest.Respond( 1213 resp, 1214 client.ByInspecting(), 1215 azure.WithErrorUnlessStatusCode(http.StatusOK), 1216 autorest.ByClosing()) 1217 result.Response = resp 1218 return 1219 } 1220 1221 func (client adl2PathClient) Lease(ctx context.Context, xMsLeaseAction adl2.PathLeaseAction, filesystem string, pathParameter string, xMsLeaseDuration *int32, xMsLeaseBreakPeriod *int32, xMsLeaseID string, xMsProposedLeaseID string, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, xMsClientRequestID string, timeout *int32, xMsDate string) (result autorest.Response, err error) { 1222 req, err := client.LeasePreparer(ctx, xMsLeaseAction, filesystem, pathParameter, xMsLeaseDuration, xMsLeaseBreakPeriod, xMsLeaseID, xMsProposedLeaseID, ifMatch, ifNoneMatch, ifModifiedSince, ifUnmodifiedSince, xMsClientRequestID, timeout, xMsDate) 1223 if err != nil { 1224 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Lease", nil, "Failure preparing request") 1225 return 1226 } 1227 1228 resp, err := client.LeaseSender(req) 1229 if err != nil { 1230 result.Response = resp 1231 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Lease", resp, "Failure sending request") 1232 return 1233 } 1234 1235 result, err = client.LeaseResponder(resp) 1236 if err != nil { 1237 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Lease", resp, "Failure responding to request") 1238 } 1239 1240 return 1241 } 1242 1243 // LeasePreparer prepares the Lease request. 1244 func (client adl2PathClient) LeasePreparer(ctx context.Context, xMsLeaseAction adl2.PathLeaseAction, filesystem string, pathParameter string, xMsLeaseDuration *int32, xMsLeaseBreakPeriod *int32, xMsLeaseID string, xMsProposedLeaseID string, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, xMsClientRequestID string, timeout *int32, xMsDate string) (*http.Request, error) { 1245 urlParameters := map[string]interface{}{ 1246 "accountName": client.AccountName, 1247 "dnsSuffix": client.DNSSuffix, 1248 } 1249 1250 pathParameters := map[string]interface{}{ 1251 "filesystem": autorest.Encode("path", filesystem), 1252 "path": autorest.Encode("path", pathParameter), 1253 } 1254 1255 queryParameters := map[string]interface{}{} 1256 if timeout != nil { 1257 queryParameters["timeout"] = autorest.Encode("query", *timeout) 1258 } 1259 1260 preparer := autorest.CreatePreparer( 1261 autorest.AsPost(), 1262 autorest.WithCustomBaseURL("http://{accountName}.{dnsSuffix}", urlParameters), 1263 autorest.WithPathParameters("/{filesystem}/{path}", pathParameters), 1264 autorest.WithQueryParameters(queryParameters), 1265 autorest.WithHeader("x-ms-lease-action", autorest.String(xMsLeaseAction))) 1266 if xMsLeaseDuration != nil { 1267 preparer = autorest.DecoratePreparer(preparer, 1268 autorest.WithHeader("x-ms-lease-duration", autorest.String(*xMsLeaseDuration))) 1269 } 1270 if xMsLeaseBreakPeriod != nil { 1271 preparer = autorest.DecoratePreparer(preparer, 1272 autorest.WithHeader("x-ms-lease-break-period", autorest.String(*xMsLeaseBreakPeriod))) 1273 } 1274 if len(xMsLeaseID) > 0 { 1275 preparer = autorest.DecoratePreparer(preparer, 1276 autorest.WithHeader("x-ms-lease-id", autorest.String(xMsLeaseID))) 1277 } 1278 if len(xMsProposedLeaseID) > 0 { 1279 preparer = autorest.DecoratePreparer(preparer, 1280 autorest.WithHeader("x-ms-proposed-lease-id", autorest.String(xMsProposedLeaseID))) 1281 } 1282 if len(ifMatch) > 0 { 1283 preparer = autorest.DecoratePreparer(preparer, 1284 autorest.WithHeader("If-Match", autorest.String(ifMatch))) 1285 } 1286 if len(ifNoneMatch) > 0 { 1287 preparer = autorest.DecoratePreparer(preparer, 1288 autorest.WithHeader("If-None-Match", autorest.String(ifNoneMatch))) 1289 } 1290 if len(ifModifiedSince) > 0 { 1291 preparer = autorest.DecoratePreparer(preparer, 1292 autorest.WithHeader("If-Modified-Since", autorest.String(ifModifiedSince))) 1293 } 1294 if len(ifUnmodifiedSince) > 0 { 1295 preparer = autorest.DecoratePreparer(preparer, 1296 autorest.WithHeader("If-Unmodified-Since", autorest.String(ifUnmodifiedSince))) 1297 } 1298 if len(xMsClientRequestID) > 0 { 1299 preparer = autorest.DecoratePreparer(preparer, 1300 autorest.WithHeader("x-ms-client-request-id", autorest.String(xMsClientRequestID))) 1301 } 1302 if len(xMsDate) > 0 { 1303 preparer = autorest.DecoratePreparer(preparer, 1304 autorest.WithHeader("x-ms-date", autorest.String(xMsDate))) 1305 } 1306 if len(client.XMsVersion) > 0 { 1307 preparer = autorest.DecoratePreparer(preparer, 1308 autorest.WithHeader("x-ms-version", autorest.String(client.XMsVersion))) 1309 } 1310 return preparer.Prepare((client.defaultRequest()).WithContext(ctx)) 1311 } 1312 1313 // LeaseSender sends the Lease request. The method will close the 1314 // http.Response Body if it receives an error. 1315 func (client adl2PathClient) LeaseSender(req *http.Request) (*http.Response, error) { 1316 sd := autorest.GetSendDecorators(req.Context(), autorest.DoRetryForStatusCodes(client.RetryAttempts, client.RetryDuration, autorest.StatusCodesForRetry...)) 1317 return autorest.SendWithSender(client, req, sd...) 1318 } 1319 1320 // LeaseResponder handles the response to the Lease request. The method always 1321 // closes the http.Response Body. 1322 func (client adl2PathClient) LeaseResponder(resp *http.Response) (result autorest.Response, err error) { 1323 err = autorest.Respond( 1324 resp, 1325 client.ByInspecting(), 1326 azure.WithErrorUnlessStatusCode(http.StatusOK, http.StatusCreated, http.StatusAccepted), 1327 autorest.ByClosing()) 1328 result.Response = resp 1329 return 1330 } 1331 1332 func (client adl2PathClient) List(ctx context.Context, recursive bool, filesystem string, directory string, continuation string, maxResults *int32, upn *bool, xMsClientRequestID string, timeout *int32, xMsDate string) (result adl2PathList, err error) { 1333 req, err := client.ListPreparer(ctx, recursive, filesystem, directory, continuation, maxResults, upn, xMsClientRequestID, timeout, xMsDate) 1334 if err != nil { 1335 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "List", nil, "Failure preparing request") 1336 return 1337 } 1338 1339 resp, err := client.ListSender(req) 1340 if err != nil { 1341 result.Response = autorest.Response{Response: resp} 1342 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "List", resp, "Failure sending request") 1343 return 1344 } 1345 1346 result, err = client.ListResponder(resp) 1347 if err != nil { 1348 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "List", resp, "Failure responding to request") 1349 } 1350 1351 return 1352 } 1353 1354 // ListPreparer prepares the List request. 1355 func (client adl2PathClient) ListPreparer(ctx context.Context, recursive bool, filesystem string, directory string, continuation string, maxResults *int32, upn *bool, xMsClientRequestID string, timeout *int32, xMsDate string) (*http.Request, error) { 1356 urlParameters := map[string]interface{}{ 1357 "accountName": client.AccountName, 1358 "dnsSuffix": client.DNSSuffix, 1359 } 1360 1361 pathParameters := map[string]interface{}{ 1362 "filesystem": autorest.Encode("path", filesystem), 1363 } 1364 1365 queryParameters := map[string]interface{}{ 1366 "recursive": autorest.Encode("query", recursive), 1367 "resource": autorest.Encode("query", "filesystem"), 1368 } 1369 if len(directory) > 0 { 1370 queryParameters["directory"] = autorest.Encode("query", directory) 1371 } 1372 if len(continuation) > 0 { 1373 queryParameters["continuation"] = autorest.Encode("query", continuation) 1374 } 1375 if maxResults != nil { 1376 queryParameters["maxresults"] = autorest.Encode("query", *maxResults) 1377 } 1378 if upn != nil { 1379 queryParameters["upn"] = autorest.Encode("query", *upn) 1380 } 1381 if timeout != nil { 1382 queryParameters["timeout"] = autorest.Encode("query", *timeout) 1383 } 1384 1385 preparer := autorest.CreatePreparer( 1386 autorest.AsGet(), 1387 autorest.WithCustomBaseURL("http://{accountName}.{dnsSuffix}", urlParameters), 1388 autorest.WithPathParameters("/{filesystem}", pathParameters), 1389 autorest.WithQueryParameters(queryParameters)) 1390 if len(xMsClientRequestID) > 0 { 1391 preparer = autorest.DecoratePreparer(preparer, 1392 autorest.WithHeader("x-ms-client-request-id", autorest.String(xMsClientRequestID))) 1393 } 1394 if len(xMsDate) > 0 { 1395 preparer = autorest.DecoratePreparer(preparer, 1396 autorest.WithHeader("x-ms-date", autorest.String(xMsDate))) 1397 } 1398 if len(client.XMsVersion) > 0 { 1399 preparer = autorest.DecoratePreparer(preparer, 1400 autorest.WithHeader("x-ms-version", autorest.String(client.XMsVersion))) 1401 } 1402 return preparer.Prepare((client.defaultRequest()).WithContext(ctx)) 1403 } 1404 1405 // ListSender sends the List request. The method will close the 1406 // http.Response Body if it receives an error. 1407 func (client adl2PathClient) ListSender(req *http.Request) (*http.Response, error) { 1408 sd := autorest.GetSendDecorators(req.Context(), autorest.DoRetryForStatusCodes(client.RetryAttempts, client.RetryDuration, autorest.StatusCodesForRetry...)) 1409 return autorest.SendWithSender(client, req, sd...) 1410 } 1411 1412 // ListResponder handles the response to the List request. The method always 1413 // closes the http.Response Body. 1414 func (client adl2PathClient) ListResponder(resp *http.Response) (result adl2PathList, err error) { 1415 err = autorest.Respond( 1416 resp, 1417 client.ByInspecting(), 1418 azure.WithErrorUnlessStatusCode(http.StatusOK), 1419 autorest.ByUnmarshallingJSON(&result), 1420 autorest.ByClosing()) 1421 result.Response = autorest.Response{Response: resp} 1422 return 1423 } 1424 1425 func (client adl2PathClient) Read(ctx context.Context, filesystem string, pathParameter string, rangeParameter string, xMsLeaseID string, xMsRangeGetContentMd5 *bool, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, xMsClientRequestID string, timeout *int32, xMsDate string) (result adl2.ReadCloser, err error) { 1426 req, err := client.ReadPreparer(ctx, filesystem, pathParameter, rangeParameter, xMsLeaseID, xMsRangeGetContentMd5, ifMatch, ifNoneMatch, ifModifiedSince, ifUnmodifiedSince, xMsClientRequestID, timeout, xMsDate) 1427 if err != nil { 1428 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Read", nil, "Failure preparing request") 1429 return 1430 } 1431 1432 resp, err := client.ReadSender(req) 1433 if err != nil { 1434 result.Response = autorest.Response{Response: resp} 1435 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Read", resp, "Failure sending request") 1436 return 1437 } 1438 1439 result, err = client.ReadResponder(resp) 1440 if err != nil { 1441 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Read", resp, "Failure responding to request") 1442 } 1443 1444 return 1445 } 1446 1447 // ReadPreparer prepares the Read request. 1448 func (client adl2PathClient) ReadPreparer(ctx context.Context, filesystem string, pathParameter string, rangeParameter string, xMsLeaseID string, xMsRangeGetContentMd5 *bool, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, xMsClientRequestID string, timeout *int32, xMsDate string) (*http.Request, error) { 1449 urlParameters := map[string]interface{}{ 1450 "accountName": client.AccountName, 1451 "dnsSuffix": client.DNSSuffix, 1452 } 1453 1454 pathParameters := map[string]interface{}{ 1455 "filesystem": autorest.Encode("path", filesystem), 1456 "path": autorest.Encode("path", pathParameter), 1457 } 1458 1459 queryParameters := map[string]interface{}{} 1460 if timeout != nil { 1461 queryParameters["timeout"] = autorest.Encode("query", *timeout) 1462 } 1463 1464 preparer := autorest.CreatePreparer( 1465 autorest.AsGet(), 1466 autorest.WithCustomBaseURL("http://{accountName}.{dnsSuffix}", urlParameters), 1467 autorest.WithPathParameters("/{filesystem}/{path}", pathParameters), 1468 autorest.WithQueryParameters(queryParameters)) 1469 if len(rangeParameter) > 0 { 1470 preparer = autorest.DecoratePreparer(preparer, 1471 autorest.WithHeader("Range", autorest.String(rangeParameter))) 1472 } 1473 if len(xMsLeaseID) > 0 { 1474 preparer = autorest.DecoratePreparer(preparer, 1475 autorest.WithHeader("x-ms-lease-id", autorest.String(xMsLeaseID))) 1476 } 1477 if xMsRangeGetContentMd5 != nil { 1478 preparer = autorest.DecoratePreparer(preparer, 1479 autorest.WithHeader("x-ms-range-get-content-md5", autorest.String(*xMsRangeGetContentMd5))) 1480 } 1481 if len(ifMatch) > 0 { 1482 preparer = autorest.DecoratePreparer(preparer, 1483 autorest.WithHeader("If-Match", autorest.String(ifMatch))) 1484 } 1485 if len(ifNoneMatch) > 0 { 1486 preparer = autorest.DecoratePreparer(preparer, 1487 autorest.WithHeader("If-None-Match", autorest.String(ifNoneMatch))) 1488 } 1489 if len(ifModifiedSince) > 0 { 1490 preparer = autorest.DecoratePreparer(preparer, 1491 autorest.WithHeader("If-Modified-Since", autorest.String(ifModifiedSince))) 1492 } 1493 if len(ifUnmodifiedSince) > 0 { 1494 preparer = autorest.DecoratePreparer(preparer, 1495 autorest.WithHeader("If-Unmodified-Since", autorest.String(ifUnmodifiedSince))) 1496 } 1497 if len(xMsClientRequestID) > 0 { 1498 preparer = autorest.DecoratePreparer(preparer, 1499 autorest.WithHeader("x-ms-client-request-id", autorest.String(xMsClientRequestID))) 1500 } 1501 if len(xMsDate) > 0 { 1502 preparer = autorest.DecoratePreparer(preparer, 1503 autorest.WithHeader("x-ms-date", autorest.String(xMsDate))) 1504 } 1505 if len(client.XMsVersion) > 0 { 1506 preparer = autorest.DecoratePreparer(preparer, 1507 autorest.WithHeader("x-ms-version", autorest.String(client.XMsVersion))) 1508 } 1509 return preparer.Prepare((client.defaultRequest()).WithContext(ctx)) 1510 } 1511 1512 // ReadSender sends the Read request. The method will close the 1513 // http.Response Body if it receives an error. 1514 func (client adl2PathClient) ReadSender(req *http.Request) (*http.Response, error) { 1515 sd := autorest.GetSendDecorators(req.Context(), autorest.DoRetryForStatusCodes(client.RetryAttempts, client.RetryDuration, autorest.StatusCodesForRetry...)) 1516 return autorest.SendWithSender(client, req, sd...) 1517 } 1518 1519 // ReadResponder handles the response to the Read request. The method always 1520 // closes the http.Response Body. 1521 func (client adl2PathClient) ReadResponder(resp *http.Response) (result adl2.ReadCloser, err error) { 1522 result.Value = &resp.Body 1523 err = autorest.Respond( 1524 resp, 1525 client.ByInspecting(), 1526 azure.WithErrorUnlessStatusCode(http.StatusOK, http.StatusPartialContent)) 1527 result.Response = autorest.Response{Response: resp} 1528 return 1529 } 1530 1531 func (client adl2PathClient) Update(ctx context.Context, action adl2.PathUpdateAction, filesystem string, pathParameter string, position *int64, retainUncommittedData *bool, closeParameter *bool, contentLength *int64, contentMD5 string, xMsLeaseID string, xMsCacheControl string, xMsContentType string, xMsContentDisposition string, xMsContentEncoding string, xMsContentLanguage string, xMsContentMd5 string, xMsProperties string, xMsOwner string, xMsGroup string, xMsPermissions string, xMsACL string, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, requestBody io.ReadCloser, xMsClientRequestID string, timeout *int32, xMsDate string) (result autorest.Response, err error) { 1532 req, err := client.UpdatePreparer(ctx, action, filesystem, pathParameter, position, retainUncommittedData, closeParameter, contentLength, contentMD5, xMsLeaseID, xMsCacheControl, xMsContentType, xMsContentDisposition, xMsContentEncoding, xMsContentLanguage, xMsContentMd5, xMsProperties, xMsOwner, xMsGroup, xMsPermissions, xMsACL, ifMatch, ifNoneMatch, ifModifiedSince, ifUnmodifiedSince, requestBody, xMsClientRequestID, timeout, xMsDate) 1533 if err != nil { 1534 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Update", nil, "Failure preparing request") 1535 return 1536 } 1537 1538 resp, err := client.UpdateSender(req) 1539 if err != nil { 1540 result.Response = resp 1541 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Update", resp, "Failure sending request") 1542 return 1543 } 1544 1545 result, err = client.UpdateResponder(resp) 1546 if err != nil { 1547 err = autorest.NewErrorWithError(err, "storagedatalake.adl2PathClient", "Update", resp, "Failure responding to request") 1548 } 1549 1550 return 1551 } 1552 1553 // UpdatePreparer prepares the Update request. 1554 func (client adl2PathClient) UpdatePreparer(ctx context.Context, action adl2.PathUpdateAction, filesystem string, pathParameter string, position *int64, retainUncommittedData *bool, closeParameter *bool, contentLength *int64, contentMD5 string, xMsLeaseID string, xMsCacheControl string, xMsContentType string, xMsContentDisposition string, xMsContentEncoding string, xMsContentLanguage string, xMsContentMd5 string, xMsProperties string, xMsOwner string, xMsGroup string, xMsPermissions string, xMsACL string, ifMatch string, ifNoneMatch string, ifModifiedSince string, ifUnmodifiedSince string, requestBody io.ReadCloser, xMsClientRequestID string, timeout *int32, xMsDate string) (*http.Request, error) { 1555 urlParameters := map[string]interface{}{ 1556 "accountName": client.AccountName, 1557 "dnsSuffix": client.DNSSuffix, 1558 } 1559 1560 pathParameters := map[string]interface{}{ 1561 "filesystem": autorest.Encode("path", filesystem), 1562 "path": autorest.Encode("path", pathParameter), 1563 } 1564 1565 queryParameters := map[string]interface{}{ 1566 "action": autorest.Encode("query", action), 1567 } 1568 if position != nil { 1569 queryParameters["position"] = autorest.Encode("query", *position) 1570 } 1571 if retainUncommittedData != nil { 1572 // query params need to be lower case otherwise azure-storage-blob-go's 1573 // SharedKeyCredential signing won't work: 1574 // https://github.com/Azure/azure-storage-blob-go/issues/146 1575 queryParameters["retainuncommitteddata"] = autorest.Encode("query", *retainUncommittedData) 1576 } 1577 if closeParameter != nil { 1578 queryParameters["close"] = autorest.Encode("query", *closeParameter) 1579 } 1580 if timeout != nil { 1581 queryParameters["timeout"] = autorest.Encode("query", *timeout) 1582 } 1583 1584 preparer := autorest.CreatePreparer( 1585 autorest.AsContentType("application/octet-stream"), 1586 autorest.AsPatch(), 1587 autorest.WithCustomBaseURL("http://{accountName}.{dnsSuffix}", urlParameters), 1588 autorest.WithPathParameters("/{filesystem}/{path}", pathParameters), 1589 autorest.WithQueryParameters(queryParameters)) 1590 if requestBody != nil { 1591 preparer = autorest.DecoratePreparer(preparer, 1592 autorest.WithFile(requestBody)) 1593 } 1594 if contentLength != nil { 1595 preparer = autorest.DecoratePreparer(preparer, 1596 autorest.WithHeader("Content-Length", autorest.String(*contentLength))) 1597 } 1598 if len(contentMD5) > 0 { 1599 preparer = autorest.DecoratePreparer(preparer, 1600 autorest.WithHeader("Content-MD5", autorest.String(contentMD5))) 1601 } 1602 if len(xMsLeaseID) > 0 { 1603 preparer = autorest.DecoratePreparer(preparer, 1604 autorest.WithHeader("x-ms-lease-id", autorest.String(xMsLeaseID))) 1605 } 1606 if len(xMsCacheControl) > 0 { 1607 preparer = autorest.DecoratePreparer(preparer, 1608 autorest.WithHeader("x-ms-cache-control", autorest.String(xMsCacheControl))) 1609 } 1610 if len(xMsContentType) > 0 { 1611 preparer = autorest.DecoratePreparer(preparer, 1612 autorest.WithHeader("x-ms-content-type", autorest.String(xMsContentType))) 1613 } 1614 if len(xMsContentDisposition) > 0 { 1615 preparer = autorest.DecoratePreparer(preparer, 1616 autorest.WithHeader("x-ms-content-disposition", autorest.String(xMsContentDisposition))) 1617 } 1618 if len(xMsContentEncoding) > 0 { 1619 preparer = autorest.DecoratePreparer(preparer, 1620 autorest.WithHeader("x-ms-content-encoding", autorest.String(xMsContentEncoding))) 1621 } 1622 if len(xMsContentLanguage) > 0 { 1623 preparer = autorest.DecoratePreparer(preparer, 1624 autorest.WithHeader("x-ms-content-language", autorest.String(xMsContentLanguage))) 1625 } 1626 if len(xMsContentMd5) > 0 { 1627 preparer = autorest.DecoratePreparer(preparer, 1628 autorest.WithHeader("x-ms-content-md5", autorest.String(xMsContentMd5))) 1629 } 1630 if len(xMsProperties) > 0 { 1631 preparer = autorest.DecoratePreparer(preparer, 1632 autorest.WithHeader("x-ms-properties", autorest.String(xMsProperties))) 1633 } 1634 if len(xMsOwner) > 0 { 1635 preparer = autorest.DecoratePreparer(preparer, 1636 autorest.WithHeader("x-ms-owner", autorest.String(xMsOwner))) 1637 } 1638 if len(xMsGroup) > 0 { 1639 preparer = autorest.DecoratePreparer(preparer, 1640 autorest.WithHeader("x-ms-group", autorest.String(xMsGroup))) 1641 } 1642 if len(xMsPermissions) > 0 { 1643 preparer = autorest.DecoratePreparer(preparer, 1644 autorest.WithHeader("x-ms-permissions", autorest.String(xMsPermissions))) 1645 } 1646 if len(xMsACL) > 0 { 1647 preparer = autorest.DecoratePreparer(preparer, 1648 autorest.WithHeader("x-ms-acl", autorest.String(xMsACL))) 1649 } 1650 if len(ifMatch) > 0 { 1651 preparer = autorest.DecoratePreparer(preparer, 1652 autorest.WithHeader("If-Match", autorest.String(ifMatch))) 1653 } 1654 if len(ifNoneMatch) > 0 { 1655 preparer = autorest.DecoratePreparer(preparer, 1656 autorest.WithHeader("If-None-Match", autorest.String(ifNoneMatch))) 1657 } 1658 if len(ifModifiedSince) > 0 { 1659 preparer = autorest.DecoratePreparer(preparer, 1660 autorest.WithHeader("If-Modified-Since", autorest.String(ifModifiedSince))) 1661 } 1662 if len(ifUnmodifiedSince) > 0 { 1663 preparer = autorest.DecoratePreparer(preparer, 1664 autorest.WithHeader("If-Unmodified-Since", autorest.String(ifUnmodifiedSince))) 1665 } 1666 if len(xMsClientRequestID) > 0 { 1667 preparer = autorest.DecoratePreparer(preparer, 1668 autorest.WithHeader("x-ms-client-request-id", autorest.String(xMsClientRequestID))) 1669 } 1670 if len(xMsDate) > 0 { 1671 preparer = autorest.DecoratePreparer(preparer, 1672 autorest.WithHeader("x-ms-date", autorest.String(xMsDate))) 1673 } 1674 if len(client.XMsVersion) > 0 { 1675 preparer = autorest.DecoratePreparer(preparer, 1676 autorest.WithHeader("x-ms-version", autorest.String(client.XMsVersion))) 1677 } 1678 return preparer.Prepare((client.defaultRequest()).WithContext(ctx)) 1679 } 1680 1681 // UpdateSender sends the Update request. The method will close the 1682 // http.Response Body if it receives an error. 1683 func (client adl2PathClient) UpdateSender(req *http.Request) (*http.Response, error) { 1684 1685 sd := autorest.GetSendDecorators(req.Context(), autorest.DoRetryForStatusCodes(client.RetryAttempts, client.RetryDuration, autorest.StatusCodesForRetry...)) 1686 return autorest.SendWithSender(client, req, sd...) 1687 } 1688 1689 // UpdateResponder handles the response to the Update request. The method always 1690 // closes the http.Response Body. 1691 func (client adl2PathClient) UpdateResponder(resp *http.Response) (result autorest.Response, err error) { 1692 err = autorest.Respond( 1693 resp, 1694 client.ByInspecting(), 1695 azure.WithErrorUnlessStatusCode(http.StatusOK, http.StatusAccepted), 1696 autorest.ByClosing()) 1697 result.Response = resp 1698 return 1699 } 1700 1701 func (client adl2PathClient) defaultRequest() *http.Request { 1702 r := &http.Request{} 1703 r.GetBody = func() (io.ReadCloser, error) { 1704 if r.Body == nil { 1705 return http.NoBody, nil 1706 } else if seeker, ok := r.Body.(io.ReadSeeker); ok { 1707 // internally goofys always uses seekable 1708 // readers, so we can rewind on 1709 // retry. autorest makes a copy of the buffer 1710 // and this avoids that waste 1711 _, err := seeker.Seek(0, 0) 1712 return &ReadSeekerCloser{seeker}, err 1713 } else { 1714 panic(fmt.Sprintf("Wrong type: %T", r.Body)) 1715 } 1716 } 1717 return r 1718 } 1719 1720 type adl2PathList struct { 1721 autorest.Response `json:"-"` 1722 Paths *[]adl2Path `json:"paths,omitempty"` 1723 } 1724 1725 type adl2Path struct { 1726 Name *string `json:"name,omitempty"` 1727 IsDirectory adl2Bool `json:"isDirectory,omitempty"` 1728 LastModified *string `json:"lastModified,omitempty"` 1729 ETag *string `json:"eTag,omitempty"` 1730 ContentLength *adl2Int64 `json:"contentLength,omitempty"` 1731 Owner *string `json:"owner,omitempty"` 1732 Group *string `json:"group,omitempty"` 1733 Permissions *string `json:"permissions,omitempty"` 1734 } 1735 1736 func (p adl2Path) isDirectory() bool { 1737 return p.IsDirectory.boolValue() 1738 } 1739 1740 func (p adl2Path) contentLength() int64 { 1741 if p.ContentLength == nil { 1742 return 0 1743 } else { 1744 return p.ContentLength.intValue() 1745 } 1746 } 1747 1748 type adl2Bool struct { 1749 bool 1750 } 1751 1752 func (b adl2Bool) boolValue() bool { 1753 return b.bool 1754 } 1755 1756 func (b *adl2Bool) UnmarshalJSON(buf []byte) error { 1757 v := string(buf) 1758 b.bool = v == "true" || v == "\"true\"" || v == "'true'" 1759 return nil 1760 } 1761 1762 type adl2Int64 struct { 1763 int64 1764 } 1765 1766 func (b *adl2Int64) intValue() int64 { 1767 return b.int64 1768 } 1769 1770 func (b *adl2Int64) UnmarshalJSON(buf []byte) error { 1771 if len(buf) == 0 { 1772 return fmt.Errorf("no input") 1773 } 1774 if buf[0] == '"' { 1775 var v string 1776 err := json.Unmarshal(buf, &v) 1777 if err != nil { 1778 return err 1779 } 1780 b.int64, err = strconv.ParseInt(v, 10, 64) 1781 return err 1782 } else { 1783 err := json.Unmarshal(buf, &b.int64) 1784 return err 1785 } 1786 }