Skip to content

Commit

Permalink
code review + unit tests
Browse files Browse the repository at this point in the history
  • Loading branch information
meevee98 committed Oct 19, 2020
1 parent f0e7d60 commit 2b50f6e
Show file tree
Hide file tree
Showing 9 changed files with 262 additions and 9 deletions.
2 changes: 2 additions & 0 deletions .github/workflows/main.yml
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ jobs:
run: dotnet test tests/Neo.SmartContract.Framework.UnitTests /p:CollectCoverage=true /p:CoverletOutput=${GITHUB_WORKSPACE}/coverage/lcov /p:MergeWith=${GITHUB_WORKSPACE}/coverage/coverage.json /p:Exclude=\"[Neo.SmartContract.*]*,[Neo.Compiler.MSIL.UnitTests]*,[Neo.Compiler.MSIL.UnitTests.*]*\" /p:CoverletOutputFormat=lcov
- name: Test Template.NEP5.UnitTests
run: dotnet test tests/Template.NEP5.UnitTests /p:CollectCoverage=true /p:CoverletOutput=${GITHUB_WORKSPACE}/coverage/lcov /p:MergeWith=${GITHUB_WORKSPACE}/coverage/coverage.json /p:Exclude=\"[Neo.SmartContract.*]*,[Neo.Compiler.MSIL.UnitTests]*,[Neo.Compiler.MSIL.UnitTests.*]*\" /p:CoverletOutputFormat=lcov
- name: Test TestEngine.UnitTests
run: dotnet test tests/TestEngine.UnitTests /p:CollectCoverage=true /p:CoverletOutput=${GITHUB_WORKSPACE}/coverage/lcov /p:MergeWith=${GITHUB_WORKSPACE}/coverage/coverage.json /p:Exclude=\"[Neo.SmartContract.*]*,[Neo.Compiler.MSIL.UnitTests]*,[Neo.Compiler.MSIL.UnitTests.*]*\" /p:CoverletOutputFormat=lcov
- name: Coveralls
uses: coverallsapp/github-action@master
with:
Expand Down
7 changes: 7 additions & 0 deletions neo-devpack-dotnet.sln
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Template.NEP5.UnitTests", "
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TestEngine", "src\TestEngine\TestEngine.csproj", "{39347E90-FC12-4018-8F22-828F0F1B2F7D}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TestEngine.UnitTests", "tests\TestEngine.UnitTests\TestEngine.UnitTests.csproj", "{FFDC189F-2F72-4542-B28B-8EFA0F28E3CF}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Expand Down Expand Up @@ -77,6 +79,10 @@ Global
{39347E90-FC12-4018-8F22-828F0F1B2F7D}.Debug|Any CPU.Build.0 = Debug|Any CPU
{39347E90-FC12-4018-8F22-828F0F1B2F7D}.Release|Any CPU.ActiveCfg = Release|Any CPU
{39347E90-FC12-4018-8F22-828F0F1B2F7D}.Release|Any CPU.Build.0 = Release|Any CPU
{FFDC189F-2F72-4542-B28B-8EFA0F28E3CF}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{FFDC189F-2F72-4542-B28B-8EFA0F28E3CF}.Debug|Any CPU.Build.0 = Debug|Any CPU
{FFDC189F-2F72-4542-B28B-8EFA0F28E3CF}.Release|Any CPU.ActiveCfg = Release|Any CPU
{FFDC189F-2F72-4542-B28B-8EFA0F28E3CF}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
Expand All @@ -92,6 +98,7 @@ Global
{ADD05222-DC45-4FDC-A41A-30A97BACC95F} = {7042EF23-826B-45A1-A905-59AD678C31B7}
{780141EE-D6E9-4591-8470-8F91B12027CA} = {D5266066-0AFD-44D5-A83E-2F73668A63C8}
{39347E90-FC12-4018-8F22-828F0F1B2F7D} = {79389FC0-C621-4CEA-AD2B-6074C32E7BCA}
{FFDC189F-2F72-4542-B28B-8EFA0F28E3CF} = {D5266066-0AFD-44D5-A83E-2F73668A63C8}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {6DA935E1-C674-4364-B087-F1B511B79215}
Expand Down
5 changes: 5 additions & 0 deletions src/TestEngine/Engine.cs
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,11 @@ public static Engine Instance
private byte[] PubKey => HexString2Bytes("03ea01cb94bdaf0cd1c01b159d474f9604f4af35a3e2196f6bdfdb33b2aa4961fa");

private Engine()
{
Reset();
}

public void Reset()
{
engine = SetupNativeContracts();
}
Expand Down
2 changes: 1 addition & 1 deletion src/TestEngine/Helper.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ public static JObject ToJson(this TestEngine testEngine)
var json = new JObject();

json["vm_state"] = testEngine.State.ToString();
json["gas_consumed"] = (new BigDecimal(testEngine.GasConsumed, NativeContract.GAS.Decimals)).ToString();
json["gasconsumed"] = (new BigDecimal(testEngine.GasConsumed, NativeContract.GAS.Decimals)).ToString();
json["result_stack"] = testEngine.ResultStack.ToJson();
json["storage"] = testEngine.Snapshot.Storages.ToJson();
json["notifications"] = new JArray(testEngine.Notifications.Select(n => n.ToJson()));
Expand Down
25 changes: 17 additions & 8 deletions src/TestEngine/Program.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,19 @@

namespace Neo.TestingEngine
{
class Program
public class Program
{
static int Main(string[] args)
{
JObject result = Run(args);
if (!result.ContainsProperty("vm_state"))
{
return -1;
}
return 0;
}

public static JObject Run(string[] args)
{
JObject result;
if (args.Length >= 2)
Expand All @@ -23,12 +33,7 @@ static int Main(string[] args)
result = BuildJsonException("One or more arguments are missing");
}

Console.WriteLine(result);
if (!result.ContainsProperty("vm_state"))
{
return -1;
}
return 0;
return result;
}

/// <summary>
Expand Down Expand Up @@ -112,7 +117,11 @@ private static StackItem[] GetStackItemParameters(JArray parameters)
items.Add(ContractParameter.FromJson(param).ToStackItem());
success = true;
}
catch { }
catch (Exception e)
{
// if something went wrong while reading the json, log the error
Console.WriteLine(e);
}
}

if (!success)
Expand Down
28 changes: 28 additions & 0 deletions tests/TestEngine.UnitTests/TestClasses/Contract1.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
namespace Neo.Compiler.MSIL.UnitTests.TestClasses
{
public class Contract1 : SmartContract.Framework.SmartContract
{
public static byte[] unitTest_001()
{
var nb = new byte[] { 1, 2, 3, 4 };
return nb;
}

public static void testVoid()
{
var nb = new byte[] { 1, 2, 3, 4 };
}

public static byte[] testArgs1(byte a)
{
var nb = new byte[] { 1, 2, 3, 3 };
nb[3] = a;
return nb;
}

public static object testArgs2(byte[] a)
{
return a;
}
}
}
19 changes: 19 additions & 0 deletions tests/TestEngine.UnitTests/TestClasses/Contract2.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
using System;
using System.ComponentModel;

namespace Neo.Compiler.MSIL.UnitTests.TestClasses
{
public class Contract2 : SmartContract.Framework.SmartContract
{
[DisplayName("event")]
public static event Action<object> notify;

public static byte UnitTest_002(object arg1, object arg2)
{
notify(arg1);
notify(arg2);
var nb = new byte[] { 1, 2, 3, 4 };
return nb[2];
}
}
}
34 changes: 34 additions & 0 deletions tests/TestEngine.UnitTests/TestEngine.UnitTests.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<TargetFramework>netcoreapp3.1</TargetFramework>

<IsPackable>false</IsPackable>
</PropertyGroup>

<ItemGroup>
<Compile Remove="TestClasses\Contract1.cs" />
<Compile Remove="TestClasses\Contract2.cs" />
</ItemGroup>

<ItemGroup>
<None Include="TestClasses\Contract1.cs">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
<None Include="TestClasses\Contract2.cs">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
</ItemGroup>

<ItemGroup>
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="16.2.0" />
<PackageReference Include="MSTest.TestAdapter" Version="2.0.0" />
<PackageReference Include="MSTest.TestFramework" Version="2.0.0" />
<PackageReference Include="coverlet.collector" Version="1.0.1" />
</ItemGroup>

<ItemGroup>
<ProjectReference Include="..\..\src\TestEngine\TestEngine.csproj" />
</ItemGroup>

</Project>
149 changes: 149 additions & 0 deletions tests/TestEngine.UnitTests/UnitTest_Invoke.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,149 @@
using Microsoft.VisualStudio.TestTools.UnitTesting;
using Neo.IO.Json;
using Neo.VM;
using Neo.VM.Types;
using System.IO;
using TestingEngine;
using Compiler = Neo.Compiler.Program;

namespace TestEngine.UnitTests
{
[TestClass]
public class UnitTest_Invoke
{
[TestInitialize]
public void Init()
{
string path = Directory.GetCurrentDirectory();
var option = new Compiler.Options()
{
File = path + "/TestClasses/Contract1.cs"
};
Compiler.Compile(option);

//Compile changes the path, reseting so that other UT won't break
Directory.SetCurrentDirectory(path);
Engine.Instance.Reset();
}

[TestMethod]
public void Test_Missing_Arguments()
{
var args = new string[] {
"./TestClasses/Contract1.nef"
};
var result = Program.Run(args);

Assert.IsTrue(result.ContainsProperty("error"));
Assert.AreEqual(result["error"].AsString(), "One or more arguments are missing");
}

[TestMethod]
public void Test_Method_Without_Parameters_Void()
{
var args = new string[] {
"./TestClasses/Contract1.nef",
"testVoid"
};
var result = Program.Run(args);

// mustn't have errors
Assert.IsTrue(result.ContainsProperty("error"));
Assert.IsNull(result["error"]);

// test state
Assert.IsTrue(result.ContainsProperty("vm_state"));
Assert.AreEqual(result["vm_state"].AsString(), VMState.HALT.ToString());

// test result
Assert.IsTrue(result.ContainsProperty("result_stack"));
Assert.IsInstanceOfType(result["result_stack"], typeof(JArray));

var resultStack = result["result_stack"] as JArray;
Assert.IsTrue(resultStack.Count == 0);
}

[TestMethod]
public void Test_Method_Without_Parameters_With_Return()
{
var args = new string[] {
"./TestClasses/Contract1.nef",
"unitTest_001"
};
var result = Program.Run(args);

// mustn't have errors
Assert.IsTrue(result.ContainsProperty("error"));
Assert.IsNull(result["error"]);

// test state
Assert.IsTrue(result.ContainsProperty("vm_state"));
Assert.AreEqual(result["vm_state"].AsString(), VMState.HALT.ToString());

// test result
StackItem wantresult = new byte[] { 1, 2, 3, 4 };
Assert.IsTrue(result.ContainsProperty("result_stack"));
Assert.IsInstanceOfType(result["result_stack"], typeof(JArray));

var resultStack = result["result_stack"] as JArray;
Assert.IsTrue(resultStack.Count == 1);
Assert.IsTrue(resultStack[0].ContainsProperty("value"));
Assert.AreEqual(resultStack[0]["value"].AsString(), wantresult.ToJson()["value"].AsString());
}

[TestMethod]
public void Test_Method_With_Parameters()
{
StackItem arguments = 16;
var args = new string[] {
"./TestClasses/Contract1.nef",
"testArgs1",
arguments.ToJson().ToString()
};
var result = Program.Run(args);

// mustn't have errors
Assert.IsTrue(result.ContainsProperty("error"));
Assert.IsNull(result["error"]);

// test state
Assert.IsTrue(result.ContainsProperty("vm_state"));
Assert.AreEqual(result["vm_state"].AsString(), VMState.HALT.ToString());

// test result
StackItem wantresult = new byte[] { 1, 2, 3, 16 };
Assert.IsTrue(result.ContainsProperty("result_stack"));
Assert.IsInstanceOfType(result["result_stack"], typeof(JArray));

var resultStack = result["result_stack"] as JArray;
Assert.IsTrue(resultStack.Count == 1);
Assert.IsTrue(resultStack[0].ContainsProperty("value"));
Assert.AreEqual(resultStack[0]["value"].AsString(), wantresult.ToJson()["value"].AsString());
}

[TestMethod]
public void Test_Method_With_Parameters_Missing()
{
var args = new string[] {
"./TestClasses/Contract1.nef",
"testArgs1"
};
var result = Program.Run(args);

// mustn have an error
Assert.IsTrue(result.ContainsProperty("error"));
Assert.IsNotNull(result["error"]);

// vm state must've faulted
Assert.IsTrue(result.ContainsProperty("vm_state"));
Assert.AreEqual(result["vm_state"].AsString(), VMState.FAULT.ToString());

// result stack must be empty
Assert.IsTrue(result.ContainsProperty("result_stack"));
Assert.IsInstanceOfType(result["result_stack"], typeof(JArray));

var resultStack = result["result_stack"] as JArray;
Assert.IsTrue(resultStack.Count == 0);
}
}
}

0 comments on commit 2b50f6e

Please sign in to comment.