关于 huawei-cloud-obs-website-host
用于为现有 Huawei Cloud OBS 存储桶配置静态网站托管并注册必需的自定义域名。该技能还可验证访问情况,并排查常见权限、路径和 DNS 问题。
主要功能
- 01配置 OBS 静态网站托管
- 02设置首页和错误文档
- 03注册必需的自定义域名
- 04验证网站及 DNS 访问
- 05排查 403 和 404 错误
适用场景
- 01为现有 OBS 存储桶启用托管
- 02将网站绑定到自定义域名
- 03检查托管网站的访问问题
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ huaweicloud/ huaweicloud-skills --skill huawei-cloud-obs-website-host安装后在 Claude Code 中输入/huawei-cloud-obs-website-host确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
references/cli-installation-guide.mdhcloud-dns-obs-website.mdiam-policies.mdobs-python-sdk-website.mdverification-method.mdscripts/set_obs_website_sdk.pyverify_obs_website.py详细介绍
Huawei Cloud OBS 网站托管
概述
使用 Huawei Cloud OBS Python SDK 配置现有的 Huawei Cloud OBS 桶以托管静态网站,并为该网站注册自定义域名。
当用户希望执行以下操作时,使用此技能:
- 启用或修复 OBS 静态网站托管
- 设置索引文档或错误文档
- 通过由 OBS 静态网站端点提供支持的自定义域名访问网站
- 添加或修复自定义域名,包括适用时配置 Huawei Cloud DNS
- 诊断托管的 OBS 网站上的 403、404 或 DNS 问题
完成标准
- 桶已启用静态网站托管。
- 桶可通过网站端点提供
index.html。 - 匿名用户可以读取网站内容。
- 访问不存在的路径时,会返回已配置的错误页面或干净的 404。
- 自定义域名已注册,并通过 DNS 解析到 OBS 网站端点。自定义域名是必需项——根据安全合规要求,在线预览对象时不得使用默认的 OBS 桶域名。
- 只有在桶上注册了自定义域名且解析正确后,才能认为配置已完成。
- 使用 OBS 网站端点,而不是常规桶 API 端点。
- 403 通常有两个常见原因:桶或对象未启用匿名/公开读取权限,或者用于 OBS 操作的 AK/SK 缺少所需的 IAM 权限。
- 404 通常表示索引文档名称或上传路径错误。
安全合规:自定义域名要求
根据 Huawei Cloud 安全合规要求,禁止使用 OBS 桶的默认域名(<bucket_name>.obs.<region>.myhuaweicloud.com)在线预览桶内的对象。因此,静态网站托管必须使用自定义域名。
如果用户尚未准备好自定义域名:
- 引导用户通过 Huawei Cloud 域名注册服务或其他常见域名注册网站注册域名。
- 对于中国大陆用户,域名还必须完成ICP备案后才能用于网站托管。
- 只有在域名注册完成后(如适用,还需完成备案),才能继续配置静态网站托管。
重要提示: 确认已满足自定义域名前置条件后,才能继续配置静态网站托管。即使在测试环境中,默认 OBS 域名也不能作为网站访问的替代方案。
所需输入
进行更改前,请收集以下信息:
regionbucket_namecustom_domain(必需——请参阅上文的“安全合规”部分)index_document(可选,默认值:index.html)error_document(可选)dns_zone或 DNS 账户上下文(可选;仅当用户希望本次运行中更改 Huawei Cloud DNS 时才需要)
假定静态网站文件已由用户上传。
依赖项
此技能依赖以下运行时/工具组件:
- Python 3.10+(
scripts/set_obs_website_sdk.py和scripts/verify_obs_website.py必需) - Huawei OBS Python SDK 包:
esdk-obs-python obsutil(用于生成和维护.obsutilconfig凭据配置)- Huawei Cloud AK/SK 凭据(来自
.obsutilconfig) - 对 OBS 端点和网站端点的网络访问
hcloudCLI(仅当此技能管理 Huawei Cloud DNS 记录操作时需要)- dig / nslookup(可选)
安装命令:
pip install esdk-obs-python
hcloud CLI 参考
需要安装和配置 hcloud CLI 或 obsutil 时,加载 references/cli-installation-guide.md。
创建或管理 OBS 静态网站自定义域名的 DNS CNAME 记录时,加载 references/hcloud-dns-obs-website.md(分步指南,包含 hcloud DNS CreateRecordSet 命令)。
安全提示:
- 切勿在脚本或提交到版本库的文件中硬编码 AK/SK。
- SDK 脚本优先使用环境变量,CLI 使用安全的本地配置文件存储。
obsutil 配置依赖
需要安装 obsutil 或了解 .obsutilconfig 配置方法时,加载 references/cli-installation-guide.md。
Python SDK 辅助脚本(scripts/set_obs_website_sdk.py)默认按以下顺序读取凭据:
- CLI 标志(
--access-key、--secret-key、--security-token) - 环境变量(
HW_ACCESS_KEY、HW_SECRET_KEY、HW_SECURITY_TOKEN) .obsutilconfig
如果所有来源中的 ak/sk 均为空,脚本必须停止,并要求用户在 .obsutilconfig 中填写缺失的密钥(或提供 CLI/环境变量凭据)。
凭据检查规则:
- 仅报告密钥(
ak、sk、securitytoken)是否存在。 - 检查时切勿打印凭据值。
- 切勿在控制台打印
.obsutilconfig的完整行。 - 将控制台输出视为模型上下文;任何值泄露都属于安全事件。
安全检查示例(仅显示状态,不显示密钥值):
Linux/macOS:
CFG="${HOME}/.obsutilconfig"
if [ ! -f "$CFG" ]; then
echo "obsutilconfig_exists=false"
echo "ak_configured=false"
echo "sk_configured=false"
echo "securitytoken_configured=false"
else
awk -F= '
BEGIN { ak=0; sk=0; st=0 }
/^[[:space:]]*#/ { next }
/^[[:space:]]*(ak|access_key_id)[[:space:]]*=/ { if ($2 ~ /[^[:space:]]/) ak=1 }
/^[[:space:]]*(sk|secret_access_key)[[:space:]]*=/ { if ($2 ~ /[^[:space:]]/) sk=1 }
/^[[:space:]]*(securitytoken|security_token|token)[[:space:]]*=/ { if ($2 ~ /[^[:space:]]/) st=1 }
END {
print "obsutilconfig_exists=true"
print "ak_configured=" (ak ? "true" : "false")
print "sk_configured=" (sk ? "true" : "false")
print "securitytoken_configured=" (st ? "true" : "false")
}
' "$CFG"
fi
Windows(PowerShell):
$cfg = Join-Path $HOME ".obsutilconfig"
if (-not (Test-Path $cfg)) {
"obsutilconfig_exists=false"
"ak_configured=false"
"sk_configured=false"
"securitytoken_configured=false"
} else {
$lines = Get-Content $cfg
$ak = $false; $sk = $false; $st = $false
foreach ($line in $lines) {
if ($line -match '^\s*#') { continue }
if ($line -match '^\s*(ak|access_key_id)\s*=\s*(\S.*)$') { $ak = $true }
if ($line -match '^\s*(sk|secret_access_key)\s*=\s*(\S.*)$') { $sk = $true }
if ($line -match '^\s*(securitytoken|security_token|token)\s*=\s*(\S.*)$') { $st = $true }
}
"obsutilconfig_exists=true"
"ak_configured=$ak"
"sk_configured=$sk"
"securitytoken_configured=$st"
}
不要使用:
cat ~/.obsutilconfiggrep -E "ak|sk|token" ~/.obsutilconfig
脚本使用意图
默认使用随附脚本完成其专门设计的任务:
scripts/set_obs_website_sdk.py会应用或更新存储桶网站配置,并注册所需的自定义域名。启用、修复或更改 OBS 静态网站托管设置时,务必使用该脚本。scripts/verify_obs_website.py用于验证已发布的网站端点。每次更改网站配置后都要使用该脚本;用户询问网站是否可访问,或排查 403/404 行为时也要使用。- 除非脚本本身损坏且必须修补,否则不要用临时编写的一次性代码替代这些脚本。
- 使用这些脚本,以确保凭据处理、SDK 对象构建和验证行为在各次运行中保持一致。
工作流
- 验证 Python 运行时和 OBS SDK 是否可用(如果缺少,请运行
pip install esdk-obs-python)。 - 验证自定义域名前置条件(参见 安全合规 部分):
- 确认用户已提供
custom_domain。 - 如果用户没有域名,引导他们在 华为云域名注册 注册域名,并为中国大陆区域完成ICP备案(网站备案)。到此为止,等待用户完成此步骤。
- 检查用户是在华为云 DNS 还是通过外部服务商管理 DNS。
- 如果本次操作涉及更改华为云 DNS,请验证
hcloud已安装并完成身份验证。 - 如果 DNS 由华为云以外的服务商管理,或不在本次操作范围内,请先明确收集这一限制,再继续操作。
- 确认用户已提供
- 验证存储桶是否存在于所请求的区域(使用下方的存储桶存在性和区域检查方法)。
- 检查调用方是否有权限更新存储桶网站设置。
- 检查是否允许匿名读取网站文件(使用下方的匿名读取检查方法)。
- 不要上传或修改网站内容对象(
index.html、资源等)。假设内容已存在于存储桶中。 - 运行
scripts/set_obs_website_sdk.py并传入--custom-domain <domain>,配置静态网站托管(如果未提供index_document,则使用index.html)。- 此脚本用于确保 SDK 对象构造和凭证查找方式一致。
- 请使用此脚本,不要在回复中编写一次性的 SDK 调用。
- 通过脚本使用的 OBS SDK 路径,在存储桶上注册所需的自定义域名:
client.setBucketCustomDomain(bucket_name, custom_domain)—— 即使 DNS CNAME 已存在,也必须执行此操作。- 如果本次操作需要更改 DNS 记录,请创建指向 OBS 网站主机名的 DNS CNAME 记录,并等待其传播。(阅读
references/hcloud-dns-obs-website.md) - 如果 DNS 由华为云以外的服务商管理,或不在本次操作范围内,请提供所需的 CNAME 目标,并明确告知用户:OBS 自定义域名注册完成后,需通过外部 DNS 服务商创建或更新 CNAME 记录。
- 对于由外部服务商管理的 DNS,请提供用户所需的实际交接信息:记录类型
CNAME、主机名/名称、目标/值,以及dig等验证命令。
- 运行
scripts/verify_obs_website.py --bucket-name <bucket_name> --region <region> [--domain <custom_domain>] [--index-document <name>],验证已发布的网站。- 如果用户提供了自定义域名,最终验证必须通过
--domain <custom_domain>使用该自定义域名。 - 仅在中间检查或未提供自定义域名时,才使用默认 OBS 主机名。
- 如果用户提供了自定义域名,最终验证必须通过
- 确认根路径返回主页(HTTP 200)。
- 确认缺失路径返回已配置的错误行为(HTTP 404 或配置的错误页面)。
- 验证 DNS 解析(
dig/nslookup)以及通过用户提供的自定义域名进行的 HTTP 访问。如果请求涉及自定义域名,不要仅凭默认 OBS 主机名就认定配置已完成。
存储桶存在性和区域检查方法
在配置网站之前,先使用 verify_obs_website.py 运行只读 SDK 检查。
python scripts/verify_obs_website.py \
--bucket-name "<bucket_name>" \
--region "<region>" \
--index-document "<index_document>"
obs endpoint 会自动构建为 https://obs.<region>.myhuaweicloud.com。
通过/失败规则:
PASS:headBucket返回2xx,且区域匹配(或者无法返回区域,但存储桶可访问并返回2xx)。FAIL:headBucket返回非2xx、getBucketLocation返回非2xx,或明确的区域不匹配。
匿名读取检查方法
使用对 OBS 网站端点发起的匿名 HTTP 请求作为事实依据(不使用 AK/SK)。
- 验证器会自动构建默认网站 URL:
http://<bucket_name>.obs.<region>.myhuaweicloud.com
- 运行内置验证器(推荐):
python scripts/verify_obs_website.py \
--bucket-name "<bucket_name>" \
--region "<region>" \
--domain "<custom_domain>" \
--index-document "<index_document>"
- 如果用户未提供自定义域名,请改为验证默认 OBS 网站端点:
python scripts/verify_obs_website.py \
--bucket-name "<bucket_name>" \
--region "<region>" \
--index-document "<index_document>"
- 如果需要快速检查单个文件,请运行:
site_url="http://<custom_domain>"
curl -s -o /dev/null -w "%{http_code}\n" "$site_url/<index_document>"
通过/失败规则:
root_path和index_document返回200:匿名读取正常。- 返回
403:应视为存在两种可能的问题,且必须都告知用户:未启用匿名/公共读取(ACL/策略问题),或者用于 SDK 验证/配置的 AK/SK 缺少所需的 IAM 权限。 - 返回
404:对象路径/名称问题(例如缺少index.html或键路径不匹配),并非匿名权限正常的证明。
出现 403 时,应视为设置失败,并告知用户以下两种常见可能性:
- 存储桶/对象未针对网站访问设置为公共读取
- AK/SK 缺少 OBS 操作所需的 IAM 权限
通过 references/iam-policies.md 提供修复方法。
回复格式
始终返回:
- 输入摘要
- 已执行的操作
- 验证结果
- 失败时的修复步骤
DNS 由外部管理时,还应添加简短的 DNS 移交说明,准确告知用户应向服务提供商配置哪个 CNAME 记录。
安全规则
- 绝不打印密钥、AK/SK 或令牌。
- 网站端点验证通过前,不得宣称成功。
- 如果用户提供了自定义域名,最终成功必须以通过该自定义域名进行的验证为依据,不能只验证默认 OBS 主机名。
- 如果缺少权限,应停止并报告缺失的权限。
- 如果未说明 DNS 服务提供商归属,先询问 DNS 区域由 Huawei Cloud DNS 还是外部服务管理,再决定是否使用
hcloud步骤。 - 如果需要更改 Huawei Cloud DNS 才能完成操作,但尚不清楚 DNS 区域,请询问区域名称,不要猜测。
- 不得将常规存储桶端点作为最终网站结果。
- 如果存储桶名称包含句点,请提醒用户 HTTPS 访问可能存在问题。
- 如果用户要求使用 HTTPS 访问,必须通过
https://验证成功。verify_obs_website.py始终会检查 HTTP 和 HTTPS 端点,因此没有有效证书的自定义域名会报告 TLS 修复步骤。OBS 仅支持在自定义域名上使用 HTTPS,且只支持国际(通用)证书,不支持 SM(国密)证书;必须通过setBucketCustomDomain(..., certificateInfo=...)将证书绑定到自定义域名。 - 绝不打印或回显通过
--private-key传入的私钥内容。 obsutil仅可用于管理~/.obsutilconfig;不得用它配置网站托管。- 不得在此技能中执行任何对象上传操作。
- 尤其在验证期间,只能执行只读检查;绝不上传测试文件。
- 对于由外部管理的 DNS,不要只说“DNS 在外部管理”;还应提供完成设置所需的 CNAME 信息,供用户配置。
权限失败处理(必须)
任何命令因 IAM 权限错误而失败时:
- 阅读
references/iam-policies.md。 - 向用户展示所需权限列表和策略 JSON。
- 指导用户创建自定义 IAM 策略,并在 Huawei Cloud IAM 控制台中授予该策略。
- 暂停执行,并等待用户确认权限已授予。
参考资料
加载 references/obs-python-sdk-website.md,了解网站托管和自定义域名注册(setBucketCustomDomain)的 SDK 方法用法。
加载 references/iam-policies.md,了解所需的 IAM 操作和策略 JSON。
加载 references/hcloud-dns-obs-website.md,了解通过华为云 DNS(hcloud CLI)配置自定义域名 DNS CNAME 的分步说明,包括查询区域、创建记录和验证。
已知陷阱: 在 esdk-obs-python >= 3.x 中,
setBucketWebsiteAPI 使用WebsiteConfiguration模型对象,而不是indexDocumentSuffix之类的关键字参数。请务必导入WebsiteConfiguration、IndexDocument和ErrorDocument并正确构造。
脚本
仅将脚本用于可重复的检查和验证。命令输出应便于阅读,并聚焦于成功或失败。
scripts/set_obs_website_sdk.py <bucket_name> <endpoint> --custom-domain <domain> [--index-document <name>] [--error-document <name>]通过 OBS SDK 应用静态网站托管设置、注册所需的自定义域名,并从 CLI 参数、环境变量或~/.obsutilconfig读取凭据。OBS 支持通过setBucketCustomDomain(..., certificateInfo=...)在自定义域名上使用 HTTPS。要绑定证书,请将--certificate-name与--certificate+--private-key(直接使用 PEM)或--certificate-id(CCM 证书)搭配使用。仅支持国际(通用)证书,不支持 SM(国密)证书。scripts/verify_obs_website.py --bucket-name <name> --region <region> [--domain <custom_domain>] [--index-document <name>] [--json]验证端点的 DNS/HTTP/HTTPS 行为,并以只读方式检查存储桶是否存在及其区域(headBucket+getBucketLocation)。如果提供了--domain,则以该自定义域名作为最终验证目标;否则会自动构建默认网站 URL:http://<bucket>.obs.<region>.myhuaweicloud.com。始终验证http://和https://,因此可以检测并报告自定义域名上的 TLS 证书问题(certificate_verify_failed / hostname mismatch),并提供修复步骤。OBS API 端点仍为https://obs.<region>.myhuaweicloud.com。脚本会打印结构化部分(Input summary、Actions performed、Verification results、Remediation steps),便于 Agent 直接复用这些内容。
验证规则
加载 references/verification-method.md 了解验证规则。