Skip to content

feat: wire multi-workflow mode into main server#124

Merged
intel352 merged 2 commits intomainfrom
feat/issue-113-multi-workflow
Feb 23, 2026
Merged

feat: wire multi-workflow mode into main server#124
intel352 merged 2 commits intomainfrom
feat/issue-113-multi-workflow

Conversation

@intel352
Copy link
Contributor

Summary

When -database-dsn is provided, the server now starts in multi-workflow mode instead of falling back to single-config mode with a TODO warning.

What changed

  • cmd/server/main.go: Replaced the TODO placeholder with a full runMultiWorkflow() implementation:

    1. Connects to PostgreSQL using the -database-dsn flag
    2. Runs database migrations via the existing store.Migrator
    3. Bootstraps an admin user when -admin-email and -admin-password are provided
    4. Creates a WorkflowEngineManager with all engine plugins registered
    5. Creates api.NewRouter() with all PG-backed stores and JWT config
    6. Mounts the REST API at /api/v1/ on the primary HTTP server (*addr)
    7. Admin UI continues to run on :8081 via the engine module system
  • -config as seed flag: When both -database-dsn and -config are provided, the YAML config is imported as the initial workflow into the database (idempotent — skips if slug already exists)

  • Backward compatibility: Without -database-dsn, the server behaves exactly as before (single-config mode, no changes)

  • Graceful shutdown: WorkflowEngineManager.StopAll(), the API HTTP server, and the admin engine are all shut down cleanly on SIGINT/SIGTERM

Minor formatting fixes

  • go fmt applied to 3 pre-existing formatting issues in module/ and plugins/api/

Closes #113

When -database-dsn is provided, the server starts in multi-workflow mode:
- Connects to PostgreSQL and runs migrations
- Creates WorkflowEngineManager for managing concurrent engines
- Mounts the REST API at /api/v1/ on the same HTTP server
- Bootstraps admin user when -admin-email and -admin-password are set
- -config flag becomes a seed for the initial workflow
- Without -database-dsn, single-config mode is preserved unchanged

Closes #113

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Copilot AI review requested due to automatic review settings February 23, 2026 10:40
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR implements multi-workflow mode for the server by wiring together PostgreSQL-backed storage, engine management, and REST API when the -database-dsn flag is provided. The implementation replaces a TODO placeholder with full multi-workflow functionality while maintaining backward compatibility with the existing single-config mode.

Changes:

  • Implements runMultiWorkflow() to connect to PostgreSQL, run migrations, bootstrap admin users, create an engine manager with all plugins, mount the REST API, and optionally seed workflows from a YAML config file
  • Adds graceful shutdown handling for multi-workflow components (engine manager, API server, admin engine, PG store)
  • Minor formatting fixes from go fmt in three existing files

Reviewed changes

Copilot reviewed 4 out of 4 changed files in this pull request and generated 9 comments.

File Description
cmd/server/main.go Implements multi-workflow mode with PostgreSQL backend, engine manager, REST API mounting, admin bootstrapping, and workflow seeding functionality; adds graceful shutdown and cleanup logic for multi-workflow mode
plugins/api/plugin.go Formatting fix: realigns default constructor assignments for better readability
module/query_handler_test.go Formatting fix: removes trailing blank line
module/command_handler_test.go Formatting fix: removes trailing blank line

Comment on lines +1528 to +1538
record := &evstore.WorkflowRecord{
ID: uuid.New(),
Name: name,
Slug: slug,
Description: "Seeded from " + configPath,
ConfigYAML: string(yamlBytes),
Version: 1,
Status: evstore.WorkflowStatusDraft,
CreatedAt: now,
UpdatedAt: now,
}
Copy link

Copilot AI Feb 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The WorkflowRecord is missing required fields: ProjectID, CreatedBy, and UpdatedBy. These fields are NOT NULL in the database schema (see store/migrations/004_workflows.sql lines 4, 12-13) and have foreign key constraints. Creating a workflow without these fields will fail with a database constraint violation.

The seed workflow needs to either:

  1. Create or reference a project and user to populate these fields, or
  2. Modify the database schema to make these fields nullable/optional for seed workflows

Copilot uses AI. Check for mistakes.
Comment on lines +1475 to +1479
existing, err := users.GetByEmail(ctx, email)
if err == nil && existing != nil {
logger.Info("Admin user already exists", "email", email)
return nil
}
Copy link

Copilot AI Feb 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Error handling is incomplete. If GetByEmail returns an error other than "not found" (e.g., database connection error, timeout), the error is silently ignored and the function proceeds to create the admin user. This could lead to:

  1. Attempting to create duplicate users if the error was transient
  2. Masking real database connectivity issues
  3. Unexpected behavior during bootstrap

Consider explicitly checking for "not found" errors and returning other errors to the caller.

Copilot uses AI. Check for mistakes.
@intel352
Copy link
Contributor Author

@copilot open a new pull request to apply changes based on the comments in this thread

Copy link
Contributor

Copilot AI commented Feb 23, 2026

@intel352 I've opened a new pull request, #138, to work on those changes. Once the pull request is ready, I'll request review from you.

* Initial plan

* fix: address all review comments for multi-workflow mode

- Extract defaultEnginePlugins() to eliminate plugin list duplication
- Fix bootstrapAdmin to check ErrNotFound explicitly; return admin UUID
- Fix seedWorkflow: handle List error, improve slug via slugify(), populate
  required WorkflowRecord fields (ProjectID, CreatedBy, UpdatedBy) using new
  ensureSystemProject() helper
- Change JWT secret logger.Warn -> logger.Error
- Use srvErrCh to propagate API server failures to initiate graceful shutdown
- Fix URL display using net.SplitHostPort for non-localhost bind addresses
- Fix misleading comment about admin infrastructure setup

Co-authored-by: intel352 <77607+intel352@users.noreply.github.com>

---------

Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>
Co-authored-by: intel352 <77607+intel352@users.noreply.github.com>
@intel352 intel352 merged commit 6587cf8 into main Feb 23, 2026
14 checks passed
@intel352 intel352 deleted the feat/issue-113-multi-workflow branch February 23, 2026 16:14
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Multi-workflow mode should replace single-config mode, not run alongside it

3 participants