# How to set up Embeddable in a Yarn/Nx monorepo

**URL:** <https://community.embeddable.com/t/how-to-set-up-embeddable-in-a-yarn-nx-monorepo/143>\
**Category:** FAQs\
**Created:** [August 12, 2025, 3:59pm UTC](https://community.embeddable.com/t/how-to-set-up-embeddable-in-a-yarn-nx-monorepo/143 "2025-08-12T15:59:05Z")\
**Posts on this page:** 1\
**Page:** 1

<div class="post-metadata">

**Author:** ![ella-embeddable](https://dub1.discourse-cdn.com/flex013/user_avatar/community.embeddable.com/ella-embeddable/32/15_2.png) [@ella-embeddable](https://community.embeddable.com/u/ella-embeddable)\
**Post date:** [August 12, 2025, 3:59pm UTC](https://community.embeddable.com/t/how-to-set-up-embeddable-in-a-yarn-nx-monorepo/143/1 "2025-08-12T15:59:05Z")

</div>

1. Monorepo baseline (Yarn workspaces + Nx)

- Your repo uses Yarn workspaces, managed by Nx.

- All packages extend a root `tsconfig.json` and target modern ESM:

`{ "compilerOptions": { "target": "ES6", "module": "esnext", "moduleResolution": "node" } } `

1. Add an Embeddable app/package

- Create a new workspace package (e.g. `@your/embeddable`) based on the **Embeddable Starter Basics** or **Vanilla Components** examples.

- Wire it into Nx for dev/build so you can use caching and a single command surface.

This standalone setup should run cleanly in the monorepo.

Just so you know

- You may see the SDK complain about not finding a TypeScript compiler. Running the command with `--force` is a safe workaround and is unrelated to the integrations below.

1. Start consuming shared code

When you’re ready to import code from other workspace packages, add a workspace dep and (optionally) a path alias.

**package.json**

`{ "name": "@your/embeddable", "dependencies": { "@your/insights": "workspace:*" } } `

**tsconfig.json**

`{ "compilerOptions": { "paths": { "@your/insights": ["path/to/insights"] } } } `

Just so you know (and how to work around it)

When introducing **tsconfig paths** and **workspace dependencies** , some setups hit module-resolution edge cases (e.g., “can’t import from directory,” “module not found,” or CommonJS interop errors from deep deps). If you see that:

**Workaround A — Preferred: feed Embeddable clean ESM builds**

- Prebundle the shared package(s) you import into **ESM output** (e.g., `.es.js`) using your bundler of choice (Rollup, tsup, Vite build).

- Point your `emb.ts` imports at those built ESM entry points.

- In Nx, make your Embeddable build depend on the shared package build (so ESM outputs exist first).

This keeps responsibility clear: your shared packages output ESM; Embeddable then bundles those ESM inputs.

**Workaround B — Smooth CJS interop when needed**  
If some private/first-party deps are CommonJS:

- In the Embeddable package `tsconfig.json`, enable:

- Prefer ESM builds of your internal libs where possible, or export dual targets (`module` ESM + `main` CJS) and import the ESM entry.

**Workaround C — Resolve path alias reliably**

- Point alias paths to the **built ESM dist** of the workspace package (e.g., `dist/insights/index.es.js`) rather than raw source, so Embeddable sees standard ESM files.

- Alternatively, remove the alias and import via the package name (after building), which avoids path resolution quirks.

1. Nx target wiring (example)

Have the shared libs build first, then Embeddable:

`// apps/embeddable/project.json { "targets": { "build": { "executor": "nx:run-commands", "options": { "command": "embeddable build --force" }, "dependsOn": ["^build"] // builds upstream libs first }, "dev": { "executor": "nx:run-commands", "options": { "command": "embeddable dev --force" }, "dependsOn": ["^build"] } } } `

1. Keep bundles lean

Prebundling per component can bloat size. A few easy wins:

- **Bundle per package** , not per component (one ESM entry that re-exports components).

- Mark packages **tree-shakable** (`"sideEffects": false` where valid).

- Import **named exports** so Embeddable can treeshake.

- Let Nx cache builds to avoid unnecessary rebuilds.
