// Code generated by protoc-gen-go. DO NOT EDIT.
// source: config/api/partner.proto

package api

import (
	fmt "fmt"
	proto "github.com/golang/protobuf/proto"
	math "math"
)

// Reference imports to suppress errors if they are not otherwise used.
var _ = proto.Marshal
var _ = fmt.Errorf
var _ = math.Inf

// This is a compile-time assertion to ensure that this generated file
// is compatible with the proto package it is being compiled against.
// A compilation error at this line likely means your copy of the
// proto package needs to be updated.
const _ = proto.ProtoPackageIsVersion3 // please upgrade the proto package

// Defines contributing partners participating in the design, execution,
// and support of chromiumos projects.
type Partner struct {
	// Globally unique partner identifier.
	Id *PartnerId `protobuf:"bytes,1,opt,name=id,proto3" json:"id,omitempty"`
	// Descriptive name (for humans) of the partner.
	Name string `protobuf:"bytes,2,opt,name=name,proto3" json:"name,omitempty"`
	// Email alias used for coordinating project execution.
	EmailGroup           string   `protobuf:"bytes,3,opt,name=email_group,json=emailGroup,proto3" json:"email_group,omitempty"`
	XXX_NoUnkeyedLiteral struct{} `json:"-"`
	XXX_unrecognized     []byte   `json:"-"`
	XXX_sizecache        int32    `json:"-"`
}

func (m *Partner) Reset()         { *m = Partner{} }
func (m *Partner) String() string { return proto.CompactTextString(m) }
func (*Partner) ProtoMessage()    {}
func (*Partner) Descriptor() ([]byte, []int) {
	return fileDescriptor_19c13223a6343523, []int{0}
}

func (m *Partner) XXX_Unmarshal(b []byte) error {
	return xxx_messageInfo_Partner.Unmarshal(m, b)
}
func (m *Partner) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
	return xxx_messageInfo_Partner.Marshal(b, m, deterministic)
}
func (m *Partner) XXX_Merge(src proto.Message) {
	xxx_messageInfo_Partner.Merge(m, src)
}
func (m *Partner) XXX_Size() int {
	return xxx_messageInfo_Partner.Size(m)
}
func (m *Partner) XXX_DiscardUnknown() {
	xxx_messageInfo_Partner.DiscardUnknown(m)
}

var xxx_messageInfo_Partner proto.InternalMessageInfo

func (m *Partner) GetId() *PartnerId {
	if m != nil {
		return m.Id
	}
	return nil
}

func (m *Partner) GetName() string {
	if m != nil {
		return m.Name
	}
	return ""
}

func (m *Partner) GetEmailGroup() string {
	if m != nil {
		return m.EmailGroup
	}
	return ""
}

type PartnerList struct {
	Value                []*Partner `protobuf:"bytes,1,rep,name=value,proto3" json:"value,omitempty"`
	XXX_NoUnkeyedLiteral struct{}   `json:"-"`
	XXX_unrecognized     []byte     `json:"-"`
	XXX_sizecache        int32      `json:"-"`
}

func (m *PartnerList) Reset()         { *m = PartnerList{} }
func (m *PartnerList) String() string { return proto.CompactTextString(m) }
func (*PartnerList) ProtoMessage()    {}
func (*PartnerList) Descriptor() ([]byte, []int) {
	return fileDescriptor_19c13223a6343523, []int{1}
}

func (m *PartnerList) XXX_Unmarshal(b []byte) error {
	return xxx_messageInfo_PartnerList.Unmarshal(m, b)
}
func (m *PartnerList) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
	return xxx_messageInfo_PartnerList.Marshal(b, m, deterministic)
}
func (m *PartnerList) XXX_Merge(src proto.Message) {
	xxx_messageInfo_PartnerList.Merge(m, src)
}
func (m *PartnerList) XXX_Size() int {
	return xxx_messageInfo_PartnerList.Size(m)
}
func (m *PartnerList) XXX_DiscardUnknown() {
	xxx_messageInfo_PartnerList.DiscardUnknown(m)
}

var xxx_messageInfo_PartnerList proto.InternalMessageInfo

func (m *PartnerList) GetValue() []*Partner {
	if m != nil {
		return m.Value
	}
	return nil
}

func init() {
	proto.RegisterType((*Partner)(nil), "chromiumos.config.api.Partner")
	proto.RegisterType((*PartnerList)(nil), "chromiumos.config.api.PartnerList")
}

func init() { proto.RegisterFile("config/api/partner.proto", fileDescriptor_19c13223a6343523) }

var fileDescriptor_19c13223a6343523 = []byte{
	// 213 bytes of a gzipped FileDescriptorProto
	0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xe2, 0x92, 0x48, 0xce, 0xcf, 0x4b,
	0xcb, 0x4c, 0xd7, 0x4f, 0x2c, 0xc8, 0xd4, 0x2f, 0x48, 0x2c, 0x2a, 0xc9, 0x4b, 0x2d, 0xd2, 0x2b,
	0x28, 0xca, 0x2f, 0xc9, 0x17, 0x12, 0x4d, 0xce, 0x28, 0xca, 0xcf, 0xcd, 0x2c, 0xcd, 0xcd, 0x2f,
	0xd6, 0x83, 0x28, 0xd2, 0x4b, 0x2c, 0xc8, 0x94, 0x92, 0xc6, 0xd4, 0x10, 0x9f, 0x99, 0x02, 0xd1,
	0xa3, 0x54, 0xc0, 0xc5, 0x1e, 0x00, 0x11, 0x13, 0x32, 0xe0, 0x62, 0xca, 0x4c, 0x91, 0x60, 0x54,
	0x60, 0xd4, 0xe0, 0x36, 0x52, 0xd0, 0xc3, 0x6a, 0x96, 0x1e, 0x54, 0xad, 0x67, 0x4a, 0x10, 0x53,
	0x66, 0x8a, 0x90, 0x10, 0x17, 0x4b, 0x5e, 0x62, 0x6e, 0xaa, 0x04, 0x93, 0x02, 0xa3, 0x06, 0x67,
	0x10, 0x98, 0x2d, 0x24, 0xcf, 0xc5, 0x9d, 0x9a, 0x9b, 0x98, 0x99, 0x13, 0x9f, 0x5e, 0x94, 0x5f,
	0x5a, 0x20, 0xc1, 0x0c, 0x96, 0xe2, 0x02, 0x0b, 0xb9, 0x83, 0x44, 0x94, 0x9c, 0xb9, 0xb8, 0xa1,
	0xa6, 0xf8, 0x64, 0x16, 0x97, 0x08, 0x99, 0x70, 0xb1, 0x96, 0x25, 0xe6, 0x94, 0xa6, 0x4a, 0x30,
	0x2a, 0x30, 0x6b, 0x70, 0x1b, 0xc9, 0xe1, 0xb7, 0x38, 0x08, 0xa2, 0xd8, 0x49, 0x2b, 0x4a, 0x23,
	0x3d, 0x1f, 0xae, 0x54, 0x2f, 0xbf, 0x28, 0x5d, 0x1f, 0xa1, 0x4f, 0x1f, 0xea, 0xe1, 0xf4, 0x7c,
	0x90, 0x9f, 0x93, 0xd8, 0xc0, 0x3e, 0x35, 0x06, 0x04, 0x00, 0x00, 0xff, 0xff, 0xe1, 0xd6, 0x17,
	0xde, 0x39, 0x01, 0x00, 0x00,
}
