Iceberry-qdd opened a new pull request, #35223: URL: https://github.com/apache/shardingsphere/pull/35223
Fixes #22719 . Changes proposed in this pull request: - This component only determines whether a DML sql take the sharding keys. So it shouldn't change the `sqlStatementContext` object, the object has `generatedKeyContext` inner it. - But it'll re-generate the key and add to the `generatedKeyContext#generatedValues` again, because it also execute the `createShardingConditions` method, see lines 75 and 177. https://github.com/apache/shardingsphere/blob/3bd8866054bfcbe4f76e20c54d00147ee64036a1/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/route/engine/condition/engine/InsertClauseShardingConditionEngine.java#L71-L77 https://github.com/apache/shardingsphere/blob/3bd8866054bfcbe4f76e20c54d00147ee64036a1/features/sharding/core/src/main/java/org/apache/shardingsphere/sharding/route/engine/condition/engine/InsertClauseShardingConditionEngine.java#L170-L183 - Actually, when an `Insert` sql be executed, and configured to use the generated key, the `generatedKeyContext#generatedValues().size()` will be `sqlStatementContext.getValueListCount() * 2` finally, the generatedKeys actually inserted to the db is generated by audit process, origin process also generated the keys, but they'll be ignored, this can be acceptable. - For `mybatis` or other frameworks(may be), it can bring out the key from the generated keys and assign it to the entity, but it requires the element count of `rs` and `iterator` to match, or it'll throw `ExecutorException`. https://github.com/mybatis/mybatis-3/blob/5f8927deebb846b299a99baba984b7db5400b312/src/main/java/org/apache/ibatis/executor/keygen/Jdbc3KeyGenerator.java#L119-L125 ```xml mapper.xml <insert id="insert" parameterType="com.iceberry.Order" keyColumn="id" useGeneratedKeys="true" keyProperty="id"> INSERT INTO tb_order (user_id, product_id, amount, count, created_time) VALUES ( #{userId}, #{productId}, #{amount}, #{count}, #{createdTime} ) </insert> ``` ```java void test_insert(Long userId, Long productId, Long count, BigDecimal amount, LocalDateTime createdTime) { Order order = new Order(null, userId, productId, count, amount, createdTime); int rows = mapper.insert(order); System.out.println(order.getId()); // will be the key generated by shardingSphere Assertions.assertEquals(1, rows); Assertions.assertNotNull(order.getId()); } ```   In the above example, the number of `rs` elements (2) is one more than the `iterator`, which causes the exception. My solution is to store a copy of getGeneratedValues() named `savedGeneratedValues` before `ShardingSpherePreconditions.checkNotEmpty()`, and after that, reassign `getGeneratedValues()` in the finally block to the `savedGeneratedValues`. --- Before committing this PR, I'm sure that I have checked the following options: - [ ] My code follows the [code of conduct](https://shardingsphere.apache.org/community/en/involved/conduct/code/) of this project. - [ ] I have self-reviewed the commit code. - [ ] I have (or in comment I request) added corresponding labels for the pull request. - [ ] I have passed maven check locally : `./mvnw clean install -B -T1C -Dmaven.javadoc.skip -Dmaven.jacoco.skip -e`. - [ ] I have made corresponding changes to the documentation. - [ ] I have added corresponding unit tests for my changes. - [ ] I have updated the Release Notes of the current development version. For more details, see [Update Release Note](https://shardingsphere.apache.org/community/en/involved/contribute/contributor/) -- This is an automated message from the Apache Git Service. To respond to the message, please log on to GitHub and use the URL above to go to the specific comment. To unsubscribe, e-mail: notifications-unsubscr...@shardingsphere.apache.org For queries about this service, please contact Infrastructure at: us...@infra.apache.org