Python: Enforce checking on script name to make sure conversion between camelCase and snake_case works correctly

* #12044 Python: Add Non-Darcy properties available in Python

* #12049 Python: Add checking for multiple consecutive upper case letters
The scripting keyword is transformed to snake_case for use in Python. When data in Python is sent back to ResInsight, the opposite operation happens. This concept works well for most variants of keywords, but there are some corner cases that is not working.

Add compile time checking to make sure that the scripting keywords are formatted correctly.

Fix keyword that has been formatted the wrong way and has never worked.

* Avoid running test if ResInsight executable path is not defined in env
* Make sure dash is allowed in enumeration text string
This commit is contained in:
Magne Sjaastad 2025-01-10 18:25:46 +01:00
parent 453f1c2a29
commit 77145fc69f
9 changed files with 320 additions and 94 deletions

View File

@ -66,11 +66,16 @@ RicfExportWellPathCompletions::RicfExportWellPathCompletions()
CAF_PDM_InitScriptableField( &m_performTransScaling, "performTransScaling", false, "Perform Transmissibility Scaling" );
CAF_PDM_InitScriptableField( &m_transScalingTimeStep, "transScalingTimeStep", 0, "Transmissibility Scaling Pressure Time Step" );
CAF_PDM_InitScriptableField( &m_transScalingInitialWBHP,
"transScalingWBHPFromSummary",
RicExportCompletionDataSettingsUi::TransScalingWBHPSource(),
"Transmissibility Scaling WBHP from summary" );
CAF_PDM_InitScriptableField( &m_transScalingWBHP, "transScalingWBHP", 200.0, "Transmissibility Scaling Constant WBHP Value" );
CAF_PDM_InitScriptableFieldWithScriptKeyword( &m_transScalingInitialWBHP,
"transScalingWBHPFromSummary",
"transScalingWbhpFromSummary",
RicExportCompletionDataSettingsUi::TransScalingWBHPSource(),
"Transmissibility Scaling WBHP from summary" );
CAF_PDM_InitScriptableFieldWithScriptKeyword( &m_transScalingWBHP,
"transScalingWBHP",
"transScalingWbhp",
200.0,
"Transmissibility Scaling Constant WBHP Value" );
CAF_PDM_InitScriptableField( &m_exportDataSourceAsComments, "exportComments", true, "Export Data Source as Comments" );
CAF_PDM_InitScriptableField( &m_exportWelspec, "exportWelspec", true, "Export WELSPEC keyword" );

View File

@ -156,34 +156,37 @@ RimFractureTemplate::RimFractureTemplate()
m_fractureContainment.uiCapability()->setUiTreeChildrenHidden( true );
// Non-Darcy Flow options
CAF_PDM_InitFieldNoDefault( &m_nonDarcyFlowType, "NonDarcyFlowType", "Non-Darcy Flow" );
CAF_PDM_InitScriptableFieldNoDefault( &m_nonDarcyFlowType, "NonDarcyFlowType", "Non-Darcy Flow" );
CAF_PDM_InitField( &m_userDefinedDFactor, "UserDefinedDFactor", 1.0, "D Factor" );
CAF_PDM_InitScriptableField( &m_userDefinedDFactor, "UserDefinedDFactor", 1.0, "D Factor" );
CAF_PDM_InitFieldNoDefault( &m_fractureWidthType, "FractureWidthType", "Type" );
CAF_PDM_InitField( &m_fractureWidth, "FractureWidth", 0.01, "Fracture Width (h)" );
CAF_PDM_InitScriptableFieldNoDefault( &m_fractureWidthType, "FractureWidthType", "Type" );
CAF_PDM_InitScriptableField( &m_fractureWidth, "FractureWidth", 0.01, "Fracture Width (h)" );
CAF_PDM_InitFieldNoDefault( &m_betaFactorType, "BetaFactorType", "Type" );
CAF_PDM_InitField( &m_inertialCoefficient, "InertialCoefficient", 0.006083236, "<html>Inertial Coefficient (&beta;)</html> [Forch. unit]" );
CAF_PDM_InitScriptableFieldNoDefault( &m_betaFactorType, "BetaFactorType", "Type" );
CAF_PDM_InitScriptableField( &m_inertialCoefficient,
"InertialCoefficient",
0.006083236,
"<html>Inertial Coefficient (&beta;)</html> [Forch. unit]" );
CAF_PDM_InitFieldNoDefault( &m_permeabilityType, "PermeabilityType", "Type" );
CAF_PDM_InitField( &m_relativePermeability, "RelativePermeability", 1.0, "Relative Permeability" );
CAF_PDM_InitField( &m_userDefinedEffectivePermeability, "EffectivePermeability", 0.0, "Effective Permeability (Ke) [mD]" );
CAF_PDM_InitScriptableFieldNoDefault( &m_permeabilityType, "PermeabilityType", "Type" );
CAF_PDM_InitScriptableField( &m_relativePermeability, "RelativePermeability", 1.0, "Relative Permeability" );
CAF_PDM_InitScriptableField( &m_userDefinedEffectivePermeability, "EffectivePermeability", 0.0, "Effective Permeability (Ke) [mD]" );
CAF_PDM_InitField( &m_relativeGasDensity,
"RelativeGasDensity",
0.8,
"<html>Relative Gas Density (&gamma;)</html>",
"",
"Relative density of gas at surface conditions with respect to air at STP",
"" );
CAF_PDM_InitField( &m_gasViscosity,
"GasViscosity",
0.02,
"<html>Gas Viscosity (&mu;)</html> [cP]",
"",
"Gas viscosity at bottom hole pressure",
"" );
CAF_PDM_InitScriptableField( &m_relativeGasDensity,
"RelativeGasDensity",
0.8,
"<html>Relative Gas Density (&gamma;)</html>",
"",
"Relative density of gas at surface conditions with respect to air at STP",
"" );
CAF_PDM_InitScriptableField( &m_gasViscosity,
"GasViscosity",
0.02,
"<html>Gas Viscosity (&mu;)</html> [cP]",
"",
"Gas viscosity at bottom hole pressure",
"" );
CAF_PDM_InitFieldNoDefault( &m_dFactorDisplayField, "dFactorDisplayField", "D Factor" );
m_dFactorDisplayField.registerGetMethod( this, &RimFractureTemplate::dFactorForTemplate );

View File

@ -88,11 +88,19 @@ RimWellPathCompletionSettings::RimWellPathCompletionSettings()
CAF_PDM_InitScriptableFieldWithScriptKeyword( &m_groupName, "WellGroupNameForExport", "GroupNameForExport", QString(), "Group Name" );
CAF_PDM_InitScriptableField( &m_referenceDepth, "ReferenceDepthForExport", QString(), "Reference Depth for BHP" );
CAF_PDM_InitScriptableFieldNoDefault( &m_preferredFluidPhase, "WellTypeForExport", "Preferred Fluid Phase" );
CAF_PDM_InitScriptableField( &m_drainageRadiusForPI, "DrainageRadiusForPI", QString( "0.0" ), "Drainage Radius for PI" );
CAF_PDM_InitScriptableFieldWithScriptKeyword( &m_drainageRadiusForPI,
"DrainageRadiusForPI",
"DrainageRadiusForPi",
QString( "0.0" ),
"Drainage Radius for PI" );
CAF_PDM_InitScriptableFieldNoDefault( &m_gasInflowEquation, "GasInflowEq", "Gas Inflow Equation" );
CAF_PDM_InitScriptableFieldNoDefault( &m_automaticWellShutIn, "AutoWellShutIn", "Automatic well shut-in" );
CAF_PDM_InitScriptableField( &m_allowWellCrossFlow, "AllowWellCrossFlow", true, "Allow Well Cross-Flow" );
CAF_PDM_InitScriptableField( &m_wellBoreFluidPVTTable, "WellBoreFluidPVTTable", 0, "Wellbore Fluid PVT table" );
CAF_PDM_InitScriptableFieldWithScriptKeyword( &m_wellBoreFluidPVTTable,
"WellBoreFluidPVTTable",
"WellBoreFluidPvtTable",
0,
"Wellbore Fluid PVT table" );
CAF_PDM_InitScriptableFieldNoDefault( &m_hydrostaticDensity, "HydrostaticDensity", "Hydrostatic Density" );
CAF_PDM_InitScriptableField( &m_fluidInPlaceRegion, "FluidInPlaceRegion", 0, "Fluid In-Place Region" );

View File

@ -51,26 +51,49 @@ RimWbsParameters::RimWbsParameters()
"",
"Data source for Non-Reservoir Pore Pressure",
"" );
CAF_PDM_InitScriptableField( &m_userDefinedPPShale, "UserPPNonReservoir", 1.0, " Multiplier of hydrostatic PP" );
CAF_PDM_InitScriptableFieldWithScriptKeyword( &m_userDefinedPPShale,
"UserPPNonReservoir",
"UserPpNonReservoir",
1.0,
" Multiplier of hydrostatic PP" );
CAF_PDM_InitScriptableFieldNoDefault( &m_poissonRatioSource, "PoissionRatioSource", "Poisson Ratio", "", "Data source for Poisson Ratio", "" );
CAF_PDM_InitScriptableFieldNoDefault( &m_ucsSource, "UcsSource", "Uniaxial Compressive Strength", "", "Data source for UCS", "" );
CAF_PDM_InitScriptableFieldNoDefault( &m_OBG0Source, "OBG0Source", "Initial Overburden Gradient", "", "Data source for OBG0", "" );
CAF_PDM_InitScriptableFieldNoDefault( &m_DFSource, "DFSource", "Depletion Factor (DF)", "", "Data source for Depletion Factor", "" );
CAF_PDM_InitScriptableFieldWithScriptKeywordNoDefault( &m_OBG0Source,
"OBG0Source",
"ObgSource",
"Initial Overburden Gradient",
"",
"Data source for OBG0",
"" );
CAF_PDM_InitScriptableFieldWithScriptKeywordNoDefault( &m_DFSource,
"DFSource",
"DfSource",
"Depletion Factor (DF)",
"",
"Data source for Depletion Factor",
"" );
CAF_PDM_InitScriptableFieldNoDefault( &m_K0SHSource,
"K0SHSource",
"K0_SH",
"",
"SH from Matthews & Kelly = K0_SH * (OBG0-PP0) + PP0 + DF * "
"(PP-PP0)\nK0_SH = "
"(SH - PP)/(OBG-PP)",
"" );
CAF_PDM_InitScriptableFieldWithScriptKeywordNoDefault( &m_K0SHSource,
"K0SHSource",
"KshSource",
"K0_SH",
"",
"SH from Matthews & Kelly = K0_SH * (OBG0-PP0) + PP0 + DF * "
"(PP-PP0)\nK0_SH = "
"(SH - PP)/(OBG-PP)",
"" );
CAF_PDM_InitScriptableFieldNoDefault( &m_FGShaleSource, "FGShaleSource", "FG in Shale Calculation" );
CAF_PDM_InitScriptableFieldNoDefault( &m_K0FGSource, "K0FGSource", "K0_FG", "", "FG in shale = K0_FG * (OBG0-PP0)\nK0_FG = (FG-PP)/(OBG-PP)", "" );
CAF_PDM_InitScriptableFieldWithScriptKeywordNoDefault( &m_FGShaleSource, "FGShaleSource", "FgShaleSource", "FG in Shale Calculation" );
CAF_PDM_InitScriptableFieldWithScriptKeywordNoDefault( &m_K0FGSource,
"K0FGSource",
"KfgSource",
"K0_FG",
"",
"FG in shale = K0_FG * (OBG0-PP0)\nK0_FG = (FG-PP)/(OBG-PP)",
"" );
CAF_PDM_InitFieldNoDefault( &m_waterDensitySource, "WaterDensitySource", "Water Density" );
m_waterDensitySource.uiCapability()->setUiHidden( true );
@ -86,10 +109,17 @@ RimWbsParameters::RimWbsParameters()
// Typical UCS for Shale is 5 - 100 MPa -> 50 - 1000 bar.
CAF_PDM_InitScriptableField( &m_userDefinedUcs, "UserUcs", 100.0, "User Defined UCS [bar]", "", "User Defined UCS [bar]", "" );
CAF_PDM_InitScriptableField( &m_userDefinedDF, "UserDF", 0.7, "User Defined DF", "", "User Defined Depletion Factor", "" );
CAF_PDM_InitScriptableField( &m_userDefinedK0FG, "UserK0FG", 0.75, "User Defined K0_FG" );
CAF_PDM_InitScriptableField( &m_userDefinedK0SH, "UserK0SH", 0.65, "User Defined K0_SH" );
CAF_PDM_InitScriptableField( &m_FGShaleMultiplier, "FGMultiplier", 1.05, "SH Multiplier for FG in Shale", "", "FG in Shale = Multiplier * SH", "" );
CAF_PDM_InitScriptableFieldWithScriptKeyword( &m_userDefinedDF, "UserDF", "UserDf", 0.7, "User Defined DF", "", "User Defined Depletion Factor", "" );
CAF_PDM_InitScriptableFieldWithScriptKeyword( &m_userDefinedK0FG, "UserK0FG", "UserKfg", 0.75, "User Defined K0_FG" );
CAF_PDM_InitScriptableFieldWithScriptKeyword( &m_userDefinedK0SH, "UserK0SH", "UserKsh", 0.65, "User Defined K0_SH" );
CAF_PDM_InitScriptableFieldWithScriptKeyword( &m_FGShaleMultiplier,
"FGMultiplier",
"FgMultiplier",
1.05,
"SH Multiplier for FG in Shale",
"",
"FG in Shale = Multiplier * SH",
"" );
CAF_PDM_InitScriptableField( &m_userDefinedDensity, "WaterDensity", 1.03, "Density of Sea Water [g/cm^3]", "", "Units: g/cm^3", "" );

View File

@ -47,6 +47,75 @@
#include <QIODevice>
#include <QTextStream>
namespace
{
constexpr bool isUpper( char c )
{
return c >= 'A' && c <= 'Z';
}
constexpr bool isLower( char c )
{
return c >= 'a' && c <= 'z';
}
constexpr bool isNumber( char c )
{
return c >= '0' && c <= '9';
}
constexpr bool isCamelCase( std::string_view str )
{
if ( str.empty() ) return false;
bool hasLower = false;
int prevUpperCount = 0;
if ( isUpper( str[0] ) || isNumber( str[0] ) ) prevUpperCount++;
for ( size_t i = 1; i < str.size(); ++i )
{
if ( isUpper( str[i] ) || isNumber( str[i] ) )
{
if ( prevUpperCount >= 2 )
{
// Three consecutive uppercase letters/numbers
return false;
}
prevUpperCount++;
}
else if ( isLower( str[i] ) )
{
prevUpperCount = 0;
hasLower = true;
}
else
{
// Invalid character
return false;
}
}
if ( prevUpperCount > 1 )
{
// Two or more consecutive uppercase letters/numbers at the end
return false;
}
return hasLower;
}
} //namespace
// The scripting system converts from camel case to snake case by inserting an underscore before each uppercase letter.
// When an object is updated in Python, the keyword is converted back to camel case. This operation does not work if
// there are three or more consecutive uppercase letters.
// See PdmPythonGenerator::camelToSnakeCase()
// See snake_to_camel() and camel_to_snake() in pdmObject.py
// Conversion of values from rips object to caf object is done in RiaGrpcServiceInterface::copyPdmObjectFromRipsToCaf
#define CAF_PDM_CheckScriptableKeyword( keyword ) \
static_assert( isCamelCase( keyword ), "Keyword used for scripting must be in compatible formatted camel casing" );
#define CAF_PDM_InitScriptableField( field, keyword, default, uiName, ... ) \
{ \
std::vector<QString> arguments = { __VA_ARGS__ }; \
@ -64,6 +133,7 @@
iconResourceName, \
caf::PdmAbstractFieldScriptingCapability::helpString( toolTip, keyword ), \
whatsThis ); \
CAF_PDM_CheckScriptableKeyword( keyword ); \
caf::AddScriptingCapabilityToField( field, keyword ); \
}
@ -83,6 +153,7 @@
iconResourceName, \
caf::PdmAbstractFieldScriptingCapability::helpString( toolTip, keyword ), \
whatsThis ); \
CAF_PDM_CheckScriptableKeyword( keyword ); \
caf::AddScriptingCapabilityToField( field, keyword ); \
}
@ -103,6 +174,7 @@
iconResourceName, \
caf::PdmAbstractFieldScriptingCapability::helpString( toolTip, scriptKeyword ), \
whatsThis ); \
CAF_PDM_CheckScriptableKeyword( scriptKeyword ); \
caf::AddScriptingCapabilityToField( field, scriptKeyword ); \
}
@ -122,6 +194,7 @@
iconResourceName, \
caf::PdmAbstractFieldScriptingCapability::helpString( toolTip, scriptKeyword ), \
whatsThis ); \
CAF_PDM_CheckScriptableKeyword( scriptKeyword ); \
caf::AddScriptingCapabilityToField( field, scriptKeyword ); \
}
@ -196,7 +269,7 @@ struct PdmFieldScriptingCapabilityIOHandler<AppEnum<T>>
while ( !inputStream.atEnd() )
{
nextChar = errorMessageContainer->peekNextChar( inputStream );
if ( nextChar.isLetterOrNumber() || nextChar == QChar( '_' ) )
if ( nextChar.isLetterOrNumber() || nextChar == QChar( '_' ) || nextChar == QChar( '-' ) )
{
currentChar = errorMessageContainer->readCharWithLineNumberCount( inputStream );
accumulatedFieldValue += currentChar;

View File

@ -64,48 +64,3 @@ def test_add_well_path_targets(rips_instance, initialize_test):
assert target.use_fixed_azimuth == False
assert target.azimuth == 0.0
assert target.inclination == 25.6
def test_add_well_path_completions(rips_instance, initialize_test):
well_path_coll = rips_instance.project.descendants(rips.WellPathCollection)[0]
well_path = well_path_coll.add_new_object(rips.ModeledWellPath)
well_path.name = "test"
well_path.update()
# Update the completion settings
completions_settings = well_path.completion_settings()
completions_settings.msw_roughness = 12.34
completions_settings.msw_liner_diameter = 0.2123
completions_settings.well_name_for_export = "file name"
completions_settings.group_name_for_export = "msj"
completions_settings.well_type_for_export = "GAS"
completions_settings.update() # Commit updates back to ResInsight
completions_settings_updated = well_path.completion_settings()
assert completions_settings_updated.msw_roughness == 12.34
assert completions_settings_updated.msw_liner_diameter == 0.2123
assert completions_settings_updated.well_name_for_export == "file name"
assert completions_settings_updated.group_name_for_export == "msj"
assert completions_settings_updated.well_type_for_export == "GAS"
msw_settings = well_path.msw_settings()
msw_settings.custom_values_for_lateral = True
msw_settings.enforce_max_segment_length = True
msw_settings.liner_diameter = 20.0
msw_settings.max_segment_length = 123.05
msw_settings.pressure_drop = "HFA"
msw_settings.reference_md_type = "UserDefined"
msw_settings.roughness_factor = 1.3
msw_settings.user_defined_reference_md = 1234.56
msw_settings.update()
msw_settings_updated = well_path.msw_settings()
assert msw_settings_updated.custom_values_for_lateral == True
assert msw_settings_updated.enforce_max_segment_length == True
assert msw_settings_updated.liner_diameter == 20.0
assert msw_settings_updated.max_segment_length == 123.05
assert msw_settings_updated.pressure_drop == "HFA"
assert msw_settings_updated.reference_md_type == "UserDefined"
assert msw_settings_updated.roughness_factor == 1.3
assert msw_settings_updated.user_defined_reference_md == 1234.56

View File

@ -14,6 +14,10 @@ import dataroot
def launch_resinsight(sec=1):
resinsight_executable_from_env = os.environ.get("RESINSIGHT_EXECUTABLE")
if resinsight_executable_from_env is None:
print("RESINSIGHT_EXECUTABLE environment variable is not set")
return
instance = rips.Instance.launch(console=True, launch_port=0)
print(instance.location)
@ -25,6 +29,10 @@ def launch_resinsight(sec=1):
def test_launch_sequential(rips_instance, initialize_test):
resinsight_executable_from_env = os.environ.get("RESINSIGHT_EXECUTABLE")
if resinsight_executable_from_env is None:
print("RESINSIGHT_EXECUTABLE environment variable is not set")
return
instance_list = []
for i in range(4):
rips_instance = rips.Instance.launch(console=True)
@ -36,6 +44,11 @@ def test_launch_sequential(rips_instance, initialize_test):
def test_launch_parallell(rips_instance, initialize_test):
resinsight_executable_from_env = os.environ.get("RESINSIGHT_EXECUTABLE")
if resinsight_executable_from_env is None:
print("RESINSIGHT_EXECUTABLE environment variable is not set")
return
process_list = []
instance_count = 10

View File

@ -23,3 +23,121 @@ def test_10k(rips_instance, initialize_test):
well_path_names=["Well-1"],
file_split="UNIFIED_FILE",
)
def test_add_well_path_completions(rips_instance, initialize_test):
well_path_coll = rips_instance.project.descendants(rips.WellPathCollection)[0]
well_path = well_path_coll.add_new_object(rips.ModeledWellPath)
well_path.name = "test"
well_path.update()
# Update the completion settings
completions_settings = well_path.completion_settings()
completions_settings.allow_well_cross_flow = True
completions_settings.auto_well_shut_in = "STOP"
completions_settings.drainage_radius_for_pi = 1.56
completions_settings.fluid_in_place_region = 99
completions_settings.gas_inflow_eq = "R-G"
completions_settings.group_name_for_export = "TestGroup"
completions_settings.hydrostatic_density = "AVG"
completions_settings.msw_liner_diameter = 0.12
completions_settings.msw_roughness = 4.66
completions_settings.reference_depth_for_export = 1234
completions_settings.well_bore_fluid_pvt_table = 33
completions_settings.well_name_for_export = "TestWellName"
completions_settings.well_type_for_export = "LIQUID"
completions_settings.update() # Commit updates back to ResInsight
completions_settings_updated = well_path.completion_settings()
assert completions_settings_updated.allow_well_cross_flow == True
assert completions_settings_updated.auto_well_shut_in == "STOP"
assert completions_settings_updated.drainage_radius_for_pi == "1.56"
assert completions_settings_updated.fluid_in_place_region == 99
assert completions_settings_updated.gas_inflow_eq == "R-G"
assert completions_settings_updated.group_name_for_export == "TestGroup"
assert completions_settings_updated.hydrostatic_density == "AVG"
assert completions_settings_updated.msw_liner_diameter == 0.12
assert completions_settings_updated.msw_roughness == 4.66
assert completions_settings_updated.reference_depth_for_export == "1234"
assert completions_settings_updated.well_bore_fluid_pvt_table == 33
assert completions_settings_updated.well_name_for_export == "TestWellName"
assert completions_settings_updated.well_type_for_export == "LIQUID"
msw_settings = well_path.msw_settings()
msw_settings.custom_values_for_lateral = True
msw_settings.enforce_max_segment_length = True
msw_settings.liner_diameter = 20.0
msw_settings.max_segment_length = 123.05
msw_settings.pressure_drop = "HFA"
msw_settings.reference_md_type = "UserDefined"
msw_settings.roughness_factor = 1.3
msw_settings.user_defined_reference_md = 1234.56
msw_settings.update()
msw_settings_updated = well_path.msw_settings()
assert msw_settings_updated.custom_values_for_lateral == True
assert msw_settings_updated.enforce_max_segment_length == True
assert msw_settings_updated.liner_diameter == 20.0
assert msw_settings_updated.max_segment_length == 123.05
assert msw_settings_updated.pressure_drop == "HFA"
assert msw_settings_updated.reference_md_type == "UserDefined"
assert msw_settings_updated.roughness_factor == 1.3
assert msw_settings_updated.user_defined_reference_md == 1234.56
def test_add_well_path_fracture_template(rips_instance, initialize_test):
# Add test for all properties
# Some properties depend on availablility of other data and is not tested, these tests are commented out
fracture_template = rips_instance.project.descendants(rips.FractureTemplate)[0]
fracture_template.azimuth_angle = 23.0
# fracture_template.beta_factor_type = "FractureBetaFactor"
fracture_template.conductivity_factor = 12.5
fracture_template.conductivity_type = "FiniteConductivity"
fracture_template.d_factor_scale_factor = 1.2
fracture_template.effective_permeability = 55
fracture_template.fracture_width = 0.5
fracture_template.fracture_width_type = "UserDefinedWidth"
fracture_template.gas_viscosity = 0.1
fracture_template.height_scale_factor = 1.2
fracture_template.height_scale_factor = 4
fracture_template.inertial_coefficient = 0.7
fracture_template.non_darcy_flow_type = "Computed"
fracture_template.orientation = "Azimuth"
fracture_template.perforation_length = 5
fracture_template.permeability_type = "UserDefinedPermeability"
fracture_template.relative_gas_density = 0.1
fracture_template.relative_permeability = 0.2
fracture_template.user_defined_d_factor = 14
fracture_template.user_defined_perforation_length = True
fracture_template.user_description = "my frac name"
fracture_template.width_scale_factor = 7
fracture_template.update()
fracture_template_updated = rips_instance.project.descendants(
rips.FractureTemplate
)[0]
assert fracture_template_updated.azimuth_angle == 23.0
# assert fracture_template_updated.beta_factor_type == "FractureBetaFactor"
assert fracture_template_updated.conductivity_factor == 12.5
assert fracture_template_updated.conductivity_type == "FiniteConductivity"
assert fracture_template_updated.d_factor_scale_factor == 1.2
assert fracture_template_updated.effective_permeability == 55
assert fracture_template_updated.fracture_width == 0.5
assert fracture_template_updated.fracture_width_type == "UserDefinedWidth"
assert fracture_template_updated.gas_viscosity == 0.1
assert fracture_template_updated.height_scale_factor == 4
assert fracture_template_updated.inertial_coefficient == 0.7
assert fracture_template_updated.non_darcy_flow_type == "Computed"
assert fracture_template_updated.orientation == "Azimuth"
assert fracture_template_updated.perforation_length == 5
assert fracture_template_updated.permeability_type == "UserDefinedPermeability"
assert fracture_template_updated.relative_gas_density == 0.1
assert fracture_template_updated.relative_permeability == 0.2
assert fracture_template_updated.user_defined_d_factor == 14
assert fracture_template_updated.user_defined_perforation_length == True
assert fracture_template_updated.user_description == "my frac name"
assert fracture_template_updated.width_scale_factor == 7

View File

@ -134,7 +134,28 @@ void RiaGrpcServiceInterface::copyPdmObjectFromRipsToCaf( const rips::PdmObject*
auto parametersMap = source->parameters();
bool printContent = false; // Flag to control debug output to debugger
// Check for duplicate lowercase keywords. If this happens, the script checking in CAF_PDM_CheckScriptableKeyword in
// cafPdmFieldScriptingCapability.h is not working as expected
{
std::set<QString> uniqueNames;
for ( const auto& p : parametersMap )
{
auto lowerCase = QString::fromStdString( p.first ).toLower();
if ( uniqueNames.count( lowerCase ) > 0 )
{
QString txt = "When receiving an object from Python, multiple key/values for a field keyword was "
"detected. This is an error will most likely fail to update the object as intende. "
"Keyword name : " +
QString::fromStdString( p.first );
RiaLogging::error( txt );
}
uniqueNames.insert( lowerCase );
}
}
bool printContent = false; // Flag to control debug output to debugger. Do not remove this code, as it is useful for
// debugging
if ( printContent )
{
for ( const auto& p : parametersMap )