Not sure if this is what you are after but...
The location tag path can't be made unique based on the querystring but
the sitemap url can.
Sitemap:
<?xml version="1.0" encoding="utf-8" ?>
<siteMap xmlns="
http://schemas.microsoft.com/AspNet/SiteMap-File-1.0" >
<siteMapNode url="~/" title="Home" roles="*">
<siteMapNode title="ServiceA" roles="ServiceA">
<siteMapNode url="~/doc.aspx?id=1" title="Doc" />
</siteMapNode>
<siteMapNode title="ServiceB" roles="ServiceB">
<siteMapNode url="~/doc.aspx?id=2" title="Doc" />
</siteMapNode>
</siteMapNode>
</siteMap>
web.confg:
<siteMap defaultProvider="default">
<providers>
<add name="default" type="System.Web.XmlSiteMapProvider"
siteMapFile="Web.sitemap" securityTrimmingEnabled="true"/>
</providers>
</siteMap>
<location path="doc.aspx">
<system.web>
<authorization>
<allow roles="ServiceA,ServiceB"/>
<deny users="*"/>
</authorization>
</system.web>
</location>
Or if you want my own cheesy hack then you can spin up your own user
for the specific request...
Protected Sub Application_PostAuthenticateRequest(ByVal sender As
Object, ByVal e As System.EventArgs)
Dim a As HttpApplication = sender
If a.Context.User Is Nothing = False _
AndAlso a.Context.User.Identity.IsAuthenticated _
AndAlso a.Request.AppRelativeCurrentExecutionFilePath =
"~/doc.aspx" _
Then
Dim id As Integer = CInt(Request.QueryString("id"))
Dim gi As GenericIdentity = New
GenericIdentity(a.Context.User.Identity.Name)
Dim r() As String = New String() {"Service" & Chr(64 + id)}
' now supporting A-Z and beyond, TODO: replace with db code.
Dim gp As GenericPrincipal = New GenericPrincipal(gi, r)
a.Context.User = gp
End If
End Sub
This at least breaks the windows rolemanager (Roles.*) for this request
but User.IsInRole, location tag locks and securityTrimming still work.