Skip to main content
Announcements
Have questions about Qlik Connect? Join us live on April 10th, at 11 AM ET: SIGN UP NOW
cancel
Showing results for 
Search instead for 
Did you mean: 
Anonymous
Not applicable

403 Forbidden Session API Failure

I've been banging my head on this and hoping to get some assistance with getting single sign on working using the Session API.

Essentially it appears that my certificates load successfully but I get an immediate 403 as soon as the call is made with no additional data. I have reviewed the logs on the Qlik server but haven't found anything has helped me yet to determine the problem.

I am using the QlikClient cert in my local store which includes the private keys - I have ensure my asp.net application pool identity has access to the cert.

Below is my code (C#) which I built following the tutorials and code samples here:

ASP.NET Session Tutorial

https://drive.google.com/file/d/0BxBEVQthCb29b3l1ME1SQXpkZkU/view

IIS Configuration Tutorial

https://drive.google.com/file/d/0BxBEVQthCb29ek52R2pCZ3ZOX00/view

Code Samples

http://branch.qlik.com/#!/project/56728f52d1e497241ae69864

I have read and re-read the docs on the forums and support pages but with no luck.

public class QlikAuthenticationService

    {     

        public Result<string> StartQlikSession(QlikUserAccessInformation access, string aspnetSessionID)

        {

            var result = new Result<string>();

            var certificate = LoadQlikCertificate(access.ClientCertificateName);

            result += certificate;

            if (certificate.Success)

            {

                try

                {

                    // ensure handling of self signed certs

                    ServicePointManager.ServerCertificateValidationCallback = delegate { return true; };

                    // establish url (ie https://reports.domain.com:4243/qps/test/session)

                    string url = $"https://{access.ServerDomain}:{access.ServerPort}/qps/{access.VirtualProxyName}/session";

                    string xrfKey = "ZYX_random_string_132456";

                    string body = $"{{ 'UserId': '{access.UserID}', 'UserDirectory':'{access.UserDirectory}', 'Attributes': [], 'SessionId':'{aspnetSessionID}' }}";

                    byte[] bodyBytes = Encoding.UTF8.GetBytes(body);

                    HttpWebRequest request = (HttpWebRequest)WebRequest.Create(url + "?Xrfkey=" + xrfKey);

                    request.ClientCertificates.Add(certificate.Value);

                    request.Method = "POST";

                    request.Accept = "application/json";

                    request.Headers.Add("X-Qlik-Xrfkey", xrfKey);

                    request.ContentType = "application/json";

                    request.ContentLength = bodyBytes.Length;

                    Stream requestStream = request.GetRequestStream();

                    requestStream.Write(bodyBytes, 0, bodyBytes.Length);

                    requestStream.Close();

                    HttpWebResponse response = (HttpWebResponse)request.GetResponse();

                    Stream stream = response.GetResponseStream();

                    if (stream != null) result.Value = new StreamReader(stream).ReadToEnd();

                }

                catch (Exception exc)

                {

                    result.AddException(exc, this, "Unable to start Qlik session.");

                }

            }

            return result;

        }

        public Result<X509Certificate2> LoadQlikCertificate(string certificateName)

        {

            Result<X509Certificate2> result = new Result<X509Certificate2>();

            try

            {

                X509Store store = new X509Store(StoreName.My, StoreLocation.LocalMachine);

                store.Open(OpenFlags.ReadOnly);

                var certificates = store.Certificates.Cast<X509Certificate2>();

                if (certificates != null && certificates.Count() > 0)

                {

                    var certificate = certificates.FirstOrDefault(c => c.FriendlyName == certificateName);

                    if (certificate != null)

                    {

                        result.Value = certificate;

                    }

                    else

                    {

                        result.AddFailure(Results.Reports.QLIK_ACCESS_FAILURE, "Unable to connect to Qlik Reporting server.", this, $"No {certificateName} certificate found in store");

                    }

                }

                else

                {

                    result.AddFailure(Results.Reports.QLIK_ACCESS_FAILURE, "Unable to connect to Qlik Reporting server.", this, "No certificates found in store");

                }

            }

            catch (Exception exc)

            {

                result.AddException(exc, this, "Unable to load Qlik client certificate.");

            }

            return result;

        }

    }

    public class QlikUserAccessInformation

    {

        public string ServerDomain { get; set; } = "reports.domain.com";

        public int ServerPort { get; set; } = 4243;

        public string VirtualProxyName { get; set; } = "test";

        public string ClientCertificateName { get; set; } = "QlikClient";

        public string UserDirectory { get; set; } = "QLIK-SENSE";

        public string UserID { get; set; } = "MyUsername";

    }

Below is my Qlik Sense Virtual Proxy Configuration:

2017-02-15 13_03_17-Edit virtual proxy - QMC.png

2017-02-15 13_03_17-Edit virtual proxy - QMC - 2.png

In the above configuration, I have replaced my actual domain name with "domain.com". The Qlik server is at reports.domain.com and my ASP.NET application is at dev.dashboard.domain.com (which I have mapped to local host using a hosts mapping on my machine). The IPs in the whitelist are my networks public IP address and the servers IP address.

One final note - I have attempted to set this up using PostMan as well, however I am always getting a 403 Forbidden but with this error message: XSRF prevention check failed. Possible XSRF discovered. I am passing the XSRF header/url param in PostMan as well.

1 Solution

Accepted Solutions
Alexander_Thor
Employee
Employee

Hey Nate,

"The only characters that are allowed for use in the Xrfkey parameter are 0 - 9, a - z, and A - Z."

Using Xrfkey headers ‒ Qlik Sense

Try dropping the _ in your xrf key

View solution in original post

4 Replies
Anonymous
Not applicable
Author

No one has any thoughts on this? Any help would be appreciated.

Thanks!

Alexander_Thor
Employee
Employee

Hey Nate,

"The only characters that are allowed for use in the Xrfkey parameter are 0 - 9, a - z, and A - Z."

Using Xrfkey headers ‒ Qlik Sense

Try dropping the _ in your xrf key

Anonymous
Not applicable
Author

Thanks - will give this a try.

Anonymous
Not applicable
Author

That did the trick. Sessions are working now for me. Thanks!

Of course the placeholder value I had in there while I was just trying to get the basics to work was the thing causing it not to. I hadn't seen that article and was just putting in something random figuring pretty much anything was acceptable as long as they matched.

For anyone curious, I did also need to add in this line after the cert validation callback to get it to work fully:


ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls