Index: content/renderer/v8_value_converter_impl_unittest.cc |
diff --git a/content/renderer/v8_value_converter_impl_unittest.cc b/content/renderer/v8_value_converter_impl_unittest.cc |
index ab092e54907a495d4e3a39566c205ce1abe282e4..f6f252d22ffd890d1a460fe30ede5785b25d4dcf 100644 |
--- a/content/renderer/v8_value_converter_impl_unittest.cc |
+++ b/content/renderer/v8_value_converter_impl_unittest.cc |
@@ -711,4 +711,169 @@ TEST_F(V8ValueConverterImplTest, MaxRecursionDepth) { |
EXPECT_TRUE(base::Value::Equals(&empty, current)) << *current; |
} |
+class V8ValueConverterOverridingStrategyForTesting |
+ : public V8ValueConverter::Strategy { |
+ public: |
+ V8ValueConverterOverridingStrategyForTesting() |
+ : reference_value_(NewReferenceValue()) {} |
+ virtual bool FromV8Object( |
+ v8::Handle<v8::Object> value, |
+ base::Value** out, |
+ v8::Isolate* isolate, |
+ const FromV8ValueCallback& callback) const OVERRIDE { |
+ *out = NewReferenceValue(); |
+ return true; |
+ } |
+ virtual bool FromV8Array(v8::Handle<v8::Array> value, |
+ base::Value** out, |
+ v8::Isolate* isolate, |
+ const FromV8ValueCallback& callback) const OVERRIDE { |
+ *out = NewReferenceValue(); |
+ return true; |
+ } |
+ virtual bool FromV8ArrayBuffer(v8::Handle<v8::Object> value, |
+ base::Value** out) const OVERRIDE { |
+ *out = NewReferenceValue(); |
+ return true; |
+ } |
+ virtual bool FromV8Number(v8::Handle<v8::Number> value, |
+ base::Value** out) const OVERRIDE { |
+ *out = NewReferenceValue(); |
+ return true; |
+ } |
+ virtual bool FromV8Undefined(base::Value** out) const OVERRIDE { |
+ *out = NewReferenceValue(); |
+ return true; |
+ } |
+ base::Value* reference_value() const { return reference_value_.get(); } |
+ |
+ private: |
+ static base::Value* NewReferenceValue() { |
+ return new base::StringValue("strategy"); |
+ } |
+ scoped_ptr<base::Value> reference_value_; |
+}; |
+ |
+TEST_F(V8ValueConverterImplTest, StrategyOverrides) { |
+ v8::HandleScope handle_scope(isolate_); |
+ v8::Local<v8::Context> context = |
+ v8::Local<v8::Context>::New(isolate_, context_); |
+ v8::Context::Scope context_scope(context); |
+ |
+ V8ValueConverterImpl converter; |
+ V8ValueConverterOverridingStrategyForTesting strategy; |
+ converter.SetStrategy(&strategy); |
+ |
+ v8::Handle<v8::Object> object(v8::Object::New(isolate_)); |
+ scoped_ptr<base::Value> object_value(converter.FromV8Value(object, context)); |
+ ASSERT_TRUE(object_value); |
+ EXPECT_TRUE( |
+ base::Value::Equals(strategy.reference_value(), object_value.get())); |
+ |
+ v8::Handle<v8::Array> array(v8::Array::New(isolate_)); |
+ scoped_ptr<base::Value> array_value(converter.FromV8Value(array, context)); |
+ ASSERT_TRUE(array_value); |
+ EXPECT_TRUE( |
+ base::Value::Equals(strategy.reference_value(), array_value.get())); |
+ |
+ v8::Handle<v8::ArrayBuffer> array_buffer(v8::ArrayBuffer::New(isolate_, 0)); |
+ scoped_ptr<base::Value> array_buffer_value( |
+ converter.FromV8Value(array_buffer, context)); |
+ ASSERT_TRUE(array_buffer_value); |
+ EXPECT_TRUE(base::Value::Equals(strategy.reference_value(), |
+ array_buffer_value.get())); |
+ |
+ v8::Handle<v8::ArrayBufferView> array_buffer_view( |
+ v8::Uint8Array::New(array_buffer, 0, 0)); |
+ scoped_ptr<base::Value> array_buffer_view_value( |
+ converter.FromV8Value(array_buffer_view, context)); |
+ ASSERT_TRUE(array_buffer_view_value); |
+ EXPECT_TRUE(base::Value::Equals(strategy.reference_value(), |
+ array_buffer_view_value.get())); |
+ |
+ v8::Handle<v8::Number> number(v8::Number::New(isolate_, 0.0)); |
+ scoped_ptr<base::Value> number_value(converter.FromV8Value(number, context)); |
+ ASSERT_TRUE(number_value); |
+ EXPECT_TRUE( |
+ base::Value::Equals(strategy.reference_value(), number_value.get())); |
+ |
+ v8::Handle<v8::Primitive> undefined(v8::Undefined(isolate_)); |
+ scoped_ptr<base::Value> undefined_value( |
+ converter.FromV8Value(undefined, context)); |
+ ASSERT_TRUE(undefined_value); |
+ EXPECT_TRUE( |
+ base::Value::Equals(strategy.reference_value(), undefined_value.get())); |
+} |
+ |
+class V8ValueConverterBypassStrategyForTesting |
+ : public V8ValueConverter::Strategy { |
+ public: |
+ virtual bool FromV8Object( |
+ v8::Handle<v8::Object> value, |
+ base::Value** out, |
+ v8::Isolate* isolate, |
+ const FromV8ValueCallback& callback) const OVERRIDE { |
+ return false; |
+ } |
+ virtual bool FromV8Array(v8::Handle<v8::Array> value, |
+ base::Value** out, |
+ v8::Isolate* isolate, |
+ const FromV8ValueCallback& callback) const OVERRIDE { |
+ return false; |
+ } |
+ virtual bool FromV8ArrayBuffer(v8::Handle<v8::Object> value, |
+ base::Value** out) const OVERRIDE { |
+ return false; |
+ } |
+ virtual bool FromV8Number(v8::Handle<v8::Number> value, |
+ base::Value** out) const OVERRIDE { |
+ return false; |
+ } |
+ virtual bool FromV8Undefined(base::Value** out) const OVERRIDE { |
+ return false; |
+ } |
+}; |
+ |
+// Verify that having a strategy that fallbacks to default behaviour |
+// actually preserves it. |
+TEST_F(V8ValueConverterImplTest, StrategyBypass) { |
+ v8::HandleScope handle_scope(isolate_); |
+ v8::Local<v8::Context> context = |
+ v8::Local<v8::Context>::New(isolate_, context_); |
+ v8::Context::Scope context_scope(context); |
+ |
+ V8ValueConverterImpl converter; |
+ V8ValueConverterBypassStrategyForTesting strategy; |
+ converter.SetStrategy(&strategy); |
+ |
+ v8::Handle<v8::Object> object(v8::Object::New(isolate_)); |
+ scoped_ptr<base::Value> object_value(converter.FromV8Value(object, context)); |
+ ASSERT_TRUE(object_value); |
+ scoped_ptr<base::Value> reference_object_value(base::test::ParseJson("{}")); |
+ EXPECT_TRUE( |
+ base::Value::Equals(reference_object_value.get(), object_value.get())); |
+ |
+ v8::Handle<v8::Array> array(v8::Array::New(isolate_)); |
+ scoped_ptr<base::Value> array_value(converter.FromV8Value(array, context)); |
+ ASSERT_TRUE(array_value); |
+ scoped_ptr<base::Value> reference_array_value(base::test::ParseJson("[]")); |
+ EXPECT_TRUE( |
+ base::Value::Equals(reference_array_value.get(), array_value.get())); |
+ |
+ // Not testing ArrayBuffers as V8ValueConverter uses blink helpers and |
+ // this requires having blink to be initialized. |
+ |
+ v8::Handle<v8::Number> number(v8::Number::New(isolate_, 0.0)); |
+ scoped_ptr<base::Value> number_value(converter.FromV8Value(number, context)); |
+ ASSERT_TRUE(number_value); |
+ scoped_ptr<base::Value> reference_number_value(base::test::ParseJson("0")); |
+ EXPECT_TRUE( |
+ base::Value::Equals(reference_number_value.get(), number_value.get())); |
+ |
+ v8::Handle<v8::Primitive> undefined(v8::Undefined(isolate_)); |
+ scoped_ptr<base::Value> undefined_value( |
+ converter.FromV8Value(undefined, context)); |
+ EXPECT_FALSE(undefined_value); |
+} |
+ |
} // namespace content |