forked from nilproject/NiL.JS
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
9249a6a
commit a4f79da
Showing
10 changed files
with
197 additions
and
74 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,64 @@ | ||
using Microsoft.VisualStudio.TestTools.UnitTesting; | ||
using NiL.JS.Core; | ||
using System.Collections.Generic; | ||
using System.Dynamic; | ||
|
||
namespace FunctionalTests | ||
{ | ||
[TestClass] | ||
public class ExpandoObjectTests | ||
{ | ||
[TestMethod] | ||
public void ReadPropertiesOfDynamicobject() | ||
{ | ||
dynamic obj = new ExpandoObject(); | ||
obj.field = "value"; | ||
var context = new Context(); | ||
context.DefineVariable("obj").Assign(JSValue.Marshal(obj)); | ||
|
||
var value = context.Eval("obj.field"); | ||
|
||
Assert.AreEqual(JSValueType.String, value.ValueType); | ||
Assert.AreEqual("value", value.Value); | ||
} | ||
|
||
[TestMethod] | ||
public void WritePropertiesOfDynamicobject() | ||
{ | ||
dynamic obj = new ExpandoObject(); | ||
var context = new Context(); | ||
context.DefineVariable("obj").Assign(JSValue.Marshal(obj)); | ||
|
||
var value = context.Eval("obj.field = 'value'"); | ||
|
||
Assert.IsInstanceOfType(obj.field, typeof(string)); | ||
Assert.AreEqual("value", obj.field); | ||
} | ||
|
||
[TestMethod] | ||
public void WritePropertiesOfDynamicobjectOverWith() | ||
{ | ||
dynamic obj = new ExpandoObject(); | ||
obj.field = null; | ||
var context = new Context(); | ||
context.DefineVariable("obj").Assign(JSValue.Marshal(obj)); | ||
|
||
var value = context.Eval("with(obj) field = 'value'"); | ||
|
||
Assert.IsInstanceOfType(obj.field, typeof(string)); | ||
Assert.AreEqual("value", obj.field); | ||
} | ||
|
||
[TestMethod] | ||
public void WriteInsideWithoShouldNotCreateNewField() | ||
{ | ||
dynamic obj = new ExpandoObject(); | ||
var context = new Context(); | ||
context.DefineVariable("obj").Assign(JSValue.Marshal(obj)); | ||
|
||
var value = context.Eval("with(obj) field = 'value'"); | ||
|
||
Assert.IsFalse((obj as IDictionary<string, object>).ContainsKey("field")); | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,91 @@ | ||
using System; | ||
using System.Collections.Generic; | ||
using System.Dynamic; | ||
using System.Linq; | ||
using System.Text; | ||
using System.Threading.Tasks; | ||
|
||
namespace NiL.JS.Core.Interop | ||
{ | ||
internal sealed class ExpandoObjectWrapper : JSObject | ||
{ | ||
private readonly ExpandoObject _target; | ||
|
||
private sealed class ValueWrapper : JSValue | ||
{ | ||
private readonly string _key; | ||
private readonly ExpandoObjectWrapper _owner; | ||
|
||
public ValueWrapper(ExpandoObjectWrapper owner, string key) | ||
{ | ||
_owner = owner; | ||
_key = key; | ||
_attributes |= JSValueAttributesInternal.Reassign; | ||
|
||
object value = null; | ||
if ((owner._target as IDictionary<string, object>).TryGetValue(key, out value)) | ||
base.Assign(Marshal(value)); | ||
} | ||
|
||
public override void Assign(JSValue value) | ||
{ | ||
(_owner._target as IDictionary<string, object>)[_key] = value.Value; | ||
|
||
base.Assign(value); | ||
} | ||
} | ||
|
||
public ExpandoObjectWrapper(ExpandoObject target) | ||
{ | ||
_valueType = JSValueType.Object; | ||
_oValue = this; | ||
_target = target; | ||
} | ||
|
||
protected internal override JSValue GetProperty(JSValue key, bool forWrite, PropertyScope propertyScope) | ||
{ | ||
if (key.ValueType == JSValueType.Symbol || propertyScope >= PropertyScope.Super) | ||
return base.GetProperty(key, forWrite, propertyScope); | ||
|
||
var keyString = key.ToString(); | ||
var targetDictionary = _target as IDictionary<string, object>; | ||
|
||
if (!forWrite) | ||
{ | ||
if (!targetDictionary.ContainsKey(keyString)) | ||
return undefined; | ||
|
||
return Marshal(targetDictionary[keyString]); | ||
} | ||
|
||
return new ValueWrapper(this, keyString); | ||
} | ||
|
||
protected internal override void SetProperty(JSValue key, JSValue value, PropertyScope propertyScope, bool throwOnError) | ||
{ | ||
if (key.ValueType == JSValueType.Symbol || propertyScope >= PropertyScope.Super) | ||
base.SetProperty(key, value, propertyScope, throwOnError); | ||
|
||
(_target as IDictionary<string, object>)[key.ToString()] = value.Value; | ||
} | ||
|
||
protected internal override bool DeleteProperty(JSValue key) | ||
{ | ||
if (key.ValueType == JSValueType.Symbol) | ||
return base.DeleteProperty(key); | ||
|
||
return (_target as IDictionary<string, object>).Remove(key.ToString()); | ||
} | ||
|
||
protected internal override IEnumerator<KeyValuePair<string, JSValue>> GetEnumerator(bool hideNonEnum, EnumerationMode enumeratorMode) | ||
{ | ||
if (enumeratorMode == EnumerationMode.KeysOnly) | ||
return (_target as IDictionary<string, object>).Keys.Select(x => new KeyValuePair<string, JSValue>(x, null)).GetEnumerator(); | ||
|
||
if (enumeratorMode == EnumerationMode.RequireValues) | ||
return (_target as IDictionary<string, object>).Select(x => new KeyValuePair<string, JSValue>(x.Key, Marshal(x.Value))).GetEnumerator(); | ||
|
||
return (_target as IDictionary<string, object>).Select(x => new KeyValuePair<string, JSValue>(x.Key, new ValueWrapper(this, x.Key))).GetEnumerator(); | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file was deleted.
Oops, something went wrong.
Oops, something went wrong.