ResourceLoad#

The load and capacity of one resource over the requested range, split into buckets. You get one ResourceLoad per requested resource in LoadProfile::resources, returned by Project::load_profile or by Project::preview with a profile query.

Declaration#

#[derive(Clone, Debug, PartialEq)]
pub struct ResourceLoad {
    pub resource: Id,
    pub capacity_mode: CapacityMode,
    pub buckets: Vec<LoadBucket>,
}

Fields#

Field Type Description
resource Id The resource this entry describes.
capacity_mode CapacityMode Where each bucket's capacity comes from: the resource's calendar or a flat value.
buckets Vec<LoadBucket> One bucket for every bucket start in the query's [from, to) range, in time order. The list is dense: a bucket with no load is still present, with load 0.

The bucket size is the profile's LoadProfile::basis. The range comes from ProfileQuery.

Example#

use plen_core::{
    AssignmentData, Basis, DateTime, ProfileQuery, Project, ProjectData, ResourceData,
    SolveOptions, TaskData,
};

fn main() -> Result<(), Box<dyn std::error::Error>> {
    let day = |d| DateTime::from_ymd_hm(2026, 1, d, 0, 0).ok_or("invalid date");

    let mut task = TaskData::new("a");
    task.start_date = Some(day(5)?);
    task.duration = Some(3.0);

    let data = ProjectData {
        tasks: vec![task],
        resources: vec![ResourceData { id: "dev".into(), capacity: None, calendar_id: None }],
        assignments: vec![AssignmentData {
            id: None,
            task: "a".into(),
            resource: "dev".into(),
            value: 1.0,
            offset: None,
            duration: None,
        }],
        ..Default::default()
    };

    let mut project = Project::default();
    project.solve(Some(data), &SolveOptions::default())?;

    let mut query = ProfileQuery::new(day(5)?, day(12)?);
    query.basis = Some(Basis::Day);

    let profile = project.load_profile(&query.into())?;
    for load in &profile.resources {
        println!("{} ({:?}): {} buckets", load.resource, load.capacity_mode, load.buckets.len());
        for bucket in &load.buckets {
            if bucket.load > bucket.capacity {
                println!("  overallocated at {:?}", bucket.start);
            }
        }
    }
    Ok(())
}