This is an automated email from the ASF dual-hosted git repository.

chengzhang pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/shardingsphere.git


The following commit(s) were added to refs/heads/master by this push:
     new 05f445463cd Add new infra algorithm load balancer module and algorithm 
implementation (#30309)
05f445463cd is described below

commit 05f445463cd5c3f5e774a5eba26100d6361b9e88
Author: Zhengqiang Duan <[email protected]>
AuthorDate: Tue Feb 27 11:51:39 2024 +0800

    Add new infra algorithm load balancer module and algorithm implementation 
(#30309)
---
 .../user-manual/error-code/sql-error-code.cn.md    |  16 ++-
 .../user-manual/error-code/sql-error-code.en.md    |  16 ++-
 features/sharding/core/pom.xml                     |   4 +-
 infra/algorithm/key-generator/core/pom.xml         |   4 +-
 .../GenerateKeyStrategyNotFoundException.java      |   2 +-
 ...eyGenerateAlgorithmInitializationException.java |   2 +-
 infra/algorithm/key-generator/pom.xml              |   2 +-
 infra/algorithm/key-generator/type/pom.xml         |   4 +-
 .../algorithm/key-generator/type/snowflake/pom.xml |   6 +-
 infra/algorithm/key-generator/type/uuid/pom.xml    |   6 +-
 .../{key-generator => load-balancer}/core/pom.xml  |   9 +-
 .../load/balancer/core/LoadBalanceAlgorithm.java}  |  23 ++--
 .../InvalidAvailableTargetWeightException.java}    |  12 +-
 ...adBalanceAlgorithmInitializationException.java} |  12 +-
 .../core/exception/LoadBalanceSQLException.java}   |  17 +--
 .../{key-generator => load-balancer}/pom.xml       |   2 +-
 .../{key-generator => load-balancer}/type/pom.xml  |   9 +-
 .../uuid => load-balancer/type/random}/pom.xml     |  10 +-
 .../random/RandomLoadBalanceAlgorithm.java}        |  21 ++--
 ...gorithm.load.balancer.core.LoadBalanceAlgorithm |  18 +++
 .../random/RandomLoadBalanceAlgorithmTest.java     |  48 ++++++++
 .../type/round-robin}/pom.xml                      |  10 +-
 .../robin/RoundRobinLoadBalanceAlgorithm.java}     |  28 +++--
 ...gorithm.load.balancer.core.LoadBalanceAlgorithm |  18 +++
 .../robin/RoundRobinLoadBalanceAlgorithmTest.java  |  49 ++++++++
 .../uuid => load-balancer/type/weight}/pom.xml     |  10 +-
 .../weight/WeightLoadBalanceAlgorithm.java         | 134 +++++++++++++++++++++
 ...gorithm.load.balancer.core.LoadBalanceAlgorithm |  18 +++
 .../weight/WeightLoadBalanceAlgorithmTest.java     |  65 ++++++++++
 infra/algorithm/pom.xml                            |   1 +
 infra/distsql-handler/pom.xml                      |   2 +-
 31 files changed, 492 insertions(+), 86 deletions(-)

diff --git a/docs/document/content/user-manual/error-code/sql-error-code.cn.md 
b/docs/document/content/user-manual/error-code/sql-error-code.cn.md
index 39d90ec239a..5c2be0d577d 100644
--- a/docs/document/content/user-manual/error-code/sql-error-code.cn.md
+++ b/docs/document/content/user-manual/error-code/sql-error-code.cn.md
@@ -212,8 +212,6 @@ SQL 错误码以标准的 SQL State,Vendor Code 和详细错误信息提供,
 | 44000     | 20086       | Some routed data sources do not belong to 
configured data sources. routed data sources: \`%s\`, configured data sources: 
\`%s\`. |
 | 44000     | 20087       | Please check your sharding conditions \`%s\` to 
avoid same record in table \`%s\` routing to multiple data nodes.               
 |
 | 44000     | 20088       | Cannot found routing table factor, data source: 
%s, actual table: %s.                                                           
 |
-| 44000     | 20090       | Can not find strategy for generate keys with table 
\`%s\`.                                                                       |
-| HY000     | 20091       | Key generate algorithm \`%s\` initialization 
failed, reason is: %s.                                                          
    |
 | HY000     | 20092       | Clock is moving backwards, last time is %d 
milliseconds, current time is %d milliseconds.                                  
      |
 | HY000     | 20099       | Sharding plugin error, reason is: %s               
                                                                              |
 
@@ -284,6 +282,20 @@ SQL 错误码以标准的 SQL State,Vendor Code 和详细错误信息提供,
 | HY000     | 20980       | Mask algorithm \`%s\` initialization failed, 
reason is: %s. |
 | 42S02     | 20990       | Invalid mask algorithm \`%s\` in database \`%s\`.  
         |
 
+### 基础算法 - 分布式序列
+
+| SQL State | Vendor Code | 错误信息                                               
         |
+|-----------|-------------|-------------------------------------------------------------|
+| 44000     | 21180       | Can not find strategy for generate keys with table 
\`%s\`.                                                                       |
+| HY000     | 21181       | Key generate algorithm \`%s\` initialization 
failed, reason is: %s.                                                          
    |
+
+### 基础算法 - 负载均衡
+
+| SQL State | Vendor Code | 错误信息                                               
         |
+|-----------|-------------|-------------------------------------------------------------|
+| 44000     | 21280       | Invalid available target weight \`%s\`.            
                 |
+| HY000     | 21281       | \'%s\' load balance algorithm initialization 
failed, reason is: %s. |
+
 ## 其他异常
 
 | SQL State | Vendor Code | 错误信息                            |
diff --git a/docs/document/content/user-manual/error-code/sql-error-code.en.md 
b/docs/document/content/user-manual/error-code/sql-error-code.en.md
index f4b6a98dc38..175d441e765 100644
--- a/docs/document/content/user-manual/error-code/sql-error-code.en.md
+++ b/docs/document/content/user-manual/error-code/sql-error-code.en.md
@@ -212,8 +212,6 @@ SQL error codes provide by standard `SQL State`, `Vendor 
Code` and `Reason`, whi
 | 44000     | 20086       | Some routed data sources do not belong to 
configured data sources. routed data sources: \`%s\`, configured data sources: 
\`%s\`. |
 | 44000     | 20087       | Please check your sharding conditions \`%s\` to 
avoid same record in table \`%s\` routing to multiple data nodes.               
 |
 | 44000     | 20088       | Cannot found routing table factor, data source: 
%s, actual table: %s.                                                           
 |
-| 44000     | 20090       | Can not find strategy for generate keys with table 
\`%s\`.                                                                       |
-| HY000     | 20091       | Key generate algorithm \`%s\` initialization 
failed, reason is: %s.                                                          
    |
 | HY000     | 20092       | Clock is moving backwards, last time is %d 
milliseconds, current time is %d milliseconds.                                  
      |
 | HY000     | 20099       | Sharding plugin error, reason is: %s               
                                                                              |
 
@@ -299,6 +297,20 @@ SQL error codes provide by standard `SQL State`, `Vendor 
Code` and `Reason`, whi
 | HY000     | 20980       | Mask algorithm \`%s\` initialization failed, 
reason is: %s. |
 | 42S02     | 20990       | Invalid mask algorithm \`%s\` in database \`%s\`.  
         |
 
+### Infra algorithm - key generate
+
+| SQL State | Vendor Code | Reason                                             
         |
+|-----------|-------------|-------------------------------------------------------------|
+| 44000     | 21180       | Can not find strategy for generate keys with table 
\`%s\`.                                                                       |
+| HY000     | 21181       | Key generate algorithm \`%s\` initialization 
failed, reason is: %s.                                                          
    |
+
+### Infra algorithm - load balance
+
+| SQL State | Vendor Code | Reason                                             
                 |
+|-----------|-------------|---------------------------------------------------------------------|
+| 44000     | 21280       | Invalid available target weight \`%s\`.            
                 |
+| HY000     | 21281       | \'%s\' load balance algorithm initialization 
failed, reason is: %s. |
+
 ## Other Exception
 
 | SQL State | Vendor Code | Reason                          |
diff --git a/features/sharding/core/pom.xml b/features/sharding/core/pom.xml
index bddc9c02c82..bb5c5447e58 100644
--- a/features/sharding/core/pom.xml
+++ b/features/sharding/core/pom.xml
@@ -85,12 +85,12 @@
         </dependency>
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-key-generator-uuid</artifactId>
+            
<artifactId>shardingsphere-infra-algorithm-key-generator-uuid</artifactId>
             <version>${project.version}</version>
         </dependency>
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            
<artifactId>shardingsphere-infra-key-generator-snowflake</artifactId>
+            
<artifactId>shardingsphere-infra-algorithm-key-generator-snowflake</artifactId>
             <version>${project.version}</version>
         </dependency>
         
diff --git a/infra/algorithm/key-generator/core/pom.xml 
b/infra/algorithm/key-generator/core/pom.xml
index 5639f7f3f53..b21376e8fa8 100644
--- a/infra/algorithm/key-generator/core/pom.xml
+++ b/infra/algorithm/key-generator/core/pom.xml
@@ -20,10 +20,10 @@
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.apache.shardingsphere</groupId>
-        <artifactId>shardingsphere-infra-key-generator</artifactId>
+        <artifactId>shardingsphere-infra-algorithm-key-generator</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator-core</artifactId>
+    <artifactId>shardingsphere-infra-algorithm-key-generator-core</artifactId>
     <name>${project.artifactId}</name>
     
     <dependencies>
diff --git 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
 
b/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
index 7b2f4dbf203..ffa90622cd2 100644
--- 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
+++ 
b/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
@@ -27,6 +27,6 @@ public final class GenerateKeyStrategyNotFoundException 
extends KeyGenerateSQLEx
     private static final long serialVersionUID = 7456922260524630374L;
     
     public GenerateKeyStrategyNotFoundException(final String tableName) {
-        super(XOpenSQLState.CHECK_OPTION_VIOLATION, 90, "Can not find strategy 
for generate keys with table `%s`.", tableName);
+        super(XOpenSQLState.CHECK_OPTION_VIOLATION, 80, "Can not find strategy 
for generate keys with table `%s`.", tableName);
     }
 }
diff --git 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/KeyGenerateAlgorithmInitializationException.java
 
b/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/KeyGenerateAlgorithmInitializationException.java
index c848db034a0..565e14189dc 100644
--- 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/KeyGenerateAlgorithmInitializationException.java
+++ 
b/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/KeyGenerateAlgorithmInitializationException.java
@@ -27,6 +27,6 @@ public final class 
KeyGenerateAlgorithmInitializationException extends KeyGenera
     private static final long serialVersionUID = 4137100879778822323L;
     
     public KeyGenerateAlgorithmInitializationException(final String 
keyGenerateType, final String reason) {
-        super(XOpenSQLState.GENERAL_ERROR, 91, "Key generate algorithm `%s` 
initialization failed, reason is: %s.", keyGenerateType, reason);
+        super(XOpenSQLState.GENERAL_ERROR, 81, "Key generate algorithm `%s` 
initialization failed, reason is: %s.", keyGenerateType, reason);
     }
 }
diff --git a/infra/algorithm/key-generator/pom.xml 
b/infra/algorithm/key-generator/pom.xml
index d737f6fdffb..eef1d157385 100644
--- a/infra/algorithm/key-generator/pom.xml
+++ b/infra/algorithm/key-generator/pom.xml
@@ -23,7 +23,7 @@
         <artifactId>shardingsphere-infra-algorithm</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator</artifactId>
+    <artifactId>shardingsphere-infra-algorithm-key-generator</artifactId>
     <packaging>pom</packaging>
     <name>${project.artifactId}</name>
     
diff --git a/infra/algorithm/key-generator/type/pom.xml 
b/infra/algorithm/key-generator/type/pom.xml
index 47c37fc365b..667e89dad1d 100644
--- a/infra/algorithm/key-generator/type/pom.xml
+++ b/infra/algorithm/key-generator/type/pom.xml
@@ -20,10 +20,10 @@
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.apache.shardingsphere</groupId>
-        <artifactId>shardingsphere-infra-key-generator</artifactId>
+        <artifactId>shardingsphere-infra-algorithm-key-generator</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator-type</artifactId>
+    <artifactId>shardingsphere-infra-algorithm-key-generator-type</artifactId>
     <packaging>pom</packaging>
     <name>${project.artifactId}</name>
     
diff --git a/infra/algorithm/key-generator/type/snowflake/pom.xml 
b/infra/algorithm/key-generator/type/snowflake/pom.xml
index 74a8b23ead4..b926f22d06c 100644
--- a/infra/algorithm/key-generator/type/snowflake/pom.xml
+++ b/infra/algorithm/key-generator/type/snowflake/pom.xml
@@ -20,10 +20,10 @@
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.apache.shardingsphere</groupId>
-        <artifactId>shardingsphere-infra-key-generator-type</artifactId>
+        
<artifactId>shardingsphere-infra-algorithm-key-generator-type</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator-snowflake</artifactId>
+    
<artifactId>shardingsphere-infra-algorithm-key-generator-snowflake</artifactId>
     <name>${project.artifactId}</name>
     
     <dependencies>
@@ -34,7 +34,7 @@
         </dependency>
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-key-generator-core</artifactId>
+            
<artifactId>shardingsphere-infra-algorithm-key-generator-core</artifactId>
             <version>${project.version}</version>
         </dependency>
         
diff --git a/infra/algorithm/key-generator/type/uuid/pom.xml 
b/infra/algorithm/key-generator/type/uuid/pom.xml
index ae9f2c70850..aca9eee90c3 100644
--- a/infra/algorithm/key-generator/type/uuid/pom.xml
+++ b/infra/algorithm/key-generator/type/uuid/pom.xml
@@ -20,10 +20,10 @@
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.apache.shardingsphere</groupId>
-        <artifactId>shardingsphere-infra-key-generator-type</artifactId>
+        
<artifactId>shardingsphere-infra-algorithm-key-generator-type</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator-uuid</artifactId>
+    <artifactId>shardingsphere-infra-algorithm-key-generator-uuid</artifactId>
     <name>${project.artifactId}</name>
     
     <dependencies>
@@ -34,7 +34,7 @@
         </dependency>
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-key-generator-core</artifactId>
+            
<artifactId>shardingsphere-infra-algorithm-key-generator-core</artifactId>
             <version>${project.version}</version>
         </dependency>
     </dependencies>
diff --git a/infra/algorithm/key-generator/core/pom.xml 
b/infra/algorithm/load-balancer/core/pom.xml
similarity index 83%
copy from infra/algorithm/key-generator/core/pom.xml
copy to infra/algorithm/load-balancer/core/pom.xml
index 5639f7f3f53..12d2c23a327 100644
--- a/infra/algorithm/key-generator/core/pom.xml
+++ b/infra/algorithm/load-balancer/core/pom.xml
@@ -20,18 +20,13 @@
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.apache.shardingsphere</groupId>
-        <artifactId>shardingsphere-infra-key-generator</artifactId>
+        <artifactId>shardingsphere-infra-algorithm-load-balancer</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator-core</artifactId>
+    <artifactId>shardingsphere-infra-algorithm-load-balancer-core</artifactId>
     <name>${project.artifactId}</name>
     
     <dependencies>
-        <dependency>
-            <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-common</artifactId>
-            <version>${project.version}</version>
-        </dependency>
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
             <artifactId>shardingsphere-infra-algorithm-core</artifactId>
diff --git 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
 
b/infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/LoadBalanceAlgorithm.java
similarity index 56%
copy from 
infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
copy to 
infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/LoadBalanceAlgorithm.java
index 7b2f4dbf203..02bfbc170bb 100644
--- 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
+++ 
b/infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/LoadBalanceAlgorithm.java
@@ -15,18 +15,23 @@
  * limitations under the License.
  */
 
-package org.apache.shardingsphere.infra.algorithm.keygen.core.exception;
+package org.apache.shardingsphere.infra.algorithm.load.balancer.core;
 
-import 
org.apache.shardingsphere.infra.exception.core.external.sql.sqlstate.XOpenSQLState;
+import org.apache.shardingsphere.infra.algorithm.core.ShardingSphereAlgorithm;
+
+import java.util.List;
 
 /**
- * Generate key strategy not found exception.
+ * Load balance algorithm.
  */
-public final class GenerateKeyStrategyNotFoundException extends 
KeyGenerateSQLException {
-    
-    private static final long serialVersionUID = 7456922260524630374L;
+public interface LoadBalanceAlgorithm extends ShardingSphereAlgorithm {
     
-    public GenerateKeyStrategyNotFoundException(final String tableName) {
-        super(XOpenSQLState.CHECK_OPTION_VIOLATION, 90, "Can not find strategy 
for generate keys with table `%s`.", tableName);
-    }
+    /**
+     * Get available target name.
+     * 
+     * @param groupName group name, which uniquely identifies a set of 
availableTargetNames
+     * @param availableTargetNames available data sources or instance id
+     * @return available target name
+     */
+    String getAvailableTargetName(String groupName, List<String> 
availableTargetNames);
 }
diff --git 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
 
b/infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/exception/InvalidAvailableTargetWeightException.java
similarity index 65%
copy from 
infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
copy to 
infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/exception/InvalidAvailableTargetWeightException.java
index 7b2f4dbf203..96e6e659e69 100644
--- 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
+++ 
b/infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/exception/InvalidAvailableTargetWeightException.java
@@ -15,18 +15,18 @@
  * limitations under the License.
  */
 
-package org.apache.shardingsphere.infra.algorithm.keygen.core.exception;
+package org.apache.shardingsphere.infra.algorithm.load.balancer.core.exception;
 
 import 
org.apache.shardingsphere.infra.exception.core.external.sql.sqlstate.XOpenSQLState;
 
 /**
- * Generate key strategy not found exception.
+ * Invalid available target weight exception.
  */
-public final class GenerateKeyStrategyNotFoundException extends 
KeyGenerateSQLException {
+public final class InvalidAvailableTargetWeightException extends 
LoadBalanceSQLException {
     
-    private static final long serialVersionUID = 7456922260524630374L;
+    private static final long serialVersionUID = -2671152203719618753L;
     
-    public GenerateKeyStrategyNotFoundException(final String tableName) {
-        super(XOpenSQLState.CHECK_OPTION_VIOLATION, 90, "Can not find strategy 
for generate keys with table `%s`.", tableName);
+    public InvalidAvailableTargetWeightException(final Object weight) {
+        super(XOpenSQLState.INVALID_DATA_TYPE, 80, "Invalid available target 
weight `%s`.", weight);
     }
 }
diff --git 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
 
b/infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/exception/LoadBalanceAlgorithmInitializationException.java
similarity index 61%
copy from 
infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
copy to 
infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/exception/LoadBalanceAlgorithmInitializationException.java
index 7b2f4dbf203..15ad2de6ce2 100644
--- 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
+++ 
b/infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/exception/LoadBalanceAlgorithmInitializationException.java
@@ -15,18 +15,18 @@
  * limitations under the License.
  */
 
-package org.apache.shardingsphere.infra.algorithm.keygen.core.exception;
+package org.apache.shardingsphere.infra.algorithm.load.balancer.core.exception;
 
 import 
org.apache.shardingsphere.infra.exception.core.external.sql.sqlstate.XOpenSQLState;
 
 /**
- * Generate key strategy not found exception.
+ * Load balance algorithm initialization exception.
  */
-public final class GenerateKeyStrategyNotFoundException extends 
KeyGenerateSQLException {
+public class LoadBalanceAlgorithmInitializationException extends 
LoadBalanceSQLException {
     
-    private static final long serialVersionUID = 7456922260524630374L;
+    private static final long serialVersionUID = 3025471428679102820L;
     
-    public GenerateKeyStrategyNotFoundException(final String tableName) {
-        super(XOpenSQLState.CHECK_OPTION_VIOLATION, 90, "Can not find strategy 
for generate keys with table `%s`.", tableName);
+    public LoadBalanceAlgorithmInitializationException(final String 
loadBalanceAlgorithmType, final String reason) {
+        super(XOpenSQLState.CHECK_OPTION_VIOLATION, 81, "'%s' load balance 
algorithm initialization failed, reason is: %s.", loadBalanceAlgorithmType, 
reason);
     }
 }
diff --git 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
 
b/infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/exception/LoadBalanceSQLException.java
similarity index 58%
copy from 
infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
copy to 
infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/exception/LoadBalanceSQLException.java
index 7b2f4dbf203..2de97c285aa 100644
--- 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
+++ 
b/infra/algorithm/load-balancer/core/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/core/exception/LoadBalanceSQLException.java
@@ -15,18 +15,21 @@
  * limitations under the License.
  */
 
-package org.apache.shardingsphere.infra.algorithm.keygen.core.exception;
+package org.apache.shardingsphere.infra.algorithm.load.balancer.core.exception;
 
-import 
org.apache.shardingsphere.infra.exception.core.external.sql.sqlstate.XOpenSQLState;
+import 
org.apache.shardingsphere.infra.exception.core.external.sql.sqlstate.SQLState;
+import 
org.apache.shardingsphere.infra.exception.core.external.sql.type.feature.FeatureSQLException;
 
 /**
- * Generate key strategy not found exception.
+ * Load balance SQL exception.
  */
-public final class GenerateKeyStrategyNotFoundException extends 
KeyGenerateSQLException {
+public abstract class LoadBalanceSQLException extends FeatureSQLException {
     
-    private static final long serialVersionUID = 7456922260524630374L;
+    private static final int FEATURE_CODE = 12;
     
-    public GenerateKeyStrategyNotFoundException(final String tableName) {
-        super(XOpenSQLState.CHECK_OPTION_VIOLATION, 90, "Can not find strategy 
for generate keys with table `%s`.", tableName);
+    private static final long serialVersionUID = -6834428848205322872L;
+    
+    protected LoadBalanceSQLException(final SQLState sqlState, final int 
errorCode, final String reason, final Object... messageArgs) {
+        super(sqlState, FEATURE_CODE, errorCode, reason, messageArgs);
     }
 }
diff --git a/infra/algorithm/key-generator/pom.xml 
b/infra/algorithm/load-balancer/pom.xml
similarity index 95%
copy from infra/algorithm/key-generator/pom.xml
copy to infra/algorithm/load-balancer/pom.xml
index d737f6fdffb..4ab2514c9c2 100644
--- a/infra/algorithm/key-generator/pom.xml
+++ b/infra/algorithm/load-balancer/pom.xml
@@ -23,7 +23,7 @@
         <artifactId>shardingsphere-infra-algorithm</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator</artifactId>
+    <artifactId>shardingsphere-infra-algorithm-load-balancer</artifactId>
     <packaging>pom</packaging>
     <name>${project.artifactId}</name>
     
diff --git a/infra/algorithm/key-generator/type/pom.xml 
b/infra/algorithm/load-balancer/type/pom.xml
similarity index 83%
copy from infra/algorithm/key-generator/type/pom.xml
copy to infra/algorithm/load-balancer/type/pom.xml
index 47c37fc365b..04d6f0edc0e 100644
--- a/infra/algorithm/key-generator/type/pom.xml
+++ b/infra/algorithm/load-balancer/type/pom.xml
@@ -20,15 +20,16 @@
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.apache.shardingsphere</groupId>
-        <artifactId>shardingsphere-infra-key-generator</artifactId>
+        <artifactId>shardingsphere-infra-algorithm-load-balancer</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator-type</artifactId>
+    <artifactId>shardingsphere-infra-algorithm-load-balancer-type</artifactId>
     <packaging>pom</packaging>
     <name>${project.artifactId}</name>
     
     <modules>
-        <module>snowflake</module>
-        <module>uuid</module>
+        <module>random</module>
+        <module>round-robin</module>
+        <module>weight</module>
     </modules>
 </project>
diff --git a/infra/algorithm/key-generator/type/uuid/pom.xml 
b/infra/algorithm/load-balancer/type/random/pom.xml
similarity index 82%
copy from infra/algorithm/key-generator/type/uuid/pom.xml
copy to infra/algorithm/load-balancer/type/random/pom.xml
index ae9f2c70850..0c5bef22e4d 100644
--- a/infra/algorithm/key-generator/type/uuid/pom.xml
+++ b/infra/algorithm/load-balancer/type/random/pom.xml
@@ -20,22 +20,24 @@
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.apache.shardingsphere</groupId>
-        <artifactId>shardingsphere-infra-key-generator-type</artifactId>
+        
<artifactId>shardingsphere-infra-algorithm-load-balancer-type</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator-uuid</artifactId>
+    
<artifactId>shardingsphere-infra-algorithm-load-balancer-random</artifactId>
     <name>${project.artifactId}</name>
     
     <dependencies>
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-common</artifactId>
+            
<artifactId>shardingsphere-infra-algorithm-load-balancer-core</artifactId>
             <version>${project.version}</version>
         </dependency>
+        
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-key-generator-core</artifactId>
+            <artifactId>shardingsphere-test-util</artifactId>
             <version>${project.version}</version>
+            <scope>test</scope>
         </dependency>
     </dependencies>
 </project>
diff --git 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
 
b/infra/algorithm/load-balancer/type/random/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/random/RandomLoadBalanceAlgorithm.java
similarity index 56%
copy from 
infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
copy to 
infra/algorithm/load-balancer/type/random/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/random/RandomLoadBalanceAlgorithm.java
index 7b2f4dbf203..235d94342c0 100644
--- 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
+++ 
b/infra/algorithm/load-balancer/type/random/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/random/RandomLoadBalanceAlgorithm.java
@@ -15,18 +15,25 @@
  * limitations under the License.
  */
 
-package org.apache.shardingsphere.infra.algorithm.keygen.core.exception;
+package org.apache.shardingsphere.infra.algorithm.load.balancer.random;
 
-import 
org.apache.shardingsphere.infra.exception.core.external.sql.sqlstate.XOpenSQLState;
+import 
org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm;
+
+import java.util.List;
+import java.util.concurrent.ThreadLocalRandom;
 
 /**
- * Generate key strategy not found exception.
+ * Random load balance algorithm.
  */
-public final class GenerateKeyStrategyNotFoundException extends 
KeyGenerateSQLException {
+public final class RandomLoadBalanceAlgorithm implements LoadBalanceAlgorithm {
     
-    private static final long serialVersionUID = 7456922260524630374L;
+    @Override
+    public String getAvailableTargetName(final String groupName, final 
List<String> availableTargetNames) {
+        return 
availableTargetNames.get(ThreadLocalRandom.current().nextInt(availableTargetNames.size()));
+    }
     
-    public GenerateKeyStrategyNotFoundException(final String tableName) {
-        super(XOpenSQLState.CHECK_OPTION_VIOLATION, 90, "Can not find strategy 
for generate keys with table `%s`.", tableName);
+    @Override
+    public String getType() {
+        return "RANDOM";
     }
 }
diff --git 
a/infra/algorithm/load-balancer/type/random/src/main/resources/META-INF/services/org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm
 
b/infra/algorithm/load-balancer/type/random/src/main/resources/META-INF/services/org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm
new file mode 100644
index 00000000000..47ea8658800
--- /dev/null
+++ 
b/infra/algorithm/load-balancer/type/random/src/main/resources/META-INF/services/org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm
@@ -0,0 +1,18 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one or more
+# contributor license agreements.  See the NOTICE file distributed with
+# this work for additional information regarding copyright ownership.
+# The ASF licenses this file to You 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.
+#
+
+org.apache.shardingsphere.infra.algorithm.load.balancer.random.RandomLoadBalanceAlgorithm
diff --git 
a/infra/algorithm/load-balancer/type/random/src/test/java/org/apache/shardingsphere/infra/algorithm/load/balancer/random/RandomLoadBalanceAlgorithmTest.java
 
b/infra/algorithm/load-balancer/type/random/src/test/java/org/apache/shardingsphere/infra/algorithm/load/balancer/random/RandomLoadBalanceAlgorithmTest.java
new file mode 100644
index 00000000000..8221af0bcda
--- /dev/null
+++ 
b/infra/algorithm/load-balancer/type/random/src/test/java/org/apache/shardingsphere/infra/algorithm/load/balancer/random/RandomLoadBalanceAlgorithmTest.java
@@ -0,0 +1,48 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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 org.apache.shardingsphere.infra.algorithm.load.balancer.random;
+
+import 
org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm;
+import org.apache.shardingsphere.infra.spi.type.typed.TypedSPILoader;
+import org.junit.jupiter.api.Test;
+
+import java.util.Arrays;
+import java.util.List;
+import java.util.Properties;
+
+import static org.junit.jupiter.api.Assertions.assertTrue;
+
+class RandomLoadBalanceAlgorithmTest {
+    
+    @Test
+    void assertGetAvailableTargetNameWithDefaultStrategy() {
+        LoadBalanceAlgorithm loadBalanceAlgorithm = 
TypedSPILoader.getService(LoadBalanceAlgorithm.class, "RANDOM", new 
Properties());
+        String availableTargetNames1 = "test_read_ds_1";
+        String availableTargetNames2 = "test_read_ds_2";
+        List<String> availableTargetNames = 
Arrays.asList(availableTargetNames1, availableTargetNames2);
+        assertRandomLoadBalance(availableTargetNames, loadBalanceAlgorithm);
+        
assertTrue(availableTargetNames.contains(loadBalanceAlgorithm.getAvailableTargetName("ds",
 availableTargetNames)));
+        
assertTrue(availableTargetNames.contains(loadBalanceAlgorithm.getAvailableTargetName("ds",
 availableTargetNames)));
+    }
+    
+    private void assertRandomLoadBalance(final List<String> 
availableTargetNames, final LoadBalanceAlgorithm loadBalanceAlgorithm) {
+        
assertTrue(availableTargetNames.contains(loadBalanceAlgorithm.getAvailableTargetName("ds",
 availableTargetNames)));
+        
assertTrue(availableTargetNames.contains(loadBalanceAlgorithm.getAvailableTargetName("ds",
 availableTargetNames)));
+        
assertTrue(availableTargetNames.contains(loadBalanceAlgorithm.getAvailableTargetName("ds",
 availableTargetNames)));
+    }
+}
diff --git a/infra/algorithm/key-generator/type/uuid/pom.xml 
b/infra/algorithm/load-balancer/type/round-robin/pom.xml
similarity index 81%
copy from infra/algorithm/key-generator/type/uuid/pom.xml
copy to infra/algorithm/load-balancer/type/round-robin/pom.xml
index ae9f2c70850..aa27e81a751 100644
--- a/infra/algorithm/key-generator/type/uuid/pom.xml
+++ b/infra/algorithm/load-balancer/type/round-robin/pom.xml
@@ -20,22 +20,24 @@
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.apache.shardingsphere</groupId>
-        <artifactId>shardingsphere-infra-key-generator-type</artifactId>
+        
<artifactId>shardingsphere-infra-algorithm-load-balancer-type</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator-uuid</artifactId>
+    
<artifactId>shardingsphere-infra-algorithm-load-balancer-round-robin</artifactId>
     <name>${project.artifactId}</name>
     
     <dependencies>
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-common</artifactId>
+            
<artifactId>shardingsphere-infra-algorithm-load-balancer-core</artifactId>
             <version>${project.version}</version>
         </dependency>
+        
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-key-generator-core</artifactId>
+            <artifactId>shardingsphere-test-util</artifactId>
             <version>${project.version}</version>
+            <scope>test</scope>
         </dependency>
     </dependencies>
 </project>
diff --git 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
 
b/infra/algorithm/load-balancer/type/round-robin/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/round/robin/RoundRobinLoadBalanceAlgorithm.java
similarity index 50%
copy from 
infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
copy to 
infra/algorithm/load-balancer/type/round-robin/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/round/robin/RoundRobinLoadBalanceAlgorithm.java
index 7b2f4dbf203..3a661bfb933 100644
--- 
a/infra/algorithm/key-generator/core/src/main/java/org/apache/shardingsphere/infra/algorithm/keygen/core/exception/GenerateKeyStrategyNotFoundException.java
+++ 
b/infra/algorithm/load-balancer/type/round-robin/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/round/robin/RoundRobinLoadBalanceAlgorithm.java
@@ -15,18 +15,32 @@
  * limitations under the License.
  */
 
-package org.apache.shardingsphere.infra.algorithm.keygen.core.exception;
+package org.apache.shardingsphere.infra.algorithm.load.balancer.round.robin;
 
-import 
org.apache.shardingsphere.infra.exception.core.external.sql.sqlstate.XOpenSQLState;
+import 
org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm;
+
+import java.util.List;
+import java.util.concurrent.atomic.AtomicInteger;
 
 /**
- * Generate key strategy not found exception.
+ * Round-robin load balance algorithm.
  */
-public final class GenerateKeyStrategyNotFoundException extends 
KeyGenerateSQLException {
+public final class RoundRobinLoadBalanceAlgorithm implements 
LoadBalanceAlgorithm {
+    
+    private final AtomicInteger count = new AtomicInteger(0);
     
-    private static final long serialVersionUID = 7456922260524630374L;
+    @Override
+    public String getAvailableTargetName(final String groupName, final 
List<String> availableTargetNames) {
+        return availableTargetNames.get(Math.abs(count.getAndIncrement()) % 
availableTargetNames.size());
+    }
+    
+    @Override
+    public String getType() {
+        return "ROUND_ROBIN";
+    }
     
-    public GenerateKeyStrategyNotFoundException(final String tableName) {
-        super(XOpenSQLState.CHECK_OPTION_VIOLATION, 90, "Can not find strategy 
for generate keys with table `%s`.", tableName);
+    @Override
+    public boolean isDefault() {
+        return true;
     }
 }
diff --git 
a/infra/algorithm/load-balancer/type/round-robin/src/main/resources/META-INF/services/org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm
 
b/infra/algorithm/load-balancer/type/round-robin/src/main/resources/META-INF/services/org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm
new file mode 100644
index 00000000000..f9032c60958
--- /dev/null
+++ 
b/infra/algorithm/load-balancer/type/round-robin/src/main/resources/META-INF/services/org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm
@@ -0,0 +1,18 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one or more
+# contributor license agreements.  See the NOTICE file distributed with
+# this work for additional information regarding copyright ownership.
+# The ASF licenses this file to You 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.
+#
+
+org.apache.shardingsphere.infra.algorithm.load.balancer.round.robin.RoundRobinLoadBalanceAlgorithm
diff --git 
a/infra/algorithm/load-balancer/type/round-robin/src/test/java/org/apache/shardingsphere/infra/algorithm/load/balancer/round/robin/RoundRobinLoadBalanceAlgorithmTest.java
 
b/infra/algorithm/load-balancer/type/round-robin/src/test/java/org/apache/shardingsphere/infra/algorithm/load/balancer/round/robin/RoundRobinLoadBalanceAlgorithmTest.java
new file mode 100644
index 00000000000..1fcde9d7b6a
--- /dev/null
+++ 
b/infra/algorithm/load-balancer/type/round-robin/src/test/java/org/apache/shardingsphere/infra/algorithm/load/balancer/round/robin/RoundRobinLoadBalanceAlgorithmTest.java
@@ -0,0 +1,49 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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 org.apache.shardingsphere.infra.algorithm.load.balancer.round.robin;
+
+import 
org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm;
+import org.apache.shardingsphere.infra.spi.type.typed.TypedSPILoader;
+import org.junit.jupiter.api.Test;
+
+import java.util.Arrays;
+import java.util.List;
+import java.util.Properties;
+
+import static org.hamcrest.CoreMatchers.is;
+import static org.hamcrest.MatcherAssert.assertThat;
+
+class RoundRobinLoadBalanceAlgorithmTest {
+    
+    @Test
+    void assertGetAvailableTargetNameWithDefaultStrategy() {
+        LoadBalanceAlgorithm loadBalanceAlgorithm = 
TypedSPILoader.getService(LoadBalanceAlgorithm.class, "ROUND_ROBIN", new 
Properties());
+        String availableTargetName1 = "test_read_ds_1";
+        String availableTargetName2 = "test_read_ds_2";
+        List<String> availableTargetNames = 
Arrays.asList(availableTargetName1, availableTargetName2);
+        assertRoundRobinLoadBalance(availableTargetName1, 
availableTargetName2, loadBalanceAlgorithm, availableTargetNames);
+    }
+    
+    private void assertRoundRobinLoadBalance(final String 
availableTargetName1, final String availableTargetName2, final 
LoadBalanceAlgorithm loadBalanceAlgorithm,
+                                             final List<String> 
availableTargetNames) {
+        assertThat(loadBalanceAlgorithm.getAvailableTargetName("ds", 
availableTargetNames), is(availableTargetName1));
+        assertThat(loadBalanceAlgorithm.getAvailableTargetName("ds", 
availableTargetNames), is(availableTargetName2));
+        assertThat(loadBalanceAlgorithm.getAvailableTargetName("ds", 
availableTargetNames), is(availableTargetName1));
+        assertThat(loadBalanceAlgorithm.getAvailableTargetName("ds", 
availableTargetNames), is(availableTargetName2));
+    }
+}
diff --git a/infra/algorithm/key-generator/type/uuid/pom.xml 
b/infra/algorithm/load-balancer/type/weight/pom.xml
similarity index 82%
copy from infra/algorithm/key-generator/type/uuid/pom.xml
copy to infra/algorithm/load-balancer/type/weight/pom.xml
index ae9f2c70850..d4db535107a 100644
--- a/infra/algorithm/key-generator/type/uuid/pom.xml
+++ b/infra/algorithm/load-balancer/type/weight/pom.xml
@@ -20,22 +20,24 @@
     <modelVersion>4.0.0</modelVersion>
     <parent>
         <groupId>org.apache.shardingsphere</groupId>
-        <artifactId>shardingsphere-infra-key-generator-type</artifactId>
+        
<artifactId>shardingsphere-infra-algorithm-load-balancer-type</artifactId>
         <version>5.4.2-SNAPSHOT</version>
     </parent>
-    <artifactId>shardingsphere-infra-key-generator-uuid</artifactId>
+    
<artifactId>shardingsphere-infra-algorithm-load-balancer-weight</artifactId>
     <name>${project.artifactId}</name>
     
     <dependencies>
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-common</artifactId>
+            
<artifactId>shardingsphere-infra-algorithm-load-balancer-core</artifactId>
             <version>${project.version}</version>
         </dependency>
+        
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-key-generator-core</artifactId>
+            <artifactId>shardingsphere-test-util</artifactId>
             <version>${project.version}</version>
+            <scope>test</scope>
         </dependency>
     </dependencies>
 </project>
diff --git 
a/infra/algorithm/load-balancer/type/weight/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/weight/WeightLoadBalanceAlgorithm.java
 
b/infra/algorithm/load-balancer/type/weight/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/weight/WeightLoadBalanceAlgorithm.java
new file mode 100644
index 00000000000..62668ffbf86
--- /dev/null
+++ 
b/infra/algorithm/load-balancer/type/weight/src/main/java/org/apache/shardingsphere/infra/algorithm/load/balancer/weight/WeightLoadBalanceAlgorithm.java
@@ -0,0 +1,134 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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 org.apache.shardingsphere.infra.algorithm.load.balancer.weight;
+
+import com.google.common.base.Preconditions;
+import lombok.Getter;
+import 
org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm;
+import 
org.apache.shardingsphere.infra.algorithm.load.balancer.core.exception.InvalidAvailableTargetWeightException;
+import 
org.apache.shardingsphere.infra.algorithm.load.balancer.core.exception.LoadBalanceAlgorithmInitializationException;
+import 
org.apache.shardingsphere.infra.exception.core.ShardingSpherePreconditions;
+
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
+import java.util.Properties;
+import java.util.concurrent.ConcurrentHashMap;
+import java.util.concurrent.ThreadLocalRandom;
+
+/**
+ * Weight load balance algorithm.
+ */
+public final class WeightLoadBalanceAlgorithm implements LoadBalanceAlgorithm {
+    
+    private static final double ACCURACY_THRESHOLD = 0.0001;
+    
+    private final Map<String, double[]> weightMap = new ConcurrentHashMap<>();
+    
+    private Properties props;
+    
+    @Getter
+    private Collection<String> availableTargetNames;
+    
+    @Override
+    public void init(final Properties props) {
+        this.props = props;
+        availableTargetNames = props.stringPropertyNames();
+        
ShardingSpherePreconditions.checkState(!availableTargetNames.isEmpty(), () -> 
new LoadBalanceAlgorithmInitializationException(getType(), "Available target is 
required"));
+        for (String each : availableTargetNames) {
+            String weight = props.getProperty(each);
+            ShardingSpherePreconditions.checkNotNull(weight,
+                    () -> new 
LoadBalanceAlgorithmInitializationException(getType(), String.format("Available 
target `%s` access weight is not configured.", each)));
+            try {
+                Double.parseDouble(weight);
+            } catch (final NumberFormatException ex) {
+                throw new InvalidAvailableTargetWeightException(weight);
+            }
+        }
+    }
+    
+    @Override
+    public String getAvailableTargetName(final String groupName, final 
List<String> availableTargetNames) {
+        double[] weight = weightMap.containsKey(groupName) && 
weightMap.get(groupName).length == availableTargetNames.size() ? 
weightMap.get(groupName) : initWeight(availableTargetNames);
+        weightMap.put(groupName, weight);
+        return getAvailableTargetName(availableTargetNames, weight);
+    }
+    
+    private String getAvailableTargetName(final List<String> 
availableTargetNames, final double[] weight) {
+        double randomWeight = ThreadLocalRandom.current().nextDouble(0, 1);
+        int index = Arrays.binarySearch(weight, randomWeight);
+        if (index < 0) {
+            index = -index - 1;
+            return index < weight.length && randomWeight < weight[index] ? 
availableTargetNames.get(index) : 
availableTargetNames.get(availableTargetNames.size() - 1);
+        }
+        return availableTargetNames.get(index);
+    }
+    
+    private double[] initWeight(final List<String> availableTargetNames) {
+        double[] result = getWeights(availableTargetNames);
+        Preconditions.checkState(!(0 != result.length && 
Math.abs(result[result.length - 1] - 1.0D) >= ACCURACY_THRESHOLD),
+                "The cumulative weight is calculated incorrectly, and the sum 
of the probabilities is not equal to 1");
+        return result;
+    }
+    
+    private double[] getWeights(final List<String> availableTargetNames) {
+        double[] exactWeights = new double[availableTargetNames.size()];
+        int index = 0;
+        double sum = 0D;
+        for (String each : availableTargetNames) {
+            double weight = getWeightValue(each);
+            exactWeights[index++] = weight;
+            sum += weight;
+        }
+        for (int i = 0; i < index; i++) {
+            if (exactWeights[i] <= 0) {
+                continue;
+            }
+            exactWeights[i] = exactWeights[i] / sum;
+        }
+        return calculateWeight(exactWeights);
+    }
+    
+    private double[] calculateWeight(final double[] exactWeights) {
+        double[] result = new double[exactWeights.length];
+        double randomRange = 0D;
+        for (int i = 0; i < result.length; i++) {
+            result[i] = randomRange + exactWeights[i];
+            randomRange += exactWeights[i];
+        }
+        return result;
+    }
+    
+    private double getWeightValue(final String readDataSourceName) {
+        Object weightObject = props.get(readDataSourceName);
+        double result = Double.parseDouble(weightObject.toString());
+        if (Double.isInfinite(result)) {
+            result = 10000.0D;
+        }
+        if (Double.isNaN(result)) {
+            result = 1.0D;
+        }
+        return result;
+    }
+    
+    @Override
+    public String getType() {
+        return "WEIGHT";
+    }
+}
diff --git 
a/infra/algorithm/load-balancer/type/weight/src/main/resources/META-INF/services/org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm
 
b/infra/algorithm/load-balancer/type/weight/src/main/resources/META-INF/services/org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm
new file mode 100644
index 00000000000..2e9e38c790e
--- /dev/null
+++ 
b/infra/algorithm/load-balancer/type/weight/src/main/resources/META-INF/services/org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm
@@ -0,0 +1,18 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one or more
+# contributor license agreements.  See the NOTICE file distributed with
+# this work for additional information regarding copyright ownership.
+# The ASF licenses this file to You 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.
+#
+
+org.apache.shardingsphere.infra.algorithm.load.balancer.weight.WeightLoadBalanceAlgorithm
diff --git 
a/infra/algorithm/load-balancer/type/weight/src/test/java/org/apache/shardingsphere/infra/algorithm/load/balancer/weight/WeightLoadBalanceAlgorithmTest.java
 
b/infra/algorithm/load-balancer/type/weight/src/test/java/org/apache/shardingsphere/infra/algorithm/load/balancer/weight/WeightLoadBalanceAlgorithmTest.java
new file mode 100644
index 00000000000..666052e8940
--- /dev/null
+++ 
b/infra/algorithm/load-balancer/type/weight/src/test/java/org/apache/shardingsphere/infra/algorithm/load/balancer/weight/WeightLoadBalanceAlgorithmTest.java
@@ -0,0 +1,65 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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 org.apache.shardingsphere.infra.algorithm.load.balancer.weight;
+
+import 
org.apache.shardingsphere.infra.algorithm.load.balancer.core.LoadBalanceAlgorithm;
+import org.apache.shardingsphere.infra.spi.type.typed.TypedSPILoader;
+import org.apache.shardingsphere.test.util.PropertiesBuilder;
+import org.apache.shardingsphere.test.util.PropertiesBuilder.Property;
+import org.junit.jupiter.api.Test;
+
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.List;
+
+import static org.hamcrest.CoreMatchers.is;
+import static org.hamcrest.CoreMatchers.notNullValue;
+import static org.hamcrest.MatcherAssert.assertThat;
+
+class WeightLoadBalanceAlgorithmTest {
+    
+    @Test
+    void assertGetSingleAvailableTarget() {
+        LoadBalanceAlgorithm loadBalanceAlgorithm = 
TypedSPILoader.getService(LoadBalanceAlgorithm.class, "WEIGHT", 
PropertiesBuilder.build(new Property("test_read_ds_1", "5")));
+        assertThat(loadBalanceAlgorithm.getAvailableTargetName("ds", 
Collections.singletonList("test_read_ds_1")), is("test_read_ds_1"));
+    }
+    
+    @Test
+    void assertGetMultipleAvailableTargets() {
+        LoadBalanceAlgorithm loadBalanceAlgorithm = 
TypedSPILoader.getService(LoadBalanceAlgorithm.class,
+                "WEIGHT", PropertiesBuilder.build(new 
Property("test_read_ds_1", "5"), new Property("test_read_ds_2", "5")));
+        String availableTargetName1 = "test_read_ds_1";
+        String availableTargetName2 = "test_read_ds_2";
+        List<String> availableTargetNames = 
Arrays.asList(availableTargetName1, availableTargetName2);
+        assertWeightLoadBalance(loadBalanceAlgorithm, availableTargetNames);
+    }
+    
+    private void assertWeightLoadBalance(final LoadBalanceAlgorithm 
loadBalanceAlgorithm, final List<String> availableTargetNames) {
+        assertThat(loadBalanceAlgorithm.getAvailableTargetName("ds", 
availableTargetNames), notNullValue());
+        assertThat(loadBalanceAlgorithm.getAvailableTargetName("ds", 
availableTargetNames), notNullValue());
+        assertThat(loadBalanceAlgorithm.getAvailableTargetName("ds", 
availableTargetNames), notNullValue());
+    }
+    
+    @Test
+    void assertGetAvailableTargetNameWhenTargetChanged() {
+        LoadBalanceAlgorithm loadBalanceAlgorithm = 
TypedSPILoader.getService(LoadBalanceAlgorithm.class,
+                "WEIGHT", PropertiesBuilder.build(new 
Property("test_read_ds_1", "5"), new Property("test_read_ds_2", "5")));
+        loadBalanceAlgorithm.getAvailableTargetName("ds", 
Arrays.asList("test_read_ds_1", "test_read_ds_1"));
+        assertThat(loadBalanceAlgorithm.getAvailableTargetName("ds", 
Collections.singletonList("test_read_ds_1")), is("test_read_ds_1"));
+    }
+}
diff --git a/infra/algorithm/pom.xml b/infra/algorithm/pom.xml
index 913ecdd8a03..c73625e760c 100644
--- a/infra/algorithm/pom.xml
+++ b/infra/algorithm/pom.xml
@@ -30,5 +30,6 @@
     <modules>
         <module>core</module>
         <module>key-generator</module>
+        <module>load-balancer</module>
     </modules>
 </project>
diff --git a/infra/distsql-handler/pom.xml b/infra/distsql-handler/pom.xml
index 0a3d472ae91..8c7efa7d661 100644
--- a/infra/distsql-handler/pom.xml
+++ b/infra/distsql-handler/pom.xml
@@ -34,7 +34,7 @@
         </dependency>
         <dependency>
             <groupId>org.apache.shardingsphere</groupId>
-            <artifactId>shardingsphere-infra-key-generator-core</artifactId>
+            
<artifactId>shardingsphere-infra-algorithm-key-generator-core</artifactId>
             <version>${project.version}</version>
         </dependency>
         <dependency>

Reply via email to