1<?php
2/**
3 * This file is part of the FreeDSx LDAP package.
4 *
5 * (c) Chad Sikorra <Chad.Sikorra@gmail.com>
6 *
7 * For the full copyright and license information, please view the LICENSE
8 * file that was distributed with this source code.
9 */
10
11namespace FreeDSx\Ldap\Operation\Request;
12
13use FreeDSx\Asn1\Asn1;
14use FreeDSx\Asn1\Type\AbstractType;
15use FreeDSx\Asn1\Type\OctetStringType;
16use FreeDSx\Ldap\Entry\Dn;
17use FreeDSx\Ldap\Exception\ProtocolException;
18
19/**
20 * RFC 4511, 4.8
21 *
22 * DelRequest ::= [APPLICATION 10] LDAPDN
23 *
24 * @author Chad Sikorra <Chad.Sikorra@gmail.com>
25 */
26class DeleteRequest implements RequestInterface, DnRequestInterface
27{
28    protected const APP_TAG = 10;
29
30    /**
31     * @var Dn
32     */
33    protected $dn;
34
35    /**
36     * @param string $dn
37     */
38    public function __construct($dn)
39    {
40        $this->setDn($dn);
41    }
42
43    /**
44     * @param string|Dn $dn
45     * @return $this
46     */
47    public function setDn($dn)
48    {
49        $this->dn = $dn instanceof Dn ? $dn : new Dn($dn);
50
51        return $this;
52    }
53
54    /**
55     * @return Dn
56     */
57    public function getDn(): Dn
58    {
59        return $this->dn;
60    }
61
62    /**
63     * {@inheritdoc}
64     */
65    public function toAsn1(): AbstractType
66    {
67        return Asn1::application(self::APP_TAG, Asn1::octetString($this->dn->toString()));
68    }
69
70    /**
71     * {@inheritdoc}
72     */
73    public static function fromAsn1(AbstractType $type)
74    {
75        self::validate($type);
76
77        return new self($type->getValue());
78    }
79
80    /**
81     * @param AbstractType $type
82     * @throws ProtocolException
83     */
84    protected static function validate(AbstractType $type): void
85    {
86        if (!$type instanceof OctetStringType || $type->getTagClass() !== AbstractType::TAG_CLASS_APPLICATION) {
87            throw new ProtocolException('The delete request must be an octet string with an application tag class.');
88        }
89        if ($type->getTagNumber() !== self::APP_TAG) {
90            throw new ProtocolException(sprintf(
91                'The delete request must have an app tag of %s, received: %s',
92                self::APP_TAG,
93                $type->getTagNumber()
94            ));
95        }
96    }
97}
98