5546e65f8f33aa7d0391ed7770e9142c4b1465c4
[m6w6/seekat] / lib / API / Links.php
1 <?php
2
3 namespace seekat\API;
4
5 use http\Header;
6 use http\Params;
7 use http\QueryString;
8 use http\Url;
9
10 class Links implements \Serializable
11 {
12 /**
13 * Parsed "Link" relations
14 * @var \http\Params
15 */
16 private $params;
17
18 /**
19 * Parsed "Link" relations
20 * @var array
21 */
22 private $relations = [];
23
24 /**
25 * Parse the hypermedia link header
26 *
27 * @var string $header_value The value of the "Link" header
28 */
29 function __construct(Header $links) {
30 if (strcasecmp($links->name, "Link")) {
31 throw new \UnexpectedValueException("Expected 'Link' header, got: '{$links->name}'");
32 }
33 $this->unserialize($links->value);
34 }
35
36 function __toString() : string {
37 return $this->serialize();
38 }
39
40 function serialize() {
41 return (string) $this->params;
42 }
43
44 function unserialize($links) {
45 $this->params = new Params($links, ",", ";", "=",
46 Params::PARSE_RFC5988 | Params::PARSE_ESCAPED);
47 if ($this->params->params) {
48 foreach ($this->params->params as $link => $param) {
49 $this->relations[$param["arguments"]["rel"]] = new Url($link);
50 }
51 }
52 }
53
54 /**
55 * Receive the link header's parsed relations
56 *
57 * @return array
58 */
59 function getRelations() : array {
60 return $this->relations;
61 }
62
63 /**
64 * Get the URL of the link's "next" relation
65 *
66 * Returns the link's "last" relation if it exists and "next" is not set.
67 *
68 * @return \http\Url
69 */
70 function getNext() {
71 if (isset($this->relations["next"])) {
72 return $this->relations["next"];
73 }
74 if (isset($this->relations["last"])) {
75 return $this->relations["last"];
76 }
77 return null;
78 }
79
80 /**
81 * Get the URL of the link's "prev" relation
82 *
83 * Returns the link's "first" relation if it exists and "prev" is not set.
84 *
85 * @return \http\Url
86 */
87 function getPrev() {
88 if (isset($this->relations["prev"])) {
89 return $this->relations["prev"];
90 }
91 if (isset($this->relations["first"])) {
92 return $this->relations["first"];
93 }
94 return null;
95 }
96
97 /**
98 * Get the URL of the link's "last" relation
99 *
100 * @return \http\Url
101 */
102 function getLast() {
103 if (isset($this->relations["last"])) {
104 return $this->relations["last"];
105 }
106 return null;
107 }
108
109 /**
110 * Get the URL of the link's "first" relation
111 *
112 * @return \http\Url
113 */
114 function getFirst() {
115 if (isset($this->relations["first"])) {
116 return $this->relations["first"];
117 }
118 return null;
119 }
120
121 /**
122 * Get the page sequence of the current link's relation
123 *
124 * @param string $which The relation of which to extract the page
125 * @return int The current page sequence
126 */
127 function getPage($which) {
128 if (($link = $this->{"get$which"}())) {
129 $url = new Url($link, null, 0);
130 $qry = new QueryString($url->query);
131 return $qry->getInt("page", 1);
132 }
133 return 1;
134 }
135 }