Skip to content

Commit 333bc54

Browse files
authored
Merge pull request #318 from ravendb/315
Fixing multi-byte characters parsing from the server
2 parents 3fad904 + 921c910 commit 333bc54

File tree

6 files changed

+61
-10
lines changed

6 files changed

+61
-10
lines changed

src/Http/RavenCommandResponsePipeline.ts

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -172,19 +172,27 @@ export class RavenCommandResponsePipeline<TStreamResult> extends EventEmitter {
172172
streams.push(...opts.jsonAsync.filters);
173173
}
174174
} else if (opts.jsonSync) {
175-
const jsonChunks = [];
175+
const bytesChunks = [];
176176
const parseJsonSyncTransform = new stream.Transform({
177177
readableObjectMode: true,
178178
transform(chunk, enc, callback) {
179-
jsonChunks.push(chunk.toString("utf8"));
179+
bytesChunks.push(chunk);
180180
callback();
181181
},
182182
flush(callback) {
183+
let str = null;
183184
try {
184-
callback(null, JSON.parse(jsonChunks.join("")));
185+
str = Buffer.concat(bytesChunks).toString('utf-8');
186+
} catch(err){
187+
callback(
188+
getError("InvalidDataException", `Failed to concat / decode server response`, err));
189+
return;
190+
}
191+
try {
192+
callback(null, JSON.parse(str));
185193
} catch (err) {
186194
callback(
187-
getError("InvalidOperationException", `Error parsing response: '${jsonChunks.join("")}'.`, err));
195+
getError("InvalidOperationException", `Error parsing response: '${str}'.`, err));
188196
}
189197
}
190198
});

src/Utility/StreamUtil.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ export async function readToEnd(readable: stream.Readable | stream.Stream): Prom
3333
readable.on("data", chunk => chunks.push(chunk));
3434

3535
await finishedAsync(readable);
36-
return chunks.join("");
36+
return Buffer.concat(chunks).toString('utf-8');
3737
}
3838

3939
export function bufferToReadable(b: Buffer) {

test/Issues/Github_315.ts

Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
import * as assert from "assert";
2+
import { testContext, disposeTestDocumentStore } from "../Utils/TestUtil";
3+
4+
import {
5+
IDocumentStore,
6+
} from "../../src";
7+
8+
describe("Issue #315", function () {
9+
10+
let store: IDocumentStore;
11+
12+
beforeEach(async function () {
13+
store = await testContext.getDocumentStore();
14+
});
15+
16+
afterEach(async () =>
17+
await disposeTestDocumentStore(store));
18+
19+
it("can use complex multi byte characters on load", async () => {
20+
21+
const str = '🐛'.repeat(50_000);
22+
{
23+
const session = store.openSession();
24+
const doc = {'str': str};
25+
await session.store(doc, "items/1");
26+
await session.saveChanges();
27+
}
28+
29+
{
30+
const session = store.openSession();
31+
const item = await session.load("items/1");
32+
assert.ok(item);
33+
assert.strictEqual(item['str'], str);
34+
}
35+
36+
{
37+
const session = store.openSession();
38+
const item = (await session.advanced.rawQuery("from @all_docs").all())[0];
39+
assert.strictEqual(item['str'], str);
40+
}
41+
});
42+
});

test/Ported/Issues/RavenDB_15497.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -54,9 +54,9 @@ describe("RavenDB_15497", function () {
5454

5555
await assertThrows(() => session.saveChanges(), e => {
5656
assertThat(e.name)
57-
.isEqualTo("TimeoutException");
57+
.isEqualTo("RavenTimeoutException");
5858
assertThat(e.message)
59-
.contains("System.TimeoutException");
59+
.contains("RavenTimeoutException");
6060
assertThat(e.message)
6161
.contains("could not verify that");
6262
});

test/Ported/Server/LogsConfigurationTest.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,9 @@ describe("LogsConfigurationTest", function () {
2424
let logsConfig = await store.maintenance.server.send(getOperation);
2525

2626
assertThat(logsConfig.currentMode)
27-
.isEqualTo("Operations");
27+
.isEqualTo("None");
2828
assertThat(logsConfig.mode)
29-
.isEqualTo("Operations");
29+
.isEqualTo("None");
3030

3131
// now try to set mode to operations and info
3232

@@ -46,7 +46,7 @@ describe("LogsConfigurationTest", function () {
4646
assertThat(logsConfig.currentMode)
4747
.isEqualTo("Information");
4848
assertThat(logsConfig.mode)
49-
.isEqualTo("Operations");
49+
.isEqualTo("None");
5050
} finally {
5151
// try to clean up
5252

test/TestDriver/RavenServerRunner.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@ export abstract class RavenServerRunner {
3535
"--RunInMemory=true",
3636
"--License.Eula.Accepted=true",
3737
"--Setup.Mode=None",
38+
"--Logs.Mode=None",
3839
`--Testing.ParentProcessId=${ process.pid }`,
3940
...locator.getCommandArguments()
4041
];

0 commit comments

Comments
 (0)