Part B

Part B implements error handling and persistence in the Two Phase Commit protocol. It also digs deeper into gRPC and how it's used as the form of communication between the leader and followers.

Retransmitted Messages

To begin part B, you will need to go back and add functionality that allows the 2PC follower to handle the cases where the 2PC follower gets a retransmission of a previously seen message. For example, if the follower gets two COMMIT or ABORT messages in a row.

2PC Crash Handling

Now that you have the Leader and Follower 2PC implemented, you should be passing all the basic 2PC tests on the autograder as well as the End to End tests. Ideally, you also pass the retransmit tests as well. This is a good indicator that your internal state is correct -- something that is crucial to Part B.

In Part B, you will implement the replayJournal function for both the Follower and the Leader. This function will iterate through the Journal and replay all the actions that have been committed to the journal. At the end, you should be able to continue receiving messages from where you left off in the Journal.

The journal can be read using an EntryIterator which as the functions HasNext and Next. The journal itself can be modified with the functions Append and Empty. You must implement journaling in the follower's vote and global functions. In the leader, you must implement journaling in Put.

In both, you should implement the replayJournal function. For the follower, this function should update the internal state based on what entries were logged. For the leader, this function should either make a global COMMIT or ABORT based on what was last logged.

When implementing replayJournal for the leader, you may at one point need to pass a context to some helper functions. The context is a concept in Golang that adds timeouts and deadlines to requests and you don't really need to understand how its used. (Although if you are curious this video is great.) The context normally comes from the gRPC Put call, but when replaying the journal we no longer have a context to work with. Thus we need to make a new context, which you can do with context.Background().

gRPC Written Responses

Create a text file called hw6.txt in the hw6 directory. In it, answer the following questions:

  1. gRPC is a remote procedure call implementation by Google using the protocol buffer. In your own words, what is a protocol buffer? Feel free to use the internet to look up the answer.

  2. gRPC protobufs are defined by a interface description language. You can see an example of this in api/kv.proto . Take a look a that file and describe what the keywords service, rpc, and message define.

  3. The proto file is then compiled into an gRPC framework for the language of your choice. From a high level, how does a Golang program use the compiled gRPC framework? You can take a look at the pkg/tpc/rpcserver.go as well as the compiled frameworks in api/kv.pb.go and pkg/rpc/tpc.pb.go.

  4. For the Two Phase Commit RPCs, the pkg/rpc/tpc.proto defines a service that implements an RPC which takes a stream and returns a stream. This RPC is called a bi-directional stream. How is the bi-directional stream different from a normal request-response RPC?

  5. Take a look at the skeleton code for how the 2PC Leader sends messages to the followers and wait for responses located in pkg/tpc/messagemanager.go. Where is the bi-directional stream between the leader and each follower created? What does the function SendMessage do?

  6. How does its behavior of SendMessage change based on the value of the retry argument? To help answer this question, take a look at the helper function sendSingleMessage. In what situtaion would the retry argument be used?

  7. SendMessage has different retry values for sending a vote request and sending a global command. Take a look at the globalRequest and voteRequest functions in pkg/tpc/tpcleader.go. Why does one have it set to true and the other have it set to false?

Last updated