A monorepo containing the in-agent UI application and shared packages for the Migration Planner project.
This project is organized as a monorepo using Yarn workspaces, which allows us to manage multiple related packages and applications in a single repository. The structure is divided into two main directories:
apps/- Contains standalone applications (e.g.,agent-ui)packages/- Contains reusable packages that can be shared across applications
This monorepo structure provides several benefits:
- Code sharing: Common functionality can be extracted into packages and reused across multiple apps
- Consistent tooling: Shared development tools and configurations ensure consistency across the codebase
- Atomic changes: Related changes across packages and apps can be made in a single commit
- Simplified dependency management: Dependencies are hoisted and shared where possible, reducing duplication
The root package.json provides workspace-wide scripts and dev dependencies that standardize development across all packages and apps:
Available Scripts:
yarn build:all- Build all packages and appsyarn bundle:all- Bundle all packages for publishingyarn clean:all- Clean all build artifactsyarn check:all- Run linting checks across all workspacesyarn check:fix:all- Auto-fix linting issuesyarn format:all- Format code across all workspacesyarn update:api-client- Regenerate the API client from OpenAPI spec
Shared Dev Dependencies:
@biomejs/biome- Linting and formatting (configured inbiome.json)@openapitools/openapi-generator-cli- OpenAPI code generationtypescript- TypeScript compiler (version ~5.5.0)vite- Build tool for applications- Various type definitions (
@types/*)
Each package and app can define its own scripts and dependencies, but they inherit the shared tooling from the root. This separation is intentional and serves to:
- Standardize packages: All packages follow similar patterns (build, bundle, clean scripts)
- Align dependency versions: Shared dev dependencies ensure consistent TypeScript versions, build tools, and linting rules across the entire monorepo
- Reduce duplication: Common tools are defined once at the root level rather than in each package
Common Package Scripts:
build- Compile TypeScript to JavaScriptbundle- Build and package for distributionclean- Remove build artifactscheck- Run linting checks using Biomecheck:fix- Auto-fix linting issues using Biomeformat- Format code using Biome
App-Specific Scripts:
Apps may include additional scripts like start and preview for development workflows.
Key Features:
- Generated from OpenAPI spec using
typescript-fetchgenerator - Type-safe API calls and models
- ES6 module support
- Isomorphic code: Works in both Node.js and browser environments
TypeScript client for the Migration Planner API, auto-generated from the OpenAPI specification. Provides type-safe API methods and models for interacting with the main Migration Planner backend.
A lightweight dependency injection (IoC) container solution for React applications, inspired by InversifyJS. Provides a simple way to manage dependencies and inject them into React components.
Key Features:
- Singleton-scoped dependency injection container
- React Context-based provider pattern
useInjectionhook for accessing dependencies in components- Minimal API surface for easy adoption
A React-based user interface application for the Migration Planner Agent. Built with Vite, React Router, and PatternFly components.
Key Technologies:
- React 18
- Vite
- React Router
- PatternFly React components
- Emotion CSS
The best approach for adding a new package or app is to copy an existing similar one and adapt it to your needs. This ensures consistency with existing patterns and configurations.
Steps:
-
Choose a similar package/app as a template (e.g., copy
packages/api-clientfor a new client package, orapps/agent-uifor a new app) -
Copy the directory to your desired location (
packages/for packages,apps/for apps) -
Update the following:
package.json: Updatename,description, and any package-specific dependenciestsconfig.json: Adjust TypeScript configuration if needed- Source code: Replace with your implementation
- README.md: Update documentation
-
Add TypeScript project reference in the root
tsconfig.json:{ "references": [ { "path": "./your-new-package/tsconfig.json" } ] } -
Ensure scripts follow conventions:
build– Compile TypeScriptbundle– Build and package (for packages)clean– Remove build artifactscheck– Run static analysis/linting (e.g., type checks, code lint)format– Format code automatically
-
Run from root to verify:
yarn install yarn build:all
This project uses the OpenAPI Generator CLI to automatically generate TypeScript clients from OpenAPI specifications. This ensures that our API clients stay in sync with the backend API definitions.
- Type Safety: Generated clients provide full TypeScript type definitions based on the OpenAPI spec
- Consistency: Ensures API clients match the backend API exactly
- Maintainability: When the API changes, we regenerate clients rather than manually updating code
- Speed: Reduces boilerplate and potential errors from manual client implementation
The OpenAPI Generator CLI is configured via openapitools.json at the root of the project.
api-client: Generates the TypeScript client from the main Migration Planner API spec
Note: The Agent API client is now consumed as a published npm package (@openshift-migration-advisor/agent-sdk) rather than being generated locally.
Via Yarn Scripts (Recommended):
# Update the API client
yarn update:api-clientVia Makefile (isolated container execution, no extra dependencies needed): The Makefile provides a way to run the OpenAPI Generator CLI in isolation using Docker/Podman, ensuring consistent execution across different environments:
# Update the API client
make api-client
# Or use the generic generate target
make generate ARGS="--generator-key api-client"
# Interact directly with the tool
make openapi-generator-cli ARGS="list"Why you should use the Makefile?
The Makefile runs the OpenAPI Generator CLI in a containerized environment, which:
- Ensures consistency: Same tool version across all developers and CI/CD
- Avoids local installation: No need to install the CLI tool locally
- Isolates dependencies: The generator runs in its own container, avoiding conflicts
- Uses pinned versions: The container image tag is pinned to a specific version (v7.18.0) for reproducibility
The container automatically mounts the project directory, so generated files are written directly to the appropriate package directories as configured in openapitools.json.
-
Install dependencies:
yarn install
-
Build all packages:
yarn build:all
-
Start an application:
cd apps/agent-ui yarn start -
Run linting:
yarn check:all
For detailed instructions on setting up a complete local development environment with the Migration Planner backend and Agent, see:
docs/DEVELOPMENT.md
To locally reproduce the publishing of a minimal OCI image (only dist/) to Quay.io and test authentication/push, follow the guide at:
docs/publish-to-quay-local.md
- Making changes: Work in the appropriate package or app directory
- Testing: Run package-specific scripts or use workspace scripts from root
- Linting/Formatting: Use
yarn check:allandyarn format:allfrom root - Updating API clients: Use
yarn update:*-clientscripts or Makefile targets when backend APIs change
When making changes to the generated client packages (e.g., api-client), you may want to test them locally in a consuming application before publishing.
Steps:
-
Generate the updated client files:
make api-client
-
Bundle the package from the top-level directory:
yarn workspace @migration-planner-ui/api-client bundle
-
Locate the generated archive. The output of the bundle command will display the path to the generated
.tgzfile:➤ YN0000: Package archive generated in <path>/out/@migration-planner-ui-api-client-1.0.0-alpha.tgz -
Install the package in your consuming application using the path from the previous step:
npm i <path-to-tgz>
⚠️ Warning: Runningnpm i <path-to-tgz>will modify the consuming application'spackage.jsonand lock file. These changes must NOT be committed to version control. Make sure to revert these files before committing any other changes.