mirror of
https://github.com/socketio/socket.io.git
synced 2026-04-30 03:00:39 -04:00
Compare commits
2 Commits
refactor/e
...
socket.io-
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
522edcdbb8 | ||
|
|
3fff7cafa9 |
@@ -2,6 +2,7 @@
|
||||
|
||||
| Version | Release date |
|
||||
|-------------------------------------------------------------------------------------------------------------|----------------|
|
||||
| [4.2.6](#426-2026-03-17) | March 2026 |
|
||||
| [4.2.5](#425-2025-12-23) | December 2025 |
|
||||
| [3.3.4](#334-2024-07-22) (from the [3.3.x](https://github.com/socketio/socket.io-parser/tree/3.3.x) branch) | July 2024 |
|
||||
| [4.2.4](#424-2023-05-31) | May 2023 |
|
||||
@@ -34,6 +35,15 @@
|
||||
| [3.3.0](#330-2018-11-07) | November 2018 |
|
||||
|
||||
|
||||
## [4.2.6](https://github.com/socketio/socket.io/compare/socket.io-parser@4.2.5...socket.io-parser@4.2.6) (2026-03-17)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **parser:** add a limit to the number of binary attachments ([3fff7ca](https://github.com/socketio/socket/commit/3fff7cafa98f1ba5840475b6917c651fe841a943))
|
||||
|
||||
|
||||
|
||||
## [4.2.5](https://github.com/socketio/socket.io/compare/socket.io-parser@4.2.4...socket.io-parser@4.2.5) (2025-12-23)
|
||||
|
||||
This release contains a bump of `debug` from `~4.3.1` to `~4.4.1`.
|
||||
|
||||
@@ -135,6 +135,20 @@ interface DecoderReservedEvents {
|
||||
decoded: (packet: Packet) => void;
|
||||
}
|
||||
|
||||
type JSONReviver = (this: any, key: string, value: any) => any;
|
||||
|
||||
export interface DecoderOptions {
|
||||
/**
|
||||
* Custom reviver to pass down to JSON.parse()
|
||||
*/
|
||||
reviver?: JSONReviver;
|
||||
/**
|
||||
* Maximum number of binary attachments per packet
|
||||
* @default 10
|
||||
*/
|
||||
maxAttachments?: number;
|
||||
}
|
||||
|
||||
/**
|
||||
* A socket.io Decoder instance
|
||||
*
|
||||
@@ -142,14 +156,20 @@ interface DecoderReservedEvents {
|
||||
*/
|
||||
export class Decoder extends Emitter<{}, {}, DecoderReservedEvents> {
|
||||
private reconstructor: BinaryReconstructor;
|
||||
private opts: Required<DecoderOptions>;
|
||||
|
||||
/**
|
||||
* Decoder constructor
|
||||
*
|
||||
* @param {function} reviver - custom reviver to pass down to JSON.stringify
|
||||
*/
|
||||
constructor(private reviver?: (this: any, key: string, value: any) => any) {
|
||||
constructor(opts?: DecoderOptions | JSONReviver) {
|
||||
super();
|
||||
this.opts = Object.assign(
|
||||
{
|
||||
reviver: undefined,
|
||||
maxAttachments: 10,
|
||||
},
|
||||
typeof opts === "function" ? { reviver: opts } : opts,
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -224,7 +244,13 @@ export class Decoder extends Emitter<{}, {}, DecoderReservedEvents> {
|
||||
if (buf != Number(buf) || str.charAt(i) !== "-") {
|
||||
throw new Error("Illegal attachments");
|
||||
}
|
||||
p.attachments = Number(buf);
|
||||
const n = Number(buf);
|
||||
if (!isInteger(n) || n < 0) {
|
||||
throw new Error("Illegal attachments");
|
||||
} else if (n > this.opts.maxAttachments) {
|
||||
throw new Error("too many attachments");
|
||||
}
|
||||
p.attachments = n;
|
||||
}
|
||||
|
||||
// look up namespace (if any)
|
||||
@@ -271,7 +297,7 @@ export class Decoder extends Emitter<{}, {}, DecoderReservedEvents> {
|
||||
|
||||
private tryParse(str) {
|
||||
try {
|
||||
return JSON.parse(str, this.reviver);
|
||||
return JSON.parse(str, this.opts.reviver);
|
||||
} catch (e) {
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "socket.io-parser",
|
||||
"version": "4.2.5",
|
||||
"version": "4.2.6",
|
||||
"description": "socket.io protocol parser",
|
||||
"homepage": "https://github.com/socketio/socket.io/tree/main/packages/socket.io-client#readme",
|
||||
"repository": {
|
||||
|
||||
@@ -107,6 +107,56 @@ describe("socket.io-parser", () => {
|
||||
}
|
||||
});
|
||||
|
||||
it("throws an error when receiving too many attachments", () => {
|
||||
const decoder = new Decoder({ maxAttachments: 2 });
|
||||
|
||||
expect(() => {
|
||||
decoder.add(
|
||||
'53-["hello",{"_placeholder":true,"num":0},{"_placeholder":true,"num":1},{"_placeholder":true,"num":2}]',
|
||||
);
|
||||
}).to.throwException(/^too many attachments$/);
|
||||
});
|
||||
|
||||
it("decodes with a custom reviver", () => {
|
||||
const decoder = new Decoder((key, value) => {
|
||||
if (key === "a") {
|
||||
return value.toUpperCase();
|
||||
} else {
|
||||
return value;
|
||||
}
|
||||
});
|
||||
|
||||
return new Promise((resolve) => {
|
||||
decoder.on("decoded", (packet) => {
|
||||
expect(packet.data).to.eql(["b", { a: "VAL" }]);
|
||||
resolve();
|
||||
});
|
||||
|
||||
decoder.add('2["b",{"a":"val"}]');
|
||||
});
|
||||
});
|
||||
|
||||
it("decodes with a custom reviver (options object)", () => {
|
||||
const decoder = new Decoder({
|
||||
reviver: (key, value) => {
|
||||
if (key === "a") {
|
||||
return value.toUpperCase();
|
||||
} else {
|
||||
return value;
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
return new Promise((resolve) => {
|
||||
decoder.on("decoded", (packet) => {
|
||||
expect(packet.data).to.eql(["b", { a: "VAL" }]);
|
||||
resolve();
|
||||
});
|
||||
|
||||
decoder.add('2["b",{"a":"val"}]');
|
||||
});
|
||||
});
|
||||
|
||||
it("throw an error upon parsing error", () => {
|
||||
const isInvalidPayload = (str) =>
|
||||
expect(() => new Decoder().add(str)).to.throwException(
|
||||
@@ -125,6 +175,16 @@ describe("socket.io-parser", () => {
|
||||
isInvalidPayload('2["connect"]');
|
||||
isInvalidPayload('2["disconnect","123"]');
|
||||
|
||||
const isInvalidAttachmentCount = (str) =>
|
||||
expect(() => new Decoder().add(str)).to.throwException(
|
||||
/^Illegal attachments$/,
|
||||
);
|
||||
|
||||
isInvalidAttachmentCount("5");
|
||||
isInvalidAttachmentCount("51");
|
||||
isInvalidAttachmentCount("5a-");
|
||||
isInvalidAttachmentCount("51.23-");
|
||||
|
||||
expect(() => new Decoder().add("999")).to.throwException(
|
||||
/^unknown packet type 9$/,
|
||||
);
|
||||
|
||||
Reference in New Issue
Block a user