Known Issues And Solutions
Ecosistema completo para organización y gestión de contenido con interfaces espaciales
Known Issues & Solutions for NX Monorepo
Last Updated: January 19, 2025
Audience: Beginner to intermediate developers
Table of Contents
- Critical Issue: TypeScript 5.8.x + ng-packagr Incompatibility
- Issue: Files Generated in Source Directories
- Issue: "Cannot destructure property" Error
- Issue: Slow Builds and Hanging
- Emergency Recovery Procedures
Critical Issue: TypeScript 5.8.x + ng-packagr Incompatibility
Status: 🔴 PERMANENT WORKAROUND REQUIRED
Impact: HIGH - Blocks all Angular library builds
Discovered: October 2024
What's the Problem? (Plain English)
Short version: The tools we use to build Angular libraries are broken and incompatible with each other.
Long version:
We use three main tools:
- TypeScript 5.8.x - Compiles TypeScript to JavaScript
- Angular 20 - Our framework (requires TypeScript 5.8.x)
- ng-packagr - Tool that packages Angular libraries
The problem:
- Angular 20 requires TypeScript 5.8.x
- ng-packagr 20.x was built for older TypeScript versions
- TypeScript 5.8.x changed how it stores information internally
- ng-packagr tries to read that information and crashes
Result: You cannot build Angular libraries using the standard NX/Angular tools.
What Error Do You See?
When you try to build a library with the standard method:
yarn nx build my-library
You get:
TypeError: Cannot destructure property 'pos' of 'file.referencedFiles[index]' as it is undefined.
at getReferencedFileLocation
at fileIncludeReasonToDiagnostics
What this means: ng-packagr is trying to read a property that doesn't exist anymore in TypeScript 5.8.x.
Why Can't We Just Update Everything?
Good question! Here's why we're stuck:
Option 1: Update ng-packagr to version 21.x?
- ❌ ng-packagr 21.x requires Node.js 18/20/22
- ❌ We use Node.js 24.7.0
- ❌ We can't downgrade Node because
superstaticpackage blocks it
Option 2: Downgrade TypeScript?
- ❌ Angular 20 requires TypeScript 5.8.x
- ❌ Can't use older TypeScript
Option 3: Downgrade Angular?
- ❌ We need Angular 20 features
- ❌ Would break existing code
We're stuck between incompatible versions!
The Solution: Custom Build Script
Instead of using ng-packagr, we use our own custom build script.
File: tools/scripts/build-scripts/build-angular-library.js
What it does:
- Compiles TypeScript directly (bypasses ng-packagr)
- Generates Angular metadata
- Compiles SCSS to CSS
- Copies HTML templates and assets
- Outputs everything to
dist/only
Benefits:
- ✅ Works with TypeScript 5.8.x
- ✅ No ng-packagr needed
- ✅ Faster than ng-packagr
- ✅ More control over the build process
- ✅ Prevents source directory pollution
How to Use the Custom Build Script
For New Libraries
When you create a new library:
# 1. Generate the library (standard way)
yarn nx generate @nx/angular:library my-new-library
# 2. Update project.json to use custom builder
Edit: libs/my-new-library/project.json
Replace this:
{
"targets": {
"build": {
"executor": "@nx/angular:ng-packagr-lite", // ← OLD (broken)
"options": {
"project": "libs/my-new-library/ng-package.json"
}
}
}
}
With this:
{
"targets": {
"build": {
"executor": "nx:run-commands", // ← NEW (works!)
"outputs": ["{workspaceRoot}/dist/libs/my-new-library"],
"options": {
"command": "node tools/scripts/build-scripts/build-angular-library.js my-new-library"
},
"configurations": {
"production": {
"command": "node tools/scripts/build-scripts/build-angular-library.js my-new-library"
},
"development": {
"command": "node tools/scripts/build-scripts/build-angular-library.js my-new-library"
}
},
"defaultConfiguration": "production",
"cache": true
}
}
}
Key points:
- Replace
LIBRARY-NAMEwith your actual library name - The
outputsarray tells NX where the build files go cache: trueenables build caching for faster rebuilds
For Existing Libraries
If you have an existing library that's broken:
Step 1: Check if it's using the old executor
cat libs/YOUR-LIBRARY/project.json | grep "executor"
If you see "@nx/angular:ng-packagr-lite", it's using the old (broken) method.
Step 2: Update project.json as shown above
Step 3: Update tsconfig.lib.json
Make sure your tsconfig.lib.json has:
{
"extends": "./tsconfig.json",
"compilerOptions": {
"outDir": "../../dist/libs/YOUR-LIBRARY", // ← Output goes here
"rootDir": "./src", // ← OR use rootDirs
"composite": false, // ← MUST be false
"declaration": true,
"declarationMap": false,
"sourceMap": false,
"types": ["node"]
},
"exclude": [
"src/**/*.spec.ts",
"src/test-setup.ts",
"jest.config.ts",
"src/**/*.test.ts"
],
"include": ["src/**/*.ts"]
}
Step 4: Clean and rebuild
# Remove old build artifacts
rm -rf dist/libs/YOUR-LIBRARY
# Build with custom script
yarn nx build YOUR-LIBRARY --skip-nx-cache
Which Libraries Are Already Fixed?
All 18 Angular libraries in our monorepo use the custom builder:
Root Level (15):
ux-ui-forms✅ux-portal✅ux-panel✅ux-loading✅ux-icons✅ux-icon-finder✅svg-connections✅prompt-system✅mock-api✅flash-animations✅dev-tools✅cosmic-backgrounds✅component-library✅catalyst-ui-kit✅auth✅
Nested in theme-system (3):
theme-dev-tools✅theme-runtime✅theme-styles✅
Plain TypeScript (not Angular-specific):
storage-system- Uses@nx/js:tsc(doesn't need custom builder)
Issue: Files Generated in Source Directories
Status: 🟢 SOLVED (with custom builder)
Impact: MEDIUM - Pollutes source code, confuses Git
What's the Problem?
After building, you find .js, .d.ts, and .js.map files inside your source directories:
libs/my-library/src/
├── index.ts
├── index.js ← Shouldn't be here!
├── index.d.ts ← Shouldn't be here!
├── index.js.map ← Shouldn't be here!
└── lib/
├── component.ts
├── component.js ← Shouldn't be here!
└── component.d.ts ← Shouldn't be here!
Why this is bad:
- Git thinks these are source files (they're not)
- You might accidentally commit them
- They can cause confusion (which file is the "real" one?)
- IDE might get confused about which file to use
What Should Happen
ALL build output should go to dist/:
libs/my-library/src/
├── index.ts ← Source files (only these!)
└── lib/
└── component.ts
dist/libs/my-library/
├── index.js ← Build output (goes here!)
├── index.d.ts
├── index.js.map
└── lib/
├── component.js
├── component.d.ts
└── component.js.map
Rule: If you see .js or .d.ts files in libs/, something is wrong!
Why Does This Happen?
Common causes:
Cause 1: Wrong outDir in tsconfig
Your tsconfig.lib.json might have:
{
"compilerOptions": {
"outDir": "./dist" // ← WRONG! This is relative to the library folder
}
}
This creates:
libs/my-library/dist/ ← Wrong place!
Fix: Use absolute path from workspace root:
{
"compilerOptions": {
"outDir": "../../dist/libs/my-library" // ← CORRECT!
}
}
Cause 2: composite: true
If your tsconfig.lib.json has:
{
"compilerOptions": {
"composite": true // ← This can cause source pollution
}
}
TypeScript's "project references" feature can output files in strange places.
Fix: Set to false:
{
"compilerOptions": {
"composite": false // ← Safe!
}
}
Cause 3: Missing rootDir
Without rootDir, TypeScript might output files in the wrong structure.
Fix: Always set rootDir:
{
"compilerOptions": {
"rootDir": "./src", // ← Forces proper structure
"outDir": "../../dist/libs/my-library"
}
}
How to Clean Up Source Pollution
If you already have generated files in your source directories:
Option 1: Automated cleanup script
node tools/scripts/cleanup-all-source-pollution.js
This script:
- ✅ Removes
.jsfiles only if a.tssource exists - ✅ Removes
.d.tsfiles only if a.tssource exists - ✅ Removes
.js.mapand.d.ts.mapfiles - ✅ Preserves standalone
.jsconfig files (likejest.config.js)
Option 2: Manual cleanup
# Find all generated files in source
find libs/ -name "*.js" -o -name "*.d.ts" -o -name "*.js.map"
# Remove them (BE CAREFUL!)
find libs/ -name "*.js" -o -name "*.d.ts" -o -name "*.js.map" | xargs rm -f
⚠️ Warning: The manual method removes ALL .js files, including config files. Use the automated script instead!
How to Prevent Source Pollution
Use our custom build script!
The custom builder at tools/scripts/build-scripts/build-angular-library.js:
- ✅ Always outputs to
dist/only - ✅ Has built-in cleanup as safety net
- ✅ Properly configures
outDirandrootDir
If you're using the custom builder and still seeing source pollution, that's a bug - report it!
Issue: "Cannot destructure property" Error
Full error message:
TypeError: Cannot destructure property 'pos' of 'file.referencedFiles[index]' as it is undefined.
at getReferencedFileLocation (/node_modules/ng-packagr/lib/ts/cache-compiler-host.js:245:58)
at fileIncludeReasonToDiagnostics (/node_modules/typescript/lib/typescript.js:140819:57)
What's happening:
This is the main symptom of the TypeScript 5.8.x + ng-packagr incompatibility described above.
Quick check:
# Check your TypeScript version
npx tsc --version
# Should show: Version 5.8.x
# Check if library uses ng-packagr
cat libs/YOUR-LIBRARY/project.json | grep "ng-packagr"
# If you see "ng-packagr-lite", that's the problem!
Solution:
Switch to the custom build script (see solution above).
Issue: Slow Builds and Hanging
Symptoms:
- Build command runs for 5+ minutes
- Terminal shows no output
- CPU usage at 100%
- Eventually times out or you have to Ctrl+C
Common Causes & Fixes
Cause 1: TypeScript Getting Stuck on Type Errors
What's happening: TypeScript is trying to resolve type errors and getting stuck in loops.
How to test:
# Try building with verbose output
yarn nx build YOUR-LIBRARY --verbose
# If it hangs at "Compiling TypeScript...", that's the issue
Fix 1: Add skipLibCheck
Edit tsconfig.lib.json:
{
"compilerOptions": {
"skipLibCheck": true // ← Skip checking .d.ts files
}
}
This makes TypeScript skip type-checking library .d.ts files, which is much faster.
Fix 2: Check for circular dependencies
# Use madge to detect circular dependencies
npx madge --circular libs/YOUR-LIBRARY/src
If you see circular dependencies, refactor your code to break the cycle.
Cause 2: Too Many Files in rootDirs
What's happening: Your tsconfig.lib.json has too many entries in rootDirs:
{
"rootDirs": [
"./src",
"../storage-system/src",
"../theme-system/src",
"../ux-icons/src",
"../ux-menu/src",
"../ux-panel/src",
// ... 10 more libraries
]
}
TypeScript has to check ALL of these directories on every compile.
Fix: Only include libraries you actively develop:
{
"rootDirs": [
"./src",
"../storage-system/src" // ← Only the essential ones
],
"paths": {
// Use dist/ for others
"@ux-icons": ["../../dist/libs/ux-icons/index"]
}
}
Cause 3: NX Cache Issues
What's happening: NX's cache is corrupted or stale.
Fix:
# Clear NX cache
yarn nx reset
# Clear all caches
rm -rf dist/ .angular/ node_modules/.cache
# Try building again
yarn nx build YOUR-LIBRARY --skip-nx-cache
Cause 4: Too Many Processes Running
What's happening: Your system is running out of resources.
Check:
# Check running node processes
ps aux | grep node | wc -l
# Check TypeScript servers
ps aux | grep tsserver
Fix:
# Kill all TypeScript servers
killall -9 tsserver node
# Or kill specific processes
pkill -f 'typescript-language-features'
# Then retry
yarn nx build YOUR-LIBRARY
Emergency Recovery Procedures
When Everything is Broken
Follow these steps in order:
Step 1: Nuclear Clean
# 1. Close your IDE completely (Cmd+Q)
# 2. Kill all Node processes
killall -9 node tsserver
# 3. Clear all caches and build artifacts
rm -rf dist/ .angular/ .nx/ node_modules/.cache
# 4. Clean source directories
node tools/scripts/cleanup-all-source-pollution.js
# 5. Reset NX
yarn nx reset
Step 2: Verify Configuration
Check: libs/YOUR-LIBRARY/project.json
Should use custom build script:
{
"targets": {
"build": {
"executor": "nx:run-commands",
"options": {
"command": "node tools/scripts/build-scripts/build-angular-library.js YOUR-LIBRARY"
}
}
}
}
Check: libs/YOUR-LIBRARY/tsconfig.lib.json
Should have proper paths:
{
"compilerOptions": {
"outDir": "../../dist/libs/YOUR-LIBRARY",
"rootDir": "./src", // OR rootDirs
"composite": false
}
}
Step 3: Rebuild Dependencies First
# Build storage-system first (most libraries depend on it)
yarn nx build storage-system --skip-nx-cache
# Then build your library
yarn nx build YOUR-LIBRARY --skip-nx-cache
Step 4: Test Build
# Build should succeed
yarn nx build YOUR-LIBRARY
# Verify output exists
ls -la dist/libs/YOUR-LIBRARY/
# Verify NO source pollution
find libs/YOUR-LIBRARY/src -name "*.js" -o -name "*.d.ts"
# Should return NOTHING (or only intentional config files)
Step 5: Restart IDE
# Reopen your IDE
# Then restart TypeScript server:
# Cmd+Shift+P → "TypeScript: Restart TS Server"
If Build Still Fails
Get diagnostic information:
# 1. Build with verbose output
yarn nx build YOUR-LIBRARY --verbose --skip-nx-cache 2>&1 | tee build-log.txt
# 2. Check TypeScript directly
cd libs/YOUR-LIBRARY
npx tsc --project tsconfig.lib.json --noEmit
# 3. Check for syntax errors
npx eslint src/
Check the build log for:
Cannot find module→ Path mapping issuenot under 'rootDir'→ NeedrootDirsCannot destructure→ Still using ng-packagr (switch to custom builder)- Syntax errors → Fix your code first
Debugging Checklist
When something goes wrong, go through this checklist:
✅ Build Configuration
-
project.jsonusesnx:run-commandsexecutor - Command points to
build-angular-library.js -
outputsarray specifies correctdist/path
✅ TypeScript Configuration
-
outDirpoints to../../dist/libs/YOUR-LIBRARY -
rootDiris./srcORrootDirsincludes dependencies -
compositeisfalse -
baseUrlis set (if using custom paths)
✅ Path Mappings
-
tsconfig.base.jsonhas entry for your library - Path points to correct location (source or dist)
- Wildcard path (
@lib/*) is also defined
✅ Source Directories
- NO
.jsfiles inlibs/YOUR-LIBRARY/src/ - NO
.d.tsfiles inlibs/YOUR-LIBRARY/src/ - Only
.ts,.html,.scss,.cssfiles in source
✅ Dependencies
- All dependency libraries are listed in
implicitDependencies - Dependencies are built before this library
- If using
rootDirs, all dependencies are listed
✅ System State
- No stale
node_modules/.cache - No stale
.nx/cache - IDE TypeScript server restarted
- No hung Node processes
Quick Reference Commands
# Clean everything
yarn nx reset && rm -rf dist/ .angular/ node_modules/.cache
# Clean source directories
node tools/scripts/cleanup-all-source-pollution.js
# Build single library (skip cache)
yarn nx build YOUR-LIBRARY --skip-nx-cache
# Build with dependencies
yarn nx build YOUR-LIBRARY --with-deps
# Check for source pollution
find libs/ -name "*.js" -o -name "*.d.ts" | grep -v node_modules | grep -v dist
# Kill stuck processes
killall -9 tsserver node
# Check TypeScript version
npx tsc --version
# Test TypeScript compilation directly
cd libs/YOUR-LIBRARY && npx tsc --project tsconfig.lib.json --noEmit
When Will This Be Fixed Upstream?
Short answer: Unknown. Could be months or years.
The situation:
- ng-packagr team is aware of the issue
- They need to update for TypeScript 5.8.x compatibility
- OR TypeScript needs to maintain backward-compatible internal APIs
- OR we need to downgrade Node.js (can't do this due to other dependencies)
Our approach:
- ✅ Use custom build script (permanent solution)
- ✅ Don't wait for upstream fix
- ✅ Custom builder actually works better than ng-packagr
History & Changes
| Date | Change | Impact |
|---|---|---|
| 2024-10-17 | Discovered TypeScript 5.8.x + ng-packagr bug | All Angular builds broken |
| 2024-10-17 | Created custom build script | Fixed all builds |
| 2024-10-17 | Migrated all 18 Angular libraries | All libraries working |
| 2024-10-17 | Created cleanup script for source pollution | Prevention-based solution |
| 2025-01-19 | Documented rootDirs pattern |
Improved developer experience |
| 2025-01-19 | Created beginner-friendly docs | Better onboarding |
Related Documentation
- Library Configuration Guide - Complete setup guide
- TypeScript Path Mappings - Understanding paths
- Troubleshooting Guide - Common errors
Remember: This is NOT a configuration mistake - it's a KNOWN BUG in the tooling. The custom build script is the correct and permanent solution. Don't waste time trying to make ng-packagr work with TypeScript 5.8.x!