Skip to content

Commit

Permalink
Merge pull request #3 from studiowebux/1-insert-album
Browse files Browse the repository at this point in the history
1 insert album
  • Loading branch information
studiowebux authored Nov 25, 2023
2 parents 9270504 + bb238e9 commit 8ec5c11
Show file tree
Hide file tree
Showing 10 changed files with 153 additions and 34 deletions.
2 changes: 1 addition & 1 deletion manifest.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{
"id": "spotify-link",
"name": "Spotify Link",
"version": "1.0.3",
"version": "1.1.0",
"minAppVersion": "0.15.0",
"description": "Include the song you're currently listening to in your note.",
"author": "Studio Webux",
Expand Down
4 changes: 2 additions & 2 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "spotify-link",
"version": "1.0.3",
"version": "1.1.0",
"description": "Include the song you're currently listening to in your Obsidian (https://obsidian.md) note",
"main": "main.js",
"scripts": {
Expand Down
3 changes: 2 additions & 1 deletion src/api.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,8 @@ import {
RefreshTokenResponse,
SpotifyAuthCallback,
} from "./types";
import { prepareData, processCurrentlyPlayingTrackInput } from "./utils";
import { prepareData } from "./utils";
import { processCurrentlyPlayingTrackInput } from "./output";

export const SPOTIFY_API_BASE_ADDRESS = "https://api.spotify.com/v1";
export const REDIRECT_URI = "obsidian://spotify-auth/";
Expand Down
19 changes: 16 additions & 3 deletions src/main.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,15 @@ import { Editor, Notice, Plugin, addIcon } from "obsidian";
import { SpotifyLinkSettings, SpotifyAuthCallback } from "./types";
import { getSpotifyUrl, handleCallback, requestRefreshToken } from "./api";
import SettingsTab, { DEFAULT_SETTINGS } from "./settingsTab";
import { handleEditor } from "./ui";
import { handleEditor, handleTemplateEditor } from "./ui";
import { onLogin, onAutoLogin } from "./events";

export default class SpotifyLinkPlugin extends Plugin {
settings: SpotifyLinkSettings;

// States
spotifyConnected: boolean = false;
spotifyUrl: string = "";
spotifyConnected = false;
spotifyUrl = "";
statusBar: HTMLElement;

async saveSettings() {
Expand Down Expand Up @@ -91,6 +91,19 @@ export default class SpotifyLinkPlugin extends Plugin {
//
// USER INTERACTION
//

this.addCommand({
id: "append-currently-playing-track-using-template",
name: "Append Spotify currently playing track using template",
editorCallback: async (editor: Editor) => {
await handleTemplateEditor(
editor,
this.settings.templates[0],
this.settings.spotifyClientId,
this.settings.spotifyClientSecret
);
},
});
this.addCommand({
id: "append-currently-playing-track",
name: "Append Spotify currently playing track with timestamp",
Expand Down
49 changes: 49 additions & 0 deletions src/output.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
import { CurrentlyPlayingTrack } from "./types";
import { millisToMinutesAndSeconds } from "./utils";

export function processCurrentlyPlayingTrackInput(
data: CurrentlyPlayingTrack
): string {
let message = "";
if (data && data.is_playing) {
message = `['**${data.item.name}**' by ***${data.item.artists
.map((a) => a.name)
.join(", ")}*** **${millisToMinutesAndSeconds(
data.progress_ms
)}** (${(
(data.progress_ms / parseInt(data.item.duration_ms)) *
100
).toFixed(0)}%)](${data.item.external_urls.spotify})`;
} else {
message = "No song is playing.";
}
return message;
}

export function processCurrentlyPlayingTrack(
data: CurrentlyPlayingTrack,
template = `'{{ song_name }}' by {{ artists }} from {{ album }} released in {{ album_release }}\n{{ timestamp }}`
): string {
let message = "";
if (data && data.is_playing) {
message = template
.replace(/{{ song_name }}|{{song_name}}/g, data.item.name)
.replace(
/{{ artists }}|{{artist}}/g,
data.item.artists.map((a) => a.name).join(", ")
)
.replace(
/{{ album_release }}|{{album_release}}/g,
data.item.album.release_date
)
.replace(/{{ album }}|{{album}}/g, data.item.album.name)
.replace(
/{{ timestamp }}|{{timestamp}}/g,
`${new Date().toDateString()} - ${new Date().toLocaleTimeString()}`
);
} else {
message = "No song is playing.";
}

return message;
}
60 changes: 57 additions & 3 deletions src/settingsTab.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ export const DEFAULT_SETTINGS: SpotifyLinkSettings = {
spotifyClientSecret: "",
spotifyScopes: "user-read-currently-playing",
spotifyState: "it-can-be-anything",
templates: [],
};

export default class SettingsTab extends PluginSettingTab {
Expand All @@ -21,7 +22,7 @@ export default class SettingsTab extends PluginSettingTab {
const { containerEl } = this;

containerEl.empty();

// INSTRUCTIONS
const div = containerEl.createDiv();
div.createEl("p", {
Expand All @@ -31,10 +32,16 @@ export default class SettingsTab extends PluginSettingTab {
href: "https://developer.spotify.com/dashboard/",
text: "Spotify Developer",
});
div.createEl("ul")
div.createEl("ol")
.createEl("li", { text: "Create an App" })
.createEl("li", { text: "Click Settings" })
.createEl("li", { text: "Copy the Client Id and Secret" });
.createEl("li", { text: "Copy the Client Id and Secret" })
.createEl("li", {
text: "Set the Redirect URI to : obsidian://spotify-auth/",
})
.createEl("li", {
text: "Select the Spotify icon located in Obsidian's left sidebar to connect.",
});
div.createEl("p", {
text: "NOTICE: The id and secret will be stored unencrypted on your local device. If you sync your data to a public source, the id and secret will be shown as-is.",
});
Expand Down Expand Up @@ -78,6 +85,46 @@ export default class SettingsTab extends PluginSettingTab {
});
text.inputEl.setAttribute("type", "password");
});
new Setting(containerEl)
.setName("Spotify Redirect URI")
.setDesc("Redirect URI (Read Only)")
.addText((text) => {
text.setValue("obsidian://spotify-auth/").setDisabled(true);
});

containerEl.createEl("hr");

containerEl.createEl("h5", { text: "Templates" });
const divDoc = containerEl.createDiv();

divDoc.createEl("a", {
href: "https://studiowebux.github.io/obsidian-plugins-docs/docs/spotify-link/custom-template",
text: "Custom Template Documentation",
});
divDoc.createEl("p", { text: "Available variables:" });
divDoc
.createEl("ul")
.createEl("li", { text: "{{ album }}" })
.createEl("li", { text: "{{ album_release }}" })
.createEl("li", { text: "{{ artists }}" })
.createEl("li", { text: "{{ song_name }}" })
.createEl("li", { text: "{{ timestamp }}" });
new Setting(containerEl)
.setName("Template")
.setDesc(
"Define a custom template to print the currently playing song"
)
.addTextArea((text) =>
text
.setPlaceholder(
"Example: '{{ song_name }}' by {{ artists }} from {{ album }} released in {{ album_release }}\n{{ timestamp }}"
)
.setValue(this.plugin.settings.templates[0])
.onChange(async (value) => {
this.plugin.settings.templates[0] = value;
await this.plugin.saveSettings();
})
);

containerEl.createEl("hr");

Expand All @@ -96,5 +143,12 @@ export default class SettingsTab extends PluginSettingTab {
await this.plugin.saveSettings();
})
);

containerEl.createEl("hr");

containerEl.createEl("a", {
href: "https://studiowebux.github.io/obsidian-plugins-docs/docs/category/plugin-spotify-link",
text: "Official Plugin Documentation",
});
}
}
3 changes: 2 additions & 1 deletion src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ export type SpotifyLinkSettings = {
spotifyClientSecret: string;
spotifyScopes: string;
spotifyState: string;
templates: string[];
};

//
Expand Down Expand Up @@ -113,7 +114,7 @@ export type CurrentlyPlayingTrack = {
href: string;
id: string;
is_playable: boolean;
linked_from: {};
linked_from: object;
restrictions: {
reason: string;
};
Expand Down
23 changes: 21 additions & 2 deletions src/ui.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
import { Editor, Notice } from "obsidian";
import { getCurrentlyPlayingTrackAsString } from "./api";
import {
getCurrentlyPlayingTrack,
getCurrentlyPlayingTrackAsString,
} from "./api";
import { processCurrentlyPlayingTrack } from "./output";

export async function handleEditor(
editor: Editor,
Expand All @@ -16,7 +20,22 @@ export async function handleEditor(
`\n> ${new Date().toDateString()} - ${new Date().toLocaleTimeString()}` +
`\n\n`
);
editor.setCursor(editor.getCursor().line - 3);
} catch (e) {
new Notice(e.message);
}
}

export async function handleTemplateEditor(
editor: Editor,
template: string,
clientId: string,
clientSecret: string
) {
try {
const track = await getCurrentlyPlayingTrack(clientId, clientSecret);
editor.replaceSelection(
`${processCurrentlyPlayingTrack(track, template)}\n\n`
);
} catch (e) {
new Notice(e.message);
}
Expand Down
22 changes: 2 additions & 20 deletions src/utils.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
import { CurrentlyPlayingTrack } from "./types";

export function prepareData(data: { [key: string]: string }) {
return Object.keys(data)
Expand All @@ -9,7 +8,7 @@ export function prepareData(data: { [key: string]: string }) {
.join("&");
}

function millisToMinutesAndSeconds(millis: number) {
export function millisToMinutesAndSeconds(millis: number) {
const minutes: number = Math.floor(millis / 60000);
const seconds: number = parseInt(((millis % 60000) / 1000).toFixed(0));
if (minutes === 0) {
Expand All @@ -18,21 +17,4 @@ function millisToMinutesAndSeconds(millis: number) {
return minutes + "m:" + (seconds < 10 ? "0" : "") + seconds + "s";
}

export function processCurrentlyPlayingTrackInput(
data: CurrentlyPlayingTrack
): string {
let message = "";
if (data && data.is_playing) {
message = `['**${data.item.name}**' by ***${data.item.artists
.map((a) => a.name)
.join(", ")}*** **${millisToMinutesAndSeconds(
data.progress_ms
)}** (${(
(data.progress_ms / parseInt(data.item.duration_ms)) *
100
).toFixed(0)}%)](${data.item.external_urls.spotify})`;
} else {
message = "No song is playing.";
}
return message;
}

0 comments on commit 8ec5c11

Please sign in to comment.