In Entra External ID (the replacement product to Azure B2C) for authenticating external users into dedicated applications (that is, not your workforce tenant) you can create custom extensions to add external functionality to the authentication or sign-up or sign-in process. If you need to delete these extensions though you might get stuck. Here is an error I got when trying to delete the EmailOTPSend extension used when customising the OTP email during authentication:

The error reads:
Cannot delete custom extension 6d0f8a3f-01d1-484d-bcba-53e9f4e9eb1f: The custom extension is in used by the listener of id 368a00b4-1323-43bc-8c2a-4fe8e3b81530
And there is nothing in the Entra External ID portal that matches this listener object – so how do I delete this object so I can delete the custom extension. Indeed, is the listener even an object that I am failing to delete?
Indeed “listeners” in Extra ID and Entra External ID are not specific objects in the directory. In Entra ID/External ID a “listener” is hook to receive notifications and events from the extension object that it is subscribed to. These notifications trigger when looking for change or event on the primary object.
Typically in Entra ID these are cleaned up when the related object is deleted, but not in the case of Custom Extensions in Entra External ID. So to delete the custom extension you need to delete the listener first. And as the listener is not in the Entra ID portal, you need to resort to Microsoft Graph directly. Now Graph is not the easiest of things to manipulate and so for this I like to use Graph Explorer. But Graph Explorer is not the easiest of things to use when logging into an External ID tenant!
So, to clean up the Custom Extension, we are going to log into Graph Explorer and into the External ID tenant, and then show the listener and then delete it.
In your browser, go to https://developer.microsoft.com/en-us/graph/graph-explorer?tenant=vvvvvvvv-wwww-xxxx-yyyy-zzzzzzzzzzzz where you use the Tenant ID in place of the GUID string at the end.
This opens Graph Explorer and prompts you to sign into the External ID tenant, which if you are signing in as a guest account from the primary tenant, will work. If you just go to https://aka.ms/ge or another URL for the Graph Explorer it will not work and only sign you into the primary tenant. The Tenant Name should show the External ID tenant if this is done correctly.

Once you are in the correct tenant you can query the custom extension ID. This you will easily get from the error message when you try and delete the extension. Look in the full error notification on the bell icon rather than try and copy the text from the error message in the popup (as that won’t work).
From the Beta endpoint, query the specific extension to ensure you have the correct one that you want to delete

If you change the action drop down to DELETE you should get the same message as in the Entra External ID portal:

If in either of the above attempts you get a permission error, change to the “Modify Permissions” tab and consent (not admin) to the best permission to do the work you want to do – for example to delete the CustomExtension object you will need CustomAuthenticationExtension.ReadWrite.All permission. If you have just granted yourself, or been granted by an admin, a new permission, you will need to wait about 10 to 15 minutes for the error to go away in the portal and the DELETE request fail with the “in use by listener” error.
Copy the listener ID from this error and then call the following cmdlet: (remember that you have DELETE in the drop-down in Graph Explorer from the previous instruction, so if you want to see the listener first change this to GET!
GET /beta/identity/authenticationEventListeners/{authenticationEventListenerId}

You should see in the listener that it is bound to your custom extension, under handler/customExtension node. In my example above this extension is called “[Do Not Use] Test OTP Send [3]“, because I had a lot of these before I worked out how to delete them!
Change the GET action to DELETE in Graph Explorer and run the query. The delete will happen and the Graph Explorer will return an empty set of braces {}, but a green bar and a 204 status code, with “No Content” returned as well:

Once the listener has been deleted, the custom extension can be deleted in the Entra ID portal, or via Graph Explorer using the DELETE action:
DELETE https://graph.microsoft.com/beta/identity/customAuthenticationExtensions/b90f13b5-7490-4af9-90f8-17d0f5be1703

Continue to use Graph Explorer to delete all your hanging authenticationEventListeners and then your customAuthenticationExtensions.
Photo by Dario Fernandez Ruz: https://www.pexels.com/photo/woman-holding-wireless-earphones-9130507/
Leave a Reply