API Referansı

HTTP Yönlendirmeleri

PlainApp, POST /graphql adresindeki GraphQL API'sinin yanında küçük bir HTTP uç noktası seti sunar. Bu uç noktalar dosya sunma, multipart yüklemeler, zip akışı, DLNA yayınlama, WebSocket olayları ve sistem kontrolünü ele alır. Tüm file/upload/zip uç noktaları c-id başlığı (ve genellikle şifrelenmiş bir id sorgu parametresi) gerektirir.

Tip Tanımları

bash
# Common headers for protected HTTP endpoints:
c-id: <client-id>
# /fs, /proxyfs, /zip/* use an encrypted "id" query parameter produced
# by the GraphQL files()/fileIds() queries. The id is opaque to the client.

# Upload endpoints additionally require an encrypted "info" multipart part:
#   info = chaCha20Encrypt(token, json({ dir, size, replace, isAppFile }))
#   file = <raw bytes>
# Chunked uploads use:
#   info = chaCha20Encrypt(token, json({ fileId, index, size }))

# Status codes follow HTTP semantics:
#   200 OK              – success
#   201 Created         – upload stored
#   204 No Content      – init pending password
#   400 Bad Request     – missing/invalid params
#   401 Unauthorized    – bad token
#   403 Forbidden       – expired/invalid encrypted id
#   404 Not Found       – file/entry missing
#   410 Gone            – server shutting down
#   429 Too Many Requests – concurrent zip limit hit

İşlemler

http

POST /graphql

Ana GraphQL uç noktası. Tüm GraphQL sorgularını ve mutasyonlarını c-id + Authorization başlıklarıyla buraya gönderin. /peer_graphql uç noktası, eşleştirilmiş cihazlar arasında kullanılan peer-to-peer eşdeğeridir.

bash
curl --request POST \
  --url http://192.168.1.100:8080/graphql \
  --header 'c-id: <client-id>' \
  --header 'Authorization: Bearer <api-token>' \
  --header 'Content-Type: application/json' \
  --data '{"query":"{ app { battery deviceName } }"}'
http

GET /fs

Bir dosya, content:// URI'si veya paket simgesi sunar. id sorgu parametresi, files()/fileIds() tarafından döndürülen şifrelenmiş bir dizedir. Küçük resim oluşturma (?w=&h=&cc=), düşük verimli taşımalar için bayt aralığı (?offset=&length=), HEIF→PNG dönüştürme, 3gp→MP4 transkodlama ve bir Content-Disposition attachment başlığıyla indirme modunu (dl=1) destekler.

bash
# Original (full size, inline)
curl http://192.168.1.100:8080/fs?id=<encrypted-id> -o file.jpg

# Thumbnail (center-cropped to 200x200)
curl 'http://192.168.1.100:8080/fs?id=<encrypted-id>&w=200&h=200' -o thumb.jpg

# Download (attachment)
curl 'http://192.168.1.100:8080/fs?id=<encrypted-id>&dl=1' -OJ

# Byte range (BLE chunked download)
curl 'http://192.168.1.100:8080/fs?id=<encrypted-id>&offset=0&length=4096' \
  -o chunk.bin
http

GET /proxyfs

Bir peer HTTP URL'sini vekil sunar. id sorgu parametresi, eşleştirilmiş bir peer cihazdaki tam bir http(s) URL'sine çözülür; sunucu upstream yanıtını geri akıtır. Wi-Fi Aware üzerinden peer-to-peer dosya indirmeleri için kullanılır.

bash
curl http://192.168.1.100:8080/proxyfs?id=<encrypted-peer-url> -o peer-file.jpg
http

POST /upload

multipart/form-data aracılığıyla tek bir dosya yükleyin. "info" kısmı (ChaCha20 ile şifrelenmiş JSON), "file" kısmından önce gelmelidir. isAppFile=true olduğunda baytlar content-addressable AppFileStore'a (hash'e göre deduplikasyon) içe aktarılır; aksi takdirde dosya info.dir/<fileName> konumuna yazılır. Son dosya adını döndürür (üzerine yazmaktan kaçınırken bir "(1)" son eki olabilir).

bash
curl --request POST \
  --url http://192.168.1.100:8080/upload \
  --header 'c-id: <client-id>' \
  --form 'info=<encrypted-info-bytes>;type=application/octet-stream' \
  --form 'file=@/path/to/local.jpg'
http

POST /upload_chunk

Devam ettirilebilen, parçalı bir yükleme için bir parça yükleyin. Her parça diske upload_tmp/{fileId}/chunk_{index} konumuna yazılır. "<index>:<savedSize>" döndürür. Tüm parçalar geldikten sonra, son dosyayı birleştirmek için mergeChunks GraphQL mutasyonunu çağırın.

bash
curl --request POST \
  --url http://192.168.1.100:8080/upload_chunk \
  --header 'c-id: <client-id>' \
  --form 'info=<encrypted-chunk-info-bytes>;type=application/octet-stream' \
  --form 'file=@/path/to/chunk_0.bin'
http

GET /zip/dir

Tek bir dizini zip arşivi olarak akıtın. id sorgu parametresi bir dizin yoluna çözülür. Cihazda aynı anda yalnızca bir zip işlemi çalışır — eşzamanlı istekler HTTP 429 alır.

bash
curl 'http://192.168.1.100:8080/zip/dir?id=<encrypted-dir-id>' \
  -o folder.zip
http

GET /zip/files

Birden fazla dosyayı (veya medya arama sonuçlarını) tek bir zip olarak akıtın. id, { type, query, id, name } değerine çözülür. FILE tipi için dosya listesi files() GraphQL sorgusu tarafından TempHelper içinde request.id altında saklanır; medya tipleri için sunucu searchZipItems(type, query, id) çalıştırır.

bash
curl 'http://192.168.1.100:8080/zip/files?id=<encrypted-request>' \
  -o selection.zip
http

GET /media/{id}

DLNA medya uç noktası. Daha önce kaydedilmiş bir medya yolunu (UrlHelper.getMediaHttpUrl ile kaydedilmiş) bir TV / DLNA renderer'ına sunar. URL kaynakları vekil sunulur, content:// URI'leri akıtılır, görseller olduğu gibi sunulur ve diğer tüm dosyalar renderer'ların akışı kabul etmesi için DLNA'ya özgü başlıklar + HTTP 206 range desteğiyle sunulur.

bash
# Play on a DLNA renderer:
curl http://192.168.1.100:8080/media/<id>.mp4 -o video.mp4
http

NOTIFY /callback/cast

DLNA renderer geri araması. Renderer'ın olay NOTIFY XML'ini alır ve CastPlayer durumunu günceller. TransportState=STOPPED'da (AVTransportURIMetaData olmadan) oynatıcı otomatik olarak çalma listesindeki bir sonraki öğeye geçer. Konum güncellemeleri için RelTime / TrackDuration'ı da ayrıştırır.

bash
# Sent by the DLNA renderer (not by the client):
NOTIFY /callback/cast HTTP/1.1
Content-Type: text/xml

<?xml ...><e:propertyset>...TransportState val="PLAYING"...</e:propertyset>
http

GET /health

Kimlik doğrulaması gerektirmeyen sağlık kontrolü uç noktası. Uygulama paketi adını düz metin olarak döndürür. HTTP sunucusunun erişilebilir olduğunu doğrulamak için bunu kullanın.

bash
curl http://192.168.1.100:8080/health
http

GET /shutdown

HTTP sunucusunu kapatır. Yalnızca localhost'tan çağrılabilir — uzak istekler HTTP 403 alır. Tüm WebSocket oturumlarını kapatır, çevrimiçi istemci setini temizler ve HTTP sunucusunu dispose eder.

bash
# Must be run on the device (e.g. via adb shell):
curl http://localhost:8080/shutdown
http

POST /init

Bir istemci oturumu başlatır. c-id başlığı gerektirir. Geçerli bir şifrelenmiş gövde mevcutsa (önbelleğe alınmış token ile çözülür), oturum kimliği doğrulanmış sayılır ve sunucu 200 yanıtlar. Aksi takdirde: parola ayarlanmadıysa, sunucu yeni sıfırlanmış bir parolayla yanıt verir (200); parola ayarlanmışsa, 204 No Content yanıt verir ve istemci WebSocket giriş akışı üzerinden kimlik doğrulaması yapmalıdır.

bash
curl --request POST \
  --url http://192.168.1.100:8080/init \
  --header 'c-id: <client-id>' \
  --data-binary '<encrypted-token-bytes>'
http

WS /

Ana WebSocket uç noktası. Bir oturum kaydetmek için ?cid=<client-id> kullanın; ilk binary çerçeve şifrelenmiş bir timestamp (veya ?auth=1 ile parolayı içeren şifrelenmiş bir AuthRequest) olmalıdır. Kimlik doğrulamadan sonra sunucu, bu soket üzerinden şifrelenmiş olay çerçeveleri (bildirimler, sohbet güncellemeleri vb.) gönderir.

bash
# Browser / JS example
const ws = new WebSocket('ws://192.168.1.100:8080/?cid=<client-id>')
ws.binaryType = 'arraybuffer'
ws.send(encryptWithToken(token, Date.now().toString()))

// Login variant:
const ws = new WebSocket('ws://192.168.1.100:8080/?cid=<client-id>&auth=1')
ws.send(encryptWithPassword(password, JSON.stringify({ password: hash })))
http

WS /status

Peer varlık WebSocket'i. Eşleştirilmiş bir peer'ı çevrimiçi olarak işaretli tutmak için ?cid=<peer-id> kullanın. İlk binary çerçeve PeerChatParser ile şifrelenmiş bir istek olmalıdır; başarı durumunda sunucu "ok" metni gönderir ve soket kapanana kadar peer'ı çevrimiçi olarak işaretler.

bash
# Peer-to-peer keepalive (typically opened automatically by the chat
# client after pairing — not usually invoked manually)
const ws = new WebSocket('ws://192.168.1.100:8080/status?cid=<peer-id>')
ws.send(peerEncryptedFrame)