Розгорніть MoreLogin на безголовому сервері Ubuntu та автоматизуйте профілі браузера через локальний API — середовище робочого столу не потрібне.
До кінця цього посібника ви матимете:
- Запущений екземпляр MoreLogin на безголовому сервері Ubuntu 24.04
- Мережеву переадресацію налаштовано, щоб зовнішні машини могли підключатися через CDP (Chrome DevTools Protocol)
- Робочий сценарій автоматизації Python, який створює, запускає, контролює та очищає профілі браузера
┌──────────────────────────────────────────────────────────┐
│ Ubuntu 24.04 Server │
│ │
│ ┌──────────────┐ ┌───────────────────────────────┐ │
│ │ xvfb │───▶│ MoreLogin AppImage │ │
│ │ (virtual │ │ Local API :40000 │ │
│ │ display) │ │ CDP debug :<dynamic> │ │
│ │ │ │ (127.0.0.1, per profile) │ │
│ └──────────────┘ └───────────────────────────────┘ │
│ │ │
│ socat forwarding │
│ │ │
│ 0.0.0.0:40001 → 127.0.0.1:40000 │
│ 0.0.0.0:<N+1> → 127.0.0.1:<N> │
└──────────────────────────────────────────────────────────┘
│
External machine
(Playwright / Puppeteer / Selenium)[!NOTE] Порт налагодження CDP є динамічним — кожен профіль браузера отримує власний порт, який повертає кінцева точка
/api/env/start. На діаграмі вище використовується<N>як заповнювач.
| Вимога | Подробиці |
|---|---|
| Операційна система | Сервер Ubuntu 24.04 (x86_64) |
| Рекомендовані характеристики | 8 vCPU, 8 ГБ оперативної пам’яті (підтримує ~5 одночасних профілів) |
| Мережа | Вихідний доступ до Інтернету; відкрийте вхідний порт 40001 і вибрані вами перенаправлені порти CDP або використовуйте натомість тунелі SSH |
| Python (необов’язково) | Python 3.8+ із pip для виконання прикладу сценарію |
Підключіться до свого сервера через SSH і встановіть необхідні пакети:
# FUSE support (required for AppImage)
sudo apt install -y libfuse2t64
# GTK / accessibility / display libraries
sudo apt install -y libatk1.0-0 libatk-bridge2.0-0 libatspi2.0-0
sudo apt install -y libcups2
sudo apt install -y libgtk-3-0 libgdk-pixbuf2.0-0
sudo apt install -y libgbm1 libxkbcommon0 libasound2t64
# Virtual framebuffer (headless display)
sudo apt install -y xvfb
# TCP forwarder
sudo apt install -y socatЯкщо сторінки браузера відображаються без тексту або показують відсутні символи, інсталюйте відповідні пакети шрифтів:
# CJK (Chinese, Japanese, Korean)
sudo apt install -y fonts-noto-cjk fonts-noto-cjk-extra
# Arabic
sudo apt install -y fonts-noto-color-emoji fonts-noto-extraДля інших мов установіть відповідний пакет Сімейство шрифтів Noto.
wget https://get.morelogin.com/client/prod/linux/x64/2.54.0/MoreLogin_x86_64_2.54.0.AppImage
chmod +x MoreLogin_x86_64_2.54.0.AppImageЗамініть
2.54.0останньою версією, доступною у вашому обліковому записі MoreLogin або на сторінці завантаження.
Використовуйте xvfb-run, щоб створити віртуальний дисплей, а потім запустіть AppImage:
nohup xvfb-run -a ./MoreLogin_x86_64_2.54.0.AppImage --no-sandbox > morelogin.log 2>&1 &Переконайтеся, що він розпочався успішно:
# Check the process is running
ps aux | grep MoreLoginПроцес повної ініціалізації може зайняти 5–10 секунд.
[!CAUTION] Ви повинні увійти в систему, перш ніж викликати будь-яку іншу локальну кінцеву точку API. На безголовому сервері немає графічного інтерфейсу для входу вручну, тому ви повинні пройти автентифікацію через API. Без цього кроку всі виклики API повернуться:
{"status": "помилка", "code": 401, "message": "Ваш статус входу минув, увійдіть знову"}
Відкрийте настільний клієнт MoreLogin (на будь-якій машині, де ви ввійшли в систему) і перейдіть до Налаштування → API та MCP. Скопіюйте APP ID і API Key із розділу Open API:

Викличте кінцеву точку входу за допомогою облікових даних:
curl -X POST http://127.0.0.1:40000/api/user/login \
-H "Content-Type: application/json" \
-d '{
"apiId": "YOUR_APP_ID",
"apiKey": "YOUR_API_KEY"
}'Успішна відповідь виглядає так:
{"code": 0, "msg": null, "data": true}Переконайтеся, що API готовий, перерахувавши профілі браузера:
curl -s -X POST http://127.0.0.1:40000/api/env/page \
-H "Content-Type: application/json" \
-d '{"pageNo": 1, "pageSize": 1}'Відповідь
{"code":0, ...}означає, що ви ввійшли в систему та API готовий.
Контрольна точка: Ваш сервер MoreLogin працює повністю. Перейдіть до кроку 4 для віддаленого доступу або перейдіть безпосередньо до кроку 5, якщо сценарії запущено на тому самому сервері.
[!NOTE] Сеанс входу триває доти, доки виконується процес MoreLogin. Якщо ви перезапустите AppImage, вам потрібно буде знову ввійти.
За замовчуванням і локальний API (:40000), і порти налагодження CDP прив’язуються до 127.0.0.1. Якщо вам потрібно отримати до них доступ із зовнішнього комп’ютера (наприклад, ноутбука для розробки), використовуйте socat для перенаправлення трафіку.
[!WARNING] Ризик безпеці — не піддавайте ці порти загальнодоступному Інтернету.
- Локальний API не має вбудованої автентифікації для більшості кінцевих точок.
- Порт налагодження CDP забезпечує повне дистанційне керування екземпляром браузера (читання файлів cookie, введення сценаріїв, створення скріншотів).
Рекомендації:
- Використовуйте тунель SSH замість socat для віддаленого доступу:
ssh -L 40000:127.0.0.1:40000 user@server- Якщо вам потрібно використовувати socat, обмежте доступ за допомогою правил брандмауера до лише певних IP-адрес
- Використовуйте VPN або групи безпеки хмарного провайдера, щоб обмежити вхідний трафік
- Ніколи не відкривайте порти
40001/ порти CDP для0.0.0.0на загальнодоступному сервері без обмежень IP
nohup socat TCP-LISTEN:40001,fork,reuseaddr,bind=0.0.0.0 TCP:127.0.0.1:40000 &Зовнішні машини тепер можуть отримати доступ до API за адресою
http://<server-ip>:40001.
Коли ви запускаєте профіль браузера через API, відповідь включає динамічний debugPort (наприклад, 9222). Кожен профіль може отримати інший порт. Передайте його, щоб зовнішні інструменти автоматизації (Playwright, Puppeteer, Selenium) могли підключитися:
# Example: if debugPort=9222, forward to external port 9223 (debugPort + 1)
# Adjust both ports to match the actual debugPort returned by /api/env/start
nohup socat TCP-LISTEN:9223,fork,reuseaddr,bind=0.0.0.0 TCP:127.0.0.1:9222 &[!WARNING] Під час одночасного запуску кількох профілів переконайтеся, що перенаправлені порти не конфліктують із портами налагодження інших профілів. Наприклад, якщо профіль A отримує
debugPort=9222і ви пересилаєте на9223, а профіль B отримуєdebugPort=9223, виникне конфлікт портів. Розгляньте можливість використання більшого зміщення або виділеного діапазону портів.
[!TIP] У виробництві створюйте переадресацію socat динамічно після кожного виклику
/api/env/start, використовуючи повернутийdebugPort. Перегляньте приклад Python, щоб дізнатися про робочу реалізацію.
Якщо сценарії автоматизації запускаються на тому самому сервері, ви можете пропустити socat і підключитися безпосередньо до
127.0.0.1.
Якщо ви використовуєте socat, обмежте доступ лише надійним IP-адресам:
# Allow only a specific IP (recommended)
sudo ufw allow from <YOUR_IP> to any port 40001 proto tcp
sudo ufw allow from <YOUR_IP> to any port 9223 proto tcp
# Or allow from any IP (NOT recommended for production)
# sudo ufw allow 40001/tcp
# sudo ufw allow 9223/tcpДля найбезпечнішого віддаленого доступу використовуйте тунель SSH — не потрібно змінювати брандмауер або socat.
Оскільки порт CDP є динамічним (призначається під час запуску профілю), робочий процес такий:
Спочатку тунелюйте порт API:
# Run this on your local machine ssh -L 40000:127.0.0.1:40000 user@<server-ip>Запустіть профіль через тунельований API (
http://127.0.0.1:40000/api/env/start) і прочитайте отриманийdebugPort.Відкрийте другий тунель для порту CDP:
# Replace <debugPort> with the actual port returned by the API ssh -L <debugPort>:127.0.0.1:<debugPort> user@<server-ip>Підключіться до
http://127.0.0.1:<debugPort>зі своїх локальних сценаріїв Playwright / Puppeteer, ніби сервер локальний.
[!TIP] Ви можете поєднати обидва тунелі в одній команді, якщо заздалегідь знаєте діапазон портів, наприклад:
ssh -L 40000:127.0.0.1:40000 -L 9222:127.0.0.1:9222 -L 9223:127.0.0.1:9223 користувач@<ip-сервер>Але на практиці простіше спочатку запустити тунель API, а потім за потреби додавати тунелі для кожного профілю.
Нижче наведено мінімальний приклад Python, який показує повний життєвий цикл профілю браузера. Щоб отримати повний сценарій, готовий до роботи, із паралелізмом і обробкою помилок, перегляньте повний приклад на GitHub.
pip install requests playwrightPlaywright використовується тут лише для клієнта CDP (
connect_over_cdp). Вам не потрібно запускатиplaywright install— MoreLogin пропонує власний браузер.
На Linux Server браузерний рушій повинен запускатися з прапором --no-sandbox. Цей параметр передається через поле startupParams при створенні або оновленні профілю браузера.
[!CAUTION] Без
--no-sandboxбраузер не зможе запуститися в більшості серверних середовищ Linux (особливо при роботі підrootабо без повноцінного сеансу робочого столу).
Використовуйте /api/env/create/advanced для створення профілю з startupParams (ендпоінт /api/env/create/quick не підтримує це поле):
curl -X POST http://127.0.0.1:40000/api/env/create/advanced \
-H "Content-Type: application/json" \
-d '{
"browserTypeId": 1,
"operatorSystemId": 5,
"startupParams": ["--no-sandbox"]
}'[!TIP] Якщо ви використовували
/api/env/create/quickдля створення профілю, викличте/api/env/updateдля додавання--no-sandboxперед запуском — див. нижче.
Якщо у вас вже є профілі браузера, створені без --no-sandbox, оновіть їх перед запуском:
curl -X POST http://127.0.0.1:40000/api/env/update \
-H "Content-Type: application/json" \
-d '{
"envId": "YOUR_ENV_ID",
"startupParams": ["--no-sandbox"]
}'[!NOTE] Поле
startupParamsприймає масив рядків. Ви також можете додати інші прапори Chrome (наприклад,["--no-sandbox", "--disable-gpu"]). Прапор--no-sandboxпотрібен лише на Linux — профілі Windows та macOS не потребують його.
У цьому прикладі передбачається, що сценарій виконується на тому самому сервері, що й MoreLogin. Для віддалених сценаріїв див. примітки після коду.
import requests
from playwright.sync_api import sync_playwright
# ── Configuration ──────────────────────────────────────────
# Local: script runs on the SAME server as MoreLogin
# Remote: script runs on a DIFFERENT machine — see notes below
API_BASE = "http://127.0.0.1:40000"
# ① Create a browser profile
resp = requests.post(f"{API_BASE}/api/env/create/quick", json={
"browserTypeId": 1,
"operatorSystemId": 5,
"quantity": 1
})
resp_data = resp.json()
assert resp_data["code"] == 0, f"Create failed: {resp_data}"
env_id = resp_data["data"]["envIds"][0]
print(f"✅ Created profile: {env_id}")
# ①-b Add --no-sandbox (required on Linux Server)
resp = requests.post(f"{API_BASE}/api/env/update", json={
"envId": env_id,
"startupParams": ["--no-sandbox"]
})
resp_data = resp.json()
assert resp_data["code"] == 0, f"Update failed: {resp_data}"
print(f"✅ Set --no-sandbox for profile: {env_id}")
# ② Start the profile (headless)
resp = requests.post(f"{API_BASE}/api/env/start", json={
"envId": env_id
})
resp_data = resp.json()
assert resp_data["code"] == 0, f"Start failed: {resp_data}"
debug_port = resp_data["data"]["debugPort"] # Dynamic — different for each profile
print(f"✅ Started — debug port: {debug_port}")
# ③ Build the CDP URL
cdp_url = f"http://127.0.0.1:{debug_port}"
# ④ Connect via CDP and automate
with sync_playwright() as p:
browser = p.chromium.connect_over_cdp(cdp_url)
page = browser.contexts[0].pages[0]
page.goto("https://www.google.com")
page.screenshot(path=f"screenshot_{env_id}.png")
print(f"✅ Screenshot saved")
# Use disconnect() — not close() — to detach without killing the browser.
# The profile will be stopped cleanly via the API in step ⑤.
browser.disconnect()
# ⑤ Stop the profile
requests.post(f"{API_BASE}/api/env/close", json={"envId": env_id})
print(f"✅ Profile stopped")
# ⑥ Delete the profile
requests.post(f"{API_BASE}/api/env/remove", json={"envIds": [env_id]})
print(f"✅ Profile deleted")[!NOTE] Запускаєте з віддаленої машини? Два підходи:
Варіант A — тунель SSH (рекомендовано): Налаштуйте тунелі SSH від вашої локальної машини до сервера (див. § 4.4), а потім збережіть
API_BASE = "http://127.0.0.1:40000"іcdp_url = f"http://127.0.0.1:{debug_port}"— SSH робить віддалені порти локальними.Варіант B — socat на сервері: На сервері запустіть переадресацію socat для порту API та для кожного порту CDP:
# Запустіть їх на СЕРВЕРІ, а не на вашій локальній машині socat TCP-LISTEN:40001,fork,reuseaddr,bind=0.0.0.0 TCP:127.0.0.1:40000 & socat TCP-LISTEN:$((debug_port+1)),fork,reuseaddr,bind=0.0.0.0 TCP:127.0.0.1:$debug_port &Потім у вашому сценарії встановіть
API_BASE = "http://<server-ip>:40001"іcdp_url = f"http://<server-ip>:{debug_port + 1}". ⚠️ Обмежте доступ за допомогою правил брандмауера — див. § 4.3.
[!IMPORTANT] Структура
resp.json()["data"]["envIds"]відповідає поточному формату відповіді/api/env/create/quick. Якщо ви зіткнулися з іншою формою (наприклад,data: ["id1", ...]), перевірте Довідник API для вашої версії — формати відповідей можуть відрізнятися для різних випусків.
На віртуальній машині сервера Ubuntu 24.04 (8 vCPU, 8 ГБ оперативної пам’яті) було отримано такі результати за допомогою [повного сценарію стрес-тесту] (https://github.com/MoreLoginBrowser/MoreLogin-API-Demos/blob/main/MoreLogin-Python/linux_server_test.py):
| Метрика | Значення |
|---|---|
| Загальна кількість пробігів | 100 |
| Параллельність | 4 (одночасно) |
| Рівень успіху | 100,0% |
| Загальний час | 604.06 с |
| Середній час виконання завдання | 6.04 с |
| Пропускна здатність | 0,17 задач/с |
Ці цифри служать базовими. Фактична продуктивність залежить від характеристик сервера, умов мережі та складності сторінки.
Для робочих серверів запустіть MoreLogin як systemd service, щоб отримати автоматичний запуск під час завантаження, перезапуск у разі збою та централізоване журналювання.
sudo tee /etc/systemd/system/morelogin.service > /dev/null <<'EOF'
[Unit]
Description=MoreLogin Browser (headless)
After=network-online.target
Wants=network-online.target
[Service]
Type=simple
User=root
WorkingDirectory=/opt/morelogin
ExecStart=/usr/bin/xvfb-run -a /opt/morelogin/MoreLogin_x86_64_2.54.0.AppImage --no-sandbox
Restart=on-failure
RestartSec=10
StandardOutput=journal
StandardError=journal
[Install]
WantedBy=multi-user.target
EOFВідкоригуйте шляхи
WorkingDirectoryіExecStartвідповідно до місця розміщення AppImage.
[!TIP] Для виробництва розгляньте можливість створення спеціального користувача (наприклад,
morelogin) замість того, щоб працювати якroot, і відповідно налаштуйте право власності на файл і дозволи. Якщо для AppImage наразі потрібні привілеї root, ви можете залишитиUser=root, але найкращою практикою є ізоляція процесу під обліковим записом без root.
sudo systemctl daemon-reload
sudo systemctl enable morelogin # Auto-start on boot
sudo systemctl start morelogin # Start nowsudo systemctl status morelogin # Check status
sudo journalctl -u morelogin -f # Stream logs
sudo systemctl restart morelogin # Restart
sudo systemctl stop morelogin # Stop[!NOTE] Після перезапуску потрібно знову викликати кінцеву точку входу — сеанс API не витримує перезапуску процесу. Для автоматичного відновлення розгляньте можливість додавання сценарію
ExecStartPostабо завдання cron перевірки справності, яке викликає кінцеву точку входу після запуску служби.
AppImages require FUSE to run.Виправлення: Встановити підтримку FUSE:
sudo apt install -y libfuse2t64Виправлення: Установіть пакет шрифтів для цільової мови (див. Крок 1 — Установіть шрифти).
Причина: порти налагодження CDP прив’язуються до 127.0.0.1 за умовчанням.
Виправлення: налаштуйте переадресацію socat (див. Крок 4) і переконайтеся, що правила брандмауера дозволяють переадресований порт.
Причина: MoreLogin ще не завершив запуск, або процес стався збій.
Виправлення:
- Зачекайте 5–10 секунд після запуску
- Перевірте
morelogin.logна наявність помилок - Переконайтеся, що процес запущено:
ps aux | grep MoreLogin
{"status": "error", "code": 401, "message": "Your login status has expired, please log in again"}Причина: Ви не ввійшли через API або процес MoreLogin було перезапущено.
Виправлення: виклик кінцевої точки входу перед будь-яким іншим викликом API (див. Крок 3).
| Мета | Посилання |
|---|---|
| Повна довідка про API браузера | API веб-переглядача |
| Налаштування автентифікації | Посібник з автентифікації |
| Драматург / Селен / Приклади лялькаря | Приклади автоматизації |
| Повний сценарій стрес-тесту Linux | GitHub — linux_server_test.py |
| Швидкий старт CLI | Посібник CLI |