CWIS Developer Documentation

- Home
- Main Page
- Namespaces
- Classes
- Files

- File List
- File Members

Axis--RSS.php
Go to the documentation of this file.
1 <?PHP
2
3 #
4 # Axis--RSS.php
5 # An Object to Support RSS 0.92 (Rich Site Summary) Output
6 #
7 # Copyright 2002 Axis Data
8 # This code is free software that can be used or redistributed under the
9 # terms of Version 2 of the GNU General Public License, as published by the
10 # Free Software Foundation (http://www.fsf.org).
11 #
12 # Author: Edward Almasy (almasy@axisdata.com)
13 #
14 # Part of the AxisPHP library v1.2.5
15 # For more information see http://www.axisdata.com/AxisPHP/
16 #
17
18
19 class RSS {
20
21 # ---- PUBLIC INTERFACE --------------------------------------------------
22
23 function RSS()
24 {
25 $this->ChannelCount = -1;
26
27 # default encoding is UTF-8
28 $this->Encoding = "UTF-8";
29 }
30
31 # required channel values
32 function AddChannel($Title, $Link, $Description, $RssLink)
33 {
34 $this->ChannelCount++;
35 $this->ItemCounts[$this->ChannelCount] = -1;
36 $this->Channels[$this->ChannelCount]["Title"] = $Title;
37 $this->Channels[$this->ChannelCount]["Link"] = $Link;
38 $this->Channels[$this->ChannelCount]["Description"] = $Description;
39 $this->Channels[$this->ChannelCount]["RssLink"] = $RssLink;
40 }
41 function SetImage($Url, $Height = NULL, $Width = NULL, $Description = NULL)
42 {
43 $this->Channels[$this->ChannelCount]["ImageUrl"] = $Url;
44 $this->Channels[$this->ChannelCount]["ImageHeight"] = $Height;
45 $this->Channels[$this->ChannelCount]["ImageWidth"] = $Width;
46 $this->Channels[$this->ChannelCount]["ImageDescription"] = $Description;
47 }
48
49 # optional channel values
50 function SetEncoding($Value) { $this->Encoding = $Value; }
51 function SetLanguage($Value) { $this->Channels[$this->ChannelCount]["Language"] = $Value; }
52 function SetCopyright($Value) { $this->Channels[$this->ChannelCount]["Copyright"] = $Value; }
53 function SetManagingEditor($Value) { $this->Channels[$this->ChannelCount]["ManagingEditor"] = $Value; }
54 function SetWebmaster($Value) { $this->Channels[$this->ChannelCount]["Webmaster"] = $Value; }
55 function SetPicsRating($Value) { $this->Channels[$this->ChannelCount]["PicsRating"] = $Value; }
56 function SetPublicationDate($Value) { $this->Channels[$this->ChannelCount]["PublicationDate"] = $this->FormatDate($Value); }
57 function SetLastChangeDate($Value) { $this->Channels[$this->ChannelCount]["LastChangeDate"] = $this->FormatDate($Value); }
58 function SetTextInput($Title, $Description, $Name)
59 {
60 $this->Channels[$this->ChannelCount]["TextInputTitle"] = $Title;
61 $this->Channels[$this->ChannelCount]["TextInputDescription"] = $Description;
62 $this->Channels[$this->ChannelCount]["TextInputName"] = $Name;
63 }
64 function SetSkipTimes($Days, $Hours)
65 {
66 # ???
67 }
68 function SetCloud($Domain, $Port, $Path, $Procedure, $Protocol)
69 {
70 # ???
71 }
72
73 # add item to channel
74 function AddItem($Title = NULL, $Link = NULL, $Description = NULL, $Date = NULL)
75 {
76 $this->ItemCounts[$this->ChannelCount]++;
77 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["Title"] = $Title;
78 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["Link"] = $Link;
79 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["Description"] = $Description;
80 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["Date"] = $this->FormatDate($Date);
81 }
82 function AddItemCategory($Category, $Url)
83 {
84 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["Category"] = $Category;
85 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["CategoryUrl"] = $Url;
86 }
87 function AddItemEnclosure($Url, $Length, $Type)
88 {
89 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["EnclosureUrl"] = $Url;
90 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["EnclosureLength"] = $Length;
91 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["EnclosureType"] = $Type;
92 }
93 function AddItemSource($Source, $Url)
94 {
95 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["Source"] = $Source;
96 $this->Items[$this->ChannelCount][$this->ItemCounts[$this->ChannelCount]]["SourceUrl"] = $Url;
97 }
98
99 # write out and RSS page
100 function PrintRSS()
101 {
102 # print opening elements
103 header("Content-type: application/rss+xml; charset=".$this->Encoding, TRUE);
104 FTOut("<?xml version='1.0' encoding='".$this->Encoding."' ?>");
105 FTOut("<rss version='2.0' xmlns:atom='http://www.w3.org/2005/Atom'>", 0);
106
107 # for each channel
108 for ($this->ChannelIndex = 0; $this->ChannelIndex <= $this->ChannelCount; $this->ChannelIndex++)
109 {
110 # open channel element
111 FTOut("<channel>");
112
113 # print required channel elements
114 $this->PrintChannelElement("Title", "title");
115 $this->PrintChannelElement("Link", "link");
116 $this->PrintChannelElement("Description", "description");
117 FTOut(
118 "<atom:link href='"
119 .$this->Channels[$this->ChannelCount]["RssLink"]
120 ."' rel='self' type='application/rss+xml' />");
121
122 # print image element if set (url, title, link required)
123 # title and link should be the same as those for the channel
124 if ($this->IsChannelElementSet("ImageUrl"))
125 {
126 FTOut("<image>");
127 $this->PrintChannelElement("ImageUrl", "url");
128 $this->PrintChannelElement("Title", "title");
129 $this->PrintChannelElement("Link", "link");
130 $this->PrintChannelElement("ImageWidth", "width");
131 $this->PrintChannelElement("ImageHeight", "height");
132 $this->PrintChannelElement("ImageDescription", "description");
133 FTOut("</image>");
134 }
135
136 # print optional channel elements
137 $this->PrintChannelElement("Language", "language");
138 $this->PrintChannelElement("Copyright", "copyright");
139 $this->PrintChannelElement("ManagingEditor", "managingEditor");
140 $this->PrintChannelElement("Webmaster", "webMaster");
141 $this->PrintChannelElement("PicsRating", "rating");
142 $this->PrintChannelElement("PublicationDate", "pubDate");
143 $this->PrintChannelElement("LastChangeDate", "lastBuildDate");
144 # ??? STILL TO DO: SkipDays, SkipHours, Cloud
145 FTOut("<docs>http://www.rssboard.org/rss-2-0-1</docs>");
146
147 # for each item in this channel
148 for ($this->ItemIndex = 0; $this->ItemIndex <= $this->ItemCounts[$this->ChannelCount]; $this->ItemIndex++)
149 {
150 # open item element
151 FTOut("<item>");
152
153 # print item elements
154 $this->PrintItemElement("Title", "title");
155 $this->PrintItemElement("Link", "link");
156 $this->PrintItemElement("Link", "guid");
157 $this->PrintItemElement("Description", "description");
158 $this->PrintItemElement("Date", "pubDate");
159 if (isset($this->Items[$this->ChannelIndex][$this->ItemIndex]["Category"])
160 && ($this->Items[$this->ChannelIndex][$this->ItemIndex]["Category"] != NULL))
161 {
162 FTOut("<category url='".$this->Items[$this->ChannelIndex][$this->ItemIndex]["CategoryUrl"]."'>");
163 FTOut($this->Items[$this->ChannelIndex][$this->ItemIndex]["Category"]);
164 FTOut("</category>");
165 }
166 if (isset($this->Items[$this->ChannelIndex][$this->ItemIndex]["EnclosureUrl"])
167 && ($this->Items[$this->ChannelIndex][$this->ItemIndex]["EnclosureUrl"] != NULL))
168 {
169 FTOut("<enclosure "
170 ."url='".$this->Items[$this->ChannelIndex][$this->ItemIndex]["EnclosureUrl"]."' "
171 ."length='".$this->Items[$this->ChannelIndex][$this->ItemIndex]["EnclosureLength"]."' "
172 ."type='".$this->Items[$this->ChannelIndex][$this->ItemIndex]["EnclosureType"]."' />");
173 }
174 if (isset($this->Items[$this->ChannelIndex][$this->ItemIndex]["Source"])
175 && ($this->Items[$this->ChannelIndex][$this->ItemIndex]["Source"] != NULL))
176 {
177 FTOut("<source url='".$this->Items[$this->ChannelIndex][$this->ItemIndex]["SourceUrl"]."'>");
178 FTOut($this->Items[$this->ChannelIndex][$this->ItemIndex]["Source"]);
179 FTOut("</source>");
180 }
181
182 # close item element
183 FTOut("</item>");
184 }
185
186 # close channel element
187 FTOut("</channel>");
188 }
189
190 # print closing elements
191 FTOut("</rss>");
192 }
193
194
195 # ---- PRIVATE INTERFACE -------------------------------------------------
196
197 var $Encoding;
198 var $Channels;
199 var $Items;
200 var $ChannelCount;
201 var $ItemCounts;
202 var $ChannelIndex;
203 var $ItemIndex;
204
210 private function IsChannelElementSet($VarName)
211 {
212 return (isset($this->Channels[$this->ChannelIndex][$VarName])
213 && $this->Channels[$this->ChannelIndex][$VarName] != NULL
214 && strlen($this->Channels[$this->ChannelIndex][$VarName]));
215 }
216
222 private function IsItemElementSet($VarName)
223 {
224 return (isset($this->Items[$this->ChannelIndex][$this->ItemIndex][$VarName])
225 && $this->Items[$this->ChannelIndex][$this->ItemIndex][$VarName] != NULL);
226 }
227
233 private function PrintChannelElement($VarName, $TagName)
234 {
235 # only print channel elements if set
236 if (!$this->IsChannelElementSet($VarName))
237 {
238 return;
239 }
240
241 $InnerText = $this->EscapeInnerText(
242 $this->Channels[$this->ChannelIndex][$VarName]);
243
244 FTOut("<${TagName}>".$InnerText."</${TagName}>");
245 }
246
252 private function PrintItemElement($VarName, $TagName)
253 {
254 # only print elements that are set
255 if (!$this->IsItemElementSet($VarName))
256 {
257 return;
258 }
259
260 $InnerText = $this->EscapeInnerText(
261 $this->Items[$this->ChannelIndex][$this->ItemIndex][$VarName]);
262
263 FTOut("<${TagName}>".$InnerText."</${TagName}>");
264 }
265
273 private function FormatDate($Value)
274 {
275 return date("D, j M Y h:i:s O", strtotime($Value));
276 }
277
284 private function EscapeInnerText($Text)
285 {
286 # remove control characters
287 $Intermediate = preg_replace("/[\\x00-\\x1F]+/", "", $Text);
288
289 # escape XML special characters for PHP version < 5.2.3
290 if (version_compare(phpversion(), "5.2.3", "<"))
291 {
292 $Intermediate = htmlspecialchars(
293 $Intermediate, ENT_QUOTES, $this->Encoding);
294 }
295
296 # escape XML special characters for PHP version >= 5.2.3
297 else
298 {
299 $Intermediate = htmlspecialchars(
300 $Intermediate, ENT_QUOTES, $this->Encoding, FALSE);
301 }
302
303 # map named entities to their hex references
304 $Replacements = array(
305 "&amp;" => "&#x26;",
306 "&lt;" => "&#x3C;",
307 "&gt;" => "&#x3E;",
308 "&quot;" => "&#x22;",
309 "&#039;" => "&#x27;");
310
311 # replace named entities with hex references for compatibility as
312 # specified by the RSS spec/best practices
313 $Intermediate = str_replace(
314 array_keys($Replacements),
315 array_values($Replacements),
316 $Intermediate);
317
318 return $Intermediate;
319 }
320
321 }
322
323 # (FTOut == Formatted Tag Output)
324 function FTOut($String, $NewIndent = NULL)
325 {
326 static $Indent = 0;
327
328 $IndentSize = 4;
329
330 # decrease indent if string contains end tag and does not start with begin tag
331 if (preg_match("/<\/[A-Za-z0-9]+>/", $String) && !preg_match("/^<[^\/]+/", $String)) { $Indent--; }
332
333 # reset indent if value is supplied
334 if ($NewIndent != NULL) { $Indent = $NewIndent; }
335
336 # print string
337 print(substr(" ",
338 0, ($Indent * $IndentSize)).$String."\n");
339
340 # inrease indent if string starts with begin tag and does not contain end tag
341 if (preg_match("/^<[^\/]+/", $String)
342 && !preg_match("/<\/[A-Za-z0-9]+>/", $String)
343 && !preg_match("/\/>$/", $String))
344 {
345 $Indent++;
346 }
347 }