Вы находитесь на странице: 1из 9

Introduccin

Para acceder a servicios de Internet, Oracle cuenta de modo nativo con el Package
UTL_HTTP.

Con el Package UTL_HTTP, se pueden escribir programas PL / SQL que se
comunican con los servidores web (HTTP).
El paquete tambin soporta HTTP en el protocolo Secured Socket Layer (SSL),
tambin conocido como HTTPS, directamente o a travs de un proxy HTTP.
Otros protocolos de acceso a datos relacionados con Internet (como el protocolo
de transferencia de archivos (FTP) o el protocolo Gopher) tambin estn
soportados mediante un servidor proxy HTTP que soporta los protocolos.


Acceso a Servicios de Red en Oracle 11g.
Oracle permite el acceso a servicios de red externos usando APIs PL/SQL
(UTL_TCP, UTL_SMTP, UTL_MAIL, UTL_HTTP and UTL_INADDR), las cuales son
implementadas usando el protocolo TCP.
En versiones previas de la base de datos, este acceso slo dependa del GRANT sobre
un package especfico a un usuario.
Oracle 11g introduce un acceso de grano fino a servicios de red usando el Access Control
List (ACL) en el repositorio XML DB, permitiendo control sobre qu usuarios accesan qu
recursos de red, independiente de los grants a los packages.
Las Access Control Lists se pueden crear, modificar y eliminar en el repositorio XML DB
usando FTP o WebDav.
Adems, Oracle proporciona los packages DBMS_NETWORK_ACL_ADMIN y
DBMS_NETWORK_ACL_UTILITY que permiten administrar la ACL desde
PL/SQL.


Crear una Access Control List (ACL)
(pondremos en rojo , lo que debemos ejecutar)
Entrar a la base de datos con usuario SYS o administrador.
Las ACLs son manipuladas usando el package DBMS_NETWORK_ACL_ADMIN
package.
El procedimiento CREATE_ACL usa los siguientes parmetros para crear un nuevo ACL:

Parmetro Descripcin
acl El nombre del archivo XML de la ACL, generado relativo al directorio "/sys/acls" en
el repositorio XML DB.
description Una descripcin del ACL.
principal La primera cuenta de usuario o rol al que se otorga (grant) o deniega permisos. El
texto es case sensitive.
is_grant TRUE para grant, FALSE para quitar el privilegio.
privilege Usar 'connect' para accesos del tipo UTL_TCP, UTL_SMTP, UTL_MAIL y
UTL_HTTP. El texto es case sensitive.
start_date Valor por defecto NULL. Cuando se especifica, el ACL estar activo a partir de la
fecha.
end_date Una fecha opcional para el fin del ACL.


En nuestro caso, primero daremos permiso al usuario para que acceda al package:
Otorgar permiso al Package
GRANT EXECUTE ON UTL_HTTP TO ADMORA;

A continuacin, crearemos el ACL.
Crear el ACL
BEGIN
DBMS_NETWORK_ACL_ADMIN.CREATE_ACL (
acl =>'acceso_utl_http.xml',
description =>'Permiso para acceder a utl_http',
principal => 'ADMORA',
is_grant => TRUE,
privilege => 'connect');
COMMIT;
END;
/

Una vez creado,el ACL es visible en el directorio "http://host:port/sys/acls/".

Se puede agregar nuevos usuarios o roles al ACL, usando el procedimiento
ADD_PRIVILEGE.

Su lista de parmetros es similar al procedimiento CREATE_ACL, con la omisin del
parmetro DESCRIPTION y la adicin del parmetro POSITION, el cual setea el orden de
precedencia.

BEGIN
DBMS_NETWORK_ACL_ADMIN.add_privilege (
acl => 'acceso_utl_http.xml',
principal => 'TEST1',
is_grant => FALSE,
privilege => 'connect',
position => NULL,
start_date => NULL,
end_date => NULL);
COMMIT;
END;
/

Los privilegios se remueven usando el procedimiento DELETE_PRIVILEGE.
Si los parmetros IS_GRANT o PRIVILEGE van NULL, todos los grants o privilegios para
el ACL son eliminados.

BEGIN
DBMS_NETWORK_ACL_ADMIN.delete_privilege (
acl => 'acceso_utl_http.xml',
principal => 'TEST1',
is_grant => FALSE,
privilege => 'connect');

COMMIT;
END;
/

Los ACLs son eliminados usando el procedimiento DROP_ACL.

BEGIN
DBMS_NETWORK_ACL_ADMIN.drop_acl (
acl => 'acceso_utl_http.xml');
COMMIT;
END;
/

Asignando un ACL a una RED
Las ACLs se asignan a redes usando el procedimiento ASSIGN_ACL, cuyos parmetros
se listan a continuacin:

Parmetro Descripcin
acl El nombre del archivo XML del ACL.
Host El hostaname, dominio, IP o subred a asignar. Los Hostnames son case sensitive, y
se permiten wildcards en las IP y dominios.
lower_port Default a NULL. Especifica el rango bajo de puerto para el privilegio 'connect'.

upper_port Default a NULL. Si se especifica lower_port, y el upper_port es NULL, se asumen
iguales.



El cdigo siguiente muestra como se asigna el ACL creado previamente a una IP
especfica.

BEGIN
DBMS_NETWORK_ACL_ADMIN.ASSIGN_ACL (
acl => 'acceso_utl_http.xml',
host => '10.200.91.125',
lower_port => 8888,
upper_port => NULL);
COMMIT;
END;
/


El procedimiento UNASSIGN_ACL permite eliminar manualmente las asignaciones.

BEGIN
DBMS_NETWORK_ACL_ADMIN.unassign_acl (
acl => 'acceso_utl_http.xml',
host => '10.200.91.125',
lower_port => 8888,
upper_port => NULL);

COMMIT;
END;

Funcin que llama a un Web Service Oracle

CREATE OR REPLACE FUNCTION get_test( p_destino IN NUMBER )
Return VARCHAR2
IS

/*
Objetivo : Llamar a WS y retornar resultado
Creado por : Waldo Gomez Alvarez
Fecha de Creacion : 15/05/2013
*/

v_req UTL_HTTP.req := NULL;
v_resp UTL_HTTP.resp := NULL;
v_retorno NUMBER;

v_respVal VARCHAR2(32767);
v_reqXML VARCHAR2(32767);
v_webservice VARCHAR2(100);

BEGIN
/* Setea estados de error de excepciones */
Utl_Http.Set_Response_Error_Check( ENABLE => TRUE );
Utl_Http.Set_Detailed_Excp_Support( ENABLE => TRUE );

-- Web Service
v_webservice := 'http://10.200.91.188:8888/integracion.pb.webservice/endpoints/TransferenciaService.wsdl';

BEGIN
-- Generamos un Request a la URL destino, el mtodo debe ser POST
v_req := UTL_HTTP.begin_request(v_webservice, 'POST');

-- Creamos un mensaje SOAP tal cual se define en el WSDL
v_reqXML := '<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:web="http://cl/banchile/integracion/pb/webservice" xmlns:int="http://integracion.pb.ws.banchile.cl">
<soapenv:Header/>
<soapenv:Body>
<web:transferenciaRequest>
<web:datosTransferencia>
<int:CuentaOrigen>100</int:CuentaOrigen>
<int:CuentaDestino>' || TO_CHAR(p_destino) || '</int:CuentaDestino>
<int:Monto>1.5E2</int:Monto>
<int:RutDestino>100</int:RutDestino>
</web:datosTransferencia>
</web:transferenciaRequest>
</soapenv:Body>
</soapenv:Envelope>';

-- El contenido que enviamos es XML:
UTL_HTTP.set_header(v_req, 'Content-Type', 'text/xml');

-- Establecemos el SOAPAction (mtodo) a invocar:
UTL_HTTP.set_header(v_req,'SOAPAction','"'||'transferencia'||'"');

-- Indicamos en el header el tamano del mensaje enviado:
UTL_HTTP.set_header(v_req, 'Content-Length', Length(v_reqXML));

-- Escribimos el body del request
UTL_HTTP.write_text(v_req,v_reqXML);

-- Obtenemos la respuesta
v_resp := UTL_HTTP.get_response(v_req);

IF (v_resp.status_code > 300) THEN
UTL_HTTP.end_response(v_resp);
raise_application_error(20000, 'Peticion HTTP rechazada');
END IF;

-- Cargamos en la variable respVal la devolucin del servidor
UTL_HTTP.read_text(v_resp, v_respVal );

-- Finalizamos la conexin HTTP
UTL_HTTP.end_response(v_resp);

-- Para facilitar el ExtractValue, se deja la eqtiqueta 'limpia'.
v_respVal := Replace(v_respVal, 'env:', '');
v_respVal := Replace(v_respVal, 'ns2:', '');


EXCEPTION
WHEN Utl_Http.Request_Failed THEN
Dbms_Output.Put_Line ( 'Peticion HTTP rechazada: ' || Utl_Http.Get_Detailed_Sqlerrm );
WHEN Utl_Http.Http_Server_Error THEN
Dbms_Output.Put_Line ( 'Error en Servidor HTTP: ' || Utl_Http.Get_Detailed_Sqlerrm );
WHEN Utl_Http.Http_Client_Error THEN
Dbms_Output.Put_Line ( 'Error en Cliente HTTP: ' || Utl_Http.Get_Detailed_Sqlerrm );
WHEN OTHERS THEN
Dbms_Output.Put_Line (SQLERRM);

END;

-- Buscamos contenido del nodo con el resultado
SELECT TO_NUMBER( EXTRACTVALUE(xmltype(v_respVal),
'Envelope/Body/transferenciaResponse/resultado'), '9999' )INTO v_retorno FROM dual;

Return v_retorno;

END;


Referencias:

Oracle-Base
http://www.oracle-base.com/articles/11g/fine-grained-access-to-network-services-11gr1.php

Вам также может понравиться