测试中使用addAll整合PaginatedQueryList遇空指针,求解决方法
Hey there, let's break down what's going wrong and fix this step by step!
1. First, Fix the Basic Code Mistake
Your line List exampleList = secondList.addAll(dynamoDbMapper.query(...)) has a critical issue: the addAll() method returns a boolean (indicating whether elements were successfully added), not a List. This won't even compile, and it's a common gotcha that can hide other logic problems. Here's the corrected approach:
// Make sure secondList is initialized (never call addAll on a null list!) List<MyDAOClass> secondList = new ArrayList<>(); // Execute the add operation - you can capture the boolean if you need to check success boolean elementsAdded = secondList.addAll(dynamoDbMapper.query(MyDAOClass.class, queryExpression)); // If you need a reference to the combined list, just use secondList directly List<MyDAOClass> exampleList = secondList;
Always ensure secondList isn't null before calling addAll()—that's a quick way to trigger a NullPointerException right there.
2. Properly Mock PaginatedQueryList in Tests
The NullPointerException in your test is almost certainly because either:
- Your mocked
dynamoDbMapper.query()is returningnull, or - The
PaginatedQueryListmock isn't properly initialized (its internal element container is null).
Option A: Use a Real PaginatedQueryList Instance (Recommended)
Instead of mocking the class outright, create a real PaginatedQueryList with an empty element set. This is safer because it behaves exactly like a real instance from the SDK:
// Create an empty list to use as the query result List<MyDAOClass> emptyResults = Collections.emptyList(); // Initialize a valid PaginatedQueryList with your empty results PaginatedQueryList<MyDAOClass> mockPaginatedList = new PaginatedQueryList<>( emptyResults, dynamoDbMapper, queryExpression, MyDAOClass.class ); // Tell your mock mapper to return this valid list when(dynamoDbMapper.query(eq(MyDAOClass.class), eq(queryExpression))).thenReturn(mockPaginatedList);
This gives you a non-null, properly initialized list that won't throw NPE when addAll() is called.
Option B: Mock Critical Methods of PaginatedQueryList
If for some reason you can't create a real instance (unlikely, but possible), mock the essential methods to avoid NPEs:
PaginatedQueryList<MyDAOClass> mockPaginatedList = mock(PaginatedQueryList.class); // Mock the iterator to return an empty iterator (prevents NPE during iteration in addAll) when(mockPaginatedList.iterator()).thenReturn(Collections.emptyIterator()); // Optional: Mock isEmpty() and size() to behave correctly for an empty list when(mockPaginatedList.isEmpty()).thenReturn(true); when(mockPaginatedList.size()).thenReturn(0); // Set your mock mapper to return this prepared mock list when(dynamoDbMapper.query(eq(MyDAOClass.class), eq(queryExpression))).thenReturn(mockPaginatedList);
3. Add Defensive Checks in Production Code
Even outside tests, it's smart to guard against potential null returns from dynamoDbMapper.query():
List<MyDAOClass> queryResults = dynamoDbMapper.query(MyDAOClass.class, queryExpression); // If queryResults is null, replace it with an empty list to avoid NPE if (queryResults == null) { queryResults = Collections.emptyList(); } secondList.addAll(queryResults);
Or use Java 8+'s Optional to make this cleaner:
Optional.ofNullable(dynamoDbMapper.query(MyDAOClass.class, queryExpression)) .ifPresent(secondList::addAll);
This ensures even if the query returns null, your code won't crash.
内容的提问来源于stack exchange,提问作者Joe

