1️⃣ 问题描述

  • 你尝试让 Gemini(Vertex AI)访问以下图片 URL:
https://xxx.360buyimg.com/xxx/xxx/xxx.jpg
https://xxx.360buyimg.com/xxx/xxx/xxx.jpg
  • 报错:
Cannot fetch contentfrom the provided URL. Status: URL_REJECTED-REJECTED_SCHEDULE_TIME_OVER_DEADLINE
  • 同时,你发现某些 URL(如 JDCloud OSS 的 ceshi.s3.cn-north-1.jdcloud-oss.com)可以正常访问。

2️⃣ 为什么 Gemini 无法访问这些图片

  1. robots.txt 限制
    • 访问 xxx.360buyimg.com/robots.txt 返回 405,说明该域名拒绝访问 robots.txt
    • Vertex AI 会遵守 robots.txt 规则,对于非信任域名,如果 robots.txt 不可访问或返回错误,通常判定为“不允许抓取”
  2. 域名非受信任云存储域
    • Gemini 对外部 URL 有一份“受信任云存储域名列表”(如 S3、OSS、GCS、Azure Blob 等)
    • xxx.360buyimg.com 不在信任列表,因此即使图片能直接访问,也会被拒绝

3️⃣ 为什么其他 URL 可以访问

一、以 JDCloud OSS 为例:

https://ceshi.s3.cn-north-1.jdcloud-oss.com/测试.png

原因:

  1. 域名在受信任云存储列表中
    • Gemini/Vertex AI 对 *.jdcloud-oss.com 默认允许抓取
  2. robots.txt 返回 403/404 不影响
    • 云存储域名的 robots.txt 通常无文件或返回错误
    • Vertex 有特例:对于受信任域名,robots.txt 不会阻止抓取
  3. 对象可公开访问
    • 图片文件 ACL 为 public-read 或 URL 带签名(可匿名访问)

二、以wiki的上的一张图片为例:

https://upload.wikimedia.org/wikipedia/commons/4/4b/Cumulus_clouds_seen_from_10%2C000_meters_above_the_ground%2C_2010.jpg
  1. robots.txt 返回200

robots.txt返回200,并且图片的路径不在Disallow的限制中


4️⃣ 排查 URL 是否可被 Gemini 访问的方法

  1. 检查 HTTPS
    • Gemini 只支持 HTTPS 协议 URL
  2. 检查域名是否在受信任云存储列表
    • 常见受信任域:*.s3.amazonaws.com, *.jdcloud-oss.com, *.storage.googleapis.com, *.aliyuncs.com, *.blob.core.windows.net
  3. 检查 robots.txt
    • 访问 <domain>/robots.txt,查看是否存在 Disallow 对应路径
    • 对受信任云存储域,robots.txt 可以忽略
  4. 检查资源是否可访问
    • 使用 curl 或浏览器访问图片 URL,HTTP 状态码应为 200
    • Content-Type 应为 image/jpegimage/png
  5. 综合判断
    • 受信任云存储 + 图片可访问 → Gemini 可抓取
    • 非信任域 + robots.txt 不可访问或禁止抓取 → Gemini 无法抓取

5️⃣ 总结

条件

Gemini 是否能访问

非信任域名 + robots.txt 不可访问

❌ 无法访问

非信任域名 + robots.txt 明确允许

⚠️ 可能访问,但受限

受信任云存储域 + 图片可访问

✅ 可以访问

受信任云存储域 + robots.txt 返回 403/404

✅ 可以访问


核心原因:受信任云存储域名 + 公共可访问的图片 URL 是 Gemini 能够抓取的关键。

6️⃣ 检测脚本

#!/usr/bin/env python3
# -*- coding: utf-8 -*-

import requests
from urllib.parse import urlparse

# === Vertex/Gemini 可直接访问的信任云域列表 ===
TRUSTED_DOMAINS = [
    ".googleusercontent.com",
    ".storage.googleapis.com",
    ".s3.amazonaws.com",
    ".s3.",
    ".aliyuncs.com",
    ".jdcloud-oss.com",
    ".blob.core.windows.net",
    ".digitaloceanspaces.com",
    ".backblazeb2.com",
]

def is_trusted_domain(domain: str) -> bool:
    """判断域名是否属于受信任的云存储域"""
    return any(domain.endswith(t) for t in TRUSTED_DOMAINS)

def check_gemini_access(url: str):
    """检测 URL 是否能被 Gemini 访问"""
    print(f"\n🔍 正在检测: {url}")
    parsed = urlparse(url)
    domain = parsed.hostname

    if not domain:
        print("❌ 无效 URL,无法解析域名")
        return

    # Step 1: 检查协议
    if parsed.scheme != "https":
        print("⚠️  Gemini 仅支持 HTTPS 访问")
        return

    # Step 2: 判断信任域
    trusted = is_trusted_domain(domain)
    print(f"🌐 域名: {domain} -> {'✅ 受信任云域' if trusted else '❌ 非信任域'}")

    # Step 3: 检查 robots.txt
    robots_url = f"{parsed.scheme}://{domain}/robots.txt"
    print("robots_url:", robots_url)
    try:
        headers = {
            'User-Agent': 'curl/7.64.1',
            'Accept': '*/*'
        }
        r = requests.get(robots_url, timeout=5, headers=headers)
        status = r.status_code
        print(r)
    except Exception:
        status = None

    if status is None:
        print("⚠️ 无法获取 robots.txt(可能被防火墙或拦截)")
    elif status in (403, 405):
        print("ℹ️ robots.txt 返回 403/405 —— 云存储域常见情况,无影响")
    elif status == 200:
        print("🧩 robots.txt 存在 (200 OK)")
        # Step 4: 测试资源访问性
        try:
            headers = {
                'User-Agent': 'curl/7.64.1',
                'Accept': '*/*'
            }
            resp = requests.head(url, timeout=8, allow_redirects=True, headers=headers)
            status = resp.status_code
            ctype = resp.headers.get("Content-Type", "未知")
        except Exception as e:
            print(f"❌ 无法访问资源: {e}")
            return

        if status == 200:
            print(f"🟢 资源可访问 (Content-Type: {ctype})")
        else:
            print(f"🔴 资源访问异常 (HTTP {status})")
    else:
        print(f"ℹ️ robots.txt 状态码: {status}")


    # Step 5: 综合判断
    if not trusted and status == 200:
        print("\n⚠️ 结论:域名未在 Vertex 信任列表,但robots.txt可访问,Gemini 大概率可以成功加载该图片。\n")
    elif trusted:
        print("\n✅ 结论:Gemini 可以成功加载该图片。\n")
    elif not trusted and status != 200:
        print("\n🚫 结论:域名未在 Vertex 信任列表,且robots.txt不可访问,Gemini 拒绝加载。\n")
    else:
        print("\n⚠️  结论:资源访问异常,需检查防盗链或 ACL 设置。\n")

def main():
    print("=== Gemini 图片访问检测工具 ===")
    print("输入图片 URL(输入 q 退出)")
    while True:
        url = input("\n请输入图片地址: ").strip()
        if not url or url.lower() == "q":
            print("👋 退出检测。")
            break
        check_gemini_access(url)

if __name__ == "__main__":
    main()

Logo

中国智能体开发者社区,聚焦智能体与大模型开发,提供前沿资讯、实用工具链、开源项目及行业案例。通过技术沙龙、开发者大赛等活动,促进经验交流与协作,助力开发者快速构建创新智能应用。

更多推荐