This document discusses metaprogramming in C++ and describes an RPC framework implemented using C++ templates and metaprogramming. It defines an interface called calc_interface for a calculator RPC with functions like add and signals like expr_evaluated. It shows how to define the interface using meta_functions, and how a client can invoke functions on the server while handling serialization, transport, and response deserialization. Key aspects covered include defining the interface, invoking functions from the client, argument checking, and verifying functions exist in the interface.
7. www.luxoft.com
Usage
server_t<calc_interface> server(transpotr);
server_t::initialize(server)
.add_handler<calc_interface::add> (
[] (double a, double b) { return a + b;} )
.add_handler<calc_interface::eval> (
[] (string expr) → int {
static int id(0); ++id;
new std::thread( [this, expr, id] () {
sleep(100);
server.emit<expr_evaluated>(expr, 12345);
} );
return id;
});
client_t<calc_interface> client(transpotr);
// subscribe to the signal ..
client.subscribe<client_t::expr_evaluated>(
[] (int id, string expr, double res)
{ cout << expr << "→" << res; }
);
// execute functions ..
cout << client.invoke<add>(1,2) << endl;
// async invoke
client.invoke(1,2, [] (double res) { cout << res << endl;
})
8. www.luxoft.com
What should be taken into account
• Wrong function parameters. e.g. the following should cause a compile time
errors
– client.invoke<add>(“hello” , 123) or client.invoke<add>(1) or
client.invoke<add>(1, 2, 3)
• Execution of nonexistent function
– interface_1 { RPC_FN (void (int), fn1) };
– interface_2 { RPC_FN (void (double), fn2) };
– client_t<interface_1>().invoke<interface_2::fn2>(5.);