Files
ruoyi-java/doc/腾讯文档API_Range格式说明.md
2025-11-06 11:05:22 +08:00

7.1 KiB
Raw Blame History

腾讯文档 API Range 格式说明

问题发现

在调用腾讯文档 V3 API 时,使用 Excel 格式的 rangeA3:Z203)会返回错误:

{
  "code": 400001,
  "message": "invalid param error: 'range' invalid"
}

正确的 Range 格式

腾讯文档 V3 API 使用索引格式,不是 Excel 的字母+数字格式。

格式规范

startRow,startColumn,endRow,endColumn

说明

  • 所有索引从 0 开始
  • 用逗号分隔四个值
  • startRow:起始行索引
  • startColumn:起始列索引
  • endRow:结束行索引
  • endColumn:结束列索引

📋 格式转换示例

示例 1读取表头第2行A到Z列

Excel 格式(错误):

A2:Z2

索引格式(正确):

1,0,1,25

解释

  • 第2行 → 索引 1行从0开始
  • A列 → 索引 0
  • 第2行 → 索引 1
  • Z列 → 索引 25A=0, B=1, ..., Z=25

示例 2读取数据行第3行到第203行A到Z列

Excel 格式(错误):

A3:Z203

索引格式(正确):

2,0,202,25

解释

  • 第3行 → 索引 2
  • A列 → 索引 0
  • 第203行 → 索引 202
  • Z列 → 索引 25

示例 3读取单个单元格M3

Excel 格式(错误):

M3

索引格式(正确):

2,12,2,12

解释

  • 第3行 → 索引 2
  • M列 → 索引 12A=0, ..., M=12
  • 结束行也是第3行 → 索引 2
  • 结束列也是M列 → 索引 12

🔢 行列索引对照表

行索引Excel行号 → 索引)

Excel 行号 索引
1 0
2 1
3 2
... ...
100 99
203 202

转换公式索引 = Excel行号 - 1

列索引(列字母 → 索引)

列字母 索引
A 0
B 1
C 2
D 3
... ...
M 12
... ...
Z 25
AA 26
AB 27

转换公式

  • 单字母:索引 = 字母 - 'A'A=0, B=1, ...
  • 多字母:索引 = (第一字母 - 'A' + 1) * 26 + (第二字母 - 'A')

💻 代码实现

Java 转换方法

/**
 * 将Excel行号转换为API索引
 * @param excelRow Excel行号从1开始
 * @return API索引从0开始
 */
public static int excelRowToIndex(int excelRow) {
    return excelRow - 1;
}

/**
 * 将列字母转换为索引
 * @param column 列字母A, B, C, ..., Z, AA, AB, ...
 * @return 列索引从0开始
 */
public static int columnLetterToIndex(String column) {
    column = column.toUpperCase();
    int index = 0;
    for (int i = 0; i < column.length(); i++) {
        index = index * 26 + (column.charAt(i) - 'A' + 1);
    }
    return index - 1;
}

/**
 * 将Excel范围转换为API range格式
 * @param excelRange Excel范围如 "A3:Z203"
 * @return API range格式如 "2,0,202,25"
 */
public static String excelRangeToApiRange(String excelRange) {
    // 解析 A3:Z203
    String[] parts = excelRange.split(":");
    String start = parts[0];  // A3
    String end = parts[1];    // Z203
    
    // 提取起始列和行
    int startCol = columnLetterToIndex(start.replaceAll("\\d", ""));  // A -> 0
    int startRow = Integer.parseInt(start.replaceAll("[A-Z]", "")) - 1;  // 3 -> 2
    
    // 提取结束列和行
    int endCol = columnLetterToIndex(end.replaceAll("\\d", ""));  // Z -> 25
    int endRow = Integer.parseInt(end.replaceAll("[A-Z]", "")) - 1;  // 203 -> 202
    
    return String.format("%d,%d,%d,%d", startRow, startCol, endRow, endCol);
}

使用示例

// 读取表头第2行
int headerRowIndex = headerRow - 1;  // 2 -> 1
String headerRange = String.format("%d,0,%d,25", headerRowIndex, headerRowIndex);
// 结果:"1,0,1,25"

// 读取数据行第3行到第203行
int startRowIndex = startRow - 1;  // 3 -> 2
int endRowIndex = endRow - 1;      // 203 -> 202
String dataRange = String.format("%d,0,%d,25", startRowIndex, endRowIndex);
// 结果:"2,0,202,25"

// 读取单个单元格M3
int rowIndex = 2;     // 第3行 -> 索引2
int colIndex = 12;    // M列 -> 索引12
String cellRange = String.format("%d,%d,%d,%d", rowIndex, colIndex, rowIndex, colIndex);
// 结果:"2,12,2,12"

🔍 API 调用示例

完整的 API URL

https://docs.qq.com/openapi/spreadsheet/v3/files/{fileId}/{sheetId}/{range}

示例

# 读取表头第2行
https://docs.qq.com/openapi/spreadsheet/v3/files/DUW50RUprWXh2TGJK/BB08J2/1,0,1,25

# 读取数据行第3行到第203行
https://docs.qq.com/openapi/spreadsheet/v3/files/DUW50RUprWXh2TGJK/BB08J2/2,0,202,25

# 读取单个单元格M3
https://docs.qq.com/openapi/spreadsheet/v3/files/DUW50RUprWXh2TGJK/BB08J2/2,12,2,12

⚠️ 常见错误

错误 1使用 Excel 格式

❌ https://.../ files/xxx/yyy/A3:Z203
✅ https://.../files/xxx/yyy/2,0,202,25

错误 2索引从 1 开始

❌ 第1行 → 索引 1
✅ 第1行 → 索引 0

❌ A列 → 索引 1
✅ A列 → 索引 0

错误 3行列顺序错误

❌ startColumn,startRow,endColumn,endRow
✅ startRow,startColumn,endRow,endColumn

正确顺序:行在前,列在后


📊 快速参考表

Excel 表示 索引格式 说明
A1:Z1 0,0,0,25 第1行A到Z列
A2:Z2 1,0,1,25 第2行A到Z列表头
A3:Z203 2,0,202,25 第3行到第203行A到Z列
A1:A100 0,0,99,0 A列前100行
M3 2,12,2,12 M列第3行单个单元格
A1 0,0,0,0 A1单元格
AA1:AZ100 0,26,99,51 AA到AZ列前100行

🔧 修改记录

修改文件

  1. TencentDocApiUtil.java

    • 更新 readSheetData 方法的注释
    • 说明 range 格式为索引格式
  2. TencentDocController.java

    • 将 range 构建从 Excel 格式改为索引格式
    • 添加详细的转换日志
  3. TencentDocServiceImpl.java

    • 添加 API 错误响应检查
    • 当 code != 0 时抛出异常

🎯 测试验证

测试参数

{
  "accessToken": "YOUR_ACCESS_TOKEN",
  "fileId": "DUW50RUprWXh2TGJK",
  "sheetId": "BB08J2",
  "headerRow": 2,
  "orderNoColumn": 2,
  "logisticsLinkColumn": 12
}

预期日志输出

读取表头 - Excel行号: 2, 索引行号: 1, range: 1,0,1,25
读取数据行 - Excel行号: 3 ~ 203, 索引: 2 ~ 202, range: 2,0,202,25

成功响应

{
  "gridData": {
    "startRow": 1,
    "startColumn": 0,
    "rows": [
      {
        "values": [
          {"cellValue": {"text": "日期"}},
          {"cellValue": {"text": "公司"}},
          {"cellValue": {"text": "草号"}},
          ...
        ]
      }
    ]
  }
}

📚 参考文档

根据实际API测试结果和错误提示总结的格式规范。

关键要点

  1. Range 使用索引格式:startRow,startColumn,endRow,endColumn
  2. 所有索引从 0 开始
  3. 顺序:行在前,列在后
  4. Excel行号需要减1转换为索引

文档版本1.0
创建时间2025-11-05
修改原因:修复 "invalid param error: 'range' invalid" 错误