# Business Logic — KKW01031SF01DBean.typeModelData() [100 LOC]

| Field | Value |
|-------|-------|
| Fully Qualified Name | `eo.web.webview.KKW01031SF.KKW01031SF01DBean` |
| Layer | Web/Screen Data Bean (X33V Framework) |
| Module | `KKW01031SF` (Package: `eo.web.webview.KKW01031SF`) |

## 1. Role

### KKW01031SF01DBean.typeModelData()

This method implements the X33V framework's data type resolution contract by mapping field names (items) and sub-keys to their corresponding Java type classes. It serves as a type-introspection dispatch mechanism used by the Futurity X33V web framework to determine the data model type for each property exposed by the data bean (DBean) on the migration reason definition screen. The method implements a **routing/dispatch design pattern** — it receives a `key` representing a field name in Japanese (the business label of a screen item) and a `subkey` representing a property accessor (typically `value` for the data value or `state` for UI state metadata), then returns the appropriate `Class<?>` descriptor.

The method handles **seven distinct business fields**: SYSID (system identifier), Service Contract Number (サービス契約番号), Migration Classification (異動区分), Migration Reason Code (異動理由コード), Migration Reason Memo (異動理由メモ), Application Number (申込番号), and Application Detail Number (申込明細番号). For most fields, the `value` and `state` sub-keys both resolve to `String.class`, reflecting that all stored data and UI state metadata are text-based. The Migration Reason Code field is the most complex — it supports indexed list access where the key includes a path separator and either an index number, an asterisk (`*`) to query list size, or the base field name. For indexed access, the method delegates to the individual list item's `typeModelData()` method. The method plays a critical role in the X33V framework's load/store cycle, enabling the framework to serialize and deserialize screen state correctly.

## 2. Processing Pattern (Detailed Business Logic)

```mermaid
flowchart TD
    START([typeModelData key subkey])
    START --> CHECK_NULL[Check if key or subkey is null]
    CHECK_NULL --> NULL_CHECK{key == null<br>or subkey == null?}
    NULL_CHECK -->|true| RETURN_NULL_1[return null]
    NULL_CHECK -->|false| FIND_SLASH[int separaterPoint = key.indexOf slash]
    FIND_SLASH --> CHECK_SYSID{key equals SYSID?}
    CHECK_SYSID -->|true| CHECK_SYSID_SUB{subkey equals value?}
    CHECK_SYSID_SUB -->|true| RETURN_SYSID_VALUE[return String.class]
    CHECK_SYSID_SUB -->|false| CHECK_SYSID_STATE{subkey equals state?}
    CHECK_SYSID_STATE -->|true| RETURN_SYSID_STATE[return String.class]
    CHECK_SYSID_STATE -->|false| CHECK_SVC{key equals SVC Contract No?}
    CHECK_SYSID -->|false| CHECK_SVC
    CHECK_SVC -->|true| CHECK_SVC_SUB{subkey equals value?}
    CHECK_SVC_SUB -->|true| RETURN_SVC_VALUE[return String.class]
    CHECK_SVC_SUB -->|false| CHECK_SVC_STATE{subkey equals state?}
    CHECK_SVC_STATE -->|true| RETURN_SVC_STATE[return String.class]
    CHECK_SVC_STATE -->|false| CHECK_IDO_DIV{key equals IDO Div?}
    CHECK_SVC -->|false| CHECK_IDO_DIV
    CHECK_IDO_DIV -->|true| CHECK_IDO_DIV_SUB{subkey equals value?}
    CHECK_IDO_DIV_SUB -->|true| RETURN_IDO_DIV_VALUE[return String.class]
    CHECK_IDO_DIV_SUB -->|false| CHECK_IDO_DIV_STATE{subkey equals state?}
    CHECK_IDO_DIV_STATE -->|true| RETURN_IDO_DIV_STATE[return String.class]
    CHECK_IDO_DIV_STATE -->|false| CHECK_IDO_RSN_CD{key equals IDO Reason Code?}
    CHECK_IDO_DIV -->|false| CHECK_IDO_RSN_CD
    CHECK_IDO_RSN_CD -->|true| SUBSTRING_KEY[key = key.substring separaterPoint plus 1]
    SUBSTRING_KEY --> CHECK_ASTERISK{key equals asterisk?}
    CHECK_ASTERISK -->|true| RETURN_INT[return Integer.class]
    CHECK_ASTERISK -->|false| PARSE_INDEX[tmpIndexInt = Integer.valueOf key]
    PARSE_INDEX --> TRY_CATCH{NumberFormatException?}
    TRY_CATCH -->|true| RETURN_NULL_2[return null]
    TRY_CATCH -->|false| CHECK_INDEX_NULL{tmpIndexInt is null?}
    CHECK_INDEX_NULL -->|true| RETURN_NULL_3[return null]
    CHECK_INDEX_NULL -->|false| CHECK_BOUNDS{tmpIndex out of bounds?}
    CHECK_BOUNDS -->|true| RETURN_NULL_4[return null]
    CHECK_BOUNDS -->|false| CALL_TYPE_MODEL[X33VDataTypeStringBean.typeModelData subkey]
    CALL_TYPE_MODEL --> RETURN_DELEGATE[return delegated typeModelData]
    CHECK_IDO_RSN_CD -->|false| CHECK_IDO_RSN_MEMO{key equals IDO Reason Memo?}
    CHECK_IDO_RSN_MEMO -->|true| CHECK_MEMO_SUB{subkey equals value?}
    CHECK_MEMO_SUB -->|true| RETURN_MEMO_VALUE[return String.class]
    CHECK_MEMO_SUB -->|false| CHECK_MEMO_STATE{subkey equals state?}
    CHECK_MEMO_STATE -->|true| RETURN_MEMO_STATE[return String.class]
    CHECK_MEMO_STATE -->|false| CHECK_MSKM_NO{key equals Application No?}
    CHECK_IDO_RSN_MEMO -->|false| CHECK_MSKM_NO
    CHECK_MSKM_NO -->|true| CHECK_MSKM_NO_SUB{subkey equals value?}
    CHECK_MSKM_NO_SUB -->|true| RETURN_MSKM_NO_VALUE[return String.class]
    CHECK_MSKM_NO_SUB -->|false| CHECK_MSKM_NO_STATE{subkey equals state?}
    CHECK_MSKM_NO_STATE -->|true| RETURN_MSKM_NO_STATE[return String.class]
    CHECK_MSKM_NO_STATE -->|false| CHECK_MSKM_DTL_NO{key equals Application Detail No?}
    CHECK_MSKM_NO -->|false| CHECK_MSKM_DTL_NO
    CHECK_MSKM_DTL_NO -->|true| CHECK_MSKM_DTL_SUB{subkey equals value?}
    CHECK_MSKM_DTL_SUB -->|true| RETURN_MSKM_DTL_VALUE[return String.class]
    CHECK_MSKM_DTL_SUB -->|false| CHECK_MSKM_DTL_STATE{subkey equals state?}
    CHECK_MSKM_DTL_STATE -->|true| RETURN_MSKM_DTL_STATE[return String.class]
    CHECK_MSKM_DTL_STATE -->|false| RETURN_NULL_5[return null no match]
    RETURN_NULL_1 --> END([END])
    RETURN_SYSID_VALUE --> END
    RETURN_SYSID_STATE --> END
    RETURN_SVC_VALUE --> END
    RETURN_SVC_STATE --> END
    RETURN_IDO_DIV_VALUE --> END
    RETURN_IDO_DIV_STATE --> END
    RETURN_INT --> END
    RETURN_NULL_2 --> END
    RETURN_NULL_3 --> END
    RETURN_NULL_4 --> END
    RETURN_DELEGATE --> END
    RETURN_MEMO_VALUE --> END
    RETURN_MEMO_STATE --> END
    RETURN_MSKM_NO_VALUE --> END
    RETURN_MSKM_NO_STATE --> END
    RETURN_MSKM_DTL_VALUE --> END
    RETURN_MSKM_DTL_STATE --> END
    RETURN_NULL_5 --> END
```

## 3. Parameter Analysis

| No | Parameter Name | Type | Business Description |
|----|---------------|------|---------------------|
| 1 | `key` | `String` | The field name (item name / 項目名) identifying which screen data property to query. Can be one of seven Japanese field labels: "SYSID" (system identifier), "サービス契約番号" (service contract number), "異動区分" (migration classification), "異動理由コード" (migration reason code), "異動理由メモ" (migration reason memo), "申込番号" (application number), or "申込明細番号" (application detail number). For the Migration Reason Code field, the key may include a "/"-separated index suffix (e.g., "異動理由コード/0" for the first list item, "異動理由コード/*" for list size). |
| 2 | `subkey` | `String` | The sub-property accessor within a field. Typically either "value" (the actual data value) or "state" (the UI state metadata). Case-insensitive matching via `equalsIgnoreCase`. Used to differentiate between the data content and its display state. |

**Instance fields read:**
| Field | Type | Business Description |
|-------|------|---------------------|
| `ido_rsn_cd_list` | `X33VDataTypeList` | List of migration reason code entries. Each element is an `X33VDataTypeStringBean` containing a migration reason code value. Used for indexed access in the "異動理由コード" branch. |
| `index` | `int` | Instance field (not directly read in this method but part of the bean's data binding state). |

## 4. CRUD Operations / Called Services

### Pre-computed evidence from code analysis graph:

| CRUD | SC / CBS | SC Code | Entity / DB | Operation Description |
|------|----------|---------|-------------|----------------------|
| - | `JKKAdEditCC.substring` | JKKAdEditCC | - | Calls `substring` in `JKKAdEditCC` |
| - | `JKKAdEdit.substring` | JKKAdEdit | - | Calls `substring` in `JKKAdEdit` |
| - | `JKKTelnoInfoAddMapperCC.substring` | JKKTelnoInfoAddMapperCC | - | Calls `substring` in `JKKTelnoInfoAddMapperCC` |
| - | `JDKejbStringEdit.substring` | JDKejbStringEdit | - | Calls `substring` in `JDKejbStringEdit` |
| - | `KKW01031SF01DBean.typeModelData` | KKW01031SF01DBean | - | Calls `typeModelData` in `KKW01031SF01DBean` |

The method `typeModelData` itself performs **no direct database or CRUD operations**. It is a pure type-inspection utility. However, within the "異動理由コード" (Migration Reason Code) branch, it calls:

| CRUD | SC / CBS | SC Code | Entity / DB | Operation Description |
|------|----------|---------|-------------|----------------------|
| R | `X33VDataTypeStringBean.typeModelData` | X33VDataTypeStringBean | - (framework bean) | Delegates to the list element's `typeModelData(subkey)` method to resolve the data type for a specific list index. This is a read operation on the `X33VDataTypeStringBean` framework object already populated in memory via `ido_rsn_cd_list`. |

## 5. Dependency Trace

| # | Caller (Screen/Batch) | Call Chain (Full Path to this Method) | Terminal (SC / CRUD / Entity) |
|---|----------------------|--------------------------------------|-------------------------------|
| 1 | Screen:KKSV0004 | KKW01031SF01DBean.typeModelData | `X33VDataTypeStringBean.typeModelData [R] ido_rsn_cd_list` |

Note: The method is part of the X33V framework's data bean interface (`X33VDataTypeBeanInterface`), so it is invoked implicitly by the X33V framework's type introspection mechanism during screen load/store cycles. The code graph analysis shows this method is called within the same class (self-referential delegation pattern).

## 6. Per-Branch Detail Blocks

**Block 1** — IF `(key == null || subkey == null)` (L506)

> Null guard: If either parameter is null, return null immediately. This prevents NPE during the dispatch logic.

| # | Type | Code |
|---|------|------|
| 1 | CHECK | `if (key == null || subkey == null)` |
| 2 | RETURN | `return null;` // Returns null for null parameters |

**Block 2** — EXEC `(separaterPoint computation)` (L510)

> Compute the position of the first "/" character in the key. Used later for the "異動理由コード" (Migration Reason Code) branch that supports indexed list access with a "/"-separated suffix.

| # | Type | Code |
|---|------|------|
| 1 | SET | `int separaterPoint = key.indexOf("/");` // Find first slash position |

**Block 3** — ELSE-IF `[key equals "SYSID"]` (L513)

> SYSID (System Identifier) branch. The key "SYSID" identifies the system ID field. Item ID: sysid.

| # | Type | Code |
|---|------|------|
| 1 | IF | `if (key.equals("SYSID"))` |

**Block 3.1** — ELSE-IF `[subkey.equalsIgnoreCase("value")]` (L514)

> For the "value" sub-key, the SYSID data value is of type String.

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // SYSID value is a String type |

**Block 3.2** — ELSE-IF `[subkey.equalsIgnoreCase("state")]` (L517)

> For the "state" sub-key, the SYSID state is also of type String. Comment: subkeyが"state"の場合、ステータスを返す。(Returns status when subkey is "state".)

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // SYSID state is a String type |

**Block 4** — ELSE-IF `[key equals "サービス契約番号"]` (L521)

> Service Contract Number (サービス契約番号 = SVC Contract No.) branch. Item ID: svc_kei_no. Represents the service contract number field on the screen.

| # | Type | Code |
|---|------|------|
| 1 | IF | `else if (key.equals("サービス契約番号"))` |

**Block 4.1** — ELSE-IF `[subkey.equalsIgnoreCase("value")]` (L522)

> The service contract number value is of type String.

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // SVC Contract No. value is String |

**Block 4.2** — ELSE-IF `[subkey.equalsIgnoreCase("state")]` (L525)

> The service contract number state is of type String. Comment: subkeyが"state"の場合、ステータスを返す。

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // SVC Contract No. state is String |

**Block 5** — ELSE-IF `[key equals "異動区分"]` (L529)

> Migration Classification (異動区分 = IDO Division/Classification) branch. Item ID: ido_div. Represents the migration type classification field.

| # | Type | Code |
|---|------|------|
| 1 | IF | `else if (key.equals("異動区分"))` |

**Block 5.1** — ELSE-IF `[subkey.equalsIgnoreCase("value")]` (L530)

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // IDO Div. value is String |

**Block 5.2** — ELSE-IF `[subkey.equalsIgnoreCase("state")]` (L533)

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // IDO Div. state is String |

**Block 6** — ELSE-IF `[key equals "異動理由コード"]` (L537)

> Migration Reason Code (異動理由コード = IDO Reason Code) branch. Item ID: ido_rsn_cd. This is the most complex branch — it handles indexed list access where the key may contain a "/"-separated suffix indicating a specific list index, an asterisk (`*`) for list size, or just the base field name. The `ido_rsn_cd_list` is an `X33VDataTypeList` containing `X33VDataTypeStringBean` elements, each representing a single migration reason code entry.

| # | Type | Code |
|---|------|------|
| 1 | IF | `else if (key.equals("異動理由コード"))` |

**Block 6.1** — SET `[substring from slash position]` (L540)

> Extract the portion of the key after the first "/" character. For example, "異動理由コード/0" becomes "0", "異動理由コード/*" becomes "*". Comment: keyの次の要素を取得。(Get the next element of key.)

| # | Type | Code |
|---|------|------|
| 1 | SET | `key = key.substring(separaterPoint + 1);` // Extract part after first slash |

**Block 6.2** — IF `[key.equals("*")]` (L542)

> The asterisk indicates a request for the list size. Returns `Integer.class` to indicate the type is an integer (the count of items in the list). Comment: インデックス値の代わりに"*"が指定されていたら、リストの要素数を返す。(If "*" is specified instead of an index value, return the list element count.)

| # | Type | Code |
|---|------|------|
| 1 | CHECK | `if (key.equals("*"))` |
| 2 | RETURN | `return Integer.class;` // "*" means return list size (Integer) |

**Block 6.3** — TRY-CATCH `[Integer.parseInt]` (L546)

> Attempt to parse the remaining key portion as an integer index into the `ido_rsn_cd_list`. Comment: 次はリスト中のインデックスを見る。(Next, look at the index in the list.)

| # | Type | Code |
|---|------|------|
| 1 | TRY | `try { tmpIndexInt = Integer.valueOf(key); }` |
| 2 | CATCH | `catch (NumberFormatException e) { return null; }` // インデックス値が数値文字列でない場合はnullを返す。(If index value is not a numeric string, return null.) |
| 3 | SET | `Integer tmpIndexInt = null;` |

**Block 6.3.1** — IF `[tmpIndexInt == null]` (L554)

> If parsing succeeded but the result is null, return null. Comment: インデックス値が数値文字列でない場合は、ここでnullを返す。

| # | Type | Code |
|---|------|------|
| 1 | CHECK | `if (tmpIndexInt == null)` |
| 2 | RETURN | `return null;` |

**Block 6.4** — IF `[index bounds check]` (L559)

> Validate the extracted index is within the bounds of `ido_rsn_cd_list`. If out of bounds, return null. Comment: インデックス値がリスト個数-1を超えたら、ここでnullを返す。(If index exceeds list count minus 1, return null here.)

| # | Type | Code |
|---|------|------|
| 1 | SET | `int tmpIndex = tmpIndexInt.intValue();` |
| 2 | CHECK | `if (tmpIndex < 0 || tmpIndex >= ido_rsn_cd_list.size())` |
| 3 | RETURN | `return null;` // Index out of bounds |

**Block 6.5** — CALL `[delegate to list element]` (L562)

> Get the list element at the validated index (cast to `X33VDataTypeStringBean`) and delegate the `typeModelData(subkey)` call to it. Comment: キャスト部分は、項目定義型にあわせてX33VDataTypeStringBean, X33VDataTypeLongBean, X33VDataTypeBooleanBeanのうちの1つを指定。(The cast part specifies one of X33VDataTypeStringBean, X33VDataTypeLongBean, X33VDataTypeBooleanBean according to the field definition type.)

| # | Type | Code |
|---|------|------|
| 1 | CALL | `((X33VDataTypeStringBean)ido_rsn_cd_list.get(tmpIndex)).typeModelData(subkey);` |
| 2 | RETURN | `return delegated typeModelData(subkey);` // Delegate to list item's typeModelData |

**Block 7** — ELSE-IF `[key equals "異動理由メモ"]` (L566)

> Migration Reason Memo (異動理由メモ = IDO Reason Memo) branch. Item ID: ido_rsn_memo. A text memo field associated with a migration reason.

| # | Type | Code |
|---|------|------|
| 1 | IF | `else if (key.equals("異動理由メモ"))` |

**Block 7.1** — ELSE-IF `[subkey.equalsIgnoreCase("value")]` (L567)

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // IDO Reason Memo value is String |

**Block 7.2** — ELSE-IF `[subkey.equalsIgnoreCase("state")]` (L570)

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // IDO Reason Memo state is String |

**Block 8** — ELSE-IF `[key equals "申込番号"]` (L574)

> Application Number (申込番号 = MSKM No.) branch. Item ID: mskm_no. Identifies the application/order number.

| # | Type | Code |
|---|------|------|
| 1 | IF | `else if (key.equals("申込番号"))` |

**Block 8.1** — ELSE-IF `[subkey.equalsIgnoreCase("value")]` (L575)

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // Application No. value is String |

**Block 8.2** — ELSE-IF `[subkey.equalsIgnoreCase("state")]` (L578)

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // Application No. state is String |

**Block 9** — ELSE-IF `[key equals "申込明細番号"]` (L582)

> Application Detail Number (申込明細番号 = MSKM Detail No.) branch. Item ID: mskm_dtl_no. Identifies the detail line number within an application.

| # | Type | Code |
|---|------|------|
| 1 | IF | `else if (key.equals("申込明細番号"))` |

**Block 9.1** — ELSE-IF `[subkey.equalsIgnoreCase("value")]` (L583)

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // Application Detail No. value is String |

**Block 9.2** — ELSE-IF `[subkey.equalsIgnoreCase("state")]` (L586)

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return String.class;` // Application Detail No. state is String |

**Block 10** — ELSE `[no matching property]` (L590)

> No matching property found. Comment: 条件に合致するプロパティが存在しない場合は、nullを返す。(If no property matches the condition, return null.)

| # | Type | Code |
|---|------|------|
| 1 | RETURN | `return null;` // No matching property defined for this key |

## 7. Glossary

| Term | Type | Business Meaning |
|------|------|------------------|
| `sysid` | Field | System Identifier — internal system tracking ID for the record. Stored as `sysid_value`, `sysid_update`, `sysid_state` fields. |
| `svc_kei_no` | Field | Service Contract Number — the contract number identifying a service agreement. Stored as `svc_kei_no_value`, `svc_kei_no_update`, `svc_kei_no_state` fields. |
| `ido_div` | Field | Migration Classification — classifies the type of migration/change being performed. Stored as `ido_div_value`, `ido_div_update`, `ido_div_state` fields. |
| `ido_rsn_cd` | Field | Migration Reason Code — the reason code for a migration/change event. Stored as a list (`ido_rsn_cd_list`) of `X33VDataTypeStringBean` entries, each containing a single reason code. |
| `ido_rsn_memo` | Field | Migration Reason Memo — free-text memo associated with a migration reason code. Stored as `ido_rsn_memo_value`, `ido_rsn_memo_update`, `ido_rsn_memo_state` fields. |
| `mskm_no` | Field | Application Number — the order/application identifier. Stored as `mskm_no_value`, `mskm_no_update`, `mskm_no_state` fields. |
| `mskm_dtl_no` | Field | Application Detail Number — the detail line identifier within an application. Stored as `mskm_dtl_no_value`, `mskm_dtl_no_update`, `mskm_dtl_no_state` fields. |
| DBean | Acronym | Data Bean — a Java bean that holds screen data and implements the X33V data type interface for framework integration. |
| X33V | Acronym | Fujitsu Futurity X33V — a web application framework used for building enterprise screen-based applications. The `typeModelData` method is part of the `X33VDataTypeBeanInterface` contract. |
| X33VDataTypeList | Type | A framework-provided list collection that holds typed data bean elements. Used here to store the migration reason code list. |
| X33VDataTypeStringBean | Type | A framework data bean representing a String-typed data type. Each element in `ido_rsn_cd_list` is this type, supporting `typeModelData`, `loadModelData`, and `storeModelData` operations. |
| X33VDataTypeBeanInterface | Interface | The X33V framework interface implemented by this class, requiring `typeModelData` to resolve field types. |
| X33VListedBeanInterface | Interface | The X33V framework interface for beans that contain list-based data (e.g., `ido_rsn_cd_list`). |
| SYSID | Japanese/English | System Identifier — the system-level unique identifier for a record. |
| サービス契約番号 | Japanese | Service Contract Number — the identifier for a telecom service contract. |
| 異動区分 | Japanese | Migration Classification — categorizes the type of service migration/change (e.g., transfer, cancellation, modification). |
| 異動理由コード | Japanese | Migration Reason Code — the coded reason for a migration event. Stored as a list to support multiple entries. |
| 異動理由メモ | Japanese | Migration Reason Memo — additional free-text details for a migration reason. |
| 申込番号 | Japanese | Application Number — the unique identifier for a service application/order. |
| 申込明細番号 | Japanese | Application Detail Number — the line-item identifier within an application. |
| value | Sub-key | The data accessor — retrieves the actual stored value of a field. |
| state | Sub-key | The state accessor — retrieves the UI state metadata of a field (e.g., display mode, validity). |
| * | Sub-key (special) | A special sub-key for the Migration Reason Code field meaning "list size" — returns `Integer.class`. |
