I’m sure this is related to how I’m implementing my return type. I have a generic ListResponse class that has a List Items property where I have my data. In fact, all of my responses have a wrapper class. SingleResponse, ListResponse, etc. The AssetAllocationDto class doesn’t get addressed when generating code from metadata or from ui.
[Api("Gets your asset allocations")]
[Description("Description of the API")]
[Notes("Full <strong>html-enabled</strong> notes about the API")]
[Route("/assets/allocations", HttpMethods.Get)]
public class GetAssetAllocations : RequestBase, IGet, IReturn<ListResponse<AssetAllocationDto>>
{
}
using System;
using System.Collections;
using System.Collections.Generic;
using System.Runtime.Serialization;
using ServiceStack;
using ServiceStack.DataAnnotations;
using Wdp.ServiceModels;
using Wdp.ServiceModels.Assets;
namespace Wdp.ServiceModels
{
public interface IHasEtag
{
string Etag { get; set; }
}
public interface IHasResponseStatus
{
ResponseStatus ResponseStatus { get; set; }
}
public interface IHasSeconds
{
double? Seconds { get; set; }
}
public interface IHasSecurityContextToken
{
string Token { get; set; }
}
public interface IResponse
: IHasResponseStatus, IHasSeconds, IHasVersion
{
}
public interface IResponseWithEtag
: IResponse, IHasEtag
{
}
public class ListResponse<T>
: ResponseBase
{
public ListResponse()
{
Items = new List<T>{};
}
public List<T> Items { get; set; }
}
public class RequestBase
: IHasSecurityContextToken, IHasVersion
{
[Input(Placeholder="If not set, defaults to bearer or basic auth username.", Type="textarea")]
public string Token { get; set; }
[Input(Placeholder="If not set, defaults to latest", Type="number")]
public int Version { get; set; }
}
public class ResponseBase
: IResponseWithEtag
{
public int Version { get; set; }
public string Etag { get; set; }
public double? Seconds { get; set; }
public ResponseStatus ResponseStatus { get; set; }
}
}
namespace Wdp.ServiceModels.Assets
{
///<summary>
///Gets your asset allocations
///</summary>
[Route("/assets/allocations", "GET")]
[Api(Description="Gets your asset allocations")]
public class GetAssetAllocations
: RequestBase, IReturn<ListResponse<AssetAllocationDto>>, IGet
{
}
}
And what’s missing from that:
public class AssetAllocationDto
{
public string AssetClass { get; set; } = default!;
public double MarketValue { get; set; } = default!;
}
It’s including the AssetAllocationDto in the generated types here, can you provide a stand-alone repro that contains the issue, e.g. from an empty web template:
/* Options:
Date: 2022-08-17 10:45:33
Version: 6.21
Tip: To override a DTO option, remove "//" prefix before updating
BaseUrl: https://localhost:5001
//GlobalNamespace:
//MakePartial: True
//MakeVirtual: True
//MakeInternal: False
//MakeDataContractsExtensible: False
//AddReturnMarker: True
//AddDescriptionAsComments: True
//AddDataContractAttributes: False
//AddIndexesToDataMembers: False
//AddGeneratedCodeAttributes: False
//AddResponseStatus: False
//AddImplicitVersion:
//InitializeCollections: True
//ExportValueTypes: False
//IncludeTypes:
//ExcludeTypes:
//AddNamespaces:
//AddDefaultXmlNamespace: http://schemas.servicestack.net/types
*/
using System;
using System.Collections;
using System.Collections.Generic;
using System.Runtime.Serialization;
using ServiceStack;
using ServiceStack.DataAnnotations;
using Wdp.ServiceModels;
using Wdp.ServiceModels.Assets;
using Test.ServiceModel;
namespace Test.ServiceModel
{
[Route("/hello")]
[Route("/hello/{Name}")]
public partial class Hello
: IReturn<HelloResponse>
{
public virtual string Name { get; set; }
}
public partial class HelloResponse
{
public virtual string Result { get; set; }
}
}
namespace Wdp.ServiceModels
{
public partial interface IHasEtag
{
string Etag { get; set; }
}
public partial interface IHasResponseStatus
{
ResponseStatus ResponseStatus { get; set; }
}
public partial interface IHasSeconds
{
double? Seconds { get; set; }
}
public partial interface IHasSecurityContextToken
{
string Token { get; set; }
}
public partial interface IResponse
: IHasResponseStatus, IHasSeconds, IHasVersion
{
}
public partial interface IResponseWithEtag
: IResponse, IHasEtag
{
}
public partial class ListResponse<T>
: ResponseBase
{
public ListResponse()
{
Items = new List<T>{};
}
public virtual List<T> Items { get; set; }
}
public partial class RequestBase
: IHasSecurityContextToken, IHasVersion
{
[Input(Placeholder="If not set, defaults to bearer or basic auth username.", Type="textarea")]
public virtual string Token { get; set; }
[Input(Placeholder="If not set, defaults to latest", Type="number")]
public virtual int Version { get; set; }
}
public partial class ResponseBase
: IResponseWithEtag
{
public virtual int Version { get; set; }
public virtual string Etag { get; set; }
public virtual double? Seconds { get; set; }
public virtual ResponseStatus ResponseStatus { get; set; }
}
}
namespace Wdp.ServiceModels.Assets
{
public partial class AssetAllocationDto
{
public virtual string ProductStyle { get; set; }
public virtual double MarketValue { get; set; }
}
public partial class AssetByProductDto
{
public virtual string ProductName { get; set; }
public virtual string ProductTicker { get; set; }
public virtual double MarketValuePercentage { get; set; }
public virtual double MarketValue { get; set; }
}
public partial class AssetByProductManagerDto
{
public virtual string ProductManager { get; set; }
public virtual double MarketValue { get; set; }
}
public partial class AssetByProductTypeDto
{
public virtual string ProductType { get; set; }
public virtual double MarketValue { get; set; }
}
public partial class AssetByRegistrationTypeDto
{
public virtual string RegistrationType { get; set; }
public virtual double HeldMarketValue { get; set; }
public virtual double HeldAwayMarketValue { get; set; }
}
///<summary>
///Gets your asset allocations
///</summary>
[Route("/assets/allocations", "GET")]
[Route("/assets/market-value/by-product-style", "GET")]
[Api(Description="Gets your asset allocations")]
public partial class GetAssetAllocations
: RequestBase, IReturn<ListResponse<AssetAllocationDto>>, IGet
{
}
///<summary>
///Concentration of individual and packaged products/portfolios
///</summary>
[Route("/assets/market-value/by-product", "GET")]
[Api(Description="Concentration of individual and packaged products/portfolios")]
public partial class GetAssetsByProduct
: RequestBase, IReturn<ListResponse<AssetByProductDto>>, IGet
{
public virtual int Count { get; set; }
}
///<summary>
///Concentration of investment managers
///</summary>
[Route("/assets/market-value/by-product-manager", "GET")]
[Api(Description="Concentration of investment managers")]
public partial class GetAssetsByProductManager
: RequestBase, IReturn<ListResponse<AssetByProductManagerDto>>, IGet
{
}
///<summary>
///Provides time series trend by line of business
///</summary>
[Route("/assets/market-value/by-product-type", "GET")]
[Api(Description="Provides time series trend by line of business")]
public partial class GetAssetsByProductType
: RequestBase, IReturn<ListResponse<AssetByProductTypeDto>>, IGet
{
}
///<summary>
///Gets your asset by registration type (held vs held away)
///</summary>
[Route("/assets/market-value/by-registration-type", "GET")]
[Api(Description="Gets your asset by registration type (held vs held away)")]
public partial class GetAssetsByRegistrationType
: RequestBase, IReturn<ListResponse<AssetByRegistrationTypeDto>>, IGet
{
}
}