postemi 0.0.0-stage → 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,102 @@
1
+ # Supported file types for `postemi upload`
2
+
3
+ **Eight types. Nothing else.** If you are here because an upload returned
4
+ `400 Unsupported file type.`, the answer is almost certainly on this page.
5
+
6
+ | MIME type | Extensions | Max size |
7
+ |---|---|---|
8
+ | `image/jpeg` | `.jpg`, `.jpeg` | 10 MB |
9
+ | `image/png` | `.png` | 10 MB |
10
+ | `image/gif` | `.gif` | 10 MB |
11
+ | `image/webp` | `.webp` | 10 MB |
12
+ | `image/avif` | `.avif` | 10 MB |
13
+ | `image/bmp` | `.bmp` | 10 MB |
14
+ | `image/tiff` | `.tif`, `.tiff` | 10 MB |
15
+ | `video/mp4` | `.mp4` | 1 GB |
16
+
17
+ That is the complete list. Source of truth:
18
+ `libraries/nestjs-libraries/src/upload/custom.upload.validation.ts` in the
19
+ Postemi server, where it is a literal `Set` of exactly these eight strings.
20
+
21
+ ## Not supported
22
+
23
+ **These will fail. They are listed because a previous version of this document
24
+ promised them.**
25
+
26
+ | | Why |
27
+ |---|---|
28
+ | `.pdf`, `.doc`, `.docx`, `.ppt` | Not a social-media asset. Postemi's media library is images and video. |
29
+ | `.mp3`, `.wav`, `.ogg`, `.aac`, `.flac`, `.m4a` | No audio type is accepted. Postemi has no audio-only post. |
30
+ | `.mov`, `.mkv`, `.webm`, `.avi`, `.wmv`, `.flv`, `.3gp` | MP4 is the only accepted video container. Convert first — see below. |
31
+ | `.svg` | Deliberately excluded. SVG is a document format that executes script; serving user-supplied SVG from Postemi's own origin would be a stored-XSS vector. |
32
+ | anything else | There is no `application/octet-stream` fallback. |
33
+
34
+ **Do not expect this list to widen.** The allowlist is narrow on purpose, and
35
+ the type is decided by sniffing the file's magic bytes, not by its extension or
36
+ by the `Content-Type` the client sends. Renaming `clip.mov` to `clip.mp4` does
37
+ not work — the server reads the bytes, sees QuickTime, and rejects it. It is
38
+ also checked twice: once by the upload interceptor as the bytes stream in, and
39
+ again by a validation pipe over the sniffed type before anything is stored.
40
+
41
+ ## Converting
42
+
43
+ ```bash
44
+ # Any video container -> MP4 (H.264 + AAC, which every platform accepts)
45
+ ffmpeg -i clip.mov -c:v libx264 -c:a aac clip.mp4
46
+ postemi upload clip.mp4
47
+
48
+ # SVG -> PNG
49
+ rsvg-convert -w 1200 logo.svg -o logo.png # or: inkscape, imagemagick
50
+ postemi upload logo.png
51
+ ```
52
+
53
+ ## Usage
54
+
55
+ ```bash
56
+ postemi upload ./images/photo.jpg
57
+ ```
58
+
59
+ ```json
60
+ {
61
+ "id": "…",
62
+ "path": "https://…/uploads/photo.jpg"
63
+ }
64
+ ```
65
+
66
+ Then use the returned `path` as the media reference on a post:
67
+
68
+ ```bash
69
+ PATH=$(postemi upload ./videos/promo.mp4 | jq -r '.path')
70
+ postemi posts:create -c "New video!" -m "$PATH" -i "<integration-id>"
71
+ ```
72
+
73
+ The media reference **must** be a path returned by `postemi upload`. Passing a
74
+ local filename (`-m "screenshot.png"`) is not an upload shortcut; it produces a
75
+ post with a broken media reference.
76
+
77
+ ## Errors
78
+
79
+ | Response | Meaning |
80
+ |---|---|
81
+ | `400 Unsupported file type.` | The sniffed type is not one of the eight above. Convert the file. |
82
+ | `400 File size exceeds the maximum allowed size of N bytes.` | Over 10 MB for an image or 1 GB for a video. |
83
+ | `400 File is too large.` | Rejected at the transport layer, before the body was read. Same cause. |
84
+ | `401 Invalid API key` | The key is wrong, revoked, or expired. |
85
+ | `403 … missing the required permission: media:write` | The key is valid but was not granted `media:write` — or its owner's role no longer permits it. Scoped keys are re-checked against their owner's current role on every request, so a role change can narrow a working key with nothing else having happened. |
86
+ | `429` | Rate limit. Every public API route is limited per key. |
87
+
88
+ ## Platform limits are a separate thing
89
+
90
+ The eight types above are what **Postemi** accepts. Each social platform then
91
+ applies its own rules to what it will publish — X caps video at 512 MB,
92
+ Instagram at 100 MB, TikTok at ~287 MB. An upload that Postemi accepts can still
93
+ be refused by a platform at publish time. Use
94
+ `postemi integrations:settings <id>` to read a channel's live rules rather than
95
+ hard-coding any of these numbers.
96
+
97
+ ---
98
+
99
+ *Corrected 2026-08-06. The previous version of this file listed PDF, DOC, DOCX,
100
+ MP3, WAV, OGG, AAC, FLAC, M4A, SVG, MOV, MKV, WEBM and AVI as supported, and
101
+ claimed "30+ file types". None of them were, and an agent reading it would send
102
+ one and get a 400 it had no way to anticipate.*