CAPTCHA 탐색적 테스트

리뷰 앱 및 로컬 개발 환경(GDK)에서 CAPTCHA를 신뢰성 있게 테스트할 수 있습니다.

항상 다음을 수행할 수 있습니다:

  • 지원되는 경우 reCAPTCHA가 표시되도록 강제로 설정할 수 있습니다.
  • 거리 표지판 이미지를 찾아 선택하는 대신 체크박스를 표시하도록 강제로 설정할 수 있습니다.

테스트를 설정하려면 이 페이지의 구성을 따르세요.

적절한 테스트 데이터 사용

스팸/CAPTCHA가 활성화된 시나리오를 테스트하는지 확인하세요. 예를 들어:

공용 스니펫을 편집하고 있는지 확인하세요. 스팸 확인은 공용 스니펫에서만 수행됩니다.

기능 플래그 활성화

스팸/CAPTCHA 지원이 기능 플래그 뒤에 있는 경우 관련 기능 플래그를 활성화하세요.

Akismet 및 reCAPTCHA 설정

  1. reCAPTCHA를 설정하려면:
    1. GitLab reCAPTCHA 문서를 검토하세요.
    2. Google의 reCAPTCHA 문서에서 안내에 따라 Google의 공식 테스트 reCAPTCHA 자격 증명을 얻으세요.
      1. 사이트 키로 다음을 사용하세요: 6LeIxAcTAAAAAJcZVRqyHh71UMIEGNQ_MXjiZKhI
      2. 비밀 키로 다음을 사용하세요: 6LeIxAcTAAAAAGG-vFI1TnRWxMZNFuojJ4WifJWe
    3. 관리자 -> 설정 -> 보고 설정으로 이동하세요: http://gdk.test:3000/admin/application_settings/reporting#js-spam-settings
    4. 스팸 및 안티봇 보호 섹션을 확장하세요.
    5. reCAPTCHA 활성화를 선택하세요. 테스트하는 기능이 아닌 한 로그인에 대한 활성화는 필요하지 않습니다.
    6. 사이트 키비밀 키를 입력하세요.
  2. Akismet을 설정하려면:
    1. Akismet에 대한 GitLab 문서를 검토하세요.
    2. Akismet API 키를 얻으세요. Akismet에서 테스트 키를 신청할 수 있습니다. 가입할 때 로컬 호스트(예: gdk.test) 및 이메일을 입력해야 합니다.
    3. GitLab Akismet 설정 페이지로 이동하세요. 예를 들어: http://gdk.test:3000/admin/application_settings/reporting#js-spam-settings
    4. Akismet을 활성화하고 Akismet API 키를 입력하세요.
  3. Akismet의 잘못된 스팸 확인을 강제로 설정하려면, Akismet API 문서Akismet 시작하기 문서를 참조하여 자세한 내용을 확인하세요:
    1. 다음 단계에 따라 스팸을 강제로 설정하기 위해 akismet-guaranteed-spam@example.com을 작성자 이메일로 사용할 수 있습니다:
      1. 사용자 이메일 설정으로 이동하세요: http://gdk.test:3000/-/profile/emails
      2. 관리자 사용자에 대한 추가 이메일로 akismet-guaranteed-spam@example.com을 추가하세요.
      3. Rails 콘솔에서 확인하세요: bin/rails c -> User.find_by_username('root').emails.last.confirm
      4. 이 확인된 이메일을 기본 이메일로 전환하세요:
        1. 아바타 드롭다운 목록 -> 프로필 편집 -> 기본 설정으로 이동하세요.
        2. 이메일akismet-guaranteed-spam@example.com을 입력하여 admin@example.com을 교체하세요.
        3. 변경 사항을 저장하려면 프로필 설정 업데이트를 선택하세요.

웹 UI에서 테스트

위의 모든 구성이 완료되면 CAPTCHA를 테스트할 수 있습니다. 다음과 같은 CAPTCHA 지원이 이미 있는 애플리케이션의 영역에서 테스트하세요:

  • 이슈 생성 또는 편집.
  • 공개 스니펫 생성 또는 편집. 공개 스니펫만 스팸 검사 대상입니다.

개발 환경에서 테스트

위의 단계를 통해 스팸 플래깅 + CAPTCHA를 강제로 활성화한 후, 스팸으로 보호된 모델/컨트롤러 작업에서 동작을 테스트할 수 있습니다.

CAPTCHA가 활성화된 상태에서 테스트 (CONDITIONAL_ALLOW verdict)

이 영역에서 CAPTCHA가 활성화된 경우, 양식을 다시 제출하기 전에 CAPTCHA 팝업 모달을 해결해야 합니다:

  • 관리자 -> 설정 -> 보고 -> 스팸
  • 봇 방지 -> reCAPTCHA 활성화

CAPTCHA가 비활성화된 상태에서 테스트 (“DISALLOW” verdict)

관리자 -> 설정 -> 보고 -> 스팸봇 방지 -> reCAPTCHA 활성화에서 CAPTCHA가 비활성화된 경우, CAPTCHA 팝업이 표시되지 않습니다. 양식을 전혀 제출할 수 없습니다.

reCAPTCHA를 렌더링하는 HTML 페이지

참고: Google의 공식 테스트 reCAPTCHA 자격 증명을 사용하면 Akismet 및 reCAPTCHA 설정하기에 나열된 대로, CAPTCHA 응답 문자열은 중요하지 않습니다. 어떤 문자열도 사용할 수 있습니다. 실제 유효한 키 쌍을 사용하는 경우, 유효한 CAPTCHA 응답을 얻기 위해 CAPTCHA를 해결해야 합니다. 이는 한 번만 수행할 수 있으며, 만료되기 전에만 가능합니다.

GraphQL Explorer(http://gdk.test:3000/-/graphql-explorer)를 통해 GraphQL API를 직접 테스트하려면, 이 양식을 통해 reCAPTCHA 응답 문자열을 가져오세요: public/recaptcha.html (http://gdk.test:3000/recaptcha.html):

<html>
<head>
  <title>reCAPTCHA 데모: onload 콜백 후 명시적 렌더링</title>
  <script type="text/javascript">
  var onloadCallback = function() {
    grecaptcha.render('html_element', {
      'sitekey' : '6Ld05AsaAAAAAMsm1yTUp4qsdFARN15rQJPPqv6i'
    });
  };
  function onSubmit() {
    window.document.getElementById('recaptchaResponse').innerHTML = grecaptcha.getResponse();
    return false;
  }
  </script>
</head>
<body>
<form onsubmit="return onSubmit()">
  <div id="html_element"></div>
  <br>
  <input type="submit" value="제출">
</form>
<div>
  <h1>recaptchaResponse:</h1>
  <div id="recaptchaResponse"></div>
</div>
<script src="https://www.google.com/recaptcha/api.js?onload=onloadCallback&render=explicit"
        async defer>
</script>
</body>
</html>

스팸/CAPTCHA API 탐색적 테스트 예제

이 섹션에서는 REST 및 GraphQL API의 스팸 및 CAPTCHA 동작에 대한 다양한 시나리오에 대한 수동 탐색적 테스트를 수행하는 데 필요한 단계를 설명합니다.

전제 조건으로는 다음을 수행해야 합니다:

  1. 개발 환경에서 스팸 및 CAPTCHA를 활성화하고, CAPTCHA가 필요한 양식 제출을 강제하기 위해 위의 모든 단계를 수행합니다.

  2. /public 디렉토리 아래에 CAPTCHA를 렌더링하는 HTML 페이지를 생성하고, 유효한 CAPTCHA 응답 문자열을 수동으로 생성하는 양식이 포함된 페이지를 만들어야 합니다. Google의 공식 테스트 reCAPTCHA 자격 증명을 사용하면 Akismet 및 reCAPTCHA 설정하기에 나열된 대로, CAPTCHA 응답 문자열의 내용은 중요하지 않습니다.

  3. 관리자 -> 설정 -> 보고 -> 스팸 및 봇 방지로 이동합니다.

  4. 시나리오에 따라 reCAPTCHA 활성화Akismet 활성화를 선택하거나 해제합니다.

다음 예제는 스니펫 생성을 예로 사용합니다. 스니펫 업데이트, 이슈 생성 또는 이슈 업데이트도 사용할 수 있습니다. 이슈와 스니펫만이 완전한 스팸 및 CAPTCHA 지원이 제공되는 모델입니다.

초기 설정

  1. API 토큰을 생성합니다.
  2. REST 명령어를 위해 터미널에서 내보냅니다: export PRIVATE_TOKEN=<your_api_token>
  3. GraphiQL 탐색기를 사용하기 전에 localhost:3000에서 GitLab 개발 환경에 로그인되어 있는지 확인하세요. 인증된 사용자가 GraphQL 쿼리를 실행하기 위한 권한으로 사용되기 때문입니다.
  4. GraphQL 예제를 위해 http://localhost:3000/-/graphql-explorer에 있는 GraphiQL 탐색기를 사용하세요.
  5. HTTP 응답 헤더와 상태 코드를 출력하려면 curl--include (-i) 옵션을 사용하세요.

시나리오: Akismet 및 CAPTCHA 활성화

이 예제에서는 Akismet 및 CAPTCHA가 활성화되어 있습니다:

  1. 초기 요청.

초기 요청

이 초기 요청은 CAPTCHA 응답이 제공되지 않아 실패합니다.

REST 요청:

curl --request POST --header "PRIVATE-TOKEN: $PRIVATE_TOKEN" "http://localhost:3000/api/v4/snippets?title=Title&file_name=FileName&content=Content&visibility=public"

REST 응답:

{"needs_captcha_response":true,"spam_log_id":42,"captcha_site_key":"XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX","message":{"error":"귀하의 스니펫이 스팸으로 인식되었습니다. 콘텐츠를 변경하거나 reCAPTCHA를 해결하여 진행하세요."}}

GraphQL 요청:

mutation {
    createSnippet(input: {
        title: "Title"
        visibilityLevel: public
        blobActions: [
            {
                action: create
                filePath: "BlobPath"
                content: "BlobContent"
            }
        ]
    }) {
        snippet {
            id
            title
        }
        errors
    }
}

GraphQL 응답:

{
  "data": {
    "createSnippet": null
  },
  "errors": [
    {
      "message": "요청이 거부되었습니다. CAPTCHA 문제를 해결하고 다시 시도하세요.",
      "locations": [
        {
          "line": 22,
          "column": 5
        }
      ],
      "path": [
        "createSnippet"
      ],
      "extensions": {
        "needs_captcha_response": true,
        "spam_log_id": 140,
        "captcha_site_key": "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
      }
    }
  ]
}

두 번째 요청

이 요청은 CAPTCHA 응답이 제공되어 성공합니다.

REST 요청:

export CAPTCHA_RESPONSE="<HTML 페이지에서 CAPTCHA를 렌더링하여 얻은 CAPTCHA 응답>"
export SPAM_LOG_ID="<초기 REST 응답에서 얻은 spam_log_id>"
curl --request POST --header "PRIVATE-TOKEN: $PRIVATE_TOKEN" --header "X-GitLab-Captcha-Response: $CAPTCHA_RESPONSE" --header "X-GitLab-Spam-Log-Id: $SPAM_LOG_ID" "http://localhost:3000/api/v4/snippets?title=Title&file_name=FileName&content=Content&visibility=public"

REST 응답:

{"id":42,"title":"Title","description":null,"visibility":"public", "other_fields": "..."}

GraphQL 요청:

참고: GitLab GraphiQL 구현은 헤더 전달을 허용하지 않으므로 이를 curl 쿼리로 작성해야 합니다. 여기서 --data-binary는 JSON에 포함된 쌍따옴표를 올바르게 처리하는 데 사용됩니다.

export CAPTCHA_RESPONSE="<HTML 페이지에서 CAPTCHA를 렌더링하여 얻은 CAPTCHA 응답>"
export SPAM_LOG_ID="<초기 REST 응답에서 얻은 spam_log_id>"
curl --include "http://localhost:3000/api/graphql" --header "Authorization: Bearer $PRIVATE_TOKEN" --header "Content-Type: application/json" --header "X-GitLab-Captcha-Response: $CAPTCHA_RESPONSE" --header "X-GitLab-Spam-Log-Id: $SPAM_LOG_ID" --request POST --data-binary '{"query": "mutation {createSnippet(input: {title: \"Title\" visibilityLevel: public blobActions: [ { action: create filePath: \"BlobPath\" content: \"BlobContent\" } ] }) { snippet { id title } errors }}"}'

GraphQL 응답:

{"data":{"createSnippet":{"snippet":{"id":"gid://gitlab/PersonalSnippet/42","title":"Title"},"errors":[]}}}

시나리오: Akismet 활성화, CAPTCHA 비활성화

이 시나리오에서는 위에 설명된 대로 관리 영역 설정에서 Enable reCAPTCHA를 해제해야 합니다.

CAPTCHA가 활성화되지 않은 경우 잠재적인 스팸으로 표시된 요청은 재전송할 수 있는 기회 없이 실패합니다.

비록 CAPTCHA가 활성화되고 성공적으로 해결되었다면 다시 제출할 수 있었던 요청일지라도 말입니다.

REST 요청은 CAPTCHA가 활성화된 경우와 동일합니다:

curl --request POST --header "PRIVATE-TOKEN: $PRIVATE_TOKEN" "http://localhost:3000/api/v4/snippets?title=Title&file_name=FileName&content=Content&visibility=public"

REST 응답:

{"message":{"error":"귀하의 스니펫이 스팸으로 인식되어 폐기되었습니다."}}

GraphQL 요청:

mutation {
    createSnippet(input: {
        title: "Title"
        visibilityLevel: public
        blobActions: [
            {
                action: create
                filePath: "BlobPath"
                content: "BlobContent"
            }
        ]
    }) {
        snippet {
            id
            title
        }
        errors
    }
}

GraphQL 응답:

{
  "data": {
    "createSnippet": null
  },
  "errors": [
    {
      "message": "요청이 거부되었습니다. 스팸이 감지되었습니다.",
      "locations": [
        {
          "line": 22,
          "column": 5
        }
      ],
      "path": [
        "createSnippet"
      ],
      "extensions": {
        "spam": true
      }
    }
  ]
}

시나리오: allow_possible_spam 애플리케이션 설정 활성화

allow_possible_spam 애플리케이션 설정이 활성화 된 경우, API는 200 응답을 반환합니다.

유효한 요청은 성공하며, 요청이 스팸으로 간주되더라도 CAPTCHA가 표시되지 않습니다.