2021-05-26 10:43:21 +00:00
|
|
|
// Copyright 2021 the V8 project authors. All rights reserved.
|
|
|
|
// Use of this source code is governed by a BSD-style license that can be
|
|
|
|
// found in the LICENSE file.
|
|
|
|
|
2021-05-27 12:06:37 +00:00
|
|
|
// Flags: --experimental-d8-web-snapshot-api
|
2021-05-26 10:43:21 +00:00
|
|
|
|
2021-06-08 11:03:17 +00:00
|
|
|
function use(exports) {
|
2021-05-27 16:22:06 +00:00
|
|
|
const result = Object.create(null);
|
2021-06-08 11:03:17 +00:00
|
|
|
exports.forEach(x => result[x] = globalThis[x]);
|
2021-05-27 16:22:06 +00:00
|
|
|
return result;
|
|
|
|
}
|
2021-05-26 10:43:21 +00:00
|
|
|
|
2021-05-27 16:22:06 +00:00
|
|
|
function takeAndUseWebSnapshot(createObjects, exports) {
|
|
|
|
// Take a snapshot in Realm r1.
|
|
|
|
const r1 = Realm.create();
|
2021-06-08 11:03:17 +00:00
|
|
|
Realm.eval(r1, createObjects, {type: 'function'});
|
2021-05-27 16:22:06 +00:00
|
|
|
const snapshot = Realm.takeWebSnapshot(r1, exports);
|
|
|
|
// Use the snapshot in Realm r2.
|
|
|
|
const r2 = Realm.create();
|
|
|
|
const success = Realm.useWebSnapshot(r2, snapshot);
|
|
|
|
assertTrue(success);
|
2021-06-08 11:03:17 +00:00
|
|
|
return Realm.eval(r2, use, {type: 'function', arguments: [exports]});
|
2021-05-27 16:22:06 +00:00
|
|
|
}
|
2021-05-26 10:43:21 +00:00
|
|
|
|
2021-05-27 16:22:06 +00:00
|
|
|
(function TestMinimal() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {
|
|
|
|
str: 'hello',
|
|
|
|
n: 42,
|
|
|
|
};
|
|
|
|
}
|
2021-06-01 13:31:49 +00:00
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals('hello', foo.str);
|
|
|
|
assertEquals(42, foo.n);
|
2021-05-26 10:43:21 +00:00
|
|
|
})();
|
2021-06-01 10:26:07 +00:00
|
|
|
|
|
|
|
(function TestEmptyObject() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {};
|
|
|
|
}
|
2021-06-01 13:31:49 +00:00
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals([], Object.keys(foo));
|
|
|
|
})();
|
|
|
|
|
|
|
|
(function TestNumbers() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {
|
|
|
|
a: 6,
|
|
|
|
b: -7,
|
|
|
|
c: 7.3,
|
|
|
|
d: NaN,
|
|
|
|
e: Number.POSITIVE_INFINITY,
|
|
|
|
f: Number.NEGATIVE_INFINITY,
|
|
|
|
};
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals(6, foo.a);
|
|
|
|
assertEquals(-7, foo.b);
|
|
|
|
assertEquals(7.3, foo.c);
|
|
|
|
assertEquals(NaN, foo.d);
|
|
|
|
assertEquals(Number.POSITIVE_INFINITY, foo.e);
|
|
|
|
assertEquals(Number.NEGATIVE_INFINITY, foo.f);
|
|
|
|
})();
|
|
|
|
|
2021-06-08 11:12:55 +00:00
|
|
|
(function TestTopLevelNumbers() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.a = 6;
|
|
|
|
globalThis.b = -7;
|
|
|
|
}
|
|
|
|
const { a, b } = takeAndUseWebSnapshot(createObjects, ['a', 'b']);
|
|
|
|
assertEquals(6, a);
|
|
|
|
assertEquals(-7, b);
|
|
|
|
})();
|
|
|
|
|
2021-06-01 13:31:49 +00:00
|
|
|
(function TestOddballs() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {
|
|
|
|
a: true,
|
|
|
|
b: false,
|
|
|
|
c: null,
|
|
|
|
d: undefined,
|
|
|
|
};
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertTrue(foo.a);
|
|
|
|
assertFalse(foo.b);
|
|
|
|
assertEquals(null, foo.c);
|
|
|
|
assertEquals(undefined, foo.d);
|
|
|
|
})();
|
|
|
|
|
2021-06-08 11:12:55 +00:00
|
|
|
(function TestTopLevelOddballs() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.a = true;
|
|
|
|
globalThis.b = false;
|
|
|
|
}
|
|
|
|
const { a, b } = takeAndUseWebSnapshot(createObjects, ['a', 'b']);
|
|
|
|
assertTrue(a);
|
|
|
|
assertFalse(b);
|
|
|
|
})();
|
|
|
|
|
2021-06-01 13:31:49 +00:00
|
|
|
(function TestFunction() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {
|
|
|
|
key: function () { return 'bar'; },
|
|
|
|
};
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals('bar', foo.key());
|
|
|
|
})();
|
|
|
|
|
|
|
|
(function TestFunctionWithContext() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {
|
|
|
|
key: (function () {
|
|
|
|
let result = 'bar';
|
|
|
|
function inner() { return result; }
|
|
|
|
return inner;
|
|
|
|
})(),
|
|
|
|
};
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals('bar', foo.key());
|
|
|
|
})();
|
|
|
|
|
|
|
|
(function TestInnerFunctionWithContextAndParentContext() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {
|
|
|
|
key: (function () {
|
|
|
|
let part1 = 'snap';
|
|
|
|
function inner() {
|
|
|
|
let part2 = 'shot';
|
|
|
|
function innerinner() {
|
|
|
|
return part1 + part2;
|
|
|
|
}
|
|
|
|
return innerinner;
|
|
|
|
}
|
|
|
|
return inner();
|
|
|
|
})()
|
|
|
|
};
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals('snapshot', foo.key());
|
|
|
|
})();
|
|
|
|
|
2021-06-08 11:12:55 +00:00
|
|
|
(function TestTopLevelFunctionWithContext() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = (function () {
|
|
|
|
let result = 'bar';
|
|
|
|
function inner() { return result; }
|
|
|
|
return inner;
|
|
|
|
})();
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals('bar', foo());
|
|
|
|
})();
|
|
|
|
|
2021-06-01 13:31:49 +00:00
|
|
|
(function TestRegExp() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {
|
|
|
|
re: /ab+c/gi,
|
|
|
|
};
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals('/ab+c/gi', foo.re.toString());
|
|
|
|
assertTrue(foo.re.test('aBc'));
|
|
|
|
assertFalse(foo.re.test('ac'));
|
|
|
|
})();
|
|
|
|
|
|
|
|
(function TestRegExpNoFlags() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {
|
|
|
|
re: /ab+c/,
|
|
|
|
};
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals('/ab+c/', foo.re.toString());
|
|
|
|
assertTrue(foo.re.test('abc'));
|
|
|
|
assertFalse(foo.re.test('ac'));
|
2021-06-01 10:26:07 +00:00
|
|
|
})();
|
2021-06-08 11:12:55 +00:00
|
|
|
|
|
|
|
(function TestTopLevelRegExp() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.re = /ab+c/gi;
|
|
|
|
}
|
|
|
|
const { re } = takeAndUseWebSnapshot(createObjects, ['re']);
|
|
|
|
assertEquals('/ab+c/gi', re.toString());
|
|
|
|
assertTrue(re.test('aBc'));
|
|
|
|
assertFalse(re.test('ac'));
|
|
|
|
})();
|
2021-06-10 08:44:57 +00:00
|
|
|
|
|
|
|
(function TestObjectReferencingObject() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {
|
|
|
|
bar: {baz: 11525}
|
|
|
|
};
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals(11525, foo.bar.baz);
|
|
|
|
})();
|
|
|
|
|
|
|
|
(function TestContextReferencingObject() {
|
|
|
|
function createObjects() {
|
|
|
|
function outer() {
|
|
|
|
let o = {value: 11525};
|
|
|
|
function inner() { return o; }
|
|
|
|
return inner;
|
|
|
|
}
|
|
|
|
globalThis.foo = {
|
|
|
|
func: outer()
|
|
|
|
};
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertEquals(11525, foo.func().value);
|
|
|
|
})();
|
|
|
|
|
|
|
|
(function TestCircularObjectReference() {
|
|
|
|
function createObjects() {
|
|
|
|
globalThis.foo = {
|
|
|
|
bar: {}
|
|
|
|
};
|
|
|
|
globalThis.foo.bar.circular = globalThis.foo;
|
|
|
|
}
|
|
|
|
const { foo } = takeAndUseWebSnapshot(createObjects, ['foo']);
|
|
|
|
assertSame(foo, foo.bar.circular);
|
|
|
|
})();
|