Permalink
Browse files

Add DB2,Oracle into travis build and add Appveyor build for SQLServer

  • Loading branch information...
smootoo committed Feb 10, 2016
1 parent a0eb1ee commit 6e8b1bb8652668f970bdbbc8c42037c47bab0c5e
View
@@ -0,0 +1,3 @@
[submodule "suegithub"]
path = travis/ZNonPublicDeps
url = https://github.com/smootoo/ZNonPublicDeps.git
View
@@ -1,6 +1,12 @@
sudo: false
language: scala
script: sbt -jvm-opts jvmopts.travis -Dslick.testkit-config=test-dbs/testkit.travis.conf +testAll
sudo: required
before_install:
# TZ needed for Oracle driver!
- export TZ=Asia/Kamchatka
- sh -v ./travis/extractNonPublicDeps
- docker version
- sh -v travis/runcontainer.sh oracle db2
- docker ps
jdk:
- oraclejdk8
notifications:
@@ -9,11 +15,15 @@ notifications:
services:
- mysql
- postgresql
- docker
addons:
apt:
packages:
- graphviz
- python-sphinx
- mysql-server
script:
- sbt -jvm-opts jvmopts.travis -Dslick.testkit-config=test-dbs/testkit.travis.conf clean +testAll
cache:
directories:
- $HOME/.sbt
View
@@ -11,17 +11,21 @@ instead of SQL, thus profiting from the static checking, compile-time safety
and compositionality of Scala. Slick features an extensible query compiler
which can generate code for different backends.
The following database systems are directly supported for type-safe queries:
- Derby/JavaDB
- H2
- HSQLDB/HyperSQL
- MySQL
- PostgreSQL
- SQLite
- Oracle 11g
- IBM DB2 LUW 10
- Microsoft SQL Server 2008
The following database systems are directly supported for type-safe queries.
These are the databases and driver versions that have explicit automated tests.
|Database|JDBC Driver|Build status|
|--------|-----------|-----------:|
|SQLServer 2008, 2012, 2014|[jtds:1.2.8](http://sourceforge.net/projects/jtds/files/jtds/) and [msjdbc:4.2](https://www.microsoft.com/en-gb/download/details.aspx?id=11774)|[![Build status](https://ci.appveyor.com/api/projects/status/mdrfd7o7067c5vcm?svg=true&branch=master)](https://ci.appveyor.com/project/slick/slick)|
|Oracle 11g|[ojdbc7:12.1.0.2](http://www.oracle.com/technetwork/database/features/jdbc/index-091264.html)|[![Build Status](https://travis-ci.org/slick/slick.svg?branch=master)](https://travis-ci.org/slick/slick)|
|DB2 10.5|[db2jcc4:4.19.20](http://www-01.ibm.com/support/docview.wss?uid=swg21363866)|[![Build Status](https://travis-ci.org/slick/slick.svg?branch=master)](https://travis-ci.org/slick/slick)|
|MySQL|mysql-connector-java:5.1.23|[![Build Status](https://travis-ci.org/slick/slick.svg?branch=master)](https://travis-ci.org/slick/slick)|
|PostgreSQL|postgresql:9.1-901.jdbc4|[![Build Status](https://travis-ci.org/slick/slick.svg?branch=master)](https://travis-ci.org/slick/slick)|
|SQLite|sqlite-jdbc:3.8.7|[![Build Status](https://travis-ci.org/slick/slick.svg?branch=master)](https://travis-ci.org/slick/slick)|
|Derby/JavaDB|derby:10.9.1.0|[![Build Status](https://travis-ci.org/slick/slick.svg?branch=master)](https://travis-ci.org/slick/slick)|
|HSQLDB/HyperSQL|hsqldb:2.2.8|[![Build Status](https://travis-ci.org/slick/slick.svg?branch=master)](https://travis-ci.org/slick/slick)|
|H2|com.h2database.h2:1.4.187|[![Build Status](https://travis-ci.org/slick/slick.svg?branch=master)](https://travis-ci.org/slick/slick)|
Accessing other database systems is possible, with a reduced feature set.
View
@@ -0,0 +1,60 @@
install:
- git submodule update --init --recursive
- ps: |
Add-Type -AssemblyName System.IO.Compression.FileSystem
if (!(Test-Path -Path "C:\sbt" )) {
(new-object System.Net.WebClient).DownloadFile(
'https://dl.bintray.com/sbt/native-packages/sbt/0.13.9/sbt-0.13.9.zip',
'C:\sbt-bin.zip'
)
[System.IO.Compression.ZipFile]::ExtractToDirectory("C:\sbt-bin.zip", "C:\sbt")
}
- cmd: SET JDK_HOME=C:\Program Files\Java\jdk1.8.0
- cmd: SET JAVA_HOME=C:\Program Files\Java\jdk1.8.0
- cmd: SET PATH=C:\sbt\sbt\bin;%JDK_HOME%\bin;%PATH%
- cmd: SET SBT_OPTS=-Xmx4g -Xss2m -Dslick.testkit-config=test-dbs/testkit-appveyor.conf
# Start up sqlservers: 2008 on port 1433, 2012 on 1533, 2014 on 1633. Enable tcp connections
- ps: |
[reflection.assembly]::LoadWithPartialName("Microsoft.SqlServer.Smo") | Out-Null;
[reflection.assembly]::LoadWithPartialName("Microsoft.SqlServer.SqlWmiManagement") | Out-Null;
$port = 1433
foreach($instancename in @('SQL2008R2SP2', 'SQL2012SP1', 'SQL2014'))
{
$wmi = New-Object('Microsoft.SqlServer.Management.Smo.Wmi.ManagedComputer');
$tcp = $wmi.GetSmoObject("ManagedComputer[@Name='${env:computername}']/ServerInstance[@Name='${instancename}']/ServerProtocol[@Name='Tcp']");
$tcp.IsEnabled = $true;
foreach ($ipAddress in $tcp.IPAddresses)
{
$ipAddress.IPAddressProperties["TcpDynamicPorts"].Value = ""
$ipAddress.IPAddressProperties["TcpPort"].Value = "${port}"
}
$tcp.Alter();
Start-Service -Name "MSSQL`$$instancename";
$wmi = New-Object('Microsoft.SqlServer.Management.Smo.Wmi.ManagedComputer');
$ipall = $wmi.GetSmoObject("ManagedComputer[@Name='${env:computername}']/ServerInstance[@Name='${instancename}']/ServerProtocol[@Name='Tcp']/IPAddress[@Name='IPAll']");
$config = @{
instanceName = $instancename;
config = @{
server = "localhost";
userName = "sa";
password = "Password12!";
options = @{
port = ${port};
database = "master";
cryptoCredentialsDetails = @{
ciphers = "RC4-MD5"
}
}
}
} | ConvertTo-Json -Depth 3;
Write-Host "${config}"
$port += 100
}
- bash -v ./travis/extractNonPublicDeps
build_script:
- sbt clean compile test:compile
test_script:
- sbt testkit/test:test
cache:
- C:\sbt\
- C:\Users\appveyor\.ivy2
@@ -13,8 +13,10 @@ trait SlickOsgiHelper {
private def makeBundle(file: File): exam.Option =
bundle(file.toURI.toASCIIString)
private def allBundleFiles: Array[File] =
Option(sys.props("slick.osgi.bundlepath")).getOrElse("").split(":").map(new File(_))
private def allBundleFiles: Array[File] = {
val paths = Option(sys.props("slick.osgi.bundlepath")).getOrElse("")
paths.split("@").map(new File(_))
}
def standardOptions: Array[exam.Option] =
allBundleFiles.map(makeBundle) ++ Array[exam.Option](junitBundles())
View
@@ -282,7 +282,7 @@ object SlickBuild extends Build {
).configs(DocTest).settings(inConfig(DocTest)(Defaults.testSettings): _*).settings(
unmanagedSourceDirectories in DocTest += (baseDirectory in slickProject).value / "src/sphinx/code",
unmanagedResourceDirectories in DocTest += (baseDirectory in slickProject).value / "src/sphinx/resources"
) dependsOn(slickProject, slickCodegenProject % "compile->compile", slickHikariCPProject % "test->compile")
) dependsOn(slickProject, slickCodegenProject % "compile->compile", slickHikariCPProject)
lazy val slickCodegenProject = Project(id = "codegen", base = file("slick-codegen"),
settings = Defaults.coreDefaultSettings ++ sdlcSettings ++ sharedSettings ++ extTarget("codegen") ++ commonSdlcSettings ++ Seq(
@@ -339,7 +339,8 @@ object SlickBuild extends Build {
fork in Test := true,
testOptions += Tests.Argument(TestFrameworks.JUnit, "-q", "-v", "-s", "-a"),
javaOptions in Test ++= Seq(
"-Dslick.osgi.bundlepath=" + osgiBundleFiles.value.map(_.getCanonicalPath).mkString(":"),
// Use '@' as a seperator that shouldn't appear in any filepaths or names
"-Dslick.osgi.bundlepath=" + osgiBundleFiles.value.map(_.getCanonicalPath).mkString("@"),
"-Dorg.ops4j.pax.logging.DefaultServiceLog.level=WARN"
),
osgiBundleFiles := Seq((OsgiKeys.bundle in slickProject).value),
@@ -26,8 +26,6 @@ object HikariCPJdbcDataSource extends JdbcDataSourceFactory {
import com.zaxxer.hikari._
def forConfig(c: Config, driver: Driver, name: String, classLoader: ClassLoader): HikariCPJdbcDataSource = {
if(driver ne null)
throw new SlickException("An explicit Driver object is not supported by HikariCPJdbcDataSource")
val hconf = new HikariConfig()
// Connection settings
@@ -45,7 +45,7 @@ class JdbcMetaTest extends AsyncTest[JdbcTestDB] {
DBIO.sequence(ps.map(_.getProcedureColumns()))
}.named("Procedures from DatabaseMetaData"),
MTable.getTables(None, None, None, None).flatMap { ts =>
tdb.profile.defaultTables.flatMap { ts =>
DBIO.sequence(ts.filter(t => Set("users", "orders") contains t.name.name).map { t =>
DBIO.seq(
t.getColumns.flatMap { cs =>
@@ -68,7 +68,7 @@ class JdbcMetaTest extends AsyncTest[JdbcTestDB] {
ifCap(tcap.jdbcMetaGetClientInfoProperties)(MClientInfoProperty.getClientInfoProperties)
.named("Client Info Properties from DatabaseMetaData"),
MTable.getTables(None, None, None, None).map(_.should(ts =>
tdb.profile.defaultTables.map(_.should(ts =>
Set("orders_xx", "users_xx") subsetOf ts.map(_.name.name).toSet
)).named("Tables before deleting")
@@ -11,6 +11,8 @@ import slick.jdbc._
import slick.jdbc.GetResult._
import slick.jdbc.meta.MTable
import org.junit.Assert
import slick.util.ConfigExtensionMethods._
import scala.concurrent.duration.Duration
import scala.concurrent.{Await, ExecutionContext}
@@ -182,24 +184,19 @@ object StandardTestDBs {
val profile = SQLServerProfile
import profile.api.actionBasedSQLInterpolation
val defaultSchema = config.getString("defaultSchema")
// sqlserver has valid "select for update" syntax, but in testing on Appveyor, the test hangs due to lock escalation
// so exclude from explicit ForUpdate testing
override def capabilities = super.capabilities - TestDB.capabilities.selectForUpdateRowLocking
val defaultSchema = config.getStringOpt("defaultSchema")
override def localTables(implicit ec: ExecutionContext): DBIO[Vector[String]] =
ResultSetAction[(String,String,String, String)](_.conn.getMetaData().getTables(testDB, defaultSchema, null, null)).map { ts =>
ts.map(_._3).sorted
}
override def localTables(implicit ec: ExecutionContext): DBIO[Vector[String]] = {
MTable.getTables(None, defaultSchema, None, Some(Seq("TABLE"))).map(_.map(_.name.name).sorted)
}
override def dropUserArtifacts(implicit session: profile.Backend#Session) = blockingRunOnSession { implicit ec =>
for {
constraints <- sql"""select constraint_name, table_name from information_schema.table_constraints where constraint_type = 'FOREIGN KEY'""".as[(String, String)]
constraintStatements = constraints.collect { case (c, t) if !c.startsWith("SQL") =>
sqlu"alter table #${profile.quoteIdentifier(t)} drop constraint #${profile.quoteIdentifier(c)}"
}
_ <- DBIO.sequence(constraintStatements)
tables <- localTables
_ <- DBIO.sequence(tables.map(t => sqlu"exec sp_MSdropconstraints #$t"))
tableStatements = tables.map(t => sqlu"drop table #${profile.quoteIdentifier(t)}")
_ <- DBIO.sequence(tableStatements)
} yield ()
@@ -209,9 +206,21 @@ object StandardTestDBs {
lazy val SQLServerJTDS = new SQLServerDB("sqlserver-jtds") {
override def capabilities = super.capabilities - TestDB.capabilities.plainSql
}
lazy val SQLServer2012JTDS = new SQLServerDB("sqlserver2012-jtds") {
override def capabilities = super.capabilities - TestDB.capabilities.plainSql
}
lazy val SQLServer2014JTDS = new SQLServerDB("sqlserver2014-jtds") {
override def capabilities = super.capabilities - TestDB.capabilities.plainSql
}
lazy val SQLServerSQLJDBC = new SQLServerDB("sqlserver-sqljdbc") {
override def capabilities = profile.capabilities - JdbcCapabilities.createModel
}
lazy val SQLServer2012SQLJDBC = new SQLServerDB("sqlserver2012-sqljdbc") {
override def capabilities = profile.capabilities - JdbcCapabilities.createModel
}
lazy val SQLServer2014SQLJDBC = new SQLServerDB("sqlserver2014-sqljdbc") {
override def capabilities = profile.capabilities - JdbcCapabilities.createModel
}
lazy val Oracle = new ExternalJdbcTestDB("oracle") {
val profile = OracleProfile
@@ -221,13 +230,26 @@ object StandardTestDBs {
override def capabilities =
super.capabilities - TestDB.capabilities.jdbcMetaGetIndexInfo - TestDB.capabilities.transactionIsolation
/* Only drop and recreate the user. This is much faster than dropping
* the tablespace. */
override def dropUserArtifacts(implicit session: profile.Backend#Session) = {
session.close()
val a = DBIO.sequence(Seq(drop(0), create(1), create(2)).map(s => sqlu"#$s"))
await(databaseFor("adminConn").run(a))
override def localTables(implicit ec: ExecutionContext): DBIO[Vector[String]] = {
val tableNames = profile.defaultTables.map(_.map(_.name.name)).map(_.toVector)
tableNames
}
override def localSequences(implicit ec: ExecutionContext): DBIO[Vector[String]] = {
// user_sequences much quicker than going to metadata if you don't know the schema they are going to be in
sql"select sequence_Name from user_sequences".as[String]
}
override def dropUserArtifacts(implicit session: profile.Backend#Session) =
blockingRunOnSession { implicit ec =>
for {
tables <- localTables
sequences <- localSequences
_ <- DBIO.seq(tables.map(t => sqlu"drop table #${profile.quoteIdentifier(t)} cascade constraints") ++
sequences.map(s => sqlu"drop sequence #${profile.quoteIdentifier(s)}"): _*)
} yield ()
}
}
}
@@ -1,5 +1,7 @@
package com.typesafe.slick.testkit.util
import java.lang.reflect.Method
import com.typesafe.config.Config
import org.junit.Assert
@@ -265,7 +267,21 @@ object ExternalTestDB {
// A cache for custom drivers to avoid excessive reloading and memory leaks
private[this] val driverCache = new mutable.HashMap[(String, String), Driver]()
def getCustomDriver(url: String, driverClass: String): Driver = synchronized {
def getCustomDriver(url: String, driverClass: String) = synchronized {
val sysloader = java.lang.ClassLoader.getSystemClassLoader
val sysclass = classOf[URLClassLoader]
// Add the supplied jar onto the system classpath
// Doing this allows Hikari to initialise the driver, if needed
try {
val method = sysclass.getDeclaredMethod("addURL", classOf[URL])
method.setAccessible(true)
method.invoke(sysloader, new URL(url))
} catch {
case t: Throwable =>
t.printStackTrace()
throw new IOException(s"Error, could not add URL $url to system classloader");
}
driverCache.getOrElseUpdate((url, driverClass),
new URLClassLoader(Array(new URL(url)), getClass.getClassLoader).loadClass(driverClass).newInstance.asInstanceOf[Driver]
)
@@ -48,5 +48,17 @@ class OracleTest extends ProfileTest(StandardTestDBs.Oracle)
@RunWith(classOf[Testkit])
class SQLServerJTDSTest extends ProfileTest(StandardTestDBs.SQLServerJTDS)
@RunWith(classOf[Testkit])
class SQLServer2012JTDSTest extends ProfileTest(StandardTestDBs.SQLServer2012JTDS)
@RunWith(classOf[Testkit])
class SQLServer2014JTDSTest extends ProfileTest(StandardTestDBs.SQLServer2014JTDS)
@RunWith(classOf[Testkit])
class SQLServerSQLJDBCTest extends ProfileTest(StandardTestDBs.SQLServerSQLJDBC)
@RunWith(classOf[Testkit])
class SQLServer2012SQLJDBCTest extends ProfileTest(StandardTestDBs.SQLServer2012SQLJDBC)
@RunWith(classOf[Testkit])
class SQLServer2014SQLJDBCTest extends ProfileTest(StandardTestDBs.SQLServer2014SQLJDBC)
@@ -96,8 +96,7 @@ trait OracleProfile extends JdbcProfile {
override def defaultTables(implicit ec: ExecutionContext): DBIO[Seq[MTable]] = {
for {
user <- SimpleJdbcAction(_.session.metaData.getUserName)
tables <- SQLActionBuilder(Seq("select TABLE_NAME from all_tables where OWNER = ?"), implicitly[SetParameter[String]].applied(user)).as[String]
mtables <- MTable.getTables(None, None, None, Some(Seq("TABLE"))).map(_.filter(t => tables contains t.name.name)) // FIXME: this should check schema and maybe more
mtables <- MTable.getTables(None, Some(user), None, Some(Seq("TABLE")))
} yield mtables
}
@@ -107,8 +107,13 @@ trait SQLServerProfile extends JdbcProfile {
override def createModelBuilder(tables: Seq[MTable], ignoreInvalidDefaults: Boolean)(implicit ec: ExecutionContext): JdbcModelBuilder =
new ModelBuilder(tables, ignoreInvalidDefaults)
override def defaultTables(implicit ec: ExecutionContext): DBIO[Seq[MTable]] =
MTable.getTables(None, None, None, Some(Seq("TABLE")))
override def defaultTables(implicit ec: ExecutionContext): DBIO[Seq[MTable]] = {
import api._
for {
schema <- Functions.user.result
mtables <- MTable.getTables(None, Some(schema), None, Some(Seq("TABLE")))
} yield mtables
}
override def defaultSqlTypeName(tmd: JdbcType[_], sym: Option[FieldSymbol]): String = tmd.sqlType match {
case java.sql.Types.VARCHAR =>
Oops, something went wrong.

0 comments on commit 6e8b1bb

Please sign in to comment.