On Sep 14, 2006, at 2:34 PM, Peter Cousins wrote:
These are interesting ideas. There are a few more things I think
should
be covered.
I understand your motivations about coupling reduction by abstraction
promotion of the underlying artifact.
One usage scenario would be logging the credentials of the requester
into a database for audit trail reasons. Given that for a given
service
component implementation, there could be multiple middleware bindings,
and each binding could have multiple types of credentials, it would be
helpful to have a declarative way for the service to declare
credentials
as authoritative.
In that scenario I see the application function as being that of
logging the credentials. In a simple case, the service interface for
the application component could be:
void logAccess(String identity)
However, that in itself is not really sufficient as the interface
does not convey what type of string should be passed. We want to know
that this really is an identity, either through a tightening of the
service contract:
void logAccess(Principal identity)
or metadata
void logAccess(@com.example.UserId String identity)
For example, if I am using AMQP/Blaze with SOAP, what do I log? It
could be any one of the following:
* "user id" message property
* "app id" message property for trusted applications
* X.509 certificate used to sign the message
* WS-Security credentials in the SOAP header
Whereas if I am using HTTPS with SOAP, it could be a similar set:
* "Authorization" http header
* "Proxy Authorization" http header
* X.509 certificate used for TLS/SSL
* WS-Security credentials in the SOAP header
These bindings have no way of knowing which credential is
authoritative
when multiple credentials are supplied, so it seems the best way is
for
bindings to register a namespace with a binding context manager, and
present whatever they have received in their binding specific context.
I'd view that slightly differently. I would like each binding to
provide metadata about what it can extract from a message. For
example, a socket processor can indicate that it is able to provide
SSL identity, whereas a HTTP processor would say it could provide
HTTP header information; a HTTPS processor could provide both.
This way an intermediate component like the "aspects" we discussed
could
be responsible for interpreting the policy to select credentials from
the lower level of abstraction and transform them into higher level of
abstraction.
With the change above, I would see this more as the responsibility of
the wiring framework rather than the aspects themselves. At the
assembly level, we know we have a wire connecting the physical
endpoint (the socket) to a component and that there are a set of
policies (and other "aspects") that we want to associated with flows
on that wire. In our scenario here, we want to invoke a component
that will log the access for us and that component has declared that
it requires the identity to log. Unfortunately, we just do not have
enough information yet to determine which which identity to pass to
the component.
In this example, there could be three namespaces in the context
manager:
http://www.osoa.org/schemas/contexts/security/authorization.xsd
which could define a structure like:
authorizationContext
userId
authorizationData
http://www.osoa.org/schemas/contexts/binding/amqp.xsd
which could define a structure like:
amqpContext
contentEncoding
headers
someCustomHeader
anotherCustomHeader
deliveryMode
priority
correlationId
replyTo
expiration
messageId
timestamp
type
userId
appId
clustered
http://www.osoa.org/schemas/contexts/binding/http.xsd
which could define a structure like:
httpContext
authorization
userId
password
cookie
certificate
issuedTo
expiration
issuingAuthority
proxyAuthentication
userId
password
http://www.osoa.org/schemas/contexts/binding/soap.xsd
which could define a structure like:
soapContext
wsseSecurity
userId
password
wsTransaction
tid
And then a security policy aspect could have the following
Source soapContext/wsseSecurity/userId
Destination authorizationContext/userId
Or could present a number of them in order of interest
Source soapContext/wsseSecurity/userId
Source httpContext/authorization/userId
Destination authorizationContext/userId
Then the application need only pull authorizationContext/userId
I'm almost with you here. The big difference I see is in "pull" -
instead, if we already know from the application what it expects, we
can push the right information into it. More importantly, we don't
need to consider (process/extract) information that it does not need.
It may be we're saying the same thing differently (email does that).
I think the moving parts are same (front-end binding, extraction/
transform aspect, logging component) and the metadata is similar
(what the binding has, what the component accepts, what the transform
can do) and if there is a difference it is just in how the IoC
controller/context manager uses that to assemble the invocation flow.
Likewise this helps with the context propagation usage scenario you
alluded to in your mail:
An aspect can be defined for call chaining that could handle amqp
context propagation, because it could take
amqpContext/correlationId
or
amqpContext/messageId
from the inbound and move it to the outbound call context
amqpContext/correlationId
or for oneway short circuiting, could be configured to take the
amqpContext/replyTo
from the inbound and put it to the same place on the outbound call,
whereas if the application is going to handle the callback,
amqpContext/replyTo could be reconfigured before setting
amqpContext/replyTo on the outbound call context.
The same approach could be used to conditionally propagate
soapContext/wsTransaction/tid.
Yes. I see a chain of contexts being constructed as an invocation
flows through from wire to wire, using references within a address
space and suitably constructed messages when we hit a physical wire.
I think it's important though to maintain separation between the
namespaces for the different domains as users will typically want to
focus on a single one. So, if I'm implementing a business component I
may want to declare some requirements on say transactional behaviour
but I should not care what the form of the transaction id is or how
it flows across; similarly at a lower level, I should be able to flow
a higher-level message that contains a transaction id and hence
propagate the transaction without actually knowing that I did so.
--
Jeremy
---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]