Skip to content

causa-io/workspace-module-core

Repository files navigation

@causa/workspace-core module

This repository contains the source code for the @causa/workspace-core Causa module. It provides the implementations of many cs commands. It also provides definitions for commands that are meant to be implemented by other modules, depending on the project types and/or languages. For more information about the Causa CLI cs, checkout its repository.

➕ Requirements

The core module requires Git and Docker for some of its operations (e.g. reading Git commit SHAs when publishing artefacts, pushing Docker image when publishing service containers, etc).

🎉 Installation

Add @causa/workspace-core to your Causa configuration in causa.modules.

🔧 Configuration

Several configurations are defined in this module, first for some generic project.types:

  • infrastructure (InfrastructureConfiguration): Projects defining infrastructure as code.
  • serverlessFunctions (ServerlessFunctionsConfiguration): Projects defining serverless functions, meant to be run on some serverlessFunctions.platform (e.g. AWS Lambda, Google Cloud Functions).
  • serviceContainer (ServiceContainerConfiguration): Projects defining a service, meant to be run as a container on some serviceContainer.platform (e.g. Kubernetes, Cloud Run, AWS ECS).

This module also exposes the DockerConfiguration, which is used by the DockerService, exposing usual Docker commands.

It also exposes the EventsConfiguration, which defines the configuration related to events and their topics (e.g. how to find topic schema files in the workspace).

The ModelConfiguration defines the configuration for business model definitions, and the related code generation utilities.

For OpenAPI generation, the OpenApiConfiguration defines a global (base) specification for workspace-wide information (e.g. info, securitySchemes, etc), as well as glob patterns for project-level specification files.

✨ Supported project types and commands

The core module defines and implements many base cs commands. As a Causa user, you may want to check the CLI repository instead. As a module developer, you may want to check the definitions and determine which ones are relevant to implement in your module.

Commands

  • cs init: Initializes the workspace. This is a no-op in most cases as the CLI takes care of bootstrapping the workspace before running. The core module does not provide any project-specific implementation.
  • cs configuration check: Validates the workspace configuration against the combined JSON Schema from all modules. Use --render to render templates (without secrets) before validating, and --projects to validate each project's configuration independently.
  • cs emulators: Provides the list, start, and stop commands. However no actual emulator is implemented by this module. Available emulators will depend on other loaded modules.
  • cs environment: Provides the prepare and deploy commands, forwarding those infrastructure commands to the project configured in infrastructure.environmentProject.
  • cs events backfill and cs events cleanBackfill: The common backfilling logic is implemented in this module. However, this logic requires several tech stack-specific functions to be implemented by other modules.
  • cs infrastructure: Provides the prepare and deploy commands. Those commands run "infrastructure processors" before the actual infrastructure operation, and tear those down afterwards. The core module does not implement actual infrastructure operations, which depend on the project's language, e.g. terraform.
  • cs publish: While many base commands (e.g. cs build) are straightforward and should be implemented by the modules handling the corresponding project types and languages, cs publish provides some logic around these base commands to both build and push a project's artefact. The artefact is tagged according to the passed value or format, e.g. my-custom-tag or semantic. (The latter will use the project's version as the tag.)
  • cs openapi generateSpecification: At the workspace level, triggers the generation of the specification in each project and merges and bundles the outputs into a single file. At the project level, merges specification files matched by openApi.specifications globs (if set). To use other project-level generation implementations, simply leave the openApi.specifications unset.
  • cs diff: Lists changed projects based on the output of git diff. This can be useful for CI workflows. This module entirely implements the logic, and no other module is expected to provide an implementation.
  • cs model generateCode: Runs the code generators defined in the model.codeGenerators configuration.
  • cs scenario run <path>: Loads a scenario YAML file and runs its steps, calling workspace functions in dependency order.

Secrets backend

The core module implements a very basic secrets backend: environmentVariable. As the name suggests, it retrieves values from the process environment:

secrets:
  mySecret:
    backend: environmentVariable
    name: SOME_ENV_VAR

📚 Definitions

The core module provides many Causa workspace function definitions. Some of those definitions are exposed as cs commands and provides the base functionalities for a Causa workspace. Some of the function definitions are implemented "generically" in this module, while others are meant to be implemented by other Causa modules, providing support of a specific project language or type.

This section provides pointers for Causa module developers. Workspace function definitions can be found in the ./src/definitions directory. Those include:

  • Emulators: Modules exposing local emulators (e.g. of databases) should implement both EmulatorStart and EmulatorStop for each of them.
  • Environment: Functions mapping to cs environment commands. Those are not meant to be implemented by other modules.
  • Event topic: Functions related to event topics, e.g. backfilling. Modules providing support for a new project type should implement EventTopicListReferencedInProject. Modules providing tech stack or cloud provider support should implement the EventTopicBroker* functions, register EventTopicCreateBackfillSource implementations for the source schemes they handle (including the "no source" / broker-default case), and implement EventTopicQueryEvents so events published to a topic can be queried.
  • Infrastructure: Modules providing support for an Infrastructure as Code tool (e.g. Terraform, Pulumi) should implement the InfrastructurePrepare and InfrastructureDeploy functions.
  • Model: Modules providing support for a programming language can implement new code generators by extending ModelRunCodeGenerator.
  • Project: Many of the definitions in this file should be implemented by modules providing support for a language and/or project type, e.g. ProjectBuildArtefact, ProjectReadVersion, ProjectPushArtefact, ProjectGetArtefactDestination.
  • OpenAPI: Functions related to OpenAPI specifications. OpenApiGenerateSpecification should be implemented by Causa modules providing support for a language / project type (if relevant).
  • Scenario: The ScenarioRun definition powering cs scenario run. The implementation is generic and shipped by this module — it dispatches to other workspace functions, so other modules only need to expose the functions referenced from scenario steps.
  • HTTP: The MakeHttpRequest function, useful as a scenario step (e.g. for end-to-end checks against a deployed service).
  • Database: The DatabaseQueryRecords function. Modules providing support for a database engine should register an implementation against their engine value.
  • Service container: The ServiceContainerQueryLogs function. Modules providing support for a deployment platform should register an implementation that fetches logs for a deployed service container.

🔨 Services

This module implements some services used by itself, but which might also come handy in other modules, namely:

  • ProcessService: Provides a normalized way to spawn child processes.
  • GitService: Runs git commands using the ProcessService.
  • DockerService: Runs docker commands using the ProcessService.
  • DockerEmulatorService: Provides a normalized way to starting and stopping containerized emulators. Also provides a way to wait for an emulator exposing an HTTP endpoint.
  • ServiceContainerBuilderService: Provides the base logic to build service container images (using the DockerService). Language-specific modules can use this service and customize build parameters.

🧱 Infrastructure processors

ProjectWriteConfigurations

ProjectWriteConfigurations is an infrastructure processor that writes the configuration of each and every project in the workspace to a single JSON file per project. This allows the configuration to be consumed by external systems that are not implemented in TypeScript and do not integrate directly with Causa. The output directory for the configuration files can be set in the causa.projectConfigurationsDirectory configuration, which defaults to .causa/project-configurations.

📫 Backfilling

One of Causa's features is the ability to backfill events to be processed by services. The cs events backfill command orchestrates the generic flow: temporary topic and trigger setup, resolving the source of events to publish, and driving the broker-specific publisher. Stack-specific logic lives in other modules through the EventTopicBroker* function definitions.

Triggers passed with --trigger are free-form URIs by default and are interpreted by the broker. Triggers matching the format <projectPath>#<triggerName>[?<options>] are treated as project-scoped: the workspace context is cloned for the referenced project (relative to the workspace root), and EventTopicBrokerCreateTrigger is called with a structured { name, options } payload on that project-scoped context. Options are parsed as a URL query string into a Record<string, string>.

The events to publish are built by EventTopicCreateBackfillSource, which returns an AsyncIterable<BackfillEvent> passed to EventTopicBrokerPublishEvents. This module ships an implementation for json://<glob> sources (newline-delimited JSON files with data, optional attributes, and optional key fields). When no --source is passed, the broker module is expected to provide an implementation that yields from its default storage for the topic. Filtering, when supported, is applied inside the source implementation — the returned iterable yields only the events that should actually be published.

🎬 Scenarios

Scenarios are YAML files that orchestrate calls to workspace functions, with templated arguments, dependency-driven scheduling, expectations, and retries. They are run with cs scenario run <path> (relative paths are resolved from the workspace root). The schema for a scenario file is shipped with this module at ./src/scenarios/schemas/scenario.yaml and embedded under dist/scenarios/schemas/ when published.

Step args and expectations are rendered with json-e and have access to:

  • ${ input('<name>') } — resolves a scenario input.
  • ${ output('<stepId>') } — resolves another step's output (and is also used to detect cross-step dependencies).
  • ${ configuration('<path>') } — resolves a value from the workspace configuration.

About

The Causa workspace module providing core function definitions and some implementations.

Topics

Resources

License

Stars

Watchers

Forks

Contributors