Javaと2 CAPTCHAを使用してrecaptcha v 2を簡単に解決する方法


こんな風に見たことある?

これは、正確にrecaptchaの種類のキャプチャです.
CAPTCHAは、ユーザーが人間かロボットであるかどうかチェックするために、多くのウェブサイトが使う挑戦反応です.
2 captchaはcaptchaの認識を提供する多くのサービスの一つです.
2 captchaはいくつかの課題を解決します、そして、recaptcha V 2はそれらの1つです.
recaptcha v 2はおそらく最も人気のある多くのサイトに採用されます.
この記事では、簡単にSDKを使用してrecaptcha v 2を解決する方法を示します.

いったんサインアップすると、リクエストの設定量を処理するために少量を支払う必要があります.
あなたは長い英数字であるAPIキーを見るべきです.

ウェブサイトでcaptchaをバイパスする簡単な方法を見ましょう.
2つのcaptcha githubにJavaコードを使用しますrepository .
これは私が作成したパッケージ構造です.
これがPOMです.XML :
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
   <modelVersion>4.0.0</modelVersion>

   <groupId>org.example</groupId>
   <artifactId>TwoCaptchaJava</artifactId>
   <version>1.0-SNAPSHOT</version>

   <properties>
       <maven.compiler.source>17</maven.compiler.source>
       <maven.compiler.target>17</maven.compiler.target>
   </properties>

   <licenses>
       <license>
           <name>MIT License</name>
           <url>http://www.opensource.org/licenses/mit-license.php</url>
           <distribution>repo</distribution>
       </license>
   </licenses>

   <developers>
       <developer>
           <email>[email protected]</email>
           <name>2captcha</name>
           <url>https://github.com/2captcha</url>
           <id>2captcha</id>
       </developer>
   </developers>

   <scm>
       <connection>scm:git:git://github.com/2captcha/2captcha-java.git</connection>
       <developerConnection>scm:git:[email protected]:2captcha/2captcha-java.git</developerConnection>
       <url>https://github.com/2captcha/2captcha-java</url>
   </scm>

   <distributionManagement>
       <repository>
           <id>ossrh</id>
           <url>https://oss.sonatype.org/service/local/staging/deploy/maven2</url>
       </repository>
       <snapshotRepository>
           <id>ossrh</id>
           <url>https://oss.sonatype.org/content/repositories/snapshots</url>
       </snapshotRepository>
   </distributionManagement>

   <dependencies>
       <dependency>
           <groupId>com.squareup.okhttp3</groupId>
           <artifactId>okhttp</artifactId>
           <version>4.7.2</version>
       </dependency>
       <dependency>
           <groupId>junit</groupId>
           <artifactId>junit</artifactId>
           <version>4.13.1</version>
           <scope>test</scope>
       </dependency>
       <dependency>
           <groupId>org.mockito</groupId>
           <artifactId>mockito-core</artifactId>
           <version>3.3.3</version>
           <scope>test</scope>
       </dependency>
       <dependency>
           <groupId>javax.servlet</groupId>
           <artifactId>javax.servlet-api</artifactId>
           <version>3.0.1</version>
           <scope>provided</scope>
       </dependency>
   </dependencies>

   <build>
       <plugins>
           <plugin>
               <groupId>org.apache.maven.plugins</groupId>
               <artifactId>maven-source-plugin</artifactId>
               <executions>
                   <execution>
                       <id>attach-sources</id>
                       <goals>
                           <goal>jar-no-fork</goal>
                       </goals>
                   </execution>
               </executions>
           </plugin>

           <plugin>
               <groupId>org.apache.maven.plugins</groupId>
               <artifactId>maven-javadoc-plugin</artifactId>
               <executions>
                   <execution>
                       <id>attach-javadocs</id>
                       <goals>
                           <goal>jar</goal>
                       </goals>
                   </execution>
               </executions>
           </plugin>

           <plugin>
               <groupId>org.apache.maven.plugins</groupId>
               <artifactId>maven-gpg-plugin</artifactId>
               <executions>
                   <execution>
                       <id>sign-artifacts</id>
                       <phase>verify</phase>
                       <goals>
                           <goal>sign</goal>
                       </goals>
                       <configuration>
                           <keyname>F8F9DA2268324C45C3A46015C273F1F4693E6F11</keyname>
                               <skip>true</skip>
                       </configuration>
                   </execution>
               </executions>
           </plugin>

       </plugins>
   </build>

</project>
apiclientは、接続に関するすべてを扱うクラスです.
package com.techwithmaddy.captcha;

import com.techwithmaddy.exception.ApiException;
import com.techwithmaddy.exception.NetworkException;
import okhttp3.FormBody;
import okhttp3.HttpUrl;
import okhttp3.MultipartBody;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.RequestBody;
import okhttp3.Response;

import java.io.File;
import java.nio.file.Files;
import java.util.Map;

public class ApiClient {

    /**
     * API server
     */
    private final String host = "2captcha.com";

    /**
     * Network client
     */
    private final OkHttpClient client = new OkHttpClient();

    /**
     * Sends captcha to /in.php
     *
     * @param params
     * @param files
     * @return
     * @throws Exception
     */
    public String in(Map<String, String> params, Map<String, File> files) throws Exception {
        HttpUrl.Builder url = new HttpUrl.Builder()
                .scheme("https")
                .host(host)
                .addPathSegment("in.php");

        RequestBody body;

        if (files.size() == 0) {
            FormBody.Builder form = new FormBody.Builder();
            params.forEach(form::add);
            body = form.build();
        } else {
            MultipartBody.Builder form = new MultipartBody.Builder();
            form.setType(MultipartBody.FORM);
            params.forEach(form::addFormDataPart);
            for (Map.Entry<String, File> entry : files.entrySet()) {
                byte[] fileBytes = Files.readAllBytes(entry.getValue().toPath());
                form.addFormDataPart(entry.getKey(), entry.getValue().getName(), RequestBody.create(fileBytes));
            }
            body = form.build();
        }

        Request request = new Request.Builder()
                .url(url.build())
                .post(body)
                .build();

        return execute(request);
    }

    /**
     * Does request to /res.php
     *
     * @param params
     * @return
     * @throws Exception
     */
    public String res(Map<String, String> params) throws Exception {
        HttpUrl.Builder url = new HttpUrl.Builder()
                .scheme("https")
                .host(host)
                .addPathSegment("res.php");

        params.forEach(url::addQueryParameter);

        Request request = new Request.Builder()
                .url(url.build())
                .build();

        return execute(request);
    }

    /**
     * Executes http request to api
     *
     * @param request
     * @return
     * @throws Exception
     */
    private String execute(Request request) throws Exception {
        try (Response response = client.newCall(request).execute()) {
            if (!response.isSuccessful()) {
                throw new NetworkException("Unexpected code " + response);
            }

            String body = response.body().string();

            if (body.startsWith("ERROR_")) {
                throw new ApiException(body);
            }

            return body;
        }
    }

}
Cattchaクラスをアプリケーションに追加しましょう.このクラスには、id、コード、params、およびファイルなどのcaptchasを構成する機能を記述するフィールドが異なります.
package com.techwithmaddy.captcha;

import java.io.File;
import java.util.HashMap;
import java.util.Map;

public abstract class Captcha {

   protected String id;
   protected String code;

   protected Map<String, String> params;
   protected Map<String, File> files;

   public Captcha() {
       params = new HashMap<>();
       files = new HashMap<>();
   }

   public String getId() {
       return id;
   }

   public void setId(String id) {
       this.id = id;
   }

   public String getCode() {
       return code;
   }

   public void setCode(String code) {
       this.code = code;
   }

   public void setProxy(String type, String uri) {
       params.put("proxy", uri);
       params.put("proxytype", type);
   }

   public void setSoftId(int softId) {
       params.put("soft_id", String.valueOf(softId));
   }

   public void setCallback(String callback) {
       params.put("pingback", callback);
   }

   public Map<String, String> getParams() {
       Map<String, String> params = new HashMap<String, String>(this.params);

       if (!params.containsKey("method")) {
           if (params.containsKey("body")) {
               params.put("method", "base64");
           } else {
               params.put("method", "post");
           }
       }

       return params;
   }

   public Map<String, File> getFiles() {
       return new HashMap<>(files);
   }

}
次に、Captchaクラスを拡張するRecaptchaクラスがあります.
このクラスには、recaptchaを解決するための3つの必須パラメータがあります.
  • サイトキー:このパラメーターは、開発者の設定で見つけることができます.
  • アクション:これは見つけるために挑戦することができますが、それは何かのような{action: do_something}
  • PageURL :あなたがrecaptchaを見るページの完全なURL.
  • package com.techwithmaddy.captcha;
    
    public class ReCaptcha extends Captcha {
    
       public ReCaptcha() {
           super();
           params.put("method", "userrecaptcha");
       }
    
       public void setSiteKey(String siteKey) {
           params.put("googlekey", siteKey);
       }
    
       public void setUrl(String url) {
           params.put("pageurl", url);
       }
    
       public void setInvisible(boolean invisible) {
           params.put("invisible", invisible ? "1" : "0");
       }
    
       public void setVersion(String version) {
           params.put("version", version);
       }
    
       public void setAction(String action) {
           params.put("action", action);
       }
    
       public void setScore(Double score) {
           params.put("min_score", String.valueOf(score));
       }
    
    }
    
    TwoCaptchaクラスはアプリケーションクラスでインスタンス化するために使用するクラスで、APIキーを解析します(実際には抽象クラスではありません).
    package com.techwithmaddy.captcha;
    
    import com.techwithmaddy.exception.ApiException;
    import com.techwithmaddy.exception.NetworkException;
    import com.techwithmaddy.exception.ValidationException;
    
    import java.io.File;
    import java.util.HashMap;
    import java.util.Map;
    import java.util.concurrent.TimeoutException;
    
    /**
    * Class com.techwithmaddy.captcha.TwoCaptcha
    */
    public class TwoCaptcha {
    
       /**
        * API KEY
        */
       private String apiKey;
    
       /**
        * ID of software developer. Developers who integrated their software
        * with our service get reward: 10% of spendings of their software users.
        */
       private int softId;
    
       /**
        * URL to which the result will be sent
        */
       private String callback;
    
       /**
        * How long should wait for captcha result (in seconds)
        */
       private int defaultTimeout = 120;
    
       /**
        * How long should wait for recaptcha result (in seconds)
        */
       private int recaptchaTimeout = 600;
    
       /**
        * How often do requests to `/res.php` should be made
        * in order to check if a result is ready (in seconds)
        */
       private int pollingInterval = 10;
    
       /**
        * Helps to understand if there is need of waiting
        * for result or not (because callback was used)
        */
       private boolean lastCaptchaHasCallback;
    
       /**
        * Network client
        */
       private ApiClient apiClient;
    
       /**
        * com.techwithmaddy.captcha.TwoCaptcha constructor
        */
       public TwoCaptcha() {
           this.apiClient = new ApiClient();
       }
    
       /**
        * com.techwithmaddy.captcha.TwoCaptcha constructor
        *
        * @param apiKey
        */
       public TwoCaptcha(String apiKey) {
           this();
           setApiKey(apiKey);
       }
    
       /**
        * @param apiKey
        */
       public void setApiKey(String apiKey) {
           this.apiKey = apiKey;
       }
    
       /**
        * @param softId
        */
       public void setSoftId(int softId) {
           this.softId = softId;
       }
    
       /**
        * @param callback
        */
       public void setCallback(String callback) {
           this.callback = callback;
       }
    
       /**
        * @param timeout
        */
       public void setDefaultTimeout(int timeout) {
           this.defaultTimeout = timeout;
       }
    
       /**
        * @param timeout
        */
       public void setRecaptchaTimeout(int timeout) {
           this.recaptchaTimeout = timeout;
       }
    
       /**
        * @param interval
        */
       public void setPollingInterval(int interval) {
           this.pollingInterval = interval;
       }
    
       /**
        * @param apiClient
        */
       public void setHttpClient(ApiClient apiClient) {
           this.apiClient = apiClient;
       }
    
       /**
        * Sends captcha to `/in.php` and waits for it's result.
        * This helper can be used instead of manual using of `send` and `getResult` functions.
        *
        * @param captcha
        * @throws Exception
        */
       public void solve(Captcha captcha) throws Exception {
           Map<String, Integer> waitOptions = new HashMap<>();
    
           if (captcha instanceof ReCaptcha) {
               waitOptions.put("timeout", recaptchaTimeout);
           }
    
           solve(captcha, waitOptions);
       }
    
       /**
        * Sends captcha to `/in.php` and waits for it's result.
        * This helper can be used instead of manual using of `send` and `getResult` functions.
        *
        * @param captcha
        * @param waitOptions
        * @throws Exception
        */
       public void solve(Captcha captcha, Map<String, Integer> waitOptions) throws Exception {
           captcha.setId(send(captcha));
    
           if (!lastCaptchaHasCallback) {
               waitForResult(captcha, waitOptions);
           }
       }
    
       /**
        * This helper waits for captcha result, and when result is ready, returns it
        *
        * @param captcha
        * @param waitOptions
        * @throws Exception
        */
       public void waitForResult(Captcha captcha, Map<String, Integer> waitOptions) throws Exception {
           long startedAt = (long)(System.currentTimeMillis() / 1000);
    
           int timeout = waitOptions.getOrDefault("timeout", this.defaultTimeout);
           int pollingInterval = waitOptions.getOrDefault("pollingInterval", this.pollingInterval);
    
           while (true) {
               long now = (long)(System.currentTimeMillis() / 1000);
    
               if (now - startedAt < timeout) {
                   Thread.sleep(pollingInterval * 1000);
               } else {
                   break;
               }
    
               try {
                   String result = getResult(captcha.getId());
                   if (result != null) {
                       captcha.setCode(result);
                       return;
                   }
               } catch (NetworkException e) {
                   // ignore network errors
               }
           }
    
           throw new TimeoutException("Timeout " + timeout + " seconds reached");
       }
    
       /**
        * Sends captcha to '/in.php', and returns its `id`
        *
        * @param captcha
        * @return
        * @throws Exception
        */
       public String send(Captcha captcha) throws Exception {
           Map<String, String> params = captcha.getParams();
           Map<String, File> files = captcha.getFiles();
    
           sendAttachDefaultParams(params);
    
           validateFiles(files);
    
           String response = apiClient.in(params, files);
    
           if (!response.startsWith("OK|")) {
               throw new ApiException("Cannot recognise api response (" + response + ")");
           }
    
           return response.substring(3);
       }
    
       /**
        * Returns result of captcha if it was solved or `null`, if result is not ready
        *
        * @param id
        * @return
        * @throws Exception
        */
       public String getResult(String id) throws Exception {
           Map<String, String> params = new HashMap<>();
           params.put("action", "get");
           params.put("id", id);
    
           String response = res(params);
    
           if (response.equals("CAPCHA_NOT_READY")) {
               return null;
           }
    
           if (!response.startsWith("OK|")) {
               throw new ApiException("Cannot recognise api response (" + response + ")");
           }
    
           return response.substring(3);
       }
    
       /**
        * Gets account's balance
        *
        * @return
        * @throws Exception
        */
       public double balance() throws Exception {
           String response = res("getbalance");
           return Double.parseDouble(response);
       }
    
       /**
        * Reports if captcha was solved correctly (sends `reportbad` or `reportgood` to `/res.php`)
        *
        * @param id
        * @param correct
        * @throws Exception
        */
       public void report(String id, boolean correct) throws Exception {
           Map<String, String> params = new HashMap<>();
           params.put("id", id);
    
           if (correct) {
               params.put("action", "reportgood");
           } else {
               params.put("action", "reportbad");
           }
    
           res(params);
       }
    
       /**
        * Makes request to `/res.php`
        *
        * @param action
        * @return
        * @throws Exception
        */
       private String res(String action) throws Exception {
           Map<String, String> params = new HashMap<>();
           params.put("action", action);
           return res(params);
       }
    
       /**
        * Makes request to `/res.php`
        *
        * @param params
        * @return
        * @throws Exception
        */
       private String res(Map<String, String> params) throws Exception {
           params.put("key", apiKey);
           return apiClient.res(params);
       }
    
       /**
        * Attaches default parameters to request
        *
        * @param params
        */
       private void sendAttachDefaultParams(Map<String, String> params) {
           params.put("key", apiKey);
    
           if (callback != null) {
               if (!params.containsKey("pingback")) {
                   params.put("pingback", callback);
               } else if (params.get("pingback").length() == 0) {
                   params.remove("pingback");
               }
           }
    
           lastCaptchaHasCallback = params.containsKey("pingback");
    
           if (softId != 0 && !params.containsKey("soft_id")) {
               params.put("soft_id", String.valueOf(softId));
           }
       }
    
       /**
        * Validates if files parameters are correct
        *
        * @param files
        * @throws ValidationException
        */
       private void validateFiles(Map<String, File> files) throws ValidationException {
           for (Map.Entry<String, File> entry : files.entrySet()) {
               File file = entry.getValue();
    
               if (!file.exists()) {
                   throw new ValidationException("File not found: " + file.getAbsolutePath());
               }
    
               if (!file.isFile()) {
                   throw new ValidationException("Resource is not a file: " + file.getAbsolutePath());
               }
           }
       }
    
    }
    
    最後に、我々はcaptchaアプリケーションがあります.このクラスでは、
  • TwoCaptchaオブジェクトをインスタンス化し、apitleキーをパースします.
  • サイトキーとURLを設定するために使用するRecaptchaオブジェクトをインスタンス化します.
  • 例外を扱うtry/catchブロック.
  • package com.techwithmaddy.example;
    
    import com.techwithmaddy.captcha.ReCaptcha;
    import com.techwithmaddy.captcha.TwoCaptcha;
    
    import java.io.IOException;
    
    public class CaptchaApplication {
    
           public static void main(String[] args) throws IOException {
    
           TwoCaptcha solver = new TwoCaptcha("ENTER_YOUR_API_KEY");
           ReCaptcha reCaptcha = new ReCaptcha();
    
           reCaptcha.setSiteKey("6LfD3PIbAAAAAJs_eEHvoOl75_83eXSqpPSRFJ_u");
           reCaptcha.setUrl("https://2captcha.com/demo/recaptcha-v2");
    
    
           try {
               solver.solve(reCaptcha);
               System.out.println("Captcha solved: " + reCaptcha.getCode() + "\nId is: " + reCaptcha.getId());
           } catch (Exception e) {
               System.out.println("Error occurred: " + e.getMessage());
           }
           }
    
    }
    
    アプリケーションを起動します.▶️
    コンソールでは、次のように表示されます.
    Captcha solved: 03AGdBq26z-vSsF2bZpq3hq_07mebsEJZJ_vqGE_nIsPacCZpXm6CAt6aEtrPoq9P40cldWH7YPuUHmRWn2povnPwwwMeZH114_frx4Zgz8OtLEtbVTT1yTv76tJpDyTmdvVyiAvZwWMkY6iBb5eR4nK9acXZyeNs_GYipI4Vxf9yuHbTWJy1CtBpOLjQKEgkgQpvpdjFim1syb0N_9gMzmzFSXbTLeG2izcaxd3VIrXKa9pjZkSRJJoEbkGeF5NHgQ9Qo4UEuenkg6xo9dLkiVqPbY5ht4f34ZCXalTVTUNLdyVy4zcKwdbmjhpvMCqRQR-LAMt7IYPyn7-a3Pnpsg0sakhoQE4E5FsZ-_ux2-2XCWjy37pXuIPrutZbaytQpNoB01oSJeFrSFynqO8wmfn3pNMIVXTI7DoiFFpuly18gMhyAV-JDX9W_cWu9Gu6OemviVubXMCrFJhl2a8Gm7Lk6ggezqJHMGCYG-hcKKFajRxmuV3pDoTZhlsHPONuz_MT71-isQ0P6AUsVss2LTtIoa38-JRZdpw
    
    それはこの記事のためです!
    あなたはSDKを使用してrecaptchaを解決する方法を学んだ.
    詳細については、これらのリンクを見てください.
  • Demo - Recaptcha V2
  • Solving ReCaptcha
  • 次回まで!👋🏾