Gis parte 2

This commit is contained in:
Jorge Luis caudillo esparza
2026-08-18 17:20:44 -07:00
parent 3c0b18f474
commit 1c84a87f11
27 changed files with 2265 additions and 1016 deletions

View File

@@ -46,6 +46,7 @@ namespace SIG.Web.AppCode.Configuration
public static IGeneralCatalogRepository GeneralCatalogRepository { get; private set; } public static IGeneralCatalogRepository GeneralCatalogRepository { get; private set; }
public static IClienteDocumentoService ClienteDocumentoService { get; private set; } public static IClienteDocumentoService ClienteDocumentoService { get; private set; }
public static IFraccionamientoService FraccionamientoService { get; private set; } public static IFraccionamientoService FraccionamientoService { get; private set; }
public static IFraccionamientoGisService FraccionamientoGisService { get; private set; }
public static ITramiteCatalogService TramiteCatalogService { get; private set; } public static ITramiteCatalogService TramiteCatalogService { get; private set; }
public static ICfdiTimbradoService CfdiTimbradoService { get; private set; } public static ICfdiTimbradoService CfdiTimbradoService { get; private set; }
public static IPublicRegistrationService PublicRegistrationService { get; private set; } public static IPublicRegistrationService PublicRegistrationService { get; private set; }
@@ -92,6 +93,14 @@ namespace SIG.Web.AppCode.Configuration
FraccionamientoService = new FraccionamientoService( FraccionamientoService = new FraccionamientoService(
new FraccionamientoRepository(DbExecutor), new FraccionamientoRepository(DbExecutor),
BitacoraService); BitacoraService);
IFraccionamientoGisRepository gisRepository =
new FraccionamientoGisRepository(DbExecutor);
IFraccionamientoGisFileStore gisFileStore =
new FraccionamientoGisFileStore();
FraccionamientoGisService = new FraccionamientoGisService(
gisRepository,
gisFileStore);
TramiteCatalogService = new TramiteCatalogService( TramiteCatalogService = new TramiteCatalogService(
new TramiteCatalogRepository(DbExecutor), new TramiteCatalogRepository(DbExecutor),
BitacoraService); BitacoraService);

View File

@@ -9,5 +9,6 @@ namespace SIG.Web.AppCode.Contracts.Fraccionamientos
bool Exists(FraccionamientoGisContextModel context); bool Exists(FraccionamientoGisContextModel context);
void Save(FraccionamientoGisContextModel context, Stream source); void Save(FraccionamientoGisContextModel context, Stream source);
Stream OpenRead(FraccionamientoGisContextModel context); Stream OpenRead(FraccionamientoGisContextModel context);
void Delete(FraccionamientoGisContextModel context);
} }
} }

View File

@@ -0,0 +1,29 @@
using System.Collections.Generic;
using System.IO;
using SIG.Web.AppCode.Models.Common;
using SIG.Web.AppCode.Models.Fraccionamientos;
namespace SIG.Web.AppCode.Contracts.Fraccionamientos
{
public interface IFraccionamientoGisService
{
DbResult<FraccionamientoGisViewModel> Get(
int stageId,
int executingUser,
string domainName);
DbResult<FraccionamientoGisSaveResultModel> Save(
int stageId,
string originalFileName,
Stream content,
long contentLength,
IList<FraccionamientoGisLotLinkModel> links,
int executingUser,
string domainName);
DbResult<FraccionamientoGisFileModel> OpenFile(
int stageId,
int executingUser,
string domainName);
}
}

View File

@@ -1,78 +1,387 @@
using System; using System;
using System.Collections.Generic;
using System.Globalization;
using System.IO; using System.IO;
using System.Web; using System.Web;
using System.Web.Script.Serialization;
using System.Web.SessionState; using System.Web.SessionState;
using SIG.Web.AppCode.Configuration; using SIG.Web.AppCode.Configuration;
using SIG.Web.AppCode.Models.Common; using SIG.Web.AppCode.Models.Common;
using SIG.Web.AppCode.Models.Documentos; using SIG.Web.AppCode.Models.Fraccionamientos;
using SIG.Web.AppCode.Services.Errors;
using SIG.Web.AppCode.Session; using SIG.Web.AppCode.Session;
namespace SIG.Web.Pages.Fraccionamientos namespace SIG.Web.Pages.Fraccionamientos
{ {
public sealed class FraccionamientoGisHandler : IHttpHandler, IRequiresSessionState public sealed class FraccionamientoGisHandler : IHttpHandler, IRequiresSessionState
{ {
private static readonly JavaScriptSerializer Json =
new JavaScriptSerializer
{
MaxJsonLength = 4 * 1024 * 1024
};
public bool IsReusable public bool IsReusable
{ {
get get { return false; }
{
return false;
}
} }
public void ProcessRequest(HttpContext context) public void ProcessRequest(HttpContext context)
{ {
if (!AppServices.UserContext.IsAuthenticated()) try
{ {
context.Response.StatusCode = 401; UserSessionModel currentUser = GetCurrentUser(context);
if (currentUser == null)
{
WriteJson(
context,
401,
new
{
success = false,
message = "Su sesión no está disponible. Inicie sesión nuevamente.",
codigo = string.Empty
});
return;
}
string method = (context.Request["metodo"] ?? string.Empty)
.Trim();
if (string.Equals(
context.Request.HttpMethod,
"POST",
StringComparison.OrdinalIgnoreCase))
{
if (!string.Equals(method, "Save", StringComparison.OrdinalIgnoreCase))
{
WriteJson(
context,
405,
new
{
success = false,
message = "La operación GIS solicitada no es válida.",
codigo = string.Empty
});
return;
}
Save(context, currentUser);
return;
}
int stageId;
if (!TryGetStageId(context, out stageId))
{
WriteJson(
context,
400,
new
{
success = false,
message = "Seleccione una etapa válida.",
codigo = string.Empty
});
return;
}
if (string.Equals(method, "Context", StringComparison.OrdinalIgnoreCase))
{
GetContext(context, currentUser, stageId);
return;
}
if (string.IsNullOrWhiteSpace(method) ||
string.Equals(method, "File", StringComparison.OrdinalIgnoreCase))
{
OpenFile(context, currentUser, stageId);
return;
}
WriteJson(
context,
405,
new
{
success = false,
message = "La operación GIS solicitada no es válida.",
codigo = string.Empty
});
}
catch (Exception ex)
{
WriteUnexpectedError(context, ex);
}
}
private static UserSessionModel GetCurrentUser(HttpContext context)
{
if (AppServices.UserContext == null ||
!AppServices.UserContext.IsAuthenticated())
{
return null;
}
return AppServices.UserContext.GetCurrentUser();
}
private static void GetContext(
HttpContext context,
UserSessionModel currentUser,
int stageId)
{
DbResult<FraccionamientoGisViewModel> result =
AppServices.FraccionamientoGisService.Get(
stageId,
currentUser.CveUsuario,
currentUser.NombreDominio);
if (!result.Success || result.Data == null)
{
WriteResultFailure(context, result, 400);
return; return;
} }
WriteJson(
context,
200,
new
{
success = true,
message = string.Empty,
data = result.Data
});
}
private static void Save(
HttpContext context,
UserSessionModel currentUser)
{
int stageId; int stageId;
if (!TryGetStageId(context, out stageId))
if (!int.TryParse(
context.Request.QueryString["etapa"],
out stageId) ||
stageId <= 0)
{ {
context.Response.StatusCode = 400; WriteJson(
context,
400,
new
{
success = false,
message = "Seleccione una etapa válida.",
codigo = string.Empty
});
return; return;
} }
UserSessionModel currentUser = IList<FraccionamientoGisLotLinkModel> links;
AppServices.UserContext.GetCurrentUser(); string linksJson = context.Request.Form["vinculos"];
if (currentUser == null) try
{ {
context.Response.StatusCode = 401; links = string.IsNullOrWhiteSpace(linksJson)
? new List<FraccionamientoGisLotLinkModel>()
: Json.Deserialize<List<FraccionamientoGisLotLinkModel>>(
linksJson);
}
catch (Exception)
{
WriteJson(
context,
400,
new
{
success = false,
message = "Los vínculos GIS enviados no tienen un formato válido.",
codigo = string.Empty
});
return; return;
} }
DbResult<ClienteDocumentoArchivoModel> result = HttpPostedFile postedFile = context.Request.Files["archivo"];
AppServices.ClienteDocumentoService.GetStageGis( Stream content = postedFile != null
? postedFile.InputStream
: null;
long contentLength = postedFile != null
? postedFile.ContentLength
: 0L;
string originalFileName = postedFile != null
? Path.GetFileName(postedFile.FileName)
: string.Empty;
DbResult<FraccionamientoGisSaveResultModel> result =
AppServices.FraccionamientoGisService.Save(
stageId,
originalFileName,
content,
contentLength,
links,
currentUser.CveUsuario,
currentUser.NombreDominio);
if (!result.Success)
{
WriteResultFailure(context, result, 400);
return;
}
WriteJson(
context,
200,
new
{
success = true,
message = "GIS y vínculos guardados correctamente.",
data = result.Data
});
}
private static void OpenFile(
HttpContext context,
UserSessionModel currentUser,
int stageId)
{
DbResult<FraccionamientoGisFileModel> result =
AppServices.FraccionamientoGisService.OpenFile(
stageId, stageId,
currentUser.CveUsuario, currentUser.CveUsuario,
currentUser.NombreDominio); currentUser.NombreDominio);
if (!result.Success || if (!result.Success ||
result.Data == null || result.Data == null ||
string.IsNullOrWhiteSpace(result.Data.RutaFisica) || result.Data.Content == null)
!File.Exists(result.Data.RutaFisica))
{ {
context.Response.StatusCode = 404; WriteResultFailure(context, result, 404);
return; return;
} }
ClienteDocumentoArchivoModel file = result.Data; FraccionamientoGisFileModel file = result.Data;
context.Response.Clear(); context.Response.Clear();
context.Response.ClearHeaders();
context.Response.TrySkipIisCustomErrors = true;
context.Response.Cache.SetCacheability(HttpCacheability.NoCache); context.Response.Cache.SetCacheability(HttpCacheability.NoCache);
context.Response.Cache.SetNoStore(); context.Response.Cache.SetNoStore();
context.Response.ContentType = file.ContentType; context.Response.ContentType = string.IsNullOrWhiteSpace(file.ContentType)
? "application/octet-stream"
: file.ContentType;
bool download = string.Equals(
context.Request.QueryString["download"],
"1",
StringComparison.Ordinal);
context.Response.AddHeader( context.Response.AddHeader(
"Content-Disposition", "Content-Disposition",
"attachment; filename=\"" + file.NombreArchivo + "\""); (download ? "attachment" : "inline") +
context.Response.TransmitFile(file.RutaFisica); "; filename=\"" +
SanitizeHeaderFileName(file.NombreArchivo) +
"\"");
using (file.Content)
{
file.Content.CopyTo(context.Response.OutputStream);
}
context.ApplicationInstance.CompleteRequest(); context.ApplicationInstance.CompleteRequest();
} }
private static bool TryGetStageId(
HttpContext context,
out int stageId)
{
string value = context.Request["CveFraccionamientoEtapa"];
if (string.IsNullOrWhiteSpace(value))
{
value = context.Request.QueryString["etapa"];
}
return int.TryParse(
value,
NumberStyles.Integer,
CultureInfo.InvariantCulture,
out stageId) &&
stageId > 0;
}
private static void WriteResultFailure<T>(
HttpContext context,
DbResult<T> result,
int statusCode)
{
string message = result == null ||
string.IsNullOrWhiteSpace(result.UserMessage)
? "No fue posible completar la operación GIS."
: result.UserMessage;
WriteJson(
context,
statusCode,
new
{
success = false,
message = message,
codigo = string.Empty
});
}
private static void WriteUnexpectedError(
HttpContext context,
Exception exception)
{
string cveUsuario;
string nombreUsuario;
int cveRol;
SIGErrorManager.ObtenerUsuarioActual(
out cveUsuario,
out nombreUsuario,
out cveRol);
string code = SIGErrorManager.Registrar(
exception,
context,
"FraccionamientoGisHandler",
cveUsuario,
nombreUsuario);
WriteJson(
context,
500,
new
{
success = false,
message = ErrorHandlerConfig.GetFriendlyMessage(exception),
codigo = code
});
}
private static void WriteJson(
HttpContext context,
int statusCode,
object value)
{
context.Response.Clear();
context.Response.ClearHeaders();
context.Response.StatusCode = statusCode;
context.Response.TrySkipIisCustomErrors = true;
context.Response.ContentType = "application/json; charset=utf-8";
context.Response.Cache.SetCacheability(HttpCacheability.NoCache);
context.Response.Cache.SetNoStore();
context.Response.Write(Json.Serialize(value));
context.ApplicationInstance.CompleteRequest();
}
private static string SanitizeHeaderFileName(string fileName)
{
string safeName = string.IsNullOrWhiteSpace(fileName)
? "archivo.gis"
: Path.GetFileName(fileName);
return safeName
.Replace("\"", string.Empty)
.Replace("\r", string.Empty)
.Replace("\n", string.Empty);
}
} }
} }

View File

@@ -1,3 +1,7 @@
using System;
using System.Collections.Generic;
using System.IO;
namespace SIG.Web.AppCode.Models.Fraccionamientos namespace SIG.Web.AppCode.Models.Fraccionamientos
{ {
public sealed class FraccionamientoGisContextModel public sealed class FraccionamientoGisContextModel
@@ -13,7 +17,40 @@ namespace SIG.Web.AppCode.Models.Fraccionamientos
{ {
public int CveFraccionamientoLote { get; set; } public int CveFraccionamientoLote { get; set; }
public string Nombre { get; set; } public string Nombre { get; set; }
public string Etapa { get; set; }
public string Numero { get; set; }
public string Tipo { get; set; }
public string Calle { get; set; }
public string Catastro { get; set; }
public decimal? MetrosCuadrados { get; set; }
public string Duplicador { get; set; }
public string GISPoligonoClave { get; set; } public string GISPoligonoClave { get; set; }
public bool EsActivo { get; set; } public bool EsActivo { get; set; }
} }
public sealed class FraccionamientoGisViewModel
{
public FraccionamientoGisContextModel Contexto { get; set; }
public List<FraccionamientoGisLotLinkModel> Lotes { get; set; }
public bool TieneArchivo { get; set; }
public string NombreArchivo { get; set; }
public DateTime? FechaArchivo { get; set; }
}
public sealed class FraccionamientoGisSaveResultModel
{
public int CveFraccionamientoEtapa { get; set; }
public int VinculosGuardados { get; set; }
public bool ArchivoGuardado { get; set; }
public bool TieneArchivo { get; set; }
public string NombreArchivo { get; set; }
public DateTime? FechaArchivo { get; set; }
}
public sealed class FraccionamientoGisFileModel
{
public string NombreArchivo { get; set; }
public string ContentType { get; set; }
public Stream Content { get; set; }
}
} }

View File

@@ -13,21 +13,20 @@ using SIG.Web.AppCode.Utilities;
namespace SIG.Web.AppCode.Repositories.Bitacora namespace SIG.Web.AppCode.Repositories.Bitacora
{ {
public sealed class BitacoraRepository : IBitacoraRepository public sealed class BitacoraRepository
: RepositoryBase, IBitacoraRepository
{ {
private const string BitacoraDomain = "Bitacora"; private const string BitacoraDomain = "Bitacora";
private readonly IDbExecutor _dbExecutor;
public BitacoraRepository(IDbExecutor dbExecutor) public BitacoraRepository(IDbExecutor dbExecutor)
: base(dbExecutor)
{ {
_dbExecutor = dbExecutor;
} }
public DbResult<long> Agregar( public DbResult<long> Agregar(
BitacoraEventoModel evento, BitacoraEventoModel evento,
BitacoraContextoModel contexto) BitacoraContextoModel contexto)
{ {
return _dbExecutor.Execute(BitacoraDomain, connection => return ExecuteCustom(BitacoraDomain, connection =>
{ {
using (IDbCommand command = connection.CreateCommand()) using (IDbCommand command = connection.CreateCommand())
{ {
@@ -121,7 +120,7 @@ namespace SIG.Web.AppCode.Repositories.Bitacora
BitacoraFiltroModel filtro, BitacoraFiltroModel filtro,
int cveUsuarioEjecuta) int cveUsuarioEjecuta)
{ {
return _dbExecutor.Execute(BitacoraDomain, connection => return ExecuteCustom(BitacoraDomain, connection =>
{ {
using (IDbCommand command = connection.CreateCommand()) using (IDbCommand command = connection.CreateCommand())
{ {
@@ -181,7 +180,7 @@ namespace SIG.Web.AppCode.Repositories.Bitacora
int registrosOmitidos = checked( int registrosOmitidos = checked(
(consulta.Pagina - 1) * consulta.RegistrosPorPagina); (consulta.Pagina - 1) * consulta.RegistrosPorPagina);
return _dbExecutor.Execute(BitacoraDomain, connection => return ExecuteCustom(BitacoraDomain, connection =>
{ {
using (IDbCommand command = connection.CreateCommand()) using (IDbCommand command = connection.CreateCommand())
{ {
@@ -275,7 +274,7 @@ namespace SIG.Web.AppCode.Repositories.Bitacora
int registrosOmitidos = checked( int registrosOmitidos = checked(
(consulta.Pagina - 1) * consulta.RegistrosPorPagina); (consulta.Pagina - 1) * consulta.RegistrosPorPagina);
return _dbExecutor.Execute(BitacoraDomain, connection => return ExecuteCustom(BitacoraDomain, connection =>
{ {
using (IDbCommand command = connection.CreateCommand()) using (IDbCommand command = connection.CreateCommand())
{ {

View File

@@ -21,13 +21,30 @@ namespace SIG.Web.AppCode.Repositories.Database
_db = db; _db = db;
} }
protected DbResult<List<T>> QueryList<T>( protected DbResult<TResult> ExecuteCustom<TResult>(
string domain,
Func<IDbConnection, TResult> action)
{
if (action == null)
{
throw new ArgumentNullException("action");
}
return _db.Execute(domain, action);
}
protected DbResult<TResult> QueryReader<TResult>(
string procedure, string procedure,
int user, int user,
string domain, string domain,
Action<IDbCommand> parameters) Action<IDbCommand> parameters,
where T : class, new() Func<IDataReader, TResult> readerMapper)
{ {
if (readerMapper == null)
{
throw new ArgumentNullException("readerMapper");
}
return _db.Execute(domain, connection => return _db.Execute(domain, connection =>
{ {
using (IDbCommand command = connection.CreateCommand()) using (IDbCommand command = connection.CreateCommand())
@@ -39,10 +56,11 @@ namespace SIG.Web.AppCode.Repositories.Database
parameters(command); parameters(command);
} }
List<T> value; TResult value;
using (IDataReader reader = command.ExecuteReader()) using (IDataReader reader = command.ExecuteReader())
{ {
value = reader.ToList<T>(); value = readerMapper(reader);
} }
StoredProcedureCommand.EnsureSuccess(command); StoredProcedureCommand.EnsureSuccess(command);
@@ -51,6 +69,21 @@ namespace SIG.Web.AppCode.Repositories.Database
}); });
} }
protected DbResult<List<T>> QueryList<T>(
string procedure,
int user,
string domain,
Action<IDbCommand> parameters)
where T : class, new()
{
return QueryReader(
procedure,
user,
domain,
parameters,
reader => reader.ToList<T>());
}
protected DbResult<T> QueryOne<T>( protected DbResult<T> QueryOne<T>(
string procedure, string procedure,
int user, int user,
@@ -58,27 +91,12 @@ namespace SIG.Web.AppCode.Repositories.Database
Action<IDbCommand> parameters) Action<IDbCommand> parameters)
where T : class, new() where T : class, new()
{ {
return _db.Execute(domain, connection => return QueryReader(
{ procedure,
using (IDbCommand command = connection.CreateCommand()) user,
{ domain,
StoredProcedureCommand.Configure(command, procedure, user); parameters,
reader => reader.ToObject<T>());
if (parameters != null)
{
parameters(command);
}
T value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.ToObject<T>();
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
} }
protected DbResult<int> QueryScalarId( protected DbResult<int> QueryScalarId(
@@ -86,6 +104,38 @@ namespace SIG.Web.AppCode.Repositories.Database
int user, int user,
string domain, string domain,
Action<IDbCommand> parameters) Action<IDbCommand> parameters)
{
return QueryReader(
procedure,
user,
domain,
parameters,
reader => reader.Read()
? Convert.ToInt32(reader.GetValue(0))
: 0);
}
protected DbResult<long> QueryScalarLong(
string procedure,
int user,
string domain,
Action<IDbCommand> parameters)
{
return QueryReader(
procedure,
user,
domain,
parameters,
reader => reader.Read()
? Convert.ToInt64(reader.GetValue(0))
: 0L);
}
protected DbResult<bool> QueryScalarBool(
string procedure,
int user,
string domain,
Action<IDbCommand> parameters)
{ {
return _db.Execute(domain, connection => return _db.Execute(domain, connection =>
{ {
@@ -98,16 +148,12 @@ namespace SIG.Web.AppCode.Repositories.Database
parameters(command); parameters(command);
} }
int value; object value = command.ExecuteScalar();
using (IDataReader reader = command.ExecuteReader())
{
value = reader.Read()
? Convert.ToInt32(reader.GetValue(0))
: 0;
}
StoredProcedureCommand.EnsureSuccess(command); StoredProcedureCommand.EnsureSuccess(command);
return value;
return value != null &&
value != DBNull.Value &&
Convert.ToBoolean(value);
} }
}); });
} }

View File

@@ -4,17 +4,15 @@ using SIG.Web.AppCode.Contracts.Documentos;
using SIG.Web.AppCode.Models.Common; using SIG.Web.AppCode.Models.Common;
using SIG.Web.AppCode.Models.Documentos; using SIG.Web.AppCode.Models.Documentos;
using SIG.Web.AppCode.Repositories.Database; using SIG.Web.AppCode.Repositories.Database;
using SIG.Web.AppCode.Utilities;
namespace SIG.Web.AppCode.Repositories.Documentos namespace SIG.Web.AppCode.Repositories.Documentos
{ {
public sealed class ClienteDocumentoRepository : IClienteDocumentoRepository public sealed class ClienteDocumentoRepository
: RepositoryBase, IClienteDocumentoRepository
{ {
private readonly IDbExecutor _db;
public ClienteDocumentoRepository(IDbExecutor db) public ClienteDocumentoRepository(IDbExecutor db)
: base(db)
{ {
_db = db;
} }
public DbResult<ClienteDocumentoEtapaContextoModel> GetStageContext( public DbResult<ClienteDocumentoEtapaContextoModel> GetStageContext(
@@ -22,31 +20,15 @@ namespace SIG.Web.AppCode.Repositories.Documentos
int executingUser, int executingUser,
string domainName) string domainName)
{ {
return _db.Execute(domainName, connection => return QueryOne<ClienteDocumentoEtapaContextoModel>(
{ "dbo.PA_Fraccionamientos_EtapaDocumentoGet",
using (IDbCommand command = connection.CreateCommand()) executingUser,
{ domainName,
StoredProcedureCommand.Configure( command => StoredProcedureCommand.AddInput(
command, command,
"dbo.PA_Fraccionamientos_EtapaDocumentoGet", "@CveFraccionamientoEtapa",
executingUser); stageId,
StoredProcedureCommand.AddInput( DbType.Int32));
command,
"@CveFraccionamientoEtapa",
stageId,
DbType.Int32);
ClienteDocumentoEtapaContextoModel value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.ToObject<ClienteDocumentoEtapaContextoModel>();
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
} }
} }
} }

View File

@@ -11,13 +11,12 @@ using SIG.Web.AppCode.Utilities;
namespace SIG.Web.AppCode.Repositories.Facturacion namespace SIG.Web.AppCode.Repositories.Facturacion
{ {
public sealed class CfdiRepository : ICfdiRepository public sealed class CfdiRepository
: RepositoryBase, ICfdiRepository
{ {
private readonly IDbExecutor _db;
public CfdiRepository(IDbExecutor db) public CfdiRepository(IDbExecutor db)
: base(db)
{ {
_db = db;
} }
public DbResult<CfdiEmisorFiscalModel> ObtenerEmisor( public DbResult<CfdiEmisorFiscalModel> ObtenerEmisor(
@@ -442,94 +441,6 @@ namespace SIG.Web.AppCode.Repositories.Facturacion
}); });
} }
private DbResult<List<T>> QueryList<T>(
string procedure,
int user,
string domain,
Action<IDbCommand> parameters)
where T : class, new()
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(
command,
procedure,
user);
parameters?.Invoke(command);
List<T> value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.ToList<T>();
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
}
private DbResult<T> QueryOne<T>(
string procedure,
int user,
string domain,
Action<IDbCommand> parameters)
where T : class, new()
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(
command,
procedure,
user);
parameters?.Invoke(command);
T value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.ToObject<T>();
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
}
private DbResult<long> QueryScalarLong(
string procedure,
int user,
string domain,
Action<IDbCommand> parameters)
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(
command,
procedure,
user);
parameters(command);
long value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.Read()
? Convert.ToInt64(reader.GetValue(0))
: 0L;
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
}
private static void Add( private static void Add(
IDbCommand command, IDbCommand command,
string name, string name,

View File

@@ -13,13 +13,12 @@ using SIG.Web.AppCode.Utilities;
namespace SIG.Web.AppCode.Repositories.Fraccionamientos namespace SIG.Web.AppCode.Repositories.Fraccionamientos
{ {
public sealed class FraccionamientoRepository : IFraccionamientoRepository public sealed class FraccionamientoRepository
: RepositoryBase, IFraccionamientoRepository
{ {
private readonly IDbExecutor _db;
public FraccionamientoRepository(IDbExecutor db) public FraccionamientoRepository(IDbExecutor db)
: base(db)
{ {
_db = db;
} }
public DbResult<List<FraccionamientoClienteOptionModel>> ListClients(int executingUser, string domainName) public DbResult<List<FraccionamientoClienteOptionModel>> ListClients(int executingUser, string domainName)
@@ -450,83 +449,5 @@ namespace SIG.Web.AppCode.Repositories.Fraccionamientos
DbType.Int32); DbType.Int32);
}); });
} }
private DbResult<List<T>> QueryList<T>(
string procedure, int user, string domain, Action<IDbCommand> parameters)
where T : class, new()
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(command, procedure, user);
if (parameters != null) parameters(command);
List<T> value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.ToList<T>();
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
}
private DbResult<T> QueryOne<T>(
string procedure, int user, string domain, Action<IDbCommand> parameters)
where T : class, new()
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(command, procedure, user);
if (parameters != null) parameters(command);
T value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.ToObject<T>();
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
}
private DbResult<int> QueryScalarId(
string procedure, int user, string domain, Action<IDbCommand> parameters)
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(command, procedure, user);
parameters(command);
int value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.Read() ? Convert.ToInt32(reader.GetValue(0)) : 0;
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
}
private DbResult<bool> Execute(
string procedure, int user, string domain, Action<IDbCommand> parameters)
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(command, procedure, user);
parameters(command);
command.ExecuteNonQuery();
StoredProcedureCommand.EnsureSuccess(command);
return true;
}
});
}
} }
} }

View File

@@ -9,61 +9,49 @@ using SIG.Web.AppCode.Utilities;
namespace SIG.Web.AppCode.Repositories.General namespace SIG.Web.AppCode.Repositories.General
{ {
public sealed class GeneralCatalogRepository : IGeneralCatalogRepository public sealed class GeneralCatalogRepository
: RepositoryBase, IGeneralCatalogRepository
{ {
private readonly IDbExecutor _dbExecutor;
public GeneralCatalogRepository(IDbExecutor dbExecutor) public GeneralCatalogRepository(IDbExecutor dbExecutor)
: base(dbExecutor)
{ {
_dbExecutor = dbExecutor;
} }
public DbResult<List<StateOptionModel>> ListStates(string domainName) public DbResult<List<StateOptionModel>> ListStates(string domainName)
{ {
return _dbExecutor.Execute(domainName, connection => return QueryList<StateOptionModel>(
{ "dbo.PA_Gral_EstadoList",
using (IDbCommand command = connection.CreateCommand()) 0,
{ domainName,
StoredProcedureCommand.Configure(command, "dbo.PA_Gral_EstadoList", 0); null);
List<StateOptionModel> states;
using (IDataReader reader = command.ExecuteReader())
{
states = reader.ToList<StateOptionModel>();
}
StoredProcedureCommand.EnsureSuccess(command);
return states;
}
});
} }
public DbResult<PostalCodeLookupModel> GetPostalCode( public DbResult<PostalCodeLookupModel> GetPostalCode(
string postalCode, string postalCode,
string domainName) string domainName)
{ {
return _dbExecutor.Execute(domainName, connection => return QueryReader<PostalCodeLookupModel>(
{ "dbo.PA_Gral_CodigoPostalGet",
using (IDbCommand command = connection.CreateCommand()) 0,
domainName,
command => StoredProcedureCommand.AddInput(
command,
"@CP",
postalCode,
DbType.String),
reader =>
{ {
StoredProcedureCommand.Configure(command, "dbo.PA_Gral_CodigoPostalGet", 0); PostalCodeLookupModel value =
StoredProcedureCommand.AddInput(command, "@CP", postalCode, DbType.String); reader.ToObject<PostalCodeLookupModel>();
PostalCodeLookupModel value; if (value != null && reader.NextResult())
using (IDataReader reader = command.ExecuteReader())
{ {
value = reader.ToObject<PostalCodeLookupModel>(); value.Colonias =
reader.ToList<NeighborhoodOptionModel>();
if (value != null && reader.NextResult())
{
value.Colonias = reader.ToList<NeighborhoodOptionModel>();
}
} }
StoredProcedureCommand.EnsureSuccess(command);
return value; return value;
} });
});
} }
} }
} }

View File

@@ -5,50 +5,29 @@ using SIG.Web.AppCode.Contracts.Menu;
using SIG.Web.AppCode.Models.Common; using SIG.Web.AppCode.Models.Common;
using SIG.Web.AppCode.Repositories.Database; using SIG.Web.AppCode.Repositories.Database;
using SIG.Web.AppCode.Session; using SIG.Web.AppCode.Session;
using SIG.Web.AppCode.Utilities;
namespace SIG.Web.AppCode.Repositories.Menu namespace SIG.Web.AppCode.Repositories.Menu
{ {
public sealed class MenuRepository : IMenuRepository public sealed class MenuRepository
: RepositoryBase, IMenuRepository
{ {
private readonly IDbExecutor _dbExecutor;
public MenuRepository(IDbExecutor dbExecutor) public MenuRepository(IDbExecutor dbExecutor)
: base(dbExecutor)
{ {
_dbExecutor = dbExecutor;
} }
public DbResult<List<MenuItemModel>> ListModules( public DbResult<List<MenuItemModel>> ListModules(
UserSessionModel user) UserSessionModel user)
{ {
return _dbExecutor.Execute( return QueryList<MenuItemModel>(
"dbo.PA_Sis_MenuList",
user.CveUsuario,
user.NombreDominio, user.NombreDominio,
connection => command => StoredProcedureCommand.AddInput(
{ command,
using (IDbCommand command = connection.CreateCommand()) "@CveRol",
{ user.CveRol,
StoredProcedureCommand.Configure( DbType.Int32));
command,
"dbo.PA_Sis_MenuList",
user.CveUsuario);
StoredProcedureCommand.AddInput(
command,
"@CveRol",
user.CveRol,
DbType.Int32);
List<MenuItemModel> items;
using (IDataReader reader = command.ExecuteReader())
{
items = reader.ToList<MenuItemModel>();
}
StoredProcedureCommand.EnsureSuccess(command);
return items;
}
});
} }
} }
} }

View File

@@ -6,13 +6,12 @@ using SIG.Web.AppCode.Repositories.Database;
namespace SIG.Web.AppCode.Repositories.Security namespace SIG.Web.AppCode.Repositories.Security
{ {
public sealed class LoginAttemptRepository : ILoginAttemptRepository public sealed class LoginAttemptRepository
: RepositoryBase, ILoginAttemptRepository
{ {
private readonly IDbExecutor _dbExecutor;
public LoginAttemptRepository(IDbExecutor dbExecutor) public LoginAttemptRepository(IDbExecutor dbExecutor)
: base(dbExecutor)
{ {
_dbExecutor = dbExecutor;
} }
public DbResult<bool> Save( public DbResult<bool> Save(
@@ -24,24 +23,48 @@ namespace SIG.Web.AppCode.Repositories.Security
string userAgent, string userAgent,
string domainName) string domainName)
{ {
return _dbExecutor.Execute(domainName, connection => return Execute(
{ "dbo.PA_Sis_IntentoInicioSesionAdd",
using (IDbCommand command = connection.CreateCommand()) cveUser ?? 0,
domainName,
command =>
{ {
StoredProcedureCommand.Configure(command, "dbo.PA_Sis_IntentoInicioSesionAdd", cveUser ?? 0); StoredProcedureCommand.AddInput(
StoredProcedureCommand.AddInput(command, "@CveUsuario", cveUser.HasValue ? (object)cveUser.Value : null, DbType.Int32); command,
StoredProcedureCommand.AddInput(command, "@NombreUsuario", username, DbType.String); "@CveUsuario",
StoredProcedureCommand.AddInput(command, "@Exitoso", wasSuccessful, DbType.Boolean); cveUser.HasValue ? (object)cveUser.Value : null,
StoredProcedureCommand.AddInput(command, "@MotivoFallo", failureReason, DbType.String); DbType.Int32);
StoredProcedureCommand.AddInput(command, "@DireccionIP", ipAddress, DbType.String); StoredProcedureCommand.AddInput(
StoredProcedureCommand.AddInput(command, "@AgenteUsuario", userAgent, DbType.String); command,
StoredProcedureCommand.AddInput(command, "@NombreDominio", domainName, DbType.String); "@NombreUsuario",
username,
command.ExecuteNonQuery(); DbType.String);
StoredProcedureCommand.EnsureSuccess(command); StoredProcedureCommand.AddInput(
return true; command,
} "@Exitoso",
}); wasSuccessful,
DbType.Boolean);
StoredProcedureCommand.AddInput(
command,
"@MotivoFallo",
failureReason,
DbType.String);
StoredProcedureCommand.AddInput(
command,
"@DireccionIP",
ipAddress,
DbType.String);
StoredProcedureCommand.AddInput(
command,
"@AgenteUsuario",
userAgent,
DbType.String);
StoredProcedureCommand.AddInput(
command,
"@NombreDominio",
domainName,
DbType.String);
});
} }
} }
} }

View File

@@ -1,4 +1,3 @@
using System;
using System.Data; using System.Data;
using SIG.Web.AppCode.Contracts.Database; using SIG.Web.AppCode.Contracts.Database;
using SIG.Web.AppCode.Contracts.Security; using SIG.Web.AppCode.Contracts.Security;
@@ -7,22 +6,22 @@ using SIG.Web.AppCode.Repositories.Database;
namespace SIG.Web.AppCode.Repositories.Security namespace SIG.Web.AppCode.Repositories.Security
{ {
public sealed class PermissionRepository : IPermissionRepository public sealed class PermissionRepository
: RepositoryBase, IPermissionRepository
{ {
private readonly IDbExecutor _dbExecutor;
public PermissionRepository(IDbExecutor dbExecutor) public PermissionRepository(IDbExecutor dbExecutor)
: base(dbExecutor)
{ {
_dbExecutor = dbExecutor;
} }
public DbResult<bool> HasPermission( public DbResult<bool> HasPermission(
int cveUser, int cveUser,
string permissionCode) string permissionCode)
{ {
return ExecuteCheck( return QueryScalarBool(
"dbo.PA_Sis_PermisoCheck", "dbo.PA_Sis_PermisoCheck",
cveUser, cveUser,
null,
command => StoredProcedureCommand.AddInput( command => StoredProcedureCommand.AddInput(
command, command,
"@CodigoPermiso", "@CodigoPermiso",
@@ -34,40 +33,15 @@ namespace SIG.Web.AppCode.Repositories.Security
int cveUser, int cveUser,
string normalizedPageUrl) string normalizedPageUrl)
{ {
return ExecuteCheck( return QueryScalarBool(
"dbo.PA_Sis_PaginaAccessCheck", "dbo.PA_Sis_PaginaAccessCheck",
cveUser, cveUser,
null,
command => StoredProcedureCommand.AddInput( command => StoredProcedureCommand.AddInput(
command, command,
"@PaginaUrl", "@PaginaUrl",
normalizedPageUrl, normalizedPageUrl,
DbType.String)); DbType.String));
} }
private DbResult<bool> ExecuteCheck(
string procedureName,
int cveUser,
Action<IDbCommand> addParameters)
{
return _dbExecutor.Execute(null, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(
command,
procedureName,
cveUser);
addParameters(command);
object value = command.ExecuteScalar();
StoredProcedureCommand.EnsureSuccess(command);
return value != null &&
value != DBNull.Value &&
Convert.ToBoolean(value);
}
});
}
} }
} }

View File

@@ -9,12 +9,12 @@ using SIG.Web.AppCode.Utilities;
namespace SIG.Web.AppCode.Repositories.Security namespace SIG.Web.AppCode.Repositories.Security
{ {
public sealed class UserAdministrationRepository : IUserAdministrationRepository public sealed class UserAdministrationRepository
: RepositoryBase, IUserAdministrationRepository
{ {
private readonly IDbExecutor _db;
public UserAdministrationRepository(IDbExecutor db) public UserAdministrationRepository(IDbExecutor db)
: base(db)
{ {
_db = db;
} }
public DbResult<List<UserAdministrationModel>> ListUsers(string text, int executingUser, string domainName) public DbResult<List<UserAdministrationModel>> ListUsers(string text, int executingUser, string domainName)
@@ -44,11 +44,12 @@ namespace SIG.Web.AppCode.Repositories.Security
public DbResult<int> SaveUser(UserAdministrationModel user, string passwordHash, int executingUser, string domainName) public DbResult<int> SaveUser(UserAdministrationModel user, string passwordHash, int executingUser, string domainName)
{ {
return _db.Execute(domainName, connection => return QueryScalarId(
{ "dbo.PA_Sis_UsuarioSave",
using (IDbCommand command = connection.CreateCommand()) executingUser,
domainName,
command =>
{ {
StoredProcedureCommand.Configure(command, "dbo.PA_Sis_UsuarioSave", executingUser);
StoredProcedureCommand.AddInput(command, "@CveUsuario", user.CveUsuario <= 0 ? (object)null : user.CveUsuario, DbType.Int32); StoredProcedureCommand.AddInput(command, "@CveUsuario", user.CveUsuario <= 0 ? (object)null : user.CveUsuario, DbType.Int32);
StoredProcedureCommand.AddInput(command, "@NombreUsuario", user.NombreUsuario, DbType.String); StoredProcedureCommand.AddInput(command, "@NombreUsuario", user.NombreUsuario, DbType.String);
StoredProcedureCommand.AddInput(command, "@CorreoElectronico", user.CorreoElectronico, DbType.String); StoredProcedureCommand.AddInput(command, "@CorreoElectronico", user.CorreoElectronico, DbType.String);
@@ -56,15 +57,7 @@ namespace SIG.Web.AppCode.Repositories.Security
StoredProcedureCommand.AddInput(command, "@HashContrasena", passwordHash, DbType.String); StoredProcedureCommand.AddInput(command, "@HashContrasena", passwordHash, DbType.String);
StoredProcedureCommand.AddInput(command, "@Activo", user.Activo, DbType.Boolean); StoredProcedureCommand.AddInput(command, "@Activo", user.Activo, DbType.Boolean);
StoredProcedureCommand.AddInput(command, "@DebeCambiarContrasena", user.DebeCambiarContrasena, DbType.Boolean); StoredProcedureCommand.AddInput(command, "@DebeCambiarContrasena", user.DebeCambiarContrasena, DbType.Boolean);
int id; });
using (IDataReader reader = command.ExecuteReader())
{
id = reader.Read() ? reader.GetInt32(0) : 0;
}
StoredProcedureCommand.EnsureSuccess(command);
return id;
}
});
} }
public DbResult<bool> DeleteUser(int userId, int executingUser, string domainName) public DbResult<bool> DeleteUser(int userId, int executingUser, string domainName)
@@ -182,77 +175,5 @@ namespace SIG.Web.AppCode.Repositories.Security
tokenHash, tokenHash,
DbType.StringFixedLength)); DbType.StringFixedLength));
} }
private DbResult<List<T>> QueryList<T>(
string procedure,
int user,
string domain,
System.Action<IDbCommand> parameters)
where T : class, new()
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(command, procedure, user);
if (parameters != null)
{
parameters(command);
}
List<T> value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.ToList<T>();
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
}
private DbResult<T> QueryOne<T>(
string procedure,
int user,
string domain,
System.Action<IDbCommand> parameters)
where T : class, new()
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(command, procedure, user);
if (parameters != null)
{
parameters(command);
}
T value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.ToObject<T>();
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
}
private DbResult<bool> Execute(string procedure, int user, string domain, System.Action<IDbCommand> parameters)
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(command, procedure, user);
if (parameters != null)
{
parameters(command);
}
command.ExecuteNonQuery();
StoredProcedureCommand.EnsureSuccess(command);
return true;
}
});
}
} }
} }

View File

@@ -1,68 +1,69 @@
using System;
using System.Data; using System.Data;
using SIG.Web.AppCode.Contracts.Database; using SIG.Web.AppCode.Contracts.Database;
using SIG.Web.AppCode.Contracts.Security; using SIG.Web.AppCode.Contracts.Security;
using SIG.Web.AppCode.Models.Common; using SIG.Web.AppCode.Models.Common;
using SIG.Web.AppCode.Models.Security; using SIG.Web.AppCode.Models.Security;
using SIG.Web.AppCode.Repositories.Database; using SIG.Web.AppCode.Repositories.Database;
using SIG.Web.AppCode.Utilities;
namespace SIG.Web.AppCode.Repositories.Security namespace SIG.Web.AppCode.Repositories.Security
{ {
public sealed class UserRepository : IUserRepository public sealed class UserRepository
: RepositoryBase, IUserRepository
{ {
private readonly IDbExecutor _dbExecutor;
public UserRepository(IDbExecutor dbExecutor) public UserRepository(IDbExecutor dbExecutor)
: base(dbExecutor)
{ {
_dbExecutor = dbExecutor;
} }
public DbResult<UserModel> ObtenerPorNombreUsuario(string username, string domainName) public DbResult<UserModel> ObtenerPorNombreUsuario(
string username,
string domainName)
{ {
return _dbExecutor.Execute(domainName, connection => return QueryOne<UserModel>(
{ "dbo.PA_Sis_UsuarioGetByName",
using (IDbCommand command = connection.CreateCommand()) 0,
{ domainName,
StoredProcedureCommand.Configure(command, "dbo.PA_Sis_UsuarioGetByName", 0); command => StoredProcedureCommand.AddInput(
StoredProcedureCommand.AddInput(command, "@NombreUsuario", username, DbType.String); command,
"@NombreUsuario",
UserModel user; username,
DbType.String));
using (IDataReader reader = command.ExecuteReader())
{
user = reader.ToObject<UserModel>();
}
StoredProcedureCommand.EnsureSuccess(command);
return user;
}
});
} }
public DbResult<bool> RegisterSuccessfulLogin(int cveUser, string domainName) public DbResult<bool> RegisterSuccessfulLogin(
int cveUser,
string domainName)
{ {
return ExecuteUserUpdate("dbo.PA_Sis_UsuarioLoginSuccessUpdate", cveUser, domainName); return ExecuteUserUpdate(
"dbo.PA_Sis_UsuarioLoginSuccessUpdate",
cveUser,
domainName);
} }
public DbResult<bool> RegisterFailedLogin(int cveUser, string domainName) public DbResult<bool> RegisterFailedLogin(
int cveUser,
string domainName)
{ {
return ExecuteUserUpdate("dbo.PA_Sis_UsuarioLoginFailedUpdate", cveUser, domainName); return ExecuteUserUpdate(
"dbo.PA_Sis_UsuarioLoginFailedUpdate",
cveUser,
domainName);
} }
private DbResult<bool> ExecuteUserUpdate(string procedureName, int cveUser, string domainName) private DbResult<bool> ExecuteUserUpdate(
string procedureName,
int cveUser,
string domainName)
{ {
return _dbExecutor.Execute(domainName, connection => return Execute(
{ procedureName,
using (IDbCommand command = connection.CreateCommand()) cveUser,
{ domainName,
StoredProcedureCommand.Configure(command, procedureName, cveUser); command => StoredProcedureCommand.AddInput(
StoredProcedureCommand.AddInput(command, "@CveUsuario", cveUser, DbType.Int32); command,
command.ExecuteNonQuery(); "@CveUsuario",
StoredProcedureCommand.EnsureSuccess(command); cveUser,
return true; DbType.Int32));
}
});
} }
} }
} }

View File

@@ -6,49 +6,68 @@ using SIG.Web.AppCode.Repositories.Database;
namespace SIG.Web.AppCode.Repositories.Security namespace SIG.Web.AppCode.Repositories.Security
{ {
public sealed class UserSessionRepository : IUserSessionRepository public sealed class UserSessionRepository
: RepositoryBase, IUserSessionRepository
{ {
private readonly IDbExecutor _dbExecutor;
public UserSessionRepository(IDbExecutor dbExecutor) public UserSessionRepository(IDbExecutor dbExecutor)
: base(dbExecutor)
{ {
_dbExecutor = dbExecutor;
} }
public DbResult<bool> StartSession(int cveUser, string sessionToken, string ipAddress, string userAgent, string domainName) public DbResult<bool> StartSession(
int cveUser,
string sessionToken,
string ipAddress,
string userAgent,
string domainName)
{ {
return _dbExecutor.Execute(domainName, connection => return Execute(
{ "dbo.PA_Sis_UsuarioSesionAdd",
using (IDbCommand command = connection.CreateCommand()) cveUser,
domainName,
command =>
{ {
StoredProcedureCommand.Configure(command, "dbo.PA_Sis_UsuarioSesionAdd", cveUser); StoredProcedureCommand.AddInput(
StoredProcedureCommand.AddInput(command, "@CveUsuario", cveUser, DbType.Int32); command,
StoredProcedureCommand.AddInput(command, "@TokenSesion", sessionToken, DbType.String); "@CveUsuario",
StoredProcedureCommand.AddInput(command, "@DireccionIP", ipAddress, DbType.String); cveUser,
StoredProcedureCommand.AddInput(command, "@AgenteUsuario", userAgent, DbType.String); DbType.Int32);
StoredProcedureCommand.AddInput(command, "@NombreDominio", domainName, DbType.String); StoredProcedureCommand.AddInput(
command,
command.ExecuteNonQuery(); "@TokenSesion",
StoredProcedureCommand.EnsureSuccess(command); sessionToken,
return true; DbType.String);
} StoredProcedureCommand.AddInput(
}); command,
"@DireccionIP",
ipAddress,
DbType.String);
StoredProcedureCommand.AddInput(
command,
"@AgenteUsuario",
userAgent,
DbType.String);
StoredProcedureCommand.AddInput(
command,
"@NombreDominio",
domainName,
DbType.String);
});
} }
public DbResult<bool> EndSession(string sessionToken, string domainName) public DbResult<bool> EndSession(
string sessionToken,
string domainName)
{ {
return _dbExecutor.Execute(domainName, connection => return Execute(
{ "dbo.PA_Sis_UsuarioSesionEnd",
using (IDbCommand command = connection.CreateCommand()) 0,
{ domainName,
StoredProcedureCommand.Configure(command, "dbo.PA_Sis_UsuarioSesionEnd", 0); command => StoredProcedureCommand.AddInput(
StoredProcedureCommand.AddInput(command, "@TokenSesion", sessionToken, DbType.String); command,
"@TokenSesion",
command.ExecuteNonQuery(); sessionToken,
StoredProcedureCommand.EnsureSuccess(command); DbType.String));
return true;
}
});
} }
} }
} }

View File

@@ -10,13 +10,12 @@ using SIG.Web.AppCode.Utilities;
namespace SIG.Web.AppCode.Repositories.Tramites namespace SIG.Web.AppCode.Repositories.Tramites
{ {
public sealed class TramiteCatalogRepository : ITramiteCatalogRepository public sealed class TramiteCatalogRepository
: RepositoryBase, ITramiteCatalogRepository
{ {
private readonly IDbExecutor _db;
public TramiteCatalogRepository(IDbExecutor db) public TramiteCatalogRepository(IDbExecutor db)
: base(db)
{ {
_db = db;
} }
public DbResult<List<EstatusSolicitudModel>> ListEstatus(string texto, bool incluirInactivos, int usuario, string dominio) public DbResult<List<EstatusSolicitudModel>> ListEstatus(string texto, bool incluirInactivos, int usuario, string dominio)
@@ -321,20 +320,17 @@ namespace SIG.Web.AppCode.Repositories.Tramites
int usuario, int usuario,
string dominio) string dominio)
{ {
return _db.Execute(dominio, connection => return Execute(
{ "dbo.PA_Tra_CatalogoOrdenMove",
using (IDbCommand command = connection.CreateCommand()) usuario,
dominio,
command =>
{ {
StoredProcedureCommand.Configure(command, "dbo.PA_Tra_CatalogoOrdenMove", usuario);
Add(command, "@Entidad", GetOrderEntityName(entity), DbType.String); Add(command, "@Entidad", GetOrderEntityName(entity), DbType.String);
Add(command, "@CveRegistro", id, DbType.Int32); Add(command, "@CveRegistro", id, DbType.Int32);
Add(command, "@CveReferencia", referenceId, DbType.Int32); Add(command, "@CveReferencia", referenceId, DbType.Int32);
Add(command, "@ColocarDespues", placeAfter, DbType.Boolean); Add(command, "@ColocarDespues", placeAfter, DbType.Boolean);
command.ExecuteNonQuery(); });
StoredProcedureCommand.EnsureSuccess(command);
return true;
}
});
} }
private static string GetOrderEntityName(TramiteCatalogOrderEntity entity) private static string GetOrderEntityName(TramiteCatalogOrderEntity entity)
@@ -356,89 +352,35 @@ namespace SIG.Web.AppCode.Repositories.Tramites
} }
} }
private DbResult<List<T>> QueryList<T>(string procedure, int user, string domain, Action<IDbCommand> parameters) private DbResult<int> Save(
where T : class, new() string procedure,
int user,
string domain,
Action<IDbCommand> parameters)
{ {
return _db.Execute(domain, connection => return QueryScalarId(
{ procedure,
using (IDbCommand command = connection.CreateCommand()) user,
{ domain,
StoredProcedureCommand.Configure(command, procedure, user); parameters);
if (parameters != null)
{
parameters(command);
}
List<T> value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.ToList<T>();
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
} }
private DbResult<T> QueryOne<T>(string procedure, int user, string domain, Action<IDbCommand> parameters) private DbResult<bool> Delete(
where T : class, new() string procedure,
string parameterName,
int id,
int user,
string domain)
{ {
return _db.Execute(domain, connection => return Execute(
{ procedure,
using (IDbCommand command = connection.CreateCommand()) user,
{ domain,
StoredProcedureCommand.Configure(command, procedure, user); command => Add(
parameters(command); command,
parameterName,
T value; id,
using (IDataReader reader = command.ExecuteReader()) DbType.Int32));
{
value = reader.ToObject<T>();
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
}
private DbResult<int> Save(string procedure, int user, string domain, Action<IDbCommand> parameters)
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(command, procedure, user);
parameters(command);
int value;
using (IDataReader reader = command.ExecuteReader())
{
value = reader.Read()
? Convert.ToInt32(reader.GetValue(0))
: 0;
}
StoredProcedureCommand.EnsureSuccess(command);
return value;
}
});
}
private DbResult<bool> Delete(string procedure, string parameterName, int id, int user, string domain)
{
return _db.Execute(domain, connection =>
{
using (IDbCommand command = connection.CreateCommand())
{
StoredProcedureCommand.Configure(command, procedure, user);
Add(command, parameterName, id, DbType.Int32);
command.ExecuteNonQuery();
StoredProcedureCommand.EnsureSuccess(command);
return true;
}
});
} }
private static object NullableId(int value) private static object NullableId(int value)

View File

@@ -51,13 +51,48 @@ namespace SIG.Web.AppCode.Services.Fraccionamientos
Directory.CreateDirectory(directory); Directory.CreateDirectory(directory);
} }
using (FileStream destination = new FileStream( string temporaryPath = Path.Combine(
path, directory,
FileMode.Create, "." + Path.GetFileName(path) + "." +
FileAccess.Write, Guid.NewGuid().ToString("N") + ".tmp");
FileShare.None))
try
{ {
source.CopyTo(destination); if (source.CanSeek)
{
source.Position = 0;
}
using (FileStream destination = new FileStream(
temporaryPath,
FileMode.CreateNew,
FileAccess.Write,
FileShare.None))
{
source.CopyTo(destination);
destination.Flush();
}
if (File.Exists(path))
{
File.Replace(
temporaryPath,
path,
null);
}
else
{
File.Move(
temporaryPath,
path);
}
}
finally
{
if (File.Exists(temporaryPath))
{
File.Delete(temporaryPath);
}
} }
} }
@@ -70,6 +105,16 @@ namespace SIG.Web.AppCode.Services.Fraccionamientos
FileShare.Read); FileShare.Read);
} }
public void Delete(FraccionamientoGisContextModel context)
{
string path = GetPhysicalPath(context);
if (File.Exists(path))
{
File.Delete(path);
}
}
private static void ValidateContext(FraccionamientoGisContextModel context) private static void ValidateContext(FraccionamientoGisContextModel context)
{ {
if (context == null) if (context == null)

View File

@@ -0,0 +1,439 @@
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using SIG.Web.AppCode.Contracts.Fraccionamientos;
using SIG.Web.AppCode.Infrastructure.Transactions;
using SIG.Web.AppCode.Models.Common;
using SIG.Web.AppCode.Models.Fraccionamientos;
using SIG.Web.AppCode.Services.Logging;
namespace SIG.Web.AppCode.Services.Fraccionamientos
{
public sealed class FraccionamientoGisService : IFraccionamientoGisService
{
private const string GisExtension = ".gis";
private const string GisContentType = "application/json";
private const long MaxFileSize = 30L * 1024L * 1024L;
private readonly IFraccionamientoGisRepository _repository;
private readonly IFraccionamientoGisFileStore _fileStore;
public FraccionamientoGisService(
IFraccionamientoGisRepository repository,
IFraccionamientoGisFileStore fileStore)
{
if (repository == null)
{
throw new ArgumentNullException("repository");
}
if (fileStore == null)
{
throw new ArgumentNullException("fileStore");
}
_repository = repository;
_fileStore = fileStore;
}
public DbResult<FraccionamientoGisViewModel> Get(
int stageId,
int executingUser,
string domainName)
{
if (stageId <= 0)
{
return Fail<FraccionamientoGisViewModel>(
"Seleccione una etapa válida.");
}
DbResult<FraccionamientoGisContextModel> contextResult =
_repository.GetContext(
stageId,
executingUser,
domainName);
if (!contextResult.Success || contextResult.Data == null)
{
return CopyFailure<FraccionamientoGisContextModel, FraccionamientoGisViewModel>(
contextResult,
"No fue posible obtener el contexto GIS de la etapa.");
}
DbResult<List<FraccionamientoGisLotLinkModel>> linksResult =
_repository.ListLinks(
stageId,
executingUser,
domainName);
if (!linksResult.Success)
{
return CopyFailure<List<FraccionamientoGisLotLinkModel>, FraccionamientoGisViewModel>(
linksResult,
"No fue posible obtener los lotes de la etapa.");
}
try
{
bool hasFile = _fileStore.Exists(contextResult.Data);
return DbResult<FraccionamientoGisViewModel>.Ok(
new FraccionamientoGisViewModel
{
Contexto = contextResult.Data,
Lotes = linksResult.Data ??
new List<FraccionamientoGisLotLinkModel>(),
TieneArchivo = hasFile,
NombreArchivo = hasFile
? Path.GetFileName(
_fileStore.GetPhysicalPath(contextResult.Data))
: string.Empty,
FechaArchivo = hasFile
? (DateTime?)File.GetLastWriteTime(
_fileStore.GetPhysicalPath(contextResult.Data))
: null
});
}
catch (Exception ex)
{
const string userMessage =
"No fue posible consultar el archivo GIS; favor de contactar a Sistemas.";
ExceptionLogger.Log(
ex,
"FraccionamientoGisService.Get",
userMessage);
return DbResult<FraccionamientoGisViewModel>.Fail(
userMessage,
ex.Message,
ex);
}
}
public DbResult<FraccionamientoGisSaveResultModel> Save(
int stageId,
string originalFileName,
Stream content,
long contentLength,
IList<FraccionamientoGisLotLinkModel> links,
int executingUser,
string domainName)
{
if (stageId <= 0)
{
return Fail<FraccionamientoGisSaveResultModel>(
"Seleccione una etapa válida.");
}
string validation = ValidateLinks(links);
if (!string.IsNullOrWhiteSpace(validation))
{
return Fail<FraccionamientoGisSaveResultModel>(validation);
}
bool hasUploadedFile = content != null && contentLength > 0;
if (hasUploadedFile)
{
if (!string.Equals(
Path.GetExtension(originalFileName),
GisExtension,
StringComparison.OrdinalIgnoreCase))
{
return Fail<FraccionamientoGisSaveResultModel>(
"El archivo seleccionado debe tener extensión .gis.");
}
if (contentLength > MaxFileSize)
{
return Fail<FraccionamientoGisSaveResultModel>(
"El archivo GIS no puede exceder 30 MB.");
}
}
DbResult<FraccionamientoGisContextModel> contextResult =
_repository.GetContext(
stageId,
executingUser,
domainName);
if (!contextResult.Success || contextResult.Data == null)
{
return CopyFailure<FraccionamientoGisContextModel, FraccionamientoGisSaveResultModel>(
contextResult,
"No fue posible obtener el contexto GIS de la etapa.");
}
FraccionamientoGisContextModel gisContext = contextResult.Data;
bool hadFile;
try
{
hadFile = _fileStore.Exists(gisContext);
}
catch (Exception ex)
{
return FileFailure<FraccionamientoGisSaveResultModel>(
ex,
"FraccionamientoGisService.Save.Exists");
}
if (!hasUploadedFile && !hadFile)
{
return Fail<FraccionamientoGisSaveResultModel>(
"Seleccione un archivo .gis antes de guardar.");
}
byte[] previousFile = null;
if (hasUploadedFile && hadFile)
{
try
{
using (Stream previous = _fileStore.OpenRead(gisContext))
using (var backup = new MemoryStream())
{
previous.CopyTo(backup);
previousFile = backup.ToArray();
}
}
catch (Exception ex)
{
return FileFailure<FraccionamientoGisSaveResultModel>(
ex,
"FraccionamientoGisService.Save.Backup");
}
}
bool fileWasWritten = false;
try
{
using (var transaction = new TransactionLogic())
{
DbResult<bool> saveLinksResult =
_repository.SaveLinks(
stageId,
links,
executingUser,
domainName);
if (!saveLinksResult.Success)
{
return DbResult<FraccionamientoGisSaveResultModel>.Fail(
saveLinksResult.UserMessage,
saveLinksResult.TechnicalMessage,
saveLinksResult.Exception);
}
if (hasUploadedFile)
{
_fileStore.Save(gisContext, content);
fileWasWritten = true;
}
transaction.Commit();
}
bool hasFile = _fileStore.Exists(gisContext);
return DbResult<FraccionamientoGisSaveResultModel>.Ok(
new FraccionamientoGisSaveResultModel
{
CveFraccionamientoEtapa = stageId,
VinculosGuardados = links.Count,
ArchivoGuardado = hasUploadedFile,
TieneArchivo = hasFile,
NombreArchivo = hasFile
? Path.GetFileName(
_fileStore.GetPhysicalPath(gisContext))
: string.Empty
});
}
catch (Exception ex)
{
if (fileWasWritten)
{
RestorePreviousFile(
gisContext,
hadFile,
previousFile);
}
return FileFailure<FraccionamientoGisSaveResultModel>(
ex,
"FraccionamientoGisService.Save");
}
}
public DbResult<FraccionamientoGisFileModel> OpenFile(
int stageId,
int executingUser,
string domainName)
{
if (stageId <= 0)
{
return Fail<FraccionamientoGisFileModel>(
"Seleccione una etapa válida.");
}
DbResult<FraccionamientoGisContextModel> contextResult =
_repository.GetContext(
stageId,
executingUser,
domainName);
if (!contextResult.Success || contextResult.Data == null)
{
return CopyFailure<FraccionamientoGisContextModel, FraccionamientoGisFileModel>(
contextResult,
"No fue posible obtener el contexto GIS de la etapa.");
}
try
{
if (!_fileStore.Exists(contextResult.Data))
{
return Fail<FraccionamientoGisFileModel>(
"No se encontró el archivo GIS de la etapa.");
}
return DbResult<FraccionamientoGisFileModel>.Ok(
new FraccionamientoGisFileModel
{
NombreArchivo = Path.GetFileName(
_fileStore.GetPhysicalPath(contextResult.Data)),
ContentType = GisContentType,
Content = _fileStore.OpenRead(contextResult.Data)
});
}
catch (Exception ex)
{
return FileFailure<FraccionamientoGisFileModel>(
ex,
"FraccionamientoGisService.OpenFile");
}
}
private void RestorePreviousFile(
FraccionamientoGisContextModel context,
bool hadFile,
byte[] previousFile)
{
try
{
if (hadFile && previousFile != null)
{
using (var backup = new MemoryStream(previousFile, false))
{
_fileStore.Save(context, backup);
}
}
else
{
_fileStore.Delete(context);
}
}
catch (Exception restoreException)
{
ExceptionLogger.Log(
restoreException,
"FraccionamientoGisService.RestorePreviousFile",
"No fue posible restaurar el archivo GIS después de un error.");
}
}
private static string ValidateLinks(
IList<FraccionamientoGisLotLinkModel> links)
{
if (links == null || links.Count == 0)
{
return "Debe vincular los polígonos del GIS con los lotes antes de guardar.";
}
var lotIds = new HashSet<int>();
var polygonKeys = new HashSet<string>(StringComparer.Ordinal);
foreach (FraccionamientoGisLotLinkModel link in links)
{
if (link == null || link.CveFraccionamientoLote <= 0)
{
return "Existe un vínculo con un lote inválido.";
}
string key = string.IsNullOrWhiteSpace(link.GISPoligonoClave)
? null
: link.GISPoligonoClave.Trim();
if (key == null)
{
return "Existe al menos un polígono sin una clave GIS válida.";
}
if (key.Length > 100)
{
return "Una clave de polígono GIS excede 100 caracteres.";
}
if (!lotIds.Add(link.CveFraccionamientoLote))
{
return "Un lote no puede vincularse con más de un polígono.";
}
if (!polygonKeys.Add(key))
{
return "Un polígono no puede vincularse con más de un lote.";
}
link.GISPoligonoClave = key;
}
return null;
}
private static DbResult<TTarget> CopyFailure<TSource, TTarget>(
DbResult<TSource> source,
string fallbackMessage)
{
if (source == null)
{
return Fail<TTarget>(fallbackMessage);
}
return DbResult<TTarget>.Fail(
string.IsNullOrWhiteSpace(source.UserMessage)
? fallbackMessage
: source.UserMessage,
source.TechnicalMessage,
source.Exception);
}
private static DbResult<T> FileFailure<T>(
Exception ex,
string origin)
{
const string userMessage =
"No fue posible procesar el archivo GIS; favor de contactar a Sistemas.";
ExceptionLogger.Log(
ex,
origin,
userMessage);
return DbResult<T>.Fail(
userMessage,
ex.Message,
ex);
}
private static DbResult<T> Fail<T>(string message)
{
return DbResult<T>.Fail(
message,
message,
null);
}
}
}

View File

@@ -12,6 +12,9 @@
<link href='<%= ResolveUrl("~/Styles/CatalogosTramites.css") %>' <link href='<%= ResolveUrl("~/Styles/CatalogosTramites.css") %>'
rel="stylesheet" rel="stylesheet"
type="text/css" /> type="text/css" />
<link href='<%= ResolveUrl("~/Styles/fraccionamiento-gis.css?v=20260818-1") %>'
rel="stylesheet"
type="text/css" />
</asp:Content> </asp:Content>
<asp:Content ID="ContentActions" ContentPlaceHolderID="A" runat="server"> <asp:Content ID="ContentActions" ContentPlaceHolderID="A" runat="server">
@@ -949,10 +952,12 @@
<div class="modal-body"> <div class="modal-body">
<asp:Label ID="LblStageGisMessage" <asp:Label ID="LblStageGisMessage"
ClientIDMode="Static"
runat="server" runat="server"
CssClass="alert alert-danger sig-modal-message sig-stage-gis-message" CssClass="alert alert-danger sig-modal-message sig-stage-gis-message"
role="alert" role="alert"
Visible="false" /> Visible="true"
style="display:none;" />
<div class="fraction-selected-stage"> <div class="fraction-selected-stage">
<span>Etapa</span> <span>Etapa</span>
@@ -962,17 +967,39 @@
</strong> </strong>
</div> </div>
<div class="form-group"> <asp:HiddenField ID="HdStageGisId"
<label for="FileStageGis">Archivo GIS *</label> ClientIDMode="Static"
<asp:FileUpload ID="FileStageGis" runat="server" />
runat="server"
ClientIDMode="Static" <div class="sig-gis-layout">
CssClass="form-control" <div class="sig-gis-panel sig-gis-panel-files">
accept=".gis" /> <div class="form-group">
<span class="help-block"> <label>Archivo GIS</label>
Seleccione un archivo con extensión .gis. <input
El nombre se asignará automáticamente al guardar. type="hidden"
</span> id="TxtGISLocal"
class="ADSdropzoneLocal"
data-maxFile="1"
data-maxfilesize="30"
data-acceptedfiles=".gis"
data-message="Arrastra aquí un archivo .gis o haz clic para seleccionarlo." />
<span class="help-block">
El archivo permanece local hasta que presione Guardar GIS.
Si ya existe un GIS puede conservarlo y modificar únicamente los vínculos.
</span>
</div>
<div id="GisVinculosStatus"
class="sig-gis-link-status"></div>
<div id="GisVinculos"
class="sig-gis-links"></div>
</div>
<div class="sig-gis-panel sig-gis-panel-map">
<div id="MapGIS"
class="sig-gis-map"></div>
</div>
</div> </div>
</div> </div>
@@ -983,18 +1010,27 @@
Cancelar Cancelar
</button> </button>
<asp:Button ID="BtnSaveStageGis" <button type="button"
id="BtnSaveStageGis"
class="btn blue">
<i class="fa fa-save"></i>
Guardar GIS
</button>
<asp:Button ID="BtnRefreshStageGis"
ClientIDMode="Static"
runat="server" runat="server"
CssClass="btn blue" CssClass="hidden"
Text="Guardar GIS"
CausesValidation="false" CausesValidation="false"
OnClick="BtnSaveStageGis_Click" /> UseSubmitBehavior="false"
OnClick="BtnRefreshStageGis_Click" />
</div> </div>
</div> </div>
</ContentTemplate> </ContentTemplate>
<Triggers> <Triggers>
<asp:PostBackTrigger <asp:AsyncPostBackTrigger
ControlID="BtnSaveStageGis" /> ControlID="BtnRefreshStageGis"
EventName="Click" />
</Triggers> </Triggers>
</asp:UpdatePanel> </asp:UpdatePanel>
</div> </div>
@@ -1278,7 +1314,21 @@
<asp:Content ID="ContentScripts" ContentPlaceHolderID="J" runat="server"> <asp:Content ID="ContentScripts" ContentPlaceHolderID="J" runat="server">
<script src='<%= ResolveUrl("~/Scripts/CatalogosTramites.js") %>' <script src='<%= ResolveUrl("~/Scripts/CatalogosTramites.js") %>'
type="text/javascript"></script> type="text/javascript"></script>
<script src='<%= ResolveUrl("~/Scripts/fraccionamiento-gis.js?v=20260818-1") %>'
type="text/javascript"></script>
<script> <script>
window.FraccionamientoGISOptions = {
modalId: 'ModalStageGis',
stageInputId: 'HdStageGisId',
fileInputId: 'TxtGISLocal',
mapId: 'MapGIS',
linksTableId: 'GisVinculos',
statusId: 'GisVinculosStatus',
saveButtonId: 'BtnSaveStageGis',
refreshButtonId: 'BtnRefreshStageGis',
handlerUrl: '<%= ResolveUrl("~/Pages/Fraccionamientos/FraccionamientoGis.ashx") %>'
};
window.SIGDetail = window.SIGDetail || {}; window.SIGDetail = window.SIGDetail || {};
window.SIGDetail.initialize = function (root) { window.SIGDetail.initialize = function (root) {

View File

@@ -450,62 +450,18 @@ namespace SIG.Web.Pages.Fraccionamientos
OpenStageGisModal(); OpenStageGisModal();
} }
protected void BtnSaveStageGis_Click( protected void BtnRefreshStageGis_Click(
object sender, object sender,
EventArgs e) EventArgs e)
{ {
if (CveFraccionamientoEtapaGisActual <= 0)
{
ShowStageGisValidation(
"Seleccione nuevamente la etapa del GIS.");
return;
}
if (!FileStageGis.HasFile ||
FileStageGis.PostedFile == null ||
FileStageGis.PostedFile.ContentLength <= 0)
{
ShowStageGisValidation(
"Seleccione un archivo GIS válido.");
return;
}
DbResult<ClienteDocumentoArchivoModel> fileResult =
AppServices.ClienteDocumentoService.SaveStageGis(
CveFraccionamientoActual,
CveFraccionamientoEtapaGisActual,
FileStageGis.PostedFile.FileName,
FileStageGis.PostedFile.InputStream,
FileStageGis.PostedFile.ContentLength,
CurrentUser.CveUsuario,
CurrentUser.NombreDominio);
if (!fileResult.Success)
{
ShowStageGisModal();
Alert(fileResult.UserMessage, TipoMensaje.MsgError);
return;
}
DbResult<FraccionamientoEtapaGisModel> result =
AppServices.FraccionamientoService.SaveStageGis(
CveFraccionamientoEtapaGisActual,
CurrentUser.CveUsuario,
CurrentUser.NombreDominio);
if (!result.Success)
{
ShowStageGisModal();
Alert(result.UserMessage, TipoMensaje.MsgError);
return;
}
HideStageGisMessage(); HideStageGisMessage();
BindSelectedStageLotsContext(); BindSelectedStageLotsContext();
UpDetailTabs.Update(); UpDetailTabs.Update();
UpStageGisModal.Update();
HideStageGisModal(); HideStageGisModal();
RefreshBitacoraDetalle(); Alert(
Alert("GIS guardado correctamente.", TipoMensaje.ToastExito); "GIS y vínculos guardados correctamente.",
TipoMensaje.ToastExito);
} }
protected void BtnClearStageLots_Click( protected void BtnClearStageLots_Click(
@@ -967,57 +923,45 @@ namespace SIG.Web.Pages.Fraccionamientos
return; return;
} }
DbResult<ClienteDocumentoEtapaContextoModel> stageResult = DbResult<FraccionamientoGisViewModel> gisResult =
AppServices.ClienteDocumentoService.GetStageContext( AppServices.FraccionamientoGisService.Get(
stageId, stageId,
CurrentUser.CveUsuario, CurrentUser.CveUsuario,
CurrentUser.NombreDominio); CurrentUser.NombreDominio);
if (!stageResult.Success || if (!gisResult.Success ||
stageResult.Data == null || gisResult.Data == null ||
stageResult.Data.CveFraccionamiento != CveFraccionamientoActual) gisResult.Data.Contexto == null)
{ {
Alert( Alert(
stageResult.Success gisResult.Success
? "La etapa no pertenece al fraccionamiento actual." ? "No fue posible obtener el contexto GIS de la etapa."
: stageResult.UserMessage, : gisResult.UserMessage,
stageResult.Success gisResult.Success
? TipoMensaje.MsgAdvertencia ? TipoMensaje.MsgAdvertencia
: TipoMensaje.MsgError); : TipoMensaje.MsgError);
return; return;
} }
DbResult<FraccionamientoEtapaGisModel> gisResult = FraccionamientoGisViewModel gis = gisResult.Data;
AppServices.FraccionamientoService.GetStageGis(
stageId,
CurrentUser.CveUsuario,
CurrentUser.NombreDominio);
if (!gisResult.Success) if (gis.Contexto.CveFraccionamiento != CveFraccionamientoActual)
{
Alert(gisResult.UserMessage, TipoMensaje.MsgError);
return;
}
FraccionamientoEtapaGisModel gis = gisResult.Data;
if (gis != null &&
(gis.CveFraccionamientoEtapa != stageId ||
gis.CveFraccionamiento != CveFraccionamientoActual))
{ {
Alert( Alert(
"El GIS consultado no pertenece al fraccionamiento actual.", "La etapa no pertenece al fraccionamiento actual.",
TipoMensaje.MsgAdvertencia); TipoMensaje.MsgAdvertencia);
return; return;
} }
HideStageGisMessage(); HideStageGisMessage();
CveFraccionamientoEtapaGisActual = stageId; CveFraccionamientoEtapaGisActual = stageId;
LitStageGisModalTitle.Text = gis == null HdStageGisId.Value = stageId.ToString(
? "Agregar GIS" CultureInfo.InvariantCulture);
: "Administrar GIS"; LitStageGisModalTitle.Text = gis.TieneArchivo
? "Administrar GIS"
: "Agregar GIS";
LitStageGisStageName.Text = EncodeDisplayValue( LitStageGisStageName.Text = EncodeDisplayValue(
stageResult.Data.Etapa); gis.Contexto.Etapa);
UpStageGisModal.Update(); UpStageGisModal.Update();
ShowStageGisModal(); ShowStageGisModal();
} }
@@ -1449,6 +1393,7 @@ namespace SIG.Web.Pages.Fraccionamientos
LitStageGisName.Text = string.Empty; LitStageGisName.Text = string.Empty;
LitStageGisUpdatedAt.Text = string.Empty; LitStageGisUpdatedAt.Text = string.Empty;
LnkStageGisOpen.NavigateUrl = string.Empty; LnkStageGisOpen.NavigateUrl = string.Empty;
HdStageGisId.Value = string.Empty;
GvLots.DataSource = new List<FraccionamientoLoteModel>(); GvLots.DataSource = new List<FraccionamientoLoteModel>();
GvLots.DataBind(); GvLots.DataBind();
} }
@@ -1462,28 +1407,29 @@ namespace SIG.Web.Pages.Fraccionamientos
LitStageGisUpdatedAt.Text = string.Empty; LitStageGisUpdatedAt.Text = string.Empty;
LnkStageGisOpen.NavigateUrl = string.Empty; LnkStageGisOpen.NavigateUrl = string.Empty;
DbResult<FraccionamientoEtapaGisModel> result = DbResult<FraccionamientoGisViewModel> result =
AppServices.FraccionamientoService.GetStageGis( AppServices.FraccionamientoGisService.Get(
stageId, stageId,
CurrentUser.CveUsuario, CurrentUser.CveUsuario,
CurrentUser.NombreDominio); CurrentUser.NombreDominio);
if (!result.Success) if (!result.Success ||
result.Data == null ||
result.Data.Contexto == null)
{ {
Alert(result.UserMessage, TipoMensaje.MsgError); Alert(
result.Success
? "No fue posible obtener el contexto GIS de la etapa."
: result.UserMessage,
result.Success
? TipoMensaje.MsgAdvertencia
: TipoMensaje.MsgError);
return; return;
} }
FraccionamientoEtapaGisModel gis = result.Data; FraccionamientoGisViewModel gis = result.Data;
if (gis == null) if (gis.Contexto.CveFraccionamiento != CveFraccionamientoActual)
{
PhStageGisMissing.Visible = true;
return;
}
if (gis.CveFraccionamientoEtapa != stageId ||
gis.CveFraccionamiento != CveFraccionamientoActual)
{ {
Alert( Alert(
"El GIS consultado no pertenece al fraccionamiento actual.", "El GIS consultado no pertenece al fraccionamiento actual.",
@@ -1491,38 +1437,30 @@ namespace SIG.Web.Pages.Fraccionamientos
return; return;
} }
DbResult<ClienteDocumentoArchivoModel> fileResult = if (!gis.TieneArchivo)
AppServices.ClienteDocumentoService.GetStageGis(
stageId,
CurrentUser.CveUsuario,
CurrentUser.NombreDominio);
if (!fileResult.Success || fileResult.Data == null)
{ {
PhStageGisMissing.Visible = true; PhStageGisMissing.Visible = true;
if (fileResult.Exception != null)
{
Alert(fileResult.UserMessage, TipoMensaje.MsgError);
}
return; return;
} }
PhStageGisExistingActions.Visible = true; PhStageGisExistingActions.Visible = true;
LitStageGisName.Text = EncodeDisplayValue( LitStageGisName.Text = EncodeDisplayValue(
fileResult.Data.NombreArchivo); gis.NombreArchivo);
DateTime updatedAt = gis.FechaModificacion ?? gis.FechaAlta; if (gis.FechaArchivo.HasValue)
LitStageGisUpdatedAt.Text = Server.HtmlEncode( {
"Actualizado " + updatedAt.ToString( LitStageGisUpdatedAt.Text = Server.HtmlEncode(
"dd/MM/yyyy HH:mm", "Actualizado " + gis.FechaArchivo.Value.ToString(
CultureInfo.CurrentCulture)); "dd/MM/yyyy HH:mm",
CultureInfo.CurrentCulture));
}
PnlStageGisExisting.Visible = true; PnlStageGisExisting.Visible = true;
LnkStageGisOpen.NavigateUrl = ResolveUrl( LnkStageGisOpen.NavigateUrl = ResolveUrl(
"~/Pages/Fraccionamientos/FraccionamientoGis.ashx?etapa=" + "~/Pages/Fraccionamientos/FraccionamientoGis.ashx" +
stageId.ToString(CultureInfo.InvariantCulture)); "?metodo=File&etapa=" +
stageId.ToString(CultureInfo.InvariantCulture) +
"&download=1");
} }
private void EditLot(int lotId) private void EditLot(int lotId)
@@ -1937,13 +1875,15 @@ namespace SIG.Web.Pages.Fraccionamientos
LblStageGisMessage.Text = Server.HtmlEncode( LblStageGisMessage.Text = Server.HtmlEncode(
message ?? string.Empty); message ?? string.Empty);
LblStageGisMessage.Visible = true; LblStageGisMessage.Visible = true;
LblStageGisMessage.Style["display"] = "block";
UpStageGisModal.Update(); UpStageGisModal.Update();
ShowStageGisModal(); ShowStageGisModal();
} }
private void HideStageGisMessage() private void HideStageGisMessage()
{ {
LblStageGisMessage.Visible = false; LblStageGisMessage.Visible = true;
LblStageGisMessage.Style["display"] = "none";
LblStageGisMessage.Text = string.Empty; LblStageGisMessage.Text = string.Empty;
} }

View File

@@ -559,14 +559,14 @@ namespace SIG.Web.Pages.Fraccionamientos
protected global::System.Web.UI.WebControls.Literal LitStageGisStageName; protected global::System.Web.UI.WebControls.Literal LitStageGisStageName;
/// <summary> /// <summary>
/// FileStageGis control. /// HdStageGisId control.
/// </summary> /// </summary>
protected global::System.Web.UI.WebControls.FileUpload FileStageGis; protected global::System.Web.UI.WebControls.HiddenField HdStageGisId;
/// <summary> /// <summary>
/// BtnSaveStageGis control. /// BtnRefreshStageGis control.
/// </summary> /// </summary>
protected global::System.Web.UI.WebControls.Button BtnSaveStageGis; protected global::System.Web.UI.WebControls.Button BtnRefreshStageGis;
/// <summary> /// <summary>
/// UpLotsModal control. /// UpLotsModal control.

View File

@@ -1,4 +1,4 @@
/* /*
* custom.js * custom.js
* Cleaned for the new C# WebForms project. * Cleaned for the new C# WebForms project.
* Notes: * Notes:
@@ -1460,7 +1460,7 @@ function ADDropzone(txtid) {
//initialize variables //initialize variables
//var txt; //var txt;
var domain = window.location.origin; var domain = window.location.origin;
this.txt = $('#' + txtid); if (txt.val() == '') { txt.val('[]'); } var txt = $('#' + txtid); if (txt.val() == '') { txt.val('[]'); }
if (txt.data('loaded') == '1') { } if (txt.data('loaded') == '1') { }
else { else {
@@ -1606,6 +1606,155 @@ function loadAdDropzone() {
} }
}); });
} }
function ADDropzoneLocal(txtid) {
var txt = $('#' + txtid);
if (!txt.length) {
return null;
}
if (typeof Dropzone === 'undefined') {
console.error('Dropzone no está disponible para #' + txtid);
return null;
}
if (txt.attr('data-sig-dropzone-local-initialized') === '1') {
return window.ADSLocalDropzone
? window.ADSLocalDropzone.instance(txtid)
: null;
}
var maxFilesize = Number(txt.attr('data-maxfilesize')) || 30;
var maxFile = parseInt(
txt.attr('data-maxFile') || txt.attr('data-maxfile'),
10);
var acceptedFiles = txt.attr('data-acceptedfiles') || null;
var message = txt.attr('data-message') ||
'Arrastra un archivo aquí o haz clic para seleccionarlo.';
var appendId = txt.attr('data-append');
var dropId = txtid + '-drop';
var existing = $('#' + dropId);
if (existing.length) {
existing.remove();
}
var mydiv = $(
'<div id="' + dropId + '" class="addropzone ADSdropzoneLocalContainer">' +
' <div class="dz-message">' + $('<div/>').text(message).html() + '</div>' +
'</div>');
if (appendId && $('#' + appendId).length) {
$('#' + appendId).empty().append(mydiv);
} else {
txt.after(mydiv);
}
var instance;
try {
instance = new Dropzone('#' + dropId, {
url: window.location.href,
autoProcessQueue: false,
uploadMultiple: false,
parallelUploads: 1,
maxFiles: isNaN(maxFile) || maxFile <= 0 ? null : maxFile,
maxFilesize: maxFilesize,
acceptedFiles: acceptedFiles,
addRemoveLinks: true,
dictRemoveFile: 'Quitar archivo',
dictInvalidFileType: 'El tipo de archivo no está permitido.',
dictFileTooBig: 'El archivo excede el tamaño permitido.',
dictMaxFilesExceeded: 'Se excedió el número máximo de archivos.',
init: function () {
var dz = this;
dz.on('addedfile', function (file) {
if (dz.options.maxFiles && dz.files.length > dz.options.maxFiles) {
dz.removeFile(file);
return;
}
var reader = new FileReader();
reader.onload = function (event) {
txt.trigger('adsdropzone:fileadded', [
file,
event.target.result,
dz
]);
};
reader.onerror = function () {
dz.removeFile(file);
txt.trigger('adsdropzone:fileerror', [
file,
'No fue posible leer el archivo seleccionado.',
dz
]);
};
reader.readAsText(file);
});
dz.on('removedfile', function (file) {
txt.trigger('adsdropzone:fileremoved', [file, dz]);
});
dz.on('error', function (file, errorMessage) {
txt.trigger('adsdropzone:fileerror', [
file,
typeof errorMessage === 'string'
? errorMessage
: 'El archivo seleccionado no es válido.',
dz
]);
});
}
});
} catch (ex) {
mydiv.remove();
txt.removeAttr('data-sig-dropzone-local-initialized');
console.error('ADDropzoneLocal Error:', ex);
return null;
}
txt.attr('data-sig-dropzone-local-initialized', '1');
window.ADSLocalDropzone = window.ADSLocalDropzone || {};
window.ADSLocalDropzone.instances =
window.ADSLocalDropzone.instances || {};
window.ADSLocalDropzone.instances[txtid] = instance;
return instance;
}
window.ADSLocalDropzone = window.ADSLocalDropzone || {};
window.ADSLocalDropzone.instances = window.ADSLocalDropzone.instances || {};
window.ADSLocalDropzone.instance = function (txtid) {
return window.ADSLocalDropzone.instances[txtid] || null;
};
window.ADSLocalDropzone.getFiles = function (txtid) {
var instance = window.ADSLocalDropzone.instance(txtid);
return instance ? instance.files.slice(0) : [];
};
window.ADSLocalDropzone.getFile = function (txtid) {
var files = window.ADSLocalDropzone.getFiles(txtid);
return files.length ? files[files.length - 1] : null;
};
window.ADSLocalDropzone.clear = function (txtid) {
var instance = window.ADSLocalDropzone.instance(txtid);
if (instance) {
instance.removeAllFiles(true);
}
};
function loadAdDropzoneLocal() {
$('.ADSdropzoneLocal[id]').each(function () {
ADDropzoneLocal($(this).attr('id'));
});
}
function setwebservice(idDdlWS, idhdValue, idhdText, btn) { function setwebservice(idDdlWS, idhdValue, idhdText, btn) {
var DdlWS = $("#" + idDdlWS); var DdlWS = $("#" + idDdlWS);
var hdValue = $("#" + idhdValue); var hdValue = $("#" + idhdValue);
@@ -2640,6 +2789,7 @@ jQuery(document).ready(function () {
DataTablePaginatorScroll(); DataTablePaginatorScroll();
DataTablePaginatorScroll2(); DataTablePaginatorScroll2();
loadAdDropzone(); loadAdDropzone();
loadAdDropzoneLocal();
clonsbuttons(); clonsbuttons();
ADScroller2(); ADScroller2();
//setTimeout(ADScroller2, 500); //setTimeout(ADScroller2, 500);

File diff suppressed because it is too large Load Diff

View File

@@ -1,14 +1,148 @@
.sig-gis-map { #ModalStageGis .modal-dialog {
width: 100%; width: 94%;
min-height: 520px; max-width: 1280px;
} }
.ads-local-dropzone { .sig-gis-layout {
min-height: 125px; display: flex;
gap: 18px;
align-items: stretch;
}
.sig-gis-panel {
min-width: 0;
}
.sig-gis-panel-files {
flex: 0 0 34%;
}
.sig-gis-panel-map {
flex: 1 1 66%;
}
.sig-gis-map {
position: relative;
width: 100%;
min-height: 480px;
border: 1px solid #d9dee4;
background: #f7f9fb;
overflow: hidden;
}
.sig-gis-svg {
display: block;
width: 100%;
height: 480px;
background: #f7f9fb;
}
.sig-gis-polygon {
cursor: pointer;
stroke: #337ab7;
stroke-width: 2;
vector-effect: non-scaling-stroke;
transition: opacity .15s ease, stroke-width .15s ease;
}
.sig-gis-polygon.is-pending {
fill: rgba(240, 173, 78, .28);
}
.sig-gis-polygon.is-linked {
fill: rgba(92, 184, 92, .34);
stroke-width: 3;
}
.sig-gis-polygon:hover {
opacity: .8;
stroke-width: 4;
}
.sig-gis-map-note {
position: absolute;
right: 8px;
bottom: 8px;
padding: 4px 8px;
background: rgba(255,255,255,.9);
border: 1px solid #d9dee4;
font-size: 11px;
color: #6b7683;
} }
.sig-gis-links { .sig-gis-links {
margin-top: 15px; max-height: 330px;
max-height: 320px; overflow: auto;
overflow-y: auto; border: 1px solid #e6e9ed;
}
.sig-gis-links-table {
margin-bottom: 0;
}
.sig-gis-links-table td,
.sig-gis-links-table th {
vertical-align: middle !important;
}
.sig-gis-link-status {
margin: 10px 0;
font-weight: 600;
}
.sig-gis-empty {
padding: 16px;
}
.ADSdropzoneLocalContainer {
min-height: 118px;
padding: 18px;
border: 2px dashed #c6ccd2;
background: #fbfcfd;
cursor: pointer;
}
.ADSdropzoneLocalContainer .dz-message {
margin: 20px 0;
text-align: center;
color: #687482;
}
.ADSdropzoneLocalContainer .dz-preview {
margin: 8px;
}
.sig-gis-current-file {
margin-top: 10px;
}
.sig-gis-assign-modal {
z-index: 1060;
}
@media (max-width: 991px) {
#ModalStageGis .modal-dialog {
width: auto;
max-width: none;
margin: 10px;
}
.sig-gis-layout {
display: block;
}
.sig-gis-panel-files,
.sig-gis-panel-map {
width: 100%;
}
.sig-gis-panel-map {
margin-top: 18px;
}
.sig-gis-map,
.sig-gis-svg {
min-height: 360px;
height: 360px;
}
} }

Binary file not shown.