From 22f5015b6ea43109c5a1ef0798a9912b3c6d54a7 Mon Sep 17 00:00:00 2001 From: andr1976 Date: Fri, 20 Mar 2026 14:03:36 +0100 Subject: [PATCH 1/2] Adding user defined heat flux as input option --- src/hyddown/HydDown.code-workspace | 7 ++ .../__pycache__/hdclass.cpython-312.pyc | Bin 113083 -> 115129 bytes .../__pycache__/validator.cpython-312.pyc | Bin 13425 -> 14107 bytes src/hyddown/examples/LPG_specified_q.yml | 30 ++++++++ src/hyddown/hdclass.py | 70 +++++++++++++----- src/hyddown/validator.py | 69 ++++++++++++++++- 6 files changed, 158 insertions(+), 18 deletions(-) create mode 100644 src/hyddown/HydDown.code-workspace create mode 100644 src/hyddown/examples/LPG_specified_q.yml diff --git a/src/hyddown/HydDown.code-workspace b/src/hyddown/HydDown.code-workspace new file mode 100644 index 0000000..e4e7c68 --- /dev/null +++ b/src/hyddown/HydDown.code-workspace @@ -0,0 +1,7 @@ +{ + "folders": [ + { + "path": "../.." + } + ] +} \ No newline at end of file diff --git a/src/hyddown/__pycache__/hdclass.cpython-312.pyc b/src/hyddown/__pycache__/hdclass.cpython-312.pyc index c7154f43b33afc2311f4680348f44e087ca60edf..7b028842fc674840d315ab08875e7f838fe92ec8 100644 GIT binary patch delta 12711 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 gc2!An&G@~`gy1DXqVo&W#< delta 11312 zcmeHN33QZ2w(k4)l1@5FCveZ_w6$)9te;Y*8m6jmS ztNM$fN`dsI$q5Obx6GkRSnD~T)DJX^Cg4A6NVP(lXGrS%0A7!|rx%o^*1q&*YrV=V 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 diff --git a/src/hyddown/__pycache__/validator.cpython-312.pyc b/src/hyddown/__pycache__/validator.cpython-312.pyc index 49bef2a409ea78ff587e34976efdf8bec106f5f7..508341b8f83f2bbdbbbe25cc9bfbd66aad9c6180 100644 GIT binary patch delta 1707 zcmcgrZD?Cn7{2G;+&0NwVomLBk~O_a+GM#&wtl5`jBe8@t%#OY%jOsDvYxbwYt!|l z=^9&Uv0Bifh=(y@@e>61Q}d^Pgdsx;f+nI+;-BC@K_$`skj@{z@6Dtb5kbTQ_c`x* z&-3J*Jm-CD$!lr*=Qf*FfH6G$N$T?3AK8C1kz_%U&EmR5J=ByUfMSZwiZqZHX)tf0 zhw?I&s0d$(>X64MOd}9UwDXQ8nwJ_@he3TLZ$kF0KzrUNurGqH_wRJ;a5Vl*9|-$F z_z(2|oW1_n|M34_rNO{IoBQvsGLSdZ7tky zh3ry-=`z1<>$a7Z%*DiXY9^JSQ;S@)54BtunFR`_EXUKig&Ez#&)P#Go8)WuQSvOm zY2O@Kf^9YdpqmUT!wO>;5bnmTnJr?>5HbjJ2x)|Qgaw3)g;(#g6YEP5`{2v4!Urw) zh>GI0S33kxpsbzeHyvm6iZ@VkY419V&hReGYS9_0%2KCVlbbpmwMa+1z2-aYwpJ$# z!Pd7#-yb1cg)x8DtTni9cx||DyiAUN7tYo> zMsoih_a7z4mm}RI$FD^^X7EwaEo_6|h|IXqEyK(V_Ay#!4Djt_RF&U=++N|S=r=N4 zrMLe<62TT^m}cmyPK?*cfVBd6jcKER5Ps$F48+J5|9W7su0lawird!(wuK24?U{$? l7ie}aae}?cV==EMBNNBZbILiKMwC^FIDT1cZY52I~iV`oFXky~Y3snxrcyMQ%2=*c-Z1R4c&irS0W_EAK zvIEL1i^V9g2MWxVJU*J zKcmb0w;SKx41*m5i~t4zgMbKN2oTj?7AeSh znb|e$i=WXx7nh1Aqf=Qc7hK*|_i2i(UFNK6b0}H2x7@hasim!VL{q!mCEE+qo$I4U z>a(BNc}^09TLMPYC@EmEjO~SWoYIg_5Uz`)QoCv2g&Z9$EN=?CAWY8E*Nz8b>?@sd zzH!XuNxWP#L8Iku^kLaO+FFs)sgqyWtZei{#XB2;MtJijV2uNM=<~`&f0&tSA-M=1 zuDS%)7$5|O@0)r~%4(5&ta7ZKx!4yqZm6gsgGtLGh zRI^3W%vg2O4#{aISD3wkAS!FiRZ}8*tDUR~iABq1_j;cwSnSJob;VpqmjXUCtNrjK z^zOXkcuBlC-avw0txx1M+_};2M(qh&-QcO^T^(iTlf!^!KnvgqfHz?vNjlij7l8Un ziXjdU44U98*GchsZ*)A|!x+K6W08>;$*AO8w<#>K SpHqe@9V+>rEVQBmp7I;N+C^Ug diff --git a/src/hyddown/examples/LPG_specified_q.yml b/src/hyddown/examples/LPG_specified_q.yml new file mode 100644 index 0000000..3a586d5 --- /dev/null +++ b/src/hyddown/examples/LPG_specified_q.yml @@ -0,0 +1,30 @@ +vessel: + length: 4.64 + diameter: 1.7 + orientation: "horizontal" + heat_capacity: 500 + density: 7700 + thickness: 0.01185 + liquid_level: 0.4668 +initial: + temperature: 279 + pressure: 550000 + fluid: "propane" +calculation: + type: "energybalance" + time_step: 1 + end_time: 720. +valve: + flow: "discharge" + type: "psv" + diameter: 0.04 + discharge_coef: 0.975 + set_pressure: 1430000 + blowdown: 0.20 + back_pressure: 101300. +heat_transfer: + type: "specified_q" + h_inner: "calc" + q_outer: + time: [0.0, 10.0, 20.0, 30.0, 40.0, 50.0, 60.0, 70.0, 80.0, 90.0, 100.0, 110.0, 120.0, 130.0, 140.0, 150.0, 160.0, 170.0, 180.0, 190.0, 200.0, 210.0, 220.0, 230.0, 240.0, 250.0, 260.0, 270.0, 280.0, 290.0, 300.0, 310.0, 320.0, 330.0, 340.0, 350.0, 360.0, 370.0, 380.0, 390.0, 400.0, 410.0, 420.0, 430.0, 440.0, 450.0, 460.0, 470.0, 480.0, 490.0, 500.0, 510.0, 520.0, 530.0, 540.0, 550.0, 560.0, 570.0, 580.0, 590.0, 600.0, 610.0, 620.0, 630.0, 640.0, 650.0, 660.0, 670.0, 680.0, 690.0, 700.0, 710.0, 720.0] + heat_flux: [252.34, 3.43, 6.86, 10.29, 13.72, 417.35, 3171.05, 12488.77, 22795.66, 33102.74, 43448.06, 53721.33, 64020.08, 68626.41, 73069.31, 73570.21, 73847.06, 74417.00, 74927.83, 75194.43, 75618.54, 76055.93, 76463.23, 76864.81, 77259.94, 77695.54, 78169.01, 78484.32, 79016.89, 79549.52, 80082.12, 80614.72, 81197.03, 81752.35, 82349.76, 83005.97, 83712.95, 84350.98, 84989.33, 85627.91, 86266.67, 86970.51, 86777.99, 86144.24, 85510.49, 84925.77, 84329.11, 83798.73, 83212.07, 82560.15, 81998.49, 81405.55, 80937.47, 81351.16, 81910.74, 82362.27, 82668.13, 82959.11, 83198.99, 83401.45, 83075.37, 82536.11, 81948.55, 81460.60, 80966.35, 80534.18, 79998.41, 79364.66, 78730.91, 78245.89, 77264.09, 42895.00, 2057.16] diff --git a/src/hyddown/hdclass.py b/src/hyddown/hdclass.py index 9b866d4..3815e64 100644 --- a/src/hyddown/hdclass.py +++ b/src/hyddown/hdclass.py @@ -285,6 +285,33 @@ def read_input(self): self.thickness = self.input["vessel"]["thickness"] if self.input["valve"]["flow"] == "filling": raise ValueError("Filling and Fire heat load not implemented") + if self.heat_method == "specified_q": + self.vessel_cp = self.input["vessel"]["heat_capacity"] + self.vessel_density = self.input["vessel"]["density"] + self.vessel_orientation = self.input["vessel"]["orientation"] + self.thickness = self.input["vessel"]["thickness"] + # Handle q_outer: can be a number (fixed) or dict (time-dependent) + q_outer_input = self.input["heat_transfer"]["q_outer"] + if isinstance(q_outer_input, (int, float)): + # Fixed heat flux + self.q_outer_func = lambda t: q_outer_input + elif isinstance(q_outer_input, dict): + # Time-dependent heat flux from dict + time_data = np.array(q_outer_input["time"]) + heat_flux_data = np.array(q_outer_input["heat_flux"]) + self.q_outer_func = lambda t: np.interp(t, time_data, heat_flux_data) + else: + raise ValueError("q_outer must be a number or dict with time/heat_flux") + # Handle h_inner + if "h_inner" in self.input["heat_transfer"]: + self.h_in = self.input["heat_transfer"]["h_inner"] + else: + self.h_in = "calc" + if self.input["valve"]["flow"] == "filling": + if "D_throat" in self.input["heat_transfer"]: + self.D_throat = self.input["heat_transfer"]["D_throat"] + else: + self.D_throat = self.input["vessel"]["diameter"] def initialize(self): """ @@ -796,7 +823,7 @@ def run(self, disable_pbar=True): # HEAT TRANSFER COEFFICIENT CALCULATIONS # ==================================================================== # Calculate convective heat transfer coefficients for specified_h or detailed methods - if self.heat_method == "specified_h" or self.heat_method == "detailed": + if self.heat_method == "specified_h" or self.heat_method == "detailed" or self.heat_method == "specified_q": if self.h_in == "calc": if self.vessel_orientation == "horizontal": L = self.diameter @@ -922,24 +949,33 @@ def run(self, disable_pbar=True): # Heat transfer from environment to unwetted outer wall # Use outer surface area directly (outer surface is exposed to environment) - self.Q_outer[i] = ( - (self.surf_area_outer - wetted_area_outer) - * self.h_out - * (self.Tamb - self.T_outer_wall[i - 1]) - ) - self.q_outer[i] = self.h_out * ( - self.Tamb - self.T_outer_wall[i - 1] - ) + if self.heat_method == "specified_q": + # User-defined heat flux (time-dependent or constant) + q_ext = self.q_outer_func(self.time_array[i]) + self.Q_outer[i] = q_ext * (self.surf_area_outer - wetted_area_outer) + self.q_outer[i] = q_ext + self.Q_outer_wetted[i] = q_ext * wetted_area_outer + self.q_outer_wetted[i] = q_ext + else: + # specified_h or detailed: convective heat transfer + self.Q_outer[i] = ( + (self.surf_area_outer - wetted_area_outer) + * self.h_out + * (self.Tamb - self.T_outer_wall[i - 1]) + ) + self.q_outer[i] = self.h_out * ( + self.Tamb - self.T_outer_wall[i - 1] + ) - self.Q_outer_wetted[i] = ( - wetted_area_outer - * self.h_out - * (self.Tamb - self.T_outer_wall_wetted[i - 1]) - ) + self.Q_outer_wetted[i] = ( + wetted_area_outer + * self.h_out + * (self.Tamb - self.T_outer_wall_wetted[i - 1]) + ) - self.q_outer_wetted[i] = self.h_out * ( - self.Tamb - self.T_outer_wall_wetted[i - 1] - ) + self.q_outer_wetted[i] = self.h_out * ( + self.Tamb - self.T_outer_wall_wetted[i - 1] + ) if np.isnan(self.Q_outer_wetted[i]): self.Q_outer_wetted[i] = 0 diff --git a/src/hyddown/validator.py b/src/hyddown/validator.py index 0013f40..49fa007 100644 --- a/src/hyddown/validator.py +++ b/src/hyddown/validator.py @@ -185,11 +185,12 @@ def validate_mandatory_ruleset(input): "fire", "s-b", "D_throat", + "q_outer", ], "schema": { "type": { "type": "string", - "allowed": ["specified_Q", "specified_h", "specified_U", "s-b"], + "allowed": ["specified_Q", "specified_h", "specified_U", "s-b", "specified_q"], }, "Q_fix": {"required": False, "type": "number"}, "U_fix": {"required": False, "type": "number", "min": 0}, @@ -207,6 +208,13 @@ def validate_mandatory_ruleset(input): ], }, "D_throat": {"required": False, "type": "number", "min": 0}, + "q_outer": { + "required": False, + "anyof": [ + {"type": "number"}, + {"type": "dict"}, + ], + }, }, }, "validation": { @@ -684,6 +692,65 @@ def heat_transfer_validation(input): }, }, } + + elif input["heat_transfer"]["type"] == "specified_q": + schema_heattransfer = { + "initial": {"required": True}, + "calculation": {"required": True}, + "validation": {"required": False}, + "valve": {"required": True}, + "rupture": {"required": False}, + "vessel": { + "required": True, + "type": "dict", + "allow_unknown": False, + "schema": { + "length": {"required": True, "type": "number"}, + "diameter": {"required": True, "type": "number"}, + "thickness": {"required": True, "type": "number", "min": 0.0}, + "heat_capacity": {"required": True, "type": "number", "min": 1}, + "density": {"required": True, "type": "number", "min": 1}, + "orientation": { + "required": True, + "type": "string", + "allowed": ["vertical", "horizontal"], + }, + "type": { + "required": False, + "type": "string", + "allowed": ["Flat-end", "DIN", "ASME F&D", "Hemispherical"], + }, + "liquid_level": { + "required": False, + "type": "number", + "min": 0, + }, + }, + }, + "heat_transfer": { + "required": True, + "type": "dict", + "allow_unknown": False, + "allowed": ["type", "q_outer", "h_inner"], + "schema": { + "type": {"type": "string", "allowed": ["specified_q"]}, + "q_outer": { + "required": True, + "anyof": [ + {"type": "number"}, + { + "type": "dict", + "schema": { + "time": {"required": True, "type": "list"}, + "heat_flux": {"required": True, "type": "list"}, + }, + }, + ], + }, + "h_inner": {"required": False, "type": ["number", "string"]}, + }, + }, + } v = Validator(schema_heattransfer) retval = v.validate(input) if v.errors: From a601a537f8e1cedab356e5ddc00697e3bc53fac3 Mon Sep 17 00:00:00 2001 From: andr1976 Date: Wed, 25 Mar 2026 13:06:10 +0100 Subject: [PATCH 2/2] Adding LPG example --- .../__pycache__/hdclass.cpython-312.pyc | Bin 115129 -> 115129 bytes .../__pycache__/validator.cpython-312.pyc | Bin 14107 -> 14107 bytes src/hyddown/examples/LPG_Droste_1.yml | 29 ++++++++++++++++++ src/hyddown/examples/LPG_specified_q.yml | 16 ++++++---- 4 files changed, 39 insertions(+), 6 deletions(-) create mode 100644 src/hyddown/examples/LPG_Droste_1.yml diff --git a/src/hyddown/__pycache__/hdclass.cpython-312.pyc b/src/hyddown/__pycache__/hdclass.cpython-312.pyc index 7b028842fc674840d315ab08875e7f838fe92ec8..458c7cdf6fe41c3a2d6d91e97d3718ac5e1a6da5 100644 GIT binary patch delta 25 fcmdnl%)Yako%=K|FBbz4ux&fs$i0=Daos@xVfF{S delta 25 fcmdnl%)Yako%=K|FBbz4a9Zze