diff --git a/opm/simulators/wells/BlackoilWellModelGasLift.hpp b/opm/simulators/wells/BlackoilWellModelGasLift.hpp index 13edca77d3..7276ced0a2 100644 --- a/opm/simulators/wells/BlackoilWellModelGasLift.hpp +++ b/opm/simulators/wells/BlackoilWellModelGasLift.hpp @@ -116,6 +116,8 @@ public: bool maybeDoGasLiftOptimize(const Simulator& simulator, const std::vector& well_container, + const std::map& node_pressures, + const bool updatePotentials, WellState& wellState, GroupState& groupState, DeferredLogger& deferred_logger); @@ -143,6 +145,12 @@ private: GLiftSyncGroups& groups_to_sync, DeferredLogger& deferred_logger); + void updateWellPotentials(const Simulator& simulator, + const std::vector& well_container, + const std::map& node_pressures, + WellState& wellState, + DeferredLogger& deferred_logger); + const PhaseUsage& phase_usage_; }; diff --git a/opm/simulators/wells/BlackoilWellModelGasLift_impl.hpp b/opm/simulators/wells/BlackoilWellModelGasLift_impl.hpp index 380c85af02..eb70361e01 100644 --- a/opm/simulators/wells/BlackoilWellModelGasLift_impl.hpp +++ b/opm/simulators/wells/BlackoilWellModelGasLift_impl.hpp @@ -29,6 +29,7 @@ #endif #include #include +#include #if HAVE_MPI #include @@ -41,6 +42,8 @@ bool BlackoilWellModelGasLift:: maybeDoGasLiftOptimize(const Simulator& simulator, const std::vector& well_container, + const std::map& node_pressures, + const bool updatePotentials, WellState& wellState, GroupState& groupState, DeferredLogger& deferred_logger) @@ -65,6 +68,11 @@ maybeDoGasLiftOptimize(const Simulator& simulator, this->last_glift_opt_time_ = simulation_time; } + // update potentials if changed by network (needed by the gaslift algorithm) + if (updatePotentials) { + updateWellPotentials(simulator, well_container, node_pressures, wellState, deferred_logger); + } + if (do_glift_optimization) { GLiftOptWells glift_wells; GLiftProdWells prod_wells; @@ -304,4 +312,48 @@ initGliftEclWellMap(const std::vector& well_container, } } +template +void +BlackoilWellModelGasLift:: +updateWellPotentials(const Simulator& simulator, + const std::vector& well_container, + const std::map& node_pressures, + WellState& wellState, + DeferredLogger& deferred_logger) +{ + auto well_state_copy = wellState; + const int np = wellState.numPhases(); + std::string exc_msg; + auto exc_type = ExceptionType::NONE; + for (const auto& well : well_container) { + if (well->isInjector() || !well->wellEcl().predictionMode()) + continue; + + const auto it = node_pressures.find(well->wellEcl().groupName()); + if (it != node_pressures.end()) { + std::vector potentials; + std::string cur_exc_msg; + auto cur_exc_type = ExceptionType::NONE; + try { + well->computeWellPotentials(simulator, well_state_copy, potentials, deferred_logger); + auto& ws = wellState.well(well->indexOfWell()); + for (int p = 0; p < np; ++p) { + // make sure the potentials are positive + ws.well_potentials[p] = std::max(Scalar{0.0}, potentials[p]); + } + } + // catch all possible exception and store type and message. + OPM_PARALLEL_CATCH_CLAUSE(cur_exc_type, cur_exc_msg); + if (cur_exc_type != ExceptionType::NONE) { + exc_msg += fmt::format("\nFor well {}: {}", well->name(), cur_exc_msg); + } + exc_type = std::max(exc_type, cur_exc_type); + } + } + if (exc_type != ExceptionType::NONE) { + const std::string msg = "Updating well potentials after network balancing failed. Continue with current potentials"; + deferred_logger.warning("WELL_POT_SOLVE_AFTER_NETWORK_FAILED", msg + exc_msg); + } +} + } // namespace Opm diff --git a/opm/simulators/wells/BlackoilWellModel_impl.hpp b/opm/simulators/wells/BlackoilWellModel_impl.hpp index 7a2142fd9b..8afcd90b0d 100644 --- a/opm/simulators/wells/BlackoilWellModel_impl.hpp +++ b/opm/simulators/wells/BlackoilWellModel_impl.hpp @@ -1269,12 +1269,18 @@ namespace Opm { bool alq_updated = false; OPM_BEGIN_PARALLEL_TRY_CATCH(); { - if (optimize_gas_lift) alq_updated = gaslift_.maybeDoGasLiftOptimize(simulator_, + if (optimize_gas_lift) { + // we need to update the potentials if the thp limit as been modified by + // the network balancing + const bool updatePotentials = (this->shouldBalanceNetwork(reportStepIdx, iterationIdx) || mandatory_network_balance); + alq_updated = gaslift_.maybeDoGasLiftOptimize(simulator_, well_container_, + this->node_pressures_, + updatePotentials, this->wellState(), this->groupState(), local_deferredLogger); - + } prepareWellsBeforeAssembling(dt, local_deferredLogger); } OPM_END_PARALLEL_TRY_CATCH_LOG(local_deferredLogger,