Core Boxx – Modular PHP Framework

Core Boxx is a PHP framework built with the concept of simplicity and modularity. Install and load only what you need, not bloated with unused features.

 

TABLE OF CONTENTS

 

 

DOWNLOAD & INSTALLATION

First, here are the download links and a quick “setup guide” for the folks who don’t want to read through everything.

 

SYSTEM REQUIREMENTS

  • LAMP/WAMP/MAMP/XAMPP
  • Apache Mod Rewrite
  • PHP MYSQL PDO Extension
  • PHP OpenSSL Extension
  • At least PHP 8.0

 

LICENSE & DOWNLOAD

GitHub | Source Forge

Core Boxx is released under the MIT License. You are free to use it for personal and commercial projects, modify it as you see fit. On the condition that the software is provided “as-is”. There are no warranties provided and “no strings attached”. Code Boxx and the authors are not liable for any claims, damages, or liabilities.

 

INSTALLATION

  1. Just copy the contents of the core folder into your HTTP folder.
  2. Access http://YOUR-SITE.com in the browser to launch the installer.

Done! You now have a basic skeleton framework. Do at least run through the quick tutorial below.

 

SORRY FOR THE ADS...

But someone has to pay the bills, and sponsors are paying for it. I insist on not turning Code Boxx into a "paid scripts" business, and I don't "block people with Adblock". Every little bit of support helps.

Buy Me A Coffee Code Boxx eBooks

 

 

A QUICK TUTORIAL

Don’t worry, Core Boxx does not have some crazy documentation that takes months to read. Let us walk through a quick example of creating a dummy “list items” module.

 

TUTORIAL FILES

All the files in this tutorial are provided in the tutorial folder.

 

CORE BOXX FOLDERS

Core Boxx only has 3 folders:

  • assets Public CSS, Javascript, images, video, audio, and whatever else.
  • pages HTML pages and templates.
  • lib Library, API, config, and SQL files should be kept in this folder.

 

DEVELOPMENT WORKFLOW

Development with Core Boxx commonly involves 4 steps:

  • Database tables.
  • Library.
  • API endpoint.
  • User interface.

 

STEP 1) CREATE DATABASE TABLES

lib/SQL-Items.sql
CREATE TABLE `items` (
  `item_id` bigint(20) NOT NULL AUTO_INCREMENT,
  `item_name` varchar(255) NOT NULL,
  PRIMARY KEY (`item_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;

Let’s keep things simple with a dummy items table:

  • item_id Primary key and auto-increment.
  • item_name The item itself.

 

 

STEP 2) DEVELOP THE LIBRARY MODULE

lib/LIB-Items.php
<?php
class Items extends Core {
  // (A) GET ALL ITEMS
  function getAll () {
    return $this->DB->fetchKV(
      "SELECT * FROM `items`", null,
      "item_id", "item_name"
    );
  }
 
  // (B) SAVE ITEM
  function save ($name, $id=null) : void {
    // (B1) DATA SETUP
    $fields = ["item_name"];
    $data = [$name];
    if ($id!=null) { $data[] = $id; }
 
    // (B2) INSERT OR UPDATE
    if ($id==null) { $this->DB->insert("items", $fields, $data); }
    else { $this->DB->update("items", $fields, "`item_id`=?", $data); }
  }
 
   // (C) DELETE ITEM
  function del ($id) : void {
    $this->DB->delete("items", "`item_id`=?", [$id]);
  }
}
  • Since we are working with list items, we will create a lib/LIB-Items.php library. Take note of the capital I.
  • Set the class name to the same as the file name, extend the core – class Items extends Core. Take note of the capital I.

Yes, we are pretty much using the database module LIB-DB.php to build this library. Modules can access each other. For example, if you want to use this items library in the future:

class Foo extends Core {
  function bar () {
    $this->Core->load("Items");
    $items = $this->Items->getAll();
  }
}

That’s the whole idea of “modular” in Core Boxx. Build the library once, load it only when needed, and reuse it everywhere.

 

STEP 3) DEVELOP THE API ENDPOINTS

lib/API-items.php
<?php
// (A) API ENDPOINTS
$_CORE->autoAPI([
  "getAll" => ["Items", "getAll"],
  "save" => ["Items", "save"],
  "del" => ["Items", "del"]
]);
 
// (B) INVALID REQUEST
$_CORE->respond(0, "Invalid request", null, null, 400);
  • API endpoints in Core Boxx have a structure of http://site.com/api/MODULE/ACTION. Examples:
    • Access http://site.com/api/items/getAll to get all the list items.
    • Send $_POST["name"]="DEMO" to http://site.com/api/items/save to add a new list item.
    • Send $_POST["id"]=123 to http://site.com/api/items/del to delete the list item.
  • So, API-items.php will deploy the endpoint at http://site.com/api/items/ACTION.
  • $_CORE->autoAPI() will map the respective ACTION => ["MODULE", "FUNCTION"].

 

 

STEP 4) USER INTERFACE

4A) CORE BOXX HTML ENGINE

pages/PAGE-items.php
<?php
// (A) HTML TOP HALF
require PATH_PAGES . "TEMPLATE-top.php";

// (B) YOUR CONTENT
$_CORE->load("items");

// (B1) GET ALL ITEMS
$items = $_CORE->items->getAll();
foreach ($items as $id=>$name) { /* DRAW HTML */ }

// (B2) SAVE ITEM
$_CORE->items->save("ANOTHER");
$_CORE->items->save("ANOTHERZZ", 123);

// (B3) DELETE ITEM
$_CORE->items->del(456);

// (C) HTML BOTTOM HALF
require PATH_PAGES . "TEMPLATE-bottom.php"; ?>
  • If you want to add an HTML page in Core Boxx:
    • http://site.com/foo will map to pages/PAGE-foo.php.
    • http://site.com/foo/bar will map to pages/PAGE-foo-bar.php.
    • So, http://site.com/items will map to pages/PAGE-items.php.
  • All pages have access to $_CORE. You can load your modules, and use that to fetch/process data accordingly.

P.S. The default HTML template is made with Bootstrap and IcoMoon. No hard rules that you must use it. Feel free to redevelop TEMPLATE-top.php and TEMPLATE-bottom.php as you see fit.

 

4B) WORK WITH THE API “EXCLUSIVELY”

// (A) HELPER - CALL API
function ajax (mod, act, data, after) {
  // (A1) FORM DATA
  let form = new FormData();
  if (data) {
    for (let [k,v] of Object.entries(data)) { form.append(k, v); }
  } 

  // (A2) AJAX FETCH
  fetch(`http://site.com/api/${mod}/${act}`, { method:"POST", body:form })
  .then(res => res.json())
  .then(res => {
    if (res.status) { after(res.data); }
    else { alert(res.message); }
  })
  .catch(err => console.error(err));
}

// (B) ADD/UPDATE ITEM
ajax("items", "save", { name: "Test" }, () => alert("OK"));
ajax("items", "save", { name: "Testzzz", id: 1 }, () => alert("OK"));

// (C) DELETE ITEM
ajax("items", "del", { id: 123 }, () => alert("OK"));

// (D) GET ALL
ajax("items", "getAll", null, data => {
  for (let [i,n] of Object.entries(data)) { BUILD HTML LIST }
});

Yep, the API is pretty much “a complete system without the user interface”. It does not matter what programming language or platform you use for the client – So long as you can communicate with the API and get a response.

 

 

REFERENCE & MODULES

Here are some links to the library references plus more Core Boxx modules.

 

LIBRARY REFERENCES & DOCUMENTATION

 

CORE BOXX MODULES

  1. Users – User register, login, logout, forgot password.
  2. Login With Google – An addition to the user login system.
  3. Login With QR – Print a “staff card” or “student card”. Login by scanning the QR code.
  4. Login With NFC – Create an NFC “staff card” or “student card”. Login by scanning the card.
  5. Passwordless Login – Login with fingerprint, pin code, face recognition, USB passkey, etc…
  6. Admin Panel – HTML admin template.
  7. One Time Password – For added security.
  8. Resumable Upload – Resumable uploads with FlowJS and FlowPHP.
  9. Dynamic Content – Store and retrieve contents from the database.
  10. Reactions – Likes & dislikes, or was it “upvote & downvote”?
  11. Star Rating – Let users review your posts/products/audio/video/image/whatever.
  12. Comments – Allow registered users to comment on your posts/products/images/videos.
  13. Calendar – Show and manage events.
  14. Web Push – Use the force. Send push notifications.
  15. Autocomplete – Or “suggestions”.
  16. AI Chatbot – Yes, a frickin local AI chatbot.

 

 

FAQ

To answer the common questions.

 

FAILED TO GENERATE VAPID KEYS

The VAPID keys are used for push notifications, make sure that your OpenSSL extension is properly installed and configured.

  • Linux
    • It is as simple as sudo apt-get install openssl, or yum install openssl for the CentOS users.
    • Then, php -i | grep -i openssl.
  • Windows – Enable OpenSSL in php.ini. Do some research on your own, too much to go through in a few lines.
  • Windows – If you have already enabled OpenSSL, it is probably a “bug” that also got me stumped for a while:
    • Start > Search for “system environment” > “Edit the system environment variables” > “Environment variables”.
    • Add a new system variable called OPENSSL_CONF and point it to the openssl.cnf file. XAMPP users, it is located at xampp\php\extras\openssl\openssl.cnf.
    • Restart your computer.

 

“AJAX ERROR” AND “BAD SERVER RESPONSE”

Open the developer’s console (F12 in most modern browsers), check the error logs, and see what your server is complaining about.

 

CHANGED DOMAIN OR PATH

  • Update SITE_NAME and HOST_BASE in lib/CORE-Config.php. If not deployed at the base URL, include the path (with a trailing slash). E.G. http://site.com/coreboxx/
  • Create init.php.
    • require "lib/CORE-Go.php";
    • $_CORE->load("Route");
    • $_CORE->load("CCache");
    • $_CORE->Route->init();
    • $_CORE->CCache->init();
  • Access http://site.com/init.php, this will automatically regenerate .htaccess, update CB-manifest.json, and CB-cache-files.json.
  • Delete init.php.

 

SUPPORTING MULTIPLE HOST/DOMAIN NAMES

  • Modify CORE-Config.php.
    • Create an array of your domains MYDOMAINS = ["A.COM", "B.COM"].
    • Detect the HTTP origin and set HOST_BASE accordingly – if (in_array(ORIGIN, MYDOMAINS)) { HOST_BASE = ORIGIN } else { ERROR! }.
  • If you have different paths, you are going to face problems with the manifest and .htaccess. E.G. https://sitea.com and https://siteb.com/coreboxx.
    • For .htaccess, do some “Apache virtual host mod_rewrite” research on your own.
    • You can create multiple CB-manifest.json, each with a different start_url and scope. In TEMPLATE-top.php, point to the “correct manifest” accordingly.
    • Alternatively, generate the manifest dynamically using PHP.

 

PAGES ARE NOT RESOLVING OR SHOWING PROPERLY

  • Make sure that MOD_REWRITE is enabled in Apache.
  • Make sure that AllowOverride is set properly in Apache.
  • If using https://, make sure that your SSL cert and host are properly set.
  • In Mac/Linux, make sure that Apache and PHP have permission to read the files and folders.

Here is a quick “working example” of a test site on my WAMP server:

httpd-vhosts.conf
<VirtualHost site.com:443>
  DocumentRoot "D:\http"
  ServerName site.com:443
  SSLEngine On
  SSLCertificateFile "C:/xampp/apache/conf/ssl.crt/server.crt"
  SSLCertificateKeyFile "C:/xampp/apache/conf/ssl.key/server.key"
  <Directory "D:\http">
    Options Indexes FollowSymLinks Includes ExecCGI
    AllowOverride All
    Require all granted
  </Directory>
</VirtualHost>

 

SETTING TIMEZONES

  • You can change the default timezone in CORE-Config.php, SYS_TZ and SYS_TZ_OFFSET. Beware though, this can mess up the timestamps in the database if you already have entries.
  • If you have to support multiple timezones, it will be wise to keep the system default to UTC. Calculate the offset in PHP or MYSQL queries instead.

 

I WANT TO CHANGE THE DATE FORMAT

  • Login > Admin > System Settings > There are 4 “MYSQL date/time format” settings, change them accordingly. These are simply formats for the MYSQL DATE_FORMAT() function.
  • Use the respective date/time format in your SQL – "SELECT DATE_FORMAT(`col`, '".DT_LONG."') FROM `table`".

 

NFC FEATURES ARE “NOT WORKING”!

At the time of writing, Web NFC only works on Android Chrome and Baidu Browser – CanIUse

 

I DELETED ALL ADMIN ACCOUNTS

recover.php
require "lib/CORE-Go.php";
$_CORE->load("Users");
$_CORE->Users->save("NAME", "EMAIL", "PASSWORD", "A");

Just create an “account recovery” script to create a new account (or update an existing one). Run and delete this afterward.

 

NOT WORKING. DON’T KNOW WHY.

Open the developer’s console, reload the page, and see the error message.

22 thoughts on “Core Boxx – Modular PHP Framework”

  1. Wonderful and Powerful CMS.

    One suggestion, please. I think it’s good to add a specific email library, such as PHPMailer into Core-Boxx, because some hosting provider disable mail function.

    Thanks in advance.

  2. It’s run fine on localhost, but I got this on cPanel: “Please enable Apache MOD_REWRITE”

    I’m using this config:

    DocumentRoot “/var/www/”
    RewriteEngine On
    DirectoryIndex index.php

    AllowOverride All
    Require all granted
    Options +FollowSymlinks

    But still not works. I consult it to my host provider, but they can’t help. Please help me, sir.

    1. * As it is – Do a “enable apache mod_rewrite” search on your own. Enable and test Apache mod rewrite on your own server.
      * Resolve this issue with your host. There’s nothing I can do if they don’t want to enable or support mod_rewrite.
      * I cannot provide free consultation for personal hosting and projects – https://code-boxx.com/faq/#help “Help and requests on a deeper level”

  3. When i use your framework , the dates and times of the DB records are different, how do I fix this. I want to get Turkey time and date.

    1. Just set the default timezone in both PHP and MYSQL?

      1) Set in php.ini – date.timezone = ABC – https://www.php.net/manual/en/timezones.php
      2) OR https://www.php.net/manual/en/function.date-default-timezone-set.php
      3) Set in my.cnf – default-time-zone = ABC
      4) OR set in __contstruct() of LIB-DB.php – https://stackoverflow.com/questions/65204518/how-to-set-pdo-timezone-at-connection

      The better way is to leave it as UTC to support multi-regions though. Modify all the SQL queries to include the timezone offset.

  4. Nice and simple framework.. clean! i’ve tried it.
    for information, dynamic properties are deprecated in PHP8.2.
    if anyone has encountered these error.. just declare the class as inheritance from stdClass.

    example at lib-Core.php :
    class CoreBoxx{…} -> class CoreBoxx extends stdClass{…}

Leave a Comment

Your email address will not be published. Required fields are marked *