Skip to content

OpendTect GR interchange

Qualified: OpendTect Free 7.0.10, Linux x86_64, with installed ODBind, the Ophiolite SDK and the OpendTect connector package (ophiolite-opendtect). This is a local adapter; Workspace does not launch or supervise OpendTect. Windows/macOS and other versions are unqualified.

Install the official free Linux 7.0.10 release with its ODBind Python component. Create/select a survey and an existing well in OpendTect. Confirm that its stored/display depth units are metres and the input axis is measured depth (MD). Do not identify a well by matching names/coordinates automatically. Importing a GR curve does not establish well trajectory, CRS or vertical datum equivalence.

Install the Ophiolite SDK first (see Ophiolite CLI), then the OpendTect connector package in the same Python environment from its source, which your administrator provides with the Ophiolite source: pip install ./ophiolite-opendtect. The connector is licensed GPL-3.0-or-later because it runs OpendTect’s own Python binding in its process; it is distributed on its own, never inside the SDK, the client kit or the server image. Set the following for your installation (example paths, not defaults), and sign in with the SDK:

Terminal window
export DTECT_APPL=/opt/OpendTect/7.0.0
export PYTHONPATH="$DTECT_APPL/bin/python"
mkdir -m 700 private
ophiolite login --configuration configuration.json --write --credentials ./private/application.json

Follow both browser authorization steps and compare confirmation codes. You need project membership and the chosen binding’s execution/publication permission. A binding is configuration, not permission. Retained-input bindings allow member execution and explicitly shared Results; live-source administrator bindings retain their existing download-only behavior. Use Workspace → Connections → Python access to choose the supported GR input and separate LAS output. Copy the binding ID.

Create destination.json yourself:

{
"data_root": "/data/od-surveys",
"survey": "My_Survey",
"well": "Chosen well",
"axis_kind": "MD",
"log_name": "OPHIOLITE_GR"
}

survey is the directory name; well is the exact existing well object name. The adapter resolves/pins its database ID and context hashes and appends a unique run suffix to log_name. Do not reuse the working directory for another request.

Terminal window
python -m ophiolite_opendtect.application prepare --directory ./run-1 \
--credentials ./private/application.json --preset ./destination.json \
--url https://workspace.example --project your-project --binding BINDING_ID
python -m ophiolite_opendtect.application apply --directory ./run-1 --credentials ./private/application.json

Between those commands, review the printed target, precision and missing-edge loss report. Close native log editors during apply. Reopen OpendTect’s Manage Wells; select the chosen well, then the printed log name. Click the pencil to edit samples. Zero is a valid value; blank is missing. Save, confirm Save in the second dialog, and reopen to verify. Close the editor before returning.

Terminal window
python -m ophiolite_opendtect.application inspect-return --directory ./run-1 --credentials ./private/application.json
# Review the exact source-index patches, then explicitly publish:
python -m ophiolite_opendtect.application publish --directory ./run-1 --credentials ./private/application.json

A separate result.las and receipt.json are downloaded. Retained-input results appear in Workspace → Data → Results; their author can explicitly share with an allowed project recipient. A colleague previews/downloads the same result. It is unreviewed and does not overwrite a source or automatically update another host.

Get a log onto a well in your survey, check, and send a well

Section titled “Get a log onto a well in your survey, check, and send a well”

The connector can also bring a gamma-ray log from the project into your survey, tell you later whether the project has a newer version of it, and send a well from your survey to the project. Download configuration.json from Connect and keep a read access key in a file only you can read (chmod 600 ./private/read.key); sending needs a key that can write (./private/write.key, also chmod 600). SURVEY is the survey folder (data root and survey name), ITEM the log’s identifier in the project and WELL the well’s name in the survey.

Terminal window
python -m ophiolite_opendtect.exchange --survey "$SURVEY" --configuration configuration.json --key-file ./private/read.key get log "$ITEM" --well "$WELL" --depth MD --datum KB
python -m ophiolite_opendtect.exchange --survey "$SURVEY" --configuration configuration.json --key-file ./private/read.key check
python -m ophiolite_opendtect.exchange --survey "$SURVEY" --configuration configuration.json --key-file ./private/write.key send well "$WELL" --rights-confirmed

get places the log only when all of these hold; otherwise it says which one does not and changes nothing:

  • the log is linked to exactly one well in the project, and that well’s stored position is the survey well’s head: the same name, the same coordinate reference system and within 1 cm;
  • you declare its depths as measured depth from the kelly bushing (--depth MD --datum KB), and the log’s depth unit is metres or feet;
  • it is a gamma-ray curve (GR) in API units, with a value at its first and last depth, depths that increase, and depths and values that survive OpendTect’s 32-bit storage unchanged;
  • the well has no log of that name yet; nothing is overwritten.

Then the version you got is recorded in the survey’s Ophiolite folder. check changes nothing in the survey’s wells and logs; it keeps its own note of what it has seen in that same Ophiolite folder. It answers, for example, “1 newer: Ophiolite GR …”. Add --json for the identifiers and details behind a sentence.

send well puts the well’s surface position and its path (every station of its track: measured depth, x, y and depth below sea level, as OpendTect stores them) into the project, both linked to one well and marked “From OpendTect, survey …”. --rights-confirmed says you may share the well. The first send makes the well in the project (or uses the one already known there by this survey and well); --project-well ID links to a well that is already in the project, after checking its position against the survey’s. Sending again with nothing changed answers “Nothing changed in F03-4 since you sent it.”; after you edit the track, a send adds version 2 of the path, and the position is sent again only when it changed. A send that stops part way says what was sent; run it again to finish it. The connector sends metre surveys whose seismic reference datum is mean sea level, in a projected coordinate system in metres; any other survey is refused with a sentence and nothing is sent. Its note of what was sent is Ophiolite/sent-wells.json in the survey.

Get a horizon, edit it in OpendTect, send it back

Section titled “Get a horizon, edit it in OpendTect, send it back”

The connector brings a horizon from the project into your survey, written as a new horizon beside yours; your horizon is never overwritten. After you edit that horizon in OpendTect, it sends it back as the next version, and it can bring back any earlier version. HORIZON is the horizon’s identifier in the project and NAME the horizon in your survey.

Terminal window
python -m ophiolite_opendtect.exchange --survey "$SURVEY" --configuration configuration.json --key-file ./private/read.key get horizon "$HORIZON"
python -m ophiolite_opendtect.exchange --survey "$SURVEY" --configuration configuration.json --key-file ./private/write.key send horizon "$NAME"
python -m ophiolite_opendtect.exchange --survey "$SURVEY" --configuration configuration.json --key-file ./private/read.key get horizon "$HORIZON" --version 1

get horizon writes the newest version as a new horizon named for it, for example “1-Top · Ophiolite v1” (”… v1 (2)” when that name is taken). It does so only when the horizon’s coordinate reference system is the survey’s, its times are two-way time in milliseconds, downwards, and every point sits on a node of the survey’s grid within 1 cm; otherwise it says which one does not hold and changes nothing. OpendTect stores some values with less precision than they were given; the sentence says how many, and --json lists each one as given and as stored. Getting a version you already have answers that it is already in the survey. get horizon "$HORIZON" --stay keeps the version the survey holds, writing it again only if its horizon is gone or changed, and says when a newer one exists; --latest takes the newest from then on.

Edit the horizon in OpendTect and save it. send horizon sends it as the next version of the horizon it came from, marked “From OpendTect, survey …”, with the values OpendTect stored; with nothing changed it answers “Nothing changed in 1-Top since you got it.” When someone has added a newer version since, the send is refused with a sentence that says who, and nothing is sent: get the newer version first. --version N brings version N back as a new horizon of its own and changes neither your edited horizon nor what you hold. The connector’s note of which horizon holds which version is Ophiolite/horizons.json in the survey.

A horizon you made in OpendTect, not one the connector wrote, is sent as a new item. --rights-confirmed says you may share it with the project.

Terminal window
python -m ophiolite_opendtect.exchange --survey "$SURVEY" --configuration configuration.json --key-file ./private/write.key send horizon "$NAME" --rights-confirmed

The first send makes one item, version 1, private until you share it, marked “From OpendTect, survey …” and naming the horizon it came from. The survey must be in two-way time and state its coordinate system, and the horizon must have values and a name of at most 160 characters; otherwise the send is refused and nothing is sent. After you edit the horizon, the same command sends version 2 of that item, and each later edit the next version; every one needs --rights-confirmed. A survey that got such an item sends its edits the same way. When someone has added a newer version first, the send says so and nothing is sent: get the latest version into the survey and look at it. Any other refusal from the project is passed on in its own words.

Before anything is sent, the connector saves the complete request in Ophiolite/horizons.json. A send that did not finish says so; running it again with the same key sends that same request once more, and the project answers it without making a second item. A send started with another key is refused until it is finished with that key. A send run by an assistant is refused: run it yourself with your own key.

Once a send has landed, the survey is recorded as holding that version, so a later check can say when a newer one exists. It is recorded only when the horizon still holds what was sent and the project’s newest version is the one just sent; otherwise the send says why it was not. get horizon "$HORIZON" records it later, without writing the survey, only while the project’s newest version is still the one your horizon holds unchanged. If a newer version was added, get brings that version in as another horizon instead.

If Ophiolite/horizons.json is deleted, the connector no longer knows the horizon was sent, and the next send makes a new item. Once a survey has sent a new item, an earlier version of the connector cannot read its horizons.json: it refuses before it changes anything. Keep using this version or a later one with that survey.

Getting a well or cube, and sending a log or fault, are not available yet: the connector says so in a sentence.

opendtect-gr-patch/1 accepts the public ophiolite.application-curve/1 GR profile, gAPI/API values and increasing MD metres, at most 200,000 source samples. Depths and values become Float32 natively; collapsed depths refuse. Native API is the host’s canonical gamma-ray unit (scale 1). Unknown units/axis interpretation refuse.

OpendTect trims missing endpoints. The adapter retains full original LAS/arrays, records the finite-ended interval’s source offset and imports interior missing values without filling/interpolating them. All-missing input refuses. On return, only edited native values replace corresponding source indices: untouched source precision, original axes/units, other curves and missing endpoints survive. The LAS NULL marker remains missing; publishing it as a real number refuses. At most 1,000 sample edits per result; resampling, unit changes, new curves and source overwrite are unsupported. Deliberate interior gap-filling is an edit, not an automatically certified scientific correction.

ODBind writes the object. Installed odpy.getLog/Well.logs resample, and the host od_WellMan JSON serializer rounds some values. Exact readback therefore uses a strict pinned dGB 7.0.10 binary reader (little-endian Float32 MD/value pairs, Header info: No, Storage type: Binary). Unknown versions/header/storage variants refuse. The shipped native CLI independently checks object identity, unit, count and status. This small version-specific format dependency is explicit maintenance cost, not a general OpendTect SDK. Source reference: https://github.com/OpendTect/OpendTect/blob/od7.0/src/Well/wellreader.cc (odReader::rdLogHdr and readLogData). Native formats are read only by our parser.

Keep the owner-private run directory. It journals command ID, binding generation, exact input, target and native/patch hashes. Retry the same command after an interrupted request. Existing names are never intentionally overwritten. An uncertain native write is accepted only when complete readback matches the baseline; otherwise inspect it and prepare a fresh run/name. No distributed transaction is claimed: the advisory lock coordinates this adapter, not other host writers.

A native change after review blocks publication until inspected again. Lost publication responses retry the same frozen patch; server digest/idempotency checks return the same result. A new edit after publication requires another run. Re-login after credential expiry; retain the directory. Disable/revoke blocks subsequent API operations, not local access to previously downloaded files.

The run’s method/parameters and native evidence are script-declared. The server validates publication contracts, not that a human used a particular GUI or that a scientific calculation was appropriate. No automatic follow/run/publish/apply, background synchronization, Petrel/Techlog qualification or OSDU publication is implied.

python -m pytest ophiolite-opendtect/tests/test_gr_patch.py ophiolite-opendtect/tests/test_application.py checks precision/null/offset mapping, fail-closed native parsing, collision prevention, resampling refusal, patch limit, interrupted-write recovery and lost publication responses. Actual-host evidence is in Integration’s docs/verification/stage3b-opendtect.md: synthetic zero/null and NLOG HON-GT-01, actual GUI edits saved/reopened, separate publication and colleague consumption.

Boundary samples changed to missing may be trimmed by OpendTect and are refused. ASCII/Swapped storage and extra native headers are unsupported. A changed survey/well context requires a new run after explicit inspection; existing journals are retained. Native file permissions follow the caller’s environment; run artifacts are private. Shared filesystem groups must be configured by the customer; cross-OS-user native collaboration has not been qualified.