Stephan van Rooij

Software architect with a passion for home automation.

Protect against SSO for Graph PowerShell

P

Why would you want to disable SSO for some cloud app, we love SSO, it makes our life easier? I agree, single-sign-on is great, until it is used without the knowledge of a user that logged-in with his admin account (don’t do that!).

Graph PowerShell

Microsoft released Graph PowerShell Modules, some time ago. It’s really easy to manage stuff in your tenant with these new modules. You can use it to do all the requests in the Microsoft Graph API.

For instance managing team owners

Single-sign-on

If you call the code below it will open a login request in your default browser. This will query the user for consent the first time. If the user already consented the requested scopes the login prompt is closed immediately, and the script has an access token that is valid for 1 hour. In this case the script can modify all groups in our tenant.

$tenantId = "21009bcd-06df-4cdf-b114-e6a326ef3368";
Connect-MgGraph -TenantId $tenantId -Scopes "User.Read.All","GroupMember.ReadWrite.All";

So if you’re logged-in, in your default browser as admin and you already used this module at least once, every script that is executed will get a token without user interaction. And this token might have access to modify group memberships (depending on the requested scopes).

You should never execute scripts that you didn’t check, but attackers might find a way to start a script without the user knowing. Being able to start a script as the current user is bad enough, but if that script is able to get this precious token for the Graph API, things might end badly.

Logoff yourself

According to the documentation your Graph PowerShell session will be kept alive in the background. It possibly has a way to use a refresh token to renew the access token indefinitely (need more details).

If you’re finished with the Graph PowerShell, be sure to call Disconnect-MgGraph. Without this the (malicious) script doesn’t even need to login.

Conditional access to the rescue

Let’s create a new conditional access policy to at least enforce the use to re-authenticate every hour. This limits the access surface. You can off course also force the use of MFA or a trusted device.

The trick is in the Cloud apps or Actions part, to target Microsoft Graph PowerShell, you’ll need the App ID, since searching won’t show what you’re looking for. The App ID used by the Graph PowerShell module is: 14d82eec-204b-4c2f-b7e8-296a70dab67e.

Next set the other parameters as required, in the sample I picked Sign-in frequency 1 hour, but your millage may vary.

Microsoft Graph conditional access

Block users from using the module

Because this module uses Azure AD authentication you can also stop users from using this PowerShell all together.

  1. Go to Azure AD, Enterprise application
  2. Switch to All Applications
  3. Search for Microsoft Graph
  4. Open the app Microsoft Graph PowerShell (one of the only apps with an icon)
  5. Go to properties
  6. Switch Assignment required to Yes (and Visible to users to No)
  7. Save the new properties

You can also add a group of users who are allowed to access this app and setup requesting access that way. Get creative.

The enterprise application also has an Sign-in logs where you can see who is using the app and an Audit logs tabs where you can see what is modified by this application.

Create Outlook category for everyone

C

Did you know you can categorize items in your Outlook calendar to give them a different color (in most official Outlook clients)? You can help your users by pre-configuring some default categories. You can also create categories for your users if you have some automation to create items in their calendar by some automated way.

Replace an owner in all their Teams

R

Microsoft Teams without an owner are no longer manageable, so what happens if some user leaves the company and he/she was an owner in several Teams?

Github Actions: Use secret file

G

Github Actions are great for automating tests and builds, among other things. If you need a secret (key/token/password), you can add those in the configuration and use them in your workflow.

Sometimes you need a file that is meant to be secret inside your workflow. This post shows you how to securely save this file as a secret and recreate the file during build. We use base64 encoding for a way to convert any file to a string that can be saved in the secrets.

This is all done in powershell core, which is available in all (Windows/Mac/Linux) runners on Github. The code below should work on any platform, but is only tested on a windows-latest runner.

Like what you're seeing? Consider Sharing on Twitter or Sponsoring me