The Design Philosophy Behind Scriptlog
Published on May 4, 2026
Built With a Clear Purpose in Mind
Every piece of software starts with a question. For Scriptlog, that question was simple: what does a personal blog actually need?
Not what a corporate CMS needs. Not what a media company publishing hundreds of articles a day needs. Not what an agency managing twenty client sites needs. Just a personal blog, written by one person, shared with whoever wants to read it.
The answer to that question shaped every decision behind how Scriptlog was built. This article walks through the core principles that guided its design, and why those principles matter to the people who use it.
Principle 1: Do One Thing Well
Scriptlog was built to run personal weblogs. That is the whole job. It was not designed to also power e-commerce stores, manage enterprise documentation, or serve as a foundation for a custom web application. It was designed to do one thing and do it properly.
This sounds like a limitation. In practice, it is a strength.
When a platform tries to serve every possible use case, it ends up bloated with features that most users will never touch. Those unused features still have to be loaded, maintained, and secured. They slow down the site and add complexity that gets in the way. Scriptlog avoids that trap by staying focused. Every feature that ships with the platform exists because it genuinely belongs in a personal blogging platform, not because it might be useful to someone somewhere under some circumstances.
The result is a codebase that is lean, coherent, and easy to reason about. When you look at how Scriptlog is put together, everything makes sense in the context of its purpose.
Principle 2: Layers That Each Do Their Own Job
One of the most important architectural decisions in Scriptlog is its layered structure. Every request flows through the same path: a front controller receives it, Bootstrap initializes the application, the Dispatcher routes it to the right controller, the controller passes work to a service, the service talks to a Data Access Object, and the DAO interacts with the database.
Each layer has one responsibility and one only.
Controllers handle HTTP. They receive a request, figure out what is being asked, and hand off the work. They do not write SQL. They do not contain business rules about how posts should be published or how comments should be moderated. That is not their job.
Services handle business logic. They know the rules of the application. They validate input, enforce constraints, and coordinate the work that needs to happen. But they do not know anything about how to talk to the database. That is not their job either.
Data Access Objects handle the database. They write the queries, use prepared statements for every operation, and return data to whoever asked for it. They do not decide what to do with that data. That is someone else's responsibility.
This discipline pays off in several ways. When something goes wrong, you know exactly where to look. When you want to add a feature, there is a clear pattern to follow that keeps everything organized. And because each layer only does one thing, testing each layer independently is straightforward.
Principle 3: Security Is Not Optional, and It Is Not a Plugin
Many platforms treat security as something you add on top. You install a security plugin here, a firewall plugin there, hope they are compatible, and remind yourself to keep them updated. Scriptlog treats security as part of the foundation.
Every design decision that touches sensitive data was made with security as a primary concern, not an afterthought.
Authentication cookies are encrypted using Defuse PHP Encryption with a randomly generated key. That key is generated during installation and stored outside the public web root whenever possible, so it cannot be accessed through the browser even if someone knows the path. Sessions include fingerprinting based on the user's IP address and browser signature, making session hijacking significantly harder. The session handler itself is custom-built rather than relying on PHP's default session behavior, giving the application direct control over how sessions are created and managed.
Every form in the application is protected against CSRF attacks, which are a common technique for tricking a logged-in user into submitting a form without realizing it. Content output runs through two separate XSS filters before it reaches the browser. Passwords are hashed with bcrypt, which is intentionally slow to compute, making brute-force attacks impractical even if someone obtains the hash.
The database layer enforces prepared statements everywhere. There is no place in the codebase where user-supplied input is concatenated directly into a SQL query. The DAO layer exists in part to make this guarantee possible, because when all database access flows through the same layer, you only have to get it right once.
None of this requires configuration. None of it depends on a third party maintaining a plugin. It ships with the platform and works from the moment you finish the installation wizard.
Principle 4: Privacy Is a Feature, Not Compliance Theatre
Scriptlog was designed with privacy as a genuine value, not a checkbox to tick for regulatory purposes.
The platform ships with a complete privacy infrastructure. There are dedicated database tables for storing cookie consent records, tracking data export and deletion requests, and maintaining an audit log of every privacy-related action taken in the system. The admin panel has a privacy section that is protected by role-based access control, visible only to users with the appropriate permission level.
Privacy policies can be stored per locale, meaning a blog that reaches readers in multiple countries can serve the appropriate version of the privacy policy in the right language automatically. This is connected directly to the internationalization system rather than being bolted on separately.
The thinking behind this is that privacy compliance should not require research, plugin hunting, and ongoing maintenance. It should be part of the platform from day one, designed to work correctly without intervention.
Principle 5: Internationalisation Is Built In, Not Added On
Scriptlog ships with support for seven languages: English, Arabic with right-to-left layout, Chinese, French, Russian, Spanish, and Indonesian. The translation system stores strings in the database and caches them as JSON files for fast retrieval. Locale detection reads from the URL prefix, the browser's Accept-Language header, or a stored session preference, in that order.
A design decision that reflects the platform's philosophy particularly well here is the separation between admin and frontend locales. The administrator's dashboard language and the reader-facing blog language are completely independent of each other. An admin can work in French while the blog serves English readers. Changing one has no effect on the other.
This kind of thoughtfulness shows up throughout the i18n system. URL routing supports locale prefixes when SEO-friendly permalinks are enabled, so multilingual content gets proper, searchable URLs. The system is designed to handle the real-world complexity of a blog that speaks to a global audience, without requiring a separate plugin to make it work.
Principle 6: Extensibility With Guardrails
Scriptlog supports a plugin system, but the design philosophy around it is deliberate. Plugins are not given unlimited access to the application. They interact with it through a controlled hook system using the clip() function. They cannot bypass the DAO layer. They cannot run direct database queries outside of their registered hooks. They live in their own directories and declare themselves through a configuration file.
This matters because one of the most common ways a platform gets compromised is through a poorly written extension that has too much access. By constraining what plugins can do and how they can do it, Scriptlog limits the blast radius of a badly written or malicious extension.
The plugin lifecycle is transparent and clean. Installing a plugin adds a database record and unpacks the files. Enabling it loads its hooks into the application. Disabling it stops those hooks from loading. Deleting it removes both the files and the record. There is no ambiguity about the state of a plugin at any given moment, and there is no situation where disabling or deleting a plugin leaves hidden fragments behind.
Principle 7: Code That Other Developers Can Trust and Extend
Scriptlog follows PSR-12 coding standards throughout, which is the current widely accepted standard for PHP code style. This matters for a practical reason: when code follows a consistent, documented standard, other developers can read it, understand it, and contribute to it without first having to decode the original author's personal preferences.
The platform uses Conventional Commits for its version history, which means that looking at the commit log gives you a clear, structured record of what changed and why. This is not just discipline for its own sake. It is respect for the people who will work with this code in the future.
The test suite reflects the same attitude. Over 1,170 PHPUnit tests across 73 files cover the application from the utility layer through the service layer and into integration tests that run against a real database. The target is 40% code coverage, which is a meaningful commitment for a project of this scope. Tests are not a luxury added after the fact. They are part of how the project demonstrates that it takes quality seriously.
Static analysis runs alongside the tests using PHPStan, which catches type errors and code quality issues without requiring the code to be executed. This combination of automated testing and static analysis gives maintainers confidence when making changes that they are not accidentally breaking something they did not realize was connected.
Principle 8: Respect for the Developer's Time
Good design, in software as in anything else, should make the right things easy and the wrong things hard.
Scriptlog tries to make the right things easy. Adding a feature follows a documented, consistent pattern. The directory structure is organized so that you can find what you are looking for. Configuration is handled through both a .env file and a config.php that stay in sync automatically. The installation wizard generates both files during setup, so you start with a working configuration rather than an empty template.
The wrong things are made harder through the architecture itself. There is no easy shortcut to bypass the DAO layer and write a raw SQL query directly in a controller. The separation of concerns is enforced by design. You can still do the wrong thing if you try hard enough, but the path of least resistance leads to the right structure.
What All of This Adds Up To
Scriptlog was not built to impress anyone with a feature list. It was built to be genuinely useful to a specific kind of person: someone who wants to run a personal blog, own their data, keep it secure, and not spend their weekends managing software.
Every principle described in this article serves that goal. The focused scope means there is no bloat. The layered architecture means the codebase is maintainable. The built-in security means you are not dependent on third-party developers for the safety of your site. The privacy infrastructure means compliance is handled before you even think to ask about it. The internationalization support means your blog can speak to readers anywhere. The constrained plugin system means extensions cannot undo the security work baked into the core. The coding standards and test coverage mean the platform is trustworthy and open to contribution.
Good software is built on good principles applied consistently over time. That is what Scriptlog is trying to be.
Scriptlog is open source and free to use under the MIT License. Source code and documentation are available on GitHub.