Azure IoT common library
Fork of azure_c_shared_utility by
httpapiexsas.c@25:8507bf644fdf, 2017-04-21 (annotated)
- Committer:
- AzureIoTClient
- Date:
- Fri Apr 21 14:51:10 2017 -0700
- Revision:
- 25:8507bf644fdf
- Parent:
- 19:2e0811512ceb
1.1.13
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
Azure.IoT Build | 0:fa2de1b79154 | 1 | // Copyright (c) Microsoft. All rights reserved. |
Azure.IoT Build | 0:fa2de1b79154 | 2 | // Licensed under the MIT license. See LICENSE file in the project root for full license information. |
Azure.IoT Build | 0:fa2de1b79154 | 3 | |
Azure.IoT Build | 0:fa2de1b79154 | 4 | #include <stdlib.h> |
Azure.IoT Build | 0:fa2de1b79154 | 5 | #include "azure_c_shared_utility/gballoc.h" |
Azure.IoT Build | 0:fa2de1b79154 | 6 | #include <stddef.h> |
Azure.IoT Build | 0:fa2de1b79154 | 7 | #include <time.h> |
Azure.IoT Build | 0:fa2de1b79154 | 8 | #include "azure_c_shared_utility/agenttime.h" |
Azure.IoT Build | 0:fa2de1b79154 | 9 | #include "azure_c_shared_utility/strings.h" |
Azure.IoT Build | 0:fa2de1b79154 | 10 | #include "azure_c_shared_utility/buffer_.h" |
Azure.IoT Build | 0:fa2de1b79154 | 11 | #include "azure_c_shared_utility/sastoken.h" |
Azure.IoT Build | 0:fa2de1b79154 | 12 | #include "azure_c_shared_utility/httpheaders.h" |
Azure.IoT Build | 0:fa2de1b79154 | 13 | #include "azure_c_shared_utility/httpapiex.h" |
Azure.IoT Build | 0:fa2de1b79154 | 14 | #include "azure_c_shared_utility/httpapiexsas.h" |
Azure.IoT Build | 6:c55b013dfc2a | 15 | #include "azure_c_shared_utility/xlogging.h" |
Azure.IoT Build | 0:fa2de1b79154 | 16 | |
Azure.IoT Build | 0:fa2de1b79154 | 17 | typedef struct HTTPAPIEX_SAS_STATE_TAG |
Azure.IoT Build | 0:fa2de1b79154 | 18 | { |
Azure.IoT Build | 0:fa2de1b79154 | 19 | STRING_HANDLE key; |
Azure.IoT Build | 0:fa2de1b79154 | 20 | STRING_HANDLE uriResource; |
Azure.IoT Build | 0:fa2de1b79154 | 21 | STRING_HANDLE keyName; |
Azure.IoT Build | 0:fa2de1b79154 | 22 | }HTTPAPIEX_SAS_STATE; |
Azure.IoT Build | 0:fa2de1b79154 | 23 | |
Azure.IoT Build | 0:fa2de1b79154 | 24 | |
Azure.IoT Build | 0:fa2de1b79154 | 25 | HTTPAPIEX_SAS_HANDLE HTTPAPIEX_SAS_Create(STRING_HANDLE key, STRING_HANDLE uriResource, STRING_HANDLE keyName) |
Azure.IoT Build | 0:fa2de1b79154 | 26 | { |
Azure.IoT Build | 0:fa2de1b79154 | 27 | HTTPAPIEX_SAS_HANDLE result = NULL; |
Azure.IoT Build | 0:fa2de1b79154 | 28 | if (key == NULL) |
Azure.IoT Build | 0:fa2de1b79154 | 29 | { |
Azure.IoT Build | 0:fa2de1b79154 | 30 | /*Codes_SRS_HTTPAPIEXSAS_06_001: [If the parameter key is NULL then HTTPAPIEX_SAS_Create shall return NULL.]*/ |
AzureIoTClient | 1:9190c0f4d23a | 31 | LogError("No key passed to HTTPAPIEX_SAS_Create."); |
Azure.IoT Build | 0:fa2de1b79154 | 32 | } |
Azure.IoT Build | 0:fa2de1b79154 | 33 | else if (uriResource == NULL) |
Azure.IoT Build | 0:fa2de1b79154 | 34 | { |
Azure.IoT Build | 0:fa2de1b79154 | 35 | /*Codes_SRS_HTTPAPIEXSAS_06_002: [If the parameter uriResource is NULL then HTTPAPIEX_SAS_Create shall return NULL.]*/ |
AzureIoTClient | 1:9190c0f4d23a | 36 | LogError("No uri resource passed to HTTPAPIEX_SAS_Create."); |
Azure.IoT Build | 0:fa2de1b79154 | 37 | } |
Azure.IoT Build | 0:fa2de1b79154 | 38 | else if (keyName == NULL) |
Azure.IoT Build | 0:fa2de1b79154 | 39 | { |
Azure.IoT Build | 0:fa2de1b79154 | 40 | /*Codes_SRS_HTTPAPIEXSAS_06_003: [If the parameter keyName is NULL then HTTPAPIEX_SAS_Create shall return NULL.]*/ |
AzureIoTClient | 1:9190c0f4d23a | 41 | LogError("No key name passed to HTTPAPIEX_SAS_Create."); |
Azure.IoT Build | 0:fa2de1b79154 | 42 | } |
Azure.IoT Build | 0:fa2de1b79154 | 43 | else |
Azure.IoT Build | 0:fa2de1b79154 | 44 | { |
AzureIoTClient | 7:1af47e3a19b6 | 45 | /*Codes_SRS_HTTPAPIEXSAS_01_001: [ HTTPAPIEX_SAS_Create shall create a new instance of HTTPAPIEX_SAS and return a non-NULL handle to it. ]*/ |
AzureIoTClient | 25:8507bf644fdf | 46 | HTTPAPIEX_SAS_STATE* state = (HTTPAPIEX_SAS_STATE*)malloc(sizeof(HTTPAPIEX_SAS_STATE)); |
Azure.IoT Build | 0:fa2de1b79154 | 47 | /*Codes_SRS_HTTPAPIEXSAS_06_004: [If there are any other errors in the instantiation of this handle then HTTPAPIEX_SAS_Create shall return NULL.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 48 | if (state != NULL) |
Azure.IoT Build | 0:fa2de1b79154 | 49 | { |
Azure.IoT Build | 0:fa2de1b79154 | 50 | state->key = NULL; |
Azure.IoT Build | 0:fa2de1b79154 | 51 | state->uriResource = NULL; |
Azure.IoT Build | 0:fa2de1b79154 | 52 | state->keyName = NULL; |
Azure.IoT Build | 0:fa2de1b79154 | 53 | if (((state->key = STRING_clone(key)) == NULL) || |
Azure.IoT Build | 0:fa2de1b79154 | 54 | ((state->uriResource = STRING_clone(uriResource)) == NULL) || |
Azure.IoT Build | 0:fa2de1b79154 | 55 | ((state->keyName = STRING_clone(keyName)) == NULL)) |
Azure.IoT Build | 0:fa2de1b79154 | 56 | { |
Azure.IoT Build | 0:fa2de1b79154 | 57 | /*Codes_SRS_HTTPAPIEXSAS_06_004: [If there are any other errors in the instantiation of this handle then HTTPAPIEX_SAS_Create shall return NULL.]*/ |
AzureIoTClient | 1:9190c0f4d23a | 58 | LogError("Unable to clone the arguments."); |
Azure.IoT Build | 0:fa2de1b79154 | 59 | HTTPAPIEX_SAS_Destroy(state); |
Azure.IoT Build | 0:fa2de1b79154 | 60 | } |
Azure.IoT Build | 0:fa2de1b79154 | 61 | else |
Azure.IoT Build | 0:fa2de1b79154 | 62 | { |
Azure.IoT Build | 0:fa2de1b79154 | 63 | result = state; |
Azure.IoT Build | 0:fa2de1b79154 | 64 | } |
Azure.IoT Build | 0:fa2de1b79154 | 65 | } |
Azure.IoT Build | 0:fa2de1b79154 | 66 | } |
Azure.IoT Build | 0:fa2de1b79154 | 67 | return result; |
Azure.IoT Build | 0:fa2de1b79154 | 68 | } |
Azure.IoT Build | 0:fa2de1b79154 | 69 | |
Azure.IoT Build | 0:fa2de1b79154 | 70 | void HTTPAPIEX_SAS_Destroy(HTTPAPIEX_SAS_HANDLE handle) |
Azure.IoT Build | 0:fa2de1b79154 | 71 | { |
Azure.IoT Build | 0:fa2de1b79154 | 72 | /*Codes_SRS_HTTPAPIEXSAS_06_005: [If the parameter handle is NULL then HTTAPIEX_SAS_Destroy shall do nothing and return.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 73 | if (handle) |
Azure.IoT Build | 0:fa2de1b79154 | 74 | { |
Azure.IoT Build | 0:fa2de1b79154 | 75 | HTTPAPIEX_SAS_STATE* state = (HTTPAPIEX_SAS_STATE*)handle; |
Azure.IoT Build | 0:fa2de1b79154 | 76 | /*Codes_SRS_HTTPAPIEXSAS_06_006: [HTTAPIEX_SAS_Destroy shall deallocate any structures denoted by the parameter handle.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 77 | if (state->key) |
Azure.IoT Build | 0:fa2de1b79154 | 78 | { |
Azure.IoT Build | 0:fa2de1b79154 | 79 | STRING_delete(state->key); |
Azure.IoT Build | 0:fa2de1b79154 | 80 | } |
Azure.IoT Build | 0:fa2de1b79154 | 81 | if (state->uriResource) |
Azure.IoT Build | 0:fa2de1b79154 | 82 | { |
Azure.IoT Build | 0:fa2de1b79154 | 83 | STRING_delete(state->uriResource); |
Azure.IoT Build | 0:fa2de1b79154 | 84 | } |
Azure.IoT Build | 0:fa2de1b79154 | 85 | if (state->keyName) |
Azure.IoT Build | 0:fa2de1b79154 | 86 | { |
Azure.IoT Build | 0:fa2de1b79154 | 87 | STRING_delete(state->keyName); |
Azure.IoT Build | 0:fa2de1b79154 | 88 | } |
Azure.IoT Build | 0:fa2de1b79154 | 89 | free(state); |
Azure.IoT Build | 0:fa2de1b79154 | 90 | } |
Azure.IoT Build | 0:fa2de1b79154 | 91 | } |
Azure.IoT Build | 0:fa2de1b79154 | 92 | |
Azure.IoT Build | 0:fa2de1b79154 | 93 | HTTPAPIEX_RESULT HTTPAPIEX_SAS_ExecuteRequest(HTTPAPIEX_SAS_HANDLE sasHandle, HTTPAPIEX_HANDLE handle, HTTPAPI_REQUEST_TYPE requestType, const char* relativePath, HTTP_HEADERS_HANDLE requestHttpHeadersHandle, BUFFER_HANDLE requestContent, unsigned int* statusCode, HTTP_HEADERS_HANDLE responseHeadersHandle, BUFFER_HANDLE responseContent) |
Azure.IoT Build | 0:fa2de1b79154 | 94 | { |
Azure.IoT Build | 0:fa2de1b79154 | 95 | /*Codes_SRS_HTTPAPIEXSAS_06_007: [If the parameter sasHandle is NULL then HTTPAPIEX_SAS_ExecuteRequest shall simply invoke HTTPAPIEX_ExecuteRequest with the remaining parameters (following sasHandle) as its arguments and shall return immediately with the result of that call as the result of HTTPAPIEX_SAS_ExecuteRequest.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 96 | if (sasHandle != NULL) |
Azure.IoT Build | 0:fa2de1b79154 | 97 | { |
Azure.IoT Build | 0:fa2de1b79154 | 98 | /*Codes_SRS_HTTPAPIEXSAS_06_008: [if the parameter requestHttpHeadersHandle is NULL then fallthrough.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 99 | if (requestHttpHeadersHandle != NULL) |
Azure.IoT Build | 0:fa2de1b79154 | 100 | { |
Azure.IoT Build | 0:fa2de1b79154 | 101 | /*Codes_SRS_HTTPAPIEXSAS_06_009: [HTTPHeaders_FindHeaderValue shall be invoked with the requestHttpHeadersHandle as its first argument and the string "Authorization" as its second argument.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 102 | /*Codes_SRS_HTTPAPIEXSAS_06_010: [If the return result of the invocation of HTTPHeaders_FindHeaderValue is NULL then fallthrough.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 103 | if (HTTPHeaders_FindHeaderValue(requestHttpHeadersHandle, "Authorization") != NULL) |
Azure.IoT Build | 0:fa2de1b79154 | 104 | { |
Azure.IoT Build | 0:fa2de1b79154 | 105 | HTTPAPIEX_SAS_STATE* state = (HTTPAPIEX_SAS_STATE*)sasHandle; |
Azure.IoT Build | 0:fa2de1b79154 | 106 | /*Codes_SRS_HTTPAPIEXSAS_06_018: [A value of type time_t that shall be known as currentTime is obtained from calling get_time.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 107 | time_t currentTime = get_time(NULL); |
Azure.IoT Build | 0:fa2de1b79154 | 108 | /*Codes_SRS_HTTPAPIEXSAS_06_019: [If the value of currentTime is (time_t)-1 is then fallthrough.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 109 | if (currentTime == (time_t)-1) |
Azure.IoT Build | 0:fa2de1b79154 | 110 | { |
AzureIoTClient | 1:9190c0f4d23a | 111 | LogError("Time does not appear to be working."); |
Azure.IoT Build | 0:fa2de1b79154 | 112 | } |
Azure.IoT Build | 0:fa2de1b79154 | 113 | else |
Azure.IoT Build | 0:fa2de1b79154 | 114 | { |
Azure.IoT Build | 0:fa2de1b79154 | 115 | /*Codes_SRS_HTTPAPIEXSAS_06_011: [SASToken_Create shall be invoked.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 116 | /*Codes_SRS_HTTPAPIEXSAS_06_012: [If the return result of SASToken_Create is NULL then fallthrough.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 117 | size_t expiry = (size_t)(difftime(currentTime, 0) + 3600); |
Azure.IoT Build | 0:fa2de1b79154 | 118 | STRING_HANDLE newSASToken = SASToken_Create(state->key, state->uriResource, state->keyName, expiry); |
Azure.IoT Build | 0:fa2de1b79154 | 119 | if (newSASToken != NULL) |
Azure.IoT Build | 0:fa2de1b79154 | 120 | { |
Azure.IoT Build | 0:fa2de1b79154 | 121 | /*Codes_SRS_HTTPAPIEXSAS_06_013: [HTTPHeaders_ReplaceHeaderNameValuePair shall be invoked with "Authorization" as its second argument and STRING_c_str (newSASToken) as its third argument.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 122 | if (HTTPHeaders_ReplaceHeaderNameValuePair(requestHttpHeadersHandle, "Authorization", STRING_c_str(newSASToken)) != HTTP_HEADERS_OK) |
Azure.IoT Build | 0:fa2de1b79154 | 123 | { |
Azure.IoT Build | 0:fa2de1b79154 | 124 | /*Codes_SRS_HTTPAPIEXSAS_06_014: [If the result of the invocation of HTTPHeaders_ReplaceHeaderNameValuePair is NOT HTTP_HEADERS_OK then fallthrough.]*/ |
AzureIoTClient | 1:9190c0f4d23a | 125 | LogError("Unable to replace the old SAS Token."); |
Azure.IoT Build | 0:fa2de1b79154 | 126 | } |
Azure.IoT Build | 0:fa2de1b79154 | 127 | /*Codes_SRS_HTTPAPIEXSAS_06_015: [STRING_delete(newSASToken) will be invoked.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 128 | STRING_delete(newSASToken); |
Azure.IoT Build | 0:fa2de1b79154 | 129 | } |
Azure.IoT Build | 0:fa2de1b79154 | 130 | else |
Azure.IoT Build | 0:fa2de1b79154 | 131 | { |
AzureIoTClient | 1:9190c0f4d23a | 132 | LogError("Unable to create a new SAS token."); |
Azure.IoT Build | 0:fa2de1b79154 | 133 | } |
Azure.IoT Build | 0:fa2de1b79154 | 134 | } |
Azure.IoT Build | 0:fa2de1b79154 | 135 | } |
Azure.IoT Build | 0:fa2de1b79154 | 136 | } |
Azure.IoT Build | 0:fa2de1b79154 | 137 | } |
Azure.IoT Build | 0:fa2de1b79154 | 138 | /*Codes_SRS_HTTPAPIEXSAS_06_016: [HTTPAPIEX_ExecuteRequest with the remaining parameters (following sasHandle) as its arguments will be invoked and the result of that call is the result of HTTPAPIEX_SAS_ExecuteRequest.]*/ |
Azure.IoT Build | 0:fa2de1b79154 | 139 | return HTTPAPIEX_ExecuteRequest(handle,requestType,relativePath,requestHttpHeadersHandle,requestContent,statusCode,responseHeadersHandle,responseContent); |
Azure.IoT Build | 0:fa2de1b79154 | 140 | } |