Страница што одговара за 200 ms кон локален Redis трае четири секунди штом клиентот седне зад VPN, додека бројачите на серверот остануваат неактивни. Бавниот дневник не покажува ништо над милисекунда, графиконот на CPU е рамен, а инстанцата без поплаки им служи на други клиенти. Она што се промени е далечината, а она што ја множи далечината е бројот на пати кога вашиот код запира и чека. Поминете ја патеката на барањето од клиентот кон надвор и решението речиси секогаш е помалку последователни чекања, а не побрз сервер.

Започнете од клиентот, а не од метриките на серверот

Набљудувајте го процесот на клиентот помеѓу првата и последната команда. Ако трагата покажува одговор, пауза, а потоа следната команда, плаќате целосно кружно патување по команда и никакво подесување на серверот тоа нема да го промени. Бавниот дневник е погрешен инструмент тука, зашто го запишува времето на извршување и намерно го исклучува комуникацискиот I/O. Чист бавен дневник до бавна крајна точка е потписот на проблем со кружни патувања.

Измерете ја самата патека пред да допрете код. redis-cli -h redis.example.internal --latency испраќа повторувачки PING и го печати просечното време на барање и одговор, што е вашата цена по размена. Помножете го тоа со бројот на последователни команди во едно дејство на корисникот и имате долна граница за крајната точка.

Избројте ги кружните патувања што навистина и се потребни на една корисничка акција

Земете една крајна точка и запишете го секој Redis повик по ред, вклучно тие скриени во ORM, меѓу-програм за сесија или пребарување на функциско знаменце. Повеќето бавни крајни точки прават дваесет или триесет повици каде што три би биле доволни, а скриените обично се мнозинство.

Синџирот на зависности не може да се свитка: ако втората команда го бара клучот што го враќа првата, чекањето е вистинско и единствените опции се друг модел на податоци или серверска операција што го изразува целиот чекор одеднаш. Независните читања се друг случај, зашто ништо не ве принудува да го чекате првиот одговор пред да го испратите вториот. Означете го секој повик како зависен или независен пред да промените нешто, и формата на решението станува очигледна.

Бројот што е важен се последователните чекања, не вкупните команди. Триесет команди во една серија уште чинат едно чекање.

Во серија ставајте само команди што не зависат една од друга

Цевководот ги става независните команди во ред и ги собира одговорите по редослед, претворајќи N чекања во едно. Повеќето клиенти го нудат како блок, повратен повик или менаџер на контекст наместо како посебен режим на врска, затоа проверете го API-то што го нуди вашата инсталирана верзија. Добивката расте со времето на кружното патување, и токму затоа е важна на VPN и едвај се забележува на localhost.

import redis

r = redis.Redis(host="redis.example.internal", port=6379, socket_timeout=2)
pipe = r.pipeline(transaction=False)
for key in ("user:1001", "user:1002", "user:1003"):
    pipe.get(key)
print(pipe.execute())

Предадете transaction=False кога сакате само серии. Стандардно клиентот ја завиткува серијата во MULTI и EXEC, што ја прави атомска и менува што другите клиенти можат да забележат во лет. Атомичноста е одлука за точност, а не лост за перформанси, и цевководот не е трансакција само затоа што двете ги намалуваат кружните патувања.

Читајте го секој одговор, а не само поднесувањето на серијата. Команда во редот може да врати грешка додека серијата како целина се довршува, а клиент што ја фрла листата одговори ја претвора неуспешната запишување во тивка. Споредете ја должината на листата одговори со бројот на команди што сте ги ставиле во ред.

Држете ја врската жива помеѓу дејствата

Секоја нова врска плаќа за разрешување имиња, TCP ракување, TLS ракување и AUTH, а преку VPN секое од нив е кружно патување што не можете да го сериите. Создајте го клиентот еднаш по процес и користете го повторно, или користете го базенот што го нуди вашата библиотека со ограничен размер. Повторното поврзување по барање е втората најчеста причина за овој симптом по чекањата по команда.

Држете го приватното име на домаќин во конфигурацијата наместо буквална адреса. Проверката на сертификат и идентитетот на услугата уште важат на приватна мрежа, а прицврстувањето на IP се крши во моментот кога провајдерот ја пренумерира подмрежата. Ако разрешувањето е бавниот дел, поправете ја патеката на резолверот, а не низата за поврзување.

Поставете експлицитен таймаут на сокетот за заглавен тунел брзо да пропадне наместо да го обеси работникот. Потоа потврдете дека базенот навистина се користи повторно со евидентирање на создавањето врски во клиентот.

Одредете ја големината на серијата пред да стане проблем со меморија

Redis ги држи одговорите во редот за целото времетраење на серијата, а клиентот потоа го држи анализираниот резултат. Цевковод од десет илјади големи вредности ги заменува мрежните чекања со мемориски скокови и долги паузи на двата краја.

Изберете големина на серијата според обемот на одговорот, а не според бројот на команди. Неколку стотини мали команди во една серија обично се удобни, додека стотина повеќекилобајтни товари не се. Делете по бајти и по број, и држете ја секоја серија во буџетот за латентност што крајната точка навистина го има.

Измерете од крај до крај по промената: redis-cli -h redis.example.internal --latency-history покажува дали самата патека е стабилна, а вашиот сопствен тајмер за барања покажува дали крајната точка се подобрила. Ако крајната точка уште е бавна додека историјата на латентност е рамна, преостанатиот трошок е работа на серверот или вашата сопствена серијализација, и следниот чекор е профил на обработувачот, а не уште една промена на сериите.

Поврзани статии