# 画面設計書 44-購読者一覧

## 概要

本ドキュメントは、QuickerSite CMSのバックサイト（管理画面）における「購読者一覧」画面の設計書です。

### 本画面の処理概要

ニュースレターの購読者（サブスクライバー）を一覧表示・管理するための画面です。カテゴリ（メーリングリスト）ごとに購読者を絞り込み、名前やメールアドレスで検索、アクティブ/非アクティブ状態でフィルタリングできます。購読者の一括削除、一括購読解除、名前の整形（Proper Case）など、大量の購読者データを効率的に管理するための機能を提供します。

**業務上の目的・背景**：メールマーケティングでは購読者リストの品質管理が重要です。本画面では、重複登録の確認、無効なメールアドレスの特定、購読解除希望者の一括処理など、リスト衛生（List Hygiene）を維持するための機能を提供します。最大2500件までの表示制限があり、それ以上は検索条件で絞り込む必要があります。これはパフォーマンス最適化のための設計です。

**画面へのアクセス方法**：ニュースレター一覧画面（bs_newsletterList.asp）の「Subscribers」ボタン、またはカテゴリ一覧画面（bs_newsletterCategoryList.asp）から購読者数リンクをクリックしてアクセスします。customer.bCanImportSubscribersがtrueの場合のみアクセス可能です。

**主要な操作・処理内容**：
1. 購読者一覧の閲覧：名前、メールアドレス、アクティブ状態、カテゴリを表示
2. 検索・フィルタリング：名前、メールアドレス、アクティブ状態、カテゴリで絞り込み
3. 購読者の編集：個別購読者の詳細編集画面へ遷移
4. 購読者の一括削除：チェックボックスで選択した購読者を一括削除
5. 全選択/全解除：チェックボックスの一括操作
6. Proper Case変換：全購読者の名前を適切な大文字小文字に変換
7. 一括購読解除：テキストエリアに入力したメールアドレスリストを一括で非アクティブ化

**画面遷移**：
- 遷移元：ニュースレター一覧画面（bs_newsletterList.asp）、カテゴリ一覧画面（bs_newsletterCategoryList.asp）
- 遷移先：購読者インポート画面（bs_newsletterImport.asp）、ニュースレター一覧画面（bs_newsletterList.asp）、購読者編集画面（bs_newsletterSubscriber.asp）

**権限による表示制御**：secondAdmin.bNewsletter権限がない場合はアクセス不可。customer.bCanImportSubscribersがfalseの場合、インポート機能リンクは非表示となります。

## 関連機能

| 機能No | 機能名 | 関連種別 | 関連する操作・処理 |
|--------|--------|----------|------------------|
| 69 | 購読者管理 | 主機能 | ニュースレター購読者の一覧・管理 |

## 画面種別

一覧・検索

## URL/ルーティング

```
/asp/bs_newsletterSubscribers.asp
/asp/bs_newsletterSubscribers.asp?iCategoryID={暗号化されたカテゴリID}
```

## 入出力項目

| 項目名 | 項目ID | 型 | 必須 | 入力/出力 | 説明 |
|--------|--------|-----|------|-----------|------|
| カテゴリID | iCategoryID | GET/hidden | - | 入力 | 絞り込み対象のカテゴリID（暗号化） |
| 名前検索 | sName | text | - | 入力 | 名前による部分一致検索（最大50文字） |
| メール検索 | sEmail | text | - | 入力 | メールアドレスによる部分一致検索（最大50文字） |
| アクティブ状態 | bActive | select | - | 入力 | Active/Inactive/Both |
| Proper Caseフラグ | pcase | hidden | - | 入力 | 名前整形処理フラグ |
| 削除対象ID | deleteID | checkbox | - | 入力 | 削除対象の購読者ID（複数選択可） |
| 一括購読解除リスト | unsubscribers | textarea | - | 入力 | 改行区切りのメールアドレスリスト |

## 表示項目

| 項目名 | 表示位置 | 説明 |
|--------|---------|------|
| Import Subscribersボタン | 上部 | 購読者インポート画面へのリンク（bCanImportSubscribers時） |
| Newsletter homeボタン | 上部 | ニュースレター一覧画面へのリンク |
| 総購読者数 | 中央 | 「Total: X subscribers」形式で表示 |
| 名前検索ボックス | テーブルヘッダー | 名前検索入力と検索リンク |
| メール検索ボックス | テーブルヘッダー | メール検索入力と検索リンク |
| アクティブ状態セレクト | テーブルヘッダー | Active/Inactive/Both選択 |
| カテゴリセレクト | テーブルヘッダー | メーリングリスト選択 |
| 購読者名 | テーブル行 | 購読者の名前（最大40文字表示） |
| メールアドレス | テーブル行 | mailto:リンク付き（最大40文字表示） |
| アクティブ状態 | テーブル行 | Yes/No表示 |
| カテゴリ名 | テーブル行 | 所属カテゴリ名 |
| 編集リンク | テーブル行 | 購読者編集画面へのリンク |
| 削除チェックボックス | テーブル行 | 削除選択用 |
| 一括購読解除テキストエリア | 下部 | メールアドレス入力エリア（カテゴリ選択時のみ表示） |
| 2500件警告 | JavaScript alert | 2500件超過時の警告メッセージ |

## イベント仕様

### 1-検索実行

名前/メール検索ボックスの「検索」リンク押下、またはアクティブ状態/カテゴリセレクトの変更時に自動的にフォーム送信されます。

**処理フロー**：
1. フォームがPOSTで送信される
2. sName、sEmail、bActive、iCategoryIDで検索条件構築
3. SQLにLIKE条件を追加してデータ取得
4. 最大2500件まで表示

### 2-選択した購読者を削除

「Delete selected」リンク押下時の処理です。

**処理フロー**：
1. JavaScript confirmで削除確認
2. 確認後、フォーム送信
3. request.form("deleteID")でチェックされたIDを取得
4. 各IDについてtblNewsletterLogとtblNewsletterCategorySubscriberから削除
5. 一覧を再表示

### 3-全選択/全解除

「Check all」「Clear all」リンク押下時の処理です。SetChecked(1)で全選択、SetChecked(0)で全解除するJavaScript関数が実行されます。

### 4-Proper Case変換

「(Proper case?)」リンク押下時の処理です。

**処理フロー**：
1. JavaScript confirmで確認
2. hiddenのpcaseを"1"に設定してフォーム送信
3. サーバー側でPCase()関数を使用して全購読者のsNameを変換
4. 一覧を再表示

### 5-一括購読解除

「Unsubscribe」ボタン押下時の処理です。

**処理フロー**：
1. JavaScript confirmで確認
2. unsubscribersテキストエリアの内容を改行で分割
3. 各メールアドレスについてbActive=falseに更新
4. 一覧を再表示

### 6-購読者編集リンク押下

個別購読者の「modify」リンク押下時、bs_newsletterSubscriber.aspに遷移します。

## データベース更新仕様

### 操作別データベース影響一覧

| 操作（イベント） | 対象テーブル | 操作種別 | 概要 |
|----------------|-------------|---------|------|
| 一覧表示 | tblNewsletterCategorySubscriber | SELECT | 購読者一覧取得 |
| 削除 | tblNewsletterLog | DELETE | 配信ログ削除 |
| 削除 | tblNewsletterCategorySubscriber | DELETE | 購読者削除 |
| Proper Case | tblNewsletterCategorySubscriber | UPDATE | 名前整形 |
| 一括購読解除 | tblNewsletterCategorySubscriber | UPDATE | bActive=false |

### テーブル別更新項目詳細

#### tblNewsletterCategorySubscriber

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| SELECT | * | iCategoryID、bActive、sName LIKE、sEmail LIKE | 検索条件 |
| UPDATE (Proper Case) | sName | PCase(sName) | 最初の文字を大文字に |
| UPDATE (購読解除) | bActive | false | メールアドレス一致条件 |
| DELETE | - | iId一致 | 選択された購読者 |

#### tblNewsletterLog

| 操作 | 項目（カラム名） | 更新値・取得条件 | 備考 |
|-----|-----------------|-----------------|------|
| DELETE | - | iSubscriberID一致 | 購読者削除時に連動削除 |

## メッセージ仕様

| メッセージID | 種別 | 表示条件 | メッセージ内容 |
|-------------|------|---------|--------------|
| (JavaScript alert) | 警告 | 2500件超過時 | "Warning! Only the first 2500 records are shown. Define your query to search for any specific subscriber." |
| (JavaScript confirm) | 確認 | 削除時 | "Are you sure to delete the selected subscribers?" |
| (JavaScript confirm) | 確認 | Proper Case時 | "Do you wish to proper case all names? - all first characters will be uppercase, the other lower case..." |
| (JavaScript confirm) | 確認 | 一括購読解除時 | "Are you sure to unsubscribe these email addresses from the selected list?" |

## 例外処理

| 例外条件 | 処理内容 |
|---------|---------|
| アクセス権限なし | secondAdmin.bNewsletter権限チェックに失敗した場合、エラー表示 |
| カテゴリ未選択時の一括購読解除 | テキストエリアが表示されないため操作不可 |
| 2500件超過 | 警告表示後、検索条件での絞り込みを促す |
| ループ中エラー | on error resume nextで継続処理 |

## 備考

- カテゴリが1つしかない場合は自動的にそのカテゴリが選択される
- 購読者の表示順はsName昇順
- メールアドレスはLIKE検索で部分一致
- cleanup()関数で入力値のサニタイズ処理
- 表示行はsubCounter変数で2500件までカウント

---

## コードリーディングガイド

本画面を理解するために参照すべきファイルと、推奨する読み解き順序を以下に示す。

### 推奨読解順序

#### Step 1: データ構造を理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 1-1 | newsletterCategory.asp | `asp/includes/newsletterCategory.asp` | cls_newsletterCategoryクラス。nmbrSubscribersプロパティを確認 |
| 1-2 | customer.asp | `asp/includes/customer.asp` | NewsletterCategoriesプロパティの実装を確認 |

**読解のコツ**: tblNewsletterCategorySubscriberテーブルが購読者データの中心。iCategoryIDで所属カテゴリ、bActiveでアクティブ状態を管理。

#### Step 2: エントリーポイントを理解する

| 順序 | ファイル | パス | 読解ポイント |
|-----|---------|------|-------------|
| 2-1 | bs_newsletterSubscribers.asp | `asp/bs_newsletterSubscribers.asp` | 画面表示のメインファイル。SetChecked()関数、検索条件構築、削除処理、Proper Case処理、一括購読解除処理の流れを確認 |

**主要処理フロー**:
1. **4-5行目**: JavaScript SetChecked関数定義
2. **14-24行目**: カテゴリ自動選択（カテゴリが1つの場合）
3. **25-35行目**: 削除処理（deleteID配列ループ）
4. **36-44行目**: アクティブ状態SQLの構築
5. **46-75行目**: 検索条件を含むSQLの構築
6. **56-67行目**: Proper Case処理（pcase="1"時）
7. **78-95行目**: 一括購読解除処理
8. **100-120行目**: 一覧テーブル出力（2500件制限）

### プログラム呼び出し階層図

```
bs_newsletterSubscribers.asp（画面表示）
    │
    ├─ begin.asp（初期化）
    │
    ├─ bs_security.asp（認証チェック）
    │      └─ logon.hasaccess(secondAdmin.bNewsletter)
    │
    ├─ JavaScript: SetChecked(val)
    │      └─ チェックボックス全選択/解除
    │
    ├─ 削除処理
    │      ├─ tblNewsletterLog DELETE
    │      └─ tblNewsletterCategorySubscriber DELETE
    │
    ├─ Proper Case処理
    │      ├─ db.getDynamicRS()
    │      ├─ PCase(sName)
    │      └─ rs.update()
    │
    ├─ 一括購読解除処理
    │      ├─ split(unsubscribers, vbcrlf)
    │      └─ bActive=false UPDATE
    │
    ├─ 検索・一覧表示
    │      ├─ SQL構築（LIKE、bActive、iCategoryID）
    │      ├─ db.execute(sql)
    │      └─ while not rs.eof（最大2500件）
    │
    └─ includes/footer.asp
```

### データフロー図

```
[入力]                      [処理]                           [出力]

検索条件
├─ sName ─────────────────▶ SQL LIKE条件構築 ────────────────▶ 購読者一覧
├─ sEmail                        │
├─ bActive                       ├─ SELECT実行
└─ iCategoryID                   │
                                 └─ 最大2500件表示

deleteID[] ────────────────▶ for each delID ──────────────────▶ tblNewsletterLog DELETE
                                 │                                tblNewsletterCategorySubscriber DELETE
                                 └─ db.execute(delete)

pcase="1" ─────────────────▶ while not rs.eof ───────────────▶ tblNewsletterCategorySubscriber UPDATE
                                 └─ PCase(sName)

unsubscribers ─────────────▶ split + for each ───────────────▶ bActive=false UPDATE
(改行区切り)                      └─ メール一致検索
```

### 関連ファイル一覧

| ファイル | パス | 種別 | 役割 |
|---------|------|------|------|
| bs_newsletterSubscribers.asp | `asp/bs_newsletterSubscribers.asp` | ソース | 購読者一覧画面 |
| bs_newsletterSubscriber.asp | `asp/bs_newsletterSubscriber.asp` | ソース | 購読者編集画面 |
| bs_newsletterImport.asp | `asp/bs_newsletterImport.asp` | ソース | 購読者インポート画面 |
| bs_newsletterList.asp | `asp/bs_newsletterList.asp` | ソース | ニュースレター一覧画面 |
| bs_newsletterCategoryList.asp | `asp/bs_newsletterCategoryList.asp` | ソース | カテゴリ一覧画面 |
| newsletterCategory.asp | `asp/includes/newsletterCategory.asp` | ソース | カテゴリクラス定義 |
| customer.asp | `asp/includes/customer.asp` | ソース | 顧客クラス（NewsletterCategories） |
| bs_security.asp | `asp/bs_security.asp` | ソース | 認証・認可処理 |
| begin.asp | `asp/begin.asp` | ソース | 共通初期化処理 |
| header.asp | `asp/includes/header.asp` | テンプレート | 共通ヘッダー |
| footer.asp | `asp/includes/footer.asp` | テンプレート | 共通フッター |
