diff --git a/Dockerfile.pkserver b/Dockerfile.pkserver
new file mode 100644
index 00000000000..d4a83b2155f
--- /dev/null
+++ b/Dockerfile.pkserver
@@ -0,0 +1,66 @@
+FROM ubuntu AS build_alist
+WORKDIR /app/
+# RUN apt update && apt install bash curl gcc git go musl-dev
+# 安装基本工具
+RUN apt update && \
+ apt install -y software-properties-common && \
+ add-apt-repository ppa:longsleep/golang-backports && \
+ apt update && \
+ apt install -y bash curl gcc git golang-go musl-dev
+COPY go.mod go.sum ./
+RUN go mod download
+COPY ./ ./
+RUN bash build.sh release docker
+
+FROM ubuntu AS install_yolov8
+RUN apt update && \
+ apt install -y python3 python3-pip python3.12-venv
+WORKDIR /app/auto_pikpak/
+# 创建虚拟环境并激活
+RUN python3 -m venv venv && \
+ . venv/bin/activate && \
+ pip install \
+ # pip install \
+ ultralytics
+
+# FROM ubuntu AS install_py2
+# COPY --from=install_yolov8 /app/auto_pikpak/venv /app/pikpak_captcha_server/venv
+# RUN apt update && \
+# apt install -y python3 python3-pip python3.12-venv
+# WORKDIR /app/pikpak_captcha_server/
+# # 使用虚拟环境中的 Python 安装其他依赖
+# RUN /app/pikpak_captcha_server/venv/bin/python -m pip install --no-cache-dir 2captcha-python Flask
+
+FROM ubuntu as pikpak_server
+RUN apt update && \
+ apt install -y git python3 python3-pip python3.12-venv
+WORKDIR /app
+RUN git clone --depth=1 --recurse-submodules https://github.com/wangjunkai2022/pikpak_captcha_server.git
+WORKDIR /app/pikpak_captcha_server
+RUN rm -rf /app/pikpak_captcha_server/pikpak_captcha/ai/ai_train_pikpak
+COPY --from=install_yolov8 /app/auto_pikpak/venv /app/pikpak_captcha_server/venv
+# 使用虚拟环境中的 Python 安装其他依赖
+RUN /app/pikpak_captcha_server/venv/bin/python -m pip install -r requirements.txt
+# 安装每个子模块的依赖项
+RUN find . -name 'requirements.txt' -exec /app/pikpak_captcha_server/venv/bin/python -m pip install -r {} \;
+
+FROM ubuntu
+ARG INSTALL_FFMPEG=false
+LABEL MAINTAINER="i@nn.ci"
+
+WORKDIR /opt/alist/
+
+RUN apt update && \
+ apt upgrade -y && \
+ apt install -y bash ca-certificates tzdata ffmpeg
+
+# 复制 auto_pikpak 到第二阶段
+COPY --from=pikpak_server /app/pikpak_captcha_server /app/pikpak_captcha_server
+COPY --from=build_alist /app/bin/alist ./
+COPY entrypoint_pkserver.sh /entrypoint_pkserver.sh
+RUN chmod +x /entrypoint_pkserver.sh && /entrypoint_pkserver.sh version
+
+ENV PUID=0 PGID=0 UMASK=022
+VOLUME /opt/alist/data/
+EXPOSE 5244 5245
+CMD [ "/entrypoint_pkserver.sh" ]
\ No newline at end of file
diff --git a/drivers/pikpak/meta.go b/drivers/pikpak/meta.go
index 4d25ecc605e..cb95c0deff3 100644
--- a/drivers/pikpak/meta.go
+++ b/drivers/pikpak/meta.go
@@ -17,6 +17,7 @@ type Addition struct {
DisableMediaLink bool `json:"disable_media_link" default:"true"`
UseLowLatencyAddress bool `json:"use_low_latency_address" default:"false"`
CustomLowLatencyAddress string `json:"custom_low_latency_address" default:""`
+ CaptchaApi string `json:"captcha_api" default:""`
}
var config = driver.Config{
diff --git a/drivers/pikpak/types.go b/drivers/pikpak/types.go
index 2a959ebf05d..a192c7265c7 100644
--- a/drivers/pikpak/types.go
+++ b/drivers/pikpak/types.go
@@ -195,3 +195,9 @@ type CaptchaTokenResponse struct {
ExpiresIn int64 `json:"expires_in"`
Url string `json:"url"`
}
+
+type CaptchaApiResponse struct {
+ Token string `json:"token"`
+ Code int64 `json:"code"`
+ Url string `json:"url_received"`
+}
diff --git a/drivers/pikpak/util.go b/drivers/pikpak/util.go
index 1fd26020a60..7f1f8689ac0 100644
--- a/drivers/pikpak/util.go
+++ b/drivers/pikpak/util.go
@@ -281,7 +281,10 @@ func (d *PikPak) request(url string, method string, callback base.ReqCallback, r
return d.request(url, method, callback, resp)
case 9: // 验证码token过期
if err = d.RefreshCaptchaTokenAtLogin(GetAction(method, url), d.GetUserID()); err != nil {
- return nil, err
+ // return nil, err
+ if err = d.login(); err != nil {
+ return nil, err
+ }
}
return d.request(url, method, callback, resp)
case 10: // 操作频繁
@@ -486,7 +489,40 @@ func (d *PikPak) refreshCaptchaToken(action string, metas map[string]string) err
}
if resp.Url != "" {
- return fmt.Errorf(`need verify: Click Here`, resp.Url)
+ // return fmt.Errorf(`need verify: Click Here`, resp.Url)
+ if d.Addition.CaptchaApi != "" {
+ var captcha_resp CaptchaApiResponse // 假设 captcha_resp 是某种结构体
+ client := resty.New().SetTimeout(time.Duration(resp.ExpiresIn) * time.Second)
+ _, err := client.R().
+ SetQueryParams(map[string]string{
+ "url": resp.Url, // 替换为实际的 URL
+ }).
+ SetResult(&captcha_resp).
+ Get(d.Addition.CaptchaApi) // 替换为实际的 API 端点
+
+ if err != nil {
+ return err
+ }
+
+ // var captcha_resp CaptchaApiResponse
+ // _, err := d.request(d.Addition.CaptchaApi, http.MethodGet, func(req *resty.Request) {
+ // queryParams := map[string]string{
+ // "url": resp.Url,
+ // }
+ // req.SetQueryParams(queryParams)
+ // }, &captcha_resp)
+ // if err != nil {
+ // return err
+ // }
+ if captcha_resp.Code == 200 {
+ d.Common.SetCaptchaToken(captcha_resp.Token)
+ return nil
+ } else {
+ return errors.New("验证失败")
+ }
+ } else {
+ return errors.New("没有配置自动验证Server")
+ }
}
if d.Common.RefreshCTokenCk != nil {
diff --git a/entrypoint_pkserver.sh b/entrypoint_pkserver.sh
new file mode 100644
index 00000000000..17b6656b31c
--- /dev/null
+++ b/entrypoint_pkserver.sh
@@ -0,0 +1,18 @@
+#!/bin/bash
+
+chown -R ${PUID}:${PGID} /opt/alist/
+
+umask ${UMASK}
+# 指定 Python 程序的工作目录
+PYTHON_DIR="/app/pikpak_captcha_server"
+
+# 启动 Python 程序
+(
+ cd "$PYTHON_DIR" && /app/pikpak_captcha_server/venv/bin/python3 server.py &
+)
+
+if [ "$1" = "version" ]; then
+ ./alist version
+else
+ exec ./alist server --no-prefix
+fi
\ No newline at end of file