PHP 7.1+ Swoole v1.9.5 vs Node.js Benchmark Test PHP7 + Swoole beats Node.js

I’d like to introduce this Swoole PHP extension:

Event-driven asynchronous & concurrent & coroutine networking engine with high performance for PHP.http://www.swoole.com/

This is a game-changing extension that would change how PHP works.

According to the bench mark here, it’s 12 times faster than Node.js.

Try swoole extension.

  • Ubuntu 16.04 LTS
  • Intel® Core™ i5-4590 CPU @ 3.30GHz × 4
  • 16G Memory
<?php
$http = new swoole_http_server("127.0.0.1", 1337, SWOOLE_BASE);

$http->set([
    'worker_num' => 4,
]);

$data = [
  'code' => 'ok',
  'error' => false,
  'payload' => 'Hello World'
];

$http->on('request', function ($request, swoole_http_response $response)  use($data)  {
    $response->header('Content-Type', 'application/json');   
    $response->end(json_encode($data));
});

$http->start();

Node.js v4.2.6

wrk -t4 -c400 -d10s http://127.0.0.1:1337/
Running 10s test @ http://127.0.0.1:1337/
  4 threads and 400 connections
  Thread Stats   Avg      Stdev     Max   +/- Stdev
    Latency    16.08ms    2.70ms 237.82ms   90.94%
    Req/Sec     6.05k   510.34     7.10k    91.00%
  240668 requests in 10.02s, 46.36MB read
Requests/sec:  24026.00
Transfer/sec:      4.63MB

PHP7.1+Swoole-v1.9.5

wrk -t4 -c400 -d10s http://127.0.0.1:1337/
Running 10s test @ http://127.0.0.1:1337/
  4 threads and 400 connections
  Thread Stats   Avg      Stdev     Max   +/- Stdev
    Latency     1.46ms    1.42ms  27.96ms   85.66%
    Req/Sec    75.29k    36.43k  183.55k    72.75%
  3007806 requests in 10.06s, 605.25MB read
Requests/sec: 299103.32
Transfer/sec:     60.19MB

 

 

What is the difference between MVC and MVVM?

Is there a difference between the standard “Model View Controller” pattern and Microsoft’s Model/View/ViewModel pattern?

MVC/MVVM is not an either/or choice.

The two patterns crop up, in different ways, in both ASP.Net and Silverlight/WPF development.

For ASP.Net, MVVM is used to two-way bind data within views. This is usually a client-side implementation (e.g. using Knockout.js). MVC on the other hand is a way of separating concerns on the server-side.

For Silverlight and WPF, the MVVM pattern is more encompassing and can appear to act as a replacement for MVC (or other patterns of organising software into separate responsibilities). One assumption, that frequently came out of this pattern, was that the ViewModel simply replaced the controller in MVC (as if you could just substitute VM for C in the acronym and all would be forgiven)…

The ViewModel does not necessarily replace the need for separate Controllers.

The problem is: that to be independently testable*, and especially reusable when needed, a view-model has no idea what view is displaying it, but more importantly no idea where its data is coming from.

*Note: in practice Controllers remove most of the logic, from the ViewModel, that requires unit testing. The VM then becomes a dumb container that requires little, if any, testing. This is a good thing as the VM is just a bridge, between the designer and the coder, so should be kept simple.

Even in MVVM, controllers will typically contain all processing logic and decide what data to display in which views using which view models.

From what we have seen so far the main benefit of the ViewModel pattern to remove code from XAML code-behind to make XAML editing a more independent task. We still create controllers, as and when needed, to control (no pun intended) the overall logic of our applications.

The basic MVCVM guidelines we follow are:

  • Views display a certain shape of data. They have no idea where the data comes from.
  • ViewModels hold a certain shape of data and commands, they do not know where the data, or code, comes from or how it is displayed.
  • Models hold the actual data (various context, store or other methods)
  • Controllers listen for, and publish, events. Controllers provide the logic that controls what data is seen and where. Controllers provide the command code to the ViewModel so that the ViewModel is actually reusable.

We also noted that the Sculpture code-gen framework implements MVVM and a pattern similar to Prism AND it also makes extensive use of controllers to separate all use-case logic.

Don’t assume controllers are made obsolete by View-models.

I have started a blog on this topic which I will add to as and when I can. There are issues with combining MVCVM with the common navigation systems, as most navigation systems just use Views and VMs, but I will go into that in later articles.

An additional benefit of using an MVCVM model is that only the controller objects need to exist in memory for the life of the application and the controllers contain mainly code and little state data (i.e. tiny memory overhead). This makes for much less memory-intensive apps than solutions where view-models have to be retained and it is ideal for certain types of mobile development (e.g. Windows Mobile using Silverlight/Prism/MEF). This does of course depend on the type of application as you may still need to retain the occasional cached VMs for responsiveness.

Note: This post has been edited numerous times, and did not specifically target the narrow question asked, so I have updated the first part to now cover that too. Much of the discussion, in comments below, relates only to ASP.Net and not the broader picture. This post was intended to cover the broader use of MVVM in Silverlight, WPF and ASP.Net and try avoid people replacing controllers with ViewModels

Fix fatal error for inlcude path and included file not existed using include or require for cron job

When running php in cron, the include and require path may not work.

Eg. when your file has below require or include statement:

require '../includes/common.php';

You will get a fatal error when running using php-cli or php-cli in cron

# php-cli
php /home/username123/public_html/cron/mycronjob.php
# cron
* * * * * php /home/username123/public_html/cron/mycronjob.php

Error got:

Fatal error: require(): Failed opening required '../includes/common.php'
 (include_path='.:/usr/lib/php:/usr/local/lib/php') in
 /home/username123/public_html/cron/mycronjob.php on line 2

To fix this, you need to use php to set include_path attributes so when running cron it’ll set the path so the script will learn where to look for the include / require files.

set_include_path

reference: http://php.net/manual/en/function.set-include-path.php

example:

set_include_path('/home/username123/public_html/includes/');
require 'common.php';

Frontend User Roles Manager Bugs fixes – for OctoberCMS Shahiem Seymor

http://octobercms.com/index.php/plugin/shahiemseymor-roles

Error: Trigger action is not specified

Fix Error: Trigger action is not specified as per https://github.com/octobercms/october/issues/1543
_list_toolbar.htm
data-trigger-action=”enable”
the above need to be added to the button

Yaml / configuration file not found error

Found some bugs in:

  1. /plugins/shahiemseymor/roles/controllers/groups/config_form.yaml
  2. /plugins/shahiemseymor/roles/controllers/groups/config_list.yaml
  3. /plugins/shahiemseymor/roles/controllers/permissions/config_form.yaml
  4. /plugins/shahiemseymor/roles/controllers/permissions/config_list.yaml

Instead of full paths to the config files with ~ or @ you can change it to $/shahiemseymor/roles/controllers/groups/config_form.yaml etc. In the last builds (347, 348) of October I’m getting errors because you used @ in /plugins/shahiemseymor/roles/controllers/groups/config_list.yaml

 

Date calculators – Date to Date Calculator, Business Date Calculator and more

This website (www.timeanddate.com/date/) comes with a lot of date time calculators handy:

Date and Time Calculators

Date to Date Calculator

Find out how many days, months and years there are between any two dates.

Date Calculator

Add or subtract any number of days to/from a start date.

Time Duration Calculator

Find the precise duration between two dates and times — down to the second.

Time Calculator

Add or subtract days, hours, minutes, and seconds to/from a start date and time.

Business Date to Date Calc.

Exclude holidays and weekend days from your date-to-date calculation.

Business Date Calculator

Add or subtract days, excluding holidays and weekend days.

 

Astronomical Sun & Moon Calculators

Sun Calculator

Sunrise & Sunset

Day length, azimuth, distance etc.

Eclipse Calculator

With 2 speed animation! Local times for Solar and Lunar Eclipses and what it will look like.

Astrononmical Seasons Calculator

Equinoxes and Solstices mark the beginning of a new astronomical sesason. Local dates and times.

Moon Calculator

Moonrise & Moonset

Direction, illumination percentage etc.

Moon Phases

New Moon, 1st Quarter, Full Moon, and 3rd Quarter. Local times worldwide.

Day and Night World Map

LIVE Map: Showing the Sun’s and Moon’s position in the sky with daylight and night time.

Week Calculators

Search Time Icon

Weekday Calculator

Find out the day of the week for a date of your choice.

Or learn to do this calculation in your head.

Week Number Calculator

Calculate the week number for a date or locate any week number on a calendar.

Time & Distance

Time Zone Converter

Find the time difference between two cities.

Distance Calculator

How far is it?

Travel Time Calculator

Time zone conversions for your flight.

International Dialing Codes

Which country & area codes do I have to dial?

Source:

https://www.timeanddate.com/date/

 

Get sizes of all databases in phpMyAdmin

If you logged in as root account you’ll be able to see the default information_schema database, and the data was included in “TABLES” table.

In order to more readable stats, you can run the following command, this will output the formatted result:

SELECT table_schema "Data Base Name",
sum( data_length + index_length ) / 1024 / 1024 "Data Base Size in MB"
FROM information_schema.TABLES GROUP BY table_schema;

source:

Get database size in phpMyAdmin

My custom logging class for PHP

// based on log class from http://www.redips.net/php/write-to-log-file/
class SysLog {
 const DEFAULT_LOG_PATH = '/var/log/httpd/mylog.log';
 // declare log file and file pointer as private properties
 private $log_file;
 private $fp;
 public $clientIp;
 // the altLogPath could be set after instance has been created
 public $altLogPath;
 // set log file (path and name)
 public $internalIpOnly;

 /**
 * Whether to use proxy addresses or not.
 * As default this setting is disabled - IP address is mostly needed to increase
 * security. HTTP_* are not reliable since can easily be spoofed. It can be enabled
 * just for more flexibility, but if user uses proxy to connect to trusted services
 * it's his/her own risk, only reliable field for IP address is $_SERVER['REMOTE_ADDR'].
 * @var bool
 */
 protected $useProxy = false;

 /**
 * List of trusted proxy IP addresses
 * @var array
 */
 protected $trustedProxies = array();

 /**
 * HTTP header to introspect for proxies
 * @var string
 */
 protected $proxyHeader = 'HTTP_X_FORWARDED_FOR';

 function SysLog()
 {
 $this->clientIp = $this->getIpAddress();
 }
 public function lfile($path = null) {
 $this->log_file = $path;
 }
 // write message to the log file
 public function lwrite($message) {
 // if file pointer doesn't exist, then open log file
 if (!is_resource($this->fp)) {
 $this->lopen();
 }
 // define script name
 // for PHP 5.2.0+
 // $script_name = pathinfo($_SERVER['PHP_SELF'], PATHINFO_FILENAME);
 // for PHP version <= 5.2.0
 $script_name = basename($_SERVER['PHP_SELF']);
 // $script_name = substr($script_name, 0, -4); // php extension and dot are not needed
 $script_name = getcwd() . DIRECTORY_SEPARATOR . $script_name;
 // define current time and suppress E_WARNING if using the system TZ settings
 // (don't forget to set the INI setting date.timezone)
 $time = @date('[d/M/Y:H:i:s]');
 // write current time, script name and message to the log file
 fwrite($this->fp, "$time ($script_name) \n$message" . PHP_EOL);
 }
 // short name for lwrite
 public function log($message) {
 $this->lwrite($message);
 }
 // takes arrays and objects as params
 public function logdump($someObj) {
 $this->log(print_r($someObj, true));
 }
 // close log file (it's always a good idea to close a file when you're done with it)
 public function lclose() {
 fclose($this->fp);
 }
 // open log file (private method)
 private function lopen() {
 // in case of Windows set default log file
 if (strtoupper(substr(PHP_OS, 0, 3)) === 'WIN') {
 $log_file_default = 'c:/php/logfile.txt';
 } elseif(isset($this->altLogPath)) {
 // alternative log path could be set, require full path;
 $log_file_default = $this->altLogPath;
 } else {
 // set default log file for Linux and other systems
 $log_file_default = self::DEFAULT_LOG_PATH;
 }
 // define log file from lfile method or use previously set default
 $lfile = $this->log_file ? $this->log_file : $log_file_default;
 // open log file for writing only and place file pointer at the end of the file
 // (if the file does not exist, try to create it)
 $this->fp = fopen($lfile, 'a') or exit("Can't open $lfile!");
 }

 /**
 * Returns client IP address.
 *
 * @return string IP address.
 */
 public function getIpAddress()
 {
 $ip = $this->getIpAddressFromProxy();
 if ($ip) {
 return $ip;
 }

 // direct IP address
 if (isset($_SERVER['REMOTE_ADDR'])) {
 return $_SERVER['REMOTE_ADDR'];
 }

 return '';
 }

 /**
 * Attempt to get the IP address for a proxied client
 *
 * @see http://tools.ietf.org/html/draft-ietf-appsawg-http-forwarded-10#section-5.2
 * @return false|string
 */
 protected function getIpAddressFromProxy()
 {
 if (!$this->useProxy
 || (isset($_SERVER['REMOTE_ADDR']) && !in_array($_SERVER['REMOTE_ADDR'], $this->trustedProxies))
 ) {
 return false;
 }

 $header = $this->proxyHeader;
 if (!isset($_SERVER[$header]) || empty($_SERVER[$header])) {
 return false;
 }

 // Extract IPs
 $ips = explode(',', $_SERVER[$header]);
 // trim, so we can compare against trusted proxies properly
 $ips = array_map('trim', $ips);
 // remove trusted proxy IPs
 $ips = array_diff($ips, $this->trustedProxies);

 // Any left?
 if (empty($ips)) {
 return false;
 }

 // Since we've removed any known, trusted proxy servers, the right-most
 // address represents the first IP we do not know about -- i.e., we do
 // not know if it is a proxy server, or a client. As such, we treat it
 // as the originating IP.
 // @see http://en.wikipedia.org/wiki/X-Forwarded-For
 $ip = array_pop($ips);
 return $ip;
 }
}

Delete all Duplicate Rows except for One record in MySQL

NB – You need to do this first on a test copy of your table!

When I did it, I found that unless I also included AND n1.id <> n2.id, it deleted every row in the table.

1) If you want to keep the row with the lowest id value:

DELETE n1 FROM names n1, names n2 WHERE n1.id > n2.id AND n1.name = n2.name

2) If you want to keep the row with the highest id value:

DELETE n1 FROM names n1, names n2 WHERE n1.id < n2.id AND n1.name = n2.name

I used this method in MySQL 5.1

Not sure about other versions.

Update: Since people Googling for removing duplicates end up here
Although the OP’s question is about DELETE, please be advised that using INSERT and DISTINCT is much faster. For a database with 8 million rows, the below query took 13 minutes, while using DELETE, it took more than 2 hours and yet didn’t complete.

INSERT INTO tempTableName(cellId,attributeId,entityRowId,value)
 SELECT DISTINCT cellId,attributeId,entityRowId,value
 FROM tableName;

Reference:

http://stackoverflow.com/questions/4685173/delete-all-duplicate-rows-except-for-one-in-mysql

Additional information

DELETE 
 t1 
FROM 
 tTable t1, tTable t2 
WHERE 
 t1.fieldName = t2.fieldName AND t1.id > t2.id

ELSE

create another table as below

CREATE TABLE myTable_new (ID INT PRIMARY KEY, Title varchar(20))

and add values as

INSERT INTO myTable_new (ID, Title) SELECT ID, DISTINCT Title FROM old_table

considering old_table is the earlier table…

source: http://stackoverflow.com/questions/9452320/remove-duplicate-records-except-one-record

NPath complexity and cyclomatic complexity explained

Both terms are used to determine the complexity of code. It’s always good to keep your code simple and readable as referred in KISS principle.

CyclomaticComplexity
https://phpmd.org/rules/codesize.html

Complexity is determined by the number of decision points in a method plus one for the method entry. The decision points are ‘if’, ‘while’, ‘for’, and ‘case labels’. Generally, 1-4 is low complexity, 5-7 indicates moderate complexity, 8-10 is high complexity, and 11+ is very high complexity.

NPath complexity

The NPath complexity of a method is the number of acyclic execution paths through that method.

References:

ttps://www.tutorialspoint.com/software_testing_dictionary/cyclomatic_complexity.htm

https://modess.io/npath-complexity-cyclomatic-complexity-explained/

Markup accessing page parameters as object or array for OctoberCMS

You can access the current URL parameters via this.param and it returns a PHP array.

Accessing page parameters

This example demonstrates how to access the tab URL parameter in a page.

url = "/account/:tab"
==
{% if this.param.tab == 'details' %}

    

Here are all your details

{% elseif this.param.tab == 'history' %}

You are viewing a blast from the past

{% endif %}

If the parameter name is also a variable, then array syntax can be used.

url = "/account/:post_id"
==
{% set name = 'post_id' %}

The post ID is: {{ this.param[name] }}

Detect iOS in OctoberCMS to differ the script or other resources loads

in the “code” section of the CMS page editor

put in below codes

function onStart()
{
 //Detect special conditions devices
 $iPod = stripos($_SERVER['HTTP_USER_AGENT'],"iPod");
 $iPhone = stripos($_SERVER['HTTP_USER_AGENT'],"iPhone");
 $iPad = stripos($_SERVER['HTTP_USER_AGENT'],"iPad");
 $Android = stripos($_SERVER['HTTP_USER_AGENT'],"Android");
 $webOS = stripos($_SERVER['HTTP_USER_AGENT'],"webOS");

 $this['isIos'] = false;

 //do something with this information
 if( $iPod || $iPhone ) {
 //browser reported as an iPhone/iPod touch -- do something here
 $this['isIos']= true;
 } else if($iPad) {
 //browser reported as an iPad -- do something here
 $this['isIos']= true;
 } else if($Android) {
 //browser reported as an Android device -- do something here
 $this['isIos']= false;
 } else if($webOS) {
 //browser reported as a webOS device -- do something here
 $this['isIos']= false;
 }
 //var_dump($this['isIos']);
}

then you can call the isIos variables in html section

{% if isIos %}
{% partial “some-partial-for-ios” %}
{% else %}
{% partial “some-partial-not-for-ios” %}
{% endif %}

reference: http://stackoverflow.com/questions/6322112/check-if-php-page-is-accessed-from-an-ios-device

 

TCPDF – PHP library for generating PDF documents on-the-fly

This is a PDF generation library that does not require external libraries for basic functions, image processing will need GD but that’s all.

In short this is a PDF generator lib with minimum system requirements, you can integrate it to some older projects.

So if you have an old server with PHP 5.2 / 5.3 and can not install anything like ImageMagicX, you can try this out.

Main Features:

  • no external libraries are required for the basic functions;

  • all standard page formats, custom page formats, custom margins and units of measure;

  • UTF-8 Unicode and Right-To-Left languages;

  • TrueTypeUnicode, OpenTypeUnicode v1, TrueType, OpenType v1, Type1 and CID-0 fonts;

  • font subsetting;

  • methods to publish some XHTML + CSS code, Javascript and Forms;

  • images, graphic (geometric figures) and transformation methods;

  • supports JPEG, PNG and SVG images natively, all images supported by GD (GD, GD2, GD2PART, GIF, JPEG, PNG, BMP, XBM, XPM) and all images supported via ImagMagick (http://www.imagemagick.org/script/formats.php)

  • 1D and 2D barcodes: CODE 39, ANSI MH10.8M-1983, USD-3, 3 of 9, CODE 93, USS-93, Standard 2 of 5, Interleaved 2 of 5, CODE 128 A/B/C, 2 and 5 Digits UPC-Based Extension, EAN 8, EAN 13, UPC-A, UPC-E, MSI, POSTNET, PLANET, RMS4CC (Royal Mail 4-state Customer Code), CBC (Customer Bar Code), KIX (Klant index – Customer index), Intelligent Mail Barcode, Onecode, USPS-B-3200, CODABAR, CODE 11, PHARMACODE, PHARMACODE TWO-TRACKS, Datamatrix, QR-Code, PDF417;

  • JPEG and PNG ICC profiles, Grayscale, RGB, CMYK, Spot Colors and Transparencies;

  • automatic page header and footer management;

  • document encryption up to 256 bit and digital signature certifications;

  • transactions to UNDO commands;

  • PDF annotations, including links, text and file attachments;

  • text rendering modes (fill, stroke and clipping);

  • multiple columns mode;

  • no-write page regions;

  • bookmarks, named destinations and table of content;

  • text hyphenation;

  • text stretching and spacing (tracking);

  • automatic page break, line break and text alignments including justification;

  • automatic page numbering and page groups;

  • move and delete pages;

  • page compression (requires php-zlib extension);

  • XOBject Templates;

  • Layers and object visibility.

  • PDF/A-1b support.

on GitHub: https://github.com/tecnickcom/TCPDF

 

Magento Marketplace / B2B related extensions and solutions

Found some of the Magento extensions are quite sophisiticated and built-ready, while searching for the B2B solutions.

These could help you to come up with a Magento B2B / Marketplace e-commerce platform very quick.

Magento Builder Theme
https://www.magentocommerce.com/magento-connect/frontend-builder-theme.html ($9.00)

B2B / Market place
[Recommended] https://www.magentocommerce.com/magento-connect/marketplace.html (Magento Marketplace Multi Vendor Module US$349.00)
[Membership addon] http://webkul.com/blog/magento-marketplace-membership/ (US$149.00)
[Marketplace Mobile App] https://www.magentocommerce.com/magento-connect/marketplace-mobile-app.html (US$599.00)
author: https://www.magentocommerce.com/magento-connect/developer/webkul
https://www.magentocommerce.com/magento-connect/b2b-suite.html (US$250.00)
https://www.magentocommerce.com/magento-connect/marketplace-2.html (FREE)

Membership
https://www.magentocommerce.com/magento-connect/membership-program-for-magento.html (US$199.00)
https://www.magentocommerce.com/magento-connect/marketplace-membership.html (US$149.00)
https://www.magentocommerce.com/magento-connect/membership-subscription.html (US$149.00)
OR build with Magento recurring profile (membership as a vitual product with recurring payment requirement):
http://docs.magento.com/m1/ce/user_guide/catalog/product-recurring-profile.html

Payment gateway – WestPac and eWay
https://www.magentocommerce.com/magento-connect/fontis-westpac-payway-and-quickgateway.html (FREE) [up to Magento 1.7]
https://www.magentocommerce.com/magento-connect/fontis-eway-au.html (FREE) [eWay transaction fee: 1.6% per transaction]
https://www.magentocommerce.com/magento-connect/eway-rapid-australia.html (FREE)

Vtiger CRM Integration
https://www.magentocommerce.com/magento-connect/vtiger-magento-integration.html (US$299.99)
https://www.magentocommerce.com/magento-connect/vtiger-crm-integration.html (US$149.00)

Laravel E-commerce payment gateway packages

Laravel payment gateway solutions

Omnipay package
https://github.com/thephpleague/omnipay
Payway
https://github.com/Moult/omnipay-payway
PayPal on Laravel 5.2 code example
https://laracasts.com/discuss/channels/laravel/paypal-on-laravel-5222

 

WestPac payway official document
https://www.westpac.com.au/business-banking/merchant-services/online-payments/
https://www.payway.com.au/downloads/WBC/PayWay_API_Developers_Guide.pdf

Comparing Blade and Twig templates in Laravel

Blade and Twig, which one is better ? which one will be your choice?

Let’s read through the comparison article listed here: Comparing Blade and Twig templates in Laravel

In my company, we use Twig instead of Blade for our Laravel projects. I know there are a lot of developers that also prefer Twig over Blade. So the question‘Why choose Twig over Blade?’ often pops up. The reason is usually just a matter of preference, but in this post we’re going to compare the Blade and Twig templating engines side-by-side.

link: https://medium.com/@barryvdh/comparing-blade-and-twig-templates-in-laravel-187fde7fcac9