5 Types of Application Design

5 Types of Web Application Development Programs

Quick definition: A web application can run on any browser. Also, this application is used on tablets, laptops and computers. We will review the five most common web applications.

Shopping Applications

The shopping applications or e-commerce applications are developed for buying and selling products or services online. This application is difficult to design because it has to accept electronic payments and shipping information. Boise Custom Development can answer your questions about shopping applications.

Portal Application

Portal applications or online web portals are developed for email, forums and chats. This tool provides data that is easy to understand. For example, your online bank will allow you to submit questions about your account by sending an email using the web portal.

Dynamic Applications

Dynamic applications or web page is a database development program that is updated often. The site’s administrator will correct or change information on the page. For instance, the health department will update its site to post numbers about a specific disease each day. Boise Custom Development can help you get your dynamic project off the ground and running.

Animation Applications

Animation applications use computer flashing technology. This technology is widely used in cartoons and video games. The characters usually are telling stories that are made for small children.

Static Applications

Finally, static applications may include electronic resumes, business portfolios or a company’s web page. Static technology is located in the browser and not on the server. Most static applications are written in HTML format.

AWS RDS SSL/TLS Certificate Upgrade

It is best to start the certificate upgrade process by first testing it on a copy of the database to ensure that if there is an issue it will not effect live users.

The creation of a copy of the RDS database and Upgrade for the certificate process for the database on AWS is as follows:

Step 1. Overview: Download the root certificate and move it to your application and then setup a script on your live server to test the connection to a test instance of the RDS DB without effecting end users. (Instructions for this section are for php but you could use other languages to achieve the same thing.)

Download the root cert that works for all AWS Regions from  https://docs.aws.amazon.com/AmazonRDS/latest/UserGuide/UsingWithRDS.SSL.html 

Under the heading Using SSL/TLS to Encrypt a Connection to a DB Instance click on the link https://s3.amazonaws.com/rds-downloads/rds-ca-2019-root.pem (Only Download the Intermediate certificate for the region where the servers are located if the previous chain certificate does not work.  Make sure to choose from the column with the newest cert.)

Use filezilla or some other method of moving the certificate to the development server.  On one server we moved the certificate to /etc/ssl/certs/ and on another we moved it to /data/webs/[base file for site]/certs/.

(The following instructions were for a server using opsworks where we have dynamic scripts setup to create files on the instances through a deployment to a specific stack. If you are not using opsworks you could just move the file strait to your production server in the correct location and setup the permissions manually.)

OPSWorks Server: Modify the build scrip for the apache recipe to grab the version of the file on the development server, recreate it, and put it on the aws server in the right location.  

We added a section to the file like the following:

file ‘/etc/ssl/certs/rds-ca-2019-root.pem’ do
content <<-EOH<?=file_get_contents(“/etc/ssl/certs/rds-ca-2019-root.pem”)?>
  EOH
  mode ‘0644’
  owner ‘root’
  group ‘root’
end   

Run the build script from the custom developer opsworks area and verify the file shows up in the body of the apabche.rb recipe. Then deploy the recipe so it will be ran on the production stack on aws and create the file in the correct location. Go on one of the instances on the production stack and verify the file has been created.    

(End of OPSWORKS Server specific section.)

Modify your database connection for your site (ours was in a specific function controlling the connection and making it available to the rest of our pages) to change the connection string for a certificate requirement. 

Mysql database specific section:
For mysql databases we modified the line:

$dblink = mysqli_connect($server, $user, $pass);

To instead use:

$certpath=trim($_SERVER[‘DOCUMENT_ROOT’].’/certs/rds-ca-2019-root.pem’);
$dblink = mysqli_init();
$dblink->options(MYSQLI_OPT_SSL_VERIFY_SERVER_CERT, true);
$dblink->ssl_set(NULL, NULL, $certpath, NULL, NULL);
$dblink->real_connect($server, $user, $pass, $name);

We first left this new section of code commented out and modified our db_connect_single function so we could include a global variable testcertrequirements that was an array containing certpath and host. If this global variable was set we would use the data to override the default connection data so we could test the connection with a developer user without causing issues for our other users on the system. This is a snippet of the code for the connection function: (d function calls just display info for developers)

function db_connect_single($name, $user, $pass, $server='')
 {
     global $testcertrequirements;
     if($_GET[debug]||$_GET[db_connect_debug])
         d("db_connect_single($name, $user, $pass, $server='')");
     if(!$server)
         $server='localhost';
if (defined("ENVIRONMENT_CURRENT"))
    $currentenv=ENVIRONMENT_CURRENT;

if (
    (strtolower($currentenv)=='prod') 
    && $testcertrequirements 
    && is_array($testcertrequirements) 
    && trim($testcertrequirements['host']) 
    && trim($testcertrequirements['certpath'])
    && file_exists(trim($testcertrequirements['certpath']))
   ) //Method for testing new certificate requirements without effecting current users on AWS. 
{
    $server=trim($testcertrequirements['host']); //AWS end point for new test db instance spun up from snapshot in RDS and that is setup with the new certificate.
    d('$testcertrequirements[certpath]',trim($testcertrequirements['certpath']));
    d('$server',$server);
    $dblink = mysqli_init();
    $dblink->options(MYSQLI_OPT_SSL_VERIFY_SERVER_CERT, true);
    $dblink->ssl_set(NULL, NULL, trim($testcertrequirements['certpath']), NULL, NULL);
    $dblink->real_connect($server, $user, $pass, $name);
}
/*   
elseif(strtolower($currentenv)=='prod') //Default on aws is to use new cert since db updated to new cert.
{
    $certpath=trim($_SERVER['DOCUMENT_ROOT'].'/certs/rds-ca-2019-root.pem');
    $dblink = mysqli_init();
    $dblink->options(MYSQLI_OPT_SSL_VERIFY_SERVER_CERT, true);
    $dblink->ssl_set(NULL, NULL, $certpath, NULL, NULL);
    $dblink->real_connect($server, $user, $pass, $name);
}
*/
 else
{
    if($testcertrequirements)
    {
        d('<span style="color:red">DID NOT USE TEST CERT REQUIREMENT FOR CONNECTION</span>');
        d('using default connection and not dynamic one.');
        d('$currentenv',$currentenv);
        d('connecting using server:'.$server.' and not test certificate requirement');
        d('$testcertrequirements',$testcertrequirements);
        if(!file_exists(trim($testcertrequirements['certpath'])))
            d('Missing cert file:',trim($testcertrequirements['certpath']));
    }   
    $dblink = mysqli_connect($server, $user, $pass);
}

(End Mysql specific section)

Postgresql database specific section:
For postgresql databases we modified the lines:

$con_str = “host=$hostname port=$port dbname=$dbname user=$user password=”.$password;
timetrack(db_connect, $con_str);
$dbconn = pg_connect($con_str);

To instead use:

$addcertrequirement=””;
if(is_aws())
$addcertrequirement=” sslmode=’verify-full’ sslrootcert=’/etc/ssl/certs/rds-ca-2019-root.pem'”;

$con_str = “host=$hostname port=$port dbname=$dbname user=$user password=”.$password.$addcertrequirement;
$dbconn = pg_connect($con_str);

We first left this new section of code commented out and modified our db_connect function so we could include a global variable testcertrequirements that was an array containing certpath and host. If this global variable was set we would use the data to override the default connection data so we could test the connection with a developer user without causing issues for our other users on the system. This is a snippet of the code for the connection function: (d function calls just display info for developers)

global $testcertrequirements;
$addcertrequirement="";
/*
if(is_aws())
    $addcertrequirement=" sslmode='verify-full' sslrootcert='/etc/ssl/certs/rds-ca-2019-root.pem'";
*/
if($testcertrequirements && is_array($testcertrequirements) && trim($testcertrequirements['host']) && trim($testcertrequirements['certpath'])) //Method for testing new certificate requirements without effecting current users on AWS. 
{
    d('$testcertrequirements',$testcertrequirements);
    $addcertrequirement=" sslmode='verify-full' sslrootcert='".$testcertrequirements['certpath']."'";
    if(!is_aws())
        $addcertrequirement=" sslmode='prefer' sslrootcert='".$testcertrequirements['certpath']."'";
    else
        $hostname=trim($testcertrequirements['host']); //AWS end point for new test db instance spun up from snapshot in RDS and tht is setup with the new certificate.

    d('$addcertrequirement',$addcertrequirement);
    d('$hostname',$hostname);     
}
//decide which server to connect to based on the environment
$con_str = "host=$hostname port=$port dbname=$dbname user=$user password=".$password.$addcertrequirement;
timetrack(db_connect, $con_str);
$dbconn = pg_connect($con_str); //@pg_connect($con_str);  use the @ to fix any errors

(End Postgresql specific section)

After setting up the database connection functions created a file to be able to setup and test the connection as a specific user on production without effecting all the other users on the system. Code snippet for our test file:


global $testcertrequirements;

$testcertrequirements=array();

if($_POST['testconnection'])
{
	if(!trim($_POST['host']))
		set_message('A hostname is requried to test the connection','error');
	if(!trim($_POST['certpath']))
		set_message('A path including the filename to the new certificate is required to test the connection with the new certificate','error');
	
if(!has_message('error'))
{   
    $testcertrequirements['host']=$_POST['host'];
    $testcertrequirements['certpath']=$_POST['certpath'];
    d('$testcertrequirements',$testcertrequirements);
    db_connect();
    $sql="[ADD AN SQL SELECT STATEMENT HERE FOR A CORE DATABASE TABLE THAT CONTAINS INFORMATION IN YOUR DATABASE]
            ";
    $logingcheckqry=db_query($sql);
    d('$logingcheck sql',$sql);
    d('$logingcheckqry',$logingcheckqry);
    if($logingcheckqry)
        set_message('Connection appears to be successful','success');
}
$testcertrequirements=array();
db_connect(); //Changing back connection to default for sql in footer.
}
display_messages('error');

$defaulttesthost=config_var('dbserver');  //Testing db instance endpoint already setup for new certificate.
if($defaulttesthost && !trim($_POST['host']))
	$_POST['host']=$defaulttesthost;

$defaulttestcertpath='/etc/ssl/certs/rds-ca-2019-root.pem';
if($defaulttestcertpath && !trim($_POST['certpath']))
	$_POST['certpath']=$defaulttestcertpath;

d('post',$_POST);	
?>
	<h3>
		Test New DB Certificate for SSL
	</h3>
	<form id="testnewcertconnection" method="POST" enctype="multipart/form-data">
		<table style='width:25%'>
			<tr>
				<td>
					Host
				</td>
				<td>
					<input type='text' name='host' id='host' value='<?=$_POST['host']?>' />
				</td>
			</tr>
			<tr class='bgmint'>
				<td>
					Certificate Path
				</td>
				<td>
					<input style='width:95%' type='text' name='certpath' id='certpath' value='<?=$_POST['certpath']?>' />
				</td>
			</tr>
			<tr>
				<td colspan=2>
					<input type="submit" value="Test Connection" name="testconnection">		
				</td>
			</tr>		
		</table>
	</form>
<?


include_once('footer.php');

Next migrate this code for the database connection and run the test file on the production site with the existing production db to verify you can select data from the database. This will showed that the test file and the connection is setup correctly.

Step 2. Overview: Create a new instance of the existing database from a snapshot to test the upgrade process so you can verify it works on a clone of the existing database with the same data.

Start by logging into the AWS Console then clicking on Services>Database> RDS>Snapshots.

Choose the newest snapshot or create a new snapshot of the database and choose it.  Copy the KMS key ID from the snapshot details page and also make a note of the DB Storage.  Click Actions> Restore Snapshot.

Select the DB Instance Class that most closely resembles the DB Storage you noted earlier for the existing snapshot of the database.  Type in a DB Instance Identifier (Identifier for the new database) like Test-DB-Cert-Upgrade.

Under Encryption Click on Master Key and select enter a key ARN. (If there is no key already shown.)  Use the key from the details for the existing database. So if the key from the snapshot was efLR5721-a243-4067-bb80-fbecd491dec0 and the region was us-west-2 the key ARN would be:

arn:aws:kms:us-west-2:[put your console login key here]:key/efLR5721-a243-4067-bb80-fbecd491dec0

All the other options you should be able to leave the same.  Next Click restore DB Instance.  Once the new instance from the snapshot is created then click on Databases from the main menu. Click on the main instance you just made and make a note of the end point for this test database.

If you have custom Network Security groups you will need to update them now on the database or you may not be able to connect to the new test database instance. Start a timer so you can get an estimate on how long the upgrade process will take. Click Modify and in the Network & Security section Click on the drop down for the security group and choose your custom group. In this same section set the Certificate authority drop down to the new certificate (In our case it was rds-ca-2019). Click Continue and select the radio button for the option to apply the changes now (Apply Immediately) and then run the modification.

Step 3. Overview: Test the connection to the db using the test script and then schedule down time with the client and upgrade the actual server.

Run the test file on the production server selecting the end point for the new test database as the host and the current path. Verify the connection works for the test db and stop the timer started in step 2 to give you an idea of how long the upgrade process and test will take. Once the test was successful then set up a time to do the update with client and delete the test instance of the database. (For us we scheduled around 30 mins and it usually took around 10 for the whole process. We already had a method for showing a downtime message on the site while it would be down.)

During the time scheduled with the client put up the site down message and migrate it to production. In the AWS console click Modify and in the Network & Security section Click on the Certificate authority drop down and set it to the new certificate (In our case it was rds-ca-2019). Click Continue and select the radio button for the option to apply the changes now (Apply Immediately) and then run the modification. (This usually takes less than a minute.)

Use the test file to verify the connection using the end point for the production database as the host and the certificate path. Once testing is successful go into the db connect function and remove the commented section so the default connection to the server will use the new certificate. Migrate this change to production and verify the connection is still working and pulling data from the existing database using the certificate. Remove the site down message and migrate it to production, verify the site down message no longer displays, and you should be finished.  

Sending Email on Servers on AWS (SES)

Sending email from PHP is often automatic and simple if setup on a traditional hosting account – however the mail() function in PHP does not work on AWS EC2 servers. AWS requires that you use the SES service. (Simple Email Service).

There are several tutorials that walk you through getting your account setup

To send email FROM your email domains you will need to setup and authorize the domain (See TIP #1 below)
https://docs.aws.amazon.com/ses/latest/DeveloperGuide/verify-domains.html

The step that is often missed is that outgoing email in new accounts is allowed ONLY to the email addresses you verify – to verify individual emails addresses.
https://docs.aws.amazon.com/ses/latest/DeveloperGuide/verify-email-addresses.html

To enable your account to send email from your verified domains, and to ANY email address, you will need to get the account removed from the sandbox mode (check the Email Sending -> Sending Statistics page for a message) Click the ‘Request a Sending Limit Increase’ button to ask to remove the account from the sandbox. (here is a tutorial –
https://docs.aws.amazon.com/ses/latest/DeveloperGuide/request-production-access.html )

TIP #1: I would suggest using route 53 for DNS for your domains, as it is a simple couple button clicks to authorize the domains, and get DKIM setup

TIP #2: make sure that you have posted a privacy policy or an email policy on your site – which explains how you send emails and handle their email information. Include a link to your policy in your request for removal from the sandbox.

Setting up TestFlight on iPhone or iPad

TestFlight is an Apple app that allows users to test their app before launching on the app store. It is a great way to see progress made and make adjustments before the final product is released to the public. After you have downloaded the TestFlight app from the app store, entered your apple id, the video above describes the final steps in order to get synced with the invite from Apple App Store Connect in order to start receiving invites to test the latest app.

1. On your iPad, download Test Flight from the App Store.

2. Check your email for the Apple Developer site email. Follow link on the email, login and accept with your Apple ID (which you use on your iPad). Once accepted, I then can add you to the testing team. Please note you do not need to download any app except TestFlight.

3. Watch your email account for a new email, from Test Flight. Open the email, select ‘View in TestFlight’. This will launch the TestFlight app where you can download the latest version of the app.

AWS – Change your Root Password

It is not a good idea to use the Root account to manage and work with your AWS account.   Ideally you have setup IAM user accounts with only the required permissions.

However occasionally you need to update your Root level account password.   This video quickly shows you how to do it

(if this video is low quality,  try opening it full screen and playing it again,  the video is short and may be done playing before YouTube can catch up with downloading a higher quality version)

AWS – Disable IAM User access to Billing Console

In an AWS Account, Root users can create IAM Users with Account Administrator Permissions

However those users do not have access to the Billing Reporting.

A Root user can enable this though – follow the steps in this video

(if this video is low quality,  try opening it full screen and playing it again,  the video is short and may be done playing before YouTube can catch up with downloading a higher quality version)

AWS – Enable IAM User access to Billing Console

In an AWS Account, Root users can create IAM Users with Account Administrator Permissions

However those users do not have access to the Billing Reporting.

A Root user can enable this though – follow the steps in this video

(if this video is low quality,  try opening it full screen and playing it again,  the video is short and may be done playing before YouTube can catch up with downloading a higher quality version)

Matraex Launches Custom App Partner Program for Agencies and Advisors

Matraex has long provided custom app services for Marketing Agencies, Business Advisors and IT Service Companies.

These partners are an important part of our business,  where we grow primarily through the referrals they bring us.

We have created a Partner Program to help formalize these relationships.

The partner program guarantees our Partners trust, a timely response, assistance identifying projects and revenue opportunities in their current client base as well as many other benefits.

To help our potential partners find out more,  we launched a partner site at https://partner.matraex.com

If you’d like to find out more about the program,  call Michael Blood at 208.344.1115 x 250 or email at michael@matraex.com

Moving PHP sites to php 7.2 – undefined constants used as a string

PHP7.2 and above will no longer allow Undefined Constants

According to the “Promote the error level of undefined constants” section of the PHP 7.2 Backwards Incompatible Changes Document

Unqualified references to undefined constants will now generate an E_WARNING (instead of an E_NOTICE). In the next major version of PHP, they will generate Error exceptions.

There have been many changes to PHP over its many versions – For Matraex’s use of PHP,   each version has been mostly compatible with the previous one with only minor changes, until a major decision affected one of the ways we deliberately used what we once called a “Feature” of PHP.  (For a full list of incompatible changes look at the Backwards Incompatible Changes sections in the PHP Appendices )

On March 5th, 2017, Rowan Collins proposed to deprecate bareword strings.  In PHP 7.2   the messages throw an E_WARNING message and in PHP 8.0 it will through an E_ERROR.

PHP has always been a loosely typed language which allows flexibility in many ways,   And we had used this flexibility in order write code in a ways that we belive made it more legible, maintainable and supportable within our coding style.   With this new change, hundreds of thousands of lines of code will need to be rewrittend before we can put it on a 7.2 or above server,  keys may be difficult to search, we will have inconsistencies in usage of keys depending on whether they are inside or out side of quotes.

Take this one example where lines 1, 3 and 4 below would work,   but line 2 would throw a warning in 7.2 and would through an error in 8.0.

  1. echo “Hello, $user[firstname],”;
  2. echo “Hello, “.$user[firstname].”,”;
  3. echo “Hello, “.$user[‘firstname’].”,”;
  4. echo “Hello, “.$user[“firstname”].”,”;

Matraex would have previously preferred to use methods 1 and then 2,  as they require fewer quotes and a search in our IDE of ‘user[first’ would have highlighted both uses.

Mr Collins did evaluate both sides of the decision and wrote a bit about it.  He described that “The value of keeping the current behaviour would be for programs written to deliberately take advantage of it”,   however he really dismisses that value and gave a stronger argument undefined constants can “mask serious bugs”.

I agree with each of the arguments and our 7.2 scripts will all comply with this new syntax requirement.  However, I disagree with the way the solution was indiscriminately executed.  A more considerate solution would have been to create a configuration option in PHP to control the requirement and allow developers and system administrators to continue to ‘deliberately’ use ‘undefined constants’.   This option would also allow existing stable programs to continue to take advantage of the other features of PHP >=7.2 without a significant refactor.    Perhaps the Impact section of the article could attempted to get more feedback from users that had deliberately made heavy investment in this feature.

To be more direct here is my request: PHP developers,  please create / allow a configuration option in PHP which will allow undefined constants to be used as strings. 

Changing existing code across the 10 + years of PHP projects will take thousands of hours to modify and test,  and that is just the projects that still exist. This is a barrier to upgrading to PHP 8.0.

Arguments for a configuration option

  • Millions of lines of code which deliberately use undefined constants as string (more likely billions or trillions – I probably have close to one million myself overtime)
  • My random belief: PHP should enforce “standards” on those that want or need them,  and allow experience users to explicitly choose to ignore them.
  • The configuration option would be disabled by default to address all of the problems mentioned in ‘the problem’ section of the article

Dealing with undefined constant warnings

Now we get to more technical area where I document some of the methods we have used to find code that needs to be updated for PHP 7.2 code.

1)  Use grep to find all uses of the code

This code finds ALL uses of lower case strings without quotes – because our standards do require constants to be in upper case

grep -Rne ‘\$[A-Z\_a-z]*\[[A-Za-Z\_]\{1,\}\]’ *.php

2)  Suppress E_WARNING messages

This is a bad idea,   while it will certainly make it so that your code continues to work in 7.2,   it will not fix it going into 8.0,   and this WILL mask other issues that you do need to know about.

If you want to learn mroe about this,   take a look at this discussion about it on Stack Overflow. Definitely read the comments about hiding warnings to get a better feel for it.

3) Create PHP configuration options to make provisions for undefined constants

These options would require the good work of a C developer that works on the PHP source. Some of these ideas may just work as described,  they really are just a good start (or continuation) of a discussion for features which could be implemented.   I don’t have a ‘bounty’ system but if you are interested in creating any of these options,  or would like to group together to coordinate it, please contact me.

  1. undefined_constants_string_level – Have a PHP directive which declares what E_ level all undefined constant warnings should – default in 8.0 can be E_ERROR
  2. undefined_constants_string_lowercase – Allow users to configure options which would allow only lowercase (or mixed case) constants as strings – which would allow / reserve upper case for use as constants.
  3. undefined_constants_string_superglobal – Allow undefined constants to be used when attempting to reference any key to a super global array (such as $_POST[mykey] or S_SERVER[HTTP_HOST]);

Matraex Releases FrameTurn SaaS

Matraex Announces the Launch of FrameTurn Application to Improve Optical Frame Sales – for BridgePoint Optics

Boise, Idaho (28 July 2018) — Matraex, Inc. (https://www.matraex.com) announces the launch of FrameTurn (https://frameturn.com) a custom application designed to help independent optometry practices use data driven techniques to enhance their business. The app was designed for Bridgepoint Optics (http://www.bridgepointoptics.com), an optical industry sales and business consultancy for independent eye care practices throughout the U.S.

Adding an on-line application provides a Software as a Service (SaaS) that extends their ability to help the optical industry, giving Bridgepoint an additional, marketable service it can provide to its own clients.

Matraex has developed a powerful on-line tool for Bridgepoint Optics that provides their clients with information that can help them make purchasing decisions in a timely and profitable manner.

“Offering a Software as a Solution (SaaS) product to its clients provides BridgePoint with additional business opportunities,” says Michael Blood, president of Matraex, Inc. “Developing a tool of this type for businesses is what drives us. We are excited to see FrameTurn go live over the next few weeks.”

From Bridgepoint’s perspective, the FrameTurn application provides an additional tool in their existing tool box of services that they can offer. It also gives them a significant edge in marketing to the vision care industry. Most importantly, however, it provides a powerful analytical tool designed to increase their clients’ bottom line at a very affordable price.

“Independents have traditionally relied on their instincts, or even guess work, rather than data to make purchasing decisions about frames for their optical shops. We’re excited to end all that! With FrameTurn, these eye care practices will have the ability to record and automatically analyze past and existing sales in various ways to determine trends that can increase their profitability,” says Dr. Rook Torres, co-founder of BridgePoint Optics and FrameTurn.

About Matraex, Inc.

Matraex, Inc. (https://www.matraex.com)  is a Boise-based software and application development company. The company has served many local and national organizations for more than 15 years, including the Better Business Bureau, Hewlett Packard, Madison Square Garden, Penn State University and the Idaho Hospital Association. The services include custom designed mobile applications (iOS, Android, etc.), as well as website development and management.

About BridgePoint Optics

BridgePoint Optics (http://www.bridgepointoptics.com) is an optical industry sales and business consultancy. For more than 25-years, they have specialized in the growth and development of independent eye care practices throughout the U.S.

PDF Version