Wie Elasticsearch NEST IGetMappingResponse für Unit-Tests Mock

stimmen
3

Ich und meine Hochschulen haben ein Datenzugriffsmodul aufgebaut, die CRUD und Suche tut Operationen auf eine ElasticeSearch (6.2.0) NoSQL-Datenbank. Wir verwenden NEST (6.2.0), ein hohes Maß Client an den Elasticsearch Abfrage DSL abzubilden. Das Modul ist in C #, in einer Klassenbibliothek in einer gezielten Framework .NET Standard 2.0 codiert worden.

Bei einigen Verfahren ist es notwendig, die Index-Mapping von Indizes in Elasticsearch gespeichert sind, abzurufen, so dass Feldinformationen wie Feldtypen und Texteigenschaften verwendet werden können Suchanfragen an die Elasticsearch Datenbank aufzubauen. Wir sind in der Lage, dies zu tun durch die Verwendung Nest Getmapping Methode (liefert Nest.IGetMappingResponse).

Wir haben keine Probleme Ausführung von Code. Alles funktioniert gut. Wenn wir jedoch es gibt die Antwort an Mock - up nicht in der Lage (IGetMappingResponse) gehen , um eine Einheit Test für Methoden zu erstellen, die die Getmapping Methode verwendet, sind wir. Früher habe ich ursprünglich FakeItEasy zu fälschen, und dann einige der Daten eingefügt ich in dem Objekt benötigt. Aber mein Problem zu erklären , ein wenig besser, ich habe eine Klasse erstellt , die IGetMappingResponse meine Antwort zu verspotten implementiert. Das Problem kommt , wenn ich versuche , eine Instanz zu erstellen TypeMappings für die Mapping - Eigenschaft IndexMapping (Im Gegenzug für die Immobilienindizes für die Mock ist). Ich erhalte eine Fehlermeldung, „‚TypMappings‘keinen Konstruktor enthält , die 0 Argumente annimmt.

public class MockedGetMappingResponse : IGetMappingResponse
    {
        public IReadOnlyDictionary<IndexName, IndexMappings> Indices
        {
            get
            {
                return new ReadOnlyDictionary<Nest.IndexName, Nest.IndexMappings>(new Dictionary<Nest.IndexName, Nest.IndexMappings>
                {
                    [statuses] = new IndexMappings
                    {
                        Mappings = new TypeMappings() //Error happens here!!
                    }                      

                });
            }
            set { }
        }

        public IReadOnlyDictionary<IndexName, IndexMappings> Mappings
        {
            get
            {
                return null;
            }
            set { }
        }

        public void Accept(IMappingVisitor visitor)
        {
            // Just a test
        }

        public bool IsValid
        {
            get
            {
                return true;
            }
        }

        public ServerError ServerError
        {
            get
            {
                return null;
            }
        }

        public Exception OriginalException
        {
            get
            {
                return null;
            }
        }

        public string DebugInformation
        {
            get
            {
                return ;
            }
        }

        public IApiCallDetails ApiCall
        {
            get
            {
                return null;
            }
            set
            {
                //do nothing
            }
        }

        public bool TryGetServerErrorReason(out string reason)
        {
            reason = ;
            return false;
        }
    }      

}

Wenn ich die Definitionen für die Nest - Typ aufblicken TypeMappings Ich sehe keinen Konstruktor gebaut. Daher gehe ich davon aus, dass es den Standard verwenden sollte, einen Konstruktor ohne Argumente. Aber anscheinend ist es nicht. Ich muss wissen , wie man über spöttischen TypeMappings in IGetMappingResponse zu gehen. Wenn es keine Möglichkeit gibt , eine Instanz von TypeMappings zu schaffen, muss ich wissen , wie man eine verspottete IGetMappingResponse meiner erwartete Antwort zu erstellen , so dass ich meinen Code testen.

Veröffentlicht am 27/11/2018 um 17:59
quelle vom benutzer
In anderen Sprachen...                            


1 antworten

stimmen
1

Mit Nkosi Hilfe fand ich , dass TypeMappings einen internen Konstruktor hat. Zu wissen , dass, habe ich eine Instanz von TypeMappings mit Reflexion. Hier ist der Code , den ich verwenden , um das Objekt zu erstellen.

IReadOnlyDictionary<TypeName, TypeMapping> backingDictionary = new ReadOnlyDictionary<TypeName, TypeMapping>(new Dictionary<TypeName, TypeMapping>
        {
            [typeName.Name] = typeMapping

        });           

        Type[] typeMappingsArgs = new Type[] { typeof(IConnectionConfigurationValues), typeof(IReadOnlyDictionary<TypeName, TypeMapping>) };
        object[] typeMappingsInputParams = new object[] { elasticClient.ConnectionSettings, backingDictionary };
        TypeMappings typeMappings = (TypeMappings)typeof(TypeMappings).GetConstructor(
              BindingFlags.NonPublic | BindingFlags.Instance,
              null, typeMappingsArgs, null).Invoke(typeMappingsInputParams);

Hier ist der Code für meine verspottete IGetMappingResponse zu schaffen. Ich benutzte FakeItEasy einige Informationen einzufügen.

private Nest.IGetMappingResponse GetFakeMappingResponse(Nest.IElasticClient elasticClient)
    {
        var fieldName = "fieldName";
        var indexName = "indexName";
        var documentTypeName = "documentTypeName";

        var typeMapping = new TypeMapping();
        var properties = new Properties();
        typeMapping.Properties = properties;

        var property = new TextProperty();
        property.Name = fieldName;            

        PropertyName propertyName = new PropertyName(fieldName);

        typeMapping.Properties.Add(propertyName, property);

        Type[] typeNameArgs = new Type[] { typeof(string) };
        object[] typeNameInputParams = new object[] { documentTypeName };
        TypeName typeName = (TypeName)typeof(TypeName).GetConstructor(
              BindingFlags.NonPublic | BindingFlags.Instance,
              null, typeNameArgs, null).Invoke(typeNameInputParams);


        IReadOnlyDictionary<TypeName, TypeMapping> backingDictionary = new ReadOnlyDictionary<TypeName, TypeMapping>(new Dictionary<TypeName, TypeMapping>
        {
            [typeName.Name] = typeMapping

        });           

        Type[] typeMappingsArgs = new Type[] { typeof(IConnectionConfigurationValues), typeof(IReadOnlyDictionary<TypeName, TypeMapping>) };
        object[] typeMappingsInputParams = new object[] { elasticClient.ConnectionSettings, backingDictionary };
        TypeMappings typeMappings = (TypeMappings)typeof(TypeMappings).GetConstructor(
              BindingFlags.NonPublic | BindingFlags.Instance,
              null, typeMappingsArgs, null).Invoke(typeMappingsInputParams);

        IndexMappings indexMappings = new IndexMappings();
        typeof(IndexMappings).GetProperty("Mappings", BindingFlags.Public | BindingFlags.Instance).SetValue(indexMappings, typeMappings);

        ReadOnlyDictionary<Nest.IndexName, Nest.IndexMappings> indices = new ReadOnlyDictionary<Nest.IndexName, Nest.IndexMappings>(new Dictionary<Nest.IndexName, Nest.IndexMappings>
        {
            [indexName] = indexMappings

        });

        var fakeMappingResponse = A.Fake<IGetMappingResponse>();
        A.CallTo(() => fakeMappingResponse.ServerError).Returns(null);
        A.CallTo(() => fakeMappingResponse.IsValid).Returns(true);
        A.CallTo(() => fakeMappingResponse.Indices).Returns(indices);

        return fakeMappingResponse;
    }
Beantwortet am 28/11/2018 um 17:37
quelle vom benutzer

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more