Complete technical documentation for the AnyChart documentation generation engine. This document is intended for developers and AI agents continuing work on this project.
- Overview
- Technology Stack
- System Architecture
- Operating Modes
- Configuration
- Generation Pipeline
- Validation & Report System
- Notification System
- Web Application & Routing
- Admin Panel
- Database Schema
- Offline ZIP Generation
- Staging vs Production
- Deployment (CI/CD)
- Source File Reference
- Custom Markdown Syntax
- Key Data Flows
The docs-engine converts markdown documentation from the docs.anychart.com repository into a fully searchable, versioned documentation website. It consists of two logical parts:
- Generator (backend) - Clones the docs repo, parses markdown, validates content, generates HTML, stores results in PostgreSQL, and triggers notifications.
- Web server (frontend) - Serves the generated HTML, handles search, version routing, admin panel, report pages, sitemap, and offline ZIP downloads.
The two parts communicate asynchronously via Redis queues. They can run together in a single process or as separate processes.
| Component | Technology | Version | Notes |
|---|---|---|---|
| Language | Clojure | 1.9.0 | JVM-based |
| Build tool | Leiningen | - | project.clj |
| Component system | Stuart Sierra Component | 0.3.2 | Lifecycle management |
| Web server | http-kit | 2.3.0 | Async HTTP server |
| Routing | Compojure | 1.6.1 | Ring-compatible |
| Middleware | Ring | 1.7.0 | JSON, params, keyword params |
| Templating | Selmer | 1.12.2 | Django-style templates |
| HTML generation | Hiccup | 1.0.5 | Clojure DSL for HTML |
| HTML parsing | Jsoup | 1.11.3 | TOC generation |
| HTML scraping | Enlive | 1.1.6 | Offline doc generation |
| Markdown | markdown-clj | 1.0.4 | With custom transformers |
| Database | PostgreSQL | 9.3+ | JSONB for config/report |
| DB access | clojure.java.jdbc | 0.7.8 | With HoneySQL query builder |
| Connection pool | c3p0 | 0.3.3 | JDBC connection pooling |
| Message queue | Redis (Carmine) | 2.19.1 | Task queuing |
| Full-text search | Sphinx | - | External search engine |
| Samples parser | playground-samples-parser | 0.2.6 | AnyChart proprietary |
| Link checker | link-checker | 0.2.10 | AnyChart proprietary |
| Image generation | PhantomJS + imgscalr | - | Screenshot generation |
| Version comparison | version-clj | 0.1.2 | Semantic version sorting |
| Parallel processing | Claypoole | 1.1.4 | Thread pool for page gen |
| CSS generation | Garden | 1.3.6 | Admin panel styles |
| Config format | TOML | 0.1.3 | Configuration files |
| Logging | Timbre | 4.10.0 | Structured logging |
| CI/CD | Travis CI | - | Branch-based deploy |
The application uses Stuart Sierra's Component library for dependency injection and lifecycle management.
+-----------+
| Notifier |
+-----+-----+
|
+-----------+-----------+
| |
+-----v-----+ +-----v-----+
| Generator | | Web |
+-----+-----+ +-----+-----+
| |
+---------+---------+ +--------+--------+
| | | | | |
+---v---+ +--v--+ +----v+ +v----+ +-v--+ +--v----+
| JDBC | |Redis| |Offline|| JDBC| |Redis| |Sphinx |
+-------+ +-----+ |Gen |+-----+ +-----+ +-------+
+------+
|
+-----+-----+
| JDBC|Redis|
+-----+-----+
| Component | Namespace | Role |
|---|---|---|
jdbc |
wiki.components.jdbc |
PostgreSQL connection pool |
redis |
wiki.components.redis |
Redis connection + worker creation |
notifier |
wiki.components.notifier |
Slack/Skype notification dispatch |
generator |
wiki.components.generator |
Redis worker that triggers doc generation |
offline-generator |
wiki.components.offline-generator |
Redis worker for ZIP generation |
web |
wiki.components.web |
http-kit web server |
sphinx |
wiki.components.sphinx |
Sphinx full-text search connection |
indexer |
wiki.components.indexer |
Redis worker that triggers search reindexing |
Entry point: wiki.core/-main
java -jar docs-engine.jar <mode> <config-path>
| Mode | System Created | Components Started | Use Case |
|---|---|---|---|
all |
all-system |
Web + Generator + Offline-generator + Indexer + Sphinx + Notifier | Single-process deployment |
frontend |
frontend-system |
Web + Indexer + Sphinx + Notifier (no generator/offline) | Serving docs only |
backend |
generator-system |
Generator + Offline-generator + Notifier (no web) | Building docs only |
Source: src/wiki/core.clj:110-119
The all mode is used for development. In production, frontend and backend can be
separated to scale independently.
Configuration is loaded from a TOML file passed as the second CLI argument.
All sections are required (validated via clojure.spec in wiki.config.spec):
| Key | Type | Description |
|---|---|---|
prefix |
string | Environment identifier: "local", "stg", or "prod" |
domain |
string | Base URL (e.g., "https://docs.anychart.com/") |
reference |
string | API reference hostname (e.g., "api.anychart.com") |
playground |
string | Playground hostname (e.g., "playground.anychart.com") |
playground-project |
string | Default playground project name |
| Key | Type | Description |
|---|---|---|
subprotocol |
string | "postgresql" |
subname |
string | "//localhost:5432/docs_db" |
classname |
string | "org.postgresql.Driver" |
user |
string | Database user |
password |
string | Database password |
| Key | Type | Description |
|---|---|---|
host |
string | Redis hostname |
port |
int | Redis port |
db |
int | Redis database number |
| Key | Type | Description |
|---|---|---|
queue |
string | Redis queue name for generation jobs |
redirects-queue |
string | Redis queue name for redirect updates |
indexer-queue |
string | Redis queue name for search reindexing |
git-ssh |
string | Path to SSH key wrapper script for git |
data-dir |
string | Working directory for cloned repos and builds |
static-dir |
string | Directory for static assets (images) |
images-dir |
string | Directory for generated screenshot images |
reference-versions |
string | URL to fetch API reference version list |
reference-default-version |
string | Fallback API version |
max-processes |
int | Max parallel processes |
show-branches |
boolean | Whether to show non-release branches |
generate-images |
boolean | Whether to generate PhantomJS screenshots |
phantom-engine |
string | Path to PhantomJS binary |
generator |
string | Generator identifier |
| Key | Type | Description |
|---|---|---|
port |
int | HTTP listen port |
debug |
boolean | Debug mode |
queue |
string | Redis queue for triggering builds from admin |
redirects-queue |
string | Redis queue for redirect updates |
zip-queue |
string | Redis queue for ZIP generation requests |
static |
int | Static file cache duration |
max-line |
int | Max line length for content |
| Key | Type | Description |
|---|---|---|
zip-dir |
string | Temporary directory for ZIP file assembly |
queue |
string | Redis queue for ZIP jobs |
| Key | Type | Description |
|---|---|---|
subprotocol |
string | "mysql" (Sphinx uses MySQL protocol) |
subname |
string | Sphinx connection string |
table |
string | Sphinx index name (e.g., "docs_stg_index") |
| Key | Type | Description |
|---|---|---|
channel |
string | Default Slack channel |
token |
string | Slack webhook token |
username |
string | Bot username |
| Key | Type | Description |
|---|---|---|
id |
string | Skype bot ID |
chat-id |
string | Skype chat ID |
key |
string | Skype API key |
release-chat-id |
string | (optional) Separate chat for releases |
Source: src/wiki/config/spec.clj, src/wiki/config/core.clj
The generation pipeline is orchestrated by wiki.generator.core/generate and
wiki.generator.core/generate-version.
1. Git Fetch & Checkout
|
2. Branch Filtering (skip unchanged commits)
|
3. Parse Directory Structure
|
4. Create Version Record in DB
|
5. Copy Static Assets (images)
|
6. Generate Pages (parallel)
|-- Parse markdown with custom transformers
|-- Validate links (canonical, HTTPS, direct, env)
|-- Detect missing/broken samples
|-- Validate image markdown syntax
|-- Generate HTML with TOC
|-- Store page in DB with metadata
|-- Collect per-page error reports
|
7. Generate Landing Page
|
8. Remove Previous Version Data
|
9. Trigger Offline ZIP Generation (async)
|
10. Check Broken Links (conditional, async)
|-- Fetch sitemap URLs
|-- Crawl all pages for 404s
|-- Deliver results via promise
|
11. Store Report in DB
|
12. Send Completion Notifications
update-repo: Runsgit fetch -p -Pto get latest refsremote-branches: Lists all remote branches and tags with commit hashescheckout: Copies repo to version-specific directory and checks out branchmerge-conflicts: Checks for conflicts between branch anddevelop
- Compares current commit hash against stored version in DB
- Skips rebuilding if commit hasn't changed (
need-rebuild?) - Filters branches based on
show-branchesconfig flag
- Recursively walks the directory tree
- Identifies
.mdfiles (excludingreadme.md) - Reads document headers (Clojure map syntax
{:index 5 :title "Custom Title"}) - Builds a hierarchical tree sorted by index and title
- Reads
group.cfgfiles for folder-level configuration
- Creates version record in
versionstable with tree structure as JSON - Copies
images/directories to static serving directory
Uses Claypoole thread pool (CPU count + 2 threads) for parallel processing.
For each page:
-
Link analysis (
wiki.generator.analysis.core/check-links): Scans raw markdown for problematic link patterns before HTML conversion. -
Markdown-to-HTML (
wiki.generator.markdown/to-html): Usesmarkdown-cljwith custom transformer chain:branch-name-transformer: Replaces{branch_name}with versionimage-checker: Validates image markdown syntax- Standard markdown transformers
sample-transformer: Processes{sample}...{sample}blocks
-
API/Playground link processing:
{api:path}text{api}→ links to API reference{pg:project/path}text{pg}→ links to playground
-
TOC generation (
wiki.generator.toc): Parses the generated HTML with Jsoup, extractsh1-h6elements, builds nested<ul>/<li>navigation. Validates heading hierarchy. -
Tag extraction: Processes
{tags}tag1, tag2{tags}blocks. -
Variable replacement: Substitutes
{{variable}}with values from version config. -
Database storage: Inserts page with URL, title, HTML content, last-modified timestamp, tags array, and config JSONB (containing links metadata).
Runs as a separate Redis worker. Uses futures for non-blocking generation. See Offline ZIP Generation.
Uses the link-checker library to crawl all pages from the sitemap:
- Fetches sitemap URLs from
{domain}sitemap/{version} - Configurable URL filtering (
check-fn,add-fn) - Excludes known false positives (LinkedIn, export-server.jar, download page)
- Results delivered via a Clojure promise to avoid blocking
- Max 45 crawl iterations
Source: src/wiki/generator/core.clj, src/wiki/generator/documents.clj
This is the engine's QA system. It runs during every build and produces a report accessible via the web interface.
| Error Key | Detected By | What It Catches |
|---|---|---|
http-links |
analysis.core/check-https |
URLs starting with http: (should be https:) |
non-canonical-links |
analysis.core/check-canonical |
Links containing version numbers like /7.13.0/ or /latest |
direct-links |
analysis.core/check-direct |
Direct versioned links to docs.anychart.com, api.anychart.com, or playground.anychart.com |
env-links |
analysis.core/check-env |
Links containing stg, develop, localhost, or 8080 |
sample-not-available |
markdown/build-sample-div |
{sample}path{sample} references a sample that doesn't exist in the parsed samples |
sample-parsing-error |
markdown/sample-transformer |
Malformed {sample}...{sample} syntax that throws an exception |
image-format-error |
markdown/image-checker |
Image markdown with invalid parameter syntax |
toc-error |
toc/add-toc, toc/menu-from-hs |
Missing <h1>, non-sequential headings (e.g., h1 → h3 skipping h2) |
| Error Key | Detected By | What It Catches |
|---|---|---|
broken-links |
analysis.core/check-broken-links |
Actual HTTP 404 errors found by crawling generated pages |
The check-links function in analysis.core scans raw markdown (before HTML conversion)
using regex to extract all [text](url) patterns. It then runs each URL through four
checker functions:
check-canonical: Rejects URLs containing /X.Y.Z/ patterns or /latest
check-https: Rejects URLs starting with http:
check-direct: Rejects versioned URLs pointing to anychart domains
check-env: Rejects URLs containing stg/develop/localhost/8080
The version-level config can specify report.http-ignore — a list of URL substrings
to exempt from the HTTPS check.
Stored as JSONB in versions.report:
{:error-links
[{:page-url "Quick_Start/Getting_Started"
:http-links ["http://example.com/resource"]
:non-canonical-links ["/7.13.0/api/anychart"]
:direct-links ["https://docs.anychart.com/7.13.0/Quick_Start"]
:env-links ["https://stg.anychart.com/something"]
:sample-not-available ["Quick_Start/Getting_Started"]
:sample-parsing-error ["Quick_Start/Getting_Started"]
:image-format-error ["Quick_Start/Getting_Started"]
:toc-error ["h3 - nested too deep"]}
;; ... one entry per page with errors
]
:broken-links
[{:url "https://docs.anychart.com/develop/Quick_Start/Getting_Started"
:links [{:href "https://broken.example.com" :text "link text"}]}
;; ... one entry per page with 404s
]
:check-broken-links-disabled false} ;; true if link checker was skippedURL: GET /:version/report
Rendered by wiki.generator.analysis.page/page using Hiccup. Shows:
- "Report for version X.Y.Z" heading with link to JSON version
- "Pages with errors" section: Table per page listing all error types and values. Shows green "Not found." if no errors.
- "Pages with 404 links" section: Table with page URL and broken links.
Shows gray message if link checker was disabled, with instructions to use
#linksor#allcommit message flags.
Source: src/wiki/generator/analysis/page.clj:17-86
URL: GET /:version/report.json
Returns the raw report JSONB with Access-Control-Allow-Origin: * header.
Source: src/wiki/web/handlers/report_handlers.clj:7-12
The admin panel at /_admin_ has a "Show report" button that opens the report page
for the currently selected version.
Controlled by wiki.generator.core/need-check-links:
Link checking is ENABLED when:
- Branch is a released version (matches v\d+ pattern)
- Branch is "master"
- Commit message contains "#links"
- Commit message contains "#all"
- Rebuild triggered with "with link checking" from admin
Link checking is DISABLED when:
- prefix is "local" (development)
- Fast mode rebuild from admin
- None of the above conditions met
When disabled, the report's check-broken-links-disabled flag is set to true and the
report page shows a gray notice explaining how to enable it.
Source: src/wiki/generator/core.clj:67-76
Notifications are dispatched through wiki.components.notifier which delegates to
wiki.notification.slack and wiki.notification.skype.
| Event | Channels | Trigger |
|---|---|---|
| Build started | Slack | New generation cycle begins |
| Version build started | Slack, Skype | Individual version build begins |
| Version build complete | Slack, Skype | Individual version finishes (with error summary) |
| Build complete | Slack | All versions finished |
| Build failed | Slack, Skype | Exception during generation |
| Sample not available | Slack (delayed) | {sample} references missing sample |
| Sample parsing error | Slack (delayed) | {sample} syntax error |
| Image format error | Slack (delayed) | Image markdown syntax error |
| 404 detected | Slack (#docs-404-errors) |
Visitor hits a 404 page |
When a version build completes, the notifier aggregates all errors into a summary:
Direct links: N
Non canonical links: N
Http links: N
Env links: N
Unavailable samples: N
Parsing samples errors: N
Parsing images errors: N
TOC errors: N
Conflicts with develop: N
404 errors: N
Only non-zero counts are included. If all counts are zero, a simple "complete" message is sent instead of a warnings summary.
- Uses Slack incoming webhooks (
anychart-team.slack.com/services/hooks/incoming-webhook) - Per-page errors (sample, image) use
sendon a Clojureagentfor batching (notify-attach-delay) — they accumulate and are sent together with the next non-delayed notification - Build lifecycle messages use
notify-attachwhich flushes the agent queue - 404 errors go to a dedicated
#docs-404-errorschannel
Source: src/wiki/notification/slack.clj, src/wiki/components/notifier.clj
The web layer is defined in wiki.web.routes using Compojure.
| Method | Path | Handler | Description |
|---|---|---|---|
| GET | / |
show-landing |
Redirects to Quick_Start |
| GET | /_admin_ |
admin-handlers/admin-page |
Admin panel |
| GET | /_redirects_ |
admin-handlers/redirects-page |
Show active redirects |
| GET | /_update_ |
admin-handlers/update-versions |
Trigger build (webhook) |
| POST | /_update_ |
admin-handlers/update-versions |
Trigger build (webhook) |
| POST | /_delete_ |
admin-handlers/delete-version |
Delete a version |
| POST | /_rebuild_ |
admin-handlers/rebuild-version |
Rebuild specific version |
| GET | /sitemap |
sitemap-handlers/show-sitemap |
Sitemap index |
| GET | /sitemap.xml |
sitemap-handlers/show-sitemap |
Sitemap XML |
| GET | /sitemap/:version |
sitemap-handlers/show-sitemap-version |
Per-version sitemap |
| GET | /latest |
show-latest |
Redirect to latest Quick_Start |
| GET | /latest/* |
try-show-latest-page |
Redirect /latest/X to /X |
| POST | /links |
links-handlers/links |
Links API |
| GET | /:version/check/* |
try-show-page |
Check if page exists |
| GET | /:version/search |
search-page |
Search within version |
| POST | /:version/search-data |
search-data |
Search API (JSON) |
| GET | /:version/_generate-zip_ |
zip-handlers/generate-zip |
Trigger ZIP generation |
| GET | /:version/download |
zip-handlers/download-zip |
Download offline ZIP |
| GET | /:version/report.json |
report-handlers/report |
JSON report |
| GET | /:version/report |
report-handlers/report-page |
HTML report page |
| GET | /*-json |
show-page-data |
Page data as JSON |
| GET | /* |
show-page-middleware |
Display documentation page |
Applied in order (bottom-up in code, outermost first):
wrap-json-response— JSON response encodingwrap-google-analytics-optimize— Detect GA Speed Insights user agentwrap-redirect— Apply configured URL redirectswrap-json-params— Parse JSON request bodieswrap-params— Parse query string parameterswrap-keyword-params— Keywordize parameter names
The check-version-middleware extracts the version from the URL path, looks up matching
versions in the database, and passes the resolved version to the handler. If no matching
version is found, it returns 404.
The check-version-middleware-by-url handles the ambiguity where the first path segment
could be either a version key or a page URL.
Source: src/wiki/web/routes.clj
URL: /_admin_
The admin panel provides version management with these controls:
| Control | Action |
|---|---|
| Start updating versions | Enqueues a generate command — equivalent to GitHub webhook |
| Version selector | Dropdown of all non-hidden versions, sorted by semantic version |
| Rebuild (dropdown) | Three rebuild modes for selected version |
| Remove | Deletes selected version from database |
| Show report | Opens /:version/report for selected version |
| Show redirects | Opens /_redirects_ to view active URL redirects |
| Mode | Parameter | Link Checking |
|---|---|---|
| Commit message flags | {} |
Based on commit message #links/#all flags |
| Fast | {:fast true} |
Disabled |
| With link checking | {:linkchecker true} |
Enabled |
When rebuilding, the existing version data is first removed from the database, then a generate job is enqueued to Redis with the version key and mode parameters.
Source: src/wiki/views/admin/admin_page.clj, src/wiki/web/handlers/admin_handlers.clj
Defined in src/sql/scheme.sql.
| Column | Type | Description |
|---|---|---|
id |
INTEGER (PK) | Auto-increment via version_id_seq |
key |
VARCHAR(255) | Version identifier (e.g., "8.0.0", "develop") |
commit |
VARCHAR(40) | Git commit hash |
hidden |
BOOLEAN | Soft-delete flag (default false) |
tree |
TEXT | JSON string of directory tree structure |
zip |
BYTEA | Binary offline documentation ZIP file |
config |
JSONB | Version configuration from config.toml in docs repo |
report |
JSONB | Validation report (see Report Data Structure) |
| Column | Type | Description |
|---|---|---|
id |
INTEGER (PK) | Auto-increment via folder_id_seq |
version_id |
INTEGER (FK) | References versions.id |
url |
VARCHAR(255) | Folder URL path |
default_page |
VARCHAR(255) | Default page name when folder URL is accessed |
| Column | Type | Description |
|---|---|---|
id |
INTEGER (PK) | Auto-increment via page_id_seq |
version_id |
INTEGER (FK) | References versions.id |
url |
VARCHAR(255) | Page URL path |
full_name |
VARCHAR(255) | Display title |
content |
TEXT | Generated HTML content |
last_modified |
BIGINT | Unix timestamp of last git commit to source file |
tags |
VARCHAR(255)[] | PostgreSQL array of tag strings |
config |
JSONB | Page metadata including links (api, playground, samples) |
versions 1──────N pages
versions 1──────N folders
When a version is deleted or rebuilt, all associated pages and folders are cascade-deleted in application code (not via DB constraints).
The system generates downloadable ZIP archives of the documentation for offline use.
- After page generation completes,
generate-zipis called on theoffline-generatorcomponent - The component uses an atom-backed state map with futures to prevent duplicate generation
wiki.offline.core/generate-zipcreates self-contained HTML files:- Downloads and embeds external resources (CSS, JS, images)
- Rewrites links for local file access
- Uses
local-page.selmertemplate (different from online template)
- The resulting ZIP is stored as BYTEA in the
versions.zipcolumn - Users download via
GET /:version/download
- Automatically after every successful version build
- Manually via
GET /:version/_generate-zip_from admin
Source: src/wiki/components/offline_generator.clj, src/wiki/offline/core.clj,
src/wiki/offline/zip.clj
The common.prefix config value determines the environment:
| Prefix | Environment | Domain |
|---|---|---|
"local" |
Development | localhost:PORT |
"stg" |
Staging | docs.anychart.stg |
"prod" |
Production | docs.anychart.com |
| Feature | Local | Staging | Production |
|---|---|---|---|
| Link checking | Always disabled | Conditional (commit flags) | Always enabled for releases |
| Branch visibility | Configurable | Configurable | Releases + master only |
| Notifications | Active | Active | Active |
| Report generation | Active | Active | Active |
| Sphinx search index | docs_local_index |
docs_stg_index |
docs_prod_index |
- Push to
stagingbranch → Travis CI builds and deploys todocs-stgservers - All branches/versions are rebuilt from git
- Reports are generated at
/:version/report - Review the report for errors before promoting to production
- Broken link checking can be triggered with
#linksin commit message - Merge
staging→masterto deploy to production
Build: lein uberjar
→ Produces: target/uberjar/wiki-2.0-standalone.jar
Branch Mapping:
master → APP=docs-prod
staging → APP=docs-stg
bible → APP=bible-stg
Deploy Steps:
1. Decrypt SSH key (.travis/id_rsa.enc)
2. SCP JAR to Server 1 (104.236.66.244:/apps/$APP/)
3. SCP JAR to Server 2 (68.183.148.118:/apps/$APP/)
4. SSH restart: supervisorctl restart $APP
- Servers run the JAR under supervisord
- Each app (
docs-prod,docs-stg,bible-stg) has its own:- Config TOML file
- PostgreSQL database
- Redis instance/database number
- Sphinx index
| File | Namespace | Purpose |
|---|---|---|
src/wiki/core.clj |
wiki.core |
Entry point, system definitions, -main |
src/wiki/config/core.clj |
wiki.config.core |
Runtime config accessor functions |
src/wiki/config/spec.clj |
wiki.config.spec |
Configuration validation specs |
| File | Namespace | Purpose |
|---|---|---|
src/wiki/components/generator.clj |
wiki.components.generator |
Redis worker for doc generation |
src/wiki/components/offline_generator.clj |
wiki.components.offline-generator |
Redis worker for ZIP generation |
src/wiki/components/web.clj |
wiki.components.web |
http-kit server component |
src/wiki/components/jdbc.clj |
wiki.components.jdbc |
PostgreSQL connection component |
src/wiki/components/redis.clj |
wiki.components.redis |
Redis connection + worker management |
src/wiki/components/sphinx.clj |
wiki.components.sphinx |
Sphinx search component |
src/wiki/components/indexer.clj |
wiki.components.indexer |
Search index updater |
src/wiki/components/notifier.clj |
wiki.components.notifier |
Notification dispatch |
| File | Namespace | Purpose |
|---|---|---|
src/wiki/generator/core.clj |
wiki.generator.core |
Main generation orchestration |
src/wiki/generator/documents.clj |
wiki.generator.documents |
Per-page generation with parallel processing |
src/wiki/generator/markdown.clj |
wiki.generator.markdown |
Markdown→HTML with custom transformers |
src/wiki/generator/toc.clj |
wiki.generator.toc |
Table of contents generation |
src/wiki/generator/git.clj |
wiki.generator.git |
Git operations (fetch, checkout, conflicts) |
src/wiki/generator/struct.clj |
wiki.generator.struct |
Directory structure parsing |
src/wiki/generator/tree.clj |
wiki.generator.tree |
Navigation tree generation |
src/wiki/generator/versions.clj |
wiki.generator.versions |
Branch filtering, version cleanup |
src/wiki/generator/api_versions.clj |
wiki.generator.api-versions |
API reference version fetching |
src/wiki/generator/analysis/core.clj |
wiki.generator.analysis.core |
Link validation + broken link crawling |
src/wiki/generator/analysis/page.clj |
wiki.generator.analysis.page |
HTML report page rendering |
src/wiki/generator/phantom/core.clj |
wiki.generator.phantom.core |
PhantomJS screenshot generation |
src/wiki/generator/phantom/download.clj |
wiki.generator.phantom.download |
Resource downloading for phantomJS |
| File | Namespace | Purpose |
|---|---|---|
src/wiki/data/versions.clj |
wiki.data.versions |
Version CRUD, report storage, ZIP access |
src/wiki/data/pages.clj |
wiki.data.pages |
Page CRUD, search |
src/wiki/data/folders.clj |
wiki.data.folders |
Folder CRUD |
src/wiki/data/search.clj |
wiki.data.search |
Sphinx search queries |
src/wiki/data/utils.clj |
wiki.data.utils |
JSONB conversion utilities |
| File | Namespace | Purpose |
|---|---|---|
src/wiki/web/routes.clj |
wiki.web.routes |
All route definitions and middleware |
src/wiki/web/helpers.clj |
wiki.web.helpers |
Request helper functions (jdbc, redis, config) |
src/wiki/web/redirects.clj |
wiki.web.redirects |
URL redirect middleware and config parsing |
src/wiki/web/tree.clj |
wiki.web.tree |
Navigation tree rendering (Selmer tag) |
src/wiki/web/handlers/admin_handlers.clj |
wiki.web.handlers.admin-handlers |
Admin panel routes |
src/wiki/web/handlers/report_handlers.clj |
wiki.web.handlers.report-handlers |
Report JSON and HTML endpoints |
src/wiki/web/handlers/search_handlers.clj |
wiki.web.handlers.search-handlers |
Search page and API |
src/wiki/web/handlers/sitemap_handlers.clj |
wiki.web.handlers.sitemap-handlers |
Sitemap generation |
src/wiki/web/handlers/zip_handlers.clj |
wiki.web.handlers.zip-handlers |
ZIP download and generation trigger |
src/wiki/web/handlers/links_handlers.clj |
wiki.web.handlers.links-handlers |
Links API |
src/wiki/web/handlers/handers_404.clj |
wiki.web.handlers.handers-404 |
404 error handler (note: typo in filename) |
| File | Namespace | Purpose |
|---|---|---|
src/wiki/views/admin/admin_page.clj |
wiki.views.admin.admin-page |
Admin panel HTML (Hiccup) |
src/wiki/views/main/main_page.clj |
wiki.views.main.main-page |
Main page HTML |
src/wiki/views/common.clj |
wiki.views.common |
Shared HTML components |
src/wiki/views/iframe.clj |
wiki.views.iframe |
Sample iframe HTML |
src/wiki/views/page404/page404.clj |
wiki.views.page404.page404 |
404 page HTML |
src/wiki/views/resources.clj |
wiki.views.resources |
Resource URL helpers |
| File | Namespace | Purpose |
|---|---|---|
src/wiki/notification/slack.clj |
wiki.notification.slack |
Slack webhook integration |
src/wiki/notification/skype.clj |
wiki.notification.skype |
Skype bot integration |
| File | Namespace | Purpose |
|---|---|---|
src/wiki/offline/core.clj |
wiki.offline.core |
Offline HTML generation |
src/wiki/offline/zip.clj |
wiki.offline.zip |
ZIP file creation |
| File | Purpose |
|---|---|
resources/templates/page.selmer |
Main documentation page template |
resources/templates/local-page.selmer |
Offline/local page template |
resources/templates/doc_sample.selmer |
Embedded sample with iframe |
resources/templates/sample.selmer |
Interactive sample with playground link |
resources/templates/samples-update.selmer |
Sample initialization script |
resources/templates/phantom.selmer |
PhantomJS rendering template |
resources/templates/search.selmer |
Search page template |
resources/templates/search-results.html |
Search results fragment |
resources/templates/404.selmer |
Error page with search |
resources/templates/google-analytics.selmer |
GA tracking code |
resources/templates/page.html |
Legacy sample page |
| File | Purpose |
|---|---|
src/sql/scheme.sql |
Database schema (versions, folders, pages) |
src/sql/search.sql |
Sphinx full-text search query |
The docs engine extends standard markdown with these custom syntax elements:
{sample}Sample_Path/Sample_Name{sample}
{sample :width 500 :height 300}Sample_Path/Sample_Name{sample}
{sample :width "100%" :height "400px"}Sample_Path/Sample_Name{sample}Embeds an interactive sample from the playground as an iframe.
The sample path is looked up in the parsed samples from the docs repo's samples/ directory.
{api:anychart.charts.Cartesian#column}column(){api}Generates a link to the API reference: //api.anychart.com/{version}/anychart.charts.Cartesian#column
{pg:project/path/to/sample}View in Playground{pg}Generates a link to the playground: //playground.anychart.com/{project}/{version}/{path}
{tags}tag1, tag2, tag3{tags}Adds tags to the page (rendered as <span> elements after the <h1>).
Must appear in the source markdown; stripped from rendered output.
{branch_name}Replaced with the current version/branch name during generation.
{{variable_name}}Replaced with values from the version config's [vars] section.
At the very beginning of a markdown file, an optional Clojure map configures the page:
{:index 5 :title "Custom Page Title"}:index— Sort order within parent folder (default: 1000):title— Override the auto-generated title (filename-based)
A group.cfg file in any folder can configure it:
{:index 3 :title "Getting Started"}GitHub push → webhook → GET /_update_
→ admin-handlers/update-versions
→ Redis enqueue {cmd: "generate"}
→ Generator worker picks up message
→ generator/generate-docs
→ generator.core/generate
→ ... (see Generation Pipeline)
Admin panel → POST /_rebuild_ {version: "8.0.0", fast: true}
→ admin-handlers/rebuild-version
→ Remove existing version from DB
→ Redis enqueue {cmd: "generate", version: "8.0.0", fast: true}
→ Generator worker picks up message
→ Rebuilds only that version
GET /8.0.0/Quick_Start
→ wrap-redirect (check for URL redirects)
→ check-version-middleware-by-url
→ Resolve "8.0.0" as version key
→ Fetch version from DB
→ Fetch page "Quick_Start" from DB
→ show-page-middleware
→ Load page HTML, tree, versions list
→ Render page.selmer template
→ Response
GET /8.0.0/report
→ report-handlers/report-page
→ vdata/version-report (query versions.report JSONB)
→ analysis-page/page (render Hiccup HTML)
→ Response (full HTML report page)
- Filename typo:
src/wiki/web/handlers/handers_404.clj— missing 'l' in "handlers" - Skype notifications partially disabled: Most Skype calls are commented out in
notifier.clj, only error/warning notifications remain active - PhantomJS: Deprecated technology, only used for screenshot generation which is
optional (
generate-imagesconfig flag) - MySQL dependency: Present in
project.cljsolely for Sphinx (which uses MySQL wire protocol), not for data storage - Clojure 1.9: Relatively old version; upgrading would enable newer spec features
- No Docker: Deployment uses direct JAR deployment via SCP, no containerization
- Travis CI: Travis CI has changed its free tier; may need migration to GitHub Actions or similar