mirror of
https://github.com/wkulhanek/bonob.git
synced 2025-12-22 01:43:29 +01:00
scroll indicies based on name, for nd needs to be based on sortname from nd api
This commit is contained in:
66
src/smapi.ts
66
src/smapi.ts
@@ -366,6 +366,54 @@ export const artist = (bonobUrl: URLBuilder, artist: ArtistSummary) => ({
|
|||||||
albumArtURI: defaultArtistArtURI(bonobUrl, artist).href(),
|
albumArtURI: defaultArtistArtURI(bonobUrl, artist).href(),
|
||||||
});
|
});
|
||||||
|
|
||||||
|
export const scrollIndicesFrom = (artists: ArtistSummary[]) => {
|
||||||
|
const indicies: Record<string, number | undefined> = {
|
||||||
|
"A":undefined,
|
||||||
|
"B":undefined,
|
||||||
|
"C":undefined,
|
||||||
|
"D":undefined,
|
||||||
|
"E":undefined,
|
||||||
|
"F":undefined,
|
||||||
|
"G":undefined,
|
||||||
|
"H":undefined,
|
||||||
|
"I":undefined,
|
||||||
|
"J":undefined,
|
||||||
|
"K":undefined,
|
||||||
|
"L":undefined,
|
||||||
|
"M":undefined,
|
||||||
|
"N":undefined,
|
||||||
|
"O":undefined,
|
||||||
|
"P":undefined,
|
||||||
|
"Q":undefined,
|
||||||
|
"R":undefined,
|
||||||
|
"S":undefined,
|
||||||
|
"T":undefined,
|
||||||
|
"U":undefined,
|
||||||
|
"V":undefined,
|
||||||
|
"W":undefined,
|
||||||
|
"X":undefined,
|
||||||
|
"Y":undefined,
|
||||||
|
"Z":undefined,
|
||||||
|
}
|
||||||
|
const sortedNames = artists.map(artist => artist.name.toUpperCase()).sort();
|
||||||
|
for(var i = 0; i < sortedNames.length; i++) {
|
||||||
|
const char = sortedNames[i]![0]!;
|
||||||
|
if(Object.keys(indicies).includes(char) && indicies[char] == undefined) {
|
||||||
|
indicies[char] = i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
var lastIndex = 0;
|
||||||
|
const result: string[] = [];
|
||||||
|
Object.entries(indicies).forEach(([letter, index]) => {
|
||||||
|
result.push(letter);
|
||||||
|
if(index) {
|
||||||
|
lastIndex = index;
|
||||||
|
}
|
||||||
|
result.push(`${lastIndex}`);
|
||||||
|
})
|
||||||
|
return result.join(",")
|
||||||
|
}
|
||||||
|
|
||||||
function splitId<T>(id: string) {
|
function splitId<T>(id: string) {
|
||||||
const [type, typeId] = id.split(":");
|
const [type, typeId] = id.split(":");
|
||||||
return (t: T) => ({
|
return (t: T) => ({
|
||||||
@@ -707,6 +755,7 @@ function bindSmapiSoapServiceToExpress(
|
|||||||
title: lang("artists"),
|
title: lang("artists"),
|
||||||
albumArtURI: iconArtURI(bonobUrl, "artists").href(),
|
albumArtURI: iconArtURI(bonobUrl, "artists").href(),
|
||||||
itemType: "container",
|
itemType: "container",
|
||||||
|
canScroll: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: "albums",
|
id: "albums",
|
||||||
@@ -945,6 +994,23 @@ function bindSmapiSoapServiceToExpress(
|
|||||||
throw `Unsupported getMetadata id=${id}`;
|
throw `Unsupported getMetadata id=${id}`;
|
||||||
}
|
}
|
||||||
}),
|
}),
|
||||||
|
getScrollIndices: async (
|
||||||
|
{ id }: { id: string },
|
||||||
|
_,
|
||||||
|
soapyHeaders: SoapyHeaders
|
||||||
|
) => {
|
||||||
|
switch(id) {
|
||||||
|
case "artists": {
|
||||||
|
return login(soapyHeaders?.credentials)
|
||||||
|
.then(({ musicLibrary }) => musicLibrary.artists({ _index: 0, _count: 999999999 }))
|
||||||
|
.then((artists) => ({
|
||||||
|
getScrollIndicesResult: scrollIndicesFrom(artists.results)
|
||||||
|
}))
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
throw `Unsupported getScrollIndices id=${id}`;
|
||||||
|
}
|
||||||
|
},
|
||||||
createContainer: async (
|
createContainer: async (
|
||||||
{ title, seedId }: { title: string; seedId: string | undefined },
|
{ title, seedId }: { title: string; seedId: string | undefined },
|
||||||
_,
|
_,
|
||||||
|
|||||||
@@ -26,6 +26,7 @@ import {
|
|||||||
sonosifyMimeType,
|
sonosifyMimeType,
|
||||||
ratingAsInt,
|
ratingAsInt,
|
||||||
ratingFromInt,
|
ratingFromInt,
|
||||||
|
scrollIndicesFrom,
|
||||||
} from "../src/smapi";
|
} from "../src/smapi";
|
||||||
|
|
||||||
import { keys as i8nKeys } from "../src/i8n";
|
import { keys as i8nKeys } from "../src/i8n";
|
||||||
@@ -56,7 +57,7 @@ import dayjs from "dayjs";
|
|||||||
import url, { URLBuilder } from "../src/url_builder";
|
import url, { URLBuilder } from "../src/url_builder";
|
||||||
import { iconForGenre } from "../src/icon";
|
import { iconForGenre } from "../src/icon";
|
||||||
import { formatForURL } from "../src/burn";
|
import { formatForURL } from "../src/burn";
|
||||||
import { range } from "underscore";
|
import _, { range } from "underscore";
|
||||||
import { FixedClock } from "../src/clock";
|
import { FixedClock } from "../src/clock";
|
||||||
import { ExpiredTokenError, InvalidTokenError, SmapiAuthTokens, SmapiToken, ToSmapiFault } from "../src/smapi_auth";
|
import { ExpiredTokenError, InvalidTokenError, SmapiAuthTokens, SmapiToken, ToSmapiFault } from "../src/smapi_auth";
|
||||||
|
|
||||||
@@ -860,6 +861,29 @@ describe("defaultArtistArtURI", () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe("scrollIndicesFrom", () => {
|
||||||
|
describe("artists", () => {
|
||||||
|
it("should be scroll indicies", () => {
|
||||||
|
const artistNames = [
|
||||||
|
"10,000 Maniacs",
|
||||||
|
"99 Bacon Sandwiches",
|
||||||
|
"Aerosmith",
|
||||||
|
"Bob Marley",
|
||||||
|
"beatles", // intentionally lower case
|
||||||
|
"Cans",
|
||||||
|
"egg heads", // intentionally lower case
|
||||||
|
"Moon Cakes",
|
||||||
|
"Moon Boots",
|
||||||
|
"Numpty",
|
||||||
|
"Yellow brick road"
|
||||||
|
]
|
||||||
|
const scrollIndicies = scrollIndicesFrom(_.shuffle(artistNames).map(name => anArtist({ name })))
|
||||||
|
|
||||||
|
expect(scrollIndicies).toEqual("A,2,B,3,C,5,D,5,E,6,F,6,G,6,H,6,I,6,J,6,K,6,L,6,M,7,N,9,O,9,P,9,Q,9,R,9,S,9,T,9,U,9,V,9,W,9,X,9,Y,10,Z,10")
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe("wsdl api", () => {
|
describe("wsdl api", () => {
|
||||||
const musicService = {
|
const musicService = {
|
||||||
generateToken: jest.fn(),
|
generateToken: jest.fn(),
|
||||||
@@ -1410,6 +1434,7 @@ describe("wsdl api", () => {
|
|||||||
title: "Artists",
|
title: "Artists",
|
||||||
albumArtURI: iconArtURI(bonobUrl, "artists").href(),
|
albumArtURI: iconArtURI(bonobUrl, "artists").href(),
|
||||||
itemType: "container",
|
itemType: "container",
|
||||||
|
canScroll: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: "albums",
|
id: "albums",
|
||||||
@@ -1498,6 +1523,7 @@ describe("wsdl api", () => {
|
|||||||
title: "Artiesten",
|
title: "Artiesten",
|
||||||
albumArtURI: iconArtURI(bonobUrl, "artists").href(),
|
albumArtURI: iconArtURI(bonobUrl, "artists").href(),
|
||||||
itemType: "container",
|
itemType: "container",
|
||||||
|
canScroll: true,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: "albums",
|
id: "albums",
|
||||||
@@ -3111,6 +3137,48 @@ describe("wsdl api", () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe("getScrollIndices", () => {
|
||||||
|
itShouldHandleInvalidCredentials((ws) =>
|
||||||
|
ws.getScrollIndicesAsync({ id: `artists` })
|
||||||
|
);
|
||||||
|
|
||||||
|
describe("for artists", () => {
|
||||||
|
let ws: Client;
|
||||||
|
|
||||||
|
const artist1 = anArtist({ name: "Aerosmith" });
|
||||||
|
const artist2 = anArtist({ name: "Bob Marley" });
|
||||||
|
const artist3 = anArtist({ name: "Beatles" });
|
||||||
|
const artist4 = anArtist({ name: "Cat Empire" });
|
||||||
|
const artist5 = anArtist({ name: "Metallica" });
|
||||||
|
const artist6 = anArtist({ name: "Yellow Brick Road" });
|
||||||
|
|
||||||
|
beforeEach(async () => {
|
||||||
|
ws = await createClientAsync(`${service.uri}?wsdl`, {
|
||||||
|
endpoint: service.uri,
|
||||||
|
httpClient: supersoap(server),
|
||||||
|
});
|
||||||
|
setupAuthenticatedRequest(ws);
|
||||||
|
musicLibrary.artists.mockResolvedValue({
|
||||||
|
results: [artist1, artist2, artist3, artist4, artist5, artist6],
|
||||||
|
total: 6
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it("should return paging information", async () => {
|
||||||
|
const root = await ws.getScrollIndicesAsync({
|
||||||
|
id: `artists`,
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(root[0]).toEqual({
|
||||||
|
getScrollIndicesResult: scrollIndicesFrom([artist1, artist2, artist3, artist4, artist5, artist6])
|
||||||
|
});
|
||||||
|
expect(musicService.login).toHaveBeenCalledWith(serviceToken);
|
||||||
|
expect(apiTokens.mint).toHaveBeenCalledWith(serviceToken);
|
||||||
|
expect(musicLibrary.artists).toHaveBeenCalledWith({ _index: 0, _count: 999999999 });
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe("createContainer", () => {
|
describe("createContainer", () => {
|
||||||
let ws: Client;
|
let ws: Client;
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user