You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@pulsar.apache.org by mm...@apache.org on 2021/06/02 21:17:45 UTC

[pulsar] branch master updated: Remove pulsar-client-admin-api dependency : pulsar-common (#10774)

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

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


The following commit(s) were added to refs/heads/master by this push:
     new 301a764  Remove pulsar-client-admin-api dependency : pulsar-common (#10774)
301a764 is described below

commit 301a76435ce918520f1b70b95b7ebed9bf1b08b5
Author: Matteo Merli <mm...@apache.org>
AuthorDate: Wed Jun 2 14:17:04 2021 -0700

    Remove pulsar-client-admin-api dependency : pulsar-common (#10774)
    
    * remove gson from admin api Topics.java
    
    * Bookies.java
    
    * Brokers.java
    
    * BrokerStats.java
    
    * fix PulsarAdminException
    
    * Clusters.java
    
    * Tenants.java
    
    * minor fix on ResourceGroups
    
    * Namespaces.java & OffloadPolicies
    
    * temp remove JsonProperty in OffloadPolicies
    
    * Topics & NonPersistentTopics
    
    * ResourceQuotas with MixIn class
    
    * Functions
    
    * Sources.java
    
    * Sinks.java
    
    * Schemas.java
    
    * resolve checkstyle
    
    * minor fix
    
    * Transactions.java
    
    * fix stylecheck
    
    * set ObjectMapper module
    
    * fix ci
    
    * fix PulsarAdminException
    
    * remove gson
    
    * remove swagger
    
    * merge master
    
    * remove swagger
    
    * remove io.swagger
    
    * remove commons-lang3
    
    * use Objects.requireNonNull
    
    * remove commons-lang3
    
    * fix interface mapping
    
    * fix ci
    
    * extract OffloadPoliciesInterface
    
    * extract FunctionStats interfaces
    
    * fix unit test
    
    * fix shaded class
    
    * add object mapper mixin tests
    
    * fix ci
    
    * fix admin exception ci error
    
    * UpdateOptions
    
    * AutoFailoverPolicyData
    
    * BrokerNamespaceIsolationData
    
    * ClusterData
    
    * FailureDomain
    
    * FunctionInstanceStats
    
    * NamespaceIsolationData
    
    * OffloadPolicies
    
    * TenantInfo
    
    * FunctionStats
    
    * fix stylecheck
    
    * Fixed interface
    
    * Fixed ClusterData equals method
    
    * Fixed merge issue
    
    * Fixed another merge issue
    
    * Fixed test issue after merge
    
    Co-authored-by: Rui Fu <fr...@gmail.com>
---
 .../pulsar/client/TlsProducerConsumerBase.java     |   8 +-
 .../apache/bookkeeper/mledger/LedgerOffloader.java |   4 +-
 .../bookkeeper/mledger/LedgerOffloaderFactory.java |  12 +-
 .../bookkeeper/mledger/impl/ManagedLedgerImpl.java |   2 +-
 .../mledger/impl/NullLedgerOffloader.java          |   4 +-
 .../mledger/impl/OffloadLedgerDeleteTest.java      |   4 +-
 .../mledger/impl/OffloadPrefixReadTest.java        |  18 +-
 .../bookkeeper/mledger/impl/OffloadPrefixTest.java |  16 +-
 .../apache/pulsar/broker/ServiceConfiguration.java |   7 +-
 .../authorization/AuthorizationProvider.java       |   5 +-
 .../broker/authorization/AuthorizationService.java |   4 +-
 .../authorization/PulsarAuthorizationProvider.java |   4 +-
 .../broker/cache/ConfigurationCacheService.java    |  41 ++--
 .../cache/ConfigurationMetadataCacheService.java   |  12 +-
 .../pulsar/broker/resources/ClusterResources.java  |  14 +-
 .../broker/resources/NamespaceResources.java       |   8 +-
 .../pulsar/broker/resources/TenantResources.java   |   6 +-
 .../apache/pulsar/PulsarClusterMetadataSetup.java  |  17 +-
 .../java/org/apache/pulsar/PulsarStandalone.java   |  19 +-
 .../org/apache/pulsar/broker/PulsarService.java    |  16 +-
 .../pulsar/broker/admin/impl/ClustersBase.java     |  66 ++---
 .../pulsar/broker/admin/impl/FunctionsBase.java    |  15 +-
 .../pulsar/broker/admin/impl/NamespacesBase.java   |  49 ++--
 .../broker/admin/impl/PersistentTopicsBase.java    |  27 +--
 .../apache/pulsar/broker/admin/impl/SinksBase.java |   4 +-
 .../pulsar/broker/admin/impl/SourcesBase.java      |   4 +-
 .../pulsar/broker/admin/impl/TenantsBase.java      |  10 +-
 .../apache/pulsar/broker/admin/v1/Namespaces.java  |   2 +-
 .../apache/pulsar/broker/admin/v2/Namespaces.java  |  10 +-
 .../pulsar/broker/admin/v2/PersistentTopics.java   |   4 +-
 .../loadbalance/impl/ModularLoadManagerImpl.java   |   4 +-
 .../pulsar/broker/namespace/NamespaceService.java  |  10 +-
 .../ResourceUsageTransportManager.java             |   4 +-
 .../pulsar/broker/service/BrokerService.java       |  17 +-
 .../nonpersistent/NonPersistentSubscription.java   |   2 +-
 .../service/persistent/PersistentSubscription.java |   5 +-
 .../broker/service/persistent/PersistentTopic.java |   2 +-
 .../pulsar/broker/web/PulsarWebResource.java       |  34 +--
 .../apache/pulsar/broker/SLAMonitoringTest.java    |   8 +-
 .../broker/admin/AdminApiDelayedDelivery.java      |   8 +-
 .../broker/admin/AdminApiGetLastMessageIdTest.java |   8 +-
 .../broker/admin/AdminApiMaxUnackedMessages.java   |   8 +-
 .../pulsar/broker/admin/AdminApiOffloadTest.java   |  33 +--
 .../broker/admin/AdminApiSchemaAutoUpdateTest.java |   8 +-
 .../pulsar/broker/admin/AdminApiSchemaTest.java    |   8 +-
 .../admin/AdminApiSchemaValidationEnforced.java    |   8 +-
 .../apache/pulsar/broker/admin/AdminApiTest.java   |  90 ++++---
 .../apache/pulsar/broker/admin/AdminApiTest2.java  | 114 ++++-----
 .../pulsar/broker/admin/AdminApiTlsAuthTest.java   |  36 +--
 .../org/apache/pulsar/broker/admin/AdminTest.java  |  58 ++---
 .../apache/pulsar/broker/admin/BookiesApiTest.java |   8 +-
 .../broker/admin/BrokerAdminClientTlsAuthTest.java |   8 +-
 .../broker/admin/IncrementPartitionsTest.java      |   9 +-
 .../apache/pulsar/broker/admin/NamespacesTest.java |  78 +++---
 .../pulsar/broker/admin/PersistentTopicsTest.java  |  14 +-
 .../pulsar/broker/admin/ResourceGroupsTest.java    |   8 +-
 .../pulsar/broker/admin/TopicMessageTTLTest.java   |  13 +-
 .../broker/admin/TopicPoliciesDisableTest.java     |   8 +-
 .../pulsar/broker/admin/TopicPoliciesTest.java     |   8 +-
 .../pulsar/broker/admin/v1/V1_AdminApiTest.java    |  63 ++---
 .../pulsar/broker/admin/v1/V1_AdminApiTest2.java   |  41 ++--
 .../broker/admin/v3/AdminApiTransactionTest.java   |   8 +-
 .../apache/pulsar/broker/auth/AuthLogsTest.java    |   8 +-
 .../pulsar/broker/auth/AuthorizationTest.java      |   8 +-
 .../broker/auth/MockAuthorizationProvider.java     |   4 +-
 .../broker/auth/MockedPulsarServiceBaseTest.java   |  14 +-
 .../AntiAffinityNamespaceGroupTest.java            |  22 +-
 .../loadbalance/LeaderElectionServiceTest.java     |   8 +-
 .../broker/loadbalance/LoadBalancerTest.java       |  16 +-
 .../loadbalance/ModularLoadManagerImplTest.java    |  16 +-
 .../loadbalance/SimpleLoadManagerImplTest.java     |   8 +-
 .../broker/lookup/http/HttpTopicLookupv2Test.java  |  10 +-
 .../OwnerShipCacheForCurrentServerTest.java        |   8 +-
 .../resourcegroup/ResourceGroupServiceTest.java    |   4 +-
 .../ResourceGroupUsageAggregationTest.java         |  10 +-
 .../ResourceUsageTransportManagerTest.java         |   4 +-
 .../broker/service/BacklogQuotaManagerTest.java    |   8 +-
 .../pulsar/broker/service/BkEnsemblesTestBase.java |   8 +-
 .../broker/service/BrokerBookieIsolationTest.java  |  16 +-
 .../pulsar/broker/service/BrokerServiceTest.java   |   7 +-
 .../pulsar/broker/service/BrokerTestBase.java      |   9 +-
 .../pulsar/broker/service/MaxMessageSizeTest.java  |   8 +-
 .../pulsar/broker/service/ReplicatorTest.java      |   4 +-
 .../pulsar/broker/service/ReplicatorTestBase.java  |  14 +-
 .../pulsar/broker/service/ResendRequestTest.java   |   8 +-
 .../SystemTopicBasedTopicPoliciesServiceTest.java  |   8 +-
 .../pulsar/broker/service/TopicOwnerTest.java      |   8 +-
 .../broker/stats/ManagedLedgerMetricsTest.java     |   4 +-
 .../broker/stats/TransactionMetricsTest.java       |   3 +-
 .../NamespaceEventsSystemTopicServiceTest.java     |   8 +-
 .../TopicTransactionBufferRecoverTest.java         |  10 +-
 .../TransactionClientReconnectTest.java            |  10 +-
 .../broker/transaction/TransactionConsumeTest.java |   8 +-
 .../broker/transaction/TransactionProduceTest.java |  10 +-
 .../buffer/TransactionBufferClientTest.java        |   8 +-
 .../buffer/TransactionLowWaterMarkTest.java        |  10 +-
 .../buffer/TransactionStablePositionTest.java      |  10 +-
 .../pendingack/PendingAckInMemoryDeleteTest.java   |  10 +-
 .../pendingack/PendingAckPersistentTest.java       |  10 +-
 .../apache/pulsar/broker/web/WebServiceTest.java   |  12 +-
 .../ZooKeeperSessionExpireRecoveryTest.java        |   8 +-
 .../api/AuthenticatedProducerConsumerTest.java     |  26 +-
 .../AuthenticationTlsHostnameVerificationTest.java |   8 +-
 .../api/AuthorizationProducerConsumerTest.java     |  19 +-
 .../pulsar/client/api/BrokerServiceLookupTest.java |  12 +-
 .../client/api/ClientDeduplicationFailureTest.java |   8 +-
 .../client/api/MessageDispatchThrottlingTest.java  |   4 +-
 .../pulsar/client/api/NonPersistentTopicTest.java  |  14 +-
 .../pulsar/client/api/ProducerConsumerBase.java    |  10 +-
 ...MultiListenersWithInternalListenerNameTest.java |  12 +-
 .../client/api/SimpleProducerConsumerStatTest.java |   4 +-
 .../org/apache/pulsar/client/api/TenantTest.java   |  10 +-
 .../pulsar/client/api/TlsProducerConsumerBase.java |   8 +-
 .../TokenAuthenticatedProducerConsumerTest.java    |   8 +-
 ...kenOauth2AuthenticatedProducerConsumerTest.java |  13 +-
 .../client/api/v1/V1_ProducerConsumerBase.java     |   8 +-
 .../client/impl/AdminApiKeyStoreTlsAuthTest.java   |  20 +-
 .../client/impl/BrokerClientIntegrationTest.java   |   4 +-
 .../client/impl/ConsumerConfigurationTest.java     |   8 +-
 ...eyStoreTlsProducerConsumerTestWithAuthTest.java |   8 +-
 ...toreTlsProducerConsumerTestWithoutAuthTest.java |   8 +-
 .../pulsar/client/impl/MessageParserTest.java      |   8 +-
 .../pulsar/client/impl/MultiTopicsReaderTest.java  |   8 +-
 .../client/impl/PatternTopicsConsumerImplTest.java |  16 +-
 .../PerMessageUnAcknowledgedRedeliveryTest.java    |   4 +-
 .../apache/pulsar/client/impl/RawReaderTest.java   |   8 +-
 .../org/apache/pulsar/client/impl/ReaderTest.java  |   8 +-
 .../pulsar/client/impl/SchemaDeleteTest.java       |   8 +-
 .../pulsar/client/impl/TopicsConsumerImplTest.java |  36 +--
 .../client/impl/TransactionEndToEndTest.java       |  12 +-
 .../pulsar/compaction/CompactedTopicTest.java      |   8 +-
 .../apache/pulsar/compaction/CompactionTest.java   |   8 +-
 .../apache/pulsar/compaction/CompactorTest.java    |   8 +-
 .../worker/PulsarFunctionE2ESecurityTest.java      |  10 +-
 .../worker/PulsarFunctionLocalRunTest.java         |   8 +-
 .../worker/PulsarFunctionPublishTest.java          |  16 +-
 .../functions/worker/PulsarFunctionTlsTest.java    |   4 +-
 .../worker/PulsarWorkerAssignmentTest.java         |   8 +-
 .../apache/pulsar/io/AbstractPulsarE2ETest.java    |  17 +-
 .../apache/pulsar/io/PulsarFunctionAdminTest.java  |   8 +-
 .../apache/pulsar/io/PulsarFunctionE2ETest.java    |  68 +++---
 .../apache/pulsar/io/PulsarFunctionTlsTest.java    |   4 +-
 .../pulsar/schema/PartitionedTopicSchemaTest.java  |  10 +-
 .../java/org/apache/pulsar/schema/SchemaTest.java  |   8 +-
 .../SchemaCompatibilityCheckTest.java              |   8 +-
 .../SchemaTypeCompatibilityCheckTest.java          |   8 +-
 .../websocket/proxy/ProxyAuthorizationTest.java    |   8 +-
 pulsar-client-admin-api/pom.xml                    |   9 +-
 .../apache/pulsar/client/admin/BrokerStats.java    |  18 +-
 .../org/apache/pulsar/client/admin/Clusters.java   |  12 +-
 .../org/apache/pulsar/client/admin/Functions.java  |   5 +-
 .../org/apache/pulsar/client/admin/ProxyStats.java |   7 +-
 .../pulsar/client/admin/PulsarAdminException.java  |  99 ++------
 .../java/org/apache/pulsar/client/admin/Sinks.java |   9 +-
 .../org/apache/pulsar/client/admin/Sources.java    |   3 +-
 .../org/apache/pulsar/client/admin/Topics.java     |   5 +-
 .../client/admin/utils/DefaultImplementation.java  |   1 +
 .../common/conf/InternalConfigurationData.java     |  14 +-
 .../apache/pulsar/common/conf/package-info.java    |   0
 .../common/functions/AuthenticationConfig.java     |   0
 .../pulsar/common/functions/ConsumerConfig.java    |   0
 .../pulsar/common/functions/CryptoConfig.java      |   0
 .../common/functions/ExternalPulsarConfig.java     |   0
 .../pulsar/common/functions/FunctionConfig.java    |   2 -
 .../pulsar/common/functions/FunctionState.java     |   2 -
 .../pulsar/common/functions/ProducerConfig.java    |   0
 .../apache/pulsar/common/functions/Resources.java  |   0
 .../pulsar/common/functions/UpdateOptions.java     |   8 +-
 .../pulsar/common/functions/WindowConfig.java      |   0
 .../apache/pulsar/common/functions/WorkerInfo.java |   0
 .../pulsar/common/functions}/package-info.java     |   4 +-
 .../apache/pulsar/common/io/BatchSourceConfig.java |   0
 .../pulsar/common/io/ConnectorDefinition.java      |   0
 .../org/apache/pulsar/common/io/SinkConfig.java    |   0
 .../org/apache/pulsar/common/io/SourceConfig.java  |   0
 .../org/apache/pulsar/common/io}/package-info.java |   4 +-
 .../apache/pulsar/common/naming/TopicDomain.java   |   0
 .../apache/pulsar/common/naming}/package-info.java |   4 +-
 .../common/partition/PartitionedTopicMetadata.java |   0
 .../pulsar/common/partition}/package-info.java     |   4 +-
 .../pulsar/common/policies/AutoFailoverPolicy.java |   0
 .../pulsar/common/policies/data/AuthAction.java    |   0
 .../pulsar/common/policies/data/AuthPolicies.java  |   8 +-
 .../policies/data/AutoFailoverPolicyData.java      |  14 +-
 .../policies/data/AutoFailoverPolicyType.java      |   6 -
 .../data/AutoSubscriptionCreationOverride.java     |   9 +-
 .../policies/data/AutoTopicCreationOverride.java   |   9 +-
 .../pulsar/common/policies/data/BacklogQuota.java  |  11 +-
 .../policies/data/BookieAffinityGroupData.java     |   8 +-
 .../pulsar/common/policies/data/BookieInfo.java    |   0
 .../common/policies/data/BookiesClusterInfo.java   |   3 +-
 .../policies/data/BookiesRackConfiguration.java    |   8 +-
 .../common/policies/data/BrokerAssignment.java     |   0
 .../pulsar/common/policies/data/BrokerInfo.java    |   2 +-
 .../data/BrokerNamespaceIsolationData.java         |  28 +--
 .../pulsar/common/policies/data/BrokerStatus.java  |   8 +-
 .../pulsar/common/policies/data/BundlesData.java   |   8 +-
 .../pulsar/common/policies/data/ClusterData.java   |  84 +++++++
 .../pulsar/common/policies/data/ConsumerStats.java |   4 +-
 .../policies/data/DelayedDeliveryPolicies.java     |   0
 .../pulsar/common/policies/data/DispatchRate.java  |  12 +-
 .../pulsar/common/policies/data/ErrorData.java     |   0
 .../common/policies/data/ExceptionInformation.java |   0
 .../pulsar/common/policies/data/FailureDomain.java |   8 +-
 .../policies/data/FunctionInstanceStats.java       |  11 +-
 .../policies/data/FunctionInstanceStatsData.java   |  22 +-
 .../data/FunctionInstanceStatsDataBase.java        |  31 ++-
 .../pulsar/common/policies/data/FunctionStats.java |  59 +++++
 .../common/policies/data/FunctionStatus.java       |   5 -
 .../policies/data/InactiveTopicDeleteMode.java     |   0
 .../policies/data/InactiveTopicPolicies.java       |   0
 .../policies/data/ManagedLedgerInternalStats.java  |   0
 .../policies/data/NamespaceIsolationData.java      |  30 +--
 .../policies/data/NamespaceOwnershipStatus.java    |   0
 .../policies/data/NonPersistentPublisherStats.java |   4 +-
 .../data/NonPersistentReplicatorStats.java         |   4 +-
 .../data/NonPersistentSubscriptionStats.java       |   4 +-
 .../policies/data/NonPersistentTopicStats.java     |  15 +-
 .../common/policies/data/OffloadPolicies.java      | 133 ++++++++++
 .../policies/data/OffloadedReadPriority.java       |  72 ++++++
 .../data/PartitionedTopicInternalStats.java        |   4 +-
 .../policies/data/PartitionedTopicStats.java       |   4 +-
 .../common/policies/data/PersistencePolicies.java  |   9 +-
 .../data/PersistentTopicInternalStats.java         |   0
 .../pulsar/common/policies/data/Policies.java      | 123 ++--------
 .../pulsar/common/policies/data/PublishRate.java   |   9 +-
 .../common/policies/data/PublisherStats.java       |   5 +-
 .../pulsar/common/policies/data/RawBookieInfo.java |   0
 .../common/policies/data/ReplicatorStats.java      |   4 +-
 .../pulsar/common/policies/data/ResourceGroup.java |   3 -
 .../pulsar/common/policies/data/ResourceQuota.java |  16 +-
 .../common/policies/data/RetentionPolicies.java    |   0
 .../SchemaAutoUpdateCompatibilityStrategy.java     |   0
 .../policies/data/SchemaCompatibilityStrategy.java |   0
 .../pulsar/common/policies/data/SinkStatus.java    |   5 -
 .../pulsar/common/policies/data/SourceStatus.java  |   5 -
 .../pulsar/common/policies/data/SubscribeRate.java |   9 +-
 .../common/policies/data/SubscriptionAuthMode.java |   0
 .../common/policies/data/SubscriptionStats.java    |  11 +-
 .../pulsar/common/policies/data/TenantInfo.java    |  13 +-
 .../pulsar/common/policies/data/TopicStats.java    |  15 +-
 .../pulsar/common/policies/data/TopicType.java     |   0
 .../policies/data/TransactionBufferStats.java      |   0
 .../data/TransactionCoordinatorInternalStats.java  |   2 +-
 .../policies/data/TransactionCoordinatorStats.java |   0
 .../data/TransactionCoordinatorStatus.java         |   4 +-
 .../policies/data/TransactionInBufferStats.java    |   0
 .../data/TransactionInPendingAckStats.java         |   2 -
 .../common/policies/data/TransactionLogStats.java  |   6 +-
 .../common/policies/data/TransactionMetadata.java  |   2 +-
 .../data/TransactionPendingAckInternalStats.java   |   2 +-
 .../policies/data/TransactionPendingAckStats.java  |   0
 .../policies/data/WorkerFunctionInstanceStats.java |   2 +-
 .../pulsar/common/policies/data}/package-info.java |   4 +-
 .../policies/impl/AutoFailoverPolicyFactory.java   |   4 +-
 .../common/policies/impl/MinAvailablePolicy.java   |  23 +-
 .../pulsar/common/policies/impl}/package-info.java |   4 +-
 .../pulsar/common/policies}/package-info.java      |   4 +-
 .../protocol/schema/IsCompatibilityResponse.java   |   0
 .../common/protocol/schema/PostSchemaPayload.java  |   0
 .../common/protocol/schema}/package-info.java      |   4 +-
 .../apache/pulsar/common/stats/AllocatorStats.java |   0
 .../org/apache/pulsar/common/stats/Metrics.java    |  18 +-
 .../apache/pulsar/common/stats}/package-info.java  |   4 +-
 .../management/core/common/PackageMetadata.java    |  18 --
 .../data/loadbalancer/LoadManagerReport.java       |   2 -
 .../data/loadbalancer/NamespaceBundleStats.java    |   3 +-
 .../policies/data/loadbalancer/ResourceUsage.java  |   0
 .../data/loadbalancer/ServiceLookupData.java       |   0
 .../policies/data/loadbalancer}/package-info.java  |   4 +-
 .../pulsar/client/admin/internal/BaseResource.java |  46 +++-
 .../client/admin/internal/BrokerStatsImpl.java     |  33 ++-
 .../pulsar/client/admin/internal/ClustersImpl.java |  70 +++---
 .../client/admin/internal/FunctionsImpl.java       |  31 ++-
 .../client/admin/internal/NamespacesImpl.java      |   8 +-
 .../client/admin/internal/ProxyStatsImpl.java      |  11 +-
 .../pulsar/client/admin/internal/SinksImpl.java    |  11 +-
 .../pulsar/client/admin/internal/SourcesImpl.java  |  11 +-
 .../pulsar/client/admin/internal/TenantsImpl.java  |   9 +-
 .../pulsar/client/admin/internal/TopicsImpl.java   |  18 +-
 .../client/admin/internal/SinksImplTest.java       |   8 +-
 .../apache/pulsar/admin/cli/CmdFunctionsTest.java  |  13 +-
 .../pulsar/admin/cli/PulsarAdminToolTest.java      |  36 +--
 .../pulsar/client/cli/PulsarClientToolTest.java    |   4 +-
 .../apache/pulsar/admin/cli/CmdBrokerStats.java    |   9 +-
 .../org/apache/pulsar/admin/cli/CmdClusters.java   |  12 +-
 .../org/apache/pulsar/admin/cli/CmdFunctions.java  |   4 +-
 .../admin/cli/CmdNamespaceIsolationPolicy.java     |  28 ++-
 .../org/apache/pulsar/admin/cli/CmdNamespaces.java |  19 +-
 .../pulsar/admin/cli/CmdPersistentTopics.java      |   2 +-
 .../org/apache/pulsar/admin/cli/CmdProxyStats.java |   6 +-
 .../java/org/apache/pulsar/admin/cli/CmdSinks.java |   4 +-
 .../org/apache/pulsar/admin/cli/CmdSources.java    |   4 +-
 .../org/apache/pulsar/admin/cli/CmdTenants.java    |   6 +-
 .../org/apache/pulsar/admin/cli/CmdTopics.java     |  11 +-
 .../apache/pulsar/admin/cli/TestCmdClusters.java   |   5 +-
 .../org/apache/pulsar/admin/cli/TestCmdSinks.java  |   6 +-
 .../apache/pulsar/admin/cli/TestCmdSources.java    |   8 +-
 pulsar-common/pom.xml                              |   6 +
 .../JsonIgnorePropertiesMixIn.java}                |  14 +-
 .../{UpdateOptions.java => UpdateOptionsImpl.java} |   6 +-
 ...cyData.java => AutoFailoverPolicyDataImpl.java} |  44 ++--
 ...PendingAckStats.java => BacklogQuotaMixIn.java} |   7 +-
 ....java => BrokerNamespaceIsolationDataImpl.java} |  26 +-
 .../{ClusterData.java => ClusterDataImpl.java}     | 125 +++-------
 .../{FailureDomain.java => FailureDomainImpl.java} |  23 +-
 .../data/FunctionInstanceStatsDataBaseImpl.java    |  57 +++++
 .../data/FunctionInstanceStatsDataImpl.java        |  50 ++++
 ...orStats.java => FunctionInstanceStatsImpl.java} |  19 +-
 .../{FunctionStats.java => FunctionStatsImpl.java} | 120 ++-------
 .../{ErrorData.java => FunctionStatusUtil.java}    |  15 +-
 .../pulsar/common/policies/data/LocalPolicies.java |   2 +-
 ...onData.java => NamespaceIsolationDataImpl.java} |  49 ++--
 ...floadPolicies.java => OffloadPoliciesImpl.java} | 124 +++-------
 .../pulsar/common/policies/data/PoliciesUtil.java  |  71 ++++++
 ...ionInformation.java => ResourceQuotaMixIn.java} |  12 +-
 .../data/{ErrorData.java => SinkStatusUtil.java}   |  15 +-
 .../data/{ErrorData.java => SourceStatusUtil.java} |  15 +-
 .../data/{TenantInfo.java => TenantInfoImpl.java}  |  18 +-
 .../pulsar/common/policies/data/TopicPolicies.java |   2 +-
 .../policies/impl/NamespaceIsolationPolicies.java  |  18 +-
 .../impl/NamespaceIsolationPolicyImpl.java         |   4 +-
 .../MetricsMixIn.java}                             |  15 +-
 .../pulsar/common/util/ObjectMapperFactory.java    |  80 ++++++
 .../policies/data/AutoFailoverPolicyDataTest.java  |   4 +-
 .../common/policies/data/ClusterDataTest.java      |  34 +--
 .../common/policies/data/LocalPolicesTest.java     |   2 +-
 .../policies/data/NamespaceIsolationDataTest.java  |  10 +-
 .../common/policies/data/OffloadPoliciesTest.java  |  29 ++-
 .../common/policies/data/PoliciesDataTest.java     |   8 +-
 .../impl/AutoFailoverPolicyFactoryTest.java        |   7 +-
 .../impl/NamespaceIsolationPoliciesTest.java       |  18 +-
 .../impl/NamespaceIsolationPolicyImplTest.java     |  10 +-
 .../common/util/ObjectMapperFactoryTest.java       |  77 ++++++
 .../discovery/service/BrokerDiscoveryProvider.java |   4 +-
 .../functions/worker/FunctionRuntimeManager.java   |  34 +--
 .../functions/worker/PulsarWorkerService.java      |  10 +-
 .../pulsar/functions/worker/WorkerUtils.java       |  14 +-
 .../functions/worker/rest/api/ComponentImpl.java   |  39 ++-
 .../functions/worker/rest/api/FunctionsImpl.java   |   4 +-
 .../functions/worker/rest/api/SinksImpl.java       |   4 +-
 .../functions/worker/rest/api/SourcesImpl.java     |   4 +-
 .../functions/worker/rest/api/WorkerImpl.java      |   6 +-
 .../worker/rest/api/v3/FunctionsApiV3Resource.java |  19 +-
 .../worker/rest/api/v3/SinksApiV3Resource.java     |   4 +-
 .../worker/rest/api/v3/SourcesApiV3Resource.java   |   4 +-
 .../functions/worker/service/api/Component.java    |  32 +--
 .../functions/worker/service/api/Functions.java    |   4 +-
 .../pulsar/functions/worker/service/api/Sinks.java |   4 +-
 .../functions/worker/service/api/Sources.java      |   4 +-
 .../worker/rest/api/FunctionsImplTest.java         |  21 +-
 .../rest/api/v2/FunctionApiV2ResourceTest.java     |   6 +-
 .../rest/api/v3/FunctionApiV3ResourceTest.java     |   6 +-
 .../worker/rest/api/v3/SinkApiV3ResourceTest.java  |   6 +-
 .../rest/api/v3/SourceApiV3ResourceTest.java       |   6 +-
 .../core/common/PackageMetadataUtil.java           |  38 +--
 .../core/impl/PackagesManagementImpl.java          |   7 +-
 .../core/common/PackageMetadataSerdeTest.java      |   6 +-
 .../core/impl/PackagesManagementImplTest.java      |   5 +-
 .../proxy/server/BrokerDiscoveryProvider.java      |   4 +-
 .../proxy/server/AuthedAdminProxyHandlerTest.java  |  12 +-
 .../ProxyAuthenticatedProducerConsumerTest.java    |   8 +-
 .../proxy/server/ProxyKeyStoreTlsTestWithAuth.java |   4 +-
 .../server/ProxyKeyStoreTlsTestWithoutAuth.java    |   4 +-
 .../pulsar/proxy/server/ProxyParserTest.java       |   4 +-
 .../org/apache/pulsar/proxy/server/ProxyTest.java  |   4 +-
 .../apache/pulsar/proxy/server/ProxyTlsTest.java   |   4 +-
 .../server/ProxyWithAuthorizationNegTest.java      |   8 +-
 .../proxy/server/ProxyWithAuthorizationTest.java   |  20 +-
 .../server/ProxyWithJwtAuthorizationTest.java      |  16 +-
 .../server/ProxyWithoutServiceDiscoveryTest.java   |   8 +-
 .../SuperUserAuthedAdminProxyHandlerTest.java      |  14 +-
 .../pulsar/sql/presto/PulsarConnectorCache.java    |   8 +-
 .../pulsar/sql/presto/PulsarConnectorConfig.java   |   6 +-
 .../pulsar/sql/presto/PulsarRecordCursor.java      |   4 +-
 .../org/apache/pulsar/sql/presto/PulsarSplit.java  |   8 +-
 .../pulsar/sql/presto/PulsarSplitManager.java      |  10 +-
 .../pulsar/sql/presto/TestCacheSizeAllocator.java  |   8 +-
 .../pulsar/sql/presto/TestPulsarConnector.java     |  12 +-
 .../sql/presto/TestPulsarConnectorConfig.java      |   4 +-
 .../pulsar/sql/presto/TestPulsarMetadata.java      |   3 +-
 .../pulsar/sql/presto/TestPulsarSplitManager.java  |   7 +-
 .../pulsar/testclient/PerformanceProducerTest.java |   8 +-
 .../apache/pulsar/websocket/WebSocketService.java  |  18 +-
 .../token/PulsarTokenAuthenticationBaseSuite.java  |  10 +-
 .../cli/ClusterMetadataTearDownTest.java           |   6 +-
 .../integration/functions/PulsarFunctionsTest.java | 270 ++++++++++-----------
 .../functions/java/PulsarFunctionsJavaTest.java    |   3 +-
 .../integration/io/sinks/PulsarIOSinkRunner.java   |   5 +-
 .../io/sources/AvroKafkaSourceTest.java            |   5 +-
 .../io/sources/PulsarIOSourceRunner.java           |   5 +-
 .../debezium/PulsarDebeziumSourcesTest.java        |   4 +-
 .../pulsar/tests/integration/proxy/TestProxy.java  |   6 +-
 .../integration/proxy/TestProxyWithWebSocket.java  |   5 +-
 .../integration/SimpleProducerConsumerTest.java    |   6 +-
 .../integration/SimpleProducerConsumerTest.java    |   7 +-
 .../integration/SimpleProducerConsumerTest.java    |   6 +-
 .../FileSystemLedgerOffloaderFactory.java          |   7 +-
 .../impl/FileSystemManagedLedgerOffloader.java     |  12 +-
 .../offload/filesystem/FileStoreTestBase.java      |   4 +-
 .../jcloud/JCloudLedgerOffloaderFactory.java       |   6 +-
 .../impl/BlobStoreManagedLedgerOffloader.java      |   6 +-
 402 files changed, 2981 insertions(+), 2666 deletions(-)

diff --git a/bouncy-castle/bcfips-include-test/src/test/java/org/apache/pulsar/client/TlsProducerConsumerBase.java b/bouncy-castle/bcfips-include-test/src/test/java/org/apache/pulsar/client/TlsProducerConsumerBase.java
index 756079f..c73d4a0 100644
--- a/bouncy-castle/bcfips-include-test/src/test/java/org/apache/pulsar/client/TlsProducerConsumerBase.java
+++ b/bouncy-castle/bcfips-include-test/src/test/java/org/apache/pulsar/client/TlsProducerConsumerBase.java
@@ -31,8 +31,8 @@ import org.apache.pulsar.client.api.ClientBuilder;
 import org.apache.pulsar.client.api.ProducerConsumerBase;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.impl.auth.AuthenticationTls;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 
@@ -104,10 +104,10 @@ public class TlsProducerConsumerBase extends ProducerConsumerBase {
         admin = spy(PulsarAdmin.builder().serviceHttpUrl(brokerUrlTls.toString())
                 .tlsTrustCertsFilePath(TLS_TRUST_CERT_FILE_PATH).allowTlsInsecureConnection(false)
                 .authentication(AuthenticationTls.class.getName(), authParams).build());
-        admin.clusters().createCluster(clusterName, new ClusterData(brokerUrl.toString(), brokerUrlTls.toString(),
+        admin.clusters().createCluster(clusterName, new ClusterDataImpl(brokerUrl.toString(), brokerUrlTls.toString(),
                 pulsar.getBrokerServiceUrl(), pulsar.getBrokerServiceUrlTls()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
         admin.namespaces().createNamespace("my-property/my-ns");
     }
 }
diff --git a/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/LedgerOffloader.java b/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/LedgerOffloader.java
index 32fbc9c..ead9db7 100644
--- a/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/LedgerOffloader.java
+++ b/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/LedgerOffloader.java
@@ -27,7 +27,7 @@ import org.apache.bookkeeper.client.api.ReadHandle;
 import org.apache.bookkeeper.common.annotation.InterfaceAudience;
 import org.apache.bookkeeper.common.annotation.InterfaceStability;
 import org.apache.bookkeeper.mledger.proto.MLDataFormats;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 
 /**
  * Interface for offloading ledgers to long-term storage.
@@ -211,7 +211,7 @@ public interface LedgerOffloader {
      *
      * @return offload policies
      */
-    OffloadPolicies getOffloadPolicies();
+    OffloadPoliciesImpl getOffloadPolicies();
 
     /**
      * Close the resources if necessary
diff --git a/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/LedgerOffloaderFactory.java b/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/LedgerOffloaderFactory.java
index dd0e6c9..c854996 100644
--- a/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/LedgerOffloaderFactory.java
+++ b/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/LedgerOffloaderFactory.java
@@ -23,7 +23,7 @@ import java.util.Map;
 import org.apache.bookkeeper.common.annotation.InterfaceAudience.LimitedPrivate;
 import org.apache.bookkeeper.common.annotation.InterfaceStability.Evolving;
 import org.apache.bookkeeper.common.util.OrderedScheduler;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 import org.apache.pulsar.common.protocol.schema.SchemaStorage;
 
 /**
@@ -50,7 +50,7 @@ public interface LedgerOffloaderFactory<T extends LedgerOffloader> {
      * @return the offloader instance
      * @throws IOException when fail to create an offloader
      */
-    T create(OffloadPolicies offloadPolicies,
+    T create(OffloadPoliciesImpl offloadPolicies,
              Map<String, String> userMetadata,
              OrderedScheduler scheduler)
         throws IOException;
@@ -65,10 +65,10 @@ public interface LedgerOffloaderFactory<T extends LedgerOffloader> {
      * @return the offloader instance
      * @throws IOException when fail to create an offloader
      */
-    default T create(OffloadPolicies offloadPolicies,
-             Map<String, String> userMetadata,
-             SchemaStorage schemaStorage,
-             OrderedScheduler scheduler)
+    default T create(OffloadPoliciesImpl offloadPolicies,
+                     Map<String, String> userMetadata,
+                     SchemaStorage schemaStorage,
+                     OrderedScheduler scheduler)
             throws IOException {
         return create(offloadPolicies, userMetadata, scheduler);
     }
diff --git a/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/impl/ManagedLedgerImpl.java b/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/impl/ManagedLedgerImpl.java
index 9c6c21f..83f82ee 100644
--- a/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/impl/ManagedLedgerImpl.java
+++ b/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/impl/ManagedLedgerImpl.java
@@ -128,7 +128,7 @@ import org.apache.commons.lang3.tuple.Pair;
 import org.apache.pulsar.common.api.proto.CommandSubscribe.InitialPosition;
 import org.apache.pulsar.common.policies.data.EnsemblePlacementPolicyConfig;
 import org.apache.pulsar.common.policies.data.ManagedLedgerInternalStats;
-import org.apache.pulsar.common.policies.data.OffloadPolicies.OffloadedReadPriority;
+import org.apache.pulsar.common.policies.data.OffloadedReadPriority;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
 import org.apache.pulsar.common.util.DateFormatter;
 import org.apache.pulsar.common.util.FutureUtil;
diff --git a/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/impl/NullLedgerOffloader.java b/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/impl/NullLedgerOffloader.java
index aa3aae7..b9a4df5 100644
--- a/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/impl/NullLedgerOffloader.java
+++ b/managed-ledger/src/main/java/org/apache/bookkeeper/mledger/impl/NullLedgerOffloader.java
@@ -24,7 +24,7 @@ import java.util.concurrent.CompletableFuture;
 
 import org.apache.bookkeeper.client.api.ReadHandle;
 import org.apache.bookkeeper.mledger.LedgerOffloader;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 
 /**
  * Null implementation that throws an error on any invokation.
@@ -63,7 +63,7 @@ public class NullLedgerOffloader implements LedgerOffloader {
     }
 
     @Override
-    public OffloadPolicies getOffloadPolicies() {
+    public OffloadPoliciesImpl getOffloadPolicies() {
         return null;
     }
 
diff --git a/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadLedgerDeleteTest.java b/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadLedgerDeleteTest.java
index 736cd8b..258987c 100644
--- a/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadLedgerDeleteTest.java
+++ b/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadLedgerDeleteTest.java
@@ -33,7 +33,7 @@ import org.apache.bookkeeper.mledger.proto.MLDataFormats;
 import org.apache.bookkeeper.mledger.util.MockClock;
 import org.apache.bookkeeper.test.MockedBookKeeperTestCase;
 
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 import org.mockito.Mockito;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -210,7 +210,7 @@ public class OffloadLedgerDeleteTest extends MockedBookKeeperTestCase {
 
     @Test
     public void isOffloadedNeedsDeleteTest() throws Exception {
-        OffloadPolicies offloadPolicies = new OffloadPolicies();
+        OffloadPoliciesImpl offloadPolicies = new OffloadPoliciesImpl();
         LedgerOffloader ledgerOffloader = Mockito.mock(LedgerOffloader.class);
         Mockito.when(ledgerOffloader.getOffloadPolicies()).thenReturn(offloadPolicies);
 
diff --git a/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadPrefixReadTest.java b/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadPrefixReadTest.java
index cc23f74..426a00d 100644
--- a/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadPrefixReadTest.java
+++ b/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadPrefixReadTest.java
@@ -58,8 +58,8 @@ import org.apache.bookkeeper.mledger.proto.MLDataFormats.ManagedLedgerInfo.Ledge
 import org.apache.bookkeeper.mledger.util.MockClock;
 import org.apache.bookkeeper.net.BookieId;
 import org.apache.bookkeeper.test.MockedBookKeeperTestCase;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
-import org.apache.pulsar.common.policies.data.OffloadPolicies.OffloadedReadPriority;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
+import org.apache.pulsar.common.policies.data.OffloadedReadPriority;
 import org.testng.Assert;
 import org.testng.annotations.Test;
 
@@ -202,14 +202,14 @@ public class OffloadPrefixReadTest extends MockedBookKeeperTestCase {
         ConcurrentHashMap<UUID, ReadHandle> offloads = new ConcurrentHashMap<UUID, ReadHandle>();
 
 
-        OffloadPolicies offloadPolicies = OffloadPolicies.create("S3", "", "", "",
+        OffloadPoliciesImpl offloadPolicies = OffloadPoliciesImpl.create("S3", "", "", "",
                 null, null,
                 null, null,
-                OffloadPolicies.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
-                OffloadPolicies.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
-                OffloadPolicies.DEFAULT_OFFLOAD_THRESHOLD_IN_BYTES,
-                OffloadPolicies.DEFAULT_OFFLOAD_DELETION_LAG_IN_MILLIS,
-                OffloadPolicies.DEFAULT_OFFLOADED_READ_PRIORITY);
+                OffloadPoliciesImpl.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_OFFLOAD_THRESHOLD_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_OFFLOAD_DELETION_LAG_IN_MILLIS,
+                OffloadPoliciesImpl.DEFAULT_OFFLOADED_READ_PRIORITY);
 
 
         @Override
@@ -246,7 +246,7 @@ public class OffloadPrefixReadTest extends MockedBookKeeperTestCase {
         };
 
         @Override
-        public OffloadPolicies getOffloadPolicies() {
+        public OffloadPoliciesImpl getOffloadPolicies() {
             return offloadPolicies;
         }
 
diff --git a/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadPrefixTest.java b/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadPrefixTest.java
index ffbc2ae..a7092e4 100644
--- a/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadPrefixTest.java
+++ b/managed-ledger/src/test/java/org/apache/bookkeeper/mledger/impl/OffloadPrefixTest.java
@@ -48,7 +48,7 @@ import org.apache.bookkeeper.mledger.proto.MLDataFormats;
 import org.apache.bookkeeper.mledger.proto.MLDataFormats.ManagedLedgerInfo.LedgerInfo;
 import org.apache.bookkeeper.test.MockedBookKeeperTestCase;
 import org.apache.commons.lang3.tuple.Pair;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.testng.annotations.Test;
@@ -991,14 +991,14 @@ public class OffloadPrefixTest extends MockedBookKeeperTestCase {
             return deletes.keySet();
         }
 
-        OffloadPolicies offloadPolicies = OffloadPolicies.create("S3", "", "", "",
+        OffloadPoliciesImpl offloadPolicies = OffloadPoliciesImpl.create("S3", "", "", "",
                 null, null,
                 null, null,
-                OffloadPolicies.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
-                OffloadPolicies.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
-                OffloadPolicies.DEFAULT_OFFLOAD_THRESHOLD_IN_BYTES,
-                OffloadPolicies.DEFAULT_OFFLOAD_DELETION_LAG_IN_MILLIS,
-                OffloadPolicies.DEFAULT_OFFLOADED_READ_PRIORITY);
+                OffloadPoliciesImpl.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_OFFLOAD_THRESHOLD_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_OFFLOAD_DELETION_LAG_IN_MILLIS,
+                OffloadPoliciesImpl.DEFAULT_OFFLOADED_READ_PRIORITY);
 
         @Override
         public String getOffloadDriverName() {
@@ -1044,7 +1044,7 @@ public class OffloadPrefixTest extends MockedBookKeeperTestCase {
         };
 
         @Override
-        public OffloadPolicies getOffloadPolicies() {
+        public OffloadPoliciesImpl getOffloadPolicies() {
             return offloadPolicies;
         }
 
diff --git a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/ServiceConfiguration.java b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/ServiceConfiguration.java
index fdc5412..2d87e57 100644
--- a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/ServiceConfiguration.java
+++ b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/ServiceConfiguration.java
@@ -25,7 +25,6 @@ import io.netty.util.internal.PlatformDependent;
 import java.util.ArrayList;
 import java.util.HashSet;
 import java.util.List;
-import java.util.Map;
 import java.util.Optional;
 import java.util.Properties;
 import java.util.Set;
@@ -34,18 +33,16 @@ import lombok.Getter;
 import lombok.Setter;
 import org.apache.bookkeeper.client.api.DigestType;
 import org.apache.pulsar.broker.authorization.PulsarAuthorizationProvider;
-import org.apache.pulsar.broker.validator.MultipleListenerValidator;
 import org.apache.pulsar.common.configuration.Category;
 import org.apache.pulsar.common.configuration.FieldContext;
 import org.apache.pulsar.common.configuration.PulsarConfiguration;
 import org.apache.pulsar.common.nar.NarClassLoader;
 import org.apache.pulsar.common.policies.data.BacklogQuota;
 import org.apache.pulsar.common.policies.data.InactiveTopicDeleteMode;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadedReadPriority;
 import org.apache.pulsar.common.policies.data.TopicType;
 import org.apache.pulsar.common.protocol.Commands;
 import org.apache.pulsar.common.sasl.SaslConstants;
-import org.apache.pulsar.policies.data.loadbalancer.AdvertisedListener;
 
 /**
  * Pulsar service configuration object.
@@ -1581,7 +1578,7 @@ public class ServiceConfiguration implements PulsarConfiguration {
 
     @FieldContext(category = CATEGORY_STORAGE_ML,
             doc = "Read priority when ledgers exists in both bookkeeper and the second layer storage.")
-    private String managedLedgerDataReadPriority = OffloadPolicies.OffloadedReadPriority.TIERED_STORAGE_FIRST
+    private String managedLedgerDataReadPriority = OffloadedReadPriority.TIERED_STORAGE_FIRST
             .getValue();
 
     /*** --- Load balancer --- ****/
diff --git a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/AuthorizationProvider.java b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/AuthorizationProvider.java
index f8e73c3..cfb191b 100644
--- a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/AuthorizationProvider.java
+++ b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/AuthorizationProvider.java
@@ -33,11 +33,10 @@ import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.policies.data.AuthAction;
 import org.apache.pulsar.common.policies.data.PolicyName;
 import org.apache.pulsar.common.policies.data.PolicyOperation;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.NamespaceOperation;
 import org.apache.pulsar.common.policies.data.TenantOperation;
 import org.apache.pulsar.common.policies.data.TopicOperation;
-import org.apache.pulsar.common.policies.data.TopicPolicies;
 import org.apache.pulsar.common.util.FutureUtil;
 import org.apache.pulsar.common.util.RestException;
 
@@ -79,7 +78,7 @@ public interface AuthorizationProvider extends Closeable {
      * @return a CompletableFuture containing a boolean in which true means the role is an admin user
      * and false if it is not
      */
-    default CompletableFuture<Boolean> isTenantAdmin(String tenant, String role, TenantInfo tenantInfo,
+    default CompletableFuture<Boolean> isTenantAdmin(String tenant, String role, TenantInfoImpl tenantInfo,
                                                      AuthenticationDataSource authenticationData) {
         return CompletableFuture.completedFuture(role != null && tenantInfo.getAdminRoles() != null && tenantInfo.getAdminRoles().contains(role) ? true : false);
     }
diff --git a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/AuthorizationService.java b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/AuthorizationService.java
index 403542f..83a9944 100644
--- a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/AuthorizationService.java
+++ b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/AuthorizationService.java
@@ -29,7 +29,7 @@ import org.apache.pulsar.common.policies.data.AuthAction;
 import org.apache.pulsar.common.policies.data.NamespaceOperation;
 import org.apache.pulsar.common.policies.data.PolicyName;
 import org.apache.pulsar.common.policies.data.PolicyOperation;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TenantOperation;
 import org.apache.pulsar.common.policies.data.TopicOperation;
 import org.apache.pulsar.common.util.FutureUtil;
@@ -80,7 +80,7 @@ public class AuthorizationService {
         return FutureUtil.failedFuture(new IllegalStateException("No authorization provider configured"));
     }
 
-    public CompletableFuture<Boolean> isTenantAdmin(String tenant, String role, TenantInfo tenantInfo,
+    public CompletableFuture<Boolean> isTenantAdmin(String tenant, String role, TenantInfoImpl tenantInfo,
                                                     AuthenticationDataSource authenticationData) {
         if (provider != null) {
             return provider.isTenantAdmin(tenant, role, tenantInfo, authenticationData);
diff --git a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/PulsarAuthorizationProvider.java b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/PulsarAuthorizationProvider.java
index 05c9fb2..ecd17f8 100644
--- a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/PulsarAuthorizationProvider.java
+++ b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/authorization/PulsarAuthorizationProvider.java
@@ -39,7 +39,7 @@ import org.apache.pulsar.common.policies.data.NamespaceOperation;
 import org.apache.pulsar.common.policies.data.Policies;
 import org.apache.pulsar.common.policies.data.PolicyName;
 import org.apache.pulsar.common.policies.data.PolicyOperation;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TenantOperation;
 import org.apache.pulsar.common.policies.data.TopicOperation;
 import org.apache.pulsar.common.util.FutureUtil;
@@ -634,7 +634,7 @@ public class PulsarAuthorizationProvider implements AuthorizationProvider {
                         return CompletableFuture.completedFuture(true);
                     } else {
                         try {
-                            TenantInfo tenantInfo = pulsarResources.getTenantResources()
+                            TenantInfoImpl tenantInfo = pulsarResources.getTenantResources()
                                     .get(path(POLICIES, tenantName))
                                     .orElseThrow(() -> new RestException(Response.Status.NOT_FOUND, "Tenant does not exist"));
                             return isTenantAdmin(tenantName, role, tenantInfo, authData);
diff --git a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/cache/ConfigurationCacheService.java b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/cache/ConfigurationCacheService.java
index fa29bdf..03069a1 100644
--- a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/cache/ConfigurationCacheService.java
+++ b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/cache/ConfigurationCacheService.java
@@ -24,12 +24,11 @@ import org.apache.bookkeeper.util.ZkUtils;
 import static org.apache.commons.lang3.StringUtils.isNotBlank;
 import org.apache.pulsar.broker.PulsarServerException;
 import org.apache.pulsar.broker.resources.PulsarResources;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.FailureDomain;
-import org.apache.pulsar.common.policies.data.NamespaceIsolationData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.FailureDomainImpl;
+import org.apache.pulsar.common.policies.data.NamespaceIsolationDataImpl;
 import org.apache.pulsar.common.policies.data.Policies;
-import org.apache.pulsar.common.policies.data.ResourceGroup;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.impl.NamespaceIsolationPolicies;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.zookeeper.ZooKeeperCache;
@@ -55,13 +54,13 @@ public class ConfigurationCacheService {
     private static final Logger LOG = LoggerFactory.getLogger(ConfigurationCacheService.class);
 
     private final ZooKeeperCache cache;
-    private ZooKeeperDataCache<TenantInfo> propertiesCache;
+    private ZooKeeperDataCache<TenantInfoImpl> propertiesCache;
     private ZooKeeperDataCache<Policies> policiesCache;
-    private ZooKeeperDataCache<ClusterData> clustersCache;
+    private ZooKeeperDataCache<ClusterDataImpl> clustersCache;
     private ZooKeeperChildrenCache clustersListCache;
     private ZooKeeperChildrenCache failureDomainListCache;
     private ZooKeeperDataCache<NamespaceIsolationPolicies> namespaceIsolationPoliciesCache;
-    private ZooKeeperDataCache<FailureDomain> failureDomainCache;
+    private ZooKeeperDataCache<FailureDomainImpl> failureDomainCache;
     @Getter
     private PulsarResources pulsarResources;
 
@@ -89,10 +88,10 @@ public class ConfigurationCacheService {
 
         initZK();
 
-        this.propertiesCache = new ZooKeeperDataCache<TenantInfo>(cache) {
+        this.propertiesCache = new ZooKeeperDataCache<TenantInfoImpl>(cache) {
             @Override
-            public TenantInfo deserialize(String path, byte[] content) throws Exception {
-                return ObjectMapperFactory.getThreadLocal().readValue(content, TenantInfo.class);
+            public TenantInfoImpl deserialize(String path, byte[] content) throws Exception {
+                return ObjectMapperFactory.getThreadLocal().readValue(content, TenantInfoImpl.class);
             }
         };
 
@@ -103,10 +102,10 @@ public class ConfigurationCacheService {
             }
         };
 
-        this.clustersCache = new ZooKeeperDataCache<ClusterData>(cache) {
+        this.clustersCache = new ZooKeeperDataCache<ClusterDataImpl>(cache) {
             @Override
-            public ClusterData deserialize(String path, byte[] content) throws Exception {
-                return ObjectMapperFactory.getThreadLocal().readValue(content, ClusterData.class);
+            public ClusterDataImpl deserialize(String path, byte[] content) throws Exception {
+                return ObjectMapperFactory.getThreadLocal().readValue(content, ClusterDataImpl.class);
             }
         };
 
@@ -122,15 +121,15 @@ public class ConfigurationCacheService {
             @SuppressWarnings("unchecked")
             public NamespaceIsolationPolicies deserialize(String path, byte[] content) throws Exception {
                 return new NamespaceIsolationPolicies(ObjectMapperFactory
-                        .getThreadLocal().readValue(content, new TypeReference<Map<String, NamespaceIsolationData>>() {
+                        .getThreadLocal().readValue(content, new TypeReference<Map<String, NamespaceIsolationDataImpl>>() {
                         }));
             }
         };
 
-        this.failureDomainCache = new ZooKeeperDataCache<FailureDomain>(cache) {
+        this.failureDomainCache = new ZooKeeperDataCache<FailureDomainImpl>(cache) {
             @Override
-            public FailureDomain deserialize(String path, byte[] content) throws Exception {
-                return ObjectMapperFactory.getThreadLocal().readValue(content, FailureDomain.class);
+            public FailureDomainImpl deserialize(String path, byte[] content) throws Exception {
+                return ObjectMapperFactory.getThreadLocal().readValue(content, FailureDomainImpl.class);
             }
         };
     }
@@ -183,7 +182,7 @@ public class ConfigurationCacheService {
         return cache;
     }
 
-    public ZooKeeperDataCache<TenantInfo> propertiesCache() {
+    public ZooKeeperDataCache<TenantInfoImpl> propertiesCache() {
         return this.propertiesCache;
     }
 
@@ -191,7 +190,7 @@ public class ConfigurationCacheService {
         return this.policiesCache;
     }
 
-    public ZooKeeperDataCache<ClusterData> clustersCache() {
+    public ZooKeeperDataCache<ClusterDataImpl> clustersCache() {
         return this.clustersCache;
     }
 
@@ -211,7 +210,7 @@ public class ConfigurationCacheService {
         return this.namespaceIsolationPoliciesCache;
     }
 
-    public ZooKeeperDataCache<FailureDomain> failureDomainCache() {
+    public ZooKeeperDataCache<FailureDomainImpl> failureDomainCache() {
         return this.failureDomainCache;
     }
 }
diff --git a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/cache/ConfigurationMetadataCacheService.java b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/cache/ConfigurationMetadataCacheService.java
index 083a7d7..3a91e5b 100644
--- a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/cache/ConfigurationMetadataCacheService.java
+++ b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/cache/ConfigurationMetadataCacheService.java
@@ -20,10 +20,10 @@ package org.apache.pulsar.broker.cache;
 
 import org.apache.pulsar.broker.PulsarServerException;
 import org.apache.pulsar.broker.resources.PulsarResources;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.FailureDomain;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.FailureDomainImpl;
 import org.apache.pulsar.common.policies.data.Policies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.impl.NamespaceIsolationPolicies;
 import org.apache.pulsar.zookeeper.ZooKeeperCache;
 import org.apache.pulsar.zookeeper.ZooKeeperChildrenCache;
@@ -44,7 +44,7 @@ public class ConfigurationMetadataCacheService extends ConfigurationCacheService
         throw new UnsupportedOperationException();
     }
 
-    public ZooKeeperDataCache<TenantInfo> propertiesCache() {
+    public ZooKeeperDataCache<TenantInfoImpl> propertiesCache() {
         throw new UnsupportedOperationException();
     }
 
@@ -52,7 +52,7 @@ public class ConfigurationMetadataCacheService extends ConfigurationCacheService
         throw new UnsupportedOperationException();
     }
 
-    public ZooKeeperDataCache<ClusterData> clustersCache() {
+    public ZooKeeperDataCache<ClusterDataImpl> clustersCache() {
         throw new UnsupportedOperationException();
     }
 
@@ -72,7 +72,7 @@ public class ConfigurationMetadataCacheService extends ConfigurationCacheService
         throw new UnsupportedOperationException();
     }
 
-    public ZooKeeperDataCache<FailureDomain> failureDomainCache() {
+    public ZooKeeperDataCache<FailureDomainImpl> failureDomainCache() {
         throw new UnsupportedOperationException();
     }
 }
diff --git a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/ClusterResources.java b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/ClusterResources.java
index 938d667..dcfc52d 100644
--- a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/ClusterResources.java
+++ b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/ClusterResources.java
@@ -22,30 +22,30 @@ import java.util.HashSet;
 import java.util.Set;
 import lombok.Getter;
 
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.FailureDomain;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.FailureDomainImpl;
 import org.apache.pulsar.metadata.api.MetadataStoreException;
 import org.apache.pulsar.metadata.api.extended.MetadataStoreExtended;
 
-public class ClusterResources extends BaseResources<ClusterData> {
+public class ClusterResources extends BaseResources<ClusterDataImpl> {
 
     public static final String CLUSTERS_ROOT = "/admin/clusters";
     @Getter
     private FailureDomainResources failureDomainResources;
 
     public ClusterResources(MetadataStoreExtended store, int operationTimeoutSec) {
-        super(store, ClusterData.class, operationTimeoutSec);
-        this.failureDomainResources = new FailureDomainResources(store, FailureDomain.class, operationTimeoutSec);
+        super(store, ClusterDataImpl.class, operationTimeoutSec);
+        this.failureDomainResources = new FailureDomainResources(store, FailureDomainImpl.class, operationTimeoutSec);
     }
 
     public Set<String> list() throws MetadataStoreException {
         return new HashSet<>(super.getChildren(CLUSTERS_ROOT));
     }
 
-    public static class FailureDomainResources extends BaseResources<FailureDomain> {
+    public static class FailureDomainResources extends BaseResources<FailureDomainImpl> {
         public static final String FAILURE_DOMAIN = "failureDomain";
 
-        public FailureDomainResources(MetadataStoreExtended store, Class<FailureDomain> clazz,
+        public FailureDomainResources(MetadataStoreExtended store, Class<FailureDomainImpl> clazz,
                 int operationTimeoutSec) {
             super(store, clazz, operationTimeoutSec);
         }
diff --git a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/NamespaceResources.java b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/NamespaceResources.java
index 4cb08f1..58d493e 100644
--- a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/NamespaceResources.java
+++ b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/NamespaceResources.java
@@ -24,7 +24,7 @@ import java.util.Optional;
 import lombok.Getter;
 
 import org.apache.pulsar.common.partition.PartitionedTopicMetadata;
-import org.apache.pulsar.common.policies.data.NamespaceIsolationData;
+import org.apache.pulsar.common.policies.data.NamespaceIsolationDataImpl;
 import org.apache.pulsar.common.policies.data.Policies;
 import org.apache.pulsar.common.policies.impl.NamespaceIsolationPolicies;
 import org.apache.pulsar.metadata.api.MetadataStoreException;
@@ -43,14 +43,14 @@ public class NamespaceResources extends BaseResources<Policies> {
         partitionedTopicResources = new PartitionedTopicResources(configurationStore, operationTimeoutSec);
     }
 
-    public static class IsolationPolicyResources extends BaseResources<Map<String, NamespaceIsolationData>> {
+    public static class IsolationPolicyResources extends BaseResources<Map<String, NamespaceIsolationDataImpl>> {
         public IsolationPolicyResources(MetadataStoreExtended store, int operationTimeoutSec) {
-            super(store, new TypeReference<Map<String, NamespaceIsolationData>>() {
+            super(store, new TypeReference<Map<String, NamespaceIsolationDataImpl>>() {
             }, operationTimeoutSec);
         }
 
         public Optional<NamespaceIsolationPolicies> getPolicies(String path) throws MetadataStoreException {
-            Optional<Map<String, NamespaceIsolationData>> data = super.get(path);
+            Optional<Map<String, NamespaceIsolationDataImpl>> data = super.get(path);
             return data.isPresent() ? Optional.of(new NamespaceIsolationPolicies(data.get())) : Optional.empty();
         }
     }
diff --git a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/TenantResources.java b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/TenantResources.java
index a92c660..3ae40ed 100644
--- a/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/TenantResources.java
+++ b/pulsar-broker-common/src/main/java/org/apache/pulsar/broker/resources/TenantResources.java
@@ -18,11 +18,11 @@
  */
 package org.apache.pulsar.broker.resources;
 
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.metadata.api.extended.MetadataStoreExtended;
 
-public class TenantResources extends BaseResources<TenantInfo> {
+public class TenantResources extends BaseResources<TenantInfoImpl> {
     public TenantResources(MetadataStoreExtended store, int operationTimeoutSec) {
-        super(store, TenantInfo.class, operationTimeoutSec);
+        super(store, TenantInfoImpl.class, operationTimeoutSec);
     }
 }
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/PulsarClusterMetadataSetup.java b/pulsar-broker/src/main/java/org/apache/pulsar/PulsarClusterMetadataSetup.java
index d3aedb2..6eb4153 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/PulsarClusterMetadataSetup.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/PulsarClusterMetadataSetup.java
@@ -19,7 +19,7 @@
 package org.apache.pulsar;
 
 import static org.apache.pulsar.broker.cache.ConfigurationCacheService.POLICIES_ROOT;
-import static org.apache.pulsar.common.policies.data.Policies.getBundles;
+import static org.apache.pulsar.common.policies.data.PoliciesUtil.getBundles;
 import com.beust.jcommander.JCommander;
 import com.beust.jcommander.Parameter;
 import java.io.IOException;
@@ -36,9 +36,9 @@ import org.apache.pulsar.common.conf.InternalConfigurationData;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.partition.PartitionedTopicMetadata;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.Policies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.functions.worker.WorkerUtils;
 import org.apache.pulsar.metadata.api.GetResult;
@@ -236,14 +236,15 @@ public class PulsarClusterMetadataSetup {
 
         createMetadataNode(configStore, "/admin/clusters", new byte[0]);
 
-        ClusterData clusterData = new ClusterData(arguments.clusterWebServiceUrl, arguments.clusterWebServiceUrlTls,
-                arguments.clusterBrokerServiceUrl, arguments.clusterBrokerServiceUrlTls);
+        ClusterDataImpl clusterData = new ClusterDataImpl(arguments.clusterWebServiceUrl,
+                arguments.clusterWebServiceUrlTls, arguments.clusterBrokerServiceUrl,
+                arguments.clusterBrokerServiceUrlTls);
         byte[] clusterDataJson = ObjectMapperFactory.getThreadLocal().writeValueAsBytes(clusterData);
 
         createMetadataNode(configStore, "/admin/clusters/" + arguments.cluster, clusterDataJson);
 
         // Create marker for "global" cluster
-        ClusterData globalClusterData = new ClusterData(null, null);
+        ClusterDataImpl globalClusterData = new ClusterDataImpl(null, null);
         byte[] globalClusterDataJson = ObjectMapperFactory.getThreadLocal().writeValueAsBytes(globalClusterData);
 
         createMetadataNode(configStore, "/admin/clusters/global", globalClusterDataJson);
@@ -278,14 +279,14 @@ public class PulsarClusterMetadataSetup {
 
         Optional<GetResult> getResult = configStore.get(tenantPath).get();
         if (!getResult.isPresent()) {
-            TenantInfo publicTenant = new TenantInfo(Collections.emptySet(), Collections.singleton(cluster));
+            TenantInfoImpl publicTenant = new TenantInfoImpl(Collections.emptySet(), Collections.singleton(cluster));
 
             createMetadataNode(configStore, tenantPath,
                     ObjectMapperFactory.getThreadLocal().writeValueAsBytes(publicTenant));
         } else {
             // Update existing public tenant with new cluster
             byte[] content = getResult.get().getValue();
-            TenantInfo publicTenant = ObjectMapperFactory.getThreadLocal().readValue(content, TenantInfo.class);
+            TenantInfoImpl publicTenant = ObjectMapperFactory.getThreadLocal().readValue(content, TenantInfoImpl.class);
 
             // Only update z-node if the list of clusters should be modified
             if (!publicTenant.getAllowedClusters().contains(cluster)) {
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/PulsarStandalone.java b/pulsar-broker/src/main/java/org/apache/pulsar/PulsarStandalone.java
index 749920e..dfaafd2 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/PulsarStandalone.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/PulsarStandalone.java
@@ -34,8 +34,8 @@ import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.client.admin.PulsarAdminBuilder;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.functions.worker.WorkerConfig;
 import org.apache.pulsar.functions.worker.WorkerService;
 import org.apache.pulsar.functions.worker.service.WorkerServiceLoader;
@@ -305,8 +305,8 @@ public class PulsarStandalone implements AutoCloseable {
                     webServiceUrl.toString()).authentication(
                     config.getBrokerClientAuthenticationPlugin(),
                     config.getBrokerClientAuthenticationParameters()).build();
-            ClusterData clusterData =
-                    new ClusterData(webServiceUrl.toString(), null, brokerServiceUrl, null);
+            ClusterDataImpl clusterData =
+                    new ClusterDataImpl(webServiceUrl.toString(), null, brokerServiceUrl, null);
             createSampleNameSpace(clusterData, cluster);
         } else {
             URL webServiceUrlTls = new URL(
@@ -333,7 +333,8 @@ public class PulsarStandalone implements AutoCloseable {
             }
 
             admin = builder.build();
-            ClusterData clusterData = new ClusterData(null, webServiceUrlTls.toString(), null, brokerServiceUrlTls);
+            ClusterDataImpl clusterData = new ClusterDataImpl(null, webServiceUrlTls.toString(),
+                    null, brokerServiceUrlTls);
             createSampleNameSpace(clusterData, cluster);
         }
 
@@ -354,7 +355,7 @@ public class PulsarStandalone implements AutoCloseable {
         try {
             if (!admin.tenants().getTenants().contains(publicTenant)) {
                 admin.tenants().createTenant(publicTenant,
-                        new TenantInfo(Sets.newHashSet(config.getSuperUserRoles()), Sets.newHashSet(cluster)));
+                        new TenantInfoImpl(Sets.newHashSet(config.getSuperUserRoles()), Sets.newHashSet(cluster)));
             }
             if (!admin.namespaces().getNamespaces(publicTenant).contains(defaultNamespace)) {
                 admin.namespaces().createNamespace(defaultNamespace);
@@ -366,7 +367,7 @@ public class PulsarStandalone implements AutoCloseable {
         }
     }
 
-    private void createSampleNameSpace(ClusterData clusterData, String cluster) {
+    private void createSampleNameSpace(ClusterDataImpl clusterData, String cluster) {
         // Create a sample namespace
         final String tenant = "sample";
         final String globalCluster = "global";
@@ -382,12 +383,12 @@ public class PulsarStandalone implements AutoCloseable {
             try {
                 admin.clusters().getCluster(globalCluster);
             } catch (PulsarAdminException.NotFoundException ex) {
-                admin.clusters().createCluster(globalCluster, new ClusterData(null, null));
+                admin.clusters().createCluster(globalCluster, new ClusterDataImpl(null, null));
             }
 
             if (!admin.tenants().getTenants().contains(tenant)) {
                 admin.tenants().createTenant(tenant,
-                        new TenantInfo(Sets.newHashSet(config.getSuperUserRoles()), Sets.newHashSet(cluster)));
+                        new TenantInfoImpl(Sets.newHashSet(config.getSuperUserRoles()), Sets.newHashSet(cluster)));
             }
 
             if (!admin.namespaces().getNamespaces(tenant).contains(namespace)) {
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/PulsarService.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/PulsarService.java
index 6bb1a16..7b71a9f 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/PulsarService.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/PulsarService.java
@@ -123,8 +123,8 @@ import org.apache.pulsar.common.configuration.VipStatus;
 import org.apache.pulsar.common.naming.NamespaceBundle;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 import org.apache.pulsar.common.protocol.schema.SchemaStorage;
 import org.apache.pulsar.common.util.FutureUtil;
 import org.apache.pulsar.common.util.netty.EventLoopUtil;
@@ -642,7 +642,7 @@ public class PulsarService implements AutoCloseable {
                     schemaStorage, config.getSchemaRegistryCompatibilityCheckers());
 
             this.defaultOffloader = createManagedLedgerOffloader(
-                    OffloadPolicies.create(this.getConfiguration().getProperties()));
+                    OffloadPoliciesImpl.create(this.getConfiguration().getProperties()));
             this.brokerInterceptor = BrokerInterceptors.load(config);
             brokerService.setInterceptor(getBrokerInterceptor());
             this.brokerInterceptor.initialize(this);
@@ -729,8 +729,8 @@ public class PulsarService implements AutoCloseable {
             this.brokerServiceUrlTls = brokerUrlTls(config);
 
             if (null != this.webSocketService) {
-                ClusterData clusterData =
-                    new ClusterData(webServiceAddress, webServiceAddressTls, brokerServiceUrl, brokerServiceUrlTls);
+                ClusterDataImpl clusterData =
+                    new ClusterDataImpl(webServiceAddress, webServiceAddressTls, brokerServiceUrl, brokerServiceUrlTls);
                 this.webSocketService.setLocalCluster(clusterData);
             }
 
@@ -1117,7 +1117,7 @@ public class PulsarService implements AutoCloseable {
      * @param offloadPolicies the OffloadPolicies
      * @return LedgerOffloader
      */
-    public LedgerOffloader getManagedLedgerOffloader(NamespaceName namespaceName, OffloadPolicies offloadPolicies) {
+    public LedgerOffloader getManagedLedgerOffloader(NamespaceName namespaceName, OffloadPoliciesImpl offloadPolicies) {
         if (offloadPolicies == null) {
             return getDefaultOffloader();
         }
@@ -1138,7 +1138,7 @@ public class PulsarService implements AutoCloseable {
         });
     }
 
-    public synchronized LedgerOffloader createManagedLedgerOffloader(OffloadPolicies offloadPolicies)
+    public synchronized LedgerOffloader createManagedLedgerOffloader(OffloadPoliciesImpl offloadPolicies)
             throws PulsarServerException {
         try {
             if (StringUtils.isNotBlank(offloadPolicies.getManagedLedgerOffloadDriver())) {
@@ -1245,7 +1245,7 @@ public class PulsarService implements AutoCloseable {
         return this.compactor;
     }
 
-    protected synchronized OrderedScheduler getOffloaderScheduler(OffloadPolicies offloadPolicies) {
+    protected synchronized OrderedScheduler getOffloaderScheduler(OffloadPoliciesImpl offloadPolicies) {
         if (this.offloaderScheduler == null) {
             this.offloaderScheduler = OrderedScheduler.newSchedulerBuilder()
                 .numThreads(offloadPolicies.getManagedLedgerOffloadMaxThreads())
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/ClustersBase.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/ClustersBase.java
index ce0f221..dd1f3fa 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/ClustersBase.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/ClustersBase.java
@@ -56,10 +56,10 @@ import org.apache.pulsar.broker.web.RestException;
 import org.apache.pulsar.client.admin.Namespaces;
 import org.apache.pulsar.common.naming.Constants;
 import org.apache.pulsar.common.naming.NamedEntity;
-import org.apache.pulsar.common.policies.data.BrokerNamespaceIsolationData;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.FailureDomain;
-import org.apache.pulsar.common.policies.data.NamespaceIsolationData;
+import org.apache.pulsar.common.policies.data.BrokerNamespaceIsolationDataImpl;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.FailureDomainImpl;
+import org.apache.pulsar.common.policies.data.NamespaceIsolationDataImpl;
 import org.apache.pulsar.common.policies.impl.NamespaceIsolationPolicies;
 import org.apache.pulsar.common.policies.impl.NamespaceIsolationPolicyImpl;
 import org.apache.pulsar.common.util.FutureUtil;
@@ -95,16 +95,16 @@ public class ClustersBase extends PulsarWebResource {
     @Path("/{cluster}")
     @ApiOperation(
         value = "Get the configuration for the specified cluster.",
-        response = ClusterData.class,
+        response = ClusterDataImpl.class,
         notes = "This operation requires Pulsar superuser privileges."
     )
     @ApiResponses(value = {
-            @ApiResponse(code = 200, message = "Return the cluster data.", response = ClusterData.class),
+            @ApiResponse(code = 200, message = "Return the cluster data.", response = ClusterDataImpl.class),
             @ApiResponse(code = 403, message = "Don't have admin permission."),
             @ApiResponse(code = 404, message = "Cluster doesn't exist."),
             @ApiResponse(code = 500, message = "Internal server error.")
     })
-    public ClusterData getCluster(
+    public ClusterDataImpl getCluster(
         @ApiParam(
             value = "The cluster name",
             required = true
@@ -159,7 +159,7 @@ public class ClustersBase extends PulsarWebResource {
                 )
             )
         )
-        ClusterData clusterData
+                ClusterDataImpl clusterData
     ) {
         validateSuperUserAccess();
         validatePoliciesReadOnlyAccess();
@@ -212,7 +212,7 @@ public class ClustersBase extends PulsarWebResource {
                 )
             )
         )
-        ClusterData clusterData
+                ClusterDataImpl clusterData
     ) {
         validateSuperUserAccess();
         validatePoliciesReadOnlyAccess();
@@ -329,7 +329,7 @@ public class ClustersBase extends PulsarWebResource {
     ) {
         validateSuperUserAccess();
         try {
-            ClusterData clusterData = clusterResources().get(path("clusters", cluster))
+            ClusterDataImpl clusterData = clusterResources().get(path("clusters", cluster))
                     .orElseThrow(() -> new RestException(Status.NOT_FOUND, "Cluster does not exist"));
             return clusterData.getPeerClusterNames();
         } catch (Exception e) {
@@ -433,7 +433,7 @@ public class ClustersBase extends PulsarWebResource {
     @Path("/{cluster}/namespaceIsolationPolicies")
     @ApiOperation(
         value = "Get the namespace isolation policies assigned to the cluster.",
-        response = NamespaceIsolationData.class,
+        response = NamespaceIsolationDataImpl.class,
         responseContainer = "Map",
         notes = "This operation requires Pulsar superuser privileges."
     )
@@ -442,7 +442,7 @@ public class ClustersBase extends PulsarWebResource {
             @ApiResponse(code = 404, message = "Cluster doesn't exist."),
             @ApiResponse(code = 500, message = "Internal server error.")
     })
-    public Map<String, NamespaceIsolationData> getNamespaceIsolationPolicies(
+    public Map<String, NamespaceIsolationDataImpl> getNamespaceIsolationPolicies(
         @ApiParam(
             value = "The cluster name",
             required = true
@@ -471,7 +471,7 @@ public class ClustersBase extends PulsarWebResource {
     @Path("/{cluster}/namespaceIsolationPolicies/{policyName}")
     @ApiOperation(
             value = "Get the single namespace isolation policy assigned to the cluster.",
-            response = NamespaceIsolationData.class,
+            response = NamespaceIsolationDataImpl.class,
             notes = "This operation requires Pulsar superuser privileges."
     )
     @ApiResponses(value = {
@@ -480,7 +480,7 @@ public class ClustersBase extends PulsarWebResource {
             @ApiResponse(code = 412, message = "Cluster doesn't exist."),
             @ApiResponse(code = 500, message = "Internal server error.")
     })
-    public NamespaceIsolationData getNamespaceIsolationPolicy(
+    public NamespaceIsolationDataImpl getNamespaceIsolationPolicy(
         @ApiParam(
             value = "The cluster name",
             required = true
@@ -520,7 +520,7 @@ public class ClustersBase extends PulsarWebResource {
     @Path("/{cluster}/namespaceIsolationPolicies/brokers")
     @ApiOperation(
         value = "Get list of brokers with namespace-isolation policies attached to them.",
-        response = BrokerNamespaceIsolationData.class,
+        response = BrokerNamespaceIsolationDataImpl.class,
         responseContainer = "set",
         notes = "This operation requires Pulsar superuser privileges."
     )
@@ -530,7 +530,7 @@ public class ClustersBase extends PulsarWebResource {
         @ApiResponse(code = 412, message = "Cluster doesn't exist."),
         @ApiResponse(code = 500, message = "Internal server error.")
     })
-    public List<BrokerNamespaceIsolationData> getBrokersWithNamespaceIsolationPolicy(
+    public List<BrokerNamespaceIsolationDataImpl> getBrokersWithNamespaceIsolationPolicy(
             @ApiParam(
                 value = "The cluster name",
                 required = true
@@ -541,7 +541,7 @@ public class ClustersBase extends PulsarWebResource {
 
         Set<String> availableBrokers;
         final String nsIsolationPoliciesPath = AdminResource.path("clusters", cluster, NAMESPACE_ISOLATION_POLICIES);
-        Map<String, NamespaceIsolationData> nsPolicies;
+        Map<String, NamespaceIsolationDataImpl> nsPolicies;
         try {
             availableBrokers = pulsar().getLoadManager().get().getAvailableBrokers();
         } catch (Exception e) {
@@ -560,7 +560,7 @@ public class ClustersBase extends PulsarWebResource {
             throw new RestException(e);
         }
         return availableBrokers.stream().map(broker -> {
-            BrokerNamespaceIsolationData brokerIsolationData = new BrokerNamespaceIsolationData();
+            BrokerNamespaceIsolationDataImpl brokerIsolationData = new BrokerNamespaceIsolationDataImpl();
             brokerIsolationData.brokerName = broker;
             if (nsPolicies != null) {
                 nsPolicies.forEach((name, policyData) -> {
@@ -584,7 +584,7 @@ public class ClustersBase extends PulsarWebResource {
     @Path("/{cluster}/namespaceIsolationPolicies/brokers/{broker}")
     @ApiOperation(
         value = "Get a broker with namespace-isolation policies attached to it.",
-        response = BrokerNamespaceIsolationData.class,
+        response = BrokerNamespaceIsolationDataImpl.class,
         notes = "This operation requires Pulsar superuser privileges."
     )
     @ApiResponses(value = {
@@ -593,7 +593,7 @@ public class ClustersBase extends PulsarWebResource {
         @ApiResponse(code = 412, message = "Cluster doesn't exist."),
         @ApiResponse(code = 500, message = "Internal server error.")
     })
-    public BrokerNamespaceIsolationData getBrokerWithNamespaceIsolationPolicy(
+    public BrokerNamespaceIsolationDataImpl getBrokerWithNamespaceIsolationPolicy(
         @ApiParam(
             value = "The cluster name",
             required = true
@@ -609,7 +609,7 @@ public class ClustersBase extends PulsarWebResource {
         validateClusterExists(cluster);
 
         final String nsIsolationPoliciesPath = AdminResource.path("clusters", cluster, NAMESPACE_ISOLATION_POLICIES);
-        Map<String, NamespaceIsolationData> nsPolicies;
+        Map<String, NamespaceIsolationDataImpl> nsPolicies;
         try {
             Optional<NamespaceIsolationPolicies> nsPoliciesResult = namespaceIsolationPolicies()
                     .getPolicies(nsIsolationPoliciesPath);
@@ -621,7 +621,7 @@ public class ClustersBase extends PulsarWebResource {
             log.error("[{}] Failed to get namespace isolation-policies {}", clientAppId(), cluster, e);
             throw new RestException(e);
         }
-        BrokerNamespaceIsolationData brokerIsolationData = new BrokerNamespaceIsolationData();
+        BrokerNamespaceIsolationDataImpl brokerIsolationData = new BrokerNamespaceIsolationDataImpl();
         brokerIsolationData.brokerName = broker;
         if (nsPolicies != null) {
             nsPolicies.forEach((name, policyData) -> {
@@ -669,7 +669,7 @@ public class ClustersBase extends PulsarWebResource {
             value = "The namespace isolation policy data",
             required = true
         )
-        NamespaceIsolationData policyData
+                NamespaceIsolationDataImpl policyData
     ) {
         validateSuperUserAccess();
         validateClusterExists(cluster);
@@ -722,7 +722,7 @@ public class ClustersBase extends PulsarWebResource {
 
     // get matched namespaces; call unload for each namespaces;
     private void filterAndUnloadMatchedNameSpaces(AsyncResponse asyncResponse,
-                                                  NamespaceIsolationData policyData) throws Exception {
+                                                  NamespaceIsolationDataImpl policyData) throws Exception {
         Namespaces namespaces = pulsar().getAdminClient().namespaces();
 
         List<String> nssToUnload = Lists.newArrayList();
@@ -886,7 +886,7 @@ public class ClustersBase extends PulsarWebResource {
             value = "The configuration data of a failure domain",
             required = true
         )
-        FailureDomain domain
+                FailureDomainImpl domain
     ) throws Exception {
         validateSuperUserAccess();
         validateClusterExists(cluster);
@@ -911,7 +911,7 @@ public class ClustersBase extends PulsarWebResource {
     @Path("/{cluster}/failureDomains")
     @ApiOperation(
         value = "Get the cluster failure domains.",
-        response = FailureDomain.class,
+        response = FailureDomainImpl.class,
         responseContainer = "Map",
         notes = "This operation requires Pulsar superuser privileges."
     )
@@ -919,7 +919,7 @@ public class ClustersBase extends PulsarWebResource {
         @ApiResponse(code = 403, message = "Don't have admin permission"),
         @ApiResponse(code = 500, message = "Internal server error")
     })
-    public Map<String, FailureDomain> getFailureDomains(
+    public Map<String, FailureDomainImpl> getFailureDomains(
         @ApiParam(
             value = "The cluster name",
             required = true
@@ -928,13 +928,13 @@ public class ClustersBase extends PulsarWebResource {
     ) throws Exception {
         validateSuperUserAccess();
 
-        Map<String, FailureDomain> domains = Maps.newHashMap();
+        Map<String, FailureDomainImpl> domains = Maps.newHashMap();
         try {
             final String failureDomainRootPath = pulsar().getConfigurationCache().CLUSTER_FAILURE_DOMAIN_ROOT;
             FailureDomainResources failureDomainListCache = clusterResources().getFailureDomainResources();
             for (String domainName : failureDomainListCache.getChildren(failureDomainRootPath)) {
                 try {
-                    Optional<FailureDomain> domain = failureDomainListCache
+                    Optional<FailureDomainImpl> domain = failureDomainListCache
                             .get(joinPath(failureDomainRootPath, domainName));
                     domain.ifPresent(failureDomain -> domains.put(domainName, failureDomain));
                 } catch (Exception e) {
@@ -955,7 +955,7 @@ public class ClustersBase extends PulsarWebResource {
     @Path("/{cluster}/failureDomains/{domainName}")
     @ApiOperation(
         value = "Get a domain in a cluster",
-        response = FailureDomain.class,
+        response = FailureDomainImpl.class,
         notes = "This operation requires Pulsar superuser privileges."
     )
     @ApiResponses(value = {
@@ -964,7 +964,7 @@ public class ClustersBase extends PulsarWebResource {
         @ApiResponse(code = 412, message = "Cluster doesn't exist"),
         @ApiResponse(code = 500, message = "Internal server error")
     })
-    public FailureDomain getDomain(
+    public FailureDomainImpl getDomain(
         @ApiParam(
             value = "The cluster name",
             required = true
@@ -1034,7 +1034,7 @@ public class ClustersBase extends PulsarWebResource {
     }
 
     private void validateBrokerExistsInOtherDomain(final String cluster, final String inputDomainName,
-            final FailureDomain inputDomain) {
+            final FailureDomainImpl inputDomain) {
         if (inputDomain != null && inputDomain.brokers != null) {
             try {
                 final String failureDomainRootPath = pulsar().getConfigurationCache().CLUSTER_FAILURE_DOMAIN_ROOT;
@@ -1044,7 +1044,7 @@ public class ClustersBase extends PulsarWebResource {
                         continue;
                     }
                     try {
-                        Optional<FailureDomain> domain =
+                        Optional<FailureDomainImpl> domain =
                                 clusterResources().getFailureDomainResources()
                                         .get(joinPath(failureDomainRootPath, domainName));
                         if (domain.isPresent() && domain.get().brokers != null) {
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/FunctionsBase.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/FunctionsBase.java
index 6eb1301..bb19dae 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/FunctionsBase.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/FunctionsBase.java
@@ -42,9 +42,10 @@ import org.apache.pulsar.broker.admin.AdminResource;
 import org.apache.pulsar.client.api.Message;
 import org.apache.pulsar.common.functions.FunctionConfig;
 import org.apache.pulsar.common.functions.FunctionState;
-import org.apache.pulsar.common.functions.UpdateOptions;
+import org.apache.pulsar.common.functions.UpdateOptionsImpl;
 import org.apache.pulsar.common.io.ConnectorDefinition;
-import org.apache.pulsar.common.policies.data.FunctionStats;
+import org.apache.pulsar.common.policies.data.FunctionInstanceStatsDataImpl;
+import org.apache.pulsar.common.policies.data.FunctionStatsImpl;
 import org.apache.pulsar.common.policies.data.FunctionStatus;
 import org.apache.pulsar.functions.worker.WorkerService;
 import org.apache.pulsar.functions.worker.service.api.Functions;
@@ -303,7 +304,7 @@ public class FunctionsBase extends AdminResource {
             )
             final @FormDataParam("functionConfig") FunctionConfig functionConfig,
             @ApiParam(value = "The update options is for the Pulsar Function that needs to be updated.")
-            final @FormDataParam("updateOptions") UpdateOptions updateOptions) throws IOException {
+            final @FormDataParam("updateOptions") UpdateOptionsImpl updateOptions) throws IOException {
 
         functions().updateFunction(tenant, namespace, functionName, uploadedInputStream, fileDetail,
                 functionPkgUrl, functionConfig, clientAppId(), clientAuthData(), updateOptions);
@@ -403,7 +404,7 @@ public class FunctionsBase extends AdminResource {
     @GET
     @ApiOperation(
             value = "Displays the stats of a Pulsar Function",
-            response = FunctionStats.class
+            response = FunctionStatsImpl.class
     )
     @ApiResponses(value = {
             @ApiResponse(code = 307, message = "Current broker doesn't serve the namespace of this function"),
@@ -413,7 +414,7 @@ public class FunctionsBase extends AdminResource {
     })
     @Produces(MediaType.APPLICATION_JSON)
     @Path("/{tenant}/{namespace}/{functionName}/stats")
-    public FunctionStats getFunctionStats(
+    public FunctionStatsImpl getFunctionStats(
             @ApiParam(value = "The tenant of a Pulsar Function")
             final @PathParam("tenant") String tenant,
             @ApiParam(value = "The namespace of a Pulsar Function")
@@ -427,7 +428,7 @@ public class FunctionsBase extends AdminResource {
     @GET
     @ApiOperation(
             value = "Displays the stats of a Pulsar Function instance",
-            response = FunctionStats.FunctionInstanceStats.FunctionInstanceStatsData.class
+            response = FunctionInstanceStatsDataImpl.class
     )
     @ApiResponses(value = {
             @ApiResponse(code = 307, message = "Current broker doesn't serve the namespace of this function"),
@@ -437,7 +438,7 @@ public class FunctionsBase extends AdminResource {
     })
     @Produces(MediaType.APPLICATION_JSON)
     @Path("/{tenant}/{namespace}/{functionName}/{instanceId}/stats")
-    public FunctionStats.FunctionInstanceStats.FunctionInstanceStatsData getFunctionInstanceStats(
+    public FunctionInstanceStatsDataImpl getFunctionInstanceStats(
             @ApiParam(value = "The tenant of a Pulsar Function") final @PathParam("tenant") String tenant,
             @ApiParam(value = "The namespace of a Pulsar Function") final @PathParam("namespace") String namespace,
             @ApiParam(value = "The name of a Pulsar Function") final @PathParam("functionName") String functionName,
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/NamespacesBase.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/NamespacesBase.java
index e7ef32e..6bae8f8 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/NamespacesBase.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/NamespacesBase.java
@@ -23,8 +23,8 @@ import static org.apache.commons.lang3.StringUtils.isBlank;
 import static org.apache.pulsar.broker.cache.ConfigurationCacheService.POLICIES;
 import static org.apache.pulsar.broker.cache.ConfigurationCacheService.RESOURCEGROUPS;
 import static org.apache.pulsar.broker.cache.LocalZooKeeperCacheService.LOCAL_POLICIES_ROOT;
-import static org.apache.pulsar.common.policies.data.Policies.defaultBundle;
-import static org.apache.pulsar.common.policies.data.Policies.getBundles;
+import static org.apache.pulsar.common.policies.data.PoliciesUtil.defaultBundle;
+import static org.apache.pulsar.common.policies.data.PoliciesUtil.getBundles;
 import com.google.common.collect.Lists;
 import com.google.common.collect.Sets;
 import com.google.common.collect.Sets.SetView;
@@ -66,7 +66,6 @@ import org.apache.pulsar.broker.systopic.SystemTopicClient;
 import org.apache.pulsar.broker.web.RestException;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.client.api.SubscriptionType;
-import org.apache.pulsar.common.api.proto.CommandSubscribe.SubType;
 import org.apache.pulsar.common.naming.NamedEntity;
 import org.apache.pulsar.common.naming.NamespaceBundle;
 import org.apache.pulsar.common.naming.NamespaceBundleFactory;
@@ -82,13 +81,13 @@ import org.apache.pulsar.common.policies.data.BacklogQuota;
 import org.apache.pulsar.common.policies.data.BacklogQuota.BacklogQuotaType;
 import org.apache.pulsar.common.policies.data.BookieAffinityGroupData;
 import org.apache.pulsar.common.policies.data.BundlesData;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.DelayedDeliveryPolicies;
 import org.apache.pulsar.common.policies.data.DispatchRate;
 import org.apache.pulsar.common.policies.data.InactiveTopicPolicies;
 import org.apache.pulsar.common.policies.data.LocalPolicies;
 import org.apache.pulsar.common.policies.data.NamespaceOperation;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.Policies;
 import org.apache.pulsar.common.policies.data.PolicyName;
@@ -193,7 +192,8 @@ public abstract class NamespacesBase extends AdminResource {
                         && !policies.replication_clusters.contains(config().getClusterName())) {
                     // the only replication cluster is other cluster, redirect
                     String replCluster = Lists.newArrayList(policies.replication_clusters).get(0);
-                    ClusterData replClusterData = clusterResources().get(AdminResource.path("clusters", replCluster))
+                    ClusterDataImpl replClusterData = clusterResources().get(
+                            AdminResource.path("clusters", replCluster))
                             .orElseThrow(() -> new RestException(Status.NOT_FOUND,
                                     "Cluster " + replCluster + " does not exist"));
                     URL replClusterUrl;
@@ -356,7 +356,8 @@ public abstract class NamespacesBase extends AdminResource {
                         && !policies.replication_clusters.contains(config().getClusterName())) {
                     // the only replication cluster is other cluster, redirect
                     String replCluster = Lists.newArrayList(policies.replication_clusters).get(0);
-                    ClusterData replClusterData = clusterResources().get(AdminResource.path("clusters", replCluster))
+                    ClusterDataImpl replClusterData =
+                            clusterResources().get(AdminResource.path("clusters", replCluster))
                             .orElseThrow(() -> new RestException(Status.NOT_FOUND,
                                     "Cluster " + replCluster + " does not exist"));
                     URL replClusterUrl;
@@ -508,7 +509,8 @@ public abstract class NamespacesBase extends AdminResource {
                         && !policies.replication_clusters.contains(config().getClusterName())) {
                     // the only replication cluster is other cluster, redirect
                     String replCluster = Lists.newArrayList(policies.replication_clusters).get(0);
-                    ClusterData replClusterData = clusterResources().get(AdminResource.path("clusters", replCluster))
+                    ClusterDataImpl replClusterData =
+                            clusterResources().get(AdminResource.path("clusters", replCluster))
                             .orElseThrow(() -> new RestException(Status.NOT_FOUND,
                                     "Cluster " + replCluster + " does not exist"));
                     URL replClusterUrl;
@@ -581,7 +583,8 @@ public abstract class NamespacesBase extends AdminResource {
                         && !policies.replication_clusters.contains(config().getClusterName())) {
                     // the only replication cluster is other cluster, redirect
                     String replCluster = Lists.newArrayList(policies.replication_clusters).get(0);
-                    ClusterData replClusterData = clusterResources().get(AdminResource.path("clusters", replCluster))
+                    ClusterDataImpl replClusterData =
+                            clusterResources().get(AdminResource.path("clusters", replCluster))
                             .orElseThrow(() -> new RestException(Status.NOT_FOUND,
                                     "Cluster " + replCluster + " does not exist"));
                     URL replClusterUrl;
@@ -1938,7 +1941,7 @@ public abstract class NamespacesBase extends AdminResource {
      */
     private void validatePeerClusterConflict(String clusterName, Set<String> replicationClusters) {
         try {
-            ClusterData clusterData = clusterResources().get(path("clusters", clusterName)).orElseThrow(
+            ClusterDataImpl clusterData = clusterResources().get(path("clusters", clusterName)).orElseThrow(
                     () -> new RestException(Status.PRECONDITION_FAILED, "Invalid replication cluster " + clusterName));
             Set<String> peerClusters = clusterData.getPeerClusterNames();
             if (peerClusters != null && !peerClusters.isEmpty()) {
@@ -2261,7 +2264,7 @@ public abstract class NamespacesBase extends AdminResource {
             final String path = path(POLICIES, namespaceName.toString());
             updatePolicies(path, (policies) -> {
                 if (policies.offload_policies == null) {
-                    policies.offload_policies = new OffloadPolicies();
+                    policies.offload_policies = new OffloadPoliciesImpl();
                 }
                 policies.offload_policies.setManagedLedgerOffloadThresholdInBytes(newThreshold);
                 policies.offload_threshold = newThreshold;
@@ -2296,7 +2299,7 @@ public abstract class NamespacesBase extends AdminResource {
             final String path = path(POLICIES, namespaceName.toString());
             updatePolicies(path, (policies) -> {
                 if (policies.offload_policies == null) {
-                    policies.offload_policies = new OffloadPolicies();
+                    policies.offload_policies = new OffloadPoliciesImpl();
                 }
                 policies.offload_policies.setManagedLedgerOffloadDeletionLagInMillis(newDeletionLagMs);
                 policies.offload_deletion_lag_ms = newDeletionLagMs;
@@ -2398,7 +2401,7 @@ public abstract class NamespacesBase extends AdminResource {
                 PolicyOperation.READ);
         Set<SubscriptionType> subscriptionTypes = new HashSet<>();
         getNamespacePolicies(namespaceName).subscription_types_enabled.forEach(subType ->
-                subscriptionTypes.add(SubscriptionType.valueOf(subType.name())));
+                subscriptionTypes.add(SubscriptionType.valueOf(subType)));
         return subscriptionTypes;
     }
 
@@ -2406,8 +2409,8 @@ public abstract class NamespacesBase extends AdminResource {
         validateNamespacePolicyOperation(namespaceName, PolicyName.SUBSCRIPTION_AUTH_MODE,
                 PolicyOperation.WRITE);
         validatePoliciesReadOnlyAccess();
-        Set<SubType> subTypes = new HashSet<>();
-        subscriptionTypesEnabled.forEach(subscriptionType -> subTypes.add(SubType.valueOf(subscriptionType.name())));
+        Set<String> subTypes = new HashSet<>();
+        subscriptionTypesEnabled.forEach(subscriptionType -> subTypes.add(subscriptionType.name()));
         mutatePolicy((policies) -> {
                     policies.subscription_types_enabled = subTypes;
                     return policies;
@@ -2446,7 +2449,7 @@ public abstract class NamespacesBase extends AdminResource {
         }
     }
 
-    protected void internalSetOffloadPolicies(AsyncResponse asyncResponse, OffloadPolicies offloadPolicies) {
+    protected void internalSetOffloadPolicies(AsyncResponse asyncResponse, OffloadPoliciesImpl offloadPolicies) {
         validateNamespacePolicyOperation(namespaceName, PolicyName.OFFLOAD, PolicyOperation.WRITE);
         validatePoliciesReadOnlyAccess();
         validateOffloadPolicies(offloadPolicies);
@@ -2455,13 +2458,13 @@ public abstract class NamespacesBase extends AdminResource {
             final String path = path(POLICIES, namespaceName.toString());
             namespaceResources().setAsync(path, (policies) -> {
                 if (Objects.equals(offloadPolicies.getManagedLedgerOffloadDeletionLagInMillis(),
-                        OffloadPolicies.DEFAULT_OFFLOAD_DELETION_LAG_IN_MILLIS)) {
+                        OffloadPoliciesImpl.DEFAULT_OFFLOAD_DELETION_LAG_IN_MILLIS)) {
                     offloadPolicies.setManagedLedgerOffloadDeletionLagInMillis(policies.offload_deletion_lag_ms);
                 } else {
                     policies.offload_deletion_lag_ms = offloadPolicies.getManagedLedgerOffloadDeletionLagInMillis();
                 }
                 if (Objects.equals(offloadPolicies.getManagedLedgerOffloadThresholdInBytes(),
-                        OffloadPolicies.DEFAULT_OFFLOAD_THRESHOLD_IN_BYTES)) {
+                        OffloadPoliciesImpl.DEFAULT_OFFLOAD_THRESHOLD_IN_BYTES)) {
                     offloadPolicies.setManagedLedgerOffloadThresholdInBytes(policies.offload_threshold);
                 } else {
                     policies.offload_threshold = offloadPolicies.getManagedLedgerOffloadThresholdInBytes();
@@ -2513,7 +2516,7 @@ public abstract class NamespacesBase extends AdminResource {
         }
     }
 
-    private void validateOffloadPolicies(OffloadPolicies offloadPolicies) {
+    private void validateOffloadPolicies(OffloadPoliciesImpl offloadPolicies) {
         if (offloadPolicies == null) {
             log.warn("[{}] Failed to update offload configuration for namespace {}: offloadPolicies is null",
                     clientAppId(), namespaceName);
@@ -2523,9 +2526,9 @@ public abstract class NamespacesBase extends AdminResource {
         if (!offloadPolicies.driverSupported()) {
             log.warn("[{}] Failed to update offload configuration for namespace {}: "
                             + "driver is not supported, support value: {}",
-                    clientAppId(), namespaceName, OffloadPolicies.getSupportedDriverNames());
+                    clientAppId(), namespaceName, OffloadPoliciesImpl.getSupportedDriverNames());
             throw new RestException(Status.PRECONDITION_FAILED,
-                    "The driver is not supported, support value: " + OffloadPolicies.getSupportedDriverNames());
+                    "The driver is not supported, support value: " + OffloadPoliciesImpl.getSupportedDriverNames());
         }
         if (!offloadPolicies.bucketValid()) {
             log.warn("[{}] Failed to update offload configuration for namespace {}: bucket must be specified",
@@ -2535,11 +2538,11 @@ public abstract class NamespacesBase extends AdminResource {
         }
     }
 
-    protected OffloadPolicies internalGetOffloadPolicies() {
+    protected OffloadPoliciesImpl internalGetOffloadPolicies() {
         validateNamespacePolicyOperation(namespaceName, PolicyName.OFFLOAD, PolicyOperation.READ);
 
         Policies policies = getNamespacePolicies(namespaceName);
-        return policies.offload_policies;
+        return (OffloadPoliciesImpl) policies.offload_policies;
     }
 
     protected int internalGetMaxTopicsPerNamespace() {
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/PersistentTopicsBase.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/PersistentTopicsBase.java
index 2d2ea69..dfa8e16 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/PersistentTopicsBase.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/PersistentTopicsBase.java
@@ -26,9 +26,6 @@ import com.github.zafarkhaja.semver.Version;
 import com.google.common.collect.Lists;
 import com.google.common.collect.Maps;
 import com.google.common.collect.Sets;
-import com.google.gson.Gson;
-import com.google.gson.GsonBuilder;
-import com.google.gson.JsonObject;
 import io.netty.buffer.ByteBuf;
 import java.io.IOException;
 import java.util.ArrayList;
@@ -108,7 +105,7 @@ import org.apache.pulsar.common.policies.data.DelayedDeliveryPolicies;
 import org.apache.pulsar.common.policies.data.DispatchRate;
 import org.apache.pulsar.common.policies.data.InactiveTopicPolicies;
 import org.apache.pulsar.common.policies.data.NamespaceOperation;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 import org.apache.pulsar.common.policies.data.PartitionedTopicInternalStats;
 import org.apache.pulsar.common.policies.data.PartitionedTopicStats;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
@@ -772,18 +769,19 @@ public class PersistentTopicsBase extends AdminResource {
         return CompletableFuture.completedFuture(delayedDeliveryPolicies);
     }
 
-    protected CompletableFuture<OffloadPolicies> internalGetOffloadPolicies(boolean applied) {
-        OffloadPolicies offloadPolicies =
+    protected CompletableFuture<OffloadPoliciesImpl> internalGetOffloadPolicies(boolean applied) {
+        OffloadPoliciesImpl offloadPolicies =
                 getTopicPolicies(topicName).map(TopicPolicies::getOffloadPolicies).orElse(null);
         if (applied) {
-            OffloadPolicies namespacePolicy = getNamespacePolicies(namespaceName).offload_policies;
-            offloadPolicies = OffloadPolicies.mergeConfiguration(offloadPolicies
+            OffloadPoliciesImpl namespacePolicy =
+                    (OffloadPoliciesImpl) getNamespacePolicies(namespaceName).offload_policies;
+            offloadPolicies = OffloadPoliciesImpl.mergeConfiguration(offloadPolicies
                     , namespacePolicy, pulsar().getConfiguration().getProperties());
         }
         return CompletableFuture.completedFuture(offloadPolicies);
     }
 
-    protected CompletableFuture<Void> internalSetOffloadPolicies(OffloadPolicies offloadPolicies) {
+    protected CompletableFuture<Void> internalSetOffloadPolicies(OffloadPoliciesImpl offloadPolicies) {
         TopicPolicies topicPolicies = null;
         try {
             topicPolicies = pulsar().getTopicPoliciesService().getTopicPolicies(topicName);
@@ -853,7 +851,7 @@ public class PersistentTopicsBase extends AdminResource {
         return pulsar().getTopicPoliciesService().updateTopicPoliciesAsync(topicName, topicPolicies);
     }
 
-    private CompletableFuture<Void> internalUpdateOffloadPolicies(OffloadPolicies offloadPolicies,
+    private CompletableFuture<Void> internalUpdateOffloadPolicies(OffloadPoliciesImpl offloadPolicies,
                                                                   TopicName topicName) {
         return pulsar().getBrokerService().getTopicIfExists(topicName.toString())
                 .thenAccept(optionalTopic -> {
@@ -1147,7 +1145,7 @@ public class PersistentTopicsBase extends AdminResource {
             getPartitionedTopicMetadataAsync(topicName,
                     authoritative, false).thenAccept(partitionMetadata -> {
                 if (partitionMetadata.partitions > 0) {
-                    final List<CompletableFuture<JsonObject>> futures = Lists.newArrayList();
+                    final List<CompletableFuture<String>> futures = Lists.newArrayList();
 
                     PartitionedManagedLedgerInfo partitionedManagedLedgerInfo = new PartitionedManagedLedgerInfo();
 
@@ -1156,21 +1154,20 @@ public class PersistentTopicsBase extends AdminResource {
                         try {
                             futures.add(pulsar().getAdminClient().topics()
                                     .getInternalInfoAsync(
-                                            topicNamePartition.toString()).whenComplete((jsonObject, throwable) -> {
+                                            topicNamePartition.toString()).whenComplete((response, throwable) -> {
                                         if (throwable != null) {
                                             log.error("[{}] Failed to get managed info for {}",
                                                     clientAppId(), topicNamePartition, throwable);
                                             asyncResponse.resume(new RestException(throwable));
                                         }
-                                        Gson gson = new GsonBuilder().setPrettyPrinting().create();
                                         try {
                                             partitionedManagedLedgerInfo.partitions.put(topicNamePartition.toString(),
-                                                    jsonMapper().readValue(gson.toJson(jsonObject),
+                                                    jsonMapper().readValue(response,
                                                             ManagedLedgerInfo.class));
                                         } catch (JsonProcessingException ex) {
                                             log.error("[{}] Failed to parse ManagedLedgerInfo for {} from [{}]",
                                                     clientAppId(),
-                                                    topicNamePartition, gson.toJson(jsonObject), ex);
+                                                    topicNamePartition, response, ex);
                                         }
                                     }));
                         } catch (Exception e) {
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/SinksBase.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/SinksBase.java
index 5d57723..e2d3a2d 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/SinksBase.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/SinksBase.java
@@ -37,7 +37,7 @@ import javax.ws.rs.PathParam;
 import javax.ws.rs.Produces;
 import javax.ws.rs.core.MediaType;
 import org.apache.pulsar.broker.admin.AdminResource;
-import org.apache.pulsar.common.functions.UpdateOptions;
+import org.apache.pulsar.common.functions.UpdateOptionsImpl;
 import org.apache.pulsar.common.io.ConfigFieldDefinition;
 import org.apache.pulsar.common.io.ConnectorDefinition;
 import org.apache.pulsar.common.io.SinkConfig;
@@ -252,7 +252,7 @@ public class SinksBase extends AdminResource {
                            )
                            final @FormDataParam("sinkConfig") SinkConfig sinkConfig,
                            @ApiParam(value = "Update options for the Pulsar Sink")
-                           final @FormDataParam("updateOptions") UpdateOptions updateOptions) {
+                           final @FormDataParam("updateOptions") UpdateOptionsImpl updateOptions) {
          sinks().updateSink(tenant, namespace, sinkName, uploadedInputStream, fileDetail,
                 sinkPkgUrl, sinkConfig, clientAppId(), clientAuthData(), updateOptions);
 
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/SourcesBase.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/SourcesBase.java
index 2d951b0..a798f0d 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/SourcesBase.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/SourcesBase.java
@@ -37,7 +37,7 @@ import javax.ws.rs.PathParam;
 import javax.ws.rs.Produces;
 import javax.ws.rs.core.MediaType;
 import org.apache.pulsar.broker.admin.AdminResource;
-import org.apache.pulsar.common.functions.UpdateOptions;
+import org.apache.pulsar.common.functions.UpdateOptionsImpl;
 import org.apache.pulsar.common.io.ConfigFieldDefinition;
 import org.apache.pulsar.common.io.ConnectorDefinition;
 import org.apache.pulsar.common.io.SourceConfig;
@@ -211,7 +211,7 @@ public class SourcesBase extends AdminResource {
             )
             final @FormDataParam("sourceConfig") SourceConfig sourceConfig,
             @ApiParam(value = "Update options for Pulsar Source")
-            final @FormDataParam("updateOptions") UpdateOptions updateOptions) {
+            final @FormDataParam("updateOptions") UpdateOptionsImpl updateOptions) {
         sources().updateSource(tenant, namespace, sourceName, uploadedInputStream, fileDetail,
             sourcePkgUrl, sourceConfig, clientAppId(), clientAuthData(), updateOptions);
     }
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/TenantsBase.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/TenantsBase.java
index 390b1fb..df42b0d 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/TenantsBase.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/impl/TenantsBase.java
@@ -47,7 +47,7 @@ import org.apache.pulsar.broker.web.RestException;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.common.naming.Constants;
 import org.apache.pulsar.common.naming.NamedEntity;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.FutureUtil;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -115,7 +115,7 @@ public class TenantsBase extends PulsarWebResource {
             @ApiResponse(code = 412, message = "Clusters do not exist") })
     public void createTenant(@Suspended final AsyncResponse asyncResponse,
             @ApiParam(value = "The tenant name") @PathParam("tenant") String tenant,
-            @ApiParam(value = "TenantInfo") TenantInfo tenantInfo) {
+            @ApiParam(value = "TenantInfo") TenantInfoImpl tenantInfo) {
 
         final String clientAppId = clientAppId();
         try {
@@ -181,7 +181,7 @@ public class TenantsBase extends PulsarWebResource {
             @ApiResponse(code = 412, message = "Clusters do not exist") })
     public void updateTenant(@Suspended final AsyncResponse asyncResponse,
             @ApiParam(value = "The tenant name") @PathParam("tenant") String tenant,
-            @ApiParam(value = "TenantInfo") TenantInfo newTenantAdmin) {
+            @ApiParam(value = "TenantInfo") TenantInfoImpl newTenantAdmin) {
         try {
             validateSuperUserAccess();
             validatePoliciesReadOnlyAccess();
@@ -197,7 +197,7 @@ public class TenantsBase extends PulsarWebResource {
                 asyncResponse.resume(new RestException(Status.NOT_FOUND, "Tenant " + tenant + " not found"));
                 return;
             }
-            TenantInfo oldTenantAdmin = tenantAdmin.get();
+            TenantInfoImpl oldTenantAdmin = tenantAdmin.get();
             Set<String> newClusters = new HashSet<>(newTenantAdmin.getAllowedClusters());
             canUpdateCluster(tenant, oldTenantAdmin.getAllowedClusters(), newClusters).thenApply(r -> {
                 tenantResources().setAsync(path(POLICIES, tenant), old -> {
@@ -334,7 +334,7 @@ public class TenantsBase extends PulsarWebResource {
         });
     }
 
-    private void validateClusters(TenantInfo info) {
+    private void validateClusters(TenantInfoImpl info) {
         // empty cluster shouldn't be allowed
         if (info == null || info.getAllowedClusters().stream().filter(c -> !StringUtils.isBlank(c))
                 .collect(Collectors.toSet()).isEmpty()
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v1/Namespaces.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v1/Namespaces.java
index 2fea925..bcc9892 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v1/Namespaces.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v1/Namespaces.java
@@ -19,7 +19,7 @@
 package org.apache.pulsar.broker.admin.v1;
 
 import static org.apache.pulsar.broker.cache.ConfigurationCacheService.POLICIES;
-import static org.apache.pulsar.common.policies.data.Policies.getBundles;
+import static org.apache.pulsar.common.policies.data.PoliciesUtil.getBundles;
 import com.google.common.collect.Lists;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v2/Namespaces.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v2/Namespaces.java
index c153ac4..85a6ac6 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v2/Namespaces.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v2/Namespaces.java
@@ -18,7 +18,7 @@
  */
 package org.apache.pulsar.broker.admin.v2;
 
-import static org.apache.pulsar.common.policies.data.Policies.getBundles;
+import static org.apache.pulsar.common.policies.data.PoliciesUtil.getBundles;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
 import io.swagger.annotations.ApiParam;
@@ -57,7 +57,7 @@ import org.apache.pulsar.common.policies.data.DelayedDeliveryPolicies;
 import org.apache.pulsar.common.policies.data.DispatchRate;
 import org.apache.pulsar.common.policies.data.InactiveTopicPolicies;
 import org.apache.pulsar.common.policies.data.NamespaceOperation;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.Policies;
 import org.apache.pulsar.common.policies.data.PolicyName;
@@ -1649,7 +1649,7 @@ public class Namespaces extends NamespacesBase {
                     message = "OffloadPolicies is empty or driver is not supported or bucket is not valid")})
     public void setOffloadPolicies(@PathParam("tenant") String tenant, @PathParam("namespace") String namespace,
                                    @ApiParam(value = "Offload policies for the specified namespace", required = true)
-                                           OffloadPolicies offload,
+                                           OffloadPoliciesImpl offload,
                                    @Suspended final AsyncResponse asyncResponse) {
         try {
             validateNamespaceName(tenant, namespace);
@@ -1688,8 +1688,8 @@ public class Namespaces extends NamespacesBase {
     @ApiResponses(value = {
             @ApiResponse(code = 403, message = "Don't have admin permission"),
             @ApiResponse(code = 404, message = "Namespace does not exist")})
-    public OffloadPolicies getOffloadPolicies(@PathParam("tenant") String tenant,
-                                              @PathParam("namespace") String namespace) {
+    public OffloadPoliciesImpl getOffloadPolicies(@PathParam("tenant") String tenant,
+                                                  @PathParam("namespace") String namespace) {
         validateNamespaceName(tenant, namespace);
         return internalGetOffloadPolicies();
     }
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v2/PersistentTopics.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v2/PersistentTopics.java
index 9c317f8..ce8eada 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v2/PersistentTopics.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/admin/v2/PersistentTopics.java
@@ -61,7 +61,7 @@ import org.apache.pulsar.common.policies.data.BacklogQuota.BacklogQuotaType;
 import org.apache.pulsar.common.policies.data.DelayedDeliveryPolicies;
 import org.apache.pulsar.common.policies.data.DispatchRate;
 import org.apache.pulsar.common.policies.data.InactiveTopicPolicies;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.PersistentOfflineTopicStats;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
@@ -306,7 +306,7 @@ public class PersistentTopics extends PersistentTopicsBase {
                                                     @PathParam("namespace") String namespace,
                                                     @PathParam("topic") @Encoded String encodedTopic,
                                                     @ApiParam(value = "Offload policies for the specified topic")
-                                                            OffloadPolicies offloadPolicies) {
+                                           OffloadPoliciesImpl offloadPolicies) {
         validateTopicName(tenant, namespace, encodedTopic);
         validateAdminAccessForTenant(tenant);
         internalSetOffloadPolicies(offloadPolicies).whenComplete((res, ex)
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/loadbalance/impl/ModularLoadManagerImpl.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/loadbalance/impl/ModularLoadManagerImpl.java
index 60bfad3..6fd2884 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/loadbalance/impl/ModularLoadManagerImpl.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/loadbalance/impl/ModularLoadManagerImpl.java
@@ -69,7 +69,7 @@ import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.common.naming.NamespaceBundleFactory;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.ServiceUnitId;
-import org.apache.pulsar.common.policies.data.FailureDomain;
+import org.apache.pulsar.common.policies.data.FailureDomainImpl;
 import org.apache.pulsar.common.policies.data.LocalPolicies;
 import org.apache.pulsar.common.policies.data.ResourceQuota;
 import org.apache.pulsar.common.stats.Metrics;
@@ -1030,7 +1030,7 @@ public class ModularLoadManagerImpl implements ModularLoadManager, Consumer<Noti
                 Map<String, String> tempBrokerToFailureDomainMap = Maps.newHashMap();
                 for (String domainName : pulsar.getConfigurationCache().failureDomainListCache().get()) {
                     try {
-                        Optional<FailureDomain> domain = pulsar.getConfigurationCache().failureDomainCache()
+                        Optional<FailureDomainImpl> domain = pulsar.getConfigurationCache().failureDomainCache()
                                 .get(clusterDomainRootPath + "/" + domainName);
                         if (domain.isPresent()) {
                             for (String broker : domain.get().brokers) {
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/namespace/NamespaceService.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/namespace/NamespaceService.java
index 01000d9..a416474 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/namespace/NamespaceService.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/namespace/NamespaceService.java
@@ -85,7 +85,7 @@ import org.apache.pulsar.common.naming.TopicDomain;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.policies.NamespaceIsolationPolicy;
 import org.apache.pulsar.common.policies.data.BrokerAssignment;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.LocalPolicies;
 import org.apache.pulsar.common.policies.data.NamespaceOwnershipStatus;
 import org.apache.pulsar.common.policies.impl.NamespaceIsolationPolicies;
@@ -146,7 +146,7 @@ public class NamespaceService implements AutoCloseable {
 
     public static final String NAMESPACE_ISOLATION_POLICIES = "namespaceIsolationPolicies";
 
-    private final ConcurrentOpenHashMap<ClusterData, PulsarClientImpl> namespaceClients;
+    private final ConcurrentOpenHashMap<ClusterDataImpl, PulsarClientImpl> namespaceClients;
 
     private final List<NamespaceBundleOwnershipListener> bundleOwnershipListeners;
 
@@ -1213,14 +1213,14 @@ public class NamespaceService implements AutoCloseable {
                 });
     }
 
-    private CompletableFuture<List<String>> getNonPersistentTopicsFromPeerCluster(ClusterData peerClusterData,
-                                                               NamespaceName namespace) {
+    private CompletableFuture<List<String>> getNonPersistentTopicsFromPeerCluster(ClusterDataImpl peerClusterData,
+                                                                                  NamespaceName namespace) {
         PulsarClientImpl client = getNamespaceClient(peerClusterData);
         return client.getLookup().getTopicsUnderNamespace(namespace, Mode.NON_PERSISTENT);
     }
 
 
-    public PulsarClientImpl getNamespaceClient(ClusterData cluster) {
+    public PulsarClientImpl getNamespaceClient(ClusterDataImpl cluster) {
         PulsarClientImpl client = namespaceClients.get(cluster);
         if (client != null) {
             return client;
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/resourcegroup/ResourceUsageTransportManager.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/resourcegroup/ResourceUsageTransportManager.java
index 7cebe43..8f0f009 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/resourcegroup/ResourceUsageTransportManager.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/resourcegroup/ResourceUsageTransportManager.java
@@ -42,7 +42,7 @@ import org.apache.pulsar.client.api.Reader;
 import org.apache.pulsar.client.api.ReaderListener;
 import org.apache.pulsar.common.allocator.PulsarByteBufAllocator;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -190,7 +190,7 @@ public class ResourceUsageTransportManager implements AutoCloseable {
         if (!tenantList.contains(tenant)) {
             try {
                 admin.tenants().createTenant(tenant,
-                  new TenantInfo(Sets.newHashSet(config.getSuperUserRoles()), Sets.newHashSet(cluster)));
+                  new TenantInfoImpl(Sets.newHashSet(config.getSuperUserRoles()), Sets.newHashSet(cluster)));
             } catch (PulsarAdminException ex1) {
                 if (!(ex1 instanceof PulsarAdminException.ConflictException)) {
                     LOG.error("Unexpected exception {} when creating tenant {}", ex1, tenant);
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/BrokerService.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/BrokerService.java
index 3b1dc63..ddca6b2 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/BrokerService.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/BrokerService.java
@@ -142,9 +142,9 @@ import org.apache.pulsar.common.partition.PartitionedTopicMetadata;
 import org.apache.pulsar.common.policies.data.AutoSubscriptionCreationOverride;
 import org.apache.pulsar.common.policies.data.AutoTopicCreationOverride;
 import org.apache.pulsar.common.policies.data.BacklogQuota;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.LocalPolicies;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.PersistentOfflineTopicStats;
 import org.apache.pulsar.common.policies.data.Policies;
@@ -1017,7 +1017,7 @@ public class BrokerService implements Closeable, ZooKeeperCacheListener<Policies
         return replicationClients.computeIfAbsent(cluster, key -> {
             try {
                 String path = PulsarWebResource.path("clusters", cluster);
-                ClusterData data = this.pulsar.getConfigurationCache().clustersCache().get(path)
+                ClusterDataImpl data = this.pulsar.getConfigurationCache().clustersCache().get(path)
                         .orElseThrow(() -> new KeeperException.NoNodeException(path));
                 ClientBuilder clientBuilder = PulsarClient.builder()
                         .enableTcpNoDelay(false)
@@ -1092,7 +1092,7 @@ public class BrokerService implements Closeable, ZooKeeperCacheListener<Policies
         return clusterAdmins.computeIfAbsent(cluster, key -> {
             try {
                 String path = PulsarWebResource.path("clusters", cluster);
-                ClusterData data = this.pulsar.getConfigurationCache().clustersCache().get(path)
+                ClusterDataImpl data = this.pulsar.getConfigurationCache().clustersCache().get(path)
                         .orElseThrow(() -> new KeeperException.NoNodeException(path));
 
                 ServiceConfiguration conf = pulsar.getConfig();
@@ -1290,7 +1290,7 @@ public class BrokerService implements Closeable, ZooKeeperCacheListener<Policies
 
             PersistencePolicies persistencePolicies = null;
             RetentionPolicies retentionPolicies = null;
-            OffloadPolicies topicLevelOffloadPolicies = null;
+            OffloadPoliciesImpl topicLevelOffloadPolicies = null;
 
             if (pulsar.getConfig().isTopicLevelPoliciesEnabled()) {
                 TopicName cloneTopicName = topicName;
@@ -1383,10 +1383,11 @@ public class BrokerService implements Closeable, ZooKeeperCacheListener<Policies
             managedLedgerConfig.setAutoSkipNonRecoverableData(serviceConfig.isAutoSkipNonRecoverableData());
             managedLedgerConfig.setLazyCursorRecovery(serviceConfig.isLazyCursorRecovery());
 
-            OffloadPolicies nsLevelOffloadPolicies = policies.map(p -> p.offload_policies).orElse(null);
-            OffloadPolicies offloadPolicies = OffloadPolicies.mergeConfiguration(
+            OffloadPoliciesImpl nsLevelOffloadPolicies =
+                    (OffloadPoliciesImpl) policies.map(p -> p.offload_policies).orElse(null);
+            OffloadPoliciesImpl offloadPolicies = OffloadPoliciesImpl.mergeConfiguration(
                     topicLevelOffloadPolicies,
-                    OffloadPolicies.oldPoliciesCompatible(nsLevelOffloadPolicies, policies.orElse(null)),
+                    OffloadPoliciesImpl.oldPoliciesCompatible(nsLevelOffloadPolicies, policies.orElse(null)),
                     getPulsar().getConfig().getProperties());
             if (topicLevelOffloadPolicies != null) {
                 try {
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/nonpersistent/NonPersistentSubscription.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/nonpersistent/NonPersistentSubscription.java
index 1a00f0b..c16065d 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/nonpersistent/NonPersistentSubscription.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/nonpersistent/NonPersistentSubscription.java
@@ -470,7 +470,7 @@ public class NonPersistentSubscription implements Subscription {
             });
         }
 
-        subStats.type = getType();
+        subStats.type = getTypeString();
         subStats.msgDropRate = dispatcher.getMessageDropRate().getValueRate();
         return subStats;
     }
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/persistent/PersistentSubscription.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/persistent/PersistentSubscription.java
index 9cd9e2d..1ad24ae 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/persistent/PersistentSubscription.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/persistent/PersistentSubscription.java
@@ -997,14 +997,15 @@ public class PersistentSubscription implements Subscription {
             });
         }
 
-        subStats.type = getType();
+        SubType subType = getType();
+        subStats.type = getTypeString();
         if (dispatcher instanceof PersistentDispatcherSingleActiveConsumer) {
             Consumer activeConsumer = ((PersistentDispatcherSingleActiveConsumer) dispatcher).getActiveConsumer();
             if (activeConsumer != null) {
                 subStats.activeConsumerName = activeConsumer.consumerName();
             }
         }
-        if (Subscription.isIndividualAckMode(subStats.type)) {
+        if (Subscription.isIndividualAckMode(subType)) {
             if (dispatcher instanceof PersistentDispatcherMultipleConsumers) {
                 PersistentDispatcherMultipleConsumers d = (PersistentDispatcherMultipleConsumers) dispatcher;
                 subStats.unackedMessages = d.getTotalUnackedMessages();
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/persistent/PersistentTopic.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/persistent/PersistentTopic.java
index ae6aa4a..58273e8 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/persistent/PersistentTopic.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/service/persistent/PersistentTopic.java
@@ -3052,7 +3052,7 @@ public class PersistentTopic extends AbstractTopic
                 return getBrokerService().getPulsar().getConfiguration()
                         .getSubscriptionTypesEnabled().contains(subType.name());
             } else {
-                return policies.get().subscription_types_enabled.contains(subType);
+                return policies.get().subscription_types_enabled.contains(subType.name());
             }
         } else {
             return getBrokerService().getPulsar().getConfiguration()
diff --git a/pulsar-broker/src/main/java/org/apache/pulsar/broker/web/PulsarWebResource.java b/pulsar-broker/src/main/java/org/apache/pulsar/broker/web/PulsarWebResource.java
index 2f39897..78526a9 100644
--- a/pulsar-broker/src/main/java/org/apache/pulsar/broker/web/PulsarWebResource.java
+++ b/pulsar-broker/src/main/java/org/apache/pulsar/broker/web/PulsarWebResource.java
@@ -76,12 +76,12 @@ import org.apache.pulsar.common.naming.NamespaceBundles;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.policies.data.BundlesData;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.NamespaceOperation;
 import org.apache.pulsar.common.policies.data.Policies;
 import org.apache.pulsar.common.policies.data.PolicyName;
 import org.apache.pulsar.common.policies.data.PolicyOperation;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TenantOperation;
 import org.apache.pulsar.common.policies.data.TopicOperation;
 import org.apache.pulsar.common.policies.path.PolicyPath;
@@ -268,7 +268,7 @@ public abstract class PulsarWebResource {
                     (isClientAuthenticated(clientAppId)), clientAppId);
         }
 
-        TenantInfo tenantInfo = pulsar.getPulsarResources().getTenantResources().get(path(POLICIES, tenant))
+        TenantInfoImpl tenantInfo = pulsar.getPulsarResources().getTenantResources().get(path(POLICIES, tenant))
                 .orElseThrow(() -> new RestException(Status.NOT_FOUND, "Tenant does not exist"));
 
         if (pulsar.getConfiguration().isAuthenticationEnabled() && pulsar.getConfiguration().isAuthorizationEnabled()) {
@@ -322,7 +322,7 @@ public abstract class PulsarWebResource {
     }
 
     protected void validateClusterForTenant(String tenant, String cluster) {
-        TenantInfo tenantInfo;
+        TenantInfoImpl tenantInfo;
         try {
             tenantInfo = pulsar().getPulsarResources().getTenantResources().get(path(POLICIES, tenant))
                     .orElseThrow(() -> new RestException(Status.NOT_FOUND, "Tenant does not exist"));
@@ -352,7 +352,8 @@ public abstract class PulsarWebResource {
      */
     protected void validateClusterOwnership(String cluster) throws WebApplicationException {
         try {
-            ClusterData differentClusterData = getClusterDataIfDifferentCluster(pulsar(), cluster, clientAppId()).get();
+            ClusterDataImpl differentClusterData =
+                    getClusterDataIfDifferentCluster(pulsar(), cluster, clientAppId()).get();
             if (differentClusterData != null) {
                 URI redirect = getRedirectionUrl(differentClusterData);
                 // redirect to the cluster requested
@@ -373,7 +374,7 @@ public abstract class PulsarWebResource {
 
     }
 
-    private URI getRedirectionUrl(ClusterData differentClusterData) throws MalformedURLException {
+    private URI getRedirectionUrl(ClusterDataImpl differentClusterData) throws MalformedURLException {
         try {
             PulsarServiceNameResolver serviceNameResolver = new PulsarServiceNameResolver();
             if (isRequestHttps() && pulsar.getConfiguration().getWebServicePortTls().isPresent()
@@ -389,10 +390,11 @@ public abstract class PulsarWebResource {
         }
     }
 
-    protected static CompletableFuture<ClusterData> getClusterDataIfDifferentCluster(PulsarService pulsar,
-         String cluster, String clientAppId) {
+    protected static CompletableFuture<ClusterDataImpl> getClusterDataIfDifferentCluster(PulsarService pulsar,
+                                                                                         String cluster,
+                                                                                         String clientAppId) {
 
-        CompletableFuture<ClusterData> clusterDataFuture = new CompletableFuture<>();
+        CompletableFuture<ClusterDataImpl> clusterDataFuture = new CompletableFuture<>();
 
         if (!isValidCluster(pulsar, cluster)) {
             try {
@@ -664,7 +666,7 @@ public abstract class PulsarWebResource {
     protected void validateGlobalNamespaceOwnership(NamespaceName namespace) {
         int timeout = pulsar().getConfiguration().getZooKeeperOperationTimeoutSeconds();
         try {
-            ClusterData peerClusterData = checkLocalOrGetPeerReplicationCluster(pulsar(), namespace)
+            ClusterDataImpl peerClusterData = checkLocalOrGetPeerReplicationCluster(pulsar(), namespace)
                     .get(timeout, SECONDS);
             // if peer-cluster-data is present it means namespace is owned by that peer-cluster and request should be
             // redirect to the peer-cluster
@@ -717,12 +719,12 @@ public abstract class PulsarWebResource {
                 });
     }
 
-    public static CompletableFuture<ClusterData> checkLocalOrGetPeerReplicationCluster(PulsarService pulsarService,
-            NamespaceName namespace) {
+    public static CompletableFuture<ClusterDataImpl> checkLocalOrGetPeerReplicationCluster(PulsarService pulsarService,
+                                                                                           NamespaceName namespace) {
         if (!namespace.isGlobal()) {
             return CompletableFuture.completedFuture(null);
         }
-        final CompletableFuture<ClusterData> validationFuture = new CompletableFuture<>();
+        final CompletableFuture<ClusterDataImpl> validationFuture = new CompletableFuture<>();
         final String localCluster = pulsarService.getConfiguration().getClusterName();
         final String path = AdminResource.path(POLICIES, namespace.toString());
 
@@ -736,7 +738,7 @@ public abstract class PulsarWebResource {
                     log.warn(msg);
                     validationFuture.completeExceptionally(new RestException(Status.PRECONDITION_FAILED, msg));
                 } else if (!policies.replication_clusters.contains(localCluster)) {
-                    ClusterData ownerPeerCluster = getOwnerFromPeerClusterList(pulsarService,
+                    ClusterDataImpl ownerPeerCluster = getOwnerFromPeerClusterList(pulsarService,
                             policies.replication_clusters);
                     if (ownerPeerCluster != null) {
                         // found a peer that own this namespace
@@ -767,14 +769,14 @@ public abstract class PulsarWebResource {
         return validationFuture;
     }
 
-    private static ClusterData getOwnerFromPeerClusterList(PulsarService pulsar, Set<String> replicationClusters) {
+    private static ClusterDataImpl getOwnerFromPeerClusterList(PulsarService pulsar, Set<String> replicationClusters) {
         String currentCluster = pulsar.getConfiguration().getClusterName();
         if (replicationClusters == null || replicationClusters.isEmpty() || isBlank(currentCluster)) {
             return null;
         }
 
         try {
-            Optional<ClusterData> cluster = pulsar.getConfigurationCache().clustersCache()
+            Optional<ClusterDataImpl> cluster = pulsar.getConfigurationCache().clustersCache()
                     .get(path("clusters", currentCluster));
             if (!cluster.isPresent() || cluster.get().getPeerClusterNames() == null) {
                 return null;
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/SLAMonitoringTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/SLAMonitoringTest.java
index 4437b43..2ee0829 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/SLAMonitoringTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/SLAMonitoringTest.java
@@ -36,9 +36,9 @@ import lombok.extern.slf4j.Slf4j;
 import org.apache.pulsar.broker.namespace.NamespaceService;
 import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.client.admin.PulsarAdminException;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.NamespaceOwnershipStatus;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.zookeeper.LocalBookkeeperEnsemble;
 import org.testng.Assert;
 import org.testng.annotations.AfterClass;
@@ -108,12 +108,12 @@ public class SLAMonitoringTest {
 
     private void createTenant(PulsarAdmin pulsarAdmin)
             throws PulsarAdminException {
-        ClusterData clusterData = new ClusterData();
+        ClusterDataImpl clusterData = new ClusterDataImpl();
         clusterData.setServiceUrl(pulsarAdmin.getServiceUrl());
         pulsarAdmins[0].clusters().createCluster("my-cluster", clusterData);
         Set<String> allowedClusters = new HashSet<>();
         allowedClusters.add("my-cluster");
-        TenantInfo adminConfig = new TenantInfo();
+        TenantInfoImpl adminConfig = new TenantInfoImpl();
         adminConfig.setAllowedClusters(allowedClusters);
         Set<String> adminRoles = new HashSet<>();
         adminRoles.add("");
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiDelayedDelivery.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiDelayedDelivery.java
index 304b79e..d5658ed 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiDelayedDelivery.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiDelayedDelivery.java
@@ -24,9 +24,9 @@ import lombok.extern.slf4j.Slf4j;
 import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
 import org.apache.pulsar.client.api.*;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.DelayedDeliveryPolicies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -51,8 +51,8 @@ public class AdminApiDelayedDelivery extends MockedPulsarServiceBaseTest {
     public void setup() throws Exception {
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("delayed-delivery-messages", tenantInfo);
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiGetLastMessageIdTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiGetLastMessageIdTest.java
index fb20be6..a0d653b 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiGetLastMessageIdTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiGetLastMessageIdTest.java
@@ -27,8 +27,8 @@ import org.apache.pulsar.client.api.MessageId;
 import org.apache.pulsar.client.api.MessageRoutingMode;
 import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.impl.MessageIdImpl;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeClass;
@@ -70,9 +70,9 @@ public class AdminApiGetLastMessageIdTest extends MockedPulsarServiceBaseTest {
     @BeforeMethod
     protected void setup() throws Exception {
         super.internalSetup();
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("prop",
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("prop/ns-abc");
         admin.namespaces().setNamespaceReplicationClusters("prop/ns-abc", Sets.newHashSet("test"));
         persistentTopics = spy(new PersistentTopics());
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiMaxUnackedMessages.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiMaxUnackedMessages.java
index 9f57532..7c11e04 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiMaxUnackedMessages.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiMaxUnackedMessages.java
@@ -29,8 +29,8 @@ import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.api.SubscriptionType;
 import org.apache.pulsar.client.api.SubscriptionInitialPosition;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -51,8 +51,8 @@ public class AdminApiMaxUnackedMessages extends MockedPulsarServiceBaseTest {
     public void setup() throws Exception {
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("max-unacked-messages", tenantInfo);
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiOffloadTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiOffloadTest.java
index c59685a..b28aa9c 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiOffloadTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiOffloadTest.java
@@ -46,9 +46,10 @@ import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.impl.MessageIdImpl;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
+import org.apache.pulsar.common.policies.data.OffloadedReadPriority;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
@@ -74,8 +75,8 @@ public class AdminApiOffloadTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         // Setup namespaces
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant(testTenant, tenantInfo);
         admin.namespaces().createNamespace(myNamespace, Sets.newHashSet("test"));
     }
@@ -170,17 +171,17 @@ public class AdminApiOffloadTest extends MockedPulsarServiceBaseTest {
         String endpoint = "test-endpoint";
         long offloadThresholdInBytes = 0;
         long offloadDeletionLagInMillis = 100L;
-        OffloadPolicies.OffloadedReadPriority priority = OffloadPolicies.OffloadedReadPriority.TIERED_STORAGE_FIRST;
+        OffloadedReadPriority priority = OffloadedReadPriority.TIERED_STORAGE_FIRST;
 
-        OffloadPolicies offload1 = OffloadPolicies.create(
+        OffloadPoliciesImpl offload1 = OffloadPoliciesImpl.create(
                 driver, region, bucket, endpoint, null, null, null, null,
                 100, 100, offloadThresholdInBytes, offloadDeletionLagInMillis, priority);
         admin.namespaces().setOffloadPolicies(namespaceName, offload1);
-        OffloadPolicies offload2 = admin.namespaces().getOffloadPolicies(namespaceName);
+        OffloadPoliciesImpl offload2 = (OffloadPoliciesImpl) admin.namespaces().getOffloadPolicies(namespaceName);
         assertEquals(offload1, offload2);
 
         admin.namespaces().removeOffloadPolicies(namespaceName);
-        OffloadPolicies offload3 = admin.namespaces().getOffloadPolicies(namespaceName);
+        OffloadPoliciesImpl offload3 = (OffloadPoliciesImpl) admin.namespaces().getOffloadPolicies(namespaceName);
         assertNull(offload3);
     }
 
@@ -191,9 +192,9 @@ public class AdminApiOffloadTest extends MockedPulsarServiceBaseTest {
         pulsarClient.newProducer().topic(topicName).create().close();
         Awaitility.await()
                 .until(() -> pulsar.getTopicPoliciesService().cacheIsInitialized(TopicName.get(topicName)));
-        OffloadPolicies offloadPolicies = admin.topics().getOffloadPolicies(topicName);
+        OffloadPoliciesImpl offloadPolicies = (OffloadPoliciesImpl) admin.topics().getOffloadPolicies(topicName);
         assertNull(offloadPolicies);
-        OffloadPolicies offload = new OffloadPolicies();
+        OffloadPoliciesImpl offload = new OffloadPoliciesImpl();
         String path = "fileSystemPath";
         offload.setFileSystemProfilePath(path);
         admin.topics().setOffloadPolicies(topicName, offload);
@@ -214,8 +215,8 @@ public class AdminApiOffloadTest extends MockedPulsarServiceBaseTest {
         pulsarClient.newProducer().topic(topicName).create().close();
         Awaitility.await()
                 .until(() -> pulsar.getTopicPoliciesService().cacheIsInitialized(TopicName.get(topicName)));
-        OffloadPolicies offloadPolicies = admin.topics().getOffloadPolicies(topicName, true);
-        OffloadPolicies brokerPolicies = OffloadPolicies
+        OffloadPoliciesImpl offloadPolicies = (OffloadPoliciesImpl) admin.topics().getOffloadPolicies(topicName, true);
+        OffloadPoliciesImpl brokerPolicies = OffloadPoliciesImpl
                 .mergeConfiguration(null,null, pulsar.getConfiguration().getProperties());
 
         assertEquals(offloadPolicies, brokerPolicies);
@@ -224,7 +225,7 @@ public class AdminApiOffloadTest extends MockedPulsarServiceBaseTest {
         when(topicOffloaded.getOffloadDriverName()).thenReturn("mock");
         doReturn(topicOffloaded).when(pulsar).createManagedLedgerOffloader(any());
 
-        OffloadPolicies namespacePolicies = new OffloadPolicies();
+        OffloadPoliciesImpl namespacePolicies = new OffloadPoliciesImpl();
         namespacePolicies.setManagedLedgerOffloadThresholdInBytes(100L);
         namespacePolicies.setManagedLedgerOffloadDeletionLagInMillis(200L);
         namespacePolicies.setManagedLedgerOffloadDriver("s3");
@@ -235,7 +236,7 @@ public class AdminApiOffloadTest extends MockedPulsarServiceBaseTest {
         assertEquals(
                 admin.topics().getOffloadPolicies(topicName, true), namespacePolicies);
 
-        OffloadPolicies topicPolicies = new OffloadPolicies();
+        OffloadPoliciesImpl topicPolicies = new OffloadPoliciesImpl();
         topicPolicies.setManagedLedgerOffloadThresholdInBytes(200L);
         topicPolicies.setManagedLedgerOffloadDeletionLagInMillis(400L);
         topicPolicies.setManagedLedgerOffloadDriver("s3");
@@ -293,7 +294,7 @@ public class AdminApiOffloadTest extends MockedPulsarServiceBaseTest {
                     , "NullLedgerOffloader");
         }
         //3 construct a topic level offloadPolicies
-        OffloadPolicies offloadPolicies = new OffloadPolicies();
+        OffloadPoliciesImpl offloadPolicies = new OffloadPoliciesImpl();
         offloadPolicies.setOffloadersDirectory(".");
         offloadPolicies.setManagedLedgerOffloadDriver("mock");
         offloadPolicies.setManagedLedgerOffloadPrefetchRounds(10);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaAutoUpdateTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaAutoUpdateTest.java
index 4d5bd13..6138746 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaAutoUpdateTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaAutoUpdateTest.java
@@ -32,8 +32,8 @@ import org.apache.pulsar.common.policies.data.SchemaCompatibilityStrategy;
 import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.api.PulsarClientException;
 import org.apache.pulsar.client.api.Schema;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.SchemaAutoUpdateCompatibilityStrategy;
 
 import org.slf4j.Logger;
@@ -55,8 +55,8 @@ public class AdminApiSchemaAutoUpdateTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         // Setup namespaces
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz/ns1", Sets.newHashSet("test"));
         admin.namespaces().createNamespace("prop-xyz/test/ns1");
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaTest.java
index 177d204..7153311 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaTest.java
@@ -41,10 +41,10 @@ import org.apache.pulsar.client.api.MessageId;
 import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.client.api.schema.SchemaDefinition;
 import org.apache.pulsar.client.impl.schema.StringSchema;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
 import org.apache.pulsar.common.policies.data.SchemaAutoUpdateCompatibilityStrategy;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.schema.SchemaInfo;
 import org.apache.pulsar.common.schema.SchemaInfoWithVersion;
 import org.testng.annotations.AfterMethod;
@@ -66,8 +66,8 @@ public class AdminApiSchemaTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         // Setup namespaces
-        admin.clusters().createCluster(cluster, new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster(cluster, new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("schematest", tenantInfo);
         admin.namespaces().createNamespace("schematest/test", Sets.newHashSet("test"));
         admin.namespaces().createNamespace("schematest/"+cluster+"/test", Sets.newHashSet("test"));
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaValidationEnforced.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaValidationEnforced.java
index 2056ed4..465c1df 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaValidationEnforced.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiSchemaValidationEnforced.java
@@ -30,8 +30,8 @@ import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.api.PulsarClientException;
 import org.apache.pulsar.client.api.Schema;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.protocol.schema.PostSchemaPayload;
 import org.apache.pulsar.common.schema.SchemaInfo;
 import org.apache.pulsar.common.schema.SchemaType;
@@ -55,8 +55,8 @@ public class AdminApiSchemaValidationEnforced extends MockedPulsarServiceBaseTes
     public void setup() throws Exception {
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("schema-validation-enforced", tenantInfo);
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTest.java
index 350eb5c..58255f7 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTest.java
@@ -36,9 +36,7 @@ import com.google.common.collect.Maps;
 import com.google.common.collect.Range;
 import com.google.common.collect.Sets;
 import com.google.common.hash.Hashing;
-import com.google.gson.Gson;
-import com.google.gson.GsonBuilder;
-import com.google.gson.JsonObject;
+
 import java.lang.reflect.Field;
 import java.net.URL;
 import java.util.ArrayList;
@@ -105,15 +103,16 @@ import org.apache.pulsar.common.naming.TopicDomain;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.partition.PartitionedTopicMetadata;
 import org.apache.pulsar.common.policies.data.AuthAction;
-import org.apache.pulsar.common.policies.data.AutoFailoverPolicyData;
+import org.apache.pulsar.common.policies.data.AutoFailoverPolicyDataImpl;
 import org.apache.pulsar.common.policies.data.AutoFailoverPolicyType;
 import org.apache.pulsar.common.policies.data.BacklogQuota;
 import org.apache.pulsar.common.policies.data.BacklogQuota.BacklogQuotaType;
 import org.apache.pulsar.common.policies.data.BacklogQuota.RetentionPolicy;
 import org.apache.pulsar.common.policies.data.BrokerAssignment;
 import org.apache.pulsar.common.policies.data.BrokerInfo;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.ConsumerStats;
+import org.apache.pulsar.common.policies.data.NamespaceIsolationDataImpl;
 import org.apache.pulsar.common.policies.data.NamespaceIsolationData;
 import org.apache.pulsar.common.policies.data.NamespaceOwnershipStatus;
 import org.apache.pulsar.common.policies.data.PartitionedTopicInternalStats;
@@ -121,9 +120,10 @@ import org.apache.pulsar.common.policies.data.PartitionedTopicStats;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
 import org.apache.pulsar.common.policies.data.Policies;
+import org.apache.pulsar.common.policies.data.PoliciesUtil;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
 import org.apache.pulsar.common.policies.data.SubscriptionStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicStats;
 import org.apache.pulsar.common.util.Codec;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
@@ -185,8 +185,8 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
         otheradmin = mockPulsarSetup.getAdmin();
 
         // Setup namespaces
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz/ns1", Sets.newHashSet("test"));
     }
@@ -233,26 +233,26 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
     @Test
     public void clusters() throws Exception {
         admin.clusters().createCluster("usw",
-                new ClusterData("http://broker.messaging.use.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.use.example.com:8080"));
         // "test" cluster is part of config-default cluster and it's znode gets created when PulsarService creates
         // failure-domain znode of this default cluster
         assertEquals(admin.clusters().getClusters(), Lists.newArrayList("test", "usw"));
 
         assertEquals(admin.clusters().getCluster("test"),
-                new ClusterData(pulsar.getWebServiceAddress()));
+                new ClusterDataImpl(pulsar.getWebServiceAddress()));
 
         admin.clusters().updateCluster("usw",
-                new ClusterData("http://new-broker.messaging.usw.example.com:8080"));
+                new ClusterDataImpl("http://new-broker.messaging.usw.example.com:8080"));
         assertEquals(admin.clusters().getClusters(), Lists.newArrayList("test", "usw"));
         assertEquals(admin.clusters().getCluster("usw"),
-                new ClusterData("http://new-broker.messaging.usw.example.com:8080"));
+                new ClusterDataImpl("http://new-broker.messaging.usw.example.com:8080"));
 
         admin.clusters().updateCluster("usw",
-                new ClusterData("http://new-broker.messaging.usw.example.com:8080",
+                new ClusterDataImpl("http://new-broker.messaging.usw.example.com:8080",
                         "https://new-broker.messaging.usw.example.com:4443"));
         assertEquals(admin.clusters().getClusters(), Lists.newArrayList("test", "usw"));
         assertEquals(admin.clusters().getCluster("usw"),
-                new ClusterData("http://new-broker.messaging.usw.example.com:8080",
+                new ClusterDataImpl("http://new-broker.messaging.usw.example.com:8080",
                         "https://new-broker.messaging.usw.example.com:4443"));
 
         admin.clusters().deleteCluster("usw");
@@ -266,7 +266,7 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
 
         // Check name validation
         try {
-            admin.clusters().createCluster("bf!", new ClusterData("http://dummy.messaging.example.com"));
+            admin.clusters().createCluster("bf!", new ClusterDataImpl("http://dummy.messaging.example.com"));
             fail("should have failed");
         } catch (PulsarAdminException e) {
             assertTrue(e instanceof PreconditionFailedException);
@@ -278,14 +278,14 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
         try {
             // create
             String policyName1 = "policy-1";
-            NamespaceIsolationData nsPolicyData1 = new NamespaceIsolationData();
+            NamespaceIsolationDataImpl nsPolicyData1 = new NamespaceIsolationDataImpl();
             nsPolicyData1.namespaces = new ArrayList<String>();
             nsPolicyData1.namespaces.add("other/use/other.*");
             nsPolicyData1.primary = new ArrayList<String>();
             nsPolicyData1.primary.add("prod1-broker[4-6].messaging.use.example.com");
             nsPolicyData1.secondary = new ArrayList<String>();
             nsPolicyData1.secondary.add("prod1-broker.*.messaging.use.example.com");
-            nsPolicyData1.auto_failover_policy = new AutoFailoverPolicyData();
+            nsPolicyData1.auto_failover_policy = new AutoFailoverPolicyDataImpl();
             nsPolicyData1.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
             nsPolicyData1.auto_failover_policy.parameters = new HashMap<String, String>();
             nsPolicyData1.auto_failover_policy.parameters.put("min_limit", "1");
@@ -293,14 +293,14 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
             admin.clusters().createNamespaceIsolationPolicy("test", policyName1, nsPolicyData1);
 
             String policyName2 = "policy-2";
-            NamespaceIsolationData nsPolicyData2 = new NamespaceIsolationData();
+            NamespaceIsolationDataImpl nsPolicyData2 = new NamespaceIsolationDataImpl();
             nsPolicyData2.namespaces = new ArrayList<String>();
             nsPolicyData2.namespaces.add("other/use/other.*");
             nsPolicyData2.primary = new ArrayList<String>();
             nsPolicyData2.primary.add("prod1-broker[4-6].messaging.use.example.com");
             nsPolicyData2.secondary = new ArrayList<String>();
             nsPolicyData2.secondary.add("prod1-broker.*.messaging.use.example.com");
-            nsPolicyData2.auto_failover_policy = new AutoFailoverPolicyData();
+            nsPolicyData2.auto_failover_policy = new AutoFailoverPolicyDataImpl();
             nsPolicyData2.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
             nsPolicyData2.auto_failover_policy.parameters = new HashMap<String, String>();
             nsPolicyData2.auto_failover_policy.parameters.put("min_limit", "1");
@@ -308,7 +308,7 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
             admin.clusters().createNamespaceIsolationPolicy("test", policyName2, nsPolicyData2);
 
             // verify create indirectly with get
-            Map<String, NamespaceIsolationData> policiesMap = admin.clusters().getNamespaceIsolationPolicies("test");
+            Map<String, ? extends NamespaceIsolationData> policiesMap = admin.clusters().getNamespaceIsolationPolicies("test");
             assertEquals(policiesMap.get(policyName1), nsPolicyData1);
             assertEquals(policiesMap.get(policyName2), nsPolicyData2);
 
@@ -347,7 +347,7 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
             assertEquals(policiesMap.get(policyName1), nsPolicyData1);
 
             // verify single get
-            NamespaceIsolationData policy1Data = admin.clusters().getNamespaceIsolationPolicy("test", policyName1);
+            NamespaceIsolationDataImpl policy1Data = (NamespaceIsolationDataImpl) admin.clusters().getNamespaceIsolationPolicy("test", policyName1);
             assertEquals(policy1Data, nsPolicyData1);
 
             // verify creation of more than one policy
@@ -419,12 +419,12 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
         }
 
         // validate regex: invlid regex for primary and seconday
-        NamespaceIsolationData nsRegexPolicy = new NamespaceIsolationData();
+        NamespaceIsolationDataImpl nsRegexPolicy = new NamespaceIsolationDataImpl();
         nsRegexPolicy.namespaces = new ArrayList<String>();
         nsRegexPolicy.namespaces.add("other/use/other.*");
         nsRegexPolicy.primary = new ArrayList<String>();
         nsRegexPolicy.primary.add("prod1-broker[45-46].messaging.use.example.com");
-        nsRegexPolicy.auto_failover_policy = new AutoFailoverPolicyData();
+        nsRegexPolicy.auto_failover_policy = new AutoFailoverPolicyDataImpl();
         nsRegexPolicy.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
         nsRegexPolicy.auto_failover_policy.parameters = new HashMap<String, String>();
         nsRegexPolicy.auto_failover_policy.parameters.put("min_limit", "1");
@@ -656,14 +656,14 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
         }
 
         Set<String> allowedClusters = Sets.newHashSet("test");
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), allowedClusters);
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), allowedClusters);
         admin.tenants().updateTenant("prop-xyz", tenantInfo);
 
         assertEquals(admin.tenants().getTenants(), Lists.newArrayList("prop-xyz"));
 
         assertEquals(admin.tenants().getTenantInfo("prop-xyz"), tenantInfo);
 
-        TenantInfo newTenantAdmin = new TenantInfo(Sets.newHashSet("role3", "role4"), allowedClusters);
+        TenantInfoImpl newTenantAdmin = new TenantInfoImpl(Sets.newHashSet("role3", "role4"), allowedClusters);
         admin.tenants().updateTenant("prop-xyz", newTenantAdmin);
 
         assertEquals(admin.tenants().getTenantInfo("prop-xyz"), newTenantAdmin);
@@ -683,12 +683,12 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
 
     @Test
     public void namespaces() throws Exception {
-        admin.clusters().createCluster("usw", new ClusterData());
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"),
+        admin.clusters().createCluster("usw", new ClusterDataImpl());
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"),
                 Sets.newHashSet("test", "usw"));
         admin.tenants().updateTenant("prop-xyz", tenantInfo);
 
-        assertEquals(admin.namespaces().getPolicies("prop-xyz/ns1").bundles, Policies.defaultBundle());
+        assertEquals(admin.namespaces().getPolicies("prop-xyz/ns1").bundles, PoliciesUtil.defaultBundle());
 
         admin.namespaces().createNamespace("prop-xyz/ns2", Sets.newHashSet("test"));
 
@@ -723,7 +723,7 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
 
         Policies policies = new Policies();
         policies.replication_clusters = Sets.newHashSet("test");
-        policies.bundles = Policies.defaultBundle();
+        policies.bundles = PoliciesUtil.defaultBundle();
         policies.auth_policies.namespace_auth.put("spiffe://developer/passport-role", EnumSet.allOf(AuthAction.class));
         policies.auth_policies.namespace_auth.put("my-role", EnumSet.allOf(AuthAction.class));
 
@@ -1094,23 +1094,21 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
         String partitionTopic0 = partitionedTopicName + "-partition-0";
         String partitionTopic1 = partitionedTopicName + "-partition-1";
 
-        JsonObject partitionTopic0Info = admin.topics().getInternalInfo(partitionTopic0);
-        JsonObject partitionTopic1Info = admin.topics().getInternalInfo(partitionTopic1);
-
-        Gson gson = new GsonBuilder().create();
+        String partitionTopic0InfoResponse = admin.topics().getInternalInfo(partitionTopic0);
+        String partitionTopic1InfoResponse = admin.topics().getInternalInfo(partitionTopic1);
 
         // expected managed info
         PartitionedManagedLedgerInfo partitionedManagedLedgerInfo = new PartitionedManagedLedgerInfo();
         partitionedManagedLedgerInfo.version = 0L;
         partitionedManagedLedgerInfo.partitions.put(partitionTopic0,
-                ObjectMapperFactory.getThreadLocal().readValue(gson.toJson(partitionTopic0Info), ManagedLedgerInfo.class));
+            ObjectMapperFactory.getThreadLocal().readValue(partitionTopic0InfoResponse, ManagedLedgerInfo.class));
         partitionedManagedLedgerInfo.partitions.put(partitionTopic1,
-                ObjectMapperFactory.getThreadLocal().readValue(gson.toJson(partitionTopic1Info), ManagedLedgerInfo.class));
+            ObjectMapperFactory.getThreadLocal().readValue(partitionTopic1InfoResponse, ManagedLedgerInfo.class));
 
         String expectedResult = ObjectMapperFactory.getThreadLocal().writeValueAsString(partitionedManagedLedgerInfo);
 
-        JsonObject partitionTopicInfo = admin.topics().getInternalInfo(partitionedTopicName);
-        assertEquals(gson.toJson(partitionTopicInfo), expectedResult);
+        String partitionTopicInfoResponse = admin.topics().getInternalInfo(partitionedTopicName);
+        assertEquals(partitionTopicInfoResponse, expectedResult);
     }
 
     @Test
@@ -1183,7 +1181,7 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
 
         // create tenant
         admin.tenants().createTenant(tenant,
-                new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test")));
 
         assertTrue(admin.tenants().getTenants().contains(tenant));
 
@@ -1214,7 +1212,7 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
         assertFalse(admin.tenants().getTenants().contains(tenant));
 
         admin.tenants().createTenant(tenant,
-                new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test")));
         assertTrue(admin.tenants().getTenants().contains(tenant));
         assertTrue(admin.namespaces().getNamespaces(tenant).isEmpty());
 
@@ -1232,7 +1230,7 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
 
         // create tenant
         admin.tenants().createTenant(tenant,
-                new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test")));
 
         assertTrue(admin.tenants().getTenants().contains(tenant));
 
@@ -2205,12 +2203,12 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
     @Test
     public void testObjectWithUnknownProperties() {
 
-        class CustomTenantAdmin extends TenantInfo {
+        class CustomTenantAdmin extends TenantInfoImpl {
             @SuppressWarnings("unused")
             public int newTenant;
         }
 
-        TenantInfo pa = new TenantInfo(Sets.newHashSet("test_appid1", "test_appid2"), Sets.newHashSet("test"));
+        TenantInfoImpl pa = new TenantInfoImpl(Sets.newHashSet("test_appid1", "test_appid2"), Sets.newHashSet("test"));
         CustomTenantAdmin cpa = new CustomTenantAdmin();
         cpa.setAdminRoles(pa.getAdminRoles());
         cpa.setAllowedClusters(pa.getAllowedClusters());
@@ -2597,8 +2595,8 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testTopicBundleRangeLookup() throws PulsarAdminException, PulsarServerException, Exception {
-        admin.clusters().createCluster("usw", new ClusterData());
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"),
+        admin.clusters().createCluster("usw", new ClusterDataImpl());
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"),
                 Sets.newHashSet("test", "usw"));
         admin.tenants().updateTenant("prop-xyz", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz/getBundleNs", 100);
@@ -2781,8 +2779,8 @@ public class AdminApiTest extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testCreateAndDeleteNamespaceWithBundles() throws Exception {
-        admin.clusters().createCluster("usw", new ClusterData());
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"),
+        admin.clusters().createCluster("usw", new ClusterDataImpl());
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"),
                 Sets.newHashSet("test", "usw"));
         admin.tenants().updateTenant("prop-xyz", tenantInfo);
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTest2.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTest2.java
index 0e5d52b..d9e1eae 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTest2.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTest2.java
@@ -41,7 +41,6 @@ import java.util.HashMap;
 import java.util.HashSet;
 import java.util.List;
 import java.util.Map;
-import java.util.Objects;
 import java.util.Optional;
 import java.util.Set;
 import java.util.UUID;
@@ -79,19 +78,21 @@ import org.apache.pulsar.client.impl.MessageIdImpl;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicDomain;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.AutoFailoverPolicyData;
+import org.apache.pulsar.common.policies.data.AutoFailoverPolicyDataImpl;
 import org.apache.pulsar.common.policies.data.AutoFailoverPolicyType;
+import org.apache.pulsar.common.policies.data.BrokerNamespaceIsolationDataImpl;
 import org.apache.pulsar.common.policies.data.BrokerNamespaceIsolationData;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.ConsumerStats;
+import org.apache.pulsar.common.policies.data.FailureDomainImpl;
 import org.apache.pulsar.common.policies.data.FailureDomain;
-import org.apache.pulsar.common.policies.data.NamespaceIsolationData;
+import org.apache.pulsar.common.policies.data.NamespaceIsolationDataImpl;
 import org.apache.pulsar.common.policies.data.PartitionedTopicStats;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
 import org.apache.pulsar.common.policies.data.SubscriptionStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicStats;
 import org.awaitility.Awaitility;
 import org.testng.Assert;
@@ -119,8 +120,8 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         mockPulsarSetup.setup();
 
         // Setup namespaces
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz/ns1", Sets.newHashSet("test"));
     }
@@ -258,8 +259,8 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         conf.setTopicLevelPoliciesEnabled(true);
         super.internalSetup();
         admin.clusters().createCluster("test"
-                , new ClusterData(pulsar.getWebServiceAddress() + ",localhost:1026," + "localhost:2050"));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+                , new ClusterDataImpl(pulsar.getWebServiceAddress() + ",localhost:1026," + "localhost:2050"));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz/ns1", Sets.newHashSet("test"));
         conf.setBrokerServicePort(Optional.of(1024));
@@ -654,13 +655,13 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
     @Test
     public void testPeerCluster() throws Exception {
         admin.clusters().createCluster("us-west1",
-                new ClusterData("http://broker.messaging.west1.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west1.example.com:8080"));
         admin.clusters().createCluster("us-west2",
-                new ClusterData("http://broker.messaging.west2.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west2.example.com:8080"));
         admin.clusters().createCluster("us-east1",
-                new ClusterData("http://broker.messaging.east1.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.east1.example.com:8080"));
         admin.clusters().createCluster("us-east2",
-                new ClusterData("http://broker.messaging.east2.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.east2.example.com:8080"));
 
         admin.clusters().updatePeerClusterNames("us-west1", Sets.newLinkedHashSet(Lists.newArrayList("us-west2")));
         assertEquals(admin.clusters().getCluster("us-west1").getPeerClusterNames(), Lists.newArrayList("us-west2"));
@@ -699,18 +700,18 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
     @Test
     public void testReplicationPeerCluster() throws Exception {
         admin.clusters().createCluster("us-west1",
-                new ClusterData("http://broker.messaging.west1.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west1.example.com:8080"));
         admin.clusters().createCluster("us-west2",
-                new ClusterData("http://broker.messaging.west2.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west2.example.com:8080"));
         admin.clusters().createCluster("us-west3",
-                new ClusterData("http://broker.messaging.west2.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west2.example.com:8080"));
         admin.clusters().createCluster("us-west4",
-                new ClusterData("http://broker.messaging.west2.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west2.example.com:8080"));
         admin.clusters().createCluster("us-east1",
-                new ClusterData("http://broker.messaging.east1.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.east1.example.com:8080"));
         admin.clusters().createCluster("us-east2",
-                new ClusterData("http://broker.messaging.east2.example.com:8080"));
-        admin.clusters().createCluster("global", new ClusterData());
+                new ClusterDataImpl("http://broker.messaging.east2.example.com:8080"));
+        admin.clusters().createCluster("global", new ClusterDataImpl());
 
         List<String> allClusters = admin.clusters().getClusters();
         Collections.sort(allClusters);
@@ -720,7 +721,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         final String property = "peer-prop";
         Set<String> allowedClusters = Sets.newHashSet("us-west1", "us-west2", "us-west3", "us-west4", "us-east1",
                 "us-east2", "global");
-        TenantInfo propConfig = new TenantInfo(Sets.newHashSet("test"), allowedClusters);
+        TenantInfoImpl propConfig = new TenantInfoImpl(Sets.newHashSet("test"), allowedClusters);
         admin.tenants().createTenant(property, propConfig);
 
         final String namespace = property + "/global/conflictPeer";
@@ -758,7 +759,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
 
         final String cluster = pulsar.getConfiguration().getClusterName();
         // create
-        FailureDomain domain = new FailureDomain();
+        FailureDomainImpl domain = new FailureDomainImpl();
         domain.setBrokers(Sets.newHashSet("b1", "b2", "b3"));
         admin.clusters().createFailureDomain(cluster, "domain-1", domain);
         admin.clusters().updateFailureDomain(cluster, "domain-1", domain);
@@ -894,7 +895,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testTenantNameWithUnderscore() throws Exception {
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop_xyz", tenantInfo);
 
         admin.namespaces().createNamespace("prop_xyz/my-namespace", Sets.newHashSet("test"));
@@ -911,7 +912,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testTenantNameWithInvalidCharacters() {
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
 
         // If we try to create property with invalid characters, it should fail immediately
         try {
@@ -935,7 +936,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         assertFalse(admin.clusters().getClusters().contains("cluster-non-existing"));
 
         Set<String> allowedClusters = Sets.newHashSet("cluster-non-existing");
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), allowedClusters);
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), allowedClusters);
 
         // If we try to create tenant with nonexistent clusters, it should fail immediately
         try {
@@ -968,14 +969,14 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         String namespaceRegex = "other/" + cluster + "/other.*";
         String brokerName = pulsar.getAdvertisedAddress();
         String brokerAddress = brokerName + ":" + pulsar.getConfiguration().getWebServicePort().get();
-        NamespaceIsolationData nsPolicyData1 = new NamespaceIsolationData();
+        NamespaceIsolationDataImpl nsPolicyData1 = new NamespaceIsolationDataImpl();
         nsPolicyData1.namespaces = new ArrayList<>();
         nsPolicyData1.namespaces.add(namespaceRegex);
         nsPolicyData1.primary = new ArrayList<>();
         nsPolicyData1.primary.add(brokerName + ":[0-9]*");
         nsPolicyData1.secondary = new ArrayList<>();
         nsPolicyData1.secondary.add(brokerName + ".*");
-        nsPolicyData1.auto_failover_policy = new AutoFailoverPolicyData();
+        nsPolicyData1.auto_failover_policy = new AutoFailoverPolicyDataImpl();
         nsPolicyData1.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
         nsPolicyData1.auto_failover_policy.parameters = new HashMap<>();
         nsPolicyData1.auto_failover_policy.parameters.put("min_limit", "1");
@@ -985,17 +986,18 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         List<BrokerNamespaceIsolationData> brokerIsolationDataList = admin.clusters()
                 .getBrokersWithNamespaceIsolationPolicy(cluster);
         assertEquals(brokerIsolationDataList.size(), 1);
-        assertEquals(brokerIsolationDataList.get(0).brokerName, brokerAddress);
-        assertEquals(brokerIsolationDataList.get(0).namespaceRegex.size(), 1);
-        assertEquals(brokerIsolationDataList.get(0).namespaceRegex.get(0), namespaceRegex);
+        assertEquals(brokerIsolationDataList.get(0).getBrokerName(), brokerAddress);
+        assertEquals(brokerIsolationDataList.get(0).getNamespaceRegex().size(), 1);
+        assertEquals(brokerIsolationDataList.get(0).getNamespaceRegex().get(0), namespaceRegex);
 
-        BrokerNamespaceIsolationData brokerIsolationData = admin.clusters()
+        BrokerNamespaceIsolationDataImpl brokerIsolationData = (BrokerNamespaceIsolationDataImpl) admin.clusters()
                 .getBrokerWithNamespaceIsolationPolicy(cluster, brokerAddress);
         assertEquals(brokerIsolationData.brokerName, brokerAddress);
         assertEquals(brokerIsolationData.namespaceRegex.size(), 1);
         assertEquals(brokerIsolationData.namespaceRegex.get(0), namespaceRegex);
 
-        BrokerNamespaceIsolationData isolationData = admin.clusters().getBrokerWithNamespaceIsolationPolicy(cluster, "invalid-broker");
+        BrokerNamespaceIsolationDataImpl isolationData = (BrokerNamespaceIsolationDataImpl) admin.clusters()
+                .getBrokerWithNamespaceIsolationPolicy(cluster, "invalid-broker");
         assertFalse(isolationData.isPrimary);
     }
 
@@ -1017,12 +1019,12 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         // create
         String policyName1 = "policy-1";
         String cluster = pulsar.getConfiguration().getClusterName();
-        NamespaceIsolationData nsPolicyData1 = new NamespaceIsolationData();
+        NamespaceIsolationDataImpl nsPolicyData1 = new NamespaceIsolationDataImpl();
         nsPolicyData1.namespaces = new ArrayList<>();
         nsPolicyData1.namespaces.add(ns1Name);
         nsPolicyData1.primary = new ArrayList<>();
         nsPolicyData1.primary.add(brokerName + ".*");
-        nsPolicyData1.auto_failover_policy = new AutoFailoverPolicyData();
+        nsPolicyData1.auto_failover_policy = new AutoFailoverPolicyDataImpl();
         nsPolicyData1.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
         nsPolicyData1.auto_failover_policy.parameters = new HashMap<>();
         nsPolicyData1.auto_failover_policy.parameters.put("min_limit", "1");
@@ -1057,7 +1059,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
     @Test
     public void clustersList() throws PulsarAdminException {
         final String cluster = pulsar.getConfiguration().getClusterName();
-        admin.clusters().createCluster("global", new ClusterData("http://localhost:6650"));
+        admin.clusters().createCluster("global", new ClusterDataImpl("http://localhost:6650"));
 
         // Global cluster, if there, should be omitted from the results
         assertEquals(admin.clusters().getClusters(), Lists.newArrayList(cluster));
@@ -1436,7 +1438,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testListOfNamespaceBundles() throws Exception {
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop-xyz2", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz2/ns1", 10);
         admin.namespaces().setNamespaceReplicationClusters("prop-xyz2/ns1", Sets.newHashSet("test"));
@@ -1449,7 +1451,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
     public void testForceDeleteNamespace() throws Exception {
         conf.setForceDeleteNamespaceAllowed(true);
         final String namespaceName = "prop-xyz2/ns1";
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop-xyz2", tenantInfo);
         admin.namespaces().createNamespace(namespaceName, 1);
         final String topic = "persistent://" + namespaceName + "/test" + UUID.randomUUID();
@@ -1465,7 +1467,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testUpdateClusterWithProxyUrl() throws Exception {
-        ClusterData cluster = new ClusterData(pulsar.getWebServiceAddress());
+        ClusterDataImpl cluster = new ClusterDataImpl(pulsar.getWebServiceAddress());
         String clusterName = "test2";
         admin.clusters().createCluster(clusterName, cluster);
         Assert.assertEquals(admin.clusters().getCluster(clusterName), cluster);
@@ -1482,8 +1484,8 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         super.internalCleanup();
         conf.setMaxNamespacesPerTenant(2);
         super.internalSetup();
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace("testTenant/ns1", Sets.newHashSet("test"));
         admin.namespaces().createNamespace("testTenant/ns2", Sets.newHashSet("test"));
@@ -1498,7 +1500,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         super.internalCleanup();
         conf.setMaxNamespacesPerTenant(0);
         super.internalSetup();
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("testTenant", tenantInfo);
         for (int i = 0; i < 10; i++) {
             admin.namespaces().createNamespace("testTenant/ns-" + i, Sets.newHashSet("test"));
@@ -1510,8 +1512,8 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         super.internalCleanup();
         conf.setMaxTopicsPerNamespace(10);
         super.internalSetup();
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace("testTenant/ns1", Sets.newHashSet("test"));
 
@@ -1533,7 +1535,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         super.internalCleanup();
         conf.setMaxTopicsPerNamespace(0);
         super.internalSetup();
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace("testTenant/ns1", Sets.newHashSet("test"));
         for (int i = 0; i < 10; ++i) {
@@ -1547,7 +1549,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         conf.setDefaultNumPartitions(3);
         conf.setAllowAutoTopicCreationType("partitioned");
         super.internalSetup();
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace("testTenant/ns1", Sets.newHashSet("test"));
 
@@ -1566,7 +1568,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         conf.setMaxTopicsPerNamespace(3);
         conf.setAllowAutoTopicCreationType("non-partitioned");
         super.internalSetup();
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace("testTenant/ns1", Sets.newHashSet("test"));
 
@@ -1601,8 +1603,8 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         conf.setMaxSubscriptionsPerTopic(2);
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace("testTenant/ns1", Sets.newHashSet("test"));
 
@@ -1626,7 +1628,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         conf.setMaxSubscriptionsPerTopic(0);
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace("testTenant/ns1", Sets.newHashSet("test"));
 
@@ -1642,7 +1644,7 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         conf.setMaxSubscriptionsPerTopic(2);
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace("testTenant/ns1", Sets.newHashSet("test"));
 
@@ -1751,8 +1753,8 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         conf.setMaxSubscriptionsPerTopic(brokerLevelMaxSub);
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         final String myNamespace = "prop-xyz/ns" + UUID.randomUUID();
         admin.namespaces().createNamespace(myNamespace, Sets.newHashSet("test"));
@@ -1808,8 +1810,8 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         conf.setMaxProducersPerTopic(maxProducersPerTopic);
         super.internalSetup();
         //init namespace
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         final String myNamespace = "prop-xyz/ns" + UUID.randomUUID();
         admin.namespaces().createNamespace(myNamespace, Sets.newHashSet("test"));
@@ -1861,8 +1863,8 @@ public class AdminApiTest2 extends MockedPulsarServiceBaseTest {
         conf.setMaxConsumersPerTopic(maxConsumersPerTopic);
         super.internalSetup();
         //init namespace
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         final String myNamespace = "prop-xyz/ns" + UUID.randomUUID();
         admin.namespaces().createNamespace(myNamespace, Sets.newHashSet("test"));
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTlsAuthTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTlsAuthTest.java
index b349733..6fe4033 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTlsAuthTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminApiTlsAuthTest.java
@@ -50,8 +50,8 @@ import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.common.tls.NoopHostnameVerifier;
 import org.apache.pulsar.common.policies.data.AuthAction;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.SecurityUtility;
 import org.glassfish.jersey.client.ClientConfig;
 import org.glassfish.jersey.client.ClientProperties;
@@ -96,7 +96,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         PulsarAdmin admin = buildAdminClient("admin");
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.close();
     }
 
@@ -152,7 +152,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testSuperUserCanListTenants() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("foobar"),
+                                         new TenantInfoImpl(ImmutableSet.of("foobar"),
                                                         ImmutableSet.of("test")));
             Assert.assertEquals(ImmutableSet.of("tenant1"), admin.tenants().getTenants());
         }
@@ -162,7 +162,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testProxyRoleCantListTenants() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("foobar"),
+                                         new TenantInfoImpl(ImmutableSet.of("foobar"),
                                                         ImmutableSet.of("test")));
         }
         try (PulsarAdmin admin = buildAdminClient("proxy")) {
@@ -177,7 +177,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testProxyRoleCantListNamespacesEvenWithAccess() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("proxy"),
+                                         new TenantInfoImpl(ImmutableSet.of("proxy"),
                                                         ImmutableSet.of("test")));
             admin.namespaces().createNamespace("tenant1/ns1");
         }
@@ -193,7 +193,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testAuthorizedUserAsOriginalPrincipal() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("proxy", "user1"),
+                                         new TenantInfoImpl(ImmutableSet.of("proxy", "user1"),
                                                         ImmutableSet.of("test")));
             admin.namespaces().createNamespace("tenant1/ns1");
         }
@@ -209,7 +209,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testUnauthorizedUserAsOriginalPrincipal() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("proxy", "user1"),
+                                         new TenantInfoImpl(ImmutableSet.of("proxy", "user1"),
                                                         ImmutableSet.of("test")));
             admin.namespaces().createNamespace("tenant1/ns1");
         }
@@ -229,7 +229,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testAuthorizedUserAsOriginalPrincipalButProxyNotAuthorized() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("user1"),
+                                         new TenantInfoImpl(ImmutableSet.of("user1"),
                                                         ImmutableSet.of("test")));
             admin.namespaces().createNamespace("tenant1/ns1");
         }
@@ -249,7 +249,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testAuthorizedUserAsOriginalPrincipalProxyIsSuperUser() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("user1"),
+                                         new TenantInfoImpl(ImmutableSet.of("user1"),
                                                         ImmutableSet.of("test")));
             admin.namespaces().createNamespace("tenant1/ns1");
         }
@@ -265,7 +265,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testUnauthorizedUserAsOriginalPrincipalProxyIsSuperUser() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("user1"),
+                                         new TenantInfoImpl(ImmutableSet.of("user1"),
                                                         ImmutableSet.of("test")));
             admin.namespaces().createNamespace("tenant1/ns1");
         }
@@ -285,7 +285,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testProxyUserViaProxy() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("proxy"),
+                                         new TenantInfoImpl(ImmutableSet.of("proxy"),
                                                         ImmutableSet.of("test")));
             admin.namespaces().createNamespace("tenant1/ns1");
         }
@@ -305,7 +305,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testSuperProxyUserAndAdminCanListTenants() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("user1"),
+                                         new TenantInfoImpl(ImmutableSet.of("user1"),
                                                         ImmutableSet.of("test")));
         }
         WebTarget root = buildWebClient("superproxy");
@@ -320,7 +320,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testSuperProxyUserAndNonAdminCannotListTenants() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("proxy"),
+                                         new TenantInfoImpl(ImmutableSet.of("proxy"),
                                                         ImmutableSet.of("test")));
         }
         WebTarget root = buildWebClient("superproxy");
@@ -339,7 +339,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
     public void testProxyCannotSetOriginalPrincipalAsEmpty() throws Exception {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("user1"),
+                                         new TenantInfoImpl(ImmutableSet.of("user1"),
                                                         ImmutableSet.of("test")));
             admin.namespaces().createNamespace("tenant1/ns1");
         }
@@ -361,7 +361,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
         try (PulsarAdmin admin = buildAdminClient("admin")) {
             log.info("Creating tenant");
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("admin"), ImmutableSet.of("test")));
+                                         new TenantInfoImpl(ImmutableSet.of("admin"), ImmutableSet.of("test")));
             log.info("Creating namespace, and granting perms to user1");
             admin.namespaces().createNamespace("tenant1/ns1", ImmutableSet.of("test"));
             admin.namespaces().grantPermissionOnNamespace("tenant1/ns1", "user1", ImmutableSet.of(AuthAction.produce));
@@ -405,7 +405,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
             // try to call admin-api which should fail due to incorrect key-cert
             try {
                 admin.tenants().createTenant("tenantX",
-                        new TenantInfo(ImmutableSet.of("foobar"), ImmutableSet.of("test")));
+                        new TenantInfoImpl(ImmutableSet.of("foobar"), ImmutableSet.of("test")));
                 Assert.fail("should have failed due to invalid key file");
             } catch (Exception e) {
                 //OK
@@ -418,7 +418,7 @@ public class AdminApiTlsAuthTest extends MockedPulsarServiceBaseTest {
             retryStrategically((test) -> {
                 try {
                     admin.tenants().createTenant("tenantX",
-                            new TenantInfo(ImmutableSet.of("foobar"), ImmutableSet.of("test")));
+                            new TenantInfoImpl(ImmutableSet.of("foobar"), ImmutableSet.of("test")));
                     success.setValue(true);
                     return true;
                 }catch(Exception e) {
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminTest.java
index b9a5b67..ee16384 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/AdminTest.java
@@ -77,14 +77,14 @@ import org.apache.pulsar.common.conf.InternalConfigurationData;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.policies.data.AuthAction;
-import org.apache.pulsar.common.policies.data.AutoFailoverPolicyData;
+import org.apache.pulsar.common.policies.data.AutoFailoverPolicyDataImpl;
 import org.apache.pulsar.common.policies.data.AutoFailoverPolicyType;
 import org.apache.pulsar.common.policies.data.BundlesData;
 import org.apache.pulsar.common.policies.data.BrokerInfo;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.NamespaceIsolationData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.NamespaceIsolationDataImpl;
 import org.apache.pulsar.common.policies.data.Policies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.ResourceQuota;
 import org.apache.pulsar.common.stats.AllocatorStats;
 import org.apache.pulsar.common.stats.Metrics;
@@ -218,7 +218,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         assertEquals(clusters.getClusters(), Lists.newArrayList());
         verify(clusters, never()).validateSuperUserAccess();
 
-        clusters.createCluster("use", new ClusterData("http://broker.messaging.use.example.com"));
+        clusters.createCluster("use", new ClusterDataImpl("http://broker.messaging.use.example.com"));
         verify(clusters, times(1)).validateSuperUserAccess();
         // ensure to read from ZooKeeper directly
         //clusters.clustersListCache().clear();
@@ -226,7 +226,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
 
         // Check creating existing cluster
         try {
-            clusters.createCluster("use", new ClusterData("http://broker.messaging.use.example.com"));
+            clusters.createCluster("use", new ClusterDataImpl("http://broker.messaging.use.example.com"));
             fail("should have failed");
         } catch (RestException e) {
             assertEquals(e.getResponse().getStatus(), Status.CONFLICT.getStatusCode());
@@ -240,13 +240,13 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
             assertEquals(e.getResponse().getStatus(), Status.NOT_FOUND.getStatusCode());
         }
 
-        assertEquals(clusters.getCluster("use"), new ClusterData("http://broker.messaging.use.example.com"));
+        assertEquals(clusters.getCluster("use"), new ClusterDataImpl("http://broker.messaging.use.example.com"));
         verify(clusters, times(4)).validateSuperUserAccess();
 
-        clusters.updateCluster("use", new ClusterData("http://new-broker.messaging.use.example.com"));
+        clusters.updateCluster("use", new ClusterDataImpl("http://new-broker.messaging.use.example.com"));
         verify(clusters, times(5)).validateSuperUserAccess();
 
-        assertEquals(clusters.getCluster("use"), new ClusterData("http://new-broker.messaging.use.example.com"));
+        assertEquals(clusters.getCluster("use"), new ClusterDataImpl("http://new-broker.messaging.use.example.com"));
         verify(clusters, times(6)).validateSuperUserAccess();
 
         try {
@@ -255,13 +255,13 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         } catch (RestException e) {
             assertEquals(e.getResponse().getStatus(), 404);
         }
-        NamespaceIsolationData policyData = new NamespaceIsolationData();
+        NamespaceIsolationDataImpl policyData = new NamespaceIsolationDataImpl();
         policyData.namespaces = new ArrayList<String>();
         policyData.namespaces.add("dummy/colo/ns");
         policyData.primary = new ArrayList<String>();
         policyData.primary.add("localhost" + ":" + pulsar.getListenPortHTTP());
         policyData.secondary = new ArrayList<String>();
-        policyData.auto_failover_policy = new AutoFailoverPolicyData();
+        policyData.auto_failover_policy = new AutoFailoverPolicyDataImpl();
         policyData.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
         policyData.auto_failover_policy.parameters = new HashMap<String, String>();
         policyData.auto_failover_policy.parameters.put("min_limit", "1");
@@ -292,7 +292,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         }
 
         try {
-            clusters.updateCluster("use", new ClusterData());
+            clusters.updateCluster("use", new ClusterDataImpl());
             fail("should have failed");
         } catch (RestException e) {
             assertEquals(e.getResponse().getStatus(), 404);
@@ -312,7 +312,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
             });
         configurationCache.clustersListCache().clear();
         // clear caches to load data from metadata-store again
-        MetadataCacheImpl<ClusterData> clusterCache = (MetadataCacheImpl<ClusterData>) pulsar.getPulsarResources()
+        MetadataCacheImpl<ClusterDataImpl> clusterCache = (MetadataCacheImpl<ClusterDataImpl>) pulsar.getPulsarResources()
                 .getClusterResources().getCache();
         MetadataCacheImpl isolationPolicyCache = (MetadataCacheImpl) pulsar.getPulsarResources()
                 .getNamespaceResources().getIsolationPolicies().getCache();
@@ -331,7 +331,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
                     && path.equals("/admin/clusters/test");
             });
         try {
-            clusters.createCluster("test", new ClusterData("http://broker.messaging.test.example.com"));
+            clusters.createCluster("test", new ClusterDataImpl("http://broker.messaging.test.example.com"));
             fail("should have failed");
         } catch (RestException e) {
             assertEquals(e.getResponse().getStatus(), Status.INTERNAL_SERVER_ERROR.getStatusCode());
@@ -344,7 +344,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         clusterCache.invalidateAll();
         store.invalidateAll();
         try {
-            clusters.updateCluster("test", new ClusterData("http://broker.messaging.test.example.com"));
+            clusters.updateCluster("test", new ClusterDataImpl("http://broker.messaging.test.example.com"));
             fail("should have failed");
         } catch (RestException e) {
             assertEquals(e.getResponse().getStatus(), Status.INTERNAL_SERVER_ERROR.getStatusCode());
@@ -390,7 +390,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
 
         // Check name validations
         try {
-            clusters.createCluster("bf@", new ClusterData("http://dummy.messaging.example.com"));
+            clusters.createCluster("bf@", new ClusterDataImpl("http://dummy.messaging.example.com"));
             fail("should have filed");
         } catch (RestException e) {
             assertEquals(e.getResponse().getStatus(), Status.PRECONDITION_FAILED.getStatusCode());
@@ -398,10 +398,10 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
 
         // Check authentication and listener name
         try {
-            clusters.createCluster("auth", new ClusterData("http://dummy.web.example.com", "",
+            clusters.createCluster("auth", new ClusterDataImpl("http://dummy.web.example.com", "",
                     "http://dummy.messaging.example.com", "",
                     "authenticationPlugin", "authenticationParameters", "listenerName"));
-            ClusterData cluster = clusters.getCluster("auth");
+            ClusterDataImpl cluster = clusters.getCluster("auth");
             assertEquals("authenticationPlugin", cluster.getAuthenticationPlugin());
             assertEquals("authenticationParameters", cluster.getAuthenticationParameters());
             assertEquals("listenerName", cluster.getListenerName());
@@ -426,11 +426,11 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         verify(properties, times(1)).validateSuperUserAccess();
 
         // create local cluster
-        clusters.createCluster(configClusterName, new ClusterData());
+        clusters.createCluster(configClusterName, new ClusterDataImpl());
 
         Set<String> allowedClusters = Sets.newHashSet();
         allowedClusters.add(configClusterName);
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), allowedClusters);
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), allowedClusters);
         response = asynRequests(ctx -> properties.createTenant(ctx, "test-property", tenantInfo));
         verify(properties, times(2)).validateSuperUserAccess();
 
@@ -442,7 +442,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         assertEquals(response, tenantInfo);
         verify(properties, times(4)).validateSuperUserAccess();
 
-        final TenantInfo newPropertyAdmin = new TenantInfo(Sets.newHashSet("role1", "other-role"), allowedClusters);
+        final TenantInfoImpl newPropertyAdmin = new TenantInfoImpl(Sets.newHashSet("role1", "other-role"), allowedClusters);
         response = asynRequests(ctx -> properties.updateTenant(ctx, "test-property", newPropertyAdmin));
         verify(properties, times(5)).validateSuperUserAccess();
 
@@ -487,7 +487,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         }
 
         // clear caches to load data from metadata-store again
-        MetadataCacheImpl<TenantInfo> cache = (MetadataCacheImpl<TenantInfo>) pulsar.getPulsarResources()
+        MetadataCacheImpl<TenantInfoImpl> cache = (MetadataCacheImpl<TenantInfoImpl>) pulsar.getPulsarResources()
                 .getTenantResources().getCache();
         AbstractMetadataStore store = (AbstractMetadataStore) cache.getStore();
         cache.invalidateAll();
@@ -564,7 +564,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         assertEquals(response, Lists.newArrayList());
 
         // Create a namespace to test deleting a non-empty property
-        TenantInfo newPropertyAdmin2 = new TenantInfo(Sets.newHashSet("role1", "other-role"), Sets.newHashSet("use"));
+        TenantInfoImpl newPropertyAdmin2 = new TenantInfoImpl(Sets.newHashSet("role1", "other-role"), Sets.newHashSet("use"));
         response = asynRequests(ctx -> properties.createTenant(ctx, "my-tenant", newPropertyAdmin2));
 
         namespaces.createNamespace("my-tenant", "use", "my-namespace", new BundlesData());
@@ -595,7 +595,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         // Check tenantInfo with empty cluster
         String blankCluster = "";
         Set<String> blankClusters = Sets.newHashSet(blankCluster);
-        TenantInfo tenantWithEmptyCluster = new TenantInfo(Sets.newHashSet("role1", "role2"), blankClusters);
+        TenantInfoImpl tenantWithEmptyCluster = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), blankClusters);
         try {
             response = asynRequests(ctx -> properties.createTenant(ctx, "tenant-config-is-empty", tenantWithEmptyCluster));
             fail("should have failed");
@@ -606,7 +606,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         // Check tenantInfo contains empty cluster
         Set<String> containBlankClusters = Sets.newHashSet(blankCluster);
         containBlankClusters.add(configClusterName);
-        TenantInfo tenantContainEmptyCluster = new TenantInfo(Sets.newHashSet(), containBlankClusters);
+        TenantInfoImpl tenantContainEmptyCluster = new TenantInfoImpl(Sets.newHashSet(), containBlankClusters);
         try {
             response = asynRequests(ctx -> properties.createTenant(ctx, "tenant-config-contain-empty", tenantContainEmptyCluster));
             fail("should have failed");
@@ -624,7 +624,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
 
     @Test
     public void brokers() throws Exception {
-        clusters.createCluster("use", new ClusterData("http://broker.messaging.use.example.com",
+        clusters.createCluster("use", new ClusterDataImpl("http://broker.messaging.use.example.com",
                 "https://broker.messaging.use.example.com:4443"));
 
         URI requestUri = new URI(
@@ -681,9 +681,9 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         }
 
         // create policies
-        TenantInfo admin = new TenantInfo();
+        TenantInfoImpl admin = new TenantInfoImpl();
         admin.getAllowedClusters().add(cluster);
-        ClusterData clusterData = new ClusterData(cluster);
+        ClusterDataImpl clusterData = new ClusterDataImpl(cluster);
         clusters.createCluster(cluster, clusterData );
         asynRequests(ctx -> properties.createTenant(ctx, property, admin));
 
@@ -740,7 +740,7 @@ public class AdminTest extends MockedPulsarServiceBaseTest {
         doReturn(policies).when(resourceQuotas).getNamespacePolicies(NamespaceName.get(property, cluster, namespace));
         doReturn("client-id").when(resourceQuotas).clientAppId();
         // create policies
-        TenantInfo admin = new TenantInfo();
+        TenantInfoImpl admin = new TenantInfoImpl();
         admin.getAllowedClusters().add(cluster);
         ZkUtils.createFullPathOptimistic(mockZooKeeperGlobal, PulsarWebResource.path(POLICIES, property, cluster, namespace),
                 ObjectMapperFactory.getThreadLocal().writeValueAsBytes(new Policies()), ZooDefs.Ids.OPEN_ACL_UNSAFE,
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/BookiesApiTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/BookiesApiTest.java
index 7e3793c..2d568c2 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/BookiesApiTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/BookiesApiTest.java
@@ -53,7 +53,7 @@ public class BookiesApiTest extends MockedPulsarServiceBaseTest {
     @Test
     public void testBasic() throws Exception {
         // no map
-        BookiesRackConfiguration conf = admin.bookies().getBookiesRackInfo();
+        BookiesRackConfiguration conf = (BookiesRackConfiguration) admin.bookies().getBookiesRackInfo();
         assertTrue(conf.isEmpty());
 
         String bookie0 = "127.0.0.1:3181";
@@ -79,7 +79,7 @@ public class BookiesApiTest extends MockedPulsarServiceBaseTest {
         admin.bookies().updateBookieRackInfo(bookie0, "default", newInfo0);
         BookieInfo readInfo0 = admin.bookies().getBookieRackInfo(bookie0);
         assertEquals(newInfo0, readInfo0);
-        conf = admin.bookies().getBookiesRackInfo();
+        conf = (BookiesRackConfiguration) admin.bookies().getBookiesRackInfo();
         // number of groups
         assertEquals(1, conf.size());
         assertEquals(Optional.of(newInfo0), conf.getBookie(bookie0));
@@ -87,7 +87,7 @@ public class BookiesApiTest extends MockedPulsarServiceBaseTest {
         admin.bookies().updateBookieRackInfo(bookie1, "default", newInfo1);
         BookieInfo readInfo1 = admin.bookies().getBookieRackInfo(bookie1);
         assertEquals(newInfo1, readInfo1);
-        conf = admin.bookies().getBookiesRackInfo();
+        conf = (BookiesRackConfiguration) admin.bookies().getBookiesRackInfo();
         // number of groups
         assertEquals(1, conf.size());
         assertEquals(Optional.of(newInfo0), conf.getBookie(bookie0));
@@ -110,7 +110,7 @@ public class BookiesApiTest extends MockedPulsarServiceBaseTest {
             assertEquals(404, pae.getStatusCode());
         }
 
-        conf = admin.bookies().getBookiesRackInfo();
+        conf = (BookiesRackConfiguration) admin.bookies().getBookiesRackInfo();
         assertTrue(conf.isEmpty());
 
         BookiesClusterInfo bookies = admin.bookies().getBookies();
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/BrokerAdminClientTlsAuthTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/BrokerAdminClientTlsAuthTest.java
index bbc70d0..847c080 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/BrokerAdminClientTlsAuthTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/BrokerAdminClientTlsAuthTest.java
@@ -34,9 +34,9 @@ import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
 import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.common.policies.data.BundlesData;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.Policies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
@@ -129,9 +129,9 @@ public class BrokerAdminClientTlsAuthTest extends MockedPulsarServiceBaseTest {
 
         /***** Broker 2 Started *****/
         try (PulsarAdmin admin = buildAdminClient("superproxy")) {
-            admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+            admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
             admin.tenants().createTenant("tenant",
-                                         new TenantInfo(ImmutableSet.of("admin"),
+                                         new TenantInfoImpl(ImmutableSet.of("admin"),
                                                         ImmutableSet.of("test")));
         }
         try (PulsarAdmin admin = buildAdminClient("admin")) {
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/IncrementPartitionsTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/IncrementPartitionsTest.java
index c8fe65e..1743593 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/IncrementPartitionsTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/IncrementPartitionsTest.java
@@ -22,7 +22,6 @@ import static org.testng.Assert.assertEquals;
 import com.google.common.collect.Lists;
 import com.google.common.collect.Sets;
 import java.util.Collections;
-import java.util.concurrent.TimeUnit;
 
 import lombok.Cleanup;
 import org.apache.pulsar.broker.BrokerTestUtil;
@@ -34,8 +33,8 @@ import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.api.Reader;
 import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -58,8 +57,8 @@ public class IncrementPartitionsTest extends MockedPulsarServiceBaseTest {
         mockPulsarSetup.setup();
 
         // Setup namespaces
-        admin.clusters().createCluster("use", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use"));
+        admin.clusters().createCluster("use", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz/use/ns1");
     }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/NamespacesTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/NamespacesTest.java
index 49ffc68..132d53e 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/NamespacesTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/NamespacesTest.java
@@ -72,6 +72,7 @@ import org.apache.pulsar.broker.web.PulsarWebResource;
 import org.apache.pulsar.broker.web.RestException;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.client.admin.PulsarAdminException.NotFoundException;
+import org.apache.pulsar.client.admin.internal.BaseResource;
 import org.apache.pulsar.client.api.Consumer;
 import org.apache.pulsar.client.api.ConsumerBuilder;
 import org.apache.pulsar.client.api.Producer;
@@ -83,15 +84,15 @@ import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.policies.data.AuthAction;
 import org.apache.pulsar.common.policies.data.BundlesData;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.OffloadPolicies;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.OffloadPoliciesImpl;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.Policies;
 import org.apache.pulsar.common.policies.data.PolicyName;
 import org.apache.pulsar.common.policies.data.PolicyOperation;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
 import org.apache.pulsar.common.policies.data.SubscribeRate;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.metadata.cache.impl.MetadataCacheImpl;
 import org.apache.pulsar.metadata.impl.AbstractMetadataStore;
@@ -165,13 +166,13 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         doReturn(null).when(namespaces).clientAuthData();
         doReturn(Sets.newTreeSet(Lists.newArrayList("use", "usw", "usc", "global"))).when(namespaces).clusters();
 
-        admin.clusters().createCluster("use", new ClusterData("http://broker-use.com:8080"));
-        admin.clusters().createCluster("usw", new ClusterData("http://broker-usw.com:8080"));
-        admin.clusters().createCluster("usc", new ClusterData("http://broker-usc.com:8080"));
+        admin.clusters().createCluster("use", new ClusterDataImpl("http://broker-use.com:8080"));
+        admin.clusters().createCluster("usw", new ClusterDataImpl("http://broker-usw.com:8080"));
+        admin.clusters().createCluster("usc", new ClusterDataImpl("http://broker-usc.com:8080"));
         admin.tenants().createTenant(this.testTenant,
-                new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use", "usc", "usw")));
+                new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use", "usc", "usw")));
         admin.tenants().createTenant(this.testOtherTenant,
-                new TenantInfo(Sets.newHashSet("role3", "role4"), Sets.newHashSet("use", "usc", "usw")));
+                new TenantInfoImpl(Sets.newHashSet("role3", "role4"), Sets.newHashSet("use", "usc", "usw")));
 
         createTestNamespaces(this.testLocalNamespaces, new BundlesData());
         createGlobalTestNamespaces(this.testTenant, this.testGlobalNamespaces.get(0).getLocalName(),
@@ -287,7 +288,7 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
                     && path.equals("/admin/policies/my-tenant");
             });
         // clear caches to load data from metadata-store again
-        MetadataCacheImpl<TenantInfo> tenantCache = (MetadataCacheImpl<TenantInfo>) pulsar.getPulsarResources()
+        MetadataCacheImpl<TenantInfoImpl> tenantCache = (MetadataCacheImpl<TenantInfoImpl>) pulsar.getPulsarResources()
                 .getTenantResources().getCache();
         AbstractMetadataStore store = (AbstractMetadataStore) tenantCache.getStore();
         tenantCache.invalidateAll();
@@ -512,7 +513,7 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         }
 
         admin.tenants().updateTenant(testTenant,
-                new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use", "usc")));
+                new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use", "usc")));
 
         try {
             namespaces.setNamespaceReplicationClusters(this.testTenant, "global",
@@ -799,8 +800,11 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
                 }));
 
         CompletableFuture<Void> preconditionFailed = new CompletableFuture<>();
-        preconditionFailed.completeExceptionally(new PulsarAdminException.PreconditionFailedException(
-                new ClientErrorException(Status.PRECONDITION_FAILED)));
+        ClientErrorException cee = new ClientErrorException(Status.PRECONDITION_FAILED);
+        int statusCode = cee.getResponse().getStatus();
+        String httpError = BaseResource.getReasonFromServer(cee);
+        preconditionFailed.completeExceptionally(new PulsarAdminException.PreconditionFailedException(cee,
+                httpError, statusCode));
         doReturn(preconditionFailed).when(namespacesAdmin)
                 .deleteNamespaceBundleAsync(Mockito.anyString(), Mockito.anyString());
 
@@ -982,7 +986,7 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
             pulsar.getConfiguration().setAuthorizationEnabled(true);
             final String path = PulsarWebResource.path(POLICIES, property);
             final String data = ObjectMapperFactory.getThreadLocal().writeValueAsString(
-                    new TenantInfo(Sets.newHashSet(namespaces.clientAppId()), Sets.newHashSet("use")));
+                    new TenantInfoImpl(Sets.newHashSet(namespaces.clientAppId()), Sets.newHashSet("use")));
             ZkUtils.createFullPathOptimistic(pulsar.getConfigurationCache().getZooKeeper(), path, data.getBytes(),
                     ZooDefs.Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT);
 
@@ -1193,7 +1197,7 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         SubscribeRate subscribeRate = new SubscribeRate(1, 5);
         String namespace = "my-tenants/my-namespace";
         admin.tenants().createTenant("my-tenants",
-                new TenantInfo(Sets.newHashSet(), Sets.newHashSet(testLocalCluster)));
+                new TenantInfoImpl(Sets.newHashSet(), Sets.newHashSet(testLocalCluster)));
         admin.namespaces().createNamespace(namespace, Sets.newHashSet(testLocalCluster));
         admin.namespaces().setSubscribeRate(namespace, subscribeRate);
         assertEquals(subscribeRate, admin.namespaces().getSubscribeRate(namespace));
@@ -1242,9 +1246,9 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
             return deletes.keySet();
         }
 
-        OffloadPolicies offloadPolicies;
+        OffloadPoliciesImpl offloadPolicies;
 
-        public MockLedgerOffloader(OffloadPolicies offloadPolicies) {
+        public MockLedgerOffloader(OffloadPoliciesImpl offloadPolicies) {
             this.offloadPolicies = offloadPolicies;
         }
 
@@ -1288,7 +1292,7 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         };
 
         @Override
-        public OffloadPolicies getOffloadPolicies() {
+        public OffloadPoliciesImpl getOffloadPolicies() {
             return offloadPolicies;
         }
 
@@ -1313,14 +1317,14 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         assertEquals(-1, admin.namespaces().getOffloadThreshold(namespace));
         // the ledger config should have the expected value
         ManagedLedgerConfig ledgerConf = pulsar.getBrokerService().getManagedLedgerConfig(topicName).get();
-        MockLedgerOffloader offloader = new MockLedgerOffloader(OffloadPolicies.create("S3", "", "", "",
+        MockLedgerOffloader offloader = new MockLedgerOffloader(OffloadPoliciesImpl.create("S3", "", "", "",
                 null, null,
                 null, null,
-                OffloadPolicies.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
-                OffloadPolicies.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
                 admin.namespaces().getOffloadThreshold(namespace),
                 pulsar.getConfiguration().getManagedLedgerOffloadDeletionLagMs(),
-                OffloadPolicies.DEFAULT_OFFLOADED_READ_PRIORITY));
+                OffloadPoliciesImpl.DEFAULT_OFFLOADED_READ_PRIORITY));
         ledgerConf.setLedgerOffloader(offloader);
         assertEquals(ledgerConf.getLedgerOffloader().getOffloadPolicies().getManagedLedgerOffloadThresholdInBytes(),
                 new Long(-1));
@@ -1330,14 +1334,14 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         assertEquals(100, admin.namespaces().getOffloadThreshold(namespace));
         ledgerConf = pulsar.getBrokerService().getManagedLedgerConfig(topicName).get();
         admin.namespaces().getOffloadPolicies(namespace);
-        offloader = new MockLedgerOffloader(OffloadPolicies.create("S3", "", "", "",
+        offloader = new MockLedgerOffloader(OffloadPoliciesImpl.create("S3", "", "", "",
                 null, null,
                 null, null,
-                OffloadPolicies.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
-                OffloadPolicies.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
                 admin.namespaces().getOffloadThreshold(namespace),
                 pulsar.getConfiguration().getManagedLedgerOffloadDeletionLagMs(),
-                OffloadPolicies.DEFAULT_OFFLOADED_READ_PRIORITY));
+                OffloadPoliciesImpl.DEFAULT_OFFLOADED_READ_PRIORITY));
         ledgerConf.setLedgerOffloader(offloader);
         assertEquals(ledgerConf.getLedgerOffloader().getOffloadPolicies().getManagedLedgerOffloadThresholdInBytes(),
                 new Long(100));
@@ -1346,14 +1350,14 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         admin.namespaces().setOffloadThreshold(namespace, -2);
         assertEquals(-2, admin.namespaces().getOffloadThreshold(namespace));
         ledgerConf = pulsar.getBrokerService().getManagedLedgerConfig(topicName).get();
-        offloader = new MockLedgerOffloader(OffloadPolicies.create("S3", "", "", "",
+        offloader = new MockLedgerOffloader(OffloadPoliciesImpl.create("S3", "", "", "",
                 null, null,
                 null, null,
-                OffloadPolicies.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
-                OffloadPolicies.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
                 admin.namespaces().getOffloadThreshold(namespace),
                 pulsar.getConfiguration().getManagedLedgerOffloadDeletionLagMs(),
-                OffloadPolicies.DEFAULT_OFFLOADED_READ_PRIORITY));
+                OffloadPoliciesImpl.DEFAULT_OFFLOADED_READ_PRIORITY));
         ledgerConf.setLedgerOffloader(offloader);
         assertEquals(ledgerConf.getLedgerOffloader().getOffloadPolicies().getManagedLedgerOffloadThresholdInBytes(),
                 new Long(-2));
@@ -1362,14 +1366,14 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         admin.namespaces().setOffloadThreshold(namespace, -1);
         assertEquals(-1, admin.namespaces().getOffloadThreshold(namespace));
         ledgerConf = pulsar.getBrokerService().getManagedLedgerConfig(topicName).get();
-        offloader = new MockLedgerOffloader(OffloadPolicies.create("S3", "", "", "",
+        offloader = new MockLedgerOffloader(OffloadPoliciesImpl.create("S3", "", "", "",
                 null, null,
                 null, null,
-                OffloadPolicies.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
-                OffloadPolicies.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_MAX_BLOCK_SIZE_IN_BYTES,
+                OffloadPoliciesImpl.DEFAULT_READ_BUFFER_SIZE_IN_BYTES,
                 admin.namespaces().getOffloadThreshold(namespace),
                 pulsar.getConfiguration().getManagedLedgerOffloadDeletionLagMs(),
-                OffloadPolicies.DEFAULT_OFFLOADED_READ_PRIORITY));
+                OffloadPoliciesImpl.DEFAULT_OFFLOADED_READ_PRIORITY));
         ledgerConf.setLedgerOffloader(offloader);
         assertEquals(ledgerConf.getLedgerOffloader().getOffloadPolicies().getManagedLedgerOffloadThresholdInBytes(),
                 new Long(-1));
@@ -1473,8 +1477,8 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         String namespace = "testTenant/ns1";
-        admin.clusters().createCluster("use", new ClusterData(brokerUrl.toString()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"),
+        admin.clusters().createCluster("use", new ClusterDataImpl(brokerUrl.toString()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"),
                 Sets.newHashSet("use"));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace(namespace, Sets.newHashSet("use"));
@@ -1523,7 +1527,7 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         conf.setAllowAutoTopicCreationType("partitioned");
         super.internalSetup();
 
-        admin.clusters().createCluster("use", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("use", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace(namespace, Sets.newHashSet("use"));
         admin.namespaces().setMaxTopicsPerNamespace(namespace, 10);
@@ -1553,7 +1557,7 @@ public class NamespacesTest extends MockedPulsarServiceBaseTest {
         conf.setAllowAutoTopicCreationType("non-partitioned");
         super.internalSetup();
 
-        admin.clusters().createCluster("use", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("use", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("testTenant", tenantInfo);
         admin.namespaces().createNamespace(namespace, Sets.newHashSet("use"));
         admin.namespaces().setMaxTopicsPerNamespace(namespace, 3);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/PersistentTopicsTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/PersistentTopicsTest.java
index 3f3883b..7985bef 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/PersistentTopicsTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/PersistentTopicsTest.java
@@ -65,9 +65,9 @@ import org.apache.pulsar.common.naming.TopicDomain;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.partition.PartitionedTopicMetadata;
 import org.apache.pulsar.common.policies.data.AuthAction;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.Policies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicStats;
 import org.apache.pulsar.zookeeper.ZooKeeperManagedLedgerCache;
 import org.apache.zookeeper.KeeperException;
@@ -128,10 +128,10 @@ public class PersistentTopicsTest extends MockedPulsarServiceBaseTest {
         doReturn(mock(AuthenticationDataHttps.class)).when(nonPersistentTopic).clientAuthData();
 
 
-        admin.clusters().createCluster("use", new ClusterData("http://broker-use.com:8080"));
-        admin.clusters().createCluster("test", new ClusterData("http://broker-use.com:8080"));
+        admin.clusters().createCluster("use", new ClusterDataImpl("http://broker-use.com:8080"));
+        admin.clusters().createCluster("test", new ClusterDataImpl("http://broker-use.com:8080"));
         admin.tenants().createTenant(this.testTenant,
-                new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet(testLocalCluster, "test")));
+                new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet(testLocalCluster, "test")));
         admin.namespaces().createNamespace(testTenant + "/" + testNamespace, Sets.newHashSet(testLocalCluster, "test"));
     }
 
@@ -631,7 +631,7 @@ public class PersistentTopicsTest extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testGetLastMessageId() throws Exception {
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz/ns1", Sets.newHashSet("test"));
         final String topicName = "persistent://prop-xyz/ns1/testGetLastMessageId";
@@ -661,7 +661,7 @@ public class PersistentTopicsTest extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testExamineMessage() throws Exception {
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("tenant-xyz", tenantInfo);
         admin.namespaces().createNamespace("tenant-xyz/ns-abc", Sets.newHashSet("test"));
         final String topicName = "persistent://tenant-xyz/ns-abc/topic-123";
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/ResourceGroupsTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/ResourceGroupsTest.java
index 7c240d5..9183d95 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/ResourceGroupsTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/ResourceGroupsTest.java
@@ -24,9 +24,9 @@ import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
 import org.apache.pulsar.broker.web.RestException;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.broker.admin.v2.ResourceGroups;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.ResourceGroup;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.annotations.AfterClass;
 import org.testng.annotations.BeforeClass;
 import org.testng.annotations.Test;
@@ -173,9 +173,9 @@ public class ResourceGroupsTest extends MockedPulsarServiceBaseTest  {
     }
 
     private void prepareData() throws PulsarAdminException {
-        admin.clusters().createCluster(testCluster, new ClusterData(pulsar.getBrokerServiceUrl()));
+        admin.clusters().createCluster(testCluster, new ClusterDataImpl(pulsar.getBrokerServiceUrl()));
         admin.tenants().createTenant(testTenant,
-                new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet(testCluster)));
+                new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet(testCluster)));
     }
 
 }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicMessageTTLTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicMessageTTLTest.java
index a31cad6..710920a 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicMessageTTLTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicMessageTTLTest.java
@@ -24,8 +24,8 @@ import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
 import org.apache.pulsar.broker.service.persistent.PersistentTopic;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.client.api.Producer;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.eclipse.jetty.http.HttpStatus;
 import org.testng.Assert;
@@ -35,7 +35,6 @@ import org.testng.annotations.Test;
 
 import java.lang.reflect.Method;
 import java.util.UUID;
-import java.util.concurrent.TimeUnit;
 
 @Slf4j
 @Test(groups = "flaky")
@@ -58,8 +57,8 @@ public class TopicMessageTTLTest extends MockedPulsarServiceBaseTest {
         this.conf.setTtlDurationDefaultInSeconds(3600);
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant(this.testTenant, tenantInfo);
         admin.namespaces().createNamespace(testTenant + "/" + testNamespace, Sets.newHashSet("test"));
         admin.topics().createPartitionedTopic(testTopic, 2);
@@ -131,8 +130,8 @@ public class TopicMessageTTLTest extends MockedPulsarServiceBaseTest {
         this.conf.setTopicLevelPoliciesEnabled(false);
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant(this.testTenant, tenantInfo);
         admin.namespaces().createNamespace(testTenant + "/" + testNamespace, Sets.newHashSet("test"));
         admin.topics().createPartitionedTopic(testTopic, 2);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicPoliciesDisableTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicPoliciesDisableTest.java
index bc194b4..2420a5b 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicPoliciesDisableTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicPoliciesDisableTest.java
@@ -23,13 +23,13 @@ import lombok.extern.slf4j.Slf4j;
 import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.common.policies.data.BacklogQuota;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.DispatchRate;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.PublishRate;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
 import org.apache.pulsar.common.policies.data.SubscribeRate;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.eclipse.jetty.http.HttpStatus;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
@@ -55,8 +55,8 @@ public class TopicPoliciesDisableTest extends MockedPulsarServiceBaseTest {
         this.conf.setTopicLevelPoliciesEnabled(false);
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant(this.testTenant, tenantInfo);
         admin.namespaces().createNamespace(testTenant + "/" + testNamespace, Sets.newHashSet("test"));
         admin.topics().createPartitionedTopic(testTopic, 2);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicPoliciesTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicPoliciesTest.java
index 7a9fb06..c227870 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicPoliciesTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/TopicPoliciesTest.java
@@ -44,7 +44,7 @@ import org.apache.pulsar.client.api.SubscriptionMode;
 import org.apache.pulsar.client.api.SubscriptionType;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.policies.data.BacklogQuota;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.DispatchRate;
 import org.apache.pulsar.common.policies.data.InactiveTopicDeleteMode;
 import org.apache.pulsar.common.policies.data.InactiveTopicPolicies;
@@ -52,7 +52,7 @@ import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.PublishRate;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
 import org.apache.pulsar.common.policies.data.SubscribeRate;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
@@ -98,8 +98,8 @@ public class TopicPoliciesTest extends MockedPulsarServiceBaseTest {
         this.conf.setDefaultNumberOfNamespaceBundles(1);
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant(this.testTenant, tenantInfo);
         admin.namespaces().createNamespace(testTenant + "/" + testNamespace, Sets.newHashSet("test"));
         admin.topics().createPartitionedTopic(testTopic, 2);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v1/V1_AdminApiTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v1/V1_AdminApiTest.java
index 47d8c60..ed60ef3 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v1/V1_AdminApiTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v1/V1_AdminApiTest.java
@@ -47,8 +47,6 @@ import java.util.concurrent.TimeUnit;
 import javax.ws.rs.client.InvocationCallback;
 import javax.ws.rs.client.WebTarget;
 
-import org.apache.pulsar.broker.ConfigHelper;
-import org.apache.pulsar.broker.PulsarServerException;
 import org.apache.pulsar.broker.PulsarService;
 import org.apache.pulsar.broker.ServiceConfiguration;
 import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
@@ -82,22 +80,24 @@ import org.apache.pulsar.common.naming.TopicDomain;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.partition.PartitionedTopicMetadata;
 import org.apache.pulsar.common.policies.data.AuthAction;
-import org.apache.pulsar.common.policies.data.AutoFailoverPolicyData;
+import org.apache.pulsar.common.policies.data.AutoFailoverPolicyDataImpl;
 import org.apache.pulsar.common.policies.data.AutoFailoverPolicyType;
 import org.apache.pulsar.common.policies.data.BacklogQuota;
 import org.apache.pulsar.common.policies.data.BacklogQuota.BacklogQuotaType;
 import org.apache.pulsar.common.policies.data.BacklogQuota.RetentionPolicy;
 import org.apache.pulsar.common.policies.data.BrokerAssignment;
 import org.apache.pulsar.common.policies.data.BrokerNamespaceIsolationData;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.NamespaceIsolationDataImpl;
 import org.apache.pulsar.common.policies.data.NamespaceIsolationData;
 import org.apache.pulsar.common.policies.data.NamespaceOwnershipStatus;
 import org.apache.pulsar.common.policies.data.PartitionedTopicStats;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
+import org.apache.pulsar.common.policies.data.PoliciesUtil;
 import org.apache.pulsar.common.policies.data.TopicStats;
 import org.apache.pulsar.common.policies.data.Policies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
 import org.apache.pulsar.common.util.Codec;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
@@ -164,8 +164,8 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
         otheradmin = mockPulsarSetup.getAdmin();
 
         // Setup namespaces
-        admin.clusters().createCluster("use", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use"));
+        admin.clusters().createCluster("use", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz/use/ns1");
     }
@@ -201,26 +201,26 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
     @Test
     public void clusters() throws Exception {
         admin.clusters().createCluster("usw",
-                new ClusterData("http://broker.messaging.use.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.use.example.com:8080"));
         // "test" cluster is part of config-default cluster and it's znode gets created when PulsarService creates
         // failure-domain znode of this default cluster
         assertEquals(admin.clusters().getClusters(), Lists.newArrayList("use", "usw"));
 
         assertEquals(admin.clusters().getCluster("use"),
-                new ClusterData(pulsar.getWebServiceAddress()));
+                new ClusterDataImpl(pulsar.getWebServiceAddress()));
 
         admin.clusters().updateCluster("usw",
-                new ClusterData("http://new-broker.messaging.usw.example.com:8080"));
+                new ClusterDataImpl("http://new-broker.messaging.usw.example.com:8080"));
         assertEquals(admin.clusters().getClusters(), Lists.newArrayList("use", "usw"));
         assertEquals(admin.clusters().getCluster("usw"),
-                new ClusterData("http://new-broker.messaging.usw.example.com:8080"));
+                new ClusterDataImpl("http://new-broker.messaging.usw.example.com:8080"));
 
         admin.clusters().updateCluster("usw",
-                new ClusterData("http://new-broker.messaging.usw.example.com:8080",
+                new ClusterDataImpl("http://new-broker.messaging.usw.example.com:8080",
                         "https://new-broker.messaging.usw.example.com:4443"));
         assertEquals(admin.clusters().getClusters(), Lists.newArrayList("use", "usw"));
         assertEquals(admin.clusters().getCluster("usw"),
-                new ClusterData("http://new-broker.messaging.usw.example.com:8080",
+                new ClusterDataImpl("http://new-broker.messaging.usw.example.com:8080",
                         "https://new-broker.messaging.usw.example.com:4443"));
 
         admin.clusters().deleteCluster("usw");
@@ -234,7 +234,7 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
 
         // Check name validation
         try {
-            admin.clusters().createCluster("bf!", new ClusterData("http://dummy.messaging.example.com"));
+            admin.clusters().createCluster("bf!", new ClusterDataImpl("http://dummy.messaging.example.com"));
             fail("should have failed");
         } catch (PulsarAdminException e) {
             assertTrue(e instanceof PreconditionFailedException);
@@ -246,7 +246,7 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
         try {
             // create
             String policyName1 = "policy-1";
-            NamespaceIsolationData nsPolicyData1 = new NamespaceIsolationData();
+            NamespaceIsolationDataImpl nsPolicyData1 = new NamespaceIsolationDataImpl();
             nsPolicyData1.namespaces = new ArrayList<>();
             nsPolicyData1.namespaces.add("other/use/other.*");
             nsPolicyData1.primary = new ArrayList<>();
@@ -255,7 +255,7 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
 
             nsPolicyData1.secondary = new ArrayList<>();
             nsPolicyData1.secondary.add("prod1-broker.*.messaging.use.example.com");
-            nsPolicyData1.auto_failover_policy = new AutoFailoverPolicyData();
+            nsPolicyData1.auto_failover_policy = new AutoFailoverPolicyDataImpl();
             nsPolicyData1.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
             nsPolicyData1.auto_failover_policy.parameters = new HashMap<>();
             nsPolicyData1.auto_failover_policy.parameters.put("min_limit", "1");
@@ -263,14 +263,14 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
             admin.clusters().createNamespaceIsolationPolicy("use", policyName1, nsPolicyData1);
 
             String policyName2 = "policy-2";
-            NamespaceIsolationData nsPolicyData2 = new NamespaceIsolationData();
+            NamespaceIsolationDataImpl nsPolicyData2 = new NamespaceIsolationDataImpl();
             nsPolicyData2.namespaces = new ArrayList<>();
             nsPolicyData2.namespaces.add("other/use/other.*");
             nsPolicyData2.primary = new ArrayList<>();
             nsPolicyData2.primary.add("prod1-broker[4-6].messaging.use.example.com");
             nsPolicyData2.secondary = new ArrayList<>();
             nsPolicyData2.secondary.add("prod1-broker.*.messaging.use.example.com");
-            nsPolicyData2.auto_failover_policy = new AutoFailoverPolicyData();
+            nsPolicyData2.auto_failover_policy = new AutoFailoverPolicyDataImpl();
             nsPolicyData2.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
             nsPolicyData2.auto_failover_policy.parameters = new HashMap<>();
             nsPolicyData2.auto_failover_policy.parameters.put("min_limit", "1");
@@ -278,14 +278,14 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
             admin.clusters().createNamespaceIsolationPolicy("use", policyName2, nsPolicyData2);
 
             // verify create indirectly with get
-            Map<String, NamespaceIsolationData> policiesMap = admin.clusters().getNamespaceIsolationPolicies("use");
+            Map<String, ? extends NamespaceIsolationData> policiesMap = admin.clusters().getNamespaceIsolationPolicies("use");
             assertEquals(policiesMap.get(policyName1), nsPolicyData1);
             assertEquals(policiesMap.get(policyName2), nsPolicyData2);
 
             // verify local broker get matched.
             List<BrokerNamespaceIsolationData> isoList = admin.clusters().getBrokersWithNamespaceIsolationPolicy("use");
             assertEquals(isoList.size(), 1);
-            assertTrue(isoList.get(0).isPrimary);
+            assertTrue(isoList.get(0).isPrimary());
 
             // verify update of primary
             nsPolicyData1.primary.remove(0);
@@ -322,7 +322,8 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
             assertEquals(policiesMap.get(policyName1), nsPolicyData1);
 
             // verify single get
-            NamespaceIsolationData policy1Data = admin.clusters().getNamespaceIsolationPolicy("use", policyName1);
+            NamespaceIsolationDataImpl policy1Data =
+                    (NamespaceIsolationDataImpl) admin.clusters().getNamespaceIsolationPolicy("use", policyName1);
             assertEquals(policy1Data, nsPolicyData1);
 
             // verify creation of more than one policy
@@ -575,14 +576,14 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
     @Test
     public void properties() throws PulsarAdminException {
         Set<String> allowedClusters = Sets.newHashSet("use");
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), allowedClusters);
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), allowedClusters);
         admin.tenants().updateTenant("prop-xyz", tenantInfo);
 
         assertEquals(admin.tenants().getTenants(), Lists.newArrayList("prop-xyz"));
 
         assertEquals(admin.tenants().getTenantInfo("prop-xyz"), tenantInfo);
 
-        TenantInfo newPropertyAdmin = new TenantInfo(Sets.newHashSet("role3", "role4"), allowedClusters);
+        TenantInfoImpl newPropertyAdmin = new TenantInfoImpl(Sets.newHashSet("role3", "role4"), allowedClusters);
         admin.tenants().updateTenant("prop-xyz", newPropertyAdmin);
 
         assertEquals(admin.tenants().getTenantInfo("prop-xyz"), newPropertyAdmin);
@@ -602,12 +603,12 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
 
     @Test
     public void namespaces() throws Exception {
-        admin.clusters().createCluster("usw", new ClusterData());
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"),
+        admin.clusters().createCluster("usw", new ClusterDataImpl());
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"),
                 Sets.newHashSet("use", "usw"));
         admin.tenants().updateTenant("prop-xyz", tenantInfo);
 
-        assertEquals(admin.namespaces().getPolicies("prop-xyz/use/ns1").bundles, Policies.defaultBundle());
+        assertEquals(admin.namespaces().getPolicies("prop-xyz/use/ns1").bundles, PoliciesUtil.defaultBundle());
 
         admin.namespaces().createNamespace("prop-xyz/use/ns2");
 
@@ -641,7 +642,7 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
         admin.namespaces().grantPermissionOnNamespace("prop-xyz/use/ns1", "my-role", EnumSet.allOf(AuthAction.class));
 
         Policies policies = new Policies();
-        policies.bundles = Policies.defaultBundle();
+        policies.bundles = PoliciesUtil.defaultBundle();
         policies.auth_policies.namespace_auth.put("my-role", EnumSet.allOf(AuthAction.class));
 
         assertEquals(admin.namespaces().getPolicies("prop-xyz/use/ns1"), policies);
@@ -1688,12 +1689,12 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
     @Test
     public void testObjectWithUnknownProperties() {
 
-        class CustomPropertyAdmin extends TenantInfo {
+        class CustomPropertyAdmin extends TenantInfoImpl {
             @SuppressWarnings("unused")
             public int newProperty;
         }
 
-        TenantInfo pa = new TenantInfo(Sets.newHashSet("test_appid1", "test_appid2"), Sets.newHashSet("use"));
+        TenantInfoImpl pa = new TenantInfoImpl(Sets.newHashSet("test_appid1", "test_appid2"), Sets.newHashSet("use"));
         CustomPropertyAdmin cpa = new CustomPropertyAdmin();
         cpa.setAdminRoles(pa.getAdminRoles());
         cpa.setAllowedClusters(pa.getAllowedClusters());
@@ -1964,8 +1965,8 @@ public class V1_AdminApiTest extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testTopicBundleRangeLookup() throws Exception {
-        admin.clusters().createCluster("usw", new ClusterData());
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"),
+        admin.clusters().createCluster("usw", new ClusterDataImpl());
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"),
                 Sets.newHashSet("use", "usw"));
         admin.tenants().updateTenant("prop-xyz", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz/use/getBundleNs", 100);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v1/V1_AdminApiTest2.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v1/V1_AdminApiTest2.java
index 2410843..71f64b4 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v1/V1_AdminApiTest2.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v1/V1_AdminApiTest2.java
@@ -59,15 +59,16 @@ import org.apache.pulsar.client.api.SubscriptionType;
 import org.apache.pulsar.client.impl.MessageIdImpl;
 import org.apache.pulsar.common.naming.TopicDomain;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.ConsumerStats;
+import org.apache.pulsar.common.policies.data.FailureDomainImpl;
 import org.apache.pulsar.common.policies.data.FailureDomain;
 import org.apache.pulsar.common.policies.data.NonPersistentTopicStats;
 import org.apache.pulsar.common.policies.data.PartitionedTopicStats;
 import org.apache.pulsar.common.policies.data.PersistencePolicies;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
 import org.apache.pulsar.common.policies.data.TopicStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
 import org.apache.pulsar.common.policies.data.SubscriptionStats;
 import org.testng.annotations.AfterMethod;
@@ -93,8 +94,8 @@ public class V1_AdminApiTest2 extends MockedPulsarServiceBaseTest {
         mockPulsarSetup.setup();
 
         // Setup namespaces
-        admin.clusters().createCluster("use", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use"));
+        admin.clusters().createCluster("use", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use"));
         admin.tenants().createTenant("prop-xyz", tenantInfo);
         admin.namespaces().createNamespace("prop-xyz/use/ns1");
     }
@@ -549,13 +550,13 @@ public class V1_AdminApiTest2 extends MockedPulsarServiceBaseTest {
     @Test
     public void testPeerCluster() throws Exception {
         admin.clusters().createCluster("us-west1",
-                new ClusterData("http://broker.messaging.west1.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west1.example.com:8080"));
         admin.clusters().createCluster("us-west2",
-                new ClusterData("http://broker.messaging.west2.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west2.example.com:8080"));
         admin.clusters().createCluster("us-east1",
-                new ClusterData("http://broker.messaging.east1.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.east1.example.com:8080"));
         admin.clusters().createCluster("us-east2",
-                new ClusterData("http://broker.messaging.east2.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.east2.example.com:8080"));
 
         admin.clusters().updatePeerClusterNames("us-west1", Sets.newLinkedHashSet(Lists.newArrayList("us-west2")));
         assertEquals(admin.clusters().getCluster("us-west1").getPeerClusterNames(), Lists.newArrayList("us-west2"));
@@ -594,23 +595,23 @@ public class V1_AdminApiTest2 extends MockedPulsarServiceBaseTest {
     @Test
     public void testReplicationPeerCluster() throws Exception {
         admin.clusters().createCluster("us-west1",
-                new ClusterData("http://broker.messaging.west1.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west1.example.com:8080"));
         admin.clusters().createCluster("us-west2",
-                new ClusterData("http://broker.messaging.west2.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west2.example.com:8080"));
         admin.clusters().createCluster("us-west3",
-                new ClusterData("http://broker.messaging.west2.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west2.example.com:8080"));
         admin.clusters().createCluster("us-west4",
-                new ClusterData("http://broker.messaging.west2.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.west2.example.com:8080"));
         admin.clusters().createCluster("us-east1",
-                new ClusterData("http://broker.messaging.east1.example.com:8080"));
+                new ClusterDataImpl("http://broker.messaging.east1.example.com:8080"));
         admin.clusters().createCluster("us-east2",
-                new ClusterData("http://broker.messaging.east2.example.com:8080"));
-        admin.clusters().createCluster("global", new ClusterData());
+                new ClusterDataImpl("http://broker.messaging.east2.example.com:8080"));
+        admin.clusters().createCluster("global", new ClusterDataImpl());
 
         final String property = "peer-prop";
         Set<String> allowedClusters = Sets.newHashSet("us-west1", "us-west2", "us-west3", "us-west4", "us-east1",
                 "us-east2");
-        TenantInfo propConfig = new TenantInfo(Sets.newHashSet("test"), allowedClusters);
+        TenantInfoImpl propConfig = new TenantInfoImpl(Sets.newHashSet("test"), allowedClusters);
         admin.tenants().createTenant(property, propConfig);
 
         final String namespace = property + "/global/conflictPeer";
@@ -648,9 +649,9 @@ public class V1_AdminApiTest2 extends MockedPulsarServiceBaseTest {
 
         final String cluster = pulsar.getConfiguration().getClusterName();
         admin.clusters().createCluster(cluster,
-                new ClusterData(pulsar.getSafeWebServiceAddress(), pulsar.getWebServiceAddressTls()));
+                new ClusterDataImpl(pulsar.getSafeWebServiceAddress(), pulsar.getWebServiceAddressTls()));
         // create
-        FailureDomain domain = new FailureDomain();
+        FailureDomainImpl domain = new FailureDomainImpl();
         domain.setBrokers(Sets.newHashSet("b1", "b2", "b3"));
         admin.clusters().createFailureDomain(cluster, "domain-1", domain);
         admin.clusters().updateFailureDomain(cluster, "domain-1", domain);
@@ -789,7 +790,7 @@ public class V1_AdminApiTest2 extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testTenantNameWithUnderscore() throws Exception {
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use"));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use"));
         admin.tenants().createTenant("prop_xyz", tenantInfo);
 
         admin.namespaces().createNamespace("prop_xyz/use/my-namespace");
@@ -809,7 +810,7 @@ public class V1_AdminApiTest2 extends MockedPulsarServiceBaseTest {
 
     @Test
     public void testTenantNameWithInvalidCharacters() throws Exception {
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use"));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("use"));
 
         // If we try to create property with invalid characters, it should fail immediately
         try {
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v3/AdminApiTransactionTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v3/AdminApiTransactionTest.java
index a355574..ee68cfd 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v3/AdminApiTransactionTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/admin/v3/AdminApiTransactionTest.java
@@ -36,9 +36,9 @@ import org.apache.pulsar.client.impl.transaction.TransactionImpl;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicDomain;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.ManagedLedgerInternalStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TransactionBufferStats;
 import org.apache.pulsar.common.policies.data.TransactionCoordinatorInternalStats;
 import org.apache.pulsar.common.policies.data.TransactionCoordinatorStats;
@@ -72,8 +72,8 @@ public class AdminApiTransactionTest extends MockedPulsarServiceBaseTest {
         conf.setSystemTopicEnabled(true);
         conf.setTransactionBufferSnapshotMaxTransactionCount(1);
         super.internalSetup();
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("pulsar", tenantInfo);
         admin.namespaces().createNamespace("pulsar/system", Sets.newHashSet("test"));
         admin.tenants().createTenant("public", tenantInfo);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/AuthLogsTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/AuthLogsTest.java
index bb9f541..d128e95 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/AuthLogsTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/AuthLogsTest.java
@@ -20,8 +20,8 @@ package org.apache.pulsar.broker.auth;
 
 import static org.testng.Assert.fail;
 
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.annotations.AfterClass;
 
 import org.testng.annotations.BeforeClass;
@@ -69,9 +69,9 @@ public class AuthLogsTest extends MockedPulsarServiceBaseTest {
         try (PulsarAdmin admin = PulsarAdmin.builder()
              .authentication(new MockAuthentication("pass.pass"))
              .serviceHttpUrl(brokerUrl.toString()).build()) {
-            admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
+            admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
             admin.tenants().createTenant("public",
-                                         new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                                         new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
             admin.namespaces().createNamespace("public/default");
             admin.namespaces().setNamespaceReplicationClusters("public/default", Sets.newHashSet("test"));
         }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/AuthorizationTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/AuthorizationTest.java
index 5c68a7b..5e5e742 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/AuthorizationTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/AuthorizationTest.java
@@ -28,8 +28,8 @@ import org.apache.pulsar.broker.authorization.AuthorizationService;
 import org.apache.pulsar.client.admin.PulsarAdminBuilder;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.policies.data.AuthAction;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.SubscriptionAuthMode;
 import org.testng.annotations.AfterClass;
 import org.testng.annotations.BeforeClass;
@@ -74,8 +74,8 @@ public class AuthorizationTest extends MockedPulsarServiceBaseTest {
 
         assertFalse(auth.canLookup(TopicName.get("persistent://p1/c1/ns1/ds1"), "my-role", null));
 
-        admin.clusters().createCluster("c1", new ClusterData());
-        admin.tenants().createTenant("p1", new TenantInfo(Sets.newHashSet("role1"), Sets.newHashSet("c1")));
+        admin.clusters().createCluster("c1", new ClusterDataImpl());
+        admin.tenants().createTenant("p1", new TenantInfoImpl(Sets.newHashSet("role1"), Sets.newHashSet("c1")));
         waitForChange();
         admin.namespaces().createNamespace("p1/c1/ns1");
         waitForChange();
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/MockAuthorizationProvider.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/MockAuthorizationProvider.java
index 421da4f..f61b0de 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/MockAuthorizationProvider.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/MockAuthorizationProvider.java
@@ -31,7 +31,7 @@ import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.policies.data.AuthAction;
 import org.apache.pulsar.common.policies.data.PolicyName;
 import org.apache.pulsar.common.policies.data.PolicyOperation;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.NamespaceOperation;
 import org.apache.pulsar.common.policies.data.TenantOperation;
 import org.apache.pulsar.common.policies.data.TopicOperation;
@@ -58,7 +58,7 @@ public class MockAuthorizationProvider implements AuthorizationProvider {
     }
 
     @Override
-    public CompletableFuture<Boolean> isTenantAdmin(String tenant, String role, TenantInfo tenantInfo,
+    public CompletableFuture<Boolean> isTenantAdmin(String tenant, String role, TenantInfoImpl tenantInfo,
                                                     AuthenticationDataSource authenticationData) {
         return roleAuthorizedAsync(role);
     }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/MockedPulsarServiceBaseTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/MockedPulsarServiceBaseTest.java
index 2175a3a..ac5f104 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/MockedPulsarServiceBaseTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/auth/MockedPulsarServiceBaseTest.java
@@ -23,7 +23,7 @@ import static org.mockito.Mockito.doReturn;
 import static org.mockito.Mockito.spy;
 import com.google.common.collect.Sets;
 import com.google.common.util.concurrent.MoreExecutors;
-import com.google.common.util.concurrent.ThreadFactoryBuilder;
+
 import java.lang.reflect.Field;
 import io.netty.channel.EventLoopGroup;
 import java.net.URI;
@@ -34,8 +34,6 @@ import java.util.Map;
 import java.util.Optional;
 import java.util.Set;
 import java.util.concurrent.CompletableFuture;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
 import java.util.concurrent.TimeUnit;
 import java.util.function.Predicate;
 import java.util.function.Supplier;
@@ -56,8 +54,8 @@ import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.client.api.ClientBuilder;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.api.PulsarClientException;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.metadata.impl.ZKMetadataStore;
 import org.apache.pulsar.tests.TestRetrySupport;
 import org.apache.pulsar.zookeeper.ZooKeeperClientFactory;
@@ -312,14 +310,14 @@ public abstract class MockedPulsarServiceBaseTest extends TestRetrySupport {
         }
     }
 
-    protected TenantInfo createDefaultTenantInfo() throws PulsarAdminException {
+    protected TenantInfoImpl createDefaultTenantInfo() throws PulsarAdminException {
         // create local cluster if not exist
         if (!admin.clusters().getClusters().contains(configClusterName)) {
-            admin.clusters().createCluster(configClusterName, new ClusterData());
+            admin.clusters().createCluster(configClusterName, new ClusterDataImpl());
         }
         Set<String> allowedClusters = Sets.newHashSet();
         allowedClusters.add(configClusterName);
-        return new TenantInfo(Sets.newHashSet(), allowedClusters);
+        return new TenantInfoImpl(Sets.newHashSet(), allowedClusters);
     }
 
     public static MockZooKeeper createMockZooKeeper() throws Exception {
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/AntiAffinityNamespaceGroupTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/AntiAffinityNamespaceGroupTest.java
index a827912..f125984 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/AntiAffinityNamespaceGroupTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/AntiAffinityNamespaceGroupTest.java
@@ -55,9 +55,9 @@ import org.apache.pulsar.common.naming.NamespaceBundleFactory;
 import org.apache.pulsar.common.naming.NamespaceBundles;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.ServiceUnitId;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.FailureDomain;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.FailureDomainImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.common.util.collections.ConcurrentOpenHashMap;
 import org.apache.pulsar.common.util.collections.ConcurrentOpenHashSet;
@@ -168,7 +168,7 @@ public class AntiAffinityNamespaceGroupTest {
     private void createCluster(ZooKeeper zk, ServiceConfiguration config) throws Exception {
         ZkUtils.createFullPathOptimistic(zk, "/admin/clusters/" + config.getClusterName(),
                 ObjectMapperFactory.getThreadLocal().writeValueAsBytes(
-                        new ClusterData("http://" + config.getAdvertisedAddress() + ":" + config.getWebServicePort().get())),
+                        new ClusterDataImpl("http://" + config.getAdvertisedAddress() + ":" + config.getWebServicePort().get())),
                 Ids.OPEN_ACL_UNSAFE, CreateMode.PERSISTENT);
     }
 
@@ -211,7 +211,7 @@ public class AntiAffinityNamespaceGroupTest {
 
         pulsar1.getConfiguration().setFailureDomainsEnabled(true);
         admin1.tenants().createTenant("my-tenant",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
 
         for (int i = 0; i < totalNamespaces; i++) {
             final String ns = namespace + i;
@@ -307,7 +307,7 @@ public class AntiAffinityNamespaceGroupTest {
         final String bundle = "/0x00000000_0xffffffff";
 
         admin1.tenants().createTenant("my-tenant",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
 
         for (int i = 0; i < totalNamespaces; i++) {
             final String ns = namespace + i;
@@ -402,15 +402,15 @@ public class AntiAffinityNamespaceGroupTest {
         final String namespace2 = tenant + "/" + cluster + "/ns2";
         final String namespaceAntiAffinityGroup = "group";
 
-        FailureDomain domain1 = new FailureDomain();
+        FailureDomainImpl domain1 = new FailureDomainImpl();
         domain1.brokers = Sets.newHashSet(broker1);
         admin1.clusters().createFailureDomain(cluster, "domain1", domain1);
 
-        FailureDomain domain2 = new FailureDomain();
+        FailureDomainImpl domain2 = new FailureDomainImpl();
         domain2.brokers = Sets.newHashSet(broker2);
         admin1.clusters().createFailureDomain(cluster, "domain2", domain2);
 
-        admin1.tenants().createTenant(tenant, new TenantInfo(null, Sets.newHashSet(cluster)));
+        admin1.tenants().createTenant(tenant, new TenantInfoImpl(null, Sets.newHashSet(cluster)));
         admin1.namespaces().createNamespace(namespace1);
         admin1.namespaces().createNamespace(namespace2);
 
@@ -460,7 +460,7 @@ public class AntiAffinityNamespaceGroupTest {
         final String bundle = "/0x00000000_0xffffffff";
 
         admin1.tenants().createTenant("my-tenant",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
 
         for (int i = 0; i < totalNamespaces; i++) {
             final String ns = namespace + i;
@@ -513,7 +513,7 @@ public class AntiAffinityNamespaceGroupTest {
         final String bundle = "0x00000000_0xffffffff";
 
         admin1.tenants().createTenant("my-tenant",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
 
         for (int i = 0; i < totalNamespaces; i++) {
             final String ns = namespace + i;
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/LeaderElectionServiceTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/LeaderElectionServiceTest.java
index 5f0a1fb..b1fd368 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/LeaderElectionServiceTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/LeaderElectionServiceTest.java
@@ -33,8 +33,8 @@ import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.api.PulsarClientException;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.functions.worker.WorkerService;
 import org.apache.pulsar.zookeeper.LocalBookkeeperEnsemble;
 import org.mockito.Mockito;
@@ -87,8 +87,8 @@ public class LeaderElectionServiceTest {
         final String namespace = "ns";
         @Cleanup
         PulsarAdmin adminClient = PulsarAdmin.builder().serviceHttpUrl(pulsar.getWebServiceAddress()).build();
-        adminClient.clusters().createCluster(clusterName, new ClusterData(pulsar.getWebServiceAddress()));
-        adminClient.tenants().createTenant(tenant, new TenantInfo(Sets.newHashSet("appid1", "appid2"),
+        adminClient.clusters().createCluster(clusterName, new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        adminClient.tenants().createTenant(tenant, new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"),
                 Sets.newHashSet(clusterName)));
         adminClient.namespaces().createNamespace(tenant + "/" + namespace, 16);
         @Cleanup
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/LoadBalancerTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/LoadBalancerTest.java
index 073694d..d48c2ca 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/LoadBalancerTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/LoadBalancerTest.java
@@ -51,10 +51,10 @@ import org.apache.pulsar.broker.loadbalance.impl.SimpleLoadManagerImpl;
 import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.client.admin.internal.NamespacesImpl;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.AutoFailoverPolicyData;
+import org.apache.pulsar.common.policies.data.AutoFailoverPolicyDataImpl;
 import org.apache.pulsar.common.policies.data.AutoFailoverPolicyType;
 import org.apache.pulsar.common.policies.data.BundlesData;
-import org.apache.pulsar.common.policies.data.NamespaceIsolationData;
+import org.apache.pulsar.common.policies.data.NamespaceIsolationDataImpl;
 import org.apache.pulsar.common.policies.data.Policies;
 import org.apache.pulsar.common.policies.data.ResourceQuota;
 import org.apache.pulsar.common.policies.impl.NamespaceIsolationPolicies;
@@ -708,7 +708,7 @@ public class LoadBalancerTest {
         NamespaceIsolationPolicies policies = new NamespaceIsolationPolicies();
 
         // set up policy that use this broker as primary
-        NamespaceIsolationData policyData = new NamespaceIsolationData();
+        NamespaceIsolationDataImpl policyData = new NamespaceIsolationDataImpl();
         policyData.namespaces = new ArrayList<String>();
         policyData.namespaces.add("pulsar/use/primary-ns.*");
         policyData.primary = new ArrayList<String>();
@@ -716,7 +716,7 @@ public class LoadBalancerTest {
             policyData.primary.add(pulsarServices[i].getAdvertisedAddress());
         }
         policyData.secondary = new ArrayList<String>();
-        policyData.auto_failover_policy = new AutoFailoverPolicyData();
+        policyData.auto_failover_policy = new AutoFailoverPolicyDataImpl();
         policyData.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
         policyData.auto_failover_policy.parameters = new HashMap<>();
         policyData.auto_failover_policy.parameters.put("min_limit", "1");
@@ -724,7 +724,7 @@ public class LoadBalancerTest {
         policies.setPolicy("primaryBrokerPolicy", policyData);
 
         // set up policy that use this broker as secondary
-        policyData = new NamespaceIsolationData();
+        policyData = new NamespaceIsolationDataImpl();
         policyData.namespaces = new ArrayList<String>();
         policyData.namespaces.add("pulsar/use/secondary-ns.*");
         policyData.primary = new ArrayList<String>();
@@ -733,7 +733,7 @@ public class LoadBalancerTest {
         for (int i = 1; i < BROKER_COUNT; i++) {
             policyData.secondary.add(pulsarServices[i].getAdvertisedAddress());
         }
-        policyData.auto_failover_policy = new AutoFailoverPolicyData();
+        policyData.auto_failover_policy = new AutoFailoverPolicyDataImpl();
         policyData.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
         policyData.auto_failover_policy.parameters = new HashMap<String, String>();
         policyData.auto_failover_policy.parameters.put("min_limit", "1");
@@ -741,7 +741,7 @@ public class LoadBalancerTest {
         policies.setPolicy("secondaryBrokerPolicy", policyData);
 
         // set up policy that do not use this broker (neither primary nor secondary)
-        policyData = new NamespaceIsolationData();
+        policyData = new NamespaceIsolationDataImpl();
         policyData.namespaces = new ArrayList<String>();
         policyData.namespaces.add("pulsar/use/shared-ns.*");
         policyData.primary = new ArrayList<String>();
@@ -750,7 +750,7 @@ public class LoadBalancerTest {
         for (int i = 1; i < BROKER_COUNT; i++) {
             policyData.secondary.add(pulsarServices[i].getAdvertisedAddress());
         }
-        policyData.auto_failover_policy = new AutoFailoverPolicyData();
+        policyData.auto_failover_policy = new AutoFailoverPolicyDataImpl();
         policyData.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
         policyData.auto_failover_policy.parameters = new HashMap<String, String>();
         policyData.auto_failover_policy.parameters.put("min_limit", "1");
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/ModularLoadManagerImplTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/ModularLoadManagerImplTest.java
index 3414afb..575a418 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/ModularLoadManagerImplTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/ModularLoadManagerImplTest.java
@@ -68,9 +68,9 @@ import org.apache.pulsar.common.naming.NamespaceBundleFactory;
 import org.apache.pulsar.common.naming.NamespaceBundles;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.ServiceUnitId;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.NamespaceIsolationData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.NamespaceIsolationDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.metadata.api.Notification;
 import org.apache.pulsar.metadata.api.NotificationType;
@@ -493,9 +493,9 @@ public class ModularLoadManagerImplTest {
         final String broker1Address = pulsar1.getAdvertisedAddress() + "0";
         final String broker2Address = pulsar2.getAdvertisedAddress() + "1";
         final String sharedBroker = "broker3";
-        admin1.clusters().createCluster(cluster, new ClusterData("http://" + pulsar1.getAdvertisedAddress()));
+        admin1.clusters().createCluster(cluster, new ClusterDataImpl("http://" + pulsar1.getAdvertisedAddress()));
         admin1.tenants().createTenant(tenant,
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet(cluster)));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet(cluster)));
         admin1.namespaces().createNamespace(tenant + "/" + cluster + "/" + namespace);
 
         // set a new policy
@@ -505,8 +505,8 @@ public class ModularLoadManagerImplTest {
                 broker2Address, 1);
         String newPolicyName = "my-ns-isolation-policies";
         ObjectMapper jsonMapper = ObjectMapperFactory.create();
-        NamespaceIsolationData nsPolicyData = jsonMapper.readValue(newPolicyJson.getBytes(),
-                NamespaceIsolationData.class);
+        NamespaceIsolationDataImpl nsPolicyData = jsonMapper.readValue(newPolicyJson.getBytes(),
+                NamespaceIsolationDataImpl.class);
         admin1.clusters().createNamespaceIsolationPolicy("use", newPolicyName, nsPolicyData);
 
         SimpleResourceAllocationPolicies simpleResourceAllocationPolicies = new SimpleResourceAllocationPolicies(
@@ -553,7 +553,7 @@ public class ModularLoadManagerImplTest {
 
         newPolicyJson = String.format(newPolicyJsonTemplate, tenant, cluster, namespace, broker1Address,
                 broker2Address, 2);
-        nsPolicyData = jsonMapper.readValue(newPolicyJson.getBytes(), NamespaceIsolationData.class);
+        nsPolicyData = jsonMapper.readValue(newPolicyJson.getBytes(), NamespaceIsolationDataImpl.class);
         admin1.clusters().createNamespaceIsolationPolicy("use", newPolicyName, nsPolicyData);
 
         // test1: shared=1, primary=1, secondary=1 => It should return primary + secondary
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/SimpleLoadManagerImplTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/SimpleLoadManagerImplTest.java
index 4307955..5e19d4f 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/SimpleLoadManagerImplTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/loadbalance/SimpleLoadManagerImplTest.java
@@ -67,9 +67,9 @@ import org.apache.pulsar.client.admin.BrokerStats;
 import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.common.naming.NamespaceBundle;
 import org.apache.pulsar.common.naming.NamespaceName;
-import org.apache.pulsar.common.policies.data.AutoFailoverPolicyData;
+import org.apache.pulsar.common.policies.data.AutoFailoverPolicyDataImpl;
 import org.apache.pulsar.common.policies.data.AutoFailoverPolicyType;
-import org.apache.pulsar.common.policies.data.NamespaceIsolationData;
+import org.apache.pulsar.common.policies.data.NamespaceIsolationDataImpl;
 import org.apache.pulsar.common.policies.data.ResourceQuota;
 import org.apache.pulsar.common.policies.impl.NamespaceIsolationPolicies;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
@@ -174,14 +174,14 @@ public class SimpleLoadManagerImplTest {
     private void createNamespacePolicies(PulsarService pulsar) throws Exception {
         NamespaceIsolationPolicies policies = new NamespaceIsolationPolicies();
         // set up policy that use this broker as primary
-        NamespaceIsolationData policyData = new NamespaceIsolationData();
+        NamespaceIsolationDataImpl policyData = new NamespaceIsolationDataImpl();
         policyData.namespaces = new ArrayList<>();
         policyData.namespaces.add("pulsar/use/primary-ns.*");
         policyData.primary = new ArrayList<>();
         policyData.primary.add(pulsar1.getAdvertisedAddress() + "*");
         policyData.secondary = new ArrayList<>();
         policyData.secondary.add("prod2-broker([78]).messaging.usw.example.co.*");
-        policyData.auto_failover_policy = new AutoFailoverPolicyData();
+        policyData.auto_failover_policy = new AutoFailoverPolicyDataImpl();
         policyData.auto_failover_policy.policy_type = AutoFailoverPolicyType.min_available;
         policyData.auto_failover_policy.parameters = new HashMap<>();
         policyData.auto_failover_policy.parameters.put("min_limit", "1");
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/lookup/http/HttpTopicLookupv2Test.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/lookup/http/HttpTopicLookupv2Test.java
index 8fb06af..a564252 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/lookup/http/HttpTopicLookupv2Test.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/lookup/http/HttpTopicLookupv2Test.java
@@ -51,7 +51,7 @@ import org.apache.pulsar.broker.service.BrokerService;
 import org.apache.pulsar.broker.web.PulsarWebResource;
 import org.apache.pulsar.broker.web.RestException;
 import org.apache.pulsar.common.naming.TopicDomain;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.Policies;
 import org.apache.pulsar.zookeeper.ZooKeeperChildrenCache;
 import org.apache.pulsar.zookeeper.ZooKeeperDataCache;
@@ -73,7 +73,7 @@ public class HttpTopicLookupv2Test {
     private ServiceConfiguration config;
     private ConfigurationCacheService mockConfigCache;
     private ZooKeeperChildrenCache clustersListCache;
-    private ZooKeeperDataCache<ClusterData> clustersCache;
+    private ZooKeeperDataCache<ClusterDataImpl> clustersCache;
     private ZooKeeperDataCache<Policies> policiesCache;
     private Set<String> clusters;
 
@@ -93,9 +93,9 @@ public class HttpTopicLookupv2Test {
         clusters.add("use");
         clusters.add("usc");
         clusters.add("usw");
-        ClusterData useData = new ClusterData("http://broker.messaging.use.example.com:8080");
-        ClusterData uscData = new ClusterData("http://broker.messaging.usc.example.com:8080");
-        ClusterData uswData = new ClusterData("http://broker.messaging.usw.example.com:8080");
+        ClusterDataImpl useData = new ClusterDataImpl("http://broker.messaging.use.example.com:8080");
+        ClusterDataImpl uscData = new ClusterDataImpl("http://broker.messaging.usc.example.com:8080");
+        ClusterDataImpl uswData = new ClusterDataImpl("http://broker.messaging.usw.example.com:8080");
         doReturn(config).when(pulsar).getConfiguration();
         doReturn(mockConfigCache).when(pulsar).getConfigurationCache();
         doReturn(clustersListCache).when(mockConfigCache).clustersListCache();
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/namespace/OwnerShipCacheForCurrentServerTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/namespace/OwnerShipCacheForCurrentServerTest.java
index 8d5fe5a..7c85c3a 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/namespace/OwnerShipCacheForCurrentServerTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/namespace/OwnerShipCacheForCurrentServerTest.java
@@ -21,8 +21,8 @@ package org.apache.pulsar.broker.namespace;
 import com.google.common.collect.Sets;
 import org.apache.pulsar.common.naming.NamespaceBundle;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -40,9 +40,9 @@ public class OwnerShipCacheForCurrentServerTest extends OwnerShipForCurrentServe
         internalSetup();
         String[] brokerServiceUrlArr = getPulsarServiceList().get(0).getBrokerServiceUrl().split(":");
         String webServicePort = brokerServiceUrlArr[brokerServiceUrlArr.length -1];
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData("http://localhost:" + webServicePort));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl("http://localhost:" + webServicePort));
         admin.tenants().createTenant(TENANT,
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NAMESPACE);
         admin.topics().createNonPartitionedTopic(TOPIC_TEST);
     }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceGroupServiceTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceGroupServiceTest.java
index df2e6a4..2f9a00c 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceGroupServiceTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceGroupServiceTest.java
@@ -29,7 +29,7 @@ import org.apache.pulsar.broker.service.resource.usage.ResourceUsage;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.testng.annotations.AfterClass;
@@ -245,6 +245,6 @@ public class ResourceGroupServiceTest extends MockedPulsarServiceBaseTest {
     private static final int PUBLISH_INTERVAL_SECS = 500;
     private void prepareData() throws PulsarAdminException {
         this.conf.setResourceUsageTransportPublishIntervalInSecs(PUBLISH_INTERVAL_SECS);
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getBrokerServiceUrl()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getBrokerServiceUrl()));
     }
 }
\ No newline at end of file
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceGroupUsageAggregationTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceGroupUsageAggregationTest.java
index a8892b2..de5aee6 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceGroupUsageAggregationTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceGroupUsageAggregationTest.java
@@ -32,11 +32,9 @@ import org.apache.pulsar.client.api.ProducerConsumerBase;
 import org.apache.pulsar.client.api.PulsarClientException;
 import org.apache.pulsar.client.api.SubscriptionType;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicStats;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
 import org.testng.Assert;
 import org.testng.annotations.AfterClass;
 import org.testng.annotations.BeforeClass;
@@ -251,9 +249,9 @@ public class ResourceGroupUsageAggregationTest extends ProducerConsumerBase {
         this.conf.setAllowAutoTopicCreation(true);
 
         final String clusterName = "test";
-        admin.clusters().createCluster(clusterName, new ClusterData(pulsar.getBrokerServiceUrl()));
+        admin.clusters().createCluster(clusterName, new ClusterDataImpl(pulsar.getBrokerServiceUrl()));
             admin.tenants().createTenant(TenantName,
-                    new TenantInfo(Sets.newHashSet("fakeAdminRole"), Sets.newHashSet(clusterName)));
+                    new TenantInfoImpl(Sets.newHashSet("fakeAdminRole"), Sets.newHashSet(clusterName)));
         admin.namespaces().createNamespace(TenantAndNsName);
         admin.namespaces().setNamespaceReplicationClusters(TenantAndNsName, Sets.newHashSet(clusterName));
     }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceUsageTransportManagerTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceUsageTransportManagerTest.java
index 89246d8..1f9f735 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceUsageTransportManagerTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/resourcegroup/ResourceUsageTransportManagerTest.java
@@ -23,7 +23,7 @@ import org.apache.pulsar.broker.service.resource.usage.NetworkUsage;
 import org.apache.pulsar.broker.service.resource.usage.ResourceUsage;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.testng.annotations.AfterClass;
 import org.testng.annotations.BeforeClass;
 import org.testng.annotations.Test;
@@ -115,6 +115,6 @@ public class ResourceUsageTransportManagerTest extends MockedPulsarServiceBaseTe
     private void prepareData() throws PulsarAdminException {
         this.conf.setResourceUsageTransportClassName("org.apache.pulsar.broker.resourcegroup.ResourceUsageTransportManager");
         this.conf.setResourceUsageTransportPublishIntervalInSecs(PUBLISH_INTERVAL_SECS);
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getBrokerServiceUrl()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getBrokerServiceUrl()));
     }
 }
\ No newline at end of file
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BacklogQuotaManagerTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BacklogQuotaManagerTest.java
index e73c437..f960e01 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BacklogQuotaManagerTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BacklogQuotaManagerTest.java
@@ -46,9 +46,9 @@ import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.api.PulsarClientException;
 import org.apache.pulsar.client.api.Reader;
 import org.apache.pulsar.common.policies.data.BacklogQuota;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicStats;
 import org.apache.pulsar.zookeeper.LocalBookkeeperEnsemble;
 import org.awaitility.Awaitility;
@@ -99,9 +99,9 @@ public class BacklogQuotaManagerTest {
             adminUrl = new URL("http://127.0.0.1" + ":" + pulsar.getListenPortHTTP().get());
             admin = PulsarAdmin.builder().serviceHttpUrl(adminUrl.toString()).build();
 
-            admin.clusters().createCluster("usc", new ClusterData(adminUrl.toString()));
+            admin.clusters().createCluster("usc", new ClusterDataImpl(adminUrl.toString()));
             admin.tenants().createTenant("prop",
-                    new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet("usc")));
+                    new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet("usc")));
             admin.namespaces().createNamespace("prop/ns-quota");
             admin.namespaces().setNamespaceReplicationClusters("prop/ns-quota", Sets.newHashSet("usc"));
             admin.namespaces().createNamespace("prop/quotahold");
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BkEnsemblesTestBase.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BkEnsemblesTestBase.java
index 68fc1ed..fbc4a99 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BkEnsemblesTestBase.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BkEnsemblesTestBase.java
@@ -24,8 +24,8 @@ import java.util.Properties;
 import org.apache.pulsar.broker.PulsarService;
 import org.apache.pulsar.broker.ServiceConfiguration;
 import org.apache.pulsar.client.admin.PulsarAdmin;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.tests.TestRetrySupport;
 import org.apache.pulsar.zookeeper.LocalBookkeeperEnsemble;
 import org.testng.Assert;
@@ -98,9 +98,9 @@ public abstract class BkEnsemblesTestBase extends TestRetrySupport {
 
             admin = PulsarAdmin.builder().serviceHttpUrl(pulsar.getWebServiceAddress()).build();
 
-            admin.clusters().createCluster("usc", new ClusterData(pulsar.getWebServiceAddress()));
+            admin.clusters().createCluster("usc", new ClusterDataImpl(pulsar.getWebServiceAddress()));
             admin.tenants().createTenant("prop",
-                    new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet("usc")));
+                    new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet("usc")));
         } catch (Throwable t) {
             log.error("Error setting up broker test", t);
             Assert.fail("Broker test setup failed");
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerBookieIsolationTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerBookieIsolationTest.java
index b30150c..1a7df97 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerBookieIsolationTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerBookieIsolationTest.java
@@ -62,9 +62,9 @@ import org.apache.pulsar.client.api.PulsarClientException.BrokerPersistenceExcep
 import org.apache.pulsar.common.policies.data.BookieAffinityGroupData;
 import org.apache.pulsar.common.policies.data.BookieInfo;
 import org.apache.pulsar.common.policies.data.BookiesRackConfiguration;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.EnsemblePlacementPolicyConfig;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.zookeeper.LocalBookkeeperEnsemble;
 import org.apache.pulsar.zookeeper.ZkBookieRackAffinityMapping;
@@ -167,9 +167,9 @@ public class BrokerBookieIsolationTest {
 
         PulsarAdmin admin = PulsarAdmin.builder().serviceHttpUrl(pulsarService.getWebServiceAddress()).build();
 
-        ClusterData clusterData = new ClusterData(pulsarService.getWebServiceAddress());
+        ClusterDataImpl clusterData = new ClusterDataImpl(pulsarService.getWebServiceAddress());
         admin.clusters().createCluster(cluster, clusterData);
-        TenantInfo tenantInfo = new TenantInfo(null, Sets.newHashSet(cluster));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(null, Sets.newHashSet(cluster));
         admin.tenants().createTenant(tenant1, tenantInfo);
         admin.namespaces().createNamespace(ns1);
         admin.namespaces().createNamespace(ns2);
@@ -310,9 +310,9 @@ public class BrokerBookieIsolationTest {
 
         PulsarAdmin admin = PulsarAdmin.builder().serviceHttpUrl(pulsarService.getWebServiceAddress()).build();
 
-        ClusterData clusterData = new ClusterData(pulsarService.getWebServiceAddress());
+        ClusterDataImpl clusterData = new ClusterDataImpl(pulsarService.getWebServiceAddress());
         admin.clusters().createCluster(cluster, clusterData);
-        TenantInfo tenantInfo = new TenantInfo(null, Sets.newHashSet(cluster));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(null, Sets.newHashSet(cluster));
         admin.tenants().createTenant(tenant1, tenantInfo);
         admin.namespaces().createNamespace(ns1);
         admin.namespaces().createNamespace(ns2);
@@ -432,9 +432,9 @@ public class BrokerBookieIsolationTest {
 
         PulsarAdmin admin = PulsarAdmin.builder().serviceHttpUrl(pulsarService.getWebServiceAddress()).build();
 
-        ClusterData clusterData = new ClusterData(pulsarService.getWebServiceAddress());
+        ClusterDataImpl clusterData = new ClusterDataImpl(pulsarService.getWebServiceAddress());
         admin.clusters().createCluster(cluster, clusterData);
-        TenantInfo tenantInfo = new TenantInfo(null, Sets.newHashSet(cluster));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(null, Sets.newHashSet(cluster));
         admin.tenants().createTenant(tenant1, tenantInfo);
         admin.namespaces().createNamespace(ns2);
         admin.namespaces().createNamespace(ns3);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerServiceTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerServiceTest.java
index 9627234..380786a 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerServiceTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerServiceTest.java
@@ -30,6 +30,7 @@ import static org.testng.Assert.assertTrue;
 import static org.testng.Assert.fail;
 import com.google.common.collect.Lists;
 import com.google.common.collect.Sets;
+import com.google.gson.Gson;
 import com.google.gson.JsonArray;
 import com.google.gson.JsonObject;
 import java.io.BufferedReader;
@@ -366,7 +367,8 @@ public class BrokerServiceTest extends BrokerTestBase {
         }
         consumer.close();
         Thread.sleep(ASYNC_EVENT_COMPLETION_WAIT);
-        JsonArray metrics = brokerStatsClient.getMetrics();
+        String json = brokerStatsClient.getMetrics();
+        JsonArray metrics = new Gson().fromJson(json, JsonArray.class);
 
         // these metrics seem to be arriving in different order at different times...
         // is the order really relevant here?
@@ -414,7 +416,8 @@ public class BrokerServiceTest extends BrokerTestBase {
         }
 
         rolloverPerIntervalStats();
-        JsonObject topicStats = brokerStatsClient.getTopics();
+        String json = brokerStatsClient.getTopics();
+        JsonObject topicStats = new Gson().fromJson(json, JsonObject.class);
         assertEquals(topicStats.size(), 2, topicStats.toString());
 
         for (String ns : nsList) {
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerTestBase.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerTestBase.java
index 4830efb..b00ac20 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerTestBase.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/BrokerTestBase.java
@@ -18,11 +18,10 @@
  */
 package org.apache.pulsar.broker.service;
 
-import org.apache.pulsar.broker.PulsarService;
 import org.apache.pulsar.broker.ServiceConfiguration;
 import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -44,9 +43,9 @@ public abstract class BrokerTestBase extends MockedPulsarServiceBaseTest {
     }
 
     private void baseSetupCommon() throws Exception {
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("prop",
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("prop/ns-abc");
         admin.namespaces().setNamespaceReplicationClusters("prop/ns-abc", Sets.newHashSet("test"));
     }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/MaxMessageSizeTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/MaxMessageSizeTest.java
index b0dcb83..4b80bcb 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/MaxMessageSizeTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/MaxMessageSizeTest.java
@@ -32,8 +32,8 @@ import org.apache.pulsar.client.api.Consumer;
 import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.api.PulsarClientException;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.zookeeper.LocalBookkeeperEnsemble;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
@@ -76,9 +76,9 @@ public class MaxMessageSizeTest {
 
             String url = "http://127.0.0.1:" + pulsar.getListenPortHTTP().get();
             admin = PulsarAdmin.builder().serviceHttpUrl(url).build();
-            admin.clusters().createCluster("max_message_test", new ClusterData(url));
+            admin.clusters().createCluster("max_message_test", new ClusterDataImpl(url));
             admin.tenants()
-                 .createTenant("test", new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet("max_message_test")));
+                 .createTenant("test", new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet("max_message_test")));
             admin.namespaces().createNamespace("test/message", Sets.newHashSet("max_message_test"));
         } catch (Exception e) {
             e.printStackTrace();
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ReplicatorTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ReplicatorTest.java
index dc23429..fd544f2 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ReplicatorTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ReplicatorTest.java
@@ -71,7 +71,7 @@ import org.apache.pulsar.client.impl.conf.ProducerConfigurationData;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.policies.data.BacklogQuota;
 import org.apache.pulsar.common.policies.data.BacklogQuota.RetentionPolicy;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.ReplicatorStats;
 import org.apache.pulsar.common.protocol.Commands;
 import org.apache.pulsar.common.util.collections.ConcurrentOpenHashMap;
@@ -206,7 +206,7 @@ public class ReplicatorTest extends ReplicatorTestBase {
     public void activeBrokerParse() throws Exception {
         pulsar1.getConfiguration().setAuthorizationEnabled(true);
         //init clusterData
-        ClusterData cluster2Data = new ClusterData();
+        ClusterDataImpl cluster2Data = new ClusterDataImpl();
         String cluster2ServiceUrls = String.format("%s,localhost:1234,localhost:5678", pulsar2.getWebServiceAddress());
         cluster2Data.setServiceUrl(cluster2ServiceUrls);
         String cluster2 = "activeCLuster2";
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ReplicatorTestBase.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ReplicatorTestBase.java
index aeaacf9..d81eb1e 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ReplicatorTestBase.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ReplicatorTestBase.java
@@ -47,8 +47,8 @@ import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.api.PulsarClientException;
 import org.apache.pulsar.client.api.TypedMessageBuilder;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.zookeeper.LocalBookkeeperEnsemble;
 import org.apache.pulsar.zookeeper.ZookeeperServerTest;
 import org.slf4j.Logger;
@@ -156,15 +156,15 @@ public abstract class ReplicatorTestBase extends TestRetrySupport {
         admin3 = PulsarAdmin.builder().serviceHttpUrl(url3.toString()).build();
 
         // Provision the global namespace
-        admin1.clusters().createCluster("r1", new ClusterData(url1.toString(), urlTls1.toString(),
+        admin1.clusters().createCluster("r1", new ClusterDataImpl(url1.toString(), urlTls1.toString(),
                 pulsar1.getSafeBrokerServiceUrl(), pulsar1.getBrokerServiceUrlTls()));
-        admin1.clusters().createCluster("r2", new ClusterData(url2.toString(), urlTls2.toString(),
+        admin1.clusters().createCluster("r2", new ClusterDataImpl(url2.toString(), urlTls2.toString(),
                 pulsar2.getSafeBrokerServiceUrl(), pulsar2.getBrokerServiceUrlTls()));
-        admin1.clusters().createCluster("r3", new ClusterData(url3.toString(), urlTls3.toString(),
+        admin1.clusters().createCluster("r3", new ClusterDataImpl(url3.toString(), urlTls3.toString(),
                 pulsar3.getSafeBrokerServiceUrl(), pulsar3.getBrokerServiceUrlTls()));
 
         admin1.tenants().createTenant("pulsar",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2", "appid3"), Sets.newHashSet("r1", "r2", "r3")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2", "appid3"), Sets.newHashSet("r1", "r2", "r3")));
         admin1.namespaces().createNamespace("pulsar/ns", Sets.newHashSet("r1", "r2", "r3"));
         admin1.namespaces().createNamespace("pulsar/ns1", Sets.newHashSet("r1", "r2"));
 
@@ -176,7 +176,7 @@ public abstract class ReplicatorTestBase extends TestRetrySupport {
         assertEquals(admin2.clusters().getCluster("r3").getBrokerServiceUrl(), pulsar3.getSafeBrokerServiceUrl());
 
         // Also create V1 namespace for compatibility check
-        admin1.clusters().createCluster("global", new ClusterData("http://global:8080", "https://global:8443"));
+        admin1.clusters().createCluster("global", new ClusterDataImpl("http://global:8080", "https://global:8443"));
         admin1.namespaces().createNamespace("pulsar/global/ns");
         admin1.namespaces().setNamespaceReplicationClusters("pulsar/global/ns", Sets.newHashSet("r1", "r2", "r3"));
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ResendRequestTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ResendRequestTest.java
index c5214e1..6faa62b 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ResendRequestTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/ResendRequestTest.java
@@ -34,7 +34,7 @@ import org.apache.pulsar.client.api.*;
 import org.apache.pulsar.client.api.Consumer;
 import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.impl.ConsumerBase;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.testng.annotations.AfterMethod;
@@ -421,7 +421,7 @@ public class ResendRequestTest extends BrokerTestBase {
         final String messagePredicate = "my-message-" + key + "-";
         final int totalMessages = 10;
         final int numberOfPartitions = 4;
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName, numberOfPartitions);
         // Special step to create partitioned topic
@@ -477,7 +477,7 @@ public class ResendRequestTest extends BrokerTestBase {
         final String messagePredicate = "my-message-" + key + "-";
         final int totalMessages = 10;
         final int numberOfPartitions = 3;
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName, numberOfPartitions);
         Random rn = new Random();
@@ -578,7 +578,7 @@ public class ResendRequestTest extends BrokerTestBase {
         final String messagePredicate = "my-message-" + key + "-";
         final int totalMessages = 10;
         final int numberOfPartitions = 3;
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName, numberOfPartitions);
         Random rn = new Random();
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/SystemTopicBasedTopicPoliciesServiceTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/SystemTopicBasedTopicPoliciesServiceTest.java
index 4d2b8cf..79715c2 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/SystemTopicBasedTopicPoliciesServiceTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/SystemTopicBasedTopicPoliciesServiceTest.java
@@ -25,8 +25,8 @@ import org.apache.pulsar.broker.systopic.NamespaceEventsSystemTopicFactory;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicPolicies;
 import org.awaitility.Awaitility;
 import org.testng.Assert;
@@ -205,9 +205,9 @@ public class SystemTopicBasedTopicPoliciesServiceTest extends MockedPulsarServic
     }
 
     private void prepareData() throws PulsarAdminException {
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getBrokerServiceUrl()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getBrokerServiceUrl()));
         admin.tenants().createTenant("system-topic",
-                new TenantInfo(Sets.newHashSet(), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet(), Sets.newHashSet("test")));
         admin.namespaces().createNamespace(NAMESPACE1);
         admin.namespaces().createNamespace(NAMESPACE2);
         admin.namespaces().createNamespace(NAMESPACE3);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/TopicOwnerTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/TopicOwnerTest.java
index 6b287bf..28cc9da 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/TopicOwnerTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/service/TopicOwnerTest.java
@@ -46,8 +46,8 @@ import org.apache.pulsar.client.api.Consumer;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.common.naming.NamespaceBundle;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.metadata.api.extended.MetadataStoreExtended;
 import org.apache.pulsar.metadata.api.extended.SessionEvent;
 import org.apache.pulsar.zookeeper.LocalBookkeeperEnsemble;
@@ -117,8 +117,8 @@ public class TopicOwnerTest {
         leaderAdmin = pulsarAdmins[0];
         Thread.sleep(1000);
 
-        pulsarAdmins[0].clusters().createCluster(testCluster, new ClusterData(pulsarServices[0].getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo();
+        pulsarAdmins[0].clusters().createCluster(testCluster, new ClusterDataImpl(pulsarServices[0].getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl();
         tenantInfo.setAllowedClusters(Sets.newHashSet(testCluster));
         pulsarAdmins[0].tenants().createTenant(testTenant, tenantInfo);
         pulsarAdmins[0].namespaces().createNamespace(testNamespace, 16);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/stats/ManagedLedgerMetricsTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/stats/ManagedLedgerMetricsTest.java
index 41ee681..9d19e3e 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/stats/ManagedLedgerMetricsTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/stats/ManagedLedgerMetricsTest.java
@@ -32,7 +32,7 @@ import org.apache.pulsar.broker.stats.metrics.ManagedLedgerMetrics;
 import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.stats.Metrics;
 import org.apache.pulsar.transaction.coordinator.TransactionCoordinatorID;
 import org.apache.pulsar.transaction.coordinator.impl.MLTransactionLogImpl;
@@ -97,7 +97,7 @@ public class ManagedLedgerMetricsTest extends BrokerTestBase {
     @Test
     public void testTransactionTopic() throws Exception {
         admin.tenants().createTenant(NamespaceName.SYSTEM_NAMESPACE.getTenant(),
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace(NamespaceName.SYSTEM_NAMESPACE.toString());
         admin.topics().createPartitionedTopic(TopicName.TRANSACTION_COORDINATOR_ASSIGN.toString(), 1);
         ManagedLedgerConfig managedLedgerConfig = new ManagedLedgerConfig();
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/stats/TransactionMetricsTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/stats/TransactionMetricsTest.java
index 682de6b..16a43b6 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/stats/TransactionMetricsTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/stats/TransactionMetricsTest.java
@@ -34,6 +34,7 @@ import org.apache.pulsar.common.api.proto.TxnAction;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.transaction.coordinator.TransactionCoordinatorID;
 import org.apache.pulsar.transaction.coordinator.TransactionSubscription;
 import org.apache.pulsar.transaction.coordinator.TxnMeta;
@@ -197,7 +198,7 @@ public class TransactionMetricsTest extends BrokerTestBase {
         String subName = "test_managed_ledger_metrics";
         admin.topics().createNonPartitionedTopic(topic);
         admin.tenants().createTenant(NamespaceName.SYSTEM_NAMESPACE.getTenant(),
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace(NamespaceName.SYSTEM_NAMESPACE.toString());
         admin.topics().createPartitionedTopic(TopicName.TRANSACTION_COORDINATOR_ASSIGN.toString(), 1);
         TransactionCoordinatorID transactionCoordinatorIDOne = TransactionCoordinatorID.get(0);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/systopic/NamespaceEventsSystemTopicServiceTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/systopic/NamespaceEventsSystemTopicServiceTest.java
index eb08913..daaf4a3 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/systopic/NamespaceEventsSystemTopicServiceTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/systopic/NamespaceEventsSystemTopicServiceTest.java
@@ -29,8 +29,8 @@ import org.apache.pulsar.common.events.PulsarEvent;
 import org.apache.pulsar.common.events.TopicPoliciesEvent;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicPolicies;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -123,9 +123,9 @@ public class NamespaceEventsSystemTopicServiceTest extends MockedPulsarServiceBa
     }
 
     private void prepareData() throws PulsarAdminException {
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getBrokerServiceUrl()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getBrokerServiceUrl()));
         admin.tenants().createTenant("system-topic",
-            new TenantInfo(Sets.newHashSet(), Sets.newHashSet("test")));
+            new TenantInfoImpl(Sets.newHashSet(), Sets.newHashSet("test")));
         admin.namespaces().createNamespace(NAMESPACE1);
         admin.namespaces().createNamespace(NAMESPACE2);
         admin.namespaces().createNamespace(NAMESPACE3);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TopicTransactionBufferRecoverTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TopicTransactionBufferRecoverTest.java
index c1913ec..2078b26 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TopicTransactionBufferRecoverTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TopicTransactionBufferRecoverTest.java
@@ -53,8 +53,8 @@ import org.apache.pulsar.client.impl.transaction.TransactionImpl;
 import org.apache.pulsar.common.events.EventsTopicNames;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.collections.ConcurrentOpenHashMap;
 import org.awaitility.Awaitility;
 import org.testng.annotations.AfterMethod;
@@ -85,16 +85,16 @@ public class TopicTransactionBufferRecoverTest extends TransactionTestBase {
 
         String[] brokerServiceUrlArr = getPulsarServiceList().get(0).getBrokerServiceUrl().split(":");
         String webServicePort = brokerServiceUrlArr[brokerServiceUrlArr.length -1];
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData("http://localhost:" + webServicePort));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl("http://localhost:" + webServicePort));
         admin.tenants().createTenant(TENANT,
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NAMESPACE1);
         admin.topics().createNonPartitionedTopic(RECOVER_COMMIT);
         admin.topics().createNonPartitionedTopic(RECOVER_ABORT);
         admin.topics().createNonPartitionedTopic(TAKE_SNAPSHOT);
 
         admin.tenants().createTenant(NamespaceName.SYSTEM_NAMESPACE.getTenant(),
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NamespaceName.SYSTEM_NAMESPACE.toString());
         admin.topics().createPartitionedTopic(TopicName.TRANSACTION_COORDINATOR_ASSIGN.toString(), 16);
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionClientReconnectTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionClientReconnectTest.java
index a672149..9c5c366 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionClientReconnectTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionClientReconnectTest.java
@@ -28,8 +28,8 @@ import org.apache.pulsar.client.impl.PulsarClientImpl;
 import org.apache.pulsar.client.impl.transaction.TransactionImpl;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.transaction.coordinator.TransactionCoordinatorID;
 import org.awaitility.Awaitility;
 import org.testng.annotations.AfterMethod;
@@ -53,12 +53,12 @@ public class TransactionClientReconnectTest extends TransactionTestBase {
 
         String[] brokerServiceUrlArr = getPulsarServiceList().get(0).getBrokerServiceUrl().split(":");
         String webServicePort = brokerServiceUrlArr[brokerServiceUrlArr.length -1];
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData("http://localhost:" + webServicePort));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl("http://localhost:" + webServicePort));
         admin.tenants().createTenant("public",
-                new TenantInfo(Sets.newHashSet(), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet(), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace("public/txn", 10);
         admin.tenants().createTenant(NamespaceName.SYSTEM_NAMESPACE.getTenant(),
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NamespaceName.SYSTEM_NAMESPACE.toString());
         admin.topics().createNonPartitionedTopic(RECONNECT_TOPIC);
         admin.topics().createSubscription(RECONNECT_TOPIC, "test", MessageId.latest);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionConsumeTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionConsumeTest.java
index 644ea9e..1d0b28e 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionConsumeTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionConsumeTest.java
@@ -42,8 +42,8 @@ import org.apache.pulsar.client.api.transaction.TxnID;
 import org.apache.pulsar.common.api.proto.MessageIdData;
 import org.apache.pulsar.common.api.proto.MessageMetadata;
 import org.apache.pulsar.common.api.proto.TxnAction;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.protocol.Commands;
 import org.awaitility.Awaitility;
 import org.testng.Assert;
@@ -69,9 +69,9 @@ public class TransactionConsumeTest extends TransactionTestBase {
 
         String[] brokerServiceUrlArr = getPulsarServiceList().get(0).getBrokerServiceUrl().split(":");
         String webServicePort = brokerServiceUrlArr[brokerServiceUrlArr.length -1];
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData("http://localhost:" + webServicePort));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl("http://localhost:" + webServicePort));
         admin.tenants().createTenant("public",
-                new TenantInfo(Sets.newHashSet(), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet(), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace("public/txn", 10);
         admin.topics().createNonPartitionedTopic(CONSUME_TOPIC);
     }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionProduceTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionProduceTest.java
index a5bae35..6b69bf1 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionProduceTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/TransactionProduceTest.java
@@ -56,8 +56,8 @@ import org.apache.pulsar.common.api.proto.MarkerType;
 import org.apache.pulsar.common.api.proto.MessageMetadata;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.protocol.Commands;
 import org.awaitility.Awaitility;
 import org.testng.Assert;
@@ -87,9 +87,9 @@ public class TransactionProduceTest extends TransactionTestBase {
 
         String[] brokerServiceUrlArr = getPulsarServiceList().get(0).getBrokerServiceUrl().split(":");
         String webServicePort = brokerServiceUrlArr[brokerServiceUrlArr.length -1];
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData("http://localhost:" + webServicePort));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl("http://localhost:" + webServicePort));
         admin.tenants().createTenant(TENANT,
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NAMESPACE1);
         admin.topics().createPartitionedTopic(PRODUCE_COMMIT_TOPIC, 3);
         admin.topics().createPartitionedTopic(PRODUCE_ABORT_TOPIC, 3);
@@ -97,7 +97,7 @@ public class TransactionProduceTest extends TransactionTestBase {
         admin.topics().createPartitionedTopic(ACK_ABORT_TOPIC, 3);
 
         admin.tenants().createTenant(NamespaceName.SYSTEM_NAMESPACE.getTenant(),
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NamespaceName.SYSTEM_NAMESPACE.toString());
         admin.topics().createPartitionedTopic(TopicName.TRANSACTION_COORDINATOR_ASSIGN.toString(), 16);
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionBufferClientTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionBufferClientTest.java
index e66333b..5fb58ae 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionBufferClientTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionBufferClientTest.java
@@ -54,8 +54,8 @@ import org.apache.pulsar.client.impl.ClientCnx;
 import org.apache.pulsar.client.impl.PulsarClientImpl;
 import org.apache.pulsar.common.api.proto.TxnAction;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.collections.ConcurrentOpenHashMap;
 import org.awaitility.Awaitility;
 import org.mockito.Mockito;
@@ -85,8 +85,8 @@ public class TransactionBufferClientTest extends TransactionMetaStoreTestBase {
 
     @Override
     protected void afterSetup() throws Exception {
-        pulsarAdmins[0].clusters().createCluster("my-cluster", new ClusterData(pulsarServices[0].getWebServiceAddress()));
-        pulsarAdmins[0].tenants().createTenant("public", new TenantInfo(Sets.newHashSet(), Sets.newHashSet("my-cluster")));
+        pulsarAdmins[0].clusters().createCluster("my-cluster", new ClusterDataImpl(pulsarServices[0].getWebServiceAddress()));
+        pulsarAdmins[0].tenants().createTenant("public", new TenantInfoImpl(Sets.newHashSet(), Sets.newHashSet("my-cluster")));
         pulsarAdmins[0].namespaces().createNamespace(namespace, 10);
         pulsarAdmins[0].topics().createPartitionedTopic(partitionedTopicName.getPartitionedTopicName(), partitions);
         pulsarClient.newConsumer()
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionLowWaterMarkTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionLowWaterMarkTest.java
index e7f1b8c..20d92fb 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionLowWaterMarkTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionLowWaterMarkTest.java
@@ -56,8 +56,8 @@ import org.apache.pulsar.client.impl.transaction.TransactionImpl;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.partition.PartitionedTopicMetadata;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.collections.ConcurrentOpenHashMap;
 import org.apache.pulsar.transaction.coordinator.TransactionCoordinatorID;
 import org.apache.pulsar.transaction.coordinator.TransactionMetadataStore;
@@ -86,13 +86,13 @@ public class TransactionLowWaterMarkTest extends TransactionTestBase {
 
         String[] brokerServiceUrlArr = getPulsarServiceList().get(0).getBrokerServiceUrl().split(":");
         String webServicePort = brokerServiceUrlArr[brokerServiceUrlArr.length -1];
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData("http://localhost:" + webServicePort));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl("http://localhost:" + webServicePort));
         admin.tenants().createTenant(TENANT,
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NAMESPACE1);
         admin.topics().createNonPartitionedTopic(TOPIC);
         admin.tenants().createTenant(NamespaceName.SYSTEM_NAMESPACE.getTenant(),
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NamespaceName.SYSTEM_NAMESPACE.toString());
         admin.topics().createPartitionedTopic(TopicName.TRANSACTION_COORDINATOR_ASSIGN.toString(), 16);
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionStablePositionTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionStablePositionTest.java
index 8937153..3c91884 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionStablePositionTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/buffer/TransactionStablePositionTest.java
@@ -39,8 +39,8 @@ import org.apache.pulsar.client.api.transaction.TransactionCoordinatorClient;
 import org.apache.pulsar.client.impl.PulsarClientImpl;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -63,13 +63,13 @@ public class TransactionStablePositionTest extends TransactionTestBase {
 
         String[] brokerServiceUrlArr = getPulsarServiceList().get(0).getBrokerServiceUrl().split(":");
         String webServicePort = brokerServiceUrlArr[brokerServiceUrlArr.length -1];
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData("http://localhost:" + webServicePort));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl("http://localhost:" + webServicePort));
         admin.tenants().createTenant(TENANT,
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NAMESPACE1);
         admin.topics().createNonPartitionedTopic(TOPIC);
         admin.tenants().createTenant(NamespaceName.SYSTEM_NAMESPACE.getTenant(),
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NamespaceName.SYSTEM_NAMESPACE.toString());
         admin.topics().createPartitionedTopic(TopicName.TRANSACTION_COORDINATOR_ASSIGN.toString(), 16);
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/pendingack/PendingAckInMemoryDeleteTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/pendingack/PendingAckInMemoryDeleteTest.java
index db7d1a8..5ed73f3 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/pendingack/PendingAckInMemoryDeleteTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/pendingack/PendingAckInMemoryDeleteTest.java
@@ -41,8 +41,8 @@ import org.apache.pulsar.client.api.transaction.Transaction;
 import org.apache.pulsar.client.api.transaction.TxnID;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.collections.BitSetRecyclable;
 import org.apache.pulsar.common.util.collections.ConcurrentOpenHashMap;
 import org.apache.pulsar.transaction.coordinator.TransactionCoordinatorID;
@@ -80,12 +80,12 @@ public class PendingAckInMemoryDeleteTest extends TransactionTestBase {
 
         String[] brokerServiceUrlArr = getPulsarServiceList().get(0).getBrokerServiceUrl().split(":");
         String webServicePort = brokerServiceUrlArr[brokerServiceUrlArr.length -1];
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData("http://localhost:" + webServicePort));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl("http://localhost:" + webServicePort));
         admin.tenants().createTenant(TENANT,
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
 
         admin.tenants().createTenant(NamespaceName.SYSTEM_NAMESPACE.getTenant(),
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NAMESPACE1);
         admin.namespaces().createNamespace(NamespaceName.SYSTEM_NAMESPACE.toString());
         admin.topics().createPartitionedTopic(TopicName.TRANSACTION_COORDINATOR_ASSIGN.toString(), 16);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/pendingack/PendingAckPersistentTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/pendingack/PendingAckPersistentTest.java
index da24426..3143916 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/pendingack/PendingAckPersistentTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/transaction/pendingack/PendingAckPersistentTest.java
@@ -46,8 +46,8 @@ import org.apache.pulsar.client.api.SubscriptionType;
 import org.apache.pulsar.client.api.transaction.Transaction;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -68,13 +68,13 @@ public class PendingAckPersistentTest extends TransactionTestBase {
 
         String[] brokerServiceUrlArr = getPulsarServiceList().get(0).getBrokerServiceUrl().split(":");
         String webServicePort = brokerServiceUrlArr[brokerServiceUrlArr.length -1];
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData("http://localhost:" + webServicePort));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl("http://localhost:" + webServicePort));
         admin.tenants().createTenant(NamespaceName.SYSTEM_NAMESPACE.getTenant(),
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NamespaceName.SYSTEM_NAMESPACE.toString());
         admin.topics().createPartitionedTopic(TopicName.TRANSACTION_COORDINATOR_ASSIGN.toString(), 16);
         admin.tenants().createTenant("public",
-                new TenantInfo(Sets.newHashSet(), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet(), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace("public/txn", 10);
         admin.topics().createNonPartitionedTopic(PENDING_ACK_REPLAY_TOPIC);
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/web/WebServiceTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/web/WebServiceTest.java
index 5036f07..ea99572 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/web/WebServiceTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/web/WebServiceTest.java
@@ -63,8 +63,8 @@ import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.client.admin.PulsarAdminBuilder;
 import org.apache.pulsar.client.admin.PulsarAdminException.ConflictException;
 import org.apache.pulsar.client.impl.auth.AuthenticationTls;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.common.util.SecurityUtility;
 import org.apache.pulsar.metadata.impl.ZKMetadataStore;
@@ -272,7 +272,7 @@ public class WebServiceTest {
                 .setHeader("Content-Type", "application/json");
 
         // HTTP server is configured to reject everything > 10K
-        TenantInfo info1 = new TenantInfo();
+        TenantInfoImpl info1 = new TenantInfoImpl();
         info1.setAdminRoles(Collections.singleton(StringUtils.repeat("*", 20 * 1024)));
         builder.setBody(ObjectMapperFactory.getThreadLocal().writeValueAsBytes(info1));
         Response res = builder.execute().get();
@@ -283,8 +283,8 @@ public class WebServiceTest {
         // Create local cluster
         String localCluster = "test";
         String clusterPath = PulsarWebResource.path("clusters", localCluster);
-        pulsar.getPulsarResources().getClusterResources().create(clusterPath, new ClusterData());
-        TenantInfo info2 = new TenantInfo();
+        pulsar.getPulsarResources().getClusterResources().create(clusterPath, new ClusterDataImpl());
+        TenantInfoImpl info2 = new TenantInfoImpl();
         info2.setAdminRoles(Collections.singleton(StringUtils.repeat("*", 1 * 1024)));
         info2.setAllowedClusters(Sets.newHashSet(localCluster));
         builder.setBody(ObjectMapperFactory.getThreadLocal().writeValueAsBytes(info2));
@@ -434,7 +434,7 @@ public class WebServiceTest {
 
         try {
             pulsarAdmin.clusters().createCluster(config.getClusterName(),
-                    new ClusterData(pulsar.getSafeWebServiceAddress()));
+                    new ClusterDataImpl(pulsar.getSafeWebServiceAddress()));
         } catch (ConflictException ce) {
             // This is OK.
         } finally {
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/broker/zookeeper/ZooKeeperSessionExpireRecoveryTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/broker/zookeeper/ZooKeeperSessionExpireRecoveryTest.java
index 6bf84b3..acd631e 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/broker/zookeeper/ZooKeeperSessionExpireRecoveryTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/broker/zookeeper/ZooKeeperSessionExpireRecoveryTest.java
@@ -25,7 +25,7 @@ import com.google.common.collect.Sets;
 
 import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
 import org.apache.pulsar.client.admin.PulsarAdminException;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.zookeeper.KeeperException.Code;
 import org.apache.zookeeper.MockZooKeeper;
 import org.testng.annotations.AfterMethod;
@@ -52,7 +52,7 @@ public class ZooKeeperSessionExpireRecoveryTest extends MockedPulsarServiceBaseT
      */
     @Test
     public void testSessionExpired() throws Exception {
-        admin.clusters().createCluster("my-cluster", new ClusterData("test-url"));
+        admin.clusters().createCluster("my-cluster", new ClusterDataImpl("test-url"));
 
         assertTrue(Sets.newHashSet(admin.clusters().getClusters()).contains("my-cluster"));
 
@@ -64,12 +64,12 @@ public class ZooKeeperSessionExpireRecoveryTest extends MockedPulsarServiceBaseT
         assertTrue(Sets.newHashSet(admin.clusters().getClusters()).contains("my-cluster"));
 
         try {
-            admin.clusters().createCluster("my-cluster-2", new ClusterData("test-url"));
+            admin.clusters().createCluster("my-cluster-2", new ClusterDataImpl("test-url"));
             fail("Should have failed, because global zk is down");
         } catch (PulsarAdminException e) {
             // Ok
         }
 
-        admin.clusters().createCluster("cluster-2", new ClusterData("test-url"));
+        admin.clusters().createCluster("cluster-2", new ClusterDataImpl("test-url"));
     }
 }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthenticatedProducerConsumerTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthenticatedProducerConsumerTest.java
index f6fa07c..86445b6 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthenticatedProducerConsumerTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthenticatedProducerConsumerTest.java
@@ -37,8 +37,8 @@ import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.client.impl.auth.AuthenticationBasic;
 import org.apache.pulsar.client.impl.auth.AuthenticationTls;
 import org.apache.pulsar.common.policies.data.AuthAction;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.zookeeper.KeeperException.Code;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -171,10 +171,10 @@ public class AuthenticatedProducerConsumerTest extends ProducerConsumerBase {
         authTls.configure(authParams);
         internalSetup(authTls);
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
 
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
 
         testSyncProducerAndConsumer(batchMessageDelayMs);
@@ -189,10 +189,10 @@ public class AuthenticatedProducerConsumerTest extends ProducerConsumerBase {
         authPassword.configure("{\"userId\":\"superUser\",\"password\":\"supepass\"}");
         internalSetup(authPassword);
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
 
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet(), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet(), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
 
         testSyncProducerAndConsumer(batchMessageDelayMs);
@@ -207,10 +207,10 @@ public class AuthenticatedProducerConsumerTest extends ProducerConsumerBase {
         authPassword.configure("{\"userId\":\"superUser2\",\"password\":\"superpassword\"}");
         internalSetup(authPassword);
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
 
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet(), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet(), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
 
         testSyncProducerAndConsumer(batchMessageDelayMs);
@@ -229,10 +229,10 @@ public class AuthenticatedProducerConsumerTest extends ProducerConsumerBase {
         authTls.configure(authParams);
         internalSetup(authTls);
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString(), brokerUrlTls.toString(),
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString(), brokerUrlTls.toString(),
                 pulsar.getBrokerServiceUrl(), pulsar.getBrokerServiceUrlTls()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("anonymousUser"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("anonymousUser"), Sets.newHashSet("test")));
 
         // make a PulsarAdmin instance as "anonymousUser" for http request
         admin.close();
@@ -270,7 +270,7 @@ public class AuthenticatedProducerConsumerTest extends ProducerConsumerBase {
         internalSetup(authTls);
 
         final String cluster = "test";
-        final ClusterData clusterData = new ClusterData(brokerUrl.toString(), brokerUrlTls.toString(),
+        final ClusterDataImpl clusterData = new ClusterDataImpl(brokerUrl.toString(), brokerUrlTls.toString(),
                 pulsar.getBrokerServiceUrl(), pulsar.getBrokerServiceUrlTls());
         try {
             admin.clusters().createCluster(cluster, clusterData);
@@ -298,10 +298,10 @@ public class AuthenticatedProducerConsumerTest extends ProducerConsumerBase {
         authTls.configure(authParams);
         internalSetup(authTls);
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString(), brokerUrlTls.toString(),
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString(), brokerUrlTls.toString(),
                 pulsar.getBrokerServiceUrl(), pulsar.getBrokerServiceUrlTls()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         String namespace = "my-property/my-ns";
         admin.namespaces().createNamespace(namespace, Sets.newHashSet("test"));
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthenticationTlsHostnameVerificationTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthenticationTlsHostnameVerificationTest.java
index 6904943..75ff745 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthenticationTlsHostnameVerificationTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthenticationTlsHostnameVerificationTest.java
@@ -34,8 +34,8 @@ import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.client.impl.auth.AuthenticationTls;
 import org.apache.pulsar.common.tls.PublicSuffixMatcher;
 import org.apache.pulsar.common.tls.TlsHostnameVerifier;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.testng.Assert;
@@ -117,10 +117,10 @@ public class AuthenticationTlsHostnameVerificationTest extends ProducerConsumerB
                 .tlsTrustCertsFilePath(TLS_MIM_TRUST_CERT_FILE_PATH).allowTlsInsecureConnection(true)
                 .authentication(authTls).enableTls(true).enableTlsHostnameVerification(hostnameVerificationEnabled));
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
 
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthorizationProducerConsumerTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthorizationProducerConsumerTest.java
index c6751d6..47c23bb 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthorizationProducerConsumerTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/AuthorizationProducerConsumerTest.java
@@ -48,12 +48,11 @@ import org.apache.pulsar.client.impl.MessageIdImpl;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.policies.data.AuthAction;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.NamespaceOperation;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TenantOperation;
 import org.apache.pulsar.common.policies.data.TopicOperation;
-import org.apache.pulsar.common.util.FutureUtil;
 import org.apache.pulsar.common.util.RestException;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -130,10 +129,10 @@ public class AuthorizationProducerConsumerTest extends ProducerConsumerBase {
                 .operationTimeout(1000, TimeUnit.MILLISECONDS)
                 .authentication(authenticationInvalidRole).build();
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
 
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
 
         // (1) Valid Producer and consumer creation
@@ -195,10 +194,10 @@ public class AuthorizationProducerConsumerTest extends ProducerConsumerBase {
 
         Authentication authentication = new ClientAuthentication(subscriptionRole);
 
-        superAdmin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        superAdmin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
 
         superAdmin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet(tenantRole), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet(tenantRole), Sets.newHashSet("test")));
         superAdmin.namespaces().createNamespace(namespace, Sets.newHashSet("test"));
         tenantAdmin.namespaces().grantPermissionOnNamespace(namespace, subscriptionRole,
                 Collections.singleton(AuthAction.consume));
@@ -292,10 +291,10 @@ public class AuthorizationProducerConsumerTest extends ProducerConsumerBase {
                 .authentication(authentication));
 
 
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
 
         admin.tenants().createTenant("prop-prefix",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("prop-prefix/ns", Sets.newHashSet("test"));
 
         // (1) Valid subscription name will be approved by authorization service
@@ -513,7 +512,7 @@ public class AuthorizationProducerConsumerTest extends ProducerConsumerBase {
         }
 
         @Override
-        public CompletableFuture<Boolean> isTenantAdmin(String tenant, String role, TenantInfo tenantInfo, AuthenticationDataSource authenticationData) {
+        public CompletableFuture<Boolean> isTenantAdmin(String tenant, String role, TenantInfoImpl tenantInfo, AuthenticationDataSource authenticationData) {
             return CompletableFuture.completedFuture(true);
         }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/BrokerServiceLookupTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/BrokerServiceLookupTest.java
index 6ce907c..8fa8d45 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/BrokerServiceLookupTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/BrokerServiceLookupTest.java
@@ -83,8 +83,8 @@ import org.apache.pulsar.common.naming.NamespaceBundle;
 import org.apache.pulsar.common.naming.ServiceUnitId;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.partition.PartitionedTopicMetadata;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.common.util.SecurityUtility;
 import org.apache.pulsar.discovery.service.DiscoveryService;
@@ -271,9 +271,9 @@ public class BrokerServiceLookupTest extends ProducerConsumerBase {
         String broker2ServiceUrl = "pulsar://localhost:" + conf2.getBrokerServicePort().get();
 
         admin.clusters().createCluster(newCluster,
-                new ClusterData(pulsar.getWebServiceAddress(), null, broker2ServiceUrl, null));
+                new ClusterDataImpl(pulsar.getWebServiceAddress(), null, broker2ServiceUrl, null));
         admin.tenants().createTenant(property,
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet(newCluster)));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet(newCluster)));
         admin.namespaces().createNamespace(property + "/" + newCluster + "/my-ns");
 
         @Cleanup
@@ -1085,9 +1085,9 @@ public class BrokerServiceLookupTest extends ProducerConsumerBase {
         final int totalPartitions = 10;
         final TopicName dest = TopicName.get("persistent", property, cluster, namespace, topicName);
         admin.clusters().createCluster(cluster,
-                new ClusterData(pulsar.getWebServiceAddress(), null, null, null));
+                new ClusterDataImpl(pulsar.getWebServiceAddress(), null, null, null));
         admin.tenants().createTenant(property,
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet(cluster)));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet(cluster)));
         admin.namespaces().createNamespace(property + "/" + cluster + "/" + namespace);
         admin.topics().createPartitionedTopic(dest.toString(), totalPartitions);
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/ClientDeduplicationFailureTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/ClientDeduplicationFailureTest.java
index 18de76e..b28c39b 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/ClientDeduplicationFailureTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/ClientDeduplicationFailureTest.java
@@ -46,9 +46,9 @@ import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.apache.pulsar.client.impl.BatchMessageIdImpl;
 import org.apache.pulsar.client.impl.MessageIdImpl;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicStats;
 import org.apache.pulsar.zookeeper.LocalBookkeeperEnsemble;
 import org.testng.annotations.AfterMethod;
@@ -106,7 +106,7 @@ public class ClientDeduplicationFailureTest {
         primaryHost = pulsar.getWebServiceAddress();
 
         // update cluster metadata
-        ClusterData clusterData = new ClusterData(url.toString());
+        ClusterDataImpl clusterData = new ClusterDataImpl(url.toString());
         admin.clusters().createCluster(config.getClusterName(), clusterData);
 
         if (pulsarClient != null) {
@@ -115,7 +115,7 @@ public class ClientDeduplicationFailureTest {
         ClientBuilder clientBuilder = PulsarClient.builder().serviceUrl(pulsar.getBrokerServiceUrl()).maxBackoffInterval(1, TimeUnit.SECONDS);
         pulsarClient = clientBuilder.build();
 
-        TenantInfo tenantInfo = new TenantInfo();
+        TenantInfoImpl tenantInfo = new TenantInfoImpl();
         tenantInfo.setAllowedClusters(Sets.newHashSet(Lists.newArrayList("use")));
         admin.tenants().createTenant(tenant, tenantInfo);
     }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/MessageDispatchThrottlingTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/MessageDispatchThrottlingTest.java
index 7bb2699..e58f21a 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/MessageDispatchThrottlingTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/MessageDispatchThrottlingTest.java
@@ -38,7 +38,7 @@ import org.apache.bookkeeper.mledger.impl.ManagedLedgerImpl;
 import org.apache.pulsar.broker.service.BrokerService;
 import org.apache.pulsar.broker.service.persistent.DispatchRateLimiter;
 import org.apache.pulsar.broker.service.persistent.PersistentTopic;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.DispatchRate;
 import org.apache.pulsar.common.policies.data.Policies;
 import org.slf4j.Logger;
@@ -668,7 +668,7 @@ public class MessageDispatchThrottlingTest extends ProducerConsumerBase {
         final int messageRate = 5;
         DispatchRate dispatchRate = new DispatchRate(messageRate, -1, 360);
 
-        admin.clusters().createCluster("global", new ClusterData("http://global:8080"));
+        admin.clusters().createCluster("global", new ClusterDataImpl("http://global:8080"));
         admin.namespaces().createNamespace(namespace);
         admin.namespaces().setNamespaceReplicationClusters(namespace, Sets.newHashSet("test"));
         admin.namespaces().setDispatchRate(namespace, dispatchRate);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/NonPersistentTopicTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/NonPersistentTopicTest.java
index deaee35..a766b40 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/NonPersistentTopicTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/NonPersistentTopicTest.java
@@ -59,12 +59,12 @@ import org.apache.pulsar.client.impl.PartitionedProducerImpl;
 import org.apache.pulsar.client.impl.ProducerImpl;
 import org.apache.pulsar.common.naming.NamespaceBundle;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.NonPersistentPublisherStats;
 import org.apache.pulsar.common.policies.data.NonPersistentSubscriptionStats;
 import org.apache.pulsar.common.policies.data.NonPersistentTopicStats;
 import org.apache.pulsar.common.policies.data.SubscriptionStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.zookeeper.LocalBookkeeperEnsemble;
 import org.apache.pulsar.zookeeper.ZookeeperServerTest;
 import org.slf4j.Logger;
@@ -1004,15 +1004,15 @@ public class NonPersistentTopicTest extends ProducerConsumerBase {
             admin3 = PulsarAdmin.builder().serviceHttpUrl(url3.toString()).build();
 
             // Provision the global namespace
-            admin1.clusters().createCluster("r1", new ClusterData(url1.toString(), null, pulsar1.getSafeBrokerServiceUrl(),
+            admin1.clusters().createCluster("r1", new ClusterDataImpl(url1.toString(), null, pulsar1.getSafeBrokerServiceUrl(),
                     pulsar1.getBrokerServiceUrlTls()));
-            admin1.clusters().createCluster("r2", new ClusterData(url2.toString(), null, pulsar2.getSafeBrokerServiceUrl(),
+            admin1.clusters().createCluster("r2", new ClusterDataImpl(url2.toString(), null, pulsar2.getSafeBrokerServiceUrl(),
                     pulsar1.getBrokerServiceUrlTls()));
-            admin1.clusters().createCluster("r3", new ClusterData(url3.toString(), null, pulsar3.getSafeBrokerServiceUrl(),
+            admin1.clusters().createCluster("r3", new ClusterDataImpl(url3.toString(), null, pulsar3.getSafeBrokerServiceUrl(),
                     pulsar1.getBrokerServiceUrlTls()));
 
-            admin1.clusters().createCluster("global", new ClusterData("http://global:8080"));
-            admin1.tenants().createTenant("pulsar", new TenantInfo(
+            admin1.clusters().createCluster("global", new ClusterDataImpl("http://global:8080"));
+            admin1.tenants().createTenant("pulsar", new TenantInfoImpl(
                     Sets.newHashSet("appid1", "appid2", "appid3"), Sets.newHashSet("r1", "r2", "r3")));
             admin1.namespaces().createNamespace("pulsar/global/ns");
             admin1.namespaces().setNamespaceReplicationClusters("pulsar/global/ns",
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/ProducerConsumerBase.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/ProducerConsumerBase.java
index 27e3131..6bcfcdf 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/ProducerConsumerBase.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/ProducerConsumerBase.java
@@ -25,8 +25,8 @@ import java.util.Random;
 import java.util.Set;
 
 import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.Assert;
 import org.testng.annotations.BeforeMethod;
 
@@ -39,15 +39,15 @@ public abstract class ProducerConsumerBase extends MockedPulsarServiceBaseTest {
     }
 
     protected void producerBaseSetup() throws Exception {
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns");
         admin.namespaces().setNamespaceReplicationClusters("my-property/my-ns", Sets.newHashSet("test"));
 
         // so that clients can test short names
         admin.tenants().createTenant("public",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("public/default");
         admin.namespaces().setNamespaceReplicationClusters("public/default", Sets.newHashSet("test"));
     }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/PulsarMultiListenersWithInternalListenerNameTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/PulsarMultiListenersWithInternalListenerNameTest.java
index 0b45289..a354751 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/PulsarMultiListenersWithInternalListenerNameTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/PulsarMultiListenersWithInternalListenerNameTest.java
@@ -44,8 +44,8 @@ import org.apache.pulsar.client.impl.LookupService;
 import org.apache.pulsar.client.impl.PulsarClientImpl;
 import org.apache.pulsar.client.impl.conf.ClientConfigurationData;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -109,8 +109,8 @@ public class PulsarMultiListenersWithInternalListenerNameTest extends MockedPuls
     }
     @Test
     public void testFindBrokerWithListenerName() throws Exception {
-        admin.clusters().createCluster("localhost", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo();
+        admin.clusters().createCluster("localhost", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl();
         tenantInfo.setAllowedClusters(Sets.newHashSet("localhost"));
         this.admin.tenants().createTenant("public", tenantInfo);
         this.admin.namespaces().createNamespace("public/default");
@@ -149,8 +149,8 @@ public class PulsarMultiListenersWithInternalListenerNameTest extends MockedPuls
 
     @Test
     public void testHttpLookupRedirect() throws Exception {
-        admin.clusters().createCluster("localhost", new ClusterData(pulsar.getWebServiceAddress()));
-        TenantInfo tenantInfo = new TenantInfo();
+        admin.clusters().createCluster("localhost", new ClusterDataImpl(pulsar.getWebServiceAddress()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl();
         tenantInfo.setAllowedClusters(Sets.newHashSet("localhost"));
         this.admin.tenants().createTenant("public", tenantInfo);
         this.admin.namespaces().createNamespace("public/default");
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/SimpleProducerConsumerStatTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/SimpleProducerConsumerStatTest.java
index 17d4b05..106a6e9 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/SimpleProducerConsumerStatTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/SimpleProducerConsumerStatTest.java
@@ -33,6 +33,7 @@ import java.util.concurrent.Future;
 import java.util.concurrent.TimeUnit;
 import java.util.concurrent.atomic.AtomicBoolean;
 
+import com.google.gson.Gson;
 import org.apache.pulsar.broker.stats.NamespaceStats;
 import org.apache.pulsar.client.admin.PulsarAdminException;
 import org.slf4j.Logger;
@@ -394,7 +395,8 @@ public class SimpleProducerConsumerStatTest extends ProducerConsumerBase {
 
         pulsar.getBrokerService().updateRates();
 
-        JsonArray metrics = admin.brokerStats().getMetrics();
+        String json = admin.brokerStats().getMetrics();
+        JsonArray metrics = new Gson().fromJson(json, JsonArray.class);
 
         boolean latencyCaptured = false;
         for (int i = 0; i < metrics.size(); i++) {
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TenantTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TenantTest.java
index 11e4daa..79a5cd2 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TenantTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TenantTest.java
@@ -21,8 +21,8 @@ package org.apache.pulsar.client.api;
 import com.google.common.collect.Sets;
 import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
 import org.apache.pulsar.client.admin.PulsarAdminException;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -47,8 +47,8 @@ public class TenantTest extends MockedPulsarServiceBaseTest {
     public void testMaxTenant() throws Exception {
         conf.setMaxTenants(2);
         super.internalSetup();
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
-        TenantInfo tenantInfo = new TenantInfo(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(Sets.newHashSet("role1", "role2"), Sets.newHashSet("test"));
         admin.tenants().createTenant("testTenant1", tenantInfo);
         admin.tenants().createTenant("testTenant2", tenantInfo);
         try {
@@ -61,7 +61,7 @@ public class TenantTest extends MockedPulsarServiceBaseTest {
         super.internalCleanup();
         conf.setMaxTenants(0);
         super.internalSetup();
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         for (int i = 0; i < 10; i++) {
             admin.tenants().createTenant("testTenant-unlimited" + i, tenantInfo);
         }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TlsProducerConsumerBase.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TlsProducerConsumerBase.java
index bd758c2..28870a7 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TlsProducerConsumerBase.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TlsProducerConsumerBase.java
@@ -28,8 +28,8 @@ import java.util.concurrent.TimeUnit;
 
 import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.client.impl.auth.AuthenticationTls;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.annotations.*;
 
 import com.google.common.collect.Sets;
@@ -102,10 +102,10 @@ public class TlsProducerConsumerBase extends ProducerConsumerBase {
         admin = spy(PulsarAdmin.builder().serviceHttpUrl(brokerUrlTls.toString())
                 .tlsTrustCertsFilePath(TLS_TRUST_CERT_FILE_PATH).allowTlsInsecureConnection(false)
                 .authentication(AuthenticationTls.class.getName(), authParams).build());
-        admin.clusters().createCluster(clusterName, new ClusterData(brokerUrl.toString(), brokerUrlTls.toString(),
+        admin.clusters().createCluster(clusterName, new ClusterDataImpl(brokerUrl.toString(), brokerUrlTls.toString(),
                 pulsar.getBrokerServiceUrl(), pulsar.getBrokerServiceUrlTls()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
         admin.namespaces().createNamespace("my-property/my-ns");
     }
 }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TokenAuthenticatedProducerConsumerTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TokenAuthenticatedProducerConsumerTest.java
index 51d755a..7c57768 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TokenAuthenticatedProducerConsumerTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TokenAuthenticatedProducerConsumerTest.java
@@ -28,8 +28,8 @@ import java.util.Set;
 import java.util.concurrent.TimeUnit;
 import org.apache.pulsar.broker.authentication.AuthenticationProviderToken;
 import org.apache.pulsar.client.admin.PulsarAdmin;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.testng.annotations.AfterMethod;
@@ -129,9 +129,9 @@ public class TokenAuthenticatedProducerConsumerTest extends ProducerConsumerBase
         clientSetup();
 
         // test rest by admin
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
 
         // test protocol by producer/consumer
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TokenOauth2AuthenticatedProducerConsumerTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TokenOauth2AuthenticatedProducerConsumerTest.java
index d2a5eef..28fa7dd 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TokenOauth2AuthenticatedProducerConsumerTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/TokenOauth2AuthenticatedProducerConsumerTest.java
@@ -35,12 +35,11 @@ import org.apache.pulsar.broker.authentication.AuthenticationProviderToken;
 import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.client.impl.ProducerImpl;
 import org.apache.pulsar.client.impl.auth.oauth2.AuthenticationFactoryOAuth2;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
-import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.DataProvider;
@@ -152,9 +151,9 @@ public class TokenOauth2AuthenticatedProducerConsumerTest extends ProducerConsum
         clientSetup();
 
         // test rest by admin
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
 
         // test protocol by producer/consumer
@@ -169,9 +168,9 @@ public class TokenOauth2AuthenticatedProducerConsumerTest extends ProducerConsum
         clientSetup();
 
         // test rest by admin
-        admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
         admin.tenants().createTenant("my-property",
-            new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+            new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
 
         Consumer<byte[]> consumer = pulsarClient.newConsumer().topic("persistent://my-property/my-ns/my-topic")
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/v1/V1_ProducerConsumerBase.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/v1/V1_ProducerConsumerBase.java
index 1119a3e..67c1ee2 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/api/v1/V1_ProducerConsumerBase.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/api/v1/V1_ProducerConsumerBase.java
@@ -24,8 +24,8 @@ import java.lang.reflect.Method;
 import java.util.Set;
 
 import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.Assert;
 import org.testng.annotations.BeforeMethod;
 
@@ -38,9 +38,9 @@ public abstract class V1_ProducerConsumerBase extends MockedPulsarServiceBaseTes
     }
 
     public void producerBaseSetup() throws Exception {
-        admin.clusters().createCluster("use", new ClusterData(pulsar.getWebServiceAddress()));
+        admin.clusters().createCluster("use", new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
         admin.namespaces().createNamespace("my-property/use/my-ns");
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/AdminApiKeyStoreTlsAuthTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/AdminApiKeyStoreTlsAuthTest.java
index 5142bbd..6985c09 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/AdminApiKeyStoreTlsAuthTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/AdminApiKeyStoreTlsAuthTest.java
@@ -47,8 +47,8 @@ import org.apache.pulsar.client.admin.internal.JacksonConfigurator;
 import org.apache.pulsar.client.api.ProducerConsumerBase;
 import org.apache.pulsar.client.impl.auth.AuthenticationKeyStoreTls;
 import org.apache.pulsar.common.tls.NoopHostnameVerifier;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.keystoretls.KeyStoreSSLContext;
 import org.glassfish.jersey.client.ClientConfig;
 import org.glassfish.jersey.client.ClientProperties;
@@ -177,9 +177,9 @@ public class AdminApiKeyStoreTlsAuthTest extends ProducerConsumerBase {
     @Test
     public void testSuperUserCanListTenants() throws Exception {
         try (PulsarAdmin admin = buildAdminClient()) {
-            admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+            admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("foobar"),
+                                         new TenantInfoImpl(ImmutableSet.of("foobar"),
                                                         ImmutableSet.of("test")));
             Assert.assertEquals(ImmutableSet.of("tenant1"), admin.tenants().getTenants());
         }
@@ -188,9 +188,9 @@ public class AdminApiKeyStoreTlsAuthTest extends ProducerConsumerBase {
     @Test
     public void testSuperUserCantListNamespaces() throws Exception {
         try (PulsarAdmin admin = buildAdminClient()) {
-            admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+            admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("proxy"),
+                                         new TenantInfoImpl(ImmutableSet.of("proxy"),
                                                         ImmutableSet.of("test")));
             admin.namespaces().createNamespace("tenant1/ns1");
             Assert.assertTrue(admin.namespaces().getNamespaces("tenant1").contains("tenant1/ns1"));
@@ -200,9 +200,9 @@ public class AdminApiKeyStoreTlsAuthTest extends ProducerConsumerBase {
     @Test
     public void testAuthorizedUserAsOriginalPrincipal() throws Exception {
         try (PulsarAdmin admin = buildAdminClient()) {
-            admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+            admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
             admin.tenants().createTenant("tenant1",
-                                         new TenantInfo(ImmutableSet.of("proxy", "user1"),
+                                         new TenantInfoImpl(ImmutableSet.of("proxy", "user1"),
                                                         ImmutableSet.of("test")));
             admin.namespaces().createNamespace("tenant1/ns1");
         }
@@ -219,9 +219,9 @@ public class AdminApiKeyStoreTlsAuthTest extends ProducerConsumerBase {
         log.info("-- Starting {} test --", methodName);
 
         try (PulsarAdmin admin = buildAdminClient()) {
-            admin.clusters().createCluster("test", new ClusterData(brokerUrl.toString()));
+            admin.clusters().createCluster("test", new ClusterDataImpl(brokerUrl.toString()));
             admin.tenants().createTenant("tenant1",
-                    new TenantInfo(ImmutableSet.of("foobar"),
+                    new TenantInfoImpl(ImmutableSet.of("foobar"),
                             ImmutableSet.of("test")));
             Assert.assertEquals(ImmutableSet.of("tenant1"), admin.tenants().getTenants());
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/BrokerClientIntegrationTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/BrokerClientIntegrationTest.java
index f7ce13b..859a8f3 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/BrokerClientIntegrationTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/BrokerClientIntegrationTest.java
@@ -92,7 +92,7 @@ import org.apache.pulsar.client.impl.schema.reader.JacksonJsonReader;
 import org.apache.pulsar.client.impl.schema.writer.JacksonJsonWriter;
 import org.apache.pulsar.common.naming.NamespaceBundle;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
 import org.apache.pulsar.common.protocol.PulsarHandler;
 import org.apache.pulsar.common.util.FutureUtil;
@@ -745,7 +745,7 @@ public class BrokerClientIntegrationTest extends ProducerConsumerBase {
     public void testCleanProducer() throws Exception {
         log.info("-- Starting {} test --", methodName);
 
-        admin.clusters().createCluster("global", new ClusterData());
+        admin.clusters().createCluster("global", new ClusterDataImpl());
         admin.namespaces().createNamespace("my-property/global/lookup");
 
         final int operationTimeOut = 500;
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/ConsumerConfigurationTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/ConsumerConfigurationTest.java
index 5feef1b..0b55ec4 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/ConsumerConfigurationTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/ConsumerConfigurationTest.java
@@ -23,8 +23,8 @@ import com.google.common.collect.Sets;
 import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
 import org.apache.pulsar.client.api.PulsarClientException.InvalidConfigurationException;
 import org.apache.pulsar.client.api.SubscriptionType;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
@@ -39,9 +39,9 @@ public class ConsumerConfigurationTest extends MockedPulsarServiceBaseTest {
     public void setup() throws Exception {
         super.internalSetup();
 
-        admin.clusters().createCluster("use", new ClusterData(pulsar.getWebServiceAddress()));
+        admin.clusters().createCluster("use", new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
         admin.namespaces().createNamespace("my-property/use/my-ns");
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/KeyStoreTlsProducerConsumerTestWithAuthTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/KeyStoreTlsProducerConsumerTestWithAuthTest.java
index c79cb5d..35811dc 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/KeyStoreTlsProducerConsumerTestWithAuthTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/KeyStoreTlsProducerConsumerTestWithAuthTest.java
@@ -39,8 +39,8 @@ import org.apache.pulsar.client.api.ProducerConsumerBase;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.api.SubscriptionType;
 import org.apache.pulsar.client.impl.auth.AuthenticationKeyStoreTls;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -155,10 +155,10 @@ public class KeyStoreTlsProducerConsumerTestWithAuthTest extends ProducerConsume
                 .tlsTrustStorePassword(BROKER_TRUSTSTORE_PW)
                 .allowTlsInsecureConnection(false)
                 .authentication(AuthenticationKeyStoreTls.class.getName(), authParams).build());
-        admin.clusters().createCluster(clusterName, new ClusterData(brokerUrl.toString(), brokerUrlTls.toString(),
+        admin.clusters().createCluster(clusterName, new ClusterDataImpl(brokerUrl.toString(), brokerUrlTls.toString(),
                 pulsar.getBrokerServiceUrl(), pulsar.getBrokerServiceUrlTls()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
         admin.namespaces().createNamespace("my-property/my-ns");
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/KeyStoreTlsProducerConsumerTestWithoutAuthTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/KeyStoreTlsProducerConsumerTestWithoutAuthTest.java
index 185df02..f09f3de 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/KeyStoreTlsProducerConsumerTestWithoutAuthTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/KeyStoreTlsProducerConsumerTestWithoutAuthTest.java
@@ -37,8 +37,8 @@ import org.apache.pulsar.client.api.ProducerConsumerBase;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.api.SubscriptionType;
 import org.apache.pulsar.client.impl.auth.AuthenticationKeyStoreTls;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -141,10 +141,10 @@ public class KeyStoreTlsProducerConsumerTestWithoutAuthTest extends ProducerCons
                 .tlsTrustStorePassword(BROKER_TRUSTSTORE_PW)
                 .allowTlsInsecureConnection(true)
                 .authentication(AuthenticationKeyStoreTls.class.getName(), authParams).build());
-        admin.clusters().createCluster(clusterName, new ClusterData(brokerUrl.toString(), brokerUrlTls.toString(),
+        admin.clusters().createCluster(clusterName, new ClusterDataImpl(brokerUrl.toString(), brokerUrlTls.toString(),
                 pulsar.getBrokerServiceUrl(), pulsar.getBrokerServiceUrlTls()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
         admin.namespaces().createNamespace("my-property/my-ns");
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/MessageParserTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/MessageParserTest.java
index 78d9d1c..20897cd 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/MessageParserTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/MessageParserTest.java
@@ -42,8 +42,8 @@ import org.apache.pulsar.common.protocol.Commands;
 import org.apache.pulsar.common.api.raw.MessageParser;
 import org.apache.pulsar.common.api.raw.RawMessage;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.testng.annotations.AfterClass;
 import org.testng.annotations.BeforeClass;
@@ -56,9 +56,9 @@ public class MessageParserTest extends MockedPulsarServiceBaseTest {
     public void setup() throws Exception {
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-tenant",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-tenant/my-ns", Sets.newHashSet("test"));
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/MultiTopicsReaderTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/MultiTopicsReaderTest.java
index ebdfb52..89a9740 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/MultiTopicsReaderTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/MultiTopicsReaderTest.java
@@ -47,11 +47,11 @@ import org.apache.pulsar.client.api.Range;
 import org.apache.pulsar.client.api.Reader;
 import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
 import org.apache.pulsar.common.policies.data.Policies;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.FutureUtil;
 import org.apache.pulsar.common.util.Murmur3_32Hash;
 import org.awaitility.Awaitility;
@@ -71,9 +71,9 @@ public class MultiTopicsReaderTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         admin.clusters().createCluster("test",
-                new ClusterData(pulsar.getWebServiceAddress()));
+                new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         Policies policies = new Policies();
         policies.replication_clusters = Sets.newHashSet("test");
         // infinite retention
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/PatternTopicsConsumerImplTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/PatternTopicsConsumerImplTest.java
index bf6edf4..b7215f4 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/PatternTopicsConsumerImplTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/PatternTopicsConsumerImplTest.java
@@ -45,7 +45,7 @@ import org.apache.pulsar.client.api.RegexSubscriptionMode;
 import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.client.api.SubscriptionType;
 import org.apache.pulsar.common.naming.NamespaceName;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.testng.annotations.AfterMethod;
@@ -86,7 +86,7 @@ public class PatternTopicsConsumerImplTest extends ProducerConsumerBase {
         final String patternString = "persistent://my-property/my-ns/pattern-topic.*";
         Pattern pattern = Pattern.compile(patternString);
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -146,7 +146,7 @@ public class PatternTopicsConsumerImplTest extends ProducerConsumerBase {
         Pattern pattern = Pattern.compile("my-property/my-ns/pattern-topic.*");
 
         // 1. create partition
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -250,7 +250,7 @@ public class PatternTopicsConsumerImplTest extends ProducerConsumerBase {
         Pattern pattern = Pattern.compile("my-property/my-ns/np-pattern-topic.*");
 
         // 1. create partition
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -341,7 +341,7 @@ public class PatternTopicsConsumerImplTest extends ProducerConsumerBase {
         Pattern pattern = Pattern.compile("my-property/my-ns/pattern-topic.*");
 
         // 1. create partition
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -491,7 +491,7 @@ public class PatternTopicsConsumerImplTest extends ProducerConsumerBase {
         Pattern pattern = Pattern.compile("persistent://my-property/my-ns/pattern-topic.*");
 
         // 1. create partition
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -579,7 +579,7 @@ public class PatternTopicsConsumerImplTest extends ProducerConsumerBase {
         Pattern pattern = Pattern.compile("persistent://my-property/my-ns/pattern-topic.*");
 
         // 1. create partition
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -688,7 +688,7 @@ public class PatternTopicsConsumerImplTest extends ProducerConsumerBase {
         Pattern pattern = Pattern.compile("persistent://my-property/my-ns/pattern-topic.*");
 
         // 1. create partition
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/PerMessageUnAcknowledgedRedeliveryTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/PerMessageUnAcknowledgedRedeliveryTest.java
index 9a49460..298a469 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/PerMessageUnAcknowledgedRedeliveryTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/PerMessageUnAcknowledgedRedeliveryTest.java
@@ -29,7 +29,7 @@ import org.apache.pulsar.client.api.Message;
 import org.apache.pulsar.client.api.MessageRoutingMode;
 import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.api.SubscriptionType;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.testng.annotations.AfterMethod;
@@ -404,7 +404,7 @@ public class PerMessageUnAcknowledgedRedeliveryTest extends BrokerTestBase {
         final String messagePredicate = "my-message-" + key + "-";
         final int totalMessages = 15;
         final int numberOfPartitions = 3;
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName, numberOfPartitions);
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/RawReaderTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/RawReaderTest.java
index 6336044..9e806b8 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/RawReaderTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/RawReaderTest.java
@@ -42,8 +42,8 @@ import org.apache.pulsar.client.api.RawMessage;
 import org.apache.pulsar.client.api.RawReader;
 import org.apache.pulsar.common.protocol.Commands;
 import org.apache.pulsar.common.api.proto.MessageMetadata;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.awaitility.Awaitility;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
@@ -61,9 +61,9 @@ public class RawReaderTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         admin.clusters().createCluster("test",
-                new ClusterData(pulsar.getWebServiceAddress()));
+                new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/ReaderTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/ReaderTest.java
index 6d27b5b..55ff8f5 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/ReaderTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/ReaderTest.java
@@ -50,9 +50,9 @@ import org.apache.pulsar.client.api.Reader;
 import org.apache.pulsar.client.api.ReaderBuilder;
 import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.Murmur3_32Hash;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
@@ -71,9 +71,9 @@ public class ReaderTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         admin.clusters().createCluster("test",
-                new ClusterData(pulsar.getWebServiceAddress()));
+                new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/SchemaDeleteTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/SchemaDeleteTest.java
index a12b000..939c6d7 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/SchemaDeleteTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/SchemaDeleteTest.java
@@ -26,9 +26,9 @@ import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.api.Reader;
 import org.apache.pulsar.client.api.Schema;
 
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.SchemaAutoUpdateCompatibilityStrategy;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -45,9 +45,9 @@ public class SchemaDeleteTest extends MockedPulsarServiceBaseTest {
         this.conf.setBrokerDeleteInactiveTopicsFrequencySeconds(5);
 
         admin.clusters().createCluster("test",
-                new ClusterData(pulsar.getWebServiceAddress()));
+                new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns", Sets.newHashSet("test"));
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/TopicsConsumerImplTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/TopicsConsumerImplTest.java
index 898e534..8ad2c0c 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/TopicsConsumerImplTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/TopicsConsumerImplTest.java
@@ -38,10 +38,10 @@ import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.client.api.SubscriptionInitialPosition;
 import org.apache.pulsar.client.api.SubscriptionType;
 import org.apache.pulsar.client.api.TopicMetadata;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.PartitionedTopicStats;
 import org.apache.pulsar.common.policies.data.SubscriptionStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicStats;
 import org.awaitility.Awaitility;
 import org.slf4j.Logger;
@@ -102,7 +102,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName3 = "persistent://prop/use/ns-abc3/topic-3-" + key;
         List<String> topicNames = Lists.newArrayList(topicName1, topicName2, topicName3);
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -131,7 +131,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName3 = "persistent://prop/use/ns-abc/topic-3-" + key;
         List<String> topicNames = Lists.newArrayList(topicName1, topicName2);
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -175,7 +175,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName3 = "persistent://prop/use/ns-abc/topic-3-" + key;
         List<String> topicNames = Lists.newArrayList(topicName1, topicName2, topicName3);
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -241,7 +241,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName3 = "persistent://prop/use/ns-abc/topic-3-" + key;
         List<String> topicNames = Lists.newArrayList(topicName1, topicName2, topicName3);
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -326,7 +326,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName3 = "persistent://prop/use/ns-abc/topic-3-" + key;
         List<String> topicNames = Lists.newArrayList(topicName1, topicName2, topicName3);
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -461,7 +461,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
     @Test
     public void testTopicNameValid() throws Exception{
         final String topicName = "persistent://prop/use/ns-abc/testTopicNameValid";
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName, 3);
         Consumer<byte[]> consumer = pulsarClient.newConsumer()
@@ -492,7 +492,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName3 = "persistent://prop/use/ns-abc/topic-3-" + key;
         List<String> topicNames = Lists.newArrayList(topicName1, topicName2, topicName3);
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -654,7 +654,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName2 = "persistent://prop/use/ns-abc/topic-2-" + key;
         final String topicName3 = "persistent://prop/use/ns-abc/topic-3-" + key;
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -724,7 +724,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName1 = "persistent://prop/use/ns-abc/topic-1-" + key;
         List<String> topicNames = Lists.newArrayList(topicName1);
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName1, 2);
 
@@ -786,7 +786,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName2 = "persistent://my-property/my-ns/topic-2-" + key;
         List<String> topicNames = Lists.newArrayList(topicName1, topicName2);
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName1, 2);
         admin.topics().createPartitionedTopic(topicName2, 2);
@@ -844,7 +844,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
     public void testConsumerDistributionInFailoverSubscriptionWhenUpdatePartitions() throws Exception {
         final String topicName = "persistent://my-property/my-ns/testConsumerDistributionInFailoverSubscriptionWhenUpdatePartitions";
         final String subName = "failover-test";
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName, 2);
         assertEquals(admin.topics().getPartitionedTopicMetadata(topicName).partitions, 2);
@@ -959,9 +959,9 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName = "persistent://" + namespace + "/expiry";
         final String subName = "expiredSub";
 
-        admin.clusters().createCluster("use", new ClusterData(brokerUrl.toString()));
+        admin.clusters().createCluster("use", new ClusterDataImpl(brokerUrl.toString()));
 
-        admin.tenants().createTenant("prop", new TenantInfo(null, Sets.newHashSet("use")));
+        admin.tenants().createTenant("prop", new TenantInfoImpl(null, Sets.newHashSet("use")));
         admin.namespaces().createNamespace(namespace);
 
         Consumer<byte[]> consumer = pulsarClient.newConsumer().topic(topicName).subscriptionName(subName)
@@ -1002,7 +1002,7 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         final String topicName3 = "persistent://prop/use/ns-abc/topic-3-" + key;
         List<String> topicNames = Lists.newArrayList(topicName1, topicName2, topicName3);
 
-        TenantInfo tenantInfo = createDefaultTenantInfo();
+        TenantInfoImpl tenantInfo = createDefaultTenantInfo();
         admin.tenants().createTenant("prop", tenantInfo);
         admin.topics().createPartitionedTopic(topicName2, 2);
         admin.topics().createPartitionedTopic(topicName3, 3);
@@ -1093,8 +1093,8 @@ public class TopicsConsumerImplTest extends ProducerConsumerBase {
         topics.add("persistent://prop/use/ns-abc/topic-1");
         topics.add("persistent://prop/use/ns-abc/topic-2");
         topics.add("persistent://prop/use/ns-abc1/topic-3");
-        admin.clusters().createCluster("use", new ClusterData(brokerUrl.toString()));
-        admin.tenants().createTenant("prop", new TenantInfo(null, Sets.newHashSet("use")));
+        admin.clusters().createCluster("use", new ClusterDataImpl(brokerUrl.toString()));
+        admin.tenants().createTenant("prop", new TenantInfoImpl(null, Sets.newHashSet("use")));
         admin.namespaces().createNamespace("prop/use/ns-abc");
         admin.namespaces().createNamespace("prop/use/ns-abc1");
         Consumer consumer = pulsarClient.newConsumer()
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/TransactionEndToEndTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/TransactionEndToEndTest.java
index 46d8928..f6bcbee 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/TransactionEndToEndTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/client/impl/TransactionEndToEndTest.java
@@ -27,7 +27,6 @@ import static org.testng.Assert.fail;
 import com.google.common.collect.Sets;
 
 import java.lang.reflect.Field;
-import java.util.Map;
 import java.util.Optional;
 import java.util.concurrent.CompletableFuture;
 import java.util.ArrayList;
@@ -66,14 +65,13 @@ import org.apache.pulsar.client.internal.DefaultImplementation;
 import org.apache.pulsar.common.api.proto.CommandAck;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.collections.ConcurrentOpenHashMap;
 import org.apache.pulsar.transaction.coordinator.TransactionCoordinatorID;
 import org.apache.pulsar.transaction.coordinator.TransactionMetadataStore;
 import org.apache.pulsar.transaction.coordinator.TransactionSubscription;
-import org.apache.pulsar.transaction.coordinator.TxnMeta;
 import org.awaitility.Awaitility;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
@@ -101,15 +99,15 @@ public class TransactionEndToEndTest extends TransactionTestBase {
 
         String[] brokerServiceUrlArr = getPulsarServiceList().get(0).getBrokerServiceUrl().split(":");
         String webServicePort = brokerServiceUrlArr[brokerServiceUrlArr.length -1];
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData("http://localhost:" + webServicePort));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl("http://localhost:" + webServicePort));
         admin.tenants().createTenant(TENANT,
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NAMESPACE1);
         admin.topics().createPartitionedTopic(TOPIC_OUTPUT, TOPIC_PARTITION);
         admin.topics().createPartitionedTopic(TOPIC_MESSAGE_ACK_TEST, 1);
 
         admin.tenants().createTenant(NamespaceName.SYSTEM_NAMESPACE.getTenant(),
-                new TenantInfo(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
+                new TenantInfoImpl(Sets.newHashSet("appid1"), Sets.newHashSet(CLUSTER_NAME)));
         admin.namespaces().createNamespace(NamespaceName.SYSTEM_NAMESPACE.toString());
         admin.topics().createPartitionedTopic(TopicName.TRANSACTION_COORDINATOR_ASSIGN.toString(), 16);
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactedTopicTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactedTopicTest.java
index 7a90971..ff03e59 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactedTopicTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactedTopicTest.java
@@ -52,8 +52,8 @@ import org.apache.pulsar.client.api.ProducerBuilder;
 import org.apache.pulsar.client.api.RawMessage;
 import org.apache.pulsar.client.impl.RawMessageImpl;
 import org.apache.pulsar.common.api.proto.MessageIdData;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.FutureUtil;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
@@ -79,9 +79,9 @@ public class CompactedTopicTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         admin.clusters().createCluster("use",
-                new ClusterData(pulsar.getWebServiceAddress()));
+                new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
         admin.namespaces().createNamespace("my-property/use/my-ns");
     }
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactionTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactionTest.java
index 25c153d..2cb6d9d 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactionTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactionTest.java
@@ -62,10 +62,10 @@ import org.apache.pulsar.client.api.PulsarClientException;
 import org.apache.pulsar.client.api.Reader;
 import org.apache.pulsar.client.api.SubscriptionInitialPosition;
 import org.apache.pulsar.client.impl.BatchMessageIdImpl;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.PersistentTopicInternalStats;
 import org.apache.pulsar.common.policies.data.RetentionPolicies;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.FutureUtil;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
@@ -83,9 +83,9 @@ public class CompactionTest extends MockedPulsarServiceBaseTest {
     public void setup() throws Exception {
         super.internalSetup();
 
-        admin.clusters().createCluster("use", new ClusterData(pulsar.getWebServiceAddress()));
+        admin.clusters().createCluster("use", new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
         admin.namespaces().createNamespace("my-property/use/my-ns");
 
         compactionScheduler = Executors.newSingleThreadScheduledExecutor(
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactorTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactorTest.java
index 69884f1..438a1bf 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactorTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/compaction/CompactorTest.java
@@ -45,8 +45,8 @@ import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.api.RawMessage;
 import org.apache.pulsar.client.impl.RawMessageImpl;
 import org.apache.pulsar.common.protocol.Commands;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -63,9 +63,9 @@ public class CompactorTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         admin.clusters().createCluster("use",
-                new ClusterData(pulsar.getWebServiceAddress()));
+                new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("use")));
         admin.namespaces().createNamespace("my-property/use/my-ns");
 
         compactionScheduler = Executors.newSingleThreadScheduledExecutor(
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionE2ESecurityTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionE2ESecurityTest.java
index 87a664f..b055d1b 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionE2ESecurityTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionE2ESecurityTest.java
@@ -60,9 +60,9 @@ import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.client.impl.auth.AuthenticationToken;
 import org.apache.pulsar.common.functions.FunctionConfig;
 import org.apache.pulsar.common.policies.data.AuthAction;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.SubscriptionStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicStats;
 import org.apache.pulsar.common.util.FutureUtil;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
@@ -171,7 +171,7 @@ public class PulsarFunctionE2ESecurityTest {
         primaryHost = pulsar.getWebServiceAddress();
 
         // update cluster metadata
-        ClusterData clusterData = new ClusterData(brokerWebServiceUrl.toString());
+        ClusterDataImpl clusterData = new ClusterDataImpl(brokerWebServiceUrl.toString());
         superUserAdmin.clusters().updateCluster(config.getClusterName(), clusterData);
 
         ClientBuilder clientBuilder = PulsarClient.builder().serviceUrl(this.workerConfig.getPulsarServiceUrl())
@@ -186,7 +186,7 @@ public class PulsarFunctionE2ESecurityTest {
         }
         pulsarClient = clientBuilder.build();
 
-        TenantInfo propAdmin = new TenantInfo();
+        TenantInfoImpl propAdmin = new TenantInfoImpl();
         propAdmin.getAdminRoles().add(ADMIN_SUBJECT);
         propAdmin.setAllowedClusters(Sets.newHashSet(Lists.newArrayList("use")));
         superUserAdmin.tenants().updateTenant(TENANT, propAdmin);
@@ -198,7 +198,7 @@ public class PulsarFunctionE2ESecurityTest {
         superUserAdmin.namespaces().setNamespaceReplicationClusters(replNamespace, clusters);
 
         // create another test tenant and namespace
-        propAdmin = new TenantInfo();
+        propAdmin = new TenantInfoImpl();
         propAdmin.setAllowedClusters(Sets.newHashSet(Lists.newArrayList("use")));
         superUserAdmin.tenants().createTenant(TENANT2, propAdmin);
         superUserAdmin.namespaces().createNamespace( TENANT2 + "/" + NAMESPACE);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionLocalRunTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionLocalRunTest.java
index 1a00043..1641022 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionLocalRunTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionLocalRunTest.java
@@ -73,11 +73,11 @@ import org.apache.pulsar.common.functions.Utils;
 import org.apache.pulsar.common.io.SinkConfig;
 import org.apache.pulsar.common.io.SourceConfig;
 import org.apache.pulsar.common.nar.NarClassLoader;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.ConsumerStats;
 import org.apache.pulsar.common.policies.data.PublisherStats;
 import org.apache.pulsar.common.policies.data.SubscriptionStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicStats;
 import org.apache.pulsar.common.util.FutureUtil;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
@@ -250,7 +250,7 @@ public class PulsarFunctionLocalRunTest {
         primaryHost = pulsar.getWebServiceAddress();
 
         // create cluster metadata
-        ClusterData clusterData = new ClusterData(urlTls.toString());
+        ClusterDataImpl clusterData = new ClusterDataImpl(urlTls.toString());
         admin.clusters().createCluster(config.getClusterName(), clusterData);
 
         ClientBuilder clientBuilder = PulsarClient.builder()
@@ -268,7 +268,7 @@ public class PulsarFunctionLocalRunTest {
         }
         pulsarClient = clientBuilder.build();
 
-        TenantInfo propAdmin = new TenantInfo();
+        TenantInfoImpl propAdmin = new TenantInfoImpl();
         propAdmin.getAdminRoles().add("superUser");
         propAdmin.setAllowedClusters(Sets.newHashSet(Lists.newArrayList(CLUSTER)));
         admin.tenants().createTenant(tenant, propAdmin);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionPublishTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionPublishTest.java
index f21aabeb..15805f9 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionPublishTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionPublishTest.java
@@ -63,10 +63,10 @@ import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.client.impl.auth.AuthenticationTls;
 import org.apache.pulsar.common.functions.FunctionConfig;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.FunctionStats;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.FunctionStatsImpl;
 import org.apache.pulsar.common.policies.data.SubscriptionStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.FutureUtil;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.functions.runtime.thread.ThreadRuntimeFactory;
@@ -176,7 +176,7 @@ public class PulsarFunctionPublishTest {
         primaryHost = pulsar.getWebServiceAddress();
 
         // update cluster metadata
-        ClusterData clusterData = new ClusterData(urlTls.toString());
+        ClusterDataImpl clusterData = new ClusterDataImpl(urlTls.toString());
         admin.clusters().updateCluster(config.getClusterName(), clusterData);
 
         ClientBuilder clientBuilder = PulsarClient.builder().serviceUrl(this.workerConfig.getPulsarServiceUrl());
@@ -192,7 +192,7 @@ public class PulsarFunctionPublishTest {
         }
         pulsarClient = clientBuilder.build();
 
-        TenantInfo propAdmin = new TenantInfo();
+        TenantInfoImpl propAdmin = new TenantInfoImpl();
         propAdmin.getAdminRoles().add("superUser");
         propAdmin.setAllowedClusters(Sets.newHashSet(Lists.newArrayList("use")));
         admin.tenants().updateTenant(tenant, propAdmin);
@@ -333,7 +333,8 @@ public class PulsarFunctionPublishTest {
 
         retryStrategically((test) -> {
             try {
-                FunctionStats functionStat = admin.functions().getFunctionStats(tenant, namespacePortion, functionName);
+                FunctionStatsImpl functionStat = (FunctionStatsImpl)
+                        admin.functions().getFunctionStats(tenant, namespacePortion, functionName);
                 return functionStat.getProcessedSuccessfullyTotal() == 5;
             } catch (PulsarAdminException e) {
                 return false;
@@ -470,7 +471,8 @@ public class PulsarFunctionPublishTest {
 
         retryStrategically((test) -> {
             try {
-                FunctionStats functionStat = admin.functions().getFunctionStats(tenant, namespacePortion, functionName);
+                FunctionStatsImpl functionStat = (FunctionStatsImpl)
+                        admin.functions().getFunctionStats(tenant, namespacePortion, functionName);
                 return functionStat.getProcessedSuccessfullyTotal() == 5;
             } catch (PulsarAdminException e) {
                 return false;
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionTlsTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionTlsTest.java
index cd0f70e..23ae6ef 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionTlsTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarFunctionTlsTest.java
@@ -40,7 +40,7 @@ import org.apache.pulsar.client.admin.PulsarAdmin;
 import org.apache.pulsar.client.api.Authentication;
 import org.apache.pulsar.client.impl.auth.AuthenticationTls;
 import org.apache.pulsar.common.functions.FunctionConfig;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ClassLoaderUtils;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.functions.api.utils.IdentityFunction;
@@ -165,7 +165,7 @@ public class PulsarFunctionTlsTest {
         leaderAdmin = pulsarAdmins[0];
         Thread.sleep(1000);
 
-        TenantInfo tenantInfo = new TenantInfo();
+        TenantInfoImpl tenantInfo = new TenantInfoImpl();
         tenantInfo.setAllowedClusters(Sets.newHashSet(testCluster));
         pulsarAdmins[0].tenants().createTenant(testTenant, tenantInfo);
         pulsarAdmins[0].namespaces().createNamespace(testNamespace, 16);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarWorkerAssignmentTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarWorkerAssignmentTest.java
index b288911..76e5b64 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarWorkerAssignmentTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/functions/worker/PulsarWorkerAssignmentTest.java
@@ -44,8 +44,8 @@ import org.apache.pulsar.client.api.ClientBuilder;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.common.configuration.PulsarConfigurationLoader;
 import org.apache.pulsar.common.functions.FunctionConfig;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.functions.proto.Function.Assignment;
 import org.apache.pulsar.functions.runtime.thread.ThreadRuntimeFactory;
@@ -108,7 +108,7 @@ public class PulsarWorkerAssignmentTest {
         primaryHost = pulsar.getWebServiceAddress();
 
         // update cluster metadata
-        final ClusterData clusterData = new ClusterData(pulsar.getBrokerServiceUrl());
+        final ClusterDataImpl clusterData = new ClusterDataImpl(pulsar.getBrokerServiceUrl());
         admin.clusters().updateCluster(config.getClusterName(), clusterData);
 
         final ClientBuilder clientBuilder = PulsarClient.builder().serviceUrl(this.workerConfig.getPulsarServiceUrl());
@@ -117,7 +117,7 @@ public class PulsarWorkerAssignmentTest {
         }
         pulsarClient = clientBuilder.build();
 
-        final TenantInfo propAdmin = new TenantInfo();
+        final TenantInfoImpl propAdmin = new TenantInfoImpl();
         propAdmin.getAdminRoles().add("superUser");
         propAdmin.setAllowedClusters(Sets.newHashSet(Lists.newArrayList("use")));
         admin.tenants().updateTenant(tenant, propAdmin);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/io/AbstractPulsarE2ETest.java b/pulsar-broker/src/test/java/org/apache/pulsar/io/AbstractPulsarE2ETest.java
index d5d83bd..a304197 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/io/AbstractPulsarE2ETest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/io/AbstractPulsarE2ETest.java
@@ -27,13 +27,9 @@ import static org.apache.pulsar.functions.worker.PulsarFunctionLocalRunTest.getP
 import static org.mockito.Mockito.spy;
 import static org.testng.Assert.assertTrue;
 
-import java.io.BufferedReader;
 import java.io.File;
 import java.io.IOException;
-import java.io.InputStreamReader;
 import java.lang.reflect.Method;
-import java.net.HttpURLConnection;
-import java.net.URL;
 import java.nio.file.Files;
 import java.util.Arrays;
 import java.util.HashMap;
@@ -41,9 +37,6 @@ import java.util.HashSet;
 import java.util.Map;
 import java.util.Optional;
 import java.util.Set;
-import java.util.TreeMap;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
 
 import org.apache.pulsar.broker.PulsarService;
 import org.apache.pulsar.broker.ServiceConfiguration;
@@ -57,8 +50,8 @@ import org.apache.pulsar.client.api.Authentication;
 import org.apache.pulsar.client.api.ClientBuilder;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.impl.auth.AuthenticationTls;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.FutureUtil;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.functions.runtime.thread.ThreadRuntimeFactory;
@@ -80,8 +73,6 @@ import org.testng.annotations.Test;
 import com.google.common.collect.Lists;
 import com.google.common.collect.Sets;
 
-import lombok.ToString;
-
 public abstract class AbstractPulsarE2ETest {
 
 	public static final Logger log = LoggerFactory.getLogger(AbstractPulsarE2ETest.class);
@@ -188,7 +179,7 @@ public abstract class AbstractPulsarE2ETest {
         primaryHost = String.format("http://%s:%d", "localhost", pulsar.getListenPortHTTP().get());
 
         // update cluster metadata
-        ClusterData clusterData = new ClusterData(pulsar.getBrokerServiceUrlTls());
+        ClusterDataImpl clusterData = new ClusterDataImpl(pulsar.getBrokerServiceUrlTls());
         admin.clusters().updateCluster(config.getClusterName(), clusterData);
 
         ClientBuilder clientBuilder = PulsarClient.builder().serviceUrl(this.workerConfig.getPulsarServiceUrl());
@@ -204,7 +195,7 @@ public abstract class AbstractPulsarE2ETest {
         }
         pulsarClient = clientBuilder.build();
 
-        TenantInfo propAdmin = new TenantInfo();
+        TenantInfoImpl propAdmin = new TenantInfoImpl();
         propAdmin.getAdminRoles().add("superUser");
         propAdmin.setAllowedClusters(Sets.newHashSet(Lists.newArrayList("use")));
         admin.tenants().updateTenant(tenant, propAdmin);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionAdminTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionAdminTest.java
index 63f57f0..a4ddd66 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionAdminTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionAdminTest.java
@@ -43,8 +43,8 @@ import org.apache.pulsar.client.api.Authentication;
 import org.apache.pulsar.client.api.ClientBuilder;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.impl.auth.AuthenticationTls;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.functions.runtime.thread.ThreadRuntimeFactory;
 import org.apache.pulsar.functions.runtime.thread.ThreadRuntimeFactoryConfig;
@@ -139,7 +139,7 @@ public class PulsarFunctionAdminTest {
         primaryHost = pulsar.getWebServiceAddress();
 
         // update cluster metadata
-        ClusterData clusterData = new ClusterData(urlTls.toString());
+        ClusterDataImpl clusterData = new ClusterDataImpl(urlTls.toString());
         admin.clusters().updateCluster(config.getClusterName(), clusterData);
 
         ClientBuilder clientBuilder = PulsarClient.builder().serviceUrl(this.workerConfig.getPulsarServiceUrl());
@@ -155,7 +155,7 @@ public class PulsarFunctionAdminTest {
         }
         pulsarClient = clientBuilder.build();
 
-        TenantInfo propAdmin = new TenantInfo();
+        TenantInfoImpl propAdmin = new TenantInfoImpl();
         propAdmin.setAllowedClusters(Sets.newHashSet(Lists.newArrayList("use")));
         admin.tenants().updateTenant(tenant, propAdmin);
 
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionE2ETest.java b/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionE2ETest.java
index 25b232e..ebd034e 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionE2ETest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionE2ETest.java
@@ -52,11 +52,11 @@ import org.apache.pulsar.client.api.Producer;
 import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.common.functions.ConsumerConfig;
 import org.apache.pulsar.common.functions.FunctionConfig;
-import org.apache.pulsar.common.io.SinkConfig;
-import org.apache.pulsar.common.policies.data.FunctionStats;
+import org.apache.pulsar.common.policies.data.FunctionInstanceStatsDataImpl;
+import org.apache.pulsar.common.policies.data.FunctionStatsImpl;
 import org.apache.pulsar.common.policies.data.FunctionStatus;
 import org.apache.pulsar.common.policies.data.SubscriptionStats;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.policies.data.TopicStats;
 import org.apache.pulsar.compaction.TwoPhaseCompactor;
 import org.apache.pulsar.functions.instance.InstanceUtils;
@@ -291,10 +291,10 @@ public class PulsarFunctionE2ETest extends AbstractPulsarE2ETest {
 
         // validate stats are empty
         FunctionRuntimeManager functionRuntimeManager = functionsWorkerService.getFunctionRuntimeManager();
-        FunctionStats functionStats = functionRuntimeManager.getFunctionStats(tenant, namespacePortion,
+        FunctionStatsImpl functionStats = functionRuntimeManager.getFunctionStats(tenant, namespacePortion,
                 functionName, null);
-        FunctionStats functionStatsFromAdmin = admin.functions().getFunctionStats(tenant, namespacePortion,
-                functionName);
+        FunctionStatsImpl functionStatsFromAdmin = (FunctionStatsImpl) admin.functions().getFunctionStats(tenant,
+                namespacePortion, functionName);
 
         assertEquals(functionStats, functionStatsFromAdmin);
 
@@ -317,15 +317,17 @@ public class PulsarFunctionE2ETest extends AbstractPulsarE2ETest {
         assertEquals(functionStats.instances.get(0).getMetrics().getProcessedSuccessfullyTotal(), 0);
         assertEquals(functionStats.instances.get(0).getMetrics().getSystemExceptionsTotal(), 0);
         assertEquals(functionStats.instances.get(0).getMetrics().getUserExceptionsTotal(), 0);
-        assertNull(functionStats.instances.get(0).getMetrics().avgProcessLatency);
-        assertEquals(functionStats.instances.get(0).getMetrics().oneMin.getReceivedTotal(), 0);
-        assertEquals(functionStats.instances.get(0).getMetrics().oneMin.getProcessedSuccessfullyTotal(), 0);
-        assertEquals(functionStats.instances.get(0).getMetrics().oneMin.getSystemExceptionsTotal(), 0);
-        assertEquals(functionStats.instances.get(0).getMetrics().oneMin.getUserExceptionsTotal(), 0);
-        assertNull(functionStats.instances.get(0).getMetrics().oneMin.getAvgProcessLatency());
-
-        assertEquals(functionStats.instances.get(0).getMetrics().getAvgProcessLatency(), functionStats.instances.get(0).getMetrics().oneMin.getAvgProcessLatency());
-        assertEquals(functionStats.instances.get(0).getMetrics().getAvgProcessLatency(), functionStats.getAvgProcessLatency());
+        assertNull(functionStats.instances.get(0).getMetrics().getAvgProcessLatency());
+        assertEquals(functionStats.instances.get(0).getMetrics().getOneMin().getReceivedTotal(), 0);
+        assertEquals(functionStats.instances.get(0).getMetrics().getOneMin().getProcessedSuccessfullyTotal(), 0);
+        assertEquals(functionStats.instances.get(0).getMetrics().getOneMin().getSystemExceptionsTotal(), 0);
+        assertEquals(functionStats.instances.get(0).getMetrics().getOneMin().getUserExceptionsTotal(), 0);
+        assertNull(functionStats.instances.get(0).getMetrics().getOneMin().getAvgProcessLatency());
+
+        assertEquals(functionStats.instances.get(0).getMetrics().getAvgProcessLatency(),
+                functionStats.instances.get(0).getMetrics().getOneMin().getAvgProcessLatency());
+        assertEquals(functionStats.instances.get(0).getMetrics().getAvgProcessLatency(),
+                functionStats.getAvgProcessLatency());
 
         // validate prometheus metrics empty
         String prometheusMetrics = PulsarFunctionTestUtils.getPrometheusMetrics(pulsar.getListenPortHTTP().get());
@@ -412,11 +414,11 @@ public class PulsarFunctionE2ETest extends AbstractPulsarE2ETest {
 
 
         // validate function instance stats empty
-        FunctionStats.FunctionInstanceStats.FunctionInstanceStatsData functionInstanceStats = functionRuntimeManager.getFunctionInstanceStats(tenant, namespacePortion,
-                functionName, 0,  null);
+        FunctionInstanceStatsDataImpl functionInstanceStats = functionRuntimeManager.getFunctionInstanceStats(tenant,
+                namespacePortion, functionName, 0,  null);
 
-        FunctionStats.FunctionInstanceStats.FunctionInstanceStatsData functionInstanceStatsAdmin = admin.functions().getFunctionStats(tenant, namespacePortion,
-                functionName, 0);
+        FunctionInstanceStatsDataImpl functionInstanceStatsAdmin = (FunctionInstanceStatsDataImpl) admin.functions().
+                getFunctionStats(tenant, namespacePortion, functionName, 0);
 
         assertEquals(functionInstanceStats, functionInstanceStatsAdmin);
         assertEquals(functionInstanceStats, functionStats.instances.get(0).getMetrics());
@@ -441,7 +443,7 @@ public class PulsarFunctionE2ETest extends AbstractPulsarE2ETest {
         functionStats = functionRuntimeManager.getFunctionStats(tenant, namespacePortion,
                 functionName, null);
 
-        functionStatsFromAdmin = admin.functions().getFunctionStats(tenant, namespacePortion,
+        functionStatsFromAdmin = (FunctionStatsImpl) admin.functions().getFunctionStats(tenant, namespacePortion,
                 functionName);
 
         assertEquals(functionStats, functionStatsFromAdmin);
@@ -465,22 +467,24 @@ public class PulsarFunctionE2ETest extends AbstractPulsarE2ETest {
         assertEquals(functionStats.instances.get(0).getMetrics().getProcessedSuccessfullyTotal(), totalMsgs);
         assertEquals(functionStats.instances.get(0).getMetrics().getSystemExceptionsTotal(), 0);
         assertEquals(functionStats.instances.get(0).getMetrics().getUserExceptionsTotal(), 0);
-        assertTrue(functionStats.instances.get(0).getMetrics().avgProcessLatency > 0);
-        assertEquals(functionStats.instances.get(0).getMetrics().oneMin.getReceivedTotal(), totalMsgs);
-        assertEquals(functionStats.instances.get(0).getMetrics().oneMin.getProcessedSuccessfullyTotal(), totalMsgs);
-        assertEquals(functionStats.instances.get(0).getMetrics().oneMin.getSystemExceptionsTotal(), 0);
-        assertEquals(functionStats.instances.get(0).getMetrics().oneMin.getUserExceptionsTotal(), 0);
-        assertTrue(functionStats.instances.get(0).getMetrics().oneMin.getAvgProcessLatency() > 0);
-
-        assertEquals(functionStats.instances.get(0).getMetrics().getAvgProcessLatency(), functionStats.instances.get(0).getMetrics().oneMin.getAvgProcessLatency());
-        assertEquals(functionStats.instances.get(0).getMetrics().getAvgProcessLatency(), functionStats.getAvgProcessLatency());
+        assertTrue(functionStats.instances.get(0).getMetrics().getAvgProcessLatency() > 0);
+        assertEquals(functionStats.instances.get(0).getMetrics().getOneMin().getReceivedTotal(), totalMsgs);
+        assertEquals(functionStats.instances.get(0).getMetrics().getOneMin().getProcessedSuccessfullyTotal(), totalMsgs);
+        assertEquals(functionStats.instances.get(0).getMetrics().getOneMin().getSystemExceptionsTotal(), 0);
+        assertEquals(functionStats.instances.get(0).getMetrics().getOneMin().getUserExceptionsTotal(), 0);
+        assertTrue(functionStats.instances.get(0).getMetrics().getOneMin().getAvgProcessLatency() > 0);
+
+        assertEquals(functionStats.instances.get(0).getMetrics().getAvgProcessLatency(),
+                functionStats.instances.get(0).getMetrics().getOneMin().getAvgProcessLatency());
+        assertEquals(functionStats.instances.get(0).getMetrics().getAvgProcessLatency(),
+                functionStats.getAvgProcessLatency());
 
         // validate function instance stats
         functionInstanceStats = functionRuntimeManager.getFunctionInstanceStats(tenant, namespacePortion,
                 functionName, 0,  null);
 
-        functionInstanceStatsAdmin = admin.functions().getFunctionStats(tenant, namespacePortion,
-                functionName, 0);
+        functionInstanceStatsAdmin = (FunctionInstanceStatsDataImpl) admin.functions().getFunctionStats(tenant,
+                namespacePortion, functionName, 0);
 
         assertEquals(functionInstanceStats, functionInstanceStatsAdmin);
         assertEquals(functionInstanceStats, functionStats.instances.get(0).getMetrics());
@@ -678,7 +682,7 @@ public class PulsarFunctionE2ETest extends AbstractPulsarE2ETest {
         admin.namespaces().setNamespaceReplicationClusters(replNamespace, clusters);
 
         String roleName = validRoleName ? "superUser" : "invalid";
-        TenantInfo propAdmin = new TenantInfo();
+        TenantInfoImpl propAdmin = new TenantInfoImpl();
         propAdmin.getAdminRoles().add(roleName);
         propAdmin.setAllowedClusters(Sets.newHashSet(Lists.newArrayList("use")));
         admin.tenants().updateTenant(tenant, propAdmin);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionTlsTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionTlsTest.java
index ac96b1d..fcb2a44 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionTlsTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/io/PulsarFunctionTlsTest.java
@@ -52,7 +52,7 @@ import org.apache.pulsar.client.api.Authentication;
 import org.apache.pulsar.client.api.PulsarClient;
 import org.apache.pulsar.client.impl.auth.AuthenticationTls;
 import org.apache.pulsar.common.functions.FunctionConfig;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.util.ClassLoaderUtils;
 import org.apache.pulsar.common.util.ObjectMapperFactory;
 import org.apache.pulsar.functions.api.utils.IdentityFunction;
@@ -126,7 +126,7 @@ public class PulsarFunctionTlsTest {
         Tenants tenants = mock(Tenants.class);
         when(admin.tenants()).thenReturn(tenants);
         Set<String> admins = Sets.newHashSet("superUser", "admin");
-        TenantInfo tenantInfo = new TenantInfo(admins, null);
+        TenantInfoImpl tenantInfo = new TenantInfoImpl(admins, null);
         when(tenants.getTenantInfo(any())).thenReturn(tenantInfo);
         Namespaces namespaces = mock(Namespaces.class);
         when(admin.namespaces()).thenReturn(namespaces);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/schema/PartitionedTopicSchemaTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/schema/PartitionedTopicSchemaTest.java
index 04b5d17..6127026 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/schema/PartitionedTopicSchemaTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/schema/PartitionedTopicSchemaTest.java
@@ -28,8 +28,8 @@ import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.client.api.SubscriptionInitialPosition;
 import org.apache.pulsar.client.api.schema.GenericRecord;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.testng.Assert;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
@@ -51,15 +51,15 @@ public class PartitionedTopicSchemaTest extends MockedPulsarServiceBaseTest {
         isTcpLookup = true;
         super.internalSetup();
 
-        admin.clusters().createCluster("test", new ClusterData(pulsar.getWebServiceAddress()));
+        admin.clusters().createCluster("test", new ClusterDataImpl(pulsar.getWebServiceAddress()));
         admin.tenants().createTenant("my-property",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("my-property/my-ns");
         admin.namespaces().setNamespaceReplicationClusters("my-property/my-ns", Sets.newHashSet("test"));
 
         // so that clients can test short names
         admin.tenants().createTenant("public",
-                new TenantInfo(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
+                new TenantInfoImpl(Sets.newHashSet("appid1", "appid2"), Sets.newHashSet("test")));
         admin.namespaces().createNamespace("public/default");
         admin.namespaces().setNamespaceReplicationClusters("public/default", Sets.newHashSet("test"));
         admin.topics().createPartitionedTopic(PARTITIONED_TOPIC, TOPIC_PARTITION);
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/schema/SchemaTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/schema/SchemaTest.java
index fe720a1..ee39f9b 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/schema/SchemaTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/schema/SchemaTest.java
@@ -64,9 +64,9 @@ import org.apache.pulsar.client.impl.schema.KeyValueSchema;
 import org.apache.pulsar.client.impl.schema.generic.GenericJsonRecord;
 import org.apache.pulsar.common.naming.TopicDomain;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.SchemaCompatibilityStrategy;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.schema.KeyValue;
 import org.apache.pulsar.common.schema.KeyValueEncodingType;
 import org.apache.pulsar.common.schema.SchemaInfo;
@@ -89,8 +89,8 @@ public class SchemaTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         // Setup namespaces
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData(pulsar.getBrokerServiceUrl()));
-        TenantInfo tenantInfo = new TenantInfo();
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl(pulsar.getBrokerServiceUrl()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl();
         tenantInfo.setAllowedClusters(Collections.singleton(CLUSTER_NAME));
         admin.tenants().createTenant(PUBLIC_TENANT, tenantInfo);
     }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/schema/compatibility/SchemaCompatibilityCheckTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/schema/compatibility/SchemaCompatibilityCheckTest.java
index fcf223f..b4eb3e4 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/schema/compatibility/SchemaCompatibilityCheckTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/schema/compatibility/SchemaCompatibilityCheckTest.java
@@ -38,9 +38,9 @@ import org.apache.pulsar.client.api.schema.SchemaDefinition;
 import org.apache.pulsar.common.naming.NamespaceName;
 import org.apache.pulsar.common.naming.TopicDomain;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.SchemaCompatibilityStrategy;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.schema.SchemaInfo;
 import org.apache.pulsar.common.schema.SchemaType;
 import org.apache.pulsar.schema.Schemas;
@@ -61,8 +61,8 @@ public class SchemaCompatibilityCheckTest extends MockedPulsarServiceBaseTest {
         super.internalSetup();
 
         // Setup namespaces
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData(pulsar.getBrokerServiceUrl()));
-        TenantInfo tenantInfo = new TenantInfo();
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl(pulsar.getBrokerServiceUrl()));
+        TenantInfoImpl tenantInfo = new TenantInfoImpl();
         tenantInfo.setAllowedClusters(Collections.singleton(CLUSTER_NAME));
         admin.tenants().createTenant(PUBLIC_TENANT, tenantInfo);
     }
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/schema/compatibility/SchemaTypeCompatibilityCheckTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/schema/compatibility/SchemaTypeCompatibilityCheckTest.java
index 61cc989..67be4eb 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/schema/compatibility/SchemaTypeCompatibilityCheckTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/schema/compatibility/SchemaTypeCompatibilityCheckTest.java
@@ -29,9 +29,9 @@ import org.apache.pulsar.client.api.Schema;
 import org.apache.pulsar.client.api.SubscriptionType;
 import org.apache.pulsar.common.naming.TopicDomain;
 import org.apache.pulsar.common.naming.TopicName;
-import org.apache.pulsar.common.policies.data.ClusterData;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
 import org.apache.pulsar.common.policies.data.SchemaCompatibilityStrategy;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.common.schema.SchemaInfo;
 import org.apache.pulsar.schema.Schemas;
 import org.testng.annotations.AfterClass;
@@ -60,9 +60,9 @@ public class SchemaTypeCompatibilityCheckTest extends MockedPulsarServiceBaseTes
         super.internalSetup();
 
         // Setup namespaces
-        admin.clusters().createCluster(CLUSTER_NAME, new ClusterData(pulsar.getBrokerServiceUrl()));
+        admin.clusters().createCluster(CLUSTER_NAME, new ClusterDataImpl(pulsar.getBrokerServiceUrl()));
 
-        TenantInfo tenantInfo = new TenantInfo();
+        TenantInfoImpl tenantInfo = new TenantInfoImpl();
         tenantInfo.setAllowedClusters(Collections.singleton(CLUSTER_NAME));
         admin.tenants().createTenant(PUBLIC_TENANT, tenantInfo);
         admin.namespaces().createNamespace(namespaceName, Sets.newHashSet(CLUSTER_NAME));
diff --git a/pulsar-broker/src/test/java/org/apache/pulsar/websocket/proxy/ProxyAuthorizationTest.java b/pulsar-broker/src/test/java/org/apache/pulsar/websocket/proxy/ProxyAuthorizationTest.java
index 96ee825..9e22219 100644
--- a/pulsar-broker/src/test/java/org/apache/pulsar/websocket/proxy/ProxyAuthorizationTest.java
+++ b/pulsar-broker/src/test/java/org/apache/pulsar/websocket/proxy/ProxyAuthorizationTest.java
@@ -35,8 +35,8 @@ import org.apache.pulsar.broker.auth.MockedPulsarServiceBaseTest;
 import org.apache.pulsar.broker.authorization.AuthorizationService;
 import org.apache.pulsar.common.naming.TopicName;
 import org.apache.pulsar.common.policies.data.AuthAction;
-import org.apache.pulsar.common.policies.data.ClusterData;
-import org.apache.pulsar.common.policies.data.TenantInfo;
+import org.apache.pulsar.common.policies.data.ClusterDataImpl;
+import org.apache.pulsar.common.policies.data.TenantInfoImpl;
 import org.apache.pulsar.metadata.impl.ZKMetadataStore;
 import org.apache.pulsar.websocket.WebSocketService;
 import org.apache.pulsar.websocket.service.WebSocketProxyConfiguration;
@@ -87,8 +87,8 @@ public class ProxyAuthorizationTest extends MockedPulsarServiceBaseTest {
 
         assertFalse(auth.canLookup(TopicName.get("persistent://p1/c1/ns1/ds1"), "my-role", null));
 
-        admin.clusters().createCluster(configClusterName, new ClusterData());
-        admin.tenants().createTenant("p1", new TenantInfo(Sets.newHashSet("role1"), Sets.newHashSet("c1")));
+        admin.clusters().createCluster(configClusterName, new ClusterDataImpl());
+        admin.tenants().createTenant("p1", new TenantInfoImpl(Sets.newHashSet("role1"), Sets.newHashSet("c1")));
         waitForChange();
         admin.namespaces().createNamespace("p1/c1/ns1");
         waitForChange();
diff --git a/pulsar-client-admin-api/pom.xml b/pulsar-client-admin-api/pom.xml
index 739ef5e..1130405 100644
--- a/pulsar-client-admin-api/pom.xml
+++ b/pulsar-client-admin-api/pom.xml
@@ -36,13 +36,14 @@
 
         <dependency>
             <groupId>${project.groupId}</groupId>
-            <artifactId>pulsar-common</artifactId>
-            <version>${project.parent.version}</version>
+            <artifactId>pulsar-client-api</artifactId>
+            <version>${project.version}</version>
         </dependency>
 
         <dependency>
-            <groupId>com.google.code.gson</groupId>
-            <artifactId>gson</artifactId>
+            <groupId>org.slf4j</groupId>
+            <artifactId>slf4j-api</artifactId>
+            <scope>provided</scope>
         </dependency>
 
     </dependencies>
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/BrokerStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/BrokerStats.java
index eb4e232..100ba10 100644
--- a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/BrokerStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/BrokerStats.java
@@ -18,8 +18,6 @@
  */
 package org.apache.pulsar.client.admin;
 
-import com.google.gson.JsonArray;
-import com.google.gson.JsonObject;
 import java.util.concurrent.CompletableFuture;
 import org.apache.pulsar.common.stats.AllocatorStats;
 import org.apache.pulsar.policies.data.loadbalancer.LoadManagerReport;
@@ -36,7 +34,7 @@ public interface BrokerStats {
      * @throws PulsarAdminException
      */
 
-    JsonArray getMetrics() throws PulsarAdminException;
+    String getMetrics() throws PulsarAdminException;
 
     /**
      * Returns Monitoring metrics asynchronously.
@@ -44,7 +42,7 @@ public interface BrokerStats {
      * @return
      */
 
-    CompletableFuture<JsonArray> getMetricsAsync();
+    CompletableFuture<String> getMetricsAsync();
 
     /**
      * Requests JSON string server mbean dump.
@@ -54,7 +52,7 @@ public interface BrokerStats {
      * @return
      * @throws PulsarAdminException
      */
-    JsonArray getMBeans() throws PulsarAdminException;
+    String getMBeans() throws PulsarAdminException;
 
     /**
      * Requests JSON string server mbean dump asynchronously.
@@ -63,7 +61,7 @@ public interface BrokerStats {
      *
      * @return
      */
-    CompletableFuture<JsonArray> getMBeansAsync();
+    CompletableFuture<String> getMBeansAsync();
 
     /**
      * Returns JSON string topics stats.
@@ -73,7 +71,7 @@ public interface BrokerStats {
      * @return
      * @throws PulsarAdminException
      */
-    JsonObject getTopics() throws PulsarAdminException;
+    String getTopics() throws PulsarAdminException;
 
     /**
      * Returns JSON string topics stats asynchronously.
@@ -82,7 +80,7 @@ public interface BrokerStats {
      *
      * @return
      */
-    CompletableFuture<JsonObject> getTopicsAsync();
+    CompletableFuture<String> getTopicsAsync();
 
     /**
      * Get pending bookie client op stats by namespace.
@@ -92,7 +90,7 @@ public interface BrokerStats {
      * @return
      * @throws PulsarAdminException
      */
-    JsonObject getPendingBookieOpsStats() throws PulsarAdminException;
+    String getPendingBookieOpsStats() throws PulsarAdminException;
 
     /**
      * Get pending bookie client op stats by namespace asynchronously.
@@ -101,7 +99,7 @@ public interface BrokerStats {
      *
      * @return
      */
-    CompletableFuture<JsonObject> getPendingBookieOpsStatsAsync();
+    CompletableFuture<String> getPendingBookieOpsStatsAsync();
 
     /**
      * Get the stats for the Netty allocator.
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Clusters.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Clusters.java
index df5d089..263d8af 100644
--- a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Clusters.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Clusters.java
@@ -289,7 +289,8 @@ public interface Clusters {
      * @throws PulsarAdminException
      *             Unexpected error
      */
-    Map<String, NamespaceIsolationData> getNamespaceIsolationPolicies(String cluster) throws PulsarAdminException;
+    Map<String, NamespaceIsolationData> getNamespaceIsolationPolicies(String cluster)
+            throws PulsarAdminException;
 
     /**
      * Get the namespace isolation policies of a cluster asynchronously.
@@ -376,7 +377,8 @@ public interface Clusters {
      * @param cluster
      * @return
      */
-    CompletableFuture<List<BrokerNamespaceIsolationData>> getBrokersWithNamespaceIsolationPolicyAsync(String cluster);
+    CompletableFuture<List<BrokerNamespaceIsolationData>> getBrokersWithNamespaceIsolationPolicyAsync(
+            String cluster);
 
     /**
      * Returns active broker with namespace-isolation policies attached to it.
@@ -511,7 +513,8 @@ public interface Clusters {
      * @throws PulsarAdminException
      *             Unexpected error
      */
-    NamespaceIsolationData getNamespaceIsolationPolicy(String cluster, String policyName) throws PulsarAdminException;
+    NamespaceIsolationData getNamespaceIsolationPolicy(String cluster, String policyName)
+            throws PulsarAdminException;
 
     /**
      * Get a single namespace isolation policy for a cluster asynchronously.
@@ -524,7 +527,8 @@ public interface Clusters {
      *          Policy name
      *
      */
-    CompletableFuture<NamespaceIsolationData> getNamespaceIsolationPolicyAsync(String cluster, String policyName);
+    CompletableFuture<NamespaceIsolationData> getNamespaceIsolationPolicyAsync(String cluster,
+                                                                               String policyName);
 
     /**
      * Create a domain into cluster.
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Functions.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Functions.java
index 5443b3c..82c47e5 100644
--- a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Functions.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Functions.java
@@ -28,6 +28,7 @@ import org.apache.pulsar.common.functions.FunctionConfig;
 import org.apache.pulsar.common.functions.FunctionState;
 import org.apache.pulsar.common.functions.UpdateOptions;
 import org.apache.pulsar.common.io.ConnectorDefinition;
+import org.apache.pulsar.common.policies.data.FunctionInstanceStatsData;
 import org.apache.pulsar.common.policies.data.FunctionStats;
 import org.apache.pulsar.common.policies.data.FunctionStatus;
 
@@ -410,7 +411,7 @@ public interface Functions {
      * @return
      * @throws PulsarAdminException
      */
-    FunctionStats.FunctionInstanceStats.FunctionInstanceStatsData getFunctionStats(
+    FunctionInstanceStatsData getFunctionStats(
             String tenant, String namespace, String function, int id)
             throws PulsarAdminException;
 
@@ -427,7 +428,7 @@ public interface Functions {
      *            Function instance-id
      * @return
      */
-    CompletableFuture<FunctionStats.FunctionInstanceStats.FunctionInstanceStatsData> getFunctionStatsAsync(
+    CompletableFuture<FunctionInstanceStatsData> getFunctionStatsAsync(
             String tenant, String namespace, String function, int id);
 
     /**
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/ProxyStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/ProxyStats.java
index d5eeee7..66eb411 100644
--- a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/ProxyStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/ProxyStats.java
@@ -18,9 +18,6 @@
  */
 package org.apache.pulsar.client.admin;
 
-import com.google.gson.JsonArray;
-import com.google.gson.JsonObject;
-
 /**
  * Admin interface for proxy stats management.
  */
@@ -33,7 +30,7 @@ public interface ProxyStats {
      * @throws PulsarAdminException
      */
 
-    JsonArray getConnections() throws PulsarAdminException;
+    String getConnections() throws PulsarAdminException;
 
     /**
      * Returns Topics metrics.
@@ -41,5 +38,5 @@ public interface ProxyStats {
      * @return
      * @throws PulsarAdminException
      */
-    JsonObject getTopics() throws PulsarAdminException;
+    String getTopics() throws PulsarAdminException;
 }
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/PulsarAdminException.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/PulsarAdminException.java
index e9a9160..041f8a6 100644
--- a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/PulsarAdminException.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/PulsarAdminException.java
@@ -18,15 +18,7 @@
  */
 package org.apache.pulsar.client.admin;
 
-import java.io.InputStream;
-import java.nio.charset.StandardCharsets;
-import javax.ws.rs.ClientErrorException;
-import javax.ws.rs.ServerErrorException;
-import javax.ws.rs.WebApplicationException;
 import lombok.extern.slf4j.Slf4j;
-import org.apache.commons.io.IOUtils;
-import org.apache.pulsar.common.policies.data.ErrorData;
-import org.apache.pulsar.common.util.ObjectMapperFactory;
 
 /**
  * Pulsar admin exceptions.
@@ -39,57 +31,16 @@ public class PulsarAdminException extends Exception {
     private final String httpError;
     private final int statusCode;
 
-    private static String getReasonFromServer(WebApplicationException e) {
-        try {
-            ErrorData errorData = e.getResponse().readEntity(ErrorData.class);
-            if (errorData == null) {
-                return e.getMessage();
-            }
-            return errorData.reason.toString();
-        } catch (Exception ex) {
-            try {
-                Object entity = e.getResponse().getEntity();
-                String errorAsString;
-                if (entity instanceof InputStream) {
-                    errorAsString =  IOUtils.toString((InputStream) entity, StandardCharsets.UTF_8.name());
-                } else {
-                    errorAsString = entity.toString();
-                }
-                return ObjectMapperFactory.getThreadLocal().readValue(
-                        errorAsString, ErrorData.class).reason;
-            } catch (Exception ex1) {
-                try {
-                    return ObjectMapperFactory.getThreadLocal().readValue(e.getMessage(), ErrorData.class).reason;
-                } catch (Exception ex2) {
-                    // could not parse output to ErrorData class
-                    return e.getMessage();
-                }
-            }
-        }
-    }
-
-    public PulsarAdminException(ClientErrorException e) {
-        super(getReasonFromServer(e), e);
-        this.httpError = getReasonFromServer(e);
-        this.statusCode = e.getResponse().getStatus();
-    }
-
-    public PulsarAdminException(ClientErrorException e, String message) {
-        super(message, e);
-        this.httpError = getReasonFromServer(e);
-        this.statusCode = e.getResponse().getStatus();
-    }
-
-    public PulsarAdminException(ServerErrorException e) {
-        super(getReasonFromServer(e), e);
-        this.httpError = getReasonFromServer(e);
-        this.statusCode = e.getResponse().getStatus();
+    public PulsarAdminException(Throwable t, String httpError, int statusCode) {
+        super(t);
+        this.httpError = httpError;
+        this.statusCode = statusCode;
     }
 
-    public PulsarAdminException(ServerErrorException e, String message) {
-        super(getReasonFromServer(e) + (message != null ? " " + message : ""), e);
-        this.httpError = getReasonFromServer(e);
-        this.statusCode = e.getResponse().getStatus();
+    public PulsarAdminException(String message, Throwable t, String httpError, int statusCode) {
+        super(message, t);
+        this.httpError = httpError;
+        this.statusCode = statusCode;
     }
 
     public PulsarAdminException(Throwable t) {
@@ -98,12 +49,6 @@ public class PulsarAdminException extends Exception {
         statusCode = DEFAULT_STATUS_CODE;
     }
 
-    public PulsarAdminException(WebApplicationException e) {
-        super(getReasonFromServer(e), e);
-        this.httpError = getReasonFromServer(e);
-        this.statusCode = e.getResponse().getStatus();
-    }
-
     public PulsarAdminException(String message, Throwable t) {
         super(message, t);
         httpError = null;
@@ -128,8 +73,8 @@ public class PulsarAdminException extends Exception {
      * Not Authorized Exception.
      */
     public static class NotAuthorizedException extends PulsarAdminException {
-        public NotAuthorizedException(ClientErrorException e) {
-            super(e);
+        public NotAuthorizedException(Throwable t, String httpError, int statusCode) {
+            super(httpError, t, httpError, statusCode);
         }
     }
 
@@ -137,8 +82,8 @@ public class PulsarAdminException extends Exception {
      * Not Found Exception.
      */
     public static class NotFoundException extends PulsarAdminException {
-        public NotFoundException(ClientErrorException e) {
-            super(e);
+        public NotFoundException(Throwable t, String httpError, int statusCode) {
+            super(httpError, t, httpError, statusCode);
         }
     }
 
@@ -146,8 +91,8 @@ public class PulsarAdminException extends Exception {
      * Not Allowed Exception.
      */
     public static class NotAllowedException extends PulsarAdminException {
-        public NotAllowedException(ClientErrorException e) {
-            super(e);
+        public NotAllowedException(Throwable t, String httpError, int statusCode) {
+            super(httpError, t, httpError, statusCode);
         }
     }
 
@@ -155,8 +100,8 @@ public class PulsarAdminException extends Exception {
      * Conflict Exception.
      */
     public static class ConflictException extends PulsarAdminException {
-        public ConflictException(ClientErrorException e) {
-            super(e);
+        public ConflictException(Throwable t, String httpError, int statusCode) {
+            super(httpError, t, httpError, statusCode);
         }
     }
 
@@ -164,8 +109,8 @@ public class PulsarAdminException extends Exception {
      * Precondition Failed Exception.
      */
     public static class PreconditionFailedException extends PulsarAdminException {
-        public PreconditionFailedException(ClientErrorException e) {
-            super(e);
+        public PreconditionFailedException(Throwable t, String httpError, int statusCode) {
+            super(httpError, t, httpError, statusCode);
         }
     }
 
@@ -182,12 +127,12 @@ public class PulsarAdminException extends Exception {
      * Server Side Error Exception.
      */
     public static class ServerSideErrorException extends PulsarAdminException {
-        public ServerSideErrorException(ServerErrorException e, String msg) {
-            super(e, msg);
+        public ServerSideErrorException(Throwable t, String message, String httpError, int statusCode) {
+            super(message, t, httpError, statusCode);
         }
 
-        public ServerSideErrorException(ServerErrorException e) {
-            super(e, "Some error occourred on the server");
+        public ServerSideErrorException(Throwable t) {
+            super("Some error occourred on the server", t);
         }
     }
 
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Sinks.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Sinks.java
index f51cf66..dae91c7 100644
--- a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Sinks.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Sinks.java
@@ -200,7 +200,8 @@ public interface Sinks {
      * @throws PulsarAdminException
      *             Unexpected error
      */
-    void updateSink(SinkConfig sinkConfig, String fileName, UpdateOptions updateOptions) throws PulsarAdminException;
+    void updateSink(SinkConfig sinkConfig, String fileName, UpdateOptions updateOptions)
+            throws PulsarAdminException;
 
     /**
      * Update the configuration for a sink asynchronously.
@@ -211,7 +212,8 @@ public interface Sinks {
      * @param updateOptions
      *            options for the update operations
      */
-    CompletableFuture<Void> updateSinkAsync(SinkConfig sinkConfig, String fileName, UpdateOptions updateOptions);
+    CompletableFuture<Void> updateSinkAsync(SinkConfig sinkConfig, String fileName,
+                                            UpdateOptions updateOptions);
 
     /**
      * Update the configuration for a sink.
@@ -288,7 +290,8 @@ public interface Sinks {
      * @param updateOptions
      *            options for the update operations
      */
-    CompletableFuture<Void> updateSinkWithUrlAsync(SinkConfig sinkConfig, String pkgUrl, UpdateOptions updateOptions);
+    CompletableFuture<Void> updateSinkWithUrlAsync(SinkConfig sinkConfig, String pkgUrl,
+                                                   UpdateOptions updateOptions);
 
     /**
      * Delete an existing sink.
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Sources.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Sources.java
index fea9374..822020b 100644
--- a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Sources.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Sources.java
@@ -212,7 +212,8 @@ public interface Sources {
      * @param updateOptions
      *            options for the update operations
      */
-    CompletableFuture<Void> updateSourceAsync(SourceConfig sourceConfig, String fileName, UpdateOptions updateOptions);
+    CompletableFuture<Void> updateSourceAsync(SourceConfig sourceConfig, String fileName,
+                                              UpdateOptions updateOptions);
 
     /**
      * Update the configuration for a source.
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Topics.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Topics.java
index d5f3f10..66ac8c4 100644
--- a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Topics.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/Topics.java
@@ -18,7 +18,6 @@
  */
 package org.apache.pulsar.client.admin;
 
-import com.google.gson.JsonObject;
 import java.util.List;
 import java.util.Map;
 import java.util.Set;
@@ -921,7 +920,7 @@ public interface Topics {
      * @throws PulsarAdminException
      *             Unexpected error
      */
-    JsonObject getInternalInfo(String topic) throws PulsarAdminException;
+    String getInternalInfo(String topic) throws PulsarAdminException;
 
     /**
      * Get a JSON representation of the topic metadata stored in ZooKeeper.
@@ -936,7 +935,7 @@ public interface Topics {
      * @throws PulsarAdminException
      *             Unexpected error
      */
-    CompletableFuture<JsonObject> getInternalInfoAsync(String topic);
+    CompletableFuture<String> getInternalInfoAsync(String topic);
 
     /**
      * Get the stats for the partitioned topic
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/utils/DefaultImplementation.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/utils/DefaultImplementation.java
index 149257f..ecd8d1f 100644
--- a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/utils/DefaultImplementation.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/client/admin/utils/DefaultImplementation.java
@@ -48,4 +48,5 @@ public class DefaultImplementation {
         return ReflectionUtils.catchExceptions(() -> OFFLOAD_PROCESS_STATUS_IMPL_status_string_messageid.newInstance(
                 status, lastError, messageId));
     }
+
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/InternalConfigurationData.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/conf/InternalConfigurationData.java
similarity index 86%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/conf/InternalConfigurationData.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/conf/InternalConfigurationData.java
index 5a1ce63..80da3ca 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/InternalConfigurationData.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/conf/InternalConfigurationData.java
@@ -18,12 +18,13 @@
  */
 package org.apache.pulsar.common.conf;
 
-import com.google.common.base.MoreObjects;
 import java.util.Objects;
+import lombok.ToString;
 
 /**
  * Internal configuration data.
  */
+@ToString
 public class InternalConfigurationData {
 
     private String zookeeperServers;
@@ -92,15 +93,4 @@ public class InternalConfigurationData {
                 stateStorageServiceUrl);
     }
 
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this)
-            .add("zookeeperServers", zookeeperServers)
-            .add("configurationStoreServers", configurationStoreServers)
-            .add("ledgersRootPath", ledgersRootPath)
-            .add("bookkeeperMetadataServiceUri", bookkeeperMetadataServiceUri)
-            .add("stateStorageServiceUrl", stateStorageServiceUrl)
-            .toString();
-    }
-
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/conf/package-info.java
similarity index 100%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/conf/package-info.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/AuthenticationConfig.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/AuthenticationConfig.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/functions/AuthenticationConfig.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/AuthenticationConfig.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/ConsumerConfig.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/ConsumerConfig.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/functions/ConsumerConfig.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/ConsumerConfig.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/CryptoConfig.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/CryptoConfig.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/functions/CryptoConfig.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/CryptoConfig.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/ExternalPulsarConfig.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/ExternalPulsarConfig.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/functions/ExternalPulsarConfig.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/ExternalPulsarConfig.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/FunctionConfig.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/FunctionConfig.java
similarity index 97%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/functions/FunctionConfig.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/FunctionConfig.java
index 1df42b93..8a83b37 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/FunctionConfig.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/FunctionConfig.java
@@ -18,7 +18,6 @@
  */
 package org.apache.pulsar.common.functions;
 
-import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
 import java.util.Collection;
 import java.util.Map;
 import lombok.AllArgsConstructor;
@@ -34,7 +33,6 @@ import org.apache.pulsar.client.api.SubscriptionInitialPosition;
 @Builder(toBuilder = true)
 @NoArgsConstructor
 @AllArgsConstructor
-@JsonIgnoreProperties(ignoreUnknown = true)
 public class FunctionConfig {
 
     /**
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/FunctionState.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/FunctionState.java
similarity index 92%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/functions/FunctionState.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/FunctionState.java
index bec7528..34f5057 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/FunctionState.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/FunctionState.java
@@ -18,7 +18,6 @@
  */
 package org.apache.pulsar.common.functions;
 
-import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
 import lombok.AllArgsConstructor;
 import lombok.Builder;
 import lombok.Data;
@@ -31,7 +30,6 @@ import lombok.NoArgsConstructor;
 @Builder(toBuilder = true)
 @NoArgsConstructor
 @AllArgsConstructor
-@JsonIgnoreProperties(ignoreUnknown = true)
 public class FunctionState {
     private String key;
     private String stringValue;
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/ProducerConfig.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/ProducerConfig.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/functions/ProducerConfig.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/ProducerConfig.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/Resources.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/Resources.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/functions/Resources.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/Resources.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionPendingAckStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/UpdateOptions.java
similarity index 83%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionPendingAckStats.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/UpdateOptions.java
index fb1b9c7..f1d946d 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionPendingAckStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/UpdateOptions.java
@@ -16,10 +16,10 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-package org.apache.pulsar.common.policies.data;
+package org.apache.pulsar.common.functions;
 
-public class TransactionPendingAckStats {
+public interface UpdateOptions {
+    boolean isUpdateAuthData();
 
-    /** The state of this pending ack. */
-    public String state;
+    void setUpdateAuthData(boolean updateAuthData);
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/WindowConfig.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/WindowConfig.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/functions/WindowConfig.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/WindowConfig.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/functions/WorkerInfo.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/WorkerInfo.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/functions/WorkerInfo.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/WorkerInfo.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/package-info.java
similarity index 91%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/package-info.java
index 28e95d0..d2c8bd8 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/functions/package-info.java
@@ -17,6 +17,6 @@
  * under the License.
  */
 /**
- * Classes for internal configuration.
+ * Implementation of policies.
  */
-package org.apache.pulsar.common.conf;
\ No newline at end of file
+package org.apache.pulsar.common.functions;
\ No newline at end of file
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/io/BatchSourceConfig.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/BatchSourceConfig.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/io/BatchSourceConfig.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/BatchSourceConfig.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/io/ConnectorDefinition.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/ConnectorDefinition.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/io/ConnectorDefinition.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/ConnectorDefinition.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/io/SinkConfig.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/SinkConfig.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/io/SinkConfig.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/SinkConfig.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/io/SourceConfig.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/SourceConfig.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/io/SourceConfig.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/SourceConfig.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/package-info.java
similarity index 91%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/package-info.java
index 28e95d0..809ad0d 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/io/package-info.java
@@ -17,6 +17,6 @@
  * under the License.
  */
 /**
- * Classes for internal configuration.
+ * Implementation of policies.
  */
-package org.apache.pulsar.common.conf;
\ No newline at end of file
+package org.apache.pulsar.common.io;
\ No newline at end of file
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/naming/TopicDomain.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/naming/TopicDomain.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/naming/TopicDomain.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/naming/TopicDomain.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/naming/package-info.java
similarity index 91%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/naming/package-info.java
index 28e95d0..39d55c3 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/naming/package-info.java
@@ -17,6 +17,6 @@
  * under the License.
  */
 /**
- * Classes for internal configuration.
+ * Implementation of policies.
  */
-package org.apache.pulsar.common.conf;
\ No newline at end of file
+package org.apache.pulsar.common.naming;
\ No newline at end of file
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/partition/PartitionedTopicMetadata.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/partition/PartitionedTopicMetadata.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/partition/PartitionedTopicMetadata.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/partition/PartitionedTopicMetadata.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/partition/package-info.java
similarity index 91%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/partition/package-info.java
index 28e95d0..ba27c98 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/conf/package-info.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/partition/package-info.java
@@ -17,6 +17,6 @@
  * under the License.
  */
 /**
- * Classes for internal configuration.
+ * Implementation of policies.
  */
-package org.apache.pulsar.common.conf;
\ No newline at end of file
+package org.apache.pulsar.common.partition;
\ No newline at end of file
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/AutoFailoverPolicy.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/AutoFailoverPolicy.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/AutoFailoverPolicy.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/AutoFailoverPolicy.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AuthAction.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AuthAction.java
similarity index 100%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AuthAction.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AuthAction.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AuthPolicies.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AuthPolicies.java
similarity index 91%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AuthPolicies.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AuthPolicies.java
index 8804096..de882d1 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AuthPolicies.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AuthPolicies.java
@@ -18,7 +18,7 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.collect.Maps;
+import java.util.HashMap;
 import java.util.Map;
 import java.util.Objects;
 import java.util.Set;
@@ -35,9 +35,9 @@ public class AuthPolicies {
     public final Map<String, Set<String>> subscription_auth_roles;
 
     public AuthPolicies() {
-        namespace_auth = Maps.newHashMap();
-        destination_auth = Maps.newHashMap();
-        subscription_auth_roles = Maps.newHashMap();
+        namespace_auth = new HashMap<>();
+        destination_auth = new HashMap<>();
+        subscription_auth_roles = new HashMap<>();
     }
 
     @Override
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionInBufferStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoFailoverPolicyData.java
similarity index 76%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionInBufferStats.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoFailoverPolicyData.java
index 194f5f38a..1c19807 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionInBufferStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoFailoverPolicyData.java
@@ -18,14 +18,14 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import lombok.Data;
+import java.util.Map;
 
-@Data
-public class TransactionInBufferStats {
+public interface AutoFailoverPolicyData {
+    AutoFailoverPolicyType getPolicy_type();
 
-    /** The start position of this transaction in transaction buffer. */
-    public String startPosition;
+    Map<String, String> getParameters();
 
-    /** The flag of this transaction have been aborted. */
-    public boolean aborted;
+    void setPolicy_type(AutoFailoverPolicyType policyType);
+
+    void setParameters(Map<String, String> parameters);
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AutoFailoverPolicyType.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoFailoverPolicyType.java
similarity index 90%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AutoFailoverPolicyType.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoFailoverPolicyType.java
index 57229e6..31d0123 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AutoFailoverPolicyType.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoFailoverPolicyType.java
@@ -18,15 +18,9 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import io.swagger.annotations.ApiModel;
-
 /**
  * The policy type of auto failover.
  */
-@ApiModel(
-    value = "AutoFailoverPolicyType",
-    description = "The policy type of auto failover."
-)
 public enum AutoFailoverPolicyType {
     min_available;
 
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AutoSubscriptionCreationOverride.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoSubscriptionCreationOverride.java
similarity index 85%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AutoSubscriptionCreationOverride.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoSubscriptionCreationOverride.java
index 221b22f..2a57b75 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AutoSubscriptionCreationOverride.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoSubscriptionCreationOverride.java
@@ -18,12 +18,13 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.base.MoreObjects;
 import java.util.Objects;
+import lombok.ToString;
 
 /**
  * Override of autoSubscriptionCreation settings on a namespace level.
  */
+@ToString
 public class AutoSubscriptionCreationOverride {
     public boolean allowAutoSubscriptionCreation;
 
@@ -47,10 +48,4 @@ public class AutoSubscriptionCreationOverride {
         }
         return false;
     }
-
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this)
-                .add("allowAutoSubscriptionCreation", allowAutoSubscriptionCreation).toString();
-    }
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AutoTopicCreationOverride.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoTopicCreationOverride.java
similarity index 90%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AutoTopicCreationOverride.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoTopicCreationOverride.java
index 552b470..750b771 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AutoTopicCreationOverride.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/AutoTopicCreationOverride.java
@@ -18,12 +18,13 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.base.MoreObjects;
 import java.util.Objects;
+import lombok.ToString;
 
 /**
  * Override of autoTopicCreation settings on a namespace level.
  */
+@ToString
 public class AutoTopicCreationOverride {
     public boolean allowAutoTopicCreation;
     public String topicType;
@@ -55,12 +56,6 @@ public class AutoTopicCreationOverride {
         return false;
     }
 
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this).add("allowAutoTopicCreation", allowAutoTopicCreation)
-                .add("topicType", topicType).add("defaultNumPartitions", defaultNumPartitions).toString();
-    }
-
     public static boolean isValidOverride(AutoTopicCreationOverride override) {
         if (override == null) {
             return false;
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BacklogQuota.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BacklogQuota.java
similarity index 91%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BacklogQuota.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BacklogQuota.java
index 5fd0907..0bb39d2 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BacklogQuota.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BacklogQuota.java
@@ -18,9 +18,8 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.fasterxml.jackson.annotation.JsonAlias;
-import com.google.common.base.MoreObjects;
 import java.util.Objects;
+import lombok.ToString;
 
 /**
  * Unit of a backlog quota configuration for a scoped resource in a Pulsar instance.
@@ -28,8 +27,8 @@ import java.util.Objects;
  * <p>A scoped resource is identified by a {@link BacklogQuotaType} enumeration type which is containing two attributes:
  * <code>limit</code> representing a quota limit in bytes and <code>policy</code> for backlog retention policy.
  */
+@ToString
 public class BacklogQuota {
-    @JsonAlias("limit")
     private long limitSize;
     // backlog quota by time in second
     private int limitTime;
@@ -90,12 +89,6 @@ public class BacklogQuota {
     }
 
     @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this).add("limitSize", limitSize).add("limitTime", limitTime)
-                .add("policy", policy).toString();
-    }
-
-    @Override
     public boolean equals(Object obj) {
         if (obj instanceof BacklogQuota) {
             BacklogQuota other = (BacklogQuota) obj;
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookieAffinityGroupData.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookieAffinityGroupData.java
similarity index 84%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookieAffinityGroupData.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookieAffinityGroupData.java
index 15f8334..1acc2bc 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookieAffinityGroupData.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookieAffinityGroupData.java
@@ -18,7 +18,7 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.base.Objects;
+import java.util.Objects;
 
 /**
  * Description of a BookKeeper's affinity group.
@@ -38,15 +38,15 @@ public class BookieAffinityGroupData {
 
     @Override
     public int hashCode() {
-        return Objects.hashCode(bookkeeperAffinityGroupPrimary, bookkeeperAffinityGroupSecondary);
+        return Objects.hash(bookkeeperAffinityGroupPrimary, bookkeeperAffinityGroupSecondary);
     }
 
     @Override
     public boolean equals(Object obj) {
         if (obj instanceof BookieAffinityGroupData) {
             BookieAffinityGroupData other = (BookieAffinityGroupData) obj;
-            return Objects.equal(bookkeeperAffinityGroupPrimary, other.bookkeeperAffinityGroupPrimary)
-                    && Objects.equal(bookkeeperAffinityGroupSecondary, other.bookkeeperAffinityGroupSecondary);
+            return Objects.equals(bookkeeperAffinityGroupPrimary, other.bookkeeperAffinityGroupPrimary)
+                    && Objects.equals(bookkeeperAffinityGroupSecondary, other.bookkeeperAffinityGroupSecondary);
         }
         return false;
     }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookieInfo.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookieInfo.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookieInfo.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookieInfo.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
similarity index 99%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
index 5d11372..e16012e 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
@@ -18,13 +18,12 @@
  */
 package org.apache.pulsar.common.policies.data;
 
+import java.util.List;
 import lombok.AllArgsConstructor;
 import lombok.Data;
 import lombok.NoArgsConstructor;
 import lombok.ToString;
 
-import java.util.List;
-
 /**
  * Raw bookies information.
  */
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesRackConfiguration.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookiesRackConfiguration.java
similarity index 92%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesRackConfiguration.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookiesRackConfiguration.java
index 60bd039..f7f477c 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesRackConfiguration.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BookiesRackConfiguration.java
@@ -18,8 +18,8 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import static com.google.common.base.Preconditions.checkNotNull;
 import java.util.Map;
+import java.util.Objects;
 import java.util.Optional;
 import java.util.TreeMap;
 
@@ -53,9 +53,9 @@ public class BookiesRackConfiguration extends TreeMap<String, Map<String, Bookie
     }
 
     public synchronized void updateBookie(String group, String address, BookieInfo bookieInfo) {
-        checkNotNull(group);
-        checkNotNull(address);
-        checkNotNull(bookieInfo);
+        Objects.requireNonNull(group);
+        Objects.requireNonNull(address);
+        Objects.requireNonNull(bookieInfo);
 
         // Remove from any group first
         removeBookie(address);
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BrokerAssignment.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerAssignment.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BrokerAssignment.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerAssignment.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BrokerInfo.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerInfo.java
similarity index 97%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BrokerInfo.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerInfo.java
index c194a78..7581049 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BrokerInfo.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerInfo.java
@@ -23,7 +23,7 @@ import lombok.Data;
 import lombok.NoArgsConstructor;
 
 /**
- * Broker Information
+ * Broker Information.
  */
 @Data
 @AllArgsConstructor
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerNamespaceIsolationData.java
similarity index 71%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerNamespaceIsolationData.java
index 5d11372..3ea8e42 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerNamespaceIsolationData.java
@@ -18,24 +18,22 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import lombok.AllArgsConstructor;
-import lombok.Data;
-import lombok.NoArgsConstructor;
-import lombok.ToString;
-
 import java.util.List;
 
-/**
- * Raw bookies information.
- */
-@Data
-@NoArgsConstructor
-@AllArgsConstructor
-@ToString
-public class BookiesClusterInfo {
+public interface BrokerNamespaceIsolationData {
+    String getBrokerName();
+
+    String getPolicyName();
+
+    boolean isPrimary();
+
+    List<String> getNamespaceRegex();
+
+    void setBrokerName(String brokerName);
 
-    private static final long serialVersionUID = 0L;
+    void setPolicyName(String policyName);
 
-    private List<RawBookieInfo> bookies;
+    void setPrimary(boolean isPrimary);
 
+    void setNamespaceRegex(List<String> namespaceRegex);
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BrokerStatus.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerStatus.java
similarity index 90%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BrokerStatus.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerStatus.java
index bd7a338..fb3498e 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BrokerStatus.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BrokerStatus.java
@@ -18,7 +18,6 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.collect.ComparisonChain;
 import lombok.EqualsAndHashCode;
 
 /**
@@ -58,8 +57,11 @@ public class BrokerStatus implements Comparable<BrokerStatus> {
 
     @Override
     public int compareTo(BrokerStatus other) {
-        return ComparisonChain.start().compare(this.loadFactor, other.loadFactor)
-                .compare(this.brokerAddress, other.brokerAddress).result();
+        int result = Integer.compare(this.loadFactor, other.loadFactor);
+        if (result == 0) {
+            result = this.brokerAddress.compareTo(other.brokerAddress);
+        }
+        return result;
     }
 
     @Override
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BundlesData.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BundlesData.java
similarity index 90%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BundlesData.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BundlesData.java
index 4bc95cb..3540a25 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BundlesData.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/BundlesData.java
@@ -18,13 +18,14 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.base.MoreObjects;
 import java.util.List;
 import java.util.Objects;
+import lombok.ToString;
 
 /**
  * Holder for bundles.
  */
+@ToString
 public class BundlesData {
     public List<String> boundaries;
     public int numBundles;
@@ -75,9 +76,4 @@ public class BundlesData {
         return false;
     }
 
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this).add("numBundles", numBundles).add("boundaries", boundaries).toString();
-    }
-
 }
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ClusterData.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ClusterData.java
new file mode 100644
index 0000000..f6685c5
--- /dev/null
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ClusterData.java
@@ -0,0 +1,84 @@
+/**
+ * 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.pulsar.common.policies.data;
+
+import java.util.LinkedHashSet;
+import org.apache.pulsar.client.api.ProxyProtocol;
+
+public interface ClusterData {
+    String getServiceUrl();
+
+    String getServiceUrlTls();
+
+    ClusterData setServiceUrl(String serviceUrl);
+
+    ClusterData setServiceUrlTls(String serviceUrlTls);
+
+    String getBrokerServiceUrl();
+
+    ClusterData setBrokerServiceUrl(String brokerServiceUrl);
+
+    String getBrokerServiceUrlTls();
+
+    ClusterData setBrokerServiceUrlTls(String brokerServiceUrlTls);
+
+    String getProxyServiceUrl();
+
+    ClusterData setProxyServiceUrl(String proxyServiceUrl);
+
+    ProxyProtocol getProxyProtocol();
+
+    ClusterData setProxyProtocol(ProxyProtocol proxyProtocol);
+
+    LinkedHashSet<String> getPeerClusterNames();
+
+    String getAuthenticationPlugin();
+
+    ClusterData setAuthenticationPlugin(String authenticationPlugin);
+
+    String getAuthenticationParameters();
+
+    ClusterData setAuthenticationParameters(String authenticationParameters);
+
+    ClusterData setPeerClusterNames(LinkedHashSet<String> peerClusterNames);
+
+    ClusterData setBrokerClientTlsEnabled(boolean enabled);
+    boolean isBrokerClientTlsEnabled();
+
+    ClusterData setTlsAllowInsecureConnection(boolean enabled);
+    boolean isTlsAllowInsecureConnection();
+
+    ClusterData setBrokerClientTlsEnabledWithKeyStore(boolean enabled);
+    boolean isBrokerClientTlsEnabledWithKeyStore();
+
+    ClusterData setBrokerClientTlsTrustStoreType(String trustStoreType);
+    String getBrokerClientTlsTrustStoreType();
+
+    ClusterData setBrokerClientTlsTrustStore(String tlsTrustStore);
+    String getBrokerClientTlsTrustStore();
+
+    ClusterData setBrokerClientTlsTrustStorePassword(String trustStorePassword);
+    String getBrokerClientTlsTrustStorePassword();
+
+    ClusterData setBrokerClientTrustCertsFilePath(String trustCertsFilePath);
+    String getBrokerClientTrustCertsFilePath();
+
+    ClusterData setListenerName(String listenerName);
+    String getListenerName();
+}
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/ConsumerStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ConsumerStats.java
similarity index 98%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/ConsumerStats.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ConsumerStats.java
index f1d7856..4bba997 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/ConsumerStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ConsumerStats.java
@@ -18,9 +18,9 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import static com.google.common.base.Preconditions.checkNotNull;
 import java.util.List;
 import java.util.Map;
+import java.util.Objects;
 
 /**
  * Consumer statistics.
@@ -97,7 +97,7 @@ public class ConsumerStats {
     private StringBuilder stringBuffer = new StringBuilder();
 
     public ConsumerStats add(ConsumerStats stats) {
-        checkNotNull(stats);
+        Objects.requireNonNull(stats);
         this.msgRateOut += stats.msgRateOut;
         this.msgThroughputOut += stats.msgThroughputOut;
         this.bytesOutCounter += stats.bytesOutCounter;
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/DelayedDeliveryPolicies.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/DelayedDeliveryPolicies.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/DelayedDeliveryPolicies.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/DelayedDeliveryPolicies.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/DispatchRate.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/DispatchRate.java
similarity index 87%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/DispatchRate.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/DispatchRate.java
index 002cdac..e9f5f8e 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/DispatchRate.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/DispatchRate.java
@@ -18,12 +18,13 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.base.MoreObjects;
 import java.util.Objects;
+import lombok.ToString;
 
 /**
  * Dispatch rate.
  */
+@ToString
 public class DispatchRate {
 
     public int dispatchThrottlingRateInMsg = -1;
@@ -68,13 +69,4 @@ public class DispatchRate {
         }
         return false;
     }
-
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this)
-                .add("dispatchThrottlingRateInMsg", dispatchThrottlingRateInMsg)
-                .add("dispatchThrottlingRateInByte", dispatchThrottlingRateInByte)
-                .add("ratePeriodInSecond", ratePeriodInSecond).toString();
-    }
-
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/ErrorData.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ErrorData.java
similarity index 100%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/ErrorData.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ErrorData.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/ExceptionInformation.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ExceptionInformation.java
similarity index 100%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/ExceptionInformation.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ExceptionInformation.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionPendingAckStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FailureDomain.java
similarity index 87%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionPendingAckStats.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FailureDomain.java
index fb1b9c7..b92717c 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionPendingAckStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FailureDomain.java
@@ -18,8 +18,10 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-public class TransactionPendingAckStats {
+import java.util.Set;
 
-    /** The state of this pending ack. */
-    public String state;
+public interface FailureDomain {
+    Set<String> getBrokers();
+
+    void setBrokers(Set<String> brokers);
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionInPendingAckStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionInstanceStats.java
similarity index 80%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionInPendingAckStats.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionInstanceStats.java
index 44beada..0371447 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/TransactionInPendingAckStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionInstanceStats.java
@@ -18,13 +18,12 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import lombok.Data;
+public interface FunctionInstanceStats {
+    int getInstanceId();
 
-import java.util.List;
+    FunctionInstanceStatsData getMetrics();
 
-@Data
-public class TransactionInPendingAckStats {
+    void setInstanceId(int instanceId);
 
-    /** The position of this transaction cumulative ack. */
-    public String cumulativeAckPosition;
+    void setMetrics(FunctionInstanceStatsData metrics);
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionInstanceStatsData.java
similarity index 69%
copy from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
copy to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionInstanceStatsData.java
index 5d11372..5d8d558 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionInstanceStatsData.java
@@ -18,24 +18,16 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import lombok.AllArgsConstructor;
-import lombok.Data;
-import lombok.NoArgsConstructor;
-import lombok.ToString;
+public interface FunctionInstanceStatsData extends FunctionInstanceStatsDataBase {
+    FunctionInstanceStatsDataBase getOneMin();
 
-import java.util.List;
+    Long getLastInvocation();
 
-/**
- * Raw bookies information.
- */
-@Data
-@NoArgsConstructor
-@AllArgsConstructor
-@ToString
-public class BookiesClusterInfo {
+    java.util.Map<String, Double> getUserMetrics();
 
-    private static final long serialVersionUID = 0L;
+    void setOneMin(FunctionInstanceStatsDataBase oneMin);
 
-    private List<RawBookieInfo> bookies;
+    void setLastInvocation(Long lastInvocation);
 
+    void setUserMetrics(java.util.Map<String, Double> userMetrics);
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AuthAction.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionInstanceStatsDataBase.java
similarity index 62%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AuthAction.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionInstanceStatsDataBase.java
index 9a1b36c..578e19e 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/AuthAction.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionInstanceStatsDataBase.java
@@ -18,25 +18,24 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-/**
- * Authorization action for Pulsar policies.
- */
-public enum AuthAction {
-    /** Permission to produce/publish messages. */
-    produce,
+public interface FunctionInstanceStatsDataBase {
+    long getReceivedTotal();
+
+    long getProcessedSuccessfullyTotal();
+
+    long getSystemExceptionsTotal();
+
+    long getUserExceptionsTotal();
+
+    Double getAvgProcessLatency();
 
-    /** Permission to consume messages. */
-    consume,
+    void setReceivedTotal(long receivedTotal);
 
-    /** Permissions for functions ops. **/
-    functions,
+    void setProcessedSuccessfullyTotal(long processedSuccessfullyTotal);
 
-    /** Permissions for sources ops. **/
-    sources,
+    void setSystemExceptionsTotal(long systemExceptionsTotal);
 
-    /** Permissions for sinks ops. **/
-    sinks,
+    void setUserExceptionsTotal(long userExceptionsTotal);
 
-    /** Permissions for packages ops. **/
-    packages
+    void setAvgProcessLatency(Double avgProcessLatency);
 }
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionStats.java
new file mode 100644
index 0000000..bf07d53
--- /dev/null
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionStats.java
@@ -0,0 +1,59 @@
+/**
+ * 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.pulsar.common.policies.data;
+
+import java.util.List;
+
+public interface FunctionStats {
+    void addInstance(FunctionInstanceStats functionInstanceStats);
+
+    FunctionStats calculateOverall();
+
+    long getReceivedTotal();
+
+    long getProcessedSuccessfullyTotal();
+
+    long getSystemExceptionsTotal();
+
+    long getUserExceptionsTotal();
+
+    Double getAvgProcessLatency();
+
+    FunctionInstanceStatsDataBase getOneMin();
+
+    Long getLastInvocation();
+
+    List<FunctionInstanceStats> getInstances();
+
+    void setReceivedTotal(long receivedTotal);
+
+    void setProcessedSuccessfullyTotal(long processedSuccessfullyTotal);
+
+    void setSystemExceptionsTotal(long systemExceptionsTotal);
+
+    void setUserExceptionsTotal(long userExceptionsTotal);
+
+    void setAvgProcessLatency(Double avgProcessLatency);
+
+    void setOneMin(FunctionInstanceStatsDataBase oneMin);
+
+    void setLastInvocation(Long lastInvocation);
+
+    void setInstances(List<FunctionInstanceStats> instances);
+}
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/FunctionStatus.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionStatus.java
similarity index 89%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/FunctionStatus.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionStatus.java
index 30b50b8..8f4f7e2 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/FunctionStatus.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/FunctionStatus.java
@@ -18,11 +18,9 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import java.io.IOException;
 import java.util.LinkedList;
 import java.util.List;
 import lombok.Data;
-import org.apache.pulsar.common.util.ObjectMapperFactory;
 
 /**
  * Data lass containing status of Pulsar Function.
@@ -79,7 +77,4 @@ public class FunctionStatus {
         instances.add(functionInstanceStatus);
     }
 
-    public static FunctionStatus decode(String json) throws IOException {
-        return ObjectMapperFactory.getThreadLocal().readValue(json, FunctionStatus.class);
-    }
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/InactiveTopicDeleteMode.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/InactiveTopicDeleteMode.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/InactiveTopicDeleteMode.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/InactiveTopicDeleteMode.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/InactiveTopicPolicies.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/InactiveTopicPolicies.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/InactiveTopicPolicies.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/InactiveTopicPolicies.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/ManagedLedgerInternalStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ManagedLedgerInternalStats.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/ManagedLedgerInternalStats.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/ManagedLedgerInternalStats.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NamespaceIsolationData.java
similarity index 67%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NamespaceIsolationData.java
index 5d11372..6feb0d7 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/BookiesClusterInfo.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NamespaceIsolationData.java
@@ -18,24 +18,24 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import lombok.AllArgsConstructor;
-import lombok.Data;
-import lombok.NoArgsConstructor;
-import lombok.ToString;
-
 import java.util.List;
 
-/**
- * Raw bookies information.
- */
-@Data
-@NoArgsConstructor
-@AllArgsConstructor
-@ToString
-public class BookiesClusterInfo {
+public interface NamespaceIsolationData {
+
+    List<String> getNamespaces();
+
+    List<String> getPrimary();
+
+    List<String> getSecondary();
+
+    AutoFailoverPolicyData getAuto_failover_policy();
+
+    void setNamespaces(List<String> namespaces);
+
+    void setPrimary(List<String> primary);
 
-    private static final long serialVersionUID = 0L;
+    void setSecondary(List<String> secondary);
 
-    private List<RawBookieInfo> bookies;
+    void setAuto_failover_policy(AutoFailoverPolicyData autoFailoverPolicyData);
 
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NamespaceOwnershipStatus.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NamespaceOwnershipStatus.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NamespaceOwnershipStatus.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NamespaceOwnershipStatus.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentPublisherStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentPublisherStats.java
similarity index 93%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentPublisherStats.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentPublisherStats.java
index f1602a4..74e1752 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentPublisherStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentPublisherStats.java
@@ -18,7 +18,7 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import static com.google.common.base.Preconditions.checkNotNull;
+import java.util.Objects;
 
 /**
  * Non-persistent publisher statistics.
@@ -31,7 +31,7 @@ public class NonPersistentPublisherStats extends PublisherStats {
     public double msgDropRate;
 
     public NonPersistentPublisherStats add(NonPersistentPublisherStats stats) {
-        checkNotNull(stats);
+        Objects.requireNonNull(stats);
         super.add(stats);
         this.msgDropRate += stats.msgDropRate;
         return this;
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentReplicatorStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentReplicatorStats.java
similarity index 93%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentReplicatorStats.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentReplicatorStats.java
index 906afde..d27813c 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentReplicatorStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentReplicatorStats.java
@@ -18,7 +18,7 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import static com.google.common.base.Preconditions.checkNotNull;
+import java.util.Objects;
 
 /**
  * Statistics for a non-persistent replicator.
@@ -31,7 +31,7 @@ public class NonPersistentReplicatorStats extends ReplicatorStats {
     public double msgDropRate;
 
     public NonPersistentReplicatorStats add(NonPersistentReplicatorStats stats) {
-        checkNotNull(stats);
+        Objects.requireNonNull(stats);
         super.add(stats);
         this.msgDropRate += stats.msgDropRate;
         return this;
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentSubscriptionStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentSubscriptionStats.java
similarity index 94%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentSubscriptionStats.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentSubscriptionStats.java
index 896e677..8d06d41 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentSubscriptionStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentSubscriptionStats.java
@@ -18,7 +18,7 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import static com.google.common.base.Preconditions.checkNotNull;
+import java.util.Objects;
 
 /**
  * Statistics for subscription to non-persistent topics.
@@ -39,7 +39,7 @@ public class NonPersistentSubscriptionStats extends SubscriptionStats {
     // if the stats are added for the 1st time, we will need to make a copy of these stats and add it to the current
     // stats
     public NonPersistentSubscriptionStats add(NonPersistentSubscriptionStats stats) {
-        checkNotNull(stats);
+        Objects.requireNonNull(stats);
         super.add(stats);
         this.msgDropRate += stats.msgDropRate;
         return this;
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentTopicStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentTopicStats.java
similarity index 88%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentTopicStats.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentTopicStats.java
index debd1a7..fd06101 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentTopicStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/NonPersistentTopicStats.java
@@ -18,11 +18,12 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import static com.google.common.base.Preconditions.checkNotNull;
-import com.google.common.collect.Lists;
-import com.google.common.collect.Maps;
+import java.util.ArrayList;
+import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
+import java.util.Objects;
+import java.util.TreeMap;
 
 /**
  * Statistics for a non-persistent topic.
@@ -45,9 +46,9 @@ public class NonPersistentTopicStats extends TopicStats {
     public Map<String, NonPersistentReplicatorStats> replication;
 
     public NonPersistentTopicStats() {
-        this.publishers = Lists.newArrayList();
-        this.subscriptions = Maps.newHashMap();
-        this.replication = Maps.newTreeMap();
+        this.publishers = new ArrayList<>();
+        this.subscriptions = new HashMap<>();
+        this.replication = new TreeMap<>();
     }
 
     public void reset() {
@@ -58,7 +59,7 @@ public class NonPersistentTopicStats extends TopicStats {
     // if the stats are added for the 1st time, we will need to make a copy of these stats and add it to the current
     // stats.
     public NonPersistentTopicStats add(NonPersistentTopicStats stats) {
-        checkNotNull(stats);
+        Objects.requireNonNull(stats);
         super.add(stats);
         this.msgDropRate += stats.msgDropRate;
         return this;
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/OffloadPolicies.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/OffloadPolicies.java
new file mode 100644
index 0000000..002e6f9
--- /dev/null
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/OffloadPolicies.java
@@ -0,0 +1,133 @@
+/**
+ * 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.pulsar.common.policies.data;
+
+public interface OffloadPolicies {
+    String getOffloadersDirectory();
+
+    String getManagedLedgerOffloadDriver();
+
+    Integer getManagedLedgerOffloadMaxThreads();
+
+    Integer getManagedLedgerOffloadPrefetchRounds();
+
+    Long getManagedLedgerOffloadThresholdInBytes();
+
+    Long getManagedLedgerOffloadDeletionLagInMillis();
+
+    OffloadedReadPriority getManagedLedgerOffloadedReadPriority();
+
+    String getS3ManagedLedgerOffloadRegion();
+
+    String getS3ManagedLedgerOffloadBucket();
+
+    String getS3ManagedLedgerOffloadServiceEndpoint();
+
+    Integer getS3ManagedLedgerOffloadMaxBlockSizeInBytes();
+
+    Integer getS3ManagedLedgerOffloadReadBufferSizeInBytes();
+
+    String getS3ManagedLedgerOffloadCredentialId();
+
+    String getS3ManagedLedgerOffloadCredentialSecret();
+
+    String getS3ManagedLedgerOffloadRole();
+
+    String getS3ManagedLedgerOffloadRoleSessionName();
+
+    String getGcsManagedLedgerOffloadRegion();
+
+    String getGcsManagedLedgerOffloadBucket();
+
+    Integer getGcsManagedLedgerOffloadMaxBlockSizeInBytes();
+
+    Integer getGcsManagedLedgerOffloadReadBufferSizeInBytes();
+
+    String getGcsManagedLedgerOffloadServiceAccountKeyFile();
+
+    String getFileSystemProfilePath();
+
+    String getFileSystemURI();
+
+    String getManagedLedgerOffloadBucket();
+
+    String getManagedLedgerOffloadRegion();
+
+    String getManagedLedgerOffloadServiceEndpoint();
+
+    Integer getManagedLedgerOffloadMaxBlockSizeInBytes();
+
+    Integer getManagedLedgerOffloadReadBufferSizeInBytes();
+
+    void setOffloadersDirectory(String offloadersDirectory);
+
+    void setManagedLedgerOffloadDriver(String managedLedgerOffloadDriver);
+
+    void setManagedLedgerOffloadMaxThreads(Integer managedLedgerOffloadMaxThreads);
+
+    void setManagedLedgerOffloadPrefetchRounds(Integer managedLedgerOffloadPrefetchRounds);
+
+    void setManagedLedgerOffloadThresholdInBytes(Long managedLedgerOffloadThresholdInBytes);
+
+    void setManagedLedgerOffloadDeletionLagInMillis(Long managedLedgerOffloadDeletionLagInMillis);
+
+    void setManagedLedgerOffloadedReadPriority(OffloadedReadPriority managedLedgerOffloadedReadPriority);
+
+    void setS3ManagedLedgerOffloadRegion(String s3ManagedLedgerOffloadRegion);
+
+    void setS3ManagedLedgerOffloadBucket(String s3ManagedLedgerOffloadBucket);
+
+    void setS3ManagedLedgerOffloadServiceEndpoint(String s3ManagedLedgerOffloadServiceEndpoint);
+
+    void setS3ManagedLedgerOffloadMaxBlockSizeInBytes(Integer s3ManagedLedgerOffloadMaxBlockSizeInBytes);
+
+    void setS3ManagedLedgerOffloadReadBufferSizeInBytes(Integer s3ManagedLedgerOffloadReadBufferSizeInBytes);
+
+    void setS3ManagedLedgerOffloadCredentialId(String s3ManagedLedgerOffloadCredentialId);
+
+    void setS3ManagedLedgerOffloadCredentialSecret(String s3ManagedLedgerOffloadCredentialSecret);
+
+    void setS3ManagedLedgerOffloadRole(String s3ManagedLedgerOffloadRole);
+
+    void setS3ManagedLedgerOffloadRoleSessionName(String s3ManagedLedgerOffloadRoleSessionName);
+
+    void setGcsManagedLedgerOffloadRegion(String gcsManagedLedgerOffloadRegion);
+
+    void setGcsManagedLedgerOffloadBucket(String gcsManagedLedgerOffloadBucket);
+
+    void setGcsManagedLedgerOffloadMaxBlockSizeInBytes(Integer gcsManagedLedgerOffloadMaxBlockSizeInBytes);
+
+    void setGcsManagedLedgerOffloadReadBufferSizeInBytes(Integer gcsManagedLedgerOffloadReadBufferSizeInBytes);
+
+    void setGcsManagedLedgerOffloadServiceAccountKeyFile(String gcsManagedLedgerOffloadServiceAccountKeyFile);
+
+    void setFileSystemProfilePath(String fileSystemProfilePath);
+
+    void setFileSystemURI(String fileSystemURI);
+
+    void setManagedLedgerOffloadBucket(String managedLedgerOffloadBucket);
+
+    void setManagedLedgerOffloadRegion(String managedLedgerOffloadRegion);
+
+    void setManagedLedgerOffloadServiceEndpoint(String managedLedgerOffloadServiceEndpoint);
+
+    void setManagedLedgerOffloadMaxBlockSizeInBytes(Integer managedLedgerOffloadMaxBlockSizeInBytes);
+
+    void setManagedLedgerOffloadReadBufferSizeInBytes(Integer managedLedgerOffloadReadBufferSizeInBytes);
+}
diff --git a/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/OffloadedReadPriority.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/OffloadedReadPriority.java
new file mode 100644
index 0000000..245ec60
--- /dev/null
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/OffloadedReadPriority.java
@@ -0,0 +1,72 @@
+/**
+ * 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.pulsar.common.policies.data;
+
+import java.util.Arrays;
+import java.util.stream.Collectors;
+import org.apache.pulsar.common.classification.InterfaceAudience;
+import org.apache.pulsar.common.classification.InterfaceStability;
+
+@InterfaceAudience.Public
+@InterfaceStability.Stable
+public enum OffloadedReadPriority {
+    /**
+     * For offloaded messages, readers will try to read from bookkeeper at first,
+     * if messages not exist at bookkeeper then read from offloaded storage.
+     */
+    BOOKKEEPER_FIRST("bookkeeper-first"),
+    /**
+     * For offloaded messages, readers will try to read from offloaded storage first,
+     * even they are still exist in bookkeeper.
+     */
+    TIERED_STORAGE_FIRST("tiered-storage-first");
+
+    private final String value;
+
+    OffloadedReadPriority(String value) {
+        this.value = value;
+    }
+
+    public boolean equalsName(String otherName) {
+        return value.equals(otherName);
+    }
+
+    @Override
+    public String toString() {
+        return value;
+    }
+
+    public static OffloadedReadPriority fromString(String str) {
+        for (OffloadedReadPriority value : OffloadedReadPriority.values()) {
+            if (value.value.equals(str)) {
+                return value;
+            }
+        }
+
+        throw new IllegalArgumentException("--offloadedReadPriority parameter must be one of "
+                + Arrays.stream(OffloadedReadPriority.values())
+                .map(OffloadedReadPriority::toString)
+                .collect(Collectors.joining(","))
+                + " but got: " + str);
+    }
+
+    public String getValue() {
+        return value;
+    }
+}
\ No newline at end of file
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicInternalStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicInternalStats.java
similarity index 94%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicInternalStats.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicInternalStats.java
index d20e03f..dad2985 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicInternalStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicInternalStats.java
@@ -18,7 +18,7 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.collect.Maps;
+import java.util.HashMap;
 import java.util.Map;
 import org.apache.pulsar.common.partition.PartitionedTopicMetadata;
 
@@ -34,7 +34,7 @@ public class PartitionedTopicInternalStats {
     public PartitionedTopicInternalStats() {
         super();
         metadata = new PartitionedTopicMetadata();
-        partitions = Maps.newHashMap();
+        partitions = new HashMap<>();
     }
 
     public PartitionedTopicInternalStats(PartitionedTopicMetadata metadata) {
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicStats.java
similarity index 94%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicStats.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicStats.java
index cce7828..699fe6e 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PartitionedTopicStats.java
@@ -18,7 +18,7 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.collect.Maps;
+import java.util.HashMap;
 import java.util.Map;
 import org.apache.pulsar.common.partition.PartitionedTopicMetadata;
 
@@ -34,7 +34,7 @@ public class PartitionedTopicStats extends TopicStats {
     public PartitionedTopicStats() {
         super();
         metadata = new PartitionedTopicMetadata();
-        partitions = Maps.newHashMap();
+        partitions = new HashMap<>();
     }
 
     public PartitionedTopicStats(PartitionedTopicMetadata metadata) {
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PersistencePolicies.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PersistencePolicies.java
similarity index 89%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PersistencePolicies.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PersistencePolicies.java
index 466b338..3456950 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PersistencePolicies.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PersistencePolicies.java
@@ -18,12 +18,13 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.base.MoreObjects;
 import java.util.Objects;
+import lombok.ToString;
 
 /**
  * Configuration of bookkeeper persistence policies.
  */
+@ToString
 public class PersistencePolicies {
     private int bookkeeperEnsemble;
     private int bookkeeperWriteQuorum;
@@ -75,10 +76,4 @@ public class PersistencePolicies {
 
         return false;
     }
-
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this).add("e", bookkeeperEnsemble).add("w", bookkeeperWriteQuorum)
-                .add("a", bookkeeperAckQuorum).add("ml-md-rate", managedLedgerMaxMarkDeleteRate).toString();
-    }
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PersistentTopicInternalStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PersistentTopicInternalStats.java
similarity index 100%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PersistentTopicInternalStats.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PersistentTopicInternalStats.java
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/Policies.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/Policies.java
similarity index 63%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/Policies.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/Policies.java
index 9c381ea..86c0b2b 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/Policies.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/Policies.java
@@ -18,38 +18,32 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.base.MoreObjects;
-import com.google.common.collect.Lists;
-import com.google.common.collect.Maps;
-import com.google.common.collect.Sets;
-
-import java.util.List;
+import java.util.HashMap;
+import java.util.HashSet;
 import java.util.Map;
 import java.util.Objects;
 import java.util.Set;
-import javax.ws.rs.core.Response.Status;
-
-import org.apache.pulsar.common.api.proto.CommandSubscribe.SubType;
-import org.apache.pulsar.common.util.RestException;
+import lombok.ToString;
 
 /**
  * Definition of Pulsar policies.
  */
+@ToString
 public class Policies {
 
     @SuppressWarnings("checkstyle:MemberName")
     public final AuthPolicies auth_policies = new AuthPolicies();
     @SuppressWarnings("checkstyle:MemberName")
-    public Set<String> replication_clusters = Sets.newHashSet();
+    public Set<String> replication_clusters = new HashSet<>();
     public BundlesData bundles;
     @SuppressWarnings("checkstyle:MemberName")
-    public Map<BacklogQuota.BacklogQuotaType, BacklogQuota> backlog_quota_map = Maps.newHashMap();
+    public Map<BacklogQuota.BacklogQuotaType, BacklogQuota> backlog_quota_map = new HashMap<>();
     @Deprecated
-    public Map<String, DispatchRate> clusterDispatchRate = Maps.newHashMap();
-    public Map<String, DispatchRate> topicDispatchRate = Maps.newHashMap();
-    public Map<String, DispatchRate> subscriptionDispatchRate = Maps.newHashMap();
-    public Map<String, DispatchRate> replicatorDispatchRate = Maps.newHashMap();
-    public Map<String, SubscribeRate> clusterSubscribeRate = Maps.newHashMap();
+    public Map<String, DispatchRate> clusterDispatchRate = new HashMap<>();
+    public Map<String, DispatchRate> topicDispatchRate = new HashMap<>();
+    public Map<String, DispatchRate> subscriptionDispatchRate = new HashMap<>();
+    public Map<String, DispatchRate> replicatorDispatchRate = new HashMap<>();
+    public Map<String, SubscribeRate> clusterSubscribeRate = new HashMap<>();
     public PersistencePolicies persistence = null;
 
     // If set, it will override the broker settings for enabling deduplication
@@ -58,10 +52,10 @@ public class Policies {
     public AutoTopicCreationOverride autoTopicCreationOverride = null;
     // If set, it will override the broker settings for allowing auto subscription creation
     public AutoSubscriptionCreationOverride autoSubscriptionCreationOverride = null;
-    public Map<String, PublishRate> publishMaxMessageRate = Maps.newHashMap();
+    public Map<String, PublishRate> publishMaxMessageRate = new HashMap<>();
 
     @SuppressWarnings("checkstyle:MemberName")
-    public Map<String, Integer> latency_stats_sample_rate = Maps.newHashMap();
+    public Map<String, Integer> latency_stats_sample_rate = new HashMap<>();
     @SuppressWarnings("checkstyle:MemberName")
     public Integer message_ttl_in_seconds = null;
     @SuppressWarnings("checkstyle:MemberName")
@@ -122,10 +116,12 @@ public class Policies {
 
     public Integer deduplicationSnapshotIntervalSeconds = null;
 
-    public Set<SubType> subscription_types_enabled = Sets.newHashSet();
+    @SuppressWarnings("checkstyle:MemberName")
+    public Set<String> subscription_types_enabled = new HashSet<>();
+
+    public Map<String, String> properties = new HashMap<>();
 
-    public Map<String, String> properties = Maps.newHashMap();
-    @SuppressWarnings("checkstype:MemberName")
+    @SuppressWarnings("checkstyle:MemberName")
     public String resource_group_name = null;
 
     @Override
@@ -183,7 +179,8 @@ public class Policies {
                     && Objects.equals(max_producers_per_topic, other.max_producers_per_topic)
                     && Objects.equals(max_consumers_per_topic, other.max_consumers_per_topic)
                     && Objects.equals(max_unacked_messages_per_consumer, other.max_unacked_messages_per_consumer)
-                    && Objects.equals(max_unacked_messages_per_subscription, other.max_unacked_messages_per_subscription)
+                    && Objects.equals(max_unacked_messages_per_subscription,
+                        other.max_unacked_messages_per_subscription)
                     && Objects.equals(max_consumers_per_subscription, other.max_consumers_per_subscription)
                     && Objects.equals(compaction_threshold, other.compaction_threshold)
                     && offload_threshold == other.offload_threshold
@@ -201,85 +198,5 @@ public class Policies {
         return false;
     }
 
-    public static BundlesData defaultBundle() {
-        BundlesData bundle = new BundlesData(1);
-        List<String> boundaries = Lists.newArrayList();
-        boundaries.add(FIRST_BOUNDARY);
-        boundaries.add(LAST_BOUNDARY);
-        bundle.setBoundaries(boundaries);
-        return bundle;
-    }
-
-    public static void setStorageQuota(Policies polices, BacklogQuota quota) {
-        if (polices == null) {
-            return;
-        }
-        polices.backlog_quota_map.put(BacklogQuota.BacklogQuotaType.destination_storage, quota);
-    }
-
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this).add("auth_policies", auth_policies)
-                .add("replication_clusters", replication_clusters)
-                .add("bundles", bundles)
-                .add("backlog_quota_map", backlog_quota_map)
-                .add("persistence", persistence)
-                .add("deduplicationEnabled", deduplicationEnabled)
-                .add("autoTopicCreationOverride", autoTopicCreationOverride)
-                .add("autoSubscriptionCreationOverride", autoSubscriptionCreationOverride)
-                .add("clusterDispatchRate", clusterDispatchRate)
-                .add("topicDispatchRate", topicDispatchRate)
-                .add("subscriptionDispatchRate", subscriptionDispatchRate)
-                .add("replicatorDispatchRate", replicatorDispatchRate)
-                .add("clusterSubscribeRate", clusterSubscribeRate)
-                .add("publishMaxMessageRate", publishMaxMessageRate)
-                .add("latency_stats_sample_rate", latency_stats_sample_rate)
-                .add("message_ttl_in_seconds", message_ttl_in_seconds)
-                .add("subscription_expiration_time_minutes", subscription_expiration_time_minutes)
-                .add("retention_policies", retention_policies)
-                .add("deleted", deleted)
-                .add("encryption_required", encryption_required)
-                .add("delayed_delivery_policies", delayed_delivery_policies)
-                .add("inactive_topic_policies", inactive_topic_policies)
-                .add("subscription_auth_mode", subscription_auth_mode)
-                .add("max_producers_per_topic", max_producers_per_topic)
-                .add("max_consumers_per_topic", max_consumers_per_topic)
-                .add("max_consumers_per_subscription", max_consumers_per_topic)
-                .add("max_unacked_messages_per_consumer", max_unacked_messages_per_consumer)
-                .add("max_unacked_messages_per_subscription", max_unacked_messages_per_subscription)
-                .add("compaction_threshold", compaction_threshold)
-                .add("offload_threshold", offload_threshold)
-                .add("offload_deletion_lag_ms", offload_deletion_lag_ms)
-                .add("schema_auto_update_compatibility_strategy", schema_auto_update_compatibility_strategy)
-                .add("schema_validation_enforced", schema_validation_enforced)
-                .add("schema_compatibility_Strategy", schema_compatibility_strategy)
-                .add("is_allow_auto_update_Schema", is_allow_auto_update_schema)
-                .add("offload_policies", offload_policies)
-                .add("subscription_types_enabled", subscription_types_enabled)
-                .add("properties", properties)
-                .add("resource_group_name", resource_group_name).toString();
-    }
-
-    private static final long MAX_BUNDLES = ((long) 1) << 32;
 
-    public static BundlesData getBundles(int numBundles) {
-        if (numBundles <= 0) {
-            throw new RestException(Status.BAD_REQUEST,
-                "Invalid number of bundles. Number of numbles has to be in the range of (0, 2^32].");
-        }
-        Long maxVal = MAX_BUNDLES;
-        Long segSize = maxVal / numBundles;
-        List<String> partitions = Lists.newArrayList();
-        partitions.add(String.format("0x%08x", 0L));
-        Long curPartition = segSize;
-        for (int i = 0; i < numBundles; i++) {
-            if (i != numBundles - 1) {
-                partitions.add(String.format("0x%08x", curPartition));
-            } else {
-                partitions.add(String.format("0x%08x", maxVal - 1));
-            }
-            curPartition += segSize;
-        }
-        return new BundlesData(partitions);
-    }
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PublishRate.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PublishRate.java
similarity index 86%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PublishRate.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PublishRate.java
index 095e4e9..79a3cd5 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PublishRate.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PublishRate.java
@@ -18,12 +18,13 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import com.google.common.base.MoreObjects;
 import java.util.Objects;
+import lombok.ToString;
 
 /**
  * Publish-rate to manage publish throttling.
  */
+@ToString
 public class PublishRate {
 
     public int publishThrottlingRateInMsg = -1;
@@ -56,10 +57,4 @@ public class PublishRate {
         return false;
     }
 
-    @Override
-    public String toString() {
-        return MoreObjects.toStringHelper(this).add("publishThrottlingRateInMsg", publishThrottlingRateInMsg)
-                .add("publishThrottlingRateInByte", publishThrottlingRateInByte).toString();
-    }
-
 }
diff --git a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PublisherStats.java b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PublisherStats.java
similarity index 98%
rename from pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PublisherStats.java
rename to pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PublisherStats.java
index d228f21..e3732fa 100644
--- a/pulsar-common/src/main/java/org/apache/pulsar/common/policies/data/PublisherStats.java
+++ b/pulsar-client-admin-api/src/main/java/org/apache/pulsar/common/policies/data/PublisherStats.java
@@ -18,7 +18,6 @@
  */
 package org.apache.pulsar.common.policies.data;
 
-import static com.google.common.base.Preconditions.checkNotNull;
 import java.util.Map;
... 7513 lines suppressed ...