PHPackages                             toubiz/phparch - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. toubiz/phparch

ActiveLibrary

toubiz/phparch
==============

Architecture Testing for PHP projects

4.0.1(5y ago)099MITPHPPHP ^7.4|^8.0

Since Nov 29Pushed 5y ago1 watchersCompare

[ Source](https://github.com/landinsicht/phparch)[ Packagist](https://packagist.org/packages/toubiz/phparch)[ RSS](/packages/toubiz-phparch/feed)WikiDiscussions main Synced 1w ago

READMEChangelog (3)Dependencies (8)Versions (15)Used By (0)

PHPArch [![Build Status](https://camo.githubusercontent.com/b730cd035b2a8a4d652e42d59e8d075936576dc538f6a4f51be78d7e370286a8/68747470733a2f2f7472617669732d63692e6f72672f6c616e64696e73696368742f706870617263682e7376673f6272616e63683d646576656c6f706d656e74)](https://travis-ci.org/landinsicht/phparch)
==========================================================================================================================================================================================================================================================================================================

[](#phparch-)

- [What is this?](#what-is-this)
- [Installation](#installation)
- [Simple Namespace validation](#simple-namespace-validation)
    - [Available Validators](#available-validators)
- [Defining an architecture](#defining-an-architecture)
    - [Syntactic sugar: Bulk definition of components](#syntactic-sugar-bulk-definition-of-components)
    - [Syntactic sugar: Chaining multiple dependency rules](#syntactic-sugar-chaining-multiple-dependency-rules)
- [Examples](#examples)

What is this?
-------------

[](#what-is-this)

PHPArch is a work in progress architectural testing library for PHP projects. It is inspired by [archlint (C#)](https://gitlab.com/iternity/archlint.cs)and [archunit (java)](https://github.com/TNG/ArchUnit).

It can be used to help enforce architectural boundaries in an application in order to prevent the architecture from rotting over time by introducing dependencies across previously well defined architectural boundaries.

Installation
------------

[](#installation)

You can install PHPArch using composer. If you don't know what composer is then you probably don't need a library for architectural testing.

```
$ composer require toubiz/phparch
```

Simple Namespace validation
---------------------------

[](#simple-namespace-validation)

The most simple type of check PHPArch can help you with are simple namespace based checks: Setup rules for which namespace is allowed or forbidden to depend on which other namespace.

```
public function testSimpleNamespaces()
{
    (new PhpArch())
        ->fromDirectory(__DIR__ . '/../../app')
        ->validate(new ForbiddenDependency('Lib\\', 'App\\'))
        ->validate(new MustBeSelfContained('App\\Utility'))
        ->validate(new MustOnlyDependOn('App\\Mailing', 'PHPMailer\\PHPMailer'))
        ->assertHasNoErrors();
}
```

### Available Validators

[](#available-validators)

Currently the following validators are available:

- `ForbiddenDependency` Lets you declare that one namespace is not allowed to depend on another namespace.
- `MustBeSelfContained` Lets you declare that a namespace must be self-contained meaning that it may not have any external dependencies.
- `MustOnlyDependOn` Lets you declare that one namespace must only depend on another namespace.
- `MustOnlyHaveAutoloadableDependencies` checks if all dependencies are autoloadable in the current environment. This can be helpful if two packages should not have any dependencies on each other but they still sneak in because the packages are often used together.
- `AllowInterfaces` is a wrapper for validators that allows dependencies if they are to interfaces.
- `MustOnlyDependOnComposerDependencies` checks if all dependencies in a given namespace are declared in the given `composer.json` file. This is useful to prevent accidental dependencies if one repository contains multiple packages.
- `ExplicitlyAllowDependency` is a wrapper for validators that allows a specific dependency.

Most architectural boundaries can be described with these rules.

Defining an architecture
------------------------

[](#defining-an-architecture)

PHPArch also contains a fluent API that allows you to define a component based architecture which is then validated. The API is based on components which are identified by one or more namespaces instead of Layers or 'Onion Peels' because it is the simplest way to communicate any architecture - no matter what the implementation details of it are.

```
public function testArchitecture()
{
    $architecture = (new Architecture())
        ->component('Components')->identifiedByNamespace('J6s\\PhpArch\\Component')
        ->mustNotDependOn('Validation')->identifiedByNamespace('J6s\\PhpArch\\Validation');

    (new PhpArch())
        ->fromDirectory(__DIR__ . '/../../app')
        ->validate($architecture)
        ->assertHasNoErrors();
}
```

Most of defining an architecture is only syntactic sugar over the namespace validators above. The following methods allow you to add assertions to your component structure:

- `mustNotDependOn`
- `mustNotDependDirectlyOn`
- `mustNotBeDependedOnBy`
- `mustOnlyDependOn`
- `mustNotDependOnAnyOtherComponent`
- `mustOnlyDependOnComposerDependencies`
- `dissallowInterdependence`
- `isAllowedToDependOn`

### Syntactic sugar: Bulk definition of components

[](#syntactic-sugar-bulk-definition-of-components)

While the speaking Api for defining an architecture is great it can get convoluted and hard to read if you have a lot of components. The `components` method can be used to define components using a simple associative array where the key is the component name and the value is the namespaces that define the component. This way definitions of components and setting up dependency rules can be split into 2 steps for better readability.

```
// This
$architecture->components([
     'Foo' => 'Vendor\\Foo',
     'Bar' => [ 'Vendor\\Bar', 'Vendor\\Deep\\Bar' ]
]);

// Is the same as this
$architecture->component('Foo')
    ->identifiedByNamespace('Vendor\\Foo')
    ->component('Bar')
    ->identifierByNamespace('Vendor\\Bar')
    ->identifiedByNamespace('Vendor\\Deep\\Bar')
```

### Syntactic sugar: Chaining multiple dependency rules

[](#syntactic-sugar-chaining-multiple-dependency-rules)

If a non-existing component is referenced in one of these methods then it will be created. These methods will also set the referenced component as the currently active one - so when using `->mustNotDependOn('FooBar')` all future operations reference the `FooBar` component.

In order to chain multiple dependency rules for a single component there are some convenience methods available:

- `andMustNotDependOn`
- `andMustNotBeDependedOnBy`

```
// This
(new Architecture)
    ->component('Foo')
    ->mustNotDependOn('Bar')
    ->andMustNotDependOn('Baz')

// Is this same as this:
(new Architecture())
    ->component('Foo')->mustNotDependOn('Bar')
    ->component('Foo')->mustNotDependOn('Baz')
```

### Shorthand for monorepos: `addComposerBasedComponent`

[](#shorthand-for-monorepos-addcomposerbasedcomponent)

In case one repository contains multiple packages that all have their own `composer.json`file it is easy to accidentally use a method or class of something that is not in the `composer.json`file of the current package.

To prevent this the `Architecture->mustOnlyDependOnComposerDependencies` method and the `MustOnlyDependOnComposerDependencies` validator can be used to check if all used namespaces are declared in a given `composer.json` file:

```
$architecture = (new Architecture)
    ->component('vendor/subpackage')
    ->identifierByNamespace('Vendor\\Subpackage\\')
    ->mustOnlyDependOnComposerDependencies('packages/subpackage/composer.json');
```

However, `composer.json` already contains information about the package name and namespaces. Therefore the `addComposerBasedComponent` method can be used in order to make things easier:

```
$architecture = (new Architecture)
    ->addComposerBasedComponent('packages/subpackage/composer.json');
```

Examples
--------

[](#examples)

- [PHPArch tests its own architecture](./tests/ArchitectureTest.php)

###  Health Score

31

—

LowBetter than 68% of packages

Maintenance20

Infrequent updates — may be unmaintained

Popularity9

Limited adoption so far

Community11

Small or concentrated contributor base

Maturity73

Established project with proven stability

 Bus Factor1

Top contributor holds 58.8% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~66 days

Recently: every ~47 days

Total

13

Last Release

1932d ago

Major Versions

0.3.1 → 1.0.02019-02-18

1.2.0 → 2.0.02020-10-14

2.0.0 → 3.0.02020-12-03

3.0.0 → 4.0.02021-01-13

PHP version history (5 changes)0.3.0PHP ^7.1

1.1.0PHP ^7.2

2.0.0PHP ^7.3

4.0.0PHP ^7.3|^8.0

4.0.1PHP ^7.4|^8.0

### Community

Maintainers

![](https://www.gravatar.com/avatar/791aed3afcdbc490d6c78359811a940abfafa7d36c1e765d801953eae403416e?d=identicon)[nepda](/maintainers/nepda)

---

Top Contributors

[![j6s](https://avatars.githubusercontent.com/u/3374170?v=4)](https://github.com/j6s "j6s (20 commits)")[![nepda](https://avatars.githubusercontent.com/u/531753?v=4)](https://github.com/nepda "nepda (12 commits)")[![JustBlackBird](https://avatars.githubusercontent.com/u/1167086?v=4)](https://github.com/JustBlackBird "JustBlackBird (1 commits)")[![Orkin](https://avatars.githubusercontent.com/u/1061903?v=4)](https://github.com/Orkin "Orkin (1 commits)")

###  Code Quality

TestsPHPUnit

Static AnalysisPHPStan

Code StylePHP\_CodeSniffer

Type Coverage Yes

### Embed Badge

![Health badge](/badges/toubiz-phparch/health.svg)

```
[![Health](https://phpackages.com/badges/toubiz-phparch/health.svg)](https://phpackages.com/packages/toubiz-phparch)
```

###  Alternatives

[infection/infection

Infection is a Mutation Testing framework for PHP. The mutation adequacy score can be used to measure the effectiveness of a test set in terms of its ability to detect faults.

2.2k26.2M1.8k](/packages/infection-infection)[humbug/box

Fast, zero config application bundler with PHARs.

1.3k801.5k69](/packages/humbug-box)[humbug/php-scoper

Prefixes all PHP namespaces in a file or directory.

7963.0M35](/packages/humbug-php-scoper)[typo3/cms

TYPO3 CMS is a free open source Content Management Framework initially created by Kasper Skaarhoj and licensed under GNU/GPL.

1.2k1.9M122](/packages/typo3-cms)[silverstripe/framework

The SilverStripe framework

7213.5M2.5k](/packages/silverstripe-framework)[worksome/envy

Automatically keep your .env files in sync.

6871.8M](/packages/worksome-envy)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
