diff --git a/.github/workflows/codesniffer.yml b/.github/workflows/codesniffer.yml new file mode 100644 index 0000000..6a730e3 --- /dev/null +++ b/.github/workflows/codesniffer.yml @@ -0,0 +1,39 @@ +name: "Codesniffer" + +on: + pull_request: + + push: + branches: [ "*" ] + + schedule: + - cron: "0 8 * * 1" + +jobs: + phpstan: + runs-on: ubuntu-latest + + steps: + - uses: actions/checkout@v3 + + - name: "Setup PHP" + uses: shivammathur/setup-php@v2 + with: + php-version: '8.2' + + - name: Validate composer.json and composer.lock + run: composer validate + + - name: Cache Composer packages + id: composer-cache + uses: actions/cache@v3 + with: + path: vendor + key: ${{ runner.os }}-php-${{ hashFiles('**/composer.lock') }} + restore-keys: | + ${{ runner.os }}-php- + + - name: Install dependencies + run: composer install --prefer-dist --no-progress + - name: Run coding standards + run: make cs \ No newline at end of file diff --git a/.github/workflows/phpstan.yml b/.github/workflows/phpstan.yml new file mode 100644 index 0000000..fba1147 --- /dev/null +++ b/.github/workflows/phpstan.yml @@ -0,0 +1,39 @@ +name: PHPstan + +on: + pull_request: + + push: + branches: [ "*" ] + + schedule: + - cron: "0 8 * * 1" + +jobs: + phpstan: + runs-on: ubuntu-latest + + steps: + - uses: actions/checkout@v3 + + - name: "Setup PHP" + uses: shivammathur/setup-php@v2 + with: + php-version: '8.2' + + - name: Validate composer.json and composer.lock + run: composer validate + + - name: Cache Composer packages + id: composer-cache + uses: actions/cache@v3 + with: + path: vendor + key: ${{ runner.os }}-php-${{ hashFiles('**/composer.lock') }} + restore-keys: | + ${{ runner.os }}-php- + + - name: Install dependencies + run: composer install --prefer-dist --no-progress + - name: Run phpstan + run: make phpstan \ No newline at end of file diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml new file mode 100644 index 0000000..f3f637d --- /dev/null +++ b/.github/workflows/tests.yml @@ -0,0 +1,39 @@ +name: PHP Unit tests + +on: + pull_request: + + push: + branches: [ "*" ] + + schedule: + - cron: "0 8 * * 1" + +jobs: + test82: + runs-on: ubuntu-latest + + steps: + - uses: actions/checkout@v3 + + - name: "Setup PHP" + uses: shivammathur/setup-php@v2 + with: + php-version: '8.2' + + - name: Validate composer.json and composer.lock + run: composer validate + + - name: Cache Composer packages + id: composer-cache + uses: actions/cache@v3 + with: + path: vendor + key: ${{ runner.os }}-php-${{ hashFiles('**/composer.lock') }} + restore-keys: | + ${{ runner.os }}-php- + + - name: Install dependencies + run: composer install --prefer-dist --no-progress + - name: Run tests + run: make tests \ No newline at end of file diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..e3abb61 --- /dev/null +++ b/.gitignore @@ -0,0 +1,9 @@ +# IDE +/.idea + +# Composer +/vendor +composer.lock + +# Tests +/coverage.xml diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..189b76b --- /dev/null +++ b/Makefile @@ -0,0 +1,22 @@ +.PHONY: install tests qa cs csf phpstan + +install: + composer install + +qa: phpstan cs + +cs: +ifdef GITHUB_ACTION + vendor/bin/phpcs --standard=ruleset.xml --encoding=utf-8 --colors -nsp -q --report=checkstyle src tests +else + vendor/bin/phpcs --standard=ruleset.xml --encoding=utf-8 --colors -nsp src tests +endif + +csf: + vendor/bin/phpcbf --standard=ruleset.xml --encoding=utf-8 --colors -nsp src tests + +phpstan: + vendor/bin/phpstan analyse -c phpstan.neon + +tests: + vendor/bin/phpunit --bootstrap vendor/autoload.php tests \ No newline at end of file diff --git a/composer.json b/composer.json new file mode 100644 index 0000000..c10374a --- /dev/null +++ b/composer.json @@ -0,0 +1,39 @@ +{ + "name": "troia-studio/ssh-key-validator-nette", + "description": "Implementation troia-studio/ssh-key-validator to Nette", + "type": "library", + "autoload": { + "psr-4": { + "TroiaStudio\\SshKeyValidator\\": "src/" + } + }, + "autoload-dev": { + "psr-4": { + "Tests\\": "tests" + } + }, + "require": { + "php": ">=8.2", + "troia-studio/ssh-key-validator": "^1.0", + "symfony/validator": "^6.3" + }, + "require-dev": { + "ext-intl": "*", + "contributte/qa": "^0.3.1", + "contributte/phpstan": "^0.1.0", + "phpunit/phpunit": "^10" + }, + "license": "MIT", + "authors": [ + { + "name": "Jan Galek", + "email": "me@jan-galek.cz" + } + ], + "minimum-stability": "stable", + "config": { + "allow-plugins": { + "dealerdirect/phpcodesniffer-composer-installer": true + } + } +} diff --git a/phpstan.neon b/phpstan.neon new file mode 100644 index 0000000..42589b0 --- /dev/null +++ b/phpstan.neon @@ -0,0 +1,15 @@ +includes: + - vendor/contributte/phpstan/phpstan.neon + +parameters: + level: 0 + phpVersion: 80200 + + scanDirectories: + - src + + fileExtensions: + - php + + paths: + - src \ No newline at end of file diff --git a/ruleset.xml b/ruleset.xml new file mode 100644 index 0000000..8b1bcde --- /dev/null +++ b/ruleset.xml @@ -0,0 +1,10 @@ + + + + + + + + + /tests/tmp + \ No newline at end of file diff --git a/src/IsSshKey.php b/src/IsSshKey.php new file mode 100644 index 0000000..757c381 --- /dev/null +++ b/src/IsSshKey.php @@ -0,0 +1,33 @@ + 'NOT_SSH_KEY_ERROR', + ]; + + public string $message = 'This value should be valid ssh key.'; + + public function __construct(mixed $options = null, ?string $message = null, ?array $groups = null, mixed $payload = null) + { + parent::__construct($options ?? [], $groups, $payload); + + $this->message = $message ?? $this->message; + } + +} diff --git a/src/IsSshKeyValidator.php b/src/IsSshKeyValidator.php new file mode 100644 index 0000000..3eb6c14 --- /dev/null +++ b/src/IsSshKeyValidator.php @@ -0,0 +1,41 @@ +validate($value)) { + return; + } + + $this->context->buildViolation($constraint->message) + ->setParameter('{{ string }}', $value) + ->setCode(IsSshKey::NOT_SSH_KEY_ERROR) + ->addViolation(); + } + +} diff --git a/tests/IsSshKeyValidatorTest.php b/tests/IsSshKeyValidatorTest.php new file mode 100644 index 0000000..e2f1ff1 --- /dev/null +++ b/tests/IsSshKeyValidatorTest.php @@ -0,0 +1,52 @@ +validator->validate(null, new IsSshKey()); + + $this->assertNoViolation(); + } + + public function testBlankIsValid(): void + { + $this->validator->validate('', new IsSshKey()); + + $this->assertNoViolation(); + } + + public function testKeyIsValid(): void + { + $this->validator->validate('ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAINCqSM/QRXfw4xbJo+DIW4k9Ehks9hpxMyN/SoFvJHNZ test ed25519', new IsSshKey()); + + $this->assertNoViolation(); + } + + public function testKeyIsInValid(): void + { + $key = 'sshed25519 AAAAC3NzaC1lZDI1NTE5AAAAINCqSM/QRXfw4xbJo+DIW4k9Ehks9hpxMyN/SoFvJHNZ test ed25519'; + $isSshKey = new IsSshKey(); + $this->validator->validate($key, $isSshKey); + + $this->buildViolation($isSshKey->message) + ->setParameter('{{ string }}', $key) + ->setCode(IsSshKey::NOT_SSH_KEY_ERROR) + ->assertRaised(); + } + + protected function createValidator(): IsSshKeyValidator + { + return new IsSshKeyValidator(); + } + +}