Remove DNS NS Records after demoting domain controller with PowerShell

 

Get-DnsServerZone | ForEach-Object { Get-DnsServerResourceRecord -ZoneName $_.ZoneName -RRType Ns | Where-Object {$_.RecordData.NameServer -like ‘DCName.fqdn.com.‘} | Remove-DnsServerResourceRecord -ZoneName $_.ZoneName -Confirm:$false }

 

Replace the bold test with the fully qualified domain name of the name server. Don’t forget to keep the period at the end of it as well.

Directory Services–Cannot Change Password – Constraint Violation nTSecurityDescriptor

 

Recently I ran into an issue where trying to enable or disable the option ‘Cannot Change Password’ in Active Directory in my C# code. Using a Domain Administrator account the code worked perfectly fine, but when it was run under a non-administrator I would get “Constrain Violation Occurred” and the following exception

"0000051B: AtrErr: DSID-030F22B2, #1:\n\t0: 0000051B: DSID-030F22B2, problem 1005 (CONSTRAINT_ATT_TYPE), data 0, Att 20119 (nTSecurityDescriptor)\n"

Now the user in question was delegated full control over the user object which made it more frustrating as it could be done manually within Active Directory Users and Computers. What I did find out is that if the non-administrator user was assigned the owner of the user in the security option the code would work and is what lead me to the answer.

 

You must have the DirectoryEntry.Options.SecurityMasks defined to SecurityMasks.Dacl for it to work for a non-administrator user.

 

Allow Change Password

   1: public static void AllowChangePassword(DirectoryEntry user)

   2:        {

   3:            user.Options.SecurityMasks = SecurityMasks.Dacl;

   4:  

   5:            // Create a Guid that identifies the Change Password right.

   6:            Guid changePasswordGuid =

   7:                new Guid("{AB721A53-1E2F-11D0-9819-00AA0040529B}");

   8:  

   9:            // Get the ActiveDirectorySecurity for the user.

  10:            ActiveDirectorySecurity userSecurity = user.ObjectSecurity;

  11:  

  12:            // Create a SecurityIdentifier object for "everyone".

  13:            SecurityIdentifier everyoneSid =

  14:                new SecurityIdentifier(WellKnownSidType.WorldSid, null);

  15:  

  16:            // Create a SecurityIdentifier object for "self".

  17:            SecurityIdentifier selfSid =

  18:                new SecurityIdentifier(WellKnownSidType.SelfSid, null);

  19:  

  20:            // Create an access rule to allow everyone the change password 

  21:            // right. 

  22:            // This is used to remove any existing access rules.

  23:            ActiveDirectoryAccessRule allowEveryone =

  24:                new ActiveDirectoryAccessRule(

  25:                    everyoneSid,

  26:                    ActiveDirectoryRights.ExtendedRight,

  27:                    AccessControlType.Allow,

  28:                    changePasswordGuid);

  29:  

  30:            // Create an access rule to deny everyone the change password right.

  31:            ActiveDirectoryAccessRule denyEveryone =

  32:                new ActiveDirectoryAccessRule(

  33:                    everyoneSid,

  34:                    ActiveDirectoryRights.ExtendedRight,

  35:                    AccessControlType.Deny,

  36:                    changePasswordGuid);

  37:  

  38:            // Create an access rule to allow self the change password right.

  39:            // This is used to remove any existing access rules.

  40:            ActiveDirectoryAccessRule allowSelf =

  41:                new ActiveDirectoryAccessRule(

  42:                    selfSid,

  43:                    ActiveDirectoryRights.ExtendedRight,

  44:                    AccessControlType.Allow,

  45:                    changePasswordGuid);

  46:  

  47:            // Create an access rule to deny self the change password right.

  48:            ActiveDirectoryAccessRule denySelf =

  49:                new ActiveDirectoryAccessRule(

  50:                    selfSid,

  51:                    ActiveDirectoryRights.ExtendedRight,

  52:                    AccessControlType.Deny,

  53:                    changePasswordGuid);

  54:  

  55:            // Remove any existing rule that gives "everyone" the change 

  56:            // password right.

  57:            userSecurity.RemoveAccessRuleSpecific(denyEveryone);

  58:  

  59:            // Add a new access rule to deny "everyone" the change password 

  60:            // right.

  61:            userSecurity.AddAccessRule(allowEveryone);

  62:  

  63:            // Remove any existing rule that gives "self" the change password 

  64:            // right.

  65:            userSecurity.RemoveAccessRuleSpecific(denySelf);

  66:  

  67:            // Add a new access rule to deny "self" the change password right.

  68:            userSecurity.AddAccessRule(allowSelf);

  69:  

  70:            // Commit the changes.

  71:            user.CommitChanges();

  72:  

  73:            user.Options.SecurityMasks = SecurityMasks.None;

  74:        }

 

Deny Change Password

   1: public static void DenyChangePassword(DirectoryEntry user)

   2:       {

   3:           user.Options.SecurityMasks = SecurityMasks.Dacl;

   4:           

   5:           // Create a Guid that identifies the Change Password right.

   6:           Guid changePasswordGuid =

   7:               new Guid("{AB721A53-1E2F-11D0-9819-00AA0040529B}");

   8:  

   9:           // Get the ActiveDirectorySecurity for the user.

  10:           ActiveDirectorySecurity userSecurity = user.ObjectSecurity;

  11:  

  12:           // Create a SecurityIdentifier object for "everyone".

  13:           SecurityIdentifier everyoneSid =

  14:               new SecurityIdentifier(WellKnownSidType.WorldSid, null);

  15:  

  16:           // Create a SecurityIdentifier object for "self".

  17:           SecurityIdentifier selfSid =

  18:               new SecurityIdentifier(WellKnownSidType.SelfSid, null);

  19:  

  20:           // Create an access rule to allow everyone the change password 

  21:           // right. 

  22:           // This is used to remove any existing access rules.

  23:           ActiveDirectoryAccessRule allowEveryone =

  24:               new ActiveDirectoryAccessRule(

  25:                   everyoneSid,

  26:                   ActiveDirectoryRights.ExtendedRight,

  27:                   AccessControlType.Allow,

  28:                   changePasswordGuid);

  29:  

  30:           // Create an access rule to deny everyone the change password right.

  31:           ActiveDirectoryAccessRule denyEveryone =

  32:               new ActiveDirectoryAccessRule(

  33:                   everyoneSid,

  34:                   ActiveDirectoryRights.ExtendedRight,

  35:                   AccessControlType.Deny,

  36:                   changePasswordGuid);

  37:  

  38:           // Create an access rule to allow self the change password right.

  39:           // This is used to remove any existing access rules.

  40:           ActiveDirectoryAccessRule allowSelf =

  41:               new ActiveDirectoryAccessRule(

  42:                   selfSid,

  43:                   ActiveDirectoryRights.ExtendedRight,

  44:                   AccessControlType.Allow,

  45:                   changePasswordGuid);

  46:  

  47:           // Create an access rule to deny self the change password right.

  48:           ActiveDirectoryAccessRule denySelf =

  49:               new ActiveDirectoryAccessRule(

  50:                   selfSid,

  51:                   ActiveDirectoryRights.ExtendedRight,

  52:                   AccessControlType.Deny,

  53:                   changePasswordGuid);

  54:  

  55:           // Remove any existing rule that gives "everyone" the change 

  56:           // password right.

  57:           userSecurity.RemoveAccessRuleSpecific(allowEveryone);

  58:  

  59:           // Add a new access rule to deny "everyone" the change password 

  60:           // right.

  61:           userSecurity.AddAccessRule(denyEveryone);

  62:  

  63:           // Remove any existing rule that gives "self" the change password 

  64:           // right.

  65:           userSecurity.RemoveAccessRuleSpecific(allowSelf);

  66:  

  67:           // Add a new access rule to deny "self" the change password right.

  68:           userSecurity.AddAccessRule(denySelf);

  69:  

  70:           // Commit the changes.

  71:           user.CommitChanges();

  72:  

  73:           user.Options.SecurityMasks = SecurityMasks.None;

  74:       }

Outlook Prompting Password using Mapi

I’ve spent hours trying to figure out why an Outlook client kept prompting for a password when I moved the users mailbox to Exchange 2016. After hours of the normal troubleshooting I found that it did not prompt for the password when cached mode was off. After having the user connect to another machine for testing and comparing the Connection Status (Shit + right click Outlook icon in systray) I found that it wasn’t making a second connection to the Exchange Directory.

I closed Outlook, went to C:\users\username\appdata\microsoft\outlook and deleted the offlineaddressbook folder and re-opened Outlook. Whola it worked again!

Group Policy Printers not installing after update KB3170455 – MS16-087

 

Microsoft changed the way printers are installed with update KB3170455 (MS16-087). Now, for printers to be installed using group policy, the print driver must be set as true under packaged in Print Management. Some vendors have not updated their drivers to make them packaged, but there is a way to force a package to be packaged.

 

Open regedit and go to HKLM\SYSTEM\CurrentControlSet\Control\Print\Environments\Windows *** (choose version)\Drivers\Version-3\**DriverName**

 

Set the attribute PrinterDriverAttributes to 1 and restart the print spooler on the server. The driver will now show true as packaged and will install using GPO.

Group Policy not applying to security filtered user or group

 

Came across an issue this week where a newly imaged computer would not apply group policies that were filtered to an Active Directory group. GPResult showed no reference of the group policy, but it did show that the user was in the correct AD group.

 

After much research, I found that Microsoft released a Security Update for Group Policy on June 14, 2016 (https://support.microsoft.com/en-us/kb/3163622). This security update changes the way a client workstation reads the group policy. Prior to this update being installed, if a GP was a user policy, the policy would have been read by the current user’s credentials. Once the security update is applied to the client’s workstation, all group policies are read by the computer account.

 

To fix the issue, go to the group policy in which has security filtering and click on the Delegation tab. Click Add and add Authenticated Users with Read permission. Or, you can add Domain Computers with Read permission. Adding the permission under the Delegation tab with either method, only allows the computer accounts to read the policy to apply it based on the security filter. It will not apply to all authenticated users or domain computers.

Sage 50–Automatic Backup – An unknown error occurred compressing the database files.

 

While setting up a new Sage 50 2015 server I kept getting an error message “An unknown error occurred compressing the database files.” After further troubleshooting with Microsoft Process Monitor (https://technet.microsoft.com/en-us/library/bb896645.aspx) I found that it was trying to put a temporary file in a folder called “Backup” inside the company folder. This is probably a rare condition and only seen if you try to select a backup folder other than the default.

Simply create a folder called “Backup” in the company folder and try it again.

Enterprise Google Chrome Extension Not Installing

 

Had a recent issue where a Google Chrome extension I built wasn’t installing via group policy. After a lot of troubleshooting I found an entry in HKLM\Software\Policies\Google\Chrome\ExtensionInstallSources. Once I deleted that entire registry key (not just the value), the and restarted Chrome, the extension installed using the pushed settings that is in HKLM\Software\Policies\Google\Chrome\ExtensionInstallSources.

SQL Select–Format for phone number

 

If you want to create a SQL query to format a phone number based on different formats that may be in a database you can use this. Modify to fit your needs.

### – Replace this with your 3 digit area code. This is used when only 7 digits are stored as the value.

Home/Cell – Replace this with your phone number column

 

   1: SELECT 

   2:       CASE

   3:           WHEN LEN(REPLACE(REPLACE(REPLACE(REPLACE(Home,')',''),'(',''),' ',''),'-','')) = '7'

   4:             THEN '###' + REPLACE(REPLACE(REPLACE(REPLACE(Home,')',''),'(',''),' ',''),'-','')

   5:           WHEN SUBSTRING (Home, 1, 1) = '1'

   6:             THEN SUBSTRING(REPLACE(REPLACE(REPLACE(REPLACE(Home,')',''),'(',''),' ',''),'-',''), 2, LEN(Home))

   7:             ELSE REPLACE(REPLACE(REPLACE(REPLACE(Home,')',''),'(',''),' ',''),'-','')

   8:       END As [Home Phone],

   9:       CASE

  10:           WHEN LEN(REPLACE(REPLACE(REPLACE(REPLACE(Cell,')',''),'(',''),' ',''),'-','')) = '7'

  11:             THEN '###' + REPLACE(REPLACE(REPLACE(REPLACE(Cell,')',''),'(',''),' ',''),'-','')

  12:           WHEN SUBSTRING (Cell, 1, 1) = '1'

  13:             THEN SUBSTRING(REPLACE(REPLACE(REPLACE(REPLACE(Cell,')',''),'(',''),' ',''),'-',''), 2, LEN(Cell))

  14:             ELSE REPLACE(REPLACE(REPLACE(REPLACE(Cell,')',''),'(',''),' ',''),'-','')

  15:       END As [Cell Phone]

  16:  

  17:   FROM DBNAME

Apple Account Auto Verify

 

A tool I wrote in C# that automatically verifies apple accounts. Below is a link to the source code (Visual Studio 2010), however if you meet the following criteria, you can use it without modifying the code.

  1. Windows computer running .Net 4.0
  2. Running Exchange 2010
  3. Know the username and password to the mailbox that the verification email from apple is in, or you know the username and password to an elevated account that has permission to view the mailbox that the verification email from apple is in.

https://www.brandonclaps.com/downloads/AppleAccountVerify.zip – Includes source code too

If you meet the above criteria, unzip and browse to AppleAccountVerify > bin > Release > and run AppleAccountVerify.exe

 

Code:

   1: private void button_Verify_Click(object sender, EventArgs e)

   2:        {

   3:            string Log = string.Empty;

   4:            using (StreamReader sr = new StreamReader(textBox_CSVFile.Text))

   5:            {

   6:                string line;

   7:                while ((line = sr.ReadLine()) != null)

   8:                {

   9:                    string[] data = line.Split(',');

  10:  

  11:                    string ExchAuthUsername = data[0];

  12:                    string ExchAuthPassword = data[1];

  13:                    string ExchAuthDomain = data[2];

  14:                    string Exch_User_Email = data[3];

  15:                    string AppleUsername = data[4];

  16:                    string ApplePassword = data[5];

  17:  

  18:                    string Verify = GetAppleVerifyURL(ExchAuthUsername, ExchAuthPassword, ExchAuthDomain, Exch_User_Email);

  19:  

  20:                    if (Verify != string.Empty)

  21:                    {

  22:                        WebBrowser web = new WebBrowser();

  23:                        web.ScriptErrorsSuppressed = true;

  24:                        web.Navigate(new Uri(Verify));

  25:  

  26:                        while (web.ReadyState != WebBrowserReadyState.Complete)

  27:                        {

  28:                            Application.DoEvents();

  29:                        }

  30:                        try

  31:                        {

  32:                            HtmlElement el = web.Document.All["appleID"];

  33:  

  34:                            el.SetAttribute("value", AppleUsername);

  35:                            el.SetAttribute("text", AppleUsername);

  36:  

  37:                            HtmlElement el2 = web.Document.All["accountpassword"];

  38:  

  39:                            el2.SetAttribute("value", ApplePassword);

  40:                            el2.SetAttribute("text", ApplePassword);

  41:  

  42:                            foreach (HtmlElement el3 in web.Document.All)

  43:                            {

  44:                                if (el3.GetAttribute("className") == "btn bigblue")

  45:                                {

  46:                                    if (el3.InnerText.ToLower() == "verify address")

  47:                                    {

  48:                                        el3.InvokeMember("click");

  49:                                    }

  50:                                }

  51:                            }

  52:                            Log = Log + Environment.NewLine + AppleUsername + " - Verified successfully.";

  53:                        }

  54:                        catch (Exception Ex)

  55:                        {

  56:                            Log = Log + Environment.NewLine + AppleUsername + " - " + Ex.Message.ToString();

  57:                        }

  58:  

  59:                        Log = Log + Environment.NewLine + AppleUsername + " - Finished reading line";

  60:                    }

  61:                }

  62:            }

  63:            Log = Log + Environment.NewLine + " - Complete";

  64:            textBox_Log.Text = Log;

  65:        

  66:        }

Updated 12/29/14 – Updated code below (source code includes update)

   1: private static string GetAppleVerifyURL(string ExchangeAuthUsername, string ExchangeAuthPassword, string ExchangeAuthDomain, string EmailAddressToLookIn)

   2:        {

   3:            string URL = string.Empty;

   4:            try

   5:            {

   6:                ExchangeService ExchService = new ExchangeService(ExchangeVersion.Exchange2010_SP2);

   7:                ExchService.Credentials = new WebCredentials(ExchangeAuthUsername, ExchangeAuthPassword, ExchangeAuthDomain);

   8:                ExchService.AutodiscoverUrl(EmailAddressToLookIn);

   9:  

  10:                FolderId InboxID = new FolderId(WellKnownFolderName.Inbox, EmailAddressToLookIn);

  11:                ItemView view = new ItemView(50, 0, OffsetBasePoint.Beginning);

  12:                view.OrderBy.Add(ItemSchema.DateTimeReceived, SortDirection.Descending);

  13:                view.PropertySet = new PropertySet(BasePropertySet.IdOnly, ItemSchema.DateTimeReceived, ItemSchema.Subject);

  14:                FindItemsResults<Item> findResults = ExchService.FindItems(InboxID, view);

  15:  

  16:                if (findResults != null && findResults.Items != null && findResults.Items.Count > 0)

  17:                    foreach (Item item in findResults.Items)

  18:                    {

  19:                        EmailMessage message = EmailMessage.Bind(ExchService, item.Id, new PropertySet(BasePropertySet.IdOnly, EmailMessageSchema.IsRead, ItemSchema.Body, ItemSchema.Subject, ItemSchema.Categories));

  20:  

  21:                        if (message.Subject.ToLower().Contains("verify your apple"))

  22:                        {

  23:                            string body = message.Body.Text;

  24:                            string[] AfterVerifyText = Regex.Split(body, "To verify this email address belongs to you");

  25:                            string[] BeginningOfURL = Regex.Split(AfterVerifyText[1], "<a href=\"");

  26:                            int Location_EndOfUrl = BeginningOfURL[1].IndexOf('"');

  27:                            URL = BeginningOfURL[1].Substring(0, Location_EndOfUrl);

  28:                            message.IsRead = true;

  29:                            message.Update(ConflictResolutionMode.AutoResolve);

  30:                        }

  31:                    }

  32:            }

  33:            catch (Exception)

  34:            {

  35:                return URL;

  36:            }

  37:  

  38:            return URL; 

  39:        }

SharePoint–Profile Pictures no longer show after MySite URL change

I was recently installed SharePoint 2013 and had it staged under a different hostname so that I could just migrate IP’s and create CNAME DNS records for minimal downtime. However I found that once I had everything swapped to the new server the profile photos wouldn’t work anymore and I kept getting error messages when running the User Profile Sync. The errors that showed up in the event log were from SharePoint Foundation and FIMSynchonizationService

Error: 8311 “An operating failed because the following certificate has validation errors. SSL policy error have been encountered. Error code ‘0x2’ ” – I found this issue to be related to the sync using the old URL but the web site in IIS had a different (correct) SSL certificate. Once I realized what was happening I deleted a CNAME DNS record I had “mysite2” and started getting the next error”

Error 6801: “The remote name could not be resolved: ‘mysite2.xxxxx.com’ – This is because I removed the CNAME DNS record.

 

To Fix

You need to use the trust tool Update-SPProfilePhotoStore and tell it of the change in Uri’s.

Update-SPProfilePhotoStore –MySiteHostLocation “https://mysite.xxxx.com/mysite/” -OldBaseUri "https://mysite2.xxxx.com/mysite/User Photos/Profile Pictures/" -NewBaseUri "https://mysite.xxxx.com/mysite/MySite/User Photos/Profile Pictures/"