diff --git a/scripts/wiki_write.py b/scripts/wiki_write.py index 8c63662..2609173 100644 --- a/scripts/wiki_write.py +++ b/scripts/wiki_write.py @@ -48,57 +48,20 @@ def write_blocks(node_token, blocks): headers=h, json={'start_index': 0, 'end_index': len(cids)} ) - # Separate table groups from normal blocks - normal_blocks = [] - table_groups = [] - i = 0 - while i < len(blocks): - b = blocks[i] - if b.get('__table'): - group = [] - table_prefix = b.get('block_id', '') - j = i - # Collect table + cells + cell content (all tagged with __table or have matching ecc_ block_id) - while j < len(blocks): - bj = blocks[j] - bid = bj.get('block_id', '') - # Same table group: __table marker, cell/child with matching prefix, or continuation - if bj.get('__table') and j != i: - break - if bj.get('block_type') == 31 and not bj.get('__table'): - break - # Stop at unrelated blocks (non-table, non-cell blocks without matching prefix) - if not bj.get('__table') and not bid.startswith('ecc_t'): - # Only include empty text blocks with block_id (spacers next to table) - if bj.get('block_type') == 2 and bid: - elements = bj.get('text', {}).get('elements', []) - if elements and all(e.get('text_run', {}).get('content', '') == '' for e in elements): - pass # empty spacer included - else: - break - else: - break - group.append(bj) - j += 1 - table_groups.append(group) - i = j - else: - normal_blocks.append(b) - i += 1 - - # Write normal blocks in batches + # Write blocks in source order: normal blocks interleaved with tables batch_size = 25 - for idx in range(0, len(normal_blocks), batch_size): - batch = normal_blocks[idx:idx + batch_size] - r = requests.post( - f'https://open.feishu.cn/open-apis/docx/v1/documents/{doc_id}/blocks/{doc_id}/children', - headers=h, json={'children': batch, 'index': -1} - ) - if r.json().get('code') != 0: - raise Exception(f"Write batch {idx // batch_size} failed: {r.json().get('msg')}") - # Write table groups via descendant API - for group_idx, group in enumerate(table_groups): + def write_normal_batch(batch): + for idx in range(0, len(batch), batch_size): + chunk = batch[idx:idx + batch_size] + r = requests.post( + f'https://open.feishu.cn/open-apis/docx/v1/documents/{doc_id}/blocks/{doc_id}/children', + headers=h, json={'children': chunk, 'index': -1} + ) + if r.json().get('code') != 0: + raise Exception(f"Write batch failed: {r.json().get('msg')}") + + def write_table_group(group): table_block = group[0] descendants = [strip_table_meta(b) for b in group] table_bid = table_block.get('block_id', table_block.get('children', [''])[0]) @@ -113,7 +76,47 @@ def write_blocks(node_token, blocks): ) rd = r.json() if rd.get('code') != 0: - raise Exception(f"Table {group_idx} descendant API failed: {rd.get('msg')}") + raise Exception(f"Table descendant API failed: {rd.get('msg')}") + + normal_batch = [] + i = 0 + while i < len(blocks): + b = blocks[i] + if b.get('__table'): + # Flush pending normal blocks before the table to keep source order + if normal_batch: + write_normal_batch(normal_batch) + normal_batch = [] + # Collect this table group: table + cells + cell content + group = [] + j = i + while j < len(blocks): + bj = blocks[j] + bid = bj.get('block_id', '') + if bj.get('__table') and j != i: + break + if bj.get('block_type') == 31 and not bj.get('__table'): + break + if not bj.get('__table') and not bid.startswith('ecc_t'): + if bj.get('block_type') == 2 and bid: + elements = bj.get('text', {}).get('elements', []) + if elements and all(e.get('text_run', {}).get('content', '') == '' for e in elements): + pass # empty spacer included + else: + break + else: + break + group.append(bj) + j += 1 + write_table_group(group) + i = j + else: + normal_batch.append(b) + i += 1 + + # Flush remaining normal blocks + if normal_batch: + write_normal_batch(normal_batch) return True