Skip to content

Commit 2f6c475

Browse files
authored
Added support for datalake SAS features in blobs (Azure#16970)
1 parent c32f09c commit 2f6c475

File tree

31 files changed

+1644
-744
lines changed

31 files changed

+1644
-744
lines changed

sdk/storage/azure-storage-blob/CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,8 @@
33
## 12.9.0-beta.3 (Unreleased)
44
- Fixed a bug where interspersed element types returned by page listing would deserialize incorrectly.
55
- Fixed a bug where BlobInputStream would not eTag lock on the blob, resulting in undesirable behavior if the blob was modified in the middle of reading.
6+
- Added support for move and execute permissions on blob SAS and container SAS, and list permissions on blob SAS.
7+
- Added support to specify a preauthorized user id and correlation id for user delegation SAS.
68
- Renamed BlobDownloadToFileOptions.rangeGetContentMd5 to BlobDownloadToFileOptions.retrieveContentRangeMd5
79

810
## 12.9.0-beta.2 (2020-10-08)

sdk/storage/azure-storage-blob/src/main/java/com/azure/storage/blob/implementation/util/BlobSasImplUtil.java

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,10 @@ public class BlobSasImplUtil {
8484

8585
private String contentType;
8686

87+
private String authorizedAadObjectId;
88+
89+
private String correlationId;
90+
8791
/**
8892
* Creates a new {@link BlobSasImplUtil} with the specified parameters
8993
*
@@ -126,6 +130,8 @@ public BlobSasImplUtil(BlobServiceSasSignatureValues sasValues, String container
126130
this.contentEncoding = sasValues.getContentEncoding();
127131
this.contentLanguage = sasValues.getContentLanguage();
128132
this.contentType = sasValues.getContentType();
133+
this.authorizedAadObjectId = sasValues.getPreauthorizedAgentObjectId();
134+
this.correlationId = sasValues.getCorrelationId();
129135
}
130136

131137
/**
@@ -199,6 +205,10 @@ private String encode(UserDelegationKey userDelegationKey, String signature) {
199205
userDelegationKey.getSignedService());
200206
tryAppendQueryParameter(sb, Constants.UrlConstants.SAS_SIGNED_KEY_VERSION,
201207
userDelegationKey.getSignedVersion());
208+
209+
/* Only parameters relevant for user delegation SAS. */
210+
tryAppendQueryParameter(sb, Constants.UrlConstants.SAS_PREAUTHORIZED_AGENT_OBJECT_ID, this.authorizedAadObjectId);
211+
tryAppendQueryParameter(sb, Constants.UrlConstants.SAS_CORRELATION_ID, this.correlationId);
202212
}
203213
tryAppendQueryParameter(sb, Constants.UrlConstants.SAS_SIGNED_RESOURCE, this.resource);
204214
tryAppendQueryParameter(sb, Constants.UrlConstants.SAS_SIGNED_PERMISSIONS, this.permissions);
@@ -314,9 +324,9 @@ private String stringToSign(final UserDelegationKey key, String canonicalName) {
314324
key.getSignedExpiry() == null ? "" : Constants.ISO_8601_UTC_DATE_FORMATTER.format(key.getSignedExpiry()),
315325
key.getSignedService() == null ? "" : key.getSignedService(),
316326
key.getSignedVersion() == null ? "" : key.getSignedVersion(),
317-
"", /* saoid - empty since this applies to HNS only accounts. */
327+
this.authorizedAadObjectId == null ? "" : this.authorizedAadObjectId,
318328
"", /* suoid - empty since this applies to HNS only accounts. */
319-
"", /* cid - empty since this applies to HNS only accounts. */
329+
this.correlationId == null ? "" : this.correlationId,
320330
this.sasIpRange == null ? "" : this.sasIpRange.toString(),
321331
this.protocol == null ? "" : this.protocol.toString(),
322332
version,

sdk/storage/azure-storage-blob/src/main/java/com/azure/storage/blob/sas/BlobContainerSasPermission.java

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,10 @@ public final class BlobContainerSasPermission {
3131

3232
private boolean tagsPermission;
3333

34+
private boolean movePermission;
35+
36+
private boolean executePermission;
37+
3438
/**
3539
* Initializes an {@code BlobContainerSasPermission} object with all fields set to false.
3640
*/
@@ -75,6 +79,12 @@ public static BlobContainerSasPermission parse(String permString) {
7579
case 't':
7680
permissions.tagsPermission = true;
7781
break;
82+
case 'm':
83+
permissions.movePermission = true;
84+
break;
85+
case 'e':
86+
permissions.executePermission = true;
87+
break;
7888
default:
7989
throw new IllegalArgumentException(
8090
String.format(Locale.ROOT, Constants.ENUM_COULD_NOT_BE_PARSED_INVALID_VALUE,
@@ -228,6 +238,42 @@ public BlobContainerSasPermission setTagsPermission(boolean tagsPermission) {
228238
return this;
229239
}
230240

241+
/**
242+
* @return the move permission status.
243+
*/
244+
public boolean hasMovePermission() {
245+
return movePermission;
246+
}
247+
248+
/**
249+
* Sets the move permission status.
250+
*
251+
* @param hasMovePermission Permission status to set
252+
* @return the updated BlobContainerSasPermission object.
253+
*/
254+
public BlobContainerSasPermission setMovePermission(boolean hasMovePermission) {
255+
this.movePermission = hasMovePermission;
256+
return this;
257+
}
258+
259+
/**
260+
* @return the execute permission status.
261+
*/
262+
public boolean hasExecutePermission() {
263+
return executePermission;
264+
}
265+
266+
/**
267+
* Sets the execute permission status.
268+
*
269+
* @param hasExecutePermission Permission status to set
270+
* @return the updated BlobContainerSasPermission object.
271+
*/
272+
public BlobContainerSasPermission setExecutePermission(boolean hasExecutePermission) {
273+
this.executePermission = hasExecutePermission;
274+
return this;
275+
}
276+
231277
/**
232278
* Converts the given permissions to a {@code String}. Using this method will guarantee the permissions are in an
233279
* order accepted by the service.
@@ -272,6 +318,14 @@ public String toString() {
272318
builder.append('t');
273319
}
274320

321+
if (this.movePermission) {
322+
builder.append('m');
323+
}
324+
325+
if (this.executePermission) {
326+
builder.append('e');
327+
}
328+
275329
return builder.toString();
276330
}
277331
}

sdk/storage/azure-storage-blob/src/main/java/com/azure/storage/blob/sas/BlobSasPermission.java

Lines changed: 84 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,12 @@ public final class BlobSasPermission {
2929

3030
private boolean tagsPermission;
3131

32+
private boolean listPermission;
33+
34+
private boolean movePermission;
35+
36+
private boolean executePermission;
37+
3238
/**
3339
* Initializes a {@code BlobSasPermission} object with all fields set to false.
3440
*/
@@ -41,7 +47,8 @@ public BlobSasPermission() {
4147
*
4248
* @param permString A {@code String} which represents the {@code BlobSasPermission}.
4349
* @return A {@code BlobSasPermission} generated from the given {@code String}.
44-
* @throws IllegalArgumentException If {@code permString} contains a character other than r, a, c, w, d, x or t.
50+
* @throws IllegalArgumentException If {@code permString} contains a character other than r, a, c, w, d, x, l, t,
51+
* m, or e.
4552
*/
4653
public static BlobSasPermission parse(String permString) {
4754
BlobSasPermission permissions = new BlobSasPermission();
@@ -70,6 +77,15 @@ public static BlobSasPermission parse(String permString) {
7077
case 't':
7178
permissions.tagsPermission = true;
7279
break;
80+
case 'l':
81+
permissions.listPermission = true;
82+
break;
83+
case 'm':
84+
permissions.movePermission = true;
85+
break;
86+
case 'e':
87+
permissions.executePermission = true;
88+
break;
7389
default:
7490
throw new IllegalArgumentException(
7591
String.format(Locale.ROOT, Constants.ENUM_COULD_NOT_BE_PARSED_INVALID_VALUE,
@@ -205,6 +221,61 @@ public BlobSasPermission setTagsPermission(boolean tagsPermission) {
205221
return this;
206222
}
207223

224+
/**
225+
* @return the list permission status.
226+
*/
227+
public boolean hasListPermission() {
228+
return listPermission;
229+
}
230+
231+
/**
232+
* Sets the list permission status.
233+
*
234+
* @param hasListPermission Permission status to set
235+
* @return the updated BlobSasPermission object.
236+
*/
237+
public BlobSasPermission setListPermission(boolean hasListPermission) {
238+
this.listPermission = hasListPermission;
239+
return this;
240+
}
241+
242+
/**
243+
* @return the move permission status.
244+
*/
245+
public boolean hasMovePermission() {
246+
return movePermission;
247+
}
248+
249+
/**
250+
* Sets the move permission status.
251+
*
252+
* @param hasMovePermission Permission status to set
253+
* @return the updated BlobSasPermission object.
254+
*/
255+
public BlobSasPermission setMovePermission(boolean hasMovePermission) {
256+
this.movePermission = hasMovePermission;
257+
return this;
258+
}
259+
260+
/**
261+
* @return the execute permission status.
262+
*/
263+
public boolean hasExecutePermission() {
264+
return executePermission;
265+
}
266+
267+
/**
268+
* Sets the execute permission status.
269+
*
270+
* @param hasExecutePermission Permission status to set
271+
* @return the updated BlobSasPermission object.
272+
*/
273+
public BlobSasPermission setExecutePermission(boolean hasExecutePermission) {
274+
this.executePermission = hasExecutePermission;
275+
return this;
276+
}
277+
278+
208279
/**
209280
* Converts the given permissions to a {@code String}. Using this method will guarantee the permissions are in an
210281
* order accepted by the service.
@@ -242,10 +313,22 @@ public String toString() {
242313
builder.append('x');
243314
}
244315

316+
if (this.listPermission) {
317+
builder.append('l');
318+
}
319+
245320
if (this.tagsPermission) {
246321
builder.append('t');
247322
}
248323

324+
if (this.movePermission) {
325+
builder.append('m');
326+
}
327+
328+
if (this.executePermission) {
329+
builder.append('e');
330+
}
331+
249332
return builder.toString();
250333
}
251334
}

sdk/storage/azure-storage-blob/src/main/java/com/azure/storage/blob/sas/BlobServiceSasSignatureValues.java

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,10 @@ public final class BlobServiceSasSignatureValues {
7777

7878
private String contentType;
7979

80+
private String preauthorizedAgentObjectId; /* saoid */
81+
82+
private String correlationId;
83+
8084
/**
8185
* Creates an object with empty values for all fields.
8286
* @deprecated Please use {@link #BlobServiceSasSignatureValues(String)},
@@ -486,6 +490,52 @@ public BlobServiceSasSignatureValues setContentType(String contentType) {
486490
return this;
487491
}
488492

493+
/**
494+
* @return The AAD object ID of a user assumed to be authorized by the owner of the user delegation key to perform
495+
* the action granted by the SAS token. The service will validate the SAS token and ensure that the owner of the
496+
* user delegation key has the required permissions before granting access but no additional permission check for
497+
* the agent object id will be performed.
498+
*/
499+
public String getPreauthorizedAgentObjectId() {
500+
return preauthorizedAgentObjectId;
501+
}
502+
503+
/**
504+
* Sets the AAD object ID of a user assumed to be authorized by the owner of the user delegation key to perform the
505+
* action granted by the SAS token.
506+
*
507+
* @param preauthorizedAgentObjectId The AAD object ID of a user assumed to be authorized by the owner of the user
508+
* delegation key to perform the action granted by the SAS token. The service will validate the SAS token and
509+
* ensure that the owner of the user delegation key has the required permissions before granting access but no
510+
* additional permission check for the agent object id will be performed.
511+
* @return the updated BlobServiceSASSignatureValues object
512+
*/
513+
public BlobServiceSasSignatureValues setPreauthorizedAgentObjectId(String preauthorizedAgentObjectId) {
514+
this.preauthorizedAgentObjectId = preauthorizedAgentObjectId;
515+
return this;
516+
}
517+
518+
/**
519+
* @return the correlation id value for the SAS.
520+
*/
521+
public String getCorrelationId() {
522+
return correlationId;
523+
}
524+
525+
/**
526+
* Sets the correlation id value for the SAS.
527+
*
528+
* <p>Note: This parameter is only valid for user delegation SAS. </p>
529+
*
530+
* @param correlationId A correlation ID used to correlate the storage audit logs with the audit logs used by the
531+
* principal generating and distributing SAS.
532+
* @return the updated BlobServiceSasSignatureValues object
533+
*/
534+
public BlobServiceSasSignatureValues setCorrelationId(String correlationId) {
535+
this.correlationId = correlationId;
536+
return this;
537+
}
538+
489539
/**
490540
* Uses an account's shared key credential to sign these signature values to produce the proper SAS query
491541
* parameters.

0 commit comments

Comments
 (0)