The page-title service provides programmatic control over title management with a token-based system, inheritance, and lifecycle hooks.
Core service managing page title tokens and DOM updates.
/**
* Service for managing page titles through a token-based system
*/
class PageTitleService extends Service {
/** Array of all registered title tokens */
tokens: PageTitleToken[];
/** Default configuration for new tokens */
_defaultConfig: PageTitleConfig;
constructor(owner: Owner);
/** Add or update a title token */
push(token: PageTitleToken): void;
/** Remove a token by its ID */
remove(id: string): void;
/** Schedule a title update on the next run loop cycle */
scheduleTitleUpdate(): void;
/** Generate the final title string from all tokens */
toString(): string;
/** Hook called after title updates (override in subclass) */
titleDidUpdate(title: string): void;
/** Update title in FastBoot environment */
updateFastbootTitle(title: string): void;
/** Apply default configuration to a token */
applyTokenDefaults(token: PageTitleToken): void;
/** Inherit properties from previous token in chain */
inheritFromPrevious(token: PageTitleToken): void;
/** Get tokens that should be displayed (respects replace behavior) */
get visibleTokens(): PageTitleToken[];
/** Get tokens in final display order (respects front, prepend, append) */
get sortedTokens(): PageTitleToken[];
/** Called when service is destroyed - cleanup router listeners */
willDestroy(): void;
}Service Usage:
import Component from '@glimmer/component';
import { service } from '@ember/service';
import type PageTitleService from 'ember-page-title/services/page-title';
export default class MyComponent extends Component {
@service('page-title') declare pageTitle: PageTitleService;
updateTitle() {
// Add a title token programmatically
this.pageTitle.push({
id: 'my-component-title',
title: 'Dynamic Title',
separator: ' - ',
prepend: true
});
}
removeTitle() {
// Remove a specific token
this.pageTitle.remove('my-component-title');
}
}The service manages titles through a token-based system with automatic ordering and inheritance.
/**
* Add or update a title token in the service
* @param token - Token to add or update
*/
push(token: PageTitleToken): void;
/**
* Remove a token by its unique ID
* @param id - Unique identifier of token to remove
*/
remove(id: string): void;
/**
* Schedule a title update on the next afterRender run loop cycle
*/
scheduleTitleUpdate(): void;Token System Examples:
// Add a basic token
this.pageTitle.push({
id: 'main-title',
title: 'My Application',
separator: ' | '
});
// Add a token that replaces others
this.pageTitle.push({
id: 'error-title',
title: 'Error Occurred',
replace: true
});
// Add a token that always goes first
this.pageTitle.push({
id: 'priority-title',
title: 'URGENT',
front: true
});
// Remove a specific token
this.pageTitle.remove('main-title');The service generates final title strings through a sophisticated ordering and inheritance system.
/**
* Generate the final title string from all tokens
* @returns Complete title string ready for DOM
*/
toString(): string;
/**
* Get tokens that should be displayed (respects replace behavior)
* @returns Array of visible tokens
*/
get visibleTokens(): PageTitleToken[];
/**
* Get tokens in final display order
* @returns Array of tokens in display order
*/
get sortedTokens(): PageTitleToken[];Title Composition Logic:
replace: true hide previous tokensfront, prepend, and append behavior// Example token processing
const tokens = [
{ id: '1', title: 'Home', separator: ' | ' },
{ id: '2', title: 'Products', separator: ' | ' },
{ id: '3', title: 'Laptop', separator: '' }
];
// Result: "Home | Products | Laptop"
console.log(this.pageTitle.toString());The service provides hooks for custom integration and monitoring.
/**
* Hook called after title updates - override for custom behavior
* @param title - The new title that was set
*/
titleDidUpdate(title: string): void;Custom Service Extension:
// app/services/page-title.js
import PageTitleService from 'ember-page-title/services/page-title';
export default class extends PageTitleService {
titleDidUpdate(title) {
super.titleDidUpdate(title);
// Custom logic after title changes
console.log('Title updated:', title);
// Track analytics
if (window.gtag) {
window.gtag('config', 'GA_MEASUREMENT_ID', {
page_title: title
});
}
// Update meta tags
document.querySelector('meta[property="og:title"]')
?.setAttribute('content', title);
}
}The service applies configurable defaults to new tokens.
/**
* Apply default configuration to a token
* @param token - Token to apply defaults to
*/
applyTokenDefaults(token: PageTitleToken): void;
/**
* Inherit properties from previous token in chain
* @param token - Token to inherit properties for
*/
inheritFromPrevious(token: PageTitleToken): void;
/** Default configuration for new tokens */
_defaultConfig: PageTitleConfig;Default Configuration:
The service reads defaults from config/environment.js:
// config/environment.js
module.exports = function(environment) {
return {
pageTitle: {
separator: ' | ', // Default separator
prepend: true, // Default prepend behavior
replace: null // Default replace behavior
}
};
};The service automatically handles server-side rendering environments.
/**
* Update title in FastBoot environment
* @param title - Title to set in server context
*/
updateFastbootTitle(title: string): void;FastBoot Features: