MakeFav API دستاویزات
اپنے کوڈ، بلڈ اسکرپٹس اور CI پائپ لائنز سے مکمل فیویکون پیکیجز بنائیں۔ ایک درخواست کسی بھی تصویر کو favicon.ico، Apple touch آئیکنز، Android اور PWA آئیکنز، ویب مینی فیسٹ اور پیسٹ کرنے کے لیے تیار HTML میں بدل دیتی ہے۔
اس صفحے پر
فوری آغاز
MakeFav API ایک سادہ HTTPS + JSON REST API ہے۔ تمام اینڈ پوائنٹس ایک ہی بیس URL کے تحت ہیں:
https://makefav.com/api/v1 - مفت اکاؤنٹ بنائیں
سائن اپ کریں، اپنے ای میل ایڈریس کی تصدیق کریں اور MakeFav نیوز لیٹر کی سبسکرپشن فعال رکھیں – مفت پلان کی بس یہی شرط ہے۔ - API کلید بنائیں
اپنے اکاؤنٹ میں API کلیدوں کا صفحہ کھولیں اور ذاتی کلید بنائیں۔ یہ mf_ سے شروع ہوتی ہے اور صرف ایک بار دکھائی جاتی ہے، اس لیے اسے محفوظ جگہ پر رکھیں۔ API کلیدیں منظم کریں - اپنی پہلی درخواست بھیجیں
جنریٹ اینڈ پوائنٹ پر تصویر اپ لوڈ کریں اور واپس ملنے والی ZIP فائل محفوظ کریں:
curl --fail-with-body -sS https://makefav.com/api/v1/generate \
-H "Authorization: Bearer $MAKEFAV_API_KEY" \
-F "[email protected]" \
-F "app_name=My App" \
-F "theme_color=#2f9e68" \
-F "radius=20" \
-o favicons.zip Unzip favicons.zip, upload the files to your website and paste the HTML code from the end of readme-makefav.txt into the <head> of every page.
تصدیق
محفوظ اینڈ پوائنٹ کی ہر درخواست میں ذاتی API کلید شامل ہونی چاہیے۔ آپ اپنے اکاؤنٹ کے صفحے پر کسی بھی وقت کلیدیں بنا سکتے ہیں، نام دے سکتے ہیں اور منسوخ کر سکتے ہیں: API کلیدیں
Send the key as a bearer token in the Authorization header, or – if your HTTP client makes that awkward – in the X-API-Key header. Both are equivalent.
Authorization: Bearer mf_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
# or, alternatively
X-API-Key: mf_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx Missing or invalid keys return 401 Unauthorized. The GET /sizes and GET /openapi.json endpoints do not require a key.
ریٹ حدود
بطور ڈیفالٹ ہر API کلید فی گھنٹہ 100 درخواستیں کر سکتی ہے۔ ہر تصدیق شدہ جواب بتاتا ہے کہ آپ کس مقام پر ہیں:
| ہیڈر | وضاحت |
|---|---|
X-RateLimit-Limit | موجودہ ونڈو میں اجازت شدہ درخواستوں کی زیادہ سے زیادہ تعداد۔ |
X-RateLimit-Remaining | موجودہ ونڈو میں باقی درخواستیں۔ |
X-RateLimit-Reset | Unix ٹائم اسٹیمپ (سیکنڈ، UTC) جب ونڈو ری سیٹ ہوگی۔ |
HTTP/1.1 200 OK
X-RateLimit-Limit: 100
X-RateLimit-Remaining: 97
X-RateLimit-Reset: 1767225600 When the limit is exceeded the API responds with HTTP 429 and the error code rate_limited. Wait until the time in X-RateLimit-Reset before retrying – do not retry in a tight loop.
HTTP/1.1 429 Too Many Requests
Content-Type: application/json
X-RateLimit-Limit: 100
X-RateLimit-Remaining: 0
X-RateLimit-Reset: 1767225600
{"error": {"code": "rate_limited", "message": "Rate limit exceeded. Try again after the reset time."}} You can check your current quota at any time with GET /me.
اینڈ پوائنٹس
| اینڈ پوائنٹ | تصدیق | وضاحت |
|---|---|---|
POST /generate | API کلید | مکمل فیویکون پیکیج بنائیں۔ |
GET /me | API کلید | آپ کا اکاؤنٹ اور موجودہ ریٹ لمٹ کی صورتحال۔ |
GET /sizes | کوئی نہیں | جنریٹر کی بنائی ہوئی تمام آئیکن فائلوں اور سائزز کی فہرست۔ |
GET /openapi.json | کوئی نہیں | مشین کے پڑھنے کے قابل OpenAPI 3.1 اسپیسیفکیشن۔ |
فیویکون پیکیج بنائیں
/generateایک سورس امیج سے مکمل فیویکون پیکیج بناتا ہے۔ امیج تین طریقوں میں سے کسی ایک سے بھیجیں:
| کانٹینٹ ٹائپ | امیج فیلڈ | وضاحت |
|---|---|---|
multipart/form-data | image | فائل اپلوڈ۔ تجویز کردہ – سب سے مؤثر طریقہ۔ |
application/json | image_base64 | Base64-encoded image, either raw base64 or a data URL such as data:image/png;base64,iVBOR…. |
application/json | image_url | امیج کا عوامی http یا https URL۔ سرور اسے ڈاؤن لوڈ کرتا ہے (زیادہ سے زیادہ 10 MB)۔ |
معاون ان پٹ فارمیٹس: PNG، JPG، WebP، AVIF، GIF، BMP، SVG اور ICO۔ فائل کا زیادہ سے زیادہ سائز: 10 MB۔
پیرامیٹرز
تمام پیرامیٹرز اختیاری ہیں۔ انہیں فارم فیلڈز (multipart) یا JSON پراپرٹیز کے طور پر بھیجیں۔ غلط ویلیوز کی صورت میں ڈیفالٹ استعمال ہوتا ہے۔
| نام | ٹائپ / رینج | ڈیفالٹ | وضاحت |
|---|---|---|---|
app_name | string، زیادہ سے زیادہ 60 حروف | My Website | آپ کی ویب سائٹ یا ایپ کا نام، جو manifest.json اور مثالی صفحے میں استعمال ہوتا ہے۔ |
short_name | string، زیادہ سے زیادہ 24 حروف | app_name کے پہلے 12 حروف | مختصر نام جو Android ہوم اسکرین پر آئیکن کے نیچے دکھائی دیتا ہے۔ |
theme_color | #rrggbb | #ffffff | براؤزر UI کا رنگ (theme-color میٹا ٹیگ اور مینی فیسٹ)۔ |
tile_color | #rrggbb | theme_color کے برابر | Windows اسٹارٹ ٹائلز کا بیک گراؤنڈ رنگ۔ |
background | transparent | #rrggbb | transparent | براؤزر، Android اور Windows آئیکنز کا بیک گراؤنڈ۔ |
apple_background | #rrggbb | #ffffff | Apple ٹچ آئیکنز اور مسک ایبل آئیکن کا بیک گراؤنڈ (iOS شفافیت کو سپورٹ نہیں کرتا)۔ اگر background کوئی رنگ ہو تو نظرانداز ہو جاتا ہے – اس کی جگہ وہی رنگ استعمال ہوتا ہے۔ |
padding | integer، 0–40 (%) | 0 | امیج کے گرد خالی جگہ، آئیکن کے سائز کے فیصد کے طور پر۔ |
radius | integer، 0–50 (%) | 0 | گول کونے۔ 50 سے دائرہ بنتا ہے۔ Apple آئیکنز پر لاگو نہیں ہوتا، کیونکہ iOS انہیں خود گول کرتا ہے۔ |
zoom | integer، 50–400 (%) | 100 | آئیکن کے اندر امیج کا اسکیل۔ 100 سے زیادہ ویلیوز امیج کو کراپ کر دیتی ہیں۔ |
offset_x, offset_y | number، -1 تا 1 | 0 | امیج کو افقی / عمودی طور پر ہلاتا ہے، آئیکن کے سائز کے ایک حصے کے طور پر۔ |
path | string | / | آپ کے سرور پر وہ فولڈر جہاں آئیکنز رکھے جائیں گے۔ HTML اسنیپٹ، مینی فیسٹ اور browserconfig میں استعمال ہوتا ہے۔ |
display | standalone | fullscreen | minimal-ui | browser | standalone | manifest میں لکھا جانے والا PWA ڈسپلے موڈ۔ |
pixelated | auto | 1 | 0 | auto | پکسل آرٹ کے لیے شارپ nearest-neighbour اسکیلنگ۔ auto اسے 64 px یا اس سے چھوٹے سورسز کے لیے فعال کرتا ہے۔ |
maskable | 1 | 0 | 1 | Android ایڈاپٹو آئیکنز کے لیے سیف زون پیڈنگ کے ساتھ maskable-icon-512x512.png بھی بناتا ہے۔ |
ico_sizes | 16، 24، 32، 48، 64، 128، 256 کی کوما سے الگ کی گئی فہرست | 16,32,48 | favicon.ico میں شامل کیے جانے والے سائزز۔ |
groups | favicon، apple، android، ms کی کوما سے الگ کی گئی فہرست | favicon,apple,android,ms | بنائے جانے والے آئیکن سیٹس: براؤزر فیویکونز، Apple ٹچ آئیکنز، Android / PWA آئیکنز اور Windows ٹائلز۔ |
format | zip | json | zip | رسپانس فارمیٹ – نیچے دیکھیں۔ |
رسپانس
format=zip- Binary ZIP archive with
Content-Type: application/zipandContent-Disposition: attachment. Default. format=json- JSON object with the package
id(32 hex characters), thehtmlsnippet for your <head> and afilesarray; each file hasname,mime,size(bytes) andbase64contents.
مثالی ریکویسٹ – multipart، ZIP رسپانس
curl --fail-with-body -sS https://makefav.com/api/v1/generate \
-H "Authorization: Bearer $MAKEFAV_API_KEY" \
-F "[email protected]" \
-F "app_name=My App" \
-F "theme_color=#2f9e68" \
-F "radius=20" \
-o favicons.zip HTTP/1.1 200 OK
Content-Type: application/zip
Content-Disposition: attachment
X-RateLimit-Limit: 100
X-RateLimit-Remaining: 99
X-RateLimit-Reset: 1767225600
<binary ZIP data> مثالی ریکویسٹ – امیج URL کے ساتھ JSON، JSON رسپانس
curl --fail-with-body -sS https://makefav.com/api/v1/generate \
-H "Authorization: Bearer $MAKEFAV_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"image_url": "https://example.com/logo.png",
"app_name": "My App",
"theme_color": "#2f9e68",
"radius": 20,
"groups": "favicon,apple,android",
"format": "json"
}' {
"id": "9f86d081884c7d659a2feaa0c55ad015",
"html": "<link rel=\"apple-touch-icon\" sizes=\"57x57\" href=\"/apple-icon-57x57.png\">\n…\n<meta name=\"theme-color\" content=\"#2f9e68\">",
"files": [
{"name": "favicon.ico", "mime": "image/x-icon", "size": 15086, "base64": "AAABAAMAEBAAAAEAIABoBAAANgAAACAg…"},
{"name": "favicon-16x16.png", "mime": "image/png", "size": 612, "base64": "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQ…"},
{"name": "manifest.json", "mime": "application/json", "size": 1094, "base64": "ewogICAgIm5hbWUiOiAiTXkgQXBwIiwK…"}
]
}
اپنا اکاؤنٹ حاصل کریں
/meAPI کلید جس صارف کی ہے اس کی معلومات اور موجودہ ریٹ لمٹ کی صورتحال لوٹاتا ہے۔ کلید کی تصدیق کے لیے مفید۔ تصدیق درکار ہے؛ کوئی پیرامیٹر نہیں۔
مثالی ریکویسٹ
curl -sS https://makefav.com/api/v1/me \
-H "Authorization: Bearer $MAKEFAV_API_KEY" مثالی رسپانس
{
"id": 1,
"email": "[email protected]",
"name": "Jane Doe",
"rate_limit": {"limit": 100, "remaining": 97, "reset": 1767225600}
}
آئیکن سائزز کی فہرست
/sizesReturns every icon file the generator can produce, with its pixel size and group. No authentication and no parameters. The group value matches the groups parameter of POST /generate.
مثالی ریکویسٹ
curl -sS https://makefav.com/api/v1/sizes مثالی رسپانس
{
"files": [
{"name": "favicon-16x16.png", "size": 16, "group": "favicon"},
{"name": "favicon-32x32.png", "size": 32, "group": "favicon"},
{"name": "apple-touch-icon.png", "size": 180, "group": "apple"},
{"name": "android-icon-192x192.png", "size": 192, "group": "android"},
{"name": "ms-icon-144x144.png", "size": 144, "group": "ms"}
]
}
OpenAPI اسپیسیفکیشن
/openapi.jsonاس API کی OpenAPI 3.1 تفصیل لوٹاتا ہے۔ تصدیق درکار نہیں۔ اسے Postman، Insomnia یا Swagger UI میں امپورٹ کریں، یا اپنی زبان کے لیے ٹائپڈ کلائنٹ بنانے کے لیے استعمال کریں۔
curl -sS https://makefav.com/api/v1/openapi.json -o makefav-openapi.json خرابیاں
Successful requests return HTTP 200. Every error returns a JSON body with a stable, machine-readable code and a human-readable message. Always branch on the code, not on the message text.
HTTP/1.1 422 Unprocessable Content
Content-Type: application/json
{
"error": {
"code": "invalid_image",
"message": "The uploaded file could not be decoded as an image."
}
} | HTTP اسٹیٹس | ایرر کوڈ | مطلب |
|---|---|---|
| 400 | bad_request | ریکویسٹ درست نہیں ہے، مثلاً کوئی امیج نہیں بھیجی گئی یا JSON باڈی غلط ہے۔ |
| 401 | unauthorized | API کلید موجود نہیں یا غلط ہے۔ |
| 403 | forbidden | کلید کے مالک کی ای میل کی تصدیق نہیں ہوئی، نیوز لیٹر سبسکرپشن غیر فعال ہے، یا اکاؤنٹ پر پابندی لگ چکی ہے۔ |
| 413 | file_too_large | امیج 10 MB سے بڑی ہے۔ |
| 415 | unsupported_type | فائل کی قسم یا ریکویسٹ کانٹینٹ ٹائپ سپورٹڈ نہیں ہے۔ |
| 422 | invalid_image | فائل کو امیج کے طور پر ڈی کوڈ نہیں کیا جا سکا، یا امیج URL ڈاؤن لوڈ نہیں ہو سکا۔ |
| 429 | rate_limited | بہت زیادہ ریکویسٹس۔ X-RateLimit-Reset تک انتظار کریں۔ |
| 500 | server_error | ہماری طرف سے کوئی مسئلہ پیش آیا۔ بعد میں دوبارہ کوشش کریں؛ اگر مسئلہ برقرار رہے تو سپورٹ سے رابطہ کریں۔ |
آؤٹ پٹ فائلیں
With all groups enabled, a package contains the files below. Files from disabled groups are left out.
| فائل | سائز | گروپ |
|---|---|---|
favicon.ico | 16, 32, 48 (قابلِ ترتیب) | ہمیشہ |
favicon-16x16.png | 16 × 16 | favicon |
favicon-32x32.png | 32 × 32 | favicon |
favicon-96x96.png | 96 × 96 | favicon |
apple-icon-57x57.png | 57 × 57 | apple |
apple-icon-60x60.png | 60 × 60 | apple |
apple-icon-72x72.png | 72 × 72 | apple |
apple-icon-76x76.png | 76 × 76 | apple |
apple-icon-114x114.png | 114 × 114 | apple |
apple-icon-120x120.png | 120 × 120 | apple |
apple-icon-144x144.png | 144 × 144 | apple |
apple-icon-152x152.png | 152 × 152 | apple |
apple-icon-180x180.png | 180 × 180 | apple |
apple-icon.png | 192 × 192 | apple |
apple-icon-precomposed.png | 192 × 192 | apple |
apple-touch-icon.png | 180 × 180 | apple |
android-icon-36x36.png | 36 × 36 | android |
android-icon-48x48.png | 48 × 48 | android |
android-icon-72x72.png | 72 × 72 | android |
android-icon-96x96.png | 96 × 96 | android |
android-icon-144x144.png | 144 × 144 | android |
android-icon-192x192.png | 192 × 192 | android |
android-icon-512x512.png | 512 × 512 | android |
web-app-manifest-192x192.png | 192 × 192 | android |
web-app-manifest-512x512.png | 512 × 512 | android |
maskable-icon-512x512.png | 512 × 512 | android |
ms-icon-70x70.png | 70 × 70 | ms |
ms-icon-144x144.png | 144 × 144 | ms |
ms-icon-150x150.png | 150 × 150 | ms |
ms-icon-310x310.png | 310 × 310 | ms |
اضافی فائلیں
| فائل | شامل | وضاحت |
|---|---|---|
favicon.svg | صرف SVG ان پٹ کے لیے، بغیر کراپ، زوم، پیڈنگ، کونوں یا بیک گراؤنڈ کے | آپ کی SVG کی صاف کی ہوئی کاپی، ان براؤزرز کے لیے جو ویکٹر فیویکونز کو سپورٹ کرتے ہیں۔ |
manifest.json, site.webmanifest | android | Android اور انسٹال ہونے والی PWAs کے لیے ویب ایپ مینی فیسٹ (دو یکساں کاپیاں)۔ |
browserconfig.xml | ms | آپ کے ٹائل رنگ کے ساتھ Windows ٹائل کنفیگریشن۔ |
readme-makefav.txt | ہمیشہ | انسٹالیشن ہدایات، جن کے آخر میں آپ کے <head> کے لیے HTML کوڈ ہے۔ |
کوڈ کی مثالیں
Each example uploads logo.png with a few options and saves favicons.zip, handling API errors. Set the environment variable MAKEFAV_API_KEY to your API key first.
Multipart اپلوڈ:
# Multipart upload (recommended). --fail-with-body exits non-zero on HTTP errors
# and still saves the JSON error body, so you can inspect it.
curl --fail-with-body -sS https://makefav.com/api/v1/generate \
-H "Authorization: Bearer $MAKEFAV_API_KEY" \
-F "[email protected]" \
-F "app_name=My App" \
-F "theme_color=#2f9e68" \
-F "radius=20" \
-o favicons.zip \
|| { echo "Request failed:"; cat favicons.zip; rm -f favicons.zip; exit 1; } base64-انکوڈڈ امیج کے ساتھ JSON باڈی (jq درکار ہے):
# JSON body with a base64-encoded image (built with jq to avoid argument length limits)
base64 < logo.png | tr -d '\n' > logo.b64
jq -n --rawfile img logo.b64 \
'{image_base64: $img, app_name: "My App", theme_color: "#2f9e68", radius: 20}' \
| curl --fail-with-body -sS https://makefav.com/api/v1/generate \
-H "Authorization: Bearer $MAKEFAV_API_KEY" \
-H "Content-Type: application/json" \
--data-binary @- \
-o favicons.zip \
|| { echo "Request failed:"; cat favicons.zip; rm -f favicons.zip; exit 1; } <?php
// Requires the curl extension. Run: MAKEFAV_API_KEY=mf_... php favicons.php
$apiKey = getenv('MAKEFAV_API_KEY') ?: exit("Set MAKEFAV_API_KEY first\n");
$ch = curl_init('https://makefav.com/api/v1/generate');
curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_TIMEOUT => 60,
CURLOPT_HTTPHEADER => ['Authorization: Bearer ' . $apiKey],
CURLOPT_POSTFIELDS => [
'image' => new CURLFile('logo.png', 'image/png', 'logo.png'),
'app_name' => 'My App',
'theme_color' => '#2f9e68',
'radius' => '20',
],
]);
$body = curl_exec($ch);
if ($body === false) {
fwrite(STDERR, 'Request failed: ' . curl_error($ch) . PHP_EOL);
exit(1);
}
$status = curl_getinfo($ch, CURLINFO_RESPONSE_CODE);
if ($status !== 200) {
$error = json_decode($body, true)['error'] ?? ['code' => 'http_' . $status, 'message' => substr($body, 0, 200)];
fwrite(STDERR, "Error {$status} {$error['code']}: {$error['message']}" . PHP_EOL);
exit(1);
}
file_put_contents('favicons.zip', $body);
echo 'Saved favicons.zip (' . strlen($body) . " bytes)\n"; # pip install requests · Run: MAKEFAV_API_KEY=mf_... python favicons.py
import os
import sys
import requests
API_KEY = os.environ["MAKEFAV_API_KEY"]
try:
with open("logo.png", "rb") as logo:
resp = requests.post(
"https://makefav.com/api/v1/generate",
headers={"Authorization": f"Bearer {API_KEY}"},
files={"image": ("logo.png", logo, "image/png")},
data={"app_name": "My App", "theme_color": "#2f9e68", "radius": 20},
timeout=60,
)
except requests.RequestException as exc:
sys.exit(f"Request failed: {exc}")
if resp.status_code != 200:
try:
err = resp.json()["error"]
sys.exit(f"Error {resp.status_code} {err['code']}: {err['message']}")
except (ValueError, KeyError, TypeError):
sys.exit(f"Error {resp.status_code}: {resp.text[:200]}")
with open("favicons.zip", "wb") as out:
out.write(resp.content)
remaining = resp.headers.get("X-RateLimit-Remaining")
print(f"Saved favicons.zip ({len(resp.content)} bytes), {remaining} requests left this hour") // favicons.mjs — Node.js 18+, no dependencies. Run: MAKEFAV_API_KEY=mf_... node favicons.mjs
import { readFile, writeFile } from 'node:fs/promises';
const form = new FormData();
form.append('image', new Blob([await readFile('logo.png')], { type: 'image/png' }), 'logo.png');
form.append('app_name', 'My App');
form.append('theme_color', '#2f9e68');
form.append('radius', '20');
const res = await fetch('https://makefav.com/api/v1/generate', {
method: 'POST',
headers: { Authorization: `Bearer ${process.env.MAKEFAV_API_KEY}` },
body: form,
});
if (!res.ok) {
const body = await res.json().catch(() => null);
console.error(`Error ${res.status} ${body?.error?.code ?? ''}: ${body?.error?.message ?? res.statusText}`);
process.exit(1);
}
await writeFile('favicons.zip', Buffer.from(await res.arrayBuffer()));
console.log(`Saved favicons.zip, ${res.headers.get('x-ratelimit-remaining')} requests left this hour`); <input type="file" id="logo" accept="image/*">
<button type="button" id="go">Generate favicons</button>
<script>
// Never put your API key in browser code. Point ENDPOINT at your own backend route,
// which forwards the multipart body to https://makefav.com/api/v1/generate and adds
// the "Authorization: Bearer mf_..." header on the server.
const ENDPOINT = '/my-backend/favicons';
document.getElementById('go').addEventListener('click', async () => {
const file = document.getElementById('logo').files[0];
if (!file) {
alert('Please choose an image first.');
return;
}
const form = new FormData();
form.append('image', file);
form.append('app_name', 'My App');
form.append('theme_color', '#2f9e68');
form.append('radius', '20');
try {
const res = await fetch(ENDPOINT, { method: 'POST', body: form });
if (!res.ok) {
const body = await res.json().catch(() => null);
throw new Error(body?.error?.message || `HTTP ${res.status}`);
}
const url = URL.createObjectURL(await res.blob());
const a = Object.assign(document.createElement('a'), { href: url, download: 'favicons.zip' });
document.body.append(a);
a.click();
a.remove();
setTimeout(() => URL.revokeObjectURL(url), 1000);
} catch (err) {
alert('Favicon generation failed: ' + err.message);
}
});
</script> // go run favicons.go (MAKEFAV_API_KEY must be set)
package main
import (
"bytes"
"encoding/json"
"fmt"
"io"
"mime/multipart"
"net/http"
"net/textproto"
"os"
"time"
)
func main() {
if err := run(); err != nil {
fmt.Fprintln(os.Stderr, err)
os.Exit(1)
}
}
func run() error {
var body bytes.Buffer
w := multipart.NewWriter(&body)
logo, err := os.ReadFile("logo.png")
if err != nil {
return err
}
h := make(textproto.MIMEHeader)
h.Set("Content-Disposition", `form-data; name="image"; filename="logo.png"`)
h.Set("Content-Type", "image/png")
part, err := w.CreatePart(h)
if err != nil {
return err
}
if _, err := part.Write(logo); err != nil {
return err
}
for k, v := range map[string]string{"app_name": "My App", "theme_color": "#2f9e68", "radius": "20"} {
if err := w.WriteField(k, v); err != nil {
return err
}
}
if err := w.Close(); err != nil {
return err
}
req, err := http.NewRequest(http.MethodPost, "https://makefav.com/api/v1/generate", &body)
if err != nil {
return err
}
req.Header.Set("Authorization", "Bearer "+os.Getenv("MAKEFAV_API_KEY"))
req.Header.Set("Content-Type", w.FormDataContentType())
client := &http.Client{Timeout: 60 * time.Second}
resp, err := client.Do(req)
if err != nil {
return err
}
defer resp.Body.Close()
if resp.StatusCode != http.StatusOK {
var apiErr struct {
Error struct {
Code string `json:"code"`
Message string `json:"message"`
} `json:"error"`
}
_ = json.NewDecoder(resp.Body).Decode(&apiErr)
return fmt.Errorf("error %d %s: %s", resp.StatusCode, apiErr.Error.Code, apiErr.Error.Message)
}
zip, err := io.ReadAll(resp.Body)
if err != nil {
return err
}
if err := os.WriteFile("favicons.zip", zip, 0o644); err != nil {
return err
}
fmt.Printf("Saved favicons.zip (%d bytes)\n", len(zip))
return nil
} # ruby favicons.rb (MAKEFAV_API_KEY must be set) — standard library only
require "net/http"
require "json"
require "uri"
uri = URI("https://makefav.com/api/v1/generate")
req = Net::HTTP::Post.new(uri)
req["Authorization"] = "Bearer #{ENV.fetch("MAKEFAV_API_KEY")}"
res = File.open("logo.png", "rb") do |logo|
req.set_form(
[
["image", logo, { filename: "logo.png", content_type: "image/png" }],
["app_name", "My App"],
["theme_color", "#2f9e68"],
["radius", "20"]
],
"multipart/form-data"
)
Net::HTTP.start(uri.host, uri.port, use_ssl: true, read_timeout: 60) { |http| http.request(req) }
end
unless res.is_a?(Net::HTTPSuccess)
err = (JSON.parse(res.body)["error"] rescue nil) || { "code" => res.code, "message" => res.body.to_s[0, 200] }
abort "Error #{res.code} #{err["code"]}: #{err["message"]}"
end
File.binwrite("favicons.zip", res.body)
puts "Saved favicons.zip (#{res.body.bytesize} bytes)" // .NET 6+ console app (Program.cs, top-level statements, implicit usings enabled)
using System.Net.Http.Headers;
using System.Text.Json;
using var http = new HttpClient { Timeout = TimeSpan.FromSeconds(60) };
http.DefaultRequestHeaders.Authorization =
new AuthenticationHeaderValue("Bearer", Environment.GetEnvironmentVariable("MAKEFAV_API_KEY"));
using var form = new MultipartFormDataContent();
var image = new ByteArrayContent(await File.ReadAllBytesAsync("logo.png"));
image.Headers.ContentType = new MediaTypeHeaderValue("image/png");
form.Add(image, "image", "logo.png");
form.Add(new StringContent("My App"), "app_name");
form.Add(new StringContent("#2f9e68"), "theme_color");
form.Add(new StringContent("20"), "radius");
using var response = await http.PostAsync("https://makefav.com/api/v1/generate", form);
if (!response.IsSuccessStatusCode)
{
var body = await response.Content.ReadAsStringAsync();
string code = "", message = body;
try
{
var error = JsonDocument.Parse(body).RootElement.GetProperty("error");
code = error.GetProperty("code").GetString() ?? "";
message = error.GetProperty("message").GetString() ?? "";
}
catch (Exception e) when (e is JsonException or KeyNotFoundException or InvalidOperationException) { }
Console.Error.WriteLine($"Error {(int)response.StatusCode} {code}: {message}");
return 1;
}
await File.WriteAllBytesAsync("favicons.zip", await response.Content.ReadAsByteArrayAsync());
Console.WriteLine("Saved favicons.zip");
return 0; // Java 11+, no dependencies. Run: MAKEFAV_API_KEY=mf_... java MakeFav.java
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.time.Duration;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.UUID;
public class MakeFav {
public static void main(String[] args) throws IOException, InterruptedException {
String boundary = "----MakeFav" + UUID.randomUUID().toString().replace("-", "");
Map<String, String> fields = new LinkedHashMap<>();
fields.put("app_name", "My App");
fields.put("theme_color", "#2f9e68");
fields.put("radius", "20");
// Build the multipart/form-data body by hand
ByteArrayOutputStream body = new ByteArrayOutputStream();
for (Map.Entry<String, String> field : fields.entrySet()) {
body.write(("--" + boundary + "\r\n"
+ "Content-Disposition: form-data; name=\"" + field.getKey() + "\"\r\n\r\n"
+ field.getValue() + "\r\n").getBytes(StandardCharsets.UTF_8));
}
body.write(("--" + boundary + "\r\n"
+ "Content-Disposition: form-data; name=\"image\"; filename=\"logo.png\"\r\n"
+ "Content-Type: image/png\r\n\r\n").getBytes(StandardCharsets.UTF_8));
body.write(Files.readAllBytes(Path.of("logo.png")));
body.write(("\r\n--" + boundary + "--\r\n").getBytes(StandardCharsets.UTF_8));
HttpRequest request = HttpRequest.newBuilder(URI.create("https://makefav.com/api/v1/generate"))
.timeout(Duration.ofSeconds(60))
.header("Authorization", "Bearer " + System.getenv("MAKEFAV_API_KEY"))
.header("Content-Type", "multipart/form-data; boundary=" + boundary)
.POST(HttpRequest.BodyPublishers.ofByteArray(body.toByteArray()))
.build();
HttpResponse<byte[]> response = HttpClient.newHttpClient()
.send(request, HttpResponse.BodyHandlers.ofByteArray());
if (response.statusCode() != 200) {
// Error body is JSON: {"error":{"code":"...","message":"..."}}
System.err.println("Error " + response.statusCode() + ": "
+ new String(response.body(), StandardCharsets.UTF_8));
System.exit(1);
}
Files.write(Path.of("favicons.zip"), response.body());
System.out.println("Saved favicons.zip (" + response.body().length + " bytes)");
}
} GitHub Actions ورک فلو – JSON فارمیٹ، فائلیں jq سے ڈی کوڈ کی گئیں:
# .github/workflows/favicons.yml — regenerate favicons whenever the logo changes.
# Add your key as a repository secret named MAKEFAV_API_KEY.
name: Favicons
on:
push:
paths: ['branding/logo.png']
workflow_dispatch:
jobs:
favicons:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Generate favicon package (JSON format)
env:
MAKEFAV_API_KEY: ${{ secrets.MAKEFAV_API_KEY }}
run: |
set -euo pipefail
curl --fail-with-body -sS https://makefav.com/api/v1/generate \
-H "Authorization: Bearer $MAKEFAV_API_KEY" \
-F "image=@branding/logo.png" \
-F "app_name=My App" \
-F "theme_color=#2f9e68" \
-F "radius=20" \
-F "path=/icons/" \
-F "format=json" \
-o favicons.json || { cat favicons.json; exit 1; }
mkdir -p public/icons
# Decode every file from the JSON response (jq is preinstalled on GitHub runners)
jq -r '.files[] | "\(.name) \(.base64)"' favicons.json |
while read -r name data; do
printf '%s' "$data" | base64 -d > "public/icons/$(basename "$name")"
done
jq -r '.html' favicons.json > public/icons/head-snippet.html
ls -l public/icons
- uses: actions/upload-artifact@v4
with:
name: favicons
path: public/icons کسی بھی CI کے لیے سادہ شیل اسکرپٹ – ZIP فارمیٹ:
#!/usr/bin/env bash
# scripts/favicons.sh — simpler variant for any CI or build step: fetch the ZIP and unpack it.
set -euo pipefail
: "${MAKEFAV_API_KEY:?Set MAKEFAV_API_KEY}"
curl --fail-with-body -sS https://makefav.com/api/v1/generate \
-H "Authorization: Bearer $MAKEFAV_API_KEY" \
-F "[email protected]" \
-F "app_name=My App" \
-F "theme_color=#2f9e68" \
-F "radius=20" \
-o favicons.zip || { cat favicons.zip; rm -f favicons.zip; exit 1; }
unzip -o -q favicons.zip -d public/
rm favicons.zip
echo "Favicons written to public/" HTML کا استعمال
Upload all files to the folder you set with path, then paste the snippet into the <head> of every page. It is included at the end of readme-makefav.txt in the package and, with format=json, returned in the html field. Example for the options used in the code examples above:
<head>
<meta charset="utf-8">
<title>My App</title>
<link rel="apple-touch-icon" sizes="57x57" href="/apple-icon-57x57.png">
<link rel="apple-touch-icon" sizes="60x60" href="/apple-icon-60x60.png">
<link rel="apple-touch-icon" sizes="72x72" href="/apple-icon-72x72.png">
<link rel="apple-touch-icon" sizes="76x76" href="/apple-icon-76x76.png">
<link rel="apple-touch-icon" sizes="114x114" href="/apple-icon-114x114.png">
<link rel="apple-touch-icon" sizes="120x120" href="/apple-icon-120x120.png">
<link rel="apple-touch-icon" sizes="144x144" href="/apple-icon-144x144.png">
<link rel="apple-touch-icon" sizes="152x152" href="/apple-icon-152x152.png">
<link rel="apple-touch-icon" sizes="180x180" href="/apple-icon-180x180.png">
<link rel="icon" type="image/png" sizes="192x192" href="/android-icon-192x192.png">
<link rel="icon" type="image/png" sizes="32x32" href="/favicon-32x32.png">
<link rel="icon" type="image/png" sizes="96x96" href="/favicon-96x96.png">
<link rel="icon" type="image/png" sizes="16x16" href="/favicon-16x16.png">
<link rel="icon" href="/favicon.ico" sizes="any">
<link rel="manifest" href="/manifest.json">
<meta name="msapplication-TileColor" content="#2f9e68">
<meta name="msapplication-TileImage" content="/ms-icon-144x144.png">
<meta name="msapplication-config" content="/browserconfig.xml">
<meta name="theme-color" content="#2f9e68">
</head> ڈیپلائے کرنے کے بعد اپنے براؤزر کا کیش صاف کریں یا سائٹ کو پرائیویٹ ونڈو میں کھولیں – براؤزرز فیویکونز کو بہت زیادہ کیش کرتے ہیں۔
تبدیلیوں کا ریکارڈ
v1
- MakeFav REST API کا ابتدائی عوامی ریلیز۔
- Endpoints
POST /generate,GET /me,GET /sizesandGET /openapi.json. - ZIP اور JSON رسپانس فارمیٹس، multipart، base64 اور URL امیج ان پٹ۔
- فی گھنٹہ 100 ریکویسٹس کے ساتھ ذاتی API کلیدیں۔
ورژن 1 مستحکم ہے: ہم صرف اختیاری پیرامیٹرز اور فیلڈز شامل کرتے ہیں۔ بریکنگ تبدیلیاں پیشگی اطلاع کے ساتھ نئے ورژن کے طور پر جاری کی جائیں گی۔
سپورٹ
سوالات، بگ رپورٹس یا زیادہ ریٹ لمٹ چاہیے؟ ہم مدد کے لیے حاضر ہیں۔ اپنے پیغام میں ریکویسٹ کا وقت اور ایرر کوڈ ضرور لکھیں – اپنی API کلید ہرگز نہیں۔