github.com/wfusion/gofusion@v1.1.14/mq/postgres.go (about) 1 package mq 2 3 import ( 4 "context" 5 "database/sql" 6 "fmt" 7 8 "github.com/pkg/errors" 9 10 "github.com/wfusion/gofusion/common/infra/watermill" 11 "github.com/wfusion/gofusion/common/utils" 12 "github.com/wfusion/gofusion/config" 13 "github.com/wfusion/gofusion/db" 14 15 millSql "github.com/wfusion/gofusion/common/infra/watermill/pubsub/sql" 16 ) 17 18 func newPostgres(ctx context.Context, appName, name string, conf *Conf, logger watermill.LoggerAdapter) ( 19 pub Publisher, sub Subscriber) { 20 instance := db.Use(ctx, conf.Endpoint.Instance, db.AppName(appName)) 21 cli := utils.Must(instance.GetProxy().DB()) 22 if conf.Producer { 23 pub = newPostgresPublisher(ctx, appName, name, conf, logger, cli) 24 } 25 26 if conf.Consumer { 27 sub = newPostgresSubscriber(ctx, appName, name, conf, logger, cli) 28 } 29 30 return 31 } 32 33 type postgresPublisher struct { 34 *abstractMQ 35 publisher *millSql.Publisher 36 } 37 38 func newPostgresPublisher(ctx context.Context, appName, name string, conf *Conf, logger watermill.LoggerAdapter, 39 cli *sql.DB) Publisher { 40 cfg := millSql.PublisherConfig{ 41 SchemaAdapter: millSql.DefaultPostgreSQLSchema{ 42 GenerateMessagesTableName: func(topic string) string { 43 return fmt.Sprintf("%s_%s", conf.MessageScheme, topic) 44 }, 45 SubscribeBatchSize: conf.ConsumerConcurrency, 46 }, 47 AutoInitializeSchema: true, 48 AppID: config.Use(appName).AppName(), 49 } 50 51 pub, err := millSql.NewPublisher(cli, cfg, logger) 52 if err != nil { 53 panic(errors.Wrapf(err, "initialize mq component postgres publisher failed: %s", err)) 54 } 55 56 return &postgresPublisher{ 57 abstractMQ: newPub(ctx, pub, appName, name, conf, logger), 58 publisher: pub, 59 } 60 } 61 62 func (p *postgresPublisher) close() (err error) { 63 return p.publisher.Close() 64 } 65 66 type postgresSubscriber struct { 67 *abstractMQ 68 subscriber *millSql.Subscriber 69 } 70 71 func newPostgresSubscriber(ctx context.Context, appName, name string, conf *Conf, logger watermill.LoggerAdapter, 72 cli *sql.DB) Subscriber { 73 cfg := millSql.SubscriberConfig{ 74 ConsumerGroup: conf.ConsumerGroup, 75 PollInterval: 0, 76 ResendInterval: 0, 77 RetryInterval: 0, 78 BackoffManager: nil, 79 SchemaAdapter: millSql.DefaultPostgreSQLSchema{ 80 GenerateMessagesTableName: func(topic string) string { 81 return fmt.Sprintf("%s_%s", conf.MessageScheme, topic) 82 }, 83 SubscribeBatchSize: conf.ConsumerConcurrency, // fetch how many rows per query 84 }, 85 OffsetsAdapter: millSql.DefaultPostgreSQLOffsetsAdapter{ 86 GenerateMessagesOffsetsTableName: func(topic string) string { 87 return fmt.Sprintf("%s_offsets_%s", conf.MessageScheme, topic) 88 }, 89 }, 90 InitializeSchema: true, 91 DisablePersistent: !conf.Persistent, 92 } 93 94 sub, err := millSql.NewSubscriber(cli, cfg, logger) 95 if err != nil { 96 panic(errors.Wrapf(err, "initialize mq component mysql subscriber failed: %s", err)) 97 } 98 99 return &postgresSubscriber{ 100 abstractMQ: newSub(ctx, sub, appName, name, conf, logger), 101 subscriber: sub, 102 } 103 } 104 105 func (p *postgresSubscriber) close() (err error) { 106 return p.subscriber.Close() 107 }