《凤凰架构》学习感悟 -- 初识Heterogeneous

0 阅读4分钟

最近感觉自己需要沉淀很多的知识,以及之前自己研究和做过的工作,另外了解了docker的底层原理和二次开发kubernetes的自定义资源Operator和CRD之后,急需一本书或者一个学习路线来帮助把这些知识整体穿成线,所以选择了《凤凰架构》,可能检索能力比较差,目前没发现我差不多处境的,希望大佬多多指点

关于Heterogeneous异构的理解

《凤凰架构》中说到,单体系统靠高质量来保证高可靠的思路,只适合于小规模软件,当面临系统规模越来越大时,交付一个可靠的单体系统就变得具有挑战性。所以就有了微服务架构,为了允许程序出现错误,获得自治与隔离的能力,以及实现可以技术异构等目标。本篇博客是作者本人在学习当中针对于异构的初次了解以及探索。当然这其中涉及到的代码只是作为展示,无需复现。

在微服务架构中,服务的异构性是其核心优势。这里将通过一个简单的 Demo,展示如何使用 gRPC 让 Go 编写的主业务服务与 Python 编写的算法服务实现跨语言通信

1. 什么是grpc

grpc是Google开源的一个高性能RPC框架。目前多应用于微服务之间的通信。当然感兴趣的可以深入了解一下,后续也会出相应的教程和博客。当然也可以选择HTTP+JSON的的通信格式,来实现异构,不过相对于grpc内部通信会比较慢和繁琐

2. 核心架构

  • Proto 协议层:定义双方沟通的契约。
  • Python 服务端:负责算法逻辑,demo实现的是if request.hobby == coding return 99.9 else 60.5
  • Go 客户端:负责业务高并发入口,发送请求到服务端

3. 代码部分

3.1 契约定义 (matcher.proto)
syntax = "proto3";
package matcher;
option go_package = "./pb";

// 定义服务
service MatchService {
  // 定义一个算分的方法:传入用户信息,返回匹配分数
  rpc CalculateScore (UserInfo) returns (MatchResult);
}

// 请求的参数格式
message UserInfo {
  string user_name = 1;
  string hobby = 2;
}

// 返回的结果格式
message MatchResult {
  float match_score = 1;
}
3.2 服务端部分 (server.py)
import grpc
import matcher_pb2
import matcher_pb2_grpc
from concurrent import futures

# 实现我们在 proto 里定义的 MatchService
class MatchServiceServicer(matcher_pb2_grpc.MatchServiceServicer):
    
    # 真正的算法逻辑写在这里
    def CalculateScore(self, request, context):
        print(f"[Python AI算法] 收到请求: 测算用户 {request.user_name} 的分数...")
        
        # 假装这里用 numpy 跑了一个复杂的机器学习模型
        score = 0.0
        if request.hobby == "coding":
            score = 99.9  # 喜欢敲代码,分数拉满!
        else:
            score = 60.5
            
        print(f"[Python AI算法] 算分完毕,结果为: {score}")
        # 把结果包装成 proto 规定的格式返回
        return matcher_pb2.MatchResult(match_score=score)

def serve():
    # 启动 gRPC 服务器,监听 50051 端口
    server = grpc.server(futures.ThreadPoolExecutor(max_workers=10))
    matcher_pb2_grpc.add_MatchServiceServicer_to_server(MatchServiceServicer(), server)
    server.add_insecure_port('[::]:50051')
    server.start()
    print("🐍 Python 匹配算法微服务已启动,监听 50051 端口...")
    server.wait_for_termination()

if __name__ == '__main__':
    serve()
3.3 客户端部分 (main.go)
package main

import (
	"context"
	"fmt"
	"log"
	"time"

	"google.golang.org/grpc"
	"google.golang.org/grpc/credentials/insecure"

	// 这里导入由 protobuf 自动生成的 go 代码包
	pb "hetero-demo/pb"
)

func main() {
	fmt.Println("🐹 Go 主业务服务启动,准备向 Python 算法服务发起调用...")

	// 1. 建立与 Python 微服务的 gRPC 连接
	conn, err := grpc.Dial("localhost:50051", grpc.WithTransportCredentials(insecure.NewCredentials()))
	if err != nil {
		log.Fatalf("连不上 Python 服务: %v", err)
	}
	defer conn.Close()

	// 2. 创建一个客户端对象
	client := pb.NewMatchServiceClient(conn)

	// 3. 构造请求参数(完全按照 proto 里的定义)
	req := &pb.UserInfo{
		UserName: "Lixy",
		Hobby:    "learning",
	}

	// 4. 发起跨语言 RPC 调用!
	ctx, cancel := context.WithTimeout(context.Background(), time.Second)
	defer cancel()

	res, err := client.CalculateScore(ctx, req)
	if err != nil {
		log.Fatalf("调用算法失败: %v", err)
	}

	// 5. 打印 Python 算出来的结果
	fmt.Printf("🐹 [Go 业务侧] 拿到 Python 算出的匹配分数: %.2f\n", res.GetMatchScore())
}

这里可以使用venv虚拟机环境来启动服务python -m venv venv以及source venv/bin/active,go需要配置一下moudule,或者直接启动go run main.go

4. 感悟

微服务架构可以直接采用go或者Java来开发客户端,能不能服务端借助于python实现大模型的功能,再返回到客户端。当docker部署在kubernetes当中的时候能不能专门来部署一个有关于Agent的容器来解决固定的功能,通过grpc来传输数据和信号呢。希望大佬多多指点