1. Go to this page and download the library: Download centralnic-reseller/php-sdk library. Choose the download type require.
2. Extract the ZIP file and open the index.php.
3. Add this code to the index.php.
<?php
require_once('vendor/autoload.php');
/* Start to develop here. Best regards https://php-download.com/ */
centralnic-reseller / php-sdk example snippets
use CNIC\ClientFactory;
// --- CNR (CentralNic Reseller, fka RRPproxy) ---
$cl = ClientFactory::cnr(); // returns a fully-typed CNR\Client
$cl->useOTESystem() // omit for LIVE (the default)
->setCredentials($user, $password); // or ->setRoleCredentials($acct, $role, $pw)
// CNR has one fixed script path, so request() defaults it — pass a command only.
$r = $cl->request(["COMMAND" => "StatusAccount"]);
if ($r->isSuccess()) {
print_r($r->getHash());
}
$cl->close(); // release the cached cURL handle
// --- IBS / Moniker (JSON API) ---
$cl = ClientFactory::ibs(); // or ClientFactory::moniker()
$cl->useOTESystem()->setCredentials($user, $password);
// This platform exposes many endpoints under one host and the *path* selects the
// operation, so pass it as the second argument — there is no default that works.
$r = $cl->request(["domain" => "example.com"], "Domain/Check");
if ($r->isSuccess()) {
print_r($r->getHash());
}
$cl->close();
use CNIC\ClientFactory;
use CNIC\CNR\SocketConfig;
$cfg = new SocketConfig();
$testMode ? $cfg->useOTESystem() : $cfg->useLIVESystem();
$cfg->setLogin($user)
->setPassword($password) // or ->setSession($sessionId) to resume a session
->setSocketTimeout(60);
$cl = ClientFactory::cnr($cfg); // correct the moment it exists
$r = $cl->request(["COMMAND" => "QueryDomainList", "LIMIT" => "100"]);
foreach ($r as $index => $rec) {
echo $index, ": ", $rec->getStringByKey("DOMAIN"), "\n";
}
$r->getRecord(0); // ?RecordInterface — by index, or null if out of range
$r->getRecords(); // RecordInterface[] — the whole list
$r->getColumn("DOMAIN"); // ?ColumnInterface — column-wise instead of row-wise
$r->getColumnKeys(); // string[] — the data columns, in wire order
> $total = $r->getRecordsTotalCount(); // ?int — was $data["TOTAL"]
> $limit = $r->getRecordsLimitation(); // ?int — was $data["LIMIT"]
> $first = $r->getFirstRecordIndex(); // ?int — was $data["FIRST"]
> $last = $r->getLastRecordIndex(); // ?int — was $data["LAST"]
>
// QueryEventList over an empty window — the response carries property[column],
// property[events count] and property[events total], but no property[event].
$r->getRecordsCount(); // 1
$r->getRecord(0)->getData(); // ["COLUMN" => "event", "EVENTSCOUNT" => "0", "EVENTSTOTAL" => "0"]
foreach ($r as $rec) {
$event = $rec->getStringByKey("EVENT");
if ($event === null) {
continue; // a row carrying no EVENT is not an event
}
// … handle $event
}
$pg = $r->getPagination();
$pg->getCurrentPageNumber(); // ?int — null if this response is not a paginated list
$pg->getNumberOfPages(); // int
$pg->hasNextPage(); // bool
$pg->getNextPageNumber(); // ?int — null on the last page
$pg->hasPreviousPage();
$pg->getPreviousPageNumber();
$pg->toArray(); // COUNT / CURRENTPAGE / FIRST / LAST / LIMIT / NEXTPAGE / PAGES / PREVIOUSPAGE / TOTAL
use CNIC\LogSinkInterface;
// 1. Keep the brand's format, change the destination.
final class FileSink implements LogSinkInterface
{
public function __construct(private readonly string $path) {}
public function write(string $message): void
{
file_put_contents($this->path, $message . PHP_EOL, FILE_APPEND);
}
}
$cl->enableDebugMode()->setLogSink(new FileSink("/var/log/cnic.log"));
// 2. Change the format too: extend CNIC\AbstractLogger and implement one
// method — the sink wiring comes with it.
final class MyLogger extends \CNIC\AbstractLogger
{
#[\Override]
public function format(string $post, \CNIC\ResponseInterface $response, ?string $error = null): string
{
return sprintf("[%d] %s\n", $response->getCode(), $post);
}
}
$cl->setCustomLogger(new MyLogger(new FileSink("/var/log/cnic.log")));
use CNIC\TransportInterface;
final class CannedTransport implements TransportInterface
{
public function __construct(private readonly string $raw) {}
/**
* @param array<int, mixed> $options
* @return array{0: string, 1: string|null}
*/
public function post(string $url, string $data, int $timeoutSeconds, string $userAgent, array $options = []): array
{
return [$this->raw, null]; // element [1] is the transport error; non-null means [0] is unusable
}
public function close(): void {}
}
$cl->setTransport(new CannedTransport("[RESPONSE]\r\nCODE=200\r\nDESCRIPTION=Command completed successfully\r\nEOF\r\n"));
$r = $cl->request(["COMMAND" => "StatusAccount"]); // no network touched
$transport = new CannedTransport($raw);
assert($cl->setTransport($transport)->getTransport() === $transport);
assert($cl->setCustomLogger($myLogger)->getLogger() === $myLogger);
ApiDateTime::tryFrom(null); // null
ApiDateTime::tryFrom("2026-02-30"); // null — refused, not coerced
> (new \DateTimeImmutable("@{$dt->ts}"))->setTimezone(new \DateTimeZone("Europe/Berlin"));
>
$rec = $response->getRecord(0);
$expiry = $rec?->getDateTimeByKey("expirationdate"); // ?ApiDateTime — works for "-" or "/" input
$expiry?->date; // "2030-07-17"
$expiry?->isDateOnly(); // true
$col = $response->getColumn("expirationdate");
$col?->getDateTimeByIndex(0); // same parsing, by column index instead of record key