Generating new SessionId in ASP.NET - asp.net

On login I want to generate a new SessionId. I have found one solution that works, but it requires some pretty hackish things and requires the app have Full Trust securityPolicy setting.
Is there any other way to achieve this?

Looks like this works:
Session.Abandon();
Response.Cookies.Add(new HttpCookie("ASP.NET_SessionId", ""));
By clearing out that cookie, a new session with a new session ID will be created at the server.
(Reference: Microsoft Support)
EDIT: Here's an example using AJAX (with jQuery) to call the server code without a page refresh - it calls twice, once to remove the first session, and once to generate a new one. There may be a better way, but this does work.
function newSession() {
jQuery.ajax({
type: "POST",
url: "WebForm1.aspx/ClearSession",
data: "{}",
dataType: "json",
contentType: "application/json; charset=utf-8",
success: function () {
jQuery.ajax({
type: "POST",
url: "WebForm1.aspx/NewSession",
data: "{}",
dataType: "json",
contentType: "application/json; charset=utf-8",
success: function () { console.log("Success!"); },
error: function (x, y, z) {
console.log("Failure!");
}
});
},
error: function (x, y, z) {
console.log("Failure!");
}
});
}
And on the code-behind (for WebForms - you could also do this with an MVC controller):
[WebMethod]
public static void ClearSession()
{
HttpContext.Current.Session.Abandon();
HttpContext.Current.Response.Cookies.Add(new HttpCookie("ASP.NET_SessionId", ""));
}
[WebMethod]
public static void NewSession()
{
HttpContext.Current.Session["x"] = 123;
}

I'm currently considering a configuration-based solution, rather than a code-based one. I would configure either the web server or load balancer to strip away request and response headers containing cookies for just the login page. Remove the "cookie" headers for request headers and "set-cookie" for response headers.
Every request (GET or POST) to the login page will contain no cookie information, thus forcing ASP.NET to create a new session and (more importantly) a new session id.
It's less efficient than forcing a new session creation on login, but the technique could be useful in cases where you cannot modify the code.

Related

How can i retrive session from asp.net using Jquery

How can I retrieve session variable stored in a.aspx using Jquery? I have username stored in the session, I need to retrieve the session to display the username in the menu bar.
A person login through A.aspx and his details has to be displayed(from database) in B.aspx
One way to handle this would be to create a Web Method or similar within your current page so that you could access the updated value of the Session via an AJAX call :
[WebMethod]
public static string GetSessionValue(string key)
{
return Session[key];
}
Then you could make a POST call via AJAX to request the specific key that you needed (or you could ignore any parameters and simply hard-code the key that you wanted to pull within the method itself) :
public static string GetSessionDisplayName()
{
// Use the name of your Session key here to retrieve your info
return Session["DisplayName"];
}
And then you could use the following jQuery code to pull it with a parameter :
$.ajax({
type: "POST",
url: "YourPage.aspx/GetSessionValue",
data: '{ key: "your-session-key" }',
contentType: "application/json; charset=utf-8",
dataType: "json",
success: function(data) {
// data will hold your Session value, use it here
alert(data);
}
});
Or without one :
$.post('YourPage.aspx/GetSessionDisplayName',function(data){
// data will hold your Session value, use it here
alert(data);
});

Send AJAX request to .aspx page and return JSON

I know that it is possible to send an AJAX request to an .asmx page. And I also know that an .asmx page handles an AJAX request via a web method.
Is it also possible to send an AJAX request to an .aspx page? If so, does an .aspx page also handle an AJAX request via a web method? Note that I would like to return a JSON response from the .aspx page. Is this possible?
You can define web methods in the code-behind of your .aspx page and then call them:
[WebMethod]
public static string doSomething(int id)
{
...
return "hello";
}
And then, to call a web method in your jQuery code:
$.ajax({
type: "POST",
url: "YourPage.aspx/doSomething",
data: "{'id':'1'}",
dataType: "json",
contentType: "application/json; charset=utf-8",
success: function (data) {
var returnedstring = data.d;
var jsondata = $.parseJSON(data.d);//if you want your data in json
}
});
Here is a good link to get started.
if i understood question correctly, Aspx is same as HTML. It will be rendered as HTML. but only difference is Server Side and Controls retaining the states with state mechanism.
so you can do jquery $.ajax() function.
$.ajax({
url: UrlToGetData,
dataType:'json',
success:function(data){
//do some thing with data.
}
});
or if you want to write out json value to the response, then use Response.ContentType
first use any Javascript serializer(JSON.NET) , then set the contentType like this.
Response.ContentType="application/json";
$.ajax({
url: "(aspx page name/method to be called from the aspx.cs page)",
type: "POST",
dataType: "json",
data: $.toJSON(jsonData),
contentType: "application/json; charset=utf-8",
success: function (data, textStatus, jqXHR) {
//TO DO after success
}
});
Try the above code

Handle session timeout in generic http handler

I have an application where around 20 http generic handler are used for ajax call.
I have used IReadOnlySessionState for accessing the session in my handlers.Everything is working fine.
But when session expires my handler is returning some html as it redirects to default page and html of default page is sent back in the response.
To overcome this issue.
I have checked the session variable in the handler and if it is null the I have written
context.Response.Write("logout")
And I check in jQuery ajax weather it is logout or anything else.
$.ajax({
url: "myhandler.ashx",
contentType: "application/json; charset=utf-8",
success: function (data) { checklogout(data); $("#loading").hide(); },
error: function () { $("#loading").hide(); },
async: false
});
If it is logout then I have used location to redirect to login page.
I am using form-authentication to authenticate user.
Is there any better approach for checking and redirecting to login page using jquery-ajax call.
You have your handlers in a directory that automatically control by the authentication of asp.net.
What I should do is to not let automatically control by the asp.net authentication by setup that on web.config so the call to the handler will done ether the user is logged in ether not, and inside the handlers I will check for that, if the user that call that handler have the session and the authentication.
Then in the case that the user did not have the authentication to read that handler I return a simple flag to my ajax call, then recognize and make redirect, eg as:
$.ajax({
url: "myhandler.ashx",
contentType: "application/json; charset=utf-8",
success: function (data)
{
if(data.redirectToLogin == true)
{
window.location = "/login.aspx"
}
else
{
// do the rest job
}
},
error: function ()
{
$("#loading").hide();
}
});

Lost connection does not return error with jQuery AJAX on live site but on dev?

I am using the following code to post data from a asp.net 2.0 site to an asp.net 2.0 web service that post the data to a server:
$.ajax({
type: "POST",
url: "SynchroniseCustomers.asmx/synchroniseCustomers",
data: JSON.stringify(customerObj),
contentType: "application/json; charset=utf-8",
dataType: "json",
error: function (xhr, status) {
// If not successfull
},
success: function (msg) {
deleteCustomer(customer.id);
}
});
I have a JavaScript function to check if I have connection or not, if I have I run the synchronisation (pulling data from web kit browser local database):
function checkConnection() {
var i = new Image();
i.onload = synchronise;
i.onerror = fail;
i.src = 'http://myurl.com/ping.gif?d=' + escape(Date());
setTimeout("checkConnection()", 60000); // Execute every minute
}
Thing is, if I run this locally and drop my internet connection the web service returns a 500 error (like I want it to do) and deleteCustomer(customer.id); is not called. However, on the live site if I drop my connection the web service does not return an error and deleteCustomer(customer.id); is called even if I don't have a connection to the internet (customer gets deleted from local database without being posted to the web server).
What's the reason for this? Please let me know if you need more code.
Thanks in advance.
You probably didn't wait a minute after dropping the connection.
There is a case that Ajax recall the cached data when you are ask for delete, and even if you are not connected to the net its get it from cache, so thats why its think that is all ok. The cache on jQuery Ajax is true by default.
So try with cache:false
$.ajax({
type: "POST",
url: "SynchroniseCustomers.asmx/synchroniseCustomers",
data: JSON.stringify(customerObj),
contentType: "application/json; charset=utf-8",
dataType: "json",
cache:false,
error: function (xhr, status) {
// If not successfull
},
success: function (msg) {
deleteCustomer(customer.id);
}
});
For the image call, its better to use Interval and not create memory again and again.
<img id="PingerImg" width="1" height="1" src="/spacer.gif?" onload="synchronise" onerror="fail" />
<script language="javascript" type="text/javascript">
var myImg = document.getElementById("PingerImg");
if (myImg){
window.setInterval(function(){myImg.src = myImg.src.replace(/\?.*$/, '?' + Math.random());}, 60000);
}
</script>
Update
The other solution is to really get a confirmation code form the server that you have delete the user, and only if you read that code , proceed to delete the user on remote.
success: function (msg) {
if(msg.confirm = true)
{
deleteCustomer(customer.id);
}
else
{
alert('Fail to delete user.');
}
}

Parameter from codebehind to jquery [ Master Page]

I am creating Menu in the master page using JQuery. i am passing the id of the link to jquery using $.ajax({});
Problem:
Getting failed: Showing error message in AjaxFailed(result) function.
Code:html[JQuery]
$.ajax({
type: "POST",
url: "Master.Master.cs/UserStatus",
contentType: "application/json; charset=utf-8",
data: "{}",
dataType: "json",
success: AjaxSucceeded,
error: AjaxFailed
});
function AjaxSucceeded(result) {
if (result.d.length != 0) {
for (var i = 0; i < result.d.length; i++) {
$(result.d[i]).hide();
}
}
}
function AjaxFailed(result) {
alert("Error");
}
c# Code:Codebehind
private static List<string> xx;
[WebMethod]
public static List<string> UserStatus()
{
return xx;
}
protected void Page_Load(object sender, EventArgs e)
{
xx = new List<string> {"#ll1", "#ll2" };
}
What the webmethod attribute does is to say that this method should respond to a certain url (a little bit like routing in asp.net mvc). As I don't use webforms I don't really know what logic it uses when it decides what url the method should respond to. But my guess is that the url should be something like "Master.cs/UserStatus" (not sure about the .cs extension). And that is of course a relative url, so you can try something like this: <%=ResolveUrl("~/Master.cs/UserStatus")%> (if the masterpage is in your root folder). Then your example should be something like this:
$.ajax({
type: "POST",
url: '<%=ResolveUrl("~/Master.cs/UserStatus")%>',
contentType: "application/json; charset=utf-8",
data: "{}",
dataType: "json",
success: AjaxSucceeded,
error: AjaxFailed
});
Update
The .cs extension is probably wrong. But I don't think you should have that in a master page anyway. You should probably have it in a web service or in a .ashx handler or something if you want to use ajax. But with you last comment it seems that you don't need to use ajax (and if you don't need that, you shouldn't). The problem in the code you wrote in the comment is probably that the id is wrong (remember that you need the client id in javascript).
But I would probably do it something like this:
<script type="text/javascript">
var statuses = [];
<%foreach(var status in UserStatus()) {%>
statuses.push(<%=status%>);
<%}%>
</script>
This will render this javascript in the browser:
<script type="text/javascript">
var statuses = [];
statuses.push("#ll1");
statuses.push("#ll2");
</script>
Then you will have your statuses in the statuses array.
Like Andre and Mattias mentioned, the .cs extension is not served, so you would have to use a .aspx extension to get to the WebMethod.
The problem I see in your example is that you are placing the method in the MasterPage (which would have a .master extension) which is also not served, so you can't call the web method from it.
A workaround you could use is to define it in a class that inherits from Page, and have all of your pages inherit from that class. Since its a public method, it will be public on all of your pages and therefore available. Basicly, a base page for your project's pages. In that case you would only need to use your current page's address to make the call. This is only usefull if it's something you will use on every page, like a menu.
A second workaround you can use is to define the WebMethod in a .asmx Webservice placed in the project. It would work like calling the WebMthod on a page, only you would have to use the .asmx Webservice's address instead of the page's to make the call.
If you've not done so you will need to add the [ScriptService] attribute to your webmethod as this
Indicates that a Web service can be
invoked from script
See ScriptServiceAttribute
I think that the problem is that you try to post to the .cs file. The extension .cs is not served by ISS due to security reasons. So even though your method lifes in the code behind file, you have to post to the .aspx file. ASP.NET will do the rest for your.
So try:
$.ajax({
type: "POST",
url: "/Master.Master.aspx/UserStatus",
contentType: "application/json; charset=utf-8",
data: "{}",
dataType: "json",
success: AjaxSucceeded,
error: AjaxFailed
});
function AjaxSucceeded(result) {
if (result.d.length != 0) {
for (var i = 0; i < result.d.length; i++) {
$(result.d[i]).hide();
}
}
}
function AjaxFailed(result) {
alert("Error");
}

Resources