feat(notify): Gets the available notification types for the receiver

This commit is contained in:
rainzm
2021-07-12 19:36:16 +08:00
parent fedfe32ada
commit f591013358
5 changed files with 71 additions and 14 deletions
+7 -3
View File
@@ -80,9 +80,13 @@ type ConfigValidateOutput struct {
}
type ConfigManagerGetTypesInput struct {
// description: domain where in config
// example: default
Domain string `json:"domain"`
// description: View the available notification channels for the domains with these DomainIds
// required: true
DomainIds []string `json:"domain_ids"`
// description: Operation of reduce
// required: false
// enum: union,merge
Operation string `json:"operation"`
}
type ConfigManagerGetTypesOutput struct {
+1 -1
View File
@@ -35,7 +35,7 @@ func init() {
NotifyReceiver = NewNotifyv2Manager(
"receiver",
"receivers",
[]string{"ID", "Name", "Email", "International_Mobile", "Enabled_Contact_Types", "Verified_Infos"},
[]string{"ID", "Name", "Domain_Id", "Project_Domain", "Email", "International_Mobile", "Enabled_Contact_Types", "Verified_Infos"},
[]string{},
)
register(&NotifyReceiver)
+2 -1
View File
@@ -125,7 +125,8 @@ func (ri *ReceiverIntellijGetOptions) Params() (jsonutils.JSONObject, error) {
}
type ReceiverGetTypeOptions struct {
Domain string `help:"Domain under where available contact methods"`
DomainIds []string `help:"View the available notification channels for the domains with these DomainIds"`
Operation string `help:"Operation of reduce" choices:"merge|union"`
}
func (rg *ReceiverGetTypeOptions) Params() (jsonutils.JSONObject, error) {
+11 -1
View File
@@ -63,7 +63,7 @@ type SConfig struct {
db.SStandaloneResourceBase
db.SDomainizedResourceBase
Type string `width:"15" nullable:"false" create:"required" get:"domain" list:"domain"`
Type string `width:"15" nullable:"false" create:"required" get:"domain" list:"domain" index:"true"`
Content jsonutils.JSONObject `nullable:"false" create:"required" update:"domain" get:"domain" list:"domain"`
Attribution string `width:"8" nullable:"false" default:"system" get:"domain" list:"domain" create:"optional"`
}
@@ -234,6 +234,16 @@ func sortContactType(ctypes []string) []string {
return ret
}
func (cm *SConfigManager) contactTypesQuery(domainId string) *sqlchemy.SQuery {
q := cm.Query("type").Distinct()
if domainId == "" {
q = q.Equals("attribution", api.CONFIG_ATTRIBUTION_SYSTEM)
} else {
q = q.Filter(sqlchemy.OR(sqlchemy.AND(sqlchemy.Equals(q.Field("attribution"), api.CONFIG_ATTRIBUTION_DOMAIN), sqlchemy.Equals(q.Field("domain_id"), domainId)), sqlchemy.Equals(q.Field("attribution"), api.CONFIG_ATTRIBUTION_SYSTEM)))
}
return q
}
func (cm *SConfigManager) availableContactTypes(domainId string) ([]string, error) {
q := cm.Query("type")
q = q.Filter(sqlchemy.OR(sqlchemy.AND(sqlchemy.Equals(q.Field("attribution"), api.CONFIG_ATTRIBUTION_DOMAIN), sqlchemy.Equals(q.Field("domain_id"), domainId)), sqlchemy.Equals(q.Field("attribution"), api.CONFIG_ATTRIBUTION_SYSTEM)))
+50 -8
View File
@@ -695,16 +695,58 @@ func (r *SReceiverManager) AllowPerformGetTypes(ctx context.Context, userCred mc
func (rm *SReceiverManager) PerformGetTypes(ctx context.Context, userCred mcclient.TokenCredential, query jsonutils.JSONObject, input api.ConfigManagerGetTypesInput) (api.ConfigManagerGetTypesOutput, error) {
output := api.ConfigManagerGetTypesOutput{}
t, err := db.TenantCacheManager.FetchDomainByIdOrName(ctx, input.Domain)
if err != nil {
return output, errors.Wrap(err, "unable to FetchDomainByIdOrName")
var reduce func([]*sqlchemy.SQuery) *sqlchemy.SQuery
var err error
switch input.Operation {
case "", "merge":
reduce = func(qs []*sqlchemy.SQuery) *sqlchemy.SQuery {
q := qs[0]
for i := 1; i < len(qs); i++ {
q = q.In("type", qs[i])
}
return q
}
case "union":
reduce = func(qs []*sqlchemy.SQuery) *sqlchemy.SQuery {
if len(qs) == 1 {
return qs[0]
}
iqs := make([]sqlchemy.IQuery, 0, len(qs))
for i := range qs {
iqs = append(iqs, qs[i])
}
union, _ := sqlchemy.UnionWithError(iqs...)
if err != nil {
}
return union.Query()
}
default:
return output, httperrors.NewInputParameterError("unkown operation %q", input.Operation)
}
ret, err := ConfigManager.availableContactTypes(t.Id)
if err != nil {
return output, errors.Wrap(err, "unable to get available contact types")
domainIds := sets.NewString(input.DomainIds...).UnsortedList()
qs := make([]*sqlchemy.SQuery, 0, len(domainIds))
if len(domainIds) == 0 {
qs = append(qs, ConfigManager.contactTypesQuery(""))
} else {
for i := range domainIds {
ctypeQ := ConfigManager.contactTypesQuery(domainIds[i])
qs = append(qs, ctypeQ)
}
}
output.Types = sortContactType(ret)
q := reduce(qs)
q.DebugQuery()
allTypes := make([]struct {
Type string
}, 0, 3)
err = q.All(&allTypes)
if err != nil {
return output, err
}
ret := make([]string, len(allTypes))
for i := range ret {
ret[i] = allTypes[i].Type
}
output.Types = ret
return output, nil
}