-
Notifications
You must be signed in to change notification settings - Fork 0
/
bsmlibrary.php
205 lines (170 loc) · 5.27 KB
/
bsmlibrary.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
<?php
// Format in which to get SmugMug feeds; "rss200" or "atom03"
define('BSM_FORMAT', 'rss200');
abstract class BSM_Consumable implements Iterator {
protected $members; // Array of values to be iterated.
protected $doc; // Instance of DOMDocument for the consumable feed.
protected $xpath; // Instance of DOMXPath, for querying the feed.
public function __construct($feedUrl) {
$this->members = array();
$this->doc = new DOMDocument();
$this->doc->load($feedUrl);
$this->xpath = new DOMXPath($this->doc);
$this->parseFeed();
}
function rewind() {
return reset($this->members);
}
function current() {
return current($this->members);
}
function key() {
return key($this->members);
}
function next() {
return next($this->members);
}
function valid() {
return key($this->members) !== NULL;
}
function size() {
return count($this->members);
}
/**
* Child classes should implement this function in order to parse gallery and
* photo data out of SmugMug's XML feeds. It's the last thing run by
* the constructor.
*/
abstract protected function parseFeed();
}
// A SmugMug photo.
class BSM_Photo {
private $title; // Title of the photo.
private $link; // Link to SmugMug permalink page for the photo.
private $guid; // Unique identifier at SmugMug.
public function __construct($params = NULL) {
if (is_array($params)) {
foreach ($params as $k => $v)
if (property_exists('BSM_Photo', $k))
$this->$k = $v;
}
}
/**
* Get the URL for a photo's image file at a given size. Examples:
*
* Pre-defined SmugMug sizes: Th, Ti, S, M, L, XL, XL2, XL3
* Any given dimensions, as a string: "640x640"
*
* SmugMug will always retain aspect ratio when resizing to arbitrary
* dimensions.
*/
public function getImageUrl($size) {
if (preg_match('/^(.+?)\/Th\/(.+?)-Th\.([a-z]+)$/i', $this->guid, $m)) {
return sprintf("%s/%s/%s-%s.%s", $m[1], $size, $m[2], $size, $m[3]);
}
elseif (preg_match('/^(.+?)-Th\.([a-z]+)$/i', $this->guid, $m)) {
return sprintf("%s-%s.%s", $m[1], $size, $m[2]);
}
else {
return null;
}
}
/**
* Get a URL to a page at SmugMug showing the photo. If the $size parameter
* is not given, the URL to the photos' gallery page will be returned. If the
* size parameter is given, a URL to a lightbox page showing the photo will be
* returned.
*/
public function getLinkUrl($size = NULL) {
return $this->link;
}
// Get the photos title at SmugMug.
public function getTitle() {
return $this->title;
}
public function getGuid() {
return $this->guid;
}
}
/**
* A SmugMug gallery. Iterate of an instance of this to traverse the photos
* contained within.
*/
class BSM_Gallery extends BSM_Consumable {
// Combine the following two in order to generate a feed or gallery URL.
private $albumId;
private $albumKey;
private $title; // Title of the gallery.
private $link; // URL to the gallery.
public function __construct($albumId, $albumKey) {
$this->albumId = $albumId;
$this->albumKey = $albumKey;
$feedUrl = sprintf(
"http://api.smugmug.com/hack/feed.mg?Type=gallery&Data=%s_%s&format=%s",
$this->albumId,
$this->albumKey,
BSM_FORMAT
);
parent::__construct($feedUrl);
}
public function getTitle() {
return $this->title;
}
public function getLink() {
return $this->link;
}
public function numPhotos() {
return $this->size();
}
public function getAlbumId() {
return $this->albumId;
}
public function getAlbumKey() {
return $this->albumKey;
}
// Extract photos and gallery meta data from its XML feed.
protected function parseFeed() {
$doc = $this->doc;
$xpath = $this->xpath;
$this->title = $xpath->query('//rss/channel/title')->item(0)->nodeValue;
$this->link = $xpath->query('//rss/channel/link')->item(0)->nodeValue;
$items = $xpath->query('//rss/channel/item');
foreach ($items as $item) {
$photo = new BSM_Photo(array(
'title' => $item->getElementsByTagName('title')->item(0)->nodeValue,
'link' => $item->getElementsByTagName('link')->item(0)->nodeValue . '&lb=1&s=A',
'guid' => $item->getElementsByTagName('guid')->item(0)->nodeValue
));
$this->members[] = $photo;
}
}
}
/**
* A SmugMug account. Iterate over an instance of this to traverse the
* galleries contained within.
*/
class BSM_Account extends BSM_Consumable {
private $nickname;
private $baseUrl;
public function __construct($nickname) {
$this->nickname = $nickname;
$feedUrl = sprintf(
"http://api.smugmug.com/hack/feed.mg?Type=nickname&Data=%s&format=%s",
$this->nickname,
BSM_FORMAT
);
parent::__construct($feedUrl);
}
// Extract galleries from XML feed.
protected function parseFeed() {
$doc = $this->doc;
$xpath = $this->xpath;
$items = $xpath->query('//rss/channel/item');
foreach ($items as $item) {
$guid = $item->getElementsByTagName('guid')->item(0)->nodeValue;
if (preg_match('/\/([a-z0-9]+)_([a-z0-9]+)\/?$/i', $guid, $m)) {
$this->members[] = new BSM_Gallery($m[1], $m[2]);
}
}
}
}