Skip to content

Commit 0a60da0

Browse files
authored
Merge pull request #1372 from spotbugs/copilot/increase-coverage-above-40-percent
Raise unit test coverage from 30% to 42%
2 parents 5d8fce8 + e1e8371 commit 0a60da0

6 files changed

Lines changed: 956 additions & 0 deletions

File tree

src/test/groovy/org/codehaus/mojo/spotbugs/ResourceHelperTest.groovy

Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -81,4 +81,110 @@ class ResourceHelperTest extends Specification {
8181
Files.deleteIfExists(outputDirectory)
8282
}
8383

84+
void 'getResourceFile handles resource without directory separator'() {
85+
given:
86+
Log log = Mock(Log) {
87+
isDebugEnabled() >> true
88+
}
89+
Path outputDirectory = Files.createTempDirectory('ResourceHelperTest-nodir')
90+
ResourceManager resourceManager = Mock(ResourceManager) {
91+
getResourceAsInputStream(_) >> new ByteArrayInputStream('content'.bytes)
92+
}
93+
ResourceHelper helper = new ResourceHelper(log, outputDirectory.toFile(), resourceManager)
94+
String resource = 'plainfile.txt'
95+
96+
when:
97+
File result = helper.getResourceFile(resource)
98+
99+
then:
100+
result.exists()
101+
result.name == 'plainfile.txt'
102+
103+
cleanup:
104+
result?.delete()
105+
Files.deleteIfExists(outputDirectory)
106+
}
107+
108+
void 'getResourceFile sanitizes special characters in path components'() {
109+
given:
110+
Log log = Mock(Log) {
111+
isDebugEnabled() >> true
112+
}
113+
Path outputDirectory = Files.createTempDirectory('ResourceHelperTest-special')
114+
ResourceManager resourceManager = Mock(ResourceManager) {
115+
getResourceAsInputStream(_) >> new ByteArrayInputStream('data'.bytes)
116+
}
117+
ResourceHelper helper = new ResourceHelper(log, outputDirectory.toFile(), resourceManager)
118+
// Path with special chars that should be sanitized to underscores
119+
String resource = 'http://example.com:8080/path?param=value/output.xml'
120+
121+
when:
122+
File result = helper.getResourceFile(resource)
123+
124+
then:
125+
result.exists()
126+
result.name == 'output.xml'
127+
128+
cleanup:
129+
result?.delete()
130+
outputDirectory.toFile().deleteDir()
131+
}
132+
133+
void 'getResourceFile wraps IOException from resourceManager in MojoExecutionException'() {
134+
given:
135+
Log log = Mock(Log) {
136+
isDebugEnabled() >> false
137+
error(*_) >> {}
138+
}
139+
Path outputDirectory = Files.createTempDirectory('ResourceHelperTest-ioex')
140+
// Use a real InputStream that throws IOException on read, avoiding mock proxy wrapping
141+
InputStream failingStream = new InputStream() {
142+
@Override
143+
int read() throws IOException {
144+
throw new IOException('simulated IO failure')
145+
}
146+
}
147+
ResourceManager resourceManager = Mock(ResourceManager) {
148+
getResourceAsInputStream(_) >> failingStream
149+
}
150+
ResourceHelper helper = new ResourceHelper(log, outputDirectory.toFile(), resourceManager)
151+
String resource = 'missing/resource.xml'
152+
153+
when:
154+
helper.getResourceFile(resource)
155+
156+
then:
157+
thrown(org.apache.maven.plugin.MojoExecutionException)
158+
159+
cleanup:
160+
outputDirectory.toFile().deleteDir()
161+
}
162+
163+
void 'ResourceHelper constructor rejects null log'() {
164+
when:
165+
new ResourceHelper(null, new File('.'), Mock(ResourceManager))
166+
167+
then:
168+
thrown(NullPointerException)
169+
}
170+
171+
void 'ResourceHelper constructor rejects null resourceManager'() {
172+
when:
173+
new ResourceHelper(Mock(Log), new File('.'), null)
174+
175+
then:
176+
thrown(NullPointerException)
177+
}
178+
179+
void 'getResourceFile rejects null resource name'() {
180+
given:
181+
ResourceHelper helper = new ResourceHelper(Mock(Log), new File('.'), Mock(ResourceManager))
182+
183+
when:
184+
helper.getResourceFile(null)
185+
186+
then:
187+
thrown(NullPointerException)
188+
}
189+
84190
}

src/test/groovy/org/codehaus/mojo/spotbugs/SourceFileIndexerTest.groovy

Lines changed: 99 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,105 @@ class SourceFileIndexerTest extends Specification {
7676
thrown(MojoExecutionException)
7777
}
7878

79+
void "searchActualFilesLocation returns null when file is not in the index"() {
80+
given:
81+
File baseDir = Files.createTempDirectory("project-notfound").toFile()
82+
File srcDir = new File(baseDir, "src/main/java")
83+
srcDir.mkdirs()
84+
File testFile = new File(srcDir, "Existing.java")
85+
testFile.text = "class Existing {}"
86+
87+
MavenProject project = Mock(MavenProject)
88+
project.getBasedir() >> baseDir
89+
project.getResources() >> []
90+
project.getTestResources() >> []
91+
project.getCompileSourceRoots() >> [srcDir.getAbsolutePath()]
92+
project.getTestCompileSourceRoots() >> []
93+
94+
MavenSession session = Mock(MavenSession)
95+
session.getExecutionRootDirectory() >> baseDir.getAbsolutePath()
96+
session.getCurrentProject() >> project
97+
98+
SourceFileIndexer indexer = new SourceFileIndexer()
99+
indexer.buildListSourceFiles(session)
100+
101+
when:
102+
String result = indexer.searchActualFilesLocation("NonExistent.java")
103+
104+
then:
105+
result == null
106+
107+
cleanup:
108+
baseDir.deleteDir()
109+
}
110+
111+
void "buildListSourceFiles scans nested subdirectories"() {
112+
given:
113+
File baseDir = Files.createTempDirectory("project-nested").toFile()
114+
File srcDir = new File(baseDir, "src/main/java")
115+
File subPkg = new File(srcDir, "com/example")
116+
subPkg.mkdirs()
117+
File nestedFile = new File(subPkg, "Service.java")
118+
nestedFile.text = "class Service {}"
119+
120+
MavenProject project = Mock(MavenProject)
121+
project.getBasedir() >> baseDir
122+
project.getResources() >> []
123+
project.getTestResources() >> []
124+
project.getCompileSourceRoots() >> [srcDir.getAbsolutePath()]
125+
project.getTestCompileSourceRoots() >> []
126+
127+
MavenSession session = Mock(MavenSession)
128+
session.getExecutionRootDirectory() >> baseDir.getAbsolutePath()
129+
session.getCurrentProject() >> project
130+
131+
SourceFileIndexer indexer = new SourceFileIndexer()
132+
133+
when:
134+
indexer.buildListSourceFiles(session)
135+
String found = indexer.searchActualFilesLocation("Service.java")
136+
137+
then:
138+
found != null
139+
found.endsWith("com/example/Service.java")
140+
141+
cleanup:
142+
baseDir.deleteDir()
143+
}
144+
145+
void "buildListSourceFiles includes files from test source roots"() {
146+
given:
147+
File baseDir = Files.createTempDirectory("project-testsrc").toFile()
148+
File testSrcDir = new File(baseDir, "src/test/java")
149+
testSrcDir.mkdirs()
150+
File testFile = new File(testSrcDir, "FooTest.java")
151+
testFile.text = "class FooTest {}"
152+
153+
MavenProject project = Mock(MavenProject)
154+
project.getBasedir() >> baseDir
155+
project.getResources() >> []
156+
project.getTestResources() >> []
157+
project.getCompileSourceRoots() >> []
158+
project.getTestCompileSourceRoots() >> [testSrcDir.getAbsolutePath()]
159+
160+
MavenSession session = Mock(MavenSession)
161+
session.getExecutionRootDirectory() >> baseDir.getAbsolutePath()
162+
session.getCurrentProject() >> project
163+
164+
SourceFileIndexer indexer = new SourceFileIndexer()
165+
166+
when:
167+
indexer.buildListSourceFiles(session)
168+
String found = indexer.searchActualFilesLocation("FooTest.java")
169+
170+
then:
171+
found != null
172+
found.endsWith("FooTest.java")
173+
174+
cleanup:
175+
baseDir.deleteDir()
176+
}
177+
79178
private static Resource resource(File dir) {
80179
Resource res = new Resource()
81180
res.setDirectory(dir.getAbsolutePath())

0 commit comments

Comments
 (0)