Delphi REST GET但不支持POST与AusPost eParcel API一起使用

西布里特

我正在为一个客户的集成项目工作,该客户需要使用Delphi 10.2 Tokyo服务程序中的eParcel REST API创建AusPost发货。

这是Constructor我班上的东西:

constructor TAusPostRESTServices.Create;
begin
  // Create the REST objects

  HTTPBasicAuthenticator := THTTPBasicAuthenticator.Create(API_KEY, API_PASSWORD);
  RESTClient := TRESTClient.Create(BASE_URL);
  RESTResponse := TRESTResponse.Create(nil);
  RESTRequest := TRESTRequest.Create(nil);

  // Set the initial properties

  RESTClient.Params.Clear;
  RESTClient.HandleRedirects := true;
  RESTClient.Authenticator := HTTPBasicAuthenticator;
  RESTClient.RaiseExceptionOn500 := false;

  RESTRequest.Client := RESTClient;
  RESTRequest.Response := RESTResponse;
  RESTRequest.SynchronizedEvents := false;
end;

以及它使用的常量(请注意,帐户和API值来自参考API,可能实际上不起作用)。

const
  BASE_URL = 'https://digitalapi.auspost.com.au/test';
  ACCOUNT = '0000123456';
  API_KEY = '601a4032-6dbd-46aa-9c6c-8c6dacca5e61';
  API_PASSWORD = 'password';

Uses子句至少具有以下内容:

REST.Client, REST.Authenticator.Basic, IPPeerClient, JSON, REST.Types

我尝试使用的eParcel API方法是创建发货获取发货

这是我的Get Shipments Delphi代码的样子(不用担心AJSONValue响应。仍在努力最终将完成什么工作):

function TAusPostRESTServices.GetShipments(var AError: String): Boolean;
var
  AStatusCode: Integer;
  AJSONString: String;
  AJSONValue: TJSonValue;
  AParameter: TRESTRequestParameter;
begin
  // Set the request header info

  RESTRequest.Method := TRESTRequestMethod.rmGET;
  RESTRequest.Resource := '/shipping/v1/shipments';
  RESTRequest.Accept := 'application/json';

  AParameter := RESTRequest.Params.AddItem;
  AParameter.ContentType := ctAPPLICATION_JSON;
  AParameter.name := 'Content-Type';
  AParameter.Value := 'application/json';
  AParameter.Kind := TRESTRequestParameterKind.pkHTTPHEADER;

  RESTRequest.Params.AddHeader('account-number', ACCOUNT);

  try
    try
      RESTRequest.Execute;
    except on E: Exception do
      ;
    end;

    // If the StatusCode is 200, then the REST method worked

    AStatusCode := RESTRequest.Response.StatusCode;

    if AStatusCode <> 200 then
      AError := RESTRequest.Response.Content
    else
    begin
      AJSONValue := TJSonObject.ParseJSONValue(RESTRequest.Response.Content);

      AJSONValue.Free;

      AError := '';
    end;
  finally
    Result := (AError = '');
  end;
end;

这可以正常工作,并从AusPost API文档中包含的示例JSON返回我使用Postman创建的一次试用演示。

{
  "shipments": [
    {
      "shipment_id": "T7sK0EA9HGcAAAFufLYgUxkK",
      "shipment_reference": "My second shipment ref",
      "shipment_creation_date": "2019-10-30T06:42:42+11:00",
      "customer_reference_1": "cb1234",
      "customer_reference_2": "cb2345",
      "sender_references": [
        "cb1234",
        "cb2345"
      ],
      "from": {
        "type": "MERCHANT_LOCATION",
        "lines": [
          "111 Bourke St"
        ],
        "suburb": "Melbourne",
        "postcode": "3000",
        "state": "VIC",
        "apcn": "2468013579",
        "name": "Carl Block",
        "country": "AU"
      },
      "to": {
        "type": "STANDARD_ADDRESS",
        "lines": [
          "PO Box 123"
        ],
        "suburb": "Rye",
        "postcode": "3941",
        "state": "VIC",
        "apcn": "1234567890",
        "name": "Blocked Carl",
        "business_name": "In debt",
        "country": "AU",
        "email": "[email protected]",
        "phone": "0356567567",
        "delivery_instructions": "please leave behind shed"
      },
      "items": [
        {
          "weight": 1,
          "height": 10,
          "length": 10,
          "width": 10,
          "contains_dangerous_goods": false,
          "authority_to_leave": true,
          "safe_drop_enabled": true,
          "allow_partial_delivery": false,
          "item_id": "3mQK0EA9CksAAAFui7YgUxkK",
          "item_reference": "blocked",
          "tracking_details": {
            "article_id": "111JD538925401000930800",
            "consignment_id": "111JD5389254"
          },
          "product_id": "7E55",
          "item_summary": {
            "total_cost": 11.48,
            "total_cost_ex_gst": 11.48,
            "total_gst": 0,
            "status": "Created"
          },
          "item_contents": [],
          "label": {
            "status": "Pending",
            "errors": []
          },
          "postage_details": {
            "price": {
              "calculated_price": 11.48,
              "calculated_price_ex_gst": 11.48,
              "calculated_gst": 0
            }
          }
        },
        {
          "weight": 2.123,
          "height": 10,
          "length": 100.1,
          "width": 10,
          "contains_dangerous_goods": false,
          "authority_to_leave": true,
          "safe_drop_enabled": true,
          "allow_partial_delivery": false,
          "item_id": "9cgK0EA9smIAAAFufrYgUxkK",
          "item_reference": "blocked",
          "tracking_details": {
            "article_id": "111JD538925403000930804",
            "consignment_id": "111JD5389254"
          },
          "product_id": "7E55",
          "item_summary": {
            "total_cost": 23.34,
            "total_cost_ex_gst": 23.34,
            "total_gst": 0,
            "status": "Created"
          },
          "item_contents": [],
          "label": {
            "status": "Pending",
            "errors": []
          },
          "postage_details": {
            "price": {
              "calculated_price": 23.34,
              "calculated_price_ex_gst": 23.34,
              "calculated_gst": 0
            }
          }
        },
        {
          "weight": 1,
          "height": 10,
          "length": 10,
          "width": 10,
          "contains_dangerous_goods": false,
          "authority_to_leave": true,
          "safe_drop_enabled": true,
          "allow_partial_delivery": false,
          "item_id": "_hEK0EA9zIIAAAFuirYgUxkK",
          "item_reference": "blocked",
          "tracking_details": {
            "article_id": "111JD538925402000930807",
            "consignment_id": "111JD5389254"
          },
          "product_id": "7E55",
          "item_summary": {
            "total_cost": 11.48,
            "total_cost_ex_gst": 11.48,
            "total_gst": 0,
            "status": "Created"
          },
          "item_contents": [],
          "label": {
            "status": "Pending",
            "errors": []
          },
          "postage_details": {
            "price": {
              "calculated_price": 11.48,
              "calculated_price_ex_gst": 11.48,
              "calculated_gst": 0
            }
          }
        }
      ],
      "options": {},
      "shipment_summary": {
        "total_cost": 47.41,
        "total_cost_ex_gst": 43.1,
        "fuel_surcharge": 1.11,
        "total_gst": 4.31,
        "status": "Created",
        "tracking_summary": {
          "Created": 3
        },
        "number_of_items": 3
      },
      "movement_type": "DESPATCH",
      "charge_to_account": "1001746337"
    }
  ],
  "pagination": {
    "total_number_of_records": 1,
    "number_of_records_per_page": 1000,
    "current_page_number": 1
  }
}

我的创建货件几乎相同:

function TAusPostRESTServices.CreateShipment(var AError: String): Boolean;
var
  AStatusCode: Integer;
  AJSONString: String;
  AJSONValue: TJSonValue;
  AParameter: TRESTRequestParameter;
begin
  // Set the request header info

  RESTRequest.Method := TRESTRequestMethod.rmPOST;
  RESTRequest.Resource := '/shipping/v1/shipments';
  RESTRequest.Accept := 'application/json';

  AParameter := RESTRequest.Params.AddItem;
  AParameter.ContentType := ctAPPLICATION_JSON;
  AParameter.name := 'Content-Type';
  AParameter.Value := 'application/json';
  AParameter.Kind := TRESTRequestParameterKind.pkHTTPHEADER;

  RESTRequest.Params.AddHeader('account-number', ACCOUNT);

  try
    AJSONString := '{'+
                   '  "shipments": ['+
                   '    {'+
                   '      "shipment_reference": "139301",'+
                   '      "customer_reference_1": "1",'+
                   '      "from": {'+
                   '        "name": "MERCHANT_LOCATION",'+
                   '        "lines": ['+
                   '          "111 Bourke St"'+
                   '        ],'+
                   '        "suburb": "MELBOURNE",'+
                   '        "postcode": "3000",'+
                   '        "state": "VIC"'+
                   '      },'+
                   '      "to": {'+
                   '        "name": "STANDARD_ADDRESS",'+
                   '        "lines": ['+
                   '          "PO Box 123"'+
                   '        ],'+
                   '        "suburb": "Rye",'+
                   '        "state": "VIC",'+
                   '        "postcode": "3941",'+
                   '        "delivery_instructions": "please leave behind shed",'+
                   '        "email": "[email protected]"'+
                   '      },'+
                   '      "items": ['+
                   '        {'+
                   '          "width": 10,'+
                   '          "height": 10,'+
                   '          "length": 10,'+
                   '          "weight": 0.19,'+
                   '          "product_id": "7E55",'+
                   '          "authority_to_leave": true'+
                   '        }'+
                   '      ]'+
                   '    }'+
                   '  ]'+
                   '}';

    RESTRequest.Body.Add(AJSONString, ctAPPLICATION_JSON);

    try
      RESTRequest.Execute;
    except on E: Exception do
      ;
    end;

    // If the StatusCode is 200, then the REST method worked

    AStatusCode := RESTRequest.Response.StatusCode;

    if AStatusCode <> 200 then
      AError := RESTRequest.Response.Content
    else
    begin
      AJSONValue := TJSonObject.ParseJSONValue(RESTRequest.Response.Content);

      AJSONValue.Free;

      AError := '';
    end;
  finally
    Result := (AError = '');
  end;
end;

运行此命令时,状态代码为404,内容文本为

{
  "code": "404",
  "name": "Not Found",
  "message": "Invalid HTTP method POST or request path /shipments. Please refer to the Developer Centre reference at https://developers.auspost.com.au/apis/shipping-and-tracking/reference for correct usage."
}

但是,如果我在Postman中设置了Create Shipment POST,而Raw Body是相同的JSON字符串,则可以正常工作,并且会得到适当的响应:

{
    "shipments": [
        {
            "shipment_id": "QdkK0EA99JoAAAFuba0gUzkF",
            "shipment_reference": "139301",
            "shipment_creation_date": "2019-11-05T11:45:03+11:00",
            "items": [
                {
                    "weight": 0.190,
                    "authority_to_leave": true,
                    "safe_drop_enabled": true,
                    "allow_partial_delivery": true,
                    "item_id": "kwgK0EA9Es8AAAFubq0gUzkF",
                    "tracking_details": {
                        "article_id": "111JD539319101000931501",
                        "consignment_id": "111JD5393191"
                    },
                    "product_id": "7E55",
                    "item_summary": {
                        "total_cost": 17.14,
                        "total_cost_ex_gst": 17.14,
                        "total_gst": 0.00,
                        "status": "Created"
                    },
                    "item_contents": []
                }
            ],
            "options": {},
            "shipment_summary": {
                "total_cost": 17.55,
                "total_cost_ex_gst": 15.95,
                "fuel_surcharge": 0.41,
                "total_gst": 1.60,
                "status": "Created",
                "tracking_summary": {
                    "Created": 1
                },
                "number_of_items": 1
            },
            "movement_type": "DESPATCH",
            "charge_to_account": "1001746337"
        }
    ]
}

我不明白的是为什么Delphi会给我这个404错误。如果我在使用Postman时未在请求中包含正文,则会收到以下响应:

{
    "errors": [
        {
            "code": "400",
            "name": "INVALID_PAYLOAD",
            "message": "Unable to deserialize payload.  Please ensure that the payload is valid JSON. Please note that when assigned, boolean fields can only accept 'true' or 'false' as values."
        }
    ]
}

但是,如果我没有在Delphi的请求中包含主体,则会收到相同的404错误。有谁知道我可以尝试使用我的代码的其他REST API?还是有人成功使用了Delphi的AusPost eParcel API,即使它是通过Indy完成的呢?

西布里特

找到了问题,即使我无法解释。一旦删除了Content-Type参数代码,post方法就可以正常工作。

// AParameter := RESTRequest.Params.AddItem;
// AParameter.ContentType := ctAPPLICATION_JSON;
// AParameter.name := 'Content-Type';
// AParameter.Value := 'application/json';
// AParameter.Kind := TRESTRequestParameterKind.pkHTTPHEADER;

不知何故,包括在请求中只是塞满了东西。没有任何原因的解释,但这可能只是那些Delphi REST库的怪癖之一。

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

与Drupal一起使用Rest API

来自分类Dev

REST POST不支持的媒体类型

来自分类Dev

为什么Window Outlook Rest API不支持Android

来自分类Dev

Coldfusion 11 REST Service与HTTP一起使用,但不适用于HTTPS(404)

来自分类Dev

Web API不支持POST方法

来自分类Dev

Web API不支持POST方法

来自分类Dev

尝试使用Rest API创建Hpalm缺陷时,获取“ 415不支持的媒体类型”

来自分类Dev

Spring Boot Rest服务| 请求方法'GET'不支持

来自分类Dev

Laravel API:此路由不支持POST方法。支持的方法:GET,HEAD

来自分类Dev

该路由不支持POST方法。支持的方法:GET,HEAD。在laravel api中

来自分类Dev

在Delphi REST Server中使用POST时无法获取查询参数的值

来自分类Dev

我正在使用 Post 方法,但 Apache 一直说不支持 GET,为什么?

来自分类Dev

您如何将cURL“ GET”与基于Python的REST API一起用于网络编程?

来自分类Dev

不能将IF NOT与delphi中的集合一起使用

来自分类Dev

不能将IF NOT与delphi中的set一起使用

来自分类Dev

使用nodejs创建与ContentBlocks一起使用的REST API(createjs.org)

来自分类Dev

使用nodejs创建与ContentBlocks一起使用的REST API(createjs.org)

来自分类Dev

在REST API中处理不支持的查询参数是否有约定?

来自分类Dev

与.include一起使用时,对象不支持#inspect

来自分类Dev

为什么将focusout与jQuery一起使用对Firefox却不支持addEventListener呢?

来自分类Dev

将SQL Server与MySQL一起使用时出现“不支持选项”错误

来自分类Dev

当与-Pz一起使用时,grep命令不支持行锚的起始'^'和'$'

来自分类Dev

我应该将核心数据与REST API后端一起使用吗?

来自分类Dev

无法使Rails REST API与Ember.js一起使用

来自分类Dev

WebDAV PROPFIND方法是否应在REST API中与JSON一起使用?

来自分类Dev

在Yii2 REST API中一起使用JSON和JSONP格式

来自分类Dev

Node和Express中的Rest API,与ejs和React.js一起使用

来自分类Dev

无法使Rails REST API与Ember.js一起使用

来自分类Dev

我应该将核心数据与REST API后端一起使用吗?

Related 相关文章

  1. 1

    与Drupal一起使用Rest API

  2. 2

    REST POST不支持的媒体类型

  3. 3

    为什么Window Outlook Rest API不支持Android

  4. 4

    Coldfusion 11 REST Service与HTTP一起使用,但不适用于HTTPS(404)

  5. 5

    Web API不支持POST方法

  6. 6

    Web API不支持POST方法

  7. 7

    尝试使用Rest API创建Hpalm缺陷时,获取“ 415不支持的媒体类型”

  8. 8

    Spring Boot Rest服务| 请求方法'GET'不支持

  9. 9

    Laravel API:此路由不支持POST方法。支持的方法:GET,HEAD

  10. 10

    该路由不支持POST方法。支持的方法:GET,HEAD。在laravel api中

  11. 11

    在Delphi REST Server中使用POST时无法获取查询参数的值

  12. 12

    我正在使用 Post 方法,但 Apache 一直说不支持 GET,为什么?

  13. 13

    您如何将cURL“ GET”与基于Python的REST API一起用于网络编程?

  14. 14

    不能将IF NOT与delphi中的集合一起使用

  15. 15

    不能将IF NOT与delphi中的set一起使用

  16. 16

    使用nodejs创建与ContentBlocks一起使用的REST API(createjs.org)

  17. 17

    使用nodejs创建与ContentBlocks一起使用的REST API(createjs.org)

  18. 18

    在REST API中处理不支持的查询参数是否有约定?

  19. 19

    与.include一起使用时,对象不支持#inspect

  20. 20

    为什么将focusout与jQuery一起使用对Firefox却不支持addEventListener呢?

  21. 21

    将SQL Server与MySQL一起使用时出现“不支持选项”错误

  22. 22

    当与-Pz一起使用时,grep命令不支持行锚的起始'^'和'$'

  23. 23

    我应该将核心数据与REST API后端一起使用吗?

  24. 24

    无法使Rails REST API与Ember.js一起使用

  25. 25

    WebDAV PROPFIND方法是否应在REST API中与JSON一起使用?

  26. 26

    在Yii2 REST API中一起使用JSON和JSONP格式

  27. 27

    Node和Express中的Rest API,与ejs和React.js一起使用

  28. 28

    无法使Rails REST API与Ember.js一起使用

  29. 29

    我应该将核心数据与REST API后端一起使用吗?

热门标签

归档