---
title: "Modifier quelques champs d'une chanson"
method: PATCH
path: "/me/songs/{songId}"
tags: ["carnet"]
---

# Modifier quelques champs d'une chanson

`PATCH /me/songs/{songId}`

## Request

- Base URL: `https://jam-jam.org/api/v1`
- URL: `https://jam-jam.org/api/v1/me/songs/{songId}`
- Auth: one of:
  - HTTP bearer
  - none

Modification PARTIELLE : seuls les champs PRESENTS bougent. Un champ
absent n'est pas touche ; un champ a `null` efface la valeur
(`artist: null`, `key: null`, `capo: null`, `bpm: null`).

`key` est la tonalite AFFICHEE, meme convention que la lecture et que
l'export ChordPro : `G` (majeur), `Am` (mineur). Elle est decomposee
vers `detectedKey` dans le payload pivot, puis recomposee a l'identique
par la lecture.

`playlistIds` est l'etat CIBLE COMPLET des appartenances : la chanson
est ajoutee aux playlists citees et RETIREE de toutes les autres.
`[]` la sort de toutes ses playlists. Declaratif, donc idempotent.
Une playlist inconnue ou appartenant a un autre compte rend le meme
`404` indifferencie qu'une chanson inconnue.

PUBLICATION SUR LE PROFIL (doctrine sociale 3.0.0) :
`publish: true` publie la chanson sur le profil de l'appelant,
`publish: false` la retire. Trois regles, toutes appliquees par la
base et non par cette API :

- PUBLIER EXIGE UNE DECLARATION DE DROITS, une fois par objet :
  joindre `publishDeclaration` (`created`,
  `imported_no_known_restriction` ou `arrangement`). Sans elle,
  `409 declaration-required`. Republier un objet deja declare ne la
  redemande pas ;
- publier exige un profil public (un pseudo `@handle` choisi dans
  l'application), sinon `409 profile-required` ;
- pendant une suspension de partage, rien ne se publie
  (`409 sharing-suspended`).

DEPUBLIER (`publish: false`) n'a AUCUNE condition : retirer son
contenu ne se negocie pas. La reponse porte alors `published`.

Publier ne monte PAS de bande-son : l'audio d'une chanson publiee ne
s'ecoute qu'entre comptes qui se suivent mutuellement, et il est
depose par l'application depuis l'appareil qui detient le fichier.

## Path parameters

- `songId` string, required

## Headers

- `If-Match` string

## Request body

- SongPatch: Corps de `PATCH /me/songs/{songId}`. Seuls les champs PRESENTS bougent ; un champ a `null` efface la valeur. Un champ inconnu est refuse (`400`), et les types ne sont PAS convertis (`"3"` n'est pas un capo).
  - `title` string
  - `artist` string, nullable
  - `key` string, nullable: Tonalite AFFICHEE (`G`, `Am`). `null` efface la tonalite.
  - `capo` integer, nullable
  - `bpm` integer, nullable
  - `playlistIds` string[]: Etat CIBLE COMPLET des appartenances (declaratif, idempotent).
  - `publish` boolean: `true` publie sur le profil (exige `publishDeclaration` a la premiere publication de cet objet, et un profil public) ; `false` depublie, sans condition.
  - `publishDeclaration` 'created' | 'imported_no_known_restriction' | 'arrangement': Declaration de droits, exigee UNE FOIS PAR OBJET a sa premiere publication. `created` : vous en etes l'auteur. `imported_no_known_restriction` : reprise dont vous ne connaissez aucune restriction. `arrangement` : votre agencement. Sans `publish: true`, ce champ est refuse (`400`).

## Response `200`

Chanson modifiee

- WriteAck: Accuse d'ecriture, identique sur les six routes qui en rendent un. Volontairement MINIMAL : l'identifiant pour adresser l'objet, et l'horodatage a renvoyer en `If-Match` a la prochaine ecriture. Relire l'objet complet se fait par `GET /me/songs/{songId}`, qui consomme du quota de LECTURE : ne pas l'imposer a chaque ecriture est delibere.
  - `id` string, required: Identifiant stable de l'objet ecrit.
  - `updatedAt` string, date-time, required: Horodatage serveur apres l'ecriture, en ISO 8601 UTC au millieme. C'est EXACTEMENT la valeur a renvoyer dans `If-Match`.
  - `published` boolean: Present UNIQUEMENT quand la requete portait `publish` : etat REEL de la publication apres l'ecriture. Un refus de publication n'est jamais un `published: false` silencieux, c'est un `409`.

## Other responses

- `400`: Toute erreur de cette API, quel que soit le code HTTP, est un `application/problem+json` (RFC 9457) avec ce meme schema : `code` est la valeur stable a tester par un client (le `status` HTTP peut varier legerement selon le contexte, `code` non). `quota` est renseigne pour les erreurs liees au quota (`quota-exhausted`, `anon-quota-exhausted`, `client-quota`).
- `401`: Toute erreur de cette API, quel que soit le code HTTP, est un `application/problem+json` (RFC 9457) avec ce meme schema : `code` est la valeur stable a tester par un client (le `status` HTTP peut varier legerement selon le contexte, `code` non). `quota` est renseigne pour les erreurs liees au quota (`quota-exhausted`, `anon-quota-exhausted`, `client-quota`).
- `403`: Toute erreur de cette API, quel que soit le code HTTP, est un `application/problem+json` (RFC 9457) avec ce meme schema : `code` est la valeur stable a tester par un client (le `status` HTTP peut varier legerement selon le contexte, `code` non). `quota` est renseigne pour les erreurs liees au quota (`quota-exhausted`, `anon-quota-exhausted`, `client-quota`).
- `404`: Toute erreur de cette API, quel que soit le code HTTP, est un `application/problem+json` (RFC 9457) avec ce meme schema : `code` est la valeur stable a tester par un client (le `status` HTTP peut varier legerement selon le contexte, `code` non). `quota` est renseigne pour les erreurs liees au quota (`quota-exhausted`, `anon-quota-exhausted`, `client-quota`).
- `409`: `conflict` (`If-Match` desynchronise ; le corps porte l'`updatedAt` serveur), `profile-required`, `declaration-required` ou `sharing-suspended`.
- `415`: Toute erreur de cette API, quel que soit le code HTTP, est un `application/problem+json` (RFC 9457) avec ce meme schema : `code` est la valeur stable a tester par un client (le `status` HTTP peut varier legerement selon le contexte, `code` non). `quota` est renseigne pour les erreurs liees au quota (`quota-exhausted`, `anon-quota-exhausted`, `client-quota`).
- `422`: Toute erreur de cette API, quel que soit le code HTTP, est un `application/problem+json` (RFC 9457) avec ce meme schema : `code` est la valeur stable a tester par un client (le `status` HTTP peut varier legerement selon le contexte, `code` non). `quota` est renseigne pour les erreurs liees au quota (`quota-exhausted`, `anon-quota-exhausted`, `client-quota`).
- `429`: Toute erreur de cette API, quel que soit le code HTTP, est un `application/problem+json` (RFC 9457) avec ce meme schema : `code` est la valeur stable a tester par un client (le `status` HTTP peut varier legerement selon le contexte, `code` non). `quota` est renseigne pour les erreurs liees au quota (`quota-exhausted`, `anon-quota-exhausted`, `client-quota`).

---

[API](https://skmtc.dev/jam-jam/apis/jam-jam-convert-api.md) · [All operations](https://skmtc.dev/jam-jam/apis/jam-jam-convert-api/llms.txt) · [OpenAPI document](https://skmtc.dev/jam-jam/apis/jam-jam-convert-api/revisions/64cd41a46e4e?raw)
