diff --git a/README.md b/README.md index c5c3c870f..a0054f3cf 100644 --- a/README.md +++ b/README.md @@ -23,11 +23,6 @@ It is required that you have created a new database and imported the [schema](sc > **Note** > At the moment **PostgreSQL** is the only database backend we support. -Additionally, it also requires you to manually insert items into the **source** table before starting the daemon. -```sql -INSERT INTO source (id, type, name) VALUES (1, 'icinga2', 'Icinga 2') -``` - Then, you can launch the daemon with the following command. ```go go run ./cmd/icinga-notifications-daemon --config config.yml diff --git a/cmd/icinga-notifications-daemon/main.go b/cmd/icinga-notifications-daemon/main.go index b0f8f438c..9eee9fcb4 100644 --- a/cmd/icinga-notifications-daemon/main.go +++ b/cmd/icinga-notifications-daemon/main.go @@ -80,6 +80,7 @@ func main() { } } + conf.UpsertSources(logs.GetChildLogger("source"), db) channel.UpsertPlugins(conf.ChannelPluginDir, logs.GetChildLogger("channel"), db) ctx, cancel := signal.NotifyContext(context.Background(), syscall.SIGINT, syscall.SIGTERM) diff --git a/icinga2.conf b/icinga2.conf index f9a6e4b27..30ea357d4 100644 --- a/icinga2.conf +++ b/icinga2.conf @@ -5,7 +5,6 @@ if (!globals.contains("IcingaNotificationsIcingaWebUrl")) { const IcingaNotificationsIcingaWebUrl = "http://localhost/icingaweb2" } if (!globals.contains("IcingaNotificationsEventSourceId")) { - // INSERT INTO source (id, type, name) VALUES (1, 'icinga2', 'Icinga 2') const IcingaNotificationsEventSourceId = 1 } if (!globals.contains("IcingaNotificationsAuth")) { diff --git a/internal/daemon/config.go b/internal/daemon/config.go index b498e4e9c..5999b6b46 100644 --- a/internal/daemon/config.go +++ b/internal/daemon/config.go @@ -6,6 +6,9 @@ import ( "github.com/creasty/defaults" "github.com/goccy/go-yaml" icingadbConfig "github.com/icinga/icingadb/pkg/config" + "github.com/icinga/icingadb/pkg/icingadb" + "github.com/icinga/icingadb/pkg/logging" + "go.uber.org/zap" "os" ) @@ -105,6 +108,34 @@ func (c *ConfigFile) Validate() error { return nil } +// UpsertSources updates the source SQL table to contain all defined ConfigFile.Sources. +func (c *ConfigFile) UpsertSources(logger *logging.Logger, db *icingadb.DB) { + // Source is a subset of ConfigSource to only contain the necessary fields for the DB transaction. + // + // Unfortunately, DB.BuildColumns does include all struct fields with a tag, not only those with the "db" tag. The + // contracts.Upserter interface only results in allowing duplicates on the listed fields, but still inserts all. + type Source struct { + Id int64 `db:"id"` + Type string `db:"type"` + Name string `db:"name"` + } + + sources := make([]*Source, 0, len(c.Sources)) + for _, source := range c.Sources { + sources = append(sources, &Source{ + Id: source.Id, + Type: source.Type, + Name: source.Name, + }) + } + + stmt, _ := db.BuildUpsertStmt(&Source{}) + _, err := db.NamedExec(stmt, sources) + if err != nil { + logger.Errorw("Failed to update sources", zap.Error(err)) + } +} + // GetSource returns the ConfigSource for a requested ID. func (c *ConfigFile) GetSource(id int64) (ConfigSource, error) { for _, source := range c.Sources {