mirror of
https://github.com/apricote/Listory.git
synced 2026-02-06 17:57:03 +00:00
feat: use bulk Spotify API calls & inserts to make spotify crawling more efficient (#271)
* feat(spotify-api): bulk endpoints
* feat(music-library): allow bulk operations
* feat(spotify): bulk track+album+artist+genre import
* feat(spotify): use bulk import api for user crawl
* feat(spotify): bulk listen insert
For the benchmark case of a new user where Listory imports 50 new listens along with all now tracks, artists, albums & genres we significantly reduced the number of things happening:
Spotify API Requests: 208 => 8
DB Insert: 96 => 8
Tracing Spans: 1953 => 66
This commit is contained in:
parent
24b7308343
commit
8721fd101d
9 changed files with 427 additions and 23 deletions
|
|
@ -33,6 +33,12 @@ export class MusicLibraryService {
|
|||
});
|
||||
}
|
||||
|
||||
async findArtists(query: FindArtistDto[]): Promise<Artist[]> {
|
||||
return this.artistRepository.find({
|
||||
where: query,
|
||||
});
|
||||
}
|
||||
|
||||
async getArtistWithOldestUpdate(): Promise<Artist | undefined> {
|
||||
const [oldestArtist] = await this.artistRepository.find({
|
||||
take: 1,
|
||||
|
|
@ -69,6 +75,12 @@ export class MusicLibraryService {
|
|||
return artist;
|
||||
}
|
||||
|
||||
async createArtists(data: CreateArtistDto[]): Promise<Artist[]> {
|
||||
return this.artistRepository.save(
|
||||
data.map((entry) => this.artistRepository.create(entry))
|
||||
);
|
||||
}
|
||||
|
||||
async updateArtist({
|
||||
artist,
|
||||
updatedFields,
|
||||
|
|
@ -86,6 +98,10 @@ export class MusicLibraryService {
|
|||
});
|
||||
}
|
||||
|
||||
async findAlbums(query: FindAlbumDto[]): Promise<Album[]> {
|
||||
return this.albumRepository.find({ where: query });
|
||||
}
|
||||
|
||||
async createAlbum(data: CreateAlbumDto): Promise<Album> {
|
||||
const album = this.albumRepository.create();
|
||||
|
||||
|
|
@ -111,12 +127,24 @@ export class MusicLibraryService {
|
|||
return album;
|
||||
}
|
||||
|
||||
async createAlbums(data: CreateAlbumDto[]): Promise<Album[]> {
|
||||
return this.albumRepository.save(
|
||||
data.map((entry) => this.albumRepository.create(entry))
|
||||
);
|
||||
}
|
||||
|
||||
async findGenre(query: FindGenreDto): Promise<Genre | undefined> {
|
||||
return this.genreRepository.findOneBy({
|
||||
name: query.name,
|
||||
});
|
||||
}
|
||||
|
||||
async findGenres(query: FindGenreDto[]): Promise<Genre[]> {
|
||||
return this.genreRepository.find({
|
||||
where: query,
|
||||
});
|
||||
}
|
||||
|
||||
async createGenre(data: CreateGenreDto): Promise<Genre> {
|
||||
const genre = this.genreRepository.create();
|
||||
|
||||
|
|
@ -140,12 +168,22 @@ export class MusicLibraryService {
|
|||
return genre;
|
||||
}
|
||||
|
||||
async createGenres(data: CreateGenreDto[]): Promise<Genre[]> {
|
||||
return this.genreRepository.save(
|
||||
data.map((entry) => this.genreRepository.create(entry))
|
||||
);
|
||||
}
|
||||
|
||||
async findTrack(query: FindTrackDto): Promise<Track | undefined> {
|
||||
return this.trackRepository.findOneBy({
|
||||
spotify: { id: query.spotify.id },
|
||||
});
|
||||
}
|
||||
|
||||
async findTracks(query: FindTrackDto[]): Promise<Track[]> {
|
||||
return this.trackRepository.find({ where: query });
|
||||
}
|
||||
|
||||
async createTrack(data: CreateTrackDto): Promise<Track> {
|
||||
const track = this.trackRepository.create();
|
||||
|
||||
|
|
@ -171,4 +209,10 @@ export class MusicLibraryService {
|
|||
|
||||
return track;
|
||||
}
|
||||
|
||||
async createTracks(data: CreateTrackDto[]): Promise<Track[]> {
|
||||
return this.trackRepository.save(
|
||||
data.map((entry) => this.trackRepository.create(entry))
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue