1// Set Date header value for authorization
2// Should be UTC GMT string
3pm.variables.set("header_date", new Date().toUTCString());
4
5// Get hash of all header-name:value
6const headers = pm.request.getHeaders({ ignoreCase: true, enabled: true });
7
8// Construct Signature value for Authorization header
9var signatureParts = [
10 pm.request.method.toUpperCase(),
11 headers["content-encoding"] || "",
12 headers["content-language"] || "",
13 headers["content-length"] || "",
14// pm.request.body ? pm.request.body.toString().length || "" : "",
15 headers["content-md5"] || "",
16 headers["content-type"] || "",
17 headers["x-ms-date"] ? "" : (pm.variables.get("header_date") || ""),
18 headers["if-modified-since"] || "",
19 headers["if-match"] || "",
20 headers["if-none-match"] || "",
21 headers["if-unmodified-since"] || "",
22 headers["range"] || ""
23];
24
25// Construct CanonicalizedHeaders
26const canonicalHeaderNames = [];
27Object.keys(headers).forEach(key => {
28 if (key.startsWith("x-ms-")) {
29 canonicalHeaderNames.push(key);
30 }
31});
32// Sort headers lexographically by name
33canonicalHeaderNames.sort();
34
35const canonicalHeaderParts = [];
36canonicalHeaderNames.forEach(key => {
37 let value = pm.request.getHeaders({ ignoreCase: true, enabled: true })[key];
38
39 // Populate variables
40 value = pm.variables.replaceIn(value);
41
42 // Replace whitespace in value but not if its within quotes
43 if (!value.startsWith("\"")) {
44 value = value.replace(/\s+/, " ");
45 }
46
47 canonicalHeaderParts.push(`${key}:${value}`);
48});
49
50// Add headers to signature
51signatureParts.push.apply(signatureParts, canonicalHeaderParts);
52
53// Construct CanonicalizedResource
54const canonicalResourceParts = [
55 `/${pm.variables.get("azure_storage_account")}${pm.request.url.getPath()}`
56];
57const canonicalQueryNames = [];
58pm.request.url.query.each(query => {
59 canonicalQueryNames.push(query.key.toLowerCase());
60});
61canonicalQueryNames.sort();
62canonicalQueryNames.forEach(queryName => {
63 const value = pm.request.url.query.get(queryName);
64
65 // NOTE: This does not properly explode multiple same query params' values
66 // and turn them into comma-separated list
67 canonicalResourceParts.push(`${queryName}:${value}`);
68});
69// Add resource to signature
70signatureParts.push.apply(signatureParts, canonicalResourceParts);
71
72console.log("Signature Parts", signatureParts);
73
74// Now, construct signature raw string
75const signatureRaw = signatureParts.join("\n");
76
77console.log("Signature String", JSON.stringify(signatureRaw));
78
79// Hash it using HMAC-SHA256 and then encode using base64
80const storageKey = pm.variables.get("azure_storage_key");
81const signatureBytes = CryptoJS.HmacSHA256(signatureRaw, CryptoJS.enc.Base64.parse(storageKey));
82const signatureEncoded = signatureBytes.toString(CryptoJS.enc.Base64);
83
84console.log("Storage Account", pm.variables.get("azure_storage_account"));
85console.log("Storage Key", storageKey);
86
87// Finally, make it available for headers
88pm.variables.set("header_authorization",
89 `SharedKey ${pm.variables.get("azure_storage_account")}:${signatureEncoded}`);
javascript