Flowable CMMN milestones

Milestones let a Flowable case record that a business point has been reached, so other parts of the case and your status reports can rely on it. This page covers how they work, how to name and configure them, and what to confirm before building.

On this page

Flowable CMMN milestones: tracking case progress against business points

A milestone in a Flowable CMMN case records a business point reached in the case, such as a customer's identity being verified or a claim being approved for payment. Because case work has no fixed sequence, a milestone gives managers a stable answer to where a case stands, and it can also trigger sentries that open or close other parts of the case and feed status reports built from case data. Teams that run knowledge work, such as complex claims, investigations, onboarding exceptions or licensing reviews, usually need milestones because the order of tasks changes from one case to the next while the business still needs to know which outcomes have happened.

A simple task list is enough when the work is short, the steps are the same for every case, and the only question is whether each step is done. In that situation a BPMN process or a flat set of human tasks is easier to model, test and report on than a case with milestones. Before you add milestones, list the business points your managers ask about and check that each one can be observed from the case, either through a completed task, a variable change or an event. A milestone that nobody can explain to an auditor or a team lead adds modeling cost without adding visibility. Confirm the exact milestone and history behavior for your Flowable version in the CMMN documentation and test it against your own case definitions before you design reports around it.

Which milestone design fits which reporting need

This table compares four ways to model a milestone in a Flowable CMMN case: as a status marker, as a sentry trigger, as a data-carrying record for reporting, and as a business-named outcome. Read each row for when the design fits, what it costs to model and test, and what to confirm in the documentation for your Flowable version. Most cases combine the second and fourth options, and the reporting option adds the most testing effort.

DesignWhen it fitsCost to model and testWhat to confirm for your version
Status marker onlyProgress views need a simple yes or no per stage, and no other plan item depends on the milestone.Low. One milestone plan item and a few tests that confirm it occurs when its parent condition is met.How milestone occurrence is recorded in history and whether your REST queries return it as expected.
Sentry triggerOther stages or tasks should start or wait only after a business point is reached, such as a review being approved.Medium. Each sentry on-part and if-part needs tests for ordering, repeats and cases where the milestone never occurs.How sentries referencing milestones are evaluated in your version, and whether an on-part reacts to the milestone event or its state.
Milestone with data for reportingDashboards or audit extracts need values captured at the moment the milestone occurred, such as an approved amount or decision date.Medium to high. Variables must be set, scoped and named consistently, and tests must cover missing, updated and repeated values.Which case or local variables are available at milestone time, and how history queries expose them to your reporting pipeline.
Business-named outcomeOperations staff, auditors or customers read case status, so milestone names should match terms the business already uses.Low to medium. Naming is cheap, but names become a contract once reports and integrations reference them.Whether milestone names are free text in your model and which identifiers reports and REST calls should use instead of display names.

When a milestone is reached and what that means for sentries

A milestone plan item occurs when the case engine decides that a condition the business cares about has been met, not when someone finishes a piece of work. A task completes when its work is done and its completion is recorded. A milestone is different: it has no work of its own, so it occurs when the engine evaluates its entry criteria and finds them satisfied, typically because a sibling task, stage, or variable has reached the state the model describes. That distinction matters for design. If a team models a milestone as though it were a task that a person must close, the case will wait on a step nobody performs. Before building, confirm in the Flowable CMMN documentation for your engine version exactly which events can make a milestone occur, how its entry criteria are written, and whether it can be reactivated or terminated.

Because a milestone occurs as a plan item event, it can satisfy a sentry. A sentry on another plan item can reference the milestone in its on-part, so work that depends on the business condition starts only after the milestone has occurred. An if-part can add a further test, such as a case variable value, so the dependent work starts only when the condition is met and the data is right. When a sentry is not satisfied, the plan item it guards stays in its available or enabled state and does not start. It does not fail, and nothing downstream runs until the sentry becomes true, which is why a missing or misnamed milestone can leave a case quietly stalled. Plan a case status check that lists which sentries are waiting, and test the paths where a milestone never occurs.

Ask your implementation partner or internal engineers to document each sentry that references a milestone, the on-part and if-part it uses, and the outcome if the milestone never occurs. Then run test cases that drive the case to each milestone in different orders and confirm the dependent work starts only where intended. The exact occurrence and sentry evaluation behavior should be verified against the documentation and test results for the specific Flowable release in your environment, since rules around events and reactivation can differ between versions.

How to set up milestones in a Flowable case

This sequence moves a milestone from a business name agreed with the process owner to a verified case plan item that fires only when its entry criteria are met, with a state the case status report can read.

  1. Agree milestone names with the process owner

    Before any modeling, the case designer and the process owner agree on the list of milestones the business will recognize, such as a named stage of approval or a point where a customer request is ready for the next team. Each name should describe a state the business can confirm, not an activity still in progress, and the list should stay short enough that a status report reads clearly. Record the agreed names and a one-line definition for each, since these become the labels in the case model, the reports and the test scripts. The step is done when the process owner signs off the list in writing and every milestone has a definition that someone outside the project could check.

  2. Model milestone plan items and entry criteria

    In the CMMN model, add a milestone plan item for each agreed name and give it the entry criteria that describe when the business state is reached. Use the plan item name or documentation to carry the business label so the model matches the list from the previous step. Keep the milestone's entry criteria tied to the work that produces the state, not to a single task completing, so that the milestone reflects the business outcome. Validate the model in your modeling tool and deploy it to a local engine. The check is that the case definition deploys without errors and that each milestone appears once with the name and documentation the process owner approved.

  3. Wire sentries to the milestones

    Connect the milestones to the rest of the case by using them as on-part or if-part conditions in the sentries of other plan items, such as a stage or task that should start only after a milestone is reached. Decide which sentries should react to the milestone event itself and which should check a case variable the milestone sets, because the two behave differently when a case is reactivated or when the milestone is reached more than once. Document each dependency in a short table so reviewers can trace why a task waits. The check is a walk through the model where each sentry points to a milestone that exists in the list from step one, with no orphaned references.

  4. Add the data the status report needs

    Decide which case variables the status report reads, such as the date the case entered a stage, the owner of the next action or the reason a milestone is still pending. Set these variables in the tasks or listeners that drive each milestone, and make sure the variable names are consistent across the model and the reporting query. Where a value is derived from the milestone itself, record it at the moment the milestone is reached rather than rebuilding it later. The check is a test run that completes the case path and shows each expected variable set, with values that match the business definition from step one.

  5. Deploy to a test environment with a test database

    Deploy the case definition to a test environment that uses the same supported database type as production, so that history tables and time precision behave as they will in production. Confirm the database type and version against the Flowable configuration documentation before you run tests, because history and timestamp behavior depends on them. Start the case through the Java API or the CMMN REST API and confirm the deployment is visible to the engine. The check is that the engine reports the deployed case definition version and that the test database accepts a case instance without errors.

  6. Verify each milestone fires only when expected

    Write one test case per milestone that drives the case to that state and asserts that the milestone plan item reaches the completed or available state. Write a second test for a path where the milestone should not fire, such as an entry criterion left unsatisfied, and assert it stays pending. For each test, query the history tables or the history API for the milestone's plan item instance and confirm its state, timestamp and the case variables it should set. Repeat the tests after any model change. The check is a passing suite in which every milestone has a positive and a negative test and each history query returns the state the business definition predicts.

  7. Confirm the report reads the milestone data

    Run the status report query or service against the test history after the milestone tests pass, and compare its output with the expected status for several case states, including a case still in progress and a case that has finished. Ask the process owner to review the report labels in a test session so the business names appear as agreed in step one. Record any mismatch, fix it in the model or the query and rerun the milestone tests. The step is complete when the process owner accepts the report output in writing and the test suite passes on the same model version that will move to production.

Reporting case status from milestone data by audience

Operations staff look for cases that have stalled. They need to see which milestones are open for each active case, when the last milestone was reached, and which plan items are holding back the next one. They should read this from live case state, because history only records what has already happened and a stalled case shows up in live state first. Most teams check these views several times per shift, so alerts based on the time since a case last reached a milestone usually work better than scanning every case by hand.

  • Open milestones and their entry criteria: which milestones are available but not yet reached, and the variables or plan items they wait on.
  • Time since the last milestone: the main signal for a stalled case, compared against a threshold the business has agreed.
  • Blocking plan items: human tasks or child cases holding a milestone back, shown with their assignee or work queue.
  • Failed or stuck jobs tied to a case: asynchronous work that prevents a milestone from being reached, read through engine tooling.
  • Business names on every milestone: operators should see the agreed label, not a model element ID they must look up.

Check that the milestone names and plan item IDs in operations views match the model version each running case uses.

Common milestone mistakes that break status reporting

Milestone reporting usually fails for reasons that have little to do with the engine. The milestones are named for developers, they stand for too much, or they feed sentries nobody has exercised. Each card below names the symptom a manager sees first and the fix to plan before the case model goes into production.

Naming milestones after task IDs

Teams often copy the internal identifier of a plan item into the milestone name, so the report reads something like Milestone_2b7 or CheckAPI. A manager cannot tell which business step was reached. Name each milestone for a business state the case owner already uses, such as credit memo approved or identity verified, and keep the technical ID in the model only. Check the names with a case owner before the model is built, and review them whenever the model changes.

One milestone for several states

A single milestone is sometimes placed after a stage that can end in approval, rejection or a request for more information. The status report then shows the milestone as reached for all three outcomes. Split the outcomes into separate milestones, or keep the milestone for the one state it truly represents. Confirm with the business owner which states must be distinguishable in reports and audits.

Status written into free-text variables

Some implementations record progress by setting a string variable such as status to a sentence the team wrote during development. Reports then depend on exact wording, and a small text change silently breaks every query. Let the milestone history carry the progression and keep case variables for values that are structured, such as an amount or a decision code. Agree on a fixed list of values if a variable must hold status at all.

Sentries that depend on untested milestones

A sentry may wait for a milestone that no test ever reaches, for example because the path that creates it only runs after a rare exception. The case then stalls with no error, and the manager sees work that never moves. Write a test for each milestone that a sentry or report relies on, covering both the normal path and the path where the milestone should not occur. Treat any sentry on a milestone as a dependency that needs a named owner.

Reporting on milestones without a history plan

Teams sometimes build a dashboard that counts milestones reached, then discover that history was configured to be removed after a short period. Trend and audit questions about past cases then have no answer. Confirm the history retention setting, the query that reads milestone events, and who needs historic progress before the reporting design is final. Test the query against finished cases, not only running ones.

Naming milestones the business recognizes

Milestone names are the part of a Flowable case model that people outside engineering will read most often, so choose them with the business before the model is built. A milestone name should describe a business fact the process owner would recognize, such as "Credit memo approved" or "Customer identity verified", rather than an internal step label like "Milestone 3" or "Check done". Keep the plan item identifier (the id attribute in the CMMN XML) in a separate, stable naming scheme that engineers own, and put the business wording in the name attribute. The identifier is what sentries, queries and migration mappings refer to, so changing it later breaks more than a label. Ask the process owner to read the list of milestone names as a plain sequence of statements and confirm that each one means the same thing to the people who act on it.

Labels shown in reports and audit extracts should come from the same vocabulary as the model, not from a second list maintained in a reporting tool. Decide who owns the glossary of milestone names, record the approved wording alongside the case definition, and make the report layer read the name value rather than hard-coding text. Check how your reporting queries pull milestone data from the history tables, because the names you see there depend on what was stored when the milestone occurred. Confirm with your audit or compliance contact whether they expect a specific wording in evidence, since an auditor will compare the milestone trail against the control description you give them. Do not treat this as settled until a test case run shows the expected names in the history output.

Keep names stable across case versions. When a business term changes, change the name and leave the identifier alone wherever possible, so that reports built on the old identifier continue to map and so that the mappings used in case instance migration still line up. Where a milestone must be split, merged or retired, record the old and new identifiers in a change note that reports and migration plans can use. Before the first deployment, walk the process owner through the full list of milestone names and identifiers, confirm the wording and agree who approves future changes. Follow the Flowable release notes when you plan a version upgrade, since a platform change can affect how names are stored or displayed in history.

Security and operational considerations for milestone data

Milestone records are small, but they feed case status, reports and sentries, so they inherit the access and retention decisions made for the whole case. The cards below cover who can see milestone state, how reports built on it are protected, what happens to it over time, and how to catch milestones that stop behaving as modeled.

Who can read milestone state

Milestone state is returned through the engine's Java services and the CMMN REST API, so any caller with access to those interfaces can see which milestones a case has reached and when. Map which roles may query case instances and history, and confirm that the application, not the engine alone, filters results by tenant, owner or organizational unit. Check this against the REST and history queries your front ends actually make.

Protecting milestone-driven reports

Status dashboards built from milestone history often run under a service account with broad read access, which turns a reporting feature into a wide data path. Give reports their own read-only identity, restrict them to the milestone and variable fields they display, and log who exported what. Treat any milestone name that encodes customer or case details as data to classify, not as a harmless label.

Retention and purge of milestone history

Milestone entries live in the engine's history tables, so they are removed only when the history of the completed case is removed. Decide how long case history must be kept for audit and dispute handling, and whether purge runs by case end date or by definition. Confirm that a purge job does not delete cases still waiting on sentries that reference their milestones, and test a restore from backup before relying on it.

Detecting stuck or unexpected milestones

A milestone that never occurs usually points to a sentry whose if-part never becomes true, a plan item that was never created, or a case stalled behind a required task. Track open cases by age and by the last milestone reached, and alert when a case sits in one state beyond the period your business defines. Use the engine's job and history data to tell a waiting case from a failed one before escalating.

Keeping milestone names stable for audit

Reports, audit queries and sentries all refer to milestone names, so a rename in a new case definition can silently break reporting or leave historical cases unreadable by the new query. Agree a naming register with the business, record which definition version introduced each milestone, and review changes as part of case instance migration. Ask your reviewers which names they will use when they test your evidence.

What teams ask before building milestone-based case reporting

What drives the cost of designing milestones in a Flowable case?

The main driver is how many business outcomes the case must report and how many people must agree on their names and meanings. Each milestone needs a clear entry condition, a defined data source, and a sign-off from the business owner who will read the status. Cost rises when milestones depend on data that lives in several systems, when the case has many stages with overlapping outcomes, or when the definition changes after testing has started. Ask any partner to price the design workshops, the modeling, the test cases for each milestone, and the rework allowance separately, since those parts behave differently over time.

How long does a first milestone model usually take?

The duration depends mostly on case size and how settled the business process is. A case with a small number of stages and milestones that map to events already in the data can be modeled quickly, while a case with many stages, unclear handoffs, or milestones that need approval logic takes longer. Before any estimate is accepted, ask for the number of milestones in scope, the number of case definitions, the systems that supply milestone data, and the review cycles assumed. A written schedule should list those inputs so you can see what changes the timeline.

What does the business and the engineering team need to provide?

The business side must supply the names it uses for progress, the rules that decide when a stage is complete, and a named owner who can confirm each milestone's meaning. Engineers need access to the case model, the test environment, the data sources that feed each milestone, and a way to see running case instances. Both groups should agree early on which status terms appear in reports, since renaming milestones later changes queries, dashboards and sometimes audit evidence. Confirm these inputs in the scope document before work starts.

Can an internal team build milestone reporting without a partner?

Yes, an internal team with Java and Flowable experience can build milestone reporting, provided it has someone who understands the CMMN model and someone who owns the business vocabulary. The work usually becomes harder where the team has not yet run cases in production, where reporting must match audit or regulatory expectations, or where the same people must also run the platform. A useful test is whether the team can explain, for each milestone, what event fires it, how that event is stored, and how a reviewer would verify it. If those answers are not ready, a short external review can reduce risk.

Which questions should a written quote answer about milestones?

A written quote should state the scope in concrete terms: the case definitions covered, the number of milestones, the data sources each milestone uses, and the reports that will read them. It should separate one-time work such as design, modeling, testing and documentation from any recurring work such as support or changes after go-live. Ask who performs each task, what the acceptance criteria are, how changes to milestone names or sentries are handled, and what remains the customer's responsibility. DeployOpen agrees scope, deliverables and timelines in writing before work starts, so ask for those items to be listed explicitly.

What breaks when milestones are reported from the wrong data?

The most common failure is a milestone that appears reached when the underlying condition was only partly satisfied, such as a case marked as approved when a required task was skipped or completed by a different role. Reports then show progress that does not match what happened, which damages trust with business users and auditors. Engineers should test each milestone with positive and negative cases, record which variables or events it depends on, and review whether history queries reproduce the same answer after a case definition changes. Flowable's history data can help here, but the reporting logic still has to be verified.

Does milestone reporting need changes when the case definition is upgraded?

It can. When a case definition gains or renames elements, milestones tied to those elements may stop firing or report against the wrong names. Teams should check the Flowable documentation and release notes for the version they plan to run, then test milestone reports against running and newly started cases before cutover. Migration of running case instances between definition versions is a separate design task, so confirm with the engineers who will perform it how milestone history will be preserved.

Limits to confirm in your environment before you build

Milestone behavior depends on the engine version, the database underneath it, the APIs you plan to query and how your case models change after go-live. Each card below names one limit to verify against the Flowable documentation and your own test results before you commit to a design.

Flowable version and baseline

Confirm the Flowable release line you will run and its platform baseline before you write milestone logic. Flowable 8.0.0 moved to Spring Framework 7 and Spring Boot 4, and the release notes state there is no backward compatibility for Spring Boot 3. If your application runs on Spring Boot 3, plan that upgrade as a separate step, and verify the milestone behavior you depend on against the version you actually deploy.

Database and timestamp precision

Milestone history records when a milestone occurred, so the timestamps you report on depend on the database you choose. The Flowable configuration docs list several supported database types. Note that MySQL versions below 5.6.4 lack millisecond precision, which can affect ordering of milestones that occur close together. Test your chosen database with two milestones fired in quick succession before you rely on their order in reports.

Milestone state in your APIs

Confirm that the milestone state you need is exposed through the interfaces your application will call, whether that is the Java API, the Spring Boot integration or the CMMN REST API. Do not assume a status field exists in every interface. Build a small query that lists completed milestones for a case instance using each interface you plan to use, and record which fields come back.

Case version changes over time

Running case instances stay on the definition version they started with unless you migrate them. If you rename a milestone, remove it or change the sentry that fires it, reports built on older instances can show different milestone names or missing events. Decide how you will version case models, map old milestones to new ones and test that a report still reads correctly across two versions before the first change ships.

Operational behavior under load

Confirm how milestone events and the jobs around them behave when several nodes run the engine. The Flowable advanced docs describe the async executor, which uses lock owners and lock expiration times stored in the database so that other nodes can recover expired locks. Test that milestone-driven sentries still fire once and only once when two nodes are active and one fails mid-task.

How DeployOpen scopes and delivers Flowable milestone work

DeployOpen plans, builds, documents and supports Flowable CMMN milestone designs inside your own infrastructure, starting from a written scope. Milestone naming, sentry wiring and status reporting are agreed with your case owners before any model is built.

How we scope

  • Inventory the case models and the business milestones your case owners recognize and need to report on.
  • Agree in writing which milestones trigger sentries, which feed status reporting, and which stay informational.
  • Confirm the Flowable engine version, database and deployment target, since these shape how milestone data is queried.
  • Engagements are fixed-scope, with deliverables and timelines agreed in writing before work starts.

How we build

  • Model milestones with names the business uses, and map each one to a single, clearly defined plan item.
  • Wire milestone occurrence into sentry if-parts and check that each trigger fires once under expected sequences.
  • Write unit tests for milestone-driven transitions and run them against the chosen Flowable engine version.
  • Build a status query over milestone history that your reporting team can read without engine internals.

How we hand over

  • Deliver the case model files, milestone naming register, sentry rules and test suite in your version control.
  • Document each milestone's meaning, entry conditions, expected history records and owner for the business team.
  • Walk your engineers through how milestones are reached, queried and changed when case definitions evolve.
  • Hand over runbooks for checking milestone reporting after a deployment or engine upgrade.

How we support

  • Review milestone naming and status reports when case definitions change or new business rules arrive.
  • Check milestone behavior again during Flowable version upgrades, since engine changes can affect history and sentries.
  • Ongoing support, upgrades and continuous testing are available as a retainer, scoped in writing.
  • Confirm recurring support needs with DeployOpen before work begins, since they are priced separately from the build.

Talk to our team.

Tell us what you're working on, whether it's a deployment, an audit, a security test or a cyber range. You'll speak with an engineer who can help you scope it.

  • 30-minute call: free, with no obligation.
  • NDA on request: we can sign before you share details.
  • Clear next steps: a scope and plan after the call.