Silverlight, per questioni di sicurezza, permette di effettuare solo chiamate remote sullo stesso dominio. Con "dominio" si intende il nome, ma anche il protocollo, la porta di connessione ed il sottodominio.
Supponiamo che la nostra applicazione sia raggiungibile all'indirizzo http://apps.miodominio.it/app.xap
le seguenti chiamate saranno bloccate da Silverlight:
Chiamata | Errore |
---|---|
http://www.miodominio.it/ |
Sottodominio differente |
https://apps.miodominio.it/ |
Protocollo differente |
http://apps.miodominio.it:4530/ |
Porta differente |
http://www.altrodominio.it/ |
Nome a dominio differente |
Quindi le uniche chiamate possibili sono quelle a http://apps.miodominio.it/
.
Policy File
Silverlight consente di fare chiamate remote "cross domain" se il servizio da invocare espone dalla root del dominio uno dei possibili policy file:
- clientaccesspolicy.xml (Silverlight)
- crossdomain.xml (Adobe Flash)
Per esempio l'accesso al dominio http://www.altrodominio.it/
sarà consentito sulla base del policy file esposto all'url http://www.altrodominio.it/clientaccesspolicy.xml
.
Il fatto che Silverlight supporti lo stesso file di Adobe Flash è un vantaggio incredibile in termini di adozione del prodotto, basta pensare che Flash esiste sul mercato già da molti anni e che i servizi che espongono il file crossdomain.xml
sono molti, quindi questa caratteristica di Silverlight ci permette di sfruttarli senza nessun problema.
Il download e l'interpretazione di questi file viene effettuata in maniera automatica da Silverlight quanto accediamo ad un servizio tramite le classi WebClient
o HttpWebRequest
. Il funzionamento è molto semplice, quando Silverlight si accorge che l'applicazione sta effettuando una chiamata cross domain, prova a scaricare il file clientaccesspolicy.xml
, se non riesce tenta di scaricare crossdomain.xml
, se non trova nemmeno quest'ultimo la chiamata verrà bloccata.
Se uno dei due file viene scaricato, Silverlight si occuperà di analizzare il contenuto e di decidere se la chiamata è ammessa o meno.
Il discorso cambia leggermente quando utilizziamo i Socket
, in questo caso Silverlight ha bisogno del cross domain policy file anche per chiamate effettuate sul medesimo dominio. Inoltre il file viene richiesto tramite TCP alla porta 943 (invece che via HTTP) inviando la stringa di richiesta <policy-file-request/>
.
Vediamo un esempio del file clientaccesspolicy.xml
che permette di accedere ai servizi da qualsiasi dominio via HTTP:
<?xml version="1.0" encoding="utf-8"?> <access-policy> <cross-domain-access> <policy > <allow-from http-request-headers="SOAPAction"> <domain uri="http://*"/> </allow-from> <grant-to> <resource path="/services/" include-subpaths="true"/> </grant-to> </policy> </cross-domain-access> </access-policy>
Tramite i tag <allow-from>
e <domain>
indichiamo da quale URL è permesso accedere al servizio. Nel tag domain
possiamo utilizzare il carattere asterisco come WildCard, ecco una tabella riassuntiva dell'uso del carattere WildCard:
Protocollo Web Service | <domain uri = *> | <domain uri= http://*> |
---|---|---|
HTTPS | Consente a tutti i chiamanti via HTTPS | Consente a tutti i chiamanti via HTTP |
HTTP | Consente tutti i chiamanti via HTTP e HTTPS | Consente a tutti i chiamanti via HTTP |
Diversamente, con i tag <grant-to>
e <resource>
indichiamo a quale risorsa è possibile accedere.
Ecco invece un esempio del file clientaccesspolicy.xml
per un servizio esposto via Socket
:
<?xml version="1.0" encoding ="utf-8"?> <access-policy> <cross-domain-access> <policy> <allow-from> <domain uri="*" /> </allow-from> <grant-to> <socket-resource port="4530" protocol="tcp" /> </grant-to> </policy> </cross-domain-access> </access-policy>
La principale differenza sta nel fatto che viene utilizzato il tag <socket-resource>
al posto di resource. Tramite questo tag definiamo a quale porta autorizziamo la connessione e con quale protocollo.