A music player that connects to your cloud/distributed storage.
5
fork

Configure Feed

Select the types of activity you want to include in your feed.

at main 225 lines 5.8 kB view raw
1module Sources.Services.Azure.Authorization exposing (Computation(..), SignatureDependencies, StorageMethod(..), makeSignature, presignedUrl) 2 3{-| Resources: 4 5 - <https://docs.microsoft.com/en-us/rest/api/storageservices/constructing-an-account-sas#account-sas-example> 6 - <https://docs.microsoft.com/en-us/rest/api/storageservices/Constructing-a-Service-SAS?redirectedfrom=MSDN> 7 8-} 9 10import Binary 11import BinaryBase64 12import Common 13import Cryptography.Hmac as Hmac 14import DateFormat as Date 15import Dict.Ext as Dict 16import SHA 17import Sources exposing (SourceData) 18import Sources.Processing exposing (HttpMethod) 19import String.Ext as String 20import Time 21import Url 22 23 24 25-- Types 26 27 28type Computation 29 = List 30 | Read 31 32 33type StorageMethod 34 = Blob 35 | File 36 37 38 39-- Public functions 40 41 42presignedUrl : 43 StorageMethod 44 -> Computation 45 -> HttpMethod 46 -> Int 47 -> Time.Posix 48 -> SourceData 49 -> String 50 -> List ( String, String ) 51 -> String 52presignedUrl storageMethod computation _ _ currentTime srcData pathToFile params = 53 let 54 azure = 55 srcData 56 57 accountName = 58 Dict.fetchUnknown "accountName" azure 59 60 accountKey = 61 Dict.fetchUnknown "accountKey" azure 62 63 container = 64 Dict.fetchUnknown "container" azure 65 66 -- {var} Time (y-MM-ddTHH:mmZ) 67 expiryTime = 68 Date.format 69 [ Date.yearNumber 70 , Date.text "-" 71 , Date.monthFixed 72 , Date.text "-" 73 , Date.dayOfMonthFixed 74 , Date.text "T" 75 , Date.hourMilitaryFixed 76 , Date.text ":" 77 , Date.minuteFixed 78 , Date.text "Z" 79 ] 80 Time.utc 81 (currentTime 82 |> Time.posixToMillis 83 |> (+) 3600000 84 |> Time.millisToPosix 85 ) 86 87 -- {var} Other 88 permissions = 89 case computation of 90 List -> 91 "l" 92 93 Read -> 94 "r" 95 96 resourceType = 97 case storageMethod of 98 Blob -> 99 "blob" 100 101 File -> 102 "file" 103 104 resType = 105 case storageMethod of 106 Blob -> 107 "container" 108 109 File -> 110 "directory" 111 112 -- Signature 113 signatureStuff = 114 { accountKey = accountKey 115 , accountName = accountName 116 , expiryTime = expiryTime 117 , permissions = permissions 118 , protocol = "https" 119 , resources = "co" 120 , services = "bf" 121 , startTime = "" 122 , version = "2017-04-17" 123 } 124 in 125 String.concat 126 [ "https://" 127 , Url.percentEncode accountName 128 , "." 129 , Url.percentEncode resourceType 130 , ".core.windows.net/" 131 , Url.percentEncode container 132 , "/" 133 , Url.percentEncode (String.chopStart "/" pathToFile) 134 135 -- Start query params 136 , case Common.queryString params of 137 "" -> 138 "?" 139 140 qs -> 141 qs 142 143 -- Query params for certain requests 144 , case computation of 145 List -> 146 "&restype=" ++ resType ++ "&comp=list" 147 148 _ -> 149 "" 150 151 -- Signature things 152 , "&sv=" 153 , Url.percentEncode signatureStuff.version 154 , "&ss=" 155 , Url.percentEncode signatureStuff.services 156 , "&srt=" 157 , Url.percentEncode signatureStuff.resources 158 , "&sp=" 159 , Url.percentEncode signatureStuff.permissions 160 , "&se=" 161 , Url.percentEncode signatureStuff.expiryTime 162 , "&spr=" 163 , Url.percentEncode signatureStuff.protocol 164 , "&sig=" 165 , Url.percentEncode (makeSignature signatureStuff) 166 ] 167 168 169 170-- Signature 171 172 173type alias SignatureDependencies = 174 { accountKey : String 175 , accountName : String 176 , expiryTime : String 177 , permissions : String 178 , protocol : String 179 , resources : String 180 , services : String 181 , startTime : String 182 , version : String 183 } 184 185 186{-| Make a signature. 187 188 >>> makeSignature { accountKey = "93K17Co74T2lDHk2rA+wmb/avIAS6u6lPnZrk2hyT+9+aov82qNhrcXSNGZCzm9mjd4d75/oxxOr6r1JVpgTLA==", accountName = "tsmatsuzsttest0001", expiryTime = "2016-07-08T04:41:20Z", permissions = "rwdlacup", protocol = "https", resources = "sco", services = "bfqt", startTime = "2016-06-29T04:41:20Z", version = "2015-04-05" } 189 "+XuDjuLE1Sv/FrJTLz8YjsaDukWNTKX7e8G8Ew+5aps=" 190 191-} 192makeSignature : SignatureDependencies -> String 193makeSignature { accountKey, accountName, expiryTime, permissions, protocol, resources, services, startTime, version } = 194 let 195 message = 196 -- accountname + "\n" + 197 -- signedpermissions + "\n" + 198 -- signedservice + "\n" + 199 -- signedresourcetype + "\n" + 200 -- signedstart + "\n" + 201 -- signedexpiry + "\n" + 202 -- signedIP + "\n" + 203 -- signedProtocol + "\n" + 204 -- signedversion + "\n" 205 String.join "\n" 206 [ accountName 207 , permissions 208 , services 209 , resources 210 , startTime 211 , expiryTime 212 , "" 213 , protocol 214 , version ++ "\n" 215 ] 216 in 217 accountKey 218 |> BinaryBase64.decode 219 |> Result.withDefault [] 220 |> List.map (Binary.fromDecimal >> Binary.ensureSize 8) 221 |> Binary.concat 222 |> Hmac.encrypt64 SHA.sha256 message 223 |> Binary.chunksOf 8 224 |> List.map Binary.toDecimal 225 |> BinaryBase64.encode