mirror of
https://gitee.com/dcren/initializr.git
synced 2026-02-26 05:32:58 +08:00
Proper exception management
This commit updates the service to throw dedicated exception types for common user error and associates proper HTTP status codes to them. Fixes gh-38
This commit is contained in:
@@ -0,0 +1,29 @@
|
||||
/*
|
||||
* 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
|
||||
|
||||
import groovy.transform.InheritConstructors
|
||||
|
||||
/**
|
||||
* Base Initializr exception.
|
||||
*
|
||||
* @author Stephane Nicoll
|
||||
* @since 1.0
|
||||
*/
|
||||
@InheritConstructors
|
||||
class InitializrException extends RuntimeException {
|
||||
}
|
||||
@@ -25,7 +25,6 @@ import groovy.transform.InheritConstructors
|
||||
* @since 1.0
|
||||
*/
|
||||
@InheritConstructors
|
||||
class InvalidInitializrMetadataException extends RuntimeException {
|
||||
|
||||
class InvalidInitializrMetadataException extends InitializrException {
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
/*
|
||||
* 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
|
||||
|
||||
import groovy.transform.InheritConstructors
|
||||
|
||||
import org.springframework.http.HttpStatus
|
||||
import org.springframework.web.bind.annotation.ResponseStatus
|
||||
|
||||
/**
|
||||
* Thrown when a {@link ProjectRequest} is invalid.
|
||||
*
|
||||
* @author Stephane Nicoll
|
||||
* @since 1.0
|
||||
*/
|
||||
@InheritConstructors
|
||||
@ResponseStatus(HttpStatus.BAD_REQUEST)
|
||||
class InvalidProjectRequestException extends InitializrException {
|
||||
}
|
||||
@@ -57,7 +57,7 @@ class ProjectRequest {
|
||||
def dependency = metadata.getDependency(it)
|
||||
if (dependency == null) {
|
||||
if (it.contains(':')) {
|
||||
throw new IllegalArgumentException("Unknown dependency '$it' check project metadata")
|
||||
throw new InvalidProjectRequestException("Unknown dependency '$it' check project metadata")
|
||||
}
|
||||
log.warn("No known dependency for style '$it' assuming spring-boot-starter")
|
||||
dependency = new InitializrMetadata.Dependency()
|
||||
|
||||
@@ -104,7 +104,7 @@ class MainController extends AbstractInitializrController {
|
||||
upload(download, dir, generateFileName(request, 'zip'), 'application/zip')
|
||||
}
|
||||
|
||||
@RequestMapping(value='/starter.tgz', produces='application/x-compress')
|
||||
@RequestMapping(value = '/starter.tgz', produces = 'application/x-compress')
|
||||
@ResponseBody
|
||||
ResponseEntity<byte[]> springTgz(ProjectRequest request) {
|
||||
def dir = projectGenerator.generateProjectStructure(request)
|
||||
@@ -112,7 +112,7 @@ class MainController extends AbstractInitializrController {
|
||||
def download = projectGenerator.createDistributionFile(dir, '.tgz')
|
||||
|
||||
new AntBuilder().tar(destfile: download, compression: 'gzip') {
|
||||
zipfileset(dir:dir, includes:'**')
|
||||
zipfileset(dir: dir, includes: '**')
|
||||
}
|
||||
upload(download, dir, generateFileName(request, 'tgz'), 'application/x-compress')
|
||||
}
|
||||
|
||||
@@ -73,7 +73,7 @@ class ProjectRequestTests {
|
||||
|
||||
request.style << 'org.foo:acme' // does not exist and
|
||||
|
||||
thrown.expect(IllegalArgumentException)
|
||||
thrown.expect(InvalidProjectRequestException)
|
||||
thrown.expectMessage('org.foo:acme')
|
||||
request.resolve(metadata)
|
||||
}
|
||||
|
||||
@@ -30,6 +30,7 @@ import org.springframework.http.HttpStatus
|
||||
import org.springframework.http.ResponseEntity
|
||||
import org.springframework.test.context.ActiveProfiles
|
||||
import org.springframework.util.StreamUtils
|
||||
import org.springframework.web.client.HttpClientErrorException
|
||||
|
||||
import static org.junit.Assert.*
|
||||
|
||||
@@ -39,6 +40,9 @@ import static org.junit.Assert.*
|
||||
@ActiveProfiles('test-default')
|
||||
class MainControllerIntegrationTests extends AbstractInitializrControllerIntegrationTests {
|
||||
|
||||
private final def slurper = new JsonSlurper()
|
||||
|
||||
|
||||
@Test
|
||||
void simpleZipProject() {
|
||||
downloadZip('/starter.zip?style=web&style=jpa').isJavaProject().isMavenProject()
|
||||
@@ -140,8 +144,23 @@ class MainControllerIntegrationTests extends AbstractInitializrControllerIntegra
|
||||
}
|
||||
|
||||
private def metricsEndpoint() {
|
||||
def slurper = new JsonSlurper()
|
||||
slurper.parseText(restTemplate.getForObject(createUrl('/metrics'), String))
|
||||
parseJson(restTemplate.getForObject(createUrl('/metrics'), String))
|
||||
}
|
||||
|
||||
@Test
|
||||
void missingDependencyProperException() {
|
||||
try {
|
||||
invoke('/starter.zip?style=foo:bar')
|
||||
} catch (HttpClientErrorException ex) {
|
||||
def error = parseJson(ex.responseBodyAsString)
|
||||
assertEquals HttpStatus.BAD_REQUEST, ex.getStatusCode()
|
||||
assertTrue 'Dependency not in error message', error.message.contains('foo:bar')
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private def parseJson(String content) {
|
||||
slurper.parseText(content)
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -212,13 +231,17 @@ class MainControllerIntegrationTests extends AbstractInitializrControllerIntegra
|
||||
}
|
||||
|
||||
|
||||
private byte[] invoke(String context) {
|
||||
restTemplate.getForObject(createUrl(context), byte[])
|
||||
}
|
||||
|
||||
private ProjectAssert downloadZip(String context) {
|
||||
def body = restTemplate.getForObject(createUrl(context), byte[])
|
||||
def body = invoke(context)
|
||||
zipProjectAssert(body)
|
||||
}
|
||||
|
||||
private ProjectAssert downloadTgz(String context) {
|
||||
def body = restTemplate.getForObject(createUrl(context), byte[])
|
||||
def body = invoke(context)
|
||||
tgzProjectAssert(body)
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user