Linq to SQL Repository问题

时间:2009-07-05 11:20:38

标签: asp.net-mvc linq-to-sql

我正在开展像NerdDinner(www.nerddinner.com)这样的类似项目。 我有类似的表,但我使用了通用存储库(从这里复制 http://www.codeproject.com/KB/architecture/linqrepository.aspx)。 它似乎没有任何问题。 这是代码。


IRepository.cs

using System;
using System.Collections.Generic;
using System.Text;
using System.Data.Linq;
using System.Linq;

namespace Listing.Repository
{

    public interface IRepository<T> where T : class
    {
        /// <summary>
        /// Return all instances of type T.
        /// </summary>
        /// <returns></returns>
        IEnumerable<T> GetAllRows();

        /// <summary>
        /// Return all instances of type T that match the expression exp.
        /// </summary>
        /// <param name="exp"></param>
        /// <returns></returns>
        IEnumerable<T> GetAllRowsWhere(Func<T, bool> exp);


        /// <summary>Returns the single entity matching the expression. Throws an exception if there is not exactly one such entity.</summary>
        /// <param name="exp"></param><returns></returns>
        T Single(Func<T, bool> exp);

        /// <summary>Returns the first element satisfying the condition.</summary>
        /// <param name="exp"></param><returns></returns>
        T First(Func<T, bool> exp);

        /// <summary>
        /// Mark an entity to be deleted when the context is saved.
        /// </summary>
        /// <param name="entity"></param>
        void Delete(T entity);

        /// <summary>
        /// Adds new entity..
        /// </summary>
        /// <param name="entity"></param>
        void Insert(T entity);



        void Update(T entity);

        /// <summary>
        /// Create a new instance of type T.
        /// </summary>
        /// <returns></returns>
        T New();

        /// <summary>Persist the data context.</summary>
        void SaveAll();
    }
}

Repository.cs

using System;
using System.Data;
using System.Data.Linq;
using System.Data.Linq.Mapping;
using System.Collections.Generic;
using System.Reflection;
using System.Linq;
using System.Linq.Expressions;

namespace Listing.Repository
{
    public class Repository<T> : IRepository<T>
        where T : class
    {
        protected Listing.Data.IDataContextFactory _dataContextFactory;

        /// <summary>
        /// Return all instances of type T.
        /// </summary>
        /// <returns></returns>


        public IEnumerable<T> GetAllRows()
        {
            return GetTable;
        }
        /// <summary>
        /// Return all instances of type T that match the expression exp.
        /// </summary>
        /// <param name="exp"></param>
        /// <returns></returns>
        public IEnumerable<T> GetAllRowsWhere(Func<T, bool> exp)
        {
            return GetTable.Where<T>(exp);
        }

        /// <summary>See _vertexRepository.</summary>
        /// <param name="exp"></param><returns></returns>
        public T Single(Func<T, bool> exp)
        {
            return GetTable.SingleOrDefault(exp);
        }

        /// <summary>See _vertexRepository.</summary>
        /// <param name="exp"></param><returns></returns>
        public T First(Func<T, bool> exp)
        {
            return GetTable.First(exp);
        }

        /// <summary>See _vertexRepository.</summary>
        /// <param name="entity"></param>
        public virtual void Delete(T entity)
        {
            _dataContextFactory.Context.GetTable<T>().DeleteOnSubmit(entity);
        }

        /// <summary>
        /// Create a new instance of type T.
        /// </summary>
        /// <returns></returns>
        public virtual T New()
        {
            T entity = Activator.CreateInstance<T>();
            GetTable.InsertOnSubmit(entity);
            return entity;
        }



        /// <summary>
        /// Adds an insance T.
        /// </summary>
        /// <returns></returns>
        public virtual void Insert(T entity)
        {
            GetTable.InsertOnSubmit(entity);
        }

        /// <summary>
        /// Update entity.
        /// </summary>
        /// <returns></returns>
        public virtual void Update(T entity)
        {
            _dataContextFactory.Context.Refresh(System.Data.Linq.RefreshMode.KeepCurrentValues, entity);
        }

        /// <summary>See _vertexRepository.</summary>
        public void SaveAll()
        {
            _dataContextFactory.SaveAll();
        }

        public Repository(Listing.Data.IDataContextFactory dataContextFactory)
        {
            _dataContextFactory = dataContextFactory;
        }

        #region Properties

        private string PrimaryKeyName
        {
            get { return TableMetadata.RowType.IdentityMembers[0].Name; }
        }

        private System.Data.Linq.Table<T> GetTable
        {
            get { return _dataContextFactory.Context.GetTable<T>(); }
        }

        private System.Data.Linq.Mapping.MetaTable TableMetadata
        {
            get { return _dataContextFactory.Context.Mapping.GetTable(typeof(T)); }
        }

        private System.Data.Linq.Mapping.MetaType ClassMetadata
        {
            get { return _dataContextFactory.Context.Mapping.GetMetaType(typeof(T)); }
        }

        #endregion
    }
}

IDataContext.cs

using System;
using System.Linq;

namespace Listing.Data
{
    public interface IDataContextFactory
    {
        System.Data.Linq.DataContext Context { get; }
        void SaveAll();
    }


    public class DataContext : IDataContextFactory
    {


        #region IDataContextFactory Members

        private System.Data.Linq.DataContext dt;

        public System.Data.Linq.DataContext Context
        {
            get
            {
                if (dt == null)
                    dt = new Listing.Data.ListingDataContext();
                return dt;
            }
        }

        public void SaveAll()
        {
            dt.SubmitChanges();
        }

        #endregion
    }
}

现在我处于一个阶段,我已将两个函数DistanceBetween和NearestDinners(我的名字不同)放到我的dbml文件中。我想用这些 函数进行一些计算。

以下是nerddinner项目中使用的代码

public IQueryable<Dinner> FindByLocation(float latitude, float longitude) {
    var dinners = from dinner in FindUpcomingDinners()
                  join i in db.NearestDinners(latitude, longitude) 
                  on dinner.DinnerID equals i.DinnerID
                  select dinner;

    return dinners;
}

我如何与我的通用存储库实现类似。 帮助将不胜感激。

此致 Paraminder

1 个答案:

答案 0 :(得分:0)

您可以使用扩展方法吗?

public static IQueryable<Dinner> FindByLocation(this IQueryable<Dinner>, float latitude, float longitude) {
    var dinners = from dinner in this
                  join i in this(latitude, longitude) 
                  on dinner.DinnerID equals i.DinnerID
                  select dinner;

    return dinners;
}