Limites liées aux UDF JavaScript¶
Pour assurer la stabilité dans l’environnement Snowflake, Snowflake impose les limites suivantes aux UDFs JavaScript. Ces limitations ne sont pas appelées lors de la création d’UDF, mais plutôt lors de l’exécution au moment de l’appel de l’UDF. Cette rubrique couvre les exigences générales et les détails d’utilisation des UDF (fonctions définies par l’utilisateur) JavaScript, ainsi que les limitations spécifiques aux UDFs JavaScript.
Dans ce chapitre :
Taille maximale du code source JavaScript¶
Snowflake limite la taille maximale du code source JavaScript dans le corps d’une UDF JavaScript. Snowflake recommande de limiter la taille à 100 KB. (Le code est stocké sous une forme compressée et la limite exacte dépend de la capacité de compression du code).
La consommation d’une trop grande quantité de mémoire entraînera l’échec de l’UDF¶
Les UDFs JavaScript échoueront si elles consomment trop de mémoire. La limite spécifique est susceptible d’être modifiée. L’utilisation d’une trop grande quantité de mémoire entraînera le retour d’une erreur.
Un délai d’exécution trop long entraînera l’arrêt de l’UDF et l’envoi d’un message d’erreur¶
Les UDFs JavaScript qui prennent trop de temps à se terminer seront arrêtées et une erreur sera retournée à l’utilisateur. De plus, les UDFs JavaScript qui commencent des boucles sans fin entraîneront des erreurs.
Une profondeur de pile excessive entraîne une erreur¶
Une profondeur de pile excessive due à la récursion entraînera une erreur.
État global¶
Snowflake préserve généralement l’état global JavaScript entre les itérations d’une UDF. Cependant, vous ne devez pas vous fier aux modifications précédentes de l’état global disponibles entre les appels de fonctions. De plus, vous ne devez pas supposer que toutes les lignes s’exécuteront dans le même environnement JavaScript.
Dans la pratique, l’état global est pertinent dans les cas suivants :
Logique d’initialisation complexe/coûteuse. Par défaut, le code de l’UDF fourni est évalué pour chaque ligne traitée. Si ce code contient une logique complexe, cela pourrait être inefficace.
Les fonctions qui contiennent du code qui n’est pas idempotent. Un modèle typique serait celui-ci :
Date.prototype._originalToString = Date.prototype.toString; Date.prototype.toString = function() { /* ... SOME CUSTOM CODE ... */ this._originalToString() }
La première fois que ce code est exécuté, il change l’état de
toString
et_originalToString
. Ces changements sont conservés dans l’état global, et la deuxième fois que ce code est exécuté, les valeurs sont à nouveau modifiées de manière à créer une récursion. La deuxième fois quetoString
est appelé, le code se répète à l’infini (jusqu’à ce qu’il n’y ait plus d’espace de pile).
Pour ces situations, un modèle recommandé est de garantir que le code pertinent n’est évalué qu’une seule fois, en utilisant la sémantique des variables globales de JavaScript. Par exemple :
var setup = function() { /* SETUP LOGIC */ }; if (typeof(setup_done) === "undefined") { setup(); setup_done = true; // setting global variable to true }
Notez que ce mécanisme n’est sûr que pour la mise en cache des effets de l’évaluation du code. Il n’est pas garanti qu’après une initialisation, le contexte global sera préservé pour toutes les lignes, et aucune logique métier ne doit en dépendre.
Bibliothèques JavaScript¶
Les UDFs JavaScript acceptent l’accès à la bibliothèque JavaScript standard. Notez que ceci exclut de nombreux objets et de nombreuses méthodes généralement fournis par les navigateurs. Il n’existe aucun mécanisme pour importer, inclure ou appeler des bibliothèques supplémentaires. Tout le code requis doit être incorporé dans l’UDF.
De plus, la fonction eval()
JavaScript intégrée est désactivée.
Taille et profondeur de la variante retournée¶
Les objets de variantes renvoyés sont soumis à des limitations de taille et de profondeur d’imbrication :
- Taille:
Actuellement limité à plusieurs mégaoctets, mais sujet à changement.
- Profondeur:
Actuellement limité à une profondeur d’imbrication de 1 000, mais sujet à changement.
Si un objet est trop grand ou trop profond, une erreur est retournée lorsque l’UDF est appelé.
Les contraintes de type d’argument et de retour sont parfois ignorées¶
Certaines caractéristiques de type déclarées pour un argument ou une valeur de retour seront ignorées lors de l’appel de l’UDF. Dans ces cas, la valeur reçue peut être utilisée telle quelle, qu’elle soit ou non conforme aux contraintes spécifiées dans la déclaration.
Les éléments suivants sont ignorés pour les UDFs dont la logique est écrite en JavaScript :
Longueur des arguments de type VARCHAR
Exemple¶
Le code de l’exemple suivant déclare que l’argument arg1
et la valeur de retour doivent être un VARCHAR d’une longueur maximale d’un caractère. Cependant, l’appel à cette fonction avec un arg1
dont la valeur est supérieure à un caractère aboutira comme si la contrainte n’était pas spécifiée.
CREATE OR REPLACE FUNCTION tf (arg1 VARCHAR(1))
RETURNS VARCHAR(1)
LANGUAGE JAVASCRIPT AS 'return A.substr(3, 3);';