none
Adding multiple cookies using WebOperationContext RRS feed

  • Question

  • Hello,

    I have a WCF service and I have hosted it as Windows Service as webHttpBinding.

    When I request this service from browser, then I get context properties of the request using WebOperationContext class.

    Now, I want add two cookies in the response. I tried following following solutions to do this:

    1. 

    WebOperationContext ctx = WebOperationContext.Current;    
    ctx.OutgoingResponse.Headers[HttpResponseHeader.SetCookie] = "SessionId=12345";
    ctx.OutgoingResponse.Headers[HttpResponseHeader.SetCookie] = "OtherId=54321";

    However, when response is received in browser, only first cookie is received.

    2. 

    WebOperationContext ctx = WebOperationContext.Current;    
    HttpResponseHeader setCookieHeader = HttpResponseHeader.SetCookie;
    
    ctx.OutgoingResponse.Headers.Add(setCookieHeader,"SessionId=12345"+";,"+"OtherId=54321")

    Here also, browser is parsing only one [first cookie] and treating other part as contents of first cookie [SessionId]

    So basically, WebOperationContext is not allowing me to add more than one cookie in response.

    What I am missing here?

    Thank you in advance!

    Navnath

    Wednesday, March 28, 2018 9:45 AM

Answers

  • Hi NavnathK,

    To narrow down your issue, I suggest you create a simple WCF Rest Service, modify the web.conig and Service to add aspNetCompatibilityEnabled, change GetData like below:

            public string GetData(int value)
            {
                var aCookie = new HttpCookie("SessionId")
                {
                    Value = "12345",
                };
                HttpContext.Current.Response.Cookies.Add(aCookie);
                var aCookie1 = new HttpCookie("OtherId")
                {
                    Value = "54321",
                };
                HttpContext.Current.Response.Cookies.Add(aCookie1);
                
                return string.Format("You entered: {0}", value);
            }

    Will it add the cookie correctly?

    Best Regards,

    Tao Zhou


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    • Marked as answer by NavnathK Tuesday, April 10, 2018 1:15 PM
    Friday, March 30, 2018 5:15 AM

All replies

  • Hi NavnthK,

    I made a test and I could reproduce your issue. As my researching, I am afraid it is impossible to achieve your requirement by WebOperationContext.

    I would suggest you try HttpContext.

                var aCookie = new HttpCookie("SessionId")
                {
                    Value = "12345",
                };
                HttpContext.Current.Response.Cookies.Add(aCookie);
                var aCookie1 = new HttpCookie("OtherId")
                {
                    Value = "54321",
                };
                HttpContext.Current.Response.Cookies.Add(aCookie1);
    

    Note, if above code did not work, please check whether aspNetCompatibilityEnabled is true in web.config.

    <system.serviceModel>       
        <serviceHostingEnvironment aspNetCompatibilityEnabled="true" multipleSiteBindingsEnabled="true" />
    </system.serviceModel>

    Best Regards,

    Tao Zhou


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    Thursday, March 29, 2018 5:09 AM
  • Hello Tao,

    Thank you for your test. I tried your suggestion. But HttpContext.Current is always returning null.

    I also added <serviceHostingEnvironment aspNetCompatibilityEnabled="true" multipleSiteBindingsEnabled="true" /> in app.config


     

    Thursday, March 29, 2018 5:48 AM
  • Please add one more step to add code below:

        [AspNetCompatibilityRequirements(RequirementsMode
           = AspNetCompatibilityRequirementsMode.Allowed)]
        public class Service1 : IService1
        {


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    Thursday, March 29, 2018 6:44 AM
  • I tried this. Still getting null for HttpContext.Current.
    Thursday, March 29, 2018 6:48 AM
  • Could you share us a simple project which could reproduce your issue?

    HttpContext.Current works correctly at my side.


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    Thursday, March 29, 2018 6:58 AM
  • I don't have simple project that can be shared here. But I am putting some code snippets/functions which leads me to this error:

    Here is my service method:

       [AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
        [ServiceBehavior(InstanceContextMode = InstanceContextMode.Single,
            ConcurrencyMode=ConcurrencyMode.Single)]
        public class ReqtifyServerService : IReqtifyServer
        {
            //Service method to process command
            public Stream ProcessCommand()
            {
    
                String path =  HostingEnvironment.ApplicationPhysicalPath;
    
                IncomingWebRequestContext request = WebOperationContext.Current.IncomingRequest;
                OutgoingWebResponseContext response = WebOperationContext.Current.OutgoingResponse;
                WebOperationContext ctx = WebOperationContext.Current;            
                string arg = String.Empty;
                WebHeaderCollection headers = request.Headers;
                string htmlResponse = "EMPTY_RESPONSE";
    
                //Handle HTTP request
                Hashtable httpResponse = new Hashtable();
                HttpProcessor hp = new HttpProcessor(ctx);
                Task t = Task.Factory.StartNew(() =>
                {                
                        httpResponse = hp.processClientInput(request);
                });
                t.Wait();
    
                if (((String)httpResponse["status"]).Equals("OK"))
                {
                    htmlResponse = (String)httpResponse["result"];
                    byte[] data = System.Text.Encoding.UTF8.GetBytes(htmlResponse);                                
                    //response.ContentType = "application/json";
                    response.ContentType = request.Accept;
                    return new MemoryStream(data);
                }
    
                byte[] resultBytes = Encoding.UTF8.GetBytes((String)httpResponse["error"]);
                response.ContentType = "text/html";
                response.StatusCode = (HttpStatusCode)httpResponse["statusCode"];
                return new MemoryStream(resultBytes);            
            }

    Here is my processClientInput method:

           public Hashtable processClientInput(IncomingWebRequestContext request)
            {                                               
                try
                {                
                    parseRequest(request);
                    readHeaders(request);
                    if (!isSessionValid())
                    {
                        //Process fresh new request
                        //Start a new Reqtify server and pass the request to it
                        //Add reqtify ReqtifyServer instance in the list
                        //Add reqtify session cookie for ReqtifyServer instance
    
                        ReqtifyInstance reqtifyServer = new ReqtifyInstance();
                        reqtifyServer.setRequestType(ServerConfig.REQUEST_TYPE_BROWSER);
                        reqtifyServer.setWebOperationContext(ctx);
                        Task t = Task.Factory.StartNew(() => { reqtifyServer.startReqtifyInstance(); });
                        t.Wait();
    
                        //Replace the port number in input command                    
                        string command = httpUrl;
    
                        int index = command.IndexOf("/api");
                        command = (index < 0)
                            ? command
                            : command.Remove(index, 4);
                        string newCommand = DataHelper.replacePortNumberOfClientInput(command, reqtifyServer.getPortNo());
                        httpResponse = reqtifyServer.getResponseFromReqtifyServer(newCommand, request);
    
                        if (((String)httpResponse["status"]).Equals("OK"))
                        {
                            string htmlResponse = (String)httpResponse["result"];
                            string cookieFromReqtify = (string)httpResponse["Cookie"];
                            string cookieFromReqtifyServer = String.Empty;
    
                            reqtifyServer.setSessionId(reqtifyServer.getPortNo().ToString());
                            cookieFromReqtifyServer = ServerConfig.SESSION_ID_COOKIE_NAME + "=" + reqtifyServer.getSessionId();
    
                            t = Task.Factory.StartNew(() =>
                            {
                                ReqtifyServerWindowsService.reqtifyServerInstances.Add(reqtifyServer);
                            });
    
                            t.Wait();
    
                            //HttpResponseHeader setCookieHeader = HttpResponseHeader.SetCookie;
                            //ctx.OutgoingResponse.Headers.Add(setCookieHeader, cookieFromReqtify + ";Max-Age=" + DataHelper.getDelayBeforeClosingSession());
    
                            var aCookie = new HttpCookie(ServerConfig.SESSION_ID_COOKIE_NAME)
                            {
                                Value = cookieFromReqtifyServer + 
                                ";Max-Age=" + 
                                DataHelper.getDelayBeforeClosingSession()+
                                ";Path=/",
                            };
                            HttpContext.Current.Response.Cookies.Add(aCookie);
    
                            var aCookie1 = new HttpCookie(ServerConfig.RECEIVER_ID_COOKIE_NAME)
                            {
                                Value = cookieFromReqtify +
                               ";Max-Age=" +
                               DataHelper.getDelayBeforeClosingSession() +
                               ";Path=/",
                            };
                            HttpContext.Current.Response.Cookies.Add(aCookie1);
    
                            handleGETRequest(httpResponse);
                            reqtifyServer.initializeTimer();
                        }
                        else
                        {
                            //Close the reqtify instance when there is Error:
                            // "Unable to connect remote server"                                               
                            if (((String)httpResponse["error"]).ToLower().
                                 Equals(ServerConfig.UNABLE_TO_CONNECT_ERROR.ToLower()))
                            {
                                reqtifyServer.closeTheReqtifyServerInstance();
                            }
                        }
    
                    }          
                }
                catch (Exception e)
                {
                    Console.WriteLine("Exception: " + e.ToString());
                    writeFailure();
                }         
    
    
                return httpResponse;
            }

    Here is my app.config:

    <?xml version="1.0"?>
    <configuration>
    <startup><supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.0"/></startup>
    
      <system.serviceModel>
        <serviceHostingEnvironment aspNetCompatibilityEnabled="true" multipleSiteBindingsEnabled="true" />
        <behaviors>
          <serviceBehaviors>        
            <behavior name="ExternalServerServiceBehavior">
              <serviceMetadata httpGetEnabled="True"></serviceMetadata>          
            </behavior>
          </serviceBehaviors>
          <endpointBehaviors>
            <behavior name="web">
              <webHttp />
            </behavior>
          </endpointBehaviors>
        </behaviors>
        <services>
          <service name="ReqtifyService.ReqtifyServerService" behaviorConfiguration="ExternalServerServiceBehavior">
            <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
          </service>
        </services>    
      </system.serviceModel>
    </configuration>
    

    Hope this helps!

    Thank you in advance!

    Thursday, March 29, 2018 9:23 AM
  • Hi NavnathK,

    To narrow down your issue, I suggest you create a simple WCF Rest Service, modify the web.conig and Service to add aspNetCompatibilityEnabled, change GetData like below:

            public string GetData(int value)
            {
                var aCookie = new HttpCookie("SessionId")
                {
                    Value = "12345",
                };
                HttpContext.Current.Response.Cookies.Add(aCookie);
                var aCookie1 = new HttpCookie("OtherId")
                {
                    Value = "54321",
                };
                HttpContext.Current.Response.Cookies.Add(aCookie1);
                
                return string.Format("You entered: {0}", value);
            }

    Will it add the cookie correctly?

    Best Regards,

    Tao Zhou


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    • Marked as answer by NavnathK Tuesday, April 10, 2018 1:15 PM
    Friday, March 30, 2018 5:15 AM
  • OK, I will check.

    However, just for curiosity, do you think it is not working because I have hosted WCF service as Windows service?

     
    Tuesday, April 10, 2018 1:14 PM