Movatterモバイル変換


[0]ホーム

URL:


Jump to content
WikibooksThe Free Textbook Project
Search

Clojure Programming/Examples/JDBC Examples

From Wikibooks, open books for an open world
<Clojure Programming |Examples

This page is intended to be a reference for using JDBC with Clojure. We'll create a simple blog database to see the basic functions in clojure.java.jdbc.

For the latest, most up-to-date community-managed documentation for the clojure.java.jdbc library, consultUsing java.jdbc on Clojure Documentation. This WikiBooks page is written around a very old version of the library and most of the examples here will not work with newer versions.

Connection Examples

[edit |edit source]

Below are several examples of connecting to a database of JDBC through Clojure. They all depend on the Clojure Contrib library org.clojure/java.jdbc. Also, you need to have the proper JDBC jar in the class path.

Microsoft SQL Server

[edit |edit source]
(use'clojure.java.jdbc)(defdb{:classname"com.microsoft.jdbc.sqlserver.SQLServerDriver":subprotocol"sqlserver":subname"//server-name:port;database=database-name;user=sql-authentication-user-name;password=password"});Add Classpath to your C:\Program Files\Java\JDBC\sqljdbc_3.0\enu\sqljdbc4.jar;Below code demos how to execute a simple sql select query and print it to console;This query will print all the user tables in your MS SQL Server Database(with-connectiondb(with-query-resultsrs["select * from sys.objects  where type = 'U'"](doseq[rowrs](println(:namerow)))));;Instead of passing user and password, you can authenticate yourself using current system user (es. current windows user);;To do this you have to add the string "integratedSecurity=true", removing user and password(defdb{:classname"com.microsoft.jdbc.sqlserver.SQLServerDriver":subprotocol"sqlserver":subname"//server-name:port;database=database-name;integratedSecurity=true"});;You have also to add the "sqljdc_auth.dll" file to your java.library.path (you can find the dll file into the JDBCDriver folder /enu/auth/platform you probably download before);;An easy way to check what is your current java.library.path is calling this from leiningen repl(.SystemgetProperty"java.library.path");;I suggest reload the shell or the system after the dll is added

Apache Derby

[edit |edit source]

Derby supports either client/server or embedded operation. This example uses the embedded mode.

(use'clojure.java.jdbc)(let[db-path"c:/derby/myblog"](defdb{:classname"org.apache.derby.jdbc.EmbeddedDriver":subprotocol"derby":subnamedb-path:createtrue}))

H2Database

[edit |edit source]
(let[db-protocol"tcp"; "file|mem|tcp"db-host"localhost:9092"; "path|host:port"db-name"Sample"](defdb{:classname"org.h2.Driver"; must be in classpath:subprotocol"h2":subname(str"jdbc:h2:"db-protocol"://"db-host"/"db-name); Any additional keys are passed to the driver; as driver-specific properties.:user"sa":password""}));; specify the path to your database driver;(add-classpath"file:///c:/Installation/h2/bin/h2.jar");;;; Here is an example of creating a symbol in the;; existing namespace as an alias to a namespace;;;(require '[clojure.java.jdbc :as sql]);(sql/with-connection db;  (sql/with-query-results rs ["select * from customer"];    (dorun (map #(println (:lastname %)) rs))))

MySQL

[edit |edit source]

The MySQL connector is fairly straightforward to set up. The classname and subprotocol are set to the values for MySQL. The db-port is set to 3306, as this is the default port for MySQL.

(use'clojure.java.jdbc)(let[db-host"localhost"db-port3306db-name"a_database"](defdb{:classname"com.mysql.jdbc.Driver"; must be in classpath:subprotocol"mysql":subname(str"//"db-host":"db-port"/"db-name); Any additional keys are passed to the driver; as driver-specific properties.:user"a_user":password"secret"}))

PostgreSQL

[edit |edit source]

The PostgreSQL connection is virtually the same as the MySQL version. The classname and subprotocol attributes are set for their appropriate PostgreSQL values. db-port is set to 5432, as this is the default PostgreSQL port.

(use'clojure.java.jdbc)(let[db-host"localhost"db-port5432db-name"a_database"](defdb{:classname"org.postgresql.Driver"; must be in classpath:subprotocol"postgresql":subname(str"//"db-host":"db-port"/"db-name); Any additional keys are passed to the driver; as driver-specific properties.:user"a_user":password"secret"}))

Oracle

[edit |edit source]

The Oracle connector is fairly straightforward to set up. The classname and subprotocol are set to the values for Oracle. The db-port is set to 1521, as this is the default port for Oracle XE.

(use'clojure.java.jdbc)(defdb{:classname"oracle.jdbc.OracleDriver"; must be in classpath:subprotocol"oracle":subname"thin:@172.27.1.7:1521:SID"; If that does not work try:   thin:@172.27.1.7:1521/SID:user"user":password"pwd"})

Virtuoso

[edit |edit source]
(use'clojure.java.jdbc)(defdb{:classname"virtuoso.jdbc.Driver":subprotocol"virtuoso":subname"//localhost:1111":user"dba":password"dba"})

DataSource - Oracle

[edit |edit source]

Here's an example of pooled db connections using the c3p0 library on top of oracle.Make sure c3p0 jars and oracle driver jar is in the classpath.

(nsexample(:useclojure.java.jdbc)(:importjavax.sql.DataSourcecom.mchange.v2.c3p0.DataSources))(defdb{:datasource(DataSources/pooledDataSource(DataSources/unpooledDataSource"jdbc:oracle:thin:USER/PASS@HOST_IP:PORT:SCHEMA"))})

DataSource - PostgreSQL

[edit |edit source]

Example of pooled db connection using PostgreSQL's PGPoolingDataSource class.Note that this is not recommended for production. Use c3p0 or similar instead.

(nsexample(:useclojure.java.jdbc)(:importjavax.sql.DataSourceorg.postgresql.dsPGPoolingDataSource))(let[db-host"localhost"db-name"example"db-user"username"db-pass"notTelling"](defdb{:datasource(doto(newPGPoolingDataSource)(.setServerNamedb-host)(.setDatabaseNamedb-name)(.setUserdb-user)(.setPassworddb-pass)(.setMaxConnections3))}))

DataSource - JNDI

[edit |edit source]

Application servers typically bind data sources into JNDI:

(nsexample(:useclojure.java.jdbc))(defdb{:name"jdbc/TestDS"})

DDL Examples

[edit |edit source]

In the following examples we'll call the database connectiondb. These examples have been tested with MySQL, Postgres would use "SERIAL" rather than "AUTO_INCREMENT".

Creating a Table

[edit |edit source]

We'll start by creating a table calledblogs. This table has three columns.

  • id (Primary Key)
  • title
  • body

Derby

[edit |edit source]

Adding a timestamp column to show off more DDL.

(defncreate-blogs"Create a table to store blog entries"[](clojure.java.jdbc/create-table:blogs[:id:int"PRIMARY KEY""GENERATED ALWAYS AS IDENTITY"][:title"varchar(255)"][:body:clob][:created_at:timestamp"NOT NULL""DEFAULT CURRENT_TIMESTAMP"]))

MySQL

[edit |edit source]
(defncreate-blogs"Create a table to store blog entries"[](clojure.java.jdbc/create-table:blogs[:id:integer"PRIMARY KEY""AUTO_INCREMENT"][:title"varchar(255)"][:body:text]))

This method will create a methodcreate-blogs that creates a table when called. You can invoke the method as follows

(clojure.java.jdbc/with-connectiondb(clojure.java.jdbc/transaction(create-blogs)))

Exercise

[edit |edit source]

Create a method to create a table namedcategories. This table has the following columns

  • id (Primary Key)
  • name

Dropping a Table

[edit |edit source]

Below is a method to drop a table.

(defndrop-blogs"Drop the blogs table"[](try(clojure.java.jdbc/drop-table:blogs)(catchException_)))

To invoke the method call it like this:

(clojure.java.jdbc/with-connectiondb(clojure.java.jdbc/transaction(drop-blogs)))

Exercise

[edit |edit source]

Create a method to drop the table namedcategories.

Dropping All Object Using do-commands

[edit |edit source]
(defndrop-all-objects[](do-commands"drop all objects;"))
(clojure.java.jdbc/with-connectiondb(clojure.java.jdbc/transaction(drop-all-objects)))

Adding Columns

[edit |edit source]

TO DO

Removing Columns

[edit |edit source]

TO DO

DML Examples

[edit |edit source]

Okay, we've got a schema. Bring on the CRUD!

SELECT

[edit |edit source]
(with-connectiondb(with-query-resultsrs["select * from blogs"]; rs will be a sequence of maps,; one for each record in the result set.(dorun(map#(println(:title%))rs))))

To retrieve the CLOB column with Derby, you can convert the returned object to a String,and you must be inside of a transaction to do that.

(defndeclob[clob]"Turn a Derby 10.6.1.0 EmbedClob into a String"(with-open[rdr(java.io.BufferedReader.(.getCharacterStreamclob))](applystr(line-seqrdr))))(with-connectiondb(transaction(with-query-resultsrs["select * from blogs"]; rs will be a sequence of maps,; one for each record in the result set.(doseq[rowrs](println(declob(:bodyrow)))))))

INSERT

[edit |edit source]

This function inserts an entry into the blog table.

(defninsert-blog-entry"Insert data into the table"[title,body](clojure.java.jdbc/insert-values:blogs[:title:body][titlebody]))

And invoking the function

(clojure.java.jdbc/with-connectiondb(clojure.java.jdbc/transaction(insert-blog-entry"Hello World""Life is awesome in the lisp world.")))

UPDATE

[edit |edit source]

Here's an example updating a blog entry.

(defnupdate-blog"This method updates a blog entry"[idattribute-map](clojure.java.jdbc/update-values:blogs["id=?"id]attribute-map))

Let's update the first blog entry.

(with-connectiondb(clojure.java.jdbc/transaction(update-blog1{:title"Awesome Title"})))

DELETE

[edit |edit source]
;; the first line allows us to say sql/with-connection instead of; clojure.java.jdbc/with-connection;(require'[clojure.java.jdbc:assql])(defndelete-blog"Deletes a blog entry given the id"[id](sql/with-connectiondb(sql/delete-rows:blogs["id=?"id])))

Transactions

[edit |edit source]
Clipboard

To do:
Describe transactions

Paging

[edit |edit source]

Oracle and HSQLDB

[edit |edit source]

Please readhttp://www.oracle.com/technetwork/issue-archive/2006/06-sep/o56asktom-086197.html.

The order collection must always contain a unique ordering value.

(defnas-str[&s](applystrs))(defncreate-query-paging[{:keys[tblpropertiesorderpredicatefrommax]:or{max100}}]"Creates a SQL query using paging and ROWNUM()"(str"SELECT * from (select "(clojure.string/join","(map#(str"a."%)properties))", ROWNUM() rnum from (select "(clojure.string/join"/"properties)" from "tbl" order by "(clojure.string/join","order)" ) a "" WHERE ROWNUM() <= "max") WHERE "(if-notpredicate""(strpredicate" and "))" rnum >= "from))(create-query-paging{:tbl"mytable":properties["*"]:order["id","ts"]:from10:max20});"SELECT * from (select a.*, ROWNUM() rnum from (select * from mytable order by id,ts ) a  WHERE ROWNUM() <= 20) WHERE rnum >= 10"
Retrieved from "https://en.wikibooks.org/w/index.php?title=Clojure_Programming/Examples/JDBC_Examples&oldid=3676447"
Category:
Hidden category:

[8]ページ先頭

©2009-2025 Movatter.jp