Skip to content

Commit

Permalink
Staging for NPM publish
Browse files Browse the repository at this point in the history
  • Loading branch information
Furry committed Mar 28, 2024
1 parent d1dcc20 commit 74799c4
Show file tree
Hide file tree
Showing 16 changed files with 198 additions and 242 deletions.
3 changes: 2 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -4,4 +4,5 @@ dist/

# Files
yarn.lock
.env
.env
package-lock.json
10 changes: 10 additions & 0 deletions .npmignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# Folders
node_modules/
src/
test/

# Files
.env
.gitignore
package-lock.json
yarn.lock
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "2captcha",
"version": "3.0.0@next",
"version": "4.0.0@next",
"description": "An asynchronous wrapper around the 2captcha API.",
"main": "dist/index.js",
"repository": "https://github.com/furry/2captcha",
Expand Down
112 changes: 101 additions & 11 deletions readme.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
<div align="center">
<center>
<h1>
2captcha
</h1>
Expand All @@ -12,18 +12,108 @@
![Size](https://img.shields.io/bundlephobia/min/2captcha)
![Downloads](https://img.shields.io/npm/dw/2captcha)

</div>
</center>

<center>A wrapper around the 2captcha API</center>

<hr>

<p align="center">A wrapper around the 2captcha API</p>
## Motive

2captcha is a service that solves many different types of captchas, this library serves as a wrapper around their API to bring easy, promise-based functionality to NodeJS. This libary specilizes in concurrent solves, and bulk-api usage.

## Features
- Strict typings & full TS/JS support
- Single-Request polling
- Promise based solves
- EventEmitter Support
- Account Endpoints
- Pingback Support
- Browser / Node
- Proxy Support

- Promise based 2captcha solving
- Browser & NodeJS Support
- Uses node-fetch, a light weight http library
- Fluent typings & TS support
- Account Interaction
- Invalid Captcha reporting
- Proxy Support

## Planned Features

- Pingback / Webhook support via express

## Install

```sh
npm install 2captcha@next
```
```sh
yarn add 2captcha@next
```

## Usage


Recaptcha,
```js
const Captcha = require("2captcha")

// A new 'solver' instance with our API key
const solver = new Captcha.Solver("<Your 2captcha api key>")

/* Example ReCaptcha Website */
solver.recaptchaV2("6Ld2sf4SAAAAAKSgzs0Q13IZhY02Pyo31S2jgOB5", "https://patrickhlauke.github.io/recaptcha/")
.then((res) => {
console.log(res)
})
.catch((err) => {
console.error(err.message)
})
```

Image,
```js
const Captcha = require("2captcha")
const fs = require("fs")

const solver = new Captcha.Solver("<Your 2captcha api key>")

// Read from a file as base64 text
solver.imageCaptcha(fs.readFileSync("./captcha.png", "base64"))
.then((res) => {
// Logs the image text
console.log(res)
})
.catch((err) => {
console.error(err.message)
})
```

Proxy,
```js
const Captcha = require("2captcha")

const solver = new Captcha.Solver("<Your 2captcha api key>")


solver.recaptchaV2("6Ld2sf4SAAAAAKSgzs0Q13IZhY02Pyo31S2jgOB5", "https://patrickhlauke.github.io/recaptcha/", true /* for proxied */, false /* not enterprise */, {
proxy: "21.214.43.26", // The (Username : Password @ Address) of our chosen proxy
proxyType: "HTTP", // The 'Type' of proxy, http, https, socks, ect.
proxyLogin: "username",
proxyPassword: "password123"
})
.then((res) => {
console.log(res)
})
.catch((err) => {
console.error(err.message)
})
```

## Commit Guidelines

The latest version of the code base will always be under the '**next**' branch!

- All pull requiests must provide a valid reason for the change or implementation
- All **CORE CHANGES** require an issue with reasoning made before a PR will even be addressed.
- All PR's must follow the general structure of the code base
- If you have questions, feel free to make an issue and i'll get to it right away!

<hr>
<div style="text-align: center">
<a href="https://www.buymeacoffee.com/ether" target="_blank"><img src="https://www.buymeacoffee.com/assets/img/custom_images/orange_img.png" alt="Buy Me A Coffee" style="height: 41px !important;width: 174px !important;box-shadow: 0px 3px 2px 0px rgba(190, 190, 190, 0.5) !important;-webkit-box-shadow: 0px 3px 2px 0px rgba(190, 190, 190, 0.5) !important;" ></a>
</div>
11 changes: 8 additions & 3 deletions src/structs/solver.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@ import {
CloudflareTurnstile,
CoordinateCaptchaResult,
CoordinatesTaskExtras,
CreatedTaskResponse,
DataDomeCaptchaResult,
DataDomeExtras,
DrawAroundResult,
Expand Down Expand Up @@ -156,7 +155,13 @@ export class Solver {
throw new NetError(err, this._locale);
})

const json = await response.json();
let json;
try {
json = await response.json();
} catch (e) {
let t = await response.text()
throw new NetError("UnexpectedHTMLResponse", this._locale);
}

if (json.errorId == 0) {
return json.taskId;
Expand Down Expand Up @@ -202,7 +207,7 @@ export class Solver {
* @param captchaId The captcha ID to get the solution of.
* @returns The resulting captcha promise.
*/
private async registerPollEntry<T>(task: number, delay = 5000): Promise<CaptchaResult<T>> {
protected async registerPollEntry<T>(task: number, delay = 5000): Promise<CaptchaResult<T>> {
const captchaPromiseObject: PendingCaptchaStorage = {
startTime: Date.now(),
captchaId: task,
Expand Down
78 changes: 74 additions & 4 deletions test/InteractiveCaptchas.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,17 +2,19 @@ import * as Captcha from "../dist/index.js";
import dotenv from "dotenv";
import fs from "fs";
import chai from "chai";
import { it } from "mocha";

const { expect } = chai;

describe("Recaptcha Test", () => {
dotenv.config();
const solver = new Captcha.Solver(process.env.TOKEN);
it("Should return a solve for the recaptcha", async () => {

// Using https://patrickhlauke.github.io/recaptcha/ for v2
const result = await solver.recaptchaV2("6Ld2sf4SAAAAAKSgzs0Q13IZhY02Pyo31S2jgOB5", "https://patrickhlauke.github.io/recaptcha/");

expect(result.solution.gRecaptchaResponse).to.greaterThan(256);
expect(result.solution.gRecaptchaResponse.length).to.be.greaterThan(64);
expect(result.solution.token.length).to.be.greaterThan(64);
});

it("Should error for invalid key", async () => {
Expand All @@ -27,7 +29,75 @@ describe("Recaptcha Test", () => {
try {
await solver.recaptchaV2("6Ld2sf4SAAAAAKSgzs0Q13IZhY02Pyo31S2jgOB5", "https://example.com/");
} catch (e) {
expect(e.message).to.equal("ERROR_CAPTCHA_UNSOLVABLE");
expect(e.code).to.equal("ERROR_CAPTCHA_UNSOLVABLE");
}
})
})
})

describe("hCaptcha Test", () => {
const solver = new Captcha.Solver(process.env.TOKEN);

it("Should return a solve", async () => {
const response = await solver.hcaptcha("e1715201-770b-4f61-87da-523133844aec", "https://vastus.github.io/login");
expect(response.solution.token.length).to.be.greaterThan(64);
})

it("Should error for invalid key", async () => {
try {
await solver.hcaptcha("Invalid Key", "https://vastus.github.io/login");
} catch (e) {
expect(e.code).to.equal("ERROR_BAD_PARAMETERS");
}
})
})

describe("Lemin Test", async () => {
dotenv.config();
const solver = new Captcha.Solver(process.env.TOKEN);

it("Should return a solve", async () => {
// const response = await solver.leminPuzzle("https://2captcha.com/demo/lemin", "CROPPED_3dfdd5c_d1872b526b794d83ba3b365eb15a200b", "lemin-cropped-captcha");
const response = await solver.leminPuzzle("https://2captcha.com/demo/lemin", "CROPPED_3dfdd5c_d1872b526b794d83ba3b365eb15a200b", "lemin-cropped-captcha")

expect(response.solution.answer.length).to.be.greaterThan(64);
expect(response.solution.challenge_id.length).to.be.greaterThan(10);
})

it("Should error for invalid key", async () => {
try {
await solver.leminPuzzle("https://2captcha.com/demo/lemin", "CROPPED_3dfdd5c_d1872b526b794d83ba3b365eb15a200bawdaawdad", "lemin-cropped-captcha", false);
} catch (e) {
expect(["ERROR_KEY_DOES_NOT_EXIST", "ERROR_CAPTCHA_UNSOLVABLE"]).to.include(e.code);
}
})
})

describe("KeyCaptcha Test", () => {
dotenv.config();
const solver = new Captcha.Solver(process.env.TOKEN)

it("Should return a solve", async () => {
const response = await solver.keycaptcha(false, {
s_s_c_user_id: 184015,
s_s_c_session_id: "9ff29e0176e78eb7ba59314f92dbac1b",
s_s_c_web_server_sign: "964635241a3e5e76980f2572e5f63452",
s_s_c_web_server_sign2: "3ca802a38ffc5831fa293ac2819b1204",
websiteURL: "https://2captcha.com/demo/keycaptcha"
})

expect(response.solution.token.length).to.be.greaterThan(64);
})
})

describe("MtCaptcha Test", () => {
dotenv.config();
const solver = new Captcha.Solver(process.env.TOKEN);

it("Should return a solve", async () => {
const response = await solver.mtCaptcha("https://2captcha.com/demo/mtcaptcha", "MTPublic-KzqLY1cKH");

expect(response.solution.answer.length).to.be.greaterThan(64);
})
})


12 changes: 0 additions & 12 deletions test/funcaptcha.test.js

This file was deleted.

41 changes: 0 additions & 41 deletions test/geetest.test.js

This file was deleted.

24 changes: 0 additions & 24 deletions test/hcaptcha.test.js

This file was deleted.

28 changes: 0 additions & 28 deletions test/imageCaptcha.test.js

This file was deleted.

Loading

0 comments on commit 74799c4

Please sign in to comment.