PyResToolbox - A collection of Reservoir Engineering Utilities

Overview

pyrestoolbox

A collection of Reservoir Engineering Utilities

This set of functions focuses on those that the author uses often while crafting programming solutions. These are the scripts that are often copy/pasted from previous work - sometimes slightly modified - resulting in a trail of slightly different versions over the years. Some attempt has been made here to make this implementation flexible enough such that it can be relied on as-is going forward.

Includes functions to perform simple calculations including;

  • Inflow for oil and gas
  • PVT Calculations for oil
  • PVT calculation for gas
  • Creation of Black Oil Table information
  • Creation of layered permeability distribution consistent with a Lorenze heterogeneity factor
  • Extract problem cells information from Intesect (IX) print files
  • Generation of AQUTAB include file influence functions for use in ECLIPSE
  • Creation of Corey and LET relative permeability tables in Eclipse format

This is the initial public release, with improvements and additions expected over time. Apologies in advance that it is only in oilfield units with no current plans to add multi-unit support.

Function List

Inflow
  • Gas Flow Rate Radial
  • Gas Flow Rate Linear
  • Oil Flow Rate Radial
  • Oil Flow Rate Linear
Gas PVT
  • Gas Tc & Pc Calculation
  • Gas Z-Factor Calculation
  • Gas Viscosity
  • Gas Viscosity * Z
  • Gas Compressibility
  • Gas Formation Volume Factor
  • Gas Density
  • Gas Water of Condensation
  • Convert P/Z to P
  • Convert Gas Gradient to SG
  • Delta Pseudopressure
  • Gas Condensate FWS SG
Oil PVT
  • Oil Density from MW
  • Oil Critical Properties with Twu
  • Incrememtal GOR post Separation
  • Oil Bubble Point Pressure
  • Oil GOR at Pb
  • Oil GOR at P
  • Oil Compressibility
  • Oil Density
  • Oil Formation Volume Factor
  • Oil Viscosity
  • Generate Black Oil Table data
  • Estimate soln gas SG from oil
  • Estimate SG of gas post separator
  • Calculate weighted average surface gas SG
Brine PVT
  • Calculate suite of brine properties
Permeability Layering
  • Lorenz coefficient from Beta value
  • Lorenz coefficient from flow fraction
  • Lorenz coefficient to flow fraction
  • Lorenz coefficient to permeability array
Simulation Helpers
  • Summarize IX convergence errors from PRT file
  • Create Aquifer Influence Functions
Relative Permeability
  • Create sets of rel perm tables

Getting Started

Install the library with pip:

pip install pyrestoolbox

Import library into your project and start using.

A simple example below of estimating oil bubble point pressure.

>>> from pyrestoolbox import pyrestoolbox as rtb
>>> rtb.oil_pbub(api=43, degf=185, rsb=2350, sg_g =0.72, pbmethod ='VALMC')
5179.51086900132

A set of Gas-Oil relative permeability curves with the LET method

>>> import matplotlib.pyplot as plt
>>> df = rtb.rel_perm(rows=25, krtable='SGOF', krfamily='LET', kromax =1, krgmax =1, swc =0.2, sorg =0.15, Lo=2.5, Eo = 1.25, To = 1.75, Lg = 1.2, Eg = 1.5, Tg = 2.0)
>>> plt.plot(df['Sg'], df['Krgo'], c = 'r', label='Gas')
>>> plt.plot(df['Sg'], df['Krog'], c = 'g', label='Oil')
>>> plt.title('SGOF Gas Oil LET Relative Permeability Curves')
>>> plt.xlabel('Sg')
>>> plt.ylabel('Kr')
>>> plt.legend()
>>> plt.grid('both')
>>> plt.plot()

SGOF Relative Permeability Curves

Or a set of Water-Oil relative permeability curves with the Corey method

>>> df = rtb.rel_perm(rows=25, krtable='SWOF', kromax =1, krwmax =0.25, swc =0.15, swcr = 0.2, sorw =0.15, no=2.5, nw=1.5)
>>> plt.plot(df['Sw'], df['Krow'], c = 'g', label='Oil')
>>> plt.plot(df['Sw'], df['Krwo'], c = 'b', label='Water')
>>> plt.title('SWOF Water Oil Corey Relative Permeability Curves')
>>> plt.xlabel('Sw')
>>> plt.ylabel('Kr')
>>> plt.legend()
>>> plt.grid('both')
>>> plt.plot()

SWOF Relative Permeability Curves

A set of dimensionless pressures for the constant terminal rate Van Everdingin & Hurst aquifer, along with an AQUTAB.INC export for use in ECLIPSE.

>>> ReDs = [1.5, 2, 3, 5, 10, 25, 1000]
>>> tds, pds = rtb.influence_tables(ReDs=ReDs, export=True)
>>>
>>> for p, pd in enumerate(pds):
>>>     plt.plot(tds, pd, label = str(ReDs[p]))
>>>
>>> plt.xscale('log')
>>> plt.yscale('log')
>>> plt.legend(loc='upper left')
>>> plt.grid(which='both')
>>> plt.xlabel('Dimensionless Time (tD)')
>>> plt.ylabel('Dimensionless Pressure Drop (PD)')
>>> plt.title('Constant Terminal Rate Solution')
>>> plt.show()

Constant Terminal Rate influence tables

Or creating black oil table information for oil

>>> results = rtb.make_bot_og(pi=4000, api=38, degf=175, sg_g=0.68, pmax=5000, pb=3900, rsb=2300, nrows=50)
>>> df, st_deno, st_deng, res_denw, res_cw, visw, pb, rsb, rsb_frac, usat = results['bot'], results['deno'], results['deng'], results['denw'], results['cw'], results['uw'], results['pb'], results['rsb'], results['rsb_scale'], results['usat']
>>> print('Stock Tank Oil Density:', st_deno, 'lb/cuft')
>>> print('Stock Tank Gas Density:', st_deng, 'lb/cuft')
>>> print('Reservoir Water Density:', res_denw, 'lb/cuft')
>>> print('Reservoir Water Compressibility:', res_cw, '1/psi')
>>> print('Reservoir Water Viscosity:', visw,'cP')

>>> fig, ((ax1, ax2), (ax3, ax4)) = plt.subplots(2, 2, figsize=(10,10))
>>> ax1.plot(df['Pressure (psia)'], df['Rs (scf/stb)'])
>>> ax2.plot(df['Pressure (psia)'], df['Bo (rb/stb)'])
>>> ax3.plot(df['Pressure (psia)'], df['uo (cP)'])
>>> ax4.semilogy(df['Pressure (psia)'], df['Co (1/psi)'])
>>> ...
>>> plt.show()
Stock Tank Oil Density: 52.05522123893805 lb/cuft
Stock Tank Gas Density: 0.052025361717109773 lb/cuft
Reservoir Water Density: 61.40223160167964 lb/cuft
Reservoir Water Compressibility: 2.930237693350768e-06 1/psi
Reservoir Water Viscosity: 0.3640686136171888 cP

Black Oil Properties

And gas

>>> fig, ((ax1, ax2), (ax3, ax4)) = plt.subplots(2, 2, figsize=(10,10))
>>> ax1.semilogy(df['Pressure (psia)'], df['Bg (rb/mscf'])
>>> ax2.plot(df['Pressure (psia)'], df['ug (cP)'])
>>> ax3.plot(df['Pressure (psia)'], df['Gas Z (v/v)'])
>>> ax4.semilogy(df['Pressure (psia)'], df['Cg (1/psi)'])
>>> ...
>>> plt.show()

Dry Gas Properties

With ability to generate Live Oil PVTO style table data as well

>>> pb = 4500
>>> results = rtb.make_bot_og(pvto=True, pi=4000, api=38, degf=175, sg_g=0.68, pmax=5500, pb=pb, nrows=25, export=True)
>>> df, st_deno, st_deng, res_denw, res_cw, visw, pb, rsb, rsb_frac, usat = results['bot'], results['deno'], results['deng'], results['denw'], results['cw'], results['uw'], results['pb'], results['rsb'], results['rsb_scale'], results['usat']
>>>
>>> if len(usat) == 0:
>>>     usat_flag = False
>>> else:
>>>     usat_flag=True
>>>     usat_p, usat_bo, usat_uo = usat
>>>
>>> try:
>>>     pb_idx = df['Pressure (psia)'].tolist().index(pb)
>>>     bob = df['Bo (rb/stb)'].iloc[pb_idx]
>>>     rsb = df['Rs (mscf/stb)'].iloc[pb_idx]
>>>     uob = df['uo (cP)'].iloc[pb_idx]
>>>     cob = df['Co (1/psi)'].iloc[pb_idx]
>>>     no_pb = False
>>> except:
>>>     print('Pb was > Pmax')
>>>     no_pb = True
>>>
>>> print('Pb (psia):', pb)
>>> print('Bob (rb/stb):', bob)
>>> print('Rsb (mscf/stb):', rsb)
>>> print('Rsb Scaling Required:', rsb_frac)
>>> print('Visob (cP):', uob)
>>> print('Cob (1/psi):', cob,'\n')
>>> print('Stock Tank Oil Density:', st_deno, 'lb/cuft')
>>> print('Stock Tank Gas Density:', st_deng, 'lb/cuft')
>>> print('Reservoir Water Density:', res_denw, 'lb/cuft')
>>> print('Reservoir Water Compressibility:', res_cw, '1/psi')
>>> print('Reservoir Water Viscosity:', visw,'cP')
>>>
>>> fig, ((ax1, ax2), (ax3, ax4)) = plt.subplots(2, 2, figsize=(10,10))
>>> ax1.plot(df['Pressure (psia)'], df['Rs (mscf/stb)'])
>>> ax2.plot(df['Pressure (psia)'], df['Bo (rb/stb)'])
>>> ax3.plot(df['Pressure (psia)'], df['uo (cP)'])
>>> ax4.semilogy(df['Pressure (psia)'], df['Co (1/psi)'])
>>>
>>> ax1.plot([pb], [rsb], 'o', c='r')
>>> ax2.plot([pb], [bob], 'o', c='r')
>>> ax3.plot([pb], [uob], 'o', c='r')
>>> ax4.plot([pb], [cob], 'o', c='r')
>>>
>>> if usat_flag:
>>>     if no_pb == False:
>>>         for i in range(len(usat_bo)):
>>>             ax2.plot(usat_p[i], usat_bo[i], c='k')
>>>             ax3.plot(usat_p[i], usat_uo[i], c='k')
>>>
>>> fig.suptitle('Black Oil Properties')
>>> ..
>>> ..
>>> plt.show()
Pb (psia): 4500
Bob (rb/stb): 1.6072798403441817
Rsb (mscf/stb): 1.2863705330979234
Rsb Scaling Required: 0.9713981737449556
Visob (cP): 0.3422139569449832
Cob (1/psi): 5.711273668114706e-05

Stock Tank Oil Density: 52.05522123893805 lb/cuft
Stock Tank Gas Density: 0.052025361717109773 lb/cuft
Reservoir Water Density: 61.40223160167964 lb/cuft
Reservoir Water Compressibility: 2.930237693350768e-06 1/psi
Reservoir Water Viscosity: 0.3640686136171888 cP

Live Oil Properties

Development

pyrestoolbox is maintained by Mark W. Burgoyne (https://github.com/mwburgoyne).

You might also like...
Python based utilities for interacting with digital multimeters that are built on the FS9721-LP3 chipset.

Python based utilities for interacting with digital multimeters that are built on the FS9721-LP3 chipset.

ZX Spectrum Utilities: (zx-spectrum-utils)
ZX Spectrum Utilities: (zx-spectrum-utils)

Here are a few utility programs that can be used with the zx spectrum. The ZX Spectrum is one of the first home computers from the early 1980s.

A collection of common regular expressions bundled with an easy to use interface.

CommonRegex Find all times, dates, links, phone numbers, emails, ip addresses, prices, hex colors, and credit card numbers in a string. We did the har

Finds price floor for every single attribute in a given collection

Solana Solanart Scanner Enjoy the Free Code Steps to run Download VS Code

Simple collection of GTPS Flood in Python.

GTPS Flood Simple collection of GTPS Flood in Python. NOTE Give me credit if you use this source, don't trade/sell this tool, And USE AT YOUR OWN RISK

A collection of custom scripts for working with Quake assets.

Custom Quake Tools A collection of custom scripts for working with Quake assets. Features Script to list all BSP files in a Quake mod

A collection of resources/tools and analyses for the angr binary analysis framework.

Awesome angr A collection of resources/tools and analyses for the angr binary analysis framework. This page does not only collect links and external r

Modest utility collection for development with AIOHTTP framework.

aiohttp-things Modest utility collection for development with AIOHTTP framework. Documentation https://aiohttp-things.readthedocs.io Installation Inst

Collection of code auto-generation utility scripts for the Horizon `Boot` system module

boot-scripts This is a collection of code auto-generation utility scripts for the Horizon Boot system module, intended for use in Atmosphère. Usage Us

Comments
  • refactor oil sg equations to func and correct 141.4 -> 141.5 per standard API equation

    refactor oil sg equations to func and correct 141.4 -> 141.5 per standard API equation

    There are 4 places in the source code where the oil/condensate specific gravity is calculated from the API. So I refactored those lines with the general equation near the top of the file.

    def oil_sg(api_value: float) -> float: """ Returns oil specific gravity given API value of oil api_value: API value """ return 141.5 / (api_value+131.5)

    The original 4 places the specific gravity was calculated using 141.4 (assume a typo). Petrowiki API Reference

    Thank you for the repo and I will continue reading the source code!

    opened by mwentzWW 1
Releases(1.3.8)
Owner
Mark W. Burgoyne
Principal Reservoir Engineer and Python enthusiast
Mark W. Burgoyne
kawadi is a versatile tool that used as a form of weapon and is used to cut, shape and split wood.

kawadi kawadi (કવાડિ in Gujarati) (Axe in English) is a versatile tool that used as a form of weapon and is used to cut, shape and split wood. kawadi

Jay Vala 2 Jan 10, 2022
Python HTTP Agent Parser

Features Fast Detects OS and Browser. Does not aim to be a full featured agent parser Will not turn into django-httpagentparser ;) Usage import ht

Shekhar 213 Dec 06, 2022
💉 코로나 잔여백신 예약 매크로 커스텀 빌드 (속도 향상 버전)

Korea-Covid-19-Vaccine-Reservation 코로나 잔여 백신 예약 매크로를 기반으로 한 커스텀 빌드입니다. 더 빠른 백신 예약을 목표로 하며, 속도를 우선하기 때문에 사용자는 이에 대처가 가능해야 합니다. 지정한 좌표 내 대기중인 병원에서 잔여 백신

Queue.ri 21 Aug 15, 2022
Creates a C array from a hex-string or a stream of binary data.

hex2array-c Creates a C array from a hex-string. Usage Usage: python3 hex2array_c.py HEX_STRING [-h|--help] Use '-' to read the hex string from STDIN.

John Doe 3 Nov 24, 2022
pydsinternals - A Python native library containing necessary classes, functions and structures to interact with Windows Active Directory.

pydsinternals - Directory Services Internals Library A Python native library containing necessary classes, functions and structures to interact with W

Podalirius 36 Dec 14, 2022
Python bytecode manipulation and import process customization to do evil stuff with format strings. Nasty!

formathack Python bytecode manipulation and import process customization to do evil stuff with format strings. Nasty! This is an answer to a StackOver

Michiel Van den Berghe 5 Jan 18, 2022
✨ Un générateur de lien raccourcis en fonction d'un lien totalement fait en Python par moi, et en français.

Shorter Link ❗ Un générateur de lien raccourcis en fonction d'un lien totalement fait en Python par moi, et en français. Dépendences : pip install pys

MrGabin 3 Jun 06, 2021
Obsidian tools - a Python package for analysing an Obsidian.md vault

obsidiantools is a Python package for getting structured metadata about your Obsidian.md notes and analysing your vault.

Mark Farragher 153 Jan 04, 2023
Various importers for cointracker

cointracker_importers Various importers for cointracker To convert nexo .csv format to cointracker .csv format: Download nexo csv file. run python Nex

Stefanos Anastasiou 9 Oct 24, 2022
A simple dork generator written in python that outputs dorks with the domain extensions you enter

Dork Gen A simple dork generator written in python that outputs dorks with the domain extensions you enter in a ".txt file". Usage The code is pretty

Z3NToX 4 Oct 30, 2022
This is a package that allows you to create a key-value vault for storing variables in a global context

This is a package that allows you to create a key-value vault for storing variables in a global context. It allows you to set up a keyring with pre-defined constants which act as keys for the vault.

Data Ductus 2 Dec 14, 2022
Small Python script to parse endlessh's output and print some neat statistics

endlessh_parser endlessh_parser is a small Python script that parses endlessh's output and prints some neat statistics about it Usage Install all the

ManicRobot 1 Oct 18, 2021
Script to autocompound 3commas BO:SO based on user provided risk factor

3commas_compounder Script to autocompound 3commas BO:SO based on user provided risk factor Setup Step 1 git clone this repo into your working director

0 Feb 24, 2022
Utility to add/remove licenses to/from source files

Utility to add/remove licenses to/from source files. Supports processing any combination of globs, files, and directories (recurse). Pruning options allow skipping non-licensing files.

Eduardo Ponce Mojica 2 Jan 29, 2022
Airspy-Utils is a small software collection to help with firmware related operations on Airspy HF+ devices.

Airspy-Utils Airspy-Utils is a small software collection to help with firmware related operations on Airspy HF+ devices on Linux (and other free syste

Dhiru Kholia 11 Oct 04, 2022
Random Name and Slug Generator

Random Name and Slug Generator

Alexander Lukanin 104 Nov 30, 2022
Macro recording and metaprogramming in Python

macro-kit is a package for efficient macro recording and metaprogramming in Python using abstract syntax tree (AST).

8 Aug 31, 2022
A tool for testing improper put method vulnerability

Putter-CUP A tool for testing improper put method vulnerability Usage :- python3 put.py -f live-subs.txt Result :- The result in txt file "result.txt"

Zahir Tariq 6 Aug 06, 2021
A small python library that helps you to generate localization strings for your mobile projects.

LocalizationUtiltiy A small python library that helps you to generate localization strings for your mobile projects. This small script aims to help yo

1 Nov 12, 2021
Automatic generator of readmes for git repositories (Includes file' listing)

Readme Generator We are bored of write the same things once and once again. We trust in the comments made inside of our files, and we decided to autom

Natalia Vera Duran 6 Jul 20, 2021