run asp.net function when The page is closing - c#

I have an asp.net page
when Loading this page it creates a Thread to do some thing
My Question is :
How to kill this thread when the user close the page ?
I have tried with "onUnload" event
but it just works with javascript function (as I know)
and we can't use asp.net code in javascript function
Do You have a way to help me ...
thanks a lot
Edit:
It 's difficult to explain what I am Trying to do.. The asp.net page must show a message to the user and this message must appear directly without refreshing so I was trying to use a thread which listen wait the message and then run an AJAX code to show the message ..

You can't. The browser and the codebehind (the C#) live in different worlds, and once the Page Lifecycle completes (shortly after RenderComplete), the server is done with the request.
It sends the generated HTML to the client and never looks back.
In the onunload event in javascript, you could send an AJAX request to the server to tell it that the user is leaving the page, but that would be highly unreliable, and if you depended on that exclusively to kill threads you would have a major problem on your hands.
Generally, what you're trying to accomplish would be better accomplished another way - so as others have said, let us know what you're trying to do and we'll give suggestions.

You can do this with PageMethods which works with Ajax
First you catch the onunload event on your script page :
body onunload='javascript:PageMethods.UnloadForm();'
then u enable PageMethods on the scriptManager AJAX you have to add to your page :
asp:ScriptManager ID="ScriptManager1" EnablePageMethods="true"
runat="server"
after, you create your PageMethods Code-behind method in C#:
[System.Web.Services.WebMethod]
public static void UnloadForm()
{
// your stuff
}
Hope this will help you.
My actual pb is that Onunload event is generated without closing my page cause of an AJAX timer. But if you don't add a timer, you shouldn't have this pb.

There is no request sent when the page is closing, so right out of the box, the answer is no. However, you have a few options.
One is to send an XmlHttpRequest (Ajax call) from the javascript onUnload event to a WebMethod.
Another is to execute code at the next beginning of the next pageload, which would cover cases besides those in which the user leaves your site for another or closes their browser.
Finally, there are server-side events you can use for, say, session expiration.
What is it exactly that you're trying to do? Maybe we can help come up with a better way to accomplish it.

Just curious: what kind of threaded process are you running? To your question, the only place you're going to be able to capture the event of the browser being closed is in Javascript... you could make an ajax call back to the server to kill whatever thread you've got running for the session, but as others have said, this isn't reliable.
In short there's no direct way to do what you're wanting to do. The best you could hope for is to hook the Sesion_OnEnd event.

It is a poor coding practice to start a worker thread that is dependent upon a page closing for its cleanup as you have little control over what happens on the client browser. Perhaps you could re-think the architecture of this, or at least expound on what this worker thread is actually doing so a better solution can be recommended for that.
If the work that the worker thread is set up to do has a clear path to code completion, the garbage collector will handle the cleanup and there is no cause for concern. If your using a thread from the thread pool to perform your background task via the QueueUserWorkItem construct, then the thread will make itself available for use again in the pool once the work is completed, and you have nothing to worry about as long as you ensure proper disposal of unmanaged resources if any.

As Mike pointed out in a comment, you should really set up a web service that some JavaScript on the page can poll periodically - this would then go and interagate the queue, check for messages, and if it finds one, display a message to the user.
This site has a function very similar to that when you are answering a question - it has a "Heartbeat" javascript call that polls the server looking for new answers - if it finds some, an orange message bar appears at the top of the page telling you there are new answers, and would you like to view them?

Related

How to wait for the post back in Watin?

In my C# code, I am using Watin to navigate the web, to log in to a page, I need to click the log in button, but right after I want to log out, so I have the click log out button right after, but the log out part doesn't work. I even tried closing the browser (using the close method) after logging in, but it didn't work. It feels like as soon as the page gets changed (i.e. after logging in) no more commands from the c# will work.
Does anyone know whats wrong?
As mentioned in another answer Thread.Sleep(milliseconds) is a way to wait for a time period for something to load. Very, very easy to implement, but it is far from optimal due to varying load times, and if you make it long enough so that it will always wait long enough you'll end up with a lot of wasted time. On one test this is not a big deal, but for instance if you have to wait 5 seconds and you have 1000 tests.... etc etc etc.
The route I've gone is:
Put in Thread.Sleep()s to determine if it is a "wait" issue.
If the the code with the Sleep() is going to be used more than once figure out what is causing the need for the sleep().
Refactor out the Sleep() using various Wait...() methods. WaitTilExists, WaitForAttributeEqualsWhatever, WaitForAsyncToFinish <- Not real methods, but WatiN has a bunch built in
The big cause of waits for me now is JQuery asynchronous calls in ASP.NET and I made a static helper class that works well for me to wait for async calls to finish. These tend to be very specific to what framework(s) the sites you're testing are written in.
The watin click command wait until the browser is loaded so practically it wait for the postback.
In case if you using ClickNoWait() command it will not wait.
So if your code looks like this it should work:
browser.GoTo("www.your-site.com");
// fill user/pass
browser.Button(Find.ByClass("login-class")).Click();
browser.Button(Find.ByClass("logout-class")).Click();
In case it's still not working you can add this after login click browser.WaitForComplete();
In Watin you will encounter many situations where the code is non blocking (you'll execute a line of code and will immediately keep going) so for those cases you'll need to find a different way to know that the next page (action, etc.) is already there. For example, on a login page you could check if that pages has a TextBox called UserName:
<code>
TextField uName = browser.TextField(Find.ByName("userName"));
if(uName.Exists)
{
// Then do the login code....
}
</code>
In the same way you should control that the page after the login is there before you keep going executing your code. So for example, if you are logging in into a page that you know that will contain the text: "Your Account Details" you might do something like this:
<code>
browser.GoTo("http://www.yourdomain.com/login.aspx");
//do your login code
browser.WaitUntilContainsText("Your Account Details", 240); // the second parameter indicates the seconds it will wait before it times out.
// your code to deal with the page after the login.
</code>
Using Thread.Sleep is a recipe for confusion and that's a problem for sure, you will NEVER get the timing right with a web page (even if you think it will take 10 seconds it might never come back and at that point the server will be terminating the opened connection).
Hope it helps.
Use Thread.sleep in your scripts to sync with logout and login...
or
instead of logout you directly close application and use ie instance to relogin to application

Modal dialog and __doPostback Infinite loop

I've got a modal dialog created using ModalPopupExtender. There is an UI created in it using Webservices and a JQuery Templates. There is also a hidden ASP.NET button which is called from the javascript using the __doPostback() technique. The javascript hides the modal popup and __doPostback is called on the button (which is inside of the ModalPopupExtender)
I use this technique to pass some parameters are from the javascript. The server-side event handler does some processing and transfers to a page (in some cases, back to itself)
This works fine when the page it transfers to is a different one but if it transfers to the same page, the postback happens over and over again until the stack blows.
How do i stop the postback from re-occurring when I postback to the same page. I guess it doesn't happen the first time around because it posts to a different page and the postback is invalidated.
Code samples are difficult to provide as it's a fairly complicated system and it's difficult to break it apart.
It sounds horrible I know, all I want to do, however, it to call a server side function from javascript with some variables. Is there a better way to do this?
Well, you're posting back, so you have server-side control over your markup. Just stick your javascript that does the repost in a container and in the case that the page posts to itself, hide that container so it's not loaded into the page....
That or you could do client cookies or a querystring param. Both might be wonky.
With out a code sample I can only speculate and hopefully point you in the right direction.
When you transfer to a new page the old page (and therefore the javascript on that page) passes out of scope and therefore does not continue to execute. If, however, the page is reloaded and the condition that invoked the __doPostback continues then you have created the circular reference that causes your problem. Before you invoke __doPostback, but while you are still on the client, you need to clear whatever condition might be causing the chain of events.
If you can not uncover what is invoking your event chain then you might consider that instead of transferring back to the same page transfer to a new page (bounce.aspx) which in turn invokes a response.redirect BACK to the page so that it is not a Postback when it is being reloaded, but a fresh instance of the page. (Yes, this is a kludge, but it might be an effective stop gap...)
Cheers,
CEC
Thanks for the responses. I think i've found the solution.
In the server-side callback I was doing this:
setupPage();
Server.Transfer("mypage.aspx", true);
changing it to this:
setupPage();
Server.Transfer("mypage.aspx");
fixes the problem.
SetupPage() stores all of the data in hidden fields and I assumed that preserving the form state would be necessary so that this resided after the transfer. This doesn't seem to be the case as all of the setup I've done in the page before the transfer seems to still be present.
Odd or perhaps I'm misunderstanding something fundamental about .NET
Edit - Yes, I do misunderstand a lot about .NET. It makes my head hurt sometimes.
Thanks for the help

How to stop loading a page after the request is sent?

I have an ASP.NET (C#) page that has a long load time (like 2 minutes). The user is presented with a little animation and a "please wait" message. If the user accidentally loads this page, they need to wait for it to load.
My question is: Is there a way to stop the page load?
Thank you
If you want to stop the server side processing then its a tricky operation. Generally once a request is made that page is rendering on its own independant of other thigns going on. What you would probably need to do is re-engineer that page to check at regular intervals whether a stop command has been issued and abort whatever it is doing at that point. The stop flag could be put in session and should be cleared out after the stoppage.
You may also need to consider how to properly identify the right one to stop (in case there is more than one running). This could be done by returning a unique ID that can be used in part of a call to the "abort" page.
My approach though rather than this complciated rigmarole is to make efforts to stop the user from making this accident. Possibly make whatever link they are clicking pop up an alert saying "the following page will take several minutes to render, do you wish to continue" and then hopefully you will effectively be aborting the page request before it is even made.
I should note that I've never tried to do this sort of thing before so there may be easier ways to do it but this is how I'd probably think abotu going about the problem.
Try window.stop() in JavaScript.

asp.net - How can I update a text box asynchronously during a long process

I'm using MS Ajax toolkit and would like to be able to display status messages back to my user asynchronously. I have an update panel wrapped around a text box, this is the desired destination for any update message. Inside the update panel I have a trigger pointing to the click event of the only button on the page. I'm able to make the call to the method without a problem aber when I do something silly like
thisTextbox.text = "I know this is silly";
at the beginning of my long process...I don't get any update on the page. I'm missing something obviously, any help you can give would be appreciated. Thanks
on a side note, it it easy to get JQuery working in an ASP.net website? I tried with DOJO a few years ago and abandoned it for the pure asp "solution"
Jim
A synchronous status updates can be tricky. It typically involves creating a separate thread to perform the long operation and building in a machanism for that thread to report its progress. The GUI can then poll the thread via a timed refresh to get the status. Using the update panel makes this timed refresh appear a bit more smooth, but the same could be accomplished by refreshing the page or using an XMLHTTP request to poll the server for progress.
Maybe I'm getting it wrong, but have you tried to say
thisTextbox.text = "I know this is silly";
UpdatePanel1.Update();

ASP.NET C# Sending Information Back to Client While Processing Web Page

Not sure if I'll explain this properly but here goes. I having written an asp.net app using C# for the code behind. After the user makes some selection and hits the "run" button I pass off the processing to a dll written in C# but what I want is a way to periodically send information back to the client so they can see what's going on like how many records have been processed and things like that. How can I accomplish this?
thanks
Have a look at Provide feedback to the user on Long Running Tasks – using loader image - MS AJAX and JQuery
Also: How Do I: Use the ASP.NET AJAX UpdateProgress Control?
There are many ways of accomplishing this kind of task. I am presenting a few ideas
Solution 1:
You can use Ajax Timer Control.
Solution 2:
Make a Windows Service that will read the information and will interact with the asp.net application to notify about the requested information. It will act as a background worker.
Hope this helps
This may have been my wording of the question but I found what I was looking for. You can use the HttpResponse.Flush method to achieve what I was trying to do.
This is often called HTTP Server Push or HTTP Streaming or Long Polling. Depending on how it's done.
You can also check out this SO question on HTTP Streaming...
Cross-browser implementation of "HTTP Streaming" (push) AJAX pattern
Or this one with an example of Long Polling
How do I implement basic "Long Polling"?
https://stackoverflow.com/questions/tagged/long-polling

Categories

Resources