Algunas compa帽铆as, incluido nuestro cliente, desarrollan el producto a trav茅s de una red de afiliados. Por ejemplo, las grandes tiendas en l铆nea est谩n integradas con un servicio de entrega: usted ordena productos y pronto recibe un n煤mero de seguimiento para el paquete. Otro ejemplo: junto con un boleto a茅reo, compra un seguro o un boleto Aeroexpress.
Para esto, se utiliza una API, que debe emitirse a los socios a trav茅s de la API de Gateway. Hemos resuelto este problema. Este art铆culo proporcionar谩 detalles.
Dado: ecosistema y portal API con una interfaz donde los usuarios est谩n registrados, reciben informaci贸n, etc. Necesitamos hacer una API de Gateway conveniente y confiable. En el proceso, necesit谩bamos proporcionar
- Registro
- Control de conexi贸n API
- Monitorear c贸mo los usuarios usan el sistema final
- contabilidad de indicadores de negocios.

En el art铆culo, hablaremos sobre nuestra experiencia en la creaci贸n de la API de Gateway, durante la cual resolvimos las siguientes tareas:
- autenticaci贸n de usuario
- autorizaci贸n de usuario
- modificaci贸n de la solicitud original,
- solicitud de representaci贸n
- postprocesamiento de la respuesta.
Hay dos tipos de gesti贸n de API:
1. Est谩ndar, que funciona de la siguiente manera. Antes de conectarse, el usuario prueba las posibilidades, luego paga e incrusta en su sitio. Con mayor frecuencia se usa en peque帽as y medianas empresas.
2. Una gran Administraci贸n de API B2B, cuando la empresa toma una decisi贸n comercial por primera vez sobre la conexi贸n, se convierte en una empresa asociada con una obligaci贸n contractual y luego se conecta a la API. Y despu茅s de resolver todas las formalidades, la empresa obtiene acceso a las pruebas, las aprueba y entra en ventas. Pero esto no es posible sin una decisi贸n de administraci贸n para conectarse.

Nuestra decision
En esta parte, hablaremos sobre la creaci贸n de la API de Gateway.
Los usuarios finales de la puerta de enlace creada a la API son los socios de nuestros clientes. Para cada uno de ellos, ya tenemos los contratos necesarios. Solo necesitaremos expandir la funcionalidad, teniendo en cuenta el acceso otorgado a la puerta de enlace. En consecuencia, se necesita una conexi贸n controlada y un proceso de control.
Por supuesto, uno podr铆a tomar una soluci贸n lista para resolver la tarea de Administraci贸n de API y crear API Gateway en particular. Por ejemplo, esto podr铆a ser
Azure API Management . No nos conven铆a, porque en nuestro caso ya ten铆amos un portal API y un gran ecosistema construido a su alrededor. Todos los usuarios ya se han registrado, ya entendieron d贸nde y c贸mo pueden obtener la informaci贸n necesaria. Las interfaces necesarias ya exist铆an en el portal API, solo necesit谩bamos API Gateway. En realidad, comenzamos a desarrollarlo.
Lo que llamamos la API de Gateway es un tipo de proxy. Aqu铆 nuevamente tuvimos una opci贸n: puede escribir su proxy o puede elegir algo listo para usar. En este caso, fuimos por el segundo camino y elegimos el paquete nginx + Lua. Por qu茅 Necesit谩bamos un software confiable y probado que sea compatible con el escalado. Despu茅s de la implementaci贸n, no quer铆amos verificar la correcci贸n de la l贸gica de negocios y la correcci贸n del proxy.
Cualquier servidor web tiene una canalizaci贸n de procesamiento de solicitudes. En el caso de nginx, se ve as铆:

(diagrama de
GitHub Lua Nginx )
Nuestro objetivo era integrarnos en esta tuber铆a en el momento en que podemos modificar la solicitud original.
Queremos crear un proxy transparente para que la solicitud permanezca funcionalmente como lleg贸. Solo controlamos el acceso a la API final, ayudamos a la solicitud para llegar a ella. En caso de que la solicitud fuera incorrecta, la API final deber铆a mostrar el error, pero no nosotros. La 煤nica raz贸n por la que podemos rechazar la solicitud es por la falta de acceso al cliente.
Para nginx, ya existe una
extensi贸n en
Lua . Lua es un lenguaje de script, es muy ligero y f谩cil de aprender. Por lo tanto, implementamos la l贸gica necesaria usando Lua.
La configuraci贸n nginx (analog铆a con la ruta de la aplicaci贸n), donde se realiza todo el trabajo, es comprensible. Cabe destacar aqu铆 la 煤ltima directiva: post_action.
location /middleware { more_clear_input_headers Accept-Encoding; lua_need_request_body on; rewrite_by_lua_file 'middleware/rewrite.lua'; access_by_lua_file 'middleware/access.lua'; proxy_pass https://someurl.com; body_filter_by_lua_file 'middleware/body_filter.lua'; post_action /process_session; }
Considere lo que sucede en esta configuraci贸n:
more_clear_input_headers : borra el valor de los encabezados especificados despu茅s de la directiva.
lua_need_request_body : controla si se debe leer el cuerpo de origen de la solicitud antes de ejecutar las directivas rewrite / access / access_by_lua o no. De forma predeterminada, nginx no lee el cuerpo de la solicitud del cliente y, si necesita acceder a 茅l, esta directiva debe estar activada.
rewrite_by_lua_file : la ruta a los scripts, que describe la l贸gica para modificar la solicitud
access_by_lua_file : la ruta al script, que describe la l贸gica que verifica el acceso al recurso.
proxy_pass : url a la que se enviar谩 la solicitud por proxy.
body_filter_by_lua_file : la ruta al script, que describe la l贸gica para filtrar la solicitud antes de regresar al cliente.
Y finalmente,
post_action es una directiva oficialmente indocumentada que se puede usar para realizar cualquier otra acci贸n despu茅s de que se da la respuesta al cliente.
A continuaci贸n, describiremos en orden c贸mo resolvimos nuestros problemas.
Autorizaci贸n / autenticaci贸n y solicitud de modificaci贸n
Iniciar sesi贸nCreamos autorizaci贸n y autenticaci贸n mediante accesos de certificados. Hay un certificado ra铆z. Cada nuevo cliente del cliente genera su certificado personal con el que puede acceder a la API. Este certificado se configura en la secci贸n del servidor de configuraci贸n nginx.
ssl on; ssl_certificate /usr/local/openresty/nginx/ssl/cert.pem; ssl_certificate_key /usr/local/openresty/nginx/ssl/cert.pem; ssl_client_certificate /usr/local/openresty/nginx/ssl/ca.crt; ssl_verify_client on;
Modificaci贸nPuede surgir una pregunta justa: 驴qu茅 hacer con un cliente certificado si de repente queremos desconectarlo del sistema? No vuelva a emitir certificados para todos los dem谩s clientes.
As铆 que nos acercamos sin problemas a la siguiente tarea: la modificaci贸n de la solicitud original. La solicitud original del cliente, en t茅rminos generales, no es v谩lida para el sistema final. Una de las tareas es agregar las partes que faltan a la solicitud para que sea v谩lida. El punto es que los datos que faltan son diferentes para cada cliente. Sabemos que el cliente nos llega con un certificado del que podemos tomar una huella digital y extraer los datos necesarios del cliente de la base de datos.
Si en alg煤n momento necesita desconectar al cliente de nuestro servicio, sus datos desaparecer谩n de la base de datos y no podr谩 hacer nada.
Trabajar con datos del cliente.
Necesit谩bamos garantizar una alta disponibilidad de la soluci贸n, especialmente c贸mo obtenemos los datos del cliente. La dificultad es que la fuente de estos datos es un servicio de terceros que no garantiza una velocidad ininterrumpida y bastante alta.
Por lo tanto, necesit谩bamos garantizar una alta disponibilidad de los datos del cliente. Como herramienta, elegimos
Hazelcast , que nos proporciona:
- acceso r谩pido a los datos
- La capacidad de organizar un cl煤ster de varios nodos con datos replicados en diferentes nodos.
Fuimos por la estrategia de entrega de cach茅 m谩s simple:

El trabajo con el sistema final ocurre dentro del marco de las sesiones y hay un l铆mite en el n煤mero m谩ximo. Si el cliente no cerr贸 la sesi贸n, tendremos que hacer esto.
Los datos de sesi贸n abierta provienen del sistema de destino y se procesan inicialmente en el lado de Lua. Decidimos usar Hazelcast para guardar estos datos con un escritor .NET. Luego, en algunos intervalos, verificamos el derecho a la vida de las sesiones abiertas y cerramos la falta.
Acceso a Hazelcast desde Lua y .NET
No hay clientes en Lua para trabajar con Hazelcast, pero Hazelcast tiene una API REST, que decidimos usar. Para .NET, hay un
cliente a trav茅s del cual planeamos acceder a los datos de Hazelcast en el lado .NET. Pero ah铆 estaba.

Al guardar datos a trav茅s de REST y recuperarlos a trav茅s del cliente .NET, se utilizan diferentes serializadores / deserializadores. Por lo tanto, es imposible poner los datos a trav茅s de REST, pero a trav茅s del cliente .NET y viceversa.
Si est谩 interesado, hablaremos m谩s sobre este problema en un art铆culo separado. Spoiler - en el shemka.

Registro y Monitoreo
Nuestro est谩ndar corporativo para iniciar sesi贸n a trav茅s de .NET es Serilog, todos los registros terminan en Elasticsearch, los analizamos a trav茅s de Kibana. Quer铆a hacer algo similar en este caso. El 煤nico
cliente que trabaj贸 con Elastic en Lua que se encontr贸 quebr贸 en el primer requerimiento. Y usamos Fluentd.
Fluentd es una soluci贸n de c贸digo abierto para proporcionar una sola capa de registro de aplicaciones. Le permite recopilar registros de diferentes capas de la aplicaci贸n y luego traducirlos a una sola fuente.
La API de Gateway funciona en K8S, por lo que decidimos agregar el contenedor con fluentd al mismo subtipo para escribir registros en el puerto tcp abierto existente fluentd.
Tambi茅n examinamos c贸mo se comportar铆a fluentd si no tuviera conexi贸n con Elasticsearch. Durante dos d铆as, las solicitudes se enviaron continuamente a la puerta de enlace, los registros se enviaron a fluentd, pero se prohibi贸 la fluidez de IP Elastic. Despu茅s de reconectarse, fluentd super贸 perfectamente todos los registros en Elastic.
Conclusi贸n
El enfoque elegido para la implementaci贸n nos permiti贸 entregar un producto realmente funcional para el entorno de combate en solo 2.5 meses.
Si alguna vez hace tales cosas, le recomendamos primero que comprenda claramente qu茅 problema est谩 resolviendo y cu谩les de los recursos que ya tiene. Tenga en cuenta las complejidades de la integraci贸n con los sistemas de gesti贸n de API existentes.
Comprenda por s铆 mismo qu茅 es exactamente lo que va a desarrollar: solo la l贸gica empresarial del procesamiento de solicitudes o, como podr铆a ser el caso en nuestro caso, el proxy completo. Recuerde que todo lo que haga usted mismo debe probarse a fondo despu茅s.