You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用discord.py开发Roblox游戏通行证校验脚本遇TypeError问题求助

问题描述

我用Python搭配discord.py开发脚本,校验Roblox用户是否拥有指定游戏通行证,通过调用API处理JSON响应实现。运行时出现错误:
discord.ext.commands.errors.CommandInvokeError: Command raised an exception: TypeError: list indices must be integers or slices, not str
试过用int()包裹疑似问题的部分,但没解决,哪里错了?

API响应示例

{"previousPageCursor":null,"nextPageCursor":null,"data":[{"type":"GamePass","id":1234567,"name":"foo","instanceId":null}]}

报错追踪信息

<Response [200]>
Ignoring exception in command foo:
Traceback (most recent call last):
  File "C:\Users\RED\AppData\Local\Programs\Python\Python310\lib\site-packages\discord\ext\commands\core.py", line 85, in wrapped
    ret = await coro(*args, **kwargs)
  File "C:\Users\RED\Documents\Programs\Python\foo.py", line 110, in robux
    if int(response['data']['id']) == int(gamepassid):
TypeError: list indices must be integers or slices, not str

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "C:\Users\RED\AppData\Local\Programs\Python\Python310\lib\site-packages\discord\ext\commands\bot.py", line 939, in invoke
    await ctx.command.invoke(ctx)
  File "C:\Users\RED\AppData\Local\Programs\Python\Python310\lib\site-packages\discord\ext\commands\core.py", line 863, in invoke
    await injected(*ctx.args, **ctx.kwargs)
  File "C:\Users\RED\AppData\Local\Programs\Python\Python310\lib\site-packages\discord\ext\commands\core.py", line 94, in wrapped
    raise CommandInvokeError(exc) from exc
discord.ext.commands.errors.CommandInvokeError: Command raised an exception: TypeError: list indices must be integers or slices, not str

完整代码

# 发送GET请求到用户信息接口并存储响应
response = requests.get(f'https://users.roblox.com/v1/users/{robloxid}')
# 响应状态码为200时处理用户信息
if response.status_code == 200:
    response = response.json()
    # 发送提示Embed
    embed = discord.Embed(title=f'Welcome {response["name"]}.', description=f'We are now checking if you own the target gamepass, please wait...', color=discord.Color.from_rgb(125,165,101))
    await ctx.send(embed=embed)
    # 从products.json读取游戏通行证ID映射
    with open('products.json') as f:
        data = json.load(f)
        print("Loaded products.json")
    # 提取商品列表
    products = data['products']
    print (products)
    # 遍历商品列表匹配目标ID
    for product in products:
        print("for loop")
        if product['productid'] == int(productid):
            print ("if statement")
            gamepassid = product['gamepassid']
            print (gamepassid)
            # 发送GET请求校验通行证拥有状态
            response = requests.get(f'https://inventory.roblox.com/v1/users/{robloxid}/items/GamePass/{gamepassid}')
            print (response)
            if response.status_code == 200:
                response = response.json()
                # 校验通行证ID是否匹配
                if int(response['data']['id']) == int(gamepassid):
                    embed = discord.Embed(title=f'You own the product!', color=discord.Color.from_rgb(125,165,101))
                    await ctx.send(embed=embed)
                else:
                    embed = discord.Embed(title=f'You do not own the product', color=discord.Color.from_rgb(255,0,0))
                    await ctx.send(embed=embed)
            else:
                embed = discord.Embed(title=f'There was an error', color=discord.Color.from_rgb(255,0,0))
                await ctx.send(embed=embed)
# 用户不存在的情况
elif response.status_code == 404:
    embed = discord.Embed(title='User does not exist', color=discord.Color.red())
    await ctx.send(embed=embed)
# 其他错误情况
else:
    embed = discord.Embed(title='An error has occurred', color=discord.Color.red())
    await ctx.send(embed=embed)
解决方案

看API响应示例就能发现,response['data']是一个列表(方括号[]包裹的部分),不是字典。你直接用response['data']['id']取值,相当于给列表传入字符串索引,这就触发了TypeError。

正确处理方式:

  1. 先判断data列表是否非空(用户拥有通行证时列表会有对应对象,未拥有则为空)
  2. 从列表中取出第一个元素(同一通行证用户只会有一条记录),再访问id字段

修改代码中的判断逻辑:

# 替换原有的if int(response['data']['id']) == int(gamepassid):
if response['data']:  # 先检查列表是否有内容
    # 取列表第一个元素的ID进行匹配
    if int(response['data'][0]['id']) == int(gamepassid):
        embed = discord.Embed(title=f'你拥有该商品!', color=discord.Color.from_rgb(125,165,101))
        await ctx.send(embed=embed)
    else:
        embed = discord.Embed(title=f'你未拥有该商品', color=discord.Color.from_rgb(255,0,0))
        await ctx.send(embed=embed)
else:
    # 列表为空,说明用户未拥有该通行证
    embed = discord.Embed(title=f'你未拥有该商品', color=discord.Color.from_rgb(255,0,0))
    await ctx.send(embed=embed)

另外,你代码里重复使用response变量存储不同接口的响应,虽然逻辑能跑,但容易混淆,建议给不同响应起不同变量名,比如user_response、gamepass_response,避免后续出错。

内容的提问来源于stack exchange,提问作者Stature Official

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.23 12:24:21