Premium support for our pure JavaScript UI components


Post by david10sing »

Hi Guys,

I am not sure who the documentation for the crudManager was written for but I have gone through it and I have no clue how to get the crudmanager to work with the react wrapper...

I also have no clue how to pass custom stores that extends the ResourceStore and EventStore to the crudmanager...


Post by pmiklashevich »

Hello,

The CrudManager is provided for the Scheduler (simple) to manage multiple stores at once. The Scheduler Pro has Project model which mixes in CrudManager functionality. Gantt's Project model does the same. So if you need to configure you stores, you need to do it for the Project model.

SchedulerPro docs are merged with the Scheduler, so most part of the guide is related to simple Scheduler. And you can find the "Pro" leaf on the left, where Pro-like guides are stored. The project data guide is stored there. Gantt docs should be more clear. Gantt has project data guide too. As well as Crud manager general info.

how to pass custom stores that extends the ResourceStore and EventStore to the crudmanager

The answer to this question you can find here: https://www.bryntum.com/docs/scheduler-pro/#guides/schedulerpro/project_data.md#adding-custom-fields-to-entities
Here is how you can extend the Resource model and set it to the CrudManager (project):

class MyResourceModel extends ResourceModel {
    static get fields() {
        return [
            { field: 'company', type: 'string' }
        ]
    }
}

const project = new ProjectModel({
    resourceModelClass  : MyResourceModel
});

You can do the same for the Resource store:

class MyResourceStore extends ResourceStore {...}

const project = new ProjectModel({
    resourceStoreClass  : MyResourceStore
});

Please see API docs:
https://www.bryntum.com/docs/scheduler-pro/#SchedulerPro/model/ProjectModel#config-resourceStoreClass
https://www.bryntum.com/docs/scheduler-pro/#SchedulerPro/model/ProjectModel#config-eventStoreClass

how to get the crudmanager to work with the react wrapper

React wrapper doesn't do anything special about the project. It's the SchedulerPro.project config: https://www.bryntum.com/docs/scheduler-pro/#SchedulerPro/view/SchedulerPro#config-project

You can check out our React demos. Most of them work with crud manager (project). For example, check out SchedulerPro/examples/frameworks/react/javascript/resource-histogram demo. You can see in resource-histogram/src/components/config.js file how the project is configured:

// project
const project = (window.project = new ProjectModel({
  transport: {
    load: {
      url: 'data/data.json',
    },
  },
  autoLoad: true,
}));

// Scheduler
export const schedulerConfig = {
  project,

And in the resource-histogram/src/components/Content.js the config is passed to the wrapper:

      <BryntumSchedulerPro {...schedulerConfig} />

Scheduler https://www.bryntum.com/docs/scheduler-pro/#guides/integration/react.md guide (copied from simple scheduler) shows how to pass properties to the wrapper, and the project property is just one of many you can pass. Indeed, "project" property is not in the list of properties, we will update the docs. But it's supported for sure. https://github.com/bryntum/support/issues/2038

Gantt https://www.bryntum.com/docs/gantt/#guides/integration/react.md#integrating-gantt-with-react guide has similar guide too and the project is mentioned in the code snippet.

Please let me know if you're able to pass custom EventStore and ResourceStore to the Project and use it in you React application. We would appreciate your feedback of what exactly was not clear and how we could improve our docs.

Cheers,
Pavel

Pavlo Miklashevych
Sr. Frontend Developer


Post by david10sing »

Hi pmiklashevich,

Thank you for all the resource you pasted above but I still cannot get ProjectModel to work or CrudManager...

I got rid of CrudManager and put it in a ProjectModel. However, in my react app, I listen to changes in filter state to then make a request to the server like this

useEffect(() => {
    rpState.filters &&
      fetchResources(rpState)
        .then(res => {
          rpDispatch({
            type: Actions.set,
            payload: res,
          });
        })
        .catch(error => {
          IS_DEV && console.log(error);
        });
  }, [rpState.filters]);

and then in the BryntumScheduler react wrapper, I set the resources and events like this

<BryntumSchedulerPro
        ref={schedulerInstance}
        minHeight="100vh"
        resources={rpState.users?.rows}
        events={rpState.bookings?.rows}
        project={pulseProject}

Now I want to make a call to the server to retrieve holidays and populate the project calendars and also add weekends so events respect these non-working days. How would I do this? I've tried to do this but it doesn't work

pulseProject.calendarManagerStore.add([
        {
          id: 'weekends',
          name: 'Weekends',
          intervals: [
            {
              recurrentStartDate: 'on Sat at 0:00',
              recurrentEndDate: 'on Mon at 0:00',
              isWorking: false,
            },
          ],
        },
      ]);

I also want to add timeRanges. Could you provide actual example please


Post by pmiklashevich »

If I got you right, you're loading data for each store individually using your code for sending requests instead of using embedded into the Project model the Crud manager functionality. Then you want to load the received data to the corresponding stores one by one. How are you going to manage and sync your data then? We would suggest to use embedded Project functionality for sending AJAX requests and keep the data up-to-date. But if you still want to retrieve data using your solution, please collect it somewhere in a format the Crud Manager expects and when all data is ready, feed it to the Project using https://www.bryntum.com/docs/scheduler-pro/#SchedulerPro/model/ProjectModel#function-loadCrudManagerData API. This method accepts the response and loads it to the project stores.

The way you bind resources and events is a shortcut. If you check out the docs of SchedurPro.resources (https://www.bryntum.com/docs/scheduler-pro/#SchedulerPro/view/SchedulerPro#config-resources) you'll see that it expects an array of resources which will be passed to the ResoueceStore. That means that all 4 types of initializing resources are equal:

  • as resources config
    new SchedulerPro({
        resources : [...]
    })
    
  • as ResourceStore config
    new SchedulerPro({
        resourceStore : {
            data : [...]
        }
    })
    
  • as resourcesData config of the project
    new SchedulerPro({
        project : {
            resourcesData : [...]
        }
    })
    
  • as ResourceStore config of the project
    new SchedulerPro({
        project : {
            resourceStore : {
                data : [...]
            }
        }
    })
    
    You can see what data is supported in the Project model docs:
    Снимок экрана 2020-12-10 в 13.25.49.png
    Снимок экрана 2020-12-10 в 13.25.49.png (299.61 KiB) Viewed 1609 times

You can also specify a new project config and pass it to the Scheduler. Please check out Big dataset demo sources to see how we do it (SchedulerPro/examples/bigdataset/app.js):

    scheduler.project = {
        assignmentStore : {
            useRawData : true,
            data       : assignments
        },
        resourceStore : {
            useRawData : true,
            data       : resources
        },
        eventStore : {
            useRawData : true,
            data       : events
        },
        dependencyStore : {
            useRawData : true,
            data       : dependencies
        }
    };

About the calendar, beside loading calendar data to the CalendarManagerStore, you also need to specify what calendar the project uses. Please see calendar field on the project model.

If you need further help with the loading data, please prepare a small runnable testcase showing how you load data. (exclude node_modules and our libs). No server side code required. Just mock up your responses.

Best,
Pavel

Pavlo Miklashevych
Sr. Frontend Developer


Post by david10sing »

Hi pmiklashevich,

Thank you for your reply. Yes the team in general preferred to use the ProjectModel and have bryntum's internal crudmanager manage the stores.

However, to get this setup with React it is quite hard.

useEffect(() => {
    loadProjectData(rpState);
  }, [rpState.filters]);

When my react component loads, we set a bunch of filters to the application state and use the useEffect hooks to listen to changes on rpState.filters. However, this fires the loadProjectDate() 3 times due to react's component lifecycle and the state changing.

Is there a way to cancel previous project.load() calls? I've tried to store the project.load() promise in a variable as follows:

const projectLoading = pulseProject.load({});

Tried to cancel as follows:

pulseProject.cancelRequest(projectLoading, () => console.log('tes't))

The callback seems to get fired but the requests in the network tabs are not...

If you need more information, please let me know. Cheers


Post by pmiklashevich »

Hello,

Indeed, cancelRequest has no options to cancel a request. It just executes the function you pass as the second parameter. And we do not provide an access to the reject function. Ticket here: https://github.com/bryntum/support/issues/2094

Please keep in mind if you call project.load() before the first request is finished, the first request will be canceled. Though the network tab will show the request but the response will be ignored due to the cancelation.

In your case I would suggest to introduce a new flag, showing that all filters are loaded, and only after that call your loadProjectData function.

Best,
Pavel

Pavlo Miklashevych
Sr. Frontend Developer


Post by david10sing »

Hi pmiklashevich,

We are handling the load request in a batch request type of endpoint and the endpoint takes some time to respond as it puts some load on the server.

Also our filters can be dynamic as in the users can change them at anytime so we won't be able to have a flag to check that all filters are set...

Would the best solution then be to use my own methods for loading and syncing the resources and events?


Post by pmiklashevich »

If your server has a restriction for requests frequency, you can limit the load calls since you call them manually. Just implement a queue. If you want to use autosync and prevent requests to be sent too often, you can set autoSync to true and bump the autoSyncTimeout to be greater than 100 ms (default value).

Pavlo Miklashevych
Sr. Frontend Developer


Post by david10sing »

Hi pmiklashevich,

I have a question with regards to the CalendarManagerStore.

I am loading the following data through project.loadCrudManagerData().

calendars: { "rows": [ { "id": "weekends", "name": "Weekends", "intervals": [ { "recurrentStartDate": "on Sat at 0:00", "recurrentEndDate": "on Mon at 0:00", "isWorking": false } ] } ] },

Now I want to add more intervals to this weekends calendar. I have tried

project.calendarManagerStore.first.appendChild({
          startDate: new Date(2020, 11, 25),
          endDate: new Date(2020, 11, 25),
          isWorking: false,
})

But when I try to create an event, it allows creating the event over the 25/12/2020. Furthermore, how would I send the date from the server itself in the calendars object?


Post by pmiklashevich »

Please start a new thread for every new question. Also specify what product you're using (including version).
I would recommend you to learn this guide first: https://www.bryntum.com/docs/scheduler-pro/#guides/schedulerpro/calendars.md

Calendars are trees. You can try to modify non-working-time demo to see how it works:
SchedulerPro/examples/non-working-time/data/data.json

{
    "success"     : true,
    "project"     : {
        "calendar" : "holidays"
    },
    "calendars": {
        "rows": [
            {
                "id": "weekends",
                "name": "Weekends",
                "intervals": [
                    {
                        "recurrentStartDate": "on Sat at 0:00",
                        "recurrentEndDate": "on Mon at 0:00",
                        "isWorking": false
                    }
                ],
                "children" : [
                    {
                        "id"           : "holidays",
                        "name"         : "Holidays",
                        "intervals"    : [
                            {
                                "startDate" : "2020-03-25",
                                "endDate"   : "2020-03-26",
                                "isWorking" : false
                            }
                        ]
                    }
                ]
            }
        ]
    },

Child calendar should be set to the project.

To see that in action need to adjust Scheduler's config a bit:
SchedulerPro/examples/non-working-time/app.js

    startDate         : '2020-03-22',
    endDate           : '2020-03-28',
    viewPreset : 'weekAndDayLetter',
Снимок экрана 2020-12-28 в 14.43.12.png
Снимок экрана 2020-12-28 в 14.43.12.png (138.69 KiB) Viewed 1521 times

You can try to achieve the same from console. First change SchedulerPro/examples/non-working-time/data/data.json

{
    "success"     : true,
    "project"     : {
        "calendar" : "weekends"
    },
    "calendars": {
        "rows": [
            {
                "id": "weekends",
                "name": "Weekends",
                "intervals": [
                    {
                        "recurrentStartDate": "on Sat at 0:00",
                        "recurrentEndDate": "on Mon at 0:00",
                        "isWorking": false
                    }
                ]
            }
        ]
    },

Project calendar is weekends again.

Run in console:

scheduler.project.calendarManagerStore.first.appendChild({
    "id"           : "holidays",
    "name"         : "Holidays",
    "intervals"    : [
        {
            "startDate" : "2020-03-25",
            "endDate"   : "2020-03-26",
            "isWorking" : false
        }
    ]
});

You add holidays calendar as a child of weekends. Now need to apply new calendar which contains info of the holiday to the project:

scheduler.project.calendar = 'holidays'

Also please pay attention to the dates of the interval. If start and end dates point to the same date, there is no interval. To make one day holiday, end date should be start date + 1 day.

Best,
Pavel

P.S. Found an issue with adding intervals to existing calendars dynamically. Ticket here: https://github.com/bryntum/support/issues/2176

Pavlo Miklashevych
Sr. Frontend Developer


Post Reply