omnix-sopiga/repository/broadcast.go

172 lines
4.7 KiB
Go
Raw Normal View History

package repository
import (
"context"
"encoding/json"
"fmt"
"github.com/jackc/pgx/v5/pgxpool"
"repository.promas.id/prana/omnix-sopiga/entity"
)
type Repository struct {
pool *pgxpool.Pool
}
func New(pool *pgxpool.Pool) *Repository {
return &Repository{pool: pool}
}
func (r *Repository) FindPending(ctx context.Context, limit int) ([]*entity.BroadcastStaging, error) {
query := `
SELECT
id, sopiga_collar_id, sopiga_template_id, message_payload,
status, error_message, error_count, sopiga_recipient_detail_id,
created_at, updated_at
FROM collection_broadcasts.broadcast_staging
WHERE status = 'pending'
ORDER BY created_at ASC
LIMIT $1
`
rows, err := r.pool.Query(ctx, query, limit)
if err != nil {
return nil, fmt.Errorf("find pending: %w", err)
}
defer rows.Close()
var records []*entity.BroadcastStaging
for rows.Next() {
var e entity.BroadcastStaging
if err := rows.Scan(
&e.ID, &e.SopigaCollarID, &e.SopigaTemplateID, &e.MessagePayload,
&e.Status, &e.ErrorMessage, &e.ErrorCount, &e.SopigaRecipientDetailID,
&e.CreatedAt, &e.UpdatedAt,
); err != nil {
return nil, fmt.Errorf("scan: %w", err)
}
records = append(records, &e)
}
return records, rows.Err()
}
func (r *Repository) FindTemplateVariables(ctx context.Context, templateID int) ([]*entity.TemplateVariableMapping, error) {
query := `
SELECT variable_order, sopiga_variable_name, variable_type, db_field_source, is_required
FROM collection_broadcasts.template_variable_mapping
WHERE sopiga_template_id = $1
ORDER BY variable_order ASC
`
rows, err := r.pool.Query(ctx, query, templateID)
if err != nil {
return nil, fmt.Errorf("find template variables: %w", err)
}
defer rows.Close()
var variables []*entity.TemplateVariableMapping
for rows.Next() {
var v entity.TemplateVariableMapping
if err := rows.Scan(&v.VariableOrder, &v.SopigaVariableName, &v.VariableType, &v.DBFieldSource, &v.IsRequired); err != nil {
return nil, fmt.Errorf("scan: %w", err)
}
variables = append(variables, &v)
}
return variables, rows.Err()
}
func (r *Repository) FindByRecipientDetailID(ctx context.Context, recipientDetailID int64) (*entity.BroadcastStaging, error) {
query := `
SELECT
id, sopiga_collar_id, sopiga_template_id, message_payload,
status, error_message, error_count, sopiga_recipient_detail_id,
created_at, updated_at
FROM collection_broadcasts.broadcast_staging
WHERE sopiga_recipient_detail_id = $1
`
var e entity.BroadcastStaging
err := r.pool.QueryRow(ctx, query, recipientDetailID).Scan(
&e.ID, &e.SopigaCollarID, &e.SopigaTemplateID, &e.MessagePayload,
&e.Status, &e.ErrorMessage, &e.ErrorCount, &e.SopigaRecipientDetailID,
&e.CreatedAt, &e.UpdatedAt,
)
if err != nil {
return nil, fmt.Errorf("find by recipient_detail_id %d: %w", recipientDetailID, err)
}
return &e, nil
}
func (r *Repository) UpdateStatus(ctx context.Context, id int64, status, errMsg string, sopigaResponse any) error {
var respJSON []byte
if sopigaResponse != nil {
var err error
respJSON, err = json.Marshal(sopigaResponse)
if err != nil {
return fmt.Errorf("marshal sopiga response: %w", err)
}
}
query := `SELECT collection_broadcasts.update_broadcast_status($1, $2, $3, $4)`
_, err := r.pool.Exec(ctx, query, id, status, errMsg, respJSON)
if err != nil {
return fmt.Errorf("update status: %w", err)
}
return nil
}
func (r *Repository) FindDispatched(ctx context.Context, limit int) ([]*entity.BroadcastStaging, error) {
query := `
SELECT
id, sopiga_collar_id, sopiga_template_id, message_payload,
status, error_message, error_count, sopiga_recipient_detail_id,
created_at, updated_at
FROM collection_broadcasts.broadcast_staging
WHERE status = 'dispatched' AND sopiga_recipient_detail_id IS NOT NULL
ORDER BY dispatched_at ASC
LIMIT $1
`
rows, err := r.pool.Query(ctx, query, limit)
if err != nil {
return nil, fmt.Errorf("find dispatched: %w", err)
}
defer rows.Close()
var records []*entity.BroadcastStaging
for rows.Next() {
var e entity.BroadcastStaging
if err := rows.Scan(
&e.ID, &e.SopigaCollarID, &e.SopigaTemplateID, &e.MessagePayload,
&e.Status, &e.ErrorMessage, &e.ErrorCount, &e.SopigaRecipientDetailID,
&e.CreatedAt, &e.UpdatedAt,
); err != nil {
return nil, fmt.Errorf("scan: %w", err)
}
records = append(records, &e)
}
return records, rows.Err()
}
func (r *Repository) UpdateDispatched(ctx context.Context, id int64, recipientDetailID int64) error {
query := `
UPDATE collection_broadcasts.broadcast_staging
SET
status = 'dispatched',
sopiga_recipient_detail_id = $1,
dispatched_at = NOW(),
updated_at = NOW()
WHERE id = $2
`
_, err := r.pool.Exec(ctx, query, recipientDetailID, id)
if err != nil {
return fmt.Errorf("update dispatched: %w", err)
}
return nil
}