File size: 4,987 Bytes
1b21241
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
const fs = require('fs');
const path = require('path');
const { XMLParser, XMLBuilder } = require('fast-xml-parser');
const StreamArray = require('stream-json/streamers/StreamArray');
const { chain } = require('stream-chain');
const { parser } = require('stream-json');
const { pick } = require('stream-json/filters/Pick');
const { ignore } = require('stream-json/filters/Ignore');
const performanceMonitor = require('./performance');

/**
 * XML与JSON处理模块
 * 演示:
 * 1. 使用 fast-xml-parser 解析和生成XML
 * 2. 使用 stream-json 流式处理大型JSON文件
 */
class XmlJsonHandler {
    constructor() {
        this.xmlParser = new XMLParser();
        this.xmlBuilder = new XMLBuilder();
    }

    /**
     * 生成测试用的 XML 数据
     */
    generateXml(itemCount = 1000) {
        performanceMonitor.start('生成XML');
        const items = [];
        for (let i = 0; i < itemCount; i++) {
            items.push({
                id: i,
                name: `Item_${i}`,
                price: Math.random() * 100,
                description: `Description for item ${i}`
            });
        }
        
        const xmlObj = {
            root: {
                metadata: { timestamp: Date.now() },
                items: { item: items }
            }
        };

        const xmlContent = this.xmlBuilder.build(xmlObj);
        performanceMonitor.end('生成XML');
        return xmlContent;
    }

    /**
     * 解析 XML 数据
     */
    parseXml(xmlContent) {
        performanceMonitor.start('解析XML');
        const result = this.xmlParser.parse(xmlContent);
        // 简单处理:统计 items 数量
        const count = result.root.items.item.length;
        console.log(`[XML处理] 解析完成,包含 ${count} 个条目`);
        performanceMonitor.end('解析XML');
        return result;
    }

    /**
     * 生成测试用的大型 JSON 文件
     */
    async generateLargeJson(filePath, itemCount = 50000) {
        performanceMonitor.start('生成大JSON文件');
        return new Promise((resolve, reject) => {
            const stream = fs.createWriteStream(filePath);
            stream.write('[\n'); // 开始 JSON 数组
            
            let i = 0;
            const writeNext = () => {
                let ok = true;
                do {
                    i++;
                    const item = {
                        id: i,
                        data: `Data_${i}`,
                        timestamp: Date.now(),
                        nested: { info: `Nested info ${i}` }
                    };
                    const isLast = i === itemCount;
                    const content = JSON.stringify(item) + (isLast ? '' : ',\n');
                    
                    if (isLast) {
                        stream.write(content);
                        stream.write('\n]'); // 结束 JSON 数组
                        stream.end();
                    } else {
                        ok = stream.write(content);
                    }
                } while (i < itemCount && ok);

                if (i < itemCount) {
                    stream.once('drain', writeNext);
                }
            };
            
            writeNext();

            stream.on('finish', () => {
                performanceMonitor.end('生成大JSON文件');
                console.log(`[JSON处理] 已生成大JSON文件: ${filePath}`);
                resolve();
            });
            stream.on('error', reject);
        });
    }

    /**
     * 流式解析大型 JSON 文件
     * 使用 stream-json 避免将整个大数组加载进内存
     */
    async processLargeJsonStream(filePath) {
        performanceMonitor.start('流式处理大JSON');
        
        return new Promise((resolve, reject) => {
            let counter = 0;
            
            // 构建流处理链:读取 -> 解析 -> 提取数组元素 -> 处理每个对象
            const pipeline = chain([
                fs.createReadStream(filePath),
                parser(),
                StreamArray.streamArray(), // 假设顶层是一个数组
            ]);

            pipeline.on('data', (data) => {
                // data 结构: { key: number, value: object }
                counter++;
                // 模拟处理逻辑,比如每处理 10000 条打印一次进度
                if (counter % 10000 === 0) {
                    // console.log(`[JSON流] 已处理 ${counter} 条记录...`);
                }
            });

            pipeline.on('end', () => {
                console.log(`[JSON流] 处理完成,共计 ${counter} 条记录`);
                performanceMonitor.end('流式处理大JSON');
                resolve();
            });

            pipeline.on('error', (err) => {
                console.error('[JSON流] 处理出错:', err);
                reject(err);
            });
        });
    }
}

module.exports = new XmlJsonHandler();