PythonとPlaywrightによるUキャンパス自動化スクリプトの設計と実装
現代のオンライン教育プラットフォームが普及する中、Uキャンパスは多くの学生にとって重要な語学学習ツールとなっています。本稿では、Pythonの自動化技術を駆使してUキャンパスプラットフォームのインテリジェントな回答機能を実装する「AutoUnipus」プロジェクトについて解説します。これは、Web自動化の実践的なケーススタディとして、技術開発者に優れた学習機会を提供します。本稿では、プロジェクトの技術アーキテクチャ、核となるアルゴリズムの実装、および実際の応用シナリオを掘り下げ、最新のブラウザ自動化技術の可能性を探ります。
プロジェクト概要と技術選定
AutoUnipusは、Uキャンパス向けに開発されたPythonベースの自動回答スクリプトであり、全自動モードと補助モードの2つの運用形態をサポートし、100%の正答率を実現します。主要なブラウザ自動化フレームワークとしてMicrosoft Playwrightを採用し、Pythonのネットワークリクエスト処理能力と組み合わせることで、堅牢で信頼性の高い自動化システムを構築しています。
従来のSeleniumフレームワークと比較して、Playwrightはより現代的なAPI設計、優れたクロスブラウザサポート、および安定したネットワークインターセプト機能を提供します。AutoUnipusプロジェクトは、Playwrightのこれらの利点を最大限に活用し、Uキャンパスプラットフォームとの深い統合と効率的な操作を実現しています。
技術アーキテクチャ詳細
3層アーキテクチャパターン
AutoUnipusは、コードの高い凝集度と低い結合度を確保するため、明確な3層アーキテクチャを採用しています。
- ユーザーインターフェース層 - AutoUnipus.pyに配置
- ビジネスロジック層 - AutoUnipus.pyおよびres/fetcher.pyに配置
- データアクセス層 - res/fetcher.pyに配置
この階層設計により、各モジュールの責任が明確になり、保守性と拡張性が向上します。ユーザーインターフェース層はブラウザ操作とページナビゲーションを担当し、ビジネスロジック層は回答プロセスを制御し、データアクセス層は回答の取得とAPIインタラクションに専念します。
インテリジェントな回答取得メカニズム
本プロジェクトの技術的な核となるのは、そのインテリジェントな回答取得アルゴリズムです。res/fetcher.pyでは、開発者がUキャンパスのAPIインターフェースをリバースエンジニアリングし、以下の主要機能を実装しています。
import json
import requests # 仮定: HTTPリクエストを送信するためのライブラリ
# 仮定: URLからコースIDとチャプターIDを抽出する関数
def extract_course_chapter_info(url: str) -> tuple[str, str]:
# 例: "https://u.unipus.cn/course/chapter/some_id" から ID を抽出
# 実際のURL構造に応じて変更が必要
parts = url.split('/')
if len(parts) >= 6:
return parts[4], parts[5] # 仮のインデックス
return "unknown_course", "unknown_chapter"
def retrieve_solution_via_api(target_page, total_questions: int, question_identifier: str) -> list[str]:
# 空の回答リストを初期化
found_answers = []
# ブラウザのローカルストレージから認証トークン(JWT)を取得
jwt_token_str = target_page.evaluate("localStorage.getItem('jwtToken')")
if not jwt_token_str:
print("エラー: JWTトークンが見つかりません。自動回答を続行できません。")
return []
# 現在のページURLからコースとチャプター情報を解析
current_url_path = target_page.url
course_segment, chapter_segment = extract_course_chapter_info(current_url_path)
# 回答提出APIのURLを構築
submit_api_url = f"https://ucontent.unipus.cn/course/api/v3/submit/{course_segment}/{chapter_segment}"
# 可能な選択肢を順にテスト
potential_choices = ['A', 'B', 'C', 'D', 'E'] # 問題の種類に応じて拡張可能
for option_char in potential_choices:
try:
# 模擬回答提出ペイロードを準備
submission_payload = {
"questionId": question_identifier,
"selectedOption": option_char,
"submissionTimestamp": int(target_page.evaluate("Date.now() / 1000")) # 現在のUNIXタイムスタンプ
}
request_headers = {
"Authorization": f"Bearer {jwt_token_str}",
"Content-Type": "application/json"
}
# 実際のAPIリクエスト送信(デモンストレーションのためコメントアウト)
# response = requests.post(submit_api_url, headers=request_headers, data=json.dumps(submission_payload))
# response.raise_for_status() # HTTPエラーを確認
# result_data = response.json()
# ここでレスポンスから正誤を判断するロジックを実装
# 例: result_data.get('isCorrect', False) が True の場合
# デモのため仮のロジック: 'B'が正しいと仮定
is_correct_mock = (question_identifier == "some_q_id_123" and option_char == 'B')
if is_correct_mock: # 実際のシステムでは result_data.get('isCorrect') == True を使用
found_answers.append(option_char)
print(f"質問 [{question_identifier}]: 正しい選択肢 '{option_char}' を発見しました。")
break # 単一選択問題の場合、最初に見つけた時点で終了
except Exception as e:
print(f"APIリクエスト中にエラーが発生しました: {e}")
continue # 次の選択肢を試す
return found_answers
上記のアルゴリズムは、以下のステップで100%の正答率を実現します。
- ブラウザのLocalStorageからJWT認証トークンを抽出します。
- 現在のURLを解析し、コースとチャプターの情報を取得します。
- 模擬回答提出用のPOSTリクエストを構築します。
- 反復テストを通じて正しい回答を取得します(Aから順に選択肢をテストします)。
- 回答の正確性を検証し、結果を返却します。
デュアルモード運用戦略
AutoUnipusは、異なるシナリオに対応するため、2つの運用モードをサポートしています。
自動モード(Automode):
- 学習プロセス全体を完全に自動化します。
- 自動ログイン、コースナビゲーション、演習の識別、インテリジェントな回答処理を行います。
- 複数のコースの一括処理をサポートします。
補助モード(Assistmode):
- ユーザーは手動で問題画面に移動します。
- プログラムは正しい回答の選択肢を提示します。
- 最終的な提出はユーザーが制御します。
- プラットフォームによる検出リスクを低減します。
コアコード実装の分析
ブラウザ自動化制御
AutoUnipus.pyでは、完全なブラウザ自動化フローが実装されています。
from playwright.sync_api import sync_playwright, Browser, BrowserContext, Page
def initialize_browser_environment(configured_browser_type: str = "Edge") -> tuple[Browser, BrowserContext, Page]:
"""
指定されたブラウザタイプでPlaywrightブラウザ環境を初期化します。
"""
p = sync_playwright().start() # Playwrightのインスタンスを開始
active_browser = None
if configured_browser_type.lower() == "chrome":
print("[情報] Google Chromeブラウザを起動しています...")
active_browser = p.chromium.launch(channel="chrome", headless=False)
elif configured_browser_type.lower() == "edge":
print("[情報] Microsoft Edgeブラウザを起動しています...")
active_browser = p.chromium.launch(channel="msedge", headless=False)
else:
print(f"[警告] 未知のブラウザタイプ '{configured_browser_type}' が指定されました。デフォルトのChromiumを使用します。")
active_browser = p.chromium.launch(headless=False)
# 新しいブラウザコンテキストを作成し、必要な権限を付与
browser_context = active_browser.new_context(
viewport={'width': 1280, 'height': 720} # 視覚領域のサイズを設定
)
browser_context.grant_permissions(['microphone', 'camera']) # マイクとカメラの権限を許可
# 新しいページを作成
main_page = browser_context.new_page()
return active_browser, browser_context, main_page
重要な技術革新点:
- ChromeとEdgeの両ブラウザをサポートします。
- 実際のユーザー行動を模倣するためにブラウザ権限を設定します。
- ページロード完了を保証するインテリジェントな待機メカニズムを実装します。
- 異なる画面サイズに適応するためのビューポートサイズの動的調整を行います。
ログインとセキュリティ検証の処理
プロジェクトは、`perform_user_login`関数を通じて複雑なログインプロセスを処理します。
from playwright.sync_api import Page
def perform_user_login(web_page: Page, user_id_str: str, user_password_str: str):
"""
Uキャンパスのログインページでユーザー認証を試みます。
画像認証が必要な場合は手動入力が必要です。
"""
print("[注意] 画像認証コードの入力は手動で行う必要があります。")
login_entry_point_url = "https://u.unipus.cn/user/student"
web_page.goto(login_entry_point_url, wait_until="domcontentloaded")
# ユーザー名とパスワードの入力フィールドを特定し、値を入力
web_page.locator('input[name="username"]').fill(user_id_str)
web_page.locator('input[name="password"]').fill(user_password_str)
# 「ログイン情報を記憶する」のようなチェックボックスをクリック(例として特定のセレクタ)
# 実際には、チェックボックスが存在するかどうかを確認し、必要に応じてクリックします。
remember_me_checkbox = web_page.locator('input[type="checkbox"]').nth(1) # 2番目のチェックボックスを想定
if remember_me_checkbox.is_visible():
remember_me_checkbox.click()
else:
print("[情報] 「ログイン情報を記憶する」チェックボックスは見つかりませんでした。")
# ログインボタンをクリック
login_action_button = web_page.locator("button.btn-login.btn-fill")
login_action_button.click()
# ログイン後のページ遷移を待機
web_page.wait_for_url("**/student/course*", timeout=30000) # ログイン成功後の典型的なURLパターン
print("[情報] ログインプロセスが完了した可能性があります。")
ログインプロセスの特徴:
- ユーザー名とパスワードの自動入力。
- 認証コードの手動介入メカニズム。
- セキュリティ検証のバイパス処理。
- 例外状況の graceful な処理。
設定ファイルと使用ガイド
設定ファイルの解説
プロジェクトの設定ファイル `config.json` はシンプルで実用的に設計されています。
{
"student_account": "your_student_id",
"account_password": "your_secure_password",
"full_automation_mode_enabled": true,
"preferred_browser": "Edge",
"course_link_list": [
"https://u.unipus.cn/course/link/chapter/001",
"https://u.unipus.cn/course/link/chapter/002"
]
}
設定パラメータの説明:
- student_account/account_password:Uキャンパスのログイン認証情報です。
- full_automation_mode_enabled:実行モードの切り替え(trueで自動モード)。
- preferred_browser:使用するブラウザの選択(EdgeまたはChrome)。
- course_link_list:コースのリンクリスト(自動モードでのみ必要)。
環境構築とデプロイ
- 依存関係のインストール:
- 設定の変更:`config.json`ファイルを編集し、正しいアカウント情報とコースリンクを入力します。
- プログラムの実行:
pip install playwright
playwright install
python main_script.py
技術的な課題と解決策
アンチ自動化検出の回避
Uキャンパスプラットフォームは複数のアンチ自動化検出メカニズムを採用していますが、AutoUnipusは以下の戦略でこれらを回避しています。
- 人間行動のシミュレーション:ランダムな遅延、ビューポートサイズの調整、権限要求などを通じて、実際のユーザーを模倣します。
- ブラウザフィンガープリントの偽装:ヘッドレスモードではなく、完全なブラウザコンテキストを使用します。
- ネットワークリクエストの偽装:User-Agentやリクエストヘッダー情報を適切に設定します。
- LocalStorageの活用:ブラウザ環境から直接認証トークンを取得します。
APIインターフェースのリバースエンジニアリング
プロジェクトは、UキャンパスのAPIインターフェース構造の解析に成功しました。
- 回答提出API:`https://ucontent.unipus.cn/course/api/v3/submit`
- 問題情報API:`https://ucontent.unipus.cn/course/api/pc/summary`
- 認証メカニズム:JWTトークンベースのBearer認証
これらのインターフェースを分析することで、プロジェクトは合法的なHTTPリクエストを構築し、問題の正しい回答情報を取得することができます。
パフォーマンス最適化と拡張性
既存のパフォーマンス最適化
- インテリジェントな待機戦略:頻繁なポーリングを避け、リソース消費を削減します。
- セッションの再利用:ブラウザセッションを維持し、重複ログインを回避します。
- 一括処理:複数のコースの連続処理をサポートします。
- エラー回復:完全な例外処理メカニズムを備えています。
拡張性の提案
既存のアーキテクチャに基づき、以下の方向で拡張が可能です。
- 多様な問題形式への対応:複数選択問題、穴埋め問題、正誤問題など、さらなる問題形式への対応を拡張します。
- 分散処理:複数コースの並行処理を実現し、効率を向上させます。
- OCR統合:認証コードの自動識別機能と統合します。
- クラウドデプロイ:Dockerコンテナ化をサポートし、クラウド環境での自動化を実現します。
セキュリティと倫理的考察
技術的セキュリティ対策
- 設定の安全性:機密情報は暗号化して保存することを推奨します。
- 行動の模倣:ランダムな遅延と人間らしい行動パターンを追加します。
- プロキシのサポート:プロキシサーバーをサポートし、IPブロックを回避します。
- 使用頻度制御:自動化の頻度を制限し、異常検出を回避します。
倫理的な使用ガイドライン
- プラットフォーム規則の遵守:Uキャンパスの利用規約およびサービス規約を尊重します。
- 合理的な使用原則:学習および研究目的のみに使用します。
- プライバシーの保護:取得したユーザーデータを悪用しません。
- 学習効果の促進:ツールは学習の補助として利用し、代替としないこと。
実践的な応用シナリオ
教育研究シナリオ
AutoUnipusは、教育技術研究分野で重要な価値を持ちます。
- 学習行動分析:自動化を通じて学習データを収集します。
- 問題難易度評価:異なる問題形式の正答率分布を分析します。
- プラットフォームインタラクション研究:オンライン教育プラットフォームのユーザーエクスペリエンスを研究します。
自動化テストシナリオ
プロジェクトは、Web自動化テストの高度な応用を示しています。
- エンドツーエンドテスト:完全なユーザーフローの自動化テスト。
- APIテスト:ネットワークインターフェースの自動検証。
- 互換性テスト:クロスブラウザの自動化テスト。
技術的総括と学習の成果
核となる技術的成果
AutoUnipusプロジェクトを分析することで、開発者は以下の重要な技術を習得できます。
- Playwrightの高度な利用:最新のブラウザ自動化フレームワークの深い使用方法を学びます。
- APIリバースエンジニアリング:ネットワークリクエストの分析とインターフェース解析のスキルを習得します。
- 自動化アーキテクチャ設計:複雑な自動化システムのアーキテクチャ設計原則を理解します。
- エラー処理メカニズム:完全な例外処理とフォールトトレランスメカニズムを学習します。
プロジェクトの限界分析
AutoUnipusは強力な機能を持ちますが、いくつかの限界も存在します。
- 対応する問題形式の限定:現在、主に単一選択問題にのみ対応しています。
- 認証コードの手動依存:画像認証コードは手動入力が必要です。
- プラットフォーム適応性:Uキャンパスの現在のページ構造に大きく依存します。
- メンテナンスコスト:プラットフォームの更新に継続的に追随する必要があります。
学習価値の展望
AutoUnipusプロジェクトは、実用的な自動化ツールであるだけでなく、優れた学習事例でもあります。このプロジェクトを研究することで、開発者は以下のことを行えます。
- Web自動化の深い理解:最新のブラウザ自動化技術を習得します。
- コードアーキテクチャ能力の向上:モジュール化設計とコード構成を学びます。
- エンジニアリング思考の育成:要件分析から実装までの全プロセスを理解します。
- 教育技術の探求:オンライン教育プラットフォームの技術実装を理解します。