Functional analysis with activities
Functional analysis can be performed in a number of subtly different ways. In the previous recipe, we started with the sequence diagram to analyze the use case. That is particularly useful when the interesting parts of the use case are the interactions. The workflow in this recipe is slightly different, although it achieves exactly the same objectives. This workflow starts with the development of an activity model and generates scenarios from that. In this recipe, just as in the previous one, when the work is all complete, it is the state machine that forms the normative specification of the use case; the activity diagram is used as a stepping stone along the way. The objective of the workflow, as with the previous recipe, is to create an executable model to identify and fix defects in the requirements, such as missing requirements, or requirements that are incomplete, incorrect, or inaccurate. Overall, this is the most favored workflow among model-based systems engineers.
Purpose
The purpose of the recipe is to create a set of high-quality requirements by identifying and characterizing the key system functions performed by the system during the execution of the use case capability. This recipe is particularly effective when the main focus of the use case is a set of system functions and not the interaction of the system with the actors.
Inputs and preconditions
A use case naming a capability of the system from an actor-use point of view.
Outputs and postconditions
There are several outcomes, the most important of which is a set of requirements accurately and appropriately specifying the behavior of the system for the use case. Additional outputs include an executable use case model, logical system interfaces to support the use case behavior and a supporting logical data schema, and a set of scenarios that can be used later as specifications of test cases.
How to do it…
Figure 2.16 shows the workflow for this recipe. It is similar to the previous recipe. The primary difference is that rather than beginning the analysis by creating scenarios with the stakeholders, it begins by creating an activity model of the set of primary flows from which the scenarios will be derived:
Identify the use case
This first step is to identify the generic usage of which the scenarios of interest, user stories, and requirements are aspects.
Describe the use case
The description of the use case should include its purpose, general description of the flows, preconditions, postconditions, and invariants (assumptions). Some modelers add the specific actors involved, user stories, and scenarios, but I prefer to use the model itself to contain those relations.
Identify related actors
The related actors are those people or systems outside our scope that interact with the system while it executes the current use case. These actors can send messages to the system, receive messages from the system, or both.
Define the execution context
The execution context is a kind of modeling sandbox that contains an executable component consisting of executable elements representing the use case and related actors. The recommended way to achieve this is to create separate blocks representing the use case and the actors, connected via ports. Having an isolated simulation sandbox allows different systems engineers to progress independently on different use case analyses.
Identify primary functional flows
The activity model identifies the functional flows of the system while it executes the use case capability. These consist of a sequenced set of actions, connected by control flows, with control nodes (notably, decision, merge, fork, and join nodes) where appropriate. In this specific recipe step, the focus is on the primary flows of the system – also known as sunny day flows – and less on the secondary and fault scenarios (known as rainy day scenarios). The actions are either system functions, reception of messages from the actors, sending messages to the actors, or waiting for timeouts.
This activity model is not complete in the sense that it will not include all possible flows within the use case. The later Create executable state model recipe step will include all flows, which is why the state machine, rather than the activity model, is the normative specification of the use case. This activity model allows the systems engineer to begin reasoning about the necessary system behavior. Most systems engineers feel very comfortable with activity models and prefer to begin the analysis here rather than with the scenarios or with the state machine.
Derive use case scenarios
The activity model identifies multiple flows, as indicated by control nodes, such as decision nodes. A specific scenario takes a singular path through the activity flow so that a single activity model results in multiple scenarios. The scenarios are useful because they are easy to review with non-technical stakeholders and because they aid in the definition of the logical interfaces between the system and the actors.
Note
The activity diagram can be made complete, but it is usually easier to do that with a state machine. If you prefer to work entirely in the activity diagram, then evolve the activity model to be executable rather than develop a state machine for this purpose.
Create ports and interfaces in the execution context
Once we have a set of scenarios, we've identified the flow from the use case to the actors and from the actors to the system. By inference, this identifies ports relating the actors and the system, and the specific flows within the interfaces that define them.
Create an executable state model
This step identifies what I call the normative state machine. Executing this state machine can recreate each of the scenarios we drew in the Capture use case scenarios section. All states, transitions, and actions represent requirements. Any state elements added only to assist in the execution but that do not represent requirements should be stereotyped «non-normative» to clearly identify this fact. It is also common to create state behavior for the actors in a step known as instrumenting the actor to support the execution of the use case in the execution context.
Verify and validate requirements
Running the execution context for the use case allows us to demonstrate that our normative state machine in fact represents the flows identified by working with the stakeholder. It also allows us to identify flows and requirements that are missing, incomplete, or incorrect. These result in Requirements_change change requests to fix the identified requirements defects.
Requirements_change
Parallel to the development and execution of the use case model, we maintain the textual requirements. This workflow event indicates the need to fix an identified requirements defect.
Update requirement set
In response to an identified requirements defect, we fix the textual requirements by adding, deleting, or modifying requirements. This will then be reflected in the updated model.
Add trace links
Once the use case model and requirements stabilize, we add trace links using the «trace» relation or something similar. This generally means backtraces to stakeholder requirements as well as forward links to any architectural elements that might already exist.
Perform the use case and requirements review
Once the work has stabilized, a review for correctness and compliance with standards may be done. This allows subject matter experts and stakeholders to review the requirements, use case, activities, states, and scenarios for correctness and for quality assurance staff to ensure compliance with modeling and requirements standards.
Example
Let's see an example here.
The example used for this recipe is the Control Resistance use case, shown in Figure 2.17 along with some other use cases:
Describe the use case
All model elements deserve a useful description. In the case of a use case, we typically use the format shown in Figure 2.18:
Identify related actors
The related actors in this example are the Rider and the Training App. The rider signals the system to change the gearing via the gears control and receives a response in terms of changing resistance as well as setting resistance mode to ERG or SIM mode. The training app, when connected, is notified of the current gearing so that it can be displayed, provides a simulated input of incline, and can, optionally change between SIM and ERG modes. The relation of the actors to the use case is shown in Figure 2.17.
Define the execution context
The execution context creates blocks that represent the actors and the use case for the purpose of the analysis. In this example, the following naming conventions are observed:
- The block representing the use case is has the use case name (with white space removed) preceded by
Uc_
. Thus, for this example, the use case block is named Uc_ControlResistance. - Blocks representing the actors are given the actor name preceded with
a
and an abbreviation of the use case. For this use case, the prefix isaCR_
so the actor blocks are named aCR_Rider and aCR_TrainingApp. - The interface blocks are named as <use case block>_<actor block>. The names of the two interface blocks are iUc_ControlResistance_aCR_Rider and iUc_ControlResistance_aCR_TrainingApp. The normal form of the interface block is associated with the proxy port on the use case block; the conjugated form is associated with the corresponding proxy port on the actor block.
All these elements are shown on the IBD in Figure 2.19:
Identify the primary functional flow
This step creates an activity model for the primary flows in the use case. The flow consists of a set of steps sequenced by control flows and mediated by a set of control nodes. In this example, we will only consider SIM mode to keep the content short and easy to understand. In SIM mode, we simulate the outside riding experience by measuring the position, speed, and force applied to the pedal, and compute the (simulated) bike inertia, speed, acceleration, and drag. From that and the currently selected gear, the system computes and applies resistance to the pedal's movement. The high-level flow is shown in Figure 2.20:
Directly from the activity diagram, we can identify a number of requirements, shown in tabular form in Table 2.1:
Derive use case scenarios
The activity flow in Figure 2.20 can be used to create scenarios in sequence diagrams. It is typical to create a set of scenarios such that each control flow is shown at least once. This is called the minimal spanning set of scenarios. In this case, because of the nature of parallelism, a high-level scenario (Figure 2.21) is developed with the more detailed flows put on the reference scenarios:
The first reference scenario (Figure 2.22) reflects the inputs, gathered via system sensors, of the pedal status. This part of the overall scenario flow provides the necessary data for the computation of resistance:
The third scenario outlines the execution of the physics model per se. This scenario outlines how the simulated bike speed, acceleration, and drag are computed, and these outputs are then used to compute the resistance the system will apply to the pedal. It is important to note that this is not intended to provide a design but rather to identify and characterize the system functions that must be part of the design:
Create ports and interfaces in the execution context
Now that we have defined some interactions between the system and the actors, we can make the interfaces to support those message exchanges. This is shown in the IBD in Figure 2.24:
Create an executable state model
Figure 2.25 shows the state machine for the Control Resistance use case:
Astute readers will note that event parameters for sending between the actors and the use case have been added. For example, evSendFileteredPowerToApp now passes measuredPedalForce, of type Real, to the Training App.
To complete the execution, we need to create (simple) implementations for the system functions referenced in the state machine, and create simple state models for the actors to support the simulation. The details of the implementation are not provided here but are available in the downloadable model:
setPedalPosition()
setPedalSpeed()
computePedalCadence()
setMeasuredPedalForce()
applyTimeFilterToPower()
computeInertia()
retrieveCurrentIncline()
computeDrag()
computeSpeed()
computeAcceleration()
computeResistancecToApplyAtThePedal()
applyResistance()
storeIncline()
computeGearRatio()
storeGearRatio()
A few of these functions, while they must be elaborated in the actual design, can have empty implementations in the simulation:
sendPedalCadenceToApp()
sendFilteredPowerToApp()
sendSpeedToApp()
sendAccelerationToApp()
Also, to support simulation, the following value properties are defined:
gearFront
:int
– this is the number of teeth in the front (simulated) chainring.gearRear
:int
– this is the number of teeth in the rear (simulated) cassette ring.gearRatio
:Real
– this is the ratio gearFront/gearRear.incline
:int
– this is the simulated incline on the bike, from -15 to +20 degrees.measuredPedalForce
:Real
– this is the force on the pedals provided by the rider.pedalPosition
:Real
– this is the position, in degrees, of the pedal.pedalSpeed
:Real
– this is the angular speed of the pedal movement.cadence: int
– this is the pedal RPM (derived directly from pedal speed).
Lastly, we need to define the value properties APP_UPDATE_TM
and PHYSICS_UPDATE_TM
. In the real world these would run quickly, but we might slow them down for debugging and simulation on the desktop. Here, we'll set APP_UPDATE_TM
to 10,000 ms and PHYSICS_UPDATE_TM
to 5,000 ms.
We also need to instrument the actors for simulation support. A simple state behavioral model for the aCR_Rider is shown in Figure 2.26:
The state machine for the Training App is shown in Figure 2.27:
Verify and validate requirements
The simulation is not meant to be a high-fidelity physics simulation of all the forces and values involved, but instead aims to be a medium-fidelity simulation to help validate the set of requirements and to identify missing or incorrect ones. A control panel was created to visualize the behavior and input the values (Figure 2.28):
Simulation of difference scenarios results in many sequence diagrams capturing the behavior, such as the (partial) one shown in Figure 2.29:
Requirements_change
A number of minor requirements defects are identified and flagged to be added to the requirements set.
Update the requirements set
The creation and execution of the use case simulation uncovers a couple of new requirements related to timing:
- The system shall update the physics model frequently enough to provide the rider with a smooth and road-like experience with respect to resistance.
- The system shall update the training app with the pedal cadence at least every 1.0 seconds.
- The system shall update the training app with rider-filtered power output at least every 0.5 seconds.
- The system shall update the training app with the simulated bike speed at least every 1.0 seconds.
Also, we discover a missing data transmission to the training app:
- The system shall send the current power in watts per kilogram to the training app for the current power output at least every 1.0 seconds.
Add trace links
The trace links are updated in the model. This is shown in matrix form in the following screenshot:
Perform a use case and requirements review
The requirements model can now be reviewed by relevant stakeholders. The work products that should be included in the review include all the diagrams shown in this section, the requirements, and the executing model. The use of the executing model allows a what-if examination of the requirements set to be easily done during the review. Such questions as How quickly does the resistance control need to be updated to simulate the road riding experience? or What is the absolute maximum resistance supported to be allowed? can be asked. Simulation of the model allows the questions to either be answered by running the simulation case or can be identified as an item that requires resolution.