Compare commits
12 Commits
5e2025e30f
...
refactor/h
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
e8fd0a21b1 | ||
|
|
137958b83b | ||
| f5014fe906 | |||
|
|
ee5d714220 | ||
|
|
5ca21e214f | ||
|
|
2df64e715e | ||
|
|
e0ea03f6cf | ||
|
|
a7cbdcd0da | ||
|
|
f0b6a733f1 | ||
|
|
c86a189795 | ||
|
|
1565cfdaba | ||
|
|
4bec3f8cc0 |
@@ -16,12 +16,6 @@ import (
|
|||||||
|
|
||||||
type StockStatus int
|
type StockStatus int
|
||||||
|
|
||||||
const (
|
|
||||||
OutOfStock StockStatus = 0
|
|
||||||
LowStock StockStatus = 1
|
|
||||||
InStock StockStatus = 2
|
|
||||||
)
|
|
||||||
|
|
||||||
type ItemMeta struct {
|
type ItemMeta struct {
|
||||||
Name string `json:"name"`
|
Name string `json:"name"`
|
||||||
Brand string `json:"brand,omitempty"`
|
Brand string `json:"brand,omitempty"`
|
||||||
@@ -37,32 +31,27 @@ type ItemMeta struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
type CartItem struct {
|
type CartItem struct {
|
||||||
Id int `json:"id"`
|
Id uint32 `json:"id"`
|
||||||
ItemId int `json:"itemId,omitempty"`
|
ItemId uint32 `json:"itemId,omitempty"`
|
||||||
ParentId int `json:"parentId,omitempty"`
|
ParentId uint32 `json:"parentId,omitempty"`
|
||||||
Sku string `json:"sku"`
|
Sku string `json:"sku"`
|
||||||
|
|
||||||
Price Price `json:"price"`
|
Price Price `json:"price"`
|
||||||
TotalPrice Price `json:"totalPrice"`
|
TotalPrice Price `json:"totalPrice"`
|
||||||
|
|
||||||
OrgPrice *Price `json:"orgPrice,omitempty"`
|
OrgPrice *Price `json:"orgPrice,omitempty"`
|
||||||
Stock StockStatus `json:"stock"`
|
Stock StockStatus `json:"stock"`
|
||||||
Quantity int `json:"qty"`
|
Quantity int `json:"qty"`
|
||||||
Discount *Price `json:"discount,omitempty"`
|
Discount *Price `json:"discount,omitempty"`
|
||||||
|
|
||||||
Disclaimer string `json:"disclaimer,omitempty"`
|
Disclaimer string `json:"disclaimer,omitempty"`
|
||||||
|
|
||||||
ArticleType string `json:"type,omitempty"`
|
ArticleType string `json:"type,omitempty"`
|
||||||
|
|
||||||
StoreId *string `json:"storeId,omitempty"`
|
StoreId *string `json:"storeId,omitempty"`
|
||||||
Meta ItemMeta `json:"meta,omitempty"`
|
Meta *ItemMeta `json:"meta,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type CartDelivery struct {
|
type CartDelivery struct {
|
||||||
Id int `json:"id"`
|
Id uint32 `json:"id"`
|
||||||
Provider string `json:"provider"`
|
Provider string `json:"provider"`
|
||||||
Price Price `json:"price"`
|
Price Price `json:"price"`
|
||||||
Items []int `json:"items"`
|
Items []uint32 `json:"items"`
|
||||||
PickupPoint *messages.PickupPoint `json:"pickupPoint,omitempty"`
|
PickupPoint *messages.PickupPoint `json:"pickupPoint,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -75,8 +64,9 @@ type CartNotification struct {
|
|||||||
|
|
||||||
type CartGrain struct {
|
type CartGrain struct {
|
||||||
mu sync.RWMutex
|
mu sync.RWMutex
|
||||||
lastItemId int
|
lastItemId uint32
|
||||||
lastDeliveryId int
|
lastDeliveryId uint32
|
||||||
|
lastVoucherId uint32
|
||||||
lastAccess time.Time
|
lastAccess time.Time
|
||||||
lastChange time.Time // unix seconds of last successful mutation (replay sets from event ts)
|
lastChange time.Time // unix seconds of last successful mutation (replay sets from event ts)
|
||||||
userId string
|
userId string
|
||||||
@@ -89,10 +79,65 @@ type CartGrain struct {
|
|||||||
PaymentInProgress bool `json:"paymentInProgress"`
|
PaymentInProgress bool `json:"paymentInProgress"`
|
||||||
OrderReference string `json:"orderReference,omitempty"`
|
OrderReference string `json:"orderReference,omitempty"`
|
||||||
PaymentStatus string `json:"paymentStatus,omitempty"`
|
PaymentStatus string `json:"paymentStatus,omitempty"`
|
||||||
Vouchers []*voucher.Voucher `json:"vouchers,omitempty"`
|
Vouchers []*Voucher `json:"vouchers,omitempty"`
|
||||||
Notifications []CartNotification `json:"cartNotification,omitempty"`
|
Notifications []CartNotification `json:"cartNotification,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type Voucher struct {
|
||||||
|
Code string `json:"code"`
|
||||||
|
Rules []*messages.VoucherRule `json:"rules"`
|
||||||
|
Id uint32 `json:"id"`
|
||||||
|
Value int64 `json:"value"`
|
||||||
|
}
|
||||||
|
|
||||||
|
func (v *Voucher) AppliesTo(cart *CartGrain) ([]*CartItem, bool) {
|
||||||
|
// No rules -> applies to entire cart
|
||||||
|
if len(v.Rules) == 0 {
|
||||||
|
return cart.Items, true
|
||||||
|
}
|
||||||
|
|
||||||
|
// Build evaluation context once
|
||||||
|
ctx := voucher.EvalContext{
|
||||||
|
Items: make([]voucher.Item, 0, len(cart.Items)),
|
||||||
|
CartTotalInc: 0,
|
||||||
|
}
|
||||||
|
|
||||||
|
if cart.TotalPrice != nil {
|
||||||
|
ctx.CartTotalInc = cart.TotalPrice.IncVat
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, it := range cart.Items {
|
||||||
|
category := ""
|
||||||
|
if it.Meta != nil {
|
||||||
|
category = it.Meta.Category
|
||||||
|
}
|
||||||
|
ctx.Items = append(ctx.Items, voucher.Item{
|
||||||
|
Sku: it.Sku,
|
||||||
|
Category: category,
|
||||||
|
UnitPrice: it.Price.IncVat,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
// All voucher rules must pass (logical AND)
|
||||||
|
for _, rule := range v.Rules {
|
||||||
|
expr := rule.GetCondition()
|
||||||
|
if expr == "" {
|
||||||
|
// Empty condition treated as pass (acts like a comment / placeholder)
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
rs, err := voucher.ParseRules(expr)
|
||||||
|
if err != nil {
|
||||||
|
// Fail closed on parse error
|
||||||
|
return nil, false
|
||||||
|
}
|
||||||
|
if !rs.Applies(ctx) {
|
||||||
|
return nil, false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return cart.Items, true
|
||||||
|
}
|
||||||
|
|
||||||
func (c *CartGrain) GetId() uint64 {
|
func (c *CartGrain) GetId() uint64 {
|
||||||
return uint64(c.Id)
|
return uint64(c.Id)
|
||||||
}
|
}
|
||||||
@@ -130,8 +175,8 @@ func (c *CartGrain) GetState() ([]byte, error) {
|
|||||||
return json.Marshal(c)
|
return json.Marshal(c)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *CartGrain) ItemsWithDelivery() []int {
|
func (c *CartGrain) ItemsWithDelivery() []uint32 {
|
||||||
ret := make([]int, 0, len(c.Items))
|
ret := make([]uint32, 0, len(c.Items))
|
||||||
for _, item := range c.Items {
|
for _, item := range c.Items {
|
||||||
for _, delivery := range c.Deliveries {
|
for _, delivery := range c.Deliveries {
|
||||||
for _, id := range delivery.Items {
|
for _, id := range delivery.Items {
|
||||||
@@ -144,8 +189,8 @@ func (c *CartGrain) ItemsWithDelivery() []int {
|
|||||||
return ret
|
return ret
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *CartGrain) ItemsWithoutDelivery() []int {
|
func (c *CartGrain) ItemsWithoutDelivery() []uint32 {
|
||||||
ret := make([]int, 0, len(c.Items))
|
ret := make([]uint32, 0, len(c.Items))
|
||||||
hasDelivery := c.ItemsWithDelivery()
|
hasDelivery := c.ItemsWithDelivery()
|
||||||
for _, item := range c.Items {
|
for _, item := range c.Items {
|
||||||
found := slices.Contains(hasDelivery, item.Id)
|
found := slices.Contains(hasDelivery, item.Id)
|
||||||
@@ -212,9 +257,12 @@ func (c *CartGrain) UpdateTotals() {
|
|||||||
for _, delivery := range c.Deliveries {
|
for _, delivery := range c.Deliveries {
|
||||||
c.TotalPrice.Add(delivery.Price)
|
c.TotalPrice.Add(delivery.Price)
|
||||||
}
|
}
|
||||||
// for _, voucher := range c.Vouchers {
|
for _, voucher := range c.Vouchers {
|
||||||
// c.TotalPrice -= voucher.Value
|
if _, ok := voucher.AppliesTo(c); ok {
|
||||||
// c.TotalTax -= voucher.TaxValue
|
value := NewPriceFromIncVat(voucher.Value, 25)
|
||||||
// c.TotalDiscountTax += voucher.TaxValue
|
|
||||||
// }
|
c.TotalDiscount.Add(*value)
|
||||||
|
c.TotalPrice.Subtract(*value)
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,13 +2,11 @@ package main
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
"git.tornberg.me/go-cart-actor/pkg/voucher"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// helper to create a cart grain with items and deliveries
|
// helper to create a cart grain with items and deliveries
|
||||||
func newTestCart() *CartGrain {
|
func newTestCart() *CartGrain {
|
||||||
return &CartGrain{Items: []*CartItem{}, Deliveries: []*CartDelivery{}, Vouchers: []*voucher.Voucher{}, Notifications: []CartNotification{}}
|
return &CartGrain{Items: []*CartItem{}, Deliveries: []*CartDelivery{}, Vouchers: []*Voucher{}, Notifications: []CartNotification{}}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestCartGrainUpdateTotalsBasic(t *testing.T) {
|
func TestCartGrainUpdateTotalsBasic(t *testing.T) {
|
||||||
@@ -22,7 +20,7 @@ func TestCartGrainUpdateTotalsBasic(t *testing.T) {
|
|||||||
{Id: 2, Price: item2Price, OrgPrice: &item2Price, Quantity: 1},
|
{Id: 2, Price: item2Price, OrgPrice: &item2Price, Quantity: 1},
|
||||||
}
|
}
|
||||||
deliveryPrice := Price{IncVat: 4900, VatRates: map[float32]int64{25: 980}}
|
deliveryPrice := Price{IncVat: 4900, VatRates: map[float32]int64{25: 980}}
|
||||||
c.Deliveries = []*CartDelivery{{Id: 1, Price: deliveryPrice, Items: []int{1, 2}}}
|
c.Deliveries = []*CartDelivery{{Id: 1, Price: deliveryPrice, Items: []uint32{1, 2}}}
|
||||||
|
|
||||||
c.UpdateTotals()
|
c.UpdateTotals()
|
||||||
|
|
||||||
|
|||||||
@@ -100,7 +100,7 @@ type MutationContext struct {
|
|||||||
func main() {
|
func main() {
|
||||||
|
|
||||||
controlPlaneConfig := actor.DefaultServerConfig()
|
controlPlaneConfig := actor.DefaultServerConfig()
|
||||||
ctx := MutationContext{}
|
|
||||||
reg := actor.NewMutationRegistry()
|
reg := actor.NewMutationRegistry()
|
||||||
reg.RegisterMutations(
|
reg.RegisterMutations(
|
||||||
actor.NewMutation(AddItem, func() *messages.AddItem {
|
actor.NewMutation(AddItem, func() *messages.AddItem {
|
||||||
@@ -130,9 +130,12 @@ func main() {
|
|||||||
actor.NewMutation(ClearCart, func() *messages.ClearCartRequest {
|
actor.NewMutation(ClearCart, func() *messages.ClearCartRequest {
|
||||||
return &messages.ClearCartRequest{}
|
return &messages.ClearCartRequest{}
|
||||||
}),
|
}),
|
||||||
actor.NewMutation(ctx.AddVoucher, func() *messages.AddVoucher {
|
actor.NewMutation(AddVoucher, func() *messages.AddVoucher {
|
||||||
return &messages.AddVoucher{}
|
return &messages.AddVoucher{}
|
||||||
}),
|
}),
|
||||||
|
actor.NewMutation(RemoveVoucher, func() *messages.RemoveVoucher {
|
||||||
|
return &messages.RemoveVoucher{}
|
||||||
|
}),
|
||||||
)
|
)
|
||||||
diskStorage := actor.NewDiskStorage[CartGrain]("data", reg)
|
diskStorage := actor.NewDiskStorage[CartGrain]("data", reg)
|
||||||
poolConfig := actor.GrainPoolConfig[CartGrain]{
|
poolConfig := actor.GrainPoolConfig[CartGrain]{
|
||||||
|
|||||||
@@ -30,9 +30,13 @@ func AddItem(g *CartGrain, m *messages.AddItem) error {
|
|||||||
|
|
||||||
// Fast path: merge with existing item having same SKU
|
// Fast path: merge with existing item having same SKU
|
||||||
if existing, found := g.FindItemWithSku(m.Sku); found {
|
if existing, found := g.FindItemWithSku(m.Sku); found {
|
||||||
|
if existing.StoreId == m.StoreId {
|
||||||
existing.Quantity += int(m.Quantity)
|
existing.Quantity += int(m.Quantity)
|
||||||
|
existing.Stock = StockStatus(m.Stock)
|
||||||
|
existing.StoreId = m.StoreId
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
g.mu.Lock()
|
g.mu.Lock()
|
||||||
defer g.mu.Unlock()
|
defer g.mu.Unlock()
|
||||||
@@ -47,10 +51,10 @@ func AddItem(g *CartGrain, m *messages.AddItem) error {
|
|||||||
|
|
||||||
g.Items = append(g.Items, &CartItem{
|
g.Items = append(g.Items, &CartItem{
|
||||||
Id: g.lastItemId,
|
Id: g.lastItemId,
|
||||||
ItemId: int(m.ItemId),
|
ItemId: uint32(m.ItemId),
|
||||||
Quantity: int(m.Quantity),
|
Quantity: int(m.Quantity),
|
||||||
Sku: m.Sku,
|
Sku: m.Sku,
|
||||||
Meta: ItemMeta{
|
Meta: &ItemMeta{
|
||||||
Name: m.Name,
|
Name: m.Name,
|
||||||
Image: m.Image,
|
Image: m.Image,
|
||||||
Brand: m.Brand,
|
Brand: m.Brand,
|
||||||
|
|||||||
@@ -1,15 +1,39 @@
|
|||||||
package main
|
package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
|
||||||
"slices"
|
"slices"
|
||||||
|
|
||||||
"git.tornberg.me/go-cart-actor/pkg/actor"
|
"git.tornberg.me/go-cart-actor/pkg/actor"
|
||||||
"git.tornberg.me/go-cart-actor/pkg/messages"
|
"git.tornberg.me/go-cart-actor/pkg/messages"
|
||||||
"git.tornberg.me/go-cart-actor/pkg/voucher"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
func (ctx *MutationContext) AddVoucher(g *CartGrain, m *messages.AddVoucher) error {
|
func RemoveVoucher(g *CartGrain, m *messages.RemoveVoucher) error {
|
||||||
|
if m == nil {
|
||||||
|
return &actor.MutationError{
|
||||||
|
Message: "RemoveVoucher: nil payload",
|
||||||
|
Code: 1003,
|
||||||
|
StatusCode: 400,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if !slices.ContainsFunc(g.Vouchers, func(v *Voucher) bool {
|
||||||
|
return v.Id == m.Id
|
||||||
|
}) {
|
||||||
|
return &actor.MutationError{
|
||||||
|
Message: "voucher not applied",
|
||||||
|
Code: 1004,
|
||||||
|
StatusCode: 400,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
g.Vouchers = slices.DeleteFunc(g.Vouchers, func(v *Voucher) bool {
|
||||||
|
return v.Id == m.Id
|
||||||
|
})
|
||||||
|
g.UpdateTotals()
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func AddVoucher(g *CartGrain, m *messages.AddVoucher) error {
|
||||||
if m == nil {
|
if m == nil {
|
||||||
return &actor.MutationError{
|
return &actor.MutationError{
|
||||||
Message: "AddVoucher: nil payload",
|
Message: "AddVoucher: nil payload",
|
||||||
@@ -18,7 +42,7 @@ func (ctx *MutationContext) AddVoucher(g *CartGrain, m *messages.AddVoucher) err
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if slices.ContainsFunc(g.Vouchers, func(v *voucher.Voucher) bool {
|
if slices.ContainsFunc(g.Vouchers, func(v *Voucher) bool {
|
||||||
return v.Code == m.Code
|
return v.Code == m.Code
|
||||||
}) {
|
}) {
|
||||||
return &actor.MutationError{
|
return &actor.MutationError{
|
||||||
@@ -28,20 +52,13 @@ func (ctx *MutationContext) AddVoucher(g *CartGrain, m *messages.AddVoucher) err
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
voucherData, err := ctx.VoucherService.GetVoucher(m.Code)
|
g.lastVoucherId++
|
||||||
if err != nil {
|
g.Vouchers = append(g.Vouchers, &Voucher{
|
||||||
return &actor.MutationError{
|
Id: g.lastVoucherId,
|
||||||
Message: fmt.Sprintf("cant find voucher: %v", err),
|
Code: m.Code,
|
||||||
Code: 1003,
|
Rules: m.VoucherRules,
|
||||||
StatusCode: 400,
|
Value: m.Value,
|
||||||
}
|
})
|
||||||
}
|
|
||||||
|
|
||||||
if voucherData == nil {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
g.Vouchers = append(g.Vouchers, voucherData)
|
|
||||||
g.UpdateTotals()
|
g.UpdateTotals()
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ func ChangeQuantity(g *CartGrain, m *messages.ChangeQuantity) error {
|
|||||||
|
|
||||||
foundIndex := -1
|
foundIndex := -1
|
||||||
for i, it := range g.Items {
|
for i, it := range g.Items {
|
||||||
if it.Id == int(m.Id) {
|
if it.Id == uint32(m.Id) {
|
||||||
foundIndex = i
|
foundIndex = i
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -30,7 +30,7 @@ func RemoveDelivery(g *CartGrain, m *messages.RemoveDelivery) error {
|
|||||||
if m == nil {
|
if m == nil {
|
||||||
return fmt.Errorf("RemoveDelivery: nil payload")
|
return fmt.Errorf("RemoveDelivery: nil payload")
|
||||||
}
|
}
|
||||||
targetID := int(m.Id)
|
targetID := uint32(m.Id)
|
||||||
index := -1
|
index := -1
|
||||||
for i, d := range g.Deliveries {
|
for i, d := range g.Deliveries {
|
||||||
if d.Id == targetID {
|
if d.Id == targetID {
|
||||||
|
|||||||
@@ -26,7 +26,7 @@ func RemoveItem(g *CartGrain, m *messages.RemoveItem) error {
|
|||||||
if m == nil {
|
if m == nil {
|
||||||
return fmt.Errorf("RemoveItem: nil payload")
|
return fmt.Errorf("RemoveItem: nil payload")
|
||||||
}
|
}
|
||||||
targetID := int(m.Id)
|
targetID := uint32(m.Id)
|
||||||
|
|
||||||
index := -1
|
index := -1
|
||||||
for i, it := range g.Items {
|
for i, it := range g.Items {
|
||||||
|
|||||||
@@ -49,7 +49,7 @@ func SetDelivery(g *CartGrain, m *messages.SetDelivery) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
withDelivery := g.ItemsWithDelivery()
|
withDelivery := g.ItemsWithDelivery()
|
||||||
targetItems := make([]int, 0)
|
targetItems := make([]uint32, 0)
|
||||||
|
|
||||||
if len(m.Items) == 0 {
|
if len(m.Items) == 0 {
|
||||||
// Use every item currently without a delivery
|
// Use every item currently without a delivery
|
||||||
@@ -57,7 +57,7 @@ func SetDelivery(g *CartGrain, m *messages.SetDelivery) error {
|
|||||||
} else {
|
} else {
|
||||||
// Validate explicit list
|
// Validate explicit list
|
||||||
for _, id64 := range m.Items {
|
for _, id64 := range m.Items {
|
||||||
id := int(id64)
|
id := uint32(id64)
|
||||||
found := false
|
found := false
|
||||||
for _, it := range g.Items {
|
for _, it := range g.Items {
|
||||||
if it.Id == id {
|
if it.Id == id {
|
||||||
|
|||||||
@@ -35,7 +35,7 @@ func SetPickupPoint(g *CartGrain, m *messages.SetPickupPoint) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
for _, d := range g.Deliveries {
|
for _, d := range g.Deliveries {
|
||||||
if d.Id == int(m.DeliveryId) {
|
if d.Id == uint32(m.DeliveryId) {
|
||||||
d.PickupPoint = &messages.PickupPoint{
|
d.PickupPoint = &messages.PickupPoint{
|
||||||
Id: m.Id,
|
Id: m.Id,
|
||||||
Name: m.Name,
|
Name: m.Name,
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ import (
|
|||||||
|
|
||||||
"git.tornberg.me/go-cart-actor/pkg/actor"
|
"git.tornberg.me/go-cart-actor/pkg/actor"
|
||||||
messages "git.tornberg.me/go-cart-actor/pkg/messages"
|
messages "git.tornberg.me/go-cart-actor/pkg/messages"
|
||||||
|
"git.tornberg.me/go-cart-actor/pkg/voucher"
|
||||||
"github.com/gogo/protobuf/proto"
|
"github.com/gogo/protobuf/proto"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -75,11 +76,11 @@ func (s *PoolServer) WriteResult(w http.ResponseWriter, result any) error {
|
|||||||
func (s *PoolServer) DeleteItemHandler(w http.ResponseWriter, r *http.Request, id CartId) error {
|
func (s *PoolServer) DeleteItemHandler(w http.ResponseWriter, r *http.Request, id CartId) error {
|
||||||
|
|
||||||
itemIdString := r.PathValue("itemId")
|
itemIdString := r.PathValue("itemId")
|
||||||
itemId, err := strconv.Atoi(itemIdString)
|
itemId, err := strconv.ParseInt(itemIdString, 10, 64)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
data, err := s.ApplyLocal(id, &messages.RemoveItem{Id: int64(itemId)})
|
data, err := s.ApplyLocal(id, &messages.RemoveItem{Id: uint32(itemId)})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@@ -88,7 +89,7 @@ func (s *PoolServer) DeleteItemHandler(w http.ResponseWriter, r *http.Request, i
|
|||||||
|
|
||||||
type SetDeliveryRequest struct {
|
type SetDeliveryRequest struct {
|
||||||
Provider string `json:"provider"`
|
Provider string `json:"provider"`
|
||||||
Items []int64 `json:"items"`
|
Items []uint32 `json:"items"`
|
||||||
PickupPoint *messages.PickupPoint `json:"pickupPoint,omitempty"`
|
PickupPoint *messages.PickupPoint `json:"pickupPoint,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -113,7 +114,7 @@ func (s *PoolServer) SetDeliveryHandler(w http.ResponseWriter, r *http.Request,
|
|||||||
func (s *PoolServer) SetPickupPointHandler(w http.ResponseWriter, r *http.Request, id CartId) error {
|
func (s *PoolServer) SetPickupPointHandler(w http.ResponseWriter, r *http.Request, id CartId) error {
|
||||||
|
|
||||||
deliveryIdString := r.PathValue("deliveryId")
|
deliveryIdString := r.PathValue("deliveryId")
|
||||||
deliveryId, err := strconv.Atoi(deliveryIdString)
|
deliveryId, err := strconv.ParseInt(deliveryIdString, 10, 64)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@@ -123,7 +124,7 @@ func (s *PoolServer) SetPickupPointHandler(w http.ResponseWriter, r *http.Reques
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
reply, err := s.ApplyLocal(id, &messages.SetPickupPoint{
|
reply, err := s.ApplyLocal(id, &messages.SetPickupPoint{
|
||||||
DeliveryId: int64(deliveryId),
|
DeliveryId: uint32(deliveryId),
|
||||||
Id: pickupPoint.Id,
|
Id: pickupPoint.Id,
|
||||||
Name: pickupPoint.Name,
|
Name: pickupPoint.Name,
|
||||||
Address: pickupPoint.Address,
|
Address: pickupPoint.Address,
|
||||||
@@ -144,7 +145,7 @@ func (s *PoolServer) RemoveDeliveryHandler(w http.ResponseWriter, r *http.Reques
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
reply, err := s.ApplyLocal(id, &messages.RemoveDelivery{Id: int64(deliveryId)})
|
reply, err := s.ApplyLocal(id, &messages.RemoveDelivery{Id: uint32(deliveryId)})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@@ -228,8 +229,15 @@ func (s *PoolServer) AddMultipleItemHandler(w http.ResponseWriter, r *http.Reque
|
|||||||
return s.WriteResult(w, reply)
|
return s.WriteResult(w, reply)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type AddRequest struct {
|
||||||
|
Sku string `json:"sku"`
|
||||||
|
Quantity int32 `json:"quantity"`
|
||||||
|
Country string `json:"country"`
|
||||||
|
StoreId *string `json:"storeId"`
|
||||||
|
}
|
||||||
|
|
||||||
func (s *PoolServer) AddSkuRequestHandler(w http.ResponseWriter, r *http.Request, id CartId) error {
|
func (s *PoolServer) AddSkuRequestHandler(w http.ResponseWriter, r *http.Request, id CartId) error {
|
||||||
addRequest := messages.AddRequest{}
|
addRequest := AddRequest{Quantity: 1}
|
||||||
err := json.NewDecoder(r.Body).Decode(&addRequest)
|
err := json.NewDecoder(r.Body).Decode(&addRequest)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
@@ -437,9 +445,20 @@ func (s *PoolServer) ProxyHandler(fn func(w http.ResponseWriter, r *http.Request
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type AddVoucherRequest struct {
|
||||||
|
VoucherCode string `json:"code"`
|
||||||
|
}
|
||||||
|
|
||||||
func (s *PoolServer) AddVoucherHandler(w http.ResponseWriter, r *http.Request, cartId CartId) error {
|
func (s *PoolServer) AddVoucherHandler(w http.ResponseWriter, r *http.Request, cartId CartId) error {
|
||||||
msg := &messages.AddVoucher{}
|
data := &AddVoucherRequest{}
|
||||||
json.NewDecoder(r.Body).Decode(msg)
|
json.NewDecoder(r.Body).Decode(data)
|
||||||
|
v := voucher.Service{}
|
||||||
|
msg, err := v.GetVoucher(data.VoucherCode)
|
||||||
|
if err != nil {
|
||||||
|
w.WriteHeader(http.StatusInternalServerError)
|
||||||
|
w.Write([]byte(err.Error()))
|
||||||
|
return err
|
||||||
|
}
|
||||||
reply, err := s.ApplyLocal(cartId, msg)
|
reply, err := s.ApplyLocal(cartId, msg)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
w.WriteHeader(http.StatusInternalServerError)
|
w.WriteHeader(http.StatusInternalServerError)
|
||||||
@@ -450,6 +469,25 @@ func (s *PoolServer) AddVoucherHandler(w http.ResponseWriter, r *http.Request, c
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (s *PoolServer) RemoveVoucherHandler(w http.ResponseWriter, r *http.Request, cartId CartId) error {
|
||||||
|
|
||||||
|
idStr := r.PathValue("voucherId")
|
||||||
|
id, err := strconv.ParseInt(idStr, 10, 64)
|
||||||
|
if err != nil {
|
||||||
|
w.WriteHeader(http.StatusInternalServerError)
|
||||||
|
w.Write([]byte(err.Error()))
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
reply, err := s.ApplyLocal(cartId, &messages.RemoveVoucher{Id: uint32(id)})
|
||||||
|
if err != nil {
|
||||||
|
w.WriteHeader(http.StatusInternalServerError)
|
||||||
|
w.Write([]byte(err.Error()))
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
s.WriteResult(w, reply)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
func (s *PoolServer) Serve() *http.ServeMux {
|
func (s *PoolServer) Serve() *http.ServeMux {
|
||||||
|
|
||||||
mux := http.NewServeMux()
|
mux := http.NewServeMux()
|
||||||
@@ -472,6 +510,7 @@ func (s *PoolServer) Serve() *http.ServeMux {
|
|||||||
mux.HandleFunc("DELETE /delivery/{deliveryId}", CookieCartIdHandler(s.ProxyHandler(s.RemoveDeliveryHandler)))
|
mux.HandleFunc("DELETE /delivery/{deliveryId}", CookieCartIdHandler(s.ProxyHandler(s.RemoveDeliveryHandler)))
|
||||||
mux.HandleFunc("PUT /delivery/{deliveryId}/pickupPoint", CookieCartIdHandler(s.ProxyHandler(s.SetPickupPointHandler)))
|
mux.HandleFunc("PUT /delivery/{deliveryId}/pickupPoint", CookieCartIdHandler(s.ProxyHandler(s.SetPickupPointHandler)))
|
||||||
mux.HandleFunc("PUT /voucher", CookieCartIdHandler(s.ProxyHandler(s.AddVoucherHandler)))
|
mux.HandleFunc("PUT /voucher", CookieCartIdHandler(s.ProxyHandler(s.AddVoucherHandler)))
|
||||||
|
mux.HandleFunc("DELETE /voucher/{voucherId}", CookieCartIdHandler(s.ProxyHandler(s.RemoveVoucherHandler)))
|
||||||
|
|
||||||
//mux.HandleFunc("GET /checkout", CookieCartIdHandler(s.ProxyHandler(s.HandleCheckout)))
|
//mux.HandleFunc("GET /checkout", CookieCartIdHandler(s.ProxyHandler(s.HandleCheckout)))
|
||||||
//mux.HandleFunc("GET /confirmation/{orderId}", CookieCartIdHandler(s.ProxyHandler(s.HandleConfirmation)))
|
//mux.HandleFunc("GET /confirmation/{orderId}", CookieCartIdHandler(s.ProxyHandler(s.HandleConfirmation)))
|
||||||
@@ -484,6 +523,8 @@ func (s *PoolServer) Serve() *http.ServeMux {
|
|||||||
mux.HandleFunc("POST /byid/{id}/delivery", CartIdHandler(s.ProxyHandler(s.SetDeliveryHandler)))
|
mux.HandleFunc("POST /byid/{id}/delivery", CartIdHandler(s.ProxyHandler(s.SetDeliveryHandler)))
|
||||||
mux.HandleFunc("DELETE /byid/{id}/delivery/{deliveryId}", CartIdHandler(s.ProxyHandler(s.RemoveDeliveryHandler)))
|
mux.HandleFunc("DELETE /byid/{id}/delivery/{deliveryId}", CartIdHandler(s.ProxyHandler(s.RemoveDeliveryHandler)))
|
||||||
mux.HandleFunc("PUT /byid/{id}/delivery/{deliveryId}/pickupPoint", CartIdHandler(s.ProxyHandler(s.SetPickupPointHandler)))
|
mux.HandleFunc("PUT /byid/{id}/delivery/{deliveryId}/pickupPoint", CartIdHandler(s.ProxyHandler(s.SetPickupPointHandler)))
|
||||||
|
mux.HandleFunc("PUT /byid/{id}/voucher", CookieCartIdHandler(s.ProxyHandler(s.AddVoucherHandler)))
|
||||||
|
mux.HandleFunc("DELETE /byid/{id}/voucher/{voucherId}", CookieCartIdHandler(s.ProxyHandler(s.RemoveVoucherHandler)))
|
||||||
//mux.HandleFunc("GET /byid/{id}/checkout", CartIdHandler(s.ProxyHandler(s.HandleCheckout)))
|
//mux.HandleFunc("GET /byid/{id}/checkout", CartIdHandler(s.ProxyHandler(s.HandleCheckout)))
|
||||||
//mux.HandleFunc("GET /byid/{id}/confirmation", CartIdHandler(s.ProxyHandler(s.HandleConfirmation)))
|
//mux.HandleFunc("GET /byid/{id}/confirmation", CartIdHandler(s.ProxyHandler(s.HandleConfirmation)))
|
||||||
|
|
||||||
|
|||||||
@@ -4,6 +4,8 @@ import (
|
|||||||
"encoding/json"
|
"encoding/json"
|
||||||
"fmt"
|
"fmt"
|
||||||
"net/http"
|
"net/http"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
|
||||||
messages "git.tornberg.me/go-cart-actor/pkg/messages"
|
messages "git.tornberg.me/go-cart-actor/pkg/messages"
|
||||||
"github.com/matst80/slask-finder/pkg/index"
|
"github.com/matst80/slask-finder/pkg/index"
|
||||||
@@ -40,22 +42,30 @@ func GetItemAddMessage(sku string, qty int, country string, storeId *string) (*m
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
return ToItemAddMessage(item, storeId, qty, country), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func ToItemAddMessage(item *index.DataItem, storeId *string, qty int, country string) *messages.AddItem {
|
||||||
orgPrice, _ := getInt(item.GetNumberFieldValue(5)) // getInt(item.Fields[5])
|
orgPrice, _ := getInt(item.GetNumberFieldValue(5)) // getInt(item.Fields[5])
|
||||||
|
|
||||||
price, priceErr := getInt(item.GetNumberFieldValue(4)) //Fields[4]
|
price, err := getInt(item.GetNumberFieldValue(4)) //Fields[4]
|
||||||
|
if err != nil {
|
||||||
if priceErr != nil {
|
return nil
|
||||||
return nil, fmt.Errorf("invalid price")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
stock := InStock
|
stock := StockStatus(0)
|
||||||
item.HasStock()
|
centralStockValue, ok := item.GetStringFieldValue(3)
|
||||||
stockValue, ok := item.GetNumberFieldValue(3)
|
if storeId == nil {
|
||||||
if !ok || stockValue == 0 {
|
if ok {
|
||||||
stock = OutOfStock
|
pureNumber := strings.Replace(centralStockValue, "+", "", -1)
|
||||||
|
if centralStock, err := strconv.ParseInt(pureNumber, 10, 64); err == nil {
|
||||||
|
stock = StockStatus(centralStock)
|
||||||
|
}
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
if stockValue < 5 {
|
storeStock, ok := item.Stock.GetStock()[*storeId]
|
||||||
stock = LowStock
|
if ok {
|
||||||
|
stock = StockStatus(storeStock)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -76,11 +86,11 @@ func GetItemAddMessage(sku string, qty int, country string, storeId *string) (*m
|
|||||||
category5, _ := item.GetStringFieldValue(14) //.Fields[14].(string)
|
category5, _ := item.GetStringFieldValue(14) //.Fields[14].(string)
|
||||||
|
|
||||||
return &messages.AddItem{
|
return &messages.AddItem{
|
||||||
ItemId: int64(item.Id),
|
ItemId: uint32(item.Id),
|
||||||
Quantity: int32(qty),
|
Quantity: int32(qty),
|
||||||
Price: int64(price),
|
Price: int64(price),
|
||||||
OrgPrice: int64(orgPrice),
|
OrgPrice: int64(orgPrice),
|
||||||
Sku: sku,
|
Sku: item.GetSku(),
|
||||||
Name: item.Title,
|
Name: item.Title,
|
||||||
Image: item.Img,
|
Image: item.Img,
|
||||||
Stock: int32(stock),
|
Stock: int32(stock),
|
||||||
@@ -98,7 +108,7 @@ func GetItemAddMessage(sku string, qty int, country string, storeId *string) (*m
|
|||||||
Country: country,
|
Country: country,
|
||||||
Outlet: outlet,
|
Outlet: outlet,
|
||||||
StoreId: storeId,
|
StoreId: storeId,
|
||||||
}, nil
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func getTax(articleType string) int32 {
|
func getTax(articleType string) int32 {
|
||||||
|
|||||||
@@ -7,12 +7,11 @@
|
|||||||
package messages
|
package messages
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
protoreflect "google.golang.org/protobuf/reflect/protoreflect"
|
||||||
|
protoimpl "google.golang.org/protobuf/runtime/protoimpl"
|
||||||
reflect "reflect"
|
reflect "reflect"
|
||||||
sync "sync"
|
sync "sync"
|
||||||
unsafe "unsafe"
|
unsafe "unsafe"
|
||||||
|
|
||||||
protoreflect "google.golang.org/protobuf/reflect/protoreflect"
|
|
||||||
protoimpl "google.golang.org/protobuf/runtime/protoimpl"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
const (
|
const (
|
||||||
@@ -22,74 +21,6 @@ const (
|
|||||||
_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
|
_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
|
||||||
)
|
)
|
||||||
|
|
||||||
type AddRequest struct {
|
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
|
||||||
Quantity int32 `protobuf:"varint,1,opt,name=quantity,proto3" json:"quantity,omitempty"`
|
|
||||||
Sku string `protobuf:"bytes,2,opt,name=sku,proto3" json:"sku,omitempty"`
|
|
||||||
Country string `protobuf:"bytes,3,opt,name=country,proto3" json:"country,omitempty"`
|
|
||||||
StoreId *string `protobuf:"bytes,4,opt,name=storeId,proto3,oneof" json:"storeId,omitempty"`
|
|
||||||
unknownFields protoimpl.UnknownFields
|
|
||||||
sizeCache protoimpl.SizeCache
|
|
||||||
}
|
|
||||||
|
|
||||||
func (x *AddRequest) Reset() {
|
|
||||||
*x = AddRequest{}
|
|
||||||
mi := &file_messages_proto_msgTypes[0]
|
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
|
||||||
ms.StoreMessageInfo(mi)
|
|
||||||
}
|
|
||||||
|
|
||||||
func (x *AddRequest) String() string {
|
|
||||||
return protoimpl.X.MessageStringOf(x)
|
|
||||||
}
|
|
||||||
|
|
||||||
func (*AddRequest) ProtoMessage() {}
|
|
||||||
|
|
||||||
func (x *AddRequest) ProtoReflect() protoreflect.Message {
|
|
||||||
mi := &file_messages_proto_msgTypes[0]
|
|
||||||
if x != nil {
|
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
|
||||||
if ms.LoadMessageInfo() == nil {
|
|
||||||
ms.StoreMessageInfo(mi)
|
|
||||||
}
|
|
||||||
return ms
|
|
||||||
}
|
|
||||||
return mi.MessageOf(x)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Deprecated: Use AddRequest.ProtoReflect.Descriptor instead.
|
|
||||||
func (*AddRequest) Descriptor() ([]byte, []int) {
|
|
||||||
return file_messages_proto_rawDescGZIP(), []int{0}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (x *AddRequest) GetQuantity() int32 {
|
|
||||||
if x != nil {
|
|
||||||
return x.Quantity
|
|
||||||
}
|
|
||||||
return 0
|
|
||||||
}
|
|
||||||
|
|
||||||
func (x *AddRequest) GetSku() string {
|
|
||||||
if x != nil {
|
|
||||||
return x.Sku
|
|
||||||
}
|
|
||||||
return ""
|
|
||||||
}
|
|
||||||
|
|
||||||
func (x *AddRequest) GetCountry() string {
|
|
||||||
if x != nil {
|
|
||||||
return x.Country
|
|
||||||
}
|
|
||||||
return ""
|
|
||||||
}
|
|
||||||
|
|
||||||
func (x *AddRequest) GetStoreId() string {
|
|
||||||
if x != nil && x.StoreId != nil {
|
|
||||||
return *x.StoreId
|
|
||||||
}
|
|
||||||
return ""
|
|
||||||
}
|
|
||||||
|
|
||||||
type ClearCartRequest struct {
|
type ClearCartRequest struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
@@ -98,7 +29,7 @@ type ClearCartRequest struct {
|
|||||||
|
|
||||||
func (x *ClearCartRequest) Reset() {
|
func (x *ClearCartRequest) Reset() {
|
||||||
*x = ClearCartRequest{}
|
*x = ClearCartRequest{}
|
||||||
mi := &file_messages_proto_msgTypes[1]
|
mi := &file_messages_proto_msgTypes[0]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -110,7 +41,7 @@ func (x *ClearCartRequest) String() string {
|
|||||||
func (*ClearCartRequest) ProtoMessage() {}
|
func (*ClearCartRequest) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *ClearCartRequest) ProtoReflect() protoreflect.Message {
|
func (x *ClearCartRequest) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[1]
|
mi := &file_messages_proto_msgTypes[0]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -123,12 +54,12 @@ func (x *ClearCartRequest) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use ClearCartRequest.ProtoReflect.Descriptor instead.
|
// Deprecated: Use ClearCartRequest.ProtoReflect.Descriptor instead.
|
||||||
func (*ClearCartRequest) Descriptor() ([]byte, []int) {
|
func (*ClearCartRequest) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{1}
|
return file_messages_proto_rawDescGZIP(), []int{0}
|
||||||
}
|
}
|
||||||
|
|
||||||
type AddItem struct {
|
type AddItem struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
ItemId int64 `protobuf:"varint,1,opt,name=item_id,json=itemId,proto3" json:"item_id,omitempty"`
|
ItemId uint32 `protobuf:"varint,1,opt,name=item_id,json=itemId,proto3" json:"item_id,omitempty"`
|
||||||
Quantity int32 `protobuf:"varint,2,opt,name=quantity,proto3" json:"quantity,omitempty"`
|
Quantity int32 `protobuf:"varint,2,opt,name=quantity,proto3" json:"quantity,omitempty"`
|
||||||
Price int64 `protobuf:"varint,3,opt,name=price,proto3" json:"price,omitempty"`
|
Price int64 `protobuf:"varint,3,opt,name=price,proto3" json:"price,omitempty"`
|
||||||
OrgPrice int64 `protobuf:"varint,9,opt,name=orgPrice,proto3" json:"orgPrice,omitempty"`
|
OrgPrice int64 `protobuf:"varint,9,opt,name=orgPrice,proto3" json:"orgPrice,omitempty"`
|
||||||
@@ -150,13 +81,14 @@ type AddItem struct {
|
|||||||
Country string `protobuf:"bytes,21,opt,name=country,proto3" json:"country,omitempty"`
|
Country string `protobuf:"bytes,21,opt,name=country,proto3" json:"country,omitempty"`
|
||||||
Outlet *string `protobuf:"bytes,12,opt,name=outlet,proto3,oneof" json:"outlet,omitempty"`
|
Outlet *string `protobuf:"bytes,12,opt,name=outlet,proto3,oneof" json:"outlet,omitempty"`
|
||||||
StoreId *string `protobuf:"bytes,22,opt,name=storeId,proto3,oneof" json:"storeId,omitempty"`
|
StoreId *string `protobuf:"bytes,22,opt,name=storeId,proto3,oneof" json:"storeId,omitempty"`
|
||||||
|
ParentId *uint32 `protobuf:"varint,23,opt,name=parentId,proto3,oneof" json:"parentId,omitempty"`
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
sizeCache protoimpl.SizeCache
|
sizeCache protoimpl.SizeCache
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *AddItem) Reset() {
|
func (x *AddItem) Reset() {
|
||||||
*x = AddItem{}
|
*x = AddItem{}
|
||||||
mi := &file_messages_proto_msgTypes[2]
|
mi := &file_messages_proto_msgTypes[1]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -168,7 +100,7 @@ func (x *AddItem) String() string {
|
|||||||
func (*AddItem) ProtoMessage() {}
|
func (*AddItem) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *AddItem) ProtoReflect() protoreflect.Message {
|
func (x *AddItem) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[2]
|
mi := &file_messages_proto_msgTypes[1]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -181,10 +113,10 @@ func (x *AddItem) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use AddItem.ProtoReflect.Descriptor instead.
|
// Deprecated: Use AddItem.ProtoReflect.Descriptor instead.
|
||||||
func (*AddItem) Descriptor() ([]byte, []int) {
|
func (*AddItem) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{2}
|
return file_messages_proto_rawDescGZIP(), []int{1}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *AddItem) GetItemId() int64 {
|
func (x *AddItem) GetItemId() uint32 {
|
||||||
if x != nil {
|
if x != nil {
|
||||||
return x.ItemId
|
return x.ItemId
|
||||||
}
|
}
|
||||||
@@ -338,16 +270,23 @@ func (x *AddItem) GetStoreId() string {
|
|||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (x *AddItem) GetParentId() uint32 {
|
||||||
|
if x != nil && x.ParentId != nil {
|
||||||
|
return *x.ParentId
|
||||||
|
}
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
type RemoveItem struct {
|
type RemoveItem struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
Id int64 `protobuf:"varint,1,opt,name=Id,proto3" json:"Id,omitempty"`
|
Id uint32 `protobuf:"varint,1,opt,name=Id,proto3" json:"Id,omitempty"`
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
sizeCache protoimpl.SizeCache
|
sizeCache protoimpl.SizeCache
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *RemoveItem) Reset() {
|
func (x *RemoveItem) Reset() {
|
||||||
*x = RemoveItem{}
|
*x = RemoveItem{}
|
||||||
mi := &file_messages_proto_msgTypes[3]
|
mi := &file_messages_proto_msgTypes[2]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -359,7 +298,7 @@ func (x *RemoveItem) String() string {
|
|||||||
func (*RemoveItem) ProtoMessage() {}
|
func (*RemoveItem) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *RemoveItem) ProtoReflect() protoreflect.Message {
|
func (x *RemoveItem) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[3]
|
mi := &file_messages_proto_msgTypes[2]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -372,10 +311,10 @@ func (x *RemoveItem) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use RemoveItem.ProtoReflect.Descriptor instead.
|
// Deprecated: Use RemoveItem.ProtoReflect.Descriptor instead.
|
||||||
func (*RemoveItem) Descriptor() ([]byte, []int) {
|
func (*RemoveItem) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{3}
|
return file_messages_proto_rawDescGZIP(), []int{2}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *RemoveItem) GetId() int64 {
|
func (x *RemoveItem) GetId() uint32 {
|
||||||
if x != nil {
|
if x != nil {
|
||||||
return x.Id
|
return x.Id
|
||||||
}
|
}
|
||||||
@@ -384,7 +323,7 @@ func (x *RemoveItem) GetId() int64 {
|
|||||||
|
|
||||||
type ChangeQuantity struct {
|
type ChangeQuantity struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
Id int64 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"`
|
Id uint32 `protobuf:"varint,1,opt,name=Id,proto3" json:"Id,omitempty"`
|
||||||
Quantity int32 `protobuf:"varint,2,opt,name=quantity,proto3" json:"quantity,omitempty"`
|
Quantity int32 `protobuf:"varint,2,opt,name=quantity,proto3" json:"quantity,omitempty"`
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
sizeCache protoimpl.SizeCache
|
sizeCache protoimpl.SizeCache
|
||||||
@@ -392,7 +331,7 @@ type ChangeQuantity struct {
|
|||||||
|
|
||||||
func (x *ChangeQuantity) Reset() {
|
func (x *ChangeQuantity) Reset() {
|
||||||
*x = ChangeQuantity{}
|
*x = ChangeQuantity{}
|
||||||
mi := &file_messages_proto_msgTypes[4]
|
mi := &file_messages_proto_msgTypes[3]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -404,7 +343,7 @@ func (x *ChangeQuantity) String() string {
|
|||||||
func (*ChangeQuantity) ProtoMessage() {}
|
func (*ChangeQuantity) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *ChangeQuantity) ProtoReflect() protoreflect.Message {
|
func (x *ChangeQuantity) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[4]
|
mi := &file_messages_proto_msgTypes[3]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -417,10 +356,10 @@ func (x *ChangeQuantity) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use ChangeQuantity.ProtoReflect.Descriptor instead.
|
// Deprecated: Use ChangeQuantity.ProtoReflect.Descriptor instead.
|
||||||
func (*ChangeQuantity) Descriptor() ([]byte, []int) {
|
func (*ChangeQuantity) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{4}
|
return file_messages_proto_rawDescGZIP(), []int{3}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *ChangeQuantity) GetId() int64 {
|
func (x *ChangeQuantity) GetId() uint32 {
|
||||||
if x != nil {
|
if x != nil {
|
||||||
return x.Id
|
return x.Id
|
||||||
}
|
}
|
||||||
@@ -437,7 +376,7 @@ func (x *ChangeQuantity) GetQuantity() int32 {
|
|||||||
type SetDelivery struct {
|
type SetDelivery struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
Provider string `protobuf:"bytes,1,opt,name=provider,proto3" json:"provider,omitempty"`
|
Provider string `protobuf:"bytes,1,opt,name=provider,proto3" json:"provider,omitempty"`
|
||||||
Items []int64 `protobuf:"varint,2,rep,packed,name=items,proto3" json:"items,omitempty"`
|
Items []uint32 `protobuf:"varint,2,rep,packed,name=items,proto3" json:"items,omitempty"`
|
||||||
PickupPoint *PickupPoint `protobuf:"bytes,3,opt,name=pickupPoint,proto3,oneof" json:"pickupPoint,omitempty"`
|
PickupPoint *PickupPoint `protobuf:"bytes,3,opt,name=pickupPoint,proto3,oneof" json:"pickupPoint,omitempty"`
|
||||||
Country string `protobuf:"bytes,4,opt,name=country,proto3" json:"country,omitempty"`
|
Country string `protobuf:"bytes,4,opt,name=country,proto3" json:"country,omitempty"`
|
||||||
Zip string `protobuf:"bytes,5,opt,name=zip,proto3" json:"zip,omitempty"`
|
Zip string `protobuf:"bytes,5,opt,name=zip,proto3" json:"zip,omitempty"`
|
||||||
@@ -449,7 +388,7 @@ type SetDelivery struct {
|
|||||||
|
|
||||||
func (x *SetDelivery) Reset() {
|
func (x *SetDelivery) Reset() {
|
||||||
*x = SetDelivery{}
|
*x = SetDelivery{}
|
||||||
mi := &file_messages_proto_msgTypes[5]
|
mi := &file_messages_proto_msgTypes[4]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -461,7 +400,7 @@ func (x *SetDelivery) String() string {
|
|||||||
func (*SetDelivery) ProtoMessage() {}
|
func (*SetDelivery) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *SetDelivery) ProtoReflect() protoreflect.Message {
|
func (x *SetDelivery) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[5]
|
mi := &file_messages_proto_msgTypes[4]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -474,7 +413,7 @@ func (x *SetDelivery) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use SetDelivery.ProtoReflect.Descriptor instead.
|
// Deprecated: Use SetDelivery.ProtoReflect.Descriptor instead.
|
||||||
func (*SetDelivery) Descriptor() ([]byte, []int) {
|
func (*SetDelivery) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{5}
|
return file_messages_proto_rawDescGZIP(), []int{4}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *SetDelivery) GetProvider() string {
|
func (x *SetDelivery) GetProvider() string {
|
||||||
@@ -484,7 +423,7 @@ func (x *SetDelivery) GetProvider() string {
|
|||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *SetDelivery) GetItems() []int64 {
|
func (x *SetDelivery) GetItems() []uint32 {
|
||||||
if x != nil {
|
if x != nil {
|
||||||
return x.Items
|
return x.Items
|
||||||
}
|
}
|
||||||
@@ -528,7 +467,7 @@ func (x *SetDelivery) GetCity() string {
|
|||||||
|
|
||||||
type SetPickupPoint struct {
|
type SetPickupPoint struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
DeliveryId int64 `protobuf:"varint,1,opt,name=deliveryId,proto3" json:"deliveryId,omitempty"`
|
DeliveryId uint32 `protobuf:"varint,1,opt,name=deliveryId,proto3" json:"deliveryId,omitempty"`
|
||||||
Id string `protobuf:"bytes,2,opt,name=id,proto3" json:"id,omitempty"`
|
Id string `protobuf:"bytes,2,opt,name=id,proto3" json:"id,omitempty"`
|
||||||
Name *string `protobuf:"bytes,3,opt,name=name,proto3,oneof" json:"name,omitempty"`
|
Name *string `protobuf:"bytes,3,opt,name=name,proto3,oneof" json:"name,omitempty"`
|
||||||
Address *string `protobuf:"bytes,4,opt,name=address,proto3,oneof" json:"address,omitempty"`
|
Address *string `protobuf:"bytes,4,opt,name=address,proto3,oneof" json:"address,omitempty"`
|
||||||
@@ -541,7 +480,7 @@ type SetPickupPoint struct {
|
|||||||
|
|
||||||
func (x *SetPickupPoint) Reset() {
|
func (x *SetPickupPoint) Reset() {
|
||||||
*x = SetPickupPoint{}
|
*x = SetPickupPoint{}
|
||||||
mi := &file_messages_proto_msgTypes[6]
|
mi := &file_messages_proto_msgTypes[5]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -553,7 +492,7 @@ func (x *SetPickupPoint) String() string {
|
|||||||
func (*SetPickupPoint) ProtoMessage() {}
|
func (*SetPickupPoint) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *SetPickupPoint) ProtoReflect() protoreflect.Message {
|
func (x *SetPickupPoint) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[6]
|
mi := &file_messages_proto_msgTypes[5]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -566,10 +505,10 @@ func (x *SetPickupPoint) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use SetPickupPoint.ProtoReflect.Descriptor instead.
|
// Deprecated: Use SetPickupPoint.ProtoReflect.Descriptor instead.
|
||||||
func (*SetPickupPoint) Descriptor() ([]byte, []int) {
|
func (*SetPickupPoint) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{6}
|
return file_messages_proto_rawDescGZIP(), []int{5}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *SetPickupPoint) GetDeliveryId() int64 {
|
func (x *SetPickupPoint) GetDeliveryId() uint32 {
|
||||||
if x != nil {
|
if x != nil {
|
||||||
return x.DeliveryId
|
return x.DeliveryId
|
||||||
}
|
}
|
||||||
@@ -632,7 +571,7 @@ type PickupPoint struct {
|
|||||||
|
|
||||||
func (x *PickupPoint) Reset() {
|
func (x *PickupPoint) Reset() {
|
||||||
*x = PickupPoint{}
|
*x = PickupPoint{}
|
||||||
mi := &file_messages_proto_msgTypes[7]
|
mi := &file_messages_proto_msgTypes[6]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -644,7 +583,7 @@ func (x *PickupPoint) String() string {
|
|||||||
func (*PickupPoint) ProtoMessage() {}
|
func (*PickupPoint) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *PickupPoint) ProtoReflect() protoreflect.Message {
|
func (x *PickupPoint) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[7]
|
mi := &file_messages_proto_msgTypes[6]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -657,7 +596,7 @@ func (x *PickupPoint) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use PickupPoint.ProtoReflect.Descriptor instead.
|
// Deprecated: Use PickupPoint.ProtoReflect.Descriptor instead.
|
||||||
func (*PickupPoint) Descriptor() ([]byte, []int) {
|
func (*PickupPoint) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{7}
|
return file_messages_proto_rawDescGZIP(), []int{6}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *PickupPoint) GetId() string {
|
func (x *PickupPoint) GetId() string {
|
||||||
@@ -704,14 +643,14 @@ func (x *PickupPoint) GetCountry() string {
|
|||||||
|
|
||||||
type RemoveDelivery struct {
|
type RemoveDelivery struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
Id int64 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"`
|
Id uint32 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"`
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
sizeCache protoimpl.SizeCache
|
sizeCache protoimpl.SizeCache
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *RemoveDelivery) Reset() {
|
func (x *RemoveDelivery) Reset() {
|
||||||
*x = RemoveDelivery{}
|
*x = RemoveDelivery{}
|
||||||
mi := &file_messages_proto_msgTypes[8]
|
mi := &file_messages_proto_msgTypes[7]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -723,7 +662,7 @@ func (x *RemoveDelivery) String() string {
|
|||||||
func (*RemoveDelivery) ProtoMessage() {}
|
func (*RemoveDelivery) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *RemoveDelivery) ProtoReflect() protoreflect.Message {
|
func (x *RemoveDelivery) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[8]
|
mi := &file_messages_proto_msgTypes[7]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -736,10 +675,10 @@ func (x *RemoveDelivery) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use RemoveDelivery.ProtoReflect.Descriptor instead.
|
// Deprecated: Use RemoveDelivery.ProtoReflect.Descriptor instead.
|
||||||
func (*RemoveDelivery) Descriptor() ([]byte, []int) {
|
func (*RemoveDelivery) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{8}
|
return file_messages_proto_rawDescGZIP(), []int{7}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *RemoveDelivery) GetId() int64 {
|
func (x *RemoveDelivery) GetId() uint32 {
|
||||||
if x != nil {
|
if x != nil {
|
||||||
return x.Id
|
return x.Id
|
||||||
}
|
}
|
||||||
@@ -760,7 +699,7 @@ type CreateCheckoutOrder struct {
|
|||||||
|
|
||||||
func (x *CreateCheckoutOrder) Reset() {
|
func (x *CreateCheckoutOrder) Reset() {
|
||||||
*x = CreateCheckoutOrder{}
|
*x = CreateCheckoutOrder{}
|
||||||
mi := &file_messages_proto_msgTypes[9]
|
mi := &file_messages_proto_msgTypes[8]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -772,7 +711,7 @@ func (x *CreateCheckoutOrder) String() string {
|
|||||||
func (*CreateCheckoutOrder) ProtoMessage() {}
|
func (*CreateCheckoutOrder) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *CreateCheckoutOrder) ProtoReflect() protoreflect.Message {
|
func (x *CreateCheckoutOrder) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[9]
|
mi := &file_messages_proto_msgTypes[8]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -785,7 +724,7 @@ func (x *CreateCheckoutOrder) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use CreateCheckoutOrder.ProtoReflect.Descriptor instead.
|
// Deprecated: Use CreateCheckoutOrder.ProtoReflect.Descriptor instead.
|
||||||
func (*CreateCheckoutOrder) Descriptor() ([]byte, []int) {
|
func (*CreateCheckoutOrder) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{9}
|
return file_messages_proto_rawDescGZIP(), []int{8}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *CreateCheckoutOrder) GetTerms() string {
|
func (x *CreateCheckoutOrder) GetTerms() string {
|
||||||
@@ -840,7 +779,7 @@ type OrderCreated struct {
|
|||||||
|
|
||||||
func (x *OrderCreated) Reset() {
|
func (x *OrderCreated) Reset() {
|
||||||
*x = OrderCreated{}
|
*x = OrderCreated{}
|
||||||
mi := &file_messages_proto_msgTypes[10]
|
mi := &file_messages_proto_msgTypes[9]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -852,7 +791,7 @@ func (x *OrderCreated) String() string {
|
|||||||
func (*OrderCreated) ProtoMessage() {}
|
func (*OrderCreated) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *OrderCreated) ProtoReflect() protoreflect.Message {
|
func (x *OrderCreated) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[10]
|
mi := &file_messages_proto_msgTypes[9]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -865,7 +804,7 @@ func (x *OrderCreated) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use OrderCreated.ProtoReflect.Descriptor instead.
|
// Deprecated: Use OrderCreated.ProtoReflect.Descriptor instead.
|
||||||
func (*OrderCreated) Descriptor() ([]byte, []int) {
|
func (*OrderCreated) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{10}
|
return file_messages_proto_rawDescGZIP(), []int{9}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *OrderCreated) GetOrderId() string {
|
func (x *OrderCreated) GetOrderId() string {
|
||||||
@@ -890,7 +829,7 @@ type Noop struct {
|
|||||||
|
|
||||||
func (x *Noop) Reset() {
|
func (x *Noop) Reset() {
|
||||||
*x = Noop{}
|
*x = Noop{}
|
||||||
mi := &file_messages_proto_msgTypes[11]
|
mi := &file_messages_proto_msgTypes[10]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -902,7 +841,7 @@ func (x *Noop) String() string {
|
|||||||
func (*Noop) ProtoMessage() {}
|
func (*Noop) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *Noop) ProtoReflect() protoreflect.Message {
|
func (x *Noop) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[11]
|
mi := &file_messages_proto_msgTypes[10]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -915,7 +854,7 @@ func (x *Noop) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use Noop.ProtoReflect.Descriptor instead.
|
// Deprecated: Use Noop.ProtoReflect.Descriptor instead.
|
||||||
func (*Noop) Descriptor() ([]byte, []int) {
|
func (*Noop) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{11}
|
return file_messages_proto_rawDescGZIP(), []int{10}
|
||||||
}
|
}
|
||||||
|
|
||||||
type InitializeCheckout struct {
|
type InitializeCheckout struct {
|
||||||
@@ -929,7 +868,7 @@ type InitializeCheckout struct {
|
|||||||
|
|
||||||
func (x *InitializeCheckout) Reset() {
|
func (x *InitializeCheckout) Reset() {
|
||||||
*x = InitializeCheckout{}
|
*x = InitializeCheckout{}
|
||||||
mi := &file_messages_proto_msgTypes[12]
|
mi := &file_messages_proto_msgTypes[11]
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
ms.StoreMessageInfo(mi)
|
ms.StoreMessageInfo(mi)
|
||||||
}
|
}
|
||||||
@@ -941,7 +880,7 @@ func (x *InitializeCheckout) String() string {
|
|||||||
func (*InitializeCheckout) ProtoMessage() {}
|
func (*InitializeCheckout) ProtoMessage() {}
|
||||||
|
|
||||||
func (x *InitializeCheckout) ProtoReflect() protoreflect.Message {
|
func (x *InitializeCheckout) ProtoReflect() protoreflect.Message {
|
||||||
mi := &file_messages_proto_msgTypes[12]
|
mi := &file_messages_proto_msgTypes[11]
|
||||||
if x != nil {
|
if x != nil {
|
||||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
if ms.LoadMessageInfo() == nil {
|
if ms.LoadMessageInfo() == nil {
|
||||||
@@ -954,7 +893,7 @@ func (x *InitializeCheckout) ProtoReflect() protoreflect.Message {
|
|||||||
|
|
||||||
// Deprecated: Use InitializeCheckout.ProtoReflect.Descriptor instead.
|
// Deprecated: Use InitializeCheckout.ProtoReflect.Descriptor instead.
|
||||||
func (*InitializeCheckout) Descriptor() ([]byte, []int) {
|
func (*InitializeCheckout) Descriptor() ([]byte, []int) {
|
||||||
return file_messages_proto_rawDescGZIP(), []int{12}
|
return file_messages_proto_rawDescGZIP(), []int{11}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (x *InitializeCheckout) GetOrderId() string {
|
func (x *InitializeCheckout) GetOrderId() string {
|
||||||
@@ -978,9 +917,79 @@ func (x *InitializeCheckout) GetPaymentInProgress() bool {
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type VoucherRule struct {
|
||||||
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
|
Type string `protobuf:"bytes,2,opt,name=type,proto3" json:"type,omitempty"`
|
||||||
|
Description string `protobuf:"bytes,3,opt,name=description,proto3" json:"description,omitempty"`
|
||||||
|
Condition string `protobuf:"bytes,4,opt,name=condition,proto3" json:"condition,omitempty"`
|
||||||
|
Action string `protobuf:"bytes,5,opt,name=action,proto3" json:"action,omitempty"`
|
||||||
|
unknownFields protoimpl.UnknownFields
|
||||||
|
sizeCache protoimpl.SizeCache
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *VoucherRule) Reset() {
|
||||||
|
*x = VoucherRule{}
|
||||||
|
mi := &file_messages_proto_msgTypes[12]
|
||||||
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
|
ms.StoreMessageInfo(mi)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *VoucherRule) String() string {
|
||||||
|
return protoimpl.X.MessageStringOf(x)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (*VoucherRule) ProtoMessage() {}
|
||||||
|
|
||||||
|
func (x *VoucherRule) ProtoReflect() protoreflect.Message {
|
||||||
|
mi := &file_messages_proto_msgTypes[12]
|
||||||
|
if x != nil {
|
||||||
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
|
if ms.LoadMessageInfo() == nil {
|
||||||
|
ms.StoreMessageInfo(mi)
|
||||||
|
}
|
||||||
|
return ms
|
||||||
|
}
|
||||||
|
return mi.MessageOf(x)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Deprecated: Use VoucherRule.ProtoReflect.Descriptor instead.
|
||||||
|
func (*VoucherRule) Descriptor() ([]byte, []int) {
|
||||||
|
return file_messages_proto_rawDescGZIP(), []int{12}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *VoucherRule) GetType() string {
|
||||||
|
if x != nil {
|
||||||
|
return x.Type
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *VoucherRule) GetDescription() string {
|
||||||
|
if x != nil {
|
||||||
|
return x.Description
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *VoucherRule) GetCondition() string {
|
||||||
|
if x != nil {
|
||||||
|
return x.Condition
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *VoucherRule) GetAction() string {
|
||||||
|
if x != nil {
|
||||||
|
return x.Action
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
type AddVoucher struct {
|
type AddVoucher struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
Code string `protobuf:"bytes,1,opt,name=code,proto3" json:"code,omitempty"`
|
Code string `protobuf:"bytes,1,opt,name=code,proto3" json:"code,omitempty"`
|
||||||
|
Value int64 `protobuf:"varint,2,opt,name=value,proto3" json:"value,omitempty"`
|
||||||
|
VoucherRules []*VoucherRule `protobuf:"bytes,3,rep,name=voucherRules,proto3" json:"voucherRules,omitempty"`
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
sizeCache protoimpl.SizeCache
|
sizeCache protoimpl.SizeCache
|
||||||
}
|
}
|
||||||
@@ -1022,142 +1031,210 @@ func (x *AddVoucher) GetCode() string {
|
|||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (x *AddVoucher) GetValue() int64 {
|
||||||
|
if x != nil {
|
||||||
|
return x.Value
|
||||||
|
}
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *AddVoucher) GetVoucherRules() []*VoucherRule {
|
||||||
|
if x != nil {
|
||||||
|
return x.VoucherRules
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
type RemoveVoucher struct {
|
||||||
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
|
Id uint32 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"`
|
||||||
|
unknownFields protoimpl.UnknownFields
|
||||||
|
sizeCache protoimpl.SizeCache
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *RemoveVoucher) Reset() {
|
||||||
|
*x = RemoveVoucher{}
|
||||||
|
mi := &file_messages_proto_msgTypes[14]
|
||||||
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
|
ms.StoreMessageInfo(mi)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *RemoveVoucher) String() string {
|
||||||
|
return protoimpl.X.MessageStringOf(x)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (*RemoveVoucher) ProtoMessage() {}
|
||||||
|
|
||||||
|
func (x *RemoveVoucher) ProtoReflect() protoreflect.Message {
|
||||||
|
mi := &file_messages_proto_msgTypes[14]
|
||||||
|
if x != nil {
|
||||||
|
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||||
|
if ms.LoadMessageInfo() == nil {
|
||||||
|
ms.StoreMessageInfo(mi)
|
||||||
|
}
|
||||||
|
return ms
|
||||||
|
}
|
||||||
|
return mi.MessageOf(x)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Deprecated: Use RemoveVoucher.ProtoReflect.Descriptor instead.
|
||||||
|
func (*RemoveVoucher) Descriptor() ([]byte, []int) {
|
||||||
|
return file_messages_proto_rawDescGZIP(), []int{14}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (x *RemoveVoucher) GetId() uint32 {
|
||||||
|
if x != nil {
|
||||||
|
return x.Id
|
||||||
|
}
|
||||||
|
return 0
|
||||||
|
}
|
||||||
|
|
||||||
var File_messages_proto protoreflect.FileDescriptor
|
var File_messages_proto protoreflect.FileDescriptor
|
||||||
|
|
||||||
var file_messages_proto_rawDesc = string([]byte{
|
var file_messages_proto_rawDesc = string([]byte{
|
||||||
0x0a, 0x0e, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f,
|
0x0a, 0x0e, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f,
|
||||||
0x12, 0x08, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x73, 0x22, 0x7f, 0x0a, 0x0a, 0x41, 0x64,
|
0x12, 0x08, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x73, 0x22, 0x12, 0x0a, 0x10, 0x43, 0x6c,
|
||||||
0x64, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x1a, 0x0a, 0x08, 0x71, 0x75, 0x61, 0x6e,
|
0x65, 0x61, 0x72, 0x43, 0x61, 0x72, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22, 0x97,
|
||||||
0x74, 0x69, 0x74, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x71, 0x75, 0x61, 0x6e,
|
0x05, 0x0a, 0x07, 0x41, 0x64, 0x64, 0x49, 0x74, 0x65, 0x6d, 0x12, 0x17, 0x0a, 0x07, 0x69, 0x74,
|
||||||
0x74, 0x69, 0x74, 0x79, 0x12, 0x10, 0x0a, 0x03, 0x73, 0x6b, 0x75, 0x18, 0x02, 0x20, 0x01, 0x28,
|
0x65, 0x6d, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0d, 0x52, 0x06, 0x69, 0x74, 0x65,
|
||||||
0x09, 0x52, 0x03, 0x73, 0x6b, 0x75, 0x12, 0x18, 0x0a, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72,
|
0x6d, 0x49, 0x64, 0x12, 0x1a, 0x0a, 0x08, 0x71, 0x75, 0x61, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x18,
|
||||||
0x79, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79,
|
0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x71, 0x75, 0x61, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x12,
|
||||||
0x12, 0x1d, 0x0a, 0x07, 0x73, 0x74, 0x6f, 0x72, 0x65, 0x49, 0x64, 0x18, 0x04, 0x20, 0x01, 0x28,
|
0x14, 0x0a, 0x05, 0x70, 0x72, 0x69, 0x63, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x03, 0x52, 0x05,
|
||||||
0x09, 0x48, 0x00, 0x52, 0x07, 0x73, 0x74, 0x6f, 0x72, 0x65, 0x49, 0x64, 0x88, 0x01, 0x01, 0x42,
|
0x70, 0x72, 0x69, 0x63, 0x65, 0x12, 0x1a, 0x0a, 0x08, 0x6f, 0x72, 0x67, 0x50, 0x72, 0x69, 0x63,
|
||||||
0x0a, 0x0a, 0x08, 0x5f, 0x73, 0x74, 0x6f, 0x72, 0x65, 0x49, 0x64, 0x22, 0x12, 0x0a, 0x10, 0x43,
|
0x65, 0x18, 0x09, 0x20, 0x01, 0x28, 0x03, 0x52, 0x08, 0x6f, 0x72, 0x67, 0x50, 0x72, 0x69, 0x63,
|
||||||
0x6c, 0x65, 0x61, 0x72, 0x43, 0x61, 0x72, 0x74, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x22,
|
0x65, 0x12, 0x10, 0x0a, 0x03, 0x73, 0x6b, 0x75, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03,
|
||||||
0xe9, 0x04, 0x0a, 0x07, 0x41, 0x64, 0x64, 0x49, 0x74, 0x65, 0x6d, 0x12, 0x17, 0x0a, 0x07, 0x69,
|
0x73, 0x6b, 0x75, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28,
|
||||||
0x74, 0x65, 0x6d, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x06, 0x69, 0x74,
|
0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x14, 0x0a, 0x05, 0x69, 0x6d, 0x61, 0x67, 0x65,
|
||||||
0x65, 0x6d, 0x49, 0x64, 0x12, 0x1a, 0x0a, 0x08, 0x71, 0x75, 0x61, 0x6e, 0x74, 0x69, 0x74, 0x79,
|
0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x12, 0x14, 0x0a,
|
||||||
0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x71, 0x75, 0x61, 0x6e, 0x74, 0x69, 0x74, 0x79,
|
0x05, 0x73, 0x74, 0x6f, 0x63, 0x6b, 0x18, 0x07, 0x20, 0x01, 0x28, 0x05, 0x52, 0x05, 0x73, 0x74,
|
||||||
0x12, 0x14, 0x0a, 0x05, 0x70, 0x72, 0x69, 0x63, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x03, 0x52,
|
0x6f, 0x63, 0x6b, 0x12, 0x10, 0x0a, 0x03, 0x74, 0x61, 0x78, 0x18, 0x08, 0x20, 0x01, 0x28, 0x05,
|
||||||
0x05, 0x70, 0x72, 0x69, 0x63, 0x65, 0x12, 0x1a, 0x0a, 0x08, 0x6f, 0x72, 0x67, 0x50, 0x72, 0x69,
|
0x52, 0x03, 0x74, 0x61, 0x78, 0x12, 0x14, 0x0a, 0x05, 0x62, 0x72, 0x61, 0x6e, 0x64, 0x18, 0x0d,
|
||||||
0x63, 0x65, 0x18, 0x09, 0x20, 0x01, 0x28, 0x03, 0x52, 0x08, 0x6f, 0x72, 0x67, 0x50, 0x72, 0x69,
|
0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x62, 0x72, 0x61, 0x6e, 0x64, 0x12, 0x1a, 0x0a, 0x08, 0x63,
|
||||||
0x63, 0x65, 0x12, 0x10, 0x0a, 0x03, 0x73, 0x6b, 0x75, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52,
|
0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x18, 0x0e, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x63,
|
||||||
0x03, 0x73, 0x6b, 0x75, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x05, 0x20, 0x01,
|
0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x12, 0x1c, 0x0a, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67,
|
||||||
0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x14, 0x0a, 0x05, 0x69, 0x6d, 0x61, 0x67,
|
0x6f, 0x72, 0x79, 0x32, 0x18, 0x0f, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x61, 0x74, 0x65,
|
||||||
0x65, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x69, 0x6d, 0x61, 0x67, 0x65, 0x12, 0x14,
|
0x67, 0x6f, 0x72, 0x79, 0x32, 0x12, 0x1c, 0x0a, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72,
|
||||||
0x0a, 0x05, 0x73, 0x74, 0x6f, 0x63, 0x6b, 0x18, 0x07, 0x20, 0x01, 0x28, 0x05, 0x52, 0x05, 0x73,
|
0x79, 0x33, 0x18, 0x10, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f,
|
||||||
0x74, 0x6f, 0x63, 0x6b, 0x12, 0x10, 0x0a, 0x03, 0x74, 0x61, 0x78, 0x18, 0x08, 0x20, 0x01, 0x28,
|
0x72, 0x79, 0x33, 0x12, 0x1c, 0x0a, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x34,
|
||||||
0x05, 0x52, 0x03, 0x74, 0x61, 0x78, 0x12, 0x14, 0x0a, 0x05, 0x62, 0x72, 0x61, 0x6e, 0x64, 0x18,
|
0x18, 0x11, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79,
|
||||||
0x0d, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x62, 0x72, 0x61, 0x6e, 0x64, 0x12, 0x1a, 0x0a, 0x08,
|
0x34, 0x12, 0x1c, 0x0a, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x35, 0x18, 0x12,
|
||||||
0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x18, 0x0e, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08,
|
0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x35, 0x12,
|
||||||
0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x12, 0x1c, 0x0a, 0x09, 0x63, 0x61, 0x74, 0x65,
|
0x1e, 0x0a, 0x0a, 0x64, 0x69, 0x73, 0x63, 0x6c, 0x61, 0x69, 0x6d, 0x65, 0x72, 0x18, 0x0a, 0x20,
|
||||||
0x67, 0x6f, 0x72, 0x79, 0x32, 0x18, 0x0f, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x61, 0x74,
|
0x01, 0x28, 0x09, 0x52, 0x0a, 0x64, 0x69, 0x73, 0x63, 0x6c, 0x61, 0x69, 0x6d, 0x65, 0x72, 0x12,
|
||||||
0x65, 0x67, 0x6f, 0x72, 0x79, 0x32, 0x12, 0x1c, 0x0a, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f,
|
0x20, 0x0a, 0x0b, 0x61, 0x72, 0x74, 0x69, 0x63, 0x6c, 0x65, 0x54, 0x79, 0x70, 0x65, 0x18, 0x0b,
|
||||||
0x72, 0x79, 0x33, 0x18, 0x10, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67,
|
0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x61, 0x72, 0x74, 0x69, 0x63, 0x6c, 0x65, 0x54, 0x79, 0x70,
|
||||||
0x6f, 0x72, 0x79, 0x33, 0x12, 0x1c, 0x0a, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79,
|
0x65, 0x12, 0x1a, 0x0a, 0x08, 0x73, 0x65, 0x6c, 0x6c, 0x65, 0x72, 0x49, 0x64, 0x18, 0x13, 0x20,
|
||||||
0x34, 0x18, 0x11, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72,
|
0x01, 0x28, 0x09, 0x52, 0x08, 0x73, 0x65, 0x6c, 0x6c, 0x65, 0x72, 0x49, 0x64, 0x12, 0x1e, 0x0a,
|
||||||
0x79, 0x34, 0x12, 0x1c, 0x0a, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x35, 0x18,
|
0x0a, 0x73, 0x65, 0x6c, 0x6c, 0x65, 0x72, 0x4e, 0x61, 0x6d, 0x65, 0x18, 0x14, 0x20, 0x01, 0x28,
|
||||||
0x12, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x61, 0x74, 0x65, 0x67, 0x6f, 0x72, 0x79, 0x35,
|
0x09, 0x52, 0x0a, 0x73, 0x65, 0x6c, 0x6c, 0x65, 0x72, 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x18, 0x0a,
|
||||||
0x12, 0x1e, 0x0a, 0x0a, 0x64, 0x69, 0x73, 0x63, 0x6c, 0x61, 0x69, 0x6d, 0x65, 0x72, 0x18, 0x0a,
|
0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x18, 0x15, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07,
|
||||||
0x20, 0x01, 0x28, 0x09, 0x52, 0x0a, 0x64, 0x69, 0x73, 0x63, 0x6c, 0x61, 0x69, 0x6d, 0x65, 0x72,
|
0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x1b, 0x0a, 0x06, 0x6f, 0x75, 0x74, 0x6c, 0x65,
|
||||||
0x12, 0x20, 0x0a, 0x0b, 0x61, 0x72, 0x74, 0x69, 0x63, 0x6c, 0x65, 0x54, 0x79, 0x70, 0x65, 0x18,
|
0x74, 0x18, 0x0c, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x06, 0x6f, 0x75, 0x74, 0x6c, 0x65,
|
||||||
0x0b, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x61, 0x72, 0x74, 0x69, 0x63, 0x6c, 0x65, 0x54, 0x79,
|
0x74, 0x88, 0x01, 0x01, 0x12, 0x1d, 0x0a, 0x07, 0x73, 0x74, 0x6f, 0x72, 0x65, 0x49, 0x64, 0x18,
|
||||||
0x70, 0x65, 0x12, 0x1a, 0x0a, 0x08, 0x73, 0x65, 0x6c, 0x6c, 0x65, 0x72, 0x49, 0x64, 0x18, 0x13,
|
0x16, 0x20, 0x01, 0x28, 0x09, 0x48, 0x01, 0x52, 0x07, 0x73, 0x74, 0x6f, 0x72, 0x65, 0x49, 0x64,
|
||||||
0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x73, 0x65, 0x6c, 0x6c, 0x65, 0x72, 0x49, 0x64, 0x12, 0x1e,
|
0x88, 0x01, 0x01, 0x12, 0x1f, 0x0a, 0x08, 0x70, 0x61, 0x72, 0x65, 0x6e, 0x74, 0x49, 0x64, 0x18,
|
||||||
0x0a, 0x0a, 0x73, 0x65, 0x6c, 0x6c, 0x65, 0x72, 0x4e, 0x61, 0x6d, 0x65, 0x18, 0x14, 0x20, 0x01,
|
0x17, 0x20, 0x01, 0x28, 0x0d, 0x48, 0x02, 0x52, 0x08, 0x70, 0x61, 0x72, 0x65, 0x6e, 0x74, 0x49,
|
||||||
0x28, 0x09, 0x52, 0x0a, 0x73, 0x65, 0x6c, 0x6c, 0x65, 0x72, 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x18,
|
|
||||||
0x0a, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x18, 0x15, 0x20, 0x01, 0x28, 0x09, 0x52,
|
|
||||||
0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x1b, 0x0a, 0x06, 0x6f, 0x75, 0x74, 0x6c,
|
|
||||||
0x65, 0x74, 0x18, 0x0c, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x06, 0x6f, 0x75, 0x74, 0x6c,
|
|
||||||
0x65, 0x74, 0x88, 0x01, 0x01, 0x12, 0x1d, 0x0a, 0x07, 0x73, 0x74, 0x6f, 0x72, 0x65, 0x49, 0x64,
|
|
||||||
0x18, 0x16, 0x20, 0x01, 0x28, 0x09, 0x48, 0x01, 0x52, 0x07, 0x73, 0x74, 0x6f, 0x72, 0x65, 0x49,
|
|
||||||
0x64, 0x88, 0x01, 0x01, 0x42, 0x09, 0x0a, 0x07, 0x5f, 0x6f, 0x75, 0x74, 0x6c, 0x65, 0x74, 0x42,
|
0x64, 0x88, 0x01, 0x01, 0x42, 0x09, 0x0a, 0x07, 0x5f, 0x6f, 0x75, 0x74, 0x6c, 0x65, 0x74, 0x42,
|
||||||
0x0a, 0x0a, 0x08, 0x5f, 0x73, 0x74, 0x6f, 0x72, 0x65, 0x49, 0x64, 0x22, 0x1c, 0x0a, 0x0a, 0x52,
|
0x0a, 0x0a, 0x08, 0x5f, 0x73, 0x74, 0x6f, 0x72, 0x65, 0x49, 0x64, 0x42, 0x0b, 0x0a, 0x09, 0x5f,
|
||||||
0x65, 0x6d, 0x6f, 0x76, 0x65, 0x49, 0x74, 0x65, 0x6d, 0x12, 0x0e, 0x0a, 0x02, 0x49, 0x64, 0x18,
|
0x70, 0x61, 0x72, 0x65, 0x6e, 0x74, 0x49, 0x64, 0x22, 0x1c, 0x0a, 0x0a, 0x52, 0x65, 0x6d, 0x6f,
|
||||||
0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x02, 0x49, 0x64, 0x22, 0x3c, 0x0a, 0x0e, 0x43, 0x68, 0x61,
|
0x76, 0x65, 0x49, 0x74, 0x65, 0x6d, 0x12, 0x0e, 0x0a, 0x02, 0x49, 0x64, 0x18, 0x01, 0x20, 0x01,
|
||||||
0x6e, 0x67, 0x65, 0x51, 0x75, 0x61, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x12, 0x0e, 0x0a, 0x02, 0x69,
|
0x28, 0x0d, 0x52, 0x02, 0x49, 0x64, 0x22, 0x3c, 0x0a, 0x0e, 0x43, 0x68, 0x61, 0x6e, 0x67, 0x65,
|
||||||
0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x02, 0x69, 0x64, 0x12, 0x1a, 0x0a, 0x08, 0x71,
|
0x51, 0x75, 0x61, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x12, 0x0e, 0x0a, 0x02, 0x49, 0x64, 0x18, 0x01,
|
||||||
0x75, 0x61, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x71,
|
0x20, 0x01, 0x28, 0x0d, 0x52, 0x02, 0x49, 0x64, 0x12, 0x1a, 0x0a, 0x08, 0x71, 0x75, 0x61, 0x6e,
|
||||||
0x75, 0x61, 0x6e, 0x74, 0x69, 0x74, 0x79, 0x22, 0x86, 0x02, 0x0a, 0x0b, 0x53, 0x65, 0x74, 0x44,
|
0x74, 0x69, 0x74, 0x79, 0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x71, 0x75, 0x61, 0x6e,
|
||||||
0x65, 0x6c, 0x69, 0x76, 0x65, 0x72, 0x79, 0x12, 0x1a, 0x0a, 0x08, 0x70, 0x72, 0x6f, 0x76, 0x69,
|
0x74, 0x69, 0x74, 0x79, 0x22, 0x86, 0x02, 0x0a, 0x0b, 0x53, 0x65, 0x74, 0x44, 0x65, 0x6c, 0x69,
|
||||||
0x64, 0x65, 0x72, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x70, 0x72, 0x6f, 0x76, 0x69,
|
0x76, 0x65, 0x72, 0x79, 0x12, 0x1a, 0x0a, 0x08, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x64, 0x65, 0x72,
|
||||||
0x64, 0x65, 0x72, 0x12, 0x14, 0x0a, 0x05, 0x69, 0x74, 0x65, 0x6d, 0x73, 0x18, 0x02, 0x20, 0x03,
|
0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x64, 0x65, 0x72,
|
||||||
0x28, 0x03, 0x52, 0x05, 0x69, 0x74, 0x65, 0x6d, 0x73, 0x12, 0x3c, 0x0a, 0x0b, 0x70, 0x69, 0x63,
|
0x12, 0x14, 0x0a, 0x05, 0x69, 0x74, 0x65, 0x6d, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0d, 0x52,
|
||||||
0x6b, 0x75, 0x70, 0x50, 0x6f, 0x69, 0x6e, 0x74, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x15,
|
0x05, 0x69, 0x74, 0x65, 0x6d, 0x73, 0x12, 0x3c, 0x0a, 0x0b, 0x70, 0x69, 0x63, 0x6b, 0x75, 0x70,
|
||||||
0x2e, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x73, 0x2e, 0x50, 0x69, 0x63, 0x6b, 0x75, 0x70,
|
0x50, 0x6f, 0x69, 0x6e, 0x74, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x15, 0x2e, 0x6d, 0x65,
|
||||||
0x50, 0x6f, 0x69, 0x6e, 0x74, 0x48, 0x00, 0x52, 0x0b, 0x70, 0x69, 0x63, 0x6b, 0x75, 0x70, 0x50,
|
0x73, 0x73, 0x61, 0x67, 0x65, 0x73, 0x2e, 0x50, 0x69, 0x63, 0x6b, 0x75, 0x70, 0x50, 0x6f, 0x69,
|
||||||
0x6f, 0x69, 0x6e, 0x74, 0x88, 0x01, 0x01, 0x12, 0x18, 0x0a, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74,
|
0x6e, 0x74, 0x48, 0x00, 0x52, 0x0b, 0x70, 0x69, 0x63, 0x6b, 0x75, 0x70, 0x50, 0x6f, 0x69, 0x6e,
|
||||||
0x72, 0x79, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72,
|
0x74, 0x88, 0x01, 0x01, 0x12, 0x18, 0x0a, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x18,
|
||||||
0x79, 0x12, 0x10, 0x0a, 0x03, 0x7a, 0x69, 0x70, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03,
|
0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x10,
|
||||||
0x7a, 0x69, 0x70, 0x12, 0x1d, 0x0a, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x18, 0x06,
|
0x0a, 0x03, 0x7a, 0x69, 0x70, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x7a, 0x69, 0x70,
|
||||||
0x20, 0x01, 0x28, 0x09, 0x48, 0x01, 0x52, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x88,
|
0x12, 0x1d, 0x0a, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x18, 0x06, 0x20, 0x01, 0x28,
|
||||||
0x01, 0x01, 0x12, 0x17, 0x0a, 0x04, 0x63, 0x69, 0x74, 0x79, 0x18, 0x07, 0x20, 0x01, 0x28, 0x09,
|
0x09, 0x48, 0x01, 0x52, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x88, 0x01, 0x01, 0x12,
|
||||||
0x48, 0x02, 0x52, 0x04, 0x63, 0x69, 0x74, 0x79, 0x88, 0x01, 0x01, 0x42, 0x0e, 0x0a, 0x0c, 0x5f,
|
0x17, 0x0a, 0x04, 0x63, 0x69, 0x74, 0x79, 0x18, 0x07, 0x20, 0x01, 0x28, 0x09, 0x48, 0x02, 0x52,
|
||||||
0x70, 0x69, 0x63, 0x6b, 0x75, 0x70, 0x50, 0x6f, 0x69, 0x6e, 0x74, 0x42, 0x0a, 0x0a, 0x08, 0x5f,
|
0x04, 0x63, 0x69, 0x74, 0x79, 0x88, 0x01, 0x01, 0x42, 0x0e, 0x0a, 0x0c, 0x5f, 0x70, 0x69, 0x63,
|
||||||
0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x42, 0x07, 0x0a, 0x05, 0x5f, 0x63, 0x69, 0x74, 0x79,
|
0x6b, 0x75, 0x70, 0x50, 0x6f, 0x69, 0x6e, 0x74, 0x42, 0x0a, 0x0a, 0x08, 0x5f, 0x61, 0x64, 0x64,
|
||||||
0x22, 0xf9, 0x01, 0x0a, 0x0e, 0x53, 0x65, 0x74, 0x50, 0x69, 0x63, 0x6b, 0x75, 0x70, 0x50, 0x6f,
|
0x72, 0x65, 0x73, 0x73, 0x42, 0x07, 0x0a, 0x05, 0x5f, 0x63, 0x69, 0x74, 0x79, 0x22, 0xf9, 0x01,
|
||||||
0x69, 0x6e, 0x74, 0x12, 0x1e, 0x0a, 0x0a, 0x64, 0x65, 0x6c, 0x69, 0x76, 0x65, 0x72, 0x79, 0x49,
|
0x0a, 0x0e, 0x53, 0x65, 0x74, 0x50, 0x69, 0x63, 0x6b, 0x75, 0x70, 0x50, 0x6f, 0x69, 0x6e, 0x74,
|
||||||
0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x0a, 0x64, 0x65, 0x6c, 0x69, 0x76, 0x65, 0x72,
|
0x12, 0x1e, 0x0a, 0x0a, 0x64, 0x65, 0x6c, 0x69, 0x76, 0x65, 0x72, 0x79, 0x49, 0x64, 0x18, 0x01,
|
||||||
0x79, 0x49, 0x64, 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52,
|
0x20, 0x01, 0x28, 0x0d, 0x52, 0x0a, 0x64, 0x65, 0x6c, 0x69, 0x76, 0x65, 0x72, 0x79, 0x49, 0x64,
|
||||||
0x02, 0x69, 0x64, 0x12, 0x17, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28,
|
0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x02, 0x69, 0x64,
|
||||||
0x09, 0x48, 0x00, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x88, 0x01, 0x01, 0x12, 0x1d, 0x0a, 0x07,
|
0x12, 0x17, 0x0a, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00,
|
||||||
0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x48, 0x01, 0x52,
|
0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x88, 0x01, 0x01, 0x12, 0x1d, 0x0a, 0x07, 0x61, 0x64, 0x64,
|
||||||
0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x88, 0x01, 0x01, 0x12, 0x17, 0x0a, 0x04, 0x63,
|
0x72, 0x65, 0x73, 0x73, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x48, 0x01, 0x52, 0x07, 0x61, 0x64,
|
||||||
0x69, 0x74, 0x79, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x48, 0x02, 0x52, 0x04, 0x63, 0x69, 0x74,
|
0x64, 0x72, 0x65, 0x73, 0x73, 0x88, 0x01, 0x01, 0x12, 0x17, 0x0a, 0x04, 0x63, 0x69, 0x74, 0x79,
|
||||||
0x79, 0x88, 0x01, 0x01, 0x12, 0x15, 0x0a, 0x03, 0x7a, 0x69, 0x70, 0x18, 0x06, 0x20, 0x01, 0x28,
|
0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x48, 0x02, 0x52, 0x04, 0x63, 0x69, 0x74, 0x79, 0x88, 0x01,
|
||||||
0x09, 0x48, 0x03, 0x52, 0x03, 0x7a, 0x69, 0x70, 0x88, 0x01, 0x01, 0x12, 0x1d, 0x0a, 0x07, 0x63,
|
0x01, 0x12, 0x15, 0x0a, 0x03, 0x7a, 0x69, 0x70, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x48, 0x03,
|
||||||
0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x18, 0x07, 0x20, 0x01, 0x28, 0x09, 0x48, 0x04, 0x52, 0x07,
|
0x52, 0x03, 0x7a, 0x69, 0x70, 0x88, 0x01, 0x01, 0x12, 0x1d, 0x0a, 0x07, 0x63, 0x6f, 0x75, 0x6e,
|
||||||
0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x88, 0x01, 0x01, 0x42, 0x07, 0x0a, 0x05, 0x5f, 0x6e,
|
0x74, 0x72, 0x79, 0x18, 0x07, 0x20, 0x01, 0x28, 0x09, 0x48, 0x04, 0x52, 0x07, 0x63, 0x6f, 0x75,
|
||||||
0x61, 0x6d, 0x65, 0x42, 0x0a, 0x0a, 0x08, 0x5f, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x42,
|
0x6e, 0x74, 0x72, 0x79, 0x88, 0x01, 0x01, 0x42, 0x07, 0x0a, 0x05, 0x5f, 0x6e, 0x61, 0x6d, 0x65,
|
||||||
0x07, 0x0a, 0x05, 0x5f, 0x63, 0x69, 0x74, 0x79, 0x42, 0x06, 0x0a, 0x04, 0x5f, 0x7a, 0x69, 0x70,
|
0x42, 0x0a, 0x0a, 0x08, 0x5f, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x42, 0x07, 0x0a, 0x05,
|
||||||
0x42, 0x0a, 0x0a, 0x08, 0x5f, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x22, 0xd6, 0x01, 0x0a,
|
0x5f, 0x63, 0x69, 0x74, 0x79, 0x42, 0x06, 0x0a, 0x04, 0x5f, 0x7a, 0x69, 0x70, 0x42, 0x0a, 0x0a,
|
||||||
0x0b, 0x50, 0x69, 0x63, 0x6b, 0x75, 0x70, 0x50, 0x6f, 0x69, 0x6e, 0x74, 0x12, 0x0e, 0x0a, 0x02,
|
0x08, 0x5f, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x22, 0xd6, 0x01, 0x0a, 0x0b, 0x50, 0x69,
|
||||||
0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x02, 0x69, 0x64, 0x12, 0x17, 0x0a, 0x04,
|
0x63, 0x6b, 0x75, 0x70, 0x50, 0x6f, 0x69, 0x6e, 0x74, 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18,
|
||||||
0x6e, 0x61, 0x6d, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x04, 0x6e, 0x61,
|
0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x02, 0x69, 0x64, 0x12, 0x17, 0x0a, 0x04, 0x6e, 0x61, 0x6d,
|
||||||
0x6d, 0x65, 0x88, 0x01, 0x01, 0x12, 0x1d, 0x0a, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73,
|
0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x48, 0x00, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x88,
|
||||||
0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x48, 0x01, 0x52, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73,
|
0x01, 0x01, 0x12, 0x1d, 0x0a, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x18, 0x03, 0x20,
|
||||||
0x73, 0x88, 0x01, 0x01, 0x12, 0x17, 0x0a, 0x04, 0x63, 0x69, 0x74, 0x79, 0x18, 0x04, 0x20, 0x01,
|
0x01, 0x28, 0x09, 0x48, 0x01, 0x52, 0x07, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x88, 0x01,
|
||||||
0x28, 0x09, 0x48, 0x02, 0x52, 0x04, 0x63, 0x69, 0x74, 0x79, 0x88, 0x01, 0x01, 0x12, 0x15, 0x0a,
|
0x01, 0x12, 0x17, 0x0a, 0x04, 0x63, 0x69, 0x74, 0x79, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x48,
|
||||||
0x03, 0x7a, 0x69, 0x70, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x48, 0x03, 0x52, 0x03, 0x7a, 0x69,
|
0x02, 0x52, 0x04, 0x63, 0x69, 0x74, 0x79, 0x88, 0x01, 0x01, 0x12, 0x15, 0x0a, 0x03, 0x7a, 0x69,
|
||||||
0x70, 0x88, 0x01, 0x01, 0x12, 0x1d, 0x0a, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x18,
|
0x70, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x48, 0x03, 0x52, 0x03, 0x7a, 0x69, 0x70, 0x88, 0x01,
|
||||||
0x06, 0x20, 0x01, 0x28, 0x09, 0x48, 0x04, 0x52, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79,
|
0x01, 0x12, 0x1d, 0x0a, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x18, 0x06, 0x20, 0x01,
|
||||||
0x88, 0x01, 0x01, 0x42, 0x07, 0x0a, 0x05, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x42, 0x0a, 0x0a, 0x08,
|
0x28, 0x09, 0x48, 0x04, 0x52, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79, 0x88, 0x01, 0x01,
|
||||||
0x5f, 0x61, 0x64, 0x64, 0x72, 0x65, 0x73, 0x73, 0x42, 0x07, 0x0a, 0x05, 0x5f, 0x63, 0x69, 0x74,
|
0x42, 0x07, 0x0a, 0x05, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x42, 0x0a, 0x0a, 0x08, 0x5f, 0x61, 0x64,
|
||||||
0x79, 0x42, 0x06, 0x0a, 0x04, 0x5f, 0x7a, 0x69, 0x70, 0x42, 0x0a, 0x0a, 0x08, 0x5f, 0x63, 0x6f,
|
0x64, 0x72, 0x65, 0x73, 0x73, 0x42, 0x07, 0x0a, 0x05, 0x5f, 0x63, 0x69, 0x74, 0x79, 0x42, 0x06,
|
||||||
0x75, 0x6e, 0x74, 0x72, 0x79, 0x22, 0x20, 0x0a, 0x0e, 0x52, 0x65, 0x6d, 0x6f, 0x76, 0x65, 0x44,
|
0x0a, 0x04, 0x5f, 0x7a, 0x69, 0x70, 0x42, 0x0a, 0x0a, 0x08, 0x5f, 0x63, 0x6f, 0x75, 0x6e, 0x74,
|
||||||
0x65, 0x6c, 0x69, 0x76, 0x65, 0x72, 0x79, 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20,
|
0x72, 0x79, 0x22, 0x20, 0x0a, 0x0e, 0x52, 0x65, 0x6d, 0x6f, 0x76, 0x65, 0x44, 0x65, 0x6c, 0x69,
|
||||||
0x01, 0x28, 0x03, 0x52, 0x02, 0x69, 0x64, 0x22, 0xb9, 0x01, 0x0a, 0x13, 0x43, 0x72, 0x65, 0x61,
|
0x76, 0x65, 0x72, 0x79, 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0d,
|
||||||
0x74, 0x65, 0x43, 0x68, 0x65, 0x63, 0x6b, 0x6f, 0x75, 0x74, 0x4f, 0x72, 0x64, 0x65, 0x72, 0x12,
|
0x52, 0x02, 0x69, 0x64, 0x22, 0xb9, 0x01, 0x0a, 0x13, 0x43, 0x72, 0x65, 0x61, 0x74, 0x65, 0x43,
|
||||||
0x14, 0x0a, 0x05, 0x74, 0x65, 0x72, 0x6d, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05,
|
0x68, 0x65, 0x63, 0x6b, 0x6f, 0x75, 0x74, 0x4f, 0x72, 0x64, 0x65, 0x72, 0x12, 0x14, 0x0a, 0x05,
|
||||||
0x74, 0x65, 0x72, 0x6d, 0x73, 0x12, 0x1a, 0x0a, 0x08, 0x63, 0x68, 0x65, 0x63, 0x6b, 0x6f, 0x75,
|
0x74, 0x65, 0x72, 0x6d, 0x73, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x74, 0x65, 0x72,
|
||||||
0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x63, 0x68, 0x65, 0x63, 0x6b, 0x6f, 0x75,
|
0x6d, 0x73, 0x12, 0x1a, 0x0a, 0x08, 0x63, 0x68, 0x65, 0x63, 0x6b, 0x6f, 0x75, 0x74, 0x18, 0x02,
|
||||||
0x74, 0x12, 0x22, 0x0a, 0x0c, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x72, 0x6d, 0x61, 0x74, 0x69, 0x6f,
|
0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x63, 0x68, 0x65, 0x63, 0x6b, 0x6f, 0x75, 0x74, 0x12, 0x22,
|
||||||
0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0c, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x72, 0x6d,
|
0x0a, 0x0c, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x72, 0x6d, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x03,
|
||||||
0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x12, 0x0a, 0x04, 0x70, 0x75, 0x73, 0x68, 0x18, 0x04, 0x20,
|
0x20, 0x01, 0x28, 0x09, 0x52, 0x0c, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x72, 0x6d, 0x61, 0x74, 0x69,
|
||||||
0x01, 0x28, 0x09, 0x52, 0x04, 0x70, 0x75, 0x73, 0x68, 0x12, 0x1e, 0x0a, 0x0a, 0x76, 0x61, 0x6c,
|
0x6f, 0x6e, 0x12, 0x12, 0x0a, 0x04, 0x70, 0x75, 0x73, 0x68, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09,
|
||||||
0x69, 0x64, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0a, 0x76,
|
0x52, 0x04, 0x70, 0x75, 0x73, 0x68, 0x12, 0x1e, 0x0a, 0x0a, 0x76, 0x61, 0x6c, 0x69, 0x64, 0x61,
|
||||||
0x61, 0x6c, 0x69, 0x64, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x18, 0x0a, 0x07, 0x63, 0x6f, 0x75,
|
0x74, 0x69, 0x6f, 0x6e, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0a, 0x76, 0x61, 0x6c, 0x69,
|
||||||
0x6e, 0x74, 0x72, 0x79, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x63, 0x6f, 0x75, 0x6e,
|
0x64, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x18, 0x0a, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72,
|
||||||
0x74, 0x72, 0x79, 0x22, 0x40, 0x0a, 0x0c, 0x4f, 0x72, 0x64, 0x65, 0x72, 0x43, 0x72, 0x65, 0x61,
|
0x79, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x63, 0x6f, 0x75, 0x6e, 0x74, 0x72, 0x79,
|
||||||
0x74, 0x65, 0x64, 0x12, 0x18, 0x0a, 0x07, 0x6f, 0x72, 0x64, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01,
|
0x22, 0x40, 0x0a, 0x0c, 0x4f, 0x72, 0x64, 0x65, 0x72, 0x43, 0x72, 0x65, 0x61, 0x74, 0x65, 0x64,
|
||||||
0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x6f, 0x72, 0x64, 0x65, 0x72, 0x49, 0x64, 0x12, 0x16, 0x0a,
|
0x12, 0x18, 0x0a, 0x07, 0x6f, 0x72, 0x64, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28,
|
||||||
0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x73,
|
0x09, 0x52, 0x07, 0x6f, 0x72, 0x64, 0x65, 0x72, 0x49, 0x64, 0x12, 0x16, 0x0a, 0x06, 0x73, 0x74,
|
||||||
0x74, 0x61, 0x74, 0x75, 0x73, 0x22, 0x06, 0x0a, 0x04, 0x4e, 0x6f, 0x6f, 0x70, 0x22, 0x74, 0x0a,
|
0x61, 0x74, 0x75, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x73, 0x74, 0x61, 0x74,
|
||||||
0x12, 0x49, 0x6e, 0x69, 0x74, 0x69, 0x61, 0x6c, 0x69, 0x7a, 0x65, 0x43, 0x68, 0x65, 0x63, 0x6b,
|
0x75, 0x73, 0x22, 0x06, 0x0a, 0x04, 0x4e, 0x6f, 0x6f, 0x70, 0x22, 0x74, 0x0a, 0x12, 0x49, 0x6e,
|
||||||
0x6f, 0x75, 0x74, 0x12, 0x18, 0x0a, 0x07, 0x6f, 0x72, 0x64, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01,
|
0x69, 0x74, 0x69, 0x61, 0x6c, 0x69, 0x7a, 0x65, 0x43, 0x68, 0x65, 0x63, 0x6b, 0x6f, 0x75, 0x74,
|
||||||
0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x6f, 0x72, 0x64, 0x65, 0x72, 0x49, 0x64, 0x12, 0x16, 0x0a,
|
0x12, 0x18, 0x0a, 0x07, 0x6f, 0x72, 0x64, 0x65, 0x72, 0x49, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28,
|
||||||
0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x73,
|
0x09, 0x52, 0x07, 0x6f, 0x72, 0x64, 0x65, 0x72, 0x49, 0x64, 0x12, 0x16, 0x0a, 0x06, 0x73, 0x74,
|
||||||
0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x2c, 0x0a, 0x11, 0x70, 0x61, 0x79, 0x6d, 0x65, 0x6e, 0x74,
|
0x61, 0x74, 0x75, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x73, 0x74, 0x61, 0x74,
|
||||||
0x49, 0x6e, 0x50, 0x72, 0x6f, 0x67, 0x72, 0x65, 0x73, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08,
|
0x75, 0x73, 0x12, 0x2c, 0x0a, 0x11, 0x70, 0x61, 0x79, 0x6d, 0x65, 0x6e, 0x74, 0x49, 0x6e, 0x50,
|
||||||
0x52, 0x11, 0x70, 0x61, 0x79, 0x6d, 0x65, 0x6e, 0x74, 0x49, 0x6e, 0x50, 0x72, 0x6f, 0x67, 0x72,
|
0x72, 0x6f, 0x67, 0x72, 0x65, 0x73, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x11, 0x70,
|
||||||
0x65, 0x73, 0x73, 0x22, 0x20, 0x0a, 0x0a, 0x41, 0x64, 0x64, 0x56, 0x6f, 0x75, 0x63, 0x68, 0x65,
|
0x61, 0x79, 0x6d, 0x65, 0x6e, 0x74, 0x49, 0x6e, 0x50, 0x72, 0x6f, 0x67, 0x72, 0x65, 0x73, 0x73,
|
||||||
0x72, 0x12, 0x12, 0x0a, 0x04, 0x63, 0x6f, 0x64, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52,
|
0x22, 0x79, 0x0a, 0x0b, 0x56, 0x6f, 0x75, 0x63, 0x68, 0x65, 0x72, 0x52, 0x75, 0x6c, 0x65, 0x12,
|
||||||
0x04, 0x63, 0x6f, 0x64, 0x65, 0x42, 0x2e, 0x5a, 0x2c, 0x67, 0x69, 0x74, 0x2e, 0x74, 0x6f, 0x72,
|
0x12, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x74,
|
||||||
0x6e, 0x62, 0x65, 0x72, 0x67, 0x2e, 0x6d, 0x65, 0x2f, 0x67, 0x6f, 0x2d, 0x63, 0x61, 0x72, 0x74,
|
0x79, 0x70, 0x65, 0x12, 0x20, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69,
|
||||||
0x2d, 0x61, 0x63, 0x74, 0x6f, 0x72, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x3b, 0x6d, 0x65, 0x73,
|
0x6f, 0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69,
|
||||||
0x73, 0x61, 0x67, 0x65, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
|
0x70, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x1c, 0x0a, 0x09, 0x63, 0x6f, 0x6e, 0x64, 0x69, 0x74, 0x69,
|
||||||
|
0x6f, 0x6e, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x6f, 0x6e, 0x64, 0x69, 0x74,
|
||||||
|
0x69, 0x6f, 0x6e, 0x12, 0x16, 0x0a, 0x06, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x05, 0x20,
|
||||||
|
0x01, 0x28, 0x09, 0x52, 0x06, 0x61, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0x71, 0x0a, 0x0a, 0x41,
|
||||||
|
0x64, 0x64, 0x56, 0x6f, 0x75, 0x63, 0x68, 0x65, 0x72, 0x12, 0x12, 0x0a, 0x04, 0x63, 0x6f, 0x64,
|
||||||
|
0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x63, 0x6f, 0x64, 0x65, 0x12, 0x14, 0x0a,
|
||||||
|
0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x03, 0x52, 0x05, 0x76, 0x61,
|
||||||
|
0x6c, 0x75, 0x65, 0x12, 0x39, 0x0a, 0x0c, 0x76, 0x6f, 0x75, 0x63, 0x68, 0x65, 0x72, 0x52, 0x75,
|
||||||
|
0x6c, 0x65, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x15, 0x2e, 0x6d, 0x65, 0x73, 0x73,
|
||||||
|
0x61, 0x67, 0x65, 0x73, 0x2e, 0x56, 0x6f, 0x75, 0x63, 0x68, 0x65, 0x72, 0x52, 0x75, 0x6c, 0x65,
|
||||||
|
0x52, 0x0c, 0x76, 0x6f, 0x75, 0x63, 0x68, 0x65, 0x72, 0x52, 0x75, 0x6c, 0x65, 0x73, 0x22, 0x1f,
|
||||||
|
0x0a, 0x0d, 0x52, 0x65, 0x6d, 0x6f, 0x76, 0x65, 0x56, 0x6f, 0x75, 0x63, 0x68, 0x65, 0x72, 0x12,
|
||||||
|
0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0d, 0x52, 0x02, 0x69, 0x64, 0x42,
|
||||||
|
0x2e, 0x5a, 0x2c, 0x67, 0x69, 0x74, 0x2e, 0x74, 0x6f, 0x72, 0x6e, 0x62, 0x65, 0x72, 0x67, 0x2e,
|
||||||
|
0x6d, 0x65, 0x2f, 0x67, 0x6f, 0x2d, 0x63, 0x61, 0x72, 0x74, 0x2d, 0x61, 0x63, 0x74, 0x6f, 0x72,
|
||||||
|
0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x3b, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x73, 0x62,
|
||||||
|
0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33,
|
||||||
})
|
})
|
||||||
|
|
||||||
var (
|
var (
|
||||||
@@ -1172,30 +1249,32 @@ func file_messages_proto_rawDescGZIP() []byte {
|
|||||||
return file_messages_proto_rawDescData
|
return file_messages_proto_rawDescData
|
||||||
}
|
}
|
||||||
|
|
||||||
var file_messages_proto_msgTypes = make([]protoimpl.MessageInfo, 14)
|
var file_messages_proto_msgTypes = make([]protoimpl.MessageInfo, 15)
|
||||||
var file_messages_proto_goTypes = []any{
|
var file_messages_proto_goTypes = []any{
|
||||||
(*AddRequest)(nil), // 0: messages.AddRequest
|
(*ClearCartRequest)(nil), // 0: messages.ClearCartRequest
|
||||||
(*ClearCartRequest)(nil), // 1: messages.ClearCartRequest
|
(*AddItem)(nil), // 1: messages.AddItem
|
||||||
(*AddItem)(nil), // 2: messages.AddItem
|
(*RemoveItem)(nil), // 2: messages.RemoveItem
|
||||||
(*RemoveItem)(nil), // 3: messages.RemoveItem
|
(*ChangeQuantity)(nil), // 3: messages.ChangeQuantity
|
||||||
(*ChangeQuantity)(nil), // 4: messages.ChangeQuantity
|
(*SetDelivery)(nil), // 4: messages.SetDelivery
|
||||||
(*SetDelivery)(nil), // 5: messages.SetDelivery
|
(*SetPickupPoint)(nil), // 5: messages.SetPickupPoint
|
||||||
(*SetPickupPoint)(nil), // 6: messages.SetPickupPoint
|
(*PickupPoint)(nil), // 6: messages.PickupPoint
|
||||||
(*PickupPoint)(nil), // 7: messages.PickupPoint
|
(*RemoveDelivery)(nil), // 7: messages.RemoveDelivery
|
||||||
(*RemoveDelivery)(nil), // 8: messages.RemoveDelivery
|
(*CreateCheckoutOrder)(nil), // 8: messages.CreateCheckoutOrder
|
||||||
(*CreateCheckoutOrder)(nil), // 9: messages.CreateCheckoutOrder
|
(*OrderCreated)(nil), // 9: messages.OrderCreated
|
||||||
(*OrderCreated)(nil), // 10: messages.OrderCreated
|
(*Noop)(nil), // 10: messages.Noop
|
||||||
(*Noop)(nil), // 11: messages.Noop
|
(*InitializeCheckout)(nil), // 11: messages.InitializeCheckout
|
||||||
(*InitializeCheckout)(nil), // 12: messages.InitializeCheckout
|
(*VoucherRule)(nil), // 12: messages.VoucherRule
|
||||||
(*AddVoucher)(nil), // 13: messages.AddVoucher
|
(*AddVoucher)(nil), // 13: messages.AddVoucher
|
||||||
|
(*RemoveVoucher)(nil), // 14: messages.RemoveVoucher
|
||||||
}
|
}
|
||||||
var file_messages_proto_depIdxs = []int32{
|
var file_messages_proto_depIdxs = []int32{
|
||||||
7, // 0: messages.SetDelivery.pickupPoint:type_name -> messages.PickupPoint
|
6, // 0: messages.SetDelivery.pickupPoint:type_name -> messages.PickupPoint
|
||||||
1, // [1:1] is the sub-list for method output_type
|
12, // 1: messages.AddVoucher.voucherRules:type_name -> messages.VoucherRule
|
||||||
1, // [1:1] is the sub-list for method input_type
|
2, // [2:2] is the sub-list for method output_type
|
||||||
1, // [1:1] is the sub-list for extension type_name
|
2, // [2:2] is the sub-list for method input_type
|
||||||
1, // [1:1] is the sub-list for extension extendee
|
2, // [2:2] is the sub-list for extension type_name
|
||||||
0, // [0:1] is the sub-list for field type_name
|
2, // [2:2] is the sub-list for extension extendee
|
||||||
|
0, // [0:2] is the sub-list for field type_name
|
||||||
}
|
}
|
||||||
|
|
||||||
func init() { file_messages_proto_init() }
|
func init() { file_messages_proto_init() }
|
||||||
@@ -1203,18 +1282,17 @@ func file_messages_proto_init() {
|
|||||||
if File_messages_proto != nil {
|
if File_messages_proto != nil {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
file_messages_proto_msgTypes[0].OneofWrappers = []any{}
|
file_messages_proto_msgTypes[1].OneofWrappers = []any{}
|
||||||
file_messages_proto_msgTypes[2].OneofWrappers = []any{}
|
file_messages_proto_msgTypes[4].OneofWrappers = []any{}
|
||||||
file_messages_proto_msgTypes[5].OneofWrappers = []any{}
|
file_messages_proto_msgTypes[5].OneofWrappers = []any{}
|
||||||
file_messages_proto_msgTypes[6].OneofWrappers = []any{}
|
file_messages_proto_msgTypes[6].OneofWrappers = []any{}
|
||||||
file_messages_proto_msgTypes[7].OneofWrappers = []any{}
|
|
||||||
type x struct{}
|
type x struct{}
|
||||||
out := protoimpl.TypeBuilder{
|
out := protoimpl.TypeBuilder{
|
||||||
File: protoimpl.DescBuilder{
|
File: protoimpl.DescBuilder{
|
||||||
GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
|
GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
|
||||||
RawDescriptor: unsafe.Slice(unsafe.StringData(file_messages_proto_rawDesc), len(file_messages_proto_rawDesc)),
|
RawDescriptor: unsafe.Slice(unsafe.StringData(file_messages_proto_rawDesc), len(file_messages_proto_rawDesc)),
|
||||||
NumEnums: 0,
|
NumEnums: 0,
|
||||||
NumMessages: 14,
|
NumMessages: 15,
|
||||||
NumExtensions: 0,
|
NumExtensions: 0,
|
||||||
NumServices: 0,
|
NumServices: 0,
|
||||||
},
|
},
|
||||||
|
|||||||
347
pkg/voucher/parser.go
Normal file
347
pkg/voucher/parser.go
Normal file
@@ -0,0 +1,347 @@
|
|||||||
|
package voucher
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
"fmt"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
"unicode"
|
||||||
|
)
|
||||||
|
|
||||||
|
/*
|
||||||
|
Package voucher - rule parser
|
||||||
|
|
||||||
|
A lightweight parser for voucher rule expressions.
|
||||||
|
|
||||||
|
Supported rule kinds (case-insensitive keywords):
|
||||||
|
|
||||||
|
sku=SKU1|SKU2|SKU3
|
||||||
|
- At least one of the listed SKUs must be present in the cart.
|
||||||
|
|
||||||
|
category=CatA|CatB|CatC
|
||||||
|
- At least one of the listed categories must be present.
|
||||||
|
|
||||||
|
min_total>=12345
|
||||||
|
- Cart total (Inc VAT) must be at least this value (int64).
|
||||||
|
|
||||||
|
min_item_price>=5000
|
||||||
|
- At least one individual item (Inc VAT single unit price) must be at least this value (int64).
|
||||||
|
|
||||||
|
Rule list grammar (simplified):
|
||||||
|
rules := rule (sep rule)*
|
||||||
|
rule := (sku|category) '=' valueList
|
||||||
|
| (min_total|min_item_price) comparator number
|
||||||
|
valueList := value ('|' value)*
|
||||||
|
comparator := '>=' (only comparator currently supported for numeric rules)
|
||||||
|
sep := ';' | ',' | newline
|
||||||
|
|
||||||
|
Whitespace is ignored around tokens.
|
||||||
|
|
||||||
|
Example:
|
||||||
|
sku=ABC123|XYZ999; category=Shoes|Bags
|
||||||
|
min_total>=10000
|
||||||
|
min_item_price>=2500, category=Accessories
|
||||||
|
|
||||||
|
Parsing returns a RuleSet which can later be evaluated against a generic context.
|
||||||
|
The evaluation context uses simple Item abstractions to avoid tight coupling with
|
||||||
|
the cart implementation (which currently lives under cmd/cart and cannot be
|
||||||
|
imported due to being in package main).
|
||||||
|
|
||||||
|
This is intentionally conservative and extensible:
|
||||||
|
* Adding new rule kinds: extend RuleKind constants, add parse + evaluate logic.
|
||||||
|
* Supporting new operators: extend numeric rule parsing & evaluation.
|
||||||
|
*/
|
||||||
|
|
||||||
|
var (
|
||||||
|
// ErrEmptyExpression is returned when the input string has only whitespace.
|
||||||
|
ErrEmptyExpression = errors.New("voucher: empty rule expression")
|
||||||
|
// ErrInvalidRule indicates a syntactic or semantic issue with a single rule fragment.
|
||||||
|
ErrInvalidRule = errors.New("voucher: invalid rule")
|
||||||
|
)
|
||||||
|
|
||||||
|
// RuleKind enumerates supported rule kinds.
|
||||||
|
type RuleKind string
|
||||||
|
|
||||||
|
const (
|
||||||
|
RuleSku RuleKind = "sku"
|
||||||
|
RuleCategory RuleKind = "category"
|
||||||
|
RuleMinTotal RuleKind = "min_total"
|
||||||
|
RuleMinItemPrice RuleKind = "min_item_price"
|
||||||
|
)
|
||||||
|
|
||||||
|
// ruleCondition represents a single, parsed rule.
|
||||||
|
type ruleCondition struct {
|
||||||
|
Kind RuleKind
|
||||||
|
StringVals []string // For sku / category multi-value list
|
||||||
|
MinValue *int64 // For numeric threshold rules
|
||||||
|
// Operator reserved for future (e.g., >, >=, ==). Currently always ">=" for numeric kinds.
|
||||||
|
Operator string
|
||||||
|
}
|
||||||
|
|
||||||
|
// RuleSet groups multiple rule conditions (logical AND).
|
||||||
|
// All conditions must pass for Applies() to return true.
|
||||||
|
type RuleSet struct {
|
||||||
|
Conditions []ruleCondition
|
||||||
|
Source string // original, trimmed source string
|
||||||
|
}
|
||||||
|
|
||||||
|
// Item is a minimal abstraction for evaluation (decoupled from cart domain structs).
|
||||||
|
type Item struct {
|
||||||
|
Sku string
|
||||||
|
Category string
|
||||||
|
UnitPrice int64 // Inc VAT (single unit)
|
||||||
|
}
|
||||||
|
|
||||||
|
// EvalContext bundles cart-like data necessary for evaluation.
|
||||||
|
type EvalContext struct {
|
||||||
|
Items []Item
|
||||||
|
CartTotalInc int64
|
||||||
|
}
|
||||||
|
|
||||||
|
// Applies returns true if all rule conditions pass for the context.
|
||||||
|
func (rs *RuleSet) Applies(ctx EvalContext) bool {
|
||||||
|
for _, c := range rs.Conditions {
|
||||||
|
switch c.Kind {
|
||||||
|
case RuleSku:
|
||||||
|
if !anyItem(ctx.Items, func(it Item) bool {
|
||||||
|
return containsFold(c.StringVals, it.Sku)
|
||||||
|
}) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
case RuleCategory:
|
||||||
|
if !anyItem(ctx.Items, func(it Item) bool {
|
||||||
|
return containsFold(c.StringVals, it.Category)
|
||||||
|
}) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
case RuleMinTotal:
|
||||||
|
if c.MinValue == nil || ctx.CartTotalInc < *c.MinValue {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
case RuleMinItemPrice:
|
||||||
|
if c.MinValue == nil {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
if !anyItem(ctx.Items, func(it Item) bool {
|
||||||
|
return it.UnitPrice >= *c.MinValue
|
||||||
|
}) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
// Unknown kinds fail closed to avoid granting unintended discounts.
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
// anyItem returns true if predicate matches any item.
|
||||||
|
func anyItem(items []Item, pred func(Item) bool) bool {
|
||||||
|
for _, it := range items {
|
||||||
|
if pred(it) {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
// ParseRules parses a rule expression into a RuleSet.
|
||||||
|
func ParseRules(input string) (*RuleSet, error) {
|
||||||
|
trimmed := strings.TrimSpace(input)
|
||||||
|
if trimmed == "" {
|
||||||
|
return nil, ErrEmptyExpression
|
||||||
|
}
|
||||||
|
|
||||||
|
fragments := splitRuleFragments(trimmed)
|
||||||
|
if len(fragments) == 0 {
|
||||||
|
return nil, ErrInvalidRule
|
||||||
|
}
|
||||||
|
|
||||||
|
var conditions []ruleCondition
|
||||||
|
for _, frag := range fragments {
|
||||||
|
if frag == "" {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
c, err := parseFragment(frag)
|
||||||
|
if err != nil {
|
||||||
|
return nil, fmt.Errorf("%w: %s (%v)", ErrInvalidRule, frag, err)
|
||||||
|
}
|
||||||
|
conditions = append(conditions, c)
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(conditions) == 0 {
|
||||||
|
return nil, ErrInvalidRule
|
||||||
|
}
|
||||||
|
|
||||||
|
return &RuleSet{
|
||||||
|
Conditions: conditions,
|
||||||
|
Source: trimmed,
|
||||||
|
}, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// splitRuleFragments splits on ; , or newline, while respecting basic structure.
|
||||||
|
func splitRuleFragments(s string) []string {
|
||||||
|
// Normalize line endings
|
||||||
|
s = strings.ReplaceAll(s, "\r\n", "\n")
|
||||||
|
|
||||||
|
// We allow separators: newline, semicolon, comma.
|
||||||
|
seps := func(r rune) bool {
|
||||||
|
return r == ';' || r == '\n' || r == ','
|
||||||
|
}
|
||||||
|
raw := strings.FieldsFunc(s, seps)
|
||||||
|
out := make([]string, 0, len(raw))
|
||||||
|
for _, f := range raw {
|
||||||
|
t := strings.TrimSpace(f)
|
||||||
|
if t != "" {
|
||||||
|
out = append(out, t)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
|
||||||
|
// parseFragment parses an individual rule fragment.
|
||||||
|
func parseFragment(frag string) (ruleCondition, error) {
|
||||||
|
lower := strings.ToLower(frag)
|
||||||
|
|
||||||
|
// Numeric rules have form: <kind> >= number
|
||||||
|
if strings.HasPrefix(lower, string(RuleMinTotal)) ||
|
||||||
|
strings.HasPrefix(lower, string(RuleMinItemPrice)) {
|
||||||
|
|
||||||
|
return parseNumericRule(frag)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Key=Value list rules (sku / category).
|
||||||
|
if i := strings.Index(frag, "="); i > 0 {
|
||||||
|
key := strings.TrimSpace(frag[:i])
|
||||||
|
valPart := strings.TrimSpace(frag[i+1:])
|
||||||
|
if key == "" || valPart == "" {
|
||||||
|
return ruleCondition{}, errors.New("empty key/value")
|
||||||
|
}
|
||||||
|
kind := RuleKind(strings.ToLower(key))
|
||||||
|
switch kind {
|
||||||
|
case RuleSku, RuleCategory:
|
||||||
|
values := splitAndClean(valPart, "|")
|
||||||
|
if len(values) == 0 {
|
||||||
|
return ruleCondition{}, errors.New("empty value list")
|
||||||
|
}
|
||||||
|
return ruleCondition{
|
||||||
|
Kind: kind,
|
||||||
|
StringVals: values,
|
||||||
|
}, nil
|
||||||
|
default:
|
||||||
|
return ruleCondition{}, fmt.Errorf("unsupported key '%s'", key)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return ruleCondition{}, fmt.Errorf("unrecognized fragment '%s'", frag)
|
||||||
|
}
|
||||||
|
|
||||||
|
func parseNumericRule(frag string) (ruleCondition, error) {
|
||||||
|
// Support only '>=' for now.
|
||||||
|
var kind RuleKind
|
||||||
|
var rest string
|
||||||
|
|
||||||
|
fragTrim := strings.TrimSpace(frag)
|
||||||
|
|
||||||
|
switch {
|
||||||
|
case strings.HasPrefix(strings.ToLower(fragTrim), string(RuleMinTotal)):
|
||||||
|
kind = RuleMinTotal
|
||||||
|
rest = strings.TrimSpace(fragTrim[len(RuleMinTotal):])
|
||||||
|
case strings.HasPrefix(strings.ToLower(fragTrim), string(RuleMinItemPrice)):
|
||||||
|
kind = RuleMinItemPrice
|
||||||
|
rest = strings.TrimSpace(fragTrim[len(RuleMinItemPrice):])
|
||||||
|
default:
|
||||||
|
return ruleCondition{}, fmt.Errorf("unknown numeric rule '%s'", frag)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Expect operator and number (>= <number>)
|
||||||
|
rest = stripLeadingSpace(rest)
|
||||||
|
if !strings.HasPrefix(rest, ">=") {
|
||||||
|
return ruleCondition{}, fmt.Errorf("expected '>=' in '%s'", frag)
|
||||||
|
}
|
||||||
|
numStr := strings.TrimSpace(rest[2:])
|
||||||
|
if numStr == "" {
|
||||||
|
return ruleCondition{}, fmt.Errorf("missing numeric value in '%s'", frag)
|
||||||
|
}
|
||||||
|
|
||||||
|
value, err := strconv.ParseInt(numStr, 10, 64)
|
||||||
|
if err != nil {
|
||||||
|
return ruleCondition{}, fmt.Errorf("invalid number '%s': %v", numStr, err)
|
||||||
|
}
|
||||||
|
if value < 0 {
|
||||||
|
return ruleCondition{}, fmt.Errorf("negative threshold %d", value)
|
||||||
|
}
|
||||||
|
|
||||||
|
return ruleCondition{
|
||||||
|
Kind: kind,
|
||||||
|
MinValue: &value,
|
||||||
|
Operator: ">=",
|
||||||
|
}, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func stripLeadingSpace(s string) string {
|
||||||
|
for len(s) > 0 && unicode.IsSpace(rune(s[0])) {
|
||||||
|
s = s[1:]
|
||||||
|
}
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func splitAndClean(s string, sep string) []string {
|
||||||
|
raw := strings.Split(s, sep)
|
||||||
|
out := make([]string, 0, len(raw))
|
||||||
|
for _, r := range raw {
|
||||||
|
t := strings.TrimSpace(r)
|
||||||
|
if t != "" {
|
||||||
|
out = append(out, t)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
|
||||||
|
func containsFold(list []string, candidate string) bool {
|
||||||
|
for _, v := range list {
|
||||||
|
if strings.EqualFold(v, candidate) {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
// Describe returns a human-friendly summary of the parsed rule set.
|
||||||
|
func (rs *RuleSet) Describe() string {
|
||||||
|
if rs == nil {
|
||||||
|
return "<nil>"
|
||||||
|
}
|
||||||
|
var parts []string
|
||||||
|
for _, c := range rs.Conditions {
|
||||||
|
switch c.Kind {
|
||||||
|
case RuleSku, RuleCategory:
|
||||||
|
parts = append(parts, fmt.Sprintf("%s in (%s)", c.Kind, strings.Join(c.StringVals, "|")))
|
||||||
|
case RuleMinTotal, RuleMinItemPrice:
|
||||||
|
if c.MinValue != nil {
|
||||||
|
parts = append(parts, fmt.Sprintf("%s %s %d", c.Kind, c.OperatorOr(">="), *c.MinValue))
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
parts = append(parts, fmt.Sprintf("unknown(%s)", c.Kind))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return strings.Join(parts, " AND ")
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c ruleCondition) OperatorOr(def string) string {
|
||||||
|
if c.Operator == "" {
|
||||||
|
return def
|
||||||
|
}
|
||||||
|
return c.Operator
|
||||||
|
}
|
||||||
|
|
||||||
|
// --- Convenience helpers for incremental adoption ---
|
||||||
|
|
||||||
|
// MustParseRules panics on parse error (useful in tests or static initialization).
|
||||||
|
func MustParseRules(expr string) *RuleSet {
|
||||||
|
rs, err := ParseRules(expr)
|
||||||
|
if err != nil {
|
||||||
|
panic(err)
|
||||||
|
}
|
||||||
|
return rs
|
||||||
|
}
|
||||||
179
pkg/voucher/parser_test.go
Normal file
179
pkg/voucher/parser_test.go
Normal file
@@ -0,0 +1,179 @@
|
|||||||
|
package voucher
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestParseRules_SimpleSku(t *testing.T) {
|
||||||
|
rs, err := ParseRules("sku=ABC123|XYZ999|def456")
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("unexpected error: %v", err)
|
||||||
|
}
|
||||||
|
if len(rs.Conditions) != 1 {
|
||||||
|
t.Fatalf("expected 1 condition got %d", len(rs.Conditions))
|
||||||
|
}
|
||||||
|
c := rs.Conditions[0]
|
||||||
|
if c.Kind != RuleSku {
|
||||||
|
t.Fatalf("expected kind sku got %s", c.Kind)
|
||||||
|
}
|
||||||
|
if len(c.StringVals) != 3 {
|
||||||
|
t.Fatalf("expected 3 sku values got %d", len(c.StringVals))
|
||||||
|
}
|
||||||
|
want := []string{"ABC123", "XYZ999", "def456"}
|
||||||
|
for i, v := range want {
|
||||||
|
if c.StringVals[i] != v {
|
||||||
|
t.Fatalf("expected sku[%d]=%s got %s", i, v, c.StringVals[i])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestParseRules_CategoryAndSkuMixedSeparators(t *testing.T) {
|
||||||
|
rs, err := ParseRules(" category=Shoes|Bags ; sku= A | B , min_total>=1000\nmin_item_price>=500")
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("unexpected error: %v", err)
|
||||||
|
}
|
||||||
|
if len(rs.Conditions) != 4 {
|
||||||
|
t.Fatalf("expected 4 conditions got %d", len(rs.Conditions))
|
||||||
|
}
|
||||||
|
|
||||||
|
kinds := []RuleKind{RuleCategory, RuleSku, RuleMinTotal, RuleMinItemPrice}
|
||||||
|
for i, k := range kinds {
|
||||||
|
if rs.Conditions[i].Kind != k {
|
||||||
|
t.Fatalf("expected condition[%d] kind %s got %s", i, k, rs.Conditions[i].Kind)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Validate numeric thresholds
|
||||||
|
if rs.Conditions[2].MinValue == nil || *rs.Conditions[2].MinValue != 1000 {
|
||||||
|
t.Fatalf("expected min_total>=1000 got %+v", rs.Conditions[2])
|
||||||
|
}
|
||||||
|
if rs.Conditions[3].MinValue == nil || *rs.Conditions[3].MinValue != 500 {
|
||||||
|
t.Fatalf("expected min_item_price>=500 got %+v", rs.Conditions[3])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestParseRules_Empty(t *testing.T) {
|
||||||
|
_, err := ParseRules(" \n ")
|
||||||
|
if !errors.Is(err, ErrEmptyExpression) {
|
||||||
|
t.Fatalf("expected ErrEmptyExpression got %v", err)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestParseRules_Invalid(t *testing.T) {
|
||||||
|
_, err := ParseRules("unknown=foo")
|
||||||
|
if err == nil {
|
||||||
|
t.Fatal("expected error for unknown key")
|
||||||
|
}
|
||||||
|
_, err = ParseRules("min_total>100") // wrong operator
|
||||||
|
if err == nil {
|
||||||
|
t.Fatal("expected error for wrong operator")
|
||||||
|
}
|
||||||
|
_, err = ParseRules("min_total>=") // missing value
|
||||||
|
if err == nil {
|
||||||
|
t.Fatal("expected error for missing numeric value")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestRuleSet_Applies(t *testing.T) {
|
||||||
|
rs := MustParseRules("sku=ABC123|XYZ999; category=Shoes|min_total>=10000; min_item_price>=3000")
|
||||||
|
|
||||||
|
ctx := EvalContext{
|
||||||
|
Items: []Item{
|
||||||
|
{Sku: "ABC123", Category: "Shoes", UnitPrice: 2500},
|
||||||
|
{Sku: "FFF000", Category: "Accessories", UnitPrice: 3200},
|
||||||
|
},
|
||||||
|
CartTotalInc: 12000,
|
||||||
|
}
|
||||||
|
|
||||||
|
if !rs.Applies(ctx) {
|
||||||
|
t.Fatalf("expected rules to apply")
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fail due to missing sku/category
|
||||||
|
ctx2 := EvalContext{
|
||||||
|
Items: []Item{
|
||||||
|
{Sku: "NOPE", Category: "Different", UnitPrice: 4000},
|
||||||
|
},
|
||||||
|
CartTotalInc: 20000,
|
||||||
|
}
|
||||||
|
if rs.Applies(ctx2) {
|
||||||
|
t.Fatalf("expected rules NOT to apply (sku/category mismatch)")
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fail due to min_total
|
||||||
|
ctx3 := EvalContext{
|
||||||
|
Items: []Item{
|
||||||
|
{Sku: "ABC123", Category: "Shoes", UnitPrice: 2500},
|
||||||
|
{Sku: "FFF000", Category: "Accessories", UnitPrice: 3200},
|
||||||
|
},
|
||||||
|
CartTotalInc: 9000,
|
||||||
|
}
|
||||||
|
if rs.Applies(ctx3) {
|
||||||
|
t.Fatalf("expected rules NOT to apply (min_total not reached)")
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fail due to min_item_price (no item >=3000)
|
||||||
|
ctx4 := EvalContext{
|
||||||
|
Items: []Item{
|
||||||
|
{Sku: "ABC123", Category: "Shoes", UnitPrice: 2500},
|
||||||
|
{Sku: "FFF000", Category: "Accessories", UnitPrice: 2800},
|
||||||
|
},
|
||||||
|
CartTotalInc: 15000,
|
||||||
|
}
|
||||||
|
if rs.Applies(ctx4) {
|
||||||
|
t.Fatalf("expected rules NOT to apply (min_item_price not satisfied)")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestRuleSet_Applies_CaseInsensitive(t *testing.T) {
|
||||||
|
rs := MustParseRules("SKU=abc123|xyz999; CATEGORY=Shoes")
|
||||||
|
ctx := EvalContext{
|
||||||
|
Items: []Item{
|
||||||
|
{Sku: "AbC123", Category: "shoes", UnitPrice: 1000},
|
||||||
|
},
|
||||||
|
CartTotalInc: 1000,
|
||||||
|
}
|
||||||
|
if !rs.Applies(ctx) {
|
||||||
|
t.Fatalf("expected rules to apply (case-insensitive match)")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestDescribe(t *testing.T) {
|
||||||
|
rs := MustParseRules("sku=A|B|min_total>=500")
|
||||||
|
desc := rs.Describe()
|
||||||
|
// Loose assertions to avoid over-specification
|
||||||
|
if desc == "" {
|
||||||
|
t.Fatalf("expected non-empty description")
|
||||||
|
}
|
||||||
|
if !(contains(desc, "sku") && contains(desc, "min_total")) {
|
||||||
|
t.Fatalf("description missing expected parts: %s", desc)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func contains(haystack, needle string) bool {
|
||||||
|
return len(haystack) >= len(needle) && indexOf(haystack, needle) >= 0
|
||||||
|
}
|
||||||
|
|
||||||
|
// Simple substring search (avoid importing strings to show intent explicitly here)
|
||||||
|
func indexOf(s, sub string) int {
|
||||||
|
outer:
|
||||||
|
for i := 0; i+len(sub) <= len(s); i++ {
|
||||||
|
for j := 0; j < len(sub); j++ {
|
||||||
|
if s[i+j] != sub[j] {
|
||||||
|
continue outer
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return i
|
||||||
|
}
|
||||||
|
return -1
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestMustParseRules_Panics(t *testing.T) {
|
||||||
|
defer func() {
|
||||||
|
if r := recover(); r == nil {
|
||||||
|
t.Fatalf("expected panic for invalid expression")
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
MustParseRules("~~ totally invalid ~~")
|
||||||
|
}
|
||||||
@@ -2,7 +2,8 @@ package voucher
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"errors"
|
"errors"
|
||||||
"math"
|
|
||||||
|
"git.tornberg.me/go-cart-actor/pkg/messages"
|
||||||
)
|
)
|
||||||
|
|
||||||
type Rule struct {
|
type Rule struct {
|
||||||
@@ -25,16 +26,14 @@ type Service struct {
|
|||||||
|
|
||||||
var ErrInvalidCode = errors.New("invalid vouchercode")
|
var ErrInvalidCode = errors.New("invalid vouchercode")
|
||||||
|
|
||||||
func (s *Service) GetVoucher(code string) (*Voucher, error) {
|
func (s *Service) GetVoucher(code string) (*messages.AddVoucher, error) {
|
||||||
value := int64(math.Round(100 * math.Pow(10, 2)))
|
|
||||||
if code == "" {
|
if code == "" {
|
||||||
return nil, ErrInvalidCode
|
return nil, ErrInvalidCode
|
||||||
}
|
}
|
||||||
return &Voucher{
|
value := int64(250_00)
|
||||||
|
return &messages.AddVoucher{
|
||||||
Code: code,
|
Code: code,
|
||||||
Value: value,
|
Value: value,
|
||||||
TaxValue: int64(float64(value) * 0.2),
|
VoucherRules: make([]*messages.VoucherRule, 0),
|
||||||
TaxRate: 2500,
|
|
||||||
rules: nil,
|
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,7 +7,7 @@ message ClearCartRequest {
|
|||||||
}
|
}
|
||||||
|
|
||||||
message AddItem {
|
message AddItem {
|
||||||
int64 item_id = 1;
|
uint32 item_id = 1;
|
||||||
int32 quantity = 2;
|
int32 quantity = 2;
|
||||||
int64 price = 3;
|
int64 price = 3;
|
||||||
int64 orgPrice = 9;
|
int64 orgPrice = 9;
|
||||||
@@ -33,17 +33,17 @@ message AddItem {
|
|||||||
}
|
}
|
||||||
|
|
||||||
message RemoveItem {
|
message RemoveItem {
|
||||||
int64 Id = 1;
|
uint32 Id = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
message ChangeQuantity {
|
message ChangeQuantity {
|
||||||
int64 id = 1;
|
uint32 Id = 1;
|
||||||
int32 quantity = 2;
|
int32 quantity = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
message SetDelivery {
|
message SetDelivery {
|
||||||
string provider = 1;
|
string provider = 1;
|
||||||
repeated int64 items = 2;
|
repeated uint32 items = 2;
|
||||||
optional PickupPoint pickupPoint = 3;
|
optional PickupPoint pickupPoint = 3;
|
||||||
string country = 4;
|
string country = 4;
|
||||||
string zip = 5;
|
string zip = 5;
|
||||||
@@ -52,7 +52,7 @@ message SetDelivery {
|
|||||||
}
|
}
|
||||||
|
|
||||||
message SetPickupPoint {
|
message SetPickupPoint {
|
||||||
int64 deliveryId = 1;
|
uint32 deliveryId = 1;
|
||||||
string id = 2;
|
string id = 2;
|
||||||
optional string name = 3;
|
optional string name = 3;
|
||||||
optional string address = 4;
|
optional string address = 4;
|
||||||
@@ -71,7 +71,7 @@ message PickupPoint {
|
|||||||
}
|
}
|
||||||
|
|
||||||
message RemoveDelivery {
|
message RemoveDelivery {
|
||||||
int64 id = 1;
|
uint32 id = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
message CreateCheckoutOrder {
|
message CreateCheckoutOrder {
|
||||||
@@ -98,6 +98,19 @@ message InitializeCheckout {
|
|||||||
bool paymentInProgress = 3;
|
bool paymentInProgress = 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
message VoucherRule {
|
||||||
|
string type = 2;
|
||||||
|
string description = 3;
|
||||||
|
string condition = 4;
|
||||||
|
string action = 5;
|
||||||
|
}
|
||||||
|
|
||||||
message AddVoucher {
|
message AddVoucher {
|
||||||
string code = 1;
|
string code = 1;
|
||||||
|
int64 value = 2;
|
||||||
|
repeated VoucherRule voucherRules = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message RemoveVoucher {
|
||||||
|
uint32 id = 1;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user