mirror of
https://gitee.com/dcren/initializr.git
synced 2025-09-19 01:58:16 +08:00
Add html unit tests
This commit integrates with spring-test-htmlunit and provides tests that use the HTML form.
This commit is contained in:
@@ -59,6 +59,10 @@
|
||||
<dependency>
|
||||
<groupId>org.skyscreamer</groupId>
|
||||
<artifactId>jsonassert</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-test-htmlunit</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
@@ -83,6 +87,11 @@
|
||||
<artifactId>jsonassert</artifactId>
|
||||
<version>1.2.3</version>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-test-htmlunit</artifactId>
|
||||
<version>1.0.0.M2</version>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
</dependencyManagement>
|
||||
|
||||
@@ -132,4 +141,21 @@
|
||||
</plugins>
|
||||
</build>
|
||||
|
||||
<profiles>
|
||||
<profile>
|
||||
<id>springMilestone</id>
|
||||
<repositories>
|
||||
<repository>
|
||||
<id>spring-milestones</id>
|
||||
<name>Spring Milestones</name>
|
||||
<url>http://repo.spring.io/milestone</url>
|
||||
<snapshots>
|
||||
<enabled>false</enabled>
|
||||
</snapshots>
|
||||
</repository>
|
||||
</repositories>
|
||||
</profile>
|
||||
|
||||
</profiles>
|
||||
|
||||
</project>
|
@@ -123,7 +123,7 @@
|
||||
</div>
|
||||
<div class="row">
|
||||
<p class="text-center">
|
||||
<button type="submit" class="btn btn-lg btn-primary" role="button">
|
||||
<button name="generate-project" type="submit" class="btn btn-lg btn-primary" role="button">
|
||||
<span class="glyphicon glyphicon-download"></span> Generate Project
|
||||
</button>
|
||||
</p>
|
||||
|
@@ -16,6 +16,7 @@
|
||||
|
||||
package io.spring.initializr.web
|
||||
|
||||
import io.spring.initializr.support.ProjectAssert
|
||||
import org.junit.Rule
|
||||
import org.junit.rules.TemporaryFolder
|
||||
import org.junit.runner.RunWith
|
||||
@@ -59,6 +60,42 @@ abstract class AbstractMainControllerIntegrationTests {
|
||||
restTemplate.exchange(createUrl('/'), HttpMethod.GET, new HttpEntity<Void>(headers), String).body
|
||||
}
|
||||
|
||||
/**
|
||||
* Return a {@link ProjectAssert} for the following archive content.
|
||||
*/
|
||||
ProjectAssert projectAssert(byte[] content, ArchiveType archiveType) {
|
||||
File archiveFile = writeArchive(content)
|
||||
|
||||
def project = folder.newFolder()
|
||||
switch (archiveType) {
|
||||
case ArchiveType.ZIP:
|
||||
new AntBuilder().unzip(dest: project, src: archiveFile)
|
||||
break
|
||||
case ArchiveType.TGZ:
|
||||
new AntBuilder().untar(dest: project, src: archiveFile, compression: 'gzip')
|
||||
break
|
||||
}
|
||||
new ProjectAssert(project)
|
||||
}
|
||||
|
||||
protected File writeArchive(byte[] body) {
|
||||
def archiveFile = folder.newFile()
|
||||
def stream = new FileOutputStream(archiveFile)
|
||||
try {
|
||||
stream.write(body)
|
||||
} finally {
|
||||
stream.close()
|
||||
}
|
||||
archiveFile
|
||||
}
|
||||
|
||||
|
||||
enum ArchiveType {
|
||||
ZIP,
|
||||
|
||||
TGZ
|
||||
}
|
||||
|
||||
@EnableAutoConfiguration
|
||||
static class Config {}
|
||||
}
|
||||
|
@@ -0,0 +1,113 @@
|
||||
/*
|
||||
* Copyright 2012-2014 the original author or authors.
|
||||
*
|
||||
* 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 io.spring.initializr.web
|
||||
|
||||
import com.gargoylesoftware.htmlunit.WebClient
|
||||
import com.gargoylesoftware.htmlunit.WebRequest
|
||||
import com.gargoylesoftware.htmlunit.html.HtmlPage
|
||||
import io.spring.initializr.support.ProjectAssert
|
||||
import io.spring.initializr.web.support.HomePage
|
||||
import org.junit.After
|
||||
import org.junit.Before
|
||||
import org.junit.Test
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired
|
||||
import org.springframework.test.context.ActiveProfiles
|
||||
import org.springframework.test.web.servlet.MockMvc
|
||||
import org.springframework.test.web.servlet.htmlunit.MockMvcWebConnection
|
||||
import org.springframework.test.web.servlet.setup.MockMvcBuilders
|
||||
import org.springframework.web.context.WebApplicationContext
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Stephane Nicoll
|
||||
*/
|
||||
@ActiveProfiles('test-default')
|
||||
class MainControllerFormIntegrationTests extends AbstractMainControllerIntegrationTests {
|
||||
|
||||
@Autowired
|
||||
private WebApplicationContext context
|
||||
|
||||
private WebClient webClient
|
||||
|
||||
@Before
|
||||
void setup() {
|
||||
MockMvc mockMvc = MockMvcBuilders
|
||||
.webAppContextSetup(context)
|
||||
.build()
|
||||
webClient = new WebClient()
|
||||
webClient.setWebConnection(new MockMvcWebConnection(mockMvc, ''))
|
||||
}
|
||||
|
||||
@After
|
||||
void cleanup() {
|
||||
this.webClient.closeAllWindows()
|
||||
}
|
||||
|
||||
@Test
|
||||
void createDefaultProject() {
|
||||
HomePage page = home()
|
||||
ProjectAssert projectAssert = projectAssert(page.generateProject(), ArchiveType.ZIP)
|
||||
projectAssert.isMavenProject().isJavaProject().hasStaticAndTemplatesResources(false)
|
||||
.pomAssert().hasDependenciesCount(1).hasSpringBootStarterDependency('test')
|
||||
}
|
||||
|
||||
@Test
|
||||
void createProjectWithCustomDefaults() {
|
||||
HomePage page = home()
|
||||
page.groupId = 'com.acme'
|
||||
page.artifactId = 'foo-bar'
|
||||
page.name = 'My project'
|
||||
page.description = 'A description for my project'
|
||||
page.dependencies << 'web' << 'data-jpa'
|
||||
ProjectAssert projectAssert = projectAssert(page.generateProject(), ArchiveType.ZIP)
|
||||
projectAssert.isMavenProject().isJavaProject().hasStaticAndTemplatesResources(true)
|
||||
|
||||
projectAssert.pomAssert().hasGroupId('com.acme').hasArtifactId('foo-bar')
|
||||
.hasName('My project').hasDescription('A description for my project')
|
||||
.hasSpringBootStarterDependency('web')
|
||||
.hasSpringBootStarterDependency('data-jpa')
|
||||
.hasSpringBootStarterDependency('test')
|
||||
}
|
||||
|
||||
@Test
|
||||
void createSimpleGradleProject() {
|
||||
HomePage page = home()
|
||||
page.type = 'gradle.zip'
|
||||
page.dependencies << 'data-jpa'
|
||||
ProjectAssert projectAssert = projectAssert(page.generateProject(), ArchiveType.ZIP)
|
||||
projectAssert.isGradleProject().isJavaProject().hasStaticAndTemplatesResources(false)
|
||||
}
|
||||
|
||||
@Test
|
||||
void createWarProject() {
|
||||
HomePage page = home()
|
||||
page.packaging = 'war'
|
||||
ProjectAssert projectAssert = projectAssert(page.generateProject(), ArchiveType.ZIP)
|
||||
projectAssert.isMavenProject().isJavaWarProject()
|
||||
.pomAssert().hasPackaging('war').hasDependenciesCount(3)
|
||||
.hasSpringBootStarterDependency('web') // Added with war packaging
|
||||
.hasSpringBootStarterDependency('tomcat')
|
||||
.hasSpringBootStarterDependency('test')
|
||||
}
|
||||
|
||||
HomePage home() {
|
||||
WebRequest request = new WebRequest(new URL('http://localhost/'), 'text/html')
|
||||
HtmlPage home = webClient.getPage(request)
|
||||
return new HomePage(home)
|
||||
}
|
||||
}
|
@@ -40,7 +40,7 @@ class MainControllerIntegrationTests extends AbstractMainControllerIntegrationTe
|
||||
|
||||
@Test
|
||||
void simpleZipProject() {
|
||||
downloadZip('/starter.zip?style=web&style=jpa').isJavaProject().isMavenProject()
|
||||
download('/starter.zip?style=web&style=jpa', ArchiveType.ZIP).isJavaProject().isMavenProject()
|
||||
.hasStaticAndTemplatesResources(true).pomAssert()
|
||||
.hasDependenciesCount(3)
|
||||
.hasSpringBootStarterDependency('web')
|
||||
@@ -50,7 +50,7 @@ class MainControllerIntegrationTests extends AbstractMainControllerIntegrationTe
|
||||
|
||||
@Test
|
||||
void simpleTgzProject() {
|
||||
downloadTgz('/starter.tgz?style=org.acme:bar').isJavaProject().isMavenProject()
|
||||
download('/starter.tgz?style=org.acme:bar', ArchiveType.TGZ).isJavaProject().isMavenProject()
|
||||
.hasStaticAndTemplatesResources(false).pomAssert()
|
||||
.hasDependenciesCount(2)
|
||||
.hasDependency('org.acme', 'bar', '2.1.0')
|
||||
@@ -58,8 +58,8 @@ class MainControllerIntegrationTests extends AbstractMainControllerIntegrationTe
|
||||
|
||||
@Test
|
||||
void gradleWarProject() {
|
||||
downloadZip('/starter.zip?style=web&style=security&packaging=war&type=gradle.zip').isJavaWarProject()
|
||||
.isGradleProject()
|
||||
download('/starter.zip?style=web&style=security&packaging=war&type=gradle.zip', ArchiveType.ZIP)
|
||||
.isJavaWarProject().isGradleProject()
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -167,36 +167,11 @@ class MainControllerIntegrationTests extends AbstractMainControllerIntegrationTe
|
||||
}
|
||||
|
||||
|
||||
private ProjectAssert downloadZip(String context) {
|
||||
private ProjectAssert download(String context, ArchiveType archiveType) {
|
||||
byte[] body = restTemplate.getForObject(createUrl(context), byte[])
|
||||
File zipFile = writeArchive(body)
|
||||
|
||||
def project = folder.newFolder()
|
||||
new AntBuilder().unzip(dest: project, src: zipFile)
|
||||
new ProjectAssert(project)
|
||||
projectAssert(body, archiveType)
|
||||
}
|
||||
|
||||
private ProjectAssert downloadTgz(String context) {
|
||||
byte[] body = restTemplate.getForObject(createUrl(context), byte[])
|
||||
File tgzFile = writeArchive(body)
|
||||
|
||||
def project = folder.newFolder()
|
||||
new AntBuilder().untar(dest: project, src: tgzFile, compression: 'gzip')
|
||||
new ProjectAssert(project)
|
||||
}
|
||||
|
||||
private File writeArchive(byte[] body) {
|
||||
def archiveFile = folder.newFile()
|
||||
def stream = new FileOutputStream(archiveFile)
|
||||
try {
|
||||
stream.write(body)
|
||||
} finally {
|
||||
stream.close()
|
||||
}
|
||||
archiveFile
|
||||
}
|
||||
|
||||
|
||||
private static JSONObject readJson(String version) {
|
||||
def resource = new ClassPathResource('metadata/test-default-' + version + '.json')
|
||||
def stream = resource.getInputStream()
|
||||
|
@@ -0,0 +1,103 @@
|
||||
/*
|
||||
* Copyright 2012-2014 the original author or authors.
|
||||
*
|
||||
* 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 io.spring.initializr.web.support
|
||||
|
||||
import com.gargoylesoftware.htmlunit.Page
|
||||
import com.gargoylesoftware.htmlunit.html.*
|
||||
import io.spring.initializr.support.ProjectAssert
|
||||
|
||||
/**
|
||||
* Represent the home page of the service.
|
||||
*
|
||||
* @author Stephane Nicoll
|
||||
*/
|
||||
class HomePage {
|
||||
|
||||
String groupId
|
||||
String artifactId
|
||||
String name
|
||||
String description
|
||||
String packageName
|
||||
String type
|
||||
String packaging
|
||||
List<String> dependencies = []
|
||||
|
||||
private final HtmlPage page
|
||||
|
||||
HomePage(HtmlPage page) {
|
||||
this.page = page
|
||||
}
|
||||
|
||||
/**
|
||||
* Generate a project using the specified temporary directory. Return
|
||||
* the {@link ProjectAssert} instance.
|
||||
* @see org.junit.rules.TemporaryFolder
|
||||
*/
|
||||
byte[] generateProject() {
|
||||
setup()
|
||||
HtmlButton submit = page.getElementByName('generate-project')
|
||||
Page newMessagePage = submit.click();
|
||||
newMessagePage.webResponse.contentAsStream.bytes
|
||||
}
|
||||
|
||||
/**
|
||||
* Setup the {@link HtmlPage} with the customization of this
|
||||
* instance. Only applied when a non-null value is set
|
||||
*/
|
||||
private void setup() {
|
||||
setTextValue('groupId', groupId)
|
||||
setTextValue('artifactId', artifactId)
|
||||
setTextValue('name', name)
|
||||
setTextValue('description', description)
|
||||
setTextValue('packageName', packageName)
|
||||
select('type', type)
|
||||
select('packaging', packaging)
|
||||
selectDependencies(dependencies)
|
||||
}
|
||||
|
||||
private void setTextValue(String elementId, String value) {
|
||||
if (value != null) {
|
||||
HtmlTextInput input = page.getHtmlElementById(elementId)
|
||||
input.setValueAttribute(value)
|
||||
}
|
||||
}
|
||||
|
||||
private void select(String selectId, String value) {
|
||||
if (value != null) {
|
||||
HtmlSelect input = page.getHtmlElementById(selectId)
|
||||
input.setSelectedAttribute(value, true)
|
||||
}
|
||||
}
|
||||
|
||||
private void selectDependencies(List<String> dependencies) {
|
||||
List<DomElement> styles = page.getElementsByName("style")
|
||||
Map<String, HtmlCheckBoxInput> allStyles = new HashMap<>()
|
||||
for (HtmlCheckBoxInput checkBoxInput : styles) {
|
||||
allStyles.put(checkBoxInput.getValueAttribute(), checkBoxInput)
|
||||
}
|
||||
for (String dependency : dependencies) {
|
||||
HtmlCheckBoxInput checkBox = allStyles.get(dependency)
|
||||
if (checkBox != null) {
|
||||
checkBox.checked = true
|
||||
} else {
|
||||
throw new IllegalArgumentException('No dependency with name '
|
||||
+ dependency + ' was found amongst ' + allStyles.keySet());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
Reference in New Issue
Block a user