> For AI agents: the complete documentation index is available at /resource/ucidm/docs/on-premise/dev/llms.txt, the full documentation bundle is available at /resource/ucidm/docs/on-premise/dev/llms-full.txt.

# ユーザープロファイル画面（管理者用） \{#user-profile-admin}

ユーザープロファイル画面（管理者用）では、主に以下の画面を提供しています。

## 管理者用画面へのアクセス \{#accessing-admin-ui}

https\://\<ホスト名>/ui/admin/login にアクセスします。

ユーザープロファイル画面へのアクセス URL は環境によって異なります。

## ログイン画面 \{#login-page}

ユーザー名/パスワードを入力し、「ログイン」ボタンを押下してログインを行います。パスワードリセットについては、[ID 連携管理画面](/resource/ucidm/docs/on-premise/dev/administration/admin-ui/index.md)で行います。

## ログイン後トップ画面 \{#post-login-top}

以下の画面に遷移するボタンが表示されます。

- ユーザーとグループ
  - ユーザー管理
  - グループ管理
- 運用
  - CSV 一括取込
  - 履歴
- 各種設定
  - 各種設定画面に遷移し、以下の設定画面を開きます。
    - 属性定義
    - ロール設定
    - パスワードポリシー設定
    - デザイン設定
    - 設定の入出力

画面左側にも同じメニューが表示されます。
メニューの最下部の「バージョン情報」を押下すると、UCIDM のバージョンを確認する画面に遷移します。

画面右上にユーザー名があり、このユーザー名を押下することで、以下の各種メニューが表示されます。

- アカウント情報
  - 押下することで、ID 連携管理画面のアカウント情報変更画面に遷移します。
- パスワード変更
  - 押下することで、ID 連携管理画面のパスワード変更画面に遷移します。
- ログアウト
  - このリンクをクリックすることで、ログアウトが行われます。

## ユーザー管理画面 \{#user-management}

- ユーザーの管理が行えます。
- キーワード検索では、検索ボックスに検索ワードを入れ検索ボタンを押下すると、属性定義で「検索の対象にする」をオンにした属性に対して検索ワードを含むユーザーを検索し、画面上に表示します。
- 詳細検索では、属性定義で「検索の対象にする」をオンにした属性の項目が表示されます。オプションを設定している属性に対してはチェックボックスが表示されます。検索ボタンを押下することで絞り込み検索が行えます。「その他」の検索では、オプション値以外で検索を行いますが、値が設定されていないユーザーを検索することはできません。
- 検索結果の表示列は、属性定義で「一覧に表示する」をオンにした属性の項目がデフォルトになります。
- 「CSV エクスポート」ボタンを押下することで、検索条件に一致するユーザーの一覧を CSV ファイルとしてエクスポートできます。
  属性定義で定義している属性が使用されます。
  「管理画面で編集不可にする」をオンにした属性は対象外となります。
- 「表示列」を押すことで表示項目の一覧が表示されます。チェックボックスを操作することで画面上に表示する項目の on/off を切り替えられます。
- 「有効状態」の列に、ユーザーが有効か無効かが表示されます。
- ユーザー名を押下すると、対象ユーザーの詳細画面に遷移します。
- 各行に、削除ボタンとユーザーのステータス切り替えボタンとパスワード変更ボタンが表示されます。
- 行の左端のチェックボックスで複数のユーザーを選ぶと、選んだユーザーをまとめて有効化・無効化・削除できます。
- 登録ボタンを押下すると、ユーザー登録画面に遷移します。
- ID 連携管理画面のURLが設定されている場合、「ログインロックアウト」ボタンが表示されます。こちらのボタンを押下することで、ID 連携管理画面のログインロックアウトのページが表示されます。
- 「一時パスワードを発行したユーザー」ボタンを押下すると、一時パスワードを発行したユーザー画面に遷移します。

### ユーザー詳細 \{#user-details}

- ユーザーの属性を更新します。
- 画面上部のタブで「属性設定」「所属グループ設定」「[認証デバイスの管理](#auth-device-settings)」を切り替えます。
- 画面上部の「パスワードの変更」ボタンを押下すると、[ユーザーパスワード変更](#user-password-change) 画面に遷移します。
- 画面上部の削除ボタンからユーザーの削除が行えます。
- 画面上部の無効化ボタンからユーザーの無効化が行えます。またすでに無効状態のユーザーの場合は有効化ボタンになり、ユーザーの有効化が行えます。無効になったユーザーはユーザープロファイル画面にログインできなくなります。
- 編集したい属性の値を書き換えて更新ボタンを押すと、ユーザーの属性を更新出来ます。
- テキストボックス下部のプラスボタンを押すと、テキストボックスが 1 つ追加されます。また、テキストボックス右側のマイナスボタンを押すと、テキストボックスが 1 つ削除されます。
- 「属性追加」を押すと編集属性を追加出来ます。属性定義に存在する属性が不足している場合は、ドロップダウンが表示されます。不足していない場合は自由入力フォームのみになります。
- 属性名左側のゴミ箱ボタンを押すと編集属性を削除出来ます。
- テキストボックス内が空の場合は更新時には値なしとして無視されます。
- 値を入力する欄の形は、属性定義の [入力の形](#attribute-type) で決まります。
- 所属グループ設定タブのテーブルにて、現在所属しているグループの一覧を確認できます。所属グループ名を入力すると検索を行えます。
- 所属グループのテーブル上部の「所属グループ登録」から、任意のグループへの所属処理が行えます。所属したいグループにチェックを入れて「所属グループ登録」ボタンを押してください。
- 所属解除したいグループにチェックを入れて「所属グループ解除」ボタンを押してください。
- 「編集」ボタンを押下すると、選択した所属グループのグループ詳細画面に遷移します（システム設定の groupMemberValueFormat が uniqueAttribute の場合）。

#### 表示値と格納値 \{#view-values}

- 属性定義のスクリプトの view 関数が値を返した属性は、その値 ([表示値](/resource/ucidm/docs/on-premise/dev/glossary/index.md#view-value)) と、LDAP に格納されている値 (格納値) を合わせて表示します。
- 表示値は更新の対象になりません。
- 表示値が `3099-12-31` または `3099-12-31T23:59:59Z` のときは「無期限」と表示します。
  `BUILTIN.AD.fromAccountExpiresAsDate` と `BUILTIN.AD.fromAccountExpires` が無期限のときに返す値です。

#### 表示属性と更新属性の行 \{#paired-attribute-row}

- 属性定義で [スクリプトを動かす属性をこの行で編集する](#edit-depends) をオンにした属性 (表示属性) は、その行で「スクリプトを動かす属性」に選んだ属性 (更新属性) を編集します。
  - 行の上段に表示属性の「現在の値」、下段に更新属性ごとの入力欄を表示します。
  - 更新属性の行は単独では表示しません。
- 表示属性は編集できません。
  表示属性の値は、更新属性の値からスクリプトが書きます。
- 入力欄の形・必須・複数値・選択肢と、編集できるかどうかは、それぞれの更新属性の設定に従います。
- 下段の「属性削除」は、その更新属性だけを削除します。
- 「入力切替」を押した状態では組にせず、それぞれの属性を別の行で表示します。

### ユーザーパスワード変更 \{#user-password-change}

- ユーザーのパスワードを管理者が設定します。
- ユーザー一覧の各行か、ユーザー詳細の「パスワードの変更」ボタンから開きます。
- このときのパスワードルールとして、パスワードの長さと禁止文字が適用されます。
- ポリシーを満たすパスワードを入力し、更新ボタンを押すことでパスワードを更新出来ます。
- AD に存在するユーザーのパスワード変更の場合、LDAPS 接続である必要があります。
- パスワードを変更した場合、パスワード確認の画面表示になります。再表示できないので、画面を閉じずに必要な操作を行う必要があります。
- ランダムパスワードを使用する場合、パスワードポリシーを満たすパスワードが生成され、手入力のパスワードは無効になります。
- 「次回ログイン時にパスワード変更を要求する」をオンにすることで、一時パスワードが発行されます。発行したかどうかは一時パスワードを発行したユーザー画面で確認します。パスワードリセットが行われるまで一般ユーザーのステータスは無効のままになります。
- 連携元が OpenLDAP で一時パスワードを発行する場合、ucidmUserEnabled を「有効・無効の値が入る属性」としたときの OpenLDAP 側の設定例は以下になります。

```
access to filter="(ucidmUserEnabled=False)" attrs=userPassword
        by * none

access to attrs=userPassword
        by anonymous auth
        by self =wx
        by * none
```

### ユーザー登録 \{#user-registration}

- ユーザーの登録が行えます。ユーザー登録、所属グループ設定、パスワード確認の順番で画面が切り替わります。
- 値のテキストボックスに設定する値を入力し、「登録して次へ」ボタンを押して登録してください。
- マルチバリューのテキストボックス下部のプラスボタンを押すと、テキストボックスが 1 つ追加されます。また、テキストボックス右側のマイナスボタンを押すと、テキストボックスが 1 つ削除されます。
- 「属性追加」を押すと属性を追加出来ます。
- テキストボックス内が空の場合、登録時にはその属性は無視されます。また、更新時には値なしとして無視されます。
- 属性定義に [登録先 OU](#target-ou) を定義している場合、ユーザーを登録する OU をプルダウンで選べます。選ばない場合は、ユーザーの検索ベースの直下に登録します。
- すべての属性で複数値を設定出来ますが、サーバー側で `SINGLE-VALUE` 制約をかけていた場合、登録に失敗する場合があります。
- 任意の属性名の属性を設定できますが、サーバー側で未定義の属性は登録に失敗する場合があります。
- パスワード属性（ `userPassword` ）は常にデフォルトのパスワードポリシーでチェックが行われます。このときのルールとして、パスワードの長さと禁止文字のみ適用されます。ポリシーを満たさない場合は登録ボタンが無効化されます。
- パスワードを含めて登録した場合、パスワード確認の画面表示になります。再表示できないので、画面を閉じずに必要な操作を行う必要があります。
- ランダムパスワードを使用する場合、パスワードポリシーを満たすパスワードが生成され、手入力のパスワードは無効になります。
- [入力の形](#attribute-type) が「userAccountControl（AD のフラグ）」の属性があるときは、アカウントを有効にして登録するとランダムパスワードを必ず使用します。
  - AD はパスワードポリシーを満たさない有効なアカウントの作成を拒否し、どのルールに反したかを返さないためです。
    UCIDM の [パスワードポリシー](#password-policy-settings) を AD のものと合わせてください。
  - 任意のパスワードで登録するときは、無効にして登録してからパスワードを変更するか、[CSV 一括取込](#csv) を使用してください。
- [入力の形](#attribute-type) と [表示属性と更新属性の行](#paired-attribute-row) の扱いは、ユーザー詳細と同じです。
  表示属性には入力欄がなく、表示属性の値は登録時にスクリプトの add 関数が書きます。
- 所属グループ設定では、グループ一覧から追加・解除を行います。
- uidNumber 属性（属性定義で「複数の値を許可する」がオフ）では「自動割当」ボタンを押すことで割り当て可能な番号が自動でセットされます。
  - ユーザー更新などで割り当て可能な番号を再取得したい場合は「最新情報取得後に割当」ボタンを使用します。

### 認証デバイスの管理 \{#auth-device-settings}

- ユーザー詳細の「認証デバイスの管理」タブに、TOTP と Passkey の設定が表示されます。
- 認証デバイスの管理では、認証デバイスの削除のみ行えます。
- TOTP の設定では、デバイス情報が見つかる場合は現在のデバイス情報が表示されます（リカバリーコードは表示されません）。
- Passkey の設定では、デバイス情報が見つかる場合は現在のデバイス情報の一覧が表示されます。

### 一時パスワードを発行したユーザー画面 \{#temporary-password-users}

- 一時パスワードを発行したユーザーの一覧が表示されます。
- 「無効にする」ボタンを押下することで、一時パスワードを無効にできます。
- 一般ユーザーが一時パスワードから新しいパスワードに変更した場合、表示されません。

## グループ管理画面 \{#group-management}

- グループの管理が行えます。
- キーワード検索では、検索ボックスに検索ワードを入れ検索ボタンを押下すると、属性定義で「検索の対象にする」をオンにした属性に対して検索ワードを含むグループを検索し、画面上に表示します。
- 詳細検索では、属性定義で「検索の対象にする」をオンにした属性の項目が表示されます。オプションを設定している属性に対してはチェックボックスが表示されます。検索ボタンを押下することで絞り込み検索が行えます。「その他」の検索では、オプション値以外で検索を行いますが、値が設定されていないグループを検索することはできません。
- 検索結果の表示列は、属性定義で「一覧に表示する」をオンにした属性の項目がデフォルトになります。
- 「CSV エクスポート」ボタンを押下することで、検索条件に一致するグループの一覧を CSV ファイルとしてエクスポートできます。
  属性定義で定義している属性が使用されます。
  「管理画面で編集不可にする」をオンにした属性は対象外となります。
- 「表示列」を押すことで表示項目の一覧が表示されます。チェックボックスを操作することで画面上に表示する項目の on/off を切り替えられます。
- グループ名を押下すると、対象グループの詳細画面に遷移します。
- 各行に削除ボタンが表示されます。
- 行の左端のチェックボックスで複数のグループを選ぶと、まとめて削除できます。
- 「メンバーシップルール」ボタンを押下すると、メンバーシップルールを持つグループの一覧が表示されます。
- 登録ボタンを押下すると、グループ登録画面に遷移します。

### グループ詳細 \{#group-details}

- グループの属性を更新します。
- 画面上部のタブで「属性設定」「メンバー設定」「[メンバーシップルール](#membership-settings)」を切り替えます。
- 画面上部の削除ボタンからグループの削除が行えます。
- 編集したい属性の値を書き換えて更新ボタンを押すと、グループの属性を更新出来ます。
- テキストボックス下部のプラスボタンを押すと、テキストボックスが 1 つ追加されます。また、テキストボックス右側のマイナスボタンを押すと、テキストボックスが 1 つ削除されます。
- 「属性追加」を押すと編集属性を追加出来ます。属性定義に存在する属性が不足している場合は、ドロップダウンが表示されます。不足していない場合は自由入力フォームのみになります。
- 属性名左側のゴミ箱ボタンを押すと編集属性を削除出来ます。
- テキストボックス内が空の場合は更新時には値なしとして無視されます。
- [表示値と格納値](#view-values)・[表示属性と更新属性の行](#paired-attribute-row)・[入力の形](#attribute-type) の扱いは、ユーザー詳細と同じです。
  グループ登録も、ユーザー登録と同じです。
- メンバー設定タブのテーブルにて、現在所属しているメンバーの一覧を確認できます。メンバー名を入力すると検索を行えます。
- メンバーのテーブル上部の「メンバー登録」から、任意のメンバーの登録処理が行えます。登録したいメンバーにチェックを入れて「メンバー登録」ボタンを押してください。
- 削除したいメンバーにチェックを入れて「削除」ボタンを押してください。
- 「編集」ボタンを押下すると、選択したメンバーのユーザー詳細画面が開きます（システム設定の groupMemberValueFormat が uniqueAttribute の場合）。

### グループ登録 \{#group-registration}

- グループの登録が行えます。グループ登録、メンバー設定の順番で画面が切り替わります。
- 値のテキストボックスに設定する値を入力し、「登録して次へ」ボタンを押して登録してください。
- マルチバリューのテキストボックス下部のプラスボタンを押すと、テキストボックスが 1 つ追加されます。また、テキストボックス右側のマイナスボタンを押すと、テキストボックスが 1 つ削除されます。
- 「属性追加」を押すと属性を追加出来ます。
- テキストボックス内が空の場合、登録時にはその属性は無視されます。また、更新時には値なしとして無視されます。
- 属性定義に [登録先 OU](#target-ou) を定義している場合、グループを登録する OU をプルダウンで選べます。選ばない場合は、グループの検索ベースの直下に登録します。
- すべての属性で複数値を設定出来ますが、サーバー側で `SINGLE-VALUE` 制約をかけていた場合、登録に失敗する場合があります。
- 任意の属性名の属性を設定できますが、サーバー側で未定義の属性は登録に失敗する場合があります。
- 画面下部の所属メンバーのテーブルにて、現在所属しているメンバーの一覧を確認できます。
- メンバー名を選択すると、選択したメンバーのユーザー詳細画面に遷移します。
- メンバー設定では、ユーザー一覧から登録・削除を行います。
- gidNumber 属性（属性定義で「複数の値を許可する」がオフ）では「自動割当」ボタンを押すことで割り当て可能な番号が自動でセットされます。
  - グループ更新などで割り当て可能な番号を再取得したい場合は「最新情報取得後に割当」ボタンを使用します。

## CSV 一括取込画面 \{#csv}

- CSV 一括取込画面で、CSV 一括処理を行えます。画面上部のタブで「即時取込」と「予約取込」を切り替えます。
  タブの右の「CSV 取込履歴」ボタンから、[CSV 取込履歴](#history-list) に遷移できます。
  - 取り込む CSV ファイルの形式・カラム名・値の書き方・操作種別ごとの仕様とサンプルデータについては [取り込み CSV の仕様](/resource/ucidm/docs/on-premise/dev/administration/ucidm-ui/csv.md) を参照してください。
- 即時取込タブでは、その場で CSV 一括処理を実行します。
  - CSV ファイル、リソースタイプ、操作種別を選択後、CSV 一括取込ボタンを押下することで、CSV データの内容が送信されます。
  - CSV ファイルを選ぶと、CSV の内容と総件数が表示されます。
- 予約取込タブでは、CSV 一括取込を指定した日時に実行する予約の登録・更新・削除が行えます。
  - 「取込の予約」では以下の値を指定します。
    - スケジュール ID
      - 他と被らない文字列を指定してください。
    - 開始時刻
      - CSV 一括取込を実行したい日時を指定してください。指定日時に一度のみ実行されます。
    - リソースタイプ、操作種別
      - 即時取込と同様に、取り込む対象と操作を選択します。
    - 説明
      - スケジュールに関する説明を任意に記述できます。
    - CSV ファイル
      - 取り込む CSV ファイルを選択します。ファイルの内容はスケジュール登録時に保存され、指定日時に取り込まれます。
  - 「予約中の取込一覧」に、登録済みの予約が一覧表示されます。
    CSV ファイル・リソースタイプ・操作種別は変更できないため、変更する場合は削除して登録し直してください。
  - 予約した取込の結果は、即時取込と同様に CSV 取込履歴で確認できます。
- CSV の一括処理が完了した後、[CSV 取込履歴](#history-list) でその結果を確認できます。
  - 失敗のレコードがある場合、「エラーファイル」を押下することで、一括処理に失敗したレコードだけが抽出された CSV ファイルをダウンロードできます。
  - 「詳細」を押下することで、CSV ID に対応する一括処理の履歴の詳細を確認できます。
  - 「パスワード出力」ボタンを押下することで、発行したパスワードのエクスポートの画面表示になります。再表示できないので、画面を閉じずに CSV エクスポートや PDF エクスポートを行う必要があります。

## 履歴画面 \{#history-list}

- 画面上部のタブで「操作履歴」と「CSV 取込履歴」を切り替えます。
  CSV 取込履歴については [CSV 一括取込画面](#csv) を参照してください。
- 操作履歴では、ログイン関係の認証履歴と LDAP の操作履歴とID 連携履歴の確認が行えます。
- 履歴の検索が行えます。
- エクスポート機能を使うことで特定の期間の全てのログを１つのファイルにまとめられます。

## ロール設定画面 \{#role-settings}

- 画面上部の「割り当て方」で、一般ユーザーにロールをどう割り当てるかを選び、「更新」ボタンを押下して保存します。
  - 「全員に標準ロールを適用する」では、すべての一般ユーザーに UCIDM のシステムロール `ldap-user`（標準ロール）が使用されます。
  - 「ユーザーごとに割り当てる」では、カスタムロールが使用されます。
    - 一般ユーザーがログインするときにカスタムロールを使うための属性名（カスタムロール属性名）やスクリプトを設定します。
    - 「カスタムロール属性のスクリプトを利用する」がオンになっている場合、カスタムロールを取得するときにスクリプトが呼び出されるようになります。オフになっている場合は、スクリプトは呼び出されません。
    - 「関数呼び出し確認」ボタンを押下することで、指定した関数の動作を確認することができます。
    - どのロールにも一致しないユーザーはログインできません。
  - 割り当て方を選び直してから保存するまでは「未保存」と表示され、ロール一覧は表示されません。
- ロール一覧には、「全員に標準ロールを適用する」では標準ロールだけが、「ユーザーごとに割り当てる」ではカスタムロールが表示されます。
- 設定したいロールの「編集」を押下することで、その詳細画面に遷移します。
- 「ロール登録」では、ロール名とそのロールの説明を入力することで、カスタムロールを登録します。
  「ユーザーごとに割り当てる」のときに表示されます。
  既存のロールから複製して登録することもできます。
- システム設定でカスタムロールを無効にしている環境（`role` セクションの `ldapAuthCustomRoleEnabled` が `false`）では、「割り当て方」は表示されず、ロール一覧には標準ロールだけが表示されます。カスタムロールの登録や編集もできません。
  - この場合、「割り当て方」の設定にかかわらず、すべての一般ユーザーに標準ロールが使用されます。
  - 「割り当て方」の設定は保存されたまま残るので、`ldapAuthCustomRoleEnabled` を `true` に戻すと、それまでの割り当て方がそのまま有効になります。

### カスタムロール有効設定のスクリプト例 \{#custom-role-enable-script}

- **ユーザーの有効・無効のスクリプトとは仕様が異なります。**
- カスタムロール名を返す `getRoleName()` という名前で関数を設定します。
- 必ず関数の戻り値を返す必要があります。
  - 関数の戻り値として null または undefined を返した場合は、ロールが割り当てられず、ログインできません。

例えば、カスタムロール属性の値の 2 番目の要素をカスタムロール名とするときは次のようになります。

```javascript
function getRoleName(values) {
  // カスタムロールを取得するときにこの関数が呼ばれる
  // 第1引数の values にはカスタムロール属性の値が文字列の配列として渡される
  // 関数の戻り値はカスタムロールの名前を表す string 値を返す
  return values[1];
}
```

### ロール設定詳細画面 \{#role-settings-details}

- 「使える画面」では、ユーザーのホーム画面で表示する画面を設定します。カスタムロールを使用することで、一部のユーザーには表示しないようにすることが可能になります。
- 「扱える項目」の属性名は、ユーザーの属性定義がセットされます。使用しない場合は、全ての権限をオフにします。属性を追加したい場合は、ユーザーの属性定義で属性を追加する必要があります。
- 属性に対して、「表示」、「編集」、「削除」を設定し、「更新」ボタンを押下することで、更新できます。
- 表示権限が与えられていない属性は、登録情報の編集画面に表示されません。
- 表示権限は、一般ユーザーは更新できず、表示のみになります。
- 編集権限は、一般ユーザーが変更できるようになります。
- 削除権限は、一般ユーザーが何も入力しない状態で更新を行うと、その属性が削除されます。
- 「編集」をオンにすると、自動で「表示」がオンになります。
- 「削除」をオンにすると、自動で「編集」がオンになります。
- 通知設定は、一般ユーザーのホーム画面にメッセージを表示する設定を行います。
  - 属性の行の「通知」を押下して設定します。
  - 条件は「値が未入力のとき」「値が次と一致するとき」「値が次と一致しないとき」から選びます。
  - 日本語と英語のメッセージを設定します。一般ユーザーの言語のメッセージが表示され、空の言語では表示されません。
  - 多値属性の場合は 1 つでも条件を満たす値が含まれているとメッセージが表示されます。
  - 属性の値を入力すると、その値のときに表示されるメッセージをプレビューで確認できます。

## 属性定義 \{#management-attributes-setting}

属性定義とは、主にシステム管理者が LDAP サーバーに対してユーザーやグループエントリーを管理するとき、エントリーの属性に対してセットする値の並び替え・入力補助・バリデーション・実行時における動的な値の生成などのために使います。

ここでスクリプトは [初期値](#preset-setting) とは用途が異なります。他属性の値の変更に連動して値をセットするなど、より柔軟な要件に対応できます。

- 主な用途
  - 画面上で任意の値を設定したい
  - 他属性の値を参照して動的に値をセットしたい
  - 他属性の値が更新されたときに連動して自動更新したい
- 実行タイミング
  - エントリーに値が未設定のときのみ実行される
  - 登録時 (初期値で値がセットされるときは実行されない)
  - 更新時
- 設定値
  - 他属性を参照して動的に値を生成

### 属性定義画面 \{#attributes-settings-page}

- 画面上部のタブで「ユーザー」と「グループ」を切り替えます。
- 定義している属性の一覧が表示されます。属性名を押下することで、その詳細画面に遷移します。
- 「検索」から、属性名・表示名と、必須・複数値・選択肢・入力規則・初期値・スクリプトの有無で絞り込めます。
- 画面上部のボタンから、次の操作が行えます。
  - 「ユーザーの有効日・無効日・削除日」（グループでは「グループの削除日」）では、[ライフサイクル設定](#lifecycle-settings) を行います。
  - 「有効・無効の判定」（ユーザーのみ）では、[ユーザーの有効・無効](#user-status-settings) の画面に遷移します。
  - 「並び順の変更」では、属性の並び順を変更します。
  - 「登録先 OU を追加」では、[登録先 OU](#target-ou) を追加します。登録先 OU が未定義のときだけ表示されます。
  - 「属性の追加」では、新しく属性を定義します。
- 属性を削除すると、その属性の入力規則・選択肢・スクリプト・初期値の設定も一緒に削除されます。LDAP に登録済みのユーザーの値は消えません。
- 属性の一覧の下に、[画面に出さない初期値](#hidden-preset-settings) が表示されます。

### 属性定義詳細画面 \{#attributes-settings-details}

- 属性に対して以下の設定が可能です。
  - 表示名
  - 注意事項
    - 注意事項においては、HTML 形式での記述が可能となります。
  - 必須にする
  - 複数の値を許可する
  - 検索の対象にする
  - 一覧に表示する
  - 管理画面で編集不可にする
    - この設定をオンにした場合、管理者用画面では対応する属性値の参照のみが許可されます。属性値を更新することはできなくなります。
  - 入力の形
  - 選択肢
  - 入力規則
  - 初期値
  - スクリプト
    - スクリプトを動かす属性をこの行で編集する
- 選択肢・入力規則・初期値・スクリプトは、「〜を設定」ボタンを押下して設定します。「設定を外す」で設定を消します。
- 各設定の下に、その設定がどこで効くかが表示されます。
- 一覧に表示する設定は、ユーザーとグループの検索結果の表示項目として使用されます。
- 検索の対象にする設定は、ユーザーとグループの検索時に使用する属性の対象になります。
- 必須にする設定は、必須属性になります。対象属性が入力されていないと更新できません。
- 複数の値を許可する設定は、対象属性に対して複数の値を入力できるようになります。
- 表示名と注意事項については、日本語と英語を両方設定するか、両方とも空にする必要があります。選択肢の表示名について設定されていないものは値がそのまま表示されます。
- 注意事項に HTML を記述した場合、スクリプトなど画面の動作に影響する要素は取り除いて表示します。
- 入力規則を設定した場合、一般ユーザーの登録情報の編集画面にて、入力規則で設定した内容により更新の可否が判断されます。
  - 入力規則の値には正規表現を記述できます。
  - 入力された値が構文エラーになる場合には本設定画面にてエラーメッセージが表示され、更新ボタンが押せなくなります。
- 属性値についてスクリプトを設定できます。
  - 「スクリプトを動かす属性」とスクリプトを入力します。
  - スクリプトを書いたときは、「スクリプトを動かす属性」を 1 つ以上選びます。
    選ばないとスクリプトは view 関数も含めて実行されないため、更新ボタンが押せなくなります。
  - リクエストデータに「スクリプトを動かす属性」が存在するときのみ、スクリプトが実行されます。
    - 「スクリプトを動かす属性」の値が変更されるときに連動して別属性の値を変更したいときに使います。
    - エントリ登録時は「スクリプトを動かす属性」がすべてリクエストデータに存在するときに実行されます。
    - エントリ更新時は「スクリプトを動かす属性」のうち 1 つでもリクエストデータに存在すれば実行されます。
  - スクリプトはエントリ登録時に add 関数、エントリ更新時に modify 関数、エントリ取得時に view 関数が呼び出されます。
  - view 関数は「スクリプトを動かす属性」がリクエストデータにあるかどうかに関係なく、エントリーを取得するたびに実行されます。
    - 格納されている値をそのまま画面に出すと読みにくい属性を、表示用の値へ変換するために使います。
    - 変換した値は LDAP エントリーに書き戻しません。API のレスポンスでは viewAttributes に入り、格納されている値は attributes に残ります。
    - ユーザー詳細・グループ詳細・登録情報の編集では、変換した値を [表示値](#view-values) として表示します。
  - 「関数呼び出し確認」ボタンを押下することで、指定した関数の動作を確認することができます。
  - 入力されたスクリプトが構文エラーになる場合には本設定画面にてエラーメッセージが表示され、更新ボタンが押せなくなります。

#### 入力の形 \{#attribute-type}

[入力の形](/resource/ucidm/docs/on-premise/dev/glossary/index.md#attribute-type) は、ユーザー詳細・グループ詳細・ユーザー登録・グループ登録・登録情報の編集で、属性の値を入力する欄の形を選ぶ設定です。

| 入力の形                        | 入力欄                          | 書き込む値                            |
| :-------------------------- | :--------------------------- | :------------------------------- |
| 文字                          | 1 行の文字の入力欄 (入力中だけ折り返して全体を表示) | 入力した文字                           |
| 複数行の文字                      | 常に折り返して表示する複数行の入力欄           | 入力した文字 (改行を含む)                   |
| 数字                          | 数字の入力欄                       | 入力した数字                           |
| 日付                          | 時刻なしのカレンダー                   | `20270401` の形式の日付                |
| 日時                          | 日時のカレンダー                     | 一般化時刻 (UTC。例: `20270331150000Z`) |
| 日付（無期限を選択可能）                | 「無期限」と「日付を指定」のラジオボタンとカレンダー   | 無期限なら `0`、日付なら `20270401` の形式の日付 |
| userAccountControl（AD のフラグ） | フラグごとのチェックボックス               | フラグの値の合計 (例: `66048`)            |

- 日時は、操作している管理者のアカウントの [タイムゾーン](/resource/ucidm/docs/on-premise/dev/administration/admin-ui/index.md#create-admin-account) で入力します。
  一般ユーザーの登録情報の編集画面では、ブラウザのタイムゾーンで入力します。
- 「複数の値を許可する」をオンにした属性では、入力欄のそれぞれがこの形になります。
- 選択肢がある属性では入力の形を選べず、`string` (文字) として保存されます。
- 管理者用画面では、[ライフサイクル設定](#lifecycle-settings) に指定した属性は入力の形に関係なく日時のカレンダーで入力します。
- UCIDM API では、属性定義の attributeType に `string`・`textarea`・`number`・`date`・`datetime`・`date_with_indefinite`・`userAccountControl` のどれかで保存されます。

「userAccountControl（AD のフラグ）」は、連携元が AD のときだけ選べます。
チェックボックスとフラグの対応は次のとおりです。

| チェックボックス            | フラグ                  | 備考                                                    |
| :------------------ | :------------------- | :---------------------------------------------------- |
| 通常のアカウント            | NORMAL_ACCOUNT       | 常に設定され、変更できません                                        |
| アカウントを無効にする         | ACCOUNTDISABLE       |                                                       |
| パスワードを無期限にする        | DONT_EXPIRE_PASSWORD |                                                       |
| 対話型ログオンにはスマートカードが必要 | SMARTCARD_REQUIRED   |                                                       |
| 他のサービスへの委任を許可しない    | NOT_DELEGATED        | 「Active Directory ユーザーとコンピューター」の「アカウントは重要なので委任できない」です |
| パスワードを必須にしない        | PASSWD_NOTREQD       | 外すことだけができます                                           |

- 表にないフラグは、値にそのまま残して保存されます。
- 「アカウントを無効にする」を変更できるのは、ユーザー登録と、その属性が [ユーザーの有効・無効](#user-status-settings) の属性でないときのユーザー詳細です。
- AD から削除できない属性のため、ユーザー詳細の「属性を削除」と登録情報の編集の「クリア」は表示されません。
- ユーザー登録では有効なアカウント (`512`) から始まり、チェックボックスの値を必ず登録するため、この属性の [初期値](#preset-setting) は使われません。
  値を指定せずに登録するときは、CSV 一括取込を使うか、入力の形を「文字」にしてください。
- 立っているフラグの名前は、[スクリプトの view 関数](#user-account-control-example) で表示します。

#### スクリプトを動かす属性をこの行で編集する \{#edit-depends}

[スクリプトを動かす属性をこの行で編集する](/resource/ucidm/docs/on-premise/dev/glossary/index.md#edit-depends) は、この属性 (表示属性) の行で、「スクリプトを動かす属性」に選んだ属性 (更新属性) を編集するための設定です。
accountExpires 属性のように、別の属性の値からスクリプトで書く属性に使います。

- スクリプトの欄のチェックボックス「スクリプトを動かす属性を、この属性の行で編集する」で設定します。
- 更新属性は複数選べます。
  この属性自身、属性定義にない属性、認証デバイスの属性、登録先 OU は更新属性になりません。
- 画面での表示は [表示属性と更新属性の行](#paired-attribute-row) を参照してください。
- 更新属性がない場合や、更新属性がほかの組と重なる場合は、更新ボタンが押せなくなります。
- 表示属性の「管理画面で編集不可にする」はオフにします。
  オンのままだと、スクリプトが書いた値をサーバーが拒否し、エントリーを保存できません。
- UCIDM API では、属性定義の evaluation の editDepends (真偽値) に保存されます。
  true にするときは、depends を 1 つ以上指定します。

### 登録先 OU \{#target-ou}

- ユーザー/グループの登録画面で、エントリーを登録する OU を選ぶ欄を作ります。属性定義に `ucidmParentDN` という名前で定義します。
- 属性定義画面の「登録先 OU を追加」から追加します。
- 設定できるのは、表示名・注意事項と、選択肢として選べる OU だけです。属性の扱い・入力規則・初期値・スクリプトは使われないため、表示されません。
- 追加するときは、LDAP 上の OU のうち、そのエントリーの検索ベースの下にあるものが選択肢に入ります。使わせたくない OU は削除してください。
- 「OU を取り込み直す」を押下すると、LDAP 上の OU のうち、まだ選択肢に無いものを追加します。削除した OU や、付けた表示名はそのまま残ります。
- 検索ベースの下に無い選択肢は、登録画面に表示されません。そのような選択肢がある場合は、警告が表示されます。

### ライフサイクル設定 \{#lifecycle-settings}

- ユーザー有効日、ユーザー無効日、ユーザー削除日、グループ削除日の値が入る属性を指定します。
  - 属性定義画面の「ユーザーの有効日・無効日・削除日」（グループでは「グループの削除日」）から設定します。
  - 選択できる属性は、属性定義のユーザーとグループで定義された属性になります。
  - 属性を使用しない場合は「なし」を設定します。

### メンバーシップルール設定 \{#membership-settings}

- ユーザーの属性値に基づいて、特定のグループへの所属を自動的に割り当てるルールを設定します。
- ルールは、グループ詳細の「メンバーシップルール」タブで作成・変更・削除します。
- 有効になっているルールは常に適用される状態になっており、無効になっているルールは適用されない状態になります。
- 対象外ユーザーの設定でユーザーを指定している場合、そのルールの適用がスキップされます。
- 「同期」ボタンを押下すると、そのグループのメンバーシップの再同期が行われます。
- グループ管理画面の「メンバーシップルール」ボタンから、メンバーシップルールを持つグループの一覧を表示できます。
- スクリプトの項目では以下の関数を使用します。
  - 以下の関数がtrueを返す場合はそのメンバーシップルールのグループメンバーに追加されます。

```javascript
function isMember(dn, attr) {
  // 第1引数の dn はユーザーのDNがセットされる
  // 第2引数の attr はユーザーの属性がセットされる
  return Boolean(attr.myemployeetype && attr.myemployeetype[0] === "dev");
}
```

### スクリプトの例 \{#mapping-script-example}

- **ユーザーの有効・無効のスクリプトとは仕様が異なります。**
- エントリーに対する処理種別に対応する関数名を設定します。
  - 一部の処理種別 (たとえば更新なら modify) のスクリプトのみ定義できます。
  - 処理種別に対応する関数が定義されていない場合はスクリプトを実行しません。
- エントリーを変更するときに更新／削除のリクエストデータにセットされている属性のスクリプトは実行しません。
  - 一般ユーザーまたは管理者が指定した属性の値はそのまま使います。
- スクリプトを実行する条件は処理種別によって異なります。
  - 登録 (add) では「スクリプトを動かす属性」がすべてリクエストデータに存在するときに実行します。
  - 更新 (modify) では「スクリプトを動かす属性」のうち 1 つでもリクエストデータの更新属性または削除属性に存在すれば実行します。
    - 更新のリクエストデータには変更された属性だけが含まれるため、「スクリプトを動かす属性」を 2 つ以上設定していても一部の属性の更新で導出先の属性を計算し直せます。
  - 取得 (view) では「スクリプトを動かす属性」を参照せず、エントリーを取得できたときに必ず実行します。
    - ただし、「スクリプトを動かす属性」を 1 つも設定していない属性では、view も実行しません。
    - view の第 1 引数にはエントリー全体が渡るため、「スクリプトを動かす属性」に挙げていない属性も読めます。
    - 実行条件から外してあるのは、UCIDM を経由せずに作られて「スクリプトを動かす属性」を持たないエントリーでも、表示用の値へ変換するためです。
- modify の第 2 引数 reqUpd には、リクエストデータに含まれない「スクリプトを動かす属性」を変更前エントリーの値で補完します。
  - 「スクリプトを動かす属性」の値がリクエストデータにあるかどうかをスクリプト側で判定せずに済みます。
  - 補完した値はスクリプトへ渡すためだけに使い、LDAP エントリーの更新には含めません。
  - 削除のリクエストデータに含まれる「スクリプトを動かす属性」は補完しません。更新後に値がなくなるためです。
  - リクエストデータにも変更前エントリーにも値がない「スクリプトを動かす属性」は、キーごとセットされません。`Object.hasOwn(reqUpd, 'givenname')` で判別できます。
- 引数から渡されるオブジェクトのキー (属性名) は全て小文字に変換されます。
  - キー (属性名) に対応する値は文字列の配列になります。
- 引数のロール名 (roleName) は取得できない状況があることを考慮する必要があります。
  - ユーザーエントリー以外のエントリーを扱うときは空文字になります。
  - カスタムロールを使うときにロール属性をリクエストデータから参照できないときは空文字になります。
- 関数の戻り値は文字列の配列を返します。
  - 戻り値として空の配列を返した場合はその属性を削除します。
  - 戻り値として null または undefined を返した場合は値をセットしません。
  - view では属性の削除が起きません。空の配列と null と undefined のいずれを返しても、その属性は viewAttributes に現れません。

```javascript
function add(req, roleName) {
  // エントリーを登録するときにこの関数が呼ばれる
  // 第1引数の req にはリクエストデータの属性がセットされる
  //   参照例) req.givenname[0], req.uidnumber[0]
  // 第2引数の roleName にはユーザー登録のみ、ロール名がセットされる (それ以外は空文字)
  return ["value1", "value2"];
}

function modify(attr, reqUpd, reqDel, roleName) {
  // エントリーを更新するときにこの関数が呼ばれる
  // 第1引数の attr には変更前エントリーの属性がセットされる
  //   参照例) attr.givenname[0]
  // 第2引数の reqUpd にはリクエストデータの更新属性がセットされる
  //   リクエストデータに含まれない「スクリプトを動かす属性」は変更前エントリーの値で補完される
  //   参照例) reqUpd.uidnumber[0]
  // 第3引数の reqDel にはリクエストデータの削除属性がセットされる
  //   参照例) reqDel.description[0], Object.hasOwn(reqDel, 'displayname')
  // 第4引数の roleName にはユーザー更新のみ、ロール名がセットされる (それ以外は空文字)
  return ["value3"];
}

function passwordModify(attr, roleName) {
  // パスワードを更新するときにこの関数が呼ばれる
  // 第1引数の attr には変更前エントリーの属性がセットされる
  //   参照例) attr.givenname[0]
  // 第2引数の roleName にはユーザー登録のみ、ロール名がセットされる (それ以外は空文字)
  return ["value4"];
}

function view(attr, roleName) {
  // エントリーを取得するときにこの関数が呼ばれる
  // 第1引数の attr にはエントリーの属性がセットされる
  //   参照例) attr.accountexpires[0], Object.hasOwn(attr, 'accountexpires')
  // 第2引数の roleName にはユーザー取得のみ、ロール名がセットされる (それ以外は空文字)
  return ["value5"];
}
```

以下に実際のスクリプト設定例をいくつか記載します。

- homeDirectory 属性に対してレコード登録時に `/home/<uid>` をセットしたい場合
  - スクリプトを動かす属性：uid

```javascript
function add(req, roleName) {
  return [`/home/${req.uid[0]}`];
}
```

- mail 属性に対してレコード登録時に `<uid>@example.com` をセットしたい場合
  - スクリプトを動かす属性：uid

```javascript
function add(req, roleName) {
  return [`${req.uid[0]}@example.com`];
}
```

- displayName 属性に対してレコード登録時に `<sn> <givenName>` をセットしたい場合
  - スクリプトを動かす属性：sn, givenname

```javascript
function add(req, roleName) {
  return [`${req.sn[0]} ${req.givenname[0]}`];
}
```

- displayName 属性に対してレコード更新時に `<sn> <givenName>` をセットし直したい場合
  - スクリプトを動かす属性：sn, givenname
  - sn と givenname の一方だけを更新したときも、もう一方は変更前エントリーの値で補完されるため、更新後の両方の値を結合します。
  - sn と givenname のどちらかを削除したときや、変更前エントリーにどちらかの値がないときは、値のある属性だけをセットします。
  - 両方の値がなくなったときは空の配列を返し、displayName を削除します。

```javascript
function modify(attr, reqUpd, reqDel, roleName) {
  var SEPARATOR = ' '; // 区切り文字

  function resolve(name) {
    if (Object.hasOwn(reqUpd, name) && reqUpd[name].length > 0) {
      return reqUpd[name][0];
    }
    return '';
  }

  var sn = resolve('sn');
  var givenName = resolve('givenname');

  var joined = [sn, givenName].filter(function (v) { return v !== ''; }).join(SEPARATOR);

  return joined ? [joined] : [];
}
```

### スクリプトから使える組み込み関数 \{#script-builtin}

- スクリプトからは、UCIDM API が用意する関数と定数を `BUILTIN` 以下の名前で呼び出せます。
- 「関数呼び出し確認」ボタンからも同じ名前で呼び出せるため、設定を保存する前に変換結果を確かめられます。
- 日時を返す関数は、ログインしているアカウントの [タイムゾーン](/resource/ucidm/docs/on-premise/dev/administration/admin-ui/index.md#create-admin-account) 設定で整形します。

| 名前                                                   | 説明                                                         |
| :--------------------------------------------------- | :--------------------------------------------------------- |
| `BUILTIN.AD.toAccountExpires(value, timezone)`       | 日時または日付を AD の accountExpires 属性の値に変換します                    |
| `BUILTIN.AD.fromAccountExpires(value)`               | accountExpires 属性の値を `2026-04-01T09:00:00+09:00` の形式に変換します |
| `BUILTIN.AD.fromAccountExpiresAsDate(value)`         | accountExpires 属性の値を `2027-04-01` の形式に変換します                |
| `BUILTIN.AD.neverExpires`                            | 無期限を表す accountExpires 属性の値 (`"0"`) です                      |
| `BUILTIN.AD.fromUserAccountControl(value, computed)` | userAccountControl 属性の値を、立っているフラグの名前の配列に変換します              |

- `toAccountExpires` の第 1 引数には、RFC 4517 の一般化時刻 (`20260401000000Z`) または日付 (`20270401`) を渡します。
  - 一般化時刻では `20260401090000+0900` のような時差表記も使えます。
  - タイムゾーンを省いた一般化時刻は受け付けません。同じ入力でも、保存した環境によって指す瞬間が変わってしまうためです。
  - 日付にはタイムゾーンがないため、第 2 引数に `Asia/Tokyo` のようなタイムゾーン名を渡します。
  - 日付の書式は `20270401` だけを受け付けます。複数の書式を認めると、区切り文字の打ち間違いが別の日付として通ってしまうためです。
- `fromAccountExpires` と `fromAccountExpiresAsDate` は、無期限を表す値をそれぞれ `3099-12-31T23:59:59Z` と `3099-12-31` に変換します。
  - AD は無期限を `0` と `9223372036854775807` の 2 通りの値で表します。どちらも同じ変換結果になるため、画面では格納されている値の違いを意識せずに「無期限」と表示できます。
- `fromUserAccountControl` の第 2 引数には msDS-User-Account-Control-Computed 属性の値を渡します。
  AD は userAccountControl 属性の LOCKOUT と PASSWORD_EXPIRED を更新しないため、この 2 つは第 2 引数から求めます。
- 変換できない値を渡すと例外が発生し、そのスクリプトを実行したエントリーの登録と更新と取得が失敗します。
  - スクリプト内の try/catch で捕捉できます。

### AD のアカウント有効期限を設定するスクリプト例 \{#account-expires-example}

AD の accountExpires 属性は、1601 年 1 月 1 日 (UTC) からの 100 ナノ秒間隔の数を格納する 18 桁の整数です。
管理者が画面から直接入力できる値ではないため、有効期限を入力する属性を別に用意し、スクリプトで accountExpires 属性の値を導出します。

ここで説明するのは、UCIDM が AD のエントリーを直接管理するときの設定です。
UCIDM から AD へ [外部連携](/resource/ucidm/docs/on-premise/dev/administration/admin-ui/destination/ad.md#accountexpires-attribute) で値を配信する経路では、外部連携モジュールが同じ属性の変換を行います。

属性定義に次の 2 つの属性を登録します。

- 有効期限を入力する属性
  - 属性名は任意です。AD のスキーマを拡張できない環境では `extensionAttribute1` などの未使用の属性を充てられます。
  - 日付と `0` を書き込むため、文字列構文の属性を使います。
  - [入力の形](#attribute-type) を「日付（無期限を選択可能）」にすると、カレンダーと「無期限」で入力できます。
  - スクリプトは不要です。
- accountExpires 属性
  - 「スクリプトを動かす属性」に有効期限を入力する属性 (`extensionAttribute1`) を指定し、スクリプトに add と modify と view の 3 つの関数を書きます。
  - [スクリプトを動かす属性をこの行で編集する](#edit-depends) をオンにします。
  - 「管理画面で編集不可にする」はオフにします。
    - on にすると、スクリプトが導出した値が「編集不可の属性は更新できない」という検査に掛かり、エントリーの更新全体が失敗します。

以下は `extensionAttribute1` に日付を入力する場合のスクリプト例です。
連携元が AD のときは、スクリプトの欄の「accountExpires 用のスクリプトを入れる」ボタンで同じスクリプトを入れられます。

```javascript
// accountExpires を extensionAttribute1 の値から作るスクリプト。
// extensionAttribute1 の日付（例: 20270401）は「この日まで使用可」の最終日として扱い、
// 翌日 0:00 に失効する値を書く。extensionAttribute1 が "0" なら無期限にする。
// TIMEZONE は AD の環境に合わせて変える。
const TIMEZONE = "Asia/Tokyo";
const EDIT = "extensionattribute1";
const NEVER = "0";

function toExpires(value) {
  if (value === NEVER) {
    return [BUILTIN.AD.neverExpires];
  }
  return [BUILTIN.AD.toAccountExpires(value, TIMEZONE)];
}

function add(upd) {
  // 期限の指定が無ければ AD の既定値（無期限）に任せる
  if (!Object.hasOwn(upd, EDIT)) {
    return;
  }
  return toExpires(upd[EDIT][0]);
}

function modify(ent, upd, del) {
  // extensionAttribute1 を消したら、属性は消さずに 0 を書いて無期限に戻す
  if (Object.hasOwn(del, EDIT)) {
    return [BUILTIN.AD.neverExpires];
  }
  if (!Object.hasOwn(upd, EDIT)) {
    return;
  }
  return toExpires(upd[EDIT][0]);
}

function view(ent) {
  if (!Object.hasOwn(ent, "accountexpires")) {
    return;
  }
  // 無期限は 3099-12-31 が返り、画面が「無期限」と表示する。
  // 読めない値でも画面を開けるように、変換の失敗は表示値なしにする
  try {
    return [BUILTIN.AD.fromAccountExpiresAsDate(ent.accountexpires[0])];
  } catch (e) {
    return;
  }
}
```

`extensionAttribute1` に `20270401` を入力してエントリーを取得すると、次のレスポンスが返ります。

```json
{
  "attributes": {
    "extensionAttribute1": ["20270401"],
    "accountExpires": ["134510652000000000"]
  },
  "viewAttributes": {
    "accountExpires": ["2027-04-01"]
  }
}
```

`0` を入力すると無期限になり、画面では「無期限」と表示されます。

設定にあたっては次の点に留意してください。

- 日付は「Active Directory ユーザーとコンピューター」と同じく最終使用日として扱い、翌日の 0 時に失効します。`20270401` であれば 4 月 1 日いっぱい使えます。
- 有効期限を解除するときは、有効期限を入力する属性を削除します。accountExpires 属性は削除されず `0` になります。
- 失効する時刻はスクリプトに書いたタイムゾーンで決まり、表示値の日付は画面を見ているアカウントのタイムゾーンで求めます。
  両者を揃えてください。
- 有効期限は [ライフサイクル設定](#lifecycle-settings) のユーザー無効日とは別の属性として設定します。
  - AD では accountExpires 属性に値を書けばドメインコントローラーが失効を判定するため、スケジューラでユーザーを無効化する必要がありません。
  - 同じ属性を共有すると、無効化したあとに日付の属性を削除する処理が動き、accountExpires 属性が無期限に戻ります。
- 有効期限が切れても AD の userAccountControl 属性の無効ビットは変化しません。
  - UCIDM の画面では、有効期限の切れたユーザーも有効なユーザーとして表示されます。

### AD の userAccountControl を設定する例 \{#user-account-control-example}

[入力の形](#attribute-type) を「userAccountControl（AD のフラグ）」にした属性で、立っているフラグの名前を [表示値](#view-values) として表示する設定です。

- 「スクリプトを動かす属性」: `userAccountControl`
- スクリプト: 次の view 関数

スクリプトの欄の「userAccountControl 用のスクリプトを入れる」ボタンでも、同じ設定を入れられます。

```javascript
// userAccountControl を、立っているフラグの名前（例: NORMAL_ACCOUNT）にして表示するスクリプト。
// LOCKOUT と PASSWORD_EXPIRED は msDS-User-Account-Control-Computed から求める。
// AD は userAccountControl のこの 2 つのビットを更新しないため。
const UAC = "useraccountcontrol";
const COMPUTED = "msds-user-account-control-computed";

function view(ent) {
  if (!Object.hasOwn(ent, UAC)) {
    return;
  }
  const computed = ent[COMPUTED];
  return BUILTIN.AD.fromUserAccountControl(
    ent[UAC][0],
    computed ? computed[0] : undefined,
  );
}
```

- msDS-User-Account-Control-Computed 属性は、「スクリプトを動かす属性」に指定しなくても view 関数に渡ります。
- UCIDM はこの属性をユーザーを 1 件取得するときだけ読むため、ユーザー一覧や検索では LOCKOUT と PASSWORD_EXPIRED が返りません。

## デザイン設定画面 \{#design-settings}

- 「ページ全体」「画面の説明文」「用語」「画像」の 4 つの設定が表示されます。
  - ページ全体では、ヘッダー、フッター、パスワードポリシー（それぞれ日本語と英語）と、アカウント通知書の HTML を設定します。この文書では、これらの HTML を「テンプレート」と呼びます。
  - 画面の説明文では、各画面の上部に表示される案内文を設定します。
  - 用語では、画面に表示される用語や注釈文を設定します。
  - 画像では、ロゴ、ファビコン、テンプレートに載せる画像を置きます。
- ページ全体では、設定したい項目の「編集」を押下することで、その詳細画面に遷移します。

### デザイン設定詳細画面 \{#design-settings-details}

- テンプレート（ヘッダー、フッター、パスワードポリシー、アカウント通知書の HTML）を 1 つずつ編集する画面が表示されます。
- 編集項目を選択し、コード編集欄に HTML を記述します（背景色は選択しない場合、transparent になります）。
- 編集後、「プレビュー」ボタンを押下することで、どのような画面になるかを確認できます。ロールが system-superadmin のときのみ確認が行えます。
- 「保存」ボタンを押下することで、編集内容を保存できます。ロールが system-superadmin のときのみ更新が行えます。
- 初めてインストールしたときは、製品の標準のテンプレートが入っています。
- テンプレートに載せる画像は、[画像](#design-images)の画面に置いた画像を名前で参照します（例: `<img src="banner.png">`）。
- ヘッダーの HTML は、ロゴ画像とアカウントメニューのあいだに表示されます。
- 背景色は、ヘッダー、フッター、パスワードポリシーごとに選べます。
- パスワードポリシーデザインの内容は、ユーザー登録画面、パスワード変更画面、パスワードリセット画面に表示されます。
- アカウント通知書の内容は、ユーザー登録、パスワード変更時に表示されるパスワード印刷画面に表示されます。印刷設定によって、デザイン設定内容と異なる場合があります。
- アカウント通知書のテンプレートが無いとき、または空のときは、印刷と PDF の出力ができません。

### 画像 \{#design-images}

- ロゴ、ファビコン、テンプレートに載せる画像を置き、差し替え、削除します。
- 1 件 5 MB まで置けます。5 MB を超える画像は、選んだ時点でエラーになります。
- ロゴは PNG、SVG、WebP、JPEG、GIF を、ファビコンは PNG、SVG、ICO を置けます。それぞれ 1 つだけで、別の形式の画像を置くと前の画像は消えます。置いていないとき、または削除したときは、製品のロゴとファビコンを表示します。

### 画面の説明文 \{#design-descriptions}

- ログイン画面やホーム画面など、各画面の上部に表示される案内文を日本語と英語で設定します。
- HTML でもテキストでも記述できます。HTML に記述した場合、スクリプトなど画面の動作に影響する要素は取り除いて表示します。
- 日本語と英語を両方とも空にした画面には、案内文を表示しません。

### 用語 \{#design-terms}

- ログイン ID、SAML ログインボタン、ワンタイムパスワードとパスキーの表示名と注釈を、日本語と英語で設定します。

### パスワードポリシーデザインの埋め込み変数 \{#password-policy-design-variables}

パスワードポリシーで設定されている値を表示するために埋め込み変数が用意してあります。デザイン設定のプレビュー画面では、デフォルトパスワードポリシーの値が表示されます。

| 埋め込み変数                 | 説明              |
| :--------------------- | :-------------- |
| .PwdMaxLength          | パスワードの最大長       |
| .PwdMinLength          | パスワードの最小長       |
| .PwdAlphabetCount      | アルファベットの文字数     |
| .PwdUpperCount         | 大文字の文字数         |
| .PwdLowerCount         | 小文字の文字数         |
| .PwdSymbolCount        | 記号の文字数          |
| .PwdDigitCount         | 数字の文字数          |
| .PwdComplexityCount    | パスワードの複雑性       |
| .PwdProhibitedString   | パスワードの禁止文字      |
| .PwdNotContainName     | ユーザー名を含めない      |
| .PwdNotSameOldPassword | パスワードが 1 つ前と異なる |

.PwdNotContainName と .PwdNotSameOldPassword は、ルールが有効なときに true、無効なときに false に置き換わります。

#### パスワードポリシーデザインの条件 \{#password-policy-design-conditions}

`[if 変数]` と `[/if]` で囲んだ部分は、条件を満たすときだけ表示されます。`[else]` の後に、満たさないときの内容も書けます。

- true / false の変数は、true のときに表示されます。
- 数値の変数は、比較（`>` `<` `>=` `<=` `=` `!=`）を書けます。比較を省くと 0 以外のときに表示されます。
- 文字列の変数は、空でないときに表示されます。

```
[if .PwdNotContainName]
  ユーザー名を含めることはできません。
[else]
  ユーザー名を含めても構いません。
[/if]
[if .PwdSymbolCount > 0]
  記号を .PwdSymbolCount 文字以上
[/if]
```

### アカウント通知書の埋め込み変数 \{#password-print-design-variables}

ユーザー登録、パスワード変更、CSV 一括取込でのアカウント通知書の印刷を行うために埋め込み変数が用意してあります。1 人のユーザーに対して複数のパスワードが存在する場合、.PrintPassword が順番に置き換わります。

| 埋め込み変数         | 説明             |
| :------------- | :------------- |
| .PrintUsername | パスワード確認時のユーザー名 |
| .PrintPassword | パスワード確認時のパスワード |
| .PrintIssuedAt | パスワード発行日時      |

## パスワードポリシー設定画面 \{#password-policy-settings}

- パスワードポリシーの一覧が表示されます。
- ユーザー登録時はデフォルトパスワードポリシー、パスワード変更、パスワードリセットについては各ユーザーのパスワードポリシーが適用されます
  - 管理者による操作については、パスワードの長さと禁止文字のルールのみが適用されます。
  - 一般ユーザーによるパスワードリセットでは、1 つ前のパスワードと異なるルールは無視されます。
- 「検索」ボタンを押下することで、設定名と対象ベース DN で検索が行えます。
- 「登録」ボタンを押下することで、パスワードポリシー登録画面に遷移します。
- 「編集」を押下することで詳細画面に遷移します。
- 「削除」を押下することで、パスワードポリシーを削除できます。デフォルトポリシーを削除することはできません。

### パスワードポリシー設定登録 \{#password-policy-registration}

- パスワードポリシーの設定とランダムパスワードの設定の登録を行います。「登録」ボタンを押下することで、設定内容が登録されます。

#### パスワードポリシー適用条件 \{#password-policy-conditions}

パスワードポリシー登録時・更新時にパスワードポリシーを適用するユーザーの条件を設定できます。
複数のパスワードポリシーにマッチする場合、設定名の昇順で最初にマッチしたパスワードポリシーが適用されます。
一覧の「評価順」にこの順番が表示されます。
ある程度複雑な条件も設定できますので、いくつかの例を以下に示します。

##### シンプルな例 \{#simple-example}

```
{"attributes.gidNumber": "10000"}
```

`attributes.<属性名>` と値をキーバリューとした JSON 形式で記述します。
属性名のキーは `attributes.` を付与する必要があり `attributes.` で始まらない場合は構文エラーになります。
値は文字列で指定する必要があり `10000` (数字)としたり、 `[10000, 20000]` (配列)とすると構文エラーになります。

##### and 条件 \{#and-condition}

```
{"attributes.gidNumber": "10000", "attributes.employeeType": "staff"}
```

複数の条件を列挙することで and 条件を利用できます。
この場合 **gidNumber が 10000 かつ、employeeType が staff** のユーザーにのみ適用されるポリシーになります。

##### or 条件 \{#or-condition}

```
{"or": [{"attributes.gidNumber": "10000"}, {"attributes.gidNumber": "20000"}]}
```

`or` というキーワードを指定し、値に条件のリストを指定することで、
リスト内の条件のいずれかを満たす、or 条件を利用できます。
この場合 **gidNumber が 10000 または、gidNumber が 20000** のユーザーにのみ適用されるポリシーになります。

##### 複雑な条件 \{#complex-condition}

```
{
  "or": [
    {"attributes.gidNumber": "10000"},
    {"attributes.gidNumber": "20000"}
  ],
  "attributes.employeeType": "staff"
}
```

みやすさのために改行入れています。
実際に入力する際は改行は不要です。
前述した and 条件と or 条件を組み合わせた複雑な条件になります。
この場合、**gidNumber が 10000 か 20000 かつ、employeeType が staff** のユーザーにのみ適用されるポリシーになります。

##### 条件エディタ \{#condition-editor}

パスワードポリシーの適用条件を作成できる UI です。
属性名と値を設定すると該当するエントリにのみパスワードポリシーが適用されるようになります。
条件の追加には「条件を追加」を押し、AND 条件か OR 条件かを選んでください。

条件には AND 条件と OR 条件を設定出来ます。
AND 条件に含まれている条件はすべて満たす必要があり、
OR 条件に含まれている条件はいずれかを満たす必要があります。

- AND 条件と OR 条件は入れ子にできます
- 条件ごとに比べ方（一致する、一致しない、正規表現に一致、いずれかに一致、より大きい、以上、より小さい、以下）と、否定を指定できます
- 条件エディタで扱えない形の条件は「JSON」タブで編集します
- AND 条件、OR 条件、属性条件ともに削除ボタンを押すと条件が削除されます

### パスワードポリシー設定詳細画面 \{#password-policy-details}

- パスワードポリシーの設定とランダムパスワードの設定を編集します。「更新」ボタンを押下して更新を行います。
- 対象ベース DN と条件に一致したユーザーにそのパスワードポリシーが適用されます。何も一致するパスワードポリシーが存在しない場合はデフォルトポリシーが適用されます。
- 「削除」ボタンを押下することで、表示されているパスワードポリシーは削除されます。デフォルトポリシーを削除することはできません。

#### パスワードポリシー \{#password-policy}

- パスワードポリシーでは以下のルールを設定できます。
  - 最大文字数
    - パスワードの最大文字数を設定します。
  - 最小文字数
    - パスワードの最小文字数を設定します。
  - アルファベットの文字数
    - パスワードに含めなければならないアルファベットの最小文字数を設定します。
  - 大文字の文字数
    - パスワードに含めなければならない大文字アルファベットの最小文字数を設定します。
  - 小文字の文字数
    - パスワードに含めなければならない小文字アルファベットの最小文字数を設定します。
  - 記号の文字数
    - パスワードに含めなければならない記号の最小文字数を設定します。
  - 数字の文字数
    - パスワードに含めなければならない数字の最小文字数を設定します。
  - 複雑度
    - 英大文字、英小文字、数字、記号という 4 つのカテゴリから、いくつのカテゴリをパスワードに含めるかを設定します。
  - 禁止文字
    - パスワードに含めてはいけない禁止文字を設定します。
  - ユーザー名を含めない
    - ユーザー名をパスワードに含めるかどうかを設定します。有効でパスワードにユーザー名を含めてはならないになります。
  - 1 つ前のパスワードと異なる
    - 1 つ前のパスワードと同じパスワード更新を許可するかどうかを設定します。有効で 1 つ前のパスワードと異なる必要があるになります。

#### ランダムパスワード \{#random-password}

- ランダムパスワードの設定では以下のルールを設定できます。
  - 文字数
    - 生成するランダムパスワードの文字数を設定します。
  - 禁止文字
    - 生成するランダムパスワードに含めてはいけない禁止文字を設定します。

## 初期値 \{#preset-setting}

初期値とは、LDAP サーバーに対してユーザーやグループエントリーを新規登録するとき、任意の属性に固定の値をセットするために使います。[属性定義](#management-attributes-setting) のスクリプトとは用途が異なります。

- 主な用途
  - 画面で管理する必要のない属性を省略できる
  - [CSV 一括処理](#csv) で同じ値をセットする属性の列を省略できる
- 実行タイミング
  - エントリーに値が未設定のときのみ実行される
  - 登録時のみ (スクリプトよりも先に実行される)
- 設定値
  - 固定の値のみ

### 初期値の設定 \{#preset-settings-page}

- 属性定義詳細画面の「初期値」で、属性ごとに初期値を設定します。
- 画面で扱わない属性の初期値は、次の「画面に出さない初期値」で設定します。

### 画面に出さない初期値 \{#hidden-preset-settings}

- 属性定義に無い属性の初期値です。登録画面・詳細画面・一覧には表示されず、登録時に値が指定されていなければセットされます。
- 属性定義画面の属性の一覧の下に、ユーザー・グループそれぞれ表示されます。
- 「登録」ボタンで、属性名と値を入力して登録します。属性定義にある属性名と、登録済みの属性名は使えません。値は 1 つ以上入力します。
- 「編集」ボタンで値を変更します。属性名は変更できないので、変更したいときは削除して登録し直します。
- 「属性を作る」ボタンで、属性名と初期値を引き継いで属性の追加画面に遷移します。作成すると、その属性の初期値として属性定義に移ります。
- 「削除」ボタンで初期値を削除します。

## ユーザーの有効・無効画面 \{#user-status-settings}

- ユーザーのステータス変更時に使用される属性名やスクリプトを設定します。属性定義画面の「有効・無効の判定」から開きます。
- 「ユーザーの有効・無効を管理する」がオンになっている場合、ステータス変更時に設定内容が使用されます。オフになっている場合は、すべてのユーザーが有効として扱われ、ステータス操作を行うことができません。
- 「有効・無効の値が入る属性」に選んだ属性の値は、ユーザーのステータス変更時に更新されます。
- 「有効・無効の判定にスクリプトを利用する」がオンになっている場合、スクリプトがステータス変更時に呼び出されるようになります。オフになっている場合は、スクリプトは呼び出されません。
- 「関数呼び出し確認」ボタンを押下することで、指定した関数の動作を確認することができます。

### ユーザーの有効・無効のスクリプト例 \{#user-status-script-example}

- **属性定義のスクリプトとは仕様が異なります。**
- ユーザーエントリーに対する処理種別に対応する関数名を設定します。
- 必ず関数の戻り値を返す必要があります。
  - 関数の戻り値として null または undefined を返した場合はエラーになります。

例えば Active Directory の `userAccountControl` 属性を変換するときは次のようになります。

```javascript
function view(values) {
  // ユーザーエントリーが有効か無効かを判別するときにこの関数が呼ばれる
  // 第1引数の values にはステータス属性の値が文字列の配列として渡される
  // 関数の戻り値は有効・無効を表す boolean 値を返す
  return (Number(values[0]) & 2) != 2;
}

function modify(values, enabled) {
  // ユーザーエントリーの有効・無効を切り替えるときにこの関数が呼ばれる
  // 第1引数の values にはステータス属性の値が文字列の配列として渡される
  // 第2引数の enabled には有効・無効を表す boolean 値が渡される
  // 関数の戻り値は文字列の配列を返す
  return [
    enabled ? String(Number(values[0]) & ~2) : String(Number(values[0]) | 2),
  ];
}
```

## 設定のエクスポート \{#export-settings}

- 各種設定の「設定の入出力」の「エクスポート」タブで行います。
- エクスポートしたい設定を選択します。設定ごとに、エクスポートするレコードも選択できます。チェックされている設定内容を JSON ファイルとしてエクスポートします。チェックが外されたものは JSON ファイルに含まれません。
- エクスポートしたファイルは、「インポート」タブで使用できます。
- システム設定でカスタムロールを無効にしている環境では、ロールの設定は標準ロールだけをエクスポートします。カスタムロールとロールの割り当て方はエクスポートしません。
- デザイン設定の画像（ロゴ、ファビコン、テンプレートに載せる画像）は、「デザイン設定の画像」でエクスポートします。画像の数と大きさの分だけファイルが大きくなるので、要らないときはチェックを外してください。

## 設定のインポート \{#import-settings}

- 各種設定の「設定の入出力」の「インポート」タブで行います。
- エクスポートした JSON ファイルを選択します。ファイル選択後、設定ごとに追加・更新されるレコードの件数が表示され、インポートするレコードを選択できます。チェックが外された設定の内容はインポートされません。
- インポートでは設定の追加と更新だけを行い、ファイルに無い設定は削除しません。不要な設定は、それぞれの設定画面で削除してください。
- インポートの結果は、レコードごとに表示されます。
- システム設定でカスタムロールを無効にしている環境では、ファイルに含まれるカスタムロールとロールの割り当て方はインポートしません。インポートしない設定は、ファイル選択後に表示されます。
- デザイン設定の画像は、ファイルにある画像を追加・置き換えします。
