Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

TranslateResultToActionResult doesn't give PagedInfo #71

Open
khandelwal-arpit opened this issue Aug 9, 2021 · 4 comments
Open

TranslateResultToActionResult doesn't give PagedInfo #71

khandelwal-arpit opened this issue Aug 9, 2021 · 4 comments
Labels
enhancement New feature or request help wanted Extra attention is needed question Further information is requested

Comments

@khandelwal-arpit
Copy link

While using TranslateResultToActionResult to return responses in the form of ActionResults, there is no way for the caller to know the details of the pagination.

The reason is because the ToActionResult method in the ResultExtensions class just cares about the "result.GetValue()" and ignores the Pagination details which were fed by the upstream services as shown below:

return Result<IEnumerable<StoryDto>>.Success(pagedStoryDtos).ToPagedResult(pagedInfo);

Is there a way we can modify this behavior so that the caller can see the pagination details too?

@ardalis
Copy link
Owner

ardalis commented Aug 10, 2021

Good question; will need to review.

@ardalis ardalis added enhancement New feature or request help wanted Extra attention is needed question Further information is requested labels Aug 10, 2021
@aurelienhayet
Copy link

Hello Steve,

I am facing the same issue.
Any news about the development of this feature ?

Aurélien

@KyleMcMaster
Copy link
Collaborator

This may not be the most elegant solution but given you have a StoryDto, could you create a PagedStoryDto (or whatever name) and use the Map method to combine StoryDto + PagedInfo into a single object that would get returned. Something like this:

return Result<IEnumerable<StoryDto>>.Success(pagedStoryDtos)
   .ToPagedResult(pagedInfo)
   .Map(r => new PagedStoryDto
   {
     StoryProperty = r.StoryProperty,
     PageNumber = r.PagedInfo.PageNumber,
     ... // other properties
   };

We might be able to add an overload of Map for paged results that does this out of the box in a future update. 🤔

@aurelienhayet
Copy link

aurelienhayet commented Mar 27, 2024

I did something a little bit more complex : I have overriden the TranslateResultToActionResultAttribute to deal with the paged results.

public class AdvancedTranslateResultToActionResultAttribute : TranslateResultToActionResultAttribute
{
    public override void OnActionExecuted(ActionExecutedContext context)
    {
        if ((context.Result as ObjectResult)?.Value is not IResult result) return;

        if (context.Controller is not ControllerBase controller) return;

        base.OnActionExecuted(context);

        if (result.Status is not ResultStatus.Ok) return;

        var type = result.GetType();
        var ardalisPagedResultType = typeof(PagedResult<>);
        if (type.Namespace != ardalisPagedResultType.Namespace
            || type.Name != ardalisPagedResultType.Name)
        {
            return;
        }

        if (!result.ValueType.IsAssignableTo(typeof(IEnumerable<object>))) return;

        var pagedInfoProperty = type.GetProperty(nameof(PagedInfo));

        if (pagedInfoProperty?.GetValue(result) is not PagedInfo pagedInfoValue) return;

        var pagedResultType = typeof(Contracts.Core.PagedResult<>);

        var itemType = result.ValueType.GetGenericArguments()[0];

        var constructed = pagedResultType.MakeGenericType(itemType);

        var pagedInfo = Contracts.Core.PagedInfo.FromArdalisPagedInfo(pagedInfoValue);

        context.Result = controller.StatusCode(
                    context.HttpContext.Response.StatusCode,
                    Activator.CreateInstance(constructed, pagedInfo, result.GetValue()));
    }
}

As you can see, I use reflection to Map Ardalis PagedResult and PagedInfo to my own equivalent classes Contracts.Core.Paged*

With this approach, I obtain a generic solution for all my controllers and paged models.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request help wanted Extra attention is needed question Further information is requested
Projects
None yet
Development

No branches or pull requests

4 participants