Muy buenas, les saluda Miguel y hoy les traigo otro artículo.
Índice
Introducción
Como la mayoría de ustedes saben, para permitir que un cliente o un servidor web se conecte a un nodo Corda; debe definir un usuario de RPC y especificar qué permisos tiene ese usuario.
Por lo general, define a ese usuario dentro del nodo node.conf
archivo, pero eso se convierte rápidamente en un inconveniente cuando desea agregar / eliminar usuarios o modificar sus permisos. Porque para que su nodo aplique los nuevos cambios a node.conf
, debes reiniciarlo; que no es algo que desee hacer a menudo si está ejecutando en producción.
Otro aspecto a tener en cuenta es ¿qué pasa si ya tiene una solución de administración de usuarios (como Active Directory) y desea integrar esa solución con su nodo Corda?
Bueno, resulta que eso se puede hacer fácilmente; todo lo que tienes que hacer es:
- Crea 3 tablas en la base de datos de tu nodo:
users
,roles_permissions
yuser_roles
. - Modifica tu
node.conf
file para leer los usuarios de RPC de la base de datos en lugar del archivo en sí.
En cuanto a cómo gestiona las entradas en esas 3 tablas, eso queda en sus manos; por ejemplo, puede crear una aplicación web sencilla o integrarla con Active Directory.
Implementación
Puede encontrar el código completo de este artículo aquí; como siempre, construí el código de muestra usando cordapp-ejemplo del repositorio de muestras de R3.
Para simplificar, el ejemplo utiliza H2 como base de datos del nodo; los pasos deben seguir siendo los mismos, independientemente de la base de datos que esté utilizando.
- Abra
build.gradle
debajoworkflows-java
y desplácese hacia abajo hastadeployNodes
tarea; Vamos a explorarPartyA
configuración de. - Configure un puerto específico para acceder a la base de datos H2:
h2Settings: [ address : 'localhost:12345' ]
- Establezca el nombre de usuario y la contraseña para el usuario de la base de datos del nodo:
dataSourceProperties: [ dataSource: [ user : "db_user", password : "db_password" ] ]
- Configure el nodo para leer los usuarios de RPC de la base de datos. Tenga en cuenta que está usando el puerto y el nombre de usuario / contraseña que definimos anteriormente; También observe que el nodo expirará el caché después de 120 segundos, por lo que cuando pruebe esta configuración y realice cambios en la base de datos; permita que pasen al menos 120 segundos antes de probar esos cambios:
security : [ "authService" : [ dataSource : [ type : "DB", connection : [ jdbcUrl : "jdbc:h2:tcp://localhost:12345/node", username : "db_user", password : "db_password", driverClassName : "org.h2.Driver" ] ], options : [ cache : [ expireAfterSecs : 120, maxEntries : 10000 ] ] ] ]
- Ahora, creemos las tablas de la base de datos; para eso necesitas instalar la consola H2. Puedes descargarlo desde aquí. Estoy usando Ubuntu y descomprimí el archivo dentro del
/bin
directorio. - Construye los nodos:
cd dynamic-rpc
entonces./gradlew deployNodes
. - comienzo
PartyA
nodo:cd dynamic-rpc/workflows-java/build/nodes/PartyA
entoncesjava -jar corda.jar
. - Espere hasta que el nodo se inicie por completo, luego abra otra terminal para iniciar la consola H2:
cd /bin/h2/bin
entoncessh h2.sh
. - Su navegador de Internet se abrirá con el inicio de sesión de la consola H2.
- Copie la URL de la base de datos de la terminal del nodo:
- Ingrese la URL, el nombre de usuario y la contraseña (usted establece el nombre de usuario y la contraseña en
build.gradle
deworkflows-java
más temprano):
- Hacer clic
Connect
. - Crea el
users
tabla (la documentación oficial indica que utilizaronVARCHAR
parausername
yTEXT
parapassword
):
CREATE TABLE users ( username VARCHAR(50) PRIMARY KEY, password TEXT NOT NULL, );
- Crea el
roles_permissions
mesa.IDENTITY
es una palabra clave específica H2 que crea una columna de incremento automático; si está usando un tipo diferente de base de datos, necesita crear una columna numérica con una secuencia relativa:
CREATE TABLE roles_permissions ( id IDENTITY, role_name VARCHAR(50) NOT NULL, permission VARCHAR(500) NOT NULL );
- Crea el
user_roles
mesa (de nuevo,IDENTITY
es un tipo de datos específico de H2):
CREATE TABLE user_roles ( id IDENTITY, username VARCHAR(50) NOT NULL, role_name VARCHAR(50) NOT NULL );
- Si abre el
build.gradle
archivo bajo elclients
módulo, verá que la tarea para comenzarPartyA
El servidor web utiliza un usuario / contraseña RPC.user1/test
:
- Agregue el mismo usuario / contraseña en la tabla
users
:
insert into users(username, password) values ('user1', 'test');
- Agregar un rol llamado
super_user
con 3 permisos:
insert into roles_permissions(role_name, permission) values ('super_user', 'InvokeRpc.nodeInfo'); insert into roles_permissions(role_name, permission) values ('super_user', 'InvokeRpc.networkMapSnapshot'); insert into roles_permissions(role_name, permission) values ('super_user', 'StartFlow.com.example.flow.ExampleFlow$Initiator');
- Agregar otro rol
normal_user
que tiene un solo permiso:
insert into roles_permissions(role_name, permission) values ('normal_user', 'InvokeRpc.nodeInfo');
- Ahora concedamos nuestro
user1
el papelnormal_user
:
insert into user_roles(username, role_name) values ('user1', 'normal_user');
- Recuerde que el nodo expira la caché después de 120 segundos, espere al menos esa cantidad de tiempo.
- Después de 120 segundos, comience
PartyA
servidor web: abra una nueva terminal ycd dynamic-rpc
entonces./gradlew runPartyAServer
- La última entrada de registro en la terminal del servidor web no debería mostrar ningún error de conexión RPC y mostrar el siguiente mensaje:
[INFO ] 22:57:02.790 [main] ServerKt.logStarted - Started ServerKt in 12.412 seconds (JVM running for 14.307)
- Si tiene algún error de conexión RPC, significa que el nodo aún no se actualizó y no conoce al usuario
user1
o sus permisos; espere un poquito más y luego intente iniciar el servidor web nuevamente.
Pruebas
Para probar los puntos finales de la API, debe utilizar Postman.
- Asegúrate de que tu
PartyA
node y su servidor web se están ejecutando. - Abra Postman y cree una nueva solicitud GET.
- Dentro
build.gradle
del móduloclients
; losrunPartyAServer
tarea especifica50005
como puerto del servidor web:
- Puede ver los diferentes puntos finales de la API dentro
clients/src/main/kotlin/com.example.server/MainController.kt
. Verás que todas las API comienzan conapi/example
:
- Usando la información proporcionada anteriormente, la URL de solicitud GET será
http://localhost:50005/api/example
más el nombre del punto final. - Uno de los puntos finales se llama
me
que devuelve el nombre X500 del nodo:
- Probemos con otro;
peers
muestra los nombres de los otros nodos que están definidos en su mapa de red:
- ¡Ups! ¿Que paso ahi? Aparentemente
user1
no tiene permiso para llamarnetworkMapSnapShot
que lapeers
usos de punto final. - Arreglemos eso, recuerde que definimos el
super_user
rol, pero no otorgamos ese rol auser1
; concedámoslo ahora. Volver a la consola de la base de datos H2:
insert into user_roles(username, role_name) values ('user1', 'super_user');
- Ahora espere 120 segundos para que expire la caché y para que el nodo se actualice automáticamente.
- Intentemos llamar a ese punto final nuevamente:
- Ahora se nota
PartyB
, que de hecho es el único otro nodo que tenemos en nuestra red. - Por cierto, podría haber actualizado el
roles_permissions
tabla y agregó el permiso paranormal_user
papel para llamarInvokeRpc.networkMapSnapshot
en lugar de agregar otro rol auser1
. Es solo un ejemplo, todo depende de cómo estructura sus roles y sus permisos.
Conclusión
Como puede ver, es muy fácil hacer que la administración de usuarios de RPC sea dinámica y sin problemas (es decir, sin requerir el reinicio del nodo); y no debería ser muy difícil para usted integrar esta función con su solución de administración de usuarios LDAP favorita.
Referencias
Gracias por leer el artículo.
Añadir comentario