325 lines
9.8 KiB
C#
325 lines
9.8 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Data.Entity;
|
|
using System.Linq;
|
|
using System.Threading.Tasks;
|
|
using System.Web;
|
|
using EnVisage.Models;
|
|
|
|
namespace EnVisage.Code.BLL
|
|
{
|
|
public class CompanyManager : ManagerBase<Company, CompanyModel>
|
|
{
|
|
public CompanyManager(EnVisageEntities dbContext)
|
|
: base(dbContext)
|
|
{
|
|
}
|
|
protected override Company InitInstance()
|
|
{
|
|
return new Company { Id = Guid.NewGuid() };
|
|
}
|
|
|
|
protected override Company RetrieveReadOnlyById(Guid key)
|
|
{
|
|
return DataTable.AsNoTracking().FirstOrDefault(t => t.Id == key);
|
|
}
|
|
|
|
public override DbSet<Company> DataTable
|
|
{
|
|
get
|
|
{
|
|
return DbContext.Companies;
|
|
}
|
|
}
|
|
|
|
#region Public Methods
|
|
public CompanyModel GetCompanyByName(string name)
|
|
{
|
|
return CompanyModelBasicQuery.Where(x => x.Name == name).FirstOrDefault();
|
|
}
|
|
public CompanyModel GetCompanyById(Guid id)
|
|
{
|
|
return CompanyModelBasicQuery.FirstOrDefault(q => q.Id == id);
|
|
}
|
|
/// <summary>Loads a first Company with parentId == null.</summary>
|
|
/// <returns>A <see cref="CompanyModel"/> object.</returns>
|
|
public CompanyModel LoadParent()
|
|
{
|
|
var parent = CompanyModelBasicQuery.FirstOrDefault(t => t.ParentCompanyId == null);
|
|
if (parent == null)
|
|
throw new BLLException("There is no Parent Company in the database. It should be created on application start.", false);
|
|
|
|
return parent;
|
|
}
|
|
|
|
public CompanyModel LoadWithChildCollections(Guid companyId)
|
|
{
|
|
var model = LoadCompanyModel(companyId);
|
|
if (model != null && model.Id != Guid.Empty)
|
|
{
|
|
model.ClientId = DbContext.Company2Client.AsNoTracking().Where(x => x.CompanyId == model.Id)
|
|
.Select(x => x.ClientId)
|
|
.ToList();
|
|
|
|
model.ViewId = DbContext.Company2View.AsNoTracking().Where(x => x.CompanyId == model.Id)
|
|
.Select(x => x.ViewId)
|
|
.ToList();
|
|
}
|
|
|
|
return model;
|
|
}
|
|
|
|
public override Company Save(CompanyModel model)
|
|
{
|
|
var company = base.Save(model);
|
|
|
|
if (Guid.Empty.Equals(model.Id))
|
|
{
|
|
if (model.ClientId != null)
|
|
{
|
|
foreach (var clientId in model.ClientId)
|
|
{
|
|
var client = DbContext.Company2Client.Create();
|
|
client.Id = Guid.NewGuid();
|
|
client.ClientId = clientId;
|
|
client.CompanyId = company.Id;
|
|
DbContext.Company2Client.Add(client);
|
|
}
|
|
}
|
|
|
|
if (model.ViewId != null)
|
|
{
|
|
foreach (var viewId in model.ViewId)
|
|
{
|
|
var company2View = DbContext.Company2View.Create();
|
|
company2View.Id = Guid.NewGuid();
|
|
company2View.ViewId = viewId;
|
|
company2View.CompanyId = company.Id;
|
|
DbContext.Company2View.Add(company2View);
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
var clients = DbContext.Company2Client.Where(x => x.CompanyId == model.Id).ToList();
|
|
clients.Where(x => model.ClientId == null || !model.ClientId.Contains(x.ClientId)).ToList().
|
|
ForEach(x => DbContext.Entry(x).State = EntityState.Deleted);
|
|
|
|
var company2Views = DbContext.Company2View.Where(x => x.CompanyId == model.Id).ToList();
|
|
company2Views.Where(x => model.ViewId == null || !model.ViewId.Contains(x.ViewId)).ToList().
|
|
ForEach(x => DbContext.Entry(x).State = EntityState.Deleted);
|
|
|
|
if (model.ClientId != null)
|
|
{
|
|
|
|
foreach (var clientId in model.ClientId.Where(c => !clients.Select(x => x.ClientId).Contains(c)))
|
|
{
|
|
var client = DbContext.Company2Client.Create();
|
|
client.Id = Guid.NewGuid();
|
|
client.ClientId = clientId;
|
|
client.CompanyId = company.Id;
|
|
DbContext.Company2Client.Add(client);
|
|
}
|
|
}
|
|
|
|
if (model.ViewId != null)
|
|
{
|
|
foreach (var viewId in model.ViewId.Where(c => !company2Views.Select(x => x.ViewId).Contains(c)))
|
|
{
|
|
var company2View = DbContext.Company2View.Create();
|
|
company2View.Id = Guid.NewGuid();
|
|
company2View.ViewId = viewId;
|
|
company2View.CompanyId = model.Id;
|
|
DbContext.Company2View.Add(company2View);
|
|
}
|
|
}
|
|
}
|
|
|
|
#region Save of attached to company watchers and contributors
|
|
|
|
// Get child companies for current, if it is parent for some
|
|
var childCompaniesForCurrent = DbContext.Companies.Where(x =>
|
|
x.ParentCompanyId.HasValue && x.ParentCompanyId.Value.Equals(company.Id)).Select(x => x.Id).ToList();
|
|
|
|
// Remove existing records for current company and it's child companies
|
|
var recsToRemove = DbContext.User2Company.Where(x =>
|
|
x.CompanyId.Equals(company.Id) || childCompaniesForCurrent.Contains(x.CompanyId)).ToList();
|
|
DbContext.User2Company.RemoveRange(recsToRemove);
|
|
|
|
SaveCompanyUsers(company.Id, model.Contributors, CollaborationRole.Contributor);
|
|
|
|
// If a user is already a contributor, we no need to save him as a watcher
|
|
var watchersFiltered = (model.Contributors != null) && (model.Watchers != null) ?
|
|
model.Watchers.Except(model.Contributors).ToList() : new List<Guid>();
|
|
|
|
SaveCompanyUsers(company.Id, watchersFiltered, CollaborationRole.Watcher);
|
|
|
|
#endregion
|
|
|
|
return company;
|
|
}
|
|
|
|
private void SaveCompanyUsers(Guid companyId, List<Guid> users, CollaborationRole role)
|
|
{
|
|
if ((users == null) || (users.Count < 1))
|
|
return;
|
|
|
|
foreach (Guid userId in users)
|
|
{
|
|
User2Company newRec = new User2Company()
|
|
{
|
|
Id = Guid.NewGuid(),
|
|
CompanyId = companyId,
|
|
UserId = userId,
|
|
RelationType = role
|
|
};
|
|
DbContext.User2Company.Add(newRec);
|
|
}
|
|
}
|
|
|
|
/// <summary>
|
|
/// Returns All companies, available for given user, ordered by parent company.
|
|
/// </summary>
|
|
/// <param name="userId">User Id</param>
|
|
/// <returns>All companies.</returns>
|
|
public IList<Company> GetCompaniesByUser(Guid? userId)
|
|
{
|
|
IQueryable<Company> qry = null;
|
|
|
|
if (userId.HasValue)
|
|
{
|
|
qry =
|
|
from c in DbContext.Companies
|
|
join u2c in DbContext.VW_User2Company on c.Id equals u2c.CompanyId
|
|
where u2c.UserId.Equals(userId.Value) && ((u2c.Read == 1) || (u2c.Write == 1))
|
|
select c;
|
|
}
|
|
else
|
|
{
|
|
qry = DbContext.Companies;
|
|
}
|
|
|
|
var result = qry.Distinct().ToList();
|
|
return result;
|
|
}
|
|
|
|
/// <summary>
|
|
/// Returns All companies, available for given user
|
|
/// </summary>
|
|
/// <param name="userId">User Id</param>
|
|
/// <returns>Companies, available for user or all companies, if user not specified</returns>
|
|
public Task<List<Company>> GetCompaniesByUserAsync(Guid? userId)
|
|
{
|
|
Task<List<Company>> result;
|
|
|
|
if (userId.HasValue)
|
|
{
|
|
result =
|
|
(from c in DbContext.Companies
|
|
join u2c in DbContext.VW_User2Company on c.Id equals u2c.CompanyId
|
|
where u2c.UserId.Equals(userId.Value) && ((u2c.Read == 1) || (u2c.Write == 1))
|
|
select c).Distinct().ToListAsync();
|
|
}
|
|
else
|
|
{
|
|
result = DbContext.Companies.ToListAsync();
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
public IList<Company> GetCompaniesByUserFiltered(List<Guid> companies)
|
|
{
|
|
if (companies == null)
|
|
throw new ArgumentNullException("companies");
|
|
|
|
var availableToUserCompanies = this.GetCompaniesByUser(null);
|
|
var result = availableToUserCompanies.Where(x => companies.Contains(x.Id)).ToList();
|
|
return result;
|
|
}
|
|
|
|
/// <summary>
|
|
/// Returns All companies, available for given user, ordered by parent company.
|
|
/// </summary>
|
|
/// <param name="userId">User Id</param>
|
|
/// <returns>All companies.</returns>
|
|
public IList<CompanyApiModel> GetCompaniesByUser4Display(Guid? userId)
|
|
{
|
|
IQueryable<CompanyApiModel> companies = null;
|
|
if (userId.HasValue)
|
|
{
|
|
companies = (from cmp in DbContext.Companies.AsNoTracking()
|
|
join visible4User in DbContext.VW_User2Company4Display on cmp.Id equals visible4User.CompanyId
|
|
where (!userId.HasValue || visible4User.UserId.Equals(userId.Value)) &&
|
|
((visible4User.Read == 1) || (visible4User.Write == 1))
|
|
select cmp).ToArray().Select(t=> new CompanyApiModel(t)).AsQueryable();
|
|
} else
|
|
{
|
|
companies = DbContext.Companies.ToArray().Select(x => new CompanyApiModel(x)).AsQueryable();
|
|
}
|
|
|
|
return companies.Distinct().ToList();
|
|
}
|
|
|
|
public CompanyModel LoadCompanyModel(Guid companyId)
|
|
{
|
|
return CompanyModelBasicQuery.FirstOrDefault(x => x.Id == companyId);
|
|
}
|
|
|
|
public List<CompanyModel> LoadCompanies()
|
|
{
|
|
return CompanyModelBasicQuery.ToList();
|
|
}
|
|
|
|
public Dictionary<KeyValuePair<Guid, string>, List<CompanyModel>> GetCompanies()
|
|
{
|
|
var data = CompanyModelBasicQuery.ToArray();
|
|
var result = new Dictionary<KeyValuePair<Guid, string>, List<CompanyModel>>();
|
|
foreach (var parent in data.Where(t => !t.ParentCompanyId.HasValue).OrderBy(t => t.Name))
|
|
{
|
|
var key = new KeyValuePair<Guid, string>(parent.Id, parent.Name);
|
|
if (!result.ContainsKey(key))
|
|
result.Add(key, new List<CompanyModel>());
|
|
}
|
|
foreach (var child in data.Where(t => t.ParentCompanyId.HasValue).OrderBy(t => t.Name))
|
|
{
|
|
var parentKey = new KeyValuePair<Guid, string>(child.ParentCompanyId.Value, child.ParentCompanyName);
|
|
// add parent if it wasnt added in previous foreach for some reason
|
|
if (!result.ContainsKey(parentKey))
|
|
result.Add(parentKey, new List<CompanyModel>());
|
|
var parent = result[parentKey];
|
|
if (parent != null)
|
|
parent.Add((CompanyModel)child);
|
|
}
|
|
return result;
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Private Members
|
|
|
|
private IQueryable<CompanyModel> CompanyModelBasicQuery
|
|
{
|
|
get
|
|
{
|
|
var query = DbContext.Companies.Include(x => x.Projects).Include(x => x.Company1)
|
|
.Include(x => x.Company2).Include(x => x.Teams).AsNoTracking()
|
|
.Select(x =>
|
|
new CompanyModel
|
|
{
|
|
Id = x.Id,
|
|
Name = x.Name,
|
|
ParentCompanyId = x.ParentCompanyId,
|
|
ParentCompanyName = x.ParentCompanyId.HasValue ? x.Company2.Name : null,
|
|
ProjectsCount = x.Projects.Count,
|
|
CompaniesCount = x.Company1.Count,
|
|
TeamsCount = x.Teams.Count
|
|
});
|
|
|
|
return query;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
}
|
|
} |