dubbo.apache.org/dubbo-go/v3@v3.1.1/metadata/service/remote/service.go (about)

     1  /*
     2   * Licensed to the Apache Software Foundation (ASF) under one or more
     3   * contributor license agreements.  See the NOTICE file distributed with
     4   * this work for additional information regarding copyright ownership.
     5   * The ASF licenses this file to You under the Apache License, Version 2.0
     6   * (the "License"); you may not use this file except in compliance with
     7   * the License.  You may obtain a copy of the License at
     8   *
     9   *     http://www.apache.org/licenses/LICENSE-2.0
    10   *
    11   * Unless required by applicable law or agreed to in writing, software
    12   * distributed under the License is distributed on an "AS IS" BASIS,
    13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    14   * See the License for the specific language governing permissions and
    15   * limitations under the License.
    16   */
    17  
    18  package remote
    19  
    20  import (
    21  	"sync"
    22  )
    23  
    24  import (
    25  	"github.com/dubbogo/gost/log/logger"
    26  
    27  	"go.uber.org/atomic"
    28  )
    29  
    30  import (
    31  	"dubbo.apache.org/dubbo-go/v3/common"
    32  	"dubbo.apache.org/dubbo-go/v3/common/constant"
    33  	"dubbo.apache.org/dubbo-go/v3/common/extension"
    34  	"dubbo.apache.org/dubbo-go/v3/metadata/definition"
    35  	"dubbo.apache.org/dubbo-go/v3/metadata/identifier"
    36  	"dubbo.apache.org/dubbo-go/v3/metadata/report/delegate"
    37  	"dubbo.apache.org/dubbo-go/v3/metadata/service"
    38  	"dubbo.apache.org/dubbo-go/v3/metadata/service/local"
    39  	"dubbo.apache.org/dubbo-go/v3/registry"
    40  )
    41  
    42  type MetadataService struct {
    43  	*local.MetadataService
    44  	exportedRevision   atomic.String
    45  	subscribedRevision atomic.String
    46  	delegateReport     *delegate.MetadataReport
    47  }
    48  
    49  var (
    50  	metadataServiceOnce           sync.Once
    51  	remoteMetadataServiceInstance service.RemoteMetadataService
    52  )
    53  
    54  func init() {
    55  	extension.SetRemoteMetadataService(GetRemoteMetadataService)
    56  }
    57  
    58  // GetRemoteMetadataService will create a new remote MetadataService instance
    59  func GetRemoteMetadataService() (service.RemoteMetadataService, error) {
    60  	var err error
    61  	metadataServiceOnce.Do(func() {
    62  		var mr *delegate.MetadataReport
    63  		mr, err = delegate.NewMetadataReport()
    64  		if err != nil {
    65  			return
    66  		}
    67  		// it will never return error
    68  		inms, _ := local.GetLocalMetadataService()
    69  		remoteMetadataServiceInstance = &MetadataService{
    70  			// todo serviceName
    71  			//BaseMetadataService:     service.NewBaseMetadataService(""),
    72  			MetadataService: inms.(*local.MetadataService),
    73  			delegateReport:  mr,
    74  		}
    75  	})
    76  	return remoteMetadataServiceInstance, err
    77  }
    78  
    79  // PublishMetadata publishes the metadata info of @service to remote metadata center
    80  func (s *MetadataService) PublishMetadata(service string) {
    81  	info, err := s.MetadataService.GetMetadataInfo("")
    82  	if err != nil {
    83  		logger.Errorf("GetMetadataInfo error[%v]", err)
    84  		return
    85  	}
    86  	if info.HasReported() {
    87  		return
    88  	}
    89  	id := identifier.NewSubscriberMetadataIdentifier(service, info.CalAndGetRevision())
    90  	err = s.delegateReport.PublishAppMetadata(id, info)
    91  	if err != nil {
    92  		logger.Errorf("Publishing metadata to error[%v]", err)
    93  		return
    94  	}
    95  	info.MarkReported()
    96  }
    97  
    98  // GetMetadata get the medata info of service from report
    99  func (s *MetadataService) GetMetadata(instance registry.ServiceInstance) (*common.MetadataInfo, error) {
   100  	revision := instance.GetMetadata()[constant.ExportedServicesRevisionPropertyName]
   101  	id := identifier.NewSubscriberMetadataIdentifier(instance.GetServiceName(), revision)
   102  	return s.delegateReport.GetAppMetadata(id)
   103  }
   104  
   105  // PublishServiceDefinition will call remote metadata's StoreProviderMetadata to store url info and service definition
   106  func (s *MetadataService) PublishServiceDefinition(url *common.URL) error {
   107  	interfaceName := url.GetParam(constant.InterfaceKey, "")
   108  	isGeneric := url.GetParamBool(constant.GenericKey, false)
   109  	if common.RoleType(common.PROVIDER).Role() == url.GetParam(constant.SideKey, "") {
   110  		if len(interfaceName) > 0 && !isGeneric {
   111  			sv := common.ServiceMap.GetServiceByServiceKey(url.Protocol, url.ServiceKey())
   112  			sd := definition.BuildFullDefinition(*sv, url)
   113  			id := &identifier.MetadataIdentifier{
   114  				BaseMetadataIdentifier: identifier.BaseMetadataIdentifier{
   115  					ServiceInterface: interfaceName,
   116  					Version:          url.GetParam(constant.VersionKey, ""),
   117  					Group:            url.GetParam(constant.GroupKey, constant.Dubbo),
   118  					Side:             url.GetParam(constant.SideKey, constant.ProviderProtocol),
   119  				},
   120  			}
   121  			s.delegateReport.StoreProviderMetadata(id, sd)
   122  			return nil
   123  		}
   124  		logger.Errorf("publishProvider interfaceName is empty . providerUrl:%v ", url)
   125  	} else {
   126  		params := make(map[string]string, len(url.GetParams()))
   127  		url.RangeParams(func(key, value string) bool {
   128  			params[key] = value
   129  			return true
   130  		})
   131  		id := &identifier.MetadataIdentifier{
   132  			BaseMetadataIdentifier: identifier.BaseMetadataIdentifier{
   133  				ServiceInterface: interfaceName,
   134  				Version:          url.GetParam(constant.VersionKey, ""),
   135  				Group:            url.GetParam(constant.GroupKey, constant.Dubbo),
   136  				Side:             url.GetParam(constant.SideKey, "consumer"),
   137  			},
   138  		}
   139  		s.delegateReport.StoreConsumerMetadata(id, params)
   140  		return nil
   141  	}
   142  
   143  	return nil
   144  }