code: private StringBuffer messageToPigScript(FieldDescriptor fieldDescriptor, int numTabs, boolean isLast) throws FrontendException {
      assert fieldDescriptor.getType() == FieldDescriptor.Type.MESSAGE : "messageToPigScript called with field of type " + fieldDescriptor.getType();
  
      if (fieldDescriptor.isRepeated()) {
        return new StringBuffer().append(tabs(numTabs)).append(fieldDescriptor.getName()).append(": bag {").append("\n")
            .append(tabs(numTabs + 1)).append(fieldDescriptor.getName()).append("_tuple: tuple (").append("\n")
            .append(toPigScriptInternal(fieldDescriptor.getMessageType(), numTabs + 2))
            .append(tabs(numTabs + 1)).append(")").append("\n")
            .append(tabs(numTabs)).append("}").append(isLast ? "" : ",").append("\n");
      } else {
        return new StringBuffer().append(tabs(numTabs)).append(fieldDescriptor.getName()).append(": tuple (").append("\n")
            .append(toPigScriptInternal(fieldDescriptor.getMessageType(), numTabs + 1))
            .append(tabs(numTabs)).append(")").append(isLast ? "" : ",").append("\n");
      }
    }
docs: Turn a nested message into a pig script load string.  For repeated nested messages, it generates a string for a bag of
  tuples.  For non-repeated nested messages, it just generates a string for the tuple itself.
  @param fieldDescriptor the descriptor object for the given field.
  @param numTabs the tab depth at the current point in the recursion, for pretty printing.
  @return the pig script load schema for the nested message.
  @throws FrontendException if Pig decides to.