PageRenderTime 44ms CodeModel.GetById 19ms RepoModel.GetById 0ms app.codeStats 0ms

/Source/facebook.Linq/Linq/FqlDataQuery.cs

https://bitbucket.org/assaframan/facebooklinq
C# | 153 lines | 133 code | 15 blank | 5 comment | 18 complexity | ef4850df23ab14a3dd60acf33fff0b0c MD5 | raw file
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Linq;
  4. using System.Text;
  5. using System.Collections;
  6. using System.Linq.Expressions;
  7. using System.ComponentModel;
  8. using facebook.Linq;
  9. namespace facebook.Linq
  10. {
  11. internal interface IFqlDataQuery
  12. {
  13. string GetQueryTextWithoutSelect();
  14. SqlNode GetSqlTree();
  15. }
  16. internal sealed class FqlDataQuery<T> : IOrderedQueryable<T>, IQueryable<T>, IQueryProvider, IEnumerable<T>, IOrderedQueryable, IQueryable, IEnumerable, IFqlDataQuery
  17. {
  18. // Fields
  19. //private IBindingList cachedList;
  20. private FqlDataContext context;
  21. private Expression queryExpression;
  22. private Type tableRowType;
  23. // Methods
  24. public FqlDataQuery(FqlDataContext context, Expression expression, Type tableRowType)
  25. {
  26. this.context = context;
  27. this.queryExpression = expression;
  28. this.tableRowType = tableRowType;
  29. }
  30. IEnumerator<T> IEnumerable<T>.GetEnumerator()
  31. {
  32. return ((IEnumerable<T>)this.context.Provider.Execute(this.queryExpression, tableRowType).ReturnValue).GetEnumerator();
  33. }
  34. IEnumerator IEnumerable.GetEnumerator()
  35. {
  36. return ((IEnumerable)this.context.Provider.Execute(this.queryExpression, tableRowType).ReturnValue).GetEnumerator();
  37. }
  38. IQueryable<S> IQueryProvider.CreateQuery<S>(Expression expression)
  39. {
  40. if (expression == null)
  41. {
  42. throw Error.ArgumentNull("expression");
  43. }
  44. if (!typeof(IQueryable<S>).IsAssignableFrom(expression.Type))
  45. {
  46. throw Error.ExpectedQueryableArgument("expression", typeof(IEnumerable<S>));
  47. }
  48. return new FqlDataQuery<S>(this.context, expression, typeof(T));
  49. }
  50. IQueryable IQueryProvider.CreateQuery(Expression expression)
  51. {
  52. if (expression == null)
  53. {
  54. throw Error.ArgumentNull("expression");
  55. }
  56. Type elementType = EnumerableHelper.GetEnumerableItemType(expression.Type);
  57. Type type2 = typeof(IQueryable<>).MakeGenericType(new Type[] { elementType });
  58. if (!type2.IsAssignableFrom(expression.Type))
  59. {
  60. throw Error.ExpectedQueryableArgument("expression", type2);
  61. }
  62. return (IQueryable)Activator.CreateInstance(typeof(FqlDataQuery<>).MakeGenericType(new Type[] { elementType }), new object[] { this.context, expression });
  63. }
  64. object IQueryProvider.Execute(Expression expression)
  65. {
  66. return this.context.Provider.Execute(expression, tableRowType).ReturnValue;
  67. }
  68. S IQueryProvider.Execute<S>(Expression expression)
  69. {
  70. object ret = this.context.Provider.Execute(expression, tableRowType).ReturnValue;
  71. if (ret != null && typeof(IEnumerable<>).MakeGenericType(typeof(S)).IsAssignableFrom(ret.GetType()))
  72. {
  73. //return first enumeration ?
  74. var en = (IEnumerable)ret;
  75. var enumerator = en.GetEnumerator();
  76. if (enumerator.MoveNext())
  77. {
  78. return (S)enumerator.Current;
  79. //One item exists
  80. }
  81. else
  82. {
  83. if (expression.NodeType == ExpressionType.Call)
  84. {
  85. var method = ((System.Linq.Expressions.MethodCallExpression)(expression)).Method;
  86. if (method.Name == "First")
  87. throw new Exception("Sequence contains no elements");
  88. else if (method.Name == "FirstOrDefault")
  89. return (S)ReflectionHelper.GetDefaultValue(typeof(S));
  90. else
  91. throw new NotImplementedException(method.Name);
  92. }
  93. throw new NotImplementedException();
  94. }
  95. }
  96. else
  97. return (S)ret;
  98. }
  99. public string GetQueryTextWithoutSelect()
  100. {
  101. string s = this.context.Provider.GetQueryText(this.queryExpression);
  102. if (s.StartsWith("select"))
  103. {
  104. s = s.Substring(s.IndexOf("from ") + 5);
  105. }
  106. return s;
  107. }
  108. public SqlNode GetSqlTree()
  109. {
  110. return this.context.Provider.GetSqlTree(this.queryExpression);
  111. }
  112. public override string ToString()
  113. {
  114. return this.context.Provider.GetQueryText(this.queryExpression);
  115. }
  116. Type IQueryable.ElementType
  117. {
  118. get
  119. {
  120. return typeof(T);
  121. }
  122. }
  123. Expression IQueryable.Expression
  124. {
  125. get
  126. {
  127. return this.queryExpression;
  128. }
  129. }
  130. IQueryProvider IQueryable.Provider
  131. {
  132. get
  133. {
  134. return this;
  135. }
  136. }
  137. }
  138. }