C++ RPC 库建议

发布于 2024-10-06 04:01:24 字数 927 浏览 4 评论 0原文

我正在为 C++ 开发人员寻找有关用 C++ 实现的 RPC 库的建议。

一些需求限制:

  • 应该在 linux/unix 和 win32 系统上工作
  • 能够执行自由函数和类方法
  • 希望用现代 C++ 而不是 90 年代/java-esque C++ 编写
  • 能够在网络和异构体系结构上运行
  • 不会太慢或效率太低
  • 希望 为 TR1 风格的 std::function 等提供接口。

我的示例用法是调用远程计算机上的自由函数 foo。

---snip---
// foo translation unit
int foo(int i, int j)
{
   return i + j;
}
---snip---


---snip---
// client side main
int main()
{
   //register foo on client and server
   //setup necassary connections and states

   int result;

   if (RPCmechanism.invoke("foo",4,9,result))
      std::cout << "foo(4,9) = " result << std::endl;
   else
      std::cout << "failed to invoke foo(4,9)!" << std::endl;

   return 0;
}
---snip---

能够实现上述或类似目标的东西就太好了。

注意:我对其他语言绑定不感兴趣。请不要提供解决方案,因为它具有其他语言绑定。我只对用 C++ 为 C++ 语言编写的精心设计的 RPC 框架感兴趣,这些框架高效且适合 HPC 场景。

I'm looking for suggestions regarding RPC libraries implemented in C++, for C++ developers.

Some requirements constraints:

  • Should work on both linux/unix and win32 systems
  • Be able to execute free function and class methods
  • Hopefully written in modern C++ not 90's/java-esque C++
  • Be able to function over networks and hetrogenous architectures
  • Not too slow or inefficient
  • Hopefully provide interfaces for TR1 style std::function's et al.

My example usage is to invoke the free function foo on a remote machine.

---snip---
// foo translation unit
int foo(int i, int j)
{
   return i + j;
}
---snip---


---snip---
// client side main
int main()
{
   //register foo on client and server
   //setup necassary connections and states

   int result;

   if (RPCmechanism.invoke("foo",4,9,result))
      std::cout << "foo(4,9) = " result << std::endl;
   else
      std::cout << "failed to invoke foo(4,9)!" << std::endl;

   return 0;
}
---snip---

Something that can achieve the above or similar would be great.

Note: I am NOT interested in other language bindings. Please do not proffer a solution because it has other language bindings. I'm only interested in well designed RPC frameworks written in C++ for the C++ language, that are efficient and appropriate for HPC scenarios.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(8

2024-10-13 04:01:24

这是一系列要求......

虽然没有满足所有要求(因为我不确定是否存在这样的野兽 - 我建议您注意 ICE 来自 ZeroC 部分由 CORBA 名声大噪的 Michi Henning 开发(问问你电信行业的朋友,这确实不是一个肮脏的词),ICE 就是 CORBA 的样子。 它是后来开始的,不是由委员会开发的。

它们的 C++ 映射与 CORBA 不同,它使用 STL 类型,并且通常感觉较新,

它比自由函数和 std::function 失败了。测试,但考虑到为整个列表找到产品的可能性不大,这对剩下的许多产品来说都很好,

祝你好运。

That's quite a set of requirements...

While not meeting all of them (as I'm not sure that any such beast exists - I commend to your attention ICE from ZeroC. Developed in part by Michi Henning of CORBA fame (and ask your friends in telecom, that really isn't a dirty word), ICE is what CORBA would have looked like if it started later and wasn't developed by a committee.

Their C++ mapping is everything that CORBA is not, it uses STL types, and is generally newer feeling.

It fails the free-function and std::function tests, but given the improbability of finding a product for that entire list, this does a good job of many of the remainder.

Good Luck

一念一轮回 2024-10-13 04:01:24

我也对可行的 C++ RPC 实现感兴趣。经过一番研究,我发现 etch、thrift 和 protocol buffers 是最有前途的解决方案,但它们实际上都不能满足我的所有需求。我的搜索条件是:

  1. 多语言,C++和PHP是必须的(C#,Java,Python,Perl现在不太重要)
  2. 服务器只能在Linux上编译/运行(使用Windows作为长期目标)
  3. 客户端必须在 Windows 和 Linux(可能还有 Mac)上运行
  4. 开源且商业友好(即无 GPL)
  5. 它必须支持开箱即用的加密

以及候选人是:

  1. 阿帕奇蚀刻

    优点:

    • C 绑定基于 APR
    • 支持加密
    • 在两个平台上运行

    缺点

    • 发展缓慢
    • 缺少 PHP 绑定
  2. Apache Thrift

    优点:

    • 多种语言绑定

    缺点:

    • 目前,它不支持加密(正在开发中,至少对于 C++ 绑定)
    • 在 Windows 上,需要 Cygwin
  3. 带有内部开发的 RPC 解决方案的协议缓冲区

    优点:

    • 多种语言绑定

    缺点:

    • 没有内置 RPC

目前,我正在评估开发的可能性使用 APR 的 Protobuf 的 RPC 层。

然而,搜索仍在继续...

编辑:我通过使用 Apache Qpid(C++ 版本)和 protobuf 进行序列化,设法解决了其中一些问题,尽管它目前缺少我需要的一些功能。

I am also interested in viable C++ RPC implementations. After some research, I found that etch, thrift and protocol buffers are the most promising solutions, however none of them actually meets all my needs. My search criteria are:

  1. multi-language, with C++ and PHP as a must (C#, Java, Python, Perl are not so important right now)
  2. the server can compile/run only on Linux (with Windows as a long-term goal)
  3. the client must run on Windows and Linux (and possibly Mac)
  4. open source and commercial friendly (that is, no GPL)
  5. it must support encryption out of the box

And the candidates are:

  1. Apache Etch

    Pros:

    • the C binding is based on the APR
    • supports encryption
    • runs on both platforms

    Cons

    • slow development
    • lacks a PHP binding
  2. Apache Thrift

    Pros:

    • small
    • multiple language bindings

    Cons:

    • currently, it doesn't support encryption (under development, at least for the C++ binding)
    • on Windows, it requires Cygwin
  3. Protocol Buffers with an in-house developed RPC solution

    Pros:

    • small
    • multiple language bindings

    Cons:

    • no built-in RPC

Currently, I am evaluating the possibility to develop the RPC layer for Protobuf using APR.

However, search continues...

EDIT: I managed to work through some of these issues by using Apache Qpid (C++ version) with protobuf for serialization, although it currently lacks some features that I need.

旧夏天 2024-10-13 04:01:24

旧版本,例如 DCE-RPC、CORBA

协议缓冲区Thrift, Etch

或者 Web 的,例如 SOAP 或 REST。

你想要哪一个取决于你想做什么。例如。用于本地网络的快速且高效的 RPC 将需要像 Protocol Buffers 这样的轻量级二进制 RPC,但用于异构 Web 服务的 RPC 将需要更详细的 SOAP。

Google 将 PB 用于其所有内部 RPC,因此它是一个不错的选择。 Facebook 使用 Thrift,所以它不是一个小玩家,而 MS 喜欢 SOAP。

old ones like DCE-RPC, CORBA,

or Protocol Buffers, or Thrift, Etch,

or web ones like SOAP, or REST.

Which one you want depends on what you want to do. eg. fast and efficient RPC for a local network would require a lightweight, binary RPC like Protocol Buffers, but a RPC for heterogenous web services would require the much more verbose SOAP.

Google uses PB for all its internal RPCs so it's a good choice. Facebook uses Thrift so its hardly a small player, and MS likes SOAP.

满栀 2024-10-13 04:01:24

您尝试过 thrift http://thrift.apache.org/ 吗?

Have you tried thrift, http://thrift.apache.org/ ?

独夜无伴 2024-10-13 04:01:24

RCF 看起来就是您想要的: http://www.deltavsoft.com/index.html

RCF looks to be what you want: http://www.deltavsoft.com/index.html

我不在是我 2024-10-13 04:01:24

您可以使用 protobuf 自己实现一个,并添加所有您想要的功能。这并不难,而且您可以从中获得很多好处。

you can use protobuf implement one by yourself, and add all you wanted featrue. It is not too hard, and you can get many benefit from it.

说不完的你爱 2024-10-13 04:01:24

以下代码取自 TAO CORBA 客户端示例,显示连接到服务器需要 3 行代码,调用函数需要一行代码。请注意,该函数调用看起来像本机本地函数调用。这可以是自由函数,也可以是成员函数。

// Bring in the IOR
Object_var factory_object =  orb->string_to_object (argv[1]);

// Now downcast the object reference 
My_Factory_var factory = My_Factory::_narrow (factory_object.in ());

// Now get the full name and price of the other arguments:
Widget_var widget = factory->get_widget (argv[i]);

// Get its name, put it on a _var so it is automatically
// released!
String_var full_name = widget->full_name ();

// Now get the price
Double price = widget->price ();

cout << "The price of a widget in \""
  << full_name.in () << "\" is $"
  << price << endl;

服务器代码显示起来有点复杂,但在 CORBA 中,对于您想要做的事情,大多数情况下,您创建一个 IDL 接口,通过编译器运行它,然后在存根中的适当插槽中填充您的应用程序逻辑。因此,您的主要代码如下所示:

// First initialize the ORB, that will remove some arguments...
ORB_var orb = ORB_init(argc, argv, "ORB" /* the ORB name, it can be anything! */);
Object_var poa_object = orb->resolve_initial_references("RootPOA");
PortableServer::POA_var poa = PortableServer::POA::_narrow(poa_object.in());
PortableServer::POAManager_var poa_manager = poa->the_POAManager();
poa_manager->activate();

// Create the servant
My_Factory_i my_factory_i;

// Activate it to obtain the object reference
My_Factory_var my_factory = my_factory_i._this();

// Put the object reference as an IOR string
String_var ior = orb->object_to_string (my_factory.in());
orb->run();

    // Now in your stub file generated by the idl compiler, 
    char * Widget_i::full_name (

  )
  ACE_THROW_SPEC ((
    ::CORBA::SystemException
  ))
{
  return "Some widget name";
}

::CORBA::Double Widget_i::price (

  )
  ACE_THROW_SPEC ((
    ::CORBA::SystemException
  ))
{
  return 1.25;
}

查看此 WikiBook 以获取更多参考和示例

The following code, pulled from an example TAO CORBA client, shows that 3 lines of code are required to connect to a server, and one line of code to call a function. Note that the function call looks like a native local function call. This can either be a free function, or a member function.

// Bring in the IOR
Object_var factory_object =  orb->string_to_object (argv[1]);

// Now downcast the object reference 
My_Factory_var factory = My_Factory::_narrow (factory_object.in ());

// Now get the full name and price of the other arguments:
Widget_var widget = factory->get_widget (argv[i]);

// Get its name, put it on a _var so it is automatically
// released!
String_var full_name = widget->full_name ();

// Now get the price
Double price = widget->price ();

cout << "The price of a widget in \""
  << full_name.in () << "\" is $"
  << price << endl;

The server code is a little more complex to show, but in CORBA, for what you are looking to do, mostly, you create an IDL interface, run it through the compiler, then fill in your app logic in the appropriate slot in the stub. So, your main code looks like the following:

// First initialize the ORB, that will remove some arguments...
ORB_var orb = ORB_init(argc, argv, "ORB" /* the ORB name, it can be anything! */);
Object_var poa_object = orb->resolve_initial_references("RootPOA");
PortableServer::POA_var poa = PortableServer::POA::_narrow(poa_object.in());
PortableServer::POAManager_var poa_manager = poa->the_POAManager();
poa_manager->activate();

// Create the servant
My_Factory_i my_factory_i;

// Activate it to obtain the object reference
My_Factory_var my_factory = my_factory_i._this();

// Put the object reference as an IOR string
String_var ior = orb->object_to_string (my_factory.in());
orb->run();

    // Now in your stub file generated by the idl compiler, 
    char * Widget_i::full_name (

  )
  ACE_THROW_SPEC ((
    ::CORBA::SystemException
  ))
{
  return "Some widget name";
}

::CORBA::Double Widget_i::price (

  )
  ACE_THROW_SPEC ((
    ::CORBA::SystemException
  ))
{
  return 1.25;
}

Have a look at This WikiBook for more references and examples

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文