MuleSoft and using Azure AD / Entra ID as an OAuth Provider

MuleSoft provide instructions for setting up Entra ID as a client provider. However, they fall short of an end-to-end guide, and in particular they don’t tell you how to set up the Entra ID side. Complete the steps below to do this first, and then run through MuleSoft’s guide.

Entra ID App Registration

  1. Sign in to Azure Portal and navigate to Entra ID → App Registrations
  2. Create an App Registration. This will represent the Anypoint Platform.
  3. On the API Permissions tab, assign the following permissions:
    • Application.ReadWrite.OwnedBy (Application)
    • User.Read (Delegated)
  4. Make a note of the following details on the created application’s overview page:
    • Client ID (Application ID)
    • Tenant ID
  5. Click on endpoints and copy the value found in WS-Federation sign-on endpoint
  6. Click on Certificate & Secrets → New client secret
    • Make a note of the secret (it will only be shown once, at creation)

Note, that handily there is a permission available that allows MuleSoft to have control over app registrations it creates while preventing it from interacting with other app registrations which are none of its business. This helps to alleviate some security and compliance concerns as the scope is limited to only what it needs.

MuleSoft Configuration

At this point you can go through the MuleSoft Configuration Walkthrough guide.

Go to Anypoint Access Management → Client Providers → Add Client Provider → OpenID Connect DCR for Azure

and fill in the following values with the details you copied down from the above steps:

  • Issuer = the WS Federation sign-on endpoint URL
  • Tenant ID
  • Client ID
  • Client Secret

The client provider is set up but now you need to associate it with one or more Environments:

Go to Access Management → Business Groups

Choose the Environment you want to be OAuth-enabled. In the client provider dropdown list, select the new client provider.

Behaviour of the Client Provider

The following are some observations of how Anypoint works after setting up the Client provider.

Secrets

Because Entra ID generates certificates with a maximum lifespan of 2 years, the following will be needed:

  1. Rotation of the secret used by the Client Provider so that it is continues to be able to make new clients after the initial 2 year period.
  2. Each client app that is created in Entra ID will also have secret with an expiry of 2 years expiry secret, so on an ongoing basis you will need to cater for monitoring of these secret expiry dates, along with a process for coordination of the replacement of these secrets with your client application providers/vendors.

The expiry date of the generated secret is not fed back to Anypoint (or at least it is not displayed), so you need to reply on the Entra ID portal to do this monitoring.

When you initially create a client app in Anypoint (via Anypoint Exchange → Request Access), behind the scenes it generates an App Registration in Entra ID. The client ID and secret are passed back to Anypoint, and so at the point of creation Anypoint and Entra ID are in sync. You can therefore use Anypoint to reveal the ID/secret and pass this to whoever manages your client application. However, if you then use the “Reset Secret” button in Anypoint, it changes the secret in Anypoint, but doe not sync it back to Entra ID.

The only secrets that matter are the ones held in Entra ID, because this is where the client will authenticate. Pressing the “Reset Secret” button in Anypoint has no effect, because the client app is never coming to Anypoint to authenticate.

To generate a new secret for a client, or to manage a rollover of a secret before it expires, you must use the Entra ID functionality, not the Anypoint functionality.

What if I don’t want OAuth on an API?

After setting an external client provider, if you go in to an API in API manager, and look at the settings tab, you will see this warning:

This might cause concern. What about the case where you just want a process API to connect to a system API, surely we aren’t going to be forced to use OAuth for this?

Thankfully, although it is not that obvious from the screens that are presented, this is not the case. The behaviour changes depending on which authentication policy you apply to an API:

If you choose Client ID Enforcement policy, then you are still able to use a basic client_id and secret. An App Registration is not created in Entra ID in this case.

If you choose OpenID Connect Access Token Enforcement, then the App Registration is created.

The OAuth flow is only invoked if the OpenID Connect policy is applied, otherwise the request is validated using the client_id and secret held locally in Anypoint.

Logging and Auditing

Entra ID

The Entra ID audit log shows the following events occurring when a new Client App is created:

ActionActivity types and details
Client App createdAdd Application
Update to the Anypoint App Registration to set it as owner of the newly created App
Setting the client secretUpdate Application – Certificate and Secrets Managment
Unknown final stepUpdate Application No propoerties identifed in the log.

Disappointingly, there is nothing in the Sign In logs (either interactive or non-interactive) that indicates the usage of the App Registration. It is impossible to tell if or how often, for where etc the client app is being used! Poor form from Microsoft!

JBL Link Music issues with Airplay 2

JBL Link Music + Airplay 2 = Frustration!

I bought a bundle pack of 2 JBL Link Music speakers for the bargain price of £70 in the pre-Christmas sales. Considering these speakers support Airplay, Google Cast, and Bluetooth, at £35 apiece, these were by far the best value Wi-Fi enabled speakers available for my new home audio setup. The next nearest devices in price supporting Airplay 2 are probably the Apple HomePod Mini (£89), and and the Sonos One (£199). At nearly 3 and 6 times the price respectively, they seemed worth a go, even if they didn’t turn out to be amazing sound quality!

The Problem

It turns out that the sound was fine, especially for this price. However I should have realised that not all Airplay speakers are created equal when the Apple Home setup process took 3 attempts to complete successfully. In the end it worked. Setup the second speaker – exactly the same issue – 1st attempt times out, 2nd attempt finds the speaker but fails to connect, 3rd or 4th time lucky and connects within seconds.

At this point, you go to your music app, send music to the speaker via the airplay menu and all seems rosy. The issues creep in over time. You come back later on, or the next day, select the speaker in the Airplay menu, the iPhone or iPad says it’s playing music, but no sound is coming from the speaker. Odd. I select the other speaker in the airplay menu – it works. I select both speakers, one works, one doesn’t. This can carry on for a few days, and then one day it will work. The next day it doesn’t. Sometimes one works, not the other, sometimes neither work.

I know the speaker is connected ok, because when it is supposedly playing music according to the Apple device, if I turn the volume up or down, the LED lights on the speaker glow accordingly.

Things I Tried

  • Powering off and on the speaker… you never know, it’s a computer after all!
  • Powering off for an extended period
  • Powering off and on the Apple device being used to send music
  • Resetting the speaker, removing from Apple Home, and completing the (buggy) setup process again.
  • Setting the speaker up in Google Home alongside Apple Home. One notable thing is that when the speaker was not working with Airplay, and the Google Home setup had also been completed, I was able to switch from Airplay to Google Cast, and the speaker would immediately play the music, so there is no hardware issue with the speaker.
  • Casting music from a different device
  • Casting music from a different app
  • Deleting the speaker from my router’s configuration

Occasionally, rebooting or resetting something would temporarily resolve the issue, but none of these worked to resolve the Airplay issue. Even resetting the speaker would not always allow the music to be played, which surprised me – makes you think it is something wrong with your device. I even ended up buying a new iPad thinking my old one must be the issue (older iOS version)! It wasn’t – new iPad on iOS 16.3 – exactly the same issue!

The “Solution”

After finding no resolution, I contacted JBL support who gave a number of canned troubleshooting steps – basically all the things listed above. It was not completely relevant to me as it was talking about Google Home mostly, but I’ll list the steps they provided for that in case it helps anyone else:

Can you please start by checking the following:

•    Your speaker is within 4-6 meters and connecting directly to your home internet router.
•    Your mobile device is using the latest version of the Google Home App.
•    You are not connecting to a business network, a shared network, or a mobile Hotspot.
•    Your mobile device and Speaker are connecting to the same network and using the correct password.

If these checks do not help get you connected, could you please try the following troubleshooting:

Step 1: – This will force the router to create a new connection to the speaker.

•    Delete the Wi-Fi connection on the mobile device you are using to set-up the speaker.
•    Remove the power from the Router.
•    Reset the Speaker whilst the Router is powered off (see manual).
•    Turn on the router and wait for Wi-Fi to become available again.
•    Re-connect your mobile device to Wi-Fi.
•    Turn on the speaker and try setting up via Google Home, making sure you connect the device to the same Wi-Fi connection.

Step 2: – If Google Home is not finding the device or the speaker is found, but you cannot connect. You can try to manually connect your phone to the speaker. 

•    Reset the speaker and power on (see manual).
•    Check the available Wi-Fi connections on your Mobile device, you should see the speakers personal network connection (SSID). E.g.,  Link Music – ######.
•    If you can see this; connect directly to this Wi-Fi connection with your mobile device, then re-launch Google Home and attempt the setup again.

Step 3: – To rule out that the mobile device is causing the issue.

•    Reset the Speaker (see manual).
•    Run the Google Home setup using an alternative mobile device.

One thing I had not tried in the above steps was rebooting the router (a Fritz!Box). I duly tried it – turned the router off, reset the speaker, removed from Apple Home, turned it all back on and… hey presto! Working again after about a week of failed experiments. Phew.

Next day… no sound again. I ended up asking to send the speakers back as this was just far too unreliable to live with day-to-day. Nobody should have to be resetting things, or rebooting routers to listen to their music!

Not All Airplay-Compatible Speakers Are Created Equal

It was very disappointing to have to send the JBL speakers back, but I moved on to my next cheapest option, which, surprisingly, turns out to be an Apple product – the HomePod Mini.

I was aware of its limitations – no Bluetooth or Chromecast support. No support for Spotify Connect and several other mainstream streaming services. But my requirement is simply to play via Airplay, and this it does without fuss.

JBL Link Music vs Apple HomePod Mini

Basic info and controls are shown in Control Center on all Apple devices when using a HomePod. This was not the case with the JBL speaker.

Compared to the JBL speaker, it’s clear that “Airplay compatible” does not mean that you get the same experience regardless of product or brand. The HomePod Mini setup worked first time with no fuss. There have been no issues with connectivity. The implementation just feels more “complete”, e.g. you get to see and control what is playing on the speaker from the Apple Home app on any Apple device on the network – as in the image – whereas the JBL speaker would just say “Not Playing”, even when it was. Although this sounds like it might not be an issue since you might not need to use this menu, it means that the deeper integration is missing. You miss out, for example, on features like being able to ask the smart speaker what song is playing. The HomePod, with this additional contextual awareness also has basic and useful features like being able to tap it to pause the music, or double tap it to skip songs.

I feel Apple should put some more stringent standards around what it means to be able to display the “Works With Apple Airplay” badge on a product, as it damages the reputation of the system when you have incomplete or poor quality implementations in the marketplace. The JBL speaker, on paper, should have been just fine for me, and the licencing of the Airplay compatibility from Apple should have made this so, so I think Apple is partly to blame for my experience. On the other hand, JBL must be shooting themselves in the foot by putting out devices with this sort of poor quality – I can’t believe I am the only one who has had these issues and had to return them, at expense to the company.

Aside: Google Cast

I found that Google Cast worked more reliably and in some ways would have been preferable:

  • The speakers are accessible with one less step in that they appear in the devices menu without having to go further in to the Airplay menu.
  • Speaker groups can be pre-defined and selected with one tap.
  • I found that the iPad would stay set to output to Chromecast for the long term. E.g. the following day if playing music, it would resume from the speakers automatically rather than having to select anything in a menu. For my setup this is ideal – I have a dedicated iPad for playing music and I always want it to be coming from the speakers rather than the iPad. In this respect Airplay is a pain as it only keeps the connection going for a short time after the music stops, and then forgets the connection.

The only reason I couldn’t use this was because of an issue with the app I want to use: Plexamp. The iPad will set the music playing, but after this it can become out of sync. Google Cast establishes a stream directly from the source (Plex server in my case) to the speaker, and then the iPad acts only as a remote control. IT seems however that the iPad loses the connection sometimes and what it thinks is playing is not what is actually playing. Or, sometimes it doesn’t know that the speaker is still playing. In this case, I think the fault lies with the app rather than the speaker.