Node.js中Hex转ASCII异常?RS232秤通信数据解析问题
Hey there! I totally get how frustrating it can be when you’ve got communication working but hit a snag parsing the data. Let’s break down what’s going on with that buffer and fix the conversion issue.
First, let’s start with the raw buffer you have:
const scaleBuffer = Buffer.from([0x06, 0x02, 0x30, 0x32, 0x1b, 0x33, 0x1b, 0x31, 0x31, 0x34, 0x34, 0x35, 0x1b, 0x30, 0x30, 0x30, 0x1b, 0x30, 0x30, 0x1b, 0x30, 0x30, 0x1b, 0x30, 0x30, 0x03]);
Why the "Error" Happens (Spoiler: It’s Probably Not an Error!)
When you convert this buffer to ASCII, you’re seeing what looks like errors because it contains control characters that are part of the RS232 protocol your scale uses:
0x06: ACK (acknowledge signal) – invisible in standard output0x02: STX (start of text) – marks the beginning of the data frame0x1b: ESC (escape character) – used to signal protocol-specific commands/segments0x03: ETX (end of text) – marks the end of the data frame
These are normal parts of the scale’s communication, not conversion errors. Let’s convert it properly and extract the useful data.
Step 1: Convert Buffer to ASCII Correctly
Use Node.js’s built-in toString('ascii') method – this won’t throw an error, but you’ll see invisible control characters in the output:
const asciiString = scaleBuffer.toString('ascii'); console.log(asciiString); // Output will look like: 0231144500000000000 // (The weird symbols are the control characters mentioned above)
Step 2: Extract Useful Data
If you want to get rid of the control characters and focus on the printable data, filter out non-printable ASCII bytes (0x20 to 0x7E are printable):
const printableData = scaleBuffer .filter(byte => byte >= 0x20 && byte <= 0x7E) .toString('ascii'); console.log(printableData); // Output: 023114450000000000
Step 3: Parse the Scale’s Protocol
For more precise parsing, use the STX and ETX markers to isolate the core data frame, then split by the ESC characters to get individual segments:
// Find positions of STX (0x02) and ETX (0x03) const stxPos = scaleBuffer.indexOf(0x02); const etxPos = scaleBuffer.indexOf(0x03); if (stxPos !== -1 && etxPos !== -1 && etxPos > stxPos) { // Extract the data between STX and ETX const dataFrame = scaleBuffer.slice(stxPos + 1, etxPos).toString('ascii'); // Split by ESC character (\x1b) to get protocol segments const protocolSegments = dataFrame.split('\x1b'); console.log('Raw data frame:', dataFrame); console.log('Parsed segments:', protocolSegments); // Output segments: ['02', '3', '11445', '000', '00', '00', '00', '00'] }
Those segments (like 11445) are likely the weight reading or other scale metrics – you’ll need to cross-reference your scale’s communication manual to know exactly what each segment represents.
内容的提问来源于stack exchange,提问作者João Moreira

