{"id":19623805,"url":"https://github.com/appleple/acms-recaptcha","last_synced_at":"2026-04-07T13:01:07.265Z","repository":{"id":41990816,"uuid":"129075232","full_name":"appleple/acms-recaptcha","owner":"appleple","description":"a-blog cms の 拡張アプリ「reCAPTCHA for a-blog cms」を使うと、GoogleのreCAPTCHAを使用してボットからの フォームアクセスを防御することが出来るようになります。","archived":false,"fork":false,"pushed_at":"2025-10-16T09:14:00.000Z","size":2148,"stargazers_count":4,"open_issues_count":0,"forks_count":0,"subscribers_count":4,"default_branch":"master","last_synced_at":"2025-10-17T11:41:32.004Z","etag":null,"topics":["ablog-cms","acms","php","recaptcha"],"latest_commit_sha":null,"homepage":"","language":"PHP","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/appleple.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2018-04-11T10:16:20.000Z","updated_at":"2025-10-16T09:14:03.000Z","dependencies_parsed_at":"2024-11-11T11:37:52.045Z","dependency_job_id":"3c0dd476-3271-4225-b18e-c46d1521bbaa","html_url":"https://github.com/appleple/acms-recaptcha","commit_stats":null,"previous_names":[],"tags_count":7,"template":false,"template_full_name":null,"purl":"pkg:github/appleple/acms-recaptcha","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/appleple%2Facms-recaptcha","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/appleple%2Facms-recaptcha/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/appleple%2Facms-recaptcha/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/appleple%2Facms-recaptcha/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/appleple","download_url":"https://codeload.github.com/appleple/acms-recaptcha/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/appleple%2Facms-recaptcha/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":31513382,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-07T03:10:19.677Z","status":"ssl_error","status_checked_at":"2026-04-07T03:10:13.982Z","response_time":105,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.5:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["ablog-cms","acms","php","recaptcha"],"created_at":"2024-11-11T11:35:33.737Z","updated_at":"2026-04-07T13:01:07.249Z","avatar_url":"https://github.com/appleple.png","language":"PHP","funding_links":[],"categories":[],"sub_categories":[],"readme":"# reCAPTCHA V3 for a-blog cms\n\na-blog cms の 拡張アプリ「reCAPTCHA for a-blog cms」を使うと、GoogleのreCAPTCHAを使用してボットからの\nフォームアクセスを防御することが出来るようになります。\n\n## ダウンロード\n\n[reCAPTCHA for a-blog cms](https://github.com/appleple/acms-recaptcha/releases/latest/download/reCAPTCHA.zip) \n\n利用するためには最新リリースから zip をダウンロード後、解凍して **extension/plugins** に設置してください。\n\n* extension/plugins/ReCaptcha\n\n## 動作環境\n\n- a-blog cms: Ver. 3.0.x – 3.2.x (3.3+ not tested yet)\n- PHP: 7.2.5 – 8.4 (8.5+ not tested yet)\n\n\n## インストール\n\n管理ページ \u003e 拡張アプリより「拡張アプリ管理」のページに移動します。そのページより下の図のようにreCAPTCHAをインストールします。\n\n![アプリ一覧](./images/app-index.png \"アプリ一覧\")\n\n## API登録とキーの取得\n\nまずreCAPTCHAを導入するために、[reCAPTCHA](https://www.google.com/recaptcha/admin#list) にアクセスして、必要な情報を取得します。\n\n**ReCAPTCHA V3** を選択し、Domainを登録します。\n\n![Register a new site](./images/api-input.png \"Register a new site\")\n\n**Site key** と **Secret key** をコピーしてメモしておきます。\n\n![Site key と　Secret key の取得](./images/api-input2.png \"Site key と　Secret key の取得\")\n\n### メモする情報\n\n* Site key\n* Secret key\n\n## 使い方\n\n### 設定\n\n管理ページ \u003e reCAPTCHA に移動し、**Site key** と **Secret key** を設定します。\n\n![拡張アプリ設定画面](./images/setting-plugin.png \"拡張アプリ設定画面\")\n\n管理ページ \u003e フォーム に移動し、reCAPTCHA を利用したいフォームIDから **reCAPTCHA連携** を有効にします。\n\n![フォーム設定画面](./images/setting-form.png \"フォーム設定画面\")\n\n### JavaScript\n\n以下コードを フォームテンプレートのhead要素内に読み込んでください。\n\n```\n\u003c!-- BEGIN_MODULE Admin_InjectTemplate id=\"recaptcha-js\" --\u003e\n\u003c!-- END_MODULE Admin_InjectTemplate --\u003e\n```\n\nこのモジュールにより、Google reCAPTCHA API スクリプトと `recaptcha.js` が自動で注入されます。キャッシュバスティング用のクエリも自動的に付与されます。\n\n#### 旧来の書き方（後方互換）\n\n`Admin_InjectTemplate` を使わずに直接書くこともできます。`ACMS.Config.ReCaptcha` を設定する既存のコードも引き続き動作します。\n\n```\n\u003c!-- BEGIN_MODULE ReCaptcha --\u003e\n\u003cscript src=\"https://www.google.com/recaptcha/api.js?render={sitekey}\"\u003e\u003c/script\u003e\n\u003cscript src=\"/extension/plugins/ReCaptcha/assets/recaptcha.js\"\u003e\u003c/script\u003e\n\u003cscript\u003e\n  if (window.ACMS === undefined) {\n    ACMS = {};\n    ACMS.Config = {};\n    ACMS.Config.ReCaptcha = '{sitekey}';\n  } else {\n    ACMS.Ready(function () {\n      ACMS.Config.ReCaptcha = '{sitekey}';\n    });\n  }\n\u003c/script\u003e\n\u003c!-- END_MODULE ReCaptcha --\u003e\n```\n\n### HTML\n\nフォーム送信時（確認画面）の form要素を修正します。\u003cbr\u003e\nform要素のclass属性に **js-recaptcha-form** クラスを追加します。\n\n```\n\u003cform action=\"thanks.html\" method=\"post\" enctype=\"multipart/form-data\" class=\"js-recaptcha-form\"\u003e\n\t...\n\t\u003cinput type=\"submit\" name=\"ACMS_POST_Form_Submit\" value=\"送信する\"/\u003e\n\u003c/form\u003e\n```\n\n### エラー表示\n\neCaptchaによってロボットだと認識された場合は、Formモジュールの **step#forbidden** ブロックが表示されます。\n\n```\n\u003c!-- BEGIN step#forbidden --\u003e\n\t\u003cp\u003e不正なアクセスです。\u003c/p\u003e\n\u003c!-- END step#forbidden --\u003e\n```\n\n### 確認\n\nクライアントサイドは完成です。フォームの確認画面まで行くと、ReCaptchaのロゴが右下に表示されていると思います。実際にフォームを送信して、送信できるか確認しましょう。\n\n![チェック画面](./images/result.png \"チェック画面\")\n\n### 注意\n\nconfig.server.phpでHOOKを有効にしておく必要があります。\n\n```\ndefine('HOOK_ENABLE', 1);\n```\n\n---\n\n## 会員機能・ログイン認証への reCAPTCHA 適用\n\na-blog cms Ver. 3.0.0 以降では、コンタクトフォームだけでなく **会員ログイン・会員登録・パスワードリセット・2段階認証リカバリー** などの認証フォームにも reCAPTCHA を適用できます。\n\n### 概要\n\n- 対象ページを管理画面の設定で有効にするだけで機能します\n- reCAPTCHA スクリプト（Google API + recaptcha.js）は対象ページの `\u003c/head\u003e` 直前に **自動で注入** されるため、テンプレートへの JavaScript 記述は不要です\n- 検証に失敗した場合は **IllegalAccess** エラーとして処理されます\n\n### 設定方法\n\n管理ページ \u003e reCAPTCHA に移動し、適用したいフォームのチェックボックスを有効にして保存します。\n\n#### Ver. 3.1.x 以降（Member / Member_Admin 名前空間）\n\n**会員機能の設定**\n\n| 設定項目 | 対象モジュール | コンフィグキー |\n|---|---|---|\n| サインイン認証 | `ACMS_POST_Member_Signin` | `google_recaptcha_member_signin` |\n| 会員登録 | `ACMS_POST_Member_Signup_Submit` | `google_recaptcha_member_signup` |\n| パスワードリセット | `ACMS_POST_Member_ResetPassword` | `google_recaptcha_member_reset_password` |\n| 2段階認証リカバリー | `ACMS_POST_Member_Tfa_Recovery` | `google_recaptcha_member_tfa_recovery` |\n\n\u003e `ACMS_POST_Member_Signin` を継承する `Member_SigninWithEmail`（認証メール送信）/ `Member_SigninWithVerifyCode`（確認コード入力）も自動的に対象となります。\n\u003e `Member_Tfa_Auth`（2段階認証コード入力）は id/pass 認証済みのステップのため除外されます。\n\n**管理ログイン機能の設定**\n\n| 設定項目 | 対象モジュール | コンフィグキー |\n|---|---|---|\n| ログイン認証 | `ACMS_POST_Member_Admin_Login` | `google_recaptcha_member_admin_login` |\n| パスワードリセット | `ACMS_POST_Member_Admin_ResetPassword` | `google_recaptcha_member_admin_reset_password` |\n| 2段階認証リカバリー | `ACMS_POST_Member_Admin_Tfa_Recovery` | `google_recaptcha_member_admin_tfa_recovery` |\n\n`ACMS_POST_Member_Admin_Login` を継承する `Admin_LoginWithEmail`（認証メール送信）/ `Admin_LoginWithVerifyCode`（確認コード入力）も自動的に対象となります。\n`Admin_Tfa_Auth`（2段階認証コード入力）は id/pass 認証済みのステップのため除外されます。\n\n#### Ver. 3.0.x（Login 名前空間）\n\n**認証機能の設定**\n\n| 設定項目 | 対象モジュール | コンフィグキー |\n|---|---|---|\n| ログイン認証 | `ACMS_POST_Login_Auth` | `google_recaptcha_login_auth` |\n| 会員登録 | `ACMS_POST_Login_Subscribe` | `google_recaptcha_login_subscribe` |\n| パスワードリセット | `ACMS_POST_Login_Remind` | `google_recaptcha_login_remind` |\n| 2段階認証リカバリー | `ACMS_POST_Login_Tfa_Recovery` | `google_recaptcha_login_tfa_recovery` |\n\n### スクリプトの自動注入について\n\n有効な設定がある場合、プラグインが対象ページの `\u003c/head\u003e` 直前に以下を自動で挿入します。\n\n```html\n\u003cscript src=\"https://www.google.com/recaptcha/api.js?render={sitekey}\"\u003e\u003c/script\u003e\n\u003cscript id=\"acms-recaptcha-js\" src=\"{recaptcha.jsのパス}\" data-sitekey=\"{sitekey}\"\u003e\u003c/script\u003e\n```\n\nサイトキーは `data-sitekey` 属性で `recaptcha.js` に渡されます。`recaptcha.js` のパスにはキャッシュバスティング用のクエリが自動で付与されます。テンプレート側でのスクリプト読み込みは不要です。\n\n### エラー表示\n\nreCAPTCHA の検証に失敗した場合、`ACMS_GET_SystemError` モジュールの `IllegalAccess` ブロックが表示されます。\n\n認証フォームのテンプレートに `SystemError` モジュールを配置し、`IllegalAccess` ブロックを定義してください。\n\n```html\n\u003c!-- BEGIN_MODULE SystemError --\u003e\n\u003c!-- BEGIN IllegalAccess --\u003e\n\u003cdiv role=\"alert\" class=\"acms-alert acms-alert-danger acms-alert-icon\"\u003e\n  \u003cspan class=\"acms-icon acms-icon-attention acms-alert-icon-before\" aria-hidden=\"true\"\u003e\u003c/span\u003e\n  不正なアクセスです。\n  \u003cbutton type=\"button\" class=\"js-acms-alert-close acms-alert-icon-after\" aria-label=\"アラートを閉じる\"\u003e×\u003c/button\u003e\n\u003c/div\u003e\n\u003c!-- END IllegalAccess --\u003e\n\u003c!-- END_MODULE SystemError --\u003e\n```\n\n`SystemError` モジュールは他のシステムエラー（CSRF トークン切れなど）にも使われるため、以下のようにすべてのブロックをまとめて定義したテンプレートを `include` として使い回すのが一般的です。\n\n```html\n\u003c!-- BEGIN_MODULE SystemError --\u003e\n\u003c!-- BEGIN IllegalPostData --\u003e\n\u003cdiv role=\"alert\" class=\"acms-alert acms-alert-danger acms-alert-icon\"\u003e\n  \u003cspan class=\"acms-icon acms-icon-attention acms-alert-icon-before\" aria-hidden=\"true\"\u003e\u003c/span\u003e\n  送信データが不完全です。\n  \u003cbutton type=\"button\" class=\"js-acms-alert-close acms-alert-icon-after\" aria-label=\"アラートを閉じる\"\u003e×\u003c/button\u003e\n\u003c/div\u003e\n\u003c!-- END IllegalPostData --\u003e\n\u003c!-- BEGIN CsrfTokenExpired --\u003e\n\u003cdiv role=\"alert\" class=\"acms-alert acms-alert-danger acms-alert-icon\"\u003e\n  \u003cspan class=\"acms-icon acms-icon-attention acms-alert-icon-before\" aria-hidden=\"true\"\u003e\u003c/span\u003e\n  ページの有効期限が切れています。\n  \u003cbutton type=\"button\" class=\"js-acms-alert-close acms-alert-icon-after\" aria-label=\"アラートを閉じる\"\u003e×\u003c/button\u003e\n\u003c/div\u003e\n\u003c!-- END CsrfTokenExpired --\u003e\n\u003c!-- BEGIN DoubleTransmission --\u003e\n\u003cdiv role=\"alert\" class=\"acms-alert acms-alert-danger acms-alert-icon\"\u003e\n  \u003cspan class=\"acms-icon acms-icon-attention acms-alert-icon-before\" aria-hidden=\"true\"\u003e\u003c/span\u003e\n  連続送信は禁止されています。\n  \u003cbutton type=\"button\" class=\"js-acms-alert-close acms-alert-icon-after\" aria-label=\"アラートを閉じる\"\u003e×\u003c/button\u003e\n\u003c/div\u003e\n\u003c!-- END DoubleTransmission --\u003e\n\u003c!-- BEGIN IllegalAccess --\u003e\n\u003cdiv role=\"alert\" class=\"acms-alert acms-alert-danger acms-alert-icon\"\u003e\n  \u003cspan class=\"acms-icon acms-icon-attention acms-alert-icon-before\" aria-hidden=\"true\"\u003e\u003c/span\u003e\n  不正なアクセスです。\n  \u003cbutton type=\"button\" class=\"js-acms-alert-close acms-alert-icon-after\" aria-label=\"アラートを閉じる\"\u003e×\u003c/button\u003e\n\u003c/div\u003e\n\u003c!-- END IllegalAccess --\u003e\n\u003c!-- END_MODULE SystemError --\u003e\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fappleple%2Facms-recaptcha","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fappleple%2Facms-recaptcha","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fappleple%2Facms-recaptcha/lists"}