使用KubeFATE部署一个多成员参与的联邦学习网络 - FederatedAI/KubeFATE GitHub Wiki

联邦学习是一种保护数据隐私的机器学习框架,能有效帮助多个机构在满足用户隐私保护、数据安全和政府法规的要求下,进行数据使用和机器学习建模。发掘了数据的价值又保护了数据隐私和安全。

遇到问题

在联邦学习应用部署的时候,需要多个机构共同参与,共同加入联邦网络组织,然而参与方太多就难以管理。

传统模式可以使用简单的各个机构之间互相链接,当随着联邦网络组织成员越来越多,机构之间的配置信息管理就变得非常复杂。

解决办法

使用exchange部署模式可以简单方便的应对多成员组织机构的网络建设,成员之间通过核心exchange来发现彼此,管理联邦学习网络变得非常简单。

KubeFATE对exchange的支持

KubeFATE v1.6.0支持了Spark和Eggroll计算引擎的exchange部署模式。

联邦学习组织搭建

组织架构

使用KubeFATE部署一个以exchange为中央节点的联邦学习网络,这个网络包含一个exchange和若干个Party。

部署结构图

exchange-structure-diagram

部署环境介绍

此处部署包含3个party和1个exchange,每个角色都有一个独立的k8s集群,所有的集群都已经部署了KubeFATE(部署KubeFATE),

party party ID k8s version k8s node IP kubefate version FATE version
exchange 1 v1.19.9 192.168.100.1 v1.4.1 v1.6.0
party-9999 9999 v1.19.9 192.168.100.9 v1.4.1 v1.6.0
party-10000 10000 v1.19.9 192.168.100.10 v1.4.1 v1.6.0
party-8888 8888 v1.19.9 192.168.100.8 v1.4.1 v1.6.0

部署exchange

我们使用FATE-Exchange的chart来部署一个exchange集群。

配置

exchange的类型分为两种,分别对应FATE的两种计算引擎(eggroll、Spark)。

  • eggroll(rollsite)

    eggroll类型的exchange集群核心是包含rollsite的组件。

    $ cat cluster-exchange.yaml
    name: fate-exchange
    namespace: fate-exchange
    chartName: fate-exchange
    chartVersion: v1.6.0
    partyId: 1
    registry: ""
    imageTag: "1.6.0-release"
    pullPolicy: 
    imagePullSecrets: 
    - name: myregistrykey
    persistence: false
    istio:
      enabled: false
    modules:
      - rollsite
    
    rollsite: 
      type: NodePort
      nodePort: 30000
      partyList:
      - partyId: 10000
        partyIp: 192.168.100.10
        partyPort: 30101
      - partyId: 9999
        partyIp: 192.168.100.9
        partyPort: 30091
      - partyId: 8888
        partyIp: 192.168.100.8
        partyPort: 30081
  • Spark(ATS)

    在部署使用Spark作为计算引擎的exchange的时候,需要先解决各个Party和exchange之间的证书配置,参考这个(pulsar与ATS的证书生成)文档,生成exchange的证书,将证书导入k8s:

    kubectl create secret generic traffic-server-cert -n fate-exchange \
    	--from-file=proxy.cert.pem=proxy.fate.org/proxy.cert.pem \
    	--from-file=proxy.key.pem=proxy.fate.org/proxy.key.pem \
    	--from-file=ca.cert.pem=certs/ca.cert.pem

    配置YAML文件,Spark计算引擎的exchange核心包含两个组件(nginx、trafficServer)。

    $ cat cluster-exchange.yaml
    name: fate-exchange
    namespace: fate-exchange
    chartName: fate-exchange
    chartVersion: v1.6.0
    partyId: 1
    registry: ""
    imageTag: "1.6.0-release"
    pullPolicy: 
    imagePullSecrets: 
    - name: myregistrykey
    persistence: false
    istio:
      enabled: false
    modules:
      - trafficServer
      - nginx
    
    trafficServer:
      type: NodePort
      nodePort: 30001
      route_table: 
        sni:
        - fqdn: 10000.fate.org
          tunnelRoute: 192.168.100.10:30109
        - fqdn: 9999.fate.org
          tunnelRoute: 192.168.100.9:30099
        - fqdn: 8888.fate.org
          tunnelRoute: 192.168.100.8:30089
    
    nginx:
      nodeSelector: 
      type: NodePort
      httpNodePort: 30003
      grpcNodePort: 30008
      route_table: 
        8888: 
          proxy: 
            - host: 192.168.100.8
              http_port: 30083
              grpc_port: 30088 
          fateflow: 
            - host: 192.168.100.8
              http_port: 30087
              grpc_port: 30082
        9999: 
          proxy: 
            - host: 192.168.100.9
              http_port: 30093
              grpc_port: 30098 
          fateflow: 
            - host: 192.168.100.9
              http_port: 30097
              grpc_port: 30092
        10000: 
          proxy: 
            - host: 192.168.100.10
              http_port: 30103
              grpc_port: 30108 
          fateflow: 
            - host: 192.168.100.10
              http_port: 30107
              grpc_port: 30102

部署

配置好YAML文件,使用exchange的kubefate部署,

(exchange)$ kubefate cluster install -f ./cluster-exchange.yaml

查看cluster的状态是否是Running确认是否成功运行。

(exchange)$ kubefate cluster ls

部署Party

添加Party

对应已经运行的exchange集群,新的Party加入,需要新增加Party信息,那么你可以修改cluster-exchange.yaml文件添加新的Party。然后呢使用kubefate的update命令更新到exchange集群。

(exchange)$ kubefate cluster update -f ./cluster-exchange.yaml

然后稍等片刻就可以生效(这是因为程序对party信息的加载有一个小的时间周期)。

配置Party

不同的计算引擎与exchange的连接有不同的方式,下边以Party-9999为例

  • eggroll(rollsite)

    配置rollsite的exchange字段就可以连接到exchange。

    $ cat cluster.yaml
    name: fate-9999
    namespace: fate-9999
    chartName: fate
    chartVersion: v1.6.0
    partyId: 9999
    registry: ""
    imageTag: "1.6.0-release"
    pullPolicy: 
    persistence: false
    istio:
      enabled: false
    modules:
      - rollsite
      - clustermanager
      - nodemanager
      - mysql
      - python
      - fateboard
      - client
    
    backend: eggroll
    
    rollsite: 
      type: NodePort
      nodePort: 30091
      exchange:
        ip: 192.168.100.1
        port: 30000
  • Spark(Pulsar)

    在部署使用Spark作为计算引擎的FATE的时候,需要先解决和exchange之间的证书配置,参考这个(pulsar与ATS的证书生成)文档,生成exchange的证书,将证书导入k8s:

    kubectl create secret generic pulsar-cert \
    	--from-file=broker.cert.pem=9999.fate.org/broker.cert.pem \
    	--from-file=broker.key-pk8.pem=9999.fate.org/broker.key-pk8.pem \
    	--from-file=ca.cert.pem=certs/ca.cert.pem

    Spark引擎的FATE就需要分别配置python,nginx和pulsar来和exchange链接

    $ cat cluster.yaml
    name: fate-9999
    namespace: fate-9999
    chartName: fate
    chartVersion: v1.6.0
    partyId: 9999
    registry: ""
    imageTag: "1.6.0-release"
    pullPolicy: 
    imagePullSecrets: 
    - name: myregistrykey
    persistence: false
    istio:
      enabled: false
    modules:
      - python
      - mysql
      - fateboard
      - client
      - spark
      - hdfs
      - nginx
      - pulsar
    
    backend: spark
    
    python:
      type: NodePort
      httpNodePort: 30097
      grpcNodePort: 30092
    
    nginx:
      type: NodePort
      httpNodePort: 30093
      grpcNodePort: 30098
      exchange:
        ip: 192.168.100.1
        httpPort: 30003
        grpcPort: 30008
    pulsar:
      type: NodePort
      httpNodePort: 30094
      httpsNodePort: 30099
      exchange:
        ip: 192.168.100.1
        port: 30001

部署

配置好YAML文件后,使用Party对应的kubefate部署FATE集群

(party-9999)$ kubefate cluster install -f ./cluster.yaml

查看cluster的状态是否是Running确认是否成功运行。

(party-9999)$ kubefate cluster ls

依次增加多个参与方

参照前边的Party配置,分别配置Party-8888和Party-10000,然后部署对应的FATE集群,加入到联邦网络中。

测试

通过上边的部署,我们已经成功部署了通过exchange互联的联邦学习网络,包含三个Party,计算引擎为eggroll。下面我们通过一些测试检查联邦学习网络的可用性。

多方连接测试

每个不同的两方测试toy_example确认双方互通。

  1. Party-9999和Party-10000

    通过命令行进入Party-9999的python container。然后运行toy命令

    kubectl -n fate-9999 exec -it svc/fateflow -c python -- bash
    cd ../examples/toy_example/
    python run_toy_example.py 9999 10000 1 
  2. Party-10000和Party-8888

    kubectl -n fate-10000 exec -it svc/fateflow -c python -- bash
    cd ../examples/toy_example/
    python run_toy_example.py 10000 8888 1 
  3. Party-8888和Party-9999

    kubectl -n fate-8888 exec -it svc/fateflow -c python -- bash
    cd ../examples/toy_example/
    python run_toy_example.py 8888 9999 1 

最后日志出现类似success to calculate secure_sum, it is 2000.0000000000002则表示toy_example互通测试成功。

多方训练测试

如何两两之间互通测试通过,我们就可以跑一个三方的min_test来测试多方的任务训练。

min_test的任务需要三方参与,Guest,Host和Arbiter。我们将Party-10000作为Guest,Party-9999作为Host,Party-8888作为Arbiter。

  1. 首先在各个Party的FATE上传min_test的数据集。

    分别在各个Party对应的k8s的master运行以下命令

    kubectl -n fate-<partyID> exec -it svc/fateflow -c python -- bash
    cd ../examples/scripts; 
    python upload_default_data.py -m 1

    <partyID>代表当前k8s所部署的Party的ID。

  2. 在其中一个Party上发起训练任务。

    我们在Party-10000发起任务

    kubectl -n fate-10000 exec -it svc/fateflow -c python -- bash
    cd ../examples/min_test_task; 
    python run_task.py -m 1 -gid 10000 -hid 9999 -aid 8888
  3. 查看任务结果。

    min_test的测试任务需要运行一些时间,等待任务结束,可以通过命令行的日志查看运行结果。

    也可以通过FATE-Board的web页面: http://10000.fateboard.example.com 来查看更多任务信息。

    fateboard

接下来就可以使用联邦学习网络计算自己的模型了。

增加参与方到exchange

在一个已经存在exchange的联邦网络中,新Party的加入变得简单,只需要配置Party和exchange的之间的信息就可以成功加入网络。

Exchange的配置参考exchange更新配置

下一步

⚠️ **GitHub.com Fallback** ⚠️