@ 2014-02-03T12:43:02Z <?php
class Cache
{
public static function has( $name ){
return false;
}
public static function get( $name ){
return null;
}
public static function put( $name, $value, $time = 1440 ){
return true;
}
}
class Collivery
{
protected $token;
protected $client;
protected $config;
protected $errors = array();
protected $check_cache = 2;
protected $default_address_id;
protected $client_id;
protected $user_id;
/**
* Setup class with basic Config
*
* @param Array $config Configuration Array
*/
function __construct( array $config = array() )
{
$this->config = (object) array(
'app_name' => 'Default App Name', // Application Name
'app_version' => '0.0.1', // Application Version
'app_host' => '', // Framework/CMS name and version, eg 'Wordpress 3.8.1 WooCommerce 2.0.20' / 'Joomla! 2.5.17 VirtueMart 2.0.26d'
'app_url' => '', // URL your site is hosted on
'user_email' => 'demo@collivery.co.za',
'user_password' => 'demo',
'demo' => false,
);
foreach ( $config as $key => $value ) {
$this->config->$key = $value;
}
if ( $this->config->demo ){
$this->config->user_email = 'demo@collivery.co.za';
$this->config->user_password = 'demo';
}
$this->authenticate();
}
/**
* Setup the Soap Object
*
* @return SoapClient MDS Collivery Soap Client
*/
protected function init ()
{
if ( ! $this->client ){
try {
$this->client = new SoapClient( // Setup the soap client
'http://www.collivery.co.za/wsdl/v2', // URL to WSDL File
array( 'cache_wsdl' => WSDL_CACHE_NONE ) // Don't cache the WSDL file
);
} catch (SoapFault $e) {
$this->catchSoapFault( $e );
return false;
}
}
return true;
}
/**
* Checks if the Soap Client has been set, and returns it.
*
* @return SoapClient Webserver Soap Client
*/
protected function client()
{
if ( ! $this->client ) {
$this->init();
}
if ( ! $this->token ) {
$this->authenticate();
}
return $this->client;
}
/**
* Authenticate and set the token
*
* @return string
*/
protected function authenticate()
{
if ( ( $this->check_cache == 2 ) && Cache::has('collivery.auth') ) {
$authenticate = Cache::get('collivery.auth');
$this->default_address_id = $authenticate['default_address_id'];
$this->client_id = $authenticate['client_id'];
$this->user_id = $authenticate['user_id'];
$this->token = $authenticate['token'];
return true;
} else {
if ( ! $this->init() ) return false;
$user_email = $this->config->user_email;
$user_password = $this->config->user_password;
try {
$authenticate = $this->client->authenticate($user_email, $user_password, $this->token,
array(
'name' => $this->config->app_name . ' mds/collivery/class',
'version' => $this->config->app_version,
'host' => $this->config->app_host,
'url' => $this->config->app_url,
'lang' => 'PHP '. phpversion(),
));
} catch (SoapFault $e) {
$this->catchSoapFault( $e );
return false;
}
if ( is_array( $authenticate ) && isset( $authenticate['token'] ) ){
if ( $this->check_cache != 0 ) Cache::put( 'collivery.auth', $authenticate, 50 );
$this->default_address_id = $authenticate['default_address_id'];
$this->client_id = $authenticate['client_id'];
$this->user_id = $authenticate['user_id'];
$this->token = $authenticate['token'];
return true;
} else {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
else
$this->setError( 'result_unexpected', 'No address_id returned.' );
return false;
}
}
}
/**
* Create a new Address and Contact
*
* @param array $data Address and Contact Information
* @return array Address ID and Contact ID
*/
public function addAddress( array $data )
{
$location_types = $this->getLocationTypes();
$towns = $this->getTowns();
$suburbs = $this->getSuburbs( $data['town_id'] );
if ( ! isset( $data['location_type'] ) )
$this->setError( 'missing_data', 'location_type not set.' );
elseif ( ! isset( $location_types[ $data['location_type'] ] ) )
$this->setError( 'invalid_data', 'Invalid location_type.' );
if ( ! isset( $data['town_id'] ) )
$this->setError( 'missing_data', 'town_id not set.' );
elseif ( ! isset( $towns[ $data['town_id'] ] ) )
$this->setError( 'invalid_data', 'Invalid town_id.' );
if ( ! isset( $data['suburb_id'] ) )
$this->setError( 'missing_data', 'suburb_id not set.' );
elseif ( ! isset( $suburbs[ $data['suburb_id'] ] ) )
$this->setError( 'invalid_data', 'Invalid suburb_id.' );
if ( ! isset( $data['street'] ) )
$this->setError( 'missing_data', 'street not set.' );
if ( ! isset( $data['full_name'] ) )
$this->setError( 'missing_data', 'full_name not set.' );
if ( isset( $data['phone'] ) || isset( $data['cellphone'] ) )
$this->setError( 'missing_data', 'Please supply ether a phone or cellphone number...' );
if ( ! $this->hasErrors() ) {
try {
$result = $this->client()->add_address( $data, $this->token );
Cache::forget( 'collivery.addresses.'. $this->client_id );
} catch (SoapFault $e) {
$this->catchSoapFault( $e );
return false;
}
if ( isset( $result['address_id'] ) ) {
return $result;
} else {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
else
$this->setError( 'result_unexpected', 'No address_id returned.' );
return false;
}
}
}
/**
* Add's a contact person for a given Address ID
*
* @param array $data New Contact Data
* @return int New Contact ID
*/
public function addContact( array $data )
{
if ( ! isset( $data['address_id'] ) )
$this->setError( 'missing_data', 'address_id not set.' );
elseif ( ! is_array( $this->getAddress( $data['address_id'] ) ) )
$this->setError( 'invalid_data', 'Invalid address_id.' );
if ( ! isset( $data['street'] ) )
$this->setError( 'missing_data', 'street not set.' );
if ( ! isset( $data['full_name'] ) )
$this->setError( 'missing_data', 'full_name not set.' );
if ( isset( $data['phone'] ) || isset( $data['cellphone'] ) )
$this->setError( 'missing_data', 'Please supply ether a phone or cellphone number...' );
if ( ! $this->hasErrors() ) {
try {
$result = $this->client()->add_address( $data, $this->token );
Cache::forget( 'collivery.addresses.'. $this->client_id );
} catch (SoapFault $e) {
$this->catchSoapFault( $e );
return false;
}
if ( isset( $result['address_id'] ) ) {
return $result;
} else {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
else
$this->setError( 'result_unexpected', 'No address_id returned.' );
return false;
}
}
}
/**
* Returns the price based on the data provided.
*
* @param array $data Your Collivery Details
* @return array Pricing for details supplied
*/
public function getPrice( array $data )
{
$towns = $this->getTowns();
if ( ! isset( $data['collivery_from'] ) && ! isset( $data['from_town_id'] ) )
$this->setError( 'missing_data', 'collivery_from/from_town_id not set.' );
elseif ( isset( $data['collivery_from'] ) && ! is_array( $this->getAddress( $data['collivery_from'] ) ) )
$this->setError( 'invalid_data', 'Invalid Address ID for: collivery_from.' );
elseif ( isset( $data['from_town_id'] ) && ! isset( $towns[ $data['from_town_id'] ] ) )
$this->setError( 'invalid_data', 'Invalid Town ID for: from_town_id.' );
if ( ! isset( $data['collivery_to'] ) && ! isset( $data['to_town_id'] ) )
$this->setError( 'missing_data', 'collivery_to/to_town_id not set.' );
elseif ( isset( $data['collivery_to'] ) && ! is_array( $this->getAddress( $data['collivery_to'] ) ) )
$this->setError( 'invalid_data', 'Invalid Address ID for: collivery_to.' );
elseif ( isset( $data['to_town_id'] ) && ! isset( $towns[ $data['to_town_id'] ] ) )
$this->setError( 'invalid_data', 'Invalid Town ID for: to_town_id.' );
if ( ! isset( $data['service'] ) )
$this->setError( 'missing_data', 'service not set.' );
if ( ! $this->hasErrors() ) {
try {
$result = $this->client()->get_price( $data, $this->token );
} catch (SoapFault $e) {
$this->catchSoapFault( $e );
return false;
}
if ( is_array( $result ) ) {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
return $result;
} else {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
else
$this->setError( 'result_unexpected', 'No address_id returned.' );
return false;
}
}
}
/**
* Validate Collivery
*
* Returns the validated data array of all details pertaining to a collivery.
* This process validates the information based on services, time frames and parcel information.
* Dates and times may be altered during this process based on the collection and delivery towns service parameters.
* Certain towns are only serviced on specific days and between certain times.
* This function automatically alters the values.
* The parcels volumetric calculations are also done at this time.
* It is important that the data is first validated before a collivery can be added.
*
* @param array $data Properties of the new Collivery
* @return array The validated data
*/
public function validate( array $data )
{
$contacts_from = $this->getContacts( $data['collivery_from'] );
$contacts_to = $this->getContacts( $data['collivery_to'] );
$parcel_types = $this->getParcelTypes();
$services = $this->getServices();
if ( ! isset( $data['collivery_from'] ) )
$this->setError( 'missing_data', 'collivery_from not set.' );
elseif ( ! is_array( $this->getAddress( $data['collivery_from'] ) ) )
$this->setError( 'invalid_data', 'Invalid Address ID for: collivery_from.' );
if ( ! isset( $data['contact_from'] ) )
$this->setError( 'missing_data', 'contact_from not set.' );
elseif ( ! isset( $contacts_from[ $data['contact_from'] ] ) )
$this->setError( 'invalid_data', 'Invalid Contact ID for: contact_from.' );
if ( ! isset( $data['collivery_to'] ) )
$this->setError( 'missing_data', 'collivery_to not set.' );
elseif ( ! is_array( $this->getAddress( $data['collivery_to'] ) ) )
$this->setError( 'invalid_data', 'Invalid Address ID for: collivery_to.' );
if ( ! isset( $data['contact_to'] ) )
$this->setError( 'missing_data', 'contact_to not set.' );
elseif ( ! isset( $contacts_to[ $data['contact_to'] ] ) )
$this->setError( 'invalid_data', 'Invalid Contact ID for: contact_to.' );
if ( ! isset( $data['collivery_type'] ) )
$this->setError( 'missing_data', 'collivery_type not set.' );
elseif ( ! isset( $parcel_types[ $data['collivery_type'] ] ) )
$this->setError( 'invalid_data', 'Invalid collivery_type.' );
if ( ! isset( $data['service'] ) )
$this->setError( 'missing_data', 'service not set.' );
elseif ( ! isset( $services[ $data['service'] ] ) )
$this->setError( 'invalid_data', 'Invalid service.' );
if ( ! $this->hasErrors() ) {
try {
$result = $this->client()->validate_collivery( $data, $this->token );
} catch (SoapFault $e) {
$this->catchSoapFault( $e );
return false;
}
if ( is_array( $result ) ) {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
return $result;
} else {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
else
$this->setError( 'result_unexpected', 'No address_id returned.' );
return false;
}
}
}
/**
* Creates a new Collivery based on the data array provided.
* The array should first be validated before passing to this function.
* The Waybill No is return apon successful creation of the collivery.
*
* @param array $data Properties of the new Collivery
* @return int New Collivery ID
*/
public function addCollivery( array $data )
{
$contacts_from = $this->getContacts( $data['collivery_from'] );
$contacts_to = $this->getContacts( $data['collivery_to'] );
$parcel_types = $this->getParcelTypes();
$services = $this->getServices();
if ( ! isset( $data['collivery_from'] ) )
$this->setError( 'missing_data', 'collivery_from not set.' );
elseif ( ! is_array( $this->getAddress( $data['collivery_from'] ) ) )
$this->setError( 'invalid_data', 'Invalid Address ID for: collivery_from.' );
if ( ! isset( $data['contact_from'] ) )
$this->setError( 'missing_data', 'contact_from not set.' );
elseif ( ! isset( $contacts_from[ $data['contact_from'] ] ) )
$this->setError( 'invalid_data', 'Invalid Contact ID for: contact_from.' );
if ( ! isset( $data['collivery_to'] ) )
$this->setError( 'missing_data', 'collivery_to not set.' );
elseif ( ! is_array( $this->getAddress( $data['collivery_to'] ) ) )
$this->setError( 'invalid_data', 'Invalid Address ID for: collivery_to.' );
if ( ! isset( $data['contact_to'] ) )
$this->setError( 'missing_data', 'contact_to not set.' );
elseif ( ! isset( $contacts_to[ $data['contact_to'] ] ) )
$this->setError( 'invalid_data', 'Invalid Contact ID for: contact_to.' );
if ( ! isset( $data['collivery_type'] ) )
$this->setError( 'missing_data', 'collivery_type not set.' );
elseif ( ! isset( $parcel_types[ $data['collivery_type'] ] ) )
$this->setError( 'invalid_data', 'Invalid collivery_type.' );
if ( ! isset( $data['service'] ) )
$this->setError( 'missing_data', 'service not set.' );
elseif ( ! isset( $services[ $data['service'] ] ) )
$this->setError( 'invalid_data', 'Invalid service.' );
if ( ! $this->hasErrors() ) {
try {
$result = $this->client()->add_collivery( $data, $this->token );
} catch (SoapFault $e) {
$this->catchSoapFault( $e );
return false;
}
if ( isset( $result['collivery_id'] ) ) {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
return $result['collivery_id'];
} else {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
else
$this->setError( 'result_unexpected', 'No address_id returned.' );
return false;
}
}
}
/**
* Accepts the newly created Collivery, moving it from Waiting Client Acceptance
* to Accepted so that it can be processed.
*
* @param int $collivery_id ID of the Collivery you wish to accept
* @return boolean Has the Collivery been accepted
*/
public function acceptCollivery( $collivery_id )
{
try {
$result = $this->client()->accept_collivery( $collivery_id, $this->token );
} catch (SoapFault $e) {
$this->catchSoapFault( $e );
return false;
}
if ( isset( $result['result'] ) ) {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
return $result['result'] == 'Accepted';
} else {
if ( isset( $result['error_id'] ) )
$this->setError( $result['error_id'], $result['error'] );
else
$this->setError( 'result_unexpected', 'No address_id returned.' );
return false;
}
}
/**
* Handle error messages in SoapFault
*
* @param SoapFault $e SoapFault Object
*/
protected function catchSoapFault( $e )
{
$this->setError( $e->faultcode, $e->faultstring );
}
/**
* Add a new error
*
* @param string $id Error ID
* @param string $text Error text
*/
protected function setError( $id, $text )
{
$this->errors[ $id ] = $text;
}
/**
* Retrieve errors
*/
public function getErrors()
{
return $this->errors;
}
/**
* Check if this instance has an error
*/
public function hasErrors()
{
return !empty($this->errors);
}
/**
* Clears all the Errors
*/
public function clearErrors()
{
$this->errors = array();
}
/**
* Disable Cached completely and retrieve data directly from the webservice
*/
public function disableCache()
{
$this->check_cache = 0;
}
/**
* Ignore Cached data and retrieve data directly from the webservice
* Save returned data to Cache
*/
public function ignoreCache()
{
$this->check_cache = 1;
}
/**
* Check if cache exists before querying the webservice
* If webservice was queried, save returned data to Cache
*/
public function enableCache()
{
$this->check_cache = 2;
}
}
Enable javascript to submit You have javascript disabled. You will not be able to edit any code.
Here you find the average performance (time & memory) of each version. A grayed out version indicates it didn't complete successfully (based on exit-code).
Version System time (s) User time (s) Memory (MiB) 7.4.0 0.008 0.010 14.89 7.3.12 0.007 0.006 14.82 7.3.11 0.005 0.014 14.81 7.3.10 0.005 0.013 14.75 7.3.9 0.005 0.009 15.00 7.3.8 0.006 0.007 14.89 7.3.7 0.011 0.005 14.82 7.3.6 0.008 0.007 14.74 7.3.5 0.005 0.007 14.80 7.3.4 0.005 0.005 14.90 7.3.3 0.006 0.006 14.77 7.3.2 0.006 0.006 16.57 7.3.1 0.009 0.006 16.40 7.3.0 0.006 0.007 16.24 7.2.25 0.003 0.016 15.00 7.2.24 0.008 0.010 15.16 7.2.23 0.003 0.009 15.03 7.2.22 0.004 0.013 15.17 7.2.21 0.006 0.009 15.04 7.2.20 0.007 0.008 14.76 7.2.19 0.003 0.009 14.85 7.2.18 0.005 0.010 14.76 7.2.17 0.003 0.012 15.11 7.2.16 0.007 0.007 15.04 7.2.15 0.005 0.008 16.71 7.2.14 0.006 0.011 16.63 7.2.13 0.005 0.009 16.80 7.2.12 0.006 0.006 16.56 7.2.11 0.007 0.009 16.59 7.2.10 0.012 0.006 16.69 7.2.9 0.005 0.009 16.81 7.2.8 0.005 0.007 16.77 7.2.7 0.006 0.006 16.60 7.2.6 0.008 0.006 16.66 7.2.5 0.007 0.004 16.69 7.2.4 0.006 0.010 16.70 7.2.3 0.003 0.010 16.62 7.2.2 0.004 0.011 16.52 7.2.1 0.006 0.008 16.56 7.2.0 0.007 0.004 16.66 7.1.33 0.003 0.011 15.58 7.1.32 0.006 0.006 15.58 7.1.31 0.010 0.003 15.57 7.1.30 0.003 0.010 15.73 7.1.29 0.002 0.013 15.53 7.1.28 0.006 0.004 15.38 7.1.27 0.007 0.007 15.47 7.1.26 0.005 0.007 15.52 7.1.25 0.004 0.008 15.44 7.1.24 0.005 0.005 15.62 7.1.23 0.002 0.012 15.56 7.1.22 0.007 0.008 15.66 7.1.21 0.005 0.008 15.46 7.1.20 0.007 0.007 15.31 7.1.19 0.004 0.009 15.63 7.1.18 0.005 0.009 15.66 7.1.17 0.011 0.006 15.56 7.1.16 0.005 0.009 15.50 7.1.15 0.002 0.012 15.58 7.1.14 0.005 0.011 15.55 7.1.13 0.010 0.006 15.68 7.1.12 0.004 0.005 15.64 7.1.11 0.006 0.008 15.55 7.1.10 0.003 0.010 15.51 7.1.9 0.005 0.010 15.71 7.1.8 0.006 0.008 15.74 7.1.7 0.005 0.008 15.76 7.1.6 0.005 0.013 16.88 7.1.5 0.005 0.012 15.95 7.1.4 0.005 0.009 15.60 7.1.3 0.009 0.004 15.59 7.1.2 0.003 0.009 15.40 7.1.1 0.007 0.007 15.59 7.1.0 0.004 0.020 17.95 7.0.33 0.000 0.012 15.10 7.0.32 0.003 0.010 15.28 7.0.31 0.002 0.010 15.23 7.0.30 0.006 0.009 15.02 7.0.29 0.005 0.007 15.12 7.0.28 0.009 0.006 15.09 7.0.27 0.005 0.008 15.34 7.0.26 0.004 0.007 15.10 7.0.25 0.006 0.009 15.24 7.0.24 0.006 0.008 15.29 7.0.23 0.009 0.005 15.45 7.0.22 0.008 0.005 15.07 7.0.21 0.006 0.006 15.20 7.0.20 0.017 0.007 15.65 7.0.19 0.006 0.006 15.24 7.0.18 0.008 0.007 15.13 7.0.17 0.008 0.005 15.35 7.0.16 0.002 0.010 15.23 7.0.15 0.005 0.006 15.13 7.0.14 0.003 0.030 17.48 7.0.13 0.003 0.007 15.27 7.0.12 0.007 0.003 15.14 7.0.11 0.002 0.011 15.15 7.0.10 0.009 0.030 16.80 7.0.9 0.015 0.031 16.97 7.0.8 0.007 0.033 16.77 7.0.7 0.005 0.031 16.90 7.0.6 0.016 0.017 16.90 7.0.5 0.008 0.021 17.03 7.0.4 0.007 0.027 15.51 7.0.3 0.006 0.036 15.65 7.0.2 0.004 0.027 15.51 7.0.1 0.008 0.029 15.47 7.0.0 0.006 0.019 15.53 5.6.40 0.004 0.007 14.37 5.6.39 0.002 0.008 14.30 5.6.38 0.007 0.007 14.11 5.6.37 0.005 0.010 14.05 5.6.36 0.009 0.004 14.36 5.6.35 0.002 0.013 14.13 5.6.34 0.005 0.006 14.09 5.6.33 0.005 0.011 14.19 5.6.32 0.008 0.009 14.27 5.6.31 0.007 0.006 14.42 5.6.30 0.006 0.008 14.32 5.6.29 0.002 0.011 14.35 5.6.28 0.004 0.030 16.49 5.6.27 0.004 0.012 14.41 5.6.26 0.009 0.006 14.09 5.6.25 0.005 0.033 16.47 5.6.24 0.007 0.030 16.43 5.6.23 0.006 0.029 16.45 5.6.22 0.008 0.031 16.29 5.6.21 0.005 0.019 16.29 5.6.20 0.008 0.033 16.52 5.6.19 0.008 0.035 16.36 5.6.18 0.008 0.032 16.56 5.6.17 0.007 0.024 16.57 5.6.16 0.007 0.022 16.59 5.6.15 0.005 0.031 16.43 5.6.14 0.009 0.033 16.67 5.6.13 0.003 0.038 16.65 5.6.12 0.009 0.036 16.47 5.6.11 0.002 0.025 16.59 5.6.10 0.011 0.026 16.52 5.6.9 0.011 0.020 16.51 5.6.8 0.002 0.021 16.24 5.6.7 0.006 0.031 16.17 5.6.6 0.006 0.025 16.21 5.6.5 0.008 0.018 16.06 5.6.4 0.010 0.028 16.18 5.6.3 0.010 0.026 16.23 5.6.2 0.007 0.034 16.27 5.6.1 0.008 0.022 16.16 5.6.0 0.006 0.032 16.13 5.5.38 0.007 0.032 16.15 5.5.37 0.005 0.022 16.17 5.5.36 0.011 0.020 16.23 5.5.35 0.012 0.024 16.13 5.5.34 0.007 0.027 16.44 5.5.33 0.008 0.019 16.35 5.5.32 0.007 0.033 16.37 5.5.31 0.005 0.033 16.32 5.5.30 0.007 0.033 16.26 5.5.29 0.004 0.038 16.46 5.5.28 0.010 0.029 16.37 5.5.27 0.006 0.018 16.20 5.5.26 0.008 0.033 16.25 5.5.25 0.002 0.028 16.05 5.5.24 0.004 0.032 16.10 5.5.23 0.009 0.029 16.08 5.5.22 0.006 0.024 16.12 5.5.21 0.005 0.029 16.13 5.5.20 0.006 0.030 16.11 5.5.19 0.006 0.032 16.11 5.5.18 0.005 0.035 16.14 5.5.17 0.002 0.012 13.97 5.5.16 0.008 0.029 16.15 5.5.15 0.007 0.032 16.22 5.5.14 0.005 0.028 16.07 5.5.13 0.006 0.029 16.05 5.5.12 0.009 0.024 16.06 5.5.11 0.011 0.034 16.14 5.5.10 0.004 0.029 15.99 5.5.9 0.010 0.024 16.02 5.5.8 0.004 0.022 16.04 5.5.7 0.006 0.033 15.89 5.5.6 0.008 0.026 16.03 5.5.5 0.007 0.027 16.07 5.5.4 0.006 0.027 15.99 5.5.3 0.011 0.028 15.93 5.5.2 0.009 0.027 15.83 5.5.1 0.004 0.021 16.16 5.5.0 0.006 0.027 16.06 5.4.45 0.004 0.030 13.90 5.4.44 0.004 0.024 13.81 5.4.43 0.009 0.016 13.86 5.4.42 0.010 0.027 13.91 5.4.41 0.006 0.028 13.84 5.4.40 0.004 0.019 13.75 5.4.39 0.006 0.032 13.75 5.4.38 0.005 0.027 13.68 5.4.37 0.008 0.022 13.76 5.4.36 0.010 0.019 13.77 5.4.35 0.005 0.027 13.76 5.4.34 0.008 0.022 13.75 5.4.33 0.003 0.005 11.08 5.4.32 0.006 0.030 13.75 5.4.31 0.007 0.018 13.70 5.4.30 0.009 0.026 13.74 5.4.29 0.005 0.027 13.80 5.4.28 0.008 0.026 13.80 5.4.27 0.009 0.026 13.77 5.4.26 0.005 0.034 13.75 5.4.25 0.007 0.014 13.71 5.4.24 0.007 0.028 13.77 5.4.23 0.005 0.021 13.79 5.4.22 0.007 0.028 13.80 5.4.21 0.004 0.029 13.74 5.4.20 0.003 0.020 13.74 5.4.19 0.005 0.032 13.75 5.4.18 0.002 0.019 13.75 5.4.17 0.010 0.022 13.72 5.4.16 0.005 0.032 13.81 5.4.15 0.012 0.022 13.69 5.4.14 0.005 0.024 12.85 5.4.13 0.002 0.021 12.90 5.4.12 0.011 0.019 12.88 5.4.11 0.009 0.020 12.85 5.4.10 0.003 0.031 12.86 5.4.9 0.004 0.025 12.88 5.4.8 0.005 0.029 12.91 5.4.7 0.006 0.028 12.92 5.4.6 0.006 0.024 12.85 5.4.5 0.007 0.025 12.88 5.4.4 0.006 0.029 12.89 5.4.3 0.005 0.029 12.86 5.4.2 0.006 0.027 12.95 5.4.1 0.007 0.027 12.86 5.4.0 0.006 0.016 12.63 5.3.29 0.004 0.030 12.32 5.3.28 0.008 0.019 12.28 5.3.27 0.006 0.028 12.28 5.3.26 0.004 0.021 12.33 5.3.25 0.005 0.027 12.30 5.3.24 0.007 0.027 12.31 5.3.23 0.001 0.020 12.34 5.3.22 0.006 0.031 12.29 5.3.21 0.009 0.028 12.30 5.3.20 0.006 0.019 12.30 5.3.19 0.001 0.035 12.27 5.3.18 0.007 0.020 12.29 5.3.17 0.007 0.025 12.29 5.3.16 0.004 0.031 12.27 5.3.15 0.005 0.019 12.28 5.3.14 0.008 0.026 12.27 5.3.13 0.005 0.027 12.29 5.3.12 0.005 0.030 12.29 5.3.11 0.004 0.019 12.31 5.3.10 0.002 0.032 12.12 5.3.9 0.003 0.021 12.10 5.3.8 0.004 0.024 12.10 5.3.7 0.004 0.016 12.10 5.3.6 0.002 0.018 12.15 5.3.5 0.002 0.030 12.06 5.3.4 0.003 0.030 12.10 5.3.3 0.002 0.021 12.04 5.3.2 0.006 0.015 12.01 5.3.1 0.004 0.027 11.98 5.3.0 0.001 0.026 12.00
preferences:dark mode live preview
38.03 ms | 401 KiB | 5 Q