diff --git a/api/src/main/java/com/alibaba/nacos/api/naming/pojo/Instance.java b/api/src/main/java/com/alibaba/nacos/api/naming/pojo/Instance.java index b1e0e2e9d25..fc4c7baa542 100644 --- a/api/src/main/java/com/alibaba/nacos/api/naming/pojo/Instance.java +++ b/api/src/main/java/com/alibaba/nacos/api/naming/pojo/Instance.java @@ -19,6 +19,7 @@ import com.alibaba.nacos.api.common.Constants; import com.alibaba.nacos.api.naming.PreservedMetadataKeys; import com.alibaba.nacos.api.naming.utils.NamingUtils; +import com.alibaba.nacos.api.utils.StringUtils; import com.fasterxml.jackson.annotation.JsonInclude; import com.fasterxml.jackson.annotation.JsonInclude.Include; @@ -26,6 +27,7 @@ import java.util.HashMap; import java.util.Map; import java.util.Objects; +import java.util.concurrent.atomic.AtomicLong; /** * Instance. @@ -35,6 +37,11 @@ @JsonInclude(Include.NON_NULL) public class Instance implements Serializable { + /** + * Instance auto-increment index, used to generate instance ID + */ + private static final AtomicLong index = new AtomicLong(); + private static final long serialVersionUID = -742906310567291979L; /** @@ -264,4 +271,14 @@ private String getMetaDataByKeyWithDefault(final String key, final String defaul return getMetadata().get(key); } + /** + * Generate and set the instance id when the instance id is empty + */ + public void setInstanceIdIfNeeded() { + if (StringUtils.isEmpty(this.instanceId)) { + long curIndex = index.getAndIncrement(); + this.instanceId = ip + Constants.COLON + port + Constants.NAMING_INSTANCE_ID_SPLITTER + curIndex + + Constants.NAMING_INSTANCE_ID_SPLITTER + System.currentTimeMillis(); + } + } } diff --git a/api/src/main/java/com/alibaba/nacos/api/naming/utils/NamingUtils.java b/api/src/main/java/com/alibaba/nacos/api/naming/utils/NamingUtils.java index 7c88abc70ad..02934e3ec10 100644 --- a/api/src/main/java/com/alibaba/nacos/api/naming/utils/NamingUtils.java +++ b/api/src/main/java/com/alibaba/nacos/api/naming/utils/NamingUtils.java @@ -184,4 +184,24 @@ public static void batchCheckInstanceIsLegal(List instances) throws Na public static boolean isNumber(String str) { return !StringUtils.isEmpty(str) && NUMBER_PATTERN.matcher(str).matches(); } + + /** + * Set instanceId if needed + * + * @param instance Instance to be registered + */ + public static void setInstanceIdIfNeeded(Instance instance) { + instance.setInstanceIdIfNeeded(); + } + + /** + * Batch set instanceId if needed + * + * @param instances List of instances to be registered + */ + public static void batchSetInstanceIdIfNeeded(List instances) { + for (Instance instance : instances) { + instance.setInstanceIdIfNeeded(); + } + } } diff --git a/api/src/test/java/com/alibaba/nacos/api/naming/utils/NamingUtilsTest.java b/api/src/test/java/com/alibaba/nacos/api/naming/utils/NamingUtilsTest.java index 159616f28aa..67b86814869 100644 --- a/api/src/test/java/com/alibaba/nacos/api/naming/utils/NamingUtilsTest.java +++ b/api/src/test/java/com/alibaba/nacos/api/naming/utils/NamingUtilsTest.java @@ -30,6 +30,8 @@ import java.util.Map; import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertNotEquals; +import static org.junit.Assert.assertNotNull; import static org.junit.Assert.assertTrue; public class NamingUtilsTest { @@ -240,4 +242,56 @@ public void testIsNumber() { String str2 = "123456"; assertTrue(NamingUtils.isNumber(str2)); } + + @Test + public void testSetInstanceIdIfNeeded() { + Instance instance = new Instance(); + NamingUtils.setInstanceIdIfNeeded(instance); + assertNotNull(instance.getInstanceId()); + String customInsId = "customId_1"; + instance.setInstanceId(customInsId); + assertEquals(customInsId, instance.getInstanceId()); + + Instance instance1 = new Instance(); + Instance instance2 = new Instance(); + Instance instance3 = new Instance(); + + NamingUtils.setInstanceIdIfNeeded(instance1); + NamingUtils.setInstanceIdIfNeeded(instance2); + NamingUtils.setInstanceIdIfNeeded(instance3); + + assertNotNull(instance1.getInstanceId()); + assertNotNull(instance2.getInstanceId()); + assertNotNull(instance3.getInstanceId()); + + assertNotEquals(instance1.getInstanceId(), instance2.getInstanceId()); + assertNotEquals(instance1.getInstanceId(), instance3.getInstanceId()); + assertNotEquals(instance2.getInstanceId(), instance3.getInstanceId()); + } + + @Test + public void testBatchSetInstanceIdIfNeeded() { + List instances = new ArrayList<>(); + Instance instance1 = new Instance(); + String customInsId = "customId_1"; + instance1.setInstanceId(customInsId); + Instance instance2 = new Instance(); + Instance instance3 = new Instance(); + + instances.add(instance1); + instances.add(instance2); + instances.add(instance3); + + NamingUtils.batchSetInstanceIdIfNeeded(instances); + + assertNotNull(instance1.getInstanceId()); + assertNotNull(instance2.getInstanceId()); + assertNotNull(instance3.getInstanceId()); + + assertEquals(customInsId, instance1.getInstanceId()); + + assertNotEquals(instance1.getInstanceId(), instance2.getInstanceId()); + assertNotEquals(instance1.getInstanceId(), instance3.getInstanceId()); + assertNotEquals(instance2.getInstanceId(), instance3.getInstanceId()); + } } diff --git a/client/src/main/java/com/alibaba/nacos/client/naming/NacosNamingService.java b/client/src/main/java/com/alibaba/nacos/client/naming/NacosNamingService.java index a03e35559e3..7b95d18b403 100644 --- a/client/src/main/java/com/alibaba/nacos/client/naming/NacosNamingService.java +++ b/client/src/main/java/com/alibaba/nacos/client/naming/NacosNamingService.java @@ -140,6 +140,7 @@ public void registerInstance(String serviceName, Instance instance) throws Nacos @Override public void registerInstance(String serviceName, String groupName, Instance instance) throws NacosException { NamingUtils.checkInstanceIsLegal(instance); + NamingUtils.setInstanceIdIfNeeded(instance); clientProxy.registerService(serviceName, groupName, instance); } @@ -147,6 +148,7 @@ public void registerInstance(String serviceName, String groupName, Instance inst public void batchRegisterInstance(String serviceName, String groupName, List instances) throws NacosException { NamingUtils.batchCheckInstanceIsLegal(instances); + NamingUtils.batchSetInstanceIdIfNeeded(instances); clientProxy.batchRegisterService(serviceName, groupName, instances); }