Loading...

Follow Mike F Robbins – Scripting | Automation | Eff.. on Feedspot

Continue with Google
Continue with Facebook
or

Valid

PowerShell version 7 is currently in preview and while it can be installed on Windows, Linux, and macOS, the examples shown in this blog article focus on installing it on a Windows based system, specifically Windows 10 using Windows PowerShell version 5 or higher which ships by default with Windows 10. Your mileage may vary with other operating systems, other versions of Windows, and/or other versions of Windows PowerShell. The easiest way that I’ve found to install the preview of PowerShell version 7 is to first install Jeff Hicks‘ PSReleaseTools PowerShell module from the PowerShell Gallery using Windows PowerShell. The first portion of the command needs to narrow the results down to a single item. If the Preview parameter is omitted, this command installs the latest version of PowerShell Core version 6 instead of 7. The remainder of the installation is a clicker-size. Want something even simpler and want to avoid the GUI clicker-size? Silently download and install the preview of PowerShell version 7 using the following command that’s also part of the PSReleaseTools module. Jeff Hicks’ PSReleaseTools module can also be found on GitHub. That’s where I’d recommend reporting any problems you run into with it and I’m also sure that Jeff would welcome pull requests with bug fixes and/or feature enhancements. Thoughts, questions, comments? Please post them as a comment to this blog article. µ
Read Full Article
  • Show original
  • .
  • Share
  • .
  • Favorite
  • .
  • Email
  • .
  • Add Tags 

I recently ran into a problem where an exported VM from Windows Server 2016 running Hyper-V wasn’t able to be imported on Windows Server 2019 running Hyper-V. When attempting to perform the import, the GUI stated “No virtual machines files found” as shown in the following image. This problem may have been due to using Hyper-V manager on a remote system running Windows Server 2012 R2, although the same system was used for the export. Since the Hyper-V servers themselves were installed with the Server Core installation option (no GUI), I decided to try importing the VM with PowerShell instead. I was able to successfully import it using the following command. What I also learned is that if the Hyper-V configuration files exist on a volume on a storage device such as a SAN and that entire volume is connected to the new server, you can simply import the VM without needing to perform an export first. It appears that all an export does is copy the VHD/VHDX files, configuration files, snapshots, etc. The previous command performs a “Register in-place” of the VM instead of performing a copy of the files. It assumes that you already have the correct file structure in place as would be the case for performing a simple migration of a storage volume and VM to a new Hyper-V server. More information can be found in this Microsoft “Export and Import virtual machines” article and the PowerShell help topic for Import-VM. Thoughts, questions, comments? Please post them as a comment to this blog article. µ
Read Full Article
  • Show original
  • .
  • Share
  • .
  • Favorite
  • .
  • Email
  • .
  • Add Tags 

Ever need to determine what generation all of the virtual machines are on your Hyper-V servers? This is simple using the Get-VM command that installs as part of the Hyper-V module for Windows PowerShell. While the previous command will work on both clients and servers, the following command could also be used on a Windows server. The generation of the VM is one of the properties from the results of Get-VM. The previous example is a list of all the VM’s on my local Windows 10 system that has the Hyper-V role installed. This same command will work on Hyper-V servers and it can always be wrapped inside of Invoke-Command to have it run against numerous remote Hyper-V servers in parallel. Thoughts, questions, comments? Please post them as a comment to this blog article. µ
Read Full Article
  • Show original
  • .
  • Share
  • .
  • Favorite
  • .
  • Email
  • .
  • Add Tags 

When it comes to security, most people normally approach it at one extreme or the other. Some people do nothing and don’t worry about it. All I can say for those folks is good luck with that and I hope your resume is updated. Others go into full blown panic mode, especially those who don’t take the time to understand vulnerabilities. Many security folks and articles on the Internet don’t help much either because they often blow things out of proportion which puts many of the people in the second category into panic mode. First, I recommend reading “Prevent a worm by updating Remote Desktop Services (CVE-2019-0708)“. As that article states, “Vulnerable in-support systems include Windows 7, Windows Server 2008 R2, and Windows Server 2008. Vulnerable out-of-support systems include Windows 2003 and Windows XP. Customers running Windows 8 and Windows 10 are not affected by this vulnerability, and it is no coincidence that later versions of Windows are unaffected.” Unless your running the specific operating systems that are vulnerable, you have absolutely nothing to worry about <period>. Support for Windows XP ended in 2014 and Windows 2003 ended in 2015 so you shouldn’t be running those operating systems in the first place and you’re only asking for trouble if you are. Support for Windows 7 and 2008/R2 ends in January of 2020 so the number of folks running those operating systems should be on the decline. You certainly can’t patch your production systems in the middle of the day, but as the previously referenced article states “There is partial mitigation on affected systems that have Network Level Authentication (NLA) enabled. The affected systems are mitigated against ‘wormable’ malware or advanced malware threats that could exploit the vulnerability, as NLA requires authentication before the vulnerability can be triggered. However, affected systems are still vulnerable to Remote Code Execution (RCE) exploitation if the attacker has valid credentials that can be used to successfully authenticate.” If an attacker has valid credentials that can be used to successfully authenticate, then you’ve got more problems than BlueKeep to worry about. I’ll simply query all of the servers in my demo environment to determine if any of them are impacted. I can see that none of them are impacted because they’re all running newer operating systems than the ones listed in the security bulletin. If the remote systems are running an older operating system without PowerShell installed (Windows 2008 non-R2) or an operating system that doesn’t have PowerShell remoting enabled, you could use the CIM cmdlets to query them using a CIM session with the DCOM option , but querying the registry is a little more difficult with WMI. An example of this can be found in my blog article on “Retrieve Basic Operating System Information with PowerShell“. I’ll go ahead and enable NLA (Network Level Authentication) on the systems since it should be enabled anyway and only prevents systems running Windows XP and 2003 from connecting when enabled. I’ll query those two systems again to …
Read Full Article
  • Show original
  • .
  • Share
  • .
  • Favorite
  • .
  • Email
  • .
  • Add Tags 

I recently worked with a vendor to remove an old application that was no longer being used from a server in one of my customer’s environments. While many applications may be left to die on the server long after they’re needed, this particular one transmitted data to a partner company so it definitely needed to be removed. The problem is the application was so old that no one knew which server of the hundreds of servers it was running on. The partner company was able to provide the display name of the service that the application runs as which made this problem fairly easy to resolve with PowerShell. For this scenario, I’ll use “OpenSSH” as the display name of the service that I’m looking for. First, you’ll need a list of all the servers in your environment to query. While this can be obtained from Active Directory, I’ve found that it’s easier to maintain a list of servers in a text file. Get-Service has a ComputerName parameter, but I don’t recommend using the ComputerName parameter on most cmdlets because they use older DCOM protocols that are typically blocked by firewalls and when querying multiple computers, they’re queried serially instead of in parallel. If one is unreachable for some reason, it has to timeout before continuing to the next system which is slow and inefficient to say the least. Instead, I recommend using the one to many PowerShell remoting Invoke-Command cmdlet and run the Get-Service command within its ScriptBlock parameter. By default, you’ll need to be an admin on the remote systems, but you can provide alternate credentials if necessary. Then those credentials can be used along with the Credential parameter. I’ve created a text file with the server names in it and I’ll query the file with Get-Content. I’ll combine those two techniques, placing Get-Content inside of parentheses so that portion of the command runs first and provides its results as the values for the ComputerName parameter of Invoke-Command. As I previously mentioned, you can also retrieve the computer names from Active Directory. All of the servers that I’ve been querying exist in a “SQL Servers” OU (Organizational Unit) so I can simply query Active Directory for all of the computer names in that particular OU. This does require the RSAT tools (Remote Server Administration Tools) to be installed on your workstation. As of Windows 10 version 1809, RSAT can be installed via Features on Demand. Keep in mind that this is running on your workstation and querying all of the specified servers remotely. The results are returned as deserialized objects. By default, Invoke-Command will run in parallel on up to 32 remote systems at once and that number can be controlled with its ThrottleLimit parameter. Thoughts, questions, comments? Please post them as a comment to this blog article. µ
Read Full Article
  • Show original
  • .
  • Share
  • .
  • Favorite
  • .
  • Email
  • .
  • Add Tags 

Earlier this month, I presented a session on Finding Performance Bottlenecks with PowerShell at the PowerShell + DevOps Global Summit 2019 in Bellevue, Washington. The session seemed to be well received by the audience based on the feedback that I received from the attendees. The video from this presentation is now available The code and slides used during the demonstration can be found in my presentations repository on GitHub. µ
Read Full Article
  • Show original
  • .
  • Share
  • .
  • Favorite
  • .
  • Email
  • .
  • Add Tags 

Earlier this week, Chris Gardner presented a session on “Managing dependencies in PowerShell” for the Mississippi PowerShell User Group. I mentioned that I had written a function to retrieve PowerShell module dependencies that’s part of my ModuleBuildTools module. Get-MrAST is one of the primary functions that numerous other functions in the module are built on. It retrieves the AST from one or more PS1 and/or PSM1 files, script blocks, or random arbitrary code. It can also be used to only retrieve specific AST types such as the definition of one or more functions. Get-MrPrivateCommand is another function in the module which is used to show private functions in a module. Notice the private function named Get-MrFunctionRequirment. Get-MrFunctionRequirment is a helper function that’s sandwiched between Get-MrAST and Get-MrRequiredModule. I’ll use a little known trick in this example to run the Get-MrFunctionRequirment private function from outside of the module by invoking it within module scope. This is the same trick I use to determine the private functions in a module by comparing the exported commands to the ones that exist in module scope. The Get-MrRequiredModule function is used to determine the required modules for one or more files or blocks of code. When the Get-MrRequiredModule is used without its Detailed parameter, it simply returns what’s listed in the Requires statement of the individual PS1 and/or PSM1 files. When its Detailed parameter is specified, it retrieves a list of all the commands used in the files and then returns the name of the function along with the module that the command is part of including built-in modules. This does require the module to exist on your system, but it’s great for figuring out what to add to the Requires statement. Of course, there’s no reason to add built-in modules to the requires statement. As you can see, the previous example also shows how easy it would be to retrieve a list of all the commands used in a function or script with the AST for auditing purposes. Want to know if someone wrote a function that uses Write-Host? That would be no problem whatsoever for an entire module or hundreds of functions or scripts. The MrModuleBuildTools PowerShell module along with all code found in this blog article can be found in my ModuleBuildTools repository on GitHub. Thought, questions, comments? Please post them as a comment to this blog article. µ
Read Full Article
  • Show original
  • .
  • Share
  • .
  • Favorite
  • .
  • Email
  • .
  • Add Tags 

A few weeks ago I was trying to figure out how to sort something in PowerShell with one property sorted descending and another one ascending. How to accomplish this was hiding in plain sight in the help examples for Sort-Object, but I thought I would documented it here for future reference. Use the Property parameter with a hash table to specify the property names and their sort orders. This same command can be written on one line. It can also be shortened with aliases and positional parameters if you’re running this in the console and don’t plan to share or save it. Technically, it doesn’t appear that you even have to specify Descending = $false as that’s the default sort order. You should of course use full cmdlet and parameter names in any command that you share or save. µ
Read Full Article
  • Show original
  • .
  • Share
  • .
  • Favorite
  • .
  • Email
  • .
  • Add Tags 

I recently saw a blog article on “How to Identify Process ID for SQL Server Services? – Interview Question of the Week #185” written by Pinal Dave. While his answer is simple with TSQL, what if you’re not a SQL guy? You can also retrieve this information with PowerShell from Windows itself. When it comes to retrieving information about Windows services with PowerShell, the first command that comes to mind is Get-Service. Unfortunately, Get-Service doesn’t return the process id for services. This means you’ll need to resort to using the CIM cmdlets to retrieve this information. This information can be retrieved from numerous remote SQL servers with the following command. One thing that I didn’t retrieve with the previous command was the start time of the services which is a little more complicated. In a previous blog article, I wrote about how to “Determine the Start Time of a Windows Service with PowerShell“. I’ll add that functionality in this example. If you wanted to maximize the efficiency of the commands shown in this blog article, you could also specify the Property parameter with Get-CimInstance to only return specific properties instead of all of them. µ
Read Full Article
  • Show original
  • .
  • Share
  • .
  • Favorite
  • .
  • Email
  • .
  • Add Tags 
I’m using VSCode for all of my PowerShell development at this point. I reloaded my system from scratch on March 13th of this year. Yesterday was the first time I’ve opened the PowerShell ISE since then and it was only to determine if something worked differently between the two (I tweeted this out yesterday). One of the common problems I hear about and have experienced myself with VSCode (Visual Studio Code) is that tabbed expansion of command and parameter names doesn’t work like it does in the ISE (Integrated Scripting Environment). That’s because tab completion is disabled by default in VSCode. Enabling it gives you a much more ISE like experience and prevents tabbing away from half completed PowerShell command and parameter names before intellisense kicks in. There’s a Microsoft article on “How to replicate the ISE experience in Visual Studio Code” that provides a more comprehensive list of VSCode options to set for a smoother transition from the PowerShell ISE to VSCode. µ
Read Full Article

Read for later

Articles marked as Favorite are saved for later viewing.
close
  • Show original
  • .
  • Share
  • .
  • Favorite
  • .
  • Email
  • .
  • Add Tags 

Separate tags by commas
To access this feature, please upgrade your account.
Start your free month
Free Preview