[ILM2007] 既存の環境を考慮した 拡張ルールの作り方

みなさま、ご無沙汰しております。ぴろとです。5月、9月に披露宴から呼んでいただいている結婚式があるので、お小遣いを貯めています。
結婚式といえば、6月は、ジューン・ブライドで世間は結婚式が多くなるそうなのですが、農閑期説や、June が結婚をつかさどる
女神 ”Juno” からきている説があるそうです。どちらの由来であったとしても、幸せになりたいという素直な気持ちを持ち続ける
ことは、すばらしいと思います。

本日のお題は、『Active Directory ID 自動管理ガイド - Microsoft Identity Lifecycle Manager 2007 で実践する ID 統合管理ソリューション』 における
Provision ルールを元に、同期シナリオを考えてみることにします。

Active Directory ID 自動管理ガイド - Microsoft Identity Lifecycle Manager 2007 で実践する ID 統合管理ソリューション

https://www.microsoft.com/japan/learning/books/JPN_ViewMsPress.aspx?Book_id=1092&list_id=1

Microsoft Identity Lifecycle Manager 2007

https://www.microsoft.com/japan/windowsserver/ilm2007/default.mspx

(ここより、本にてご紹介させていただいたサンプルコードがダウンロードできます)

今回の着目する点は、

・すでに一度でも同期が行われている

・すでに構築されている Active Directory への同期

のシナリオとなります。上記の本の場合であれば、新規で対応させる OU にオブジェクトがない場合が前提となっているためです。

この場合に発生する可能性のある問題点およびに、対処方法について考えてみます。

今回のシナリオ(本のシナリオに基づき、SQL Server MA と Active Directory MA にて構成)

1. Full Import Stage Only 操作を全ての MA にて実施する

2. SQL Server MA にて、Full/Delta Sync を行う

3. Active Directory MA にて、Full/Delta Sync を行う

4. 両方のMA にて、Export を実施する。

[新規作成したActive Directory の場合]

1.の操作にて、Connector Space 上に Importされたデータが作成される。
この時、OU 等の情報のみが読み込まれるため、図としては、次のようになる。

2. の操作にて、SQL Server 側の Connector Space Entry オブジェクトが、Projection されるため、
Meta Verse オブジェクトとして構成され、Provision が行われる。

 

[既存の環境の場合]

1.の操作にて、Connector Space 上に Importされたデータが作成される。この時、OU 等の情報および、ユーザー等のオブジェクトが読み込まれるため、図としては、次のようになる。(Active Directory 側の Connector Space 上にオブジェクトがいる点が異なる)

 

2. の操作時に、同様にProjection / Provision が行われるが、すでにConnector Space 上に同名 オブジェクトが存在するためにエラーとなる。

 

[Provisioning ルール]

Provision のルールは、LAB-Files\3.ExtensionRules\MVExtension に格納されておりますので、こちらを開いていただきたく存じます。MVExtension.vb を開き、次の箇所に着目を行います。

        Try

            …(省略)…

            numConnectors = coNNectedMA.Connectors.Count

            If 0 = numConnectors Then 接続先の数

                'CSエントリを新規作成

                csentry = coNNectedMA.Connectors.StartNewConnector(objectType)

          csentry.DN = dn

                Select Case objectType

                    Case "user"

                        csentry("unicodepwd").Values.Add(strInitPwd)

                        csentry("pwdLastSet").Value = "0"

                End Select

         csentry.CommitNewConnector()

            ElseIf 1 = numConnectors Then 接続先の数

                'CS内にコネクタオブジェクトが既に存在すれば、

                '移動先のDN値をセット

                'まず最初にコネクタオブジェクトを取得

                myConnector = coNNectedMA.Connectors.ByIndex(0)

                '下記でセットしたDN属性値が以前と変わっていれば、

                'ILM 2007が自動的にOU移動処理を実行する

                myConnector.DN = dn

            Else

                Throw New UnexpectedDataException("コネクタが複数です")

            End If

            successful = True

        Catch ex As ObjectAlreadyExistsException オブジェクト重複を検出

            Throw New UnexpectedDataException("オブジェクトは既にあります")

        Finally

        End Try

今回着目すべき点は、numConnectos となります。ここで、指している numConnectors の数ですが、Join されている オブジェクトの数を指しています。

            If 0 = numConnectors Then ‘ 接続先の数

と表現されている箇所での処理は、Join されていないことを示しますので、その後、StartNewConnector にて、Provisioning をするという構成になっています。そのため、Provision 時に Connector Space 上にオブジェクトが存在しない場合は、そのままとなり、すでにオブジェクトがある場合、ObjectAlreadyExistsException が発生します。

既存のオブジェクトが存在する場合、規定のGalsync.dll の場合 CN名に (1)… という形で作成します。それにより、Retry を行わせた際に正常にオブジェクトを作成させるという操作を行わせていますが、今回は無視させるように実装してみます。

        Try

            …(省略)…

            numConnectors = coNNectedMA.Connectors.Count

            If 0 = numConnectors Then 接続先の数

                'CSエントリを新規作成

                csentry = coNNectedMA.Connectors.StartNewConnector(objectType)

                csentry.DN = dn

                Select Case objectType

                    Case "user"

                        csentry("unicodepwd").Values.Add(strInitPwd)

                        csentry("pwdLastSet").Value = "0"

          End Select

                csentry.CommitNewConnector()

            ElseIf 1 = numConnectors Then 接続先の数

                'CS内にコネクタオブジェクトが既に存在すれば、

                '移動先のDN値をセット

                'まず最初にコネクタオブジェクトを取得

                myConnector = coNNectedMA.Connectors.ByIndex(0)

                '下記でセットしたDN属性値が以前と変わっていれば、

                'ILM 2007が自動的にOU移動処理を実行する

                myConnector.DN = dn

            Else

                Throw New UnexpectedDataException("コネクタが複数です")

            End If

        successful = True

        Catch ex As ObjectAlreadyExistsException オブジェクト重複を検出

            ‘ Throw New UnexpectedDataException(" オブジェクトは既にあります") ‘コメント化

            Successful = True ‘ これを設定しないと、無限ループになります。

        Finally

        End Try

ここで、無視させた場合、Active Directory MA 上のすでにある Connector Space Entry オブジェクトと Meta Verse については、連結がないため、Meta Verse の情報が反映されない状況となってしまいます。

ここで、関係が出てくるのは、Join ルールになります。本で設定している操作は、Active Directory MA の ”Configure Join and Projection Rule” にて、employeeID を元に Join させる設定となっているため、Active Directory MA を同期させるとConnector Space Entry オブジェクトが Projection されている Meta Verse Entry オブジェクトとJoin が行われます。

(もちろん、こちらもExtension でコード実装が可能となります!)

 

この場合の、Provision ルールは、ElseIf 1 = numConnectors Then 接続先の数 の場合の処理となります。

つまり、既存環境に適用させるコードを行う場合、ObjectAlreadyExistsException が発生した場合に、エラーを Throw させるのではなく、無視させることで実装が可能となります。

 

GUI 上で、Provisionさせないようにすることもできますので、アプローチとしては、2つ

・コードでObjectAlreadyExistsException が発生しても無視させる

・”Identity Manager” にて、メニューより ”Tools” -> “Options” を選択いただき、”Enable Provisioning Rules Extension”
 のチェックボックスを OFF にし、1~3 を行い、チェックボックスを ON に戻し、1~4 を再度実行させて、
 未 Join の Provision を期待するという動作となります。

ご参考になれば、幸いです。今度、Galsync.dll の動作について、今回のように オペレーションが複雑な回復を要求される場合
がありますので、ご紹介させていただく予定です。

~ ぴろと@ミニ四駆の改造のために、ボール盤購入計画か? ~