Las funciones definidas por el usuario (UDF) son una característica que existe en la mayoría de los RDBMS. Ya se trate de Oracle PL/SQL (Procedural Language for SQL), SQL Server T-SQL (Transact-SQL), PL/pgSQL (Procedural Language/PostgreSQL) u otras variantes, todos estos lenguajes tienen las características generales de proporcionar una estructura de bloques, control de condiciones, bucle de iteración y gestión de errores. Estos bloques permiten desarrollar tareas complejas, que pueden aislarse para mejorar el mantenimiento y la integridad de la aplicación.
En el caso de Couchbase, los criterios a la hora de elegir el idioma para SQL Las Funciones Definidas por el Usuario son bastante claras - deben ser capaces de soportar todas las capacidades que existen en las implementaciones RDBMS actuales o al mismo nivel que el servicio Couchbase Query puede, y también reflejar la preferencia de los desarrolladores de hoy en día. Según las encuestas a desarrolladores de Stack Overflow, el lenguaje de programación más utilizado en el mundo en 2020 es JavaScript.
SQL++ UDF/JS
Couchbase es una base de datos de documentos que almacena sus datos de forma nativa en formato JSON (JavaScript Objeto Notación). Su lenguaje de consulta, SQL++ , es SQL para JSON. El lenguaje JavaScript es, por tanto, la forma más natural de acceder y manipular datos JSON.
Consulte la documentación de Couchbase para obtener más información sobre la función implementación completa de JavaScript en Couchbase.
La UDF de JavaScript para recorrer árboles
JavaScript es potente, flexible y relativamente fácil de empezar a utilizar. Para mostrar su versatilidad, he creado una UDF Javascript para este artículo que atraviesa una estructura de árbol, como una estructura organizativa.
UDF: traverseTree
La UDF realiza una búsqueda recursiva en una colección utilizando las dos conecte (hacia y desde) para la recursión.
Los parámetros se muestran en la siguiente tabla:
# | Nombre | Descripción |
1 | kSpace | El espacio clave para la consulta. Puede ser una colección o una consulta. |
2 | startWith | Inicia la búsqueda con este valor para el connectToFld. Si está vacío, la búsqueda se realizará para todos los valores connectTo |
3 | connectTo | El nombre del campo de la colección donde se utilizará el campo connectTo |
4 | connectFrom | El nombre del campo de la colección donde se utilizará el campo connectFrom |
5 | informeHier | El nombre del campo de la matriz jerárquica |
6 | logKSpace | El espacio clave donde se escribe el registro opcional para UDF. Tenga en cuenta que este parámetro sólo se puede ejecutar cuando se ejecuta con EXECUTE FUNCTION. |
Ejemplos de jerarquía
Consideremos una estructura jerárquica organizativa como la siguiente.
En emp La colección cuenta con los siguientes documentos:
1 2 3 4 5 6 7 8 |
[ { "empid": 1, "nombre": "JeffC" }, { "empid": 2, "nombre": "SteveA", "reportsTo": "JeffC" }, { "empid": 3, "nombre": "AmitG", "reportsTo": "JeffC" }, { "empid": 4, "nombre": "BrendaM", "reportsTo": "SteveA" }, { "empid": 5, "nombre": "WillG", "reportsTo": "SteveA" }, { "empid": 6, "nombre": "PaulD", "reportsTo": "BrendaM" } ] |
1 |
SELECCIONE e.* DESDE traverseTree('traversal.hierarchy.emp','',nombre,'reportsTo',jerarquía del informe,'') e; |
La consulta produce los siguientes resultados:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 |
[ { "ReportHierarchy": [], "nombre": "JeffC" }, { "ReportHierarchy": [ { "nivel": 1,"nombre": "JeffC" } ], "nombre": "SteveA", "reportsTo": "JeffC" }, { "ReportHierarchy": [ { "nivel": 1,"nombre": "JeffC" } ], "nombre": "AmitG", "reportsTo": "JeffC" }, { "ReportHierarchy": [ { "nivel": 1,"nombre": "SteveA","reportsTo": "JeffC" }, { "nivel": 2,"nombre": "JeffC" } ], "nombre": "BrendaM", "reportsTo": "SteveA" }, { "ReportHierarchy": [ { "nivel": 1,"nombre": "SteveA","reportsTo": "JeffC" }, { "nivel": 2,"nombre": "JeffC" } ], "nombre": "WillG", "reportsTo": "SteveA" }, { "ReportHierarchy": [ { "nivel": 1,"nombre": "BrendaM","reportsTo": "SteveA" }, { "nivel": 2,"nombre": "SteveA", "reportsTo": "JeffC" }, { "nivel": 3,"nombre": "JeffC" } ], "nombre": "PaulD", "reportsTo": "BrendaM" } ] |
Crear el traverseTree función definida por el usuario
En Couchbase SQL++, una UDF puede definirse de varias maneras.
UDF como función escalar
1 2 3 4 5 |
CREAR FUNCIÓN to_meters(...) { args[0] * 0.3048 }; SELECCIONE nombre del aeropuerto, RONDA(to_meters(geo.alt)) AS mamsl DESDE `viaje-muestra`.inventario.aeropuerto LÍMITE 5; |
Como función en línea con una subconsulta
1 2 3 4 5 6 7 8 |
CREAR FUNCIÓN lugares(vActividad) { ( SELECCIONE id, nombre, dirección, ciudad DESDE `viaje-muestra`.inventario.hito DONDE actividad = vActividad) }; SELECCIONE l.nombre, l.ciudad DESDE lugares("comer") AS l DONDE l.ciudad = "Gillingham"; |
Definida como una función externa
En traverseTree UDF utiliza el mecanismo de función externa. Pero en este caso, proporcionamos la biblioteca de código externo para la función. Consulta la documentación de Couchbase para más detalles sobre Función externa.
A continuación se explica cómo crear una biblioteca de funciones JavaScript:
1- Crear la biblioteca de funciones - En este ejemplo, utilizamos Query Workbench para crear la biblioteca JavaScript.
2 - Añadir y editar el código JavaScript
Consulte este [enlace] para ver el código completo de la biblioteca JavaScript de traverseTree.
3 - Crear la función SQL++ definida por el usuario
1 2 3 |
CREAR FUNCIÓN traverseTree(kSpace,startWith, connectTo, connectFrom,informeHier, debugKSpace) IDIOMA JAVASCRIPT AS "traverseTree" EN "árbol"; |
Tenga en cuenta que también puede crear la UDF utilizando el Query Workbench.
Notas importantes
Couchbase 7.0 añadió SQL++ UDFs para JavaScript. A Couchbase 7.1 añadimos la capacidad de ejecutar SQL++ DMLs desde dentro del código JavaScript. También hay varias mejoras en el Query Workbench UI para el manejo de UDFs.
Descargo de responsabilidad - Tenga en cuenta que el código JavaScript proporcionado en este artículo no es parte del producto Couchase. Se proporciona aquí sólo para ilustrar las capacidades de SQL++ UDF usando JavaScript. Se anima a los usuarios a verificar su corrección y a realizar modificaciones para adaptarlo a sus necesidades.