A music player that connects to your cloud/distributed storage.
0
fork

Configure Feed

Select the types of activity you want to include in your feed.

fix: type errors

+132 -39
+1 -1
deno.jsonc
··· 149 149 }, 150 150 "gen:defs:types": { 151 151 "description": "Generate definition Typescript types", 152 - "command": "deno run -A npm:@atcute/lex-cli generate -c ./lexicon.config.js", 152 + "command": "deno run -A npm:@atcute/lex-cli generate -c ./lexicon.config.js && deno run -A ./tasks/replace-gen-import-extensions.ts", 153 153 }, 154 154 "lume": { 155 155 "description": "Run Lume command",
+23 -2
src/components/transformer/output/bytes/automerge/constants.js
··· 2 2 import { base64 } from "iso-base/rfc4648"; 3 3 4 4 /** 5 - * @import { TracksDocument } from "./types.d.ts"; 5 + * @import { ConstituentsDocument, PlaylistsDocument, ThemesDocument, TracksDocument } from "./types.d.ts"; 6 6 */ 7 7 8 + /** @type {Automerge.Doc<ConstituentsDocument>} */ 9 + export const INITIAL_CONSTITUENTS_DOCUMENT = Automerge.load( 10 + base64.decode( 11 + "hW9Kg1fmLLcAeAEQZ2dnbV0O8AUftAeEXT1QVQHsmc9lhGh1ysz4ECa3pEUgzSZG2aF8hob78u7FqeybBQYBAgMCEwIjBkACVgIHFQwhAiMCNAFCAlYCgAECfwB/AX8Bf8KTqcwGfwB/B38KY29sbGVjdGlvbn8AfwEBfwJ/AH8AAA", 12 + ), 13 + ); 14 + 15 + /** @type {Automerge.Doc<PlaylistsDocument>} */ 16 + export const INITIAL_PLAYLISTS_DOCUMENT = Automerge.load( 17 + base64.decode( 18 + "hW9Kg5IPZcsAeAEQIyp0LRYp0l9bpZKWJXTPlgGtUD/lrIatFjiIwoUdtJhh/sBQFIcpPppxduoIp1ArXwYBAgMCEwIjBkACVgIHFQwhAiMCNAFCAlYCgAECfwB/AX8Bf8eTqcwGfwB/B38KY29sbGVjdGlvbn8AfwEBfwJ/AH8AAA", 19 + ), 20 + ); 21 + 22 + /** @type {Automerge.Doc<ThemesDocument>} */ 23 + export const INITIAL_THEMES_DOCUMENT = Automerge.load( 24 + base64.decode( 25 + "hW9Kgw5i4LcAeAEQzljXzJAwgqwMkIT3CseCywF4jHbKg9Q2XqVU26bSDj0GtjkQq1HyriZedXU+vUt5wAYBAgMCEwIjBkACVgIHFQwhAiMCNAFCAlYCgAECfwB/AX8Bf8iTqcwGfwB/B38KY29sbGVjdGlvbn8AfwEBfwJ/AH8AAA", 26 + ), 27 + ); 28 + 8 29 /** @type {Automerge.Doc<TracksDocument>} */ 9 30 export const INITIAL_TRACKS_DOCUMENT = Automerge.load( 10 31 base64.decode( 11 - "hW9Kg3QEcPYAeAEQhsIBj6DgCDtXSHEiZhcqigHxj0/xVpP8KdUJQ8e6qVEgaz7v6CpLuCGB58iHmx4plQYBAgMCEwIjBkACVgIHFQwhAiMCNAFCAlYCgAECfwB/AX8Bf9Xbz8sGfwB/B38KY29sbGVjdGlvbn8AfwEBfwJ/AH8AAA", 32 + "hW9Kg+NQ56QAeAEQxkdUqSHSfh9+5TiM1gnDswH+Nh6PA98q+0oB013slgls/ARH8Fi5NvI9jhK2RZ1DTgYBAgMCEwIjBkACVgIHFQwhAiMCNAFCAlYCgAECfwB/AX8Bf5eSqcwGfwB/B38KY29sbGVjdGlvbn8AfwEBfwJ/AH8AAA", 12 33 ), 13 34 );
+39 -7
src/components/transformer/output/bytes/automerge/element.js
··· 2 2 import { isUint8Array } from "iso-base/utils"; 3 3 4 4 import { computed } from "@common/signal.js"; 5 + import { recursivelyCloneRecords } from "@common/utils.js"; 5 6 import { OutputTransformer } from "../../base.js"; 6 - import { INITIAL_TRACKS_DOCUMENT } from "./constants.js"; 7 - import { recursivelyCloneRecords } from "@toko/diffuse/common/utils.js"; 7 + import { 8 + INITIAL_CONSTITUENTS_DOCUMENT, 9 + INITIAL_TRACKS_DOCUMENT, 10 + } from "./constants.js"; 8 11 9 12 /** 10 13 * @import { SignalReader } from "@common/signal.d.ts"; 11 14 * @import { OutputManagerDeputy } from "@components/output/types.d.ts" 12 - * @import { Track } from "@definitions/types.d.ts" 13 - * @import { TracksDocument } from "./types.d.ts" 15 + * @import { ConstituentsDocument, PlaylistsDocument, ThemesDocument, TracksDocument } from "./types.d.ts" 14 16 */ 15 17 16 18 /** ··· 22 24 23 25 const base = this.base(); 24 26 27 + /** @type {SignalReader<Automerge.Doc<ConstituentsDocument>>} */ 28 + const constituentsDocument = computed(() => { 29 + const value = base.constituents.collection(); 30 + 31 + if (isUint8Array(value)) { 32 + return Automerge.load(value); 33 + } else if (value == undefined) { 34 + return INITIAL_CONSTITUENTS_DOCUMENT; 35 + } else { 36 + // TODO: Better error 37 + throw new Error("Invalid data type"); 38 + } 39 + }); 40 + 25 41 /** @type {SignalReader<Automerge.Doc<TracksDocument>>} */ 26 - const document = computed(() => { 42 + const tracksDocument = computed(() => { 27 43 const value = base.tracks.collection(); 28 44 29 45 if (isUint8Array(value)) { ··· 38 54 39 55 /** @type {OutputManagerDeputy} */ 40 56 const manager = { 57 + constituents: { 58 + ...base.constituents, 59 + collection: computed(() => constituentsDocument().collection), 60 + save: async (newConstituents) => { 61 + const doc = Automerge.change(constituentsDocument(), (d) => { 62 + const clonedCollection = newConstituents.map((constituent) => { 63 + return recursivelyCloneRecords(constituent); 64 + }); 65 + 66 + d.collection = clonedCollection; 67 + }); 68 + 69 + const bytes = Automerge.save(doc); 70 + await base.constituents.save(bytes); 71 + }, 72 + }, 41 73 tracks: { 42 74 ...base.tracks, 43 - collection: computed(() => document().collection), 75 + collection: computed(() => tracksDocument().collection), 44 76 save: async (newTracks) => { 45 - const doc = Automerge.change(document(), (d) => { 77 + const doc = Automerge.change(tracksDocument(), (d) => { 46 78 const clonedCollection = newTracks.map((track) => { 47 79 return recursivelyCloneRecords(track); 48 80 });
+9 -1
src/components/transformer/output/bytes/automerge/types.d.ts
··· 1 - import type { Track } from "@definitions/types.d.ts"; 1 + import type { 2 + Constituent, 3 + Playlist, 4 + Theme, 5 + Track, 6 + } from "@definitions/types.d.ts"; 2 7 8 + export type ConstituentsDocument = { collection: Constituent[] }; 9 + export type PlaylistsDocument = { collection: Playlist[] }; 10 + export type ThemesDocument = { collection: Theme[] }; 3 11 export type TracksDocument = { collection: Track[] };
+2 -2
src/components/transformer/output/bytes/automerge/utils.js
··· 2 2 import { base64 } from "iso-base/rfc4648"; 3 3 4 4 /** 5 - * Generate a new tracks document to put in the `INITIAL_TRACKS_DOCUMENT` constant. 5 + * Generate a new collection document. 6 6 */ 7 - export function initTracksDoc() { 7 + export function initCollectionDoc() { 8 8 const doc = Automerge.change(Automerge.init(), (doc) => { 9 9 doc.collection = []; 10 10 });
+43 -22
src/components/transformer/output/bytes/json/element.js
··· 3 3 4 4 /** 5 5 * @import { OutputManagerDeputy } from "@components/output/types.d.ts" 6 - * @import { Track } from "@definitions/types.d.ts" 6 + * @import { Constituent, Track } from "@definitions/types.d.ts" 7 7 */ 8 8 9 9 /** ··· 17 17 18 18 /** @type {OutputManagerDeputy} */ 19 19 const manager = { 20 + constituents: { 21 + ...base.constituents, 22 + collection: computed(() => { 23 + const data = base.constituents.collection(); 24 + /** @type {Constituent[]} */ 25 + const c = parseArray(data); 26 + return c; 27 + }), 28 + save: async (newConstituents) => { 29 + const json = JSON.stringify(newConstituents); 30 + const encoder = new TextEncoder(); 31 + const bytes = encoder.encode(json); 32 + await base.constituents.save(bytes); 33 + }, 34 + }, 20 35 tracks: { 21 36 ...base.tracks, 22 37 collection: computed(() => { 23 - let data = base.tracks.collection(); 24 - 25 - let json; 26 - 27 - if (data instanceof Uint8Array) { 28 - const decoder = new TextDecoder(); 29 - json = decoder.decode(data); 30 - } 31 - 32 - if (typeof data !== "string") json = "[]"; 33 - else json = data; 34 - 35 - // Try parsing JSON 36 - try { 37 - return JSON.parse(json); 38 - } catch (err) { 39 - console.error( 40 - "components/transformer/output/string/json: Failed to parse JSON", 41 - ); 42 - return []; 43 - } 38 + const data = base.tracks.collection(); 39 + /** @type {Track[]} */ 40 + const c = parseArray(data); 41 + return c; 44 42 }), 45 43 save: async (newTracks) => { 46 44 const json = JSON.stringify(newTracks); ··· 53 51 54 52 // Assign manager properties to class 55 53 this.tracks = manager.tracks; 54 + } 55 + } 56 + 57 + /** 58 + * @param {Uint8Array | string | undefined} data 59 + */ 60 + function parseArray(data) { 61 + let json; 62 + 63 + if (data instanceof Uint8Array) { 64 + const decoder = new TextDecoder(); 65 + json = decoder.decode(data); 66 + } else if (data === undefined) { 67 + return []; 68 + } else { 69 + json = data; 70 + } 71 + 72 + try { 73 + return JSON.parse(json); 74 + } catch (err) { 75 + console.error(err); 76 + return []; 56 77 } 57 78 } 58 79
+4 -4
src/definitions/index.ts
··· 1 - export * as ShDiffuseOutputConstituent from "./types/sh/diffuse/output/constituent.js"; 2 - export * as ShDiffuseOutputPlaylist from "./types/sh/diffuse/output/playlist.js"; 3 - export * as ShDiffuseOutputTheme from "./types/sh/diffuse/output/theme.js"; 4 - export * as ShDiffuseOutputTrack from "./types/sh/diffuse/output/track.js"; 1 + export * as ShDiffuseOutputConstituent from "./types/sh/diffuse/output/constituent.ts"; 2 + export * as ShDiffuseOutputPlaylist from "./types/sh/diffuse/output/playlist.ts"; 3 + export * as ShDiffuseOutputTheme from "./types/sh/diffuse/output/theme.ts"; 4 + export * as ShDiffuseOutputTrack from "./types/sh/diffuse/output/track.ts";
+2
src/definitions/types.d.ts
··· 10 10 Transformation, 11 11 } from "./types/sh/diffuse/output/playlist.ts"; 12 12 13 + export type { Main as Theme } from "./types/sh/diffuse/output/theme.ts"; 14 + 13 15 export type { 14 16 Main as Track, 15 17 Stats as TrackStats,
+9
tasks/replace-gen-import-extensions.ts
··· 1 + import { readTextFileSync } from "@std/fs/unstable-read-text-file"; 2 + import { writeTextFileSync } from "@std/fs/unstable-write-text-file"; 3 + 4 + const PATH = "./src/definitions/index.ts"; 5 + 6 + const text = readTextFileSync(PATH); 7 + const withTsImports = text.replaceAll(/\.js";/g, '.ts";'); 8 + 9 + writeTextFileSync(PATH, withTsImports);