{"id":22350916,"url":"https://github.com/johnae/spotnix","last_synced_at":"2026-03-10T15:03:46.519Z","repository":{"id":38215959,"uuid":"216281407","full_name":"johnae/spotnix","owner":"johnae","description":"Spotify for UNIX","archived":false,"fork":false,"pushed_at":"2023-03-06T06:04:59.000Z","size":142,"stargazers_count":4,"open_issues_count":5,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-10-20T18:14:00.114Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/johnae.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2019-10-19T23:09:02.000Z","updated_at":"2023-02-13T19:32:47.000Z","dependencies_parsed_at":"2024-12-04T12:11:45.675Z","dependency_job_id":"97f3202f-ab7f-486c-b628-2bb4ea5848c7","html_url":"https://github.com/johnae/spotnix","commit_stats":{"total_commits":63,"total_committers":2,"mean_commits":31.5,"dds":"0.23809523809523814","last_synced_commit":"095706780a0a60351712d46cf9cc12c454b07806"},"previous_names":[],"tags_count":2,"template":false,"template_full_name":null,"purl":"pkg:github/johnae/spotnix","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/johnae%2Fspotnix","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/johnae%2Fspotnix/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/johnae%2Fspotnix/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/johnae%2Fspotnix/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/johnae","download_url":"https://codeload.github.com/johnae/spotnix/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/johnae%2Fspotnix/sbom","scorecard":{"id":528172,"data":{"date":"2025-08-11","repo":{"name":"github.com/johnae/spotnix","commit":"095706780a0a60351712d46cf9cc12c454b07806"},"scorecard":{"version":"v5.2.1-40-gf6ed084d","commit":"f6ed084d17c9236477efd66e5b258b9d4cc7b389"},"score":2.8,"checks":[{"name":"Code-Review","score":0,"reason":"Found 0/19 approved changesets -- score normalized to 0","details":null,"documentation":{"short":"Determines if the project requires human code review before pull requests (aka merge requests) are merged.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#code-review"}},{"name":"Dangerous-Workflow","score":10,"reason":"no dangerous workflow patterns detected","details":null,"documentation":{"short":"Determines if the project's GitHub Action workflows avoid dangerous patterns.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#dangerous-workflow"}},{"name":"Maintained","score":0,"reason":"0 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 0","details":null,"documentation":{"short":"Determines if the project is \"actively maintained\".","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#maintained"}},{"name":"Packaging","score":-1,"reason":"packaging workflow not detected","details":["Warn: no GitHub/GitLab publishing workflow detected."],"documentation":{"short":"Determines if the project is published as a package that others can easily download, install, easily update, and uninstall.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#packaging"}},{"name":"Binary-Artifacts","score":10,"reason":"no binaries found in the repo","details":null,"documentation":{"short":"Determines if the project has generated executable (binary) artifacts in the source repository.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#binary-artifacts"}},{"name":"Token-Permissions","score":0,"reason":"detected GitHub workflow tokens with excessive permissions","details":["Warn: no topLevel permission defined: .github/workflows/ci.yaml:1","Info: no jobLevel write permissions found"],"documentation":{"short":"Determines if the project's workflows follow the principle of least privilege.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#token-permissions"}},{"name":"CII-Best-Practices","score":0,"reason":"no effort to earn an OpenSSF best practices badge detected","details":null,"documentation":{"short":"Determines if the project has an OpenSSF (formerly CII) Best Practices Badge.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#cii-best-practices"}},{"name":"Pinned-Dependencies","score":0,"reason":"dependency not pinned by hash detected -- score normalized to 0","details":["Warn: GitHub-owned GitHubAction not pinned by hash: .github/workflows/ci.yaml:13: update your workflow using https://app.stepsecurity.io/secureworkflow/johnae/spotnix/ci.yaml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/ci.yaml:14: update your workflow using https://app.stepsecurity.io/secureworkflow/johnae/spotnix/ci.yaml/main?enable=pin","Warn: third-party GitHubAction not pinned by hash: .github/workflows/ci.yaml:20: update your workflow using https://app.stepsecurity.io/secureworkflow/johnae/spotnix/ci.yaml/main?enable=pin","Info:   0 out of   1 GitHub-owned GitHubAction dependencies pinned","Info:   0 out of   2 third-party GitHubAction dependencies pinned"],"documentation":{"short":"Determines if the project has declared and pinned the dependencies of its build process.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#pinned-dependencies"}},{"name":"Security-Policy","score":0,"reason":"security policy file not detected","details":["Warn: no security policy file detected","Warn: no security file to analyze","Warn: no security file to analyze","Warn: no security file to analyze"],"documentation":{"short":"Determines if the project has published a security policy.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#security-policy"}},{"name":"Fuzzing","score":0,"reason":"project is not fuzzed","details":["Warn: no fuzzer integrations found"],"documentation":{"short":"Determines if the project uses fuzzing.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#fuzzing"}},{"name":"License","score":10,"reason":"license file detected","details":["Info: project has a license file: LICENSE:0","Info: FSF or OSI recognized license: MIT License: LICENSE:0"],"documentation":{"short":"Determines if the project has defined a license.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#license"}},{"name":"Signed-Releases","score":-1,"reason":"no releases found","details":null,"documentation":{"short":"Determines if the project cryptographically signs release artifacts.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#signed-releases"}},{"name":"Branch-Protection","score":-1,"reason":"internal error: error during branchesHandler.setup: internal error: githubv4.Query: Resource not accessible by integration","details":null,"documentation":{"short":"Determines if the default and release branches are protected with GitHub's branch protection settings.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#branch-protection"}},{"name":"SAST","score":0,"reason":"SAST tool is not run on all commits -- score normalized to 0","details":["Warn: 0 commits out of 12 are checked with a SAST tool"],"documentation":{"short":"Determines if the project uses static code analysis.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#sast"}},{"name":"Vulnerabilities","score":0,"reason":"33 existing vulnerabilities detected","details":["Warn: Project is vulnerable to: RUSTSEC-2021-0139","Warn: Project is vulnerable to: RUSTSEC-2021-0145 / GHSA-g98v-hv3f-hcfr","Warn: Project is vulnerable to: RUSTSEC-2024-0375","Warn: Project is vulnerable to: RUSTSEC-2020-0159","Warn: Project is vulnerable to: RUSTSEC-2022-0021 / GHSA-6888-wf7j-34jq","Warn: Project is vulnerable to: RUSTSEC-2022-0041 / GHSA-qc84-gqf4-9926","Warn: Project is vulnerable to: RUSTSEC-2021-0141","Warn: Project is vulnerable to: RUSTSEC-2019-0036 / RUSTSEC-2020-0036 / GHSA-jq66-xh47-j9f3 / GHSA-r98r-j25q-rmpr","Warn: Project is vulnerable to: RUSTSEC-2023-0034 / GHSA-f8vr-r385-rh5r","Warn: Project is vulnerable to: RUSTSEC-2024-0003 / GHSA-8r5v-vm4m-4g25","Warn: Project is vulnerable to: RUSTSEC-2024-0332 / GHSA-q6cp-qfwq-4gcv","Warn: Project is vulnerable to: RUSTSEC-2021-0079 / GHSA-5h46-h7hh-c6x9","Warn: Project is vulnerable to: RUSTSEC-2021-0078 / GHSA-f3pg-qwvg-p99c","Warn: Project is vulnerable to: RUSTSEC-2022-0022 / GHSA-f67m-9j94-qv9j","Warn: Project is vulnerable to: RUSTSEC-2024-0421 / GHSA-h97m-ww89-6jmq","Warn: Project is vulnerable to: RUSTSEC-2020-0070 / GHSA-5wg8-7c9q-794v / GHSA-gmv4-vmx3-x9f3 / GHSA-hj9h-wrgg-hgmx / GHSA-ppj3-7jw3-8vc4 / GHSA-vh4p-6j7g-f4j9","Warn: Project is vulnerable to: RUSTSEC-2023-0045 / GHSA-wfg4-322g-9vqv","Warn: Project is vulnerable to: RUSTSEC-2020-0016","Warn: Project is vulnerable to: RUSTSEC-2023-0022 / GHSA-3gxf-9r58-2ghg","Warn: Project is vulnerable to: RUSTSEC-2023-0024 / GHSA-6hcf-g6gr-hhcr","Warn: Project is vulnerable to: RUSTSEC-2023-0023 / GHSA-9qwg-crg9-m2vc","Warn: Project is vulnerable to: RUSTSEC-2023-0044 / GHSA-xcf7-rvmh-g6q4","Warn: Project is vulnerable to: RUSTSEC-2023-0072","Warn: Project is vulnerable to: GHSA-q445-7m23-qrmw","Warn: Project is vulnerable to: RUSTSEC-2024-0357","Warn: Project is vulnerable to: RUSTSEC-2025-0004 / GHSA-rpmj-rpgj-qmpm","Warn: Project is vulnerable to: RUSTSEC-2024-0370","Warn: Project is vulnerable to: RUSTSEC-2023-0018 / GHSA-mc8h-8q98-g5hr","Warn: Project is vulnerable to: RUSTSEC-2022-0004 / GHSA-2226-4v3c-cff8","Warn: Project is vulnerable to: RUSTSEC-2025-0025","Warn: Project is vulnerable to: RUSTSEC-2020-0071 / GHSA-wcg3-cvx6-7396","Warn: Project is vulnerable to: RUSTSEC-2021-0124 / GHSA-fg7r-2g4j-5cgr","Warn: Project is vulnerable to: GHSA-m589-mv4q-p7rj"],"documentation":{"short":"Determines if the project has open, known unfixed vulnerabilities.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#vulnerabilities"}}]},"last_synced_at":"2025-08-20T04:59:49.252Z","repository_id":38215959,"created_at":"2025-08-20T04:59:49.252Z","updated_at":"2025-08-20T04:59:49.252Z"},"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":30338599,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-03-10T15:02:55.010Z","status":"ssl_error","status_checked_at":"2026-03-10T15:02:36.911Z","response_time":106,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.5:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-12-04T12:11:41.734Z","updated_at":"2026-03-10T15:03:46.215Z","avatar_url":"https://github.com/johnae.png","language":"Rust","funding_links":[],"categories":[],"sub_categories":[],"readme":"### Spotify for Unix\n\nWhat does that even mean? It means that this is how I like to search for music and listen to music on a Unix system. This is a spotify controller and does not (yet anyway) include a way to stream the actual music. But there's already a very good such player (which I use with Spotnix): https://github.com/spotifyd/spotifyd.\n\n_It's really really early days so there's likely to be some rough edges, missing features and scrappyness... however, I use it daily._\n\nFirst, here's a taste of what a session might look like (spotnix on the left, on the right we search and select what to play):\n\n![spotnix](https://user-images.githubusercontent.com/28332/67158210-93343800-f335-11e9-93fc-45cafd964a8b.gif)\n\n\nSo what's so special about this then? Well, you get three named pipes and that's it. What's not to like :-)? The standard names of those pipes:\n\n`./input` (eg. play something, pause, list devices, search etc.)\n\n`./output` (results of a search, results of list devices etc.)\n\n`./status` (playback status such as progress, track name etc). This is json.\n\n```sh\necho search_playlist electronic \u003e ./input\n```\n\nTo get the results and select something to play (you can ofc use https://github.com/junegunn/fzf as well, I like https://github.com/lotabout/skim - probably just because I'm biased as I'm very fond of the Rust programming language):\n\n```sh\ncat ./output | sk | awk '{print $NF}' | xargs -r -I{} echo play {} \u003e ./input\n```\n\nOr just all in one:\n\n```sh\necho search_playlist electronic \u003e ./input; cat ./output | sk | awk '{print $NF}' | xargs -r -I{} echo play {} \u003e ./input\n```\n\nTo get playback status (eg. progress, name of song / album etc):\n\n```sh\ncat ./status\n```\n\n(The above updates every 1 second. Just `cat` again or read that pipe in a loop or whatever you like for updates.)\n\nObviously you'd probably put all the above things in scripts - but it's up to you how you use it, these are just building blocks - the Unix way. For some basic example scripts, see: [examples](examples/)\n\n\nThe available commands at the moment are (those you send into the ./input pipe):\n\n```sh\nplay \u003coptional spotify uri\u003e (without uri - resume playback)\npause\nshuffle true/false\nsearch_track \u003csearch string\u003e\nsearch_album \u003csearch string\u003e\nsearch_artist \u003csearch string\u003e\nsearch_playlist \u003csearch string\u003e\ndevices (list devices available)\ndevice \u003cdevice id\u003e (selects the device use for playback)\nnext\nprev\n```\n\nThe search results are returned in pages with the spotify enforced maximum of 50 items. Since this tool is meant to be used on the command line and actual selection of what to play will likely happen from a newline delimited list of results (using tools like above mentioned `fzf` or `skim`), there's a command line option for setting the number of pages to fetch (default is 4). These pages are fetched concurrently using the awesome `rayon` crate.\n\n### Installing\n\nAt the moment there's no packages so you'll have to build it. First, install [Rust](https://www.rust-lang.org/tools/install) then\n\n```bash\ncargo install spotnix\n```\n\nPersonally I use [Nix](https://nixos.org/nix) to manage dependencies, including the Rust toolchain, but I know [Rustup](https://rustup.rs/) is really good. You do need *openssl* installed for compilation.\n\nTo update spotnix you can run\n\n```bash\ncargo install spotnix --force\n```\n\n## To use this program, you must connect to Spotify's Web API\n\n`spotnix` talks to Spotify's Web API to do it's thing (eg. search, play, pause etc.).\n\nWhen you start `spotnix` the first time, you will be asked to login to spotify BUT - to really make it work, you must actually do a little bit more:\n\n1. Open the [Spotify applications dashboard](https://developer.spotify.com/dashboard/applications)\n2. Click `Create a Client ID` and create an app\n3. Click `Edit Settings`\n4. Add `http://localhost:8182/spotnix` to the Redirect URIs\n5. Now you can authenticate with Spotify!\n6. So back in the terminal, run `CLIENT_ID=abcde12345 CLIENT_SECRET=sasjfijs2983 REDIRECT_URI=http://localhost:8182/spotnix`\n7. Now you'll be redirected - in your browser - to Spotify which will ask you to grant permissions.\n8. After accepting, you'll be redirected to localhost which will very likely refuse the connection (unless you really have a web server running on port 8182). Either way, copy the URL and paste into the the terminal where it asks for it (you may need to close the browser window before it asks you for it in the terminal).\n\n\n### Usage\n\nThis is currently the help output of spotnix:\n\n```sh\nspotnix 0.1.2\nspotify as a series of \"tubes\"... or rather named pipes.\n\nUSAGE:\n    spotnix [OPTIONS]\n\nFLAGS:\n    -h, --help       Prints help information\n    -V, --version    Prints version information\n\nOPTIONS:\n    -d, --device \u003cdevice\u003e    Default device to use by name\n    -s, --status \u003cstatus\u003e      All events go here (a named pipe) [default: ./status]\n    -i, --input \u003cinput\u003e      All input goes here (a named pipe) [default: ./input]\n    -o, --output \u003coutput\u003e    All output goes here (a named pipe) [default: ./output]\n    -r, --pages \u003cpages\u003e      Max number of search result pages to fetch (a page contains 50 items) [default: 4]\n```\n\nSo that is Spotify for Unix - you get to use all those command line tools you know and love to find and listen to music!\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjohnae%2Fspotnix","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjohnae%2Fspotnix","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjohnae%2Fspotnix/lists"}