mirror of
https://github.com/JKorf/CryptoExchange.Net
synced 2026-02-16 14:13:46 +00:00
wip
This commit is contained in:
parent
42736f3003
commit
bb2f6c0a14
@ -5,40 +5,36 @@ using System.Text;
|
||||
namespace CryptoExchange.Net.Converters.MessageParsing.DynamicConverters
|
||||
{
|
||||
/// <summary>
|
||||
/// Message evaluator
|
||||
/// Message type definition
|
||||
/// </summary>
|
||||
public class MessageEvaluator
|
||||
public class MessageTypeDefinition
|
||||
{
|
||||
/// <summary>
|
||||
/// The priority of this evaluator, higher prio evaluators (with lower Priority number) will be checked for matches before lower ones
|
||||
/// </summary>
|
||||
public int Priority { get; set; }
|
||||
/// <summary>
|
||||
/// Whether to immediately match the evaluator when it is matched. Can only be used when the evaluator has a single unique field to look for
|
||||
/// Whether to immediately select the definition when it is matched. Can only be used when the evaluator has a single unique field to look for
|
||||
/// </summary>
|
||||
public bool ForceIfFound { get; set; }
|
||||
/// <summary>
|
||||
/// The fields this evaluator has to look for
|
||||
/// The fields a message needs to contain for this definition
|
||||
/// </summary>
|
||||
public MessageFieldReference[] Fields { get; set; } = [];
|
||||
/// <summary>
|
||||
/// The callback for getting the identifier string
|
||||
/// </summary>
|
||||
public Func<SearchResult, string>? IdentifyMessageCallback { get; set; }
|
||||
public Func<SearchResult, string>? TypeIdentifierCallback { get; set; }
|
||||
/// <summary>
|
||||
/// The static identifier string to return when this evaluator is matched
|
||||
/// </summary>
|
||||
public string? StaticIdentifier { get; set; }
|
||||
|
||||
internal string? IdentifyMessage(SearchResult result)
|
||||
internal string? GetMessageType(SearchResult result)
|
||||
{
|
||||
if (StaticIdentifier != null)
|
||||
return StaticIdentifier;
|
||||
|
||||
return IdentifyMessageCallback!(result);
|
||||
return TypeIdentifierCallback!(result);
|
||||
}
|
||||
|
||||
internal bool Statisfied(SearchResult result)
|
||||
internal bool Satisfied(SearchResult result)
|
||||
{
|
||||
foreach(var field in Fields)
|
||||
{
|
||||
|
||||
@ -9,7 +9,7 @@ namespace CryptoExchange.Net.Converters.MessageParsing.DynamicConverters
|
||||
public bool SkipReading { get; set; }
|
||||
public bool OverlappingField { get; set; }
|
||||
public MessageFieldReference Field { get; set; }
|
||||
public MessageEvaluator? ForceEvaluator { get; set; }
|
||||
public MessageTypeDefinition? ForceEvaluator { get; set; }
|
||||
|
||||
public MessageEvalutorFieldReference(MessageFieldReference field)
|
||||
{
|
||||
|
||||
@ -20,7 +20,82 @@ namespace CryptoExchange.Net.Converters.MessageParsing.DynamicConverters
|
||||
/// <summary>
|
||||
/// Callback to check if the field value matches an expected constraint
|
||||
/// </summary>
|
||||
public Func<string?, bool>? Constraint { get; set; }
|
||||
public Func<string?, bool>? Constraint { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Check whether the value is one of the string values in the set
|
||||
/// </summary>
|
||||
public MessageFieldReference WithFilterContstraint(HashSet<string?> set)
|
||||
{
|
||||
Constraint = set.Contains;
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check whether the value is equal to a string
|
||||
/// </summary>
|
||||
public MessageFieldReference WithEqualContstraint(string compare)
|
||||
{
|
||||
Constraint = x => x != null && x.Equals(compare, StringComparison.Ordinal);
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check whether the value is not equal to a string
|
||||
/// </summary>
|
||||
public MessageFieldReference WithNotEqualContstraint(string compare)
|
||||
{
|
||||
Constraint = x => x == null || !x.Equals(compare, StringComparison.Ordinal);
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check whether the value is not null
|
||||
/// </summary>
|
||||
public MessageFieldReference WithNotNullContstraint()
|
||||
{
|
||||
Constraint = x => x != null;
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check whether the value starts with a certain string
|
||||
/// </summary>
|
||||
public MessageFieldReference WithStartsWithContstraint(string start)
|
||||
{
|
||||
Constraint = x => x != null && x.StartsWith(start, StringComparison.Ordinal);
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check whether the value starts with a certain string
|
||||
/// </summary>
|
||||
public MessageFieldReference WithStartsWithContstraints(params string[] startValues)
|
||||
{
|
||||
Constraint = x =>
|
||||
{
|
||||
if (x == null)
|
||||
return false;
|
||||
|
||||
foreach (var item in startValues)
|
||||
{
|
||||
if (x!.StartsWith(item, StringComparison.Ordinal))
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
};
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Check whether the value starts with a certain string
|
||||
/// </summary>
|
||||
public MessageFieldReference WithCustomContstraint(Func<string?, bool> constraint)
|
||||
{
|
||||
Constraint = constraint;
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// ctor
|
||||
|
||||
@ -1,8 +1,5 @@
|
||||
using CryptoExchange.Net.Converters.MessageParsing.DynamicConverters;
|
||||
using System;
|
||||
#if !NETSTANDARD
|
||||
using System.Collections.Frozen;
|
||||
#endif
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
using System.Linq;
|
||||
@ -22,18 +19,17 @@ namespace CryptoExchange.Net.Converters.SystemTextJson
|
||||
/// </summary>
|
||||
public abstract JsonSerializerOptions Options { get; }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Message evaluators
|
||||
/// </summary>
|
||||
protected abstract MessageEvaluator[] TypeEvaluators { get; }
|
||||
protected abstract MessageTypeDefinition[] TypeEvaluators { get; }
|
||||
|
||||
private readonly SearchResult _searchResult = new();
|
||||
|
||||
private bool _hasArraySearches;
|
||||
private bool _initialized;
|
||||
private int _maxSearchDepth;
|
||||
private MessageEvaluator? _topEvaluator;
|
||||
private MessageTypeDefinition? _topEvaluator;
|
||||
private List<MessageEvalutorFieldReference>? _searchFields;
|
||||
private Dictionary<Type, Func<object, string?>>? _baseTypeMapping;
|
||||
private Dictionary<Type, Func<object, string?>>? _mapping;
|
||||
@ -56,7 +52,7 @@ namespace CryptoExchange.Net.Converters.SystemTextJson
|
||||
|
||||
_maxSearchDepth = int.MinValue;
|
||||
_searchFields = new List<MessageEvalutorFieldReference>();
|
||||
foreach (var evaluator in TypeEvaluators.OrderBy(x => x.Priority))
|
||||
foreach (var evaluator in TypeEvaluators)
|
||||
{
|
||||
_topEvaluator ??= evaluator;
|
||||
foreach (var field in evaluator.Fields)
|
||||
@ -105,7 +101,7 @@ namespace CryptoExchange.Net.Converters.SystemTextJson
|
||||
foreach(var sameSearchField in existingSameSearchField)
|
||||
{
|
||||
if (sameSearchField.SkipReading == true
|
||||
&& (evaluator.IdentifyMessageCallback != null || field.Constraint != null))
|
||||
&& (evaluator.TypeIdentifierCallback != null || field.Constraint != null))
|
||||
{
|
||||
sameSearchField.SkipReading = false;
|
||||
}
|
||||
@ -121,7 +117,7 @@ namespace CryptoExchange.Net.Converters.SystemTextJson
|
||||
|
||||
_searchFields.Add(new MessageEvalutorFieldReference(field)
|
||||
{
|
||||
SkipReading = evaluator.IdentifyMessageCallback == null && field.Constraint == null,
|
||||
SkipReading = evaluator.TypeIdentifierCallback == null && field.Constraint == null,
|
||||
ForceEvaluator = !existingSameSearchField.Any() ? (evaluator.ForceIfFound ? evaluator : null) : null,
|
||||
OverlappingField = overlapping.Any()
|
||||
});
|
||||
@ -309,7 +305,7 @@ namespace CryptoExchange.Net.Converters.SystemTextJson
|
||||
return field.ForceEvaluator.StaticIdentifier;
|
||||
|
||||
// Force the immediate return upon encountering this field
|
||||
return field.ForceEvaluator.IdentifyMessage(_searchResult);
|
||||
return field.ForceEvaluator.GetMessageType(_searchResult);
|
||||
}
|
||||
|
||||
written = true;
|
||||
@ -320,8 +316,8 @@ namespace CryptoExchange.Net.Converters.SystemTextJson
|
||||
if (!written)
|
||||
continue;
|
||||
|
||||
if (_topEvaluator!.Statisfied(_searchResult))
|
||||
return _topEvaluator.IdentifyMessage(_searchResult);
|
||||
if (_topEvaluator!.Satisfied(_searchResult))
|
||||
return _topEvaluator.GetMessageType(_searchResult);
|
||||
|
||||
if (_searchFields.Count == _searchResult.Count)
|
||||
break;
|
||||
@ -330,8 +326,8 @@ namespace CryptoExchange.Net.Converters.SystemTextJson
|
||||
|
||||
foreach (var evaluator in TypeEvaluators)
|
||||
{
|
||||
if (evaluator.Statisfied(_searchResult))
|
||||
return evaluator.IdentifyMessage(_searchResult);
|
||||
if (evaluator.Satisfied(_searchResult))
|
||||
return evaluator.GetMessageType(_searchResult);
|
||||
}
|
||||
|
||||
return null;
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user