Skip to content

Commit

Permalink
[FIX] Resource: Keep stats size up to date (#253)
Browse files Browse the repository at this point in the history
Ensure statInfo.size is always set when resource's content is modified.

Co-authored-by: Matthias Osswald <mat.osswald@sap.com>
  • Loading branch information
tobiasso85 and matz3 authored Jun 26, 2020
1 parent bc5eafb commit 0ef976f
Show file tree
Hide file tree
Showing 2 changed files with 95 additions and 5 deletions.
25 changes: 20 additions & 5 deletions lib/Resource.js
Original file line number Diff line number Diff line change
Expand Up @@ -70,11 +70,14 @@ class Resource {
birthtime: new Date()
};

this._createStream = createStream || null;
this._stream = stream || null;
this._buffer = buffer || null;
if (typeof string === "string" || string instanceof String) {
this._buffer = Buffer.from(string, "utf8");
if (createStream) {
this._createStream = createStream;
} else if (stream) {
this._stream = stream;
} else if (buffer) {
this.setBuffer(buffer);
} else if (typeof string === "string" || string instanceof String) {
this.setString(string);
}

// Tracing:
Expand Down Expand Up @@ -117,6 +120,7 @@ class Resource {
this._buffer = buffer;
this._contentDrained = false;
this._streamDrained = false;
this._setSize(this._buffer.byteLength);
}

/**
Expand Down Expand Up @@ -207,6 +211,17 @@ class Resource {
this._streamDrained = false;
}

/**
* Set the size in bytes
*
* @param {number} size byte size
* @private
* @see https://nodejs.org/api/fs.html#fs_stats_size
*/
_setSize(size) {
this._statInfo.size = size;
}

/**
* Gets the resources path
*
Expand Down
75 changes: 75 additions & 0 deletions test/lib/Resource.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@ const test = require("ava");
const Stream = require("stream");
const fs = require("fs");
const path = require("path");
const {promisify} = require("util");
const stat = promisify(fs.stat);
const Resource = require("../../lib/Resource");

function createBasicResource() {
Expand Down Expand Up @@ -142,6 +144,58 @@ test("Resource: setString", (t) => {
});
});

test("Resource: size modification", async (t) => {
const resource = new Resource({
path: "my/path/to/resource"
});
t.falsy(resource.getStatInfo().size, "initial size is not defined");

// string
resource.setString("Content");

t.is(resource.getStatInfo().size, 7, "size after manually setting the string");
t.is(new Resource({
path: "my/path/to/resource",
string: "Content"
}).getStatInfo().size, 7, "size when passing string to constructor");


// buffer
resource.setBuffer(Buffer.from("Super"));

t.is(resource.getStatInfo().size, 5, "size after manually setting the string");

const clonedResource1 = await resource.clone();
t.is(clonedResource1.getStatInfo().size, 5, "size after cloning the resource");


// buffer with alloc
const buf = Buffer.alloc(1234);
buf.write("some string", 0, "utf8");
resource.setBuffer(buf);

t.is(resource.getStatInfo().size, 1234, "buffer with alloc after setting the buffer");
t.is(new Resource({
path: "my/path/to/resource",
buffer: buf
}).getStatInfo().size, 1234, "buffer with alloc when passing buffer to constructor");

const clonedResource2 = await resource.clone();
t.is(clonedResource2.getStatInfo().size, 1234, "buffer with alloc atfer clone");
});

test("Resource: _setSize", (t) => {
t.plan(1);

const resource = new Resource({
path: "my/path/to/resource"
});

resource._setSize(1337);

t.is(resource.getStatInfo().size, 1337);
});

test("Resource: setStream", (t) => {
t.plan(1);

Expand Down Expand Up @@ -267,3 +321,24 @@ test("getBuffer from Stream content: Subsequent content requests should not thro
// to throw "Content stream of Resource /app/index.html is flagged as drained."
await t.notThrowsAsync(p2);
});

test("integration stat - resource size", async (t) => {
const fsPath = path.join("test", "fixtures", "application.a", "webapp", "index.html");
const statInfo = await stat(fsPath);

const resource = new Resource({
path: fsPath,
statInfo,
createStream: () => {
return fs.createReadStream(fsPath);
}
});
t.is(resource.getStatInfo().size, 91);

// Setting the same content again should end up with the same size
resource.setString(await resource.getString());
t.is(resource.getStatInfo().size, 91);

resource.setString("myvalue");
t.is(resource.getStatInfo().size, 7);
});

0 comments on commit 0ef976f

Please sign in to comment.