3

I am developing a website using ASP.NET MVC 3.

I have a number of sections containing news from different departments, as shown in the picture below:

https://i.stack.imgur.com/G21qi.png

The sections are added to the masterpage by using

@Html.Action("_News", "Home", new { id = 1 })

Where id 1 = "Ledelsen", 2 = "Omstillingen" and so on.

My Controller contains the following Action:

[ChildActionOnly]
public ActionResult _News(int id)
{
    // controller logic to fetch correct data from database
    return PartialView();
}

I got CRUD up and running, but my question is how I can refresh the PartialViews without postback, at a set interval?

I'm guessing I have to use Javascript/jQuery to accomplish this, but I have not been able to.

Can anyone point me in the right direction or better yet, provide an example of how to do this?

Thanks in advance

EDIT: Just to clarify I do not want the whole page to refresh, but only do an asynchronous refresh of the partialviews

Casper
  • 193
  • 1
  • 2
  • 12

2 Answers2

8

In your partial view, I'd suggest wrapping the whole thing in a div:

<div id="partial1">

In javascript you'll need a function to use AJAX to load the partial view into the div:

$("#partial1").load("_News", { id="1"} );

That's using jQuery. Some documentation here. Basically, that will replace the div indicated with view generated from the call to your _News action. The id can be varied if you add some logic to the javascript call.

Then wrap the call to load() in a setTimeout():

var t = setTimeout(function () {$("#partial1").load("_News", { id="1"} );}, 60000);

That will run the included function every 60 seconds. t can be used, thusly clearTimeout(t) anywhere in your javascript code to stop the auto refreshing.

EDIT

This should address the caching issue. Thanks @iko for the suggestion. I've noticed you need cache: false for this to work.

var t = setTimeout(function () { $.ajax({ 
                                     url: "_News", 
                                     data: { "id": "1" }, 
                                     type: "POST", 
                                     cache: false, 
                                     success: function (data) { 
                                          $("#partial1").innerHTML = data; 
                                     }}); }, 60000);
Steve Mallory
  • 4,245
  • 1
  • 28
  • 31
  • I am, like, no jQuery expert, but aren't you missing a function wrapper around the call in setTimeout? This look like it would call load and then pass whatever the load function returns (a request object?) into setTimeout, which i would guess would result in an error. – AHM May 30 '11 at 00:23
  • @AHM I think the example is correct, though I wouldn't say it's complete. .load() is a wrapper around .ajax(). It loads the returned html into the calling element. You _can_ include a callback function, buts it's not required. And setTimeout simply calls the includes code on schedule. – Steve Mallory May 30 '11 at 12:36
  • Hmmm.... unless load returns a closure, then this is wrong. SetTimeout definitely requires a callback as it's first argument. I think this should be setTimeout(function(){$("#partial1").load("_News", { id="1"} )}, 60000) – AHM May 30 '11 at 13:38
  • @AHM Yes, you are correct. I was going from memory, always a bad decision in my case. I'm updating my answer. Thanks. – Steve Mallory May 30 '11 at 14:00
  • I ended up using this solution which worked perfectly on localhost. On the server however, it always refreshes the sections according to their content at page load. This means that even if I submit something, it will wait the 60 seconds and the first time jQuery reloads, it will load the old content, as if it is caching it. Any ideas? As I said it works perfectly on my local machine. – Casper Jun 07 '11 at 14:17
  • Just as a side note, if I manually load the section in a new tab using "/Home/_News/1" (or 2/3), I will get the actual content and once this is loaded, the other tab will load correctly at next refresh, but only for that refresh. The problem persists when more data is submitted (or deleted for that matter) – Casper Jun 07 '11 at 14:20
  • @Casper You need to use `$.ajax( type: "POST", ... )` or `$.post(...)` to prevent e.g. IE from caching. IE will aggressively cache and will show the same data even if you send a different ID with a similarly formed get via Ajax. I would recommend changing the example to $.post or $.ajax for this reason. – lko Mar 01 '12 at 11:39
0

I'm going to refer you an answer I gave to a related question "UpdatePanel" in Razor (mvc 3) for a starting point. Note, that its not that different to Steve Mallory's answer but highlights some other points.

The difference however being, that you may need to remove the [ChildActionOnly] attribute if you want to update each partial view individually (update id 1 only or update id 2 only).

This script can be placed in the returned partial.

<script type="text/javascript">
    setInterval(function()
    {
          $.load('<%= Url.Action("_News", "Home", new { id = Model.Id } ) %>', function(data) {
          $('#partial_'@(Model.Id)').html(data);
      });
    }
    , 30000);
</script>

<div id="partial_@(Model.Id)" />
Community
  • 1
  • 1
Ahmad
  • 22,657
  • 9
  • 52
  • 84