Excel VBAでオブジェクト指向プログラミング(Notesデータベース編)

2024-01-05

目次

■Notesのオブジェクトについて

HCLからNotesの機能を利用するためのオブジェクト群が提供されていますが、下位オブジェクト(サブクラス)の種類が非常に多いため、NotesSessionクラス、NotesDatabaseクラス、NotesDocumentクラス、NotesViewクラス、NotesACLクラスに絞った階層構造(依存関係)を掲載したうえ、主なオブジェクトについて概要を説明します。
⇒詳細はIBMのサイト(Notes~クラス)を参照して下さい(※)。

(※)NotesはもともとLotus社の製品でしたが、1995年にIBM社が買収してIBM製品となり、2019年にはIBM社からHCL社に売却されました。Notes関連オブジェクトのドキュメントは、今でもIBM社の方がわかり易いと思います。

Notes関連オブジェクト群の階層構造

Notes関連オブジェクト群の中で、最上位に位置するものはNotesSessionクラスですが、実際の処理を行うためにはNotesDatabaseクラス→NotesDocumentクラス・NotesViewクラス・NotesACLクラス等の順で下位のオブジェクトを生成して行く必要があります。
下表はNotesSessionクラス、NotesDatabaseクラス、NotesDocumentクラス、NotesViewクラス、NotesACLクラスの下位オブジェクト(サブクラス)を一覧化したもの(※)で、Notes関連オブジェクト群のオブジェクトの大半が含まれています。
各オブジェクトには多くのメソッドやプロパティが実装されていますので、次項では後述するサンプル・プログラムで使用しているメソッドやプロパティを中心に説明します。

NotesSessionクラス
NotesAdministrationProcessクラス
NotesAgentクラス
NotesColorObjectクラス
NotesDatabaseクラス
NotesACLクラス
NotesACLEntryクラス
NotesAgentクラス
NotesDocumentクラス
NotesDateRangeクラス
NotesDateTimeクラス
NotesEmbeddedObjectクラス
NotesItemクラス
NotesDataRangeクラス
NotesDateTimeクラス
NotesMIMEEntityクラス
NotesMIMEEntityクラス
NotesRichTextItemクラス
NotesDocumentCollectionクラス
NotesFormクラス
NotesNoteCollectionクラス
NotesOutlineクラス
NotesReplicationクラス
NotesViewクラス
NotesViewColumnクラス
NotesViewEntryクラス
NotesViewEntryCollectionクラス
NotesViewNavigatorクラス
NotesDateRangeクラス
NotesDateTimeクラス
NotesDbDirectoryクラス
NotesDirectoryクラス
NotesDocumentCollectionクラス
NotesDOMParserクラス
NotesDXLExporterクラス
NotesDXLImporterクラス
NotesInternationalクラス
NotesLogクラス
NotesNameクラス
NotesNewsletterクラス
NotesPropertyBrokerクラス
NotesRegistrationクラス
NotesRichTextParagraphStyleクラス
NotesRichTextStyleクラス
NotesSAXParserクラス
NotesStreamクラス
NotesTimerクラス
NotesXSLTransformerクラス

■NotesSessionクラスの詳細

Notesを使用する際には最初にNotesSessionオブジェクトをインスタンス化し、GetDatabaseメソッドでNotesDatabaseオブジェクトを生成します。

Notesのオブジェクトを使用するための手順

Notesのオブジェクトを使用するための手順は、以下の3ステップです。
⇒オブジェクトを使用するための事前準備とオブジェクトブラウザによる調査方法については、Excel VBAでオブジェクト指向プログラミング(事前準備編)を参照して下さい。

①ライブラリの参照設定
Visual Basic Editor(VBE)のファイルメニューから[ツール]-[参照設定]を選択し、参照設定ダイアログでLotus Notes Automation Classesのチェックボックスにチェックを入れ、[OK]ボタンを押下。

②オブジェクト変数の定義
プログラムの宣言部でオブジェクト変数を定義。

  1. Dim session, db As Object

③インスタンスの生成
プログラムの処理部でインスタンスを生成。

  1. Set session = CreateObject(“Notes.NOTESSESSION")
  2. Set db = session.GETDATABASE(“", “xxx.nsf")
  3. 'ここにNotesを使用した処理を記述
  4. Set db = Nothing
  5. Set session = Nothing

(注)参照設定で事前バインディングを行っていますが、「Set session = New Notes.NOTESSESSION」と記述するとエラーが出るため、「Set session = CreateObject(“Notes.NOTESSESSION")」と記述しています。

GetDatabaseメソッド

NotesSessionオブジェクトのGetDatabaseメソッドを実行すると、NotesDatabaseオブジェクトを作成できます。

  1. session.GETDATABASE(SERVER As String, FILE As String, [CREATEONFAIL])

引数として指定できる項目は下表の通りですが、指定必須の引数はサーバー名とファイル名です。

引数 説明
SERVER データベースが存在するサーバー名
(ローカル・ドライブ場合は""(空値)を指定)
FILE ファイル名またはファイルのパス
(Notesディレクトリ以外の場合はフルパスを指定)
CREATEONFAIL True:DBを開けなくてもオブジェクトを作成する(既定値)
False:DBを開けない場合はオブジェクトを作成しない

■NotesDatabaseクラスの詳細

NotesDatabaseクラスには多くのメソッドとプロパティがありますが、後述するサンプル・プログラムで使用しているものを中心に主なものを下表に掲載します。

NotesDatabaseクラスのメソッド

NotesDatabaseクラスの主なメソッドは、下表の通りです。

項目 説明
CreateDocumentメソッド 新規文書を作成し、NotesDocumentオブジェクトを返す
GetAllReadDocumentsメソッド 全ての既読文書のコレクション(NotesDocumentCollectionオブジェクト)を返す
GetAllUnreadDocumentsメソッド 全ての未読文書のコレクション(NotesDocumentCollectionオブジェクト)を返す
GetDocumentByIDメソッド 指定したNote IDの文書(NotesDocumentオブジェクト)を返す
GetDocumentByUNIDメソッド 指定したユニバーサルIDの文書(NotesDocumentオブジェクト)を返す
GetDocumentByURLメソッド 指定したURLの文書(NotesDocumentオブジェクト)を返す
GetFormメソッド 指定したフォーム名のフォーム(NotesFormオブジェクト)を返す
GetModifiedDocumentsメソッド 指定した時刻以後に更新された文書のコレクション(NotesDocumentCollectionオブジェクト)を返す
GetViewメソッド 指定したビュー名のビュー(NotesViewオブジェクト)を返す
Searchメソッド 条件を満たす全ての文書のコレクション(NotesDocumentCollectionオブジェクト)を返す

NotesDatabaseクラスのプロパティ

NotesDatabaseクラスの主なプロパティは、下表の通りです。

項目 説明
ACLプロパティ アクセス制御リスト(NotesACLオブジェクト)を返す
AllDocumentsプロパティ 全ての文書のコレクション(NotesDocumentCollectionオブジェクト)を返す
Formsプロパティ 全てのフォーム(NotesFormオブジェクト)の配列を返す
Viewsプロパティ 全てのビュー(NotesViewオブジェクト)の配列を返す

■NotesDocumentCollectionクラスの詳細

NotesDatabaseオブジェクトのメソッドやプロパティからNotesDocumentCollectionオブジェクトを取得した場合、以下のメソッドを使用して個々の文書(NotesDocumentオブジェクト)を取得します。

NotesDocumentCollectionクラスのメソッド

文書(NotesDocumentオブジェクト)を取得するために使用するメソッドは、下表の通りです。

項目 説明
GetFirstDocumentメソッド コレクションの最初の文書(NotesDocumentオブジェクト)を返す
GetLastDocumentメソッド コレクションの最後の文書(NotesDocumentオブジェクト)を返す
GetNextDocumentメソッド 指定された文書の次の文書(NotesDocumentオブジェクト)を返す
GetNthDocumentメソッド コレクション内の指定された位置番号の文書(NotesDocumentオブジェクト)を返す
GetPrevDocumentメソッド 指定された文書の直前の文書(NotesDocumentオブジェクト)を返す

NotesDocumentCollectionオブジェクトからNotesDocumentオブジェクトを取得する処理

Notesのドキュメントを見ると、以下のようなサンプル・コーディングが示されており、これ以外の記述(「For Each doc In docs」等)をすると、エラーになってうまく処理できません。

  1. Set docs = db.ALLDOCUMENTS
  2. Set doc = docs.GETFIRSTDOCUMENT
  3. While Not (doc Is Nothing)
  4.     'NotesDocumentオブジェクトを使用する処理を記述
  5.     Set doc = docs.GETNEXTDOCUMENT(doc)
  6. Wend

■NotesDocumentクラスの詳細

NotesDocumentクラスには多くのメソッドとプロパティがありますが、後述するサンプル・プログラムで使用しているものを中心に主なものを下表に掲載します。

NotesDocumentクラスのメソッド

NotesDocumentクラスの主なメソッドは、下表の通りです。

項目 説明
CreateReplyMessageメソッド 返答文書を新規作成し、NotesDocumentオブジェクトを返す
GetAttachmentメソッド 添付ファイル(NotesEmbeddedObject)を返す
GetFirstItemメソッド 指定された名前を持つ最初のアイテム(NotesItemオブジェクト)を返す
GetItemValueメソッド 指定された名前のアイテムの値を返す
Sendメソッド 文書をメールで送信する

NotesDocumentクラスのプロパティ

NotesDocumentクラスの主なプロパティは、下表の通りです。

項目 説明
Createdプロパティ 文書の作成日を返す
Itemsプロパティ 全てのNotesItemオブジェクトを返す
LastAccessedプロパティ 文書の最終アクセス日を返す
LastModifiedプロパティ 文書の最終更新日を返す
NoteIDプロパティ 文書のNote IDを返す
NotesURLプロパティ 文書のURLを返す
Responsesプロパティ 返答文書のコレクション(NotesDocumentCollectionオブジェクト)を返す
Sizeプロパティ 文書のサイズを返す
UniversalIDプロパティ 文書のユニバーサルIDを返す

■データベース内のフォームとフィールドを一覧表示する処理

Notesに接続してデータベースをオープンし、フォームとフィールドの一覧を作成するExcelツールです。

処理の概要

処理の流れは以下の通りです。
①Notesに接続し、データベースをオープン
②全てのフォームとフィールドを順に参照し、Excelシートにフォーム名とフィールド名をセット
③使用済のオブジェクトを破棄し、プログラムを終了

サンプル・プログラム

行番号6でNotesに接続し、行番号7でデータベースをオープン(NotesDatabaseオブジェクトを取得)しています。
行番号10でNotesDatabaseオブジェクトのFormsプロパティからフォーム(NotesFormオブジェクト)を取得し、行番号12でNotesFormオブジェクトのNameプロパティからフォーム名を取得し、ExcelシートのA列にセットしています。
行番号14でNotesFormオブジェクトのFieldsプロパティからフィールドを取得し、行番号16でExcelシートのB列以降にセットしています。

(※)サンプル・プログラムではfieldをObject型で定義しましたが、NotesFormオブジェクトのドキュメントによると、Fieldsプロパティの戻り値は「String型の配列」と記載されていますので、Variant型で定義するのが正しいと思います。

  1. Dim sht, session, db, form, field As Object
  2. Dim i, j As Integer
  3. Private Sub Sample1()
  4.     Set sht = ActiveSheet
  5.     Set session = CreateObject(“Notes.NOTESSESSION")
  6.     Set db = session.GETDATABASE(“", “xxx.nsf")
  7.     i = 0
  8.     For Each form In db.forms
  9.         i = i + 1
  10.         sht.Cells(i, 1) = form.Name
  11.         j = 1
  12.         For Each field In form.FIELDS
  13.             j = j + 1
  14.             sht.Cells(i, j) = field
  15.         Next field
  16.     Next form
  17.     Set field = Nothing
  18.     Set form = Nothing
  19.     Set db = Nothing
  20.     Set session = Nothing
  21. End Sub

■データベース内のビューとカラムを一覧表示する処理

Notesに接続してデータベースをオープンし、ビューとカラムの一覧を作成するExcelツールです。

処理の概要

処理の流れは以下の通りです。
①Notesに接続し、データベースをオープン
②全てのビューとカラムを順に参照し、Excelシートにビュー名とカラム名をセット
③使用済のオブジェクトを破棄し、プログラムを終了

サンプル・プログラム

行番号6でNotesに接続し、行番号7でデータベースをオープン(NotesDatabaseオブジェクトを取得)しています。
行番号10でNotesDatabaseオブジェクトのViewsプロパティからビュー(NotesViewオブジェクト)を取得し、行番号12でNotesViewオブジェクトのNameプロパティからビュー名を取得し、ExcelシートのA列にセットしています。
行番号14でNotesViewオブジェクトのColumnsプロパティからカラム(NotesViewColumnオブジェクト)を取得し、行番号16でExcelシートのB列以降にセットしています。

  1. Dim sht, session, db, view, column As Object
  2. Dim i, j As Integer
  3. Private Sub Sample2()
  4.     Set sht = ActiveSheet
  5.     Set session = CreateObject(“Notes.NOTESSESSION")
  6.     Set db = session.GETDATABASE(“", “xxx.nsf")
  7.     i = 0
  8.     For Each view In db.views
  9.         i = i + 1
  10.         sht.Cells(i, 1) = view.Name
  11.         j = 1
  12.         For Each column In view.Columns
  13.             j = j + 1
  14.             sht.Cells(i, j) = column.Title
  15.         Next column
  16.     Next view
  17.     Set column = Nothing
  18.     Set view = Nothing
  19.     Set db = Nothing
  20.     Set session = Nothing
  21. End Sub

■データベース内の文書を一覧表示する処理

Notesに接続してデータベースをオープンし、文書の一覧を作成するExcelツールです。

処理の概要

処理の流れは以下の通りです。
①Notesに接続し、データベースをオープン
②全ての文書を順に参照し、Excelシートに文書名とサイズをセット
③使用済のオブジェクトを破棄し、プログラムを終了

サンプル・プログラム

行番号6でNotesに接続し、行番号7でデータベースをオープン(NotesDatabaseオブジェクトを取得)しています。
行番号8でNotesDatabaseオブジェクトのAllDocumentsプロパティから全ての文書のコレクション(NotesDocumentCollectionオブジェクト)を取得し、行番号9で最初の文書(NotesDocumentオブジェクト)を取得しています。
行番号12~17は文書が無くなるまで繰り返す処理になっており、行番号14で文書名(※)、行番号15でサイズを取得して、ExcelシートのA列、B列にセットし、行番号16で次の文書を取得しています。

(※)このサンプルは文書名が「Title」という名称で定義されている例ですが、文書内のアイテム名については事前に確認する必要があります。
⇒文書内のアイテムを一覧表示する処理については、次項を参照して下さい。

  1. Dim sht, session, db, docs, doc As Object
  2. Dim i, j As Integer
  3. Private Sub Sample3()
  4.     Set sht = ActiveSheet
  5.     Set session = CreateObject(“Notes.NOTESSESSION")
  6.     Set db = session.GETDATABASE(“", “xxx.nsf")
  7.     Set docs = db.ALLDOCUMENTS
  8.     Set doc = docs.GETFIRSTDOCUMENT
  9.     i = 0
  10.     While Not (doc Is Nothing)
  11.         i = i + 1
  12.         sht.Cells(i, 1) = doc.GETITEMVALUE(“Title")
  13.         sht.Cells(i, 2) = doc.Size
  14.         Set doc = docs.GETNEXTDOCUMENT(doc)
  15.     Wend
  16.     Set doc = Nothing
  17.     Set db = Nothing
  18.     Set session = Nothing
  19. End Sub

■文書内のアイテムを一覧表示する処理

Notesに接続してデータベースをオープンして文書を読み込み、アイテムの一覧を作成するExcelツールです。

処理の概要

処理の流れは以下の通りです。
①Notesに接続し、データベースをオープン
②全ての文書を順に参照し、Excelシートに文書名とサイズをセット
③使用済のオブジェクトを破棄し、プログラムを終了

サンプル・プログラム

行番号6でNotesに接続し、行番号7でデータベースをオープン(NotesDatabaseオブジェクトを取得)しています。
行番号8でNotesDatabaseオブジェクトのAllDocumentsプロパティから全ての文書のコレクション(NotesDocumentCollectionオブジェクト)を取得し、行番号9で最初の文書(NotesDocumentオブジェクト)を取得しています。
行番号12でNotesDocumentオブジェクトのItemsプロパティから全てのアイテム(NotesItemオブジェクト)のコレクションを取得し、行番号14でNotesItemオブジェクトのNameプロパティからアイテム名を取得して、ExcelシートのA列にセットしています。

  1. Dim sht, session, db, docs, doc, item As Object
  2. Dim i As Integer
  3. Private Sub Sample4()
  4.     Set sht = ActiveSheet
  5.     Set session = CreateObject(“Notes.NOTESSESSION")
  6.     Set db = session.GETDATABASE(“", “xxx.nsf")
  7.     Set docs = db.ALLDOCUMENTS
  8.     Set doc = docs.GETFIRSTDOCUMENT
  9.     i = 0
  10.     For Each item In doc.ITEMS
  11.          i = i + 1
  12.         sht.Cells(i, 1) = item.Name
  13.     Next item
  14.     Set item = Nothing
  15.     Set doc = Nothing
  16.     Set docs = Nothing
  17.     Set db = Nothing
  18.     Set session = Nothing
  19. End Sub

サンプル・プログラム(その2)

複数の環境で動作確認を行ったところ、「For Each item In doc.ITEMS」の箇所でエラーになるケースがあり、以下のように修正すると正常に動作しました。
行番号6でNotesに接続し、行番号7でデータベースをオープン(NotesDatabaseオブジェクトを取得)しています。
行番号8でNotesDatabaseオブジェクトのAllDocumentsプロパティから全ての文書のコレクション(NotesDocumentCollectionオブジェクト)を取得し、行番号9で最初の文書(NotesDocumentオブジェクト)を取得しています。
行番号10でNotesDocumentオブジェクトのItemsプロパティから全てのアイテム(NotesItemオブジェクト)のコレクションを取得し、行番号15でNotesItemオブジェクトのNameプロパティからアイテム名を取得して、ExcelシートのA列にセットしています。

  1. Dim sht, session, db, items As Object
  2. Dim i, cnt As Integer
  3. Private Sub Sample5()
  4.     Set sht = ActiveSheet
  5.     Set session = CreateObject(“Notes.NOTESSESSION")
  6.     Set db = session.GETDATABASE(“", “xxx.nsf")
  7.     Set docs = db.ALLDOCUMENTS
  8.     Set doc = docs.GETFIRSTDOCUMENT
  9.     items = doc.items
  10.     cnt = 0
  11.     For i = LBound(items) To UBound(items)
  12.         cnt = cnt + 1
  13.         sht.Cells(cnt, 1) = items(i).Name
  14.     Next i
  15.     Set items = Nothing
  16.     Set doc = Nothing
  17.     Set docs = Nothing
  18.     Set db = Nothing
  19.     Set session = Nothing
  20. End Sub

■文書のコレクション(NotesDocumentCollectionオブジェクト)を取得する処理

前項のサンプル・プログラムでは、全文書のコレクションを取得していますが、他にも色々な方法がありますので、いくつか例示しておきます。

全文書を取得する処理

NotesDatabaseオブジェクトのAllDocumentsプロパティを使用します。

  1. Set docs = db.ALLDOCUMENTS

既読文書を取得する処理

NotesDatabaseオブジェクトのGetAllReadDocumentsメソッドを使用します。

  1. Set docs = db.GetAllReadDocuments()

未読文書を取得する処理

NotesDatabaseオブジェクトのGetAllUnreadDocumentsメソッドを使用します。

  1. Set docs = db.GetAllUnreadDocuments()

指定した時刻以後に更新された文書を取得する処理

NotesSessionオブジェクトのCreateDateTimeメソッドにより、NotesDateTimeオブジェクトを作成した後、NotesDatabaseオブジェクトのGetModifiedDocumentsメソッドを使用します。

  1. Set dt = session.CREATEDATETIME(“2021/10/29 00:00:00")
  2. Set docs = db.getModifiedDocuments(dt)

指定した条件を満たす文書を取得する処理

NotesDatabaseオブジェクトのSearchメソッドを使用します。

  1. Dim key As String
  2. key = “@Contains(Title;""" & “連絡" & “"")
  3. Set docs = db.Search(key, Nothing, 0)

(参考)Searchメソッドの引数は、下表の通りです。

引数 説明
formula$ 検索条件(Notesの@関数式で指定)
notesDateTime 切り離し日(切り離し日以降に作成・変更された文書を検索)
maxDocs% 返される文書の最大数(全て返す場合は0を指定)

■カレンダー情報を取得する処理

Notesに接続してデータベースをオープンして文書を読み込み、カレンダー情報を取得するExcelツールです。

処理の概要

処理の流れは以下の通りです。
①Notesに接続し、データベースをオープン
②カレンダー情報を取得し、指定した範囲の情報を抽出してExcelシートにセット
③使用済のオブジェクトを破棄し、プログラムを終了

サンプル・プログラム

行番号6でNotesに接続し、行番号7でデータベース(通常はメールDB)をオープン(NotesDatabaseオブジェクトを取得)し、行番号8でカレンダー情報(NotesCalendarオブジェクト)を取得しています。
行番号9~10で抽出するカレンダー情報の範囲を「今日の9時から17時まで」に設定し、行番号13~16で抽出したカレンダー情報をExcelシートにセットしています(※)。

(※)ここで取得できるカレンダー情報は、通称「iCalendar」と呼ばれる形式になっていますので、詳細は「RFC 5545 – Internet Calendaring and Scheduling Core Object Specification(iCalendar)」を参照して下さい。

  1. Dim sht, session, db, cal, cale, dt1, dt2 As Object
  2. Dim i As Integer
  3. Private Sub Sample6()
  4.     Set sht = ActiveSheet
  5.     Set session = CreateObject(“Notes.NOTESSESSION")
  6.     Set db = session.GETDATABASE(“", “xxx.nsf")
  7.     Set cal = session.getCalendar(db)
  8.     Set dt1 = session.CREATEDATETIME(“Today 09")
  9.     Set dt2 = session.CREATEDATETIME(“Today 17")
  10.     i = 0
  11.     For Each cale In cal.getEntries(dt1, dt2)
  12.         i = i + 1
  13.         sht.Cells(i, 1) = cale.READ()
  14.     Next cale
  15.     Set cale = Nothing
  16.     Set dt2 = Nothing
  17.     Set dt1 = Nothing
  18.     Set cal = Nothing
  19.     Set db = Nothing
  20.     Set session = Nothing
  21. End Sub

■データベースのアクセス制御リストを一覧表示する処理

Notesに接続してデータベースをオープンし、文書の一覧を作成するExcelツールです。

処理の概要

処理の流れは以下の通りです。
①Notesに接続し、データベースをオープン
②全ての文書を順に参照し、Excelシートに文書名とサイズをセット
③使用済のオブジェクトを破棄し、プログラムを終了

サンプル・プログラム

行番号6でNotesに接続し、行番号7でデータベースをオープン(NotesDatabaseオブジェクトを取得)しています。
行番号8でNotesDatabaseオブジェクトのACLプロパティからアクセス制御リスト(NotesACLオブジェクト)を取得し、行番号9で最初のエントリ(NotesACLEntryオブジェクト)を取得しています。
行番号12~18はエントリが無くなるまで繰り返す処理になっており、行番号14でエントリ名、行番号15でユーザ・タイプ、行番号16でアクセス・レベルを取得して、ExcelシートのA列~C列にセットし、行番号17で次のエントリを取得しています。

  1. Dim sht, session, db, acl, acle As Object
  2. Dim i As Integer
  3. Private Sub Sample7()
  4.     Set sht = ActiveSheet
  5.     Set session = CreateObject(“Notes.NOTESSESSION")
  6.     Set db = session.GETDATABASE(“", “xxx.nsf")
  7.     Set acl = db.acl
  8.     Set acle = acl.GETFIRSTENTRY
  9.     i = 0
  10.     While Not (acle Is Nothing)
  11.         i = i + 1
  12.         sht.Cells(i, 1) = acle.Name
  13.         sht.Cells(i, 2) = acle.USERTYPE
  14.         sht.Cells(i, 3) = acle.LEVEL
  15.         Set acle = acl.GETNEXTENTRY(acle)
  16.     Wend
  17.     Set acle = Nothing
  18.     Set acl = Nothing
  19.     Set db = Nothing
  20.     Set session = Nothing
  21. End Sub

 

国本温子(著),緑川吉行(著),できるシリーズ編集部(著)
出版社:インプレス
発売日:2022/3/23
単行本(ソフトカバー):A5判/912ページ

大村あつし(著),古川順平(著)
出版社:技術評論社
発売日:2021/1/9
単行本(ソフトカバー):A5判/800ページ

高橋宣成(著)
出版社:技術評論社
発売日:2019/11/25
単行本(ソフトカバー):B5変形判/576ページ