syntax = "proto3";
package pulse.cdm.bind;
option java_package = "com.kitware.pulse.cdm.bind";
option csharp_namespace = "pulse.cdm.bind";
option optimize_for = SPEED;

import "pulse/cdm/bind/Enums.proto";
import "pulse/cdm/bind/Events.proto";
import "pulse/cdm/bind/Actions.proto";
import "pulse/cdm/bind/Patient.proto";
import "pulse/cdm/bind/PatientActions.proto";
import "pulse/cdm/bind/PatientConditions.proto";
import "pulse/cdm/bind/EnvironmentActions.proto";
import "pulse/cdm/bind/EnvironmentConditions.proto";
import "pulse/cdm/bind/EquipmentActions.proto";
import "pulse/cdm/bind/Properties.proto";

message EngineInitializationStatusData
{
  eEngineInitializationState                           InitializationState              = 2;/**<<@brief Why was the engine unable to initialize. */
  string                                               CSVFilename                      = 3;/**<<@brief Optional csv file location. */
  string                                               LogFilename                      = 4;/**<<@brief Optional log file location. */
  double                                               StabilizationTime_s              = 5;/**<<@brief How long did stabilization take, 0 if a state was loaded. */
}

message EngineInitializationStatusListData
{
  repeated EngineInitializationStatusData              EngineInitializationStatus       = 1;
}

message DecimalFormatData
{
enum eType
{
  SystemFormatting  = 0;/*<<@brief Not provided, let the system do what it wants */
  DefaultFloat      = 1;
  FixedMantissa     = 2;
  SignificantDigits = 3;
}

  eType                                                Type                             = 1;
  uint32                                               Precision                        = 2;
}

message DataRequestData
{
  enum eCategory
  {
    Patient              = 0;
    Physiology           = 1;
    Environment          = 2;
    Action               = 3;
    GasCompartment       = 4;
    LiquidCompartment    = 5;
    ThermalCompartment   = 6;
    TissueCompartment    = 7;
    Substance            = 8;
    AnesthesiaMachine    = 9;
    BagValveMask         = 10;
    ECG                  = 11;
    ECMO                 = 12;
    Inhaler              = 13;
    MechanicalVentilator = 14;
  }

  DecimalFormatData                                     DecimalFormat                   = 1;/**<<@brief If writing to a file, specify the decimal formatting */
  eCategory                                             Category                        = 2;/**<<@brief A category assocated with the Name */
  string                                                ActionName                      = 3;/**<<@brief The action name the property is on */
  string                                                CompartmentName                 = 4;/**<<@brief The compartment name the property could be associated with */
  string                                                SubstanceName                   = 5;/**<<@brief The substance name the property could be associated with */
  string                                                PropertyName                    = 6;/**<<@brief The name of the property requested */
  string                                                Unit                            = 7;/**<<@brief If writing to a file, the unit the data will be in. */
}
message DataRequestManagerData
{
  string                                                ResultsFilename                 = 1;
  double                                                SamplesPerSecond                = 2;
  DecimalFormatData                                     DefaultDecimalFormatting        = 3;
  DecimalFormatData                                     OverrideDecimalFormatting       = 4;
  repeated DataRequestData                              DataRequest                     = 5;
}

message DataRequestListData
{
  repeated DataRequestData                              DataRequest                     = 1;
}

// Premilinary structure for passing data from an external engine to the requesting client
message DataRequestedData
{
  int32                                                 ID                              = 1;/**<< @brief A unique id associated with this engine, required when using pools. */
  bool                                                  IsActive                        = 2;
  repeated EventChangeData                              EventChange                     = 3;
  LogMessagesData                                       LogMessages                     = 4;

  message SegmentData
  {
    int32                                               ID                              = 1;
    double                                              SimTime_s                       = 2;
    repeated double                                     Value                           = 3;
  }


  repeated string                                       Headers                         = 5;
  repeated SegmentData                                  Segment                         = 6;
}
message DataRequestedListData
{
  repeated DataRequestedData                            DataRequested                   = 1;
}

message AnyConditionData
{
  oneof Condition
  {
    AnyPatientConditionData                             PatientCondition                = 1;
    AnyEnvironmentConditionData                         EnvironmentCondition            = 2;
  }
}
message ConditionListData
{
  repeated AnyConditionData                             AnyCondition                    = 1;
}

message AnyActionData
{
  oneof Action
  {
    AdvanceTimeData                                     AdvanceTime                     = 1;
    AdvanceUntilStableData                              AdvanceUntilStable              = 2;
    SerializeStateData                                  SerializeState                  = 3;
    SerializeRequestedData                              SerializeRequested              = 4;
    OverridesData                                       Overrides                       = 5;
    AnyPatientActionData                                PatientAction                   = 6;
    AnyEnvironmentActionData                            EnvironmentAction               = 7;
    AnyEquipmentActionData                              EquipmentAction                 = 8;
  }
}
message ActionListData
{
  repeated AnyActionData                                AnyAction                       = 1;
}

message ActionMapData
{
  map<int32, ActionListData>                            ActionMap                       = 1;
}

// message DataSetsData // This could hold all on disk data sets (Stabilization Criteria, Substances, Stabilization, Nutrition, Environments, ECG, patients, etc.)
// At this point I am fine with having to have files on disk to create a new patient configuration

message PatientConfigurationData
{
  string                                                DataRoot                        = 1;
  oneof PatientType
  {
    PatientData                                         Patient                         = 2;
    string                                              PatientFile                     = 3;
  }
  ConditionListData                                     Conditions                      = 4;
}

message EngineInitializationData
{
  int32                                                 ID                              = 1;/**<< @brief A unique id associated with this engine, required when using pools. */
  oneof StartType
  {
    PatientConfigurationData                            PatientConfiguration            = 2;/**<< @brief Create an engine using a patient configuration. */
    string                                              StateFilename                   = 3;/**<< @brief Create an engine using a patient state file. */
    string                                              State                           = 4;/**<< @brief Create an engine using a patient state.*/
  }
  DataRequestManagerData                                DataRequestManager              = 5;/**<< @brief Data Requests to use for this engine*/
  string                                                LogFilename                     = 6;/**<< @brief Log file to create for engine. */
  bool                                                  KeepLogMessages                 = 7;/**<< @brief Keep log messages from engine, used when building DataRequested objects. */
  bool                                                  KeepEventChanges                = 8;/**<< @brief Keep event changes from engine, used when building DataRequested objects. */
}

message EngineInitializationListData
{
  repeated EngineInitializationData                     EngineInitialization            = 1;/**<< @brief Create an engine for each provided configuration. */
}

/** @brief Static timed stabilization lengths */
message TimedStabilizationData
{
  map<string,ScalarTimeData>                            ConvergenceCriteria             = 1;/**<< @brief */
}

/** @brief A properties target percent difference allowed */
message DynamicStabilizationPropertyConvergenceData
{
  DataRequestData                                       DataRequest                     = 1;/**<< @brief */
  double                                                PercentDifference               = 2;/**<< @brief */
}
/** @brief A properties convergence timing */
message DynamicStabilizationEngineConvergenceData
{
  ScalarTimeData                                        ConvergenceTime                 = 1;/**<< @brief */
  ScalarTimeData                                        MinimumReactionTime             = 2;/**<< @brief */
  ScalarTimeData                                        MaximumAllowedStabilizationTime = 3;/**<< @brief */
  repeated DynamicStabilizationPropertyConvergenceData  PropertyConvergence             = 4;/**<< @brief */
}
/** @brief Dynamic stabilization parameters */
message DynamicStabilizationData
{
  map<string,DynamicStabilizationEngineConvergenceData> ConvergenceCriteria             = 1;/**<< @brief */
}

message LogMessagesData
{
  repeated string                                       DebugMessages                   = 1;
  repeated string                                       InfogMessages                   = 2;
  repeated string                                       WarningMessages                 = 3;
  repeated string                                       ErrorMessages                   = 4;
  repeated string                                       FatalMessages                   = 5;
}
