Persist currentView state

Hi,
for a scalable application it would be great to avoid costly calls to persist application data. When appointments have been loaded on demand, let's say for a given month, the view settings are posted to GetData (CurrentView, CurrentDate, CurrentAction). However, once a batch action has completed these parameters are no longer available. Is there a way to add them to the CRUD URL?
Example:
User1 loads Schedule -> public IEnumerable<ScheduleDatabase> GetData([FromBody] ScheduleGetDataRequest request)
User2 adds an appointment within the same view.
User1 updates an appointment: public JsonResult Batch([FromBody] EditParams param)

Now at the end of the batch method, I'd like to return the same data that GetData([FromBody] ScheduleGetDataRequest request) would return.

Storing ScheduleGetDataRequest request in a session or cookie does not appear sensible. I'm sure you have a much better way!
Thanks again
Stefan

6 Replies

ST Stefan November 1, 2017 09:20 PM UTC

I may have figured this out now, not sure how to sensibly post code here. In essence, I add GET parameters to the CRUD URL, and update those later on "onNavigation".

e.g. <ej-schedule id="YourSchedule" .... current-date="@DateTime.Now" current-view="Month" enable-load-on-demand="true" navigation="onNavigation">

<e-datamanager url="Schedule/GetData" crud-url="Schedule/[email protected]&amp;currentView=month" adaptor="UrlAdaptor" cross-domain="true"></e-datamanager>

One would need to include currentDate and currentView because a Crud operation could happen before any navigation occured.

Finally, we need

function onNavigation(args) {
        var scheduler = $("#YourSchedule").data("ejSchedule");
        console.log("onNavigation");
        scheduler._dataManager.dataSource.crudUrl = "Schedule/Batch?CurrentDate=" + args.currentDate.toISOString() + "&currentView=" + args.currentView;
    }

Now the Controller Batch method can look like this

public JsonResult Batch([FromBody] EditParams param, [FromQuery] ScheduleGetDataRequest request)

where ScheduleGetDataRequest is the same as for getData with load-on-demand=true; it simply contains
    
public DateTime CurrentDate { get; set; }
     public string CurrentView { get; set; }
     public string CurrentAction { get; set; }

Maybe this helps someone.



NR Nevitha Ravi Syncfusion Team November 2, 2017 04:53 PM UTC

Hi Stefan, 

Thanks for you update. 

We regret for the delayed post. When LoadOnDemand is enabled, GetData will call after every CRUD operations. If you want to pass current date and current view to Batch function, we can pass it to headers of urlAdaptor and access it in the function as an alternate to your solution. We have prepared the below sample for your reference 
 
 
<ej-schedule id="Schedule1" width="100%" height="525px" enable-load-on-demand="true" action-complete="onCreate" current-date="new DateTime(2014, 12, 5)"> 
    <e-appointment-settings apply-time-offset="false" id="Id" subject='"Subject"' start-time='"StartTime"' end-time='"EndTime"' all-day='"AllDay"' recurrence='"Recurrence"' recurrence-rule='"RecurrenceRule"'> 
        <e-datamanager id="myData" url="Home/GetData" crud-url="Home/Batch" adaptor="UrlAdaptor"></e-datamanager> 
    </e-appointment-settings> 
</ej-schedule> 
@section scripts{ 
    <script> 
        function onCreate(args) { 
           
            var customAdaptor = new ej.UrlAdaptor().extend({ 
                beforeSend: function (request, settings) { 
                    var schObj = $("#Schedule1").data("ejSchedule"); 
                    currentDate = schObj.model.currentDate; 
                    currentView = schObj.model.currentView; 
                    settings.setRequestHeader("CurrentDate", currentDate); 
                    settings.setRequestHeader("CurrentView", currentView); 
                } 
            });       
        this.model.appointmentSettings.dataSource.adaptor = new customAdaptor(); 
    } 
    </script> 
} 
Controller: 
public List<DefaultSchedule> Batch([FromBody] EditParams param, [FromHeader(Name = "CurrentDate")] DateTime currentDate, [FromHeader(Name = "CurrentView")] DateTime currentView) 
        { 
            if (param.action == "insert" || (param.action == "batch" && (param.added.Count>0))) // this block of code will execute while inserting the appointments 
            { 
                DefaultSchedule appoint = new DefaultSchedule(); 
                object result; 
                if (param.action == "insert") 
                { 
                    var value = param.value; 
                    foreach (var fieldName in value.GetType().GetProperties()) 
                    { 
                        var newName = fieldName.ToString().Split(null); 
                        if (newName[1] == "Id") result = (_context.DefaultSchedule.ToList().Count > 0 ? _context.DefaultSchedule.ToList().Max(p => p.Id) : 1) + 1; 
                        else if (newName[1] == "StartTime" || newName[1] == "EndTime") result = Convert.ToDateTime(fieldName.GetValue(value)); 
                        else result = fieldName.GetValue(value); 
                        fieldName.SetValue(appoint, result); 
                    } 
                    _context.DefaultSchedule.Add(appoint); 
                } 
        

Regards, 
Nevitha. 
 



ST Stefan November 2, 2017 06:28 PM UTC

Hi Nevitha,

thank you very much for the update. I didn't realise that GetData is called after Batch, this solves the problem without any changes. It might be useful to add this piece of information to your documentation?

Also, the controller sample in the documentation is specified as 

public JsonResult Batch([FromBody] EditParams param)

and in fact returns a list of appointments (from the documentation: return List<ScheduleDatabase> appointments = _context.ScheduleDatabase.Take(500).ToList())

In fact, it could return void and save a call to the database, since GetData takes care of that.

Thanks for pointing this out.




KK Karthigeyan Krishnamurthi Syncfusion Team November 3, 2017 11:06 AM UTC

 
We are happy to hear from you. 
 
We will consider your valuable suggestion for documentation. 
 
Regards, 
Karthigeyan 
 




ST Stefan November 3, 2017 03:12 PM UTC

Just for anyone following this thread, my assumptions weren't entirely correct. The batch method does indeed have to return a result, otherwise the Schedule component will run into a lot of xyz is undefined Javascript errors.

The way I have done this now is to only return what was changed in the dbContext.

public JsonResult Batch([FromBody] EditParams param)
{
    switch (param.Action)
    {
            case "insert":
                    appointment = _manipulateAppointment(param.Value);
                    _context.ScheduleDatabase.Add(appointment);
                    break;

            [...]

    _context.SaveChanges();
    return Json(_context.ScheduleDatabase.Local.ToList());

This appears to be working fine.



NR Nevitha Ravi Syncfusion Team November 6, 2017 04:41 PM UTC

Hi Stefan, 

Thanks for your update. 

Yes, the batch method should return appointment collection. By default, when loadOnDemand is enabled, the updated appointment collection (which sent to source from batch method) will pass to GetData method after every CRUD operations.  

Regards, 
Nevitha. 


Loader.
Up arrow icon