Lines 84.61% 22 / 26
Methods 66.66% 6 / 9
Classes 0.00% 0 / 1
Covered by tests of size
Name Lines Methods CRAP
 __construct 100.00% 1 / 1 100.00% 1 / 1 1
 getEncryptionContainer 100.00% 2 / 2 100.00% 1 / 1 1
 getErrors 100.00% 2 / 2 100.00% 1 / 1 3
 addError 0.00% 0 / 1 0.00% 0 / 1 2
 selectAuth 80.00% 8 / 10 0.00% 0 / 1 4.13
 enableReadOnly 100.00% 3 / 3 100.00% 1 / 1 1
 disableReadOnly 100.00% 3 / 3 100.00% 1 / 1 1
 isReadOnly 100.00% 1 / 1 100.00% 1 / 1 1
 encrypt 66.66% 2 / 3 0.00% 0 / 1 2.15
41class Auth
42{
43    private const string PMF_ERROR_USER_NO_AUTH_TYPE = 'Specified authentication access class could not be found.';
44
45    /**
46     * Public array that contains error messages.
47     *
48     * @var array<string>
49     */
50    protected array $errors = [];
51
52    /**
53     * Container that stores the encryption object.
54     */
55    protected ?Encryption $encContainer = null;
56
57    /**
58     * Read-only flag.
59     */
60    private bool $readOnly = false;
61
62    /**
63     * Constructor.
64     */
65    public function __construct(
66        protected Configuration $configuration,
67    ) {
68    }
69
70    /**
71     * Instantiates an Encryption implementation based on the given type.
72     */
73    public function getEncryptionContainer(string $encType): Encryption
74    {
75        $this->encContainer = Encryption::getInstance($encType, $this->configuration);
76        return $this->encContainer;
77    }
78
79    /**
80     * Returns a string with all collected error messages, each separated by a new line.
81     */
82    public function getErrors(): string
83    {
84        $message = $this->errors !== [] ? implode(separator: PHP_EOL, array: $this->errors) . PHP_EOL : '';
85        return $message . ($this->encContainer instanceof \phpMyFAQ\Encryption ? $this->encContainer->error() : '');
86    }
87
88    /**
89     * Adds an error message to the list of errors.
90     */
91    public function addError(string $message): void
92    {
93        $this->errors[] = $message;
94    }
95
96    /**
97     * Returns an authentication object for the specified method.
98     *
99     * @throws Exception If the auth class cannot be found
100     */
101    public function selectAuth(string $method): Auth&AuthDriverInterface
102    {
103        $method = ucfirst(strtolower($method));
104        $authClass = '\\phpMyFAQ\\Auth\\Auth' . $method;
105
106        if (!class_exists($authClass) || !is_subclass_of($authClass, self::class)) {
107            $this->errors[] = self::PMF_ERROR_USER_NO_AUTH_TYPE;
108            throw new Exception(message: self::PMF_ERROR_USER_NO_AUTH_TYPE);
109        }
110
111        $auth = new $authClass($this->configuration);
112        if (!$auth instanceof AuthDriverInterface) {
113            $this->errors[] = self::PMF_ERROR_USER_NO_AUTH_TYPE;
114            throw new Exception(message: self::PMF_ERROR_USER_NO_AUTH_TYPE);
115        }
116
117        return $auth;
118    }
119
120    /**
121     * Enables read-only mode and returns the previous state.
122     */
123    public function enableReadOnly(): bool
124    {
125        $oldReadOnly = $this->readOnly;
126        $this->readOnly = true;
127
128        return $oldReadOnly;
129    }
130
131    /**
132     * Disables read-only mode and returns the previous state.
133     */
134    public function disableReadOnly(): bool
135    {
136        $oldReadOnly = $this->readOnly;
137        $this->readOnly = false;
138
139        return $oldReadOnly;
140    }
141
142    /**
143     * Returns the current read-only state.
144     */
145    public function isReadOnly(): bool
146    {
147        return $this->readOnly;
148    }
149
150    /**
151     * Encrypts a string using the configured encryption container.
152     *
153     * @throws Exception If no encryption container was configured
154     */
155    public function encrypt(#[SensitiveParameter] string $string): string
156    {
157        if (!$this->encContainer instanceof \phpMyFAQ\Encryption) {
158            throw new Exception(message: 'No encryption container configured. Call getEncryptionContainer() first.');
159        }
160
161        return $this->encContainer->encrypt($string);
162    }
163}