Skip to content
Snippets Groups Projects

Compare revisions

Changes are shown as if the source revision was being merged into the target revision. Learn more about comparing revisions.

Source

Select target project
No results found

Target

Select target project
  • awit-whmcs/whmcs-coza-epp
  • weheartwebsites/whmcs-coza-epp
  • qbitza/whmcs-coza-epp
  • wyrie/whmcs-coza-epp
  • Woklet/whmcs-coza-epp
  • jaymcc/whmcs-coza-epp
  • cmcawood/whmcs-coza-epp
7 results
Show changes
Showing
with 2611 additions and 0 deletions
......@@ -24,52 +24,110 @@
* @revision $Id: Protocol.php,v 1.4 2011/06/28 09:48:02 gavin Exp $
*/
require_once('PEAR.php');
/**
* Low-level functions useful for both EPP clients and servers
* @package Net_EPP
*/
class Net_EPP_Protocol {
/**
* get an EPP frame from the remote peer
* @param resource $socket a socket connected to the remote peer
* @return PEAR_Error|string either an error or a string
*/
static function getFrame($socket) {
if (@feof($socket)) return new PEAR_Error('connection closed (socket is EOF)');
$hdr = @fread($socket, 4);
if (empty($hdr) && feof($socket)) {
return new PEAR_Error('connection closed (no header received and socket is EOF)');
static function _fread_nb($socket,$length) {
$result = '';
// Loop reading and checking info to see if we hit timeout
$info = stream_get_meta_data($socket);
$time_start = microtime(true);
while (!$info['timed_out'] && !feof($socket)) {
// Try read remaining data from socket
$buffer = @fread($socket,$length - strlen($result));
// If the buffer actually contains something then add it to the result
if ($buffer !== false) {
$result .= $buffer;
// If we hit the length we looking for, break
if (strlen($result) == $length) {
break;
}
} else {
// Sleep 0.25s
usleep(250000);
}
// Update metadata
$info = stream_get_meta_data($socket);
$time_end = microtime(true);
if (($time_end - $time_start) > 10) {
throw new exception('Timeout while reading from EPP Server');
}
}
// Check for timeout
if ($info['timed_out']) {
throw new Exception('Timeout while reading data from socket');
}
} elseif (false === $hdr) {
return new PEAR_Error('Error reading from peer: '.$php_errormsg);
return $result;
}
} else {
$unpacked = unpack('N', $hdr);
$length = $unpacked[1];
if ($length < 5) {
return new PEAR_Error(sprintf('Got a bad frame header length of %d bytes from peer', $length));
static function _fwrite_nb($socket,$buffer,$length) {
// Loop writing and checking info to see if we hit timeout
$info = stream_get_meta_data($socket);
$time_start = microtime(true);
$pos = 0;
while (!$info['timed_out'] && !feof($socket)) {
// Some servers don't like alot of data, so keep it small per chunk
$wlen = $length - $pos;
if ($wlen > 1024) { $wlen = 1024; }
// Try write remaining data from socket
$written = @fwrite($socket,substr($buffer,$pos),$wlen);
// If we read something, bump up the position
if ($written && $written !== false) {
$pos += $written;
// If we hit the length we looking for, break
if ($pos == $length) {
break;
}
} else {
$length -= 4; // discard the length of the header itself
// Sleep 0.25s
usleep(250000);
}
// Update metadata
$info = stream_get_meta_data($socket);
$time_end = microtime(true);
if (($time_end - $time_start) > 10) {
throw new exception('Timeout while writing to EPP Server');
}
}
// Check for timeout
if ($info['timed_out']) {
throw new Exception('Timeout while writing data to socket');
}
// sometimes the socket can be buffered with a limit below the frame
// length, so we continually read from the socket until we get the full frame:
$frame = '';
while (strlen($frame) < $length) $frame .= fread($socket, ($length));
return $pos;
}
if (strlen($frame) > $length) {
return new PEAR_Error(sprintf("Frame length (%d bytes) doesn't match header (%d bytes)", strlen($frame), ($length)));
/**
* get an EPP frame from the remote peer
* @param resource $socket a socket connected to the remote peer
* @throws Exception on frame errors.
* @return string the frame
*/
static function getFrame($socket) {
// Read header
$hdr = Net_EPP_Protocol::_fread_nb($socket,4);
if (strlen($hdr) < 4) {
throw new Exception(sprintf('Short read of %d bytes from peer', strlen($hdr)));
}
} else {
return $frame;
// Unpack first 4 bytes which is our length
$unpacked = unpack('N', $hdr);
$length = $unpacked[1];
if ($length < 5) {
throw new Exception(sprintf('Got a bad frame header length of %d bytes from peer', $length));
}
}
} else {
$length -= 4; // discard the length of the header itself
// Read frame
return Net_EPP_Protocol::_fread_nb($socket,$length);
}
}
......@@ -77,8 +135,18 @@ class Net_EPP_Protocol {
* send an EPP frame to the remote peer
* @param resource $socket a socket connected to the remote peer
* @param string $xml the XML to send
* @throws Exception when it doesn't complete the write to the socket
* @return the amount of bytes written to the frame
*/
static function sendFrame($socket, $xml) {
fwrite($socket, pack('N', (strlen($xml)+4)).$xml);
// Grab XML length & add on 4 bytes for the counter
$length = strlen($xml) + 4;
$res = Net_EPP_Protocol::_fwrite_nb($socket, pack('N',$length) . $xml,$length);
// Check our write matches
if ($length != $res) {
throw new Exception("Short write when sending XML");
}
return $res;
}
}
<?php
# Copyright (c) 2012-2018, AllWorldIT
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
# Official Website:
# http://devlabs.linuxassist.net/projects/whmcs-coza-epp
# Lead developer:
# Nigel Kukard <nkukard@lbsd.net>
# ! ! P L E A S E N O T E ! !
# * If you make changes to this file, please consider contributing
# anything useful back to the community. Don't be a sour prick.
# * If you find this module useful please consider making a
# donation to support modules like this.
# WHMCS hosting, theming, module development, payment gateway
# integration, customizations and consulting all available from
# http://allworldit.com
# Make sure we not being accssed directly
if (!defined("WHMCS"))
die("This file cannot be accessed directly");
# Configuration array
function cozaepp_getConfigArray() {
$configarray = array(
"Username" => array( "Type" => "text", "Size" => "20", "Description" => "Enter your username here" ),
"Password" => array( "Type" => "password", "Size" => "20", "Description" => "Enter your password here" ),
"SSL" => array( "Type" => "yesno" ),
"Certificate" => array( "Type" => "text", "Description" => "Path of certificate .pem" )
);
return $configarray;
}
function cozaepp_AdminCustomButtonArray() {
$buttonarray = array(
"Approve Transfer" => "ApproveTransfer",
"Cancel Transfer Request" => "CancelTransferRequest",
"Reject Transfer" => "RejectTransfer",
"Recreate Contact" => "RecreateContact",
);
return $buttonarray;
}
# Function to return current nameservers
function cozaepp_GetNameservers($params) {
# Grab variables
$sld = $params["sld"];
$tld = $params["tld"];
$domain = strtolower("$sld.$tld");
# Get client instance
try {
$client = _cozaepp_Client($domain);
# Get list of nameservers for domain
$result = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:info>
<domain:info xsi:schemaLocation="urn:ietf:params:xml:ns:domain-1.0 domain-1.0.xsd">
<domain:name hosts="all">'.$domain.'</domain:name>
</domain:info>
</epp:info>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc = new DOMDocument();
$doc->loadXML($result);
logModuleCall('Cozaepp', 'GetNameservers', $xml, $result);
# Pull off status
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check the result is ok
if($coderes != '1000') {
$values["error"] = "GetNameservers/domain-info($domain): Code ($coderes) $msg";
return $values;
}
# Grab hostname array
$ns = $doc->getElementsByTagName('hostName');
# Extract nameservers & build return result
$i = 1; $values = array();
foreach ($ns as $nn) {
$values["ns{$i}"] = $nn->nodeValue;
$i++;
}
$values["status"] = $msg;
} catch (Exception $e) {
$values["error"] = 'GetNameservers/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
# Function to save set of nameservers
function cozaepp_SaveNameservers($params) {
# Grab variables
$sld = $params["sld"];
$tld = $params["tld"];
$domain = strtolower("$sld.$tld");
# Generate XML for nameservers
if ($nameserver1 = $params["ns1"]) {
$add_hosts = '
<domain:hostAttr>
<domain:hostName>'.$nameserver1.'</domain:hostName>
</domain:hostAttr>
';
}
if ($nameserver2 = $params["ns2"]) {
$add_hosts .= '
<domain:hostAttr>
<domain:hostName>'.$nameserver2.'</domain:hostName>
</domain:hostAttr>
';
}
if ($nameserver3 = $params["ns3"]) {
$add_hosts .= '
<domain:hostAttr>
<domain:hostName>'.$nameserver3.'</domain:hostName>
</domain:hostAttr>
';
}
if ($nameserver4 = $params["ns4"]) {
$add_hosts .= '
<domain:hostAttr>
<domain:hostName>'.$nameserver4.'</domain:hostName>
</domain:hostAttr>';
}
if ($nameserver5 = $params["ns5"]) {
$add_hosts .= '
<domain:hostAttr>
<domain:hostName>'.$nameserver5.'</domain:hostName>
</domain:hostAttr>';
}
# Get client instance
try {
$client = _cozaepp_Client($domain);
# Grab list of current nameservers
$request = $client->request( $xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:info>
<domain:info xsi:schemaLocation="urn:ietf:params:xml:ns:domain-1.0 domain-1.0.xsd">
<domain:name hosts="all">'.$domain.'</domain:name>
</domain:info>
</epp:info>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'SaveNameservers', $xml, $request);
# Pull off status
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check if result is ok
if($coderes != '1000') {
$values["error"] = "SaveNameservers/domain-info($domain): Code ($coderes) $msg";
return $values;
}
$values["status"] = $msg;
# Generate list of nameservers to remove
$hostlist = $doc->getElementsByTagName('hostName');
foreach ($hostlist as $host) {
$rem_hosts .= '
<domain:hostAttr>
<domain:hostName>'.$host->nodeValue.'</domain:hostName>
</domain:hostAttr>
';
}
# Build request
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xmlns:cozadomain="http://co.za/epp/extensions/cozadomain-1-0"
xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:update>
<domain:update>
<domain:name>'.$domain.'</domain:name>
<domain:add>
<domain:ns>'.$add_hosts.' </domain:ns>
</domain:add>
<domain:rem>
<domain:ns>'.$rem_hosts.'</domain:ns>
</domain:rem>
</domain:update>
</epp:update>
<epp:extension>
<cozadomain:update xsi:schemaLocation="http://co.za/epp/extensions/cozadomain-1-0 coza-domain-1.0.xsd">
<cozadomain:chg><cozadomain:autorenew>false</cozadomain:autorenew></cozadomain:chg></cozadomain:update>
</epp:extension>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'SaveNameservers', $xml, $request);
# Pull off status
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check if result is ok
if($coderes != '1001') {
$values["error"] = "SaveNameservers/domain-update($domain): Code ($coderes) $msg";
return $values;
}
$values['status'] = "Domain update Pending. Based on .co.za policy, the estimated time taken is around 5 days.";
} catch (Exception $e) {
$values["error"] = 'SaveNameservers/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
# NOT IMPLEMENTED
function cozaepp_GetRegistrarLock($params) {
# Grab variables
$sld = $params["sld"];
$tld = $params["tld"];
$domain = strtolower("$sld.$tld");
# Get lock status
$lock = 0;
if ($lock=="1") {
$lockstatus="locked";
} else {
$lockstatus="unlocked";
}
return $lockstatus;
}
# NOT IMPLEMENTED
function cozaepp_SaveRegistrarLock($params) {
$values["error"] = "SaveRegistrarLock: Current co.za policy does not allow for the addition of client-side statuses on domains.";
return $values;
}
# Function to retrieve an available contact id
function _cozaepp_CheckContact($domain,$type) {
$prehash = $domain . time() . rand(0, 1000000) . $type;
$contactid = substr(md5($prehash), 0,15);
# Get client instance and check for available contact id
try {
$client = _cozaepp_Client($domain);
$contactAvailable = 0;
$count = 0;
while ($contactAvailable == 0) {
# Check if contact exists
$request = $client->request($xml = '
<epp xmlns="urn:ietf:params:xml:ns:epp-1.0">
<command>
<check>
<contact:check xmlns:contact="urn:ietf:params:xml:ns:contact-1.0">
<contact:id>'.$contactid.'</contact:id>
</contact:check>
</check>
</command>
</epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'RegisterDomain:CheckContact', $xml, $request);
# Pull off status
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$contactAvailable = $doc->getElementsByTagName('id')->item(0)->getAttribute('avail');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes == '1000') {
$values['contact'] = 'Contact Created';
} else if($coderes == '2302') {
$values['contact'] = 'Contact Already exists';
} else if($coderes == '2201') {
$values['contact'] = 'Contact Already exists and is not owned by you';
} else {
$values["error"] = "RegisterDomain/contact-check($contactid): Code ($coderes) $msg";
return $values;
}
$values["status"] = $msg;
# If contact still isn't available attempt to add a random time again rehash and return
if ($contactAvailable == 0) {
$contactAvailable = substr(md5($prehash . time() . rand(0, 1000000) . $count), 0,15);
}
if ($count >= 10) {
break;
}
$count++;
}
return $contactid;
} catch (Exception $e) {
$values["error"] = 'RegisterDomain/EPP: '.$e->getMessage();
return $values;
}
}
# Function to register domain
function cozaepp_RegisterDomain($params) {
# Grab varaibles
$sld = $params["sld"];
$tld = $params["tld"];
$domain = strtolower("$sld.$tld");
$regperiod = $params["regperiod"];
# Get registrant details
$RegistrantFirstName = $params["firstname"];
$RegistrantLastName = $params["lastname"];
$RegistrantAddress1 = $params["address1"];
$RegistrantAddress2 = $params["address2"];
$RegistrantCity = $params["city"];
$RegistrantStateProvince = $params["state"];
$RegistrantPostalCode = $params["postcode"];
$RegistrantCountry = $params["country"];
$RegistrantEmailAddress = $params["email"];
$RegistrantPhone = $params["fullphonenumber"];
# Get admin details
$AdminFirstName = $params["adminfirstname"];
$AdminLastName = $params["adminlastname"];
$AdminAddress1 = $params["adminaddress1"];
$AdminAddress2 = $params["adminaddress2"];
$AdminCity = $params["admincity"];
$AdminStateProvince = $params["adminstate"];
$AdminPostalCode = $params["adminpostcode"];
$AdminCountry = $params["admincountry"];
$AdminEmailAddress = $params["adminemail"];
$AdminPhone = $params["adminfullphonenumber"];
# Registrar contactid hash
$contactid = substr(md5($domain), 0,15);
# Admin/Tech/Billing contactid hash
$additional_contactid = substr(md5($AdminFirstName.$AdminLastName), 0,15);
# Generate XML for namseverss
if ($nameserver1 = $params["ns1"]) {
$add_hosts = '
<domain:hostAttr>
<domain:hostName>'.$nameserver1.'</domain:hostName>
</domain:hostAttr>
';
}
if ($nameserver2 = $params["ns2"]) {
$add_hosts .= '
<domain:hostAttr>
<domain:hostName>'.$nameserver2.'</domain:hostName>
</domain:hostAttr>
';
}
if ($nameserver3 = $params["ns3"]) {
$add_hosts .= '
<domain:hostAttr>
<domain:hostName>'.$nameserver3.'</domain:hostName>
</domain:hostAttr>
';
}
if ($nameserver4 = $params["ns4"]) {
$add_hosts .= '
<domain:hostAttr>
<domain:hostName>'.$nameserver4.'</domain:hostName>
</domain:hostAttr>
';
}
if ($nameserver5 = $params["ns5"]) {
$add_hosts .= '
<domain:hostAttr>
<domain:hostName>'.$nameserver5.'</domain:hostName>
</domain:hostAttr>
';
}
# Get client instance
try {
$client = _cozaepp_Client($domain);
# registry.net.za expects 'coza' as the password
$pw = "coza";
# Send registration
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:contact="urn:ietf:params:xml:ns:contact-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:create>
<contact:create xsi:schemaLocation="urn:ietf:params:xml:ns:contact-1.0 contact-1.0.xsd">
<contact:id>'.$contactid.'</contact:id>
<contact:postalInfo type="loc">
<contact:name>'.$RegistrantFirstName.' '.$RegistrantLastName.'</contact:name>
<contact:addr>
<contact:street>'.$RegistrantAddress1.'</contact:street>
<contact:street>'.$RegistrantAddress2.'</contact:street>
<contact:city>'.$RegistrantCity.'</contact:city>
<contact:sp>'.$RegistrantStateProvince.'</contact:sp>
<contact:pc>'.$RegistrantPostalCode.'</contact:pc>
<contact:cc>'.$RegistrantCountry.'</contact:cc>
</contact:addr>
</contact:postalInfo>
<contact:voice>'.$RegistrantPhone.'</contact:voice>
<contact:fax></contact:fax>
<contact:email>'.$RegistrantEmailAddress.'</contact:email>
<contact:authInfo>
<contact:pw>'.$pw.'</contact:pw>
</contact:authInfo>
</contact:create>
</epp:create>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'RegisterDomain', $xml, $request);
# Pull off status
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes == '1000') {
$values['contact'] = 'Contact Created';
} else if($coderes == '2302') {
$values['contact'] = 'Contact Already exists';
} else {
$values["error"] = "RegisterDomain/contact-create($contactid): Code ($coderes) $msg";
return $values;
}
$values["status"] = $msg;
$domaincreate = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xmlns:cozadomain="http://co.za/epp/extensions/cozadomain-1-0"
xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:create>
<domain:create xsi:schemaLocation="urn:ietf:params:xml:ns:domain-1.0 domain-1.0.xsd">
<domain:name>'.$domain.'</domain:name>
<domain:ns>'.$add_hosts.'</domain:ns>
<domain:registrant>'.$contactid.'</domain:registrant>';
# Some SLDs require the presence of admin, billing and tech contacts.
# Check if our domain has the requirement and get/create the required contact id.
$_server = _cozaepp_SldLookup($domain);
if ($_server['additional_contacts']) {
# Generate a random password to be used for the additional contact
$pw = substr(md5($domain . time() . rand(0, 1000000)), 0,15);
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:contact="urn:ietf:params:xml:ns:contact-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:create>
<contact:create xsi:schemaLocation="urn:ietf:params:xml:ns:contact-1.0 contact-1.0.xsd">
<contact:id>'.$additional_contactid.'</contact:id>
<contact:postalInfo type="loc">
<contact:name>'.$AdminFirstName.' '.$AdminLastName.'</contact:name>
<contact:addr>
<contact:street>'.$AdminAddress1.'</contact:street>
<contact:street>'.$AdminAddress2.'</contact:street>
<contact:city>'.$AdminCity.'</contact:city>
<contact:sp>'.$AdminStateProvince.'</contact:sp>
<contact:pc>'.$AdminPostalCode.'</contact:pc>
<contact:cc>'.$AdminCountry.'</contact:cc>
</contact:addr>
</contact:postalInfo>
<contact:voice>'.$AdminPhone.'</contact:voice>
<contact:fax></contact:fax>
<contact:email>'.$AdminEmailAddress.'</contact:email>
<contact:authInfo>
<contact:pw>'.$pw.'</contact:pw>
</contact:authInfo>
</contact:create>
</epp:create>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'RegisterDomain', $xml, $request);
# Pull off status
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes == '1000') {
$values['contact'] = 'Contact Created';
} else if($coderes == '2302') {
$values['contact'] = 'Contact Already exists';
} else {
$values["error"] = "RegisterDomain/additional-create($additional_contactid): Code ($coderes) $msg";
return $values;
}
$domaincreate .= '
<domain:contact type="admin">'.$additional_contactid.'</domain:contact>
<domain:contact type="tech">'.$additional_contactid.'</domain:contact>
<domain:contact type="billing">'.$additional_contactid.'</domain:contact>';
}
# registry.net.za expects 'coza' as the password
$pw = "coza";
$domaincreate .= '
<domain:authInfo>
<domain:pw>'.$pw.'</domain:pw>
</domain:authInfo>
</domain:create>
</epp:create>
<epp:extension>
<cozadomain:create>
<cozadomain:autorenew>false</cozadomain:autorenew>
</cozadomain:create>
</epp:extension>
</epp:command>
</epp:epp>
';
$request = $client->request($domaincreate);
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'RegisterDomain', $domaincreate, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes != '1000') {
$values["error"] = "RegisterDomain/domain-create($domain): Code ($coderes) $msg";
return $values;
}
$values["status"] = $msg;
} catch (Exception $e) {
$values["error"] = 'RegisterDomain/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
# Function to transfer a domain
function cozaepp_TransferDomain($params) {
# Grab variables
$testmode = $params["TestMode"];
$sld = $params["sld"];
$tld = $params["tld"];
$domain = strtolower("$sld.$tld");
# Domain info
$regperiod = $params["regperiod"];
$transfersecret = $params["transfersecret"];
$nameserver1 = $params["ns1"];
$nameserver2 = $params["ns2"];
# Registrant Details
$RegistrantFirstName = $params["firstname"];
$RegistrantLastName = $params["lastname"];
$RegistrantAddress1 = $params["address1"];
$RegistrantAddress2 = $params["address2"];
$RegistrantCity = $params["city"];
$RegistrantStateProvince = $params["state"];
$RegistrantPostalCode = $params["postcode"];
$RegistrantCountry = $params["country"];
$RegistrantEmailAddress = $params["email"];
$RegistrantPhone = $params["fullphonenumber"];
# Admin details
$AdminFirstName = $params["adminfirstname"];
$AdminLastName = $params["adminlastname"];
$AdminAddress1 = $params["adminaddress1"];
$AdminAddress2 = $params["adminaddress2"];
$AdminCity = $params["admincity"];
$AdminStateProvince = $params["adminstate"];
$AdminPostalCode = $params["adminpostcode"];
$AdminCountry = $params["admincountry"];
$AdminEmailAddress = $params["adminemail"];
$AdminPhone = $params["adminfullphonenumber"];
# Our details
$contactid = substr(md5($domain), 0,15);
# Get client instance
try {
$client = _cozaepp_Client($domain);
# Initiate transfer
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:domain="urn:ietf:params:xml:ns:domain-1.0">
<epp:command>
<epp:transfer op="request">
<domain:transfer>
<domain:name>'.$domain.'</domain:name>
</domain:transfer>
</epp:transfer>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'TransferDomain', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# We should get a 1001 back
if($coderes != '1001') {
$values["error"] = "TransferDomain/domain-transfer($domain): Code ($coderes) $msg";
return $values;
}
} catch (Exception $e) {
$values["error"] = 'TransferDomain/EPP: '.$e->getMessage();
return $values;
}
$values["status"] = $msg;
return $values;
}
# Function to renew domain
function cozaepp_RenewDomain($params) {
# Grab variables
$sld = $params["sld"];
$tld = $params["tld"];
$regperiod = $params["regperiod"];
$domain = strtolower("$sld.$tld");
# Get client instance
try {
$client = _cozaepp_Client($domain);
# Send renewal request
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:info>
<domain:info xsi:schemaLocation="urn:ietf:params:xml:ns:domain-1.0 domain-1.0.xsd">
<domain:name hosts="all">'.$domain.'</domain:name>
</domain:info>
</epp:info>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'RenewDomain', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes != '1000') {
$values["error"] = "RenewDomain/domain-info($domain)): Code ($coderes) $msg";
return $values;
}
$values["status"] = $msg;
# Sanitize expiry date
$expdate = substr($doc->getElementsByTagName('exDate')->item(0)->nodeValue,0,10);
if (empty($expdate)) {
$values["error"] = "RenewDomain/domain-info($domain): Domain info not available";
return $values;
}
# Send request to renew
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:domain="urn:ietf:params:xml:ns:domain-1.0">
<epp:command>
<epp:renew>
<domain:renew>
<domain:name>'.$domain.'</domain:name>
<domain:curExpDate>'.$expdate.'</domain:curExpDate>
</domain:renew>
</epp:renew>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'RenewDomain', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes != '1000') {
$values["error"] = "RenewDomain/domain-renew($domain,$expdate): Code (".$coderes.") ".$msg;
return $values;
}
$values["status"] = $msg;
} catch (Exception $e) {
$values["error"] = 'RenewDomain/EPP: '.$e->getMessage();
return $values;
}
# If error, return the error message in the value below
return $values;
}
function __getContact($contactID,$client = null) {
# Get client instance
try {
if (!isset($client)) {
$client = _cozaepp_Client($domain);
}
# Grab contact info
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:contact="urn:ietf:params:xml:ns:contact-1.0">
<epp:command>
<epp:info>
<contact:info>
<contact:id>'.$contactID.'</contact:id>
</contact:info>
</epp:info>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', '__getContact', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check result
if($coderes != '1000') {
$values["error"] = "__getContact/contact-info($contactID): Code (".$coderes.") ".$msg;
return $values;
}
$nodes = $doc->getElementsByTagName('postalInfo');
for ($i = 0; ($i < $nodes->length); $i++) {
if ($nodes->item($i)->getAttributeNode('type')->nodeValue == 'loc') {
$childNodes = $nodes->item($i);
$results["Contact Name"] = $childNodes->getElementsByTagName('name')->item(0)->nodeValue;
$results["Organisation"] = $childNodes->getElementsByTagName('org')->item(0)->nodeValue;
$results["Address line 1"] = $childNodes->getElementsByTagName('street')->item(0)->nodeValue;
$results["Address line 2"] = $childNodes->getElementsByTagName('street')->item(1)->nodeValue;
$results["TownCity"] = $childNodes->getElementsByTagName('city')->item(0)->nodeValue;
$results["State"] = $childNodes->getElementsByTagName('sp')->item(0)->nodeValue;
$results["Zip code"] = $childNodes->getElementsByTagName('pc')->item(0)->nodeValue;
$results["Country Code"] = $childNodes->getElementsByTagName('cc')->item(0)->nodeValue;
}
}
$results["Phone"] = $doc->getElementsByTagName('voice')->item(0)->nodeValue;
$results["Email"] = $doc->getElementsByTagName('email')->item(0)->nodeValue;
return $results;
} catch (Exception $e) {
$values["error"] = '__getContact/EPP: '.$e->getMessage();
return $values;
}
}
function _getContactDetails($domain, $client = null) {
# Get client instance
try {
if (!isset($client)) {
$client = _cozaepp_Client($domain);
}
# Grab domain info
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:info>
<domain:info xsi:schemaLocation="urn:ietf:params:xml:ns:domain-1.0 domain-1.0.xsd">
<domain:name hosts="all">'.$domain.'</domain:name>
</domain:info>
</epp:info>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', '_GetContactDetails', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check result
if($coderes != '1000') {
$values["error"] = "_GetContactDetails/domain-info($domain): Code (".$coderes.") ".$msg;
return $values;
}
# Grab contact ID's
$registrantContactID = $doc->getElementsByTagName('registrant')->item(0)->nodeValue;
if (empty($registrantContactID)) {
$values["error"] = "_GetContactDetails/domain-info($domain): Registrant contact info not available => $request";
return $values;
}
$contactNodes = $doc->getElementsByTagName('contact');
foreach ($contactNodes as $contactNode) {
# Check if we have found the relevant contact nodes
$type = $contactNode->getAttribute('type');
if ($type == "admin") {
$adminContactID = $contactNode->nodeValue;
} elseif ($type == "tech") {
$techContactID = $contactNode->nodeValue;
} elseif ($type == "billing") {
$billingContactID = $contactNode->nodeValue;
}
}
if (empty($adminContactID)) {
$values["error"] = "_GetContactDetails/domain-info($domain): Admin contact info not available";
return $values;
}
if (empty($techContactID)) {
$values["error"] = "_GetContactDetails/domain-info($domain): Technical contact info not available";
return $values;
}
if (empty($billingContactID)) {
$values["error"] = "_GetContactDetails/domain-info($domain): Billing contact info not available";
return $values;
}
} catch (Exception $e) {
$values["error"] = '_GetContactDetails/EPP: '.$e->getMessage();
return $values;
}
# Grab contacts
$registrantContactInfo = __getContact($registrantContactID,$client);
# If there was an error return it
if (isset($registrantContactInfo["error"])) {
return $registrantContactInfo;
}
$adminContactInfo = __getContact($adminContactID,$client);
# If there was an error return it
if (isset($adminContactInfo["error"])) {
return $adminContactInfo;
}
$techContactInfo = __getContact($techContactID,$client);
# If there was an error return it
if (isset($techContactInfo["error"])) {
return $techContactInfo;
}
$billingContactInfo = __getContact($billingContactID,$client);
# If there was an error return it
if (isset($billingContactInfo["error"])) {
return $billingContactInfo;
}
$results['Registrant'] = $registrantContactInfo;
$results['Admin'] = $adminContactInfo;
$results['Technical'] = $techContactInfo;
$results['Billing'] = $billingContactInfo;
return $results;
}
# Function to grab contact details
function cozaepp_GetContactDetails($params) {
# Grab variables
$sld = $params["sld"];
$tld = $params["tld"];
$domain = strtolower("$sld.$tld");
# Fetching contact details
$contacts = _getContactDetails($domain);
# If there was an error return it
if (isset($contacts["error"])) {
return $contacts;
}
# What we going to do here is make sure all the attirbutes we return back are set
# If we don't do this WHMCS won't display the options for editing
foreach (array("Registrant","Admin","Technical","Billing") as $type) {
foreach (
array("Contact Name","Organisation","Address line 1","Address line 2","TownCity","State","Zip code","Country Code",
"Phone","Email")
as $item
) {
# Check if the item is set
if (empty($contacts[$type][$item])) {
# Just set it to -
$values[$type][$item] = "-";
} else {
# We setting this here so we maintain the right order, else we get the set
# things first and all the unsets second, which looks crap
$values[$type][$item] = $contacts[$type][$item];
}
}
}
return $values;
}
/**
* Catching all the different variations of params as encountered by clients
* This has only been reported to have occured in WHMCS 5.2 and 5.3.7
* References to the occurences of this particular issue can be found at the followinf urls:
* https://gitlab.devlabs.linuxassist.net/awit-whmcs/whmcs-coza-epp/issues/11#note_630
* http://lists.linuxassist.net/pipermail/whmcs-coza-epp_lists.linuxassist.net/2013-April/000319.html
*/
function _getContactDetailsFromParams($params,$type) {
$results = array();
$results["Contact Name"] = $params["contactdetails"][$type]["Contact Name"];
# Catching different variations of Organisation
if (isset($params["contactdetails"][$type]["Organisation"])) {
$results["Organisation"] = $params["contactdetails"][$type]["Organisation"];
} else if (isset($params["contactdetails"][$type]["Company Name"])) {
$results["Organisation"] = $params["contactdetails"][$type]["Company Name"];
} else {
$results["Organisation"] = "";
}
# Catching different variations of Address line 1
if (isset($params["contactdetails"][$type]["Address line 1"])) {
$results["Address line 1"] = $params["contactdetails"][$type]["Address line 1"];
} else if (isset($params["contactdetails"][$type]["Address 1"])) {
$results["Address line 1"] = $params["contactdetails"][$type]["Address 1"];
} else {
$results["Address line 1"] = "";
}
# Catching different variations of Address line 2
if (isset($params["contactdetails"][$type]["Address line 2"])) {
$results["Address line 2"] = $params["contactdetails"][$type]["Address line 2"];
} else if (isset($params["contactdetails"][$type]["Address 2"])) {
$results["Address line 2"] = $params["contactdetails"][$type]["Address 2"];
} else {
$results["Address line 2"] = "";
}
# Catching different variations of TownCity
if (isset($params["contactdetails"][$type]["TownCity"])) {
$results["TownCity"] = $params["contactdetails"][$type]["TownCity"];
} else if (isset($params["contactdetails"][$type]["City"])) {
$results["TownCity"] = $params["contactdetails"][$type]["City"];
} else {
$results["TownCity"] = "";
}
$results["State"] = $params["contactdetails"][$type]["State"];
# Catching different variations of Postal Code
if (isset($params["contactdetails"][$type]["Zip code"])) {
$results["Zip code"] = $params["contactdetails"][$type]["Zip code"];
} else if (isset($params["contactdetails"][$type]["ZIP Code"])) {
$results["Zip code"] = $params["contactdetails"][$type]["ZIP Code"];
} else if (isset($params["contactdetails"][$type]["Postcode"])) {
$results["Zip code"] = $params["contactdetails"][$type]["Postcode"];
} else {
$results["Zip code"] = "";
}
# Catching different variations of Country Code
if (isset($params["contactdetails"][$type]["Country Code"])) {
$results["Country Code"] = $params["contactdetails"][$type]["Country Code"];
} else if (isset($params["contactdetails"][$type]["Country"])) {
$results["Country Code"] = $params["contactdetails"][$type]["Country"];
} else {
$results["Country Code"] = "";
}
$results["Phone"] = $params["contactdetails"][$type]["Phone"];
$results["Email"] = $params["contactdetails"][$type]["Email"];
return $results;
}
# Function to actually do the saving of contact details
function __saveContact($contactID,$contacts,$type,$client = null) {
# Get client instance
try {
if (!isset($client)) {
$client = _cozaepp_Client($domain);
}
# Grab contact
$contact = $contacts[$type];
# Save contact details
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:contact="urn:ietf:params:xml:ns:contact-1.0">
<epp:command>
<epp:update>
<contact:update>
<contact:id>'.$contactID.'</contact:id>
<contact:chg>
<contact:postalInfo type="loc">
<contact:name>'.$contact['Contact Name'].'</contact:name>
<contact:org>'.$contact['Organization'].'</contact:org>
<contact:addr>
<contact:street>'.$contact['Address line 1'].'</contact:street>
<contact:street>'.$contact['Address line 2'].'</contact:street>
<contact:city>'.$contact['TownCity'].'</contact:city>
<contact:sp>'.$contact['State'].'</contact:sp>
<contact:pc>'.$contact['Zip code'].'</contact:pc>
<contact:cc>'.$contact['Country Code'].'</contact:cc>
</contact:addr>
</contact:postalInfo>
<contact:voice>'.$contact['Phone'].'</contact:voice>
<contact:fax></contact:fax>
<contact:email>'.$contact['Email'].'</contact:email>
</contact:chg>
</contact:update>
</epp:update>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'SaveContactDetails', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes != '1001') {
$values["error"] = "SaveContactDetails/contact-update($registrant): Code ($coderes) $msg";
return $values;
}
$values["status"] = $msg;
return $values;
} catch (Exception $e) {
$values["error"] = 'SaveContactDetails/EPP: '.$e->getMessage();
return $values;
}
}
# Function to save contact details
function cozaepp_SaveContactDetails($params) {
# Grab variables
$tld = $params["tld"];
$sld = $params["sld"];
$domain = strtolower("$sld.$tld");
# Registrant details
$registrantContactDetails = _getContactDetailsFromParams($params,"Registrant");
$adminContactDetails = _getContactDetailsFromParams($params,"Admin");
$technicalContactDetails = _getContactDetailsFromParams($params,"Technical");
$billingContactDetails = _getContactDetailsFromParams($params,"Billing");
# Get client instance
try {
$client = _cozaepp_Client($domain);
# Grab domain info
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:info>
<domain:info xsi:schemaLocation="urn:ietf:params:xml:ns:domain-1.0 domain-1.0.xsd">
<domain:name hosts="all">'.$domain.'</domain:name>
</domain:info>
</epp:info>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'SaveContactDetails', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes != '1000') {
$values["error"] = "SaveContactDetails/domain-info($domain): Code (".$coderes.") ".$msg;
return $values;
}
# Grab contact ID's
$registrantContactID = $doc->getElementsByTagName('registrant')->item(0)->nodeValue;
if (empty($registrantContactID)) {
$values["error"] = "_SaveContactDetails/domain-info($domain): Registrant contact info not available";
return $values;
}
$contactNodes = $doc->getElementsByTagName('contact');
foreach ($contactNodes as $contactNode) {
# Check if we have found the relevant contact nodes
$type = $contactNode->getAttribute('type');
if ($type == "admin") {
$adminContactID = $contactNode->nodeValue;
} elseif ($type == "tech") {
$techContactID = $contactNode->nodeValue;
} elseif ($type == "billing") {
$billingContactID = $contactNode->nodeValue;
}
}
if (empty($adminContactID)) {
$values["error"] = "_SaveContactDetails/domain-info($domain): Admin contact info not available";
return $values;
}
if (empty($techContactID)) {
$values["error"] = "_SaveContactDetails/domain-info($domain): Technical contact info not available";
return $values;
}
if (empty($billingContactID)) {
$values["error"] = "_SaveContactDetails/domain-info($domain): Billing contact info not available";
return $values;
}
# Create contacts for use in our recreate below
$contacts['Registrant'] = $registrantContactDetails;
$contacts['Admin'] = $adminContactDetails;
$contacts['Technical'] = $technicalContactDetails;
$contacts['Billing'] = $billingContactDetails;
# We'll store the XML in here if we need to recreate contacts, this happens if admin/tech/billing are the same as
# registrant
$contactXML_chg = '';
$contactXML_rem = '';
$contactXML_add = '';
# Store errors we got
$errors = '';
# Check the contact ID's differ, if not, recreate the extra ones
if ($adminContactID == $registrantContactID || $adminContactID == $techContactID || $adminContactID == $billingContactID) {
$adminContact = __recreateContact($domain,$contacts,"Admin",$client);
# If there was an error return it
if (!isset($adminContact["error"])) {
$contactXML_rem .= '<domain:contact type="admin">'.$adminContactID.'</domain:contact>';
$adminContactID = $adminContact['contactid'];
$contactXML_add .= '<domain:contact type="admin">'.$adminContactID.'</domain:contact>';
} else {
$errors .= $adminContact["error"];
}
} else {
$values = __saveContact($adminContactID,$contacts,"Admin",$client);
# If there was an error return it
if (isset($values["error"])) {
$errors .= $values["error"];
}
}
if ($techContactID == $registrantContactID || $techContactID == $adminContactID || $techContactID == $billingContactID) {
$techContact = __recreateContact($domain,$contacts,"Technical",$client);
# If there was an error return it
if (!isset($techContact["error"])) {
$contactXML_rem .= '<domain:contact type="tech">'.$techContactID.'</domain:contact>';
$techContactID = $techContact['contactid'];
$contactXML_add .= '<domain:contact type="tech">'.$techContactID.'</domain:contact>';
} else {
$errors .= $adminContact["error"];
}
} else {
$values = __saveContact($techContactID,$contacts,"Technical",$client);
# If there was an error return it
if (isset($values["error"])) {
$errors .= $values["error"];
}
}
if ($billingContactID == $registrantContactID || $billingContactID == $adminContactID || $billingContactID == $techContactID) {
$billingContact = __recreateContact($domain,$contacts,"Billing",$client);
# If there was an error return it
if (!isset($billingContact["error"])) {
$contactXML_rem .= '<domain:contact type="billing">'.$billingContactID.'</domain:contact>';
$billingContactID = $billingContact['contactid'];
$contactXML_add .= '<domain:contact type="billing">'.$billingContactID.'</domain:contact>';
} else {
$errors .= $billingContact["error"];
}
} else {
$values = __saveContact($billingContactID,$contacts,"Billing",$client);
# If there was an error return it
if (isset($values["error"])) {
$errors .= $values["error"];
}
}
# Save registrant
$values = __saveContact($registrantContactID,$contacts,"Registrant",$client);
# If there was an error return it
if (isset($values["error"])) {
$errors .= $values["error"];
}
$contactXML_chg .= '<domain:registrant>'.$registrantContactID.'</domain:registrant>';
# Build the XML for the updates we need to do
$contactXML = "";
if (!empty($contactXML_add)) {
$contactXML .= '<domain:add>'.$contactXML_add.'</domain:add>';
}
if (!empty($contactXML_rem)) {
$contactXML .= '<domain:rem>'.$contactXML_rem.'</domain:rem>';
}
if (!empty($contactXML_chg)) {
$contactXML .= '<domain:chg>'.$contactXML_chg.'</domain:chg>';
}
# Check if we need to do a contact ID update
if (!empty($contactXML)) {
# Update domain contacts if any changed
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xmlns:cozadomain="http://co.za/epp/extensions/cozadomain-1-0"
xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:update>
<domain:update>
<domain:name>'.$domain.'</domain:name>
'.$contactXML.'
</domain:update>
</epp:update>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'SaveContactDetails', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes != '1001') {
$errors .= "_SaveContactDetails/domain-info($domain): Code (".$coderes.") ".$msg;
}
}
# Check what we're going to return
unset($values);
if ($errors) {
$values["error"] = $errors;
} else {
$values['msg'] = "Contact details saved.";
}
return $values;
} catch (Exception $e) {
$values["error"] = 'SaveContactDetails/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
# NOT IMPLEMENTED
function cozaepp_GetEPPCode($params) {
# Grab variables
$username = $params["Username"];
$password = $params["Password"];
$testmode = $params["TestMode"];
$sld = $params["sld"];
$tld = $params["tld"];
$domain = strtolower("$sld.$tld");
$values["eppcode"] = '';
# If error, return the error message in the value below
//$values["error"] = 'error';
return $values;
}
# Function to register nameserver
function cozaepp_RegisterNameserver($params) {
# Grab varaibles
$username = $params["Username"];
$password = $params["Password"];
$testmode = $params["TestMode"];
$sld = $params["sld"];
$tld = $params["tld"];
$domain = strtolower("$sld.$tld");
$nameserver = $params["nameserver"];
$ipaddress = $params["ipaddress"];
# Grab client instance
try {
$client = _cozaepp_Client($domain);
# Register nameserver
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:domain="urn:ietf:params:xml:ns:domain-1.0">
<epp:command>
<epp:update>
<domain:update>
<domain:name>'.$domain.'</domain:name>
<domain:add>
<domain:ns>
<domain:hostAttr>
<domain:hostName>'.$nameserver.'</domain:hostName>
<domain:hostAddr ip="v4">'.$ipaddress.'</domain:hostAddr>
</domain:hostAttr>
</domain:ns>
</domain:add>
</domain:update>
</epp:update>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'RegisterNameserver', $xml, $request);
# Pull off status
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check if result is ok
if($coderes != '1001') {
$values["error"] = "RegisterNameserver/domain-update($domain): Code ($coderes) $msg";
return $values;
}
$values['status'] = $msg;
} catch (Exception $e) {
$values["error"] = 'SaveNameservers/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
# Modify nameserver
function cozaepp_ModifyNameserver($params) {
# Grab variables
$username = $params["Username"];
$password = $params["Password"];
$testmode = $params["TestMode"];
$tld = $params["tld"];
$sld = $params["sld"];
$domain = strtolower("$sld.$tld");
$nameserver = $params["nameserver"];
$currentipaddress = $params["currentipaddress"];
$newipaddress = $params["newipaddress"];
# Grab client instance
try {
$client = _cozaepp_Client($domain);
# Modify nameserver
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:domain="urn:ietf:params:xml:ns:domain-1.0">
<epp:command>
<epp:update>
<domain:update>
<domain:name>'.$domain.'</domain:name>
<domain:add>
<domain:ns>
<domain:hostAttr>
<domain:hostName>'.$nameserver.'</domain:hostName>
<domain:hostAddr ip="v4">'.$newipaddress.'</domain:hostAddr>
</domain:hostAttr>
</domain:ns>
</domain:add>
</domain:update>
</epp:update>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'ModifyNameserver', $xml, $request);
# Pull off status
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check if result is ok
if($coderes != '1001') {
$values["error"] = "ModifyNameserver/domain-update($domain): Code ($coderes) $msg";
return $values;
}
$values['status'] = $msg;
} catch (Exception $e) {
$values["error"] = 'SaveNameservers/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
# Delete nameserver
function cozaepp_DeleteNameserver($params) {
# Grab variables
$username = $params["Username"];
$password = $params["Password"];
$testmode = $params["TestMode"];
$tld = $params["tld"];
$sld = $params["sld"];
$domain = strtolower("$sld.$tld");
$nameserver = $params["nameserver"];
# Grab client instance
try {
$client = _cozaepp_Client($domain);
# If we were given hostname. blow away all of the stuff behind it and allow us to remove hostname
$nameserver = preg_replace('/\.\.\S+/','',$nameserver);
# Delete nameserver
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:domain="urn:ietf:params:xml:ns:domain-1.0">
<epp:command>
<epp:update>
<domain:update>
<domain:name>'.$domain.'</domain:name>
<domain:rem>
<domain:ns>
<domain:hostAttr>
<domain:hostName>'.$nameserver.'</domain:hostName>
</domain:hostAttr>
</domain:ns>
</domain:rem>
</domain:update>
</epp:update>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'DeleteNameserver', $xml, $request);
# Pull off status
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check if result is ok
if($coderes != '1001') {
$values["error"] = "DeleteNameserver/domain-update($domain): Code ($coderes) $msg";
return $values;
}
$values['status'] = $msg;
} catch (Exception $e) {
$values["error"] = 'SaveNameservers/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
# Function to return meaningful message from response code
function _cozaepp_message($code) {
return "Code $code";
}
# Ack a POLL message
function _cozaepp_ackpoll($client,$msgid) {
# Ack poll message
$request = $client->request($xml = '
<epp xmlns="urn:ietf:params:xml:ns:epp-1.0">
<command>
<poll op="ack" msgID="'.$msgid.'"/>
</command>
</epp>
');
# Decipher XML
$doc = new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'ackpoll', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check result
if($coderes != '1301' && $coderes != '1300' && $coderes != 1000) {
throw new Exception("ackpoll/poll-ack($id): Code ($coderes) $msg");
}
}
# Helper function to centrally provide data and information about different SLDs.
function _cozaepp_SldLookup($domain) {
# TLD server data provided by ZACR
$tldservers = array(
'co.za' => array(
'fqdn' => 'epp.coza.net.za',
'port' => 3121,
'additional_contacts' => true
),
'org.za' => array(
'fqdn' => 'org-epp.registry.net.za',
'port' => 3121,
'additional_contacts' => true
),
'web.za' => array(
'fqdn' => 'web-epp.registry.net.za',
'port' => 3121,
'additional_contacts' => true
),
'net.za' => array(
'fqdn' => 'net-epp.registry.net.za',
'port' => 3121,
'additional_contacts' => true
),
);
if (!is_null($domain)) {
foreach ($tldservers as $tld => $data) {
if (preg_match("/$tld$/i", $domain)) {
return $data;
}
}
throw new Exception('SLD lookup failed to find: '.$domain);
} else { # defaults to co.za server.
return $tldservers['co.za'];
}
}
# Function to create internal COZA EPP request
function _cozaepp_Client($domain=null) {
# Setup include dir
$include_path = ROOTDIR . '/modules/registrars/cozaepp';
set_include_path($include_path . PATH_SEPARATOR . get_include_path());
# Include EPP stuff we need
require_once 'Net/EPP/Client.php';
require_once 'Net/EPP/Protocol.php';
# Grab module parameters
$params = getregistrarconfigoptions('cozaepp');
# Set server address and port based on parsed domain name
$_server = _cozaepp_SldLookup($domain);
# Check if module parameters are sane
if (empty($params['Username']) || empty($params['Password'])) {
throw new Exception('System configuration error(1), please contact your provider');
}
# Create SSL context
$context = stream_context_create();
# Are we using ssl?
$use_ssl = false;
if (!empty($params['SSL']) && $params['SSL'] == 'on') {
$use_ssl = true;
}
# Set certificate if we have one
if ($use_ssl && !empty($params['Certificate'])) {
if (!file_exists($params['Certificate'])) {
throw new Exception("System configuration error(3), please contact your provider");
}
# Set client side certificate
stream_context_set_option($context, 'ssl', 'local_cert', $params['Certificate']);
}
# Create EPP client
$client = new Net_EPP_Client();
# Connect
$res = $client->connect($_server['fqdn'], $_server['port'], 10, $use_ssl, $context);
# Perform login
$request = $client->request($xml = '
<epp xmlns="urn:ietf:params:xml:ns:epp-1.0">
<command>
<login>
<clID>'.$params['Username'].'</clID>
<pw>'.$params['Password'].'</pw>
<options>
<version>1.0</version>
<lang>en</lang>
</options>
<svcs>
<objURI>urn:ietf:params:xml:ns:domain-1.0</objURI>
<objURI>urn:ietf:params:xml:ns:contact-1.0</objURI>
</svcs>
</login>
</command>
</epp>
');
logModuleCall('Cozaepp', 'Connect', $xml, $request);
return $client;
}
function cozaepp_TransferSync($params) {
$domainid = $params['domainid'];
$domain = $params['domain'];
$sld = $params['sld'];
$tld = $params['tld'];
$domain = strtolower("$sld.$tld");
$registrar = $params['registrar'];
$regperiod = $params['regperiod'];
$status = $params['status'];
$dnsmanagement = $params['dnsmanagement'];
$emailforwarding = $params['emailforwarding'];
$idprotection = $params['idprotection'];
# Other parameters used in your _getConfigArray() function would also be available for use in this function
# Grab domain info
try {
$client = _cozaepp_Client($domain);
# Grab domain info
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:info>
<domain:info xsi:schemaLocation="urn:ietf:params:xml:ns:domain-1.0 domain-1.0.xsd">
<domain:name hosts="all">'.$domain.'</domain:name>
</domain:info>
</epp:info>
</epp:command>
</epp:epp>
');
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'TransferSync', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check result
if ($coderes == '2303') {
$values['error'] = "TransferSync/domain-info($domain): Domain not found";
return $values;
} else if ($coderes != '1000') {
$values['error'] = "TransferSync/domain-info($domain): Code("._cozaepp_message($coderes).") $msg";
return $values;
}
# Check if we can get a status back
if ($doc->getElementsByTagName('status')->item(0)) {
$statusres = $doc->getElementsByTagName('status')->item(0)->getAttribute('s');
$createdate = substr($doc->getElementsByTagName('crDate')->item(0)->nodeValue,0,10);
$nextduedate = substr($doc->getElementsByTagName('exDate')->item(0)->nodeValue,0,10);
} else {
$values['error'] = "TransferSync/domain-info($domain): Domain not found";
return $values;
}
$values['status'] = $msg;
# Check status and update
if ($statusres == "ok") {
$values['completed'] = true;
} else {
$values['error'] = "TransferSync/domain-info($domain): Unknown status code '$statusres' (File a bug report here: http://gitlab.devlabs.linuxassist.net/awit-whmcs/whmcs-coza-epp/issues/new)";
}
$values['expirydate'] = $nextduedate;
} catch (Exception $e) {
$values["error"] = 'TransferSync/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
function __recreateContact($domain,$contacts,$type,$client = null) {
# Get client instance
try {
if (!isset($client)) {
$client = _cozaepp_Client($domain);
}
# Check for available contact id
$contactID = _cozaepp_CheckContact($domain,$type);
# Generate a random password for the contact
$pw = substr(md5($domain . time() . rand(0, 1000000)), 0,15);
# Recreate contact
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:contact="urn:ietf:params:xml:ns:contact-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:create>
<contact:create xsi:schemaLocation="urn:ietf:params:xml:ns:contact-1.0 contact-1.0.xsd">
<contact:id>'.$contactID.'</contact:id>
<contact:postalInfo type="loc">
<contact:name>'.$contacts[$type]["Contact Name"].'</contact:name>
<contact:org>'.$contacts[$type]["Organisation"].'</contact:org>
<contact:addr>
<contact:street>'.$contacts[$type]["Address line 1"].'</contact:street>
<contact:street>'.$contacts[$type]["Address line 2"].'</contact:street>
<contact:city>'.$contacts[$type]["TownCity"].'</contact:city>
<contact:sp>'.$contacts[$type]["State"].'</contact:sp>
<contact:pc>'.$contacts[$type]["Zip code"].'</contact:pc>
<contact:cc>'.$contacts[$type]["Country Code"].'</contact:cc>
</contact:addr>
</contact:postalInfo>
<contact:voice>'.$contacts[$type]["Phone"].'</contact:voice>
<contact:fax></contact:fax>
<contact:email>'.$contacts[$type]["Email"].'</contact:email>
<contact:authInfo>
<contact:pw>'.$pw.'</contact:pw>
</contact:authInfo>
</contact:create>
</epp:create>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', '__recreateContact', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes != '1000') {
$values["error"] = "__recreateContact/contact-create($contactID:$type): Code ($coderes) $msg";
return $values;
}
$values["contactid"] = $contactID;
return $values;
} catch (Exception $e) {
$values["error"] = '__recreateContact/EPP: '.$e->getMessage();
return $values;
}
}
function cozaepp_RecreateContact($params) {
# Grab variables
$tld = $params["tld"];
$sld = $params["sld"];
$domain = strtolower("$sld.$tld");
# Get client instance
try {
$client = _cozaepp_Client($domain);
# Fetching contact details
$contacts = _getContactDetails($domain, $client);
# If there was an error return it
if (isset($contacts["error"])) {
return $contacts;
}
# Create contacts
$registrantContact = __recreateContact($domain,$contacts,"Registrant",$client);
# If there was an error return it
if (isset($registrantContact["error"])) {
return $registrantContact;
}
$registrantContactID = $registrantContact['contactid'];
$adminContact = __recreateContact($domain,$contacts,"Admin",$client);
# If there was an error return it
if (isset($adminContact["error"])) {
return $adminContact;
}
$adminContactID = $adminContact['contactid'];
$techContact = __recreateContact($domain,$contacts,"Technical",$client);
# If there was an error return it
if (isset($techContact["error"])) {
return $techContact;
}
$techContactID = $techContact['contactid'];
$billingContact = __recreateContact($domain,$contacts,"Billing",$client);
# If there was an error return it
if (isset($billingContact["error"])) {
return $billingContact;
}
$billingContactID = $billingContact['contactid'];
# Update domain registrant
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:domain="urn:ietf:params:xml:ns:domain-1.0">
<epp:command>
<epp:update>
<domain:update>
<domain:name>'.$domain.'</domain:name>
<domain:chg>
<domain:registrant>'.$registrantContactID.'</domain:registrant>
<domain:admin>'.$adminContactID.'</domain:admin>
<domain:tech>'.$techContactID.'</domain:tech>
<domain:billing>'.$billingContactID.'</domain:billing>
</domain:chg>
</domain:update>
</epp:update>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'RecreateContact', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
if($coderes != '1001') {
$values["error"] = "RecreateContact/domain-info($domain): Code (".$coderes.") ".$msg;
return $values;
}
$values["status"] = $msg;
} catch (Exception $e) {
$values["error"] = 'RecreateContact/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
function cozaepp_Sync($params) {
$domainid = $params['domainid'];
$domain = $params['domain'];
$sld = $params['sld'];
$tld = $params['tld'];
$domain = strtolower("$sld.$tld");
$registrar = $params['registrar'];
$regperiod = $params['regperiod'];
$status = $params['status'];
$dnsmanagement = $params['dnsmanagement'];
$emailforwarding = $params['emailforwarding'];
$idprotection = $params['idprotection'];
# Other parameters used in your _getConfigArray() function would also be available for use in this function
# Grab domain info
try {
$client = _cozaepp_Client($domain);
# Grab domain info
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:info>
<domain:info xsi:schemaLocation="urn:ietf:params:xml:ns:domain-1.0 domain-1.0.xsd">
<domain:name hosts="all">'.$domain.'</domain:name>
</domain:info>
</epp:info>
</epp:command>
</epp:epp>
');
$doc= new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'Sync', $xml, $request);
# Initialize the owningRegistrar which will contain the owning registrar
# The <domain:clID> element contains the unique identifier of the registrar that owns the domain.
$owningRegistrar = NULL;
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check result
if ($coderes == '2303') {
# Code 2303, domain not found
$values['error'] = "TransferSync/domain-info($domain): Domain not found";
return $values;
} else if ($coderes == '1000') {
# Code 1000, success
if (
$doc->getElementsByTagName('infData') &&
$doc->getElementsByTagName('infData')->item(0)->getElementsByTagName('ns')->item(0) &&
$doc->getElementsByTagName('infData')->item(0)->getElementsByTagName('clID')
) {
$owningRegistrar = $doc->getElementsByTagName('infData')->item(0)->getElementsByTagName('clID')->item(0)->nodeValue;
}
} else {
$values['error'] = "Sync/domain-info($domain): Code("._cozaepp_message($coderes).") $msg";
return $values;
}
# Check if we can get a status back
if ($doc->getElementsByTagName('status')->item(0)) {
$statusres = $doc->getElementsByTagName('status')->item(0)->getAttribute('s');
$createdate = substr($doc->getElementsByTagName('crDate')->item(0)->nodeValue,0,10);
$nextduedate = substr($doc->getElementsByTagName('exDate')->item(0)->nodeValue,0,10);
} else if (!empty($owningRegistrar) && $owningRegistrar != $username) {
# If we got an owningRegistrar back and we're not the owning registrar, return error
$values['error'] = "Sync/domain-info($domain): Domain belongs to a different registrar, (owning registrar: $owningRegistrar, your registrar: $username)";
return $values;
} else {
$values['error'] = "Sync/domain-info($domain): Domain not found";
return $values;
}
$values['status'] = $msg;
# Check status and update
if ($statusres == "ok") {
$values['active'] = true;
} elseif ($statusres == "pendingUpdate") {
} elseif ($statusres == "serverHold") {
} elseif ($statusres == "expired" || $statusres == "pendingDelete" || $statusres == "inactive") {
$values['expired'] = true;
} else {
$values['error'] = "Sync/domain-info($domain): Unknown status code '$statusres' (File a bug report here: http://gitlab.devlabs.linuxassist.net/awit-whmcs/whmcs-coza-epp/issues/new)";
}
$values['expirydate'] = $nextduedate;
} catch (Exception $e) {
$values["error"] = 'Sync/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
function cozaepp_RequestDelete($params) {
$sld = $params['sld'];
$tld = $params['tld'];
$domain = strtolower("$sld.$tld");
# Grab domain info
try {
$client = _cozaepp_Client($domain);
# Grab domain info
$request = $client->request($xml = '
<epp:epp xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:epp="urn:ietf:params:xml:ns:epp-1.0"
xmlns:domain="urn:ietf:params:xml:ns:domain-1.0" xsi:schemaLocation="urn:ietf:params:xml:ns:epp-1.0 epp-1.0.xsd">
<epp:command>
<epp:delete>
<domain:delete xsi:schemaLocation="urn:ietf:params:xml:ns:domain-1.0 domain-1.0.xsd">
<domain:name>'.$domain.'</domain:name>
</domain:delete>
</epp:delete>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc = new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'RequestDelete', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check result
if($coderes != '1001') {
$values['error'] = 'RequestDelete/domain-info('.$domain.'): Code('._cozaepp_message($coderes).") $msg";
return $values;
}
$values['status'] = $msg;
} catch (Exception $e) {
$values["error"] = 'RequestDelete/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
function cozaepp_ApproveTransfer($params) {
$sld = $params['sld'];
$tld = $params['tld'];
$domain = strtolower("$sld.$tld");
# Grab domain info
try {
$client = _cozaepp_Client($domain);
# Grab domain info
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:domain="urn:ietf:params:xml:ns:domain-1.0">
<epp:command>
<epp:transfer op="approve">
<domain:transfer>
<domain:name>'.$domain.'</domain:name>
</domain:transfer>
</epp:transfer>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc = new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'ApproveTransfer', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check result
if($coderes != '1000') {
$values['error'] = 'ApproveTransfer/domain-info('.$domain.'): Code('._cozaepp_message($coderes).") $msg";
return $values;
}
$values['status'] = $msg;
} catch (Exception $e) {
$values["error"] = 'ApproveTransfer/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
function cozaepp_CancelTransferRequest($params) {
$sld = $params['sld'];
$tld = $params['tld'];
$domain = strtolower("$sld.$tld");
# Grab domain info
try {
$client = _cozaepp_Client($domain);
# Grab domain info
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:domain="urn:ietf:params:xml:ns:domain-1.0">
<epp:command>
<epp:transfer op="cancel">
<domain:transfer>
<domain:name>'.$domain.'</domain:name>
</domain:transfer>
</epp:transfer>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc = new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'CancelTransferRequest', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check result
if($coderes != '1000') {
$values['error'] = 'CancelTransferRequest/domain-info('.$domain.'): Code('._cozaepp_message($coderes).") $msg";
return $values;
}
$values['status'] = $msg;
} catch (Exception $e) {
$values["error"] = 'CancelTransferRequest/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
function cozaepp_RejectTransfer($params) {
$sld = $params['sld'];
$tld = $params['tld'];
$domain = strtolower("$sld.$tld");
# Grab domain info
try {
$client = _cozaepp_Client($domain);
# Grab domain info
$request = $client->request($xml = '
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:domain="urn:ietf:params:xml:ns:domain-1.0">
<epp:command>
<epp:transfer op="reject">
<domain:transfer>
<domain:name>'.$domain.'</domain:name>
</domain:transfer>
</epp:transfer>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc = new DOMDocument();
$doc->loadXML($request);
logModuleCall('Cozaepp', 'RejectTransfer', $xml, $request);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
$msg = $doc->getElementsByTagName('msg')->item(0)->nodeValue;
# Check result
if($coderes != '1000') {
$values['error'] = 'RejectTransfer/domain-info('.$domain.'): Code('._cozaepp_message($coderes).") $msg";
return $values;
}
$values['status'] = $msg;
} catch (Exception $e) {
$values["error"] = 'RejectTransfer/EPP: '.$e->getMessage();
return $values;
}
return $values;
}
<?php
# Copyright (c) 2012-2015, AllWorldIT
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
# Official Website:
# http://devlabs.linuxassist.net/projects/whmcs-coza-epp
# Lead developer:
# Nigel Kukard <nkukard@lbsd.net>
# ! ! P L E A S E N O T E ! !
# * If you make changes to this file, please consider contributing
# anything useful back to the community. Don't be a sour prick.
# * If you find this module useful please consider making a
# donation to support modules like this.
# WHMCS hosting, theming, module development, payment gateway
# integration, customizations and consulting all available from
# http://allworldit.com
# This file brings in a few constants we need
require_once dirname(__FILE__) . '/../../../init.php';
# Setup include dir
$include_path = ROOTDIR . '/modules/registrars/cozaepp';
set_include_path($include_path . PATH_SEPARATOR . get_include_path());
# Include EPP stuff we need
require_once 'cozaepp.php';
# Additional functions we need
require_once ROOTDIR . '/includes/functions.php';
# Include registrar functions aswell
require_once ROOTDIR . '/includes/registrarfunctions.php';
require_once 'Net/EPP/Frame.php';
require_once 'Net/EPP/Frame/Command.php';
require_once 'Net/EPP/ObjectSpec.php';
# Grab module parameters
$params = getregistrarconfigoptions('cozaepp');
echo("COZA-EPP Poll Report\n");
echo("---------------------------------------------------\n");
# Request balance from registrar
try {
$client = _cozaepp_Client();
# Loop with message queue
while (!$last) {
# Request messages
$request = $client->request('
<epp xmlns="urn:ietf:params:xml:ns:epp-1.0">
<command>
<poll op="req"/>
</command>
</epp>
');
# Decode response
$doc= new DOMDocument();
$doc->loadXML($request);
# Pull off code
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
if ($coderes == 1301 || $coderes == 1300) {
$msgs = $doc->getElementsByTagName('msg');
for ($m = 0; $m < $msgs->length; $m++) {
echo "CODE: $coderes, MESSAGE: '".$msgs->item($m)->textContent."'\n";
// Messages to ignore
$ignored = array(
'Command completed successfully; ack to dequeue',
'Command completed successfully; no messages'
);
// Logging message
if (!in_array(trim($msgs->item($m)->textContent), $ignored)) {
$message = mysql_real_escape_string(trim($msgs->item($m)->textContent));
$result = mysql_query("
INSERT INTO mod_awit_cozaepp_messages
(
created,
code,
message
)
VALUES
(
now(),
'$coderes',
'$message'
)
");
if (mysql_error($result)) {
echo "ERROR: couldn't log epp message: " . mysql_error($result);
}
}
}
# This is the last one
if ($coderes == 1300) {
$last = 1;
}
$msgq = $doc->getElementsByTagName('msgQ')->item(0);
if ($msgq) {
$msgid = $doc->getElementsByTagName('msgQ')->item(0)->getAttribute('id');
try {
$res = _cozaepp_ackpoll($client,$msgid);
} catch (Exception $e) {
echo("ERROR: ".$e->getMessage()."\n");
}
}
} else {
$msgid = $doc->getElementsByTagName('svTRID')->item(0)->textContent;
$msgs = $doc->getElementsByTagName('msg');
for ($m = 0; $m < $msgs->length; $m++) {
echo "\n";
echo "UNKNOWN CODE: $coderes, MESSAGE: '".$msgs->item($m)->textContent."', ID: $msgid\n";
echo $request;
echo "\n\n";
}
}
}
} catch (Exception $e) {
echo("ERROR: ".$e->getMessage(). "\n");
exit;
}
modules/registrars/cozaepp/logo.gif

5.04 KiB

<?php
# Copyright (c) 2012-2015, AllWorldIT
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
# Official Website:
# http://devlabs.linuxassist.net/projects/whmcs-coza-epp
# Lead developer:
# Nigel Kukard <nkukard@lbsd.net>
# ! ! P L E A S E N O T E ! !
# * If you make changes to this file, please consider contributing
# anything useful back to the community. Don't be a sour prick.
# * If you find this module useful please consider making a
# donation to support modules like this.
# WHMCS hosting, theming, module development, payment gateway
# integration, customizations and consulting all available from
# http://allworldit.com
# Function to implement the cozaepp balance widget
function widget_cozaepp_balance($vars) {
# Setup include dir
$include_path = ROOTDIR . '/modules/registrars/cozaepp';
set_include_path($include_path . PATH_SEPARATOR . get_include_path());
# Include EPP stuff we need
require_once 'cozaepp.php';
# Include registrar functions aswell
require_once ROOTDIR . '/includes/registrarfunctions.php';
# Grab module parameters
$params = getregistrarconfigoptions('cozaepp');
# Set widget contents
$title = "COZA EPP Balance";
$template = '<p align = "center" class="textblack"><strong>%s</strong></p>';
# Request balance from registrar
try {
$client = _cozaepp_Client();
$output = $client->request('
<epp:epp xmlns:epp="urn:ietf:params:xml:ns:epp-1.0" xmlns:contact="urn:ietf:params:xml:ns:contact-1.0"
xmlns:cozacontact="http://co.za/epp/extensions/cozacontact-1-0">
<epp:command>
<epp:info>
<contact:info>
<contact:id>'.$params['Username'].'</contact:id>
</contact:info>
</epp:info>
<epp:extension>
<cozacontact:info>
<cozacontact:balance>true</cozacontact:balance>
</cozacontact:info>
</epp:extension>
</epp:command>
</epp:epp>
');
# Parse XML result
$doc= new DOMDocument();
$doc->loadXML($output);
$coderes = $doc->getElementsByTagName('result')->item(0)->getAttribute('code');
if ($coderes == '1000') {
$balancestr = "Current registrar balance is R ".$doc->getElementsByTagName('balance')->item(0)->nodeValue;
} else {
$balancestr = 'ERROR: Parsing';
}
} catch (Exception $e) {
return array('title'=>$title,'content'=>sprintf($template,"ERROR: ".$e->getMessage()));
}
return array('title'=>$title,'content'=>sprintf($template,$balancestr));
}
add_hook("AdminHomeWidgets",1,"widget_cozaepp_balance");