Перейти к содержанию

API для Pawn-плагинов#

Python-плагин может отдавать свои нативы и форварды Pawn-плагинам. amxpyc генерирует для них .inc, и Pawn-плагин работает с ними как с любым другим модулем.

Нативы#

from amxpy import Player, Router

from .state import vips

router = Router()


@router.native
def vip_is_user_vip(player: Player) -> bool:
    """Является ли игрок VIP."""
    return player in vips


@router.native("vip_days")             # имя для Pawn отличается от имени функции
def days_left(player: Player) -> int:
    """Сколько дней VIP осталось: -1 — навсегда, 0 — не VIP."""
    vip = vips.get(player)
    return vip.days_left if vip else 0
  • Типы параметров — int, float, bool, str, Player; результат — они же или None. Без аннотаций натив не соберётся (AMX201).
  • Натив не может быть async: Pawn ждёт ответ сразу.
  • Docstring попадает в .inc комментарием.

Форварды#

vip_granted = router.forward("vip_granted", player=Player, days=int)

...
vip_granted.emit(player, 30)          # разослать Pawn- и Python-подписчикам

emit возвращает ответ Pawn-обработчиков (0, если их нет). Python-плагины подписываются на форвард через @plugin.on_forward — и получают его сразу, без смены карты.

Сгенерированный .inc#

amxpy build кладёт .inc в dist/include/, а amxpy deploy — в addons/amxmodx/scripting/include/ на сервере. Для VIP-примера:

vip.inc
// VIP: natives and forwards of the amxpy plugin "vip".
// Generated by amxpyc - do not edit.

#if defined _vip_included
    #endinput
#endif
#define _vip_included

#pragma reqlib vip

/**
 * Является ли игрок VIP.
 */
native bool:vip_is_user_vip(player);

/**
 * Сколько дней VIP осталось: -1 — навсегда, 0 — не VIP.
 */
native vip_days_left(player);

forward vip_granted(player, days);

Pawn-плагин подключает его как обычно:

#include <amxmodx>
#include <vip>

public plugin_init() {
    register_clcmd("say /status", "status");
}

public status(id) {
    if (vip_is_user_vip(id))
        client_print(id, print_chat, "VIP: %d дн.", vip_days_left(id));
}

public vip_granted(player, days) {
    client_print(player, print_chat, "Вам выдан VIP на %d дн.", days);
}

#pragma reqlib vip гарантирует, что Pawn-плагин загрузится только вместе с плагином amxpy.

Новые нативы — после рестарта сервера

AMXX принимает нативы модуля только при его подключении. Новый натив или смена сигнатуры заработают в Pawn после рестарта; тело натива можно менять горячей перезагрузкой. Подробнее — Горячая перезагрузка.

В тестах#

assert server.native("vip_is_user_vip", bob) == 1      # как вызвал бы Pawn-плагин
assert server.forwards[-1] == ("vip_granted", (bob.index, 30))