Add Device page UIExtension - shows AD managedBy comparison and last login
This commit is contained in:
@@ -0,0 +1,188 @@
|
||||
using Disco.Models.UI.Device;
|
||||
using Disco.Services.Interop.ActiveDirectory;
|
||||
using Disco.Services.Plugins;
|
||||
using Disco.Services.Plugins.Features.UIExtension;
|
||||
using System;
|
||||
using System.Text;
|
||||
using System.Web.Mvc;
|
||||
|
||||
namespace Disco.Plugins.ADCompare.Features
|
||||
{
|
||||
[PluginFeature(Id = "ADCompareDeviceUI", Name = "Device Page - AD Compare")]
|
||||
public class DeviceUIExtension : UIExtensionFeature<DeviceShowModel>
|
||||
{
|
||||
public override UIExtensionResult ExecuteAction(ControllerContext context, DeviceShowModel model)
|
||||
{
|
||||
var device = model.Device;
|
||||
if (device == null || string.IsNullOrEmpty(device.DeviceDomainId))
|
||||
return Nothing();
|
||||
|
||||
var html = new StringBuilder();
|
||||
html.Append("<div class='form-group' style='margin-top:15px;'>");
|
||||
html.Append("<h4 style='border-bottom:1px solid #ddd;padding-bottom:5px;'>");
|
||||
html.Append("<i class='fa fa-exchange'></i> AD Compare</h4>");
|
||||
|
||||
try
|
||||
{
|
||||
var adAccount = ActiveDirectory.RetrieveADMachineAccount(
|
||||
device.DeviceDomainId,
|
||||
new[] { "managedBy", "lastLogonTimestamp" });
|
||||
|
||||
if (adAccount == null)
|
||||
{
|
||||
html.Append("<div class='alert alert-danger'>");
|
||||
html.Append("<i class='fa fa-times-circle'></i> Computer not found in Active Directory");
|
||||
html.Append("</div>");
|
||||
}
|
||||
else
|
||||
{
|
||||
var managedByDN = adAccount.GetPropertyValue<string>("managedBy");
|
||||
var discoAssignedUser = device.AssignedUserId;
|
||||
var hasManagedBy = !string.IsNullOrEmpty(managedByDN);
|
||||
var hasAssignment = !string.IsNullOrEmpty(discoAssignedUser);
|
||||
|
||||
string adManagedByUserId = null;
|
||||
string adManagedByName = null;
|
||||
|
||||
if (hasManagedBy)
|
||||
{
|
||||
try
|
||||
{
|
||||
var managedByUser = ActiveDirectory.RetrieveADUserAccount(managedByDN);
|
||||
if (managedByUser != null)
|
||||
{
|
||||
adManagedByUserId = managedByUser.Id;
|
||||
adManagedByName = managedByUser.DisplayName;
|
||||
}
|
||||
else
|
||||
{
|
||||
adManagedByUserId = managedByDN;
|
||||
}
|
||||
}
|
||||
catch
|
||||
{
|
||||
adManagedByUserId = managedByDN;
|
||||
}
|
||||
}
|
||||
|
||||
bool isMatch = false;
|
||||
if (!hasAssignment && !hasManagedBy)
|
||||
isMatch = true;
|
||||
else if (hasAssignment && hasManagedBy)
|
||||
isMatch = string.Equals(discoAssignedUser, adManagedByUserId, StringComparison.OrdinalIgnoreCase);
|
||||
|
||||
html.Append("<table class='table table-condensed' style='margin-bottom:10px;'>");
|
||||
|
||||
if (isMatch)
|
||||
{
|
||||
html.Append("<tr class='success'><td colspan='2'>");
|
||||
html.Append("<i class='fa fa-check-circle'></i> <strong>Managed By matches Assigned User</strong>");
|
||||
html.Append("</td></tr>");
|
||||
}
|
||||
else
|
||||
{
|
||||
html.Append("<tr class='warning'><td colspan='2'>");
|
||||
html.Append("<i class='fa fa-exclamation-triangle'></i> <strong>Managed By does NOT match Assigned User</strong>");
|
||||
html.Append("</td></tr>");
|
||||
}
|
||||
|
||||
html.Append("<tr><td style='width:180px;'><strong>Disco Assigned User</strong></td><td>");
|
||||
if (hasAssignment)
|
||||
{
|
||||
html.Append(Encode(discoAssignedUser));
|
||||
if (device.AssignedUser != null)
|
||||
{
|
||||
html.Append(" <span class='text-muted'>(");
|
||||
html.Append(Encode(device.AssignedUser.DisplayName));
|
||||
html.Append(")</span>");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
html.Append("<em class='text-muted'>Not assigned</em>");
|
||||
}
|
||||
html.Append("</td></tr>");
|
||||
|
||||
html.Append("<tr><td><strong>AD Managed By</strong></td><td>");
|
||||
if (hasManagedBy)
|
||||
{
|
||||
html.Append(Encode(adManagedByUserId));
|
||||
if (!string.IsNullOrEmpty(adManagedByName))
|
||||
{
|
||||
html.Append(" <span class='text-muted'>(");
|
||||
html.Append(Encode(adManagedByName));
|
||||
html.Append(")</span>");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
html.Append("<em class='text-muted'>Empty</em>");
|
||||
}
|
||||
html.Append("</td></tr>");
|
||||
|
||||
var lastLogonTicks = adAccount.GetPropertyValue<long>("lastLogonTimestamp");
|
||||
html.Append("<tr><td><strong>Last Login</strong></td><td>");
|
||||
if (lastLogonTicks > 0)
|
||||
{
|
||||
try
|
||||
{
|
||||
var lastLogon = DateTime.FromFileTime(lastLogonTicks);
|
||||
var ago = DateTime.Now.Subtract(lastLogon);
|
||||
html.Append(Encode(lastLogon.ToString("dd/MM/yyyy hh:mm tt")));
|
||||
html.Append(" <span class='text-muted'>(");
|
||||
html.Append(FormatTimeAgo(ago));
|
||||
html.Append(")</span>");
|
||||
}
|
||||
catch
|
||||
{
|
||||
html.Append("<em class='text-muted'>Unable to parse</em>");
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
html.Append("<em class='text-muted'>Never</em>");
|
||||
}
|
||||
html.Append("</td></tr>");
|
||||
|
||||
if (adAccount.IsDisabled)
|
||||
{
|
||||
html.Append("<tr class='danger'><td><strong>AD Status</strong></td><td>");
|
||||
html.Append("<i class='fa fa-ban'></i> <strong>Disabled</strong>");
|
||||
html.Append("</td></tr>");
|
||||
}
|
||||
|
||||
html.Append("</table>");
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
html.Append("<div class='alert alert-warning'>");
|
||||
html.Append("<i class='fa fa-exclamation-triangle'></i> AD lookup error: ");
|
||||
html.Append(Encode(ex.Message));
|
||||
html.Append("</div>");
|
||||
}
|
||||
|
||||
html.Append("</div>");
|
||||
return Literal(html.ToString());
|
||||
}
|
||||
|
||||
private string Encode(string value)
|
||||
{
|
||||
if (string.IsNullOrEmpty(value)) return "";
|
||||
return System.Web.HttpUtility.HtmlEncode(value);
|
||||
}
|
||||
|
||||
private string FormatTimeAgo(TimeSpan span)
|
||||
{
|
||||
if (span.TotalDays >= 365)
|
||||
return string.Format("{0} year(s) ago", (int)(span.TotalDays / 365));
|
||||
if (span.TotalDays >= 30)
|
||||
return string.Format("{0} month(s) ago", (int)(span.TotalDays / 30));
|
||||
if (span.TotalDays >= 1)
|
||||
return string.Format("{0} day(s) ago", (int)span.TotalDays);
|
||||
if (span.TotalHours >= 1)
|
||||
return string.Format("{0} hour(s) ago", (int)span.TotalHours);
|
||||
return "Just now";
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user