Copyright 2002-2005 HSQLDB Development Group. Permission is granted to distribute this document without any alteration under the terms of the HSQLDB license.
$Date: 2005/07/25 23:02:52 $
Table of Contents
List of Tables
List of Examples
Table Des Matières
Si vous remarquez quelques erreurs dans ce documents, veuillez en avertir l'un des auteurs listés en début de chapitre.
Si vous rencontrez des problèmes avec les procédures elles même, veuillez utiliser les possibilités de support HSQLDB lesquelles sont répertoriées à l'adresse http://hsqldb.org/web/hsqlSupport.html.
This document is available in several formats.
You may be reading this document right now at http://hsqldb.org/doc/guide, or in a distribution somewhere else. I hereby call the document distribution from which you are reading this, your current distro.
http://hsqldb.org/doc/guide hosts the latest production versions of all available formats. If you want a different format of the same version of the document you are reading now, then you should try your current distro. If you want the latest production version, you should try http://hsqldb.org/doc/guide.
Sometimes, distributions other than http://hsqldb.org/doc/guide do not host all available formats. So, if you can't access the format that you want in your current distro, you have no choice but to use the newest production version at http://hsqldb.org/doc/guide.
Table 1. Alternate formats of this document
| format | your distro | at http://hsqldb.org/doc/guide |
|---|---|---|
| Chunked HTML | index.html | http://hsqldb.org/doc/guide/index.html |
| All-in-one HTML | guide.html | http://hsqldb.org/doc/guide/guide.html |
| guide.pdf | http://hsqldb.org/doc/guide/guide.pdf |
Copyright 2002-2005 Fred Toussi. Permission is granted to distribute this document without any alteration under the terms of the HSQLDB license. Additional permission is granted to the HSQLDB Development Group to distribute this document with or without alterations under the terms of the HSQLDB license.
$Date: 2005/07/02 09:11:39 $
Table des matières
Le package jar HSQLDB est situé dans le répertoire the /lib
et contient les composants et programmes nécéssaire.
Differentes commandes sont utilisées pour lancer chacun des programmes.
Composants du package jar Hsqldb
HSQLDB RDBMS
HSQLDB JDBC Driver
Database Manager (version Swing et version AWT )
Query Tool (AWT)
Sql Tool (en lignes de commande)
Le composant HSQLDB RDBMS et le pilote JDBC provide the core functionality.
The rest are general-purpose database tools
qui peuvent être utilisé avec un moteur de Base de Données (à l'avenir : BD) disposant d'un pilote JDBC .
Tous les outils peuvent être lancés en standart par la classe Java archivée .
Dans l'exemple suivant la version AWT du gestionnaire de BD est utilisé.
hsqldb.jar est situé dans le répertoire ../lib relatif au repertoire courrant.
java -cp ../lib/hsqldb.jar org.hsqldb.util.DatabaseManager
si le fichier hsqldb.jarest dans le répertoire courrant la commabnde devient :
java -cp hsqldb.jar org.hsqldb.util.DatabaseManager
Classes principales (main) des outils Hsqldb:
org.hsqldb.util.DatabaseManager
org.hsqldb.util.DatabaseManagerSwing
org.hsqldb.util.Transfer
org.hsqldb.util.QueryTool
org.hsqldb.util.SqlTool
Certains outils, comme le gestionnaire de BD ou l'outils SQL, peuvent être utilisés en ligne de commandes ou ...
or entirely rely on them.
En ligne de commande, ajouter l'argument -? pour obtenir la liste des arguments disponibles pour chaque outils.
Les fonctionnalités du gestionnaire de BD et des outils disposant d'interface utilisateur graphique (à l'avenir : outils graphique) peuvent être explorés de manière interactive.
HSQLDB peut être lancé de différentes façon.
En général ces solutions sont divisées en deux groupes : le Mode Serveur et le mode "tout local" (aussi appelé en Mode Standalone).
Différent sous programmes du jar sont utilisés pour lancer HSQLDB dans chaque mode.
Chaque BD HSQLDB comprends entre 2 et 5 fichiers, portant le mêmle nom mais d'extention différentes, situé dans le même répertoire.
Par exemple, la BD "test" contiendra les fichiers suivant:
| Nom de fichier | Rôle |
| test.properties | Contient les paramètres générales de la BD |
| test.script | Contient la définition des tables et des autres objets de la BD Ainsi que les données des tables "non-cached" (visibles en somme) |
| test.log | Contient les changements récents |
| test.data | Contient les données des tables cachées ("cached") |
| test.backup | Contient le fichier de sauvegarde compressé contenant la derniere version stable connu du fichier data |
Tous ces fichiers sont essentiels et ne doivent jamais être effacés.
Si la BD n'a pas de tables cachées, test.data et test.backup n'existent pas.
De plus, pour ces fichiers, HSQLDB database may link to any formatted text files, such as CSV lists, anywhere on the disk.
__proposition : la BD HSQLBD peut être stockée dans un fichier text formaté , comme un fichier CSV, n'importe ou sur le disque __
Tant que la BD test est utilisée, le fichier test.log est utilisé pour tracer les changements opérés sur lers données.
Ce fichier est effacé lors de la fermeture (normale) de lea BD. Après une fermeture anormale de la Base, il est utilisé pour "rejouer" ces changements.
Le ficheir test.lck est utilisé pour marque le fait que la BD est ouverte. Ce dernier est effacer à la fermeture (normale) de la BD
Dans certaines circonstances, le fichier test.data.old est créé et effacé afterwards.
Quand le moteur de BD est en cours de fermeture, il créé des fichiers temporaires d'extention .new qui sont renomés selon la liste ci-dessus.
Several different programs can connect to the server and retrieve or update information.
Les programmes des applications (clients) se connectent au serveur de BD via le pilote JDBC HSQLDB.
En général, le serveur peut servir 10 BD simultanémlent.
Server modes can use preset properties or command line arguments as detailed in the Advanced Topics chapter.
Il existe 3 modes serveur basé sur le protocol de communicatioon entre le serveur et le client.
java -cp ../lib/hsqldb.jar org.hsqldb.Server -database.0 mydb -dbname.0 xdb
L' argument -? rappelle la liste des arguments disponibles.
Le serveur Web HSQLDB est une serveur Web spécial autorisant au client JDBC de se connecter via HTTP. Depuis la version 1.7.2 ce mode supporte les transactions.
Pour utiliser ce mode, replacer la classe main pour kle serveur dans la ligne de commande ci-dessus (above = ci-dessus ?) par la classe suivante :
org.hsqldb.WebServer
L' argument -? rappelle la liste des arguments disponibles
__ Ajout personnel __ ce qui donne si j'ai bien compris :.
java -cp ../lib/hsqldb.jar org.hsqldb.WebServer -database.0 mydb -dbname.0 xdb
__ Fin ajout personnel
Utilise le même protocole que celui utilisé par le mode Web Server. Utilisé lorsqu'un un moteur de Servelet externe (ou application Serveur), tel que Tomcat or Resin, accède directement à la Base. Ce mode est dépendant du moteur de servelt. La classe hsqlServlet du HSQLDB jar doit être installé dans l'application serveur pour se connecter. La BD à utiliser est préciser dans les propriété de l'application serveur.
Pour plus de détail, se referer au fichier source hsqlServlet.java
Les deux modes Web Server et Servlet ne peuvent acceder aux BD qu'en utilisant le pilote JDBC at the client end. They do not provide a web front end to the database. Le mode Servelet ne peut répondre qu'a une seule BD (-> connection mono-BD azu sein d'une appli serveur).
Please note that you do not normally use this mode if you are using the database engine in an application server.
__ Proposition : Vous ne devez pas utiliser ce mode si vous utilisez déjà un moteur de BD dans votre application serveur __
Une fois le serveur HSQLDB lancé, les programmes clients peuvent s'y conbnecter en utilisant le pilote JDBC HSQLDB inclus dans le fichier hsqldb.jar. Toutes les informations sur comment se connecter au serveur sont fournies dans la documentation Java jdbcConnection (situé dans le répertoire /doc/src de la distribution HSQLDB) . Un exemple de connexion sur le port par défaut (9001) pour le protocol hsql de la m^me machine:
Example 1.1. Code Java code pour se connecter à un Serveur local Server
try {
Class.forName("org.hsqldb.jdbcDriver" );
} catch (Exception e) {
System.out.println("ERROR: failed to load HSQLDB JDBC driver.");
e.printStackTrace();
return;
}
Connection c = DriverManager.getConnection("jdbc:hsqldb:hsql://localhost/xdb", "sa", "");
Dans certaines circonstances, vous pouvez avoir à utiliser la ligne suivante pour activer le pilote :
Class.forName("org.hsqldb.jdbcDriver").newInstance();
Remarque : dans une telle connexion URL, le fichier de la BD n'est pas mentionné,, comme cela était spécifié lors du lancement du serveur.
A la place on utilise la valeur définie par dbname.0 . Consulter le chapitre Sujets avancés sur les connexion URL lorsque vous avez plus d'une BD par instance.
Lorsque HSQLDB tourne sur le serveur, les accès réseaux devraient être protégés de manière adéquate. Les adresses IP des accèdant peuvent être restreint par l'utilisation de filtres TCP ou par les programmes du firewall, ou par le firewall local. Si les flux reseaux ne sont pas protégés (comme sur Internet) , le flux devraient alors être cryptés (par exemple par un VPN, la technologie ssh, ou TLS utilisant le SSL ce qui autorise les varaintes HSQLS et HTTPS des modes Serveur et Web Serveur).
Seuls les passwords sécirisés devrait être utilisés -- Le plus important, le mot de passe par défaut de l'utilisateur Systèm, une chaine vide, DOIT être changé . Si vous proposez des données au public, les connections réseaux ouvertes au public doivent être sur un accès exclusivement public dont le compte donne un accès en lecture seules aux données exclusivement.
(I.e., neither secure data nor privileged accounts should use this connection).
Ces considérations sont applicables aux serveurs HSQLDB utilisant le protocole HTTP.
Ce mode utilise le moteur de BD comme partie intégrante de votre application au sein de la même JVM. Pour beaucoup d'application ce mode est plus rapide, car les données ne sont pas converties et ne transitent pas via le reseau.
Par défaut il n'est pas possible de se connecter à la BD en dehors de l'application. Par conséquent , il et impossible de vérifier le contenu de la BD par des outils externes comme le gestionnaire de BD tant que votre application tourne. Dans la version 1.8.0, vous pouvez lancer une instance de serveur dans un processus depuis la m^me machine virtuelle que votre application ce qui procure un accès externe à vos traitements de BD .
Il est recomandé d'utiliser le mode in-process dans les application utilisant une instance serveur HSQLDB pour la BD durant les phases de développement d'application et passer au mode In-Process mode pour le déploiment.
En Mode In-Process la BD est lancée depuis le JDBC, avec le chemin du ficher de la BD specifié dans l'URL de connexion.
Par exemple, si le nom de la BD est testdb et ses fichiers sont situés dans le mêm répertoire que celui où sont lancé les commandes pour executer l'application, le code suivant est utilisé pour établir la connexion:
Connection c = DriverManager.getConnection("jdbc:hsqldb:file:testdb", "sa", "");
Le chemin de la BD peut contenir des "forward slashes" que la station tourne sous Windows ou sou linux. Les chemins relatifs ou les chemins se référenat au même répertoire du m^me disque peuvent être identique. Par exemple si votre chemin de BD sous Linux est /opt/db/testdb et que vous creez une arborescence de répertoires respectant la même structure sur le disque C: d'un poste Windows , vous pouvez utiliser la même URL pour Windows et pour Linux:
Connection c = DriverManager.getConnection("jdbc:hsqldb:file:/opt/db/testdb", "sa", "");
Lorsque les chemins relatifs sont utilisés, ces chemins seront relatifs au répertoire dans lequel les commandes shell pour démarer la JVM sont executées. . Se referer à la Javadoc jdbcConnection pour plus de détail.
Il est possible d'executer HSQLDB de telle sorte que la BD ne soit pas persistente (??? un DBA saura certainement ce que cela signifie)) et existe entièrement chargée en mémoire vive . Aucune information ne seront écrite sur disque.
this mode should be used only for internal processing of application data, in applets or certain special applications
__ Proposition : Ce mode doit être utilisé uniquement pour les traitements internes d'application, dans les applets ou certaines applications spéciales __
Ce mode et spécifié par la valeur mem du protoicole :
Connection c = DriverManager.getConnection("jdbc:hsqldb:mem:aname", "sa", "");
Une instance serveur peut être utilisée en mode memory-only en spécifiant la même URL dans server.properties.
Cette utilisation n'est pas courrante et est limitée aux solutions où le serveur de BD n'est utilisé que pour l'echange d' information entre clients, ou pour les données non-persistentes.
Lors de l'execution d'un SHUTDOWN, il est proceder un rollback sur toutes les transactions actoves.
Cas particulier la commande SHUTDOWN COMPACT. Cette commande ré-écrit le fichier .data, qui contient les informations stockées dans les tables CACHED (stockées en mémoire cache, voir les explications plus bas dans le paragraphe différents types de tables), en le compressant.
Cette commande doit être passée périodiquement, en particulier lorsque beaucoup d'INSERT , UPDATE ou de DELETE ont été effectués sur les tables. Changer la structure d'une BD, comme dropp, ou modifier les tables CACHED, ou indexer ont pour effet de laisser une large place perdue dans le fichier, cette commande permet de la recupérer.
Le sujet des compatibilité est traité dans le chapitre Advanced Topics .
Cette caractéristique perd beaucoup de nouveau utilisateurs. Si une erreur est faite dans le chemin spécifié pour se connecter à une BD existante, une connexion est de toute façon réalisée en créant au passage une nouvelle BD. Pour eviter les éccueil, vous pouvez spécifier dans les propriété de connexion ifexists=true pour n' autoriser de connexion qu' aux BD existantes et éviter de créer intempestivement de nouveles BD. Dans ce cas, si la BD n'existe pas la méthode getConnection() retourne une exception.
La Javadoc au sujet de jdbcConnection , jdbcDriver , jdbcDatabaseMetadata , jdbcResultSet , jdbcStatement , et jdbcPreparedStatement lliste toutes les méthodes supportées par le JDBC avec les informations relatives au HSQLDB.
Les méthodes JDBC sont de plusieurs sortes: les méthodes relatives aux connexions, les méta-méthodes et les méthodes d'accès aux BD .
Les méthodes d'accès aux BD utilisent les commandes SQL pour agir sur la BD et retourne chaque résultat
as a Java primitive type
ou comme instance de la classe java.sql.ResultSet .
Vous pouvez utilisez le gestionnaire de BD ou les autres outils sous formes d'accès Java aux BD pour explorer votre BD et la mettre à Jours via les commandes SQL. Ces programmes utilisent un pilote JDBC interne pour envoyer vos commandes au moteur de BD et en afficher le résultat dans un format intelligible.
Le langage SQL utilsé par HSQLDB est le combiné des standarts SQL92 et SQL2000
as it has been possible to achieve so far in a small-footprint database engine.
La liste complète des commandes SQL est traitée au chapitre SQL Syntax .
HSQLDB supporte les tables temporaires TEMP et trois sortes de tables persistantes.
Les tables temporaires ne sont pas écrites sur le disque et leur durée de vie est limitée à celle de la connexion . Leur contenu n'est visible qu'au sein de la connexion utilisée lors de leur génération; Toutes autre connexion concurrente à la BD n' auront accès qu'a des copies
Depuis la version 1.8.0 La définition d'une table temporaire est conforme au type GLOBAL TEMPORARY du SQL standard.
La definition de la table perdure mais chaque nouvelle connexion ne voit que ses propres copies de cette table, laquelle est vide au début. Lorsque la connexion est lkancée, cette table est vidée. Si la définition de la table inclu ON COMMIT PRESERVE ROWS, alors le contenu sera garder lors de l'execution du commit.
Les 3 types de tables prsistantes sont MEMORY , CACHED et TEXT .
Memory tables est le type par défaut utilisé lors du CREATE TABLE . Les données sont stockées entièrement en mémoire mais les changement de dstructure ou de contenu sont écrits dans le fichier <dbname>.script . Ce fichier est lu lors de la prochaine ouverture de la BD, et les MEMORY tables sont recrées avec leur contenu Ainsi contrairement aux TEMP table, les MEMORY tables (default) sont persistantes.
CACHED tables sont crées avec la commande CREATE CACHED TABLE . Seules une partie des données ou index sont stockés en mémoire, permettant aux tables d'atteindre plusieurs centaines de megabit. Un autre avantage des cached tables est que le moteur de BD prend moins de temps à se lancer lorsque les cached table pour manipuler beaucoup de données (remarque personelle : cela ne doit pas être perceptible pour les petites BD, ou les ressources systèmes seront de toute les manières plus importantes que les ressources nécéssaire aux accès aux BD).
L'inconvénient est la réduction des performances. Ne pas utiliser les cached tables si le volume de vos données est petit.
Dans les applications avec quelques petites tables et quelque grosses tables,il est préférable d'utiliser par défaut le mode MEMORY pour les petites tables.
TEXT tables supportées depuis la version 1.7.0 et utilisent le format CSV (séparateur virgule) ou autre fichier texte délimité comme source de données. Vous pouvez spécifier un fichier CSV existant, tel un fichier Dump provenant d'un autre SGBDR, comme source d'une TEXT table. Sinon, vous pouvez spécifier un fichier vide qui sera remplis avec les données par le moteur de BD. TEXT tables sont efficaces en mode in memory
as they cache only part of the text data and all of the indexes.
Les sources des TEXT tables peuvent toujours être reassignés à d'autres fichier si nécéssaire.
Deux commandes sont utiles pour initialiuser une TEXT table . Elles sont détaillées dans le chapitre Text Tables .
Avec les BD en mode memory-only , les tables de type MEMORY et CACHED sont traitées comme des tables non-persistentes, tandisque les TEXT table sont interedites.
HSQLDB créé un indes interne pour supporter les contraintes PRIMARY KEY, UNIQUE et FOREIGN KEY : un index unique est créé pour chaque contrainte PRIMARY KEY ou UNIQUE ; un index ordinaire est créé pour chaque FOREIGN KEY. Aussi, vous ne devez pas creer d'index duplicate user-defined su r la même colonne que celle utilisé par ces contraintes. Cela alourdirait les performances sans intérèt. cf. la discussion à ce sujet au chapitre SQL Issues .
L'importance des indexes est crucial pour les performances . Lorsque une jointure sur de multiples tables est réalisée, il doit y avoir plusieurs index utilisés dans les colonnes intervenant dans chaque jointures entre 2 tables. Lorsque des conditions d'ordonnancement ou d'égalités sont utilisés e.g. SELECT ... WHERE acol >10 AND bcol = 0, un index est requis pour la colonne acol qui est utilisée dans la condition.
Les Indexes n'ont aucun effet dans les clause ORDER BY ou les conditions LIKE .
As a rule of thumb, HSQLDB peut réaliser des traitement de plus de 100,000 lignes par secondes . Une requete executée en beaucoup seconde devrait être étudiée et des indexes devraient être ajouter sur des colonnes intervenant dedans si nécéssaire.
Les commandes supportées sont listées au chapitre SQL Syntax . Pour un bon guide sur le SQL basique avec exemples consulter PostgreSQL: Introduction and Concepts ecrit par Bruce Momjian, disponible sur le web. La plus part des livre sur le SQL s'appliquent à HSQLDB.Il y a quelques differences de syntaxes d'un moteur de BD à un autre (OUTER, OID's, etc.) ou d'utilisation (IDENTITY/SERIAL, TRIGGER, SEQUENCE, etc.).
Copyright 2002-2005 Fred Toussi. Permission is granted to distribute this document without any alteration under the terms of the HSQLDB license. Additional permission is granted to the HSQLDB Development Group to distribute this document with or without alterations under the terms of the HSQLDB license.
$Date: 2005/07/01 17:06:32 $
Table of Contents
Toutefois, certaines caractèristiques ne sont pas supportées, aussi nous ne prétendons pas assurer un support pour la totalité des caractèristiques du standart.
Les syntaxes SQL supportées sont listées dans ce guide SQL Syntax qui liste la titalité des mots clés et leur syntaxe associé. Lorsqu'une SQL DLL (Data Definition Language) ou une DML (Data Manipulation Language) est écrite (ou convertie à partir d'une existante) pour HSQLDB, vous devriez consulter la syntaxe supportée et modifier vos programmes en conséquence.
Certains mots réservés par les standart ne peuvent être utilisés dans les nom de table ou de colonnes. Par exemple le mot clé POSITION est reservé et sa fonction est défini par les standarts comme étant un rôle similaire à la fonction String.indexOf() du langage Java . HSQLDB ne vous protege pas de l'emploi de mot reservés s'il ne sont pas supportés car il ne peut alors pas les distinguer. Par exemple BEGIN est un mot reservé qui n'est pas encore supporté par HSQLDB, il est donc possible de l'utiliser dans les noms de colonnes. Vous ne devriez pas utiliser (vous ne devez pas !) de tels mots afin que les bases que vous creer aujourd'hui puissent être compatible avec les futures version de HSQLDB qui pourrait supporter effectivement certains de ces mots.
La liste entière des mots SQL se trouve dans le source de la classe org.hsqldb.Token
Par ailleurs HSQLDB supporte quelque mot clé ou expressions propriétaire.
Les expressions telles que
SELECT TOP 5 FROM ..,
SELECT LIMIT 0 10 FROM ...
ou
DROP TABLE mytable IF EXISTS
ont été ajoutées
Tous les mots clés peuvent être utilisés par les objets de base de données s'ils sont entourés de double quotes.
La contrainte unique sur plusieurs colonne (c1, c2, c3, ..) indique que vous ne pouvez pas avoir deux jeux de valeurs identiques sur ces colonnes à l'exception de la valeur NULL. En revanche chaque colonne seule peut avoir des doublons.
L'exemple suivant répond à la contrainte unique sur deux colonnes :
Example 2.1. Valeur des colonnes répondant à la contrainte UNIQUE sur deux colonnes.
| 1, | 2 |
| 2, | 1 |
| 2, | 2 |
| NULL, | 1 |
| NULL, | 1 |
| 1, | NULL |
| NULL, | NULL |
| NULL, | NULL |
Depuis la version 1.7.2 le comportement des contrintes d'unicité et des indexes avec le respect de la valeur NULL a changé pour se conformer aux standarts du SQL. Une ligne dont la valeur d'une colonne à contrainte UNIQUE est NULL peut toujours être ajoutée à la table. Ainsi plusieurs lignes peuvent contenir la même valeur de colonne porteuse de la contrainte UNIQUE si cette valeur est NULL.
CONSTRAINT <name> UNIQUE créé toujours en interne un index unique sur les colonnes, comme dans les précédentes versions. Aussi cela a exactement le même effet que la déclaration, désuette, de l'index UNIQUE .
Chaque couple référence et colonne référencée au sein d'une clé etragère doivent être de même type.
Lorsque une clé étrangère est déclarée, la contrainte UNIQUE doit exister (ou clé-primaire) sur les colonnes référenceées dans la table des clés primaires. Un index non-unique est automatiquement créé sur les colonnes referencées. Exemple :
CREATE TABLE child(c1 INTEGER, c2 VARCHAR, FOREIGN KEY (c1, c2) REFERENCES parent(p1, p2));
Ici, il doit y avoir une contrainte UNIQUE sur les colonnes (p1,p2)dans la table nomée "parent".
Un index non-unique est automatiquement créé sur les colonnes (c1, c2) dans la table nommée "child".
Les colonnes p1 et c1 doivent être du même type (INTEGER).
Les colonnes p2 et c2 doivent être du même type (VARCHAR).
Les indexes sont particulièrement important dans les requetes à jointures multiples. SELECT ... FROM t1 JOIN t2 ON t1.c1 = t2.c2 est executée en prenant les lignes de T1 et en cherchant la corespondance dans t2 une par une. S'il n'y a pas d'index sur t2.c2 alors pour chaque ligne de t1; chaque ligne de t2 doit être pointée. Tandisque avec un index une ligne correspondant peut être trouvée en une fraction de temps.
Si la requete a la condition sur T1,ex: SELECT ... FROM t1 JOIN t2 ON t1.c1 = t2.c2 WHERE t1.c3 = 4 alors un indes sur t1.c3 devrait éliminer des vérifications, toutes les lignes de t1 une par une,et devrait réduire le temps de la requete à moins d'une miliseconde par ligne retournée. Ainsi si t1 et t2 contiennet chacune 10,000 lignes, la requete sans index devant vérifier une combinatoire égale à 100,000,000 lignes. Avec un index sur t2.c2 , cela est réduit à 10,000 lignes à vérifier and index lookups. Avec l'index additionnel sur t2.c2, seulement 4 lignes sont vérifiées pour obtenir la première ligne de résultat.
Les indexes sont automatiquement créés sur les clé primaires et sur les colonnes porteuse de la contrainte UNIQUE. Sinon vous pouvez utiliser la commande CREATE INDEX .
Remarque dans HSQLDB un index unique sur des colonnes multiples peut être utilisé en interne comme un index non-unique sur la premiere colonne de la liste. Par exemple : CONSTRAINT name1 UNIQUE (c1, c2, c3); est équivalent à CREATE INDEX name2 ON atable(c1); Donc vous n'avez pas besoin de spécifier d'index supplementaire sur la premiere colonne de la liste des colonnes visées par un index.
En v 1.8.0, un index multi-colonne augmentera la vitesse des requetes contenant une jointure ou valeur sur toutes les colonnes. (de l'index je suppose)
Vous n'avez pas besoin de declarer d'index individuel sur chacune de ces colonnes tant que vous utilisez des requetes qui recherche seulement un subset de ces colonnes. Par exemple, les lignes d'une tables ayant une PRIMARY KEY ou une contrainte UNIQUE sur 3 colonnes, ou simplement un index ordinaire sur l'une de ces colonnes peut être trouvé efficacement quand les valeur des 3 colonnes sont spécifiées dans les clauses du WHERE .
SELECT ... FROM t1 WHERE t1.c1 = 4 AND t1.c2 = 6 AND t1.c3 = 8 utilisera un index sur t1(c1,c2,c3)s'il existe.
Finalement, le gain du résultat via des indexes sur des clés multiples, l'oredre de déclarations des colonnes dans les indexes ou dans les contraintes a moins d'impacte sur la vitesse de recherche qu'avant. Si la colonne qui contient le plus de valeurs apparit en premier, la rechercher sera d'autant plus rapide.
Un index multi-colonnes n'augmentera pas la vitesse d'interrogation sur la seconde ou sur la troisième colonne uiniquement.. La première colonne doit être spécifiée dans les conditions JOI N, ON ou WHERE.
La vitesse dépend beaucoup de l'ordre des tables dans les jointures. Par exemple la seconde requete ci-dessous devrait être plus facile avec de grosses tables (parce qu'il y a un index sur TB.COL3). Cela est dû au fait que TB.COL3 peut être évalué très rapidement s'il est appliqué à la première table (et il y a un index sur TB.COL3):
(TB is a very large table with only a few rows where TB.COL3 = 4)
SELECT * FROM TA JOIN TB ON TA.COL1 = TB.COL2 AND TB.COL3 = 4;
SELECT * FROM TB JOIN TA ON TA.COL1 = TB.COL2 AND TB.COL3 = 4;
La règle générale et de mettre en premier la table qui a ??? that has a narrowing condition on one of its columns.
en 1.7.3 ces caractèristiques étaient automatique, sur les index volants (???) des vues et les sous select (requete SQL imbriquées) utilisés dans les requetes. Un index est ajouté à une vue lorsqu'elle est joint à une table ou à une autre vue.
Cette requete implique TA.COL1 = TB.COL2 mais ne le met pas explicitement dans ses conditions. Si TA et TB contiennent chacun 100 lignes, 10000 combinaisons seront jointe avec TC pour appliquer la condition sur la colonne,Aussi il devrait y avoir un index pour joindre les colonnes. Avec le mot clé JOIN , la condition TA.COL1 = TB.COL2 est explicite et diminuent d'autant les combinaisons de TA et TB avant de les appliquer à la jointure avec TC , le resultat est beaucoup plus rapoide avec de grosses tables:
SELECT ... FROM TA JOIN TB ON TA.COL1 = TB.COL2 JOIN TC ON TB.COL2 = TC.COL3 WHERE TC.COL4 = 1
La performance peut être encore augmentée en changeant l'ordre des tables,ainsi TC.COL1 = 1 est appliquer en premier et le plus petit jeu de lignes sont jontes par la suite:
SELECT ... FROM TC JOIN TB ON TC.COL3 = TB.COL2 JOIN TA ON TC.COL3 = TA.COL1 WHERE TC.COL4 = 1
Dans cet exemple le moteur applique automatiquement TC.COL4 = 1 à TC et ne fait la jointure avec les autres tables que sur le jeu des lignes répondant à cette condition . Les index sur TC.COL4, TB.COL2 et sur TA.COL1 seront utilisés s'ils sont présents pour accelerer la requete.
Par exemple la seconde requete ci-dessous sera généralement plus efficace (plus rapide) si il existe un index sur TA.COL1 et TB.COL3
Exemple 2.2. Comparaison de requetes
SELECT ... FROM TA WHERE TA.COL1 = (SELECT MAX(TB.COL2) FROM TB WHERE TB.COL3 = 4)
SELECT ... FROM (SELECT MAX(TB.COL2) C1 FROM TB WHERE TB.COL3 = 4) T2 JOIN TA ON TA.COL1 = T2.C1
La seconde requete execute MAX(TB.COL2)dans une seule ligne de la table puis fais la jointure avec TA. Avec une index sur TA.COL1 cela sera vraiment très rapide.
La première requete testera chaque ligne TA et evaluera MAX(TB.COL2)encore et encore.
Les anciennes versions de HSQLDB etaient pauvres en matière de gestion des opérations arithmetiques. Par exemple il n'etait pas possible d'inserer 10/2.5 dans un DOUBLE ou un DECIMAL
Depuis la versione 1.7.0, les opérations sont pleinement possible avec les regles suivantes:
TINYINT, SMALLINT, INTEGER, BIGINT, NUMERIC et DECIMAL (sans le point decimal) supportent les types integral, et le mappage de byte, short, int, long et BigDecimal dans Java.
The SQL type dictates the maximum and minimum values that can be held in a field of each type. For example the value range for TINYINT is -128 to +127, although the actual Java type used for handling TINYINT is java.lang.Integer.
REAL, FLOAT, DOUBLE are all mapped to double in Java.
DECIMAL and NUMERIC are mapped to java.math.BigDecimal and can have very large numbers of digits.
If the SELECT statement refers to a simple column or function, then the return type is the type corresponding to the column or the return type of the function. For example:
CREATE TABLE t(a INTEGER, b BIGINT); SELECT MAX(a), MAX(b) FROM t;
would return a result set where the type of the first column is java.lang.Integer and the second column is java.lang.Long. However,
SELECT MAX(a) + 1, MAX(b) + 1 FROM t;
would return java.lang.Long and BigDecimal values, generated as a result of uniform type promotion for all the return values.
There is no built-in limit on the size of intermediate integral values in expressions. As a result, you should check for the type of the ResultSet column and choose an appropriate getXXXX() method to retrieve it. Alternatively, you can use the getObject() method, then cast the result to java.lang.Number and use the intValue() or longValue() methods on the result.
When the result of an expression is stored in a column of a database table, it has to fit in the target column, otherwise an error is returned. For example when 1234567890123456789012 / 12345687901234567890 is evaluated, the result can be stored in any integral type column, even a TINYINT column, as it is a small value.
In SQL statements, numbers with a decimal point are treated as DECIMAL unless they are written with an exponent. Thus 0.2 is considered a DECIMAL value but 0.2E0 is considered a DOUBLE value.
When PreparedStatement.setDouble() or setFloat() is used, the value is treated as a DOUBLE automatically.
When a REAL, FLOAT or DOUBLE (all synonymous) is part of an expression, the type of the result is DOUBLE.
Otherwise, when no DOUBLE value exists, if a DECIMAL or NUMERIC value is part an expression, the type of the result is DECIMAL. The result can be retrieved from a ResultSet in the required type so long as it can be represented. This means DECIMAL values can be converted to DOUBLE unless they are beyond the Double.MIN_VALUE - Double.MAX_VALUE range. Similar to integral values, when the result of an expression is stored in a table column, it has to fit in the target column, otherwise an error is returned.
The distinction between DOUBLE and DECIMAL is important when a division takes place. When the terms are DECIMAL, the result is a value with a scale (number of digits to the right of the decimal point) equal to the larger of the scales of the two terms. With a DOUBLE term, the scale will reflect the actual result of the operation. For example, 10.0/8.0 (DECIMAL) equals 1.2 but 10.0E0/8.0E0 (DOUBLE) equals 1.25. Without division operations, DECIMAL values represent exact arithmetic; the resulting scale is the sum of the scales of the two terms when multiplication is performed.
REAL, FLOAT and DOUBLE values are all stored in the database as java.lang.Double objects. Special values such as NaN and +-Infinity are also stored and supported. These values can be submitted to the database via JDBC PreparedStatement methods and are returned in ResultSet objects.
Since 1.7.2, BIT is simply an alias for BOOLEAN. The primary representation of BOOLEAN column is 'true' or 'false' either as the boolean type or as strings when used from JDBC. This type of column can also be initialised using values of any numeric type. In this case 0 is translated to false and any other value such as 1 is translated to true.
Since 1.7.3 the BOOLEAN type conforms to the SQL standards and supports the UNDEFINED state in addition to TRUE or FALSE. NULL values are treated as undefined. This improvement affects queries that contain NOT IN. See the test text file, TestSelfNot.txt, for examples of the queries.
Since version 1.7.2 this support has improved and any serializable JAVA Object can be inserted directly into a column of type OTHER using any variation of PreparedStatement.setObject() methods.
For comparison purposes and in indexes, any two Java Objects are considered equal unless one of them is NULL. You cannot search for a specific object or perform a join on a column of type OTHER.
Please note that HSQLDB is not an object-relational database. Java Objects can simply be stored internally and no operations should be performed on them other than assignment between columns of type OTHER or tests for NULL. Tests such as WHERE object1 = object2, or WHERE object1 = ? do not mean what you might expect, as any non-null object would satisfy such a tests. But WHERE object1 IS NOT NULL is perfectly acceptable.
The engine does not return errors when normal column values are assigned to Java Object columns (for example assigning an INTEGER or STRING to such a column with an SQL statement such as UPDATE mytable SET objectcol = intcol WHERE ...) but this is highly likely to be disallowed in future. So please use columns of type OTHER only to store your objects and nothing else.
Prior to 1.7.2, all table column type definitions with a column size, precision or scale qualifier were accepted and ignored.
In 1.8.0, such qualifiers must conform to the SQL standards. For example INTEGER(8) is no longer acceptable. The qualifiers are still ignored unless you set a database property. SET PROPERTY "sql.enforce_strict_size" TRUE will enforce sizes for CHARACTER or VARCHAR columns and pad any strings when inserting or updating a CHARACTER column. The precision and scale qualifiers are also enforced for DECIMAL and NUMERIC types. TIMESTAMP can be used with a precision of 0 or 6 only.
Casting a value to a qualified CHARACTER type will result in truncation or padding as you would expect. So a test such as CAST (mycol AS VARCHAR(2)) = 'xy' will find the values beginning with 'xy'. This is the equivalent of SUBSTRING(mycol FROM 1 FOR 2) = 'xy'.
The SEQUENCE keyword was introduced in 1.7.2 with a subset of the SQL 200n standard syntax. Corresponding SQL 200n syntax for IDENTITY columns has also been introduced.
Each table can contain one auto-increment column, known as the IDENTITY column. An IDENTITY column is always treated as the primary key for the table (as a result, multi-column primary keys are not possible with an IDENTITY column present). Support has been added for CREATE TABLE <tablename>(<colname> IDENTITY, ...) as a shortcut.
Since 1.7.2, the SQL standard syntax is used by default, which allows the initial value to be specified. The supported form is(<colname> INTEGER GENERATED BY DEFAULT AS IDENTITY(START WITH n, [INCREMENT BY m])PRIMARY KEY, ...). Support has also been added for BIGINT identity columns. As a result, an IDENTITY column is simply an INTEGER or BIGINT column with its default value generated by a sequence generator.
When you add a new row to such a table using an INSERT INTO <tablename> ...; statement, you can use the NULL value for the IDENTITY column, which results in an auto-generated value for the column. The IDENTITY() function returns the last value inserted into any IDENTITY column by this connection. Use CALL IDENTITY(); as an SQL statement to retrieve this value. If you want to use the value for a field in a child table, you can use INSERT INTO <childtable> VALUES (...,IDENTITY(),...);. Both types of call to IDENTITY() must be made before any additional update or insert statements are issued on the database.
The next IDENTITY value to be used can be set with the
ALTER TABLE ALTER COLUMN <column name> RESTART WITH <new value>;
The SQL 200n syntax and usage is different from what is supported by many existing database engines. Sequences are created with the CREATE SEQUENCE command and their current value can be modified at any time with ALTER SEQUENCE. The next value for a sequence is retrieved with the NEXT VALUE FOR <name> expression. This expression can be used for inserting and updating table rows. You can also use it in select statements. For example, if you want to number the returned rows of a SELECT in sequential order, you can use:
Example 2.3. Numbering returned rows of a SELECT in sequential order
SELECT NEXT VALUE FOR mysequence, col1, col2 FROM mytable WHERE ...
Please note that the semantics of sequences is not exactly the same as defined by SQL 200n. For example if you use the same sequence twice in the same row insert query, you will get two different values, not the same value as required by the standard.
You can query the SYSTEM_SEQUENCES table for the next value that will be returned from any of the defined sequences. The SEQUENCE_NAME column contains the name and the NEXT_VALUE column contains the next value to be returned.
HSQLDB supports transactions at the READ_UNCOMMITTED level, also known as level 0 transaction isolation. This means that during the lifetime of a transaction, other connections to the database can see the changes made to the data. Transaction support works well in general. Reported bugs concerning transactions being committed if the database is abruptly closed have been fixed. However, the following issues may be encountered only with multiple connections to a database using transactions:
If two transactions modify the same row, no exception is raised when both transactions are committed. This can be avoided by designing your database in such a way that application data consistency does not depend on exclusive modification of data by one transaction. You can set a database property to cause an exception when this happens.
SET PROPERTY "sql.tx_no_multi_rewrite" TRUEWhen an ALTER TABLE .. INSERT COLUMN or DROP COLUMN command results in changes to the table structure, the current session is committed. If an uncommitted transaction started by another connections has changed the data in the affected table, it may not be possible to roll it back after the ALTER TABLE command. This may also apply to ADD INDEX or ADD CONSTRAINT commands. It is recommended to use these ALTER commands only when it is known that other connections are not using transactions.
After a CHECKPOINT command is issued, uncommitted transactions can be continued, committed, or rolled back. However, if the database is not subsequently closed properly with the SHUTDOWN command, any such transaction that still remains uncommitted at the time of shutdown, is part committed (to the state at CHECKPOINT) at the next startup. It is recommended to use the CHECKPOINT command either when no uncommitted transactions is in progress, or it is known that any such transaction is not likely to last for such a long time that an abnormal shutdown might affect its data.
In recent versions leading to 1.8.0 many enhancements were made for better SQL support. These are listed in the SQL Syntax chapter, in ../changelog_1_8_0.txt and ../changelog_1_7_2.txt. Functions and expressions such as POSITION(), SUBSTRING(), NULLIF(), COALESCE(), CASE ... WHEN .. ELSE, ANY, ALL etc. are among them. Other enhancements may not be very obvious in the documentation but can result in changes of behaviour from previous versions. Most significant among these are handling of NULL values in joins (null columns are no longer joined) and OUTER joins (the results are now correct). You should test your applications with the new version to ensure they do not rely on past incorrect behaviour of the engine. The engine will continue to evolve in future versions towards full SQL standard support, so it is best not to rely on any non-standard feature of the current version.
Table of Contents
This chapter explains how to quickly install, run, and use HSQLDB on UNIX.
HSQLDB has lots of great optional features. I intend to cover very few of them. I do intend to cover what I think is the most common UNIX setup: To run a multi-user database with permament data persistence. (By the latter I mean that data is stored to disk so that the data will persist across database shutdowns and startups). I also cover how to run HSQLDB as a system daemon.
Go to http://sourceforge.net/projects/hsqldb and click on the "files" link. You want the current version. This will be the highest numbered version under the plain black "hsqldb" heading. See if there's a distribution for the current HSQLDB version in the format that you want.
If you want an rpm, you should still find out the current version of HSQLDB as described in the previous paragraph. Then click "hsqldb" in the "free section" of http://www.jpackage.org/ and see if they have the current HSQLDB version built yet. Hopefully, the JPackage folk will document what JVM versions their rpm will support (currently they document this neither on their site nor within the package itself). (I really can't document how to download from a site that is totally beyond my control).
It could very well happen that some of the file formats which I discuss below are not in fact offered. If so, then we have not gotten around to building them.
Binary installation depends on the package format that you downloaded.
This package is only for use by a Solaris super-user. It's a System V package. Download then uncompress the package with uncompress or gunzip
uncompress filename.pkg.Z
pkginfo -l -d filename.pkg
pkgadd -d filename.pkg
This is a Linux rpm package. After you download the rpm, you can read about it by running
rpm -qip /path/to/file.rpm
Rpms can be installed or upgraded by running
rpm -Uvh /path/to/file.rpm
Extract the zip file to the parent directory of the new HSQLDB home. You don't need to create the HSQLDB_HOME directory because the extraction will create it for you with the right name)
cd parent/of/new/hsqldb/home
unzip /path/to/file.zip
All the files in the zip archive will be extracted to underneath a new hsqldb directory.
Take a look at the files you installed. (Under hsqldb for zip file installations. Otherwise, use the utilities for your packaging system). The most important file of the hsqldb system is hsqldb.jar, which resides in the directory lib.
For the purposes of this chapter, I define HSQLDB_HOME to be the parent directory of the lib directory that contains hsqldb.jar. E.g., if your path to hsqldb.jar is /a/b/hsqldb/lib/hsqldb.jar, then your HSQLDB_HOME is /a/b/hsqldb.
If the description of your distribution says that the hsqldb.jar file will work for your Java version, then you are finished with installation. Otherwise you need to build a new hsqldb.jar file.
If you followed the instructions above and you still don't know what Java version your hsqldb.jar supports, then read HSQLDB_HOME/readme.txt and HSQLDB_HOME/index.html. If that still doesn't help, then you can just try your hsqldb.jar and see if it works, or build your own.
To use the supplied hsqldb.jar, just skip to the next section of this document. Otherwise build a new hsqldb.jar.
Procedure 3.1. Building hsqldb.jar
If you don't already have Ant, download the latest stable binary version from http://ant.apache.org. cd to where you want Ant to live, and extract from the archive with
unzip /path/to/file.zip
tar -xzf /path/to/file.tar.gz
bunzip2 -c /path/to/file.tar.bz2 | tar -xzf -
Set the environmental variable JAVA_HOME to the base directory of your Java JRE or SDK, like
export JAVA_HOME; JAVA_HOME=/usr/java/j2sdk1.4.0
Remove the existing file HSQLDB_HOME/lib/hsqldb.jar.
cd to HSQLDB_HOME/build. Make sure that the bin directory under your Ant home is in your search path. Run the following command.
ant hsqldb
See the Building HSQLDB appendix if you want to build anything other than hsqldb.jar with all default settings.
If you installed from an OS-specific package, you may already have a database instance and server pre-configured. See if your package includes a file named server.properties (make use of your packaging utilities). If you do, then I suggest that you still read this section while you poke around, in order to understand your setup.
Select a UNIX user to run the database as. If this database is for the use of multiple users, or is a production system (or to emulate a production system), you should dedicate a UNIX user for this purpose. In my examples, I use the user name hsqldb. In this chapter, I refer to this user as the HSQLDB_OWNER, since that user will own the database instance files and processes.
If the account doesn't exist, then create it. On all system-5 UNIXes and most hybrids (including Linux), you can run (as root) something like
useradd -c 'HSQLDB Database Owner' -s /bin/bash -m hsqldb
Become the HSQLDB_OWNER. Copy the sample file HSQLDB_HOME/src/org/hsqldb/sample/sample-server.properties to the HSQLDB_OWNER's home directory and rename it to server.properties.
# Hsqldb Server cfg file. # See the Advanced Topics chapter of the Hsqldb User Guide. server.database.0 file:db0/db0
Since the value of the first database (server.database.0) begins with file:, the database instance will be persisted to a set of files in the specified directory with names beginning with the specified name. Set the path to whatever you want (relative paths will be relative to the directory containing the properties file). You can read about how to specify other database instances of various types, and how to make settings for the listen port and many other things, in the Advanced Topics chapter.
Set and export the environmental variable CLASSPATH to the value of HSQLDB_HOME (as described above) plus "/lib/hsqldb.jar", like
export CLASSPATH; CLASSPATH=/path/to/hsqldb/lib/hsqldb.jar
nohup java org.hsqldb.Server &
This will start the Server process in the background, and will create your new database instance "db0". Continue on when you see the message containing HSQLDB server... is online. nohup just makes sure that the command will not quit when you exit the current shell (omit it if that's what you want to do).
Copy the file HSQLDB_HOME/src/org/hsqldb/sample/sqltool.rc to the HSQLDB_OWNER's home directory. Use chmod to make the file readable and writable only to HSQLDB_OWNER.
# $Id: sqltool.rc,v 1.14 2005/05/22 04:46:16 unsaved Exp $ # This is a sample RC configuration file used by SqlTool, DatabaseManager, # and any other program that uses the org.hsqldb.util.RCData class. # You can run SqlTool right now by copying this file to your home directory # and running # java -jar /path/to/hsqldb.jar mem # This will access the first urlid definition below in order to use a # personal Memory-Only database. # If you have the least concerns about security, then secure access to # your RC file. # See the documentation for SqlTool for various ways to use this file. # A personal Memory-Only database. urlid mem url jdbc:hsqldb:mem:memdbid username sa password # This is for a hsqldb Server running with default settings on your local # computer (and for which you have not changed the password for "sa"). urlid localhost-sa url jdbc:hsqldb:hsql://localhost username sa password # Template for a urlid for an Oracle database. # You will need to put the oracle.jdbc.OracleDriver class into your # classpath. # In the great majority of cases, you want to use the file classes12.zip # (which you can get from the directory $ORACLE_HOME/jdbc/lib of any # Oracle installation compatible with your server). # Since you need to add to the classpath, you can't invoke SqlTool with # the jar switch, like "java -jar .../hsqldb.jar..." or # "java -jar .../hsqlsqltool.jar...". # Put both the HSQLDB jar and classes12.zip in your classpath (and export!) # and run something like "java org.hsqldb.util.SqlTool...". #urlid cardiff2 #url jdbc:oracle:thin:@aegir.admc.com:1522:TRAFFIC_SID #username blaine #password secretpassword #driver oracle.jdbc.OracleDriver # Template for a TLS-encrypted HSQLDB Server. # Remember that the hostname in hsqls (and https) JDBC URLs must match the # CN of the server certificate (the port and instance alias that follows # are not part of the certificate at all). # You only need to set "truststore" if the server cert is not approved by # your system default truststore (which a commercial certificate probably # would be). #urlid tls #url jdbc:hsqldb:hsqls://db.admc.com:9001/lm2 #username blaine #password asecret #truststore /home/blaine/ca/db/db-trust.store # Template for a Postgresql database #urlid blainedb #url jdbc:postgresql://idun.africawork.org/blainedb #username blaine #password losung1 #driver org.postgresql.Driver # Template for a MySQL database #urlid mysql-testdb #url jdbc:mysql:///test #username root #username blaine #password hiddenpwd #driver com.mysql.jdbc.Driver
We will be using the "localhost-sa" sample urlid definition from the config file. The JDBC URL for this urlid is jdbc:hsqldb:hsql://localhost. That is the URL for the default database instance of a HSQLDB Server running on the default port of the local host. You can read about URLs to connect to other instances and other servers in the Advanced Topics chapter.
Run SqlTool.
java -jar path/to/hsqldb.jar localhost-sa
set password "newpassword";
When you're finished playing, exit with the command \q.
If you changed the SA password, then you need to fix the password in the sqltool.rc file accordingly.
You can, of course, also access the database with any JDBC client program. See the First JDBC Client Example appendix. You will need to modify your classpath to include hsqldb.jar as well as your client class(es). You can also use the other HSQLDB client programs, such as org.hsqldb.util.DatabasManagerSwing, a graphical client with a similar purpose to SqlTool.
You can use any normal UNIX account to run the JDBC clients, including SqlTool, as long as the account has read access to the hsqldb.jar file and to an sqltool.rc file. See the SqlTool chapter about where to put sqltool.rc, how to execute sql files, and other SqlTool features.
Connect to the database as SA (or any other Administrative user) and run CREATE USER to create new accounts for your database instance. HSQLDB accounts are database-instance-specific, not Server-specific.
For the current version of HSQLDB, only users with Role of DBA may create or own database objects. DBA members have privileges to do anything. Non-DBAs may be granted some privileges, but may never create or own database objects. (Before long, non-DBAs will be able to create objects if they have permission to do so in the target schema). When you first create a hsqldb database, it has only one database user-- SA, a DBA account, with an empty string password. You should set a password (as described above). You can create as many additional users as you wish. To make a user a DBA, you can use the "ADMIN" option to the CREATE USER command, or GRANT the DBA Role to the account after creating it.
If you create a user without the ADMIN tag (and without granting the DBA role to them) this user will be able to read the data dictionary tables, but will be able unable to create or own his own objects. He will have only the rights which the pseudo-user PUBLIC has. To give him more permissions, even rights to read objects, you can GRANT permissions for specific objects, grant Roles (which encompass a set of permissions), or grant the DBA Role itself.
Since only people with a database account may do anything at all with the database, it is often useful to permit other database users to view the data in your tables. To optimize performance, reduce contention, and minimize administration, it is often best to grant SELECT to PUBLIC on any object that needs to be accessed by multiple database users (with the significant exception of any data which you want to keep secret).
Do a clean database shutdown when you are finished with the database instance. You need to connect up as SA or some other Admin user, of course. With SqlTool, you can run
java -jar path/to/hsqldb.jar --sql shutdown localhost-sa
You can, of course, run HSQLDB through inittab on System V UNIXes, but usually an init script is more convenient and manageable. This section explains how to set up and use our UNIX init script. Our init script is only for use by root. (That is not to say that the Server will run as root-- it usually should not).
The main purpose of the init script is to start up a Server with the database instances specified in your server.properties file; and to shut down all of those instances plus additional urlids which you may (optionally) list in your init script config file. These urlids must all have entries in a sqltool.rc file. If, due to firewall issues, you want to run a WebServer instead of a Server, then make sure you have a healthy WebServer with a webserver.properties set up, adjust your URLs in sqltool.rc, and set TARGET_CLASS in the config file. (By following the commented examples in the config file, you can start up any number of Server and/or WebServer listeners with or without TLS ecryption).
After you have the init script set up, root can use it anytime to start or stop HSQLDB. (I.e., not just at system bootup or shutdown).
The primary design criterion of the init script is portability. It does not print pretty color startup/shutdown messages as is common in late-model Linuxes and HPUX; and it does not keep subsystem state files or use the startup/shutdown functions supplied by many UNIXes, because these features are all non-portable.
Offsetting these limitations, this one script does it's intended job great on the UNIX varieties I have tested, and can easily be modified to accommodate other UNIXes. While you don't have tight integration with OS-specific daemon administration guis, etc., you do have a well tested and well behaved script that gives good, utilitarian feedback.
The strategy taken here is to get the init script to run your single Server or WebServer first (as specified by TARGET_CLASS). After that's working, you can customize the JVM that is run by running additional Servers in it, running your own application in it (embedding), or even overriding HSQLDB behavior with your own overriding classes.
Copy the init script hsqldb from HSQLDB_HOME/bin into the directory where init scripts live on your variety of UNIX. The most common locations are /etc/init.d or /etc/rc.d/init.d on System V style UNIXes, /usr/local/etc/rc.d on BSD style UNIXes, and /Library/StartupItems/hsqldb on OS X (you'll need to create the directory for the last).
Look at the comment towards the top of the init script which lists recommended locations for the configuration file for various UNIX platforms. Copy the sample config file HSQLDB_HOME/src/org/hsqldb/sample/sample-hsqldb.cfg to one of the listed locations (your choice). Edit the config file according to the instructions in it.
# $Id: sample-hsqldb.cfg,v 1.16 2005/07/24 18:33:13 unsaved Exp $ # Sample configuration file for HSQLDB database server. # See the "UNIX Quick Start" chapter of the Hsqldb User Guide. # N.b.!!!! You must place this in the right location for your type of UNIX. # See the init script "hsqldb" to see where this must be placed and # what it should be renamed to. # This file is "sourced" by a Bourne shell, so use Bourne shell syntax. # This file WILL NOT WORK until you set (at least) the non-commented # variables to the appropriate values for your system. # Life will be easier if you avoid all filepaths with spaces or any other # funny characters. Don't ask for support if you ignore this advice. # Thanks to Meikel Bisping for his contributions. -- Blaine JAVA_EXECUTABLE=/usr/bin/java # Unless you copied a hsqldb.jar file from another system, this typically # resides at $HSQLDB_HOME/lib/hsqldb.jar, where $HSQLDB_HOME is your HSQLDB # software base directory. HSQLDB_JAR_PATH=/opt/hsqldb/lib/hsqldb.jar # Where the file "server.properties" resides. SERVER_HOME=/opt/hsqldb/data # What UNIX user the server will run as. # (The shutdown client is always run as root or the invoker of the init script). # Runs as root by default, but you should take the time to set database file # ownerships to another user and set that user name here. HSQLDB_OWNER=hsqldb # The HSQLDB jar file specified in HSQLDB_JAR_PATH above will automatically # be in the class path. This arg specifies additional classpath elements. # To embed your own application, add your jar file(s) or class base # directories here, and add your main class to the INVOC_ADDL_ARGS setting # below. #SERVER_ADDL_CLASSPATH=/usr/local/dist/currencybank.jar # We require all Server/WebServer instances to be accessible within # $MAX_START_SECS from when the Server/WebServer is started. # Defaults to 60. # Raise this is you are running lots of DB instances or have a slow server. #MAX_START_SECS=200 # Time to allow for JVM to die after all HSQLDB instances stopped. # Defaults to 1. #MAX_TERMINATE_SECS=0 # These are "urlid" values from a SqlTool authentication file # ** IN ADDITION TO THOSE IN YOUR server.properties OR webserver.properties ** # file. All server.urlid.X values from your properties file will automatically # be started/stopped/tested. $SHUTDOWN_URLIDS is for additional urlids which # will stopped. (Therefore, most users will not set this at all). # Separate multiple values with white space. NO OTHER SPECIAL CHARACTERS! # Make sure to quote the entire value if it contains white space separator(s). # Defaults to none (i.e., only urlids set in properties file will be stopped). #SHUTDOWN_URLIDS='sa mygms' # SqlTool authentication file used only for shutdown. # The default value will be sqltool.rc in root's home directory, since it is # root who runs the init script. # (See the SqlTool chapter of the HSQLDB User Guide if you don't understand # this). #AUTH_FILE=/home/blaine/sqltool.rc # Set this to either 'WebServer' or 'Server'. Defaults to Server. # The JVM that is started can invoke many classes (see the following item # about that), but this is the Server that is used (1) to check status, # (2) to shut down the JVM, (3) to get urlids for #1 from the # server's server/webserver.properties file. #TARGET_CLASS=WebServer # Note that you don't specify the org.hsqldb package, since you have no # choice in the matter (you can only run org.hsqldb.Server or # org.hsqldb.WebServer). If you specify additional classes with # INVOC_ADDL_ARGS (described next), you do need to specify the # full class name with package name. # This is where you specify exactly what your HSQLDB JVM will run. # The class org.hsqldb.util.MainInvoker will run the TARGET_CLASS # specified above with any arguments supplied here + any other classes # and arguments. Every additional class (in addition to the TARGET_CLASS) # must be preceded with an empty string, so that MainInvoker will know # you are giving a class name. MainInvoker will invoke the normal # static main(String[]) method of each such class. # By default, MainInvoker will just run TARGET_CLASS with no args. # Example that runs just the TARGET_CLASS with the specified arguments: #INVOC_ADDL_ARGS='-silent false' # Example that runs the TARGET_CLASS plus a WebServer: #INVOC_ADDL_ARGS='"" org.hsqldb.WebServer' # Note the empty string preceding the class name. # Example that starts TARGET_CLASS with an argument + a WebServer + # your own application with its args (i.e., the HSQLDB Servers are # "embedded" in your application). (Set SERVER_ADDL_CLASSPATH too).: #INVOC_ADDL_ARGS='-silent false "" org.hsqldb.WebServer "" com.acme.Stone --env prod localhost' # Example to run a non-TLS server in same JVM with a TLS server. In this # case, TARGET_CLASS is Server which will run in TLS mode by virtue of # setting TLS_KEYSTORE and TLS_PASSWORD above. The "additional" Server # here overrides the 'tls' and 'port' settings: #INVOC_ADDL_ARGS="'' org.hsqldb.Server -port 9002 -tls false" # Note that you use nested quotes to group arguments and to specify the # empty-string delimiter. # For TLS encryption for your Server, set these two variables. # N.b.: If you set these, then make this file unreadable to non-root users!!!! # See the TLS chapter of the HSQLDB User Guide, paying attention to the # security warning(s). # If you are running with a private server cert, then you will also need to # set "truststore" in the your SqlTool config file (location is set by the # AUTH_FILE variable in this file, or it must be at the default location for # HSQLDB_OWNER). #TLS_KEYSTORE=/path/to/jks/server.store #TLS_PASSWORD=password # Any JVM args for the invocation of the JDBC client used to verify DB # instances and to shut them down (SqlToolSprayer). # This example specifies the location of a private trust store for TLS # encryption. # For multiple args, put quotes around entire value. #CLIENT_JVMARGS=-Djavax.net.debug=ssl # Any JVM args for the server. # For multiple args, put quotes around entire value. #SERVER_JVMARGS=-Xmx512m
Either copy HSQLDB_OWNER's sqltool.rc file into root's home directory, or set the value of AUTH_FILE to the absolute path of HSQLDB_OWNER's sqltool.rc file. This file is read (for stops) directly by root, even if you run hsqldb as non-root (by setting HSQLDB_OWNER in the config file). If you copy the file, make sure to use chmod to restrict permissions on the new copy. (The init script now enforces permissions on this file).
Edit your server.properties file. For every server.database.X that you have defined, set a property of name server.urlid.X to the urlid for an Administrative user for that database instance.
Example 3.1. server.properties fragment
server.database.0=file://home/hsqldb/data/db1
server.urlid.0=localhostdb1
Make sure to add a urlid for each and every database instance. If you don't then the init script will never know about databases that become inaccessible and will give false diagnostics.
For this example, you would need to define the urlid localhostdb1 in your sqltool.rc file.
Verify that the init script works.
Just run
/path/to/hsqldb
/path/to/hsqldb status
at any time to see whether your HSQLDB Server is running.
Re-run the script with each of the possible arguments to really test it good. If anything doesn't work right, then see the Troubleshooting the Init Script section.
Tell your OS to run the init script upon system startup and shutdown. If you are using a UNIX variant that has /etc/rc.conf or /etc/rc.conf.local (like BSD variants and Gentoo), you must set "hsqldb_enable" to "YES" in either of those files. (Just run cd /etc; ls rc.conf rc.conf.local to see if you have one of these files). For good UNIXes that use System V style init, you must set up hard links or soft links either manually or with management tools (such as chkconfig or insserv) or Gui's (like run level editors).
This paragraph is for Mac OS X users only. If you followed the instructions above, your init script should reside at /Library/StartupItems/hsqldb/hsqldb. Now copy the file StartupParameters.plist from the directory src/org.hsqldb/sample of your HSQLDB distribution to the same directory as the init script. As long as these two files reside in /Library/StartupItems/hsqldb, your init script is active (for portability reasons, it doesn't check for a setting in /etc/hostconfig). You can run it as a Startup Item by running
SystemStarter {start|stop|restart} Hsqldb
Hsqldb is the service name. See the man page for SystemStarter. To disable the init script, wipe out the /Library/StartupItems/hsqldb directory. Hard to believe, but the Mac people tell me that during system shutdown the Startup Items don't run at all. Therefore, if you don't want your data corrupted, make sure to run "SystemStarter stop Hsqldb" before shutting down your Mac.
Follow the examples in the config file to add additional classes to the server JVM's classpath and to execute additional classes in your JVM. (See the SERVER_ADDL_CLASSPATH and INVOC_ADDL_ARGS items).
Do a ps to look for processes containing the string hsqldb, and try to connect to the database from any client. If the init script starts up your database successfully, but incorrectly reports that it has not, then your problem is with specification of urlid(s) or SqlTool setup. If your database really did not start, then skip to the next paragraph. Verify that the urlid(s) listed in the server.properties or webserver.properties are correct. and verify that you can run SqlTool as root to connect to the instances. (For the latter test, use the --rcfile switch if you are setting AUTH_FILE in the init script config file).
If your database really is not starting, then verify that you can su to the database owner account and start the database. The command su USERNAME -c ... won't work on most UNIXes unless the target user has a real login shell. Therefore, if you try to tighten up security by disabling this user's login shell, you will break the init script. If these possibilities don't pan out, then debug the init script or seek help, as described below.
To debug the init script, run it in verbose mode to see exactly what is happening (and perhaps manually run the steps that are suspect). To run an init script (in fact, any sh shell script) in verbose mode, use sh with the -x or -v switch, like
sh -x path/to/hsqldb start
See the man page for sh if you don't know the difference between -v and -x.
If you want troubleshooting help, use the HSQLDB lists/forums or email me at blaine.simpson@admc.com. If you email me, make sure to include the revision number from your hsqldb init script (it's towards the top in the line that starts like "# $Id:"), and the output of a run of
sh -x path/to/hsqldb start > /tmp/hstart.log 2>&1
Copyright 2002-2005 Fred Toussi. Permission is granted to distribute this document without any alteration under the terms of the HSQLDB license. Additional permission is granted to the HSQLDB Development Group to distribute this document with or without alterations under the terms of the HSQLDB license.
$Date: 2005/06/30 22:38:54 $
Table of Contents
Many questions repeatedly asked in Forums and mailing lists are answered in this guide. If you want to use HSQLDB with your application, you should read this guide. This document covers system related issues. For issues related to SQL see the SQL Issues chapter.
The normal method of accessing an HSQLDB database is via the JDBC Connection interface. An introduction to different methods of providing database services and accessing them can be found in the SQL Issues chapter. Details and examples of how to connect via JDBC are provided in our JavaDoc for jdbcConnection.
Version 1.7.2 introduced a uniform method of distinguishing between different types of connection, alongside new capabilities to provide access to multiple databases. The common driver identifier is jdbc:hsqldb: followed by a protocol identifier (mem: file: res: hsql: http: hsqls: https:) then followed by host and port identifiers in the case of servers, then followed by database identifier.
Table 4.1. Hsqldb URL Components
| Driver and Protocol | Host and Port | Database | ||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
not available |
|
||||||||||
|
Lowercase, single-word identifier creates the in-memory database when the first connection is made. Subsequent use of the same Connection URL connects to the existing DB. The old form for the URL, jdbc:hsqldb:. creates or connects to the same database as the new form for the URL, jdbc:hsqldb:mem:. |
||||||||||||
|
not available |
|
||||||||||
|
The file path specifies the database file. In the above examples the first one refers to a set of mydb.* files in the directory where the javacommand for running the application was issued. The second and third examples refer to absolute paths on the host machine. |
||||||||||||
|
not available |
|
||||||||||
| Database files can be loaded from one of the jars specified as part of the Java command the same way as resource files are accessed in Java programs. The /adirectory above stands for a directory in one of the jars. | ||||||||||||
|
|
|
||||||||||
|
The host and port specify the IP address or host name of the server and an optional port number. The database to connect to is specified by an alias. This alias is a lowercase string defined in the server.properties file to refer to an actual database on the file system of the server or a transient, in-memory database on the server. The following example lines in server.properties or webserver.properties define the database aliases listed above and accessible to clients to refer to different file and in-memory databases.
database.0=file:/opt/db/accounts
dbname.0=an_alias
database.1=file:/opt/db/mydb
dbname.1=enrollments
database.2=mem:adatabase
dbname.2=quickdb
The old form for the server URL, e.g., jdbc:hsqldb:hsql//localhost connects to the same database as the new form for the URL, jdbc:hsqldb:hsql//localhost/ where the alias is a zero length string. In the example below, the database files lists.* in the /home/dbmaster/ directory are associated with the empty alias:
database.3=/home/dbmaster/lists
dbname.3=
|
||||||||||||
Each new JDBC Connection to a database can specify connection properties. The properties user and password are always required. In 1.8.0 the following optional properties can also be used.
Connection properties are specified either by establishing the connection via the:
DriverManager.getConnection (String url, Properties info);
method call, or the property can be appended to the full Connection URL.
Table 4.2. Connection Properties
| get_column_name | true | column name in ResultSet |
|
This property is used for compatibility with other JDBC driver implementations. When true (the default), ResultSet.getColumnName(int c) returns the underlying column name When false, the above method returns the same value as ResultSet.getColumnLabel(int column) Example below:
jdbc:hsqldb:hsql://localhost/enrollments;get_column_name=false
When a ResultSet is used inside a user-defined stored procedure, the default, true, is always used for this property. |
||
| ifexists | false | connect only if database already exists |
|
Has an effect only with mem: and file: database. When true, will not create a new database if one does not already exist for the URL. When false (the default), a new mem: or file: database will be created if it does not exist. Setting the property to true is useful when troubleshooting as no database is created if the URL is malformed. Example below:
jdbc:hsqldb:file:enrollments;ifexists=true
|
||
| shutdown | false | shut down the database when the last connection is closed |
|
This mimics the behaviour of 1.7.1 and older versions. When the last connection to a database is closed, the database is automatically shut down. The property takes effect only when the first connection is made to the database. This means the connection that opens the database. It has no effect if used with subsequent, simultaneous connections. This command has two uses. One is for test suites, where connections to the database are made from one JVM context, immediately followed by another context. The other use is for applications where it is not easy to configure the environment to shutdown the database. Examples reported by users include web application servers, where the closing of the last connection conisides with the web app being shut down. |
||
In addition, when a connection to an in-process database creates a new database, or opens an existing database (i.e. it is the first connection made to the database by the application), all the user-defined database properties can be specified as URL properties. This can be used to specify properties to enforce more strict SQL adherence, or to change cache_scale or similar properties before the database files are created. However, for new databases, it is recommended to use the SET PROPERTY command for such settings.
HSQLDB relies on a set of properties files for different settings. Since 1.7.0 property naming has been streamlined and a number of new properties have been introduced.
In all properties files, values are case-sensitive. All values apart from names of files or pages are required in lowercase (e.g. server.silent=FALSE will have no effect, but server.silent=false will work).
The properties files and the settings stored in them are as follows:
Table 4.3. Hsqldb Server Properties Files
| File Name | Location | Function |
|---|---|---|
| server.properties | the directory where the command to run the Server class is issued | settings for running HSQLDB as a database server communicating with the HSQL protocol |
| webserver.properties | the directory where the command to run the WebServer class is issued | settings for running HSQLDB as a database server communicating with the HTTP protocol |
| <dbname>.properties | the directory where all the files for a database are located | settings for each particular database |
Properties files for running the servers are not created automatically. You should create your own files that contain server.property=value pairs for each property.
The properties file for each database is generated by the database engine. This file can be edited after closing the database. In 1.8.0, most of these properties can be changed via SQL commands.
In both server.properties and webserver.properties files, supported values and their defaults are as follows:
Table 4.4. Property File Properties
| Value | Default | Description |
|---|---|---|
| server.database.0 | test | the path and file name of the first database file to use |
| server.dbname.0 | "" | lowercase server alias for the first database file |
| server.urlid.0 | NONE | SqlTool urlid used by UNIX init script. (This property is not used if your are running Server/Webserver on a platform other than UNIX, or of you are not using our UNIX init script). |
| server.silent | true | no extensive messages displayed on console |
| server.trace | false | JDBC trace messages displayed on console |
In 1.8.0, each server can serve up to 10 different databases simultaneously. The server.database.0 property defines the filename / path whereas the server.dbname.0 defines the lowercase alias used by clients to connect to that database. The digit 0 is incremented for the second database and so on. Values for the server.database.{0-9} property can use the mem:, file: or res: prefixes and properties as discussed above under CONNECTIONS. For example,
database.0=mem:temp;sql.enforce_strict_size=true;
Values specific to server.properties are:
Table 4.5. Server Property File Properties
| Value | Default | Description |
|---|---|---|
| server.port | 9001 | TCP/IP port used for talking to clients. All databases are served on the same port. |
| server.no_system_exit | true | no System.exit() call when the database is closed |
Values specific to webserver.properties are:
Table 4.6. WebServer Property File Properties
| Value | Default | Description |
|---|---|---|
| server.port | 80 | TCP/IP port used for talking to clients |
| server.default_page | index.html | the default web page for server |
| server.root | ./ | the location of served pages |
| .<extension> | ? | multiple entries such as .html=text/html define the mime types of the static files served by the web server. See the source for WebServer.java for a list. |
All the above values can be specified on the command line to start the server by omitting the server. prefix.
If you want to start the server from within your application, as opposed to the command line or batch files, you should create an instance of Server or Web Server, then assign the properties in the form of a String and start the Server. An example of this can be found in the org.hsqldb.test.TestBase source.
Upgrading: If you have existing custom properties files, change the values to the new naming convention. Note the use of digits at the end of server.database.n and server.dbname.n properties.
Each database has its own <dbname>.properties file as part of a small group of files which also includes <dbname>.script and <dbname>.data. The properties files contain key/value pairs for some important settings.
In version 1.8.0 a new SQL command allows most database properties to be modified as follows:
SET PROPERTY "property_name" property_value
Properties that can be modified via SET PROPERTY are indicated in the table below. Other properties are indicated as PROPERTIES FILE ONLY and can be modified only by editing the .properties file after a shutdown and before a restart. Only the user-defined values listed below should ever be modified. Changing any other value could result in unexpected malfunction in database operations. Most of these values have been introduced for the new features since 1.7.0:
Table 4.7. Database-specific Property File Properties
| Value | Default | Description |
|---|---|---|
| readonly | no | whole database is read-only |
|
When true, the database cannot be modified in use. This setting can be changed to yes if the database is to be opened from a CD. Prior to changing this setting, the database should be closed with the SHUTDOWN COMPACT command to ensure consistency and compactness of the data. (PROPERTIES FILE ONLY) but can be used as a connection property to open a normal database as readonly. |
||
| hsqldb.files_readonly | false | database files will not be written to |
|
When true, data in MEMORY tables can be modified and new MEMORY tables can be added. However, these changes are not saved when the database is shutdown. CACHED and TEXT tables are always readonly when this setting is true. (PROPERTIES FILE ONLY) |
||
| hsqldb.cache_file_scale | 1 | Set larger data file limits. Once set, the limit will go up to 8GB. |
|
This property can be set to 8 to increase the size limit of the .data file from 2GB to 8GB. To apply the change to an existing database, SHUTDOWN SCRIPT should be performed first, then the property=value line below should be added to the .properties file before reopening the database. hsqldb.cache_file_scale=8 The property can be set with the SQL command (as opposed to changing the value in the properties file) when the database has no CACHED tables (e.g. a new database). (SET PROPERTY) |
||
| sql.enforce_size | false | trimming and padding string columns |
|
This property is no longer supported. Use sql.enforce_sctrict_size |
||
| sql.enforce_strict_size | false | size enforcement and padding string columns |
|
Conforms to SQL standards for size and precision of data types. When true, all CHARACTER, VARCHAR, NUMERIC and DECIMAL values that are in a row affected by an INSERT INTO or UPDATE statement are checked against the size specified in the SQL table definition. An exception is thrown if the value is too long. Also all CHARACTER values that are shorter than the specified size are padded with spaces. TIMESTAMP(0) and TIMESTAMP(6) are also allowed in order to specify the subsecond resolution of the values. When false (default), stores the exact string that is inserted. (SET PROPERTY) |
||
| sql.tx_no_multi_rewrite | false | transaction management |
|
In the default READ_UNCOMMITED mode, a transaction can write over rows inserted or updated by another uncommitted transaction. Setting this property to true will raise an exception when such a write is attempted (SET PROPERTY) |
||
| hsqldb.cache_scale | 14 | memory cache exponent |
|
Indicates the maximum number of rows of cached tables that are held in memory, calculated as 3 *(2**value) (three multiplied by (two to the power value)). The default results in up to 3*16384 rows from all cached tables being held in memory at any time. The value can range between 8-18. (SET PROPERTY). If the value is set via SET PROPERTY then it becomes effective after the next database SHUTDOWN or CHECKPOINT. (SET PROPERTY) |
||
| hsqldb.cache_size_scale | 10 | memory cache exponent |
|
Indicates the average size of each row in the memory cache used with cached tables, calculated as 2**value (two to the power value). This result value is multiplied by the maximum number of rows defined by hsqldb.cache_scale to form the maximum number of bytes for all the rows in memory cache. The default results in 1024 bytes per row. This default, combined with the default number of rows, results in approximately 50MB of the .data file to be stored in the memory cache. The value can range between 6-20. (SET PROPERTY). If the value is set via SET PROPERTY then it becomes effective after the next database SHUTDOWN or CHECKPOINT. (SET PROPERTY) |
||
| hsqldb.log_size | 200 | size of log when checkpoint is performed |
|
The value is the size in megabytes that the .log file can reach before an automatic checkpoint occurs. A checkpoint and rewrites the .script file and clears the .log file. The value can be changed via the SET LOGSIZE nnn SQL command. |
||
| runtime.gc_interval | 0 | forced garbage collection |
|
This setting forces garbage collection each time a set number of result set row or cache row objects are created. The default, "0" means no garbage collection is forced by the program. This should not be set when the database engine is acting as a server inside an exclusive JVM. The setting can be useful when the database is used in-process with the application with some Java Runtime Environments (JRE's). Some JRE's increase the size of the memory heap before doing any automatic garbage collection. This setting would prevent any unnecessary enlargement of the heap. Typical values for this setting would probably be between 10,000 to 100,000. (PROPERTIES FILE ONLY) |
||
| hsqldb.nio_data_file | true | use of nio access methods for the .data file |
|
When HSQLDB is compiled and run in Java 1.4 or higher, setting this property to false will avoid the use of nio access methods, resulting in somewhat reduced speed. If the data file is larger than 256MB when it is first opened, nio access methods are not used. Also, if the file gets larger than the amount of available computer memory that needs to be allocated for nio access, non-nio access methods are used. (SET PROPERTY). If used before defining any CACHED table, it applies to the current session, otherwise it comes to effect after a SHUTDOWN and restart or CHECKPOINT. |
||
| hsqldb.default_table_type | memory | type of table created with unqualified CREATE TABLE |
|
The CREATE TABLE command results in a MEMORY table by default. Setting the value "cached" for this property will result in a cached table by default. The qualified forms such as CREATE MEMORY TABLE or CREATE CACHED TABLE are not affected at all by this property. (SET PROPERTY) |
||
| hsqldb.applog | 0 | application logging level |
|
The default level 0 indicates no logging. Level 1 results in events related to persistence to be logged, including any failures. The events are logged in a file ending with .app.log |
||
| textdb.* | 0 | default properties for new text tables |
|
Properties that override the database engine defaults for newly created text tables. Settings in the text table SET <tablename> SOURCE <source string> command override both the engine defaults and the database properties defaults. Individual textdb.* properties are listed in the Text Tables chapter. (SET PROPERTY) |
||
When connecting to an in-process database creates a new database, or opens an existing database (i.e. it is the first connection made to the database by the application), all the user-defined database properties listed in this section can be specified as URL properties.
Upgrading: From 1.7.0, the location of the database files can no longer be overridden by paths defined in the properties file. All files belonging to a database should reside in the same directory.
The property sql.compare_in_locale=true is no longer supported. If the line exists in a .properties file, it will switch the database to the collation for the current default. See the SET DATABASE COLLATION[1] command.
When HSQLDB is used in OpenOffice.org, some property values will have a different default. The properties and values are:
hsqldb.default_table_type=cached hsqldb.cache_scale=13 hsqldb.log_size=10; hsqldb.nio_data_file=false sql.enforce_strict_size=true
There are some database properties that are set with dedicated SQL commands beginning with SET.
Table 4.8. SQL command properties
| SET WRITE_DELAY {{true | false} | <seconds> | <milliseconds> MILLIS |
|
The default is TRUE and indicates that the changes to the database that have been logged are synched to the file system once every 20 seconds. FALSE indicates there is no delay and at each commit a file synch operation is performed. Numeric values from 0 can also be specified for the synch delay. The purpose of this command is to control the amount of data loss in case of a total system crash. A delay of 1 second means at most the data written to disk during the last second before the crash is lost. All data written prior to this has been synced and should be recoverable This setting should be specified on the basis of the reliability of the hardware used for running the database engine, the type of disk system used, the possibility of power failure etc. Also the nature of the data stored should be considered. In general, when the system is very reliable, the setting can be left to the default. If it is not very reliable, or the data is critical a setting of 1 or 2 seconds would suffice. Only in the worst case scenario or with the most critical data should a setting of 0 or FALSE be specified as this will slow the engine down to the speed at which the file synch operation can be performed by the disk subsystem. Values down to 10 millisconds can be specified by adding MILLIS to the command, but in practice a delay of 100 milliseconds provides 99.99999% reliability with an average one system crash per 6 days. |
| SET LOG_SIZE <numeric value> |
|
The engine writes out a log of all the changes to the database as they occur. This log is synched to the disk based on the WRITE_DELAY property above. The log is never reused unless there is an abnormal termination, i.e. the database process is terminated without SHUTDOWN, or it was terminated using SHUTDOWN IMMEDIATELY. The default maximum size of the .log file is 200 MB. When the maximum size is reached, a CHECKPOINT operation is performed. This operation will save the other database files in a consistent state and delete the old log. A value of 0 indicates no limit for the .log file. |
| SET CHECKPOINT DEFRAG <numeric value> |
|
When rows in CACHED tables are updated or deleted, the spaces are mostly reused. However, in time, some unused spaces are left in the .data file, especially when large tables are dropped or their structure is modified. A CHECKPOINT operation does not normally reclaim the empty spaces, whereas CHECKPOINT DEFRAG always does. This property determines when a normal CHECKPOINT, whether initiated by an administrator or when the size of the log exceeds its limit. The numeric value is the number of megabytes of recorded empty spaces in the .data file that would force a DEFRAG operation. Low values result in more frequent DEFRAG operations. A value of 0 indicates no automatic DEFRAG is performed. The default is 200 megabytes of lost space. |
| SET REFERENTIAL INTEGRITY {true | false} |
|
This is TRUE by default. If bulk data needs to be loaded into the database, this property can be set FALSE for the duration of bulk load operation. This allows loading data for related tables in any order. The property should be set TRUE after bulk load. If the loaded data is not guaranteed to conform to the referential integrity constraints, SQL queries should be run after loading to identify and modify any non-conforming rows. |
Copyright 2005 Fred Toussi. Permission is granted to distribute this document without any alteration under the terms of the HSQLDB license. Additional permission is granted to the HSQLDB Development Group to distribute this document with or without alterations under the terms of the HSQLDB license.
$Date: 2005/07/02 09:11:39 $
Table of Contents
Many questions repeatedly asked in Forums and mailing lists are answered in this guide. If you want to use HSQLDB with your application, you should read this guide. This document covers system related issues. For issues related to SQL see the SQL Issues chapter.
HSQLDB has many modes of operation and features that allow it to be used in very different scenarios. Levels of memory usage, speed and accessibility by different applications are influenced by how HSQLDB is deployed.
The decision to run HSQLDB as a separate server process or as an in-process database should be based on the following:
When HSQLDB is run as a server on a separate machine, it is isolated from hardware failures and crashes on the hosts running the application.
When HSQLDB is run as a server on the same machine, it is isolated from application crashes and memory leaks.
Server connections are slower than in-process connections due to the overhead of streaming the data for each JDBC call.
TEXT tables are designed for special applications where the data has to be in an interchangeable format, such as CSV. TEXT tables should not be used for routine storage of data.
MEMORY tables and CACHED tables are generally used for data storage. The difference between the two is as follows:
The data for all MEMORY tables is read from the .script file when the database is started and stored in memory. In contrast the data for cached tables is not read into memory until the table is accessed. Furthermore, only part of the data for each CACHED table is held in memory, allowing tables with more data than can be held in memory.
When the database is shutdown in the normal way, all the data for MEMORY tables is written out to the disk. In comparison, the data in CACHED tables that has changed is written out at shutdown, plus a compressed backup of all the data in all cached tables.
The size and capacity of the data cache for all the CACHED tables is configurable. This makes it possible to allow all the data in CACHED tables to be cached in memory. In this case, speed of access is good, but slightly slower than MEMORY tables.
For normal applications it is recommended that MEMORY tables are used for small amounts of data, leaving CACHED tables for large data sets. For special applications in which speed is paramount and a large amount of free memory is available, MEMORY tables can be used for large tables as well
JDBC Clobs are supported as columns of the type LONGVARCHAR. JDBC Blobs are supported as columns of the type LONGVARBINARY. When large objects (LONGVARCHAR, LONGVARBINARY, OBJECT) are stored with table definitions that contain several normal fields, it is better to use two tables instead. The first table to contain the normal fields and the second table to contain the large object plus an identity field. Using this method has two benefits. (a) The first table can usually be created as a MEMORY table while only the second table is a CACHED table. (b) The large objects can be retrieved individually using their identity, instead of getting loaded into memory for finding the rows during query processing. An example of two tables and a select query that exploits the separation between the two follows:
CREATE MEMORY TABLE MAINTABLE(MAINID INTEGER, ......);
CREATE CACHED TABLE LOBTABLE(LOBID INTEGER, LOBDATA LONGVARBINARY);
SELECT * FROM (SELECT * FROM MAINTABLE <join any other table> WHERE <various conditions apply>) JOIN LOBTABLE ON MAINID=LOBID;
The inner SELECT finds the required rows without reference to the LOBTABLE and when it has found all the rows, retrieves the required large objects from the LOBTABLE.
The files used for storing HSQLDB database data are all in the same directory. New files are always created and deleted by the database engine. Two simple principles must be observed:
The Java process running HSQLDB must have full privileges on the directory where the files are stored. This include create and delete privileges.
The file system must have enough spare room both for the 'permanent' and 'temporary' files. The default maximum size of the .log file is 200MB. The .data file can grow to up to 8GB. The .backup file can be up to 50% of the .data file. The temporary file created at the time of a SHUTDOWN COMPACT can be equal in size to the .data file.
Memory used by the program can be thought of as two distinct pools: memory used for table data, and memory used for building result sets and other internal operations. In addition, when transactions are used, memory is utilised for storing the information needed for a rollback.
Since version 1.7.1, memory use has been significantly reduced compared to previous versions. The memory used for a MEMORY table is the sum of memory used by each row. Each MEMORY table row is a Java object that has 2 int or reference variables. It contains an array of objects for the fields in the row. Each field is an object such as Integer, Long, String, etc. In addition each index on the table adds a node object to the row. Each node object has 6 int or reference variables. As a result, a table with just one column of type INTEGER will have four objects per row, with a total of 10 variables of 4 bytes each - currently taking up 80 bytes per row. Beyond this, each extra column in the table adds at least a few bytes to the size of each row.
The memory used for a result set row has fewer overheads (fewer variables and no index nodes) but still uses a lot of memory. All the rows in the result set are built in memory, so very large result sets may not be possible. In server mode databases, the result set memory is released from the server once the database server has returned the result set. In-process databases release the memory when the application program releases the java.sql.ResultSet object. Server modes require additional memory for returning result sets, as they convert the full result set into an array of bytes which is then transmitted to the client.
When UPDATE and DELETE queries are performed on CACHED tables, the full set of rows that are affected, including those affected due to ON UPDATE actions, is held in memory for the duration of the operation. This means it may not be possible to perform deletes or updates involving very large numbers of rows of CACHED tables. Such operations should be performed in smaller sets.
When transactions support is enabled with SET AUTOCOMMIT OFF, lists of all insert, delete or update operations are stored in memory so that they can be undone when ROLLBACK is issued. Transactions that span hundreds of modification to data will take up a lot of memory until the next COMMIT or ROLLBACK clears the list.
Most JVM implementations allocate up to a maximum amount of memory (usually 64 MB by default). This amount is generally not adequate when large memory tables are used, or when the average size of rows in cached tables is larger than a few hundred bytes. The maximum amount of allocated memory can be set on the java ... command line that is used for running HSQLDB. For example, with Sun JVM version 1.3.0 the parameter -Xmx256m increases the amount to 256 MB.
1.8.0 uses a fast cache for immutable objects such as Integer or String that are stored in the database. In most circumstances, this reduces the memory footprint still further as fewer copies of the most frequently-used objects are kept in memory.
With CACHED tables, the data is stored on disk and only up to a maximum number of rows are held in memory at any time. The default is up to 3*16384 rows. The hsqldb.cache_scale database property can be set to alter this amount. As any random subset of the rows in any of the CACHED tables can be held in the cache, the amount of memory needed by cached rows can reach the sum of the rows containing the largest field data. For example if a table with 100,000 rows contains 40,000 rows with 1,000 bytes of data in each row and 60,000 rows with 100 bytes in each, the cache can grow to contain nearly 50,000 rows, including all the 40,000 larger rows.
An additional property, hsqldb.cache_size_scale can be used in conjunction with the hsqldb.cache_scale property. This puts a limit in bytes on the total size of rows that are cached. When the default values is used for both properties, the limit on the total size of rows is approximately 50MB. (This is the size of binary images of the rows and indexes. It translates to more actual memory, typically 2-4 times, used for the cache because the data is represented by Java objects.)
If memory is limited, the hsqldb.cache_scale or hsqldb.cache_size_scale database properties can be reduced. In the example above, if the hsqldb.cache_size_scale is reduced from 10 to 8, then the total binary size limit is reduced from 50MB to 12.5 MB. This will allow the number of cached rows to reach 50,000 small rows, but only 12,500 of the larger rows.
In all running modes (server or in-process) multiple connections to the database engine are supported. In-process (standalone) mode supports connections from the client in the same Java Virtual Machine, while server modes support connections over the network from several different clients.
Connection pooling software can be used to connect to the database but it is not generally necessary. With other database engines, connection pools are used for reasons that may not apply to HSQLDB.
To allow new queries to be performed while a time-consuming query is being performed in the background. This is not possible with HSQLDB 1.8.0 as it blocks while performing the first query and deals with the next query once it has finished it. This capability is under development and will be introduced in a future version.
To limit the maximum number of simultaneous connections to the database for performance reasons. With HSQLDB this can be useful only if your application is designed in a way that opens and closes connections for each small task.
To control transactions in a multi-threaded application. This can be useful with HSQLDB as well. For example, in a web application, a transaction may involve some processing between the queries or user action across web pages. A separate connection should be used for each HTTP session so that the work can be committed when completed or rolled back otherwise. Although this usage cannot be applied to most other database engines, HSQLDB is perfectly capable of handling over 100 simultaneous HTTP sessions as individual JDBC connections.
An application that is not both multi-threaded and transactional, such as an application for recording user login and logout actions, does not need more than one connection. The connection can stay open indefinitely and reopened only when it is dropped due to network problems.
When using an in-process database with versions prior to 1.7.2 the application program had to keep at least one connection to the database open, otherwise the database would have been closed and further attempts to create connections could fail. This is not necessary since 1.7.2, which does not automatically close an in-process database that is opened by establishing a connection. An explicit SHUTDOWN command, with or without an argument, is required to close the database. In version 1.8.0 a connection property can be used to revert to the old behaviour.
When using a server database (and to some extent, an in-process database), care must be taken to avoid creating and dropping JDBC Connections too frequently. Failure to observe this will result in unsuccessful connection attempts when the application is under heavy load.
Any database not produced with the release version of HSQLDB 1.8.0 must be upgraded to this version. This includes databases created with the RC versions of 1.8.0. The instructions under the Upgrading Using the SCRIPT Command section should be followed in all cases.
Once a database is upgraded to 1.8.0, it can no longer be used with Hypersonic or previous versions of HSQLDB.
There may be some potential legacy issues in the upgrade which should be resolved by editing the .script file:
Version 1.8.0 does not accept duplicate names for indexes that were allowed before 1.7.2.
Version 1.8.0 does not accept duplicate names for table columns that were allowed before 1.7.0.
Version 1.8.0 does not create the same type of index for foreign keys as versions before 1.7.2.
Version 1.8.0 does not accept table or column names that are SQL identifiers without double quoting.
To upgrade from 1.7.2 or 1.7.3 to 1.8.0, simply issue the SET SCRIPTFORMAT TEXT and SHUTDOWN SCRIPT commands with the old version, then open with the new version of the engine. The upgrade is then complete.
To upgrade from older version database files (1.7.1 and older) that do not contain CACHED tables, simple SHUTDOWN with the older version and open with the new version. If there is any error in the .script file, try again after editing the .script file.
To upgrade from older version database files (1.7.1 and older) that contain CACHED tables, use the SCRIPT procedure below. In all versions of HSQLDB and Hypersonic 1.43, the SCRIPT 'filename' command (used as an SQL query) allows you to save a full record of your database, including database object definitions and data, to a file of your choice. You can export a script file using the old version of the database engine and open the script as a database with 1.8.0.
Procedure 5.1. Upgrade Using SCRIPT procedure
Open the original database in the old version of DatabaseManager
Issue the SCRIPT command, for example SCRIPT 'newversion.script' to create a script file containing a copy of the database.
Use the 1.8.0 version of DatabaseManager to create a new database, in this example 'newversion' in a different directory.
SHUTDOWN this database.
Copy the newversion.script file from step 2 over the file of the same name for the new database created in 4.
Try to open the new database using DatabaseManager.
If there is any inconsistency in the data, the script line number is reported on the console and the opening process is aborted. Edit and correct any problems in the newversion.script before attempting to open again. Use the guidelines in the next section (Manual Changes to the .script File). Use a programming editor that is capable of handling very large files and does not wrap long lines of text.
In 1.8.0 the full range of ALTER TABLE commands is available to change the data structures and their names. However, if an old database cannot be opened due to data inconsistencies, or the use of index or column names that are not compatible with 1.8.0, manual editing of the SCRIPT file can be performed.
The following changes can be applied so long as they do not affect the integrity of existing data.
Names of tables, columns and indexes can be changed.
CREATE UNIQUE INDEX ... to CREATE INDEX ... and vice versa
A unique index can always be converted into a normal index. A non-unique index can only be converted into a unique index if the table data for the column(s) is unique in each row.
NOT NULL
A not-null constraint can always be removed. It can only be added if the table data for the column has no null values.
PRIMARY KEY
A primary key constraint can be removed or added. It cannot be removed if there is a foreign key referencing the column(s).
COLUMN TYPES
Some changes to column types are possible. For example an INTEGER column can be changed to BIGINT, or DATE, TIME and TIMESTAMP columns can be changed to VARCHAR.
After completing the changes and saving the modified *.script file, you can open the database as normal.
The data for each database consists of up to 5 files in the same directory. The endings are *.properties, *.script, *.data, *.backup and *.log (a file with the *.lck ending is used for controlling access to the database and should not be backed up). These should be backed up together. The files can be backed up while the engine is running but care should be taken that a CHECKPOINT or SHUTDOWN operation does not take place during the backup. It is more efficient to perform the backup immediately after a CHECKPOINT. The *.data file can be excluded from the backup. In this case, when restoring, a dummy *.data file is needed which can be an empty, 0 length file. The engine will expand the *.backup file to replace this dummy file if the backup is restored. If the *.data file is not backed up, the *.properties file may have to be modified to ensure it contain modified=yes instead of modified=no prior to restoration. If a backup immediately follows a checkpoint, then the *.log file can also be excluded, reducing the significant files to *.properties, *.script and *.backup. Normal backup methods, such as archiving the files in a compressed bundle can be used.
Copyright 2002-2005 Bob Preston and Fred Toussi. Permission is granted to distribute this document without any alteration under the terms of the HSQLDB license. Additional permission is granted to the HSQLDB Development Group to distribute this document with or without alterations under the terms of the HSQLDB license.
$Date: 2005/06/29 23:15:13 $
Table of Contents
Text Table support for HSQLDB was originally developed by Bob Preston independently from the Project. Subsequently Bob joined the Project and incorporated this feature into version 1.7.0, with a number of enhancements, especially the use of conventional SQL commands for specifying the files used for Text Tables.
In a nutshell, Text Tables are CSV or other delimited files treated as SQL tables. Any ordinary CSV or other delimited file can be used. The full range of SQL queries can be performed on these files, including SELECT, INSERT, UPDATE and DELETE. Indexes and unique constraints can be set up, and foreign key constraints can be used to enforce referential integrity between Text Tables themselves or with conventional tables.
HSQLDB with Text Table support is the only comprehensive solution that employs the power of SQL and the universal reach of JDBC to handle data stored in text files and will have wide-ranging use way beyond the currently established Java realm of HSQLDB.
Goals of the Implementation
We aimed to finalise the DDL for Text Tables so that future releases of HSQLDB use the same DDL scripts.
We aimed to support Text Tables as GLOBAL TEMPORARY or GLOBAL BASE tables in the SQL domain.
Text Tables are defined similarly to conventional tables with the added TEXT keyword:
CREATE TEXT TABLE <tablename> (<column definition> [<constraint definition>])
In addition, a SET command specifies the file and the separator character that the Text table uses:
SET TABLE <tablename> SOURCE <quoted_filename_and_options> [DESC]
Text Tables cannot be created in memory-only databases (databases that have no script file).
A Text table without a file assigned to it is READ ONLY and EMPTY.
A Temporary Text table has the scope and the lifetime of the SQL session (a JDBC Connection).
Reassigning a Text Table definition to a new file has implications in the following areas:
The user is required to be an administrator.
Existing transactions are committed at this point.
Constraints, including foreign keys referencing this table, are kept intact. It is the responsibility of the administrator to ensure their integrity.
From version 1.7.2 the new source file is scanned and indexes are built when it is assigned to the table. At this point any violation of NOT NULL, UNIQUE or PRIMARY KEY constrainst are caught and the assignment is aborted. owever, foreign key constraints are not checked at the time of assignment or reassignment of the source file.
This has changed since 1.7.2 to support both null values and empty strings.
Empty fields are treated as NULL. These are fields where there is nothing or just spaces between the separators.
Quoted empty strings are treated as empty strings.
The default field separator is a comma (,). A different field separator can be specified within the SET TABLE SOURCE statement. For example, to change the field separator for the table mytable to a vertical bar, place the following in the SET TABLE SOURCE statement, for example:
SET TABLE mytable SOURCE "myfile;fs=|"
Since HSQLDB treats CHAR's, VARCHARs, and LONGVARCHARs the same, the ability to assign different separators to the latter two is provided. When a different separator is assigned to a VARCHAR or LONGVARCHAR field, it will terminate any CSV field of that type. For example, if the first field is CHAR, and the second field LONGVARCHAR, and the separator fs has been defined as the pipe (|) and vs as the period (.) then the data in the CSV file for a row will look like:
First field data|Second field data.Third field data
The following example shows how to change the default separator to the pipe (|), VARCHAR separator to the period (.) and the LONGVARCHAR separator to the tilde (~). Place the following within the SET TABLE SOURCE statement, for example:
SET TABLE mytable SOURCE "myfile;fs=|;vs=.;lvs=~"
HSQLDB also recognises the following special indicators for separators:
special indicators for separators
semicolon
qoute
space character
apostrophe
newline - Used as an end anchor (like $ in regular expressions)
carriage return
tab
backslash
a Unicode character specified in hexadecimal
Furthermore, HSQLDB provides csv file support with three additional boolean options: ignore_first, quoted and all_quoted. The ignore_first option (default false) tells HSQLDB to ignore the first line in a file. This option is used when the first line of the file contains column headings. The all_quoted option (default false) tells the program that it should use quotes around all character fields when writing to the source file. The quoted option (default true) uses quotes only when necessary to distinguish a field that contains the separator character. It can be set to false to prevent the use of quoting altogether and treat quote characters as normal characters. These options may be specified within the SET TABLE SOURCE statement:
SET TABLE mytable SOURCE "myfile;ignore_first=true;all_quoted=true"
When the default options all_quoted= false and quoted=true are in force, fields that are written to a line of the csv file will be quoted only if they contain the separator or the quote character. The quote character is doubled when used inside a string. When all_quoted=false and quoted=false the quote character is not doubled. With this option, it is not possible to insert any string containing the separator into the table, as it would become impossible to distinguish from a separator. While reading an existing data source file, the program treats each individual field separately. It determines that a field is quoted only if the first character is the quote character. It interprets the rest of the field on this basis.
The character encoding for the source file is ASCII by default. To support UNICODE or source files preprared with different encodings this can be changed to UTF-8 or any other encoding. The default is encoding=ASCII and the option encoding=UTF-8 or other supported encodings can be used.
Finally, HSQLDB provides the ability to read a text file from the bottom up and making them READ ONLY, by placing the keyword "DESC" at the end of the SET TABLE SOURCE statement:
SET TABLE mytable SOURCE "myfile" DESC
This feature provides functionality similar to the Unix tail command, by re-reading the file each time a select is executed. Using this feature sets the table to read-only mode. Afterwards, it will no longer be possible to change the read-only status with SET TABLE <tablename> READONLY TRUE.
Text table source files are cached in memory. The maximum number of rows of data that are in memory at any time is controlled by the textdb.cache_scale property. The default value for textdb.cache_scale is 10 and can be changed by setting the property in the .properties file for the database. The number of rows in memory is calculated as 3*(2**scale), which translates to 3072 rows for the default textdb.cache_scale setting (10). The property can also be set for individual text tables:
SET TABLE mytable SOURCE "myfile;ignore_first=true;all_quoted=true;cache_scale=12"
Text File Issues
File locations are restricted to below the directory that contains the database, unless the textdb.allow_full_path property is set true in the database properties file.
Blank lines are allowed anywhere in the text file, and are ignored.
The file location for a text table created with
SELECT <select list> INTO TEXT <tablename> FROM
is the directory that contains the database and the file name is based on the table name. The table name is converted into the file name by replacing all the non-alphanumeric characters with the underscore character, conversion into lowercase, and adding the ".csv" suffix.
From version 1.7.2 it is possible to define a primay key or identity column for text tables.
When a table source file is used with the ignore_first=true option, the first, ignored line is replaced with a blank line after a SHUTDOWN COMPACT.
An existing table source file may include CHARACTER fields that do not begin with the quote character but contain instances of the quote character. These fields are read as literal strings. Alternatively, if any field begins with the quote character, then it is interpreted as a quoted string that should end with the quote character and any instances of the quote character within the string is doubled. When any field containing the quote character or the separator is written out to the source file by the program, the field is enclosed in quote character and any instance of the quote character inside the field is doubled.
Inserts or updates of CHARACTER type field values are allowed with strings that contains the linefeed or the carriage return character. This feature is disabled when both quoted and all_quoted properties are false.
Complete list of supported global properties in *.properties files
textdb.fs
textdb.lvs
textdb.quoted
textdb.all_quoted
textdb.ignore_first
textdb.encoding
textdb.cache_scale
textdb.allow_full_path
The directory src/org/hsqldb/sample in your HSQLDB distibution contains a file named load_binding_lu.sql. This is a working SQL file which imports a pipe-delimited text file from the database's file directory into an existing normal table. You can edit a copy of this file and use it directly with SqlTool, or you can use the SQL therein as a model (using any SQL client at all).
Table of Contents
The instructions in this document are liable to change at any time. In particular, we will be changing the method to supply the server-side certificate password.
Hsqldb TLS Support Requirements
Sun Java 2.x and up. (This is probably possible with IBM's Java, but I don't think anybody has attempted to run HSQLDB with TLS under IBM's Java, and I'm sure that nobody in the HSQLDB Development Group has documented how to set up the environment).
If Java 2.x or 3.x, then you will need need to install JSSE. Your server and/or client will start up much slower than that of Java 4.x users. Client-side users will not be able to use the https: JDBC protocol (because the https protocol handler is not implemented in 2.x/3.x Java JSSE; if there is demand, we could work around this).
A JKS keystore containing a private key, in order to run a server.
If you are running the server side, then you'll need to run a HSQLDB Server or WebServer. It doesn't matter if the underlying database instances are new, and it doesn't matter if you are making a new Server configuration or encrypting an existing Server configuration. (You can turn encryption on and off at will).
You need a HSQLDB jar file that was built with JSSE present. If you got your HSQLDB 1.7.2 distribution from us, you are all set, because we build with Java 1.4 (which contains JSSE). If you build your own jar file with Java 1.3, make sure to install JSSE first.
At this time, only 1-way, server-cert encryption is tested.
Just use one of the following protocol prefixes.
Hsqldb TLS URL Prefixes
jdbc:hsqldb:hsqls://
jdbc:hsqldb:https://
At this time, the latter will only work for clients running with Java 1.4.
If the server you wish to connect to is using a certificate approved by your default trust keystores, then there is nothing else to do. If not, then you need to tell Java to "trust" the server cert. (It's a slight over-simplification to say that if the server certificate was purchased, then you are all set; if somebody "signed their own" certificate by self-signing or using a private ca certificate, then you need to set up trust).
First, you need to obtain the cert (only the "public" part of it). Since this cert is passed to all clients, you could obtain it by writing a java client that dumps it to file, or perhaps by using openssl s_client. Since in most cases, if you want to trust a non-commercial cert, you probably have access to the server keystore, I'll show an example of how to get what you need from the server-side JKS keystore.
You may already have an X509 cert for your server. If you have a server keystore, then you can generate a X590 cert like this.
Example 7.1. Exporting certificate from the server's keystore
keytool -export -keystore server.store -alias existing_alias -file server.cer
Now, you need to add this cert to one of the system trust keystores or to a keystore of your own. See the Customizing Stores section in JSSERefGuide.html to see where your system trust keystores are. You can put private keystores anywhere you want to. The following command will add the cert to an existing keystore, or create a new keystore if client.store doesn't exist.
Example 7.2. Adding a certificate to the client keystore
keytool -import -trustcacerts -keystore trust.store -alias new_alias -file server.cer
If you are making a new keystore, you probably want to start with a copy of your system default keystore which you can find somewhere under your JAVA_HOME directory (typically jre/lib/security/cacerts for a JDK, but I forget exactly where it is for a JRE).
Unless your OS can't stop other people from writing to your files, you probably do not want to set a password on the trust keystore.
If you added the cert to a system trust store, then you are finished. Otherwise you will need to specify your custom trust keystore to your client program. The generic way to set the trust keystore is to set the sytem property javax.net.ssl.trustStore every time that you run your client program. For example
Example 7.3. Specifying your own trust store to a JDBC client
java -Djavax.net.ssl.trustStore=/home/blaine/trust.store -jar /path/to/hsqldb.jar dest-urlid
N.b. The hostname in your database URL must match the Common Name of the server's certificate exactly. That means that if a site certificate is admc.com, you can not use jdbc:hsqldb:hsqls://localhost or jdbc:hsqldb:hsqls://www.admc.com:1100 to connect to it.
If you want more details on anything, see JSSERefGuide.html on Sun's site, or in the subdirectory docs/guide/security/jsse of your Java SE docs.
Get yourself a JKS keystore containing a private key. Then set the system property javax.net.ssl.keyStore to the path to that file, and javax.net.ssl.keyStorePassword to the password of the keystore (and to the private key-- they have to be the same).
Example 7.4. Running an Hsqldb server with TLS encryption
java -Djavax.net.ssl.keyStorePassword=secret -Djavax.net.ssl.keyStore=/usr/hsqldb/db/db3/server.store \
-cp /path/to/hsqldb.jar org.hsqldb.Server
(This is a single command that I have broken into 2 lines using my shell's \ line-continuation feature. In this example, I'm using a server.properties file so that I don't need to give arguments to specify database instances or the server endpoint).
Specifying a password on the command-line is definitely not secure. It's really only appropriate when untrusted users do not have any access to your computer.
If there is any user demand, we will have a more secure way to supply the password before long.
If you are running Java 4.x, then you are all set. Java 1.x users, you are on your own (Sun does not provide a JSSE that will work with 1.x). Java 2.x and 3.x users continue...
Go to http://java.sun.com/products/jsse/index-103.html. If you agree to the terms and meet the requirements, download the domestic or global JSSE software. All you need from the software distro is the three jar files. If you have a JDK installation, then move the 3 jar files into the directory $JAVA_HOME/jre/lib/ext. If you have a JRE installation, then move the 3 jar files into the directory $JAVA_HOME/lib/ext.
Pretty painless.
There are two main ways to do this. Either you can use a certificate signed by a certificate authority, or you can make your own. One thing that you need to know in both cases is, the Common Name of the cert has to be the exact hostname that JDBC clients will use in their database URL.
I'm not going to tell you how to get a CA-signed SSL certificate. That is well documented at many other places.
Assuming that you have a standard pem-style private key certificate, here's how you can use openssl and the program DERImport to get it into a JKS keystore.
Because I have spent a lot of time on this document already, I am just giving you an example.
Example 7.5. Getting a pem-style private key into a JKS keystore
openssl pkcs8 -topk8 -outform DER -in Xpvk.pem -inform PEM -out Xpvk.pk8 -nocrypt
openssl x509 -in Xcert.pem -out Xcert.der -outform DER
java DERImport new.keystore NEWALIAS Xpvk.pk8 Xcert.der
Make sure to set the password of the key exactly the same as the password for the keystore!
You need the program DERImport.class of course. Do some internet searches to find DERImport.java or DERImport.class and download it.
If DERImport has become difficult to obtain, I can write a program to do the same thing-- just let me know.
Run man keytool or see the Creating a Keystore section of JSSERefGuide.html.
If you are on UNIX and want to automatically start and stop a Server or WebServer running with encryption, follow the instructions in the UNIX Quick Start chapter, and remember to make the init script configuration file readable only to root and to set the variables TLS_PASSWORD and TLS_KEYSTORE.
If you are using a private server certificate, make sure to also set the trust store filepath as shown in the sample init script configuration file.
The cautionary warning above still applies. The password will be visible to any minimally competent local UNIX user who wants to see it.
Table of Contents
This document explains how to use SqlTool, the main purpose of which is to read your SQL text file or stdin, and execute the SQL commands therein against a JDBC database. There are also a great number of features to facilitate both interactive use (such as command-line editing and PL aliases) and automation (such as scripting variables and SQL transaction control and error handling).
Some of the examples below use quoting which works exactly as-is for any normal UNIX shell. I have not yet tested these commands on Windows, and I doubt whether the quoting will work just like this (though it is possible). SqlTool is still a very useful tool even if you have no quoting capability at all.
This document is now updated for version 1.46 of SqlTool and 1.114 of SqlFile (the latter is the class which does most of the work for SqlTool). The startup banner will report both versions when you run SqlTool interactively. I expect this version of this document to accurately describe SqlTool for some unknown number of versions into the future.
This section lists changes to SqlTool since the last major release of HSQLDB. For this version of this document, that means, changes since HSQLDB versions 1.7.x.
If you are using an Oracle database server, it will commit your current transaction if you cleanly disconnect, regardless of whether you have set auto-commit or not. This will occur if you exit SqlTool (or any other client) in the normal way (as opposed to killing the process or using Ctrl-C, etc.). This is mentioned in this section only for brevity, so I don't need to mention it in the main text in the many places where auto-commit is discussed. This behavior has nothing to do with SqlTool. It is a quirk of Oracle.
If you want to use SqlTool, then you either have an SQL text file, or you want to interactively type in SQL commands. If neither case applies to you, then you are looking at the wrong program.
Procedure 8.1. To run SqlTool...
Copy the file sqltool.rc from the directory src/org/hsqldb/sample of your HSQLDB distribution to your home directory and secure access to it if your home directory is accessible to anybody else. This file will work as-is for a Memory Only database instance; or if your target is a HSQLDB Server running on your local computer with default settings and the password for the "sa" account is blank (the sa password is blank when new HSQLDB database instances are created). Edit the file if you need to change the target Server URL, username, password, character set, JDBC driver, or TLS trust store as documented in the RC File Authentication Setup section.
Find out where your hsqldb.jar file resides. It typically resides at HSQLDB_HOME/lib/hsqldb.jar where HSQLDB_HOME is the base directory of your HSQLDB software installation. For this reason, I'm going to use "$HSQLDB_HOME/lib/hsqldb.jar" as the path to hsqldb.jar for my examples, but understand that you need to use the actual path to your own hsqldb.jar file.
Run
java -jar $HSQLDB_HOME/lib/hsqldb.jar --help
java -jar $HSQLDB_HOME/lib/hsqldb.jar mem
java -jar $HSQLDB_HOME/lib/hsqldb.jar --sql 'SQL statement' mem
java -jar $HSQLDB_HOME/lib/hsqldb.jar mem filepath1.sql...
The urlid mem in these commands is a key into your RC file, as explained in the RC File Authentication Setup section. Since this is a Memory Only database, you can use SqlTool with this urlid immediately with no database setup whatsoever (however, you can't persist any changes that you make to this database). The sample sqltool.rc file also defines the urlid "localhost-sa" for a local HSQLDB Server. At the end of this section, I explain how you can load some sample data to play with, if you want to.
SqlTool does not commit DML changes by default. This leaves it to the user's disgression whether to commit or rollback their modifications. Remember to either run the command commit; before quitting SqlTool, or use the --autoCommit command-line switch.
If you put a file named auto.sql into your home directory, this file will be executed automatically every time that you run SqlTool interactively and without the --noAutoFile switch.
To use a JDBC Driver other than the HSQLDB driver, you can't use the -jar switch because you need to modify the classpath. You must add the hsqldb.jar file and your JDBC driver classes to your classpath, and you must tell SqlTool what the JDBC driver class name is. The latter can be accomplished by either using the "--driver" switch, or setting "driver" in your config file. The RC File Authentication Setup section. explains the second method. Here's an example of the first method (after you have set the classpath appropriately).
java org.hsqldb.util.SqlTool --driver oracle.jdbc.OracleDriver urlid
If the tables of query output on your screen are all messy because of lines wrapping, the best and easiest solution is usually to resize your terminal emulator window to make it wider. (With some terms you click & drag the frame edges to resize, with others you use a menu system where you can enter the number of columns).
There are many SQL types which SqlTool (being a text-based program) can't display properly. This includes the SQL types BLOB, JAVA_OBJECT, STRUCT, and OTHER. When you run a query that returns any of these, SqlTool will save the very first such value obtained to the binary buffer and will not display any output from this query. You can then save the binary value to a file, as explained in the Storing and retrieving binary files section.
There are other types, such as BINARY, which JDBC can make displayable (by using ResultSet.getString()), but which you may very well want to retrieve in raw binary format. You can use the \b command to retrieve any-column-type-at-all in raw binary format (so you can later store the value to a binary file).
Another restriction which all text-based database clients have is the practical inability for the user to type in binary data such as photos, audio streams, and serialized Java objects. You can use SqlTool to load any binary object into a database by telling SqlTool to get the insert/update datum from a file. This is also explained in the Storing and retrieving binary files section.
Desktop shortcuts and quick launch icons are useful, especially if you often run SqlTool with the same set of arguments. It's really easy to set up several of them-- one for each way that you invoke SqlTool (i.e., each one would start SqlTool with all the arguments for one of your typical startup needs). One typical setup is to have one shortcut for each database account which you normally use (use a different --urlid switch in each shortcut's Target specification.
Desktop icon setup varies depending on your Desktop manager, of course. I'll explain how to set up a SqlTool startup icon in Windows XP. Linux and Mac users should be able to take it from there, since it's easier with the common Linux and Mac desktops.
Procedure 8.2. Creating a Desktop Shortcut for SqlTool
Right click in the main Windows background.
Navigate to where your good JRE lives. For recent Sun JRE's, it installs to C:\Program Files\Java\*\bin by default (the * will be a JDK or JRE name and version number).
Select java.exe.
Enter any name
Right click the new icon.
Edit the Target field.
Leave the path to java.exe exactly as it is, including the quotes, but append to what is there. Beginning with a space, enter the command-line that you want run.
to a pretty icon.
If you want a quick-launch icon instead of (or in addition to) a desktop shortcut icon, click and drag it to your quick launch bar. (You may or may not need to edit the Windows Toolbar properties to let you add new items).
\i HSQLDB_HOME/src/org/hsqldb/sample/sampledata.sqlwhere HSQLDB_HOME is the base directory of your HSQLDB software installation.
For memory-only databases, you'll need to run this every time that you run SqlTool. For other (persistent) databases, the data will reside in your database until you drop the tables.
Dans cette section, quand je dis fichier de configuration ou config , je pense à ce fichier de configuration RC. il peut être utilisé par un client JDBC qui utilise la classe org.hsqldb.util.RCData -- cela est valable pour les outils SqlTool, DatabaseManager, DatabaseManagerSwing.
Vous pouvez l'utilisez dans votre propre programe basé sur un client JDBC .
L'exemple suivant du fichier RCse trouve dans src/org/hsqldb/sample/sqltool.rc de votre distribution de HSQLDB .
Exemple 8.1. Exemple de fichier RC
# $Id: sqltool.rc,v 1.14 2005/05/22 04:46:16 unsaved Exp $ # This is a sample RC configuration file used by SqlTool, DatabaseManager, # and any other program that uses the org.hsqldb.util.RCData class. # You can run SqlTool right now by copying this file to your home directory # and running # java -jar /path/to/hsqldb.jar mem # This will access the first urlid definition below in order to use a # personal Memory-Only database. # If you have the least concerns about security, then secure access to # your RC file. # See the documentation for SqlTool for various ways to use this file. # A personal Memory-Only database. urlid mem url jdbc:hsqldb:mem:memdbid username sa password # This is for a hsqldb Server running with default settings on your local # computer (and for which you have not changed the password for "sa"). urlid localhost-sa url jdbc:hsqldb:hsql://localhost username sa password # Template for a urlid for an Oracle database. # You will need to put the oracle.jdbc.OracleDriver class into your # classpath. # In the great majority of cases, you want to use the file classes12.zip # (which you can get from the directory $ORACLE_HOME/jdbc/lib of any # Oracle installation compatible with your server). # Since you need to add to the classpath, you can't invoke SqlTool with # the jar switch, like "java -jar .../hsqldb.jar..." or # "java -jar .../hsqlsqltool.jar...". # Put both the HSQLDB jar and classes12.zip in your classpath (and export!) # and run something like "java org.hsqldb.util.SqlTool...". #urlid cardiff2 #url jdbc:oracle:thin:@aegir.admc.com:1522:TRAFFIC_SID #username blaine #password secretpassword #driver oracle.jdbc.OracleDriver # Template for a TLS-encrypted HSQLDB Server. # Remember that the hostname in hsqls (and https) JDBC URLs must match the # CN of the server certificate (the port and instance alias that follows # are not part of the certificate at all). # You only need to set "truststore" if the server cert is not approved by # your system default truststore (which a commercial certificate probably # would be). #urlid tls #url jdbc:hsqldb:hsqls://db.admc.com:9001/lm2 #username blaine #password asecret #truststore /home/blaine/ca/db/db-trust.store # Template for a Postgresql database #urlid blainedb #url jdbc:postgresql://idun.africawork.org/blainedb #username blaine #password losung1 #driver org.postgresql.Driver # Template for a MySQL database #urlid mysql-testdb #url jdbc:mysql:///test #username root #username blaine #password hiddenpwd #driver com.mysql.jdbc.Driver
Ce fichier peut être mis n'importe où, mais son chemin doit être spécifié dans la commande de lancement des l'outils SqlTool/DatabaseManager/DatabaseManagerSwing via l'argument --rcfile. S'il n'y a pas de raison de ne pas utiliser le chemin par défaut (et il y a des situations où vous ne le voudrez pas non plus), alors utiliser le chemin par défaut sans donner d'argument --rcfile (ouais, bbah ca marche pas chez moi !!!)
le fichier par défaut utilisé est sqltool.rc ou dbmanager.rc dans votre repertoire home (correspondant au programme qui l'utilise).
En cas de doute sur votre home directory, lancer simplement SqlTool avec un urlid phony et l'outil vous dirra ou est attendu le fichier de configuration .
java -jar $HSQLDB_HOME/lib/hsqldb.jar x
set HSQLDB_HOME="D:\tst\HSQLDB1802" |
|
java -jar %HSQLDB_HOME%\lib\hsqldb.jar x |
The config file consists of stanza(s) like this:
urlid web
url jdbc:hsqldb:hsql://localhost
username web
password webspassword
Ces 4 lignes sont nécéssaire pour déclarer une urlid.
(Il existe un parametrage optionnel, utilisé pour décrire a couple paragraphs down). Vous pouvez avoir plusiurs lignes de blanc ou de commentaire.
# ceci est un commentaire
in the file as you like. The whole point is that the urlid that you give in your SqlTool/DatabaseManager command must match a urlid in your configuration file.
Exemple personnel : J'ai mis dans mon fichier de configuration, que j'ai appelé sqltool_idx.rc:
# A personal Standalone database. |
Commentaire | |
urlid index |
Nom arbitraire que je donne au pavé de connection. Dans le fichier de configuration plusieurs connexion aux bases de données peuvent être déclarées. |
|
url jdbc:hsqldb:file:idx/idx |
Ce que j'ai lu dans l'utilitaire de connection de DBmanager | |
username sa |
je n'ai pas changé le code utilisateur créé par défaut | |
password |
je n'ai pas changer le mot de passe non plus donc il reste vide |
D |
disque D, racine | |
+TST |
repetoire de tst | |
|+HSQLBD1802 |
sous repertoire | |
||+data |
mon répertoire des bases de données (il peut y en avoir plusieurs) | |
|||+IDX |
jle repertoire de la BD IDX | |
||||-idx.log |
fichier journal de ma base de donnée | |
||||-idx.properties |
ma base de données idx | |
||||-idx.script |
ma base de données idx | |
||+lib |
répertoire contenant notement hsqldb.jar | |
||-SQLTool.bat |
fichier de lancement de l'outil SQLTOOL | |
||-MgrDB.bat |
fichier de lancement du DBManager |
Contenu de MgrDB.bat :
cd data java -Drepl=true -cp ..\lib\hsqldb.jar;..\lib\javagroups-core;..\lib\xercesimpl-2.1.0.jar;..\lib\xercesxmlapi-2.1.0.jar org.hsqldb.util.DatabaseManager %1 %2 %3 %4 %5 %6 %7 %8 %9
Ca marche mais il faut reprécisé la DB à l'ouverture
Contenu de SQLtool.bat :
java -Drepl=true -cp lib\hsqldb.jar;lib\sdbc_hsqldb.jar org.hsqldb.util.SqlTool --rcfile data\sqltool_idx.rc indexCa marche.
Conclusion : ce fichier de configuration doit correspondre au fichier tnsname.ora pour oracle
il peut être utilisé par des programmes java (cf mon petit exemple)
Use whatever facilities are at your disposal to protect your configuration file.
It should be readable, both locally and remotely, only to users who run programs that need it. On UNIX, this is easily accomplished by using chmod/chown commands and making sure that it is protected from anonymous remote access (like via NFS, FTP or Samba).
You can also put the following optional settings into a urlid stanza. The setting will, of course, only apply to that urlid.
Property and SqlTool command-line switches override settings made in the configuration file.
This procedure will allow users of a legacy version of HSQLDB to use all of the new features of SqlTool. You will also get the new versions of the DatabaseManagers! This procedure works for distros going back to 1.7.3.3 at least, probably much farther.
These instructions assume that you are capable of running an Ant build. See the Building HSQLDB chapter.
Download and extract a current HSQLDB distribution. If you don't want to use the source code, documentation, etc., you can use a temporary directory and remove it afterwards.
Cd to the build directory under the root directory where you extracted the distribution to.
Run ant hsqldbutil. Do not run ant hsqltool, because hsqlbutil.jar files contain the HSQLDB JDBC driver, and you can not use a newer JDBC driver with an older HSQLDB database.
If you're going to wipe out the build directory, copy hsqldbutil.jar to a safe location first.
For now on, whenver you are going to run SqlTool, make sure that you have this hsqldbutil.jar as the first item in your CLASSPATH. You can't run SqlTool with the "-jar" switch (because the -jar switch doesn't permit setting your own class path).
Here's a UNIX example where somebody wants to use the new SqlTool with their older HSQLDB database, as well as with Postgresql and a local application.
CLASSPATH=/path/to/hsqldbutil.jar:/home/bob/myapp/classes:/usr/local/lib/pg.jdbc3.jar export CLASSPATH java org.hsqldb.util.SqlTool urlid
Do read the The Bare Minimum section before you read this section.
You run SqlTool interactively by specifying no SQL filepaths on the SqlTool command line. Like this.
java -jar $HSQLDB_HOME/lib/hsqldb.jar urlid
Procedure 8.4. What happens when SqlTool is run interactively (using all default settings)
SqlTool starts up and connects to the specified database, using your SqlTool configuration file (as explained in the RC File Authentication Setup section).
SQL file auto.sql in your home directory is executed (if there is one),
SqlTool displays a banner showing the SqlTool and SqlFile version numbers and describes the different command types that you can give, as well as commands to list all of the specific commands available to you.
You exit your session by using the "\q" special command or ending input (like with Ctrl-D or Ctrl-Z).
Every command (regardless of type) and comment must begin at the beginning of a line (or immediately after a comment ends with "*/").
You can't nest commands or comments. You can only start new commands (and comments) after the preceding statement has been terminated. (Remember that if you're running SqlTool interactively, you can terminate an SQL statement without executing it by entering a blank line).
(Special Commands, Buffer Commands and PL Commands always consist of just one line. Any of these commands or comments may be preceded by space characters.)
These rules do not apply at all to Raw Mode. Raw mode is for use by advanced users when they want to completely bypass SqlTool processing in order to enter a chunk of text for direct transmission to the database engine.
When you are typing into SqlTool, you are always typing part of the current command. The buffer is the last SQL command. If you're typing an SQL command, then the previous SQL command will be in the buffer, not the one you are currently typing. The current command could be any type of command, but only SQL When you type command-editing commands, the current command is the editing command (like ":s/tbl/table/"), the result of which is to modify the SQL command in the buffer (which can thereafter be executed). The ":a" command (with no argument) is special in that it takes a copy of the SQL command in the buffer and makes that the current command, leaving you in a state where you are appending to that now current command. The buffer is the zeroeth item of the SQL command history.
Command types
Above, we said that if you enter an SQL command, one SQL command corresponds to one SqlTool command. This is the most typical usage, however, you can actually put multiple SQL statements into one SQL command. One example would be
INSERT INTO t1 VALUES(0); SELECT * FROM t1;
Any command that you enter which does not begin with "\", ":", or "* " is an SQL Statement. The command is not terminated when you hit ENTER, like most OS shells. You terminate SQL Statements with either ";" at the end of a line, or with a blank line. In the former case, the SQL Statement will be executed against the SQL database and the command will go into the command buffer and SQL command history for editing or viewing later on. In the former case, execute against the SQL database means to transmit the SQL text to the database engine for execution. In the latter case (you end an SQL Statement with a blank line), the command will go to the buffer and SQL history, but will not be executed (but you can execute it later from the buffer). (See the note immediately above about multiple SQL statements in one SqlTool command).
(Blank lines are only interpreted this way when SqlTool is run interactively. In SQL files, blank lines inside of SQL statements remain part of the SQL statement).
As a result of these termination rules, whenever you are entering text that is not a Special Command, Buffer Command, or PL Command, you are always appending lines to an SQL Statement. (In the case of the first line, you will be appending to an empty SQL statement. I.e. you will be starting a new SQL Statement).
Procedural Langage commands. Run the command "*?" to list the PL Commands. All of the PL Commands begin with "*". PL commands are for setting and using scripting variables and conditional and flow control statements like * if and * while. A few PL features (such as PL aliases and updating and selecing data directly from/to files) can be a real convenience for nearly all users, so these features will be discussed briefly in this section. More detailed explanation of PL variables and the other PL features, with examples, are covered in the SqlTool Procedural Language section.
Essential Special Commands
Lists available objects of the given type.
If you supply an optional filter substring, then only items which contain the given substring (in the object name or schema name) will be listed.
The substring test is case-sensitive! Even though in SQL queries and for the "\d objectname" command object names are usually case-insensitive, for the \dX commands, you must capitalize the filter substring exactly as it will appear in the special command output. This is an inconvenience, since the database engine will change names in SQL to default case unless you double-quote the name, but that is server-side functionality which cannot (portably) be reproduced by SqlTool. You can use spaces and other special characters in the string.
Note that this is a change in behavior from SqlFile before about version 1.100, where substring tests were case-insensitive.Beginning with the current version of SqlFile, filter substrings ending with "." are special. If a substring ends with ".", then this means to narrow the search by the exact, case-sensitive schema name given. For example, if I run "\d* BLAINE.", this will list all table-like database objects in the "BLAINE" schema. The capitalization of the schema must be exactly the same as how the schema name is listed by the "\dn" command. You can use spaces and other special characters in the string. (I.e., enter the name exactly how you would enter it inside of double-quotes in an SQL command). This is an inconvenience, since the database engine will change names in SQL to default case unless you double-quote the name, but that is server-side functionality which cannot (portably) be reproduced by SqlTool.
Several new \dX commands have been added with the current of SqlFile. Be aware that the meaning of the \s command has changed!
Indexes may not be searched for by substring, only by exact target table name. So if I1 is an index on table T1, then you list this index by running "\di T1". In addition, many database vendors will report on indexes only if a target table is identified. Therefore, "\di" with no argument will fail if your database vendor does not support it.
Lists names of columns in the specified table or view. objectname may be a base table name or a schema.object name.
If you supply a filter string, then only columns with a name containing the given filter will be listed. The objectname is nearly always case-insensitive (depends on your database), but the filter is always case-sensitive. You'll find this filter is a great convenience compared to other database utilities, where you have to list all columns of large tables when you are only interested in one of them.
When working with real data (as opposed to learning or playing), I often find it useful to run two SqlTool sessions in two side-by-side terminal emulator windows. I do all of my real work in one window, and use the other mostly for \d commands. This way I can refer to the data dictionary while writing SQL commands, without having to scroll.
Enter "\" followed by the command number from SQL history, like "\-3". That command will be written to the buffer so that you can execute it or edit it using buffer commands.
(You can append a semicolon to a recall command in order to execute the recalled buffer immediately, like "\-3;". This is actually just a shortcut for running the Special Command "\-3" and the Buffer Command ":;".)
This list here includes only the essential Special Commands, but n.b. that there are other useful Special Commands which you can list by running \?. (You can, for example, execute SQL from external SQL files, and save your interactive SQL commands to files). Some specifics of these other commands are specified immediately below, and the Generating Text or HTML Reports section explains how to use the "\o" and "\H" special commands to generate reports.
Be aware that the \! Special Command does not work for external programs that read from standard input. You can invoke non-interactive and graphical interactive programs, but not command-line interactive programs.
SqlTool executes \! programs directly, it does not run an operating system shell (this is to avoid OS-specific code in SqlTool). Because of this, you can give as many command-line arguments as you wish, but you can't use shell wildcards or redirection.
The \w command can be used to store any command in your SQL history to a file. Just restore the command to the buffer (which is the 0th element of the history) with a command like "\-4" before you give the \w command.
Buffer Commands
Enter append mode with the contents of the buffer as the current SQL Statement. Things will be exactly as if you physically re-typed the command that is in the buffer. Whatever line you type next will be appended to the SQL Statement. You can execute the command by terminating a line with ";", or send it back to the buffer by entering a blank line.
You can, optionally, put a string after the :a, in which case this text will be appended and you will remain in append mode. (Unless the text ends with ';', in which case the resultant statement will be executed immediately). Note that if you do put text after the "a", exactly what you type immediately after "a" will be appended. If your buffer contains SELECT x FROM mytab and you run a:le, the resultant command will be SELECT x FROM mytable. If your buffer contains SELECT x FROM mytab and you run a: ORDER BY y, the resultant command will be SELECT x FROM mytab ORDER BY y. Notice that in the latter case the append text begins with a space character.
This is the primary command for SqlTool command editing-- it operates upon the current buffer. The "to string" and the "switches" are both optional. To start with, I'll discuss the use and behavior if you don't supply any substitution mode switches.
Don't use "/" if it occurs in either "from string" or "to string". You can use any character that you want in place of "/", but it must not occur in the from or to strings. Example
:s@from string@to string@
The to string is substituted for the first occurrence of the (case-specific)from string. The replacement will consider the entire SQL statement, even if it is a multi-line statement.
All occurrences of "$" in the from string and the to string are treated as line breaks. For example, from string of "*$FROM mytable" would actually look for occurrences of
*
FROM mytable
Here is a another meaningful example using $.
:s/e)$/e) WHERE col1 is not null$/
This command appends "WHERE col1 is not null" to the line(s) which end with "e)".
The to string may be empty, in which case, occurrences of the from string are just deleted. For example
:s/this//
would remove the first occurrence of "this". (With the "g" substitution mode switch, as explained below, it would remove all occurrences of "this").
Don't end a to string with ";" in attempt to make a SQL statement execute. There is a substitution mode switch to use for that purpose.
You can use any combination of the substitution mode switches.
Use "i" to make the searches for from string case insensitive.
Use "g" to substitute globally, i.e., for all occurrences of from string which are found in the text under consideration.
Use ";" to execute the command immediately after the substitution is performed.
Use an integer (from 1 to 9) to narrow the text under consideration to a specific line of a multi-line buffer.
The substitution facility doesn't support any regular expressions at all. When we stop supporting Java versions older than 1.4, I'll start supporting regular expressions and other advanced string manipulation functions.
Essential PL Command
Set the value of a variable. If the variable doesn't exist yet, it will be created. The most common use for this is so that you can later use it in SQL statements, print statements, and PL conditionals, by using the *{varname} construct.
If you set a variable to an SQL statement (without the terminating ";") you can then use it as a PL alias like *VARNAME, as shown in this example.
Example 8.2. Defining and using a PL alias (PL variable)
* q = SELECT COUNT(*) FROM mytable
\p The stored query is '*{q}'
/q;
/q WHERE mass > 200;
If you put variable definitions into the SQL file auto.sql in your home directory, those aliases/variables will always be available for interactive use.
Note that PL commands are used to upload and download column values to/from local ASCII files, but the corresponding actions for binary files use the special \b commands. This is because PL variables are used for ASCII values and you can store any number of column values in PL variables. This is not true for binary column values. The \b commands work with a single binary byte buffer.
See the SqlTool Procedural Language section below for information on using variables in other ways, and information on the other PL commands and features.
You can upload binary files such as photographs, audio files, or serialized Java objects into database columns. SqlTool keeps one binary buffer which you can load from files with the \bl command, or from a database query by doing a one-row query for any non-displayable type (including BLOB, OBJECT, and OTHER). In the latter case, the data returned for the first non-displayable column of the first result row will be stored into the binary buffer.
Once you have data in the binary buffer, you can upload it to a database column (including BLOB, OBJECT, and OTHER type columns), or save it to a file. The former is accomplished by the special command \bp followed by a prepared SQL query containing one question mark place-holder to indicate where the data gets inserted. The latter is accomplished with the \bd command.
You can also store the output from normal, displayable column into the binary buffer by using the special command \b. The very first column value from the first result row of the next SQL command will be stored to the binary byte buffer.
Example 8.3. Inserting binary data into database from a file
\bl /tmp/favoritesong.mp3
\bp
INSERT INTO musictbl (id, stream) VALUES(3112, ?);
Example 8.4. Downloading binary data from database to a file
SELECT stream FROM musictbl WHERE id = 3112;
\bd /tmp/favoritesong.mp3
You can also store and retrieve text column values to/from ASCII files, as documented in the Essential PL Command section.
The SQL history shown by the \s command, and used by other commands, is truncated to 20 entries, since the utility comes from being able to quickly view the history list. You can change the history length by setting the system property sqltool.historyLength to an integer like
java -Dsqltool.historyLength=40 -jar $HSQLDB_HOME/lib/hsqldb.jar urlid
The SQL history list explicitly does not contain Special, Buffer, or PL commands. It only contains SQL commands, valid or invalid, successful or unsuccessful. The reason for including bad SQL commands is so that you can recall and edit them if you want to. The same applies to the editing buffer (which is element 0 of the history).
You normally use non-interactive mode for piping. You specify "-" as the SQL file name. See the Piping and shell scripting subsection of the Non-Interactive chapter.
You can run SqlTool interactively, but have SqlTool behave exactly as if it were processing an SQL file (i.e., no command-line prompts, error-handling that defaults to fail-upon-error, etc.). Just specify "-" as the SQL file name in the command line. This is a good way to test what SqlTool will do when it encounters any specific command in an SQL file. See the Piping and shell scripting subsection of the Non-Interactive chapter for an example.
Read the Interactive section if you have not already, because much of what is in this section builds upon that. Even if your plans are to run SqlTool non-interactively, you should really learn to run it interactively because it's such a powerful debugging tool, and you can use it to prototype sql scripts.
If you're doing data updates, remember to issue a commit command or use the --autoCommit switch.
As you'll see, SqlTool has many features that are very convenient for scripting. But what really makes it superior for automation tasks (as compared to SQL tools from other vendors) is the ability to reliably detect errors and to control JDBC transactions.
If you just have a couple SQL commands to run, you can run them directly from the comand-line or from a shell script without an SQL file, like this.
java -jar $HSQLDB_HOME/lib/hsqldb.jar --sql 'SQL statement' urlid
With the current version of SqlTool, we have changed the default behavior of the --sql switch. The --sql automatically implies --noinput, so if you want to execute the specified SQL before and in addition to an interactive session (or stdin piping), then you must also give the (new) --stdinput switch. This was changed because it turns out that this is the desired behavior well over 90% of the time that you would want to use the --sql switch.
Beginning with the current version of SqlTool, SqlTool will automatically add a trailing semicolon to your --sql SQL. You may still give the trailing semicolon if you wish to, and you must still delimit multiple SQL commands with a simicolon, of course. This was changed because in the very few sitations where you do not want to execute your SQL by a terminating semicolon, you would be better off using an SQL file.
Since SqlTool transmits SQL statements to the database engine only when a line is terminated with ";", if you want feedback from multiple SQL statements in an --sql expression, you will need to use functionality of your OS shell to include linebreaks after the semicolons in the expression. With any Bourne-compatible shell, you can include linebreaks in the SQL statements like this.
java -jar $HSQLDB_HOME/lib/hsqldb.jar --sql 'SQL statement' urlid '
SQL statement number one;
SQL statement
number two;
SQL statement three;
' urlid
The --sql switch is very useful for setting shell variables to the output of SQL Statements, like this.
# A shell script
USERCOUNT=`java -jar $HSQLDB_HOME/lib/hsqldb.jar --sql 'select count(*) from usertbl' urlid` || {
# Handle the SqlTool error
}
echo "There are $USERCOUNT users registered in the database."
[ "$USECOUNT" -gt 3 ] && { # If there are more than 3 users registered
# Some conditional shell scripting
Just give paths to sql text file(s) on the command line after the urlid.
Often, you will want to redirect output to a file, like
java -jar $HSQLDB_HOME/lib/hsqldb.jar sql... > /tmp/log.sql 2>&1
(Skip the "2>&1" if you're on Windows).
You can also execute SQL files from an interactive session with the "\i"' Special Command, but be aware that the default behavior in an interactive session is to continue upon errors. If the SQL file was written without any concern for error handling, then the file will continue to execute after errors occur. You could run \c false before \i filename, but then your SqlTool session will exit if an error is encountered in the SQL file. If you have an SQL file without error handling, and you want to abort that file when an error occurs, but not exit SqlTool, the easiest way to accomplish this is usually to add \c false to the top of the script.
If you specify multiple SQL files on the command-line, the default behavior is to exit SqlTool if any of the SQL files encounters an error.
SQL files themselves have ultimate control over error handling. Regardless of what command-line options are set, or what commands you give interactively, if a SQL file gives error handling statements, they will take precedence.
You can also use \i in SQL files. This results in nested SQL files.
You can use the following SQL file, sample.sql, which resides in the src/org/hsqldb/sample directory of your HSQLDB distribution. It contains SQL as well as Special Commands making good use of most of the Special Commands documented below.
/*
$Id: sample.sql,v 1.5 2005/05/02 15:07:27 unsaved Exp $
Examplifies use of SqlTool.
PCTASK Table creation
*/
/* Ignore error for these two statements */
\c true
DROP TABLE pctasklist;
DROP TABLE pctask;
\c false
\p Creating table pctask
CREATE TABLE pctask (
id integer identity,
name varchar(40),
description varchar,
url varchar,
UNIQUE (name)
);
\p Creating table pctasklist
CREATE TABLE pctasklist (
id integer identity,
host varchar(20) not null,
tasksequence int not null,
pctask integer,
assigndate timestamp default current_timestamp,
completedate timestamp,
show bit default true,
FOREIGN KEY (pctask) REFERENCES pctask,
UNIQUE (host, tasksequence)
);
\p Granting privileges
GRANT select ON pctask TO public;
GRANT all ON pctask TO tomcat;
GRANT select ON pctasklist TO public;
GRANT all ON pctasklist TO tomcat;
\p Inserting test records
INSERT INTO pctask (name, description, url) VALUES (
'task one', 'Description for task 1', 'http://cnn.com');
INSERT INTO pctasklist (host, tasksequence, pctask) VALUES (
'admc-masq', 101, SELECT id FROM pctask WHERE name = 'task one');
commit;
You can execute this SQL file with a Memory Only database with a command like
java -jar $HSQLDB_HOME/lib/hsqldb.jar --sql "create user 'tomcat' password 'x'" mem path/to/hsqldb/src/org/hsqldb/sample/sample.sql
(The --sql "create..." arguments create an account which the script uses).
You can of course, redirect output from SqlTool to a file or another program.
java -jar $HSQLDB_HOME/lib/hsqldb.jar urlid file.sql > file.txt 2>&1
java -jar $HSQLDB_HOME/lib/hsqldb.jar urlid file.sql 2>&1 | someprogram...
You can type commands in to SqlTool while being in non-interactive mode by supplying "-" as the file name. This is a good way to test how SqlTool will behave when processing your SQL files.
java -jar $HSQLDB_HOME/lib/hsqldb.jar urlid -
This is how you have SqlTool read its input from another program:
Example 8.5. Piping input into SqlTool
echo "Some SQL commands with '$VARIABLES';" |
java -jar $HSQLDB_HOME/lib/hsqldb.jar urlid -
Make sure that you also read the Giving SQL on the Command Line section. The --sql switch is a great facility to use with shell scripts.
If you want your SQL scripts optimally compatible among other SQL tools, then don't use any Special or PL Commands. SqlTool has default behavior which I think is far superior to the other SQL tools, but you will have to disable these defaults in order to have optimally compatible behavior.
These switches provide compatibilty at the cost of poor control and error detection.
--continueOnErr
The output will still contain error messages about everything that SqlTool doesn't like (malformatted commands, SQL command failures, empty SQL commands), but SqlTool will continue to run. Errors will not cause rollbacks (but that won't matter because of the following setting).
You don't have to worry about accidental expansion of PL variables, since SqlTool will never expand PL variables if you don't set any variables on the command line, or give any "* " PL commands. (And you could not have "* " commands in a compatible SQL file).
SQL comments of the form /*...*/ must begin where a (SQL/Special/Buffer/PL) Command could begin, and they end with the very first "*/" (regardless of quotes, nesting, etc. You may have as many blank lines as you want inside of a comment.
Example 8.6. Valid comment example
SELECT count(*) FROM atable;
/* Lots of
comments interspersed among
several lines */ SELECT count(*)
FROM btable;
Notice that a command can start immediate after the comment ends.
This comment is invalid because you could not start another command at the comment location (because it is within an SQL Statement).
You can try using /*...*/ in other locations, and -- style SQL comments, but SqlTool will not treat them as comments. If they occur within an SQL Statment, SqlTool will pass them to the database engine, and the DB engine will determine whether to parse them as comments.
Don't use Buffer Commands in your sql files, because they won't work. Buffer Commands are for interactive use only. (But, see the Raw Mode section for an exception).
Be aware that the \q command will cause SqlTool to completely exit. If a script x.sql has a \q command in it, then it doesn't matter if the script is executed like
java -jar .../hsqldb.jar urlid a.sql x.sql z.sql
or if you use \i to read it in interactively, or if another SQL file uses \i to nest it. If \q is encountered, SqlTool will quit. See the SqlTool Procedural Language section for commands to abort an SQL file (or even parts of an SQL file) without causing SqlTool to exit.
\q takes an optional argument, which is an abort message. If you give an abort message, the message is displayed to the user and SqlTool will exit with a failure status. If you give no abort message, then SqlTool will exit quietly with successful status.
Toggle HTML output mode. If you redirect output to a file, this can make a long session log much easier to view. This will HTML-ify the entire session. For example,
java -jar $HSQLDB_HOME/lib/hsqldb.jar urlid filepath1.sql... > /tmp/log.html 2>&1
A "true" setting tells SqlTool to Continue when errors are encountered. The current transaction will not be rolled back upon SQL errors, so if \c is true, then run the ROLLCACK; command yourself if that's what you want to happen. The default for interactive use is to continue upon error, but the default for non-interactive use is to abort upon error. You can override this behavior by using the --continueOnErr or the --abortOnErr command-line switch.
With database setup scripts, I usually find it convenient to set "true" before dropping tables (so that things will continue if the tables aren't there), then set it back to false so that real errors are caught. DROP TABLE tablename IF EXISTS; is a more elegant, but less portable, way to accomplish the same thing.
It depends on what you want your SQL files to do, of course, but I usually want my SQL files to abort when an error is encountered, without necessarily killing the SqlTool session. If this is the behavior that you want, then put an explicit \c false at the top of your SQL file and turn on continue-upon-error only for sections where you really want to permit errors, or where you are using PL commands to handle errors manually. This will give the desired behavior whether your script is called by somebody interactively, from the SqlTool command-line, or included in another SQL file (i.e. nested).
The default settings are usually best for people who don't want to put in any explicit \c or error handling code at all. If you run SQL files from the SqlTool command line, then any errors will cause SqlTool to roll back and abort immediately. If you run SqlTool interactively and invoke SQL files with \i commands, the scripts will continue to run upon errors (and will not roll back). This behavior was chosen because there are lots of SQL files out there that produce errors which can be ignored; but we don't want to ignore errors that a user won't see. I reiterate that any and all of this behavior can (and often should) be changed by Special Commands run in your interactive shell or in the SQL files. Only you know whether errors in your SQL files can safely be ignored.
In previous versions of SqlTool, this special command was "\*". This usage is still supported, but is deprecated. It was changed because "\*" is a very poor mnemonic. Even the author of the program had to constantly look up whether "\* true" meant to Continue on error or to Abort upon error. Now, the "c" signifies Continue.
SqlTool is ideal for mission-critical automation because, unlike other SQL tools, SqlTool returns a dependable exit status and gives you control over error handling and SQL transactions. Autocommit is off by default, so you can build a completely dependable solution by intelligently using \c commands (Continue upon Errors) and commit statements, and by verifying exit statuses.
Using the SqlTool Procedural Language, you have ultimate control over program flow, and you can use variables for database input and output as well as for many other purposes. See the SqlTool Procedural Language section.
Some script developers may run into cases where they want to run with sql files but they alwo want SqlTool's interactive behavior. For example, they may want to do command recall in the sql file, or they may want to log SqlTool's command-line prompts (which are not printed in non-interactive mode). In this case, do not give the sql file(s) as an argument to SqlTool, but pipe them in instead, like
java -jar $HSQLDB_HOME/lib/hsqldb.jar urlid < filepath1.sql > /tmp/log.html 2>&1
cat filepath1.sql... | java -jar $HSQLDB_HOME/lib/hsqldb.jar urlid > /tmp/log.html 2>&1
java -Dsqlfile.charset=UTF-8 -jar $HSQLDB_HOME/lib/hsqldb.jar urlid filepath1.sql...
Procédure 8.5. Ecrire une sortie de requête dans un fichier externe
1. Par défaut toute sortie est réalisé en texte pure. Si vous voulez que votre sortie soit au format HTML, utiliser le paramètre de la commande \H. Puis vous voudrez probablement utiliser le suffixe ".html" ou ".htm" à la place de ".txt".
2. Lancer la commande \o path/to/reportfile.txt. A partir de ce point, les sorties de vos requêtes iront alimenter le fichier spécifié.. (I.e. une autre copy le la sortie est générée.)
This way you can continue to monitor or use output as usual as the report is generated.
3. Quand vous souhaitez que SqlTool arrête d’écrire le fichier, entrez la commande \o (ou simplement quitter SqlTool si vous n’avez pas d’autre travail en cours).
4. Si vous utilisez le mode HTML avec la commande \H, entrez de nouveau \H pour arrêter ce mode.
Ce n’est pas seulement les sorties de "SELECT" sui peuvent faire l’objet de sorties fichiers, mais
Peuvent faire l’objet de résultat fichier via la commande \o :
Les autres objets de sorties sont dirigées vers votre écran ou vers la sortie standard “stdout”, mais n’est pas faite dans un fichier de rapport. Remarquez que les messages d’erreur ne viennent pas polluer le fichier de rapport.
Si SqlTool tourne dans un mode non-interactif (y compris si vous donnez un fichier SQL en entrée de ligne de commande), SqlTool s’arrêtera éventuellement en erreur en retournant le statut de l’erreur rencontrée. Pour gérer les erreurs, analyser le status de sortie de SqlTool. (La description des erreurs récupérées peut être modifiée en ligne de commande par SqlTool).
Exemple personnel : Appel de l'outil SQLtoll, en précisant le fichier de configuration, le pavé de connexion dans ce fichier qui doit être pris en compte, le nom du fichier contenant une requete sql et des commandes PL/SQL , et le nom du fichier de sortie redirigée
java -Drepl=true -cp lib\hsqldb.jar;lib\sdbc_hsqldb.jar;lib\xercesImpl.jar;lib\xml-apis.jar org.hsqldb.util.SqlTool --rcfile data\sqltool_idx.rc index test.sql > tst.htm
Ca génère bien un fichier d'extention htm, tst.htm le résultat est mis en forme.si la requete passée est entourée des commandes /H
Visualiser le Fichier contenant la requete entourée des commandes /H : test.sql
Visualiser le fichier de propriété sqltool_idx.rc
Visualiser le script Cr_shema.sql ayant permis de créer la base visée et de renseignere quelques lignes
Ainsi les balises Html, générées parcequ'elles sont le résultat de la concaténation au sein de la requete, de champ texte stockées dans la base sont correctement interprétées.
La commande \o ajoute le résultat en fin d’un fichier nommé. Si vous souhaitez un nouveau fichier, alors utiliser un nouveau nom ou effacer auparavant le fichier cible.
So that I don't end up with a bunch of junk in my report file, I usually leave \o off while I perfect my SQL. With \o off, I perfect the SQL query until it produces on my screen exactly what I want saved to file. At this point I turn on \o and run ":;" to repeat the last SQL command. If I have several complex queries to run, I turn \o off and repeat until I'm finished. (Every time you turn \o on, it will append to the file, just like we need).
Usually it doesn't come to mind that I need a wider screen until a query produces lines that are too long. In this case, stretch your window and repeat the last command with the ":;" Buffer Command.
Most importantly, run SqlTool interactively and give the "*?" command to see what PL commands are available to you.
PL variables will only be expanded after you run a PL command (or set variable(s) from the command-line). We only want to turn on variable expansion if the user wants variable expansion. People who don't use PL don't have to worry about strings getting accidentally expanded.
All other PL commands imply the "*" command, so you only need to use the "*" statement if your script uses PL variables and it is possible that no variables may be set before-hand (and no PL commands have been run previously). In this case, without "*", your script would silently use a literal value like "*{x}" instead of trying to expand it. With a preceding "*" command, PL will notice that the variable x has not been set and will generate an error. (If x had been set here will be no issue because setting a variable automatically turns on PL variable expansion).
PL is also used to upload and download column values to/from local ASCII files, analogously to the special \b commands for binary files. This is explained above in the Interactive Essential PL Command section above.
A variable written like /VARNAME is expanded if it begins an SQL Statement. This usage is called PL Aliasing. See the PL Aliases section below.
You can't do math with expression variables, but you can get functionality like the traditional for (i = 0; i < x; i++) by appending to a variable and testing the string length, like
* while (*i < ${x})
* i = *{i}.
i will be a growing line of dots.
Variable names must not contain white space, or the characters "}" or "=".
PL Aliasing just means the use of a PL variable as the first thing in an SQL statement, with the shortcut notation /VARNAME.
/VARNAME must be followed by whitespace or terminate the Statement, in order for SqlFile to tell where the variable name ends.
Note that PL aliases are a very different thing from SQL aliases or HSQLDB aliases, which are features of databases, not SqlFile.
If the value of a variable is an entire SQL command, you generally do not want to include the terminating ";" in the value. There is an example of this above.
PL aliasing may only be used for SQL statements. You can define variables for everything in a Special or PL Command, except for the very first character ("\" or "*"). Therefore, you can use variables other than alias variables in Special and PL Commands. Here is a hyperbolically impractical example to show the extent to which PL variables can be used in Special commands even though you can not use them as PL aliases.
sql> * qq = p Hello Butch
sql> \*{qq} done now
Hello Butch done now
(Note that the \* here is not the special command "\*", but is the special command "\p" because "*{qq}" resolves to "p").Here is a short SQL file that gives the specified user write permissions on some application tables.
Example 8.8. Simple SQL file using PL
/*
grantwrite.sql
Run SqlTool like this:
java -jar path/to/hsqldb.jar -setvar USER=debbie grantwrite.sql
*/
/* Explicitly turn on PL variable expansion, in case no variables have
been set yet. (Only the case if user did not set USER).
*/
*
GRANT all ON book TO *{user};
GRANT all ON category TO *{user};
Note that this script will work for any (existing) user just by supplying a different user name on the command-line. I.e., no need to modify the tested and proven script. There is no need for a commit statement in this SQL file since no DML is done. If the script is accidentally run without setting the USER variable, SqlTool will give a very clear notificaton of that.
The purpose of the plain "*" command is just so that the *{user} variables will be expanded. (This would not be necessary if the USER variable, or any other variable, were set, but we don't want to depend upon that).
Logical expressions occur only inside of logical expression parentheses in PL statements. For example, if (*var1 > astring) and while (*checkvar). (The parentheses after "foreach" do not enclose a logical expression, they just enclose a list).
There is a critical difference between *{varname} and *VARNAME inside logical expressions. *{varname} is expanded one time when the parser first encounters the logical expression. *VARNAME is re-expanded every time that the expression is evaluated. So, you would never want to code * while (*{x} < 5) because the statement will always be true or always be false. (I.e. the following block will loop infinitely or will never run).
Don't use quotes or whitespace of any kind in *{varname} variables in expressions. (They would expand and then the expression would most likely no longer be a valid expression as listed in the table below). Quotes and whitespace are fine in *VARNAME variables, but it is the entire value that will be used in evaluations, regardless of whether quotes match up, etc. I.e. quotes and whitespace are not special to the token evaluator.
Logical Operators
*VARNAMEs in logical expressions, where the VARNAME variable is not set, evaluate to an empty string. Therefore (*UNSETVAR = 0) would be false, even though (*UNSETVAR) by itself is false and (0) by itself is false.
When developing scripts, you definitely use SqlTool interactively to verify that SqlTool evaluates logical expressions as you expect. Just run * if commands that print something (i.e. \p) if the test expression is true.
Flow control works by conditionally executing blocks of Commands according to conditions specified by logical expressions.
The conditionally executed blocks are called PL Blocks. These PL Blocks always occur between a PL flow control statement (like * foreach, *while, * if) and a corresponding * end PL Command (like * end foreach).
Be aware that the PL block reader is ignorant about SQL statements and comments when looking for the end of the block. It just looks for lines beginning with some specific PL commands. Therefore, if you put a comment line before a PL statement, or if a line of a multi-line SQL statement has a line beginning with a PL command, things may break.
I am not saying that you shouldn't use PL commands or SQL commands inside of PL blocks-- you definitely should! I'm saying that in PL blocks you should not have lines inside of SQL statments or comments which could be mistaken for PL commands. (Especially, "commenting out" PL end statements will not work if you leave * end at the beginning of the line).
(This limitation will very likely be removed in a future version of SqlTool).
The values of control variables for foreach and while PL blocks will change as expected.
There are * break and * continue, which work as any shell scripter would expect them to. The * break command can also be used to quit the current SQL file without triggering any error processing. (I.e. processing will continue with the next line in the including SQL file or interactive session, or with the next SQL file if you supplied multiple on the command-line).
Below is an example SQL File that shows how to use most PL features. If you have a question about how to use a particular PL feature, check this example before asking for help. This file resides in the src/org/hsqldb/sample directory with the name pl.sql. Definitely give it a run, like
java -jar $HSQLDB_HOME/lib/hsqldb.jar mem $HSQLDB_HOME/src/org/hsqldb/sample/pl.jar
Example 8.9. SQL File showing use of most PL features
/*
$Id: pl.sql,v 1.4 2005/05/02 15:07:26 unsaved Exp $
SQL File to illustrate the use of SqlTool PL features.
Invoke like
java -jar .../hsqldb.jar .../pl.sql mem
-- blaine
*/
* if (! *MYTABLE)
\p MYTABLE variable not set!
/* You could use \q to Quit SqlTool, but it's often better to just
break out of the current SQL file.
If people invoke your script from SqlTool interactively (with
\i yourscriptname.sql) any \q will kill their SqlTool session. */
\p Use arguments "--setvar MYTABLE=mytablename" for SqlTool
* break
* end if
/* Turning on Continue-upon-errors so that we can check for errors ourselves.*/
\c true
\p
\p Loading up a table named '*{mytable}'...
/* This sets the PL variable 'retval' to the return status of the following
SQL command */
* retval ~
CREATE TABLE *{mytable} (
i int,
s varchar
);
\p CREATE status is *{retval}
\p
/* Validate our return status. In logical expressions, unset variables like
*unsetvar are equivalent to empty string, which is not equal to 0
(though both do evaluate to false on their own, i.e. (*retval) is false
and (0) is false */
* if (*retval != 0)
\p Our CREATE TABLE command failed.
* break
* end if
/* Default Continue-on-error behavior is what you usually want */
\c false
\p
/* Insert data with a foreach loop.
These values could be from a read of another table or from variables
set on the command line like
*/
\p Inserting some data int our new table (you should see 3 row update messages)
* foreach VALUE (12 22 24 15)
* if (*VALUE > 23)
\p Skipping *{value} because it is greater than 23
* continue
\p YOU WILL NEVER SEE THIS LINE, because we just 'continued'.
* end if
INSERT INTO *{mytable} VALUES (*{value}, 'String of *{value}');
* end foreach
\p
* themax ~
/* Can put Special Commands and comments between "* VARNAME ~" and the target
SQL statement. */
\p We're saving the max value for later. You'll still see query output here:
SELECT MAX(i) FROM *{mytable};
/* This is usually unnecessary because if the SELECT failed, retval would
be undefined and the following print statement would make SqlTool exit with
a failure status */
* if (! *themax)
\p Failed to get the max value.
/* It's possible that the query succeeded but themax is "0".
You can check for that if you need to. */
* break
\p YOU WILL NEVER SEE THIS LINE, because we just 'broke'.
* end if
\p
\p ##############################################################
\p The results of our work:
SELECT * FROM *{mytable};
\p MAX value is *{themax}
\p
\p Everything worked.
We hereby call the ability to transmit multiple SQL commands to the database in one transmission chunking. Unless you are in Raw mode, SqlTool only transmits commands to the database engine when it reads in a ";" at the end of a line of an SQL command. Therefore, you normally want to end each and every SQL command with ";" at the end of a line. This is because the database can only send one status reply to each JDBC transmission. So, while you could run
SELECT * FROM t1; SELECT * FROM t2;
The first general reason to chunk SQL commands is performance. For standalone databases, the most common performance bottleneck is network latency. Chunking SQL commands can dramatically reduce network traffic.
The second general reason to chunk SQL commands is if your database requires you to send multiple commands in one transmission. This is often the case when you need to tell the database the SQL or PL/SQL commands that comprise a stored procedure, function, trigger, etc.
The most simple way is enter as many SQL commands as you want, but just do not end a line with ";" until you want the chunk to transmit.
Example 8.11. Multi-line chunking example
INSERT INTO t1 VALUES (1)
; INSERT INTO t1 VALUES (2)
; SELECT * FROM t1;
The other method is by using Raw Mode. Go to the Raw Mode section to see how. You can enter any text at all, exactly how you want it to be sent to the database engine. Therefore, in addition to chunking SQL commands, you can give commands for non-SQL extensions to the database. For example, you could enter JavaScript code to be used in a stored procedure.
You begin raw mode by issuing the Special Command "\.". You can then enter as much text in any format you want. When you are finished, enter a line consisting of only ".". If you are running SqlTool interactively, you'll notice that your prompt will be the continuation prompt until you enter the "." line.
When you terminate raw entry with the "\." line, the command does not execute, it just goes into the command buffer. If running interactively, you can look at the buffer with the ":l" Buffer Command. What you will normally want to do is to enter the Buffer Command ":;" to transmit the buffer to the database engine.
Example 8.12. Raw Mode example
sql> \.
Enter RAW SQL. No \, :, * commands. End with a line containing only ".":
raw> line one;
+> line two;
+> line three;
+> .
Raw SQL chunk moved into buffer. Run ":;" to execute the chunk.
sql> :;
Executing command from buffer:
line one;
line two;
line three;
SQL Error at 'stdin' line 13:
"line one;
line two;
line three;"
Unexpected token: LINE in statement [line]
sql>
Buffer Commands are generally unavailable when runninb SqlTool interactively. However, the command ":;", and the command buffer have been enabled for non-interactive use, because they are required for using raw mode, and it is definitely useful to be able to use raw mode in SQL files.
PL/SQL is not the same as PL. PL is the procedural language of SqlFile and is independent of your back-end database. PL commands always begin with *. PL/SQL is processed on the server side and you can only use it of your database supports it. You can not intermix PL and PL/SQL (except for setting a PL variable to the output of PL/SQL execution), because when you enter PL/SQL to SqlTool that input is not processed by SqlFile.
Use Raw Mode to send PL/SQL code blocks to the database engine. You do not need to enter the "\." command to enter raw mode. Just begin a new SqlTool command line with "DECLARE" or "BEGIN", and SqlTool will automatically put you into raw mode. See the Raw Mode section for details.
The following sample SQL file resides at src/org/hsqldb/sample/plsql.sql in your HSQLDB distribution. This script will only work if your database engine supports standard PL/SQL, if you have permission to create the table "T1" in the default schema, and if that object does not already exist.
Example 8.13. PL/SQL Example
/*
* $Id: plsql.sql,v 1.3 2005/05/02 15:09:11 unsaved Exp $
*
* This example is copied from the "Simple Programs in PL/SQL"
* example by Yu-May Chang, Jeff Ullman, Prof. Jennifer Widom at
* the Standord University Database Group's page
* http://www-db.stanford.edu/~ullman/fcdb/oracle/or-plsql.html .
* I have only removed some blank lines (because you can't use blank
* lines inside of SQL commands in non-raw mode SqlTool when running
* it interactively); and, at the bottom I have replaced the
* client-specific, non-standard command "run;" with SqlTool's
* corresponding command ":;" and added a plain SQL SELECT command
* to show whether the PL/SQL code worked. - Blaine
*/
CREATE TABLE T1(
e INTEGER,
f INTEGER
);
DELETE FROM T1;
INSERT INTO T1 VALUES(1, 3);
INSERT INTO T1 VALUES(2, 4);
/* Above is plain SQL; below is the PL/SQL program. */
DECLARE
a NUMBER;
b NUMBER;
BEGIN
SELECT e,f INTO a,b FROM T1 WHERE e>1;
INSERT INTO T1 VALUES(b,a);
END;
.
/**************************************************************************/
/* Remaining SqlTool-specific code added by Blaine Simpson of the
* HSQLDB Development Group.
*/
:;
/* This should show 3 rows, one containing values 4 and 2 (in this order)...*/
SELECT * FROM t1;
This section is only for those users who want to use SqlTool but without the overhead of hsqldb.jar.
If you do not need to directly use JDBC URLs like jdbc:hsqldb:mem: + something, jdbc:hsqldb:file: + something, or jdbc:hsqldb:res: + something, then you can use hsqltool.jar in place of the much larger hsqldb.jar file. hsqltool.jar will work for all JDBC databases other than HSQLDB Memory-only and In-process databases (the latter are fine if you access them via a HSQLB Server or WebServer). You will have to supply the JDBC driver for non-HSQLDB URLs, of course.
hsqltool.jar includes the HSQLDB JDBC driver. If you do not need to connect to HSQLDB databases at all, then hsqldbutil.jar is what you need. hsqldbutil.jar contains everything you need to run SqlTool and DatabaseManagerSwing against non-HSQLDB databases... well, besides the JDBC drivers for the target databases.
The HSQLDB distribution doesn't "come with" a pre-built hsqltool.jar and hsqldbutil.jar files. You should build the hsqltool or hsqldbutil target, as explained in the Building HSQLDB appendix.
If you are using the HSQLDB JDBC driver (i.e., you're connecting up to a URL like jdbc:hsqldb:hsql + something or jdbc:hsqldb:http + something), you run SqlTool exactly as with hsqldb.jar except you use the file path to your new jar file instead of the path to hsqldb.jar.
If you are using a non-HSQLDB JDBC driver, follow the instructions at the end of the The Bare Minimum section, but use your new file in place of hsqldb.jar.
A unit testing framework is in place. This assures the robustness of SqlTool. See the file testrun/sqltool/readme.txt for instructions on running, modifying, or creating unit tests. To create a new unit test, you create a SQL file and embed metacommands in the SQL file inside of comments. The metacommands tell the test harness (org.hsqldb.test.SqlToolHarness) how to run SqlTool (like with what arguments) and what output to expect (i.e. the test criteria). You can run tests without JUnit, or you can make a JUnit wrapper in the normal fashion. Any SQL test file can be added to our JUnit SqlTool test suite by just adding the SQL file name and description to the testrun/sqltool/*.list file for the desired JUnit test method.
(The SqlTool unit tests require java 1.4).
Table of Contents
HSQLDB version 1.8.0 supports the SQL statements and syntax described in this chapter.
[A] means A is optional.
{ b | c } means either B or C must be used.
[{ b | c }] means either B or C may optionally be used, or nothing at all.
( and ) are the actual characters '(' and ')' used in statements.
UPPERCASE words are keywords
Le nom de l'index peut être changé tant qu'il ne rentre pas en conflit avec un autre nom d'objet défini par l'utilisateur ou un autre nom d'objet système.
Réinitialise la prochaine valeur retournée par la sequence.
Renome le shéma comme spécifié. Tous les objects du shéma seront accessibkle ensuite seulement avec le nouveau nom de shéma.
Nécéssite le privilèges administrateur.
Ajoute une colonne à la fin de la liste des colonnes. L'option BEFORE <existingcolumn> peut être utilisé pour indiquer avant quelle colonne doit être inserer la nouvelle colonne.
Sont acceptées le même définitions que celle de l'instruction CREATE TABLE. Si la condition NOT NULL est spécifiée et que la table n'est pas vide, une valeur par défaut doit être spécifiée.
Si une vue contient SELECT * FROM <tablename> dans son scripte de création, la nouvelle colonne et aussi ajoutée à la vue (ouaaaa ! super !) C'est une fonction non standart susceptible de changer dans le future. (ooohhh ! pfff !!!)
ALTER TABLE <tablename> DROP [COLUMN] <columnname>;
Enlève une colonne de la table. Les clé primaire sur colonne unique ou contraintes associées à la colonne à effacer tombent avec.
La commande est inopérante si'il existe une cle sur multiple colonne contenant cette dernière ou si la colonne à effacer est referencée par une cle etrangère. Cela plantera aussi si cette colonne est contenu dans le script SQL d'une vue.
It will also fail if an SQL view includes the column.
ALTER TABLE <tablename> ALTER COLUMN <columnname> RENAME TO <newname>
Change le nom de colonne.
ALTER TABLE <tablename> ALTER COLUMN <columnname> SET DEFAULT <defaultvalue>};
Ajoute une valeur par défaut sur la colonne. Utiliser la valeur NULL pour enlever une valeur par défaut
ALTER TABLE <tablename> ALTER COLUMN <columnname> SET [NOT] NULL
Mets ou enlève la contrainte NOT NULL sur une colonne.
ALTER TABLE <tablename> ALTER COLUMN <columnDefinition>;
Cette combinaison de commande ALTER TABLE ALTER COLUMN accepte les Definitions de colonnes de la commande CREATE TABLE , avec les restrictions suivantes :
Restrictions
ALTER TABLE <tablename> ALTER COLUMN <columnname> RESTART WITH <new sequence vale>
This form is used exclusively for IDENTITY columns and changes the next automatic value for the identity sequence.
ALTER TABLE <tablename> ADD [CONSTRAINT <constraintname>] CHECK (<search condition>);
Adds a check constraint to the table. In the current version, a check constraint can reference only the row being inserted or updated.
ALTER TABLE <tablename> ADD [CONSTRAINT <constraintname>] UNIQUE (<column list>);
Adds a unique constraint to the table. This will not work if there is already a unique constraint covering exactly the same <column list>.
This will work only if the values of the column list for the existing rows are unique or include a null value.
ALTER TABLE <tablename> ADD [CONSTRAINT <constraintname>] PRIMARY KEY (<column list>);
Adds a primary key constraint to the table, using the same constraint syntax as when the primary key is specified in a table definition.
ALTER TABLE <tablename> ADD [CONSTRAINT <constraintname>] FOREIGN KEY (<column list>) REFERENCES <exptablename> (<column list>)
[ON {delete | update} {CASCADE | SET DEFAULT | SET NULL}];
Adds a foreign key constraint to the table, using the same constraint syntax as when the foreign key is specified in a table definition.
This will fail if for each existing row in the referring table, a matching row (with equal values for the column list) is not found in the referenced tables.
ALTER TABLE <tablename> DROP CONSTRAINT <constraintname>;
Drop a named unique, check or foreign key constraint from the table.
ALTER TABLE <tablename> RENAME TO <newname>;
Change le mot de passe d'un utilisateur existant. Le mot de pass doit encadré de doubles quotes. Utiliser "" pour les mot de passe vides.
Nécéssite le privilèges administrateur.
Une expression peut être appelée comme une procedure stockée, Y compris, mais pas seulement des procedures Java ou des fonctions.
Cette commande retourne un résultat avec une colonne et une ligne comme si un select retournant une seule ligne une seule colonne avaut été passé.
Ferme le fichier de Base de données, réécrit les fichiers de scripts, efface le fichier de log et celui de la base ouverte.
Si l'option DEFRAG est spécifiée la commande optimise le fichier .data dans sa taille minimale.
Voir: SHUTDOWN, SET LOGSIZE.
Termine une transaction et effectuie les changements de manière permanente
Voir: ROLLBACK, SET AUTOCOMMIT, SET LOGSIZE.
Se connecte à la BD avec un utilisateur différent. Le mot de pass doit encadré de doubles quotes. Utiliser "" pour les mot de passe vides.
Créer un Alias pour une fonction JAVA. La fonction doit être accessible par la JVM avec laquelle la BD est executée. Exemple :
CREATE ALIAS ABS FOR "java.lang.Math.abs";
Voir: CALL, Stored Procedures / Functions.
Crééer un index sur une ou plusiezurs colonnes dans la table.
Créer un index sur les colonnes utilisées dans les recherches peut augmenter les performances. Le complement DESC peut être présent pour rendre compatible la commande avec d'autre base de données, mais cela n'a pas d'autre effet. L'index unique peut être défini mais cela est desuet. Utiliser à la place la contrainte UNIQUE . Le nom de l'index doiot être unique au travers de toute la base.
Voir: CREATE TABLE, DROP INDEX.
Créer une rôle nomé sans membre. (??? j'ai laissé lla phrase d'origine endessous ???) Nécéssite le privilèges administrateur
Creates the named role with no members. Requires Administrative privileges.
Créé un shéma nomé.
Nécéssite le privilèges administrateur
Les options CREATE et GRANT ne peuven,t être données que pour les nouveaux objets du shéma. Seul le dernier état nested doit être terminé avec un poit virgule, car un point virgule rencontré apres un "CREATE SCHEMA" terminera la commande "CREATE SCHEMA". Dans l'exemple ci-dessous, un nouveau schéma, ACCOUNTS est créé, ainsi que deux tables et des vues sont ajoutées à ce shéma, puis sont ajoutées quelque règle de droit sur ces objets.
CREATE SCHEMA ACCOUNTS AUTHORIZATION DBA
CREATE TABLE AB(A INTEGER, ...)
CREATE TABLE CD(C CHAHR, ...)
CREATE VIEW VI AS SELECT ...
GRANT SELECT TO PUBLIC ON AB
GRANT SELECT TO JOE ON CD;
Requires Administrative privileges.
Créé une sequence. Le type par défaut est INTEGER. La valeur par défaut est 0 et l'incrément est 1.
Les valeurs négatives ne sont pas autorisées.
If a sequence goes beyond Integer.MAXVALUE or Long.MAXVALUE, the next result is determined by 2's complement arithmetic.
La prochaine valeur pour une sequence peut être inclues dans un SELECT, INSERT et un UPDATE comme dans les exemples suivants:
SELECT [...,] NEXT VALUE FOR <sequencename> [, ...] FROM <tablename>
En SQL 200n et dans la version courrante il n'y a pas de possibilité de retrouver la dernière valeur de la sequence retournée.
CREATE [MEMORY | CACHED | [GLOBAL] TEMPORARY | TEMP [1] | TEXT[1]] TABLE <name> ( <columnDefinition> [, ...] [, <constraintDefinition>...] ) [ON COMMIT {delete | preserve} ROWS];
Creates a tables in memory (default) or on disk and only cached in memory. If the database is all-in-memory, both MEMORY and CACHED forms of CREATE TABLE return a MEMORY table while the TEXT form is not allowed.
Components of a CREATE TABLE command
columnname Datatype [(columnSize[,precision])] [{DEFAULT <defaultValue> | GENERATED BY DEFAULT AS IDENTITY (START WITH <n>[, INCREMENT BY <m>])}] | [[NOT] NULL] [IDENTITY] [PRIMARY KEY]
Default values that are allowed are constant values or certain SQL datetime functions.
Allowed Default Values in Column Definitions
For character column, a single-quoted string or NULL. The only SQL function that can be used is CURRENT_USER.
For datetime columns, a single-quoted DATE, TIME or TIMESTAMP value or NULL. Or a datetime SQL function such as CURRENT_DATE, CURRENT_TIME, CURRENT_TIMESTAMP, TODAY, NOW. Each function is allowed for a certain datetime type.
For BOOLEAN columns, the literals FALSE, TRUE, NULL.
For numeric columns, any valid number or NULL.
For binary columns, any valid hex string or NULL.
Only one identity column is allowed in each table. Identity columns are autoincrement columns. They must be of INTEGER or BIGINT type and are automatically primary key columns (as a result, multi-column primary keys are not possible with an IDENTITY column present). Using the long SQL syntax the (START WITH <n>) clause specifies the first value that will be used. The last inserted value into an identity column for a connection is available using the function IDENTITY(), for example (where Id is the identity column):
INSERT INTO Test (Id, Name) VALUES (NULL,'Test');
CALL IDENTITY();
[CONSTRAINT <name>]
UNIQUE ( <column> [,<column>...] ) |
PRIMARY KEY ( <column> [,<column>...] ) |
FOREIGN KEY ( <column> [,<column>...] ) REFERENCES <refTable> ( <column> [,<column>...])
[ON {delete | update} {CASCADE | SET DEFAULT | SET NULL}][1] |
CHECK(<search condition>)[1]
Both ON DELETE and ON UPDATE clauses can be used in a single foreign key definition.
A search condition is similar to the set of conditions in a WHERE clause. In the current version of HSQLDB, the conditions for a CHECK constraint can only reference the current row, meaning there should be no SELECT statement. Sample table definitions with CHECK constraints are in TestSelfCheckConstraints.txt. This file is in the /hsqldb/testrun/hsqldb/ directory of the zip.
HSQLDB databases are initially created in a legacy mode that does not enforce column size and precision. You can set the property: sql.enforce_strict_size=true to enable this feature. When this property has been set, Any supplied column size and precision for numeric and character types (CHARACTER and VARCHAR) are enforced. Use the command, SET PROPERTY "sql.enforce_strict_size" TRUE once before defining the tables.
NOT NULL constraints can be part of the column definition only. Other constraints cannot be part of the column definition and must appear at the end of the column definition list.
TEMPORARY TABLE contents for each session (connection) are emptied by default at each commit or rollback. The optional qualifier ON COMMIT PRESERVE ROWS can be used to keep the rows while the session is open. The default is ON COMMIT DELETE ROWS.
See also: DROP TABLE.
CREATE TRIGGER <name> {before | after} {INSERT | UPDATE | DELETE} ON <table> [FOR EACH ROW] [QUEUE n] [NOWAIT] CALL <TriggerClass>;
TriggerClass is an application-supplied class that implements the org.hsqldb.Trigger interface e.g. "mypackage.TrigClass". It is the fire method of this class that is invoked when the trigger event occurs. You should provide this class, which can have any name, and ensure that this TriggerClass is present in the classpath which you use to start hsqldb.
Since 1.7.2 the implementation has been changed and enhanced. When the 'fire' method is called, it is passed the following arguments:
fire (String name, String table, Object row1[], Object row2[])
where 'row1' and 'row2' represent the 'before' and 'after' states of the row acted on, with each column being a member of the array. The mapping of members of the row arrays to database types is specified in Data Types. For example, BIGINT is represented by a java.lang.Long Object. Note that the number of elements in the row arrays is larger than the number of columns by one or two elements. Never modify the last elements of the array, which are not part of the actual row.
If the trigger method wants to access the database, it must establish its own JDBC connection. This can cause data inconsistency and other problems so it is not recommended. The jdbc:default:connection: URL is not currently supported.
Implementation note:
If QUEUE 0 is specified, the fire method is execued in the same thread as the database engine. This allows trigger action to alter the data that is about to be stored in the database. Data can be checked or modified in BEFORE INSERT / UPDATE + FOR EACH ROW triggers. All table constraints are then enforced by the database engine and if there is a violation, the action is rejected for the SQL command that initiated the INSERT or UPDATE. There is an exception to this rule, that is with UPDATE queries, referential integrity and cascading actions resulting from ON UPDATE CASCASE / SET NULL / SET DEFAULT are all performed prior to the invocation of the trigger method. If an invalid value that breaks referential integrity is inserted in the row by the trigger method, this action is not checked and results in inconsistent data in the table.
Alternatively, if the trigger is used for external communications and not for checking or altering the data, a queue size larger than zero can be specified. This is in the interests of not blocking the database's main thread as each trigger will run in a thread that will wait for its firing event to occur. When this happens, the trigger's thread calls TriggerClass.fire. There is a queue of events waiting to be run by each trigger thread. This is particularly useful for 'FOR EACH ROW' triggers, when a large number of trigger events occur in rapid succession, without the trigger thread getting a chance to run. If the queue becomes full, subsequent additions to it cause the database engine to suspend awaiting space in the queue. Take great care to avoid this situation if the trigger action involves accessing the database, as deadlock will occur. This can be avoided either by ensuring the QUEUE parameter makes a large enough queue, or by using the NOWAIT parameter, which causes a new trigger event to overwrite the most recent event in the queue. The default queue size is 1024. Note also that the timing of trigger method calls is not guaranteed, so applications should implement their own synchronization measures if necessary.
With a non-zero QUEUE parameter, if the trigger methods modifies the 'row2' values, these changes may or may not affect the database and will almost certainly result in data inconsistency.
Please refer to the code for org.hsqldb.sample.Trigger and org.hsqldb.sample.TriggerSample for more information on how to write a trigger class.
See also: DROP TRIGGER.
Créer un nouvel utilisateur ou un nouvel administrateur de BD. Le mot de passe doit être entre double-quotes. Unmot passe peut être vide, auquel cas utiliser "". Il est possible de changer le mot de passe vai la comande ALTER USER[1] .
Nécéssite les droits administrateur.
Voir: CONNECT, GRANT, REVOKE. ALTER USER[1],
CREATE VIEW <viewname>[(<viewcolumn>,..) AS SELECT ... FROM ... [WHERE Expression]; [ORDER BY orderExpression [, ...]] [LIMIT <limit> [OFFSET <offset>]];
A view can be thought of as either a virtual table or a stored query. The data accessible through a view is not stored in the database as a distinct object. What is stored in the database is a SELECT statement. The result set of the SELECT statement forms the virtual table returned by the view. A user can use this virtual table by referencing the view name in SQL statements the same way a table is referenced. A view is used to do any or all of these functions:
Restrict a user to specific rows in a table. For example, allow an employee to see only the rows recording his or her work in a labor-tracking table.
Restrict a user to specific columns. For example, allow employees who do not work in payroll to see the name, office, work phone, and department columns in an employee table, but do not allow them to see any columns with salary information or personal information.
Join columns from multiple tables so that they look like a single table.
Aggregate information instead of supplying details. For example, present the sum of a column, or the maximum or minimum value from a column.
Views are created by defining the SELECT statement that retrieves the data to be presented by the view. The data tables referenced by the SELECT statement are known as the base tables for the view. In this example, is a view that selects data from three base tables to present a virtual table of commonly needed data:
CREATE VIEW mealsjv AS
SELECT m.mid mid, m.name name, t.mealtype mt, a.aid aid,
a.gname + ' ' + a.sname author, m.description description,
m.asof asof
FROM meals m, mealtypes t, authors a
WHERE m.mealtype = t.mealtype
AND m.aid = a.aid;
You can then reference mealsjv in statements in the same way you would reference a table:
SELECT * FROM mealsjv;
A view can reference another view. For example, mealsjv presents information that is useful for long descriptions that contain identifiers, but a short list might be all a web page display needs. A view can be built that selects only specific mealsjv columns:
CREATE VIEW mealswebv AS SELECT name, author FROM mealsjv;
The SELECT statement in a VIEW definition should return columns with distinct names. If the names of two columns in the SELECT statement are the same, use a column alias to distinguish between them. A list of new column names can always be defined for a view.
CREATE VIEW aview (new_name, new_author) AS
SELECT name, author
FROM mealsjv
See also: SQL Expression, SELECT[1], DROP VIEW[1].
Efface une occurence d'une table.
Voir SQL Expression, INSERT, SELECT[1].
Ferme la connexion.
Il n'est pas nécéssaire d'appeler cette commande lorsque l'interface JDBC est utilisée car elle est appelée automatiquement. Une fois déconnecté, il n'ets plus possibkle d'executer d'autres requetes y compris CONNECT avec cette connexion.
Voir: CONNECT.
Retire l'index spécifié de la BD. Cela ne marche pas avec les indexes UNIQUE des clé étrangères FOREIGN KEY .
Voir: CREATE INDEX.
Retire tous les membres du rôle spécifié, puis efface le rôle lui même.
Removes the specified sequence from the database. When IF EXIST is used, the statement returns without an error if the sequence does not exist. The RESTRICT option is in effect by default, meaning that DROP will fail if any view reference the sequence. Specify the CASCADE option to silently drop all dependent database objects.
Removes the specified schema from the database. The RESTRICT option is in effect by default, meaning that DROP will fail if any objects such as tables or sequences have been defined in the schema. Specify the CASCADE option to silently drop all database objects in the schema.
Requires Administrative privileges.
Removes a table, the data and indexes from the database. When IF EXIST is used, the statement returns without an error even if the table does not exist.
The RESTRICT option is in effect by default, meaning that DROP will fail if any tables or views refer to this table. Specify the CASCADE option to silently drop all dependent views, and to drop any foreign key constraint that links this table with other tables.
See also:
Removes a view from the database. When IF EXIST is used, the statement returns without an error if the view does not exist. The RESTRICT option is in effect by default, meaning that DROP will fail if any other view refers to this view. Specify the CASCADE option to silently drop all dependent views.
See also: CREATE VIEW[1].
EXPLAIN PLAN FOR can be used with any query to get a detailed list of the elements in the execution plan.
This list includes the indexes used for performing the query and can be used to optimise the query or to add indexes to tables.
GRANT <rolename> [,...] TO <grantee>[1];
<grantee> is either a user name, a role name, or PUBLIC. PUBLIC means all users.
The first form of the GRANT command assigns privileges to a grantee for a table or for a class. To allow a user to call a function from a class, the right ALL must be used. Examples:
GRANT SELECT ON Test TO GUEST;
GRANT ALL ON CLASS "java.lang.String" TO PUBLIC;
The second form of the GRANT command gives the specified <grantee> membership in the specified role.
Require Administrative privileges.
See also: REVOKE, CREATE USER, CREATE ROLE[1].
Ajoute une ou plusieurs occurences dans la table.
REVOKE { SELECT | DELETE | INSERT | UPDATE | ALL } [,...]
ON { table | CLASS "package.class" } FROM <grantee>;
REVOKE <rolename> [,...] FROM <grantee>[1];
<grantee> is either a user name, a role name, or PUBLIC. PUBLIC means all users.
The first form of the REVOKE command withdraws privileges from a grantee for a table or for a class.
The second form of the REVOKE command withdraws membership of the specified <grantee> from the specified role.
Both forms require Administrative privileges.
See also: GRANT.
ROLLBACK used on its own, or with WORK, undoes changes made since the last COMMIT or ROLLBACK.
ROLLBACK TO SAVEPOINT <savepoint name> undoes the change since the named savepoint. It has no effect if the savepoint is not found.
See also: COMMIT.
Sets up a SAVEPOINT for use with ROLLBACK TO SAVEPOINT.
See also: COMMIT.
SCRIPT ['file'];
Creates an SQL script describing the database. If the file is not specified, a result set containing only the DDL script is returned. If the file is specified then this file is saved with the path relative to the machine where the database engine is located.
Only an administrator may do this.
SELECT [{LIMIT <offset> <limit> | TOP <limit>}[1]][ALL | DISTINCT]
{ selectExpression | table.* | * } [, ...]
[INTO [CACHED | TEMP | TEXT][1] newTable]
FROM tableList
[WHERE Expression]
[GROUP BY Expression [, ...]]
[HAVING Expression]
[{ UNION [ALL | DISTINCT] | {MINUS [DISTINCT] | EXCEPT [DISTINCT] } | INTERSECT [DISTINCT] } selectStatement]
[ORDER BY orderExpression [, ...]]
[LIMIT <limit> [OFFSET <offset>]];
Rechercher les informations depuis une ou plusieurs table de la BD.
Les composants de la commande SELECT :
table [{CROSS | INNER | LEFT OUTER | RIGHT OUTER} JOIN table ON Expression] [, ...]
{ (selectStatement) [AS] label | tableName}
{ Expression | COUNT(*) | {COUNT | MIN | MAX | SUM | AVG | SOME | EVERY | VAR_POP | VAR_SAMP | STDDEV_POP | STDDEV_SAMP} ([ALL | DISTINCT][1]] Expression) } [[AS] label]
si DISTINCT est spécifié, seule une instance des valeurs équivalentes est retournée avec la fonction d'aggrégation.
If DISTINCT is specified, only one instance of several equivalent values is used in the aggregate function.
A l'exception de COUNT(*), toutes les fonctonction d'aggrégation ignorent la valeur NULL.
Les types de valeurs retournées par les fonctions d'aggrégation sont :
| Fonction d'aggrégation | Type de valeur retournée |
| COUNT | INTEGER |
| MIN | le m^me que celui de la colonne sur laquelle s'pplique la fonction |
| MAX | le m^me que celui de la colonne sur laquelle s'pplique la fonction |
| AVG | le m^me que celui de la colonne sur laquelle s'pplique la fonction |
| SUM | is subject to deterministic widenning to ensure lossless results. |
| SOME | BOOLEAN |
| EVERY | BOOLEAN |
Les types de valeurs retournées par les fonctions statistiques est toujours DOUBLE . Ces dernières n'autorusent pas l'mploi des options ALL ou DISTINCT.
| Fonction statistiques | Type de valeur retournée |
| VAR_POP | DOUBLE |
| VAR_SAMP | DOUBLE |
| STDDEV_POP | DOUBLE |
| STDDEV_SAMP | DOUBLE |
Si CROSS JOIN est spécifié sans l'expression ON, elle sera prise pour un simple JOIN.
{ columnNr | columnAlias | selectExpression } [ASC | DESC]
Retourne les n premiers occurensces résultat d'un select (OFFSET) puis retourne les m dernières occurences résultat du m^me select (LIMIT).
Creates the result set for the SELECT statement first and then discards the first n rows (OFFSET) and returns the first m rows of the remaining result set (LIMIT).
Cas particulier: LIMIT 0 m est equivalent à TOP m ou FIRST m dans d'autre moteurs de BD.
LIMIT n 0 ne retourne pas les n premières lignes rows puis retourne le reste du résultat de la requete.
Cette forme est utilisée à la fin des select. Le terme OFFSET est optionnel.
This form is used at the end of the SELECT statement. The OFFSET term is optional.
Equivalent à LIMIT 0 m.
Plusieurs SELECT peuvent être associés par les commandes UNION, EXCEPT et INTERSECT. Chaque SELECT est alors traité en tant que terme d'une experssion. L'expression est évaluée de gauche à droite, mais INTERSECT est traité en premier. L'utilisation de parenthèses permet de changer les priorités d"évaluations.
SET AUTOCOMMIT { true | false };
Switches on or off the connection's auto-commit mode. If switched on, then all statements will be committed as individual transactions. Otherwise, the statements are grouped into transactions that are terminated by either COMMIT or ROLLBACK. By default, new connections are in auto-commit mode. This command should not be used directly. Use the JDBC equivalent method, Connection.setAutoCommit(boolean autocommit).
SET DATABASE COLLATION <double quoted collation name>;
Each database can have its own collation. Sets the collation from the set of collations in the source for org.hsqldb.Collation. Once this command has been issued, the database can be opened in any JVM and will retain its collation.
Once this command has been issued, the database can be opened in any JVM and will retain its collation.
SET CHECKPOINT DEFRAG <size>;
The parameter size is the megabytes of abandoned space in the .data file. When a CHECKPOINT is performed either as a result of the .log file reaching the limit set by "SET LOGSIZE size", or by the user issuing a CHECKPOINT command, the amount of space abandoned during the session is checked and if it is larger than size, a CHECKPOINT DEFRAG is performed instead of a checkpoint.
SET IGNORECASE { true | false };
Disables (ignorecase = true) or enables (ignorecase = false) the case sensitivity of text comparison and indexing for new tables. By default, character columns in new databases are case sensitive. The sensitivity must be switched before creating tables. Existing tables and their data are not affected. When switched on, the data type VARCHAR is set to VARCHAR_IGNORECASE in new tables. Alternatively, you can specify the VARCHAR_IGNORECASE type for the definition of individual columns. So it is possible to have some columns case sensitive and some not, even in the same table.
Only an administrator may do this.
SET LOGSIZE <size>;
Sets the maximum size in MB of the .log file. Default is 200 MB. The database will be closed and opened (just like using CHECKPOINT) if the .log file gets over this limit, and so the .log file will shrink. 0 means no limit.
See also: CHECKPOINT.
Change le mot de passe de l'utilisateur courrant connecté.
Le mot de pass doit encadré de doubles quotes. Utiliser "" pour les mot de passe vides.
Sets a database property. Properties that can be set using this command are either boolean or integral and are listed in the Advanced Topics chapter.
SET REFERENTIAL_INTEGRITY { true | false };
This commands enables / disables the referential integrity checking (foreign keys). Normally it should be switched on (this is the default) but when importing data (and the data is imported in the 'wrong' order) the checking can be switched off.
Note that when referential integrity is switched back on, no check is made that the changes to the data are consistent with the existing referential integrity constraints. You can verify consistency using SQL queries and take appropriate actions.
Only an administrator may do this.
See also: CREATE TABLE.
SET SCHEMA <schemaname>;
Sets the current JDBC session's schema. The sole purpose for the session schema is to provide a default schema name for schema objects that do not have the schema name specified explicitly in the SQL command, or by association with another object of known schema. For example, if you run SELECT * FROM atbl;, HSQLDB will look for the table or view named atbl in the session's current schema.
Session schemas last only for the duration of the current session. When a new JDBC session is obtained, the new session will have the default schema.
SET SCRIPTFORMAT {TEXT | BINARY | COMPRESSED};
Changes the format of the script file. BINARY and COMPRESSED formats are slightly faster and more compact than the default TEXT. Recommended only for very large script files.
SET TABLE tableName INDEX 'index1rootPos index2rootPos ... ';
This command is only used internally to store the position of index roots in the .data file. It appears only in database script files; it should not be used directly.
Positionne la table en lecture seule.
SET TABLE <tablename> SOURCE <file and options> [DESC];
For details see the Text Tables chapter.
This command is used exclusively with TEXT tables to specify which file is used for storage of the data. The optional DESC qualifier results in the text file indexed from the end and opened as readonly. The <file and options> argument is a double quoted string that consists of:
<file and options>::= <doublequote> <filepath> [<semicolon> <option>...] <doublequote>
Example:
SET TABLE mytable SOURCE "myfile;fs=|;vs=.;lvs=~"
Supported Properties
default is true. If false, treats double quotes as normal characters
default is false. If true, adds double quotes around all fields.
character encoding for text and character fields, for example, encoding=UTF-8
default is false. If true ignores the first line of the file
exponent to calculate rows of the text file in cache. Default is 8, equivalent to nearly 800 rows
exponent to calculate average size of each row in cache. Default is 8, equivalent to 256 bytes per row.
field separator
varchar separator
long varchar separator
Special indicators for Hsqldb Text Table separators
semicolon
quote
space character
apostrophe
newline - Used as an end anchor (like $ in regular expressions)
carriage return
tab
backslash
a Unicode character specified in hexadecimal
Only an administrator may do this.
SET WRITE_DELAY {{ true | false } | <seconds> | <milliseconds> MILLIS};
This controls the frequency of file sync for the log file. When WRITE_DELAY is set to FALSE or 0, the sync takes place immediately at each COMMIT. WRITE_DELAY TRUE performs the sync once every 20 seconds (which is the default). A numeric value can be specified instead.
The purpose of this command is to control the amount of data loss in case of a total system crash. A delay of 1 second means at most the data written to disk during the last second before the crash is lost. All data written prior to this has been synced and should be recoverable.
A write delay of 0 impacts performance in high load situations, as the engine has to wait for the file system to catch up.
To avoid this, you can set write delay down to 10 milliseconds. In practice, a write delay of 100 milliseconds provides better than 99.9999% reliability with an average one system crash per day, or 99.99999% with an average one system crash per 6 days.
Each time a SET WRITE_DELAY is issued with any value, a sync is immediately performed.
Only an administrator may do this.
Closes the current database.
Varieties of the SHUTDOWN command
Performs a checkpoint to creates a new .script file that has the minimum size and contains the data for memory tables only. It then backs up the .data file containing the CACHED TABLE data in zipped format to the .backup file and closes the database.
Just closes the database files (like when the Java process for the database is terminated); this command is used in tests of the recovery mechanism. This command should not be used as the routine method of closing the database.
Writes out a new .script file which contains the data for all the tables, including CACHED and TEXT tables. It then deletes the existing text table files and the .data file before rewriting them. After this, it backs up the .data file in the same way as normal SHUTDOWN. This operation shrinks all files to the minimum size.
Similar to SHUTDOWN COMPACT but after writing the script and deleting the existing files, it does not rewrite the .data and text table files. After SHUTDOWN SCRIPT, only the .script and .properties file remain. At the next startup, these files are processed and the .data and .backup files are created. This command in effect performs part of the job of SHUTDOWN COMPACT, leaving the other part to be performed automatically at the next startup.
This command produces a full script of the database which can be edited for special purposes prior to the next startup.
Only an administrator may use the SHUTDOWN command.
Table 9.1. Data Types. The types on the same line are equivalent.
| Name | Range | Java Type |
|---|---|---|
| INTEGER | INT | as Java type | int | java.lang.Integer |
| DOUBLE [PRECISION] | FLOAT | as Java type | double | java.lang.Double |
| VARCHAR | as Integer.MAXVALUE | java.lang.String |
| VARCHAR_IGNORECASE | as Integer.MAXVALUE | java.lang.String |
| CHAR | CHARACTER | as Integer.MAXVALUE | java.lang.String |
| LONGVARCHAR | as Integer.MAXVALUE | java.lang.String |
| DATE | as Java type | java.sql.Date |
| TIME | as Java type | java.sql.Time |
| TIMESTAMP | DATETIME | as Java type | java.sql.Timestamp |
| DECIMAL | No limit | java.math.BigDecimal |
| NUMERIC | No limit | java.math.BigDecimal |
| BOOLEAN | BIT | as Java type | boolean | java.lang.Boolean |
| TINYINT | as Java type | byte | java.lang.Byte |
| SMALLINT | as Java type | short | java.lang.Short |
| BIGINT | as Java type | long | java.lang.Long |
| REAL | as Java type | double | java.lang.Double[1] |
| BINARY | as Integer.MAXVALUE | byte[] |
| VARBINARY | as Integer.MAXVALUE | byte[] |
| LONGVARBINARY | as Integer.MAXVALUE | byte[] |
| OTHER | OBJECT | as Integer.MAXVALUE | java.lang.Object |
The uppercase names are the data types names defined by the SQL standard or commonly used by RDMS's. The data types in quotes are the Java class names - if these type names are used then they must be enclosed in quotes because in Java names are case-sensitive. Range indicates the maximum size of the object that can be stored. Where Integer.MAXVALUE is stated, this is a theoretical limit and in practice the maximum size of a VARCHAR or BINARY object that can be stored is dictated by the amount of memory available. In practice, objects of up to a megabyte in size have been successfully used in production databases.
The recommended Java mapping for the JDBC datatype FLOAT is as a Java type "double". Because of the potential confusion it is recommended that DOUBLE is used instead of FLOAT.
VARCHAR_IGNORECASE is a special case-insensitive type of VARCHAR. This type is not portable.
In table definition statements, HSQLDB accepts size, precision and scale qualifiers only for certain types: CHAR(s), VARCHAR(s), DOUBLE(p), NUMERIC(p), DECIMAL(p,s) and TIMESTAMP(p).
TIMESTAMP(p) can take only 0 or 6 as precision. Zero indicates no subsecond part. Without the precision, the default is 6.
By default specified precision and scale for the column is simply ignored by the engine. Instead, the values for the corresponding Java types are always used, which in the case of DECIMAL is an unlimited precision and scale. If a size is specified, it is stored in the database definition but is not enforeced by default. Once you have created the database (before adding data), you can add a database property value to enforce the sizes:
SET PROPERTY "sql.enforce_strict_size" true
This will enforce the specified size and pad CHAR fields with spaces to fill the size. This complies with SQL standards by throwing an exception if an attempt is made to insert a string longer than the maximum size. It also results in all DECIMAL values conforming to the specified precision and scale.
CHAR and VARCHAR and LONGVARCHAR columns are by default compared and sorted according to POSIX standards. See the SET DATABASE COLLATION[1] section above to modify this behavior. The property sql.compare_in_locale is no longer supported. Instead, you can define a collation to be used for all character comparisons.
Columns of the type OTHER or OBJECT contain the serialized form of a Java Object in binary format. To insert or update such columns, a binary format string (see below under Expression) should be used. Using PreparedStatements with JDBC automates this transformation.
| -- SQL style line comment |
| // Java style line comment |
| /* C style line comment */ |
All these types of comments are ignored by the database.
Stored procedures are Java functions that are called directly from the SQL language or using an alias. Calling Java functions (directly or using the alias) requires that the Java class can be reached by the database (server). The syntax is:
"java.lang.Math.sqrt"(2.0)
This means the package must be provided, and the name must be written as one word, and inside " because otherwise it is converted to uppercase (and not found).
An alias can be created using the command CREATE ALIAS:
CREATE ALIAS SQRT FOR "java.lang.Math.sqrt";
When an alias is defined, then the function can be called additionally using this alias:
SELECT SQRT(A) , B FROM MYTABLE;
Only static java methods can be used as stored procedures. If, within the same class, there are overloaded methods with the same number of arguments, then the first one encountered by the program will be used. If you want to use Java library methods, it is recommended that you create your own class with static methods that act as wrappers around the Java library methods. This will allow you to control which method signature is used to call each Java library method.
Numerical built-in Functions / Stored Procedures
retourne la valeur absolue du DOUBLE d
returns the absolute value of a double value
retourne le cosinus de l'angle d
returns the arc cosine of an angle
retourne le sinus de l'angle d
returns the arc sine of an angle
retourne la tangeante de l'angle d
returns the arc tangent of an angle
returns the tangent of a/b
return a & b
returns a | b
retourne le plus petit entier qui n'est pas inféruieur à d
returns the smallest integer that is not less than d
retourne le cosinus de l'angle d
returns the cosine of an angle
returns the cotangent of an angle
Converti des radian en degrés (unité de mesure des angles je crois)
converts radians to degrees
returns e (2.718...) raised to the power of d
returns the largest integer that is not greater than d
returns the natural logarithm (base e)
returns the logarithm (base 10)
returns a modulo b
returns pi (3.1415...)
returns a raised to the power of b
Converti des degrés en radian (unité de mesure des angles je crois)
converts degrees to radians
Retourne un nombre aléatoir x plus grand que 0.0 et plus petit que 1.0
returns a random number x bigger or equal to 0.0 and smaller than 1.0
rounds a to b digits after the decimal point
solves rounding problems such as 3.11-3.1-0.01
returns -1 if d is smaller than 0, 0 if d==0 and 1 if d is bigger than 0
retourne le sinus de l'angle d
returns the sine of an angle
returns the square root
retourne la tangeante trigonometrique de l'angle A
returns the trigonometric tangent of an angle
truncates a to b digits after the decimal point
String built-in Functions / Stored Procedures
returns the ASCII code of the leftmost character of s
returns the length of the string in bits
returns a character that has the ASCII code c
returns the length of the string in characters
retourne le résultat de la concaténation des chaines str1 et str2
remarque : apparement str1 et str2 ne peuvent pas être des expressions, il s'agit vraiment de chaines de caractères. Cela semble être confirmé par mes test.
returns str1 + str2
returns the difference between the sound of s1 and s2
returns translated string
returns a string where len number of characters beginning at start has been replaced by s2
converti la chaine s en minuscule
returns the leftmost count of characters of s) - requires double quoting - use SUBSTRING() instead
Retourne le nombre de caractères de la chaine s
returns the number of characters in s
returns the first index (1=left, 0=not found) where search is found in s, starting at start
Retire tous les blancs répétés de la chaine s
removes all leading blanks in s
returns the length of the string in bytes (twice the number of characters)
returns translated string
returns s repeated count times
replaces all occurrences of replace in s with s2
returns the rightmost count of characters of s
removes all trailing spaces
returns a four character code representing the sound of s
Retourne la chaine de caractère constituée de count espaces
returns a string consisting of count spaces
alias pour substring
retourne la sous chaine commencant en position start sur une longueur de len
returns the substring starting at start (1=left) with length len
converti la chaine s en majuscule
converts s to upper case
converti la chaine s en minuscule
converts s to lower case
converti la chaine s en majuscule
converts s to upper case
Date/Time built-in Functions / Stored Procedures
returns the current date
returns the current time
returns the count of units of time elapsed from datetime1 to datetime2. The string indicates the unit of time and can have the following values 'ms'='millisecond', 'ss'='second','mi'='minute','hh'='hour', 'dd'='day', 'mm'='month', 'yy' = 'year'. Both the long and short form of the strings can be used.
returns the name of the day
returns the day of the month (1-31)
returns the day of the week (1 means Sunday)
returns the day of the year (1-366)
return the hour (0-23)
returns the minute (0-59)
returns the month (1-12)
returns the name of the month
returns the current date and time as a timestamp) - use CURRENT_TIMESTAMP instead
returns the quarter (1-4)
returns the second (0-59)
returns the week of this year (1-53)
returns the year
returns the current date
returns the current time
returns the current timestamp
System/Connection built-in Functions / Stored Procedures
returns the name of the database of this connection
returns the user name of this connection
SQL standard function, returns the user name of this connection
returns the last identity values that was inserted by this connection
System built-in Functions / Stored Procedures
if exp is null, value is returned else exp) - use COALESCE() instead
if exp is true, v1 is returned, else v2) - use CASE WHEN instead
converts exp to another data type
converts exp to another data type
if expr1 is not null then it is returned else, expr2 is evaluated and if not null it is returned and so on
if v1 equals v2 return null, otherwise v1
CASE v1 WHEN v2 THEN v3 [ELSE v4] END
when v1 equals v2 return v3 [otherwise v4 or null if there is no ELSE]
CASE WHEN expr1 THEN v1[WHEN expr2 THEN v2] [ELSE v4] END
when expr1 is true return v1 [optionally repeated for more cases] [otherwise v4 or null if there is no ELSE]
EXTRACT ({YEAR | MONTH | DAY | HOUR | MINUTE | SECOND} FROM <datetime value>)
POSITION(<string expression> IN <string expression>)
if the first string is a sub-string of the second one, returns the position of the sub-string, counting from one; otherwise 0
SUBSTRING(<string expression> FROM <numeric expression> [FOR <numeric expression>])
TRIM([{LEADING | TRAILING | BOTH}] FROM <string expression>)
See also: CALL, CREATE ALIAS.
[NOT] condition [{ or | and } condition]
Components of SQL Expressions
{ value [|| value]
| value { = | < | <= | > | >= | <> | != } value
| value IS [NOT] NULL
| EXISTS(selectStatement)
| value BETWEEN value AND value
| value [NOT] IN ( {value [, ...] | selectStatement } )
| value [NOT] LIKE value [ESCAPE] value }
[+ | -] { term [{ + | - | * | / | || } term]
| ( condition )
| function ( [parameter] [,...] )
| selectStatement giving one value
| {any|all} (selectStatement giving single column)
{ 'string' | number | floatingpoint
| [table.]column | TRUE | FALSE | NULL }
NEXT VALUE FOR <sequence>
HSQLDB does not currently enforce the SQL 200n proposed rules on where sequence generated values are allowed to be used. In general, these values can be used in insert and update statements but not in CASE statements, order by clauses, search conditions, aggregate functions, or grouped queries.
Les chaines en HSQLDB sont des chaines UNICODE.
Elles sont entourées de simple cotes, ou de doubles cotes si la simple cote est un caractère utilisé pdans la chaine.
La concaténation devrait mieux fonctionner avec l'opérateur du SQL standart || qu'avec l'opérateur non standart +
Strings in HSQLDB are Unicode strings. A string starts and ends with a single ' (singlequote). In a string started with ' (singlequote) use '' (two singlequotes) to create a ' (singlequote).String contatenation should be performed with the standard SQL operator || rather than the non-standard + operator.
The LIKE keyword uses '%' to match any (including 0) number of characters, and '_' to match exactly one character. To search for '%' or '_' itself an escape character must also be specified using the ESCAPE clause. For example, if the backslash is the escaping character, '\%' and '\_' can be used to find the '%' and '_' characters themselves. For example, SELECT .... LIKE '\_%' ESCAPE '\' will find the strings beginning with an underscore.
The character set for quoted identifiers (names) in HSQLDB is Unicode.
A unquoted identifier (name) starts with a letter and is followed by any number of ASCII letters or digits. When an SQL statement is issued, any lowercase characters in unquoted identifiers are converted to uppercase. Because of this, unquoted names are in fact ALL UPPERCASE when used in SQL statements. An important implication of this is the for accessing columns names via JDBC DatabaseMetaData: the internal form, which is the ALL UPPERCASE must be used if the column name was not quoted in the CREATE TABLE statement.
Quoted identifiers can be used as names (for tables, columns, constraints or indexes). Quoted identifiers start and end with " (one doublequote). A quoted identifier can contain any Unicode character, including space. In a quoted identifier use "" (two doublequotes) to create a " (one doublequote). With quoted identifiers it is possible to create mixed-case table and column names. Example:
CREATE TABLE "Address" ("Nr" INTEGER,"Name" VARCHAR); SELECT "Nr", "Name" FROM "Address";
The equivalent quoted identifier can be used for an unquoted identifer by converting the identifier to all uppercase and quoting it. For example, if a table name is defined as Address2 (unquoted), it can be referred to by its quoted form, "ADDRESS2", as well as address2, aDDress2 and ADDRESS2. Quoted identifiers should not be confused with SQL strings.
Quoting can sometimes be used for identifiers, aliases or functions when there is an ambiguity. For example:
SELECT COUNT(*) "COUNT" FROM MYTABLE;
SELECT "LEFT"(COL1, 2) FROM MYTABLE;
Although HSQLDB 1.8.0 does not force unquoted identifiers to contain only ASCII characters, the use of non-ASCII characters in these identifiers does not comply with SQL standards. Portability between different JRE locales could be an issue when accented characters (or extended unicode characters) are used in unquoted identifiers. Because native Java methods are used to convert the identifier to uppercase, the result may vary not be expected in different locales. It is recommended that accented characters are used only in quoted identifiers.
When using JDBC DatabaseMetaData methods that take table, column, or index identifiers as arguments, treat the names as they are registered in the database. With these methods, unquoted identifiers should be used in all-uppercase to get the correct result. Quoted identifiers should be used in the exact case combination as they were defined - no quote character should be included around the name. JDBC methods that return a result set containing such identifiers return unquoted identifiers as all-uppercase and quoted identifiers in the exact case they are registered in the database (a change from 1.6.1 and previous versions).
Please also note that the JDBC getXXX(String columnName) methods interpret the columnName as case-independent. This is a general feature of JDBC and not specific to HSQLDB.
Passwords must be double quoted and used consistently. Passwords are case insensitive only for backward compatibility. This may change in future versions.
A DATE literal starts and ends with ' (singlequote), the format is yyyy-mm-dd (see java.sql.Date.
A TIME liteal starts and ends with ' (singlequote), the format is hh:mm:ss (see java.sql.Time).
A TIMESTAMP or DATETIME literal starts and ends with ' (singlequote), the format is yyyy-mm-dd hh:mm:ss.SSSSSSSSS (see java.sql.Timestamp).
When specifying default values for date / time columns in CREATE TABLE statements, or in SELECT,INSERT, and UPDATE statements, special SQL functions: NOW, SYSDATE, TODAY, CURRENT_TIMESTAMP, CURRENT_TIME and CURRENT_DATE (case independent) can be used. NOW is used for TIME and TIMESTAMP columns, TODAY is used for DATE columns. The data and time variants CURRENT_* are SQL standard versions and should be used in preference to others. Example:
CREATE TABLE T(D DATE DEFAULT CURRENT_DATE);
CREATE TABLE T1(TS TIMESTAMP DEFAULT CURRENT_TIMESTAMP);
Binary data starts and ends with ' (singlequote), the format is hexadecimal. '0004ff' for example is 3 bytes, first 0, second 4 and last 255 (0xff).
Any number of commands may be combined. With combined commands, ';' (semicolon) must be used at the end of each command to ensure data integrity, despite the fact that the engine may understand the end of commands and not return an error when a semicolon is not used.
Table of Contents
From 1.8.0, the supplied hsqldb.jar file is built with Java 1.5. If you want to run the engine under JDK1.3 or earlier, you should rebuild the jar with Ant.
Ant (Another Neat Tool) is used for building hsqldb. The version currently used to test the build script is 1.6.1 but versions since 1.5.1 should also be compatible.
Ant is a part of the Jakarta/Apache Project.
The Installing Ant page of the Ant Manual . Follow the directions for your platform.
Once you have unpacked the zip package for hsqldb, under the /hsqldb folder, in /build there is a build.xml file that builds the hsqldb.jar with Ant (Ant must be already installed). To use it, change to /build then type:
ant -projecthelp
This displays the available ant targets, which you can supply as command line arguments to ant. These include
to make the hsqldb.jar
Lists all targets which build jar files, with an explanation of the purposes of the different jars.
to clean up the /classes directory that is created
to remove the old jar as well
to build javadoc
to build a smaller jar for HSQLDB that does not contain utilities
to build an extremely small jar containing only the client-side JDBC driver (does not support direct connection to HSQLDB URLs of the form jdbc:hsldb:mem:*, jdbc:hsqldb:file:*, nor jdbc:hsqldb:res:*).
to build a small jar that supports HSQLDB URLs of the form jdbc:hsqldb:mem:*, jdbc:hsqld:file*, jdbc:hsqldb:res:*; but not network URLs like jdbc:hsql* or jdbc:http*.
to build a larger jar for hsqldb that contains tests
Many more targets are available. Run ant -projecthelp and ant explainjars.
HSQLDB can be built in any combination of three JRE (Java Runtime Environment) versions and many jar file sizes. The smallest jar size(hsqljdbc.jar) contains only the HSQLDB JDBC Driver client. The default size (hsqldb.jar) also contains server mode support and the utilities. The largest size (hsqldbtest.jar)includes some test classes as well. Before building the hsqldbtest.jar package, you should download the junit jar from http://www.junit.org and put it in the /lib directory, alongside servlet.jar, which is included in the .zip package.
Just run ant explainjars for a concise list of all available jar files.
If you want your code built for debugging, as opposed to high performance, make a file named build.properties in your build directory with the contents
build.debug: true
The preferred method of rebuilding the jar is with Ant. After installing Ant on your system use the following command from the /build directory:
ant explainjars
The command displays a list of different options for building different sizes of the HSQLDB Jar. The default is built using:
The Ant method always builds a jar with the JDK that is used by Ant and specified in its JAVA_HOME environment variable. Building with JDK 1.4.x or 1.5.x will result in a jar that is not backward compatible.
From version 1.7.2, use of JDK 1.1.x is not recommended for building the JAR, even for running under JDK 1.1.x -- use JDK 1.3.1 for compatibility with 1.1.x. This is done in the following way. JDK 1.3.1 should be used as the JAVA_HOME for ant. You then issue the following commands. The first command will make the sources compatible with JDK 1.3, the second command modifies the sources further so that the compiled result can run under jdk 1.1 as well. The third command builds the jar.
ant switchtojdk12 ant switchtojava1target ant hsqldb
UNIX users must use Ant to build hsqldb.
For DOS/Windows users, a set of MSDOS batch files is provided as an example. These files produce only the default jar size. The path and classpath variables for the JDK should of course be set before running any of the batch files. These files are not currently maintained and will probably need some additions and changes to work correctly. Please see the build.xml file for up-to-date file
If you are compiling for JDK's other than 1.4.x, you should use the appropriate switchToJDK11.bat or switchToJDK12.bat to adapt the source files to the target JDK before running the appropriate buildJDK11.bat or buildJDK12.bat JDK and JRE versions.
CodeSwitcher is a tool to manage different version of Java source code. It allows to compile HSQLDB for different JDKs. It is something like a precompiler in C but it works directly on the source code and does not create intermediate output or extra files.
CodeSwitcher is used internally in HSQLDB build scripts. You do not have to use it separately to compile HSQLDB.
CodeSwitcher reads the source code of a file, removes comments where appropriate and comments out the blocks that are not used for a particular version of the file. This operation is done for all files of a defined directory, and all subdirectories.
Example A.2. Example source code before CodeSwitcher is run
...
//#ifdef JAVA2
properties.store(out,"hsqldb database");
//#else
/*
properties.save(out,"hsqldb database");
*/
//#endif
...
The next step is to run CodeSwitcher.
The '.' means the program works on the current directory (all subdirectories are processed recursively). -JAVA2 means the code labelled with JAVA2 must be switched off.
Example A.4. Source code after CodeSwitcher processing
...
//#ifdef JAVA2
/*
pProperties.store(out,"hsqldb database");
*/
//#else
pProperties.save(out,"hsqldb database");
//#endif
...
For detailed information on the command line options run java org.hsqldb.util.CodeSwitcher. Usage examples can be found in the switchtojdk1*.bat files in the /build directory.
To build the User Guide in HTML format, you must have the Docbook stylesheets installed locally. The Docbook stylesheets are available on the Internet. On Linux, just install the docbook-xsl-stylesheets rpm. Then add an entry to build.properties in your build directory with contents like
docbook.xsl.home: /usr/share/sgml/docbook/docbook-xsl-stylesheets
To build the User Guide in PDF format, you must also have the Java FOP system installed locally. FOP is available for free download on the Internet. Add an entry to build.properties in your build directory with contents like
fop.home /usr/local/fop-0.20.5
By default, your docs will fail to build if you do not have Internet connectivity. This is because our primary Docbook source file references the Docbook DTDs via Internet URL. You can build without Internet connectivity by installing the Docbook DTDs and editing our primary Docbook source file. Docbook is available on the Internet. On Linux, just install the docbook-dtds or docbook rpm. Then make one edit to the file docsrc/guide/guide.xml in your HSQLDB distribution. Change the line containing
"http://www.oasis-open.org/docbook/xml/4.2CR1/docbookx.dtd" [to
"file:///usr/share/xml/docbook/schema/dtd/4.2/docbookx.dtd" [where the second filepath is the path to the docbookx.dtd file within your Docbook installation.
Pour lancer le résultat du programme je passe les commandes de lancemant dans un fichier HSQLDBase.bat (gare au class path)
Visualiser le source commenté en francais HSQLDBase.java
Ce programme réalise les étapes suivantes:
* ETAPE I : Chargement du pilote dans la JVM (Java Virtual Machine)
* ETAPE II : Etablissement de la connexion
avec passage des parametres en dur si l'on est en mode debug (debug ==true)
Lecture des parametres de connexion dans le fichier de propriété sqltool_idx.rc
* ETAPE III: Exécution d'une requête SQL
requete de type select
requete de type update
* ETAPE IV : Analyse des résultats
Merci à Olivier Capuozzo pour ces explications
Visualiser le fichier de propriété sqltool_idx.rc
Visualiser le script Cr_shema.sql ayant permis de créer la base visée et de renseignere quelques lignes
La base de données est crée dans le repertoire data (cf exemple rc), elle s'appelle idx.
elle est créé avec le dbmanager que j'ai lancer avec le fichier de commande MgrDB.bat (qui me place dans data) en passant les paramètres
Setting name |
idx |
|
Type |
standalone |
|
Driver |
org.hsqldb.jdbcDriver |
|
Url |
jdbc:hsqldb:file:idx/idx |
|
user |
sa |
|
password |
|
Le fichier HSQLDBase.class issu de la compilation de HSQLDBase.java est placé dans data, ainsi que HSQLDBase.bat et sqltool_idx.rc
Ci-dessous est une copie de Testdb.java qui se truove dans le répertoire src/org/hsqldb/sample de votre distribution HSQLDB :
Example B.1. JDBC Client source code example
/* Copyright (c) 2001-2005, The HSQL Development Group
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* Redistributions of source code must retain the above copyright notice, this
* list of conditions and the following disclaimer.
*
* Redistributions in binary form must reproduce the above copyright notice,
* this list of conditions and the following disclaimer in the documentation
* and/or other materials provided with the distribution.
*
* Neither the name of the HSQL Development Group nor the names of its
* contributors may be used to endorse or promote products derived from this
* software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL HSQL DEVELOPMENT GROUP, HSQLDB.ORG,
* OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package org.hsqldb.sample;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.sql.Statement;
/**
* Title: Testdb
* Description: simple hello world db example of a
* standalone persistent db application
*
* every time it runs it adds four more rows to sample_table
* it does a query and prints the results to standard out
*
* Author: Karl Meissner karl@meissnersd.com
*/
public class Testdb {
Connection conn; //our connnection to the db - presist for life of program
// we dont want this garbage collected until we are done
public Testdb(String db_file_name_prefix) throws Exception { // note more general exception
// Load the HSQL Database Engine JDBC driver
// hsqldb.jar should be in the class path or made part of the current jar
Class.forName("org.hsqldb.jdbcDriver");
// connect to the database. This will load the db files and start the
// database if it is not alread running.
// db_file_name_prefix is used to open or create files that hold the state
// of the db.
// It can contain directory names relative to the
// current working directory
conn = DriverManager.getConnection("jdbc:hsqldb:"
+ db_file_name_prefix, // filenames
"sa", // username
""); // password
}
public void shutdown() throws SQLException {
Statement st = conn.createStatement();
// db writes out to files and performs clean shuts down
// otherwise there will be an unclean shutdown
// when program ends
st.execute("SHUTDOWN");
conn.close(); // if there are no other open connection
}
//use for SQL command SELECT
public synchronized void query(String expression) throws SQLException {
Statement st = null;