code: public boolean equalsContents(Object o) {
          if (this == o) {
              return true;
          }
  
          if (o == null) {
              return false;
          }
  
          if (o.getClass() != getClass()) {
              return false;
          }
  
          Struct obj = (Struct)o;
          if(!typeName.equals(obj.getTypeName())) {
              return false;
          }
  
          if(!values.equals(obj.getValuesMap())) {
              return false;
          }
  
          return true;
      }
docs: equalContents instead of equals since values is a mutable attribute and could lead
  to incorrect behaviour when added to collections and mutated after that
  i.e when the attribute is mutated collections.contains(struct) returns false
  due to hashcode having changed for the struct.
  @param o
  @return