通用基础项目

    15. 完成统计和消耗机制

    会员专享 · 非会员仅可阅读 30% 的正文。

    发布时间
    August 10, 2025
    阅读时间
    2 min read
    作者
    Felix
    访问
    会员专享
    这是预览内容

    非会员仅可阅读 30% 的正文。

    因为我们是做AI应用,就需要对于用户的消耗进行统计,以便限制无限的刷量,而现在市面上有两种最主流对于用户消耗限制的方法:

    - 基于Token的计算

    - 这种方法主要用于大语言模型(LLM)API的计费,如OpenAI的GPT系列模型 - Token是文本的基本单位,通常一个单词约为1.3个token,一个汉字约为2个token - 优点:精确反映模型处理的实际计算量,与模型的计算成本直接相关 - 缺点:对于用户来说较难理解,不同语言的token数量差异较大 - 实现方式:通过模型返回的token消耗,累计计费

    - 基于次数的计算: - 这种方法以用户的请求次数为基础进行计费 - 优点:简单直观,用户容易理解自己的使用情况 - 缺点:自己在计算成本和消耗的时候会比较困难,并且太透明了 - 实现方式:记录API调用次数,可以按不同功能或模型分别统计

    而我比较倾向Token的计算消耗机制,举个例子:你某个功能最开始让用户用5次,但这时候我们发现消耗成本太大了,发现你要削减次数,你一削减次数用户就抱怨。 如果采用Token机制,你可以自己调控消耗倍率,原本是一倍的消耗,如果这时候要提高收益率就可以提升到2倍的消耗,这比较隐形(大多数用户是不会去算的),并且使用Token的机制会更好的统计成本。

    本章Tag

    完成表结构

    非常简单,只需要加一个关联用户消耗的关联表即可,跑一下pnpm db:generatepnpm db:migrate-local

    // next-cloudflare-template/lib/db/schema.ts
    export const userUsage = sqliteTable('userUsage', {
      id: text('id')
        .primaryKey()
        .$defaultFn(() => crypto.randomUUID()),
      userId: text('userId')
        .notNull()
        .references(() => users.id, { onDelete: 'cascade' }),
      usedTokens: integer('usedTokens').notNull().default(0),
      totalTokens: integer('totalTokens').notNull().default(0)
    })
    ```
    
    表里有二个字段解释一下:
    
    1. `usedTokens`:消耗的总Token数量
    2. `totalTokens`:拥有的总Token数量
    
    实际上,更完备的做法是两张表、一张是总消耗的聚合表、一张是每一条消耗的具体信息(包含各种模型参数、输入、输出)。但在初期这是没必要的,只需要一张消耗聚合表(`userUsage`)就够了,一条记录对应一个用户的消耗。
    
    > 有一件非常讨厌的事情,就是D1是不支持事务的,所以在表结构设计(尽量单表、幂等、补偿)的时候要去尽量避免事务,这里有一个为什么不支持的[文档](https://blog.cloudflare.com/whats-new-with-d1/)。
    
    ## 完成API和基本逻辑
    
    ### 插入逻辑
    
    这张表适插入新的数据时机是当用户注册创建的时候(因为会需要展示用户一共有多少用量),在Auth添加一个 createUser 事件处理器
    
    ```typescript
    //lib/auth.ts
    events: {
      createUser: async ({ user }) => {
        db.insert(userUsage).values({
          userId: user.id!,
          usedTokens: 0,
          totalTokens: 1000
        })
      }
    }
    ```
    
    简单尝试一下,本地新注册一下,可以看到是正常插入的。
    
    ![](https://ik.imagekit.io/ixou4q6nu/insert-usage.png?updatedAt=1750497093998)
    
    ### 添加Google生态的API
    
    因为要做模型消耗的统计,正好就把Google生态的AI接入,最近他们的表现非常好。`pnpm add @google/genai`,紧接着`https://cloud.google.com/`去领取300$,最后去`https://aistudio.google.com/apikey`创建API Key。
    
    后续的调试模型也是直接在`Studio`里调试,在开发之前,我们需要把上一步得到的`key`贴到`env`中(我的变量名是叫`GEMINI_API_KEY`),同样先完成Actions```typescript
    'use server'
    
    import { GoogleGenAI } from '@google/genai'
    
    export type GeminiGenerationParams = {
      prompt: string
      userId: string
      model?: string
      temperature?: number
      maxOutputTokens?: number
      systemPrompt?: string
      userPrompt?:
    会员专享

    订阅后解锁完整文章

    支持创作、解锁全文,未来更新也会第一时间送达。

    评论

    加入讨论

    0 条评论
    登录后评论

    还没有评论,来占个沙发吧。