Skip to content

Commit 337b9d6

Browse files
authored
CSHARP-989 Fix writetime support in LINQ (#582)
Integration test and fix on top of #581
1 parent a9e3236 commit 337b9d6

File tree

3 files changed

+52
-4
lines changed

3 files changed

+52
-4
lines changed

src/Cassandra.IntegrationTests/Linq/LinqRealClusterTests.cs

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,13 +17,16 @@
1717
using System;
1818
using System.Collections.Generic;
1919
using System.Linq;
20+
using System.Threading;
2021
using System.Threading.Tasks;
2122
using Cassandra.Data.Linq;
2223
using Cassandra.IntegrationTests.Linq.Structures;
2324
using Cassandra.IntegrationTests.TestBase;
2425
using Cassandra.Mapping;
2526
using Cassandra.Tests;
2627
using Cassandra.Tests.Mapping.Pocos;
28+
using Newtonsoft.Json.Linq;
29+
2730
using NUnit.Framework;
2831

2932
namespace Cassandra.IntegrationTests.Linq
@@ -328,6 +331,43 @@ public void LinqUdt_Where_Contains()
328331
Assert.AreEqual(song.Title, recordsArr[0].Song.Title);
329332
}
330333

334+
[Test]
335+
public void Linq_Writetime_Returns_ValidResult()
336+
{
337+
DateTimeOffset UnixStart = new DateTimeOffset(1970, 1, 1, 0, 0, 0, 0, TimeSpan.Zero);
338+
var ticks = (DateTime.UtcNow - UnixStart).Ticks;
339+
var now = (ticks / TimeSpan.TicksPerMillisecond) * 1000;
340+
ticks = (DateTime.UtcNow.AddMinutes(5) - UnixStart).Ticks;
341+
var nowPlus5Minutes = (ticks / TimeSpan.TicksPerMillisecond) * 1000;
342+
var writetimeEntityTableName = "writetime_entities";
343+
Session.Execute($"CREATE TABLE IF NOT EXISTS {writetimeEntityTableName} (id uuid primary key, propertyint int, propertystring text)");
344+
345+
var table = new Table<WritetimeEntity>(Session, new MappingConfiguration().Define(
346+
new Map<WritetimeEntity>().TableName(writetimeEntityTableName)));
347+
var id = Guid.NewGuid();
348+
var writetimeEntity = new WritetimeEntity()
349+
{
350+
Id = id,
351+
PropertyInt = 100,
352+
PropertyString = "text",
353+
};
354+
table.Insert(writetimeEntity).Execute();
355+
Thread.Sleep(200);
356+
table.Where(sr => sr.Id == id).Select(sr => new WritetimeEntity { PropertyInt = 99 }).Update().Execute();
357+
var records = table
358+
.Select(wte => new { Id = wte.Id, wt1 = CqlFunction.WriteTime(wte.PropertyString), wt2 = CqlFunction.WriteTime(wte.PropertyInt) })
359+
.Where(wte => wte.Id == id).Execute();
360+
Assert.NotNull(records);
361+
var recordsArr = records.ToArray();
362+
Assert.AreEqual(1, recordsArr.Length);
363+
Assert.NotNull(recordsArr[0]);
364+
Assert.GreaterOrEqual(recordsArr[0].wt1, now);
365+
Assert.Greater(recordsArr[0].wt2, now);
366+
Assert.Greater(recordsArr[0].wt2, recordsArr[0].wt1);
367+
Assert.Less(recordsArr[0].wt1, nowPlus5Minutes);
368+
Assert.Less(recordsArr[0].wt2, nowPlus5Minutes);
369+
}
370+
331371
private Table<Album> GetAlbumTable()
332372
{
333373
return new Table<Album>(Session, new MappingConfiguration().Define(new Map<Album>().TableName(_tableNameAlbum)));
@@ -339,5 +379,14 @@ internal class SongRecords
339379
public Song2 Song { get; set; }
340380
public int Broadcast { get; set; }
341381
}
382+
383+
internal class WritetimeEntity
384+
{
385+
public Guid Id { get; set; }
386+
387+
public int PropertyInt { get; set; }
388+
389+
public string PropertyString { get; set; }
390+
}
342391
}
343392
}

src/Cassandra/Data/Linq/CqlExpressionVisitor.cs

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -796,12 +796,12 @@ protected override Expression VisitUnary(UnaryExpression node)
796796
}
797797
if (_parsePhase.Get() == ParsePhase.SelectBinding)
798798
{
799-
if (node.NodeType == ExpressionType.Convert && node.Type.Name == "Nullable`1")
799+
var column = _pocoData.GetColumnByMemberName(_currentBindingName.Get());
800+
if (node.NodeType == ExpressionType.Convert && (node.Type.Name == "Nullable`1" || column == null || !column.IsCounter))
800801
{
801802
// ReSharper disable once AssignNullToNotNullAttribute
802803
return Visit(node.Operand);
803804
}
804-
var column = _pocoData.GetColumnByMemberName(_currentBindingName.Get());
805805
if (column != null && column.IsCounter)
806806
{
807807
var value = Expression.Lambda(node).Compile().DynamicInvoke();
@@ -813,7 +813,6 @@ protected override Expression VisitUnary(UnaryExpression node)
813813
_selectFields.Add(column.ColumnName);
814814
return node;
815815
}
816-
817816
}
818817
throw new CqlLinqNotSupportedException(node, _parsePhase.Get());
819818
}

src/Cassandra/Data/Linq/CqlFunction.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,7 @@ public static CqlFunction Token(object key1, object key2, object key3, object ke
8181
/// <summary>
8282
/// CQL function writetime
8383
/// </summary>
84-
public static DateTimeOffset WriteTime(object key)
84+
public static long WriteTime(object key)
8585
{
8686
throw new InvalidOperationException();
8787
}

0 commit comments

Comments
 (0)