From: "Chang, Abner" <abner.chang@amd.com>
To: Igor Kulchytskyy <igork@ami.com>,
"devel@edk2.groups.io" <devel@edk2.groups.io>
Cc: "nickle.wang@hpe.com" <nickle.wang@hpe.com>
Subject: Re: [PATCH V4 3/3] RedfishPkg: Redfish functions for REST requests are not fully spec complied
Date: Fri, 19 Aug 2022 07:52:07 +0000 [thread overview]
Message-ID: <MN2PR12MB3966B8FE16C12F79FBA8A13DEA6C9@MN2PR12MB3966.namprd12.prod.outlook.com> (raw)
In-Reply-To: <1660851683-3680-1-git-send-email-igork@ami.com>
[AMD Official Use Only - General]
Reviewed-by: Abner Chang <abner.chang@amd.com>
Thanks!
> -----Original Message-----
> From: Igor Kulchytskyy <igork@ami.com>
> Sent: Friday, August 19, 2022 3:41 AM
> To: devel@edk2.groups.io
> Cc: Chang, Abner <Abner.Chang@amd.com>; nickle.wang@hpe.com; Igor
> Kulchytskyy <igork@ami.com>; Chang, Abner <Abner.Chang@amd.com>
> Subject: [PATCH V4 3/3] RedfishPkg: Redfish functions for REST requests are
> not fully spec complied
>
> [CAUTION: External Email]
>
> There is no function to send POST request with the ContentType different
> from "application\json".
> There is no function to send DELETE request with the body.
>
> Cc: Abner Chang <abner.chang@amd.com>
> Cc: Nickle Wang <nickle.wang@hpe.com>
> Signed-off-by: Igor Kulchytskyy <igork@ami.com>
> ---
> RedfishPkg/Include/Library/RedfishLib.h | 80 +++++++++
> RedfishPkg/PrivateLibrary/RedfishLib/RedfishLib.c | 189
> ++++++++++++++++++++
>
> RedfishPkg/PrivateLibrary/RedfishLib/edk2libredfish/include/redfishService.
> h | 8 +
> RedfishPkg/PrivateLibrary/RedfishLib/edk2libredfish/src/service.c | 41
> ++++-
> 4 files changed, 316 insertions(+), 2 deletions(-)
>
> diff --git a/RedfishPkg/Include/Library/RedfishLib.h
> b/RedfishPkg/Include/Library/RedfishLib.h
> index b2488ab..ce39ce3 100644
> --- a/RedfishPkg/Include/Library/RedfishLib.h
> +++ b/RedfishPkg/Include/Library/RedfishLib.h
> @@ -380,6 +380,49 @@ RedfishPatchToPayload (
> OUT REDFISH_RESPONSE *RedResponse
> );
>
> +
> +/**
> + Use HTTP POST to create new Redfish resource in the Resource Collection.
> +
> + The POST request should be submitted to the Resource Collection in
> + which the new resource is to belong. The Resource Collection is
> + addressed by URI. The Redfish may ignore any service controlled
> + properties. The corresponding redfish response will returned, including
> HTTP StatusCode, Headers and Payload which record any HTTP response
> messages.
> +
> + Callers are responsible for freeing the HTTP StatusCode, Headers and
> + Payload returned in redfish response data.
> +
> + @param[in] RedfishService The Service to access the Redfish
> resources.
> + @param[in] Uri Relative path to address the resource.
> + @param[in] Content JSON represented properties to be update.
> + @param[in] ContentSize Size of the Content to be send to Redfish
> service
> + @param[in] ContentType Type of the Content to be send to Redfish
> service
> + @param[out] RedResponse Pointer to the Redfish response data.
> +
> + @retval EFI_SUCCESS The opeartion is successful, indicates the HTTP
> StatusCode is not
> + NULL and the value is 2XX. The Redfish resource will be
> returned
> + in Payload within RedResponse if server send it back in the
> HTTP
> + response message body.
> + @retval EFI_INVALID_PARAMETER RedfishService, Uri, Content, or
> RedResponse is NULL.
> + @retval EFI_DEVICE_ERROR An unexpected system or network error
> occurred. Callers can get
> + more error info from returned HTTP StatusCode, Headers
> and Payload
> + within RedResponse:
> + 1. If the returned StatusCode is NULL, indicates any error
> happen.
> + 2. If the returned StatusCode is not NULL and the value is
> not 2XX,
> + indicates any error happen.
> +**/
> +EFI_STATUS
> +EFIAPI
> +RedfishPostToUri (
> + IN REDFISH_SERVICE RedfishService,
> + IN CONST CHAR8 *Uri,
> + IN CONST CHAR8 *Content,
> + IN UINTN ContentSize,
> + IN CONST CHAR8 *ContentType,
> + OUT REDFISH_RESPONSE *RedResponse
> + );
> +
> +
> /**
> Use HTTP POST to create a new resource in target payload.
>
> @@ -451,6 +494,43 @@ RedfishDeleteByUri (
> );
>
> /**
> + Use HTTP DELETE to remove a resource.
> +
> + This function uses the RedfishService to remove a Redfish resource
> + which is addressed by input Uri (only the relative path is required).
> + The corresponding redfish response will returned, including HTTP
> + StatusCode, Headers and Payload which record any HTTP response
> messages.
> +
> + Callers are responsible for freeing the HTTP StatusCode, Headers and
> + Payload returned in redfish response data.
> +
> + @param[in] RedfishService The Service to access the Redfish
> resources.
> + @param[in] Uri Relative path to address the resource.
> + @param[in] Content JSON represented properties to be deleted.
> + @param[out] RedResponse Pointer to the Redfish response data.
> +
> + @retval EFI_SUCCESS The opeartion is successful, indicates the HTTP
> StatusCode is not
> + NULL and the value is 2XX, the Redfish resource has been
> removed.
> + If there is any message returned from server, it will be
> returned
> + in Payload within RedResponse.
> + @retval EFI_INVALID_PARAMETER RedfishService, Uri, or RedResponse is
> NULL.
> + @retval EFI_DEVICE_ERROR An unexpected system or network error
> occurred. Callers can get
> + more error info from returned HTTP StatusCode, Headers
> and Payload
> + within RedResponse:
> + 1. If the returned StatusCode is NULL, indicates any error
> happen.
> + 2. If the returned StatusCode is not NULL and the value is
> not 2XX,
> + indicates any error happen.
> +**/
> +EFI_STATUS
> +EFIAPI
> +RedfishDeleteByUriEx (
> + IN REDFISH_SERVICE RedfishService,
> + IN CONST CHAR8 *Uri,
> + IN CONST CHAR8 *Content,
> + OUT REDFISH_RESPONSE *RedResponse
> + );
> +
> +/**
> Dump text in fractions.
>
> @param[in] String ASCII string to dump.
> diff --git a/RedfishPkg/PrivateLibrary/RedfishLib/RedfishLib.c
> b/RedfishPkg/PrivateLibrary/RedfishLib/RedfishLib.c
> index 9f9d377..6c0f426 100644
> --- a/RedfishPkg/PrivateLibrary/RedfishLib/RedfishLib.c
> +++ b/RedfishPkg/PrivateLibrary/RedfishLib/RedfishLib.c
> @@ -583,6 +583,104 @@ RedfishPatchToPayload (
> return EFI_SUCCESS;
> }
>
> +
> +/**
> + Use HTTP POST to create new Redfish resource in the Resource Collection.
> +
> + The POST request should be submitted to the Resource Collection in
> + which the new resource is to belong. The Resource Collection is
> + addressed by URI. The Redfish may ignore any service controlled
> + properties. The corresponding redfish response will returned, including
> HTTP StatusCode, Headers and Payload which record any HTTP response
> messages.
> +
> + Callers are responsible for freeing the HTTP StatusCode, Headers and
> + Payload returned in redfish response data.
> +
> + @param[in] RedfishService The Service to access the Redfish
> resources.
> + @param[in] Uri Relative path to address the resource.
> + @param[in] Content JSON represented properties to be update.
> + @param[in] ContentSize Size of the Content to be send to Redfish
> service
> + @param[in] ContentType Type of the Content to be send to Redfish
> service
> + @param[out] RedResponse Pointer to the Redfish response data.
> +
> + @retval EFI_SUCCESS The opeartion is successful, indicates the HTTP
> StatusCode is not
> + NULL and the value is 2XX. The Redfish resource will be
> returned
> + in Payload within RedResponse if server send it back in the
> HTTP
> + response message body.
> + @retval EFI_INVALID_PARAMETER RedfishService, Uri, Content, or
> RedResponse is NULL.
> + @retval EFI_DEVICE_ERROR An unexpected system or network error
> occurred. Callers can get
> + more error info from returned HTTP StatusCode, Headers
> and Payload
> + within RedResponse:
> + 1. If the returned StatusCode is NULL, indicates any error
> happen.
> + 2. If the returned StatusCode is not NULL and the value is
> not 2XX,
> + indicates any error happen.
> +**/
> +EFI_STATUS
> +EFIAPI
> +RedfishPostToUri (
> + IN REDFISH_SERVICE RedfishService,
> + IN CONST CHAR8 *Uri,
> + IN CONST CHAR8 *Content,
> + IN UINTN ContentSize,
> + IN CONST CHAR8 *ContentType,
> + OUT REDFISH_RESPONSE *RedResponse
> + )
> +{
> + EFI_STATUS Status;
> + EDKII_JSON_VALUE JsonValue;
> +
> + Status = EFI_SUCCESS;
> + JsonValue = NULL;
> +
> + if ((RedfishService == NULL) || (Uri == NULL) || (Content == NULL) ||
> (RedResponse == NULL)) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + ZeroMem (RedResponse, sizeof (REDFISH_RESPONSE));
> +
> + JsonValue = (EDKII_JSON_VALUE)postUriFromService (
> + RedfishService,
> + Uri,
> + Content,
> + ContentSize,
> + ContentType,
> + &(RedResponse->StatusCode)
> + );
> +
> + //
> + // 1. If the returned StatusCode is NULL, indicates any error happen.
> + //
> + if (RedResponse->StatusCode == NULL) {
> + Status = EFI_DEVICE_ERROR;
> + goto ON_EXIT;
> + }
> +
> + //
> + // 2. If the returned StatusCode is not NULL and the value is not 2XX,
> indicates any error happen.
> + // NOTE: If there is any error message returned from server, it will be
> returned in
> + // Payload within RedResponse.
> + //
> + if ((*(RedResponse->StatusCode) < HTTP_STATUS_200_OK) || \
> + (*(RedResponse->StatusCode) >
> HTTP_STATUS_206_PARTIAL_CONTENT))
> + {
> + Status = EFI_DEVICE_ERROR;
> + }
> +
> +ON_EXIT:
> + if (JsonValue != NULL) {
> + RedResponse->Payload = createRedfishPayload (JsonValue,
> RedfishService);
> + if (RedResponse->Payload == NULL) {
> + //
> + // Ignore the error when create RedfishPayload, just free the JsonValue
> since it's not what
> + // we care about if the returned StatusCode is 2XX.
> + //
> + JsonValueFree (JsonValue);
> + }
> + }
> +
> + return Status;
> +}
> +
> +
> /**
> Use HTTP POST to create a new resource in target payload.
>
> @@ -738,6 +836,97 @@ ON_EXIT:
> return Status;
> }
>
> +
> +/**
> + Use HTTP DELETE to remove a resource.
> +
> + This function uses the RedfishService to remove a Redfish resource
> + which is addressed by input Uri (only the relative path is required).
> + The corresponding redfish response will returned, including HTTP
> + StatusCode, Headers and Payload which record any HTTP response
> messages.
> +
> + Callers are responsible for freeing the HTTP StatusCode, Headers and
> + Payload returned in redfish response data.
> +
> + @param[in] RedfishService The Service to access the Redfish
> resources.
> + @param[in] Uri Relative path to address the resource.
> + @param[in] Content JSON represented properties to be deleted.
> + @param[out] RedResponse Pointer to the Redfish response data.
> +
> + @retval EFI_SUCCESS The opeartion is successful, indicates the HTTP
> StatusCode is not
> + NULL and the value is 2XX, the Redfish resource has been
> removed.
> + If there is any message returned from server, it will be
> returned
> + in Payload within RedResponse.
> + @retval EFI_INVALID_PARAMETER RedfishService, Uri, or RedResponse is
> NULL.
> + @retval EFI_DEVICE_ERROR An unexpected system or network error
> occurred. Callers can get
> + more error info from returned HTTP StatusCode, Headers
> and Payload
> + within RedResponse:
> + 1. If the returned StatusCode is NULL, indicates any error
> happen.
> + 2. If the returned StatusCode is not NULL and the value is
> not 2XX,
> + indicates any error happen.
> +**/
> +EFI_STATUS
> +EFIAPI
> +RedfishDeleteByUriEx (
> + IN REDFISH_SERVICE RedfishService,
> + IN CONST CHAR8 *Uri,
> + IN CONST CHAR8 *Content,
> + OUT REDFISH_RESPONSE *RedResponse
> + )
> +{
> + EFI_STATUS Status;
> + EDKII_JSON_VALUE JsonValue;
> +
> + Status = EFI_SUCCESS;
> + JsonValue = NULL;
> +
> + if ((RedfishService == NULL) || (Content == NULL) || (Uri == NULL) ||
> (RedResponse == NULL)) {
> + return EFI_INVALID_PARAMETER;
> + }
> +
> + ZeroMem (RedResponse, sizeof (REDFISH_RESPONSE));
> +
> + JsonValue = (EDKII_JSON_VALUE)deleteUriFromServiceEx (
> + RedfishService,
> + Uri,
> + Content,
> + &(RedResponse->StatusCode)
> + );
> +
> + //
> + // 1. If the returned StatusCode is NULL, indicates any error happen.
> + //
> + if (RedResponse->StatusCode == NULL) {
> + Status = EFI_DEVICE_ERROR;
> + goto ON_EXIT;
> + }
> +
> + //
> + // 2. If the returned StatusCode is not NULL and the value is not 2XX,
> indicates any error happen.
> + // NOTE: If there is any error message returned from server, it will be
> returned in
> + // Payload within RedResponse.
> + //
> + if ((*(RedResponse->StatusCode) < HTTP_STATUS_200_OK) || \
> + (*(RedResponse->StatusCode) >
> HTTP_STATUS_206_PARTIAL_CONTENT))
> + {
> + Status = EFI_DEVICE_ERROR;
> + }
> +
> +ON_EXIT:
> + if (JsonValue != NULL) {
> + RedResponse->Payload = createRedfishPayload (JsonValue,
> RedfishService);
> + if (RedResponse->Payload == NULL) {
> + //
> + // Ignore the error when create RedfishPayload, just free the JsonValue
> since it's not what
> + // we care about if the returned StatusCode is 2XX.
> + //
> + JsonValueFree (JsonValue);
> + }
> + }
> +
> + return Status;
> +}
> +
> /**
> Dump text in fractions.
>
> diff --git
> a/RedfishPkg/PrivateLibrary/RedfishLib/edk2libredfish/include/redfishServic
> e.h
> b/RedfishPkg/PrivateLibrary/RedfishLib/edk2libredfish/include/redfishServic
> e.h
> index 5c13b68..75afadc 100644
> ---
> a/RedfishPkg/PrivateLibrary/RedfishLib/edk2libredfish/include/redfishServic
> e.h
> +++ b/RedfishPkg/PrivateLibrary/RedfishLib/edk2libredfish/include/redfis
> +++ hService.h
> @@ -129,6 +129,14 @@ deleteUriFromService (
> EFI_HTTP_STATUS_CODE **StatusCode
> );
>
> +json_t *
> +deleteUriFromServiceEx (
> + redfishService *service,
> + const char *uri,
> + const char *content,
> + EFI_HTTP_STATUS_CODE **StatusCode
> + );
> +
> redfishPayload *
> getRedfishServiceRoot (
> redfishService *service,
> diff --git a/RedfishPkg/PrivateLibrary/RedfishLib/edk2libredfish/src/service.c
> b/RedfishPkg/PrivateLibrary/RedfishLib/edk2libredfish/src/service.c
> index afa172b..086e04a 100644
> --- a/RedfishPkg/PrivateLibrary/RedfishLib/edk2libredfish/src/service.c
> +++ b/RedfishPkg/PrivateLibrary/RedfishLib/edk2libredfish/src/service.c
> @@ -923,10 +923,12 @@ ON_EXIT:
> return ret;
> }
>
> +
> json_t *
> -deleteUriFromService (
> +deleteUriFromServiceEx (
> redfishService *service,
> const char *uri,
> + const char *content,
> EFI_HTTP_STATUS_CODE **StatusCode
> )
> {
> @@ -937,6 +939,8 @@ deleteUriFromService (
> EFI_HTTP_REQUEST_DATA *RequestData = NULL;
> EFI_HTTP_MESSAGE *RequestMsg = NULL;
> EFI_HTTP_MESSAGE ResponseMsg;
> + CHAR8 ContentLengthStr[80];
> + size_t contentLength;
>
> ret = NULL;
>
> @@ -956,7 +960,7 @@ deleteUriFromService (
> //
> // Step 1: Create HTTP request message with 4 headers:
> //
> - HttpIoHeader = HttpIoCreateHeader ((service->sessionToken || service-
> >basicAuthStr) ? 5 : 4);
> + HttpIoHeader = HttpIoCreateHeader ((service->sessionToken ||
> + service->basicAuthStr) ? 8 : 7);
> if (HttpIoHeader == NULL) {
> ret = NULL;
> goto ON_EXIT;
> @@ -979,6 +983,23 @@ deleteUriFromService (
> Status = HttpIoSetHeader (HttpIoHeader, "Connection", "Keep-Alive");
> ASSERT_EFI_ERROR (Status);
>
> + Status = HttpIoSetHeader (HttpIoHeader, "Content-Type",
> + "application/json"); ASSERT_EFI_ERROR (Status);
> +
> + if(content != NULL){
> + contentLength = strlen (content);
> + AsciiSPrint (
> + ContentLengthStr,
> + sizeof (ContentLengthStr),
> + "%lu",
> + (UINT64)contentLength
> + );
> + Status = HttpIoSetHeader (HttpIoHeader, "Content-Length",
> ContentLengthStr);
> + ASSERT_EFI_ERROR (Status);
> + Status = HttpIoSetHeader (HttpIoHeader, "OData-Version", "4.0");
> + ASSERT_EFI_ERROR (Status);
> + }
> +
> //
> // Step 2: build the rest of HTTP request info.
> //
> @@ -1004,6 +1025,11 @@ deleteUriFromService (
> RequestMsg->HeaderCount = HttpIoHeader->HeaderCount;
> RequestMsg->Headers = HttpIoHeader->Headers;
>
> + if(content != NULL){
> + RequestMsg->BodyLength = contentLength;
> + RequestMsg->Body = (VOID *)content;
> + }
> +
> ZeroMem (&ResponseMsg, sizeof (ResponseMsg));
>
> //
> @@ -1057,6 +1083,17 @@ ON_EXIT:
> return ret;
> }
>
> +json_t *
> +deleteUriFromService (
> + redfishService *service,
> + const char *uri,
> + EFI_HTTP_STATUS_CODE **StatusCode
> + )
> +{
> + return deleteUriFromServiceEx(service, uri, NULL, StatusCode); }
> +
> +
> redfishPayload *
> getRedfishServiceRoot (
> redfishService *service,
> --
> 2.6.1.windows.1
> -The information contained in this message may be confidential and
> proprietary to American Megatrends (AMI). This communication is intended
> to be read only by the individual or entity to whom it is addressed or by their
> designee. If the reader of this message is not the intended recipient, you are
> on notice that any distribution of this message, in any form, is strictly
> prohibited. Please promptly notify the sender by reply e-mail or by
> telephone at 770-246-8600, and then delete or destroy all copies of the
> transmission.
prev parent reply other threads:[~2022-08-19 7:52 UTC|newest]
Thread overview: 2+ messages / expand[flat|nested] mbox.gz Atom feed top
2022-08-18 19:41 [PATCH V4 3/3] RedfishPkg: Redfish functions for REST requests are not fully spec complied Igor Kulchytskyy
2022-08-19 7:52 ` Chang, Abner [this message]
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-list from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=MN2PR12MB3966B8FE16C12F79FBA8A13DEA6C9@MN2PR12MB3966.namprd12.prod.outlook.com \
--to=devel@edk2.groups.io \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox