diff --git a/build.gradle b/build.gradle index 090d9b6336..acc2ea2537 100644 --- a/build.gradle +++ b/build.gradle @@ -1,77 +1,28 @@ -ext.githubProjectName = 'RxJava' - -apply from: file('gradle/convention.gradle') -apply from: file('gradle/maven.gradle') -//apply from: file('gradle/check.gradle') -apply from: file('gradle/license.gradle') -apply from: file('gradle/release.gradle') - buildscript { repositories { mavenLocal() mavenCentral() // maven { url 'http://jcenter.bintray.com/' } + repositories { maven { url 'http://dl.bintray.com/content/netflixoss/external-gradle-plugins/' } } // For gradle-release + } + dependencies { + classpath 'nl.javadude.gradle.plugins:license-gradle-plugin:0.6.1' + classpath 'com.mapvine:gradle-cobertura-plugin:0.1' + classpath 'gradle-release:gradle-release:1.1.5' + classpath 'org.ajoberstar:gradle-git:0.5.0' } - apply from: file('gradle/buildscript.gradle'), to: buildscript } +ext.githubProjectName = 'RxJava' + allprojects { + group = "com.netflix.rxjava" apply plugin: 'eclipse' apply plugin: 'idea' - repositories { - mavenLocal() - mavenCentral() // maven { url: 'http://jcenter.bintray.com/' } - } } -subprojects { - apply plugin: 'java' - group = "com.netflix.rxjava" - - // make 'examples' use the same classpath - configurations { - examplesCompile.extendsFrom compile - examplesRuntime.extendsFrom runtime - perfCompile.extendsFrom compile - perfRuntime.extendsFrom runtime - } - - - tasks.withType(Javadoc).each { - it.classpath = sourceSets.main.compileClasspath - } - - sourceSets { - //include /src/examples folder - examples - //include /src/perf folder - // perf //-> Not working so commented out - } - - tasks.build { - //include 'examples' in build task - dependsOn(examplesClasses) - //include 'perf' in build task - // dependsOn(perfClasses) //-> Not working so commented out - } - - eclipse { - classpath { - // include 'provided' dependencies on the classpath - plusConfigurations += configurations.provided - - downloadSources = true - downloadJavadoc = true - } - } - - idea { - module { - // include 'provided' dependencies on the classpath - scopes.PROVIDED.plus += configurations.provided - } - } -} - -project(':rxjava-core') { - sourceSets.test.java.srcDir 'src/test/java' -} +apply from: file('gradle/convention.gradle') +apply from: file('gradle/maven.gradle') +//apply from: file('gradle/check.gradle') +apply from: file('gradle/license.gradle') +apply from: file('gradle/release.gradle') +apply from: file('gradle/github-pages.gradle') diff --git a/gradle/buildscript.gradle b/gradle/buildscript.gradle deleted file mode 100644 index 0b6da7ce84..0000000000 --- a/gradle/buildscript.gradle +++ /dev/null @@ -1,11 +0,0 @@ -// Executed in context of buildscript -repositories { - // Repo in addition to maven central - repositories { maven { url 'http://dl.bintray.com/content/netflixoss/external-gradle-plugins/' } } // For gradle-release -} -dependencies { - classpath 'nl.javadude.gradle.plugins:license-gradle-plugin:0.6.1' - classpath 'com.mapvine:gradle-cobertura-plugin:0.1' - classpath 'gradle-release:gradle-release:1.1.5' - classpath 'org.ajoberstar:gradle-git:0.5.0' -} diff --git a/gradle/check.gradle b/gradle/check.gradle index a3e4b4e7f5..1b06d64ce9 100644 --- a/gradle/check.gradle +++ b/gradle/check.gradle @@ -1,26 +1,23 @@ subprojects { -// Checkstyle -apply plugin: 'checkstyle' -checkstyle { - ignoreFailures = true - configFile = rootProject.file('codequality/checkstyle.xml') -} + apply plugin: 'checkstyle' + checkstyle { + ignoreFailures = true + configFile = rootProject.file('codequality/checkstyle.xml') + } -// FindBugs -apply plugin: 'findbugs' -findbugs { - ignoreFailures = true -} + apply plugin: 'findbugs' + findbugs { + ignoreFailures = true + } -// PMD -apply plugin: 'pmd' -//tasks.withType(Pmd) { reports.html.enabled true } + apply plugin: 'pmd' + //tasks.withType(Pmd) { reports.html.enabled true } -apply plugin: 'cobertura' -cobertura { - sourceDirs = sourceSets.main.java.srcDirs - format = 'html' - includes = ['**/*.java', '**/*.groovy'] - excludes = [] -} + apply plugin: 'cobertura' + cobertura { + sourceDirs = sourceSets.main.java.srcDirs + format = 'html' + includes = ['**/*.java', '**/*.groovy'] + excludes = [] + } } diff --git a/gradle/convention.gradle b/gradle/convention.gradle index f581db7cc5..33afde279b 100644 --- a/gradle/convention.gradle +++ b/gradle/convention.gradle @@ -1,31 +1,62 @@ -// GRADLE-2087 workaround, perform after java plugin -status = project.hasProperty('preferredStatus')?project.preferredStatus:(version.contains('SNAPSHOT')?'snapshot':'release') +subprojects { + if (!subprojects.empty) { // is a container + return + } + + description = name.capitalize().replaceAll("-\\w") { " " + (it.toUpperCase() - "-") }.replaceAll("Rxjava", "RxJava") + + apply plugin: 'java' + apply plugin: 'osgi' + + repositories { + mavenLocal() + mavenCentral() // maven { url: 'http://jcenter.bintray.com/' } + } + + dependencies { + if (project.path != ":rxjava-core") { + compile project(':rxjava-core') + } -subprojects { project -> - apply plugin: 'java' // Plugin as major conventions + testCompile 'junit:junit-dep:4.10' + testCompile 'org.mockito:mockito-core:1.8.5' + } - sourceCompatibility = 1.6 + sourceCompatibility = JavaVersion.VERSION_1_6 + targetCompatibility = JavaVersion.VERSION_1_6 - // Restore status after Java plugin - status = rootProject.status + status = project.hasProperty('preferredStatus') ? project.preferredStatus : (version.contains('SNAPSHOT') ? 'snapshot' : 'release') - task sourcesJar(type: Jar, dependsOn:classes) { + task sourcesJar(type: Jar, dependsOn: classes) { from sourceSets.main.allSource classifier 'sources' extension 'jar' } - task javadocJar(type: Jar, dependsOn:javadoc) { + task javadocJar(type: Jar, dependsOn: javadoc) { from javadoc.destinationDir classifier 'javadoc' extension 'jar' } - configurations.create('sources') - configurations.create('javadoc') - configurations.archives { - extendsFrom configurations.sources - extendsFrom configurations.javadoc + jar { + manifest { + name = project.name + instruction 'Bundle-Vendor', 'Netflix' + instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' + if (project.path != ":rxjava-core") { + instruction 'Fragment-Host', 'com.netflix.rxjava.core' + } + } + } + + configurations { + create("sources") + create("javadoc") + archives { + extendsFrom configurations.sources + extendsFrom configurations.javadoc + } } // When outputing to an Ivy repo, we want to use the proper type field @@ -56,46 +87,65 @@ subprojects { project -> } } - project.sourceSets { - main.compileClasspath += project.configurations.provided - main.runtimeClasspath -= project.configurations.provided - test.compileClasspath += project.configurations.provided - test.runtimeClasspath += project.configurations.provided + sourceSets { + main { + compileClasspath += configurations.provided + runtimeClasspath -= configurations.provided + } + test { + compileClasspath += configurations.provided + runtimeClasspath += configurations.provided + } + examples { + compileClasspath += configurations.provided + main.output + } + perf { + compileClasspath += configurations.provided + main.output + } } -} - -apply plugin: 'github-pages' // Used to create publishGhPages task - -def docTasks = [:] -[Javadoc,ScalaDoc,Groovydoc].each{ Class docClass -> - def allSources = allprojects.tasks*.withType(docClass).flatten()*.source - if (allSources) { - def shortName = docClass.simpleName.toLowerCase() - def docTask = task "aggregate${shortName.capitalize()}"(type: docClass, description: "Aggregate subproject ${shortName}s") { - source = allSources - destinationDir = file("${project.buildDir}/docs/${shortName}") - doFirst { - def classpaths = allprojects.findAll { it.plugins.hasPlugin(JavaPlugin) }.collect { it.sourceSets.main.compileClasspath } - classpath = files(classpaths) - } + + configurations { + examplesCompile.extendsFrom testCompile + examplesRuntime.extendsFrom testRuntime + perfCompile.extendsFrom testCompile + perfRuntime.extendsFrom testRuntime + } + + javadoc { + options { + doclet = "org.benjchristensen.doclet.DocletExclude" + docletpath = [rootProject.file('gradle/doclet-exclude.jar')] + stylesheetFile = rootProject.file('gradle/javadocStyleSheet.css') + windowTitle = "$project.description Javadoc $project.version" + addStringOption('top').value = '

' + project.description + '

'.toString() } - docTasks[shortName] = docTask - processGhPages.dependsOn(docTask) + classpath += configurations.provided + } + + build { + dependsOn examplesClasses } -} - -githubPages { - repoUri = "git@github.com:Netflix/${rootProject.githubProjectName}.git" - pages { - docTasks.each { shortName, docTask -> - from(docTask.outputs.files) { - into "docs/${shortName}" + + // Individual projects will apply specific language plugins which add to source sets… + // do this late so we get those additions + afterEvaluate { + idea { + module { + [sourceSets.examples, sourceSets.perf].each { + [it.allSource.srcDirs, it.resources.srcDirs].each { + testSourceDirs += it + } + } + scopes.PROVIDED.plus += configurations.provided + } + } + + eclipse { + classpath { + plusConfigurations += configurations.provided + downloadJavadoc = true } } } -} -// Generate wrapper, which is distributed as part of source to alleviate the need of installing gradle -task createWrapper(type: Wrapper) { - gradleVersion = '1.6' -} +} \ No newline at end of file diff --git a/gradle/github-pages.gradle b/gradle/github-pages.gradle new file mode 100644 index 0000000000..4b1831c60e --- /dev/null +++ b/gradle/github-pages.gradle @@ -0,0 +1,32 @@ +apply plugin: 'github-pages' // Used to create publishGhPages task + +def docTasks = [:] +[Javadoc, ScalaDoc, Groovydoc].each { Class docClass -> + def allSources = allprojects.tasks*.withType(docClass).flatten()*.source + if (allSources) { + def shortName = docClass.simpleName.toLowerCase() + def docTask = task "aggregate${shortName.capitalize()}"(type: docClass, description: "Aggregate subproject ${shortName}s") { + source = allSources + destinationDir = file("${project.buildDir}/docs/${shortName}") + doFirst { + def classpaths = allprojects.findAll { it.plugins.hasPlugin(JavaPlugin) }.collect { + it.sourceSets.main.compileClasspath + } + classpath = files(classpaths) + } + } + docTasks[shortName] = docTask + processGhPages.dependsOn(docTask) + } +} + +githubPages { + repoUri = "git@github.com:Netflix/${rootProject.githubProjectName}.git" + pages { + docTasks.each { shortName, docTask -> + from(docTask.outputs.files) { + into "docs/${shortName}" + } + } + } +} \ No newline at end of file diff --git a/gradle/license.gradle b/gradle/license.gradle index abd2e2c0e1..71d2ce373d 100644 --- a/gradle/license.gradle +++ b/gradle/license.gradle @@ -1,10 +1,8 @@ -// Dependency for plugin was set in buildscript.gradle - subprojects { -apply plugin: 'license' //nl.javadude.gradle.plugins.license.LicensePlugin -license { - header rootProject.file('codequality/HEADER') - ext.year = Calendar.getInstance().get(Calendar.YEAR) - skipExistingHeaders true -} + apply plugin: 'license' //nl.javadude.gradle.plugins.license.LicensePlugin + license { + header rootProject.file('codequality/HEADER') + ext.year = Calendar.getInstance().get(Calendar.YEAR) + skipExistingHeaders true + } } diff --git a/gradle/maven.gradle b/gradle/maven.gradle index 817846d77f..827b3731a7 100644 --- a/gradle/maven.gradle +++ b/gradle/maven.gradle @@ -1,4 +1,3 @@ -// Maven side of things subprojects { apply plugin: 'maven' // Java plugin has to have been already applied for the conf2scope mappings to work apply plugin: 'signing' @@ -8,63 +7,63 @@ subprojects { sign configurations.archives } -/** - * Publishing to Maven Central example provided from http://jedicoder.blogspot.com/2011/11/automated-gradle-project-deployment-to.html - * artifactory will execute uploadArchives to force generation of ivy.xml, and we don't want that to trigger an upload to maven - * central, so using custom upload task. - */ -task uploadMavenCentral(type:Upload, dependsOn: signArchives) { - configuration = configurations.archives - onlyIf { ['release', 'snapshot'].contains(project.status) } + /** + * Publishing to Maven Central example provided from http://jedicoder.blogspot.com/2011/11/automated-gradle-project-deployment-to.html + * artifactory will execute uploadArchives to force generation of ivy.xml, and we don't want that to trigger an upload to maven + * central, so using custom upload task. + */ + task uploadMavenCentral(type: Upload, dependsOn: signArchives) { + configuration = configurations.archives + onlyIf { ['release', 'snapshot'].contains(project.status) } repositories.mavenDeployer { beforeDeployment { signing.signPom(it) } - // To test deployment locally, use the following instead of oss.sonatype.org - //repository(url: "file://localhost/${rootProject.rootDir}/repo") + // To test deployment locally, use the following instead of oss.sonatype.org + //repository(url: "file://localhost/${rootProject.rootDir}/repo") - def sonatypeUsername = rootProject.hasProperty('sonatypeUsername')?rootProject.sonatypeUsername:'' - def sonatypePassword = rootProject.hasProperty('sonatypePassword')?rootProject.sonatypePassword:'' + def sonatypeUsername = rootProject.hasProperty('sonatypeUsername') ? rootProject.sonatypeUsername : '' + def sonatypePassword = rootProject.hasProperty('sonatypePassword') ? rootProject.sonatypePassword : '' - repository(url: 'https://oss.sonatype.org/service/local/staging/deploy/maven2') { - authentication(userName: sonatypeUsername, password: sonatypePassword) - } + repository(url: 'https://oss.sonatype.org/service/local/staging/deploy/maven2') { + authentication(userName: sonatypeUsername, password: sonatypePassword) + } - snapshotRepository(url: 'https://oss.sonatype.org/content/repositories/snapshots/') { - authentication(userName: sonatypeUsername, password: sonatypePassword) - } + snapshotRepository(url: 'https://oss.sonatype.org/content/repositories/snapshots/') { + authentication(userName: sonatypeUsername, password: sonatypePassword) + } - // Prevent datastamp from being appending to artifacts during deployment - uniqueVersion = false + // Prevent datastamp from being appending to artifacts during deployment + uniqueVersion = false - // Closure to configure all the POM with extra info, common to all projects - pom.project { - name "${project.name}" - description "${project.name} developed by Netflix" - developers { - developer { - id 'netflixgithub' - name 'Netflix Open Source Development' - email 'talent@netflix.com' - } - } - licenses { - license { - name 'The Apache Software License, Version 2.0' - url 'http://www.apache.org/licenses/LICENSE-2.0.txt' - distribution 'repo' - } + // Closure to configure all the POM with extra info, common to all projects + pom.project { + name "${project.name}" + description "${project.name} developed by Netflix" + developers { + developer { + id 'netflixgithub' + name 'Netflix Open Source Development' + email 'talent@netflix.com' } - url "https://github.com/Netflix/$%7BrootProject.githubProjectName%7D" - scm { - connection "scm:git:git@github.com:Netflix/${rootProject.githubProjectName}.git" - url "scm:git:git@github.com:Netflix/${rootProject.githubProjectName}.git" - developerConnection "scm:git:git@github.com:Netflix/${rootProject.githubProjectName}.git" - } - issueManagement { - system 'github' - url "https://github.com/Netflix/$%7BrootProject.githubProjectName%7D/issues" + } + licenses { + license { + name 'The Apache Software License, Version 2.0' + url 'http://www.apache.org/licenses/LICENSE-2.0.txt' + distribution 'repo' } } + url "https://github.com/Netflix/$%7BrootProject.githubProjectName%7D" + scm { + connection "scm:git:git@github.com:Netflix/${rootProject.githubProjectName}.git" + url "scm:git:git@github.com:Netflix/${rootProject.githubProjectName}.git" + developerConnection "scm:git:git@github.com:Netflix/${rootProject.githubProjectName}.git" + } + issueManagement { + system 'github' + url "https://github.com/Netflix/$%7BrootProject.githubProjectName%7D/issues" + } } } + } } diff --git a/language-adaptors/rxjava-clojure/build.gradle b/language-adaptors/rxjava-clojure/build.gradle index 6e59b61305..3fa9b95e08 100644 --- a/language-adaptors/rxjava-clojure/build.gradle +++ b/language-adaptors/rxjava-clojure/build.gradle @@ -1,52 +1,24 @@ +buildscript { + repositories { maven { url "http://clojars.org/repo" } } + dependencies { classpath "clojuresque:clojuresque:1.5.8" } +} + apply plugin: 'clojure' -apply plugin: 'osgi' -dependencies { - compile project(':rxjava-core') +repositories { + clojarsRepo() +} - // clojure +dependencies { compile 'org.clojure:clojure:1.4.+' - - // this should be 'compile' for the 'examples' module ... can't figure that out right now so making 'provided' - provided 'clj-http:clj-http:0.6.4' // https://clojars.org/clj-http + examplesCompile 'clj-http:clj-http:0.6.4' // https://clojars.org/clj-http } -tasks.compileExamplesClojure.classpath = files(tasks.compileClojure.destinationDir) + tasks.compileClojure.classpath - -/* - * Clojure - */ aotCompile = true warnOnReflection = false -buildscript { - repositories { maven { url "http://clojars.org/repo" } } - dependencies { classpath "clojuresque:clojuresque:1.5.8" } -} - -repositories { - clojarsRepo() -} - -/* - * Add Counterclockwise and include 'provided' dependencies - */ eclipse { project { natures "ccw.nature" } } - -tasks.clojureTest { - classpath = classpath + configurations.provided -} - -jar { - manifest { - name = 'rxjava-clojure' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - instruction 'Fragment-Host', 'com.netflix.rxjava.core' - } -} diff --git a/language-adaptors/rxjava-groovy/build.gradle b/language-adaptors/rxjava-groovy/build.gradle index c26a383a34..24e45c1604 100644 --- a/language-adaptors/rxjava-groovy/build.gradle +++ b/language-adaptors/rxjava-groovy/build.gradle @@ -1,19 +1,5 @@ apply plugin: 'groovy' -apply plugin: 'osgi' dependencies { - compile project(':rxjava-core') compile 'org.codehaus.groovy:groovy-all:2.+' - provided 'junit:junit-dep:4.10' - provided 'org.mockito:mockito-core:1.8.5' } - -jar { - manifest { - name = 'rxjava-groovy' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - instruction 'Fragment-Host', 'com.netflix.rxjava.core' - } -} \ No newline at end of file diff --git a/language-adaptors/rxjava-jruby/build.gradle b/language-adaptors/rxjava-jruby/build.gradle index 0369d6e36e..2f4a9f1c6a 100644 --- a/language-adaptors/rxjava-jruby/build.gradle +++ b/language-adaptors/rxjava-jruby/build.gradle @@ -1,5 +1,3 @@ -apply plugin: 'osgi' - repositories { maven { url 'http://deux.gemjars.org/' @@ -20,10 +18,7 @@ sourceSets { } dependencies { - compile project(':rxjava-core') compile 'org.jruby:jruby:1.7+' - provided 'junit:junit-dep:4.10' - provided 'org.mockito:mockito-core:1.8.5' rspec 'org.jruby:jruby-complete:1.7.4' rspec 'org.rubygems:rspec:2.14.1' } @@ -36,14 +31,4 @@ task(rspec, type: JavaExec) { } tasks.build.dependsOn << 'rspec' -*/ - -jar { - manifest { - name = 'rxjava-jruby' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - instruction 'Fragment-Host', 'com.netflix.rxjava.core' - } -} +*/ \ No newline at end of file diff --git a/language-adaptors/rxjava-kotlin/build.gradle b/language-adaptors/rxjava-kotlin/build.gradle index aa44049d05..08433b7947 100644 --- a/language-adaptors/rxjava-kotlin/build.gradle +++ b/language-adaptors/rxjava-kotlin/build.gradle @@ -9,21 +9,7 @@ buildscript { } apply plugin: 'kotlin' -apply plugin: 'osgi' dependencies { - compile project(':rxjava-core') compile 'org.jetbrains.kotlin:kotlin-stdlib:0.6.1673' - provided 'junit:junit-dep:4.10' - provided 'org.mockito:mockito-core:1.8.5' -} - -jar { - manifest { - name = 'rxjava-kotlin' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - instruction 'Fragment-Host', 'com.netflix.rxjava.core' - } } \ No newline at end of file diff --git a/language-adaptors/rxjava-scala/build.gradle b/language-adaptors/rxjava-scala/build.gradle index 8083feaf37..6f2bd507fe 100644 --- a/language-adaptors/rxjava-scala/build.gradle +++ b/language-adaptors/rxjava-scala/build.gradle @@ -1,5 +1,4 @@ apply plugin: 'scala' -apply plugin: 'osgi' tasks.withType(ScalaCompile) { scalaCompileOptions.fork = true @@ -12,50 +11,9 @@ tasks.withType(ScalaCompile) { } } -sourceSets { - main { - scala { - srcDir 'src/main/scala' - } - } - test { - scala { - srcDir 'src/main/scala' - srcDir 'src/test/scala' - srcDir 'src/examples/scala' - //srcDir 'src/examples/java' - } - java.srcDirs = [] - } - examples { - // It seems that in Gradle, the dependency "compileScala depends on compileJava" is hardcoded, - // or at least not meant to be removed. - // However, compileScala also runs javac at the very end, so we just add the Java sources to - // the scala source set: - scala { - srcDir 'src/examples/scala' - //srcDir 'src/examples/java' - } - java.srcDirs = [] - } -} - dependencies { compile 'org.scala-lang:scala-library:2.10.+' - - compile project(':rxjava-core') - - provided 'junit:junit-dep:4.10' - provided 'org.mockito:mockito-core:1.8.5' - provided 'org.scalatest:scalatest_2.10:1.9.1' -} - -tasks.compileScala { - classpath = classpath + (configurations.compile + configurations.provided) -} - -tasks.compileExamplesScala { - classpath = classpath + files(compileScala.destinationDir) + (configurations.compile + configurations.provided) + testCompile 'org.scalatest:scalatest_2.10:1.9.1' } // Add RxJava core to Scaladoc input: @@ -71,14 +29,4 @@ task test(overwrite: true, dependsOn: testClasses) << { ant.scalatest(runpath: sourceSets.test.output.classesDir, haltonfailure: 'true', fork: 'false') {reporter(type: 'stdout')} -} - -jar { - manifest { - name = 'rxjava-scala' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,!org.scalatest.*,*' - instruction 'Fragment-Host', 'com.netflix.rxjava.core' - } -} +} \ No newline at end of file diff --git a/language-adaptors/rxjava-scala/src/examples/java/rx/lang/scala/examples/MovieLibUsage.java b/language-adaptors/rxjava-scala/src/examples/scala/rx/lang/scala/examples/MovieLibUsage.java similarity index 100% rename from language-adaptors/rxjava-scala/src/examples/java/rx/lang/scala/examples/MovieLibUsage.java rename to language-adaptors/rxjava-scala/src/examples/scala/rx/lang/scala/examples/MovieLibUsage.java diff --git a/rxjava-contrib/rxjava-android/build.gradle b/rxjava-contrib/rxjava-android/build.gradle index 144d3cd68a..430ebc08ce 100644 --- a/rxjava-contrib/rxjava-android/build.gradle +++ b/rxjava-contrib/rxjava-android/build.gradle @@ -1,33 +1,8 @@ -apply plugin: 'osgi' - dependencies { - compile project(':rxjava-core') provided 'com.google.android:android:4.0.1.2' provided 'com.google.android:support-v4:r7' - // testing - provided 'junit:junit-dep:4.10' - provided 'org.mockito:mockito-core:1.8.5' - provided 'org.robolectric:robolectric:2.1.1' -} - -javadoc { - options { - doclet = "org.benjchristensen.doclet.DocletExclude" - docletpath = [rootProject.file('./gradle/doclet-exclude.jar')] - stylesheetFile = rootProject.file('./gradle/javadocStyleSheet.css') - windowTitle = "RxJava Android Javadoc ${project.version}" - } - options.addStringOption('top').value = '

RxJava Android

' -} - -jar { - manifest { - name = 'rxjava-android' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - } + testCompile 'org.robolectric:robolectric:2.1.1' } test { diff --git a/rxjava-contrib/rxjava-apache-http/build.gradle b/rxjava-contrib/rxjava-apache-http/build.gradle index 81d150ccc3..fbc99f7179 100644 --- a/rxjava-contrib/rxjava-apache-http/build.gradle +++ b/rxjava-contrib/rxjava-apache-http/build.gradle @@ -1,20 +1,5 @@ -apply plugin: 'osgi' - -sourceCompatibility = JavaVersion.VERSION_1_6 -targetCompatibility = JavaVersion.VERSION_1_6 - dependencies { - compile project(':rxjava-core') compile 'org.apache.httpcomponents:httpclient:4.3' compile 'org.apache.httpcomponents:httpcore-nio:4.3' compile 'org.apache.httpcomponents:httpasyncclient:4.0' } - -jar { - manifest { - name = 'rxjava-apache-http' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - } -} diff --git a/rxjava-contrib/rxjava-async-util/build.gradle b/rxjava-contrib/rxjava-async-util/build.gradle index 09d9aae655..374e1d8c37 100644 --- a/rxjava-contrib/rxjava-async-util/build.gradle +++ b/rxjava-contrib/rxjava-async-util/build.gradle @@ -1,20 +1,3 @@ -apply plugin: 'osgi' - -sourceCompatibility = JavaVersion.VERSION_1_6 -targetCompatibility = JavaVersion.VERSION_1_6 - dependencies { - compile project(':rxjava-core') - testCompile project(":rxjava-core").sourceSets.test.output - provided 'junit:junit-dep:4.10' - provided 'org.mockito:mockito-core:1.8.5' -} - -jar { - manifest { - name = 'rxjava-async-util' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - } + testCompile project(":rxjava-test") } diff --git a/rxjava-contrib/rxjava-computation-expressions/build.gradle b/rxjava-contrib/rxjava-computation-expressions/build.gradle deleted file mode 100644 index 21bc395344..0000000000 --- a/rxjava-contrib/rxjava-computation-expressions/build.gradle +++ /dev/null @@ -1,20 +0,0 @@ -apply plugin: 'osgi' - -sourceCompatibility = JavaVersion.VERSION_1_6 -targetCompatibility = JavaVersion.VERSION_1_6 - -dependencies { - compile project(':rxjava-core') - testCompile project(":rxjava-core").sourceSets.test.output - provided 'junit:junit-dep:4.10' - provided 'org.mockito:mockito-core:1.8.5' -} - -jar { - manifest { - name = 'rxjava-computation-expressions' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - } -} diff --git a/rxjava-contrib/rxjava-string/build.gradle b/rxjava-contrib/rxjava-string/build.gradle index 5c578ae04d..31ec9b1875 100644 --- a/rxjava-contrib/rxjava-string/build.gradle +++ b/rxjava-contrib/rxjava-string/build.gradle @@ -1,30 +1,3 @@ -apply plugin: 'osgi' - -sourceCompatibility = JavaVersion.VERSION_1_6 -targetCompatibility = JavaVersion.VERSION_1_6 - dependencies { - compile project(':rxjava-core') - testCompile project(":rxjava-core").sourceSets.test.output - provided 'junit:junit-dep:4.10' - provided 'org.mockito:mockito-core:1.8.5' -} - -javadoc { - options { - doclet = "org.benjchristensen.doclet.DocletExclude" - docletpath = [rootProject.file('./gradle/doclet-exclude.jar')] - stylesheetFile = rootProject.file('./gradle/javadocStyleSheet.css') - windowTitle = "RxJava Javadoc ${project.version}" - } - options.addStringOption('top').value = '

RxJava

' -} - -jar { - manifest { - name = 'rxjava-string' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - } -} + testCompile project(":rxjava-test") +} \ No newline at end of file diff --git a/rxjava-contrib/rxjava-swing/build.gradle b/rxjava-contrib/rxjava-swing/build.gradle deleted file mode 100644 index ea863813a2..0000000000 --- a/rxjava-contrib/rxjava-swing/build.gradle +++ /dev/null @@ -1,29 +0,0 @@ -apply plugin: 'osgi' - -sourceCompatibility = JavaVersion.VERSION_1_6 -targetCompatibility = JavaVersion.VERSION_1_6 - -dependencies { - compile project(':rxjava-core') - provided 'junit:junit-dep:4.10' - provided 'org.mockito:mockito-core:1.8.5' -} - -javadoc { - options { - doclet = "org.benjchristensen.doclet.DocletExclude" - docletpath = [rootProject.file('./gradle/doclet-exclude.jar')] - stylesheetFile = rootProject.file('./gradle/javadocStyleSheet.css') - windowTitle = "RxJava Javadoc ${project.version}" - } - options.addStringOption('top').value = '

RxJava

' -} - -jar { - manifest { - name = 'rxjava-swing' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - } -} diff --git a/rxjava-contrib/rxjava-swing/src/main/java/rx/schedulers/SwingScheduler.java b/rxjava-contrib/rxjava-swing/src/main/java/rx/schedulers/SwingScheduler.java index 7ce2c4e2d1..1a794e0dcc 100644 --- a/rxjava-contrib/rxjava-swing/src/main/java/rx/schedulers/SwingScheduler.java +++ b/rxjava-contrib/rxjava-swing/src/main/java/rx/schedulers/SwingScheduler.java @@ -15,24 +15,6 @@ */ package rx.schedulers; -import static org.junit.Assert.*; -import static org.mockito.Mockito.*; - -import java.awt.EventQueue; -import java.awt.event.ActionEvent; -import java.awt.event.ActionListener; -import java.util.concurrent.CountDownLatch; -import java.util.concurrent.TimeUnit; -import java.util.concurrent.atomic.AtomicReference; - -import javax.swing.SwingUtilities; -import javax.swing.Timer; - -import org.junit.Rule; -import org.junit.Test; -import org.junit.rules.ExpectedException; -import org.mockito.InOrder; - import rx.Scheduler; import rx.Subscription; import rx.subscriptions.CompositeSubscription; @@ -40,6 +22,13 @@ import rx.util.functions.Action0; import rx.util.functions.Func2; +import javax.swing.*; +import java.awt.*; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; +import java.util.concurrent.TimeUnit; +import java.util.concurrent.atomic.AtomicReference; + /** * Executes work on the Swing UI thread. * This scheduler should only be used with actions that execute quickly. @@ -157,118 +146,4 @@ private static void assertThatTheDelayIsValidForTheSwingTimer(long delay) { } } - public static class UnitTest { - @Rule - public ExpectedException exception = ExpectedException.none(); - - @Test - public void testInvalidDelayValues() { - final SwingScheduler scheduler = new SwingScheduler(); - final Action0 action = mock(Action0.class); - - exception.expect(IllegalArgumentException.class); - scheduler.schedulePeriodically(action, -1L, 100L, TimeUnit.SECONDS); - - exception.expect(IllegalArgumentException.class); - scheduler.schedulePeriodically(action, 100L, -1L, TimeUnit.SECONDS); - - exception.expect(IllegalArgumentException.class); - scheduler.schedulePeriodically(action, 1L + Integer.MAX_VALUE, 100L, TimeUnit.MILLISECONDS); - - exception.expect(IllegalArgumentException.class); - scheduler.schedulePeriodically(action, 100L, 1L + Integer.MAX_VALUE / 1000, TimeUnit.SECONDS); - } - - @Test - public void testPeriodicScheduling() throws Exception { - final SwingScheduler scheduler = new SwingScheduler(); - - final CountDownLatch latch = new CountDownLatch(4); - - final Action0 innerAction = mock(Action0.class); - final Action0 action = new Action0() { - @Override - public void call() { - try { - innerAction.call(); - assertTrue(SwingUtilities.isEventDispatchThread()); - } finally { - latch.countDown(); - } - } - }; - - Subscription sub = scheduler.schedulePeriodically(action, 50, 200, TimeUnit.MILLISECONDS); - - if (!latch.await(5000, TimeUnit.MILLISECONDS)) { - fail("timed out waiting for tasks to execute"); - } - - sub.unsubscribe(); - waitForEmptyEventQueue(); - verify(innerAction, times(4)).call(); - } - - @Test - public void testNestedActions() throws Exception { - final SwingScheduler scheduler = new SwingScheduler(); - - final Action0 firstStepStart = mock(Action0.class); - final Action0 firstStepEnd = mock(Action0.class); - - final Action0 secondStepStart = mock(Action0.class); - final Action0 secondStepEnd = mock(Action0.class); - - final Action0 thirdStepStart = mock(Action0.class); - final Action0 thirdStepEnd = mock(Action0.class); - - final Action0 firstAction = new Action0() { - @Override - public void call() { - assertTrue(SwingUtilities.isEventDispatchThread()); - firstStepStart.call(); - firstStepEnd.call(); - } - }; - final Action0 secondAction = new Action0() { - @Override - public void call() { - assertTrue(SwingUtilities.isEventDispatchThread()); - secondStepStart.call(); - scheduler.schedule(firstAction); - secondStepEnd.call(); - } - }; - final Action0 thirdAction = new Action0() { - @Override - public void call() { - assertTrue(SwingUtilities.isEventDispatchThread()); - thirdStepStart.call(); - scheduler.schedule(secondAction); - thirdStepEnd.call(); - } - }; - - InOrder inOrder = inOrder(firstStepStart, firstStepEnd, secondStepStart, secondStepEnd, thirdStepStart, thirdStepEnd); - - scheduler.schedule(thirdAction); - waitForEmptyEventQueue(); - - inOrder.verify(thirdStepStart, times(1)).call(); - inOrder.verify(thirdStepEnd, times(1)).call(); - inOrder.verify(secondStepStart, times(1)).call(); - inOrder.verify(secondStepEnd, times(1)).call(); - inOrder.verify(firstStepStart, times(1)).call(); - inOrder.verify(firstStepEnd, times(1)).call(); - } - - private static void waitForEmptyEventQueue() throws Exception { - EventQueue.invokeAndWait(new Runnable() { - @Override - public void run() { - // nothing to do, we're just waiting here for the event queue to be emptied - } - }); - } - } } diff --git a/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/AbstractButtonSource.java b/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/AbstractButtonSource.java index ef5c7db50a..d01b7bd9a6 100644 --- a/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/AbstractButtonSource.java +++ b/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/AbstractButtonSource.java @@ -15,23 +15,16 @@ */ package rx.swing.sources; -import static org.mockito.Mockito.*; - -import java.awt.event.ActionEvent; -import java.awt.event.ActionListener; - -import javax.swing.AbstractButton; - -import org.junit.Test; -import org.mockito.Matchers; - import rx.Observable; import rx.Observable.OnSubscribeFunc; import rx.Observer; import rx.Subscription; import rx.subscriptions.Subscriptions; import rx.util.functions.Action0; -import rx.util.functions.Action1; + +import javax.swing.*; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; public enum AbstractButtonSource { ; // no instances @@ -60,42 +53,4 @@ public void call() { }); } - public static class UnitTest { - @Test - public void testObservingActionEvents() { - @SuppressWarnings("unchecked") - Action1 action = mock(Action1.class); - @SuppressWarnings("unchecked") - Action1 error = mock(Action1.class); - Action0 complete = mock(Action0.class); - - final ActionEvent event = new ActionEvent(this, 1, "command"); - - @SuppressWarnings("serial") - class TestButton extends AbstractButton { - void testAction() { - fireActionPerformed(event); - } - } - - TestButton button = new TestButton(); - Subscription sub = fromActionOf(button).subscribe(action, error, complete); - - verify(action, never()).call(Matchers.any()); - verify(error, never()).call(Matchers.any()); - verify(complete, never()).call(); - - button.testAction(); - verify(action, times(1)).call(Matchers.any()); - - button.testAction(); - verify(action, times(2)).call(Matchers.any()); - - sub.unsubscribe(); - button.testAction(); - verify(action, times(2)).call(Matchers.any()); - verify(error, never()).call(Matchers.any()); - verify(complete, never()).call(); - } - } } diff --git a/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/KeyEventSource.java b/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/KeyEventSource.java index e3b37a7868..ad193d600c 100644 --- a/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/KeyEventSource.java +++ b/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/KeyEventSource.java @@ -15,32 +15,22 @@ */ package rx.swing.sources; -import static java.util.Arrays.*; -import static org.mockito.Mockito.*; - -import java.awt.Component; -import java.awt.event.KeyEvent; -import java.awt.event.KeyListener; -import java.util.Collections; -import java.util.HashSet; -import java.util.Set; - -import javax.swing.JPanel; - -import org.junit.Test; -import org.mockito.InOrder; -import org.mockito.Matchers; - import rx.Observable; import rx.Observable.OnSubscribeFunc; import rx.Observer; import rx.Subscription; import rx.subscriptions.Subscriptions; import rx.util.functions.Action0; -import rx.util.functions.Action1; import rx.util.functions.Func1; import rx.util.functions.Func2; +import java.awt.*; +import java.awt.event.KeyEvent; +import java.awt.event.KeyListener; +import java.util.Collections; +import java.util.HashSet; +import java.util.Set; + public enum KeyEventSource { ; // no instances /** @@ -110,88 +100,5 @@ public Boolean call(KeyEvent event) { return filteredKeyEvents.scan(Collections.emptySet(), new CollectKeys()); } - - public static class UnitTest { - private Component comp = new JPanel(); - - @Test - public void testObservingKeyEvents() { - @SuppressWarnings("unchecked") - Action1 action = mock(Action1.class); - @SuppressWarnings("unchecked") - Action1 error = mock(Action1.class); - Action0 complete = mock(Action0.class); - - final KeyEvent event = mock(KeyEvent.class); - - Subscription sub = fromKeyEventsOf(comp).subscribe(action, error, complete); - - verify(action, never()).call(Matchers.any()); - verify(error, never()).call(Matchers.any()); - verify(complete, never()).call(); - - fireKeyEvent(event); - verify(action, times(1)).call(Matchers.any()); - - fireKeyEvent(event); - verify(action, times(2)).call(Matchers.any()); - - sub.unsubscribe(); - fireKeyEvent(event); - verify(action, times(2)).call(Matchers.any()); - verify(error, never()).call(Matchers.any()); - verify(complete, never()).call(); - } - - @Test - public void testObservingPressedKeys() { - @SuppressWarnings("unchecked") - Action1> action = mock(Action1.class); - @SuppressWarnings("unchecked") - Action1 error = mock(Action1.class); - Action0 complete = mock(Action0.class); - - Subscription sub = currentlyPressedKeysOf(comp).subscribe(action, error, complete); - - InOrder inOrder = inOrder(action); - inOrder.verify(action, times(1)).call(Collections.emptySet()); - verify(error, never()).call(Matchers.any()); - verify(complete, never()).call(); - - fireKeyEvent(keyEvent(1, KeyEvent.KEY_PRESSED)); - inOrder.verify(action, times(1)).call(new HashSet(asList(1))); - verify(error, never()).call(Matchers.any()); - verify(complete, never()).call(); - - fireKeyEvent(keyEvent(2, KeyEvent.KEY_PRESSED)); - fireKeyEvent(keyEvent(KeyEvent.VK_UNDEFINED, KeyEvent.KEY_TYPED)); - inOrder.verify(action, times(1)).call(new HashSet(asList(1, 2))); - - fireKeyEvent(keyEvent(2, KeyEvent.KEY_RELEASED)); - inOrder.verify(action, times(1)).call(new HashSet(asList(1))); - - fireKeyEvent(keyEvent(3, KeyEvent.KEY_RELEASED)); - inOrder.verify(action, times(1)).call(new HashSet(asList(1))); - - fireKeyEvent(keyEvent(1, KeyEvent.KEY_RELEASED)); - inOrder.verify(action, times(1)).call(Collections.emptySet()); - - sub.unsubscribe(); - fireKeyEvent(keyEvent(1, KeyEvent.KEY_PRESSED)); - inOrder.verify(action, never()).call(Matchers.>any()); - verify(error, never()).call(Matchers.any()); - verify(complete, never()).call(); - } - - private KeyEvent keyEvent(int keyCode, int id) { - return new KeyEvent(comp, id, -1L, 0, keyCode, ' '); - } - - private void fireKeyEvent(KeyEvent event) { - for (KeyListener listener: comp.getKeyListeners()) { - listener.keyTyped(event); - } - } - } } diff --git a/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/MouseEventSource.java b/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/MouseEventSource.java index f6589da054..2aad7ccf93 100644 --- a/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/MouseEventSource.java +++ b/rxjava-contrib/rxjava-swing/src/main/java/rx/swing/sources/MouseEventSource.java @@ -15,30 +15,20 @@ */ package rx.swing.sources; -import static org.mockito.Mockito.*; - -import java.awt.Component; -import java.awt.Point; -import java.awt.event.MouseEvent; -import java.awt.event.MouseListener; -import java.awt.event.MouseMotionListener; - -import javax.swing.JPanel; - -import org.junit.Test; -import org.mockito.InOrder; -import org.mockito.Matchers; - import rx.Observable; import rx.Observable.OnSubscribeFunc; import rx.Observer; import rx.Subscription; import rx.subscriptions.Subscriptions; import rx.util.functions.Action0; -import rx.util.functions.Action1; import rx.util.functions.Func1; import rx.util.functions.Func2; +import java.awt.*; +import java.awt.event.MouseEvent; +import java.awt.event.MouseListener; +import java.awt.event.MouseMotionListener; + public enum MouseEventSource { ; // no instances /** @@ -151,50 +141,5 @@ public Point call(OldAndRelative oar) { .map(new OnlyRelative()) .skip(2); // skip the useless initial value and the invalid first computation } - - public static class UnitTest { - private Component comp = new JPanel(); - - @Test - public void testRelativeMouseMotion() { - @SuppressWarnings("unchecked") - Action1 action = mock(Action1.class); - @SuppressWarnings("unchecked") - Action1 error = mock(Action1.class); - Action0 complete = mock(Action0.class); - - Subscription sub = fromRelativeMouseMotion(comp).subscribe(action, error, complete); - - InOrder inOrder = inOrder(action); - - verify(action, never()).call(Matchers.any()); - verify(error, never()).call(Matchers.any()); - verify(complete, never()).call(); - - fireMouseEvent(mouseEvent(0, 0)); - verify(action, never()).call(Matchers.any()); - - fireMouseEvent(mouseEvent(10, -5)); - inOrder.verify(action, times(1)).call(new Point(10, -5)); - - fireMouseEvent(mouseEvent(6, 10)); - inOrder.verify(action, times(1)).call(new Point(-4, 15)); - - sub.unsubscribe(); - fireMouseEvent(mouseEvent(0, 0)); - inOrder.verify(action, never()).call(Matchers.any()); - verify(error, never()).call(Matchers.any()); - verify(complete, never()).call(); - } - - private MouseEvent mouseEvent(int x, int y) { - return new MouseEvent(comp, MouseEvent.MOUSE_MOVED, 1L, 0, x, y, 0, false); - } - - private void fireMouseEvent(MouseEvent event) { - for (MouseMotionListener listener: comp.getMouseMotionListeners()) { - listener.mouseMoved(event); - } - } - } + } diff --git a/rxjava-contrib/rxjava-swing/src/test/java/rx/schedulers/SwingSchedulerTest.java b/rxjava-contrib/rxjava-swing/src/test/java/rx/schedulers/SwingSchedulerTest.java new file mode 100644 index 0000000000..cafa469e1c --- /dev/null +++ b/rxjava-contrib/rxjava-swing/src/test/java/rx/schedulers/SwingSchedulerTest.java @@ -0,0 +1,147 @@ +/** + * Copyright 2013 Netflix, Inc. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package rx.schedulers; + +import org.junit.Rule; +import org.junit.Test; +import org.junit.rules.ExpectedException; +import org.mockito.InOrder; +import rx.Subscription; +import rx.util.functions.Action0; + +import javax.swing.*; +import java.awt.*; +import java.util.concurrent.CountDownLatch; +import java.util.concurrent.TimeUnit; + +import static org.junit.Assert.assertTrue; +import static org.junit.Assert.fail; +import static org.mockito.Mockito.*; + +public class SwingSchedulerTest { + @Rule + public ExpectedException exception = ExpectedException.none(); + + @Test + public void testInvalidDelayValues() { + final SwingScheduler scheduler = SwingScheduler.getInstance(); + final Action0 action = mock(Action0.class); + + exception.expect(IllegalArgumentException.class); + scheduler.schedulePeriodically(action, -1L, 100L, TimeUnit.SECONDS); + + exception.expect(IllegalArgumentException.class); + scheduler.schedulePeriodically(action, 100L, -1L, TimeUnit.SECONDS); + + exception.expect(IllegalArgumentException.class); + scheduler.schedulePeriodically(action, 1L + Integer.MAX_VALUE, 100L, TimeUnit.MILLISECONDS); + + exception.expect(IllegalArgumentException.class); + scheduler.schedulePeriodically(action, 100L, 1L + Integer.MAX_VALUE / 1000, TimeUnit.SECONDS); + } + + @Test + public void testPeriodicScheduling() throws Exception { + final SwingScheduler scheduler = SwingScheduler.getInstance(); + + final CountDownLatch latch = new CountDownLatch(4); + + final Action0 innerAction = mock(Action0.class); + final Action0 action = new Action0() { + @Override + public void call() { + try { + innerAction.call(); + assertTrue(SwingUtilities.isEventDispatchThread()); + } finally { + latch.countDown(); + } + } + }; + + Subscription sub = scheduler.schedulePeriodically(action, 50, 200, TimeUnit.MILLISECONDS); + + if (!latch.await(5000, TimeUnit.MILLISECONDS)) { + fail("timed out waiting for tasks to execute"); + } + + sub.unsubscribe(); + waitForEmptyEventQueue(); + verify(innerAction, times(4)).call(); + } + + @Test + public void testNestedActions() throws Exception { + final SwingScheduler scheduler = SwingScheduler.getInstance(); + + final Action0 firstStepStart = mock(Action0.class); + final Action0 firstStepEnd = mock(Action0.class); + + final Action0 secondStepStart = mock(Action0.class); + final Action0 secondStepEnd = mock(Action0.class); + + final Action0 thirdStepStart = mock(Action0.class); + final Action0 thirdStepEnd = mock(Action0.class); + + final Action0 firstAction = new Action0() { + @Override + public void call() { + assertTrue(SwingUtilities.isEventDispatchThread()); + firstStepStart.call(); + firstStepEnd.call(); + } + }; + final Action0 secondAction = new Action0() { + @Override + public void call() { + assertTrue(SwingUtilities.isEventDispatchThread()); + secondStepStart.call(); + scheduler.schedule(firstAction); + secondStepEnd.call(); + } + }; + final Action0 thirdAction = new Action0() { + @Override + public void call() { + assertTrue(SwingUtilities.isEventDispatchThread()); + thirdStepStart.call(); + scheduler.schedule(secondAction); + thirdStepEnd.call(); + } + }; + + InOrder inOrder = inOrder(firstStepStart, firstStepEnd, secondStepStart, secondStepEnd, thirdStepStart, thirdStepEnd); + + scheduler.schedule(thirdAction); + waitForEmptyEventQueue(); + + inOrder.verify(thirdStepStart, times(1)).call(); + inOrder.verify(thirdStepEnd, times(1)).call(); + inOrder.verify(secondStepStart, times(1)).call(); + inOrder.verify(secondStepEnd, times(1)).call(); + inOrder.verify(firstStepStart, times(1)).call(); + inOrder.verify(firstStepEnd, times(1)).call(); + } + + private static void waitForEmptyEventQueue() throws Exception { + EventQueue.invokeAndWait(new Runnable() { + @Override + public void run() { + // nothing to do, we're just waiting here for the event queue to be emptied + } + }); + } +} diff --git a/rxjava-contrib/rxjava-swing/src/test/java/rx/swing/sources/AbstractButtonSourceTest.java b/rxjava-contrib/rxjava-swing/src/test/java/rx/swing/sources/AbstractButtonSourceTest.java new file mode 100644 index 0000000000..c4196540e2 --- /dev/null +++ b/rxjava-contrib/rxjava-swing/src/test/java/rx/swing/sources/AbstractButtonSourceTest.java @@ -0,0 +1,66 @@ +/** + * Copyright 2013 Netflix, Inc. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package rx.swing.sources; + +import org.junit.Test; +import org.mockito.Matchers; +import rx.Subscription; +import rx.util.functions.Action0; +import rx.util.functions.Action1; + +import javax.swing.*; +import java.awt.event.ActionEvent; + +import static org.mockito.Mockito.*; + +public class AbstractButtonSourceTest { + @Test + public void testObservingActionEvents() { + @SuppressWarnings("unchecked") + Action1 action = mock(Action1.class); + @SuppressWarnings("unchecked") + Action1 error = mock(Action1.class); + Action0 complete = mock(Action0.class); + + final ActionEvent event = new ActionEvent(this, 1, "command"); + + @SuppressWarnings("serial") + class TestButton extends AbstractButton { + void testAction() { + fireActionPerformed(event); + } + } + + TestButton button = new TestButton(); + Subscription sub = AbstractButtonSource.fromActionOf(button).subscribe(action, error, complete); + + verify(action, never()).call(Matchers.any()); + verify(error, never()).call(Matchers.any()); + verify(complete, never()).call(); + + button.testAction(); + verify(action, times(1)).call(Matchers.any()); + + button.testAction(); + verify(action, times(2)).call(Matchers.any()); + + sub.unsubscribe(); + button.testAction(); + verify(action, times(2)).call(Matchers.any()); + verify(error, never()).call(Matchers.any()); + verify(complete, never()).call(); + } +} diff --git a/rxjava-contrib/rxjava-swing/src/test/java/rx/swing/sources/KeyEventSourceTest.java b/rxjava-contrib/rxjava-swing/src/test/java/rx/swing/sources/KeyEventSourceTest.java new file mode 100644 index 0000000000..332da5ff66 --- /dev/null +++ b/rxjava-contrib/rxjava-swing/src/test/java/rx/swing/sources/KeyEventSourceTest.java @@ -0,0 +1,118 @@ +/** + * Copyright 2013 Netflix, Inc. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package rx.swing.sources; + +import org.junit.Test; +import org.mockito.InOrder; +import org.mockito.Matchers; +import rx.Subscription; +import rx.util.functions.Action0; +import rx.util.functions.Action1; + +import javax.swing.*; +import java.awt.*; +import java.awt.event.KeyEvent; +import java.awt.event.KeyListener; +import java.util.Collections; +import java.util.HashSet; +import java.util.Set; + +import static java.util.Arrays.asList; +import static org.mockito.Mockito.*; + +public class KeyEventSourceTest { + private Component comp = new JPanel(); + + @Test + public void testObservingKeyEvents() { + @SuppressWarnings("unchecked") + Action1 action = mock(Action1.class); + @SuppressWarnings("unchecked") + Action1 error = mock(Action1.class); + Action0 complete = mock(Action0.class); + + final KeyEvent event = mock(KeyEvent.class); + + Subscription sub = KeyEventSource.fromKeyEventsOf(comp).subscribe(action, error, complete); + + verify(action, never()).call(Matchers.any()); + verify(error, never()).call(Matchers.any()); + verify(complete, never()).call(); + + fireKeyEvent(event); + verify(action, times(1)).call(Matchers.any()); + + fireKeyEvent(event); + verify(action, times(2)).call(Matchers.any()); + + sub.unsubscribe(); + fireKeyEvent(event); + verify(action, times(2)).call(Matchers.any()); + verify(error, never()).call(Matchers.any()); + verify(complete, never()).call(); + } + + @Test + public void testObservingPressedKeys() { + @SuppressWarnings("unchecked") + Action1> action = mock(Action1.class); + @SuppressWarnings("unchecked") + Action1 error = mock(Action1.class); + Action0 complete = mock(Action0.class); + + Subscription sub = KeyEventSource.currentlyPressedKeysOf(comp).subscribe(action, error, complete); + + InOrder inOrder = inOrder(action); + inOrder.verify(action, times(1)).call(Collections.emptySet()); + verify(error, never()).call(Matchers.any()); + verify(complete, never()).call(); + + fireKeyEvent(keyEvent(1, KeyEvent.KEY_PRESSED)); + inOrder.verify(action, times(1)).call(new HashSet(asList(1))); + verify(error, never()).call(Matchers.any()); + verify(complete, never()).call(); + + fireKeyEvent(keyEvent(2, KeyEvent.KEY_PRESSED)); + fireKeyEvent(keyEvent(KeyEvent.VK_UNDEFINED, KeyEvent.KEY_TYPED)); + inOrder.verify(action, times(1)).call(new HashSet(asList(1, 2))); + + fireKeyEvent(keyEvent(2, KeyEvent.KEY_RELEASED)); + inOrder.verify(action, times(1)).call(new HashSet(asList(1))); + + fireKeyEvent(keyEvent(3, KeyEvent.KEY_RELEASED)); + inOrder.verify(action, times(1)).call(new HashSet(asList(1))); + + fireKeyEvent(keyEvent(1, KeyEvent.KEY_RELEASED)); + inOrder.verify(action, times(1)).call(Collections.emptySet()); + + sub.unsubscribe(); + + fireKeyEvent(keyEvent(1, KeyEvent.KEY_PRESSED)); + inOrder.verify(action, never()).call(Matchers.>any()); + verify(error, never()).call(Matchers.any()); + verify(complete, never()).call(); + } + + private KeyEvent keyEvent(int keyCode, int id) { + return new KeyEvent(comp, id, -1L, 0, keyCode, ' '); + } + + private void fireKeyEvent(KeyEvent event) { + for (KeyListener listener: comp.getKeyListeners()) { + listener.keyTyped(event); + } + } +} diff --git a/rxjava-contrib/rxjava-swing/src/test/java/rx/swing/sources/MouseEventSourceTest.java b/rxjava-contrib/rxjava-swing/src/test/java/rx/swing/sources/MouseEventSourceTest.java new file mode 100644 index 0000000000..7e36e6764f --- /dev/null +++ b/rxjava-contrib/rxjava-swing/src/test/java/rx/swing/sources/MouseEventSourceTest.java @@ -0,0 +1,76 @@ +/** + * Copyright 2013 Netflix, Inc. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package rx.swing.sources; + +import org.junit.Test; +import org.mockito.InOrder; +import org.mockito.Matchers; +import rx.Subscription; +import rx.util.functions.Action0; +import rx.util.functions.Action1; + +import javax.swing.*; +import java.awt.*; +import java.awt.event.MouseEvent; +import java.awt.event.MouseMotionListener; + +import static org.mockito.Mockito.*; + +public class MouseEventSourceTest { + private Component comp = new JPanel(); + + @Test + public void testRelativeMouseMotion() { + @SuppressWarnings("unchecked") + Action1 action = mock(Action1.class); + @SuppressWarnings("unchecked") + Action1 error = mock(Action1.class); + Action0 complete = mock(Action0.class); + + Subscription sub = MouseEventSource.fromRelativeMouseMotion(comp).subscribe(action, error, complete); + + InOrder inOrder = inOrder(action); + + verify(action, never()).call(Matchers.any()); + verify(error, never()).call(Matchers.any()); + verify(complete, never()).call(); + + fireMouseEvent(mouseEvent(0, 0)); + verify(action, never()).call(Matchers.any()); + + fireMouseEvent(mouseEvent(10, -5)); + inOrder.verify(action, times(1)).call(new Point(10, -5)); + + fireMouseEvent(mouseEvent(6, 10)); + inOrder.verify(action, times(1)).call(new Point(-4, 15)); + + sub.unsubscribe(); + fireMouseEvent(mouseEvent(0, 0)); + inOrder.verify(action, never()).call(Matchers.any()); + verify(error, never()).call(Matchers.any()); + verify(complete, never()).call(); + } + + private MouseEvent mouseEvent(int x, int y) { + return new MouseEvent(comp, MouseEvent.MOUSE_MOVED, 1L, 0, x, y, 0, false); + } + + private void fireMouseEvent(MouseEvent event) { + for (MouseMotionListener listener: comp.getMouseMotionListeners()) { + listener.mouseMoved(event); + } + } +} diff --git a/rxjava-core/build.gradle b/rxjava-core/build.gradle index 1732de3017..1d1bf4bf9c 100644 --- a/rxjava-core/build.gradle +++ b/rxjava-core/build.gradle @@ -1,33 +1,7 @@ -apply plugin: 'maven' -apply plugin: 'osgi' - -sourceCompatibility = JavaVersion.VERSION_1_6 -targetCompatibility = JavaVersion.VERSION_1_6 - dependencies { - provided 'junit:junit-dep:4.10' - provided 'org.mockito:mockito-core:1.8.5' -} - -javadoc { - // we do not want the org.rx.operations package include - exclude '**/operations/**' - - options { - doclet = "org.benjchristensen.doclet.DocletExclude" - docletpath = [rootProject.file('./gradle/doclet-exclude.jar')] - stylesheetFile = rootProject.file('./gradle/javadocStyleSheet.css') - windowTitle = "RxJava Javadoc ${project.version}" - } - options.addStringOption('top').value = '

RxJava

' -} - -jar { - manifest { - name = 'rxjava-core' - instruction 'Bundle-Vendor', 'Netflix' - instruction 'Bundle-DocURL', 'https://github.com/Netflix/RxJava' - instruction 'Import-Package', '!org.junit,!junit.framework,!org.mockito.*,*' - } + testCompile project(":rxjava-test") } +test { + maxParallelForks 4 +} \ No newline at end of file diff --git a/rxjava-core/src/test/java/rx/util/AssertObservable.java b/rxjava-test/src/main/java/rx/util/AssertObservable.java similarity index 100% rename from rxjava-core/src/test/java/rx/util/AssertObservable.java rename to rxjava-test/src/main/java/rx/util/AssertObservable.java diff --git a/rxjava-core/src/test/java/rx/util/AssertObservableTest.java b/rxjava-test/src/test/java/rx/util/AssertObservableTest.java similarity index 100% rename from rxjava-core/src/test/java/rx/util/AssertObservableTest.java rename to rxjava-test/src/test/java/rx/util/AssertObservableTest.java diff --git a/settings.gradle b/settings.gradle index 22dd94ec82..3ec339a5ed 100644 --- a/settings.gradle +++ b/settings.gradle @@ -1,13 +1,15 @@ -rootProject.name='rxjava' -include 'rxjava-core', \ -'language-adaptors:rxjava-groovy', \ -'language-adaptors:rxjava-clojure', \ -'language-adaptors:rxjava-jruby', \ -'language-adaptors:rxjava-scala', \ -'language-adaptors:rxjava-kotlin', \ -'rxjava-contrib:rxjava-swing', \ -'rxjava-contrib:rxjava-android', \ -'rxjava-contrib:rxjava-apache-http', \ -'rxjava-contrib:rxjava-string', \ -'rxjava-contrib:rxjava-async-util', \ -'rxjava-contrib:rxjava-computation-expressions' +rootProject.name = 'rxjava' + +include 'rxjava-core', + 'rxjava-test', + 'language-adaptors:rxjava-groovy', + 'language-adaptors:rxjava-clojure', + 'language-adaptors:rxjava-jruby', + 'language-adaptors:rxjava-scala', + 'language-adaptors:rxjava-kotlin', + 'rxjava-contrib:rxjava-swing', + 'rxjava-contrib:rxjava-android', + 'rxjava-contrib:rxjava-apache-http', + 'rxjava-contrib:rxjava-string', + 'rxjava-contrib:rxjava-async-util', + 'rxjava-contrib:rxjava-computation-expressions'