Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/CodeGeneration/DocGenerator/StringExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ public static class StringExtensions
{ "Script.Map", "\"if (doc['state'].value == \\\"Stable\\\") { params._agg.commits.add(doc['numberOfCommits'].value) }\"" },
{ "Script.Combine", "\"def sum = 0.0; for (c in params._agg.commits) { sum += c } return sum\"" },
{ "Script.Reduce", "\"def sum = 0.0; for (a in params._aggs) { sum += a } return sum\"" },
{ "EnvelopeCoordinates", @"new [] { new [] { 45.0, -45.0 }, new [] { -45.0, 45.0 }}" },
{ "EnvelopeCoordinates", @"new [] { new [] { -45.0, 45.0 }, new [] { 45.0, -45.0 }}" },
{ "CircleCoordinates", @"new [] { 45.0, -45.0 }" },
{ "MultiPointCoordinates", @"new [] { new [] {38.897676, -77.03653}, new [] {38.889939, -77.009051} }" },
{
Expand Down
3 changes: 3 additions & 0 deletions src/Nest/Mapping/Visitor/PropertyWalker.cs
Original file line number Diff line number Diff line change
Expand Up @@ -163,6 +163,9 @@ private static IProperty InferProperty(PropertyInfo propertyInfo)
if (type == typeof(QueryContainer))
return new PercolatorProperty();

if (type == typeof(IGeoShape))
return new GeoShapeProperty();

return new ObjectProperty();
}

Expand Down
89 changes: 49 additions & 40 deletions src/Nest/QueryDsl/Geo/Shape/GeoShapeBase.cs
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using Elasticsearch.Net.Extensions;
using Elasticsearch.Net.Utf8Json;
using Elasticsearch.Net.Utf8Json.Internal;

namespace Nest
{
Expand Down Expand Up @@ -41,8 +43,6 @@ internal static class GeoShapeType
/// </summary>
public abstract class GeoShapeBase : IGeoShape
{
internal static readonly GeoShapeFormatter ShapeFormatter = new GeoShapeFormatter();

protected GeoShapeBase(string type) => Type = type;

/// <inheritdoc />
Expand All @@ -54,15 +54,22 @@ public abstract class GeoShapeBase : IGeoShape
internal class GeoShapeFormatter<TShape> : IJsonFormatter<TShape>
where TShape : IGeoShape
{
public void Serialize(ref JsonWriter writer, TShape value, IJsonFormatterResolver formatterResolver) =>
GeoShapeBase.ShapeFormatter.Serialize(ref writer, value, formatterResolver);

public TShape Deserialize(ref JsonReader reader, IJsonFormatterResolver formatterResolver) =>
(TShape)GeoShapeBase.ShapeFormatter.Deserialize(ref reader, formatterResolver);
(TShape)GeoShapeFormatter.Instance.Deserialize(ref reader, formatterResolver);

public void Serialize(ref JsonWriter writer, TShape value, IJsonFormatterResolver formatterResolver) =>
GeoShapeFormatter.Instance.Serialize(ref writer, value, formatterResolver);
}

internal class GeoShapeFormatter : IJsonFormatter<IGeoShape>
{
private static readonly AutomataDictionary CircleFields = new AutomataDictionary { { "coordinates", 0 }, { "radius", 1 } };
private static readonly byte[] CoordinatesField = JsonWriter.GetEncodedPropertyNameWithoutQuotation("coordinates");
private static readonly byte[] GeometriesField = JsonWriter.GetEncodedPropertyNameWithoutQuotation("geometries");
internal static readonly GeoShapeFormatter Instance = new GeoShapeFormatter();

private static readonly byte[] TypeField = JsonWriter.GetEncodedPropertyNameWithoutQuotation("type");

public IGeoShape Deserialize(ref JsonReader reader, IJsonFormatterResolver formatterResolver)
{
var token = reader.GetCurrentJsonToken();
Expand Down Expand Up @@ -179,12 +186,14 @@ internal static IGeoShape ReadShape(ref JsonReader reader, IJsonFormatterResolve

while (segmentReader.ReadIsInObject(ref count))
{
var propertyName = segmentReader.ReadPropertyName();
if (propertyName == "type")
var propertyName = segmentReader.ReadPropertyNameSegmentRaw();
if (propertyName.EqualsBytes(TypeField))
{
typeName = segmentReader.ReadString().ToUpperInvariant();
break;
}

segmentReader.ReadNextBlock();
}

segmentReader = new JsonReader(segment.Array, segment.Offset);
Expand Down Expand Up @@ -217,18 +226,21 @@ internal static IGeoShape ReadShape(ref JsonReader reader, IJsonFormatterResolve
private static GeometryCollection ParseGeometryCollection(ref JsonReader reader, IJsonFormatterResolver formatterResolver)
{
var count = 0;
var geoShapes = Enumerable.Empty<IGeoShape>();
var geometries = Enumerable.Empty<IGeoShape>();
while (reader.ReadIsInObject(ref count))
{
var propertyName = reader.ReadPropertyName();
if (propertyName == "geometries")
geoShapes = formatterResolver.GetFormatter<IEnumerable<IGeoShape>>()
var propertyName = reader.ReadPropertyNameSegmentRaw();
if (propertyName.EqualsBytes(GeometriesField))
{
geometries = formatterResolver.GetFormatter<IEnumerable<IGeoShape>>()
.Deserialize(ref reader, formatterResolver);
else
reader.ReadNextBlock();
break;
}

reader.ReadNextBlock();
}

return new GeometryCollection { Geometries = geoShapes };
return new GeometryCollection { Geometries = geometries };
}

private static MultiPolygonGeoShape ParseMultiPolygonGeoShape(ref JsonReader reader, IJsonFormatterResolver formatterResolver) =>
Expand All @@ -247,10 +259,7 @@ private static PointGeoShape ParsePointGeoShape(ref JsonReader reader, IJsonForm
new PointGeoShape { Coordinates = GetCoordinates<GeoCoordinate>(ref reader, formatterResolver) };

private static MultiLineStringGeoShape ParseMultiLineStringGeoShape(ref JsonReader reader, IJsonFormatterResolver formatterResolver) =>
new MultiLineStringGeoShape
{
Coordinates = GetCoordinates<IEnumerable<IEnumerable<GeoCoordinate>>>(ref reader, formatterResolver)
};
new MultiLineStringGeoShape { Coordinates = GetCoordinates<IEnumerable<IEnumerable<GeoCoordinate>>>(ref reader, formatterResolver) };

private static LineStringGeoShape ParseLineStringGeoShape(ref JsonReader reader, IJsonFormatterResolver formatterResolver) =>
new LineStringGeoShape { Coordinates = GetCoordinates<IEnumerable<GeoCoordinate>>(ref reader, formatterResolver) };
Expand All @@ -265,27 +274,26 @@ private static CircleGeoShape ParseCircleGeoShape(ref JsonReader reader, IJsonFo
GeoCoordinate coordinate = null;
while (reader.ReadIsInObject(ref count))
{
var propertyName = reader.ReadPropertyName();
switch (propertyName)
var propertyName = reader.ReadPropertyNameSegmentRaw();

if (CircleFields.TryGetValue(propertyName, out var value))
{
case "coordinates":
coordinate = formatterResolver.GetFormatter<GeoCoordinate>()
.Deserialize(ref reader, formatterResolver);
break;
case "radius":
radius = reader.ReadString();
break;
default:
reader.ReadNextBlock();
break;
switch (value)
{
case 0:
coordinate = formatterResolver.GetFormatter<GeoCoordinate>()
.Deserialize(ref reader, formatterResolver);
break;
case 1:
radius = reader.ReadString();
break;
}
}
else
reader.ReadNextBlock();
}

return new CircleGeoShape
{
Coordinates = coordinate,
Radius = radius
};
return new CircleGeoShape { Coordinates = coordinate, Radius = radius };
}

private static T GetCoordinates<T>(ref JsonReader reader, IJsonFormatterResolver formatterResolver)
Expand All @@ -294,14 +302,15 @@ private static T GetCoordinates<T>(ref JsonReader reader, IJsonFormatterResolver
var coordinates = default(T);
while (reader.ReadIsInObject(ref count))
{
var propertyName = reader.ReadPropertyName();
if (propertyName == "coordinates")
var propertyName = reader.ReadPropertyNameSegmentRaw();
if (propertyName.EqualsBytes(CoordinatesField))
{
var formatter = formatterResolver.GetFormatter<T>();
coordinates = formatter.Deserialize(ref reader, formatterResolver);
break;
}
else
reader.ReadNextBlock();

reader.ReadNextBlock();
}

return coordinates;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,6 @@ public LikeDocument(Id id)

public LikeDocument(TDocument document)
{
Id = Id.From(document);
Document = document;
Index = typeof(TDocument);
}
Expand Down Expand Up @@ -98,11 +97,7 @@ public LikeDocumentDescriptor<TDocument> Fields(Func<FieldsDescriptor<TDocument>

public LikeDocumentDescriptor<TDocument> Fields(Fields fields) => Assign(fields, (a, v) => a.Fields = v);

public LikeDocumentDescriptor<TDocument> Document(TDocument document) => Assign(document, (a, v) =>
{
a.Id = Infer.Id(v);
a.Document = v;
});
public LikeDocumentDescriptor<TDocument> Document(TDocument document) => Assign(document, (a, v) => a.Document = v);

public LikeDocumentDescriptor<TDocument> PerFieldAnalyzer(
Func<PerFieldAnalyzerDescriptor<TDocument>, IPromise<IPerFieldAnalyzer>> analyzerSelector
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -329,7 +329,10 @@ public static PropertiesDescriptor<TProject> ProjectProperties<TProject>(Propert
.Properties(DeveloperProperties)
)
.GeoPoint(g => g
.Name(p => p.Location)
.Name(p => p.LocationPoint)
)
.GeoShape(g => g
.Name(p => p.LocationShape)
)
.Completion(cm => cm
.Name(p => p.Suggest)
Expand Down
12 changes: 7 additions & 5 deletions src/Tests/Tests.Domain/Project.cs
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,8 @@ public class Project
public JoinField Join => JoinField.Root<Project>();
public DateTime LastActivity { get; set; }
public Developer LeadDeveloper { get; set; }
public SimpleGeoPoint Location { get; set; }
public SimpleGeoPoint LocationPoint { get; set; }
public IGeoShape LocationShape { get; set; }
public Dictionary<string, Metadata> Metadata { get; set; }
public string Name { get; set; }
public int? NumberOfCommits { get; set; }
Expand Down Expand Up @@ -59,7 +60,8 @@ public class Project
.RuleFor(p => p.LeadDeveloper, p => Developer.Developers[Gimme.Random.Number(0, Developer.Developers.Count - 1)])
.RuleFor(p => p.Tags, f => Tag.Generator.Generate(Gimme.Random.Number(2, 50)))
.RuleFor(p => p.CuratedTags, f => Tag.Generator.Generate(Gimme.Random.Number(1, 5)))
.RuleFor(p => p.Location, f => SimpleGeoPoint.Generator.Generate())
.RuleFor(p => p.LocationPoint, f => SimpleGeoPoint.Generator.Generate())
.RuleFor(p => p.LocationShape, f => new PointGeoShape(new GeoCoordinate(f.Address.Latitude(), f.Address.Latitude())))
.RuleFor(p => p.NumberOfCommits, f => Gimme.Random.Number(1, 1000))
.RuleFor(p => p.NumberOfContributors, f => Gimme.Random.Number(1, 200))
.RuleFor(p => p.Ranges, f => Ranges.Generator.Generate())
Expand All @@ -86,7 +88,7 @@ public class Project
LeadDeveloper = new Developer() { FirstName = "Martijn", LastName = "Laarman" },
StartedOn = new DateTime(2015, 1, 1),
DateString = new DateTime(2015, 1, 1).ToString("yyyy-MM-ddTHH\\:mm\\:ss.fffffffzzz"),
Location = new SimpleGeoPoint { Lat = 42.1523, Lon = -80.321 },
LocationPoint = new SimpleGeoPoint { Lat = 42.1523, Lon = -80.321 },
SourceOnly = TestConfiguration.Instance.Random.SourceSerializer ? new SourceOnlyObject() : null
};

Expand All @@ -102,7 +104,7 @@ public class Project
numberOfContributors = 0,
dateString = new DateTime(2015, 1, 1).ToString("yyyy-MM-ddTHH\\:mm\\:ss.fffffffzzz"),
leadDeveloper = new { gender = "Male", id = 0, firstName = "Martijn", lastName = "Laarman" },
location = new { lat = Instance.Location.Lat, lon = Instance.Location.Lon }
locationPoint = new { lat = Instance.LocationPoint.Lat, lon = Instance.LocationPoint.Lon }
};

private static readonly object InstanceAnonymousSourceSerializer = new
Expand All @@ -117,7 +119,7 @@ public class Project
numberOfContributors = 0,
dateString = new DateTime(2015, 1, 1).ToString("yyyy-MM-ddTHH\\:mm\\:ss.fffffffzzz"),
leadDeveloper = new { gender = "Male", id = 0, firstName = "Martijn", lastName = "Laarman" },
location = new { lat = Instance.Location.Lat, lon = Instance.Location.Lon },
locationPoint = new { lat = Instance.LocationPoint.Lat, lon = Instance.LocationPoint.Lon },
sourceOnly = new { notWrittenByDefaultSerializer = "written" }
};

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ public GeoDistanceAggregationUsageTests(ReadOnlyCluster i, EndpointUsage usage)
{
geo_distance = new
{
field = "location",
field = "locationPoint",
origin = new
{
lat = 52.376,
Expand All @@ -39,7 +39,7 @@ public GeoDistanceAggregationUsageTests(ReadOnlyCluster i, EndpointUsage usage)

protected override Func<AggregationContainerDescriptor<Project>, IAggregationContainer> FluentAggs => a => a
.GeoDistance("rings_around_amsterdam", g => g
.Field(p => p.Location)
.Field(p => p.LocationPoint)
.Origin(52.376, 4.894)
.Ranges(
r => r.To(100),
Expand All @@ -51,7 +51,7 @@ public GeoDistanceAggregationUsageTests(ReadOnlyCluster i, EndpointUsage usage)
protected override AggregationDictionary InitializerAggs =>
new GeoDistanceAggregation("rings_around_amsterdam")
{
Field = Field((Project p) => p.Location),
Field = Field((Project p) => p.LocationPoint),
Origin = "52.376, 4.894",
Ranges = new List<AggregationRange>
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ public GeoHashGridAggregationUsageTests(ReadOnlyCluster i, EndpointUsage usage)
{
geohash_grid = new
{
field = "location",
field = "locationPoint",
precision = 3,
size = 1000,
shard_size = 100
Expand All @@ -29,7 +29,7 @@ public GeoHashGridAggregationUsageTests(ReadOnlyCluster i, EndpointUsage usage)

protected override Func<AggregationContainerDescriptor<Project>, IAggregationContainer> FluentAggs => a => a
.GeoHash("my_geohash_grid", g => g
.Field(p => p.Location)
.Field(p => p.LocationPoint)
.GeoHashPrecision(GeoHashPrecision.Precision3)
.Size(1000)
.ShardSize(100)
Expand All @@ -38,7 +38,7 @@ public GeoHashGridAggregationUsageTests(ReadOnlyCluster i, EndpointUsage usage)
protected override AggregationDictionary InitializerAggs =>
new GeoHashGridAggregation("my_geohash_grid")
{
Field = Field<Project>(p => p.Location),
Field = Field<Project>(p => p.LocationPoint),
Precision = GeoHashPrecision.Precision3,
Size = 1000,
ShardSize = 100
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,20 +19,20 @@ public GeoBoundsAggregationUsageTests(ReadOnlyCluster i, EndpointUsage usage) :
{
geo_bounds = new
{
field = "location",
field = "locationPoint",
wrap_longitude = true
}
}
};

protected override Func<AggregationContainerDescriptor<Project>, IAggregationContainer> FluentAggs => a => a
.GeoBounds("viewport", gb => gb
.Field(p => p.Location)
.Field(p => p.LocationPoint)
.WrapLongitude()
);

protected override AggregationDictionary InitializerAggs =>
new GeoBoundsAggregation("viewport", Field<Project>(p => p.Location))
new GeoBoundsAggregation("viewport", Field<Project>(p => p.LocationPoint))
{
WrapLongitude = true
};
Expand Down
Loading