Files
AntiCaptcha/pkg/opencv/opencv.go
T
admin 524c404194
Build and Deploy / build-frontend (push) Failing after 2s
Build and Deploy / build-backend (push) Has been skipped
Build and Deploy / build-docker (push) Has been skipped
Build and Deploy / deploy (push) Has been skipped
feat: initial commit - Go + CGO captcha recognition service
Features:
- Go + CGO ONNX/OpenCV wrapper for high performance
- SQLite (default) / MySQL database support
- Optional Redis caching
- JWT authentication system
- Multiple captcha recognition APIs:
  - OCR text recognition
  - Slider captcha matching
  - Image similarity comparison
  - Rotation captcha detection
  - Object detection
- React frontend with install wizard
- Docker and docker-compose support
- Gitea CI/CD pipeline

Project structure:
- cmd/server: Main entry point
- internal/: Core business logic
- pkg/onnx: ONNX Runtime CGO wrapper
- pkg/opencv: OpenCV CGO wrapper
- web/: React frontend
- deploy/: Deployment configs
- scripts/: Utility scripts
2026-07-16 08:56:38 +00:00

146 lines
3.0 KiB
Go

package opencv
/*
#cgo CXXFLAGS: -std=c++17
#cgo linux LDFLAGS: -lopencv_core -lopencv_imgproc -lopencv_imgcodecs -lopencv_objdetect
#cgo darwin LDFLAGS: -lopencv_core -lopencv_imgproc -lopencv_imgcodecs -lopencv_objdetect
#include <stdlib.h>
#ifdef __cplusplus
extern "C" {
#endif
// 图像结构
typedef struct {
unsigned char* data;
int width;
int height;
int channels;
} Image;
// 图像操作
Image* cv_imdecode(const unsigned char* buf, size_t size);
void cv_image_free(Image* img);
// 滑块匹配
int cv_slider_match(const Image* target, const Image* background, int* out_x);
int cv_slider_comparison(const Image* target, const Image* background, int* out_x);
// 旋转检测
float cv_detect_rotation(const Image* img);
// 模板匹配
int cv_template_match(const Image* src, const Image* templ, double* max_val, int* max_x, int* max_y);
// 特征点检测
int cv_detect_features(const Image* img, int** points_x, int** points_y, int* count);
// 图像相似度
float cv_compare_similarity(const Image* img1, const Image* img2);
// 错误信息
const char* cv_get_last_error();
#ifdef __cplusplus
}
#endif
*/
import "C"
import (
"encoding/base64"
"errors"
"fmt"
"unsafe"
)
// Image 封装图像数据
type Image struct {
img *C.Image
}
// DecodeFromBase64 从 Base64 解码图像
func DecodeFromBase64(data string) (*Image, error) {
decoded, err := base64.StdEncoding.DecodeString(data)
if err != nil {
return nil, fmt.Errorf("base64 解码失败: %v", err)
}
img := C.cv_imdecode(
(*C.uchar)(unsafe.Pointer(&decoded[0])),
C.size_t(len(decoded)),
)
if img == nil {
return nil, errors.New(C.GoString(C.cv_get_last_error()))
}
return &Image{img: img}, nil
}
// Free 释放图像内存
func (i *Image) Free() {
if i.img != nil {
C.cv_image_free(i.img)
i.img = nil
}
}
// Width 获取宽度
func (i *Image) Width() int {
return int(i.img.width)
}
// Height 获取高度
func (i *Image) Height() int {
return int(i.img.height)
}
// SliderMatch 滑块缺口匹配
func SliderMatch(target, background *Image) (int, error) {
var outX C.int
result := C.cv_slider_match(
(*C.Image)(target.img),
(*C.Image)(background.img),
&outX,
)
if result != 0 {
return 0, errors.New(C.GoString(C.cv_get_last_error()))
}
return int(outX), nil
}
// SliderComparison 阴影滑块匹配
func SliderComparison(target, background *Image) (int, error) {
var outX C.int
result := C.cv_slider_comparison(
(*C.Image)(target.img),
(*C.Image)(background.img),
&outX,
)
if result != 0 {
return 0, errors.New(C.GoString(C.cv_get_last_error()))
}
return int(outX), nil
}
// DetectRotation 检测旋转角度
func DetectRotation(img *Image) (float32, error) {
angle := C.cv_detect_rotation((*C.Image)(img.img))
return float32(angle), nil
}
// CompareSimilarity 比较图像相似度
func CompareSimilarity(img1, img2 *Image) (float32, error) {
similarity := C.cv_compare_similarity(
(*C.Image)(img1.img),
(*C.Image)(img2.img),
)
return float32(similarity), nil
}