1<?php
2
3/**
4 * This file is part of the FreeDSx LDAP package.
5 *
6 * (c) Chad Sikorra <Chad.Sikorra@gmail.com>
7 *
8 * For the full copyright and license information, please view the LICENSE
9 * file that was distributed with this source code.
10 */
11
12namespace FreeDSx\Ldap\Control\Vlv;
13
14use FreeDSx\Asn1\Asn1;
15use FreeDSx\Asn1\Exception\EncoderException;
16use FreeDSx\Asn1\Type\AbstractType;
17use FreeDSx\Ldap\Control\Control;
18use FreeDSx\Ldap\Exception\RuntimeException;
19use FreeDSx\Ldap\Search\Filter\GreaterThanOrEqualFilter;
20
21/**
22 * Represents a VLV Request. draft-ietf-ldapext-ldapv3-vlv-09
23 *
24 * VirtualListViewRequest ::= SEQUENCE {
25 *     beforeCount    INTEGER (0..maxInt),
26 *     afterCount     INTEGER (0..maxInt),
27 *     target       CHOICE {
28 *         byOffset        [0] SEQUENCE {
29 *             offset          INTEGER (1 .. maxInt),
30 *             contentCount    INTEGER (0 .. maxInt) },
31 *         greaterThanOrEqual [1] AssertionValue },
32 *     contextID     OCTET STRING OPTIONAL }
33 *
34 * @author Chad Sikorra <Chad.Sikorra@gmail.com>
35 */
36class VlvControl extends Control
37{
38    use VlvTrait;
39
40    /**
41     * @var int
42     */
43    protected $after;
44
45    /**
46     * @var int
47     */
48    protected $before;
49
50    /**
51     * @var null|GreaterThanOrEqualFilter
52     */
53    protected $filter;
54
55    /**
56     * @param int $before
57     * @param int $after
58     * @param null|int $offset
59     * @param null|int $count
60     * @param GreaterThanOrEqualFilter|null $filter
61     * @param null|string $contextId
62     */
63    public function __construct(int $before, int $after, ?int $offset = null, ?int $count = null, GreaterThanOrEqualFilter $filter = null, ?string $contextId = null)
64    {
65        $this->before = $before;
66        $this->after = $after;
67        $this->offset = $offset;
68        $this->count = $count;
69        $this->filter = $filter;
70        $this->contextId = $contextId;
71        parent::__construct(self::OID_VLV);
72    }
73
74    /**
75     * @return int
76     */
77    public function getAfter(): int
78    {
79        return $this->after;
80    }
81
82    /**
83     * @param int $after
84     * @return $this
85     */
86    public function setAfter(int $after)
87    {
88        $this->after = $after;
89
90        return $this;
91    }
92
93    /**
94     * @return int
95     */
96    public function getBefore(): int
97    {
98        return $this->before;
99    }
100
101    /**
102     * @param int $before
103     * @return $this
104     */
105    public function setBefore(int $before)
106    {
107        $this->before = $before;
108
109        return $this;
110    }
111
112    /**
113     * @param null|int $count
114     * @return $this
115     */
116    public function setCount(?int $count)
117    {
118        $this->count = $count;
119
120        return $this;
121    }
122
123    /**
124     * @param string|null $contextId
125     * @return $this
126     */
127    public function setContextId($contextId)
128    {
129        $this->contextId = $contextId;
130
131        return $this;
132    }
133
134    /**
135     * @param null|int $offset
136     * @return $this
137     */
138    public function setOffset(?int $offset)
139    {
140        $this->offset = $offset;
141
142        return $this;
143    }
144
145    /**
146     * @return null|GreaterThanOrEqualFilter
147     */
148    public function getFilter(): ?GreaterThanOrEqualFilter
149    {
150        return $this->filter;
151    }
152
153    /**
154     * @param GreaterThanOrEqualFilter|null $filter
155     * @return $this
156     */
157    public function setFilter(GreaterThanOrEqualFilter $filter = null)
158    {
159        $this->filter = $filter;
160
161        return $this;
162    }
163
164    /**
165     * @throws EncoderException
166     * @throws RuntimeException
167     */
168    public function toAsn1(): AbstractType
169    {
170        $this->controlValue = Asn1::sequence(
171            Asn1::integer($this->before),
172            Asn1::integer($this->after)
173        );
174        if ($this->filter === null && ($this->count === null || $this->offset === null)) {
175            throw new RuntimeException('You must specify a filter or offset and count for a VLV request.');
176        }
177        if ($this->filter !== null) {
178            $this->controlValue->addChild(Asn1::context(1, $this->filter->toAsn1()));
179        } else {
180            $this->controlValue->addChild(Asn1::context(0, Asn1::sequence(
181                Asn1::integer((int) $this->offset),
182                Asn1::integer((int) $this->count)
183            )));
184        }
185
186        return parent::toAsn1();
187    }
188
189    /**
190     * {@inheritDoc}
191     * @return void
192     */
193    public static function fromAsn1(AbstractType $type)
194    {
195        // TODO: Implement fromAsn1() method.
196    }
197}
198