> For the complete documentation index, see [llms.txt](https://docs.sonarsource.com/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.sonarsource.com/sonarqube-server/10.2/analyzing-source-code/languages/php-analysis.md).

# PHP

PHP analysis is available in all editions of SonarQube Server 10.2.

{% hint style="info" %}
**For AI agents:** You're in the SonarQube Server 10.2 documentation. For a list of all 10.2 pages, see the [SonarQube Server 10.2 page index](https://2995682738-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2F9JA8mmyfC7QWzIoP9Meh%2Fuploads%2FQfpu1DTKUwWYFCaHqyVO%2Fsonarqube-server-10.2-llms.txt?alt=media). For the whole site, see the [page index](https://docs.sonarsource.com/llms.txt) or the [full text](https://docs.sonarsource.com/llms-full.txt). For another version, replace 10.2 in the URL with that version. The [latest version](https://docs.sonarsource.com/sonarqube-server/) has no version number in its URL.
{% endhint %}

## Supported Versions <a href="#supported-versions" id="supported-versions"></a>

|             |                 |
| ----------- | --------------- |
| **Version** | **Status**      |
| 5.x         | Fully Supported |
| 7.x         | Fully Supported |
| 8.x         | Fully Supported |

## Language-specific properties <a href="#language-specific-properties" id="language-specific-properties"></a>

Discover and update the PHP-specific [Analysis parameters](/sonarqube-server/10.2/analyzing-source-code/analysis-parameters.md) in **Administration > General Settings > Languages > PHP**

## Turning issues off <a href="#turning-issues-off" id="turning-issues-off"></a>

The best way to deactivate an individual issue you don’t intend to fix is to mark it "Won’t Fix" or "False Positive" through the Sonar UI.

If you need to deactivate a rule (or all rules) for an entire file, then issue exclusions are the way to go. But if you only want to deactivate a rule across a subset of a file - all the lines of a method or a class - you can use a PHPDoc comment `/* @SuppressWarnings("php:S2077") */` or an attribute `#[SuppressWarnings("php:S2077")]`.

## Analyze php.ini Files <a href="#analyze-files" id="analyze-files"></a>

The PHP analyzer can analyze `php.ini` files with some specific rules (if these rules are activated in your quality profile). `php.ini` files must be part of the project you are analyzing, meaning the `php.ini` files have to be inside the directories listed in `sonar.sources`. Rules targeting `php.ini` files can be quickly identified through the php-ini tag set on them.

## Custom Rules <a href="#custom-rules" id="custom-rules"></a>

### Overview <a href="#overview" id="overview"></a>

The PHP analyzer parses the source code, creates an Abstract Syntax Tree (AST), and then walks through the entire tree. A coding rule is a visitor that is able to visit nodes from this AST.

As soon as the coding rule visits a node, it can navigate its children and log issues if necessary.

### Example plugin <a href="#example-plugin" id="example-plugin"></a>

To get started a sample plugin can be found here: [php-custom-rules](https://github.com/SonarSource/sonar-custom-rules-examples/tree/master/php-custom-rules).

### Writing a plugin <a href="#writing-a-plugin" id="writing-a-plugin"></a>

Custom rules for PHP can be added by writing a SonarQube Server Plugin and using PHP analyzer APIs. Here are the steps to follow:

**Create SonarQube plugin**

* create a standard SonarQube Server plugin project
* attach this plugin to the SonarQube Server PHP analyzer through the `pom.xml`:
  * add the dependency to the PHP analyzer.
  * add the following line in the sonar-packaging-maven-plugin configuration. `<basePlugin>php</basePlugin>`
* implement the following extension points:
  * [Plugin](https://javadocs.sonarsource.org/latest/org/sonar/api/Plugin.html)
  * [RulesDefinition](https://javadocs.sonarsource.org/latest/org/sonar/api/server/rule/RulesDefinition.html) and [PHPCustomRuleRepository](https://github.com/SonarSource/sonar-php/blob/master/php-frontend/src/main/java/org/sonar/plugins/php/api/visitors/PHPCustomRuleRepository.java), which can be implemented by a single class, to declare your custom rules
* declare the RulesDefinition as an extension in the Plugin extension point.

**Implement a rule**

* create a class that will hold the implementation of the rule, it should:
  * extend `PHPVisitorCheck` or `PHPSubscriptionCheck`
  * define the rule name, key, tags, etc. with Java annotations.
* declare this class in the `RulesDefinition`.

**Implementation details**

**Using** **`PHPVisitorCheck`**

To explore a part of the AST, override a method from the PHPVisitorCheck. For example, if you want to explore "if statement" nodes, override [PHPVisitorCheck#visitIfStatement](https://github.com/SonarSource/sonar-php/blob/master/php-frontend/src/main/java/org/sonar/plugins/php/api/visitors/PHPVisitorCheck.java#L265) method that will be called each time an [ifStatementTree](https://github.com/SonarSource/sonar-php/blob/master/php-frontend/src/main/java/org/sonar/plugins/php/api/tree/statement/IfStatementTree.java) node is encountered in the AST.

When overriding a visit method, you must call the super method in order to allow the visitor to visit the children of the node.

**Using** **`PHPSubscriptionCheck`**

To explore a part of the AST, override [`PHPSubscriptionCheck#nodesToVisit`](https://github.com/SonarSource/sonar-php/blob/master/php-frontend/src/main/java/org/sonar/plugins/php/api/visitors/PHPSubscriptionCheck.java#L33) by returning the list of the [`Tree#Kind`](https://github.com/SonarSource/sonar-php/blob/master/php-frontend/src/main/java/org/sonar/plugins/php/api/tree/Tree.java#L124) of node you want to visit. For example, if you want to explore "if statement" nodes the method will return a list containing the element [`Tree#Kind#IF_STATEMENT`](https://github.com/SonarSource/sonar-php/blob/master/php-frontend/src/main/java/org/sonar/plugins/php/api/tree/Tree.java#L761).

**Create Issues**

From the check, the issue can be created by calling [`CheckContext#newIssue`](https://github.com/SonarSource/sonar-php/blob/master/php-frontend/src/main/java/org/sonar/plugins/php/api/visitors/CheckContext.java#L90) method.

**Testing Checks**

To test custom checks you can use the method [`PHPCheckVerifier#verify`](https://github.com/SonarSource/sonar-php/blob/master/php-frontend/src/main/java/org/sonar/plugins/php/api/tests/PHPCheckVerifier.java#L55). You should end each line with an issue with a comment in the following form:

```php
// Noncompliant {{Message}}
```

Comment syntax is described [here](https://github.com/SonarSource/sonar-analyzer-commons/blob/master/test-commons/README.md).

## Related Pages <a href="#related-pages" id="related-pages"></a>

* [External Analyzer Reports](https://github.com/SonarSource/sonar-php/blob/master/#sonarqube-admin#/admin/settings?category=external+analyzers) ([PHPStan](https://phpstan.org/), [Psalm](https://psalm.dev/))
* [Overview](/sonarqube-server/10.2/analyzing-source-code/test-coverage/overview.md)
* [Adding coding rules](/sonarqube-server/10.2/extension-guide/adding-coding-rules.md)


---

# Agent Instructions
This documentation is published with GitBook. GitBook is the documentation platform designed so that both humans and AI agents can read, navigate, and reason over technical content effectively. Learn more at gitbook.com.

## Querying This Documentation
If you need additional information that is not directly available in this page, you can query the documentation by asking a question.

Perform an HTTP GET request on the following URL with the `ask` and `goal` query parameters:

```
GET https://docs.sonarsource.com/sonarqube-server/10.2/analyzing-source-code/languages/php-analysis.md?ask=<question>&goal=<user_goal>
```

`ask` is the immediate question: it should be specific, self-contained, and written in natural language.
`goal` is what the user is ultimately trying to achieve, the reason they need the answer. Sharing it helps GitBook give you a better, more relevant answer. A goal is most helpful when it describes the outcome the user wants rather than restating the question. For example, with `ask=how do I create an API token`, a goal like `automate deployments from our CI pipeline` lets GitBook tailor the answer to that use case.

The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
