Kotlin Branch Test coverage question

I have this line of code:
if (neighborhood.street.house?.family?.contains("Steve") == true) {
if (neighborhood.street.house?.family?.contains("Steve") == true) {
Test coverage is saying 1 out of 8 branches missed. But how in the world are there eight branches here??? IMO there are only 4 branches: 1). house is null 2). house isn't null but family is null 3). neither house nor family is null and family doesn't contain Steve 4). neither house nor family is null and family contains Steve
12 Replies
JavaBot
JavaBot6d ago
This post has been reserved for your question.
Hey @halofixer! Please use /close or the Close Post button above when your problem is solved. Please remember to follow the help guidelines. This post will be automatically marked as dormant after 300 minutes of inactivity.
TIP: Narrow down your issue to simple and precise questions to maximize the chance that others will reply in here.
Jenis
Jenis6d ago
hello, how are you, your error is very simple, i can do it perfectly, can you talk with me now?
0x150
0x1506d ago
what? show bytecode
halofixer
halofixerOP6d ago
how do I get the bytecode?
0x150
0x1506d ago
well where is the code? gradle or maven project?
JavaBot
JavaBot6d ago
💤 Post marked as dormant
This post has been inactive for over 300 minutes, thus, it has been archived. If your question was not answered yet, feel free to re-open this post or create a new one. In case your post is not getting any attention, you can try to use /help ping. Warning: abusing this will result in moderative actions taken against you.
puggy
puggy6d ago
Hi @halofixer , The reason you're seeing 8 branches instead of 4 is due to how the compiler breaks down your null-safe calls (?.) and logical operations when generating bytecode. Each null check (neighborhood, street, house, family) and the method call (contains) is treated as a separate conditional path. Here's the breakdown: 1. neighborhood is null. 2. neighborhood.street is null. 3. neighborhood.street.house is null. 4. neighborhood.street.house.family is null. 5. family.contains("Steve") returns false. 6. family.contains("Steve") returns true. 7. The == true comparison for true. 8. The == true comparison for false. To confirm, you can decompile the bytecode using javap -c and see how the branches are split. To achieve 100% test coverage, you'll need test cases covering all these possibilities, including combinations of null values and different results for contains.
halofixer
halofixerOP6d ago
wow im very surprised by this. If neighborhood is null, that would throw a NPE. Same for if neighborhood.street is null
puggy
puggy6d ago
Ah, I see it now — you’re using the null-safe operator (?.) only after house. My mistake here. From what I know about how Kotlin generates bytecode, it should be the next 8 branches: Each ?. operator (like the one after house) introduces 2 branches: 1. One for when the value is null (short-circuits the rest of the chain). 2. One for when the value is not null (proceeds to the next step). The contains("Steve") method call introduces 2 branches: 1. One for when it returns true. 2. One for when it returns false. The == true comparison adds another 2 branches: 1. One for when the result matches true. 2. One for when it does not match true. That’s how you end up with 8 branches: 2 (for ?.) × 2 (for contains) × 2 (for == true). I missed this earlier because I was thinking about the null-safety starting at the very beginning of the chain :< Does it make sense now for you? 4 branches are a high-level conceptual view, but a great catch here
0x150
0x1506d ago
@puggy are you using chatgpt
puggy
puggy6d ago
nope, i just compiled this code after @halofixer highlighted that it was null safe check
JavaBot
JavaBot6d ago
💤 Post marked as dormant
This post has been inactive for over 300 minutes, thus, it has been archived. If your question was not answered yet, feel free to re-open this post or create a new one. In case your post is not getting any attention, you can try to use /help ping. Warning: abusing this will result in moderative actions taken against you.
Want results from more Discord servers?
Add your server