94class BlackoilWellModelGeneric
98 BlackoilWellModelGeneric(Schedule& schedule,
100 const SummaryState& summaryState,
101 const EclipseState& eclState,
103 const Parallel::Communication& comm);
105 virtual ~BlackoilWellModelGeneric() =
default;
106 virtual int compressedIndexForInteriorLGR([[maybe_unused]]
const std::string& lgr_tag,
107 [[maybe_unused]]
const Connection& conn)
const
109 throw std::runtime_error(
"compressedIndexForInteriorLGR not implemented");
112 int numLocalWells()
const;
113 int numLocalWellsEnd()
const;
114 int numLocalNonshutWells()
const;
115 int numPhases()
const;
130 bool anyMSWellOpenLocal()
const;
132 const std::vector<Well>& eclWells()
const
133 {
return wells_ecl_; }
135 bool terminalOutput()
const
136 {
return terminal_output_; }
138 const Well& getWellEcl(
const std::string& well_name)
const;
139 std::vector<Well> getLocalWells(
const int timeStepIdx)
const;
140 const Schedule& schedule()
const {
return schedule_; }
142 const GroupState<Scalar>& groupState()
const {
return this->active_wgstate_.group_state; }
143 std::vector<const WellInterfaceGeneric<Scalar, IndexTraits>*> genericWells()
const
144 {
return {well_container_generic_.begin(), well_container_generic_.end()}; }
146 std::vector<WellInterfaceGeneric<Scalar, IndexTraits>*> genericWells()
147 {
return well_container_generic_; }
154 return this->active_wgstate_.well_state;
162 return this->active_wgstate_.well_state;
171 return this->nupcol_wgstate_.well_state;
175 WellTestState& wellTestState() {
return this->active_wgstate_.well_test_state; }
177 const WellTestState& wellTestState()
const {
return this->active_wgstate_.well_test_state; }
179 Scalar wellPI(
const int well_index)
const;
180 Scalar wellPI(
const std::string& well_name)
const;
182 void updateEclWells(
const int timeStepIdx,
183 const SimulatorUpdate& sim_update,
184 const SummaryState& st);
186 void initFromRestartFile(
const RestartValue& restartValues,
187 std::unique_ptr<WellTestState> wtestState,
188 const std::size_t numCells,
190 bool enable_distributed_wells);
192 void prepareDeserialize(
int report_step,
193 const std::size_t numCells,
195 bool enable_distributed_wells);
205 this->last_valid_wgstate_ = this->active_wgstate_;
206 this->last_valid_node_pressures_ = this->node_pressures_;
209 data::GroupAndNetworkValues groupAndNetworkData(
const int reportStepIdx)
const;
222 const double simulation_time,
223 const bool dont_shut_grup_wells);
225 const std::vector<PerforationData<Scalar>>& perfData(
const int well_idx)
const
226 {
return well_perf_data_[well_idx]; }
228 const Parallel::Communication& comm()
const {
return comm_; }
230 const EclipseState& eclipseState()
const {
return eclState_; }
232 const SummaryState& summaryState()
const {
return summaryState_; }
234 const GuideRate& guideRate()
const {
return guideRate_; }
235 GuideRate& guideRate() {
return guideRate_; }
237 const std::map<std::string, double>& wellOpenTimes()
const {
return well_open_times_; }
238 const std::map<std::string, double>& wellCloseTimes()
const {
return well_close_times_; }
241 std::vector<int> getCellsForConnections(
const Well& well)
const;
243 bool reportStepStarts()
const {
return report_step_starts_; }
245 bool shouldBalanceNetwork(
const int reportStepIndex,
246 const int iterationIdx)
const;
248 void updateClosedWellsThisStep(
const std::string& well_name)
const
250 this->closed_this_step_.insert(well_name);
252 bool wasDynamicallyShutThisTimeStep(
const std::string& well_name)
const;
254 void logPrimaryVars()
const;
256 template<
class Serializer>
257 void serializeOp(Serializer& serializer)
259 serializer(initial_step_);
260 serializer(report_step_starts_);
261 serializer(last_run_wellpi_);
262 serializer(local_shut_wells_);
263 serializer(closed_this_step_);
264 serializer(guideRate_);
265 serializer(node_pressures_);
266 serializer(last_valid_node_pressures_);
267 serializer(prev_inj_multipliers_);
268 serializer(active_wgstate_);
269 serializer(last_valid_wgstate_);
270 serializer(nupcol_wgstate_);
271 serializer(switched_prod_groups_);
272 serializer(switched_inj_groups_);
273 serializer(closed_offending_wells_);
274 serializer(gen_gaslift_);
277 bool operator==(
const BlackoilWellModelGeneric& rhs)
const;
280 parallelWellInfo(
const std::size_t idx)
const
281 {
return local_parallel_well_info_[idx].get(); }
283 bool isOwner(
const std::string& wname)
const
285 return this->parallelWellSatisfies
286 (wname, [](
const auto& pwInfo) {
return pwInfo.isOwner(); });
289 bool hasLocalCells(
const std::string& wname)
const
291 return this->parallelWellSatisfies
292 (wname, [](
const auto& pwInfo) {
return pwInfo.hasLocalCells(); });
296 {
return conn_idx_map_[idx]; }
328 return this->last_valid_wgstate_.well_state;
333 return this->last_valid_wgstate_;
343 this->last_valid_wgstate_ = std::move(wgstate);
353 this->active_wgstate_ = this->last_valid_wgstate_;
354 this->node_pressures_ = this->last_valid_node_pressures_;
362 void updateNupcolWGState()
364 this->nupcol_wgstate_ = this->active_wgstate_;
367 void reportGroupSwitching(
DeferredLogger& local_deferredLogger)
const;
371 std::vector<std::reference_wrapper<ParallelWellInfo<Scalar>>>
374 void initializeWellProdIndCalculators();
375 void initializeWellPerfData();
377 bool wasDynamicallyShutThisTimeStep(
const int well_index)
const;
379 Scalar updateNetworkPressures(
const int reportStepIdx,
380 const Scalar damping_factor,
381 const Scalar update_upper_bound);
383 void updateWsolvent(
const Group& group,
384 const int reportStepIdx,
386 void setWsolvent(
const Group& group,
387 const int reportStepIdx,
389 virtual void calcResvCoeff(
const int fipnum,
391 const std::vector<Scalar>& production_rates,
392 std::vector<Scalar>& resv_coeff) = 0;
393 virtual void calcInjResvCoeff(
const int fipnum,
395 std::vector<Scalar>& resv_coeff) = 0;
415 const int reportStepIndex)
const;
417 void assignWellTargets(data::Wells& wsrpt)
const;
418 void assignProductionWellTargets(
const Well& well, data::WellControlLimits& limits)
const;
419 void assignInjectionWellTargets(
const Well& well, data::WellControlLimits& limits)
const;
421 void assignGroupControl(
const Group& group,
422 data::GroupData& gdata)
const;
423 void assignGroupValues(
const int reportStepIdx,
424 std::map<std::string, data::GroupData>& gvalues)
const;
425 void assignNodeValues(std::map<std::string, data::NodeData>& nodevalues,
426 const int reportStepIdx)
const;
428 void calculateEfficiencyFactors(
const int reportStepIdx);
430 void checkGconsaleLimits(
const Group& group,
432 const int reportStepIdx,
435 void checkGEconLimits(
const Group& group,
436 const double simulation_time,
437 const int report_step_idx,
440 bool checkGroupHigherConstraints(
const Group& group,
442 const int reportStepIdx,
443 const int max_number_of_group_switch,
444 const bool update_group_switching_log);
446 void updateAndCommunicateGroupData(
const int reportStepIdx,
447 const int iterationIdx,
448 const Scalar tol_nupcol,
449 const bool update_wellgrouptarget,
452 void inferLocalShutWells();
454 void setRepRadiusPerfLength();
456 virtual void computePotentials(
const std::size_t widx,
458 std::string& exc_msg,
459 ExceptionType::ExcEnum& exc_type,
463 void updateWellPotentials(
const int reportStepIdx,
464 const bool onlyAfterEvent,
465 const SummaryConfig& summaryConfig,
473 void updateFiltrationModelsPostStep(
const double dt,
474 const std::size_t water_index,
477 void updateFiltrationModelsPreStep(
DeferredLogger& deferred_logger);
480 virtual void createWellContainer(
const int time_step) = 0;
481 virtual void initWellContainer(
const int reportStepIdx) = 0;
483 virtual void calculateProductivityIndexValuesShutWells(
const int reportStepIdx,
485 virtual void calculateProductivityIndexValues(
DeferredLogger& deferred_logger) = 0;
487 void runWellPIScaling(
const int reportStepIdx,
493 std::vector<std::vector<int>> getMaxWellConnections()
const;
495 std::vector<std::string> getWellsForTesting(
const int timeStepIdx,
496 const double simulationTime);
498 using WellTracerRates = std::unordered_map<int, std::vector<WellTracerRate<Scalar>>>;
499 void assignWellTracerRates(data::Wells& wsrpt,
500 const WellTracerRates& wellTracerRates,
501 const unsigned reportStep)
const;
503 using MswTracerRates = std::unordered_map<int, std::vector<MSWellTracerRate<Scalar>>>;
504 void assignMswTracerRates(data::Wells& wsrpt,
505 const MswTracerRates& mswTracerRates,
506 const unsigned reportStep)
const;
508 void assignMassGasRate(data::Wells& wsrpt,
509 const Scalar gasDensity)
const;
513 const SummaryState& summaryState_;
514 const EclipseState& eclState_;
515 const Parallel::Communication& comm_;
521 bool terminal_output_{
false};
522 bool wells_active_{
false};
523 bool network_active_{
false};
524 bool initial_step_{};
525 bool report_step_starts_{};
527 std::optional<int> last_run_wellpi_{};
529 std::vector<Well> wells_ecl_;
530 std::vector<std::vector<PerforationData<Scalar>>> well_perf_data_;
533 std::map<std::string, double> well_open_times_;
536 std::map<std::string, double> well_close_times_;
538 std::vector<ConnectionIndexMap> conn_idx_map_{};
539 std::function<bool(
const std::string&)> not_on_process_{};
542 std::vector<WellInterfaceGeneric<Scalar, IndexTraits>*> well_container_generic_{};
544 std::vector<int> local_shut_wells_{};
546 std::vector<ParallelWellInfo<Scalar>> parallel_well_info_;
547 std::vector<std::reference_wrapper<ParallelWellInfo<Scalar>>> local_parallel_well_info_;
549 std::vector<WellProdIndexCalculator<Scalar>> prod_index_calc_;
551 std::vector<int> pvt_region_idx_;
553 mutable std::unordered_set<std::string> closed_this_step_;
555 GuideRate guideRate_;
556 std::unique_ptr<VFPProperties<Scalar, IndexTraits>> vfp_properties_{};
559 std::map<std::string, Scalar> node_pressures_;
561 std::map<std::string, Scalar> last_valid_node_pressures_;
564 std::unordered_map<std::string, std::vector<Scalar>> prev_inj_multipliers_;
567 std::unordered_map<std::string, WellFilterCake<Scalar, IndexTraits>> filter_cake_;
575 WGState<Scalar, IndexTraits> active_wgstate_;
576 WGState<Scalar, IndexTraits> last_valid_wgstate_;
577 WGState<Scalar, IndexTraits> nupcol_wgstate_;
580 bool wellStructureChangedDynamically_{
false};
583 std::map<std::string, std::vector<Group::ProductionCMode>> switched_prod_groups_;
584 std::map<std::string, std::array<std::vector<Group::InjectionCMode>, 3>> switched_inj_groups_;
586 std::map<std::string, std::pair<std::string, std::string>> closed_offending_wells_;
591 template <
typename Iter,
typename Body>
592 void wellUpdateLoop(Iter first, Iter last,
const int timeStepIdx, Body&& body);
594 void updateEclWellsConstraints(
const int timeStepIdx,
595 const SimulatorUpdate& sim_update,
596 const SummaryState& st);
598 void updateEclWellsCTFFromAction(
const int timeStepIdx,
599 const SimulatorUpdate& sim_update);
614 template <
typename Predicate>
615 bool parallelWellSatisfies(
const std::string& wname, Predicate&& p)
const
617 auto pwInfoPos = std::find_if(this->parallel_well_info_.begin(),
618 this->parallel_well_info_.end(),
619 [&wname](
const auto& pwInfo)
620 { return pwInfo.name() == wname; });
622 return (pwInfoPos != this->parallel_well_info_.end())
641 template <
typename LoopBody>
642 void loopOwnedWells(LoopBody&& loopBody)
const;