package sharedmodel

import (
	"encoding/json"

	"google.golang.org/protobuf/types/known/structpb"
	"gorm.io/gorm"
	"src.whiteboxsystems.nl/DECOZO/okapi"
)

type ServiceDefinition struct {
	gorm.Model
	ServiceID          string
	Name               string
	Description        string
	SubscriptionPolicy okapi.SubscriptionPolicy
	ConsentPolicy      okapi.ConsentPolicy
	FetchProtocols     ProtocolArray `gorm:"type:text"`
	PushProtocols      ProtocolArray `gorm:"type:text"`
}

func (s ServiceDefinition) GetFetchProtocols() []*okapi.ProtocolDefinition {
	protoDefs := []*okapi.ProtocolDefinition{}
	for _, sd := range s.FetchProtocols {
		protoDefs = append(protoDefs, &okapi.ProtocolDefinition{
			Protocol:    sd.Protocol,
			AuthMethods: sd.AuthMethods,
		})
	}

	return protoDefs
}

func (s ServiceDefinition) GetPushProtocols() []*okapi.ProtocolDefinition {
	protoDefs := []*okapi.ProtocolDefinition{}
	for _, sd := range s.PushProtocols {
		protoDefs = append(protoDefs, &okapi.ProtocolDefinition{
			Protocol:    sd.Protocol,
			AuthMethods: sd.AuthMethods,
		})
	}

	return protoDefs
}

type ProtocolConfig struct {
	gorm.Model
	Protocol     string
	AuthConfigID uint
	AuthConfig   *AuthConfig `gorm:"constraint:OnDelete:CASCADE;"`
	Config       string
}

func (pc ProtocolConfig) UnmarshalConfig(in interface{}) error {
	return json.Unmarshal([]byte(pc.Config), in)
}

func (pc ProtocolConfig) ConfigToOkapi() *structpb.Struct {
	config := map[string]interface{}{}
	pc.UnmarshalConfig(&config)

	cnf, _ := structpb.NewStruct(config)

	return cnf
}

func (pc *ProtocolConfig) SetConfig(in interface{}) error {
	b, err := json.Marshal(in)
	if err != nil {
		return err
	}

	pc.Config = string(b)
	return nil
}

type ServiceConfig struct {
	gorm.Model
	ServiceID       uint
	Service         ServiceDefinition
	ConnectionID    uint
	Connection      Connection `json:"-"`
	PushProtocolID  uint
	PushProtocol    *ProtocolConfig `gorm:"foreignKey:PushProtocolID;constraint:OnDelete:CASCADE;"`
	FetchProtocolID uint
	FetchProtocol   *ProtocolConfig `gorm:"foreignKey:FetchProtocolID;constraint:OnDelete:CASCADE;"`
	Subscriptions   []*Subscription `gorm:"constraint:OnDelete:CASCADE;"`
}
