Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
310 views
in Technique[技术] by (71.8m points)

asp.net core 3.1 - Session data not stored in the next request

I have a ASP.NET Core web application that hits a webservice endpoint and then that webservice sends requests to my application.

When I hit that webservice endpoint I receive a web token with a string value and expiry time. I am saving it in the session, so I can verify it later.

When the webservice sends request to my application it sends the same token that I have received.

I need to make sure to validate that the token as it is the same that I initially received on my first request. I am currently storing them in the database and I DO not want to do that. I want to store it in the context.

I had a look and I saw I could store the token in the session.

Here the session keys count is 1.

public async Task<IActionResult> Index(string sortOrder, string employeeIdFilter, string whenFilter, 
string currentFilter, int? pageNumber)
    {
        if (await tokenService.TokenAlreadyExistsAsync(Request))
        {
            return await ArrivalsFromDatabase(sortOrder, employeeIdFilter, whenFilter, currentFilter, pageNumber);
        }

        var exampleDate = new DateTime(2016, 3, 10);
        bool success = false;

        var token = await this.tokenService.GetServiceToken(exampleDate);
        var f = HttpContext.Session.Keys.ToList();

        this.tokenService.TryGetTokenFromSession(token.Token);
        tokenFromService = token.Token;
        if (token != null && !string.IsNullOrEmpty(token.Token))
        {
            await this.tokenService.SavesTokenAsync(token);
            success = true;
        }
        
        if (!success)
        {
            return RedirectToAction("PageNotFound", "Error");
        }
        var y = HttpContext.Session.Keys.ToList();
        return await ArrivalsFromDatabase(sortOrder, employeeIdFilter, whenFilter, currentFilter, pageNumber);
    }

After the index is completed a new request from the service is sent to the Web App where the session keys count is 0 and it breaks on SetString method in the TryGetTokenFromSession method below:

    public async Task<IActionResult> ReceiveArrivalInfoFromService()
    {
        var y = HttpContext.Session.Keys.ToList();

        this.tokenService.TryGetTokenFromSession(tokenFromService);

        await tokenService.ReadTokenAsync(Request);
        var arrivals = await tokenService.CollectArrivals(Request);
        await arrivalService.AddRangeAsync(arrivals);
        return Ok();
    }


 public void TryGetTokenFromSession(string token)
    {
        if (!this.httpContextAccessor.HttpContext.Session.TryGetValue("ServiceToken", out byte[] 
value))
        {
            this.httpContextAccessor.HttpContext.Session.SetString("ServiceToken", token);
        }
        else
        {
            // Get The Token.
            string result = Encoding.UTF8.GetString(value);
            this.httpContextAccessor.HttpContext.Session.SetString("ServiceToken", result);

            // TODO: Validate Here Or In The Middleware.
        }
    }

Service token Session Middleware:

public class ServiceToken
{
    private readonly RequestDelegate _next;

    public ServiceToken(RequestDelegate next)
    {
        _next = next;
    }

    public Task Invoke(HttpContext httpContext)
    {
        // Add Token To Context If Found.
        string token = httpContext.Session.GetString("ServiceToken");

        // Check Something Was Found.
        if (!string.IsNullOrEmpty(token))
        {
            // Add The Custom Token Here.
            httpContext.Request.Headers.TryAdd("ServiceToken", token);
        }

        // Next.
        return _next(httpContext);
    }
}


// Extension method used to add the middleware to the HTTP request pipeline.
public static class ServiceTokenExtensions
{
    public static IApplicationBuilder UseServiceToken(this IApplicationBuilder builder)
    {
        return builder.UseMiddleware<ServiceToken>();
    }
}

in Startup:

        services.AddSession(options =>
        {
            options.IdleTimeout = TimeSpan.FromSeconds(10);
            options.Cookie.HttpOnly = true;
            options.Cookie.IsEssential = true;
        });

{"String reference not set to an instance of a String. (Parameter 's')"}

question from:https://stackoverflow.com/questions/65644262/session-data-not-stored-in-the-next-request

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)
Waitting for answers

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...