-
Notifications
You must be signed in to change notification settings - Fork 46
Description
Scope of simulation subsection:
Acidification of Calcium Lactate with H2SO4 to get L-Lactic Acid & Gypsum (Latter to be filtered off eventually). Acidification Reactor based on CSTR. Goal of the whole process simulation is correct energy and mass balance for an LCA at the end of the whole process simulation.
Issue:
Failed to evaluate liquid viscosity method 'NEGLECT_P' at T=298.15 K and P=101325.0 Pa for component with CASRN '10101-41-4' (Gypsum).
--> Complete Traceback at the end of post!
So, I don't understand what the NEGLECT_P Method actually does and why it fails. I think it is because Gypsum is a solid (and defined as such in my chemicals list). However, my fermentor also inherits from the CSTR unit and even though solid biomass is produced in that reactor, no issues were observed concerning viscosity.
I would be very thankful, if you could propose a solution, to avoid this issue, without having to neglect energy and mass balances (or having to manually calculate energy balance here).
Any tipps and insights are highly appreciated!
Code Section (incl. code irrelevant to the issue at hand, but necessary for _system.py to work)
_chemicals.py:
import thermosteam as tmo
import biosteam as bst
from thermosteam import Chemicals, Chemical
def create_chemicals():
chemicals = Chemicals([])
def add_chemical(ID, ref=None, **data):
chemical = Chemical(ID, **data) if ref is None else ref.copy(ID, **data)
chemicals.append(chemical)
return chemical
Water = add_chemical('H2O')
Glucose = add_chemical('Glucose', phase='l', rho=1560, Cp=1.213)
CaCO3 = add_chemical('CaCO3', phase='s', rho=2710, Cp=0.834, default=True)
CalciumLactate = add_chemical('CalciumLactate', phase='l', Hf=-1686100, rho=1494)
lla = add_chemical('L-LacticAcid', phase='l', Hf=-686300, Cp=2.109, rho=1206)
SulfuricAcid = add_chemical('H2SO4', phase='l', rho=1840, Cp=1.38)
CarbonDioxide = add_chemical('CO2', phase='g')
Gypsum = add_chemical('CaSO4_2H2O', phase='s', rho=2320, MW=172.18, Hf=-2023000, Cp=1.081, mu=1e10, CAS='10101-41-4', search_db=False)
Biomass_l = add_chemical('Biomass_l', phase='l', formula='CH1.8O0.5N0.2', MW=24.626, rho=1050, Hf=-106800, Cp=1.25, search_db=False)
Biomass_s = add_chemical('Biomass_s', phase='s', formula='CH1.8O0.5N0.2', MW=24.626, rho=1093, Hf=-106800, Cp=1.25, search_db=False)
EthylAcetate = add_chemical('EthylAcetate', phase='l', Hf=-479860, Cp=1.924)
Octanol = add_chemical('Octanol', phase='l', Hf=-426600, Cp=2.334)
chemicals.compile()
return chemicals
chemicals = create_chemicals()
_reactions.py:
import thermosteam as tmo
# Fermentor Unit Parallel Reactions
def fermentation_reactions():
fermentation = tmo.Reaction(reaction='Glucose -> 2 L-LacticAcid', reactant='Glucose', X=0.92, basis='mol')
BM_growth = tmo.Reaction(reaction='Glucose -> 10.97 Biomass_s', reactant='Glucose', X=0.08, basis='mol') # NOTE: Coefficient for biomass calculated from lit. yield and conversion eff.
return tmo.ParallelReaction([fermentation, BM_growth])
# Separate Neutralization for correct mass balance (has to happen when lla alreaedy formed)
def neutralization_reaction():
neutralization = tmo.Reaction(reaction='2 L-LacticAcid + CaCO3 -> CalciumLactate + CO2 + H2O', reactant='L-LacticAcid', X=1, basis='mol')
return neutralization
# Acidification Tank Unit
def acidification_reaction():
acidification = tmo.Reaction(reaction='CalciumLactate + H2SO4 -> 2 L-LacticAcid + CaSO4_2H2O', reactant='CalciumLactate', X=1, basis='mol')
return acidification
_settings.py:
import thermosteam as tmo
import biosteam as bst
from _chemicals import chemicals
from thermosteam import settings
tmo.settings.set_thermo(chemicals)
bst.settings.set_thermo(chemicals)
_units.py:
import biosteam as bst
import thermosteam as tmo
from biosteam import CSTR
import numpy as np
from _reactions import fermentation_reactions, neutralization_reaction, acidification_reaction
class Fermentor(bst.CSTR):
_N_ins = 1
_N_outs = 2
def __init__(self, ID='Fermentor', ins=None, outs=(), thermo=None, *, T=313.15, **kwargs):
if outs == ():
outs = [None, None] # liquid, gas
super().__init__(ID, ins, outs, thermo=thermo, **kwargs)
self.T=T
self.fermentation_rxns = fermentation_reactions()
self.neutralization_rxn = neutralization_reaction()
def _run(self):
feed = self.ins[0]
liquid_effluent, gas_vent = self.outs
liquid_effluent.copy_like(feed)
self.fermentation_rxns(liquid_effluent.mol)
self.neutralization_rxn(liquid_effluent.mol)
# Handle gas separation - remove CO2 from liquid and send to gas vent
gas_vent.copy_flow(liquid_effluent, 'CO2', remove=True)
liquid_effluent.phase = 'l'
gas_vent.phase = 'g'
liquid_effluent.T = gas_vent.T = self.T
# Custom Acidification Reactor
class AcidificationReactor(bst.CSTR):
_N_ins = 2
_N_outs = 1
def __init__(self, ID='', ins=None, outs=(), P=101325, T=298.15, tau=1):
super().__init__(ID, ins, outs)
self.P = P
self.T = T
self.tau = tau
self.acidification_rxn = acidification_reaction()
def _run(self):
feed, acid = self.ins
effluent = self.outs[0]
n_CL = feed.imol['CalciumLactate'] # looks for mols of CaLac in connected stream (flowsheet)
n_H2SO4 = n_CL * 1.1 # 10% excess acid wanted
acid.imol['H2SO4'] = n_H2SO4
acid.imass['H2O'] = acid.imass['H2SO4'] / 0.93 * 0.07 # acid stream composition
effluent.mix_from([feed, acid]) # mix feed & acid (no mixer)
effluent.T = self.T
effluent.P = self.P
self.acidification_rxn(effluent) # reaction applied
_system.py:
import biosteam as bst
from _units import Fermentor, AcidificationReactor # custom classes
from _reactions import fermentation_reactions, acidification_reaction # reaction functions
from _settings import chemicals # compiled thermo package
# -------------------- FEED STREAMS --------------------
glucose_feed = bst.Stream('glucose_feed', Glucose=80, Water=920, units='kg/hr')
CaCO3_feed = bst.Stream('CaCO3_feed', CaCO3=44.5, Water=82.6, units='kg/hr')
# -------------------- SUBSYSTEM 1: CONVERSION --------------------
# Unit and stream definitions
feedstock_mixer = bst.Mixer('feedstock_mixer', ins=[glucose_feed, CaCO3_feed])
feed_pump = bst.Pump('feed_pump', P=110000) # NOTE: Provisional Pump; missing correct settings
preheater = bst.HXutility('preheater', T=313.15) # NOTE: placeholder 40°C
fermentor = Fermentor('fermentor', P=110000, T=313.15, tau=24, V_wf=0.8)
ferm_cooler = bst.HXutility('fermentor_cooler', T=298.15)
# Connect the Conversion section
feed_pump.ins[0] = feedstock_mixer.outs[0]
preheater.ins[0] = feed_pump.outs[0]
fermentor.ins[0] = preheater.outs[0]
ferm_cooler.ins[0] = fermentor.outs[0] # Liquid to cooler
# Create the Conversion subsystem
conversion_sys = bst.System('conversion_sys', path=[feedstock_mixer, feed_pump, preheater, fermentor, ferm_cooler])
# -------------------- SUBSYSTEM 2.1: SEPARATION --------------------
# Biomass Removal --> NOTE: Fine tuning of splits, realism vs. idealism
gravity_decanter = bst.units.SolidsSeparator('GravityDecanter',
ins=ferm_cooler.outs[0], outs=('decanted_cake', 'decanted_broth'),
split={'Biomass_s': 1, 'CaCO3': 1, 'CalciumLactate': 0.15}, # NOTE: FINE TUNING, HOW MUCH PRODUCT LOST?
moisture_content=0.55)
bm_Filter = bst.units.SolidsSeparator('BM_Filter',
ins=gravity_decanter.outs[0], outs=('BM_cake', 'BM_filtrate'),
split={'Biomass_s': 1, 'CaCO3': 1},
moisture_content=0.15)
filtrate_mixer = bst.Mixer('filtrate_mixer', ins=(gravity_decanter.outs[1], bm_Filter.outs[1]), outs='clarified_broth')
# Acidification & Gypsum Filtration
acidification_reactor = AcidificationReactor('AcidificationReactor', ins=[filtrate_mixer.outs[0], 'H2SO4_feed'], outs=('acidified_slurry'))
# Create the Separation subsystem
Sep_BM_sys = bst.System('Sep_BM_sys', path=[gravity_decanter, bm_Filter, filtrate_mixer, acidification_reactor])
# -------------------- MAIN SYSTEM --------------------
lactic_acid_system = bst.System('lactic_acid_system',
path=[conversion_sys, Sep_BM_sys])
# SIMULATION
if __name__ == '__main__':
lactic_acid_system.simulate()
print("Simulation completed!")
TRACEBACK:
Traceback (most recent call last):
File "c:\Users\ivano\Desktop\Masterarbeit\Code_system.py", line 60, in
lactic_acid_system.simulate()
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam_system.py", line 3105, in simulate
with self.flowsheet:
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam_flowsheet.py", line 120, in exit
if exception: raise exception
^^^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam_system.py", line 3166, in simulate
raise error
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam_system.py", line 3154, in simulate
if design_and_cost: self._summary()
^^^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam_system.py", line 2862, in _summary
f(i, i._summary)
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam\exceptions.py", line 94, in try_method_with_object_stamp
raise_error_with_object_stamp(object, error)
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam\exceptions.py", line 84, in raise_error_with_object_stamp
raise error
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam\exceptions.py", line 88, in try_method_with_object_stamp
return method(*args)
^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam_system.py", line 2862, in _summary
f(i, i._summary)
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam\exceptions.py", line 94, in try_method_with_object_stamp
raise_error_with_object_stamp(object, error)
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam\exceptions.py", line 84, in raise_error_with_object_stamp
raise error
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam\exceptions.py", line 88, in try_method_with_object_stamp
return method(*args)
^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam_unit.py", line 1191, in _summary
self._design(**design_kwargs) if design_kwargs else self._design()
^^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam\units\stirred_tank_reactor.py", line 337, in _design
self.recirculation_pump.simulate()
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam_unit.py", line 1314, in simulate
self._summary(design_kwargs, cost_kwargs)
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam_unit.py", line 1191, in _summary
self._design(**design_kwargs) if design_kwargs else self._design()
^^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\biosteam\units_pump.py", line 175, in _design
nu = si.nu
^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam_stream.py", line 1450, in nu
mu = self.mu
^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam_stream.py", line 1415, in mu
return self._get_property('mu')
^^^^^^^^^^^^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam_stream.py", line 1351, in _get_property
property_cache[name] = value = calculate(
^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam\mixture\ideal_mixture_model.py", line 62, in call
return sum([j * models[i](phase, T, P) for i, j in mol.dct.items()])
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam\mixture\ideal_mixture_model.py", line 62, in
return sum([j * models[i](phase, T, P) for i, j in mol.dct.items()])
^^^^^^^^^^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam\base\phase_handle.py", line 131, in call
return self.model(T, P)
^^^^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermosteam\thermo\tp_dependent_property.py", line 44, in call
return self.TP_dependent_property(T, P)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "C:\Users\ivano\miniconda3\envs\glukose-env\Lib\site-packages\thermo\utils\tp_dependent_property.py", line 281, in TP_dependent_property
raise RuntimeError(f"Failed to evaluate {self.name.lower()} method '{method_P}' at T={T} K and P={P} Pa for component with CASRN '{self.CASRN}'")
RuntimeError: <System: Sep_BM_sys> <AcidificationReactor: AcidificationReactor> Failed to evaluate liquid viscosity method 'NEGLECT_P' at T=298.15 K and P=101325.0 Pa for component with CASRN '10101-41-4'