簡體   English   中英

轉換 CookComputing XMLRpcStruct (IEnumerable<Object> ) 到實際的 C# 類

[英]Convert CookComputing XMLRpcStruct (IEnumerable<Object>) to an actual C# class

因此,我正在使用 CookComputings XMLRPC庫來與InfusionSoft (它是一個非常流行的在線 CRM)對話。 主要方法是:

 [XmlRpcMethod("DataService.query")]
 IEnumerable<object> QuerySubscriptionStatus(string apiKey, 
        string table, int limit, int page, 
        IDictionary queryData, string[] selectedFields);

遺憾的是,我需要使用IEnumerable<object> ,因為 InfusionSoft XML/RPC API 需要它。 我希望不是這樣,但遺憾的是。

由於我使用 .NET 4.5,我想我可以做一個動態轉換:

  var subStatus = proxy.QuerySubscriptionStatus(
      _key, "RecurringOrder", 500, 0, dict, sarray);
  var result = subStatus.Cast<SubscriptionStatus>();

不幸的是,這不起作用,我從 C# 中得到了一個非常令人沮喪的錯誤:

無法將“CookComputing.XmlRpc.XmlRpcStruct”類型的對象轉換為“WBI.Model.SubscriptionStatus”。`

我試過將我的類指定為struct XMLRpcMember()我什至嘗試用XMLRpcMember()標簽指定它,但不,它只是不會轉換。

如何與IEnumerable的數據進行交互?

我嘗試過的類/結構類型

public struct SubStatus
{
    public int AffiliateId;
    public int AutoCharge;
    public double BillingAmt;
    public string BillingCycle;
    public int CC1;
    public int CC2;
    public int ContactId;
    public DateTime EndDate;
    public int Frequency;
    public int Id;
    public DateTime LastBillDate;
    public int LeadAffiliateId;
    public int MaxRetry;
    public int MerchantAccountId;
    public DateTime NextBillDate;
    public int NumDaysBetweenRetry;
    public int OriginatingOrderId;
    public DateTime PaidThruDate;
    public int PaymentGatewayId;
    public int ProductId;
    public int ProgramId;
    public string PromoCode;
    public int Qty;
    public string ReasonStopped;
    public int ShippingOptionId;
    public DateTime StartDate;
    public string Status;
    public int SubscriptionPlanId;
}

我也只是嘗試了一個帶有XMLRpcMember標簽的簡單類:

public class SubscriptionStatus
{
    [XmlRpcMember("AffiliateId")]
    public int AffiliateId { get; set; }
    [XmlRpcMember("AutoCharge")]
    public int AutoCharge { get; set; }
    [XmlRpcMember("BillingAmt")]
    public double BillingAmt { get; set; }
    [XmlRpcMember("BillingCycle")]
    public string BillingCycle { get; set; }
    [XmlRpcMember("CC1")]
    public int CC1 { get; set; }
    [XmlRpcMember("CC2")]
    public int CC2 { get; set; }
    [XmlRpcMember("ContactId")]
    public int ContactId { get; set; }
    [XmlRpcMember("EndDate")]
    public DateTime EndDate { get; set; }
    [XmlRpcMember("Frequency")]
    public int Frequency { get; set; }
    [XmlRpcMember("Id")]
    public int Id { get; set; }
    [XmlRpcMember("LastBillDate")]
    public DateTime LastBillDate { get; set; }
    [XmlRpcMember("LeadAffiliateId")]
    public int LeadAffiliateId { get; set; }
    [XmlRpcMember("MaxRetry")]
    public int MaxRetry { get; set; }
    [XmlRpcMember("MerchantAccountId")]
    public int MerchantAccountId { get; set; }
    [XmlRpcMember("NextBillDate")]
    public DateTime NextBillDate { get; set; }
    [XmlRpcMember("NumDaysBetweenRetry")]
    public int NumDaysBetweenRetry { get; set; }
    [XmlRpcMember("OriginatingOrderId")]
    public int OriginatingOrderId { get; set; }
    [XmlRpcMember("PaidThruDate")]
    public DateTime PaidThruDate { get; set; }
    [XmlRpcMember("PaymentGatewayId")]
    public int PaymentGatewayId { get; set; }
    [XmlRpcMember("ProductId")]
    public int ProductId { get; set; }
    [XmlRpcMember("ProgramId")]
    public int ProgramId { get; set; }
    [XmlRpcMember("PromoCode")]
    public string PromoCode { get; set; }
    [XmlRpcMember("Qty")]
    public int Qty { get; set; }
    [XmlRpcMember("ReasonStopped")]
    public string ReasonStopped { get; set; }
    [XmlRpcMember("ShippingOptionId")]
    public int ShippingOptionId { get; set; }
    [XmlRpcMember("StartDate")]
    public DateTime StartDate { get; set; }
    [XmlRpcMember("Status")]
    public string Status { get; set; }
    [XmlRpcMember("SubscriptionPlanId")]
    public int SubscriptionPlanId { get; set; }
}

因此,經過另一位高級開發人員的一些擴展幫助,結果證明我們能夠對結構進行一些更改:

    private string[] retFlds = { "Id", "ContactId", "OriginatingOrderId", "ProgramId", "SubscriptionPlanId", "ProductId", "StartDate", "NextBillDate", "BillingCycle", "Frequency", "BillingAmt", "Status", "ReasonStopped", "AutoCharge", "CC1", "CC2", "NumDaysBetweenRetry", "MaxRetry", "MerchantAccountId", "AffiliateId", "PromoCode", "LeadAffiliateId", "Qty", "ShippingOptionId" };
    private string table = "RecurringOrder";
    private DataTable dt = new DataTable();
    // here's the query 
    XmlRpcStruct[] retData = proxy.Query(Auth.key, table, 1000, 0, qryData, returnFields);
    dt = StructArrayToDT(retData);

    public static DataTable StructArrayToDT(XmlRpcStruct[] data)
    {
        DataTable dt = new DataTable();
        if (data.Length == 0) { return dt; }

        // do columns
        foreach (DictionaryEntry d in data[0])
        {
            dt.Columns.Add(d.Key.ToString(), typeof(object));
        }

        foreach (XmlRpcStruct xmlstruct in data)
        {
            DataRow dr = dt.NewRow();
            foreach (DictionaryEntry d in xmlstruct)
            {
                try
                {
                    dr[d.Key.ToString()] = d.Value;
                }
                catch (Exception ex)
                { 
                    // handle errors
                }

            }
            dt.Rows.Add(dr);
        }
        return dt;
    }

現在終於可以毫無問題地訪問該數據了。

查看 QuerySubscriptionStatus 其返回的 IEnumerable 的簽名。 同樣,如果您查看實現 IDictionary、ICollection、IEnumerable 的 XmlRpcStruct(XML.Rpc.Net 的Fork )的定義。 因此,如果我們假設 QuerySubscriptionStatus 正在返回實現 IEnumerable 的 XmlRpcStruct,那么您將獲得 Enumeration 作為響應,它本質上是項目的集合(即使它包含單個項目)。 您正在嘗試將枚舉類型轉換為不是集合的結構 (SubscriptionStatus)。 因此錯誤。 如果包含在 Enumeration 中的項目屬於 SubscriptionStatus 結構類型,那么以下行應該可以解決問題。

var resultList = subStatus.ToList<SubscriptionStatus();

然后循環遍歷 resultList 以訪問來自 QuerySubscriptionStatus 方法的響應。

foreach(var result in resultList)
{

}

或者,如果您確定響應列表只有一個條目,那么您也可以使用以下內容

var result = resultList.FirstOrDefault();

希望有幫助。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM