Get ETag info

I recently ran into a problem where I needed something called “ETag” AKA “@odata.etag” AKA “If-Match” in order to send a PATCH request to IFS.

To save anyone else more struggle than I did, I want to comment here the steps you should take.

Assumptions

  • Connect
  • IFS Cloud
  • Flowscript REST requests

Steps

  1. In your GET step, add into your type declaration the '@odata.etag': text?
  2. If you haven’t added Open Seq; in your flowscript step, go ahead and add it (can be anywhere, I did mine right above the return statement
  3. The next part is confusing, so I will briefly explain then show a real life example…
  4. You must map your response and add a new column to your record or sequence called “etag” using with

Example

Given this type

type SuccessResponseType = {
    value: {
            luname: text,
            keyref: text,
            Objkey: text,
            SelectLine: boolean,
            OrderLineMatch: boolean,
            QtyToReceive: number?,
            CatchQtyToReceive: number?,
            Quantity: number,
            CatchQuantity: number?,
            CatchUom: text,
            DeliveringContract: text,
            DeliveringWarehouseId: text,
            Contract: text,
            ReceivingWarehouseId: text,
            PartNo: text,
            ConfigurationId: text,
            HandlingUnitId: number,
            LotBatchNo: text,
            SerialNo: text,
            EngChgLevel: text,
            WaivDevRejNo: text,
            '@odata.etag': text?
    }*
};

Map a new field called “etag” to the response received from IFS in the return:

return {
    HttpStatusCode       : Response.statusCode,
    ErrorMessage         : ErrorResponse.error.message,
    DetailedErrorMessage : ErrorResponse.error.details.message,
    Result               : {value: SuccessResponse.value.map(t => t with {etag: t."@odata.etag"})}
};

Let’s break it down…

Result is where we would normally see everything we have chosen to receive as defined by the type. But, as you can notice or may have noticed, that having quotes, at symbols, and a period all in the same element can be tricky to overcome. This is where we map the values…

Because of our type, we set our Result to value which is a sequence (table) of our type.

{value: SuccessResponse.value}

We then actually go to map… SuccessResponse.value is where our data is we need to map. Adding .map let’s us define a variable (t in this example but you can use anything you want) and gives us the ability to map to that variable.

{value: SuccessResponse.value.map(t

The next step is to map the variable to itself and update itself with a new column etag and then we want to map the '@odata.etag' column to this new column so we can use it outside of this flowscript step. To accomplish this, we use the with keyword.

{value: SuccessResponse.value.map(t => t with {etag:

Finally, we map the old column to the new using t."@odata.etag". This looks weird, and it only works here!

{value: SuccessResponse.value.map(t => t with {etag: t."@odata.etag"})}

Congratulations! You can now use your newly mapped etag variable to make you DELETE, PUT, and PATCH steps!

Where to add the etag in patch?

It should be passed in as a header (If-Match) like so:

let etag2 = InvPartInTransitLinesGetMsg.Result.value.first().etag;
let Response = HTTP.patchText(
                            ifsURL,
                             {
                               "Accept":"application/json; odata.metadata=minimal",
                               "Content-Type":"application/json; odata.metadata=minimal",
                               "If-Match": etag2
                             },
                             JSON.serialize(ThisBody)
                           );

That’s it for now. Thanks to the Novacura team to help me figure this one out!

5 Likes

Nice work, and thank you for taking the time to write it up!

In case someone is reading this and wondering about the root cause: what’s presented here is work-around for a bug in the REST connector. The bug cases record fields containing a dot (.) to go missing when transferred from the Connector Agent to the Client. When this bug is fixed, you will not need the mapping step.

Note also that the syntax t."@odata.etag" works for any irregularly named record member:

let test = {
  x: 1,
  "A very long label...": "test"
}

return test."A very long label..."; // returns "test"