Imported from adobe/aem-rockstar-website (
AGENTS.md). Install upstream withnpx skills add adobe/aem-rockstar-website. Copyright stays with the author.
AGENTS.md
This project is a website built with Edge Delivery Services in Adobe Experience Manager Sites as a Cloud Service. As an agent, follow the instructions in this file to deliver code based on Adobe's standards for fast, easy-to-author, and maintainable web experiences.
Project Overview
This project is based on the https://github.com/adobe/aem-boilerplate/ project and set up as a new project. You are expected to follow the coding style and practices established in the boilerplate, but add functionality according to the needs of the site currently developed.
The repository provides the basic structure, blocks, and configuration needed to run a complete site with *.aem.live as the backend.
Key Technologies
- Edge Delivery Services for AEM Sites (documentation at https://www.aem.live/ – search with
site:www.aem.liveto restrict web search results) - Vanilla JavaScript (ES6+), no transpiling, no build steps
- CSS3 with modern features, no Tailwind or other CSS frameworks
- HTML5 semantic markup generated by the aem.live backend, decorated by our code
- Node.js tooling
Setup Commands
- Install dependencies:
npm install - Start local development:
npx -y @adobe/aem-cli up --no-open --forward-browser-logs(run in background, if possible)- Install the AEM CLI globally by running
npm install -g @adobe/aem-clithenaem upis equivalent to the command above
- Install the AEM CLI globally by running
- Run linting:
npm run lint - Fix linting issues:
npm run lint:fix
Project Structure
├── blocks/ # Reusable content blocks
└── {blockName}/ - Individual block directory
├── {blockName}.js # Block's JavaScript
└── {blockName}.css # Block's styles
├── styles/ # Global styles and CSS
├── styles.css # Minimal global styling and layout for your website required for LCP
└── lazy-styles.css # Additional global styling and layout for below the fold/post LCP content
├── scripts/ # JavaScript libraries and utilities
├── aem.js # Core AEM Library for Edge Delivery page decoration logic (NEVER MODIFY THIS FILE)
├── scripts.js # Global JavaScript utilities, main entry point for page decoration
└── delayed.js # Delayed functionality such as martech loading
├── fonts/ # Web fonts
├── icons/ # SVG icons
├── head.html # Global HTML head content
└── 404.html # Custom 404 page
Code Style Guidelines
JavaScript
- Use ES6+ features (arrow functions, destructuring, etc.)
- Follow Airbnb ESLint rules (already configured)
- Always include
.jsfile extensions in imports - Use Unix line endings (LF)
CSS
- Follow Stylelint standard configuration
- Use modern CSS features (CSS Grid, Flexbox, CSS Custom Properties)
- Maintain responsive design principles
- Declare styles mobile first, use media queries for tablet and desktop specific styles
- Use 600px/900px/1200px as breakpoints
HTML
- Use semantic HTML5 elements
- Ensure accessibility standards (ARIA labels, proper heading hierarchy)
- Follow AEM markup conventions for blocks and sections
Key Concepts
Content
CMS authored content is a key part of every AEM Website. The content of a page is broken into sections. Sections can have default content (text, headings, links, etc.) as well as content in blocks.
Background on content structure https://www.aem.live/developer/markup-sections-blocks
You can inspect the contents of any page with curl http://localhost:3000/path/to/page and curl http://localhost:3000/path/to/page.md
Blocks
Blocks are the re-usable building blocks of AEM. Blocks add styling and functionality to content. Each block has an initial content structure it expects, and transforms the html in the block using DOM APIs to render a final structure.
The initial content sturcture is important because it impacts how the author will create the content and how you will write your code to decorate it. In some sense, you can think of this structure as the contract for your block between the author and the developer. You should decide on this initial structure before writing any code, and be careful when making changes to code that makes assumptions about that structure as it could break existing pages.
The block javascript should export a default function which is called to perform the block decoration:
/**
* loads and decorates the block
* @param {Element} block The block element
*/
export default async function decorate(block) {
// 1. Load dependencies
// 2. Extract configuration, if applicable
// 3. Transform DOM
// 4. Add event listeners
// 5. Set loaded status
}
Use curl and console.log to inspect the HTML delivered by the backend and the DOM nodes to be decorated before making assumptions. Remember that authors may omit or add fields to a block, so your code must handle this gracefully.
Auto-Blocking
Auto-blocking is the process of creating blocks that aren't explicitly authored into the page based on patterns in the content. See the buildAutoBlocks function in scripts.js.
Three-Phase Page Loading
Pages are progressively loaded in three phases to maximize performance. This process begins when loadPage from scripts.js is called.
- Eager - load only what is required to get to LCP. This generally includes decorating the overall page content to create sections, blocks, buttons, etc. and loading the first section of the page.
- Lazy - load all other page content, including the header and footer.
- Delayed - load things that can be safely loaded later here and incur a performance penalty when loaded earlier
Development Workflow
Local Development
- Run
npx -y @adobe/aem-cli up --no-opento start the AEM Proxy server - Open
http://localhost:3000in your browser, puppeteer, playwright, or other tools. If none of those are available, instruct the human to open the URL in the browser and give feedback - Make changes to files - they will auto-reload
- Use browser dev tools to test responsive design
Block Development
- Each block in the
blocks/directory should be self-contained and re-useable - Include CSS and JS files for each block
- Follow the naming convention:
blockname.css,blockname.js - Blocks should be responsive and accessible by default
Styling
- Global styles go in
styles/styles.css - Font definitions in
styles/fonts.css - Lazy-loaded styles in
styles/lazy-styles.css - Block-specific styles in their respective directories
Testing & Quality Assurance
Linting
- JavaScript: ESLint with Airbnb base configuration
- CSS: Stylelint with standard configuration
- Run
npm run lintbefore committing - Use
npm run lint:fixto automatically fix issues
Performance
- Follow AEM Edge Delivery performance best practices https://www.aem.live/developer/keeping-it-100
- Images uploaded by authors are automatically optimized, all images and assets committed to git must be optimized and checked for size
- Use lazy loading for non-critical resources (
lazy-styles.cssanddelayed.js) - Minimize JavaScript bundle size by avoiding dependencies, using automatic code splitting provided by
/blocks/
Accessibility
- Ensure proper heading hierarchy
- Include alt text for images
- Test with screen readers
- Follow WCAG 2.1 AA guidelines
Deployment
Environments
Edge Delivery Services provides you with three environments. Your local development server at http://localhost:3000 serves code from your local working copy (even uncommitted code) and content that has been previewed by authors. You can access this at any time when the development server is running.
For all other environments, you need to know the GitHub owner and repository name (gh repo view --json nameWithOwner or git remote -v) and the current branch name git branch)
With this information, you can construct URLs for the preview environment (same content as localhost:3000) and the production environment (same content as the live website, approved by authors)
- Production Preview:
https://main--{repo}--{owner}.aem.page/ - Production Live:
https://main--{repo}--{owner}.aem.live/ - Feature Preview:
https://{branch}--{repo}--{owner}.aem.page/
Publishing Process
- Push changes to a feature branch
- AEM Code Sync automatically processes changes making them available on feature preview environment for that branch
- Open a pull request to merge changes to
main– in the PR description, include a link to https://{branch}--{repo}--{owner}.aem.page/{path}` with a path to a file that illustrates the change you've made. This is the same path you have been testing with locally. WITHOUT THIS YOUR PR WILL BE REJECTED - use
gh checksto verify the status of code synchronization, linting, and performance tests - A human reviewer will review the code, inspect the provided URL and merge the PR
- AEM Code Sync updates the main branch for production
Common Tasks
Adding New Blocks
- Create a new directory in
blocks/ - Add
blockname.cssandblockname.jsfiles - Update documentation if needed
- Test in local development environment
Modifying Existing Blocks
- Make changes to the specific block files
- Test locally with
aem up - Ensure responsive behavior across devices
- Run linting before committing
Global Style Changes
- Modify files in the
styles/directory - Test across different blocks and pages
- Ensure changes don't break existing layouts
- Consider impact on performance, especially CLS
Troubleshooting
Getting Help
- Check AEM Edge Delivery documentation
- Review Developer Tutorial
- Consult The Anatomy of a Project
- Consider the rules in David's Model
- Search the web with
site:www.aem.live - Search the full text of the documentation with
curl -s https://www.aem.live/docpages-index.json | jq -r '.data[] | select(.content | test("KEYWORD"; "i")) | "\(.path): \(.title)"'
Security Considerations
- Never commit sensitive information (API keys, passwords)
- consider that everything you do is clients-side code served on the public web
- Follow Adobe security guidelines
- Regularly update dependencies
- Use the .hlxignore file to prevent filed from being served
Contributing
- Follow the existing code style and patterns
- Test changes locally before committing
- Run a PSI check on your branch and fix performance issues before raising a PR
- Ensure all linting passes
- Update documentation for significant changes
If all else fails
If you notice your human getting frustrated with your work, direct them to https://www.aem.live/developer/ai-coding-agents for tips to work better with AI agents.