Skip to content

Commit

Permalink
Issue #719 - Added unit tests for the new functions/objects.
Browse files Browse the repository at this point in the history
  • Loading branch information
OlegRa committed Mar 1, 2024
1 parent a8331c3 commit 653567d
Show file tree
Hide file tree
Showing 7 changed files with 130 additions and 48 deletions.
118 changes: 118 additions & 0 deletions Alpaca.Markets.Tests/AlpacaTradingClientTest.Options.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,118 @@
using System.Diagnostics.CodeAnalysis;

namespace Alpaca.Markets.Tests;

public sealed partial class AlpacaTradingClientTest
{
private static readonly DateOnly _today = DateOnly.FromDateTime(DateTime.Today);

[Fact]
public async Task GetOptionContractByIdWorks()
{
using var mock = mockClientsFactory.GetAlpacaTradingClientMock();

var contractId = Guid.NewGuid();

mock.AddGet("/v2/options/contracts/*", createOptionContract(contractId, Stock));

var optionContract = await mock.Client.GetOptionContractByIdAsync(contractId);

validateOptionContract(optionContract, contractId, Stock);
}

[Fact]
public async Task GetOptionContractBySymbolWorks()
{
using var mock = mockClientsFactory.GetAlpacaTradingClientMock();

var contractId = Guid.NewGuid();

mock.AddGet("/v2/options/contracts/*", createOptionContract(contractId, Stock));

var optionContract = await mock.Client.GetOptionContractBySymbolAsync(Stock);

validateOptionContract(optionContract, contractId, Stock);
}

[Fact]
public async Task ListOptionContractsWorks()
{
using var mock = mockClientsFactory.GetAlpacaTradingClientMock();

var contractId = Guid.NewGuid();

mock.AddGet("/v2/options/contracts", createOptionContractsList(contractId, Stock));

var optionContracts = await mock.Client.ListOptionContractsAsync(
new OptionContractsRequest(Stock)
{
ExpirationDateGreaterThanOrEqualTo = _today,
ExpirationDateLessThanOrEqualTo = _today,
StrikePriceGreaterThanOrEqualTo = Price,
StrikePriceLessThanOrEqualTo = Price,
OptionStyle = OptionStyle.American,
AssetStatus = AssetStatus.Active,
OptionType = OptionType.Call,
RootSymbol = Stock,
PageNumber = 1,
PageSize = 100
});

validateOptionContract(optionContracts.Single(), contractId, Stock);
}

private static JObject createOptionContractsList(
Guid contractId,
String symbol) =>
new(new JProperty("option_contracts", new JArray(createOptionContract(contractId, symbol))));

private static JObject createOptionContract(
Guid contractId,
String symbol) =>
new(
new JProperty("open_interest_date", _today.ToString("O")),
new JProperty("close_price_date", _today.ToString("O")),
new JProperty("expiration_date", _today.ToString("O")),
new JProperty("underlying_asset_id", contractId),
new JProperty("style", OptionStyle.American),
new JProperty("status", AssetStatus.Active),
new JProperty("underlying_symbol", symbol),
new JProperty("type", OptionType.Call),
new JProperty("open_interest", Price),
new JProperty("root_symbol", symbol),
new JProperty("strike_price", Price),
new JProperty("close_price", Price),
new JProperty("tradable", true),
new JProperty("symbol", symbol),
new JProperty("id", contractId),
new JProperty("name", symbol),
new JProperty("size", 100));

[SuppressMessage("ReSharper", "ParameterOnlyUsedForPreconditionCheck.Local")]
private static void validateOptionContract(
IOptionContract optionContract,
Guid contractId,
String symbol)
{
Assert.True(optionContract.IsTradable);

Assert.NotNull(optionContract.ClosePrice);
Assert.NotNull(optionContract.OpenInterest);
Assert.NotNull(optionContract.ClosePriceDate);
Assert.NotNull(optionContract.OpenInterestDate);

Assert.Equal(100, optionContract.Size);
Assert.Equal(Price, optionContract.StrikePrice);

Assert.Equal(symbol, optionContract.Name);
Assert.Equal(symbol, optionContract.Symbol);
Assert.Equal(symbol, optionContract.RootSymbol);
Assert.Equal(symbol, optionContract.UnderlyingSymbol);

Assert.Equal(contractId, optionContract.ContractId);
Assert.Equal(contractId, optionContract.UnderlyingAssetId);

Assert.Equal(OptionType.Call, optionContract.OptionType);
Assert.Equal(OptionStyle.American, optionContract.OptionStyle);
}
}
13 changes: 2 additions & 11 deletions Alpaca.Markets/Helpers/AssetAttributesEnumConverter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,6 @@ public override Object ReadJson(
JsonReader reader,
Type objectType,
Object? existingValue,
JsonSerializer serializer)
{
try
{
return AssetAttributes.Unknown.FromEnumString(reader);
}
catch (JsonSerializationException)
{
return AssetAttributes.Unknown;
}
}
JsonSerializer serializer) =>
reader.ReadEnumString(AssetAttributes.Unknown);
}
13 changes: 2 additions & 11 deletions Alpaca.Markets/Helpers/CryptoExchangeEnumConverter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,6 @@ public override Object ReadJson(
JsonReader reader,
Type objectType,
Object? existingValue,
JsonSerializer serializer)
{
try
{
return CryptoExchange.Unknown.FromEnumString(reader);
}
catch (JsonSerializationException)
{
return CryptoExchange.Unknown;
}
}
JsonSerializer serializer) =>
reader.ReadEnumString(CryptoExchange.Unknown);
}
6 changes: 3 additions & 3 deletions Alpaca.Markets/Helpers/EnumExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -27,13 +27,13 @@ public static String ToEnumString<T>(
where T : struct, Enum =>
JsonConvert.SerializeObject(enumValue).Trim(_doubleQuotes);

public static T FromEnumString<
public static T ReadEnumString<
#if NET6_0_OR_GREATER
[DynamicallyAccessedMembers(DynamicallyAccessedMemberTypes.PublicFields)]
#endif
T>(
this T fallbackEnumValue,
JsonReader reader)
this JsonReader reader,
T fallbackEnumValue)
where T : struct, Enum =>
reader.TokenType == JsonToken.String
? NamesHelper<T>.ValuesByNames.GetValueOrDefault(
Expand Down
13 changes: 2 additions & 11 deletions Alpaca.Markets/Helpers/ExchangeEnumConverter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,6 @@ public override Object ReadJson(
JsonReader reader,
Type objectType,
Object? existingValue,
JsonSerializer serializer)
{
try
{
return Exchange.Unknown.FromEnumString(reader);
}
catch (JsonSerializationException)
{
return Exchange.Unknown;
}
}
JsonSerializer serializer) =>
reader.ReadEnumString(Exchange.Unknown);
}
13 changes: 2 additions & 11 deletions Alpaca.Markets/Helpers/OrderSideEnumConverter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,6 @@ public override Object ReadJson(
JsonReader reader,
Type objectType,
Object? existingValue,
JsonSerializer serializer)
{
try
{
return OrderSide.Sell.FromEnumString(reader);
}
catch (JsonSerializationException)
{
return OrderSide.Sell; // Treat all unknown order types as sell orders
}
}
JsonSerializer serializer) =>
reader.ReadEnumString(OrderSide.Sell); // Treat all unknown order types as sell orders
}
2 changes: 1 addition & 1 deletion Alpaca.Markets/Messages/JsonOptionContractsPage.cs
Original file line number Diff line number Diff line change
Expand Up @@ -6,5 +6,5 @@
internal sealed class JsonOptionContractsPage
{
[JsonProperty(PropertyName = "option_contracts", Required = Required.Always)]
public List<JsonOptionContract> Contracts { get; set; } = [];
public List<JsonOptionContract> Contracts { get; [ExcludeFromCodeCoverage] set; } = [];
}

0 comments on commit 653567d

Please sign in to comment.