Takenoff Labs

Lotus Notes/Domino に関する Tips や、クラシックの名曲などを紹介します

[Notes/Domino] 設計解析講座: ノートの取得

更新サボっていてすみませんでした(_ _;; ちょっとここのところ体調が悪かったのと、記事用にコードを書いたり調べものをしたりするのが、かなり時間がかかっているもので。なるべく週次で更新したいとは思っていますが、どうなりますやら。

さて今回は、ノートの取得方法について解説します。設計を取得するためには、何らかの方法でノートを取得しなければなりません。取得方法は簡単なので、今回はさらっと読んでいただければと。

NotesNoteCollection

ノートのコレクションを取得するのに一番簡単な方法は、LotusScript の NotesNoteCollection クラスを使うことです。この方法だと、API 関数を一切使わずにノートを取得できます。

以下は、全設計要素を取得するサンプルです。

Dim ss As New NotesSession
Dim db As NotesDatabase
Dim ncl As NotesNoteCollection
Dim doc As NotesDocument
Dim id As String

Set db = ss.Currentdatabase

Set ncl = db.Createnotecollection(False)
Call ncl.Selectalldesignelements(True)
Call ncl.Buildcollection()

id = ncl.Getfirstnoteid()
Do Until id = ""
    
    Set doc = db.GetDocumentByID(id)
    If Not doc Is Nothing Then
        '処理
    End If
    
    id = ncl.Getnextnoteid(id)
Loop

doc が取得できれば、あとは doc.handle を API 関数に渡せば楽勝ですね。テキストや数値などの基本データなら、「doc.~$TITLE(0)」のようにすれば簡単に取得できます。

また、プロパティを変更すれば、いろいろな切り口でノートを取得できますし、検索式による検索もできます(詳しくはデザイナーヘルプを見てください)。

ただし、NotesNoteCollection で注意が必要なのは、文書数が非常に多いDBでは、最初の1回目の実行が非常に遅くなる場合がある、ということです。2回目以降は速いですが、サーバー側かクライアント側のキャッシュ(?)が消えると、再び遅くなります。したがって、サーバーの全DBをスキャンする、といったような処理には使うべきではありません

NotesNoteCollection は、とても手軽で便利なだけに、上記の制限は残念ですね(x_x) いつか改善されることを期待しています……。

IDテーブル

API 関数で IDテーブルを検索すれば、NotesNoteCollection よりは速くなるはずです。どれくらい速いかは試していないですが(^^;

IDテーブルを検索するには、NSFDbGetModifiedNoteTable を使います。たとえば、全設計要素を取得するのは、以下のようになります。

※ DBハンドルを取得する処理や、APIGetError 関数などは省略しています。

Public Const NOTE_CLASS_DOCUMENT       = &H0001
Public Const NOTE_CLASS_DATA           = NOTE_CLASS_DOCUMENT
Public Const NOTE_CLASS_INFO           = &H0002
Public Const NOTE_CLASS_FORM           = &H0004
Public Const NOTE_CLASS_VIEW           = &H0008
Public Const NOTE_CLASS_ICON           = &H0010
Public Const NOTE_CLASS_DESIGN         = &H0020
Public Const NOTE_CLASS_ACL            = &H0040
Public Const NOTE_CLASS_HELP_INDEX     = &H0080
Public Const NOTE_CLASS_HELP           = &H0100
Public Const NOTE_CLASS_FILTER         = &H0200
Public Const NOTE_CLASS_FIELD          = &H0400
Public Const NOTE_CLASS_REPLFORMULA    = &H0800
Public Const NOTE_CLASS_PRIVATE        = &H1000
Public Const NOTE_CLASS_DEFAULT        = &H8000
Public Const NOTE_CLASS_NOTIFYDELETION = NOTE_CLASS_DEFAULT
Public Const NOTE_CLASS_ALL            = &H7fff
Public Const NOTE_CLASS_ALLNONDATA     = &H7ffe
Public Const NOTE_CLASS_NONE           = &H0000

Public Const NOTESDLL = "nnotes.dll"

Declare Function IDEntries Lib NOTESDLL (ByVal hTable As Long) As Long

Declare Function IDScan Lib NOTESDLL (ByVal hTable As Long, ByVal fFirst As Integer, retID As Long) As Integer

Declare Function NSFDbGetModifiedNoteTable Lib NOTESDLL (ByVal hDB As Long, _
ByVal NoteClassMask As Integer, ByVal Since As Double, retUntil As Double, rethTable As Long) As Integer

Declare Sub TimeConstruct Lib NOTESDLL (ByVal lDate As Long, ByVal lTime As Long, result As Double)

Declare Sub OSMemFree Lib NOTESDLL (ByVal hHandle)

Sub Initialize
    Dim doc As NotesDocument
    Dim dblBegin As Double
    Dim dblEnd   As Double
    Dim hIdTable As Long
    Dim lngId    As Long
    Dim hNote    As Integer
    Dim intRet   As Integer
    Dim strFlags As String
    
    '中略
    
    Call TimeConstruct(&HFFFFFFFF, &HFFFFFFFF, dblBegin)
    intRet = NSFDbGetModifiedNoteTable(hDb, NOTE_CLASS_ALLNONDATA, dblBegin, dblEnd , hIdTable)
    If intRet <> 0 Then
        MsgBox APIGetError(intRet), 0, "エラー"
        Call NSFDbClose(hDb)
        Exit Sub
    End If
    If IDEntries(hIdTable) <> 0 Then
        If IDScan(hIdTable, True, lngId) Then
            Do
                Set doc = db.Getdocumentbyid(Hex(lngId))
                If not doc Is Nothing Then
                    '処理
                End If
            Loop While IDScan(hIdTable, False, lngId)
        End If
    End If
    
    Call OSMemFree(hIdTable)
    
    '後略
End Sub

NSFDbGetModifiedNoteTable の第2引数を変えれば、いろいろな切り口でIDテーブルを取得できます。たとえば、NOTE_CLASS_ALLNONDATA を NOTE_CLASS_FORM に変えれば、フォームクラスのノートがすべてが取得されます。

ただし、ここで言う「フォームクラス」とは、いわゆる「フォーム」だけではなく、ページやサブフォームなども含まれます。ノートの種類を判別する方法は、次回ご紹介する予定です。

TimeConstruct は TIMEDATE 構造体を作成しています(Double型で代用)。今回はあまり気にしないでください。TIMEDATE も、今後どこかで解説したいと思います。

デフォルト設計要素

デフォルトの設計要素は、「FFFF」で始まる特殊なノートIDによって簡単に取得できます。特殊なノートIDについては、nsftools の Getting Default Elements in the Database を参照してください(丸投げ)。

たとえばデータベースアイコンは、以下のような簡単なコードで取得できます。

Set doc = db.GetDocumentByID("FFFF0010")

API 関数では「NSFDbGetSpecialNoteID」という関数が該当しますが、LotusScript の場合は上記のコードのほうが圧倒的に楽です。

ちなみに、「FFFF0020」の「Database Design Collection (view)」というものは見慣れないものかと思います。これは、設計要素のコレクションを管理している特殊なビューです。選択式とインデックスしかない($UpdatedByなどのアイテムはありますが)ビューで、$TITLEでソートされています。

たぶん「NIFFindDesignNoteByName」あたりで内部的に使われているんじゃないかと思います(推測ですが)。これをプログラムから使用することはほとんど無いと思いますので、あまり気にしないでください。

その他のAPI関数

その他、設計要素を取得する API 関数は、以下があります。全部解説すると長くなりますし、設計名から取得するケースはそれほど多くないかな、と思いますので、リファレンスへのリンクのみにしておきます。解説希望があったらコメントしてください。

1 Star2 Stars3 Stars4 Stars5 Stars (1 votes, average: 5.00 out of 5)
読み込み中...

トラックバック

トラックバックはありません

コメント

コメントはありません

※コメントは承認制となっております。管理者が承認するまで表示されません。申し訳ありませんが、投稿が表示されるまでしばらくお待ちください。





(以下のタグが使えます)
<a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>

For spam filtering purposes, please copy the number 4814 to the field below:

^
×