[Canonical page](<https://docs.dhtmlx.com/planning-engine/java/api/errors/plen-exception/>)
[Full documentation index](<https://docs.dhtmlx.com/planning-engine/llms.txt>)


# PlenException

Abstract base of every exception the engine throws: [`InputException`](<https://docs.dhtmlx.com/planning-engine/java/api/errors/input-exception.md>) for invalid input, and [`ProjectException`](<https://docs.dhtmlx.com/planning-engine/java/api/errors/project-exception.md>) for a call that doesn't fit the project's state. It's unchecked, so no method declares it in `throws`. Catch it to handle any engine failure in one place.

## Declaration

```java
package org.dhtmlx.plen;

public abstract class PlenException extends RuntimeException
```

## Constructors

### PlenException

```java
public PlenException(String message)
```

Sets the exception message. Called by the subclass constructors; application code doesn't create engine exceptions.

**Parameters**

| Name | Type | Description |
|---|---|---|
| `message` | `String` | Text returned by `getMessage()` |

## Methods

### getMessage

```java
public String getMessage()
```

Inherited from `Throwable`. The text depends on the subclass: the validation message for [`InputException`](<https://docs.dhtmlx.com/planning-engine/java/api/errors/input-exception.md>), the kebab-case error code (`"no-baseline"`, `"stale-baseline"`, `"needs-resync"`) for [`ProjectException`](<https://docs.dhtmlx.com/planning-engine/java/api/errors/project-exception.md>).

**Returns** the message passed to the constructor.

## Subclasses

| Subclass | When it occurs |
|---|---|
| [`InputException`](<https://docs.dhtmlx.com/planning-engine/java/api/errors/input-exception.md>) | The input is invalid. `kind` and `path` say what failed and where. |
| [`ProjectException`](<https://docs.dhtmlx.com/planning-engine/java/api/errors/project-exception.md>) | The call doesn't fit the project's state. `code` names the state. |

Each operation page lists which of the two it throws. [`MatchException`](<https://docs.dhtmlx.com/planning-engine/java/api/errors/match-exception.md>), thrown by [`SkillLayer.slots`](<https://docs.dhtmlx.com/planning-engine/java/api/skill-layer-slots.md>), doesn't extend `PlenException`; its `toPlenException()` returns the matching `InputException` or `ProjectException`. JDK exceptions (`NullPointerException` for a `null` argument, and others) don't extend it either. Conflicts, cycles, failure to converge and operations rejected by [`Project#apply`](<https://docs.dhtmlx.com/planning-engine/java/api/project-apply.md>) come back in results, not as exceptions. See [Error handling](<https://docs.dhtmlx.com/planning-engine/java/error-handling.md>).

## Example

```java
import java.util.List;
import org.dhtmlx.plen.*;

public class Main {
    public static void main(String[] args) throws Exception {
        Moment start = Moment.fromYmdHm(2026, 1, 5, 8, 0);

        // Two tasks with the same id fail validation.
        ProjectData data = new ProjectData().withTasks(List.of(
            new TaskData(Id.num(1)).withStartDate(start).withDuration(2.0),
            new TaskData(Id.num(1)).withStartDate(start).withDuration(3.0)));

        Project project = new Project();

        try {
            project.solve(data, new SolveOptions());
        } catch (PlenException e) {
            switch (e) {
                case InputException input ->
                    System.out.println("Invalid input at " + input.path + ": " + input.getMessage());
                case ProjectException state ->
                    System.out.println("Project state: " + state.code);
                default ->
                    System.out.println(e.getMessage());
            }
        }
    }
}
```

## Related

- [`InputException`](<https://docs.dhtmlx.com/planning-engine/java/api/errors/input-exception.md>) - invalid input
- [`ProjectException`](<https://docs.dhtmlx.com/planning-engine/java/api/errors/project-exception.md>) - a call that doesn't fit the project state
- [`MatchException`](<https://docs.dhtmlx.com/planning-engine/java/api/errors/match-exception.md>) - the skill layer's exception, outside this hierarchy
- [Error handling](<https://docs.dhtmlx.com/planning-engine/java/error-handling.md#catching-errors>) - catching engine errors in one place
