Library to read Serato DJ history files and emit change events
npm install serato-connectA comprehensive library for reading Serato DJ data, including history files, cue points, beatgrid, crates, and the full track library.
ready, poll, track, history, session, error``bash`
npm install serato-connect
`ts
import { SeratoConnect } from 'serato-connect';
const serato = new SeratoConnect();
// Real-time track monitoring
serato.on('track', async (payload) => {
console.log('Now playing:', payload.track.artist, '-', payload.track.title);
// Get cue points and beatgrid from the audio file
const metadata = await serato.getTrackMetadata(payload.track.filePath);
if (metadata?.markers) {
console.log('Cue points:', metadata.markers.cuePoints);
console.log('Track color:', metadata.markers.trackColor);
}
// Find which crates contain this track
const crates = await serato.findCratesForTrack(payload.track.filePath);
console.log('In crates:', crates);
});
serato.start();
`
`ts`
const serato = new SeratoConnect({
seratoPath?: string, // Path to _Serato_ folder (default: ~/Music/_Serato_)
pollIntervalMs?: number, // Polling interval in ms (default: 2000)
historyMaxRows?: number, // Max history entries per event (default: 100)
});
#### Monitoring Methods
- start() — Begin monitoring history filesstop()
- — Stop monitoringgetNowPlaying()
- — Get currently playing trackgetDeckStates()
- — Get all 4 deck statesrunning
- — Boolean indicating if monitoring is active
#### Library Methods
- getTrackMetadata(filePath) — Read GEOB metadata from audio filegetCrates()
- — Get all cratesgetCrate(name)
- — Get a specific cratefindCratesForTrack(filePath)
- — Find crates containing a trackgetLibraryTracks({ limit?, offset? })
- — Get tracks from databasesearchLibrary(query)
- — Search tracksgetDatabaseStats()
- — Get library statistics
#### Events
- ready — { seratoPath, sessionCount } when history is loadedpoll
- — Emitted on each poll cycletrack
- — { track, deckId } when currently playing track changeshistory
- — { seratoPath, count, tracks } with recent history entriessession
- — { session } when a new session is detectederror
- — (error) for any recoverable errors
#### Track Metadata
`ts
import { getTrackMetadata } from 'serato-connect';
const metadata = await getTrackMetadata('/path/to/track.mp3');
console.log(metadata.markers?.cuePoints); // Cue points
console.log(metadata.markers?.loops); // Loops
console.log(metadata.beatgrid?.markers); // Beatgrid
console.log(metadata.autotags?.bpm); // Analyzed BPM
`
#### GEOB Parsers (Low-level)
`ts
import {
parseMarkers2,
parseBeatgrid,
parseAutotags,
} from 'serato-connect';
// Parse raw GEOB frame data
const markers = parseMarkers2(geobBuffer);
const beatgrid = parseBeatgrid(beatgridBuffer);
`
#### Crates
`ts
import { getAllCrates, parseCrate, findCratesForTrack } from 'serato-connect';
const crates = await getAllCrates('/path/to/_Serato_');
const crate = await parseCrate('/path/to/crate.crate');
const crateNames = await findCratesForTrack('/path/to/_Serato_', '/path/to/track.mp3');
`
#### Database
`ts
import {
getLibraryTracks,
searchLibrary,
getDatabaseStats,
} from 'serato-connect';
const tracks = await getLibraryTracks('/path/to/_Serato_');
const results = await searchLibrary('/path/to/_Serato_', 'daft punk');
const stats = await getDatabaseStats('/path/to/_Serato_');
`
#### Encoding Utilities
`ts
import {
decodeSerato32,
encodeSerato32,
decodeWithLinebreaks,
encodeWithLinebreaks,
} from 'serato-connect';
// Serato32 encoding (for colors and positions)
const [r, g, b] = decodeSerato32(enc1, enc2, enc3, enc4);
// Base64 with linebreaks (for FLAC/Vorbis comments)
const decoded = decodeWithLinebreaks(base64String);
`
`ts
interface SeratoCuePoint {
index: number; // 0-7
position: number; // Milliseconds
color: SeratoColor; // { r, g, b }
name?: string; // Up to 51 chars
}
interface SeratoLoop {
index: number;
startPosition: number; // Milliseconds
endPosition: number; // Milliseconds
color: SeratoColor; // { r, g, b, a }
locked: boolean;
name?: string;
}
interface SeratoBeatgridMarker {
position: number; // Seconds
bpm?: number; // Terminal marker only
beatsToNext?: number; // Non-terminal markers
}
interface SeratoCrate {
name: string;
path: string;
trackPaths: string[];
}
interface SeratoDatabaseTrack {
filePath: string;
title?: string;
artist?: string;
album?: string;
genre?: string;
key?: string;
bpm?: number;
// ... and more
}
``
This library's format parsing is based on research and code from:
- triseratops by @Holzhaus — Rust library for Serato metadata (MPL-2.0)
- serato-tags by @Holzhaus — Format documentation
- serato-tools by @bvandercar-vt — Python library for Serato data
- seratoparser by @SpinTools — Go library for Serato database
- Mixxx Wiki — Database format documentation
- music-metadata by @Borewit — Audio file tag reading
- alphatheta-connect — Pioneer Pro DJ Link integration
- rekordbox-connect — Rekordbox database integration
- stagelinq — Denon StageLinq integration
These libraries power Now Playing — a real-time track display app for DJs and streamers.
MIT