2008-10-14 8 views
26

Si j'ai un Linq à SQL expression comme ceci:Comment utiliser les commandes GETDATE() et DATEADD() de SQL dans une expression Linq to SQL?

from subscription in dbContext.Subscriptions 
where subscription.Expires > DateTime.Now 
select subscription 

Je veux que cela utiliser les serveurs SQL GETDATE() fonction au lieu du temps de la machine exécutant le programme C#.

La question suivante serait de savoir comment traduire ceci:

DateTime.Now.AddDays(2) 

à ceci:

DATEADD(dd, 2, GETDATE()) 

Répondre

43

Essayez this:

[Function(Name="GetDate", IsComposable=true)] 
public DateTime GetSystemDate() 
{ 
    MethodInfo mi = MethodBase.GetCurrentMethod() as MethodInfo; 
    return (DateTime)this.ExecuteMethodCall(this, mi, new object[]{}).ReturnValue; 
} 

EDIT: cela doit faire partie de votre classe DataContext.

Maintenant vous pouvez utiliser GetSystemDate() au lieu de DateTime.Now dans vos requêtes. En ce qui concerne les différences de date, jetez un oeil à l'espace de noms System.Data.Linq.SqlClient, en particulier les fonctions DayDiffXXX de la classe SqlMethods.

+1

Remarque: ceci est traduit directement dans la fonction GETDATE(), par ex. pas d'appels distincts à SQL Server. Je viens de le vérifier. – liggett78

+0

Génie! Belle solution et très appréciée. –

+1

MethodInfo est System.Reflection.MethodInfo et la fonction est System.Data.Linq.Mapping.Function – Trisped

0

Vous pouvez utiliser le ExecuteQuery pour prendre le contrôle complet de la sql http://weblogs.asp.net/scottgu/archive/2007/08/27/linq-to-sql-part-8-executing-custom-sql-expressions.aspx

Je sais Il semble que ce soit très peu de gain (ou peut-être sur le contrairy) sur ADO.NET cependant.

+0

Eh bien ... alors ce n'est pas une expression LINQ ;-) –

+0

true :) mais si linq2sql est censé être une abstraction sur sql, vous ne devriez pas être capable d'utiliser une fonction sql en premier lieu? : P –

6

Si vous ne me dérange pas d'interroger la base de données avant chaque utilisation, je suggère la solution suivante: Utiliser ExecuteQuery en un seul endroit pour obtenir la date dans le contexte de données comme ceci:

public partial class YourDataContext 
{ 
    public DateTime GetDate() 
    { 
    return ExecuteQuery<DateTime>("SELECT GETDATE()").First(); 
    } 
} 

et vous peut écrire

from subscription in dbContext.Subscriptions 
where subscription > dbContext.GetDate().AddDays(2) 
select subscription