]> git.mxchange.org Git - friendica.git/blob - mod/dfrn_confirm.php
e5a550cd9511c26969bcf60d2a75523c5c4ba7a7
[friendica.git] / mod / dfrn_confirm.php
1 <?php
2
3
4
5 function dfrn_confirm_post(&$a) {
6         
7         if($a->argc > 1)
8                 $node = $a->argv[1];
9
10         if(x($_POST,'source_url')) {
11
12                 // We are processing an external confirmation to an introduction created by our user.
13
14                 $public_key = $_POST['public_key'];
15                 $dfrn_id = $_POST['dfrn_id'];
16                 $source_url = $_POST['source_url'];
17                 $aes_key = $_POST['aes_key'];
18
19                 // Find our user's account
20
21                 $r = q("SELECT * FROM `user` WHERE `nickname` = '%s' LIMIT 1",
22                         dbesc($node));
23
24                 if(! count($r)) {
25                         xml_status(3); // failure
26                 }
27
28                 $my_prvkey = $r[0]['prvkey'];
29                 $local_uid = $r[0]['uid'];
30
31                 $decrypted_source_url = "";
32
33                 // verify everything
34
35                 openssl_private_decrypt($source_url,$decrypted_source_url,$my_prvkey);
36
37
38                 $ret = q("SELECT * FROM `contact` WHERE `url` = '%s' AND `uid` = %d LIMIT 1",
39                         dbesc($decrypted_source_url),
40                         intval($local_uid));
41
42                 if(! count($ret)) {
43                         // this is either a bogus confirmation or we deleted the original introduction.
44                         xml_status(3); 
45                 }
46
47                 // Decrypt all this stuff we just received
48
49                 $foreign_pubkey = $ret[0]['site-pubkey'];
50                 $dfrn_record = $ret[0]['id'];
51                 $decrypted_dfrn_id = "";
52                 openssl_public_decrypt($dfrn_id,$decrypted_dfrn_id,$foreign_pubkey);
53
54                 if(strlen($aes_key)) {
55                         $decrypted_aes_key = "";
56                         openssl_private_decrypt($aes_key,$decrypted_aes_key,$my_prvkey);
57                         $dfrn_pubkey = openssl_decrypt($public_key,'AES-256-CBC',$decrypted_aes_key);
58                 }
59                 else {
60                         $dfrn_pubkey = $public_key;
61                 }
62
63                 $r = q("SELECT * FROM `contact` WHERE `dfrn-id` = '%s' LIMIT 1",
64                         dbesc($decrypted_dfrn_id),
65                         intval($local_uid));
66                 if(count($r))
67                         xml_status(1); // Birthday paradox - duplicate dfrn-id
68
69                 $r = q("UPDATE `contact` SET `dfrn-id` = '%s', `pubkey` = '%s' WHERE `id` = %d LIMIT 1",
70                         dbesc($decrypted_dfrn_id),
71                         dbesc($dfrn_pubkey),
72                         intval($dfrn_record));
73                 if($r) {
74
75                         // We're good but now we have to scrape the profile photo and send notifications.
76
77                         require_once("Photo.php");
78
79                         $photo_failure = false;
80
81                         $r = q("SELECT `photo` FROM `contact` WHERE `id` = %d LIMIT 1",
82                                 intval($dfrn_record));
83                         if(count($r)) {
84
85                                 $filename = basename($r[0]['photo']);
86                                 $img_str = fetch_url($r[0]['photo'],true);
87                                 $img = new Photo($img_str);
88                                 if($img) {
89
90                                         $img->scaleImageSquare(175);
91                                         
92                                         $hash = hash('md5',uniqid(mt_rand(),true));
93
94                                         $r = q("INSERT INTO `photo` ( `uid`, `contact-id`, `resource-id`, `created`, `edited`, `filename`, `album`, `height`, `width`, `data`, `scale` )
95                                                 VALUES ( %d, %d, '%s', '%s', '%s', '%s', '%s', %d, %d, '%s', 4 )",
96                                                 intval($local_uid),
97                                                 intval($dfrn_record),
98                                                 dbesc($hash),
99                                                 datetime_convert(),
100                                                 datetime_convert(),
101                                                 dbesc(basename($r[0]['photo'])),
102                                                 dbesc( t('Contact Photos') ),
103                                                 intval($img->getHeight()),
104                                                 intval($img->getWidth()),
105                                                 dbesc($img->imageString())
106                                         );
107                                         if($r === false)
108                                                 $photo_failure = true;
109                                         
110                                         $img->scaleImage(80);
111                                         $r =  q("INSERT INTO `photo` ( `uid`, `contact-id`, `resource-id`, `created`, `edited`, `filename`, `album`, `height`, `width`, `data`, `scale` )
112                                                 VALUES ( %d, %d, '%s', '%s', '%s', '%s', '%s', %d, %d, '%s', 5 )",
113                                                 intval($local_uid),
114                                                 intval($dfrn_record),
115                                                 dbesc($hash),
116                                                 datetime_convert(),
117                                                 datetime_convert(),
118                                                 dbesc(basename($r[0]['photo'])),
119                                                 dbesc( t('Contact Photos')),
120                                                 intval($img->getHeight()),
121                                                 intval($img->getWidth()),
122                                                 dbesc($img->imageString())
123                                         );
124                                         if($r === false)
125                                                 $photo_failure = true;
126
127                                         $photo = $a->get_baseurl() . '/photo/' . $hash . '-4.jpg';
128                                         $thumb = $a->get_baseurl() . '/photo/' . $hash . '-5.jpg';      
129                                 }
130                                 else
131                                         $photo_failure = true;
132                         }
133                         else
134                                 $photo_failure = true;
135
136                         if($photo_failure) {
137                                 $photo = $a->get_baseurl() . '/images/default-profile.jpg';
138                                 $thumb = $a->get_baseurl() . '/images/default-profile-sm.jpg';
139                         }
140
141                         $r = q("UPDATE `contact` SET `photo` = '%s', `thumb` = '%s', `blocked` = 0, `pending` = 0 WHERE `id` = %d LIMIT 1",
142                                 dbesc($photo),
143                                 dbesc($thumb),
144                                 intval($dfrn_record)
145                         );
146                         if($r === false)
147                                 notice( t("Unable to set contact photo info.") . EOL);
148
149                         // Otherwise everything seems to have worked and we are almost done. Yay!
150                         // Send an email notification
151
152                         $r = q("SELECT * FROM `contact` LEFT JOIN `user` ON `contact`.`uid` = `user`.`uid`
153                                 WHERE `contact`.`id` = %d LIMIT 1",
154                                 intval($dfrn_record));
155                         if((count($r)) && ($r[0]['notify-flags'] & NOTIFY_CONFIRM)) {
156
157                                 $tpl = file_get_contents('view/intro_complete_eml.tpl');
158                         
159                                 $email_tpl = replace_macros($tpl, array(
160                                         '$sitename' => $a->config['sitename'],
161                                         '$siteurl' =>  $a->get_baseurl(),
162                                         '$username' => $r[0]['username'],
163                                         '$email' => $r[0]['email'],
164                                         '$fn' => $r[0]['name'],
165                                         '$dfrn_url' => $r[0]['url'],
166                                         '$uid' => $newuid )
167                                 );
168         
169                                 $res = mail($r[0]['email'], t("Introduction accepted at ") . $a->config['sitename'],
170                                         $email_tpl,t("From: Administrator@") . $_SERVER[SERVER_NAME] );
171                                 if(!$res) {
172                                         notice( t("Email notification failed.") . EOL );
173                                 }
174                         }
175                         xml_status(0); // Success
176
177                         return; // NOTREACHED
178                 }
179                 else {
180                         xml_status(2);  // Hopefully temporary problem that can be retried.
181                 }
182                 return; // NOTREACHED
183
184         ////////////////////// End of this scenario ///////////////////////////////////////////////
185         }
186         else {
187
188                 // We are processing a local confirmation initiated on this system by our user to an external introduction.
189
190                 $uid = $_SESSION['uid'];
191
192                 if(! $uid) {
193                         notice(t("Permission denied.") . EOL );
194                         return;
195                 }       
196         
197                 $dfrn_id = ((x($_POST,'dfrn_id')) ? notags(trim($_POST['dfrn_id'])) : "");
198                 $intro_id = intval($_POST['intro_id']);
199
200                 $r = q("SELECT * FROM `contact` WHERE `issued-id` = '%s' AND `uid` = %d LIMIT 1",
201                                 dbesc($dfrn_id),
202                                 intval($uid)
203                                 );
204
205                 if((! $r) || (! count($r))) {
206                         notice( t('Node does not exist.') . EOL );
207                         return;
208                 }
209
210                 $contact_id = $r[0]['id'];
211                 $site_pubkey = $r[0]['site-pubkey'];
212                 $dfrn_confirm = $r[0]['confirm'];
213                 $aes_allow = $r[0]['aes_allow'];
214
215                 $res=openssl_pkey_new(array(
216                         'digest_alg' => 'whirlpool',
217                         'private_key_bits' => 4096,
218                         'encrypt_key' => false ));
219
220
221                 $private_key = '';
222
223                 openssl_pkey_export($res, $private_key);
224
225
226                 $pubkey = openssl_pkey_get_details($res);
227                 $public_key = $pubkey["key"];
228
229                 $r = q("UPDATE `contact` SET `issued-pubkey` = '%s', `prvkey` = '%s' WHERE `id` = %d AND `uid` = %d LIMIT 1",
230                         dbesc($public_key),
231                         dbesc($private_key),
232                         intval($contact_id),
233                         intval($uid) 
234                 );
235
236
237                 $params = array();
238
239                 $src_aes_key = random_string();
240                 $result = "";
241
242                 openssl_private_encrypt($dfrn_id,$result,$a->user['prvkey']);
243
244                 $params['dfrn_id'] = $result;
245                 $params['public_key'] = $public_key;
246
247
248                 openssl_public_encrypt($_SESSION['my_url'], $params['source_url'], $site_pubkey);
249
250                 if($aes_allow && function_exists('openssl_encrypt')) {
251                         openssl_public_encrypt($src_aes_key, $params['aes_key'], $site_pubkey);
252                         $params['public_key'] = openssl_encrypt($public_key,'AES-256-CBC',$src_aes_key);
253                 }
254
255                 $res = post_url($dfrn_confirm,$params);
256
257 // uncomment the following two lines and comment the following xml/status lines
258 // to debug the remote confirmation section (when both confirmations 
259 // and responses originate on this system)
260
261 // echo $res;
262 // $status = 0;
263
264                 $xml = simplexml_load_string($res);
265                 $status = (int) $xml->status;
266                 switch($status) {
267                         case 0:
268                                 notice( t("Confirmation completed successfully") . EOL);
269                                 break;
270                         case 1:
271
272                                 // birthday paradox - generate new dfrn-id and fall through.
273
274                                 $new_dfrn_id = random_string();
275                                 $r = q("UPDATE contact SET `issued-id` = '%s' WHERE `id` = %d AND `uid` = %d LIMIT 1",
276                                         dbesc($new_dfrn_id),
277                                         intval($contact_id),
278                                         intval($uid) 
279                                 );
280
281                         case 2:
282                                 notice( t("Temporary failure. Please wait and try again.") . EOL);
283                                 break;
284
285
286                         case 3:
287                                 notice( t("Introduction failed or was revoked. Cannot complete.") . EOL);
288                                 break;
289                 }
290
291                 if(($status == 0 || $status == 3) && ($intro_id)) {
292
293                         //delete the notification
294
295                         $r = q("DELETE FROM `intro` WHERE `id` = %d AND `uid` = %d LIMIT 1",
296                                 intval($intro_id),
297                                 intval($uid)
298                         );
299                         
300                 }
301                 if($status != 0) 
302                         return;
303                 
304
305                 require_once("Photo.php");
306
307                 $photo_failure = false;
308
309                 $r = q("SELECT `photo` FROM `contact` WHERE `id` = %d LIMIT 1",
310                         intval($contact_id));
311                 if(count($r)) {
312
313                         $filename = basename($r[0]['photo']);
314                         $img_str = fetch_url($r[0]['photo'],true);
315                         $img = new Photo($img_str);
316                         if($img) {
317
318                                 $img->scaleImageSquare(175);
319                                         
320                                 $hash = hash('md5',uniqid(mt_rand(),true));
321
322                                 $r = q("INSERT INTO `photo` ( `uid`, `resource-id`, `created`, `edited`, `filename`, `album`, `height`, `width`, `data`, `scale` )
323                                         VALUES ( %d, '%s', '%s', '%s', '%s', '%s', %d, %d, '%s', 4 )",
324                                         intval($local_uid),
325                                         dbesc($hash),
326                                         datetime_convert(),
327                                         datetime_convert(),
328                                         dbesc(basename($r[0]['photo'])),
329                                         dbesc( t('Contact Photos') ),
330                                         intval($img->getHeight()),
331                                         intval($img->getWidth()),
332                                         dbesc($img->imageString())
333                                 );
334                                 if($r === false)
335                                         $photo_failure = true;
336                                 $img->scaleImage(80);
337                                 $r =  q("INSERT INTO `photo` ( `uid`, `resource-id`, `created`, `edited`, `filename`, `album`, `height`, `width`, `data`, `scale` )
338                                         VALUES ( %d, '%s', '%s', '%s', '%s', '%s', %d, %d, '%s', 5 )",
339                                         intval($local_uid),
340                                         dbesc($hash),
341                                         datetime_convert(),
342                                         datetime_convert(),
343                                         dbesc(basename($r[0]['photo'])),
344                                         dbesc( t('Contact Photos') ),
345                                         intval($img->getHeight()),
346                                         intval($img->getWidth()),
347                                         dbesc($img->imageString())
348                                 );
349                                 if($r === false)
350                                         $photo_failure = true;
351
352                                 $photo = $a->get_baseurl() . '/photo/' . $hash . '-4.jpg';
353                                 $thumb = $a->get_baseurl() . '/photo/' . $hash . '-5.jpg';
354                         }
355                         else
356                                 $photo_failure = true;
357                 }
358                 else
359                         $photo_failure = true;
360
361                 if($photo_failure) {
362                         $photo = $a->get_baseurl() . '/images/default-profile.jpg';
363                         $thumb = $a->get_baseurl() . '/images/default-profile-sm.jpg';
364                 }
365
366                 $r = q("UPDATE `contact` SET `photo` = '%s', `thumb` = '%s', `blocked` = 0, `pending` = 0 WHERE `id` = %d LIMIT 1",
367                         dbesc($photo),
368                         dbesc($thumb),
369                         intval($contact_id)
370                 );
371                 if($r === false)
372                         notice( t('Unable to set contact photo.') . EOL);
373
374                 goaway($a->get_baseurl() . '/contacts/' . intval($contact_id));
375                 return;  //NOTREACHED
376
377         }
378
379         return;
380 }