# Upgrade assessment — 7.6.1.3 → 9.2

| | |
|---|---|
| Customer | Kestrel Energy |
| Export taken | 2026-09-10 |
| Assessed | 2026-11-08T00:00:36Z |
| Produced by | mxh 0.13.0, metadata pack 2026.09 |
| Run id | `5a249250012e4f6bb012088dac6d3e394b1332cdd787bfcc2357e571c9582efe` |
| Disclosure | Demonstration package. Kestrel Energy is fictional: the dictionary export, the Java, the automation script and the screen assessed here are synthetic customer inputs. The 7.6.1.3 and 9.2 dictionaries, the Oil & Gas add-on columns, IBM's upgrade scripts and the psdi API index they are assessed against are real. |
| From | customer export at `examples/customer-upgrade/export` (4 objects) |
| To | shipped 9.2 dictionary (1866 objects) |
| Code scanned | 3 file(s), 10 attribute reference(s), 1 relationship(s), 8 psdi type(s), 14 reference(s) not tied to an object — see *Not assessed* |
| Objects assessed | 4 |
| Relationship graph | their own MAXRELATIONSHIP extract, 3 rows, which wins every hop it defines, then the 9.2 relationship graph mxh ships, 7166 rows; 3 screen binding(s) followed through it, 2 entirely on their own rows and 1 needing the shipped graph for at least one hop |
| Shipped configuration | 8841 entity(s) compared, 422 difference(s), 0 named by the supplied code |
| Industry solutions | oilandgas |

## Route and prerequisites

| | |
|---|---|
| Source | 7.6.1.3 — your export at examples/customer-upgrade/export (4 objects); IBM's own at this release: mxh's shipped evidence at 7.6.1.3 |
| Target | 9.2 — mxh's shipped 9.2 dictionary (1866 objects), metadata pack 2026.09, signed |
| Evidence between them | 7.6.7.1 (scripts) → 7.6.7.2 (scripts) → 7.6.7.3 (scripts) → 7.6.8 (scripts) → 7.6.8.1 (scripts) → 7.6.8.2 (scripts) → 8.5 (scripts) → 8.6 (scripts) → 8.7 (scripts) → 8.9 (scripts) → 9.0 (scripts and dictionary) → 9.1 (scripts and dictionary) → 9.2 (scripts and dictionary) |

The prerequisites of the move, each with what the package established and what to do next. A row whose evidence is imported was checked from what you supplied; a row with none names the artefact that settles it.

| Prerequisite | Established | Next | Evidence |
|---|---|---|---|
| Source release 7.6.1.3 | 7.6.1.3 is one of the three classic levels the Manage upgrade accepts (7.6.0.10, 7.6.1.2, 7.6.1.3). The system's own level is not in the package. | Export MAXVARS (varname, varvalue) into the configuration directory; MAXUPG is then checked against the declared release here. | none supplied: configuration/maxvars.json |
| Integrity Checker on the source database | Run IBM's Integrity Checker on the source database before cutover; its log is not in the package. | Supply the checker's log as configuration/integrity-checker.log; its error and warning lines are then counted here. | none supplied: configuration/integrity-checker.log |
| Customisation deployment | Supply the deployed customisation JAR (or its lib directory) as java-jars; every class the findings cite is then checked for presence in what is deployed. | Take businessobjects customisations from the deployed lib directory, not from a developer's build, so the check is against what runs. | none supplied: java-jars |
| Platform, database and licensing | Confirm the target's OpenShift, database and AppPoint prerequisites with the platform team. No table a Maximo export carries states them, so the package cannot. | Record the confirmation in the work package that carries cutover; nothing in this assessment moves with it. | not an export: no artefact establishes it |
| Industry solutions at the target | oilandgas applied to both sides of the comparison; the source's installed products are not in the package. No product marker was established from the supplied surfaces. | Read applications/maximo/properties/product/*.xml on the source server into configuration/products.json; the installed add-ons and their levels are then compared with what the manifest declares. | none supplied: configuration/products.json |

## Industry solutions

Their columns are folded into both sides of the comparison, because the same add-on ships for both releases.

- **oilandgas** — declared with --solutions

Implementing classes are **not** derived from them: no solution's definition declares a classname on a base object, so the class chain for a stack is not in the data IBM ships. Take it from the target system's own `MAXOBJECT.CLASSNAME`.

_Available and not applied: acm, aviation, civil, envizi, health, hse, icd, nuclear, oracleadapter, sapadapter, serviceprovider, spatial, strategize, transportation, tririga, utilities, workday._

## Coverage

| | |
|---|---|
| Objects in your dictionary | 4 |
| Objects compared against the target | 4 |
| Objects with at least one finding | 4 |
| Objects your code, screens, rows or grants reach | 2 |
| Attribute references tied to an object | 10 by object hint; 14 untied |

Every finding says how far it reaches: **cited** when a line, screen, row or grant names it; **referenced** when something supplied works on the object; **inventory** when the dictionary changed and nothing supplied goes near it. The comparison is the whole dictionary; the reach is the priority.

## Blocking — 1

An incompatible dependency or unmet prerequisite supported by the cited evidence. Resolve it, or retire the affected function, before cutover. Runtime failure is not asserted unless observed.

- **class-removed** — psdi.iface.jms.ErrorQueueNotfCronTask no longer exists in 9.1 and your code references it  
 _evidence: A2 · IBM's API at 9.1_ 
  your code: `examples/customer-upgrade/src/java/com/kestrel/maximo/PermitGate.java:8`  
  owner: Customisation developer  
  action: Replace the reference. The type does not exist at the target, so the customisation will not compile; find the supported equivalent or remove the dependency.  
  done when: The customisation compiles against the target's `businessobjects.jar` with no unresolved import.  
  proposed: **Replace** — The type or member is gone at the target (A2). What references it has to point at what the target ships for the same purpose.

## Review required — 13

A real difference whose consequence depends on what the code does with it. Someone has to look at each one; most will be fine.

11 on objects your code, screens, rows or grants reach, in full below; 2 on the rest of the dictionary, in the table after them.

- **screen-field-local-extension** — ASSET.KEINSPECTIONCLASS is bound on a screen through WORKORDER.ASSET → ASSET, and it is your own column: in your export, not in IBM's shipped dictionary at either release. The stock 9.2 dictionary not carrying it is expected — an in-place upgrade carries your own columns forward — so this is not a release removal and the screen is not known to be broken. Confirm the column is present on the upgraded system before cutover; if it is, the binding is unaffected. At least one hop was read from the 9.2 relationship graph mxh ships rather than from your own MAXRELATIONSHIP rows, so which object the field lands on is our assumption about your install — confirm the relationship too.  
  _evidence: B2 · not present in IBM's shipped dictionary at either release; bound by the screen, followed through the 9.2 relationship graph mxh ships_  
  your code: `examples/customer-upgrade/src/screens/wotrack.xml`  
  owner: Application Designer / configuration  
  action: Confirm the column on the upgraded system, then leave the screen alone. The field is your own column, which an in-place upgrade carries forward; the stock target dictionary not listing it is expected, not a broken binding. If the column is not there after the upgrade, re-apply it — a database change — before the screen is opened.  
  done when: `select 1 from maxattribute where objectname = <object> and attributename = <attribute>` on the upgraded system returns a row, and the screen renders with the field populated.  
  proposed: **Retain** — Your own column or object: in your export, not in IBM's dictionary at either release. An in-place upgrade carries it forward; confirm it on the upgraded system.
- **attribute-removed** — ASSET.PLUSSGEOJSON is removed on the path to 9.2 (no reference found in the code supplied)  
 _evidence: A1 · IBM upgrade script, 9.0_ 
  owner: Customisation developer  
  action: Change every cited site before cutover. The column is gone at the target: a read throws and a write fails.  
  done when: `select 1 from maxattribute where objectname = <object> and attributename = <attribute>` on the target returns no row, and no cited site references it.  
  proposed: **Investigate** — The removal is stated by IBM's own evidence (A1) but no supplied line was seen to depend on it. Confirm nothing outside the supplied surfaces does.
- **attribute-removed** — WORKORDER.PLUSSGEOJSON is removed on the path to 9.2 (no reference found in the code supplied)  
 _evidence: A1 · IBM upgrade script, 9.0_ 
  owner: Customisation developer  
  action: Change every cited site before cutover. The column is gone at the target: a read throws and a write fails.  
  done when: `select 1 from maxattribute where objectname = <object> and attributename = <attribute>` on the target returns no row, and no cited site references it.  
  proposed: **Investigate** — The removal is stated by IBM's own evidence (A1) but no supplied line was seen to depend on it. Confirm nothing outside the supplied surfaces does.
- **method-removed** — psdi.app.person.Person.getAvailableHours(Ljava/util/Date;Lpsdi/app/person/PersonCalRemote;Lpsdi/app/common/AvailCalc;)D is gone in 8.7; you reference the class — check the call  
 _evidence: A2 · IBM's API at 8.7_ 
  your code: `examples/customer-upgrade/src/java/com/kestrel/maximo/PermitGate.java:9`  
  owner: Customisation developer  
  action: Check each cited site. The class survives but this member does not, so a call compiles today and fails at the target.  
  done when: The customisation compiles against the target's `businessobjects.jar`, and the cited lines either no longer call the member or call its replacement.  
  proposed: **Replace** — The type or member is gone at the target (A2). What references it has to point at what the target ships for the same purpose.
- **method-removed** — psdi.app.person.Person.getAvailableMbo(Ljava/util/Date;Lpsdi/app/person/PersonCalRemote;Lpsdi/app/common/AvailCalc;)Lpsdi/mbo/MboRemote; is gone in 8.7; you reference the class — check the call  
 _evidence: A2 · IBM's API at 8.7_ 
  your code: `examples/customer-upgrade/src/java/com/kestrel/maximo/PermitGate.java:9`  
  owner: Customisation developer  
  action: Check each cited site. The class survives but this member does not, so a call compiles today and fails at the target.  
  done when: The customisation compiles against the target's `businessobjects.jar`, and the cited lines either no longer call the member or call its replacement.  
  proposed: **Replace** — The type or member is gone at the target (A2). What references it has to point at what the target ships for the same purpose.
- **method-removed** — psdi.app.person.Person.getAvailableMboList(Ljava/util/Date;Lpsdi/app/person/PersonCalRemote;Lpsdi/app/common/AvailCalc;)Ljava/util/List; is gone in 8.7; you reference the class — check the call  
 _evidence: A2 · IBM's API at 8.7_ 
  your code: `examples/customer-upgrade/src/java/com/kestrel/maximo/PermitGate.java:9`  
  owner: Customisation developer  
  action: Check each cited site. The class survives but this member does not, so a call compiles today and fails at the target.  
  done when: The customisation compiles against the target's `businessobjects.jar`, and the cited lines either no longer call the member or call its replacement.  
  proposed: **Replace** — The type or member is gone at the target (A2). What references it has to point at what the target ships for the same purpose.
- **type-changed** — ASSET.ASSETHEALTH type INTEGER → DECIMAL. Check stored values and consumers for case, rounding and conversion effects. A type difference alone does not establish a failure. No line of the supplied code reads or writes it, so nothing you own is known to break; anything outside the supplied code that carries it — an integration, a report — is what to check. The same column carries this change on 2 tables: ASSET, LOCATIONS.  
  _evidence: B2 · dictionary 7.6.1.3 vs 9.2_  
  owner: Customisation developer  
  action: Validate existing values and every cited consumer against the new type, including case, rounding, range and truth semantics. A metadata difference alone does not establish a failing operation.  
  done when: Each cited site has been read against the new type and either changed or recorded as unaffected, with the reason.  
  proposed: **Investigate** — The column still exists with a different definition. Whether a cited site cares is a judgement about the code, not a fact in the dictionary.
- **scale-changed** — ASSET.ASSETHEALTH scale 0 → 2 The same column carries this change on 2 tables: ASSET, LOCATIONS.  
  _evidence: B2 · dictionary 7.6.1.3 vs 9.2_  
  owner: Customisation developer  
  action: Check arithmetic and rounding at every cited site, and any total that has to reconcile.  
  done when: A worked example at the new scale reconciles against the same example at the old one, or the difference is accepted and recorded.  
  proposed: **Investigate** — The column still exists with a different definition. Whether a cited site cares is a judgement about the code, not a fact in the dictionary.
- **type-changed** — ASSET.GEOMETRY type BLOB → CLOB. Check stored values and consumers for case, rounding and conversion effects. A type difference alone does not establish a failure. No line of the supplied code reads or writes it, so nothing you own is known to break; anything outside the supplied code that carries it — an integration, a report — is what to check. The same column carries this change on 3 tables: ASSET, LOCATIONS, WORKORDER.  
 _evidence: B1 · dictionary 7.6.1.3 vs 9.2, corroborated by IBM's upgrade script, 9.0_ 
  owner: Customisation developer  
  action: Validate existing values and every cited consumer against the new type, including case, rounding, range and truth semantics. A metadata difference alone does not establish a failing operation.  
  done when: Each cited site has been read against the new type and either changed or recorded as unaffected, with the reason.  
  proposed: **Investigate** — The column still exists with a different definition. Whether a cited site cares is a judgement about the code, not a fact in the dictionary.
- **persistence-changed** — ASSET.GEOMETRY persistent true → false The same column carries this change on 3 tables: ASSET, LOCATIONS, WORKORDER.  
 _evidence: B1 · dictionary 7.6.1.3 vs 9.2, corroborated by IBM's upgrade script, 9.0_ 
  owner: Customisation developer  
  action: A non-persistent attribute is not in the table. Anything that queries, indexes, reports on or joins to it stops working, even though reading it through the MBO still does.  
  done when: No SQL, report or integration references the attribute as a column on the target.  
  proposed: **Investigate** — The column still exists with a different definition. Whether a cited site cares is a judgement about the code, not a fact in the dictionary.
- **persistence-changed** — ASSET.METHODNAME persistent false → true The same column carries this change on 2 tables: ASSET, LOCATIONS.  
  _evidence: B2 · dictionary 7.6.1.3 vs 9.2_  
  owner: Customisation developer  
  action: A non-persistent attribute is not in the table. Anything that queries, indexes, reports on or joins to it stops working, even though reading it through the MBO still does.  
  done when: No SQL, report or integration references the attribute as a column on the target.  
  proposed: **Investigate** — The column still exists with a different definition. Whether a cited site cares is a judgement about the code, not a fact in the dictionary.

**The rest of the dictionary — 2 review required finding(s) on objects nothing supplied references.** The same comparison, the same evidence; listed compactly because no line, screen, row or grant of yours names them.

| Kind | Object.attribute | Observed | Evidence | Proposed |
|---|---|---|---|---|
| type-changed | `LOCATIONS.HEALTH` | LOCATIONS.HEALTH type INTEGER → DECIMAL. Check stored values and consumers for case, rounding and conversion effects. A type difference alone does not establish a failure. No line of the supplied code reads or writes it, so nothing you own is known to break; anything outside the supplied code that carries it — an integration, a report — is what to check. | B2 · dictionary 7.6.1.3 vs 9.2 | Investigate |
| scale-changed | `LOCATIONS.HEALTH` | LOCATIONS.HEALTH scale 0 → 2 | B2 · dictionary 7.6.1.3 vs 9.2 | Investigate |

## Environment-dependent — 8

Differs between the two systems but is not a property of the release — installed industry solutions, or installation-configured values. Confirm against the target system itself, not against a release number.

6 on objects your code, screens, rows or grants reach, in full below; 2 on the rest of the dictionary, in the table after them.

- **local-extension** — ASSET.KECORROSIONLOOP is not part of IBM's own 7.6.1.3 dictionary either — it is your own field, not something the release removes. Decide whether to carry it forward to 9.2. Your code reads or writes it.  
  _evidence: B2 · not present in IBM's shipped 7.6.1.3 dictionary_  
  your code: `examples/customer-upgrade/src/screens/wotrack.xml:24`  
  owner: Database / migration  
  action: Decide whether to carry it forward. It is your own field, not part of IBM's dictionary at either release, so its absence at the target is not release evidence — re-applying it is a database change, not a code change.  
  done when: Either the attribute exists on the target with the type, length and required flag your code expects, or every cited site has been changed to stop using it. One or the other, recorded.  
  proposed: **Retain** — Your own column or object: in your export, not in IBM's dictionary at either release. An in-place upgrade carries it forward; confirm it on the upgraded system.
- **local-extension** — ASSET.KEINSPECTIONCLASS is not part of IBM's own 7.6.1.3 dictionary either — it is your own field, not something the release removes. Decide whether to carry it forward to 9.2. Your code reads or writes it.  
  _evidence: B2 · not present in IBM's shipped 7.6.1.3 dictionary_  
  your code: `examples/customer-upgrade/src/screens/wotrack.xml:25`  
  owner: Database / migration  
  action: Decide whether to carry it forward. It is your own field, not part of IBM's dictionary at either release, so its absence at the target is not release evidence — re-applying it is a database change, not a code change.  
  done when: Either the attribute exists on the target with the type, length and required flag your code expects, or every cited site has been changed to stop using it. One or the other, recorded.  
  proposed: **Retain** — Your own column or object: in your export, not in IBM's dictionary at either release. An in-place upgrade carries it forward; confirm it on the upgraded system.
- **local-extension** — WORKORDER.KEFLARINGHOURS is not part of IBM's own 7.6.1.3 dictionary either — it is your own field, not something the release removes. Decide whether to carry it forward to 9.2. Your code reads or writes it.  
  _evidence: B2 · not present in IBM's shipped 7.6.1.3 dictionary_  
  your code: `examples/customer-upgrade/src/screens/wotrack.xml:15`  
  owner: Database / migration  
  action: Decide whether to carry it forward. It is your own field, not part of IBM's dictionary at either release, so its absence at the target is not release evidence — re-applying it is a database change, not a code change.  
  done when: Either the attribute exists on the target with the type, length and required flag your code expects, or every cited site has been changed to stop using it. One or the other, recorded.  
  proposed: **Retain** — Your own column or object: in your export, not in IBM's dictionary at either release. An in-place upgrade carries it forward; confirm it on the upgraded system.
- **local-extension** — WORKORDER.KEPERMITSTATUS is not part of IBM's own 7.6.1.3 dictionary either — it is your own field, not something the release removes. Decide whether to carry it forward to 9.2. Your code reads or writes it.  
  _evidence: B2 · not present in IBM's shipped 7.6.1.3 dictionary_  
  your code: `examples/customer-upgrade/src/screens/wotrack.xml:14`  
  owner: Database / migration  
  action: Decide whether to carry it forward. It is your own field, not part of IBM's dictionary at either release, so its absence at the target is not release evidence — re-applying it is a database change, not a code change.  
  done when: Either the attribute exists on the target with the type, length and required flag your code expects, or every cited site has been changed to stop using it. One or the other, recorded.  
  proposed: **Retain** — Your own column or object: in your export, not in IBM's dictionary at either release. An in-place upgrade carries it forward; confirm it on the upgraded system.
- **local-extension** — WORKORDER.KESHUTDOWNREF is not part of IBM's own 7.6.1.3 dictionary either — it is your own field, not something the release removes. Decide whether to carry it forward to 9.2. Your code reads or writes it.  
  _evidence: B2 · not present in IBM's shipped 7.6.1.3 dictionary_  
  your code: `examples/customer-upgrade/src/screens/wotrack.xml:13`  
  owner: Database / migration  
  action: Decide whether to carry it forward. It is your own field, not part of IBM's dictionary at either release, so its absence at the target is not release evidence — re-applying it is a database change, not a code change.  
  done when: Either the attribute exists on the target with the type, length and required flag your code expects, or every cited site has been changed to stop using it. One or the other, recorded.  
  proposed: **Retain** — Your own column or object: in your export, not in IBM's dictionary at either release. An in-place upgrade carries it forward; confirm it on the upgraded system.
- **local-extension** — WORKORDER.KEWELLID is not part of IBM's own 7.6.1.3 dictionary either — it is your own field, not something the release removes. Decide whether to carry it forward to 9.2. Your code reads or writes it.  
  _evidence: B2 · not present in IBM's shipped 7.6.1.3 dictionary_  
  your code: `examples/customer-upgrade/src/screens/wotrack.xml:12`  
  owner: Database / migration  
  action: Decide whether to carry it forward. It is your own field, not part of IBM's dictionary at either release, so its absence at the target is not release evidence — re-applying it is a database change, not a code change.  
  done when: Either the attribute exists on the target with the type, length and required flag your code expects, or every cited site has been changed to stop using it. One or the other, recorded.  
  proposed: **Retain** — Your own column or object: in your export, not in IBM's dictionary at either release. An in-place upgrade carries it forward; confirm it on the upgraded system.

**The rest of the dictionary — 2 environment-dependent finding(s) on objects nothing supplied references.** The same comparison, the same evidence; listed compactly because no line, screen, row or grant of yours names them.

| Kind | Object.attribute | Observed | Evidence | Proposed |
|---|---|---|---|---|
| local-extension | `FAILUREREPORT.KEROOTCAUSECODE` | FAILUREREPORT.KEROOTCAUSECODE is not part of IBM's own 7.6.1.3 dictionary either — it is your own field, not something the release removes. Decide whether to carry it forward to 9.2. | B2 · not present in IBM's shipped 7.6.1.3 dictionary | Retain |
| local-extension | `LOCATIONS.KEPLATFORM` | LOCATIONS.KEPLATFORM is not part of IBM's own 7.6.1.3 dictionary either — it is your own field, not something the release removes. Decide whether to carry it forward to 9.2. | B2 · not present in IBM's shipped 7.6.1.3 dictionary | Retain |

## Decisions

What to do about each finding. mxh proposes one of five words from the kind, the grade and the evidence class, and says why on the finding; the proposal is advice. A reviewer's decision, where the package carries one, is printed beside it and never over it.

| Disposition | Proposed by mxh | Decided by the reviewer |
|---|---|---|
| Retain — keep it as it is; confirm it on the upgraded system | 9 | 0 |
| Change — change the cited code, screen or row before cutover | 0 | 0 |
| Replace — replace it with what the target ships for the same purpose | 4 | 0 |
| Retire — remove it; nothing supplied needs it on the target | 0 | 0 |
| Investigate — read it against the target before deciding | 9 | 0 |

0 finding(s) decided, 22 not yet decided.

## Work packages

The findings grouped into related decisions and tests with a common owner, blocking first. A package's acceptance test is the closure tests of the findings in it — each is a query or a compilation somebody runs on the target, and every one is in the technical findings above. Counts are of findings, not of days; sizing a package is the partner's, against their own delivery model.

| Package | Owner | Subject | Blocking | Review | Environment | Proposed | Decided |
|---|---|---|---|---|---|---|---|
| WP-ee4980cc | Customisation developer | `Class removed` | 1 | 0 | 0 | 1 replace | 0 of 1 |
| WP-cf44bbb5 | Customisation developer | `Validate changed datatypes against actual usage` | 0 | 3 | 0 | 3 investigate | 0 of 3 |
| WP-395a9c9b | Customisation developer | `Method removed` | 0 | 3 | 0 | 3 replace | 0 of 3 |
| WP-232873dd | Customisation developer | `Attribute removed` | 0 | 2 | 0 | 2 investigate | 0 of 2 |
| WP-15e67888 | Customisation developer | `Persistence changed` | 0 | 2 | 0 | 2 investigate | 0 of 2 |
| WP-1683a233 | Customisation developer | `Scale changed` | 0 | 2 | 0 | 2 investigate | 0 of 2 |
| WP-253434f3 | Application Designer / configuration | `Screen field local extension` | 0 | 1 | 0 | 1 retain | 0 of 1 |
| WP-1af3c60d | Database / migration | `Local extension` | 0 | 0 | 8 | 8 retain | 0 of 8 |

**Suggested order**, which is advice and not a finding: packages with blocking findings first; within them, dictionary and migration work before code, code before configuration and screens, because a screen or an escalation is tested against the column and class it will find on the target. A package is closed when every acceptance test in it has been run on the target and read — `mxh verify-closure` runs the ones an export can answer.

**What mxh did not estimate.** No effort, duration, cost, team size or date appears in this assessment, and none should be read into a count. The partner supplies: the delivery model, the number of environments and the test approach, the code-freeze and cutover dates, whether the customisation JAR is rebuilt or redeployed, and the sign-off for each package.

## What depends on each object

Every cited site of every finding, arranged by the object it depends on. Change the object's columns and these are the places that notice. The count is of findings on the object; a site appears once however many findings cite it.

| Object | Findings | Depends on it |
|---|---|---|
| `ASSET` | 9 | screens (1): `examples/customer-upgrade/src/screens/wotrack.xml` |
| `FAILUREREPORT` | 1 | no supplied site cites it — the finding is dictionary-only |
| `LOCATIONS` | 3 | no supplied site cites it — the finding is dictionary-only |
| `WORKORDER` | 5 | screens (1): `examples/customer-upgrade/src/screens/wotrack.xml` |

## Not assessed

A clean report above means only what was actually checked. It does not
mean the upgrade is safe.

- 14 attribute reference(s) in the supplied code could not be tied to an object, so they were NOT checked: the file names no object (no launch point for the script, no `mboname`/`objectName`, no `mxh:object=` comment). Supply the SCRIPTLAUNCHPOINT export so each script's object is known, or add a `# mxh:object=<OBJECT>` line to the file. First sites: examples/customer-upgrade/src/java/com/kestrel/maximo/PermitGate.java:23, examples/customer-upgrade/src/java/com/kestrel/maximo/PermitGate.java:24, examples/customer-upgrade/src/java/com/kestrel/maximo/PermitGate.java:33, examples/customer-upgrade/src/java/com/kestrel/maximo/PermitGate.java:41, examples/customer-upgrade/src/scripts/KESHUTDOWN.py:8, examples/customer-upgrade/src/scripts/KESHUTDOWN.py:9, examples/customer-upgrade/src/scripts/KESHUTDOWN.py:10, examples/customer-upgrade/src/scripts/KESHUTDOWN.py:12.
- 1 screen field(s) run through a relationship path that was followed using the 9.2 relationship graph mxh ships, because your own MAXRELATIONSHIP export does not define the hop. Their attributes were checked against the 9.2 dictionary the same way every other field was, but which object each one lands on is IBM's out-of-the-box answer rather than yours — Application Designer lets a relationship be redefined, and a redefined hop lands somewhere else. Findings from those paths carry evidence class B2 and are graded for review; a clean result on them is weaker than a clean result on a path your own rows answered. `mxh import-dd` against your full MAXRELATIONSHIP extract settles it.
- 1 screen field(s) run through a relationship this run could not follow, so they were not checked: WORKORDER.KEWELLHEAD. Neither your own MAXRELATIONSHIP export nor the 9.2 relationship graph mxh ships defines a relationship of that name on that object. An export scoped to some objects does not carry every relationship, so this is missing evidence rather than a broken screen — it is not reported as a finding.
- No automation-script launch points were supplied, so what fires each script was not checked — only what the script does. A script whose code has not changed still breaks when the column its launch point binds to is gone at the target, and no code scan can see that. Export `SCRIPTLAUNCHPOINT` and `LAUNCHPOINTVARS` and point the manifest's `launch-points` surface at them.
- No configuration export was supplied, so your own escalations, cron task instances, actions, workflow conditions, communication templates, domain values and property values were NOT checked. An escalation whose condition names a column the target dropped does not fail at import; it fails on its first run, in a log. Export `ESCALATION`, `ESCREFPOINT`, `CRONTASKDEF`, `CRONTASKINSTANCE`, `ACTION`, `WFPROCESS`, `WFCONDITION`, `COMMTEMPLATE`, `MAXDOMAIN`, `SYNONYMDOMAIN`, `ALNDOMAIN` and `MAXPROP` as JSON and point the manifest's `configuration` surface at them.
- No security export was supplied, so **who** each finding above affects was not assessed — only what it breaks. Security-group grants and restrictions are a customer's own rather than IBM's, so nothing shipped can answer it: a restriction pointing at a column the target dropped stops applying silently, and rows it was hiding become visible with nothing in any log to say so. Export `MAXGROUP`, `APPLICATIONAUTH`, `SECURITYRESTRICT` and group membership **as counts** (`SELECT groupname, COUNT(*) ... GROUP BY groupname` over active users — never user ids) and point the manifest's `security` surface at them.
- Shipped configuration is compared — action, application, commtemplate, crontask, doctype, endpoint, escalation, intobject, kpi, property, report, restriction, securitygroup, sigoption, workflow — and a difference becomes a finding where the supplied code names it. Configuration reached only from the database (an escalation whose action row points at a class, a report the code never names) is not seen by a code scan, and neither are security-group grants or menu placement, which are a customer's own rather than IBM's. Those come in from the customer's own configuration export, the same way `--export` brings their dictionary in.
- `object-structures` was declared not supplied by Kestrel Energy — the integration framework was not exported for this engagement, so no object-structure schemas were available to check. `mxh assess` now reads them when supplied: point the manifest's object-structures surface at a directory of the customer's own exported OSLC `/oslc/jsonschemas/<os>` responses (or an OpenAPI document) and every field one publishes outside the code-scanned objects is compared against the target dictionary the same way a plain attribute is.
- `launch-points` was declared not supplied by Kestrel Energy — the automation scripts were exported as source only, so SCRIPTLAUNCHPOINT and LAUNCHPOINTVARS were not taken and what fires each script was not checked — only what it does. `mxh assess` now reads them when supplied: point the manifest's launch-points surface at the customer's own export of those two tables and every object and column a trigger binds to, plus every variable bound to a bare attribute, is compared against the target dictionary the same way a plain attribute is.
- `java-inventory` was declared not supplied by Kestrel Energy — no JAR inventory was taken for this engagement, so only the Java under src/java is scanned for psdi references. `mxh assess` now reads compiled JARs too when supplied: point the manifest's java-jars surface at the customisation's lib directory (or a WAR's WEB-INF/lib) and every class file's constant pool is checked for removed psdi signatures the same way source is — no execution, no classloading.
- Dictionary differences that need no work, so not raised: 2 where IBM's own 7.6.1.3 definition already matches 9.2 (the difference is your customisation, and an in-place upgrade carries it), 54 where 9.2 only relaxes the column (longer, or a type that accepts more), so every existing value and consumer still fits, and 0 fields of yours that 9.2 defines identically.
- 5 of your own columns bound on your screens are already listed as local extensions; the upgrade carries the column and the binding, so the screens raise nothing further for them.
- 8 IBM objects and columns removed on the path to 9.2 are used by nothing you supplied, so the upgrade drops them with no work on your side; if you keep rows in any of them, export those rows before cutover: FAILUREREPORT.EXCEPTIONDATE, FAILUREREPORT.EXCEPTIONREASON, FAILUREREPORT.EXCEPTIONREFERENCE, FAILUREREPORT.IMMEDIATEACTION, FAILUREREPORT.QUALITYIMPACT, FAILUREREPORT.READYTOUSEAFTERCORRECTION, FAILUREREPORT.USEDAFTEROVERDUE, LOCATIONS.PLUSSGEOJSON.

---

**What proves each finding.** Every finding above carries an evidence-confidence class. It is not a second severity: the grade says how much a finding hurts, the class says how much weight it will bear. A blocking finding on weak evidence is a claim a customer can knock down, which is worse than not making it.

- **A1 — IBM upgrade-script stated** (2 findings). State it as what the release does, and name the script.  
  _Not from this: Do not state it as an outcome without checking the target dictionary agrees. A script that drops an attribute and adds it back has redefined it, not removed it._
- **A2 — Bytecode/API confirmed** (4 findings). State that the type or member is gone at the target release.  
  _Not from this: Do not call a member removed when it is still reachable on a supertype. Do not count IBM's own *.unittest.* classes as API changes — that is packaging._
- **B1 — Dictionary observed and independently corroborated** (2 findings). State it as a release change, naming both the dictionary difference and the corroborating script.  
  _Not from this: Do not claim the script's specific values. Corroboration says the release touched the attribute; the values still come from the dictionary._
- **B2 — Dictionary observed only** (14 findings). Say "between these two dictionaries", and say which two.  
  _Not from this: Never state it as a release change, and never as something IBM did. A dump is an environment: the difference may be the installed industry solutions, not the release. Say so rather than hiding it._

Anything that cannot be attributed to the release is graded environment-dependent rather than presented as an upgrade breaker.
