Merge remote-tracking branch 'upstream/develop' into 1601-api-statuses-lookup
This commit is contained in:
commit
542be50e26
152 changed files with 8519 additions and 7585 deletions
104
boot.php
104
boot.php
|
|
@ -6,11 +6,11 @@
|
|||
|
||||
/**
|
||||
* Friendica
|
||||
*
|
||||
*
|
||||
* Friendica is a communications platform for integrated social communications
|
||||
* utilising decentralised communications and linkage to several indie social
|
||||
* projects - as well as popular mainstream providers.
|
||||
*
|
||||
*
|
||||
* Our mission is to free our friends and families from the clutches of
|
||||
* data-harvesting corporations, and pave the way to a future where social
|
||||
* communications are free and open and flow between alternate providers as
|
||||
|
|
@ -18,7 +18,7 @@
|
|||
*/
|
||||
|
||||
require_once('include/autoloader.php');
|
||||
|
||||
|
||||
require_once('include/config.php');
|
||||
require_once('include/network.php');
|
||||
require_once('include/plugin.php');
|
||||
|
|
@ -30,7 +30,7 @@ require_once('include/cache.php');
|
|||
require_once('library/Mobile_Detect/Mobile_Detect.php');
|
||||
require_once('include/features.php');
|
||||
require_once('include/identity.php');
|
||||
|
||||
require_once('include/pidfile.php');
|
||||
require_once('update.php');
|
||||
require_once('include/dbstructure.php');
|
||||
|
||||
|
|
@ -465,11 +465,12 @@ class App {
|
|||
public $plugins;
|
||||
public $apps = array();
|
||||
public $identities;
|
||||
public $is_mobile;
|
||||
public $is_tablet;
|
||||
public $is_mobile = false;
|
||||
public $is_tablet = false;
|
||||
public $is_friendica_app;
|
||||
public $performance = array();
|
||||
public $callstack = array();
|
||||
public $theme_info = array();
|
||||
|
||||
public $nav_sel;
|
||||
|
||||
|
|
@ -855,11 +856,11 @@ class App {
|
|||
|
||||
$shortcut_icon = get_config("system", "shortcut_icon");
|
||||
if ($shortcut_icon == "")
|
||||
$shortcut_icon = $this->get_baseurl()."/images/friendica-32.png";
|
||||
$shortcut_icon = "images/friendica-32.png";
|
||||
|
||||
$touch_icon = get_config("system", "touch_icon");
|
||||
if ($touch_icon == "")
|
||||
$touch_icon = $this->get_baseurl()."/images/friendica-128.png";
|
||||
$touch_icon = "images/friendica-128.png";
|
||||
|
||||
$tpl = get_markup_template('head.tpl');
|
||||
$this->page['htmlhead'] = replace_macros($tpl,array(
|
||||
|
|
@ -938,6 +939,25 @@ class App {
|
|||
}
|
||||
|
||||
|
||||
/**
|
||||
* @brief Removes the baseurl from an url. This avoids some mixed content problems.
|
||||
*
|
||||
* @param string $url
|
||||
*
|
||||
* @return string The cleaned url
|
||||
*/
|
||||
function remove_baseurl($url){
|
||||
|
||||
// Is the function called statically?
|
||||
if (!is_object($this))
|
||||
return(self::$a->remove_baseurl($url));
|
||||
|
||||
$url = normalise_link($url);
|
||||
$base = normalise_link($this->get_baseurl());
|
||||
$url = str_replace($base."/", "", $url);
|
||||
return $url;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Register template engine class
|
||||
*
|
||||
|
|
@ -1027,11 +1047,21 @@ class App {
|
|||
function save_timestamp($stamp, $value) {
|
||||
$duration = (float)(microtime(true)-$stamp);
|
||||
|
||||
if (!isset($this->performance[$value])) {
|
||||
// Prevent ugly E_NOTICE
|
||||
$this->performance[$value] = 0;
|
||||
}
|
||||
|
||||
$this->performance[$value] += (float)$duration;
|
||||
$this->performance["marktime"] += (float)$duration;
|
||||
|
||||
$callstack = $this->callstack();
|
||||
|
||||
if (!isset($this->callstack[$value][$callstack])) {
|
||||
// Prevent ugly E_NOTICE
|
||||
$this->callstack[$value][$callstack] = 0;
|
||||
}
|
||||
|
||||
$this->callstack[$value][$callstack] += (float)$duration;
|
||||
|
||||
}
|
||||
|
|
@ -1068,6 +1098,55 @@ class App {
|
|||
return($this->is_friendica_app);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Checks if the maximum load is reached
|
||||
*
|
||||
* @return bool Is the load reached?
|
||||
*/
|
||||
function maxload_reached() {
|
||||
|
||||
$maxsysload = intval(get_config('system', 'maxloadavg'));
|
||||
if ($maxsysload < 1)
|
||||
$maxsysload = 50;
|
||||
|
||||
$load = current_load();
|
||||
if ($load) {
|
||||
if (intval($load) > $maxsysload) {
|
||||
logger('system: load '.$load.' too high.');
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Checks if the process is already running
|
||||
*
|
||||
* @param string $taskname The name of the task that will be used for the name of the lockfile
|
||||
* @param string $task The path and name of the php script
|
||||
* @param int $timeout The timeout after which a task should be killed
|
||||
*
|
||||
* @return bool Is the process running?
|
||||
*/
|
||||
function is_already_running($taskname, $task = "", $timeout = 540) {
|
||||
|
||||
$lockpath = get_lockpath();
|
||||
if ($lockpath != '') {
|
||||
$pidfile = new pidfile($lockpath, $taskname);
|
||||
if ($pidfile->is_already_running()) {
|
||||
logger("Already running");
|
||||
if ($pidfile->running_time() > $timeout) {
|
||||
$pidfile->kill();
|
||||
logger("killed stale process");
|
||||
// Calling a new instance
|
||||
if ($task != "")
|
||||
proc_run('php', $task);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -1419,7 +1498,7 @@ function login($register = false, $hiddens=false) {
|
|||
|
||||
$noid = get_config('system','no_openid');
|
||||
|
||||
$dest_url = $a->get_baseurl(true) . '/' . $a->query_string;
|
||||
$dest_url = $a->query_string;
|
||||
|
||||
if(local_user()) {
|
||||
$tpl = get_markup_template("logout.tpl");
|
||||
|
|
@ -1479,6 +1558,9 @@ function killme() {
|
|||
* @brief Redirect to another URL and terminate this process.
|
||||
*/
|
||||
function goaway($s) {
|
||||
if (!strstr(normalise_link($s), "http://"))
|
||||
$s = App::get_baseurl()."/".$s;
|
||||
|
||||
header("Location: $s");
|
||||
killme();
|
||||
}
|
||||
|
|
@ -1738,9 +1820,9 @@ function current_theme_url() {
|
|||
|
||||
$opts = (($a->profile_uid) ? '?f=&puid=' . $a->profile_uid : '');
|
||||
if (file_exists('view/theme/' . $t . '/style.php'))
|
||||
return($a->get_baseurl() . '/view/theme/' . $t . '/style.pcss' . $opts);
|
||||
return('view/theme/'.$t.'/style.pcss'.$opts);
|
||||
|
||||
return($a->get_baseurl() . '/view/theme/' . $t . '/style.css');
|
||||
return('view/theme/'.$t.'/style.css');
|
||||
}
|
||||
|
||||
function feed_birthday($uid,$tz) {
|
||||
|
|
|
|||
15
database.sql
15
database.sql
|
|
@ -201,17 +201,6 @@ CREATE TABLE IF NOT EXISTS `deliverq` (
|
|||
PRIMARY KEY(`id`)
|
||||
) DEFAULT CHARSET=utf8;
|
||||
|
||||
--
|
||||
-- TABLE dsprphotoq
|
||||
--
|
||||
CREATE TABLE IF NOT EXISTS `dsprphotoq` (
|
||||
`id` int(10) unsigned NOT NULL auto_increment,
|
||||
`uid` int(11) NOT NULL DEFAULT 0,
|
||||
`msg` mediumtext NOT NULL,
|
||||
`attempt` tinyint(4) NOT NULL DEFAULT 0,
|
||||
PRIMARY KEY(`id`)
|
||||
) DEFAULT CHARSET=utf8;
|
||||
|
||||
--
|
||||
-- TABLE event
|
||||
--
|
||||
|
|
@ -912,13 +901,11 @@ CREATE TABLE IF NOT EXISTS `session` (
|
|||
CREATE TABLE IF NOT EXISTS `sign` (
|
||||
`id` int(10) unsigned NOT NULL auto_increment,
|
||||
`iid` int(10) unsigned NOT NULL DEFAULT 0,
|
||||
`retract_iid` int(10) unsigned NOT NULL DEFAULT 0,
|
||||
`signed_text` mediumtext NOT NULL,
|
||||
`signature` text NOT NULL,
|
||||
`signer` varchar(255) NOT NULL DEFAULT '',
|
||||
PRIMARY KEY(`id`),
|
||||
INDEX `iid` (`iid`),
|
||||
INDEX `retract_iid` (`retract_iid`)
|
||||
INDEX `iid` (`iid`)
|
||||
) DEFAULT CHARSET=utf8;
|
||||
|
||||
--
|
||||
|
|
|
|||
|
|
@ -37,10 +37,7 @@ General
|
|||
* o: Profile
|
||||
* t: Contacts
|
||||
* d: Common friends
|
||||
* b: Toggle Blocked status
|
||||
* i: Toggle Ignored status
|
||||
* v: Toggle Archive status
|
||||
* r: Repair
|
||||
* r: Advanced
|
||||
|
||||
/message
|
||||
--------
|
||||
|
|
|
|||
|
|
@ -143,6 +143,56 @@ Map
|
|||
You can embed maps from coordinates or addresses.
|
||||
This require "openstreetmap" addon version 1.3 or newer.
|
||||
|
||||
-----------------------------------------------------------
|
||||
|
||||
Abstract for longer posts
|
||||
-------------------------
|
||||
|
||||
If you want to spread your post to several third party networks you can have the problem that these networks have (for example) a length limitation.
|
||||
(Like on Twitter)
|
||||
|
||||
Friendica is using a semi intelligent mechanism to generate a fitting abstract.
|
||||
But it can be interesting to define an own abstract that will only be displayed on the external network.
|
||||
This is done with the [abstract]-element.
|
||||
Example:
|
||||
|
||||
<pre>[abstract]Totally interesting! A must-see! Please click the link![/abstract]
|
||||
I want to tell you a really boring story that you really never wanted
|
||||
to hear.</pre>
|
||||
|
||||
Twitter would display the text "Totally interesting! A must-see! Please click the link!".
|
||||
On Friendica you would only see the text after "I want to tell you a really ..."
|
||||
|
||||
It is even possible to define abstracts for separate networks:
|
||||
|
||||
<pre>
|
||||
[abstract]Hi friends Here are my newest pictures![abstract]
|
||||
[abstract=twit]Hi my dear Twitter followers. Do you want to see my new
|
||||
pictures?[abstract]
|
||||
[abstract=apdn]Helly my dear followers on ADN. I made sone new pictures
|
||||
that I wanted to share with you.[abstract]
|
||||
Today I was in the woods and took some real cool pictures ...
|
||||
</pre>
|
||||
|
||||
For Twitter and App.net the system will use the defined abstracts.
|
||||
For other networks (e.g. when you are using the "statusnet" connector that is used to post to GNU Social) the general abstract element will be used.
|
||||
|
||||
If you use (for example) the "buffer" connector to post to Facebook or Google+ you can use this element to define an abstract for a longer blogpost that you don't want to post completely to these networks.
|
||||
|
||||
Networks like Facebook or Google+ aren't length limited.
|
||||
For this reason the [abstract] element isn't used.
|
||||
Instead you have to name the explicit network:
|
||||
|
||||
<pre>
|
||||
[abstract]These days I had a strange encounter ...[abstract]
|
||||
[abstract=goog]Helly my dear Google+ followers. You have to read my
|
||||
newest blog post![abstract]
|
||||
[abstract=face]Hello my Facebook friends. These days happened something
|
||||
really cool.[abstract]
|
||||
While taking pictures in the woods I had a really strange encounter ... </pre>
|
||||
|
||||
The [abstract] element isn't working with the native OStatus connection or with connectors where we post the HTML.
|
||||
(Like Tumblr, Wordpress or Pump.io)
|
||||
|
||||
Special
|
||||
-------
|
||||
|
|
@ -150,5 +200,3 @@ Special
|
|||
If you need to put literal bbcode in a message, [noparse], [nobb] or [pre] are used to escape bbcode:
|
||||
|
||||
<pre>[noparse][b]bold[/b][/noparse]</pre> : [b]bold[/b]
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -6,6 +6,8 @@ Bugs and Issues
|
|||
If your server has a support page, you should report any bugs/issues you encounter there first.
|
||||
Reporting to your support page before reporting to the developers makes their job easier, as they don't have to deal with bug reports that might not have anything to do with them.
|
||||
This helps us get new features faster.
|
||||
You can also contact the [friendica support forum](https://helpers.pyxis.uberspace.de/profile/helpers) and report your problem there.
|
||||
Maybe someone from another node encountered the problem as well and can help you.
|
||||
|
||||
If you're a technical user, or your site doesn't have a support page, you'll need to use the [Bug Tracker](http://bugs.friendica.com/).
|
||||
Please perform a search to see if there's already an open bug that matches yours before submitting anything.
|
||||
|
|
|
|||
|
|
@ -57,13 +57,15 @@ All that the pages need to have is a discoverable feed using either the RSS or A
|
|||
Twitter
|
||||
---
|
||||
|
||||
To follow a Twitter member, put the URL of the Twitter member's main page into the Connect box on your [Contacts](contacts) page.
|
||||
To follow a Twitter member, the Twitter-Connector (Addon) needs to be configured on your node.
|
||||
If this is the case put the URL of the Twitter member's main page into the Connect box on your [Contacts](contacts) page.
|
||||
To reply, you must have the Twitter connector installed, and reply using your own status editor.
|
||||
Begin the message with @twitterperson replacing with the Twitter username.
|
||||
|
||||
Email
|
||||
---
|
||||
|
||||
If the php module for IMAP support is available on your server, Friendica can connect to email contacts as well.
|
||||
Configure the email connector from your [Settings](settings) page.
|
||||
Once this has been done, you may enter an email address to connect with using the Connect box on your [Contacts](contacts) page.
|
||||
They must be the sender of a message which is currently in your INBOX for the connection to succeed.
|
||||
|
|
|
|||
|
|
@ -83,11 +83,11 @@ Ask us to find out whom to talk to about their experiences.
|
|||
Do not worry about cross-posting.
|
||||
|
||||
###Client software
|
||||
There are free software clients that do somehow work with Friendica but most of them need love and maintenance.
|
||||
Also, they were mostly made for other platforms using the GNU Social API.
|
||||
This means they lack the features that are really specific to Friendica.
|
||||
Popular clients you might want to have a look at are:
|
||||
As Friendica is using a [Twitter/GNU Social compatible API](help/api) any of the clients for those platforms should work with Friendica as well.
|
||||
Furthermore there are several client projects, especially for use with Friendica.
|
||||
If you are interested in improving those clients, please contact the developers of the clients directly.
|
||||
|
||||
* [Hotot (Linux)](http://hotot.org/) - abandoned
|
||||
* [Friendica for Android](https://github.com/max-weller/friendica-for-android) - abandoned
|
||||
* You can find more working client software in [Wikipedia](https://en.wikipedia.org/wiki/Friendica).
|
||||
* Android / CynogenMod: **Friendica for Android** [src](https://github.com/max-weller/friendica-for-android), [homepage](http://friendica.android.max-weller.de/) - abandoned
|
||||
* iOS: *currently no client*
|
||||
* SailfishOS: **Friendiy** [src](https://kirgroup.com/projects/fabrixxm/harbour-friendly) - developed by [Fabio](https://kirgroup.com/profile/fabrixxm/?tab=profile)
|
||||
* Windows: **Friendica Mobile** for Windows versions [before 8.1](http://windowsphone.com/s?appid=e3257730-c9cf-4935-9620-5261e3505c67) and [Windows 10](https://www.microsoft.com/store/apps/9nblggh0fhmn) - developed by [Gerhard Seeber](http://mozartweg.dyndns.org/friendica/profile/gerhard/?tab=profile)
|
||||
|
|
|
|||
|
|
@ -11,8 +11,6 @@ Hot Keys
|
|||
Friendica traps the following keyboard events:
|
||||
|
||||
* [Pause] - Pauses "Ajax" update activity. This is the process that provides updates without reloading the page. You may wish to pause it to reduce network usage and/or as a debugging aid for javascript developers. A pause indicator will appear at the lower right hand corner of the page. Hit the [pause] key once again to resume.
|
||||
* [F8] - Displays a language selector
|
||||
|
||||
|
||||
Birthday Notifications
|
||||
---
|
||||
|
|
|
|||
14
doc/api.md
14
doc/api.md
|
|
@ -1,6 +1,6 @@
|
|||
Friendica API
|
||||
===
|
||||
The Friendica API aims to be compatible to the [GNU Social API](http://skilledtests.com/wiki/Twitter-compatible_API) and the [Twitter API](https://dev.twitter.com/rest/public).
|
||||
The Friendica API aims to be compatible to the [GNU Social API](http://wiki.gnusocial.de/gnusocial:api) and the [Twitter API](https://dev.twitter.com/rest/public).
|
||||
|
||||
Please refer to the linked documentation for further information.
|
||||
|
||||
|
|
@ -388,6 +388,18 @@ Friendica doesn't allow showing friends of other users.
|
|||
---
|
||||
### statusnet/config (*)
|
||||
|
||||
---
|
||||
### statusnet/conversation (*; AUTH)
|
||||
It shows all direct answers (excluding the original post) to a given id.
|
||||
|
||||
#### Parameter
|
||||
* id: id of the post
|
||||
* count: Items per page (default: 20)
|
||||
* page: page number
|
||||
* since_id: minimal id
|
||||
* max_id: maximum id
|
||||
* include_entities: "true" shows entities for pictures and links (Default: false)
|
||||
|
||||
---
|
||||
### statusnet/version (*)
|
||||
|
||||
|
|
|
|||
|
|
@ -15,7 +15,6 @@ Database Tables
|
|||
| [contact](help/database/db_contact) | contact table |
|
||||
| [conv](help/database/db_conv) | private messages |
|
||||
| [deliverq](help/database/db_deliverq) | |
|
||||
| [dsprphotoq](help/database/db_dsprphotoq) | |
|
||||
| [event](help/database/db_event) | Events |
|
||||
| [fcontact](help/database/db_fcontact) | friend suggestion stuff |
|
||||
| [ffinder](help/database/db_ffinder) | friend suggestion stuff |
|
||||
|
|
|
|||
|
|
@ -1,11 +0,0 @@
|
|||
Table dsprphotoq
|
||||
================
|
||||
|
||||
| Field | Description | Type | Null | Key | Default | Extra |
|
||||
|---------|------------------|------------------|------|-----|---------|----------------|
|
||||
| id | sequential ID | int(10) unsigned | NO | PRI | NULL | auto_increment |
|
||||
| uid | | int(11) | NO | | 0 | |
|
||||
| msg | | mediumtext | NO | | NULL | |
|
||||
| attempt | | tinyint(4) | NO | | 0 | |
|
||||
|
||||
Return to [database documentation](help/database)
|
||||
|
|
@ -5,7 +5,6 @@ Table sign
|
|||
| ------------ | ------------- | ---------------- | ---- | --- | ------- | --------------- |
|
||||
| id | sequential ID | int(10) unsigned | NO | PRI | NULL | auto_increment |
|
||||
| iid | item.id | int(10) unsigned | NO | MUL | 0 | |
|
||||
| retract_iid | | int(10) unsigned | NO | MUL | 0 | |
|
||||
| signed_text | | mediumtext | NO | | NULL | |
|
||||
| signature | | text | NO | | NULL | |
|
||||
| signer | | varchar(255) | NO | | | |
|
||||
|
|
|
|||
|
|
@ -131,8 +131,7 @@ Außerdem kann *url* die genaue url zu einer ogg Datei sein, die dann per H
|
|||
|
||||
<pre>[url]*url*[/url]</pre>
|
||||
|
||||
Wenn *url* entweder oembed oder opengraph unterstützt wird das eingebettete
|
||||
Objekt (z.B. ein Dokument von scribd) eingebunden.
|
||||
Wenn *url* entweder oembed oder opengraph unterstützt wird das eingebettete Objekt (z.B. ein Dokument von scribd) eingebunden.
|
||||
Der Titel der Seite mit einem Link zur *url* wird ebenfalls angezeigt.
|
||||
|
||||
Um eine Karte in einen Beitrag einzubinden, muss das *openstreetmap* Addon aktiviert werden. Ist dies der Fall, kann mit
|
||||
|
|
@ -145,11 +144,54 @@ eine Karte von [OpenStreetmap](http://openstreetmap.org) eingebettet werden. Zur
|
|||
|
||||
oder eine Adresse in obiger Form verwendet werden.
|
||||
|
||||
Zusammenfassung für längere Beiträge
|
||||
------------------------------------
|
||||
|
||||
Wenn man seine Beiträge über mehrere Netzwerke verbreiten möchte, hat man häufig das Problem, dass diese Netzwerke z.B. eine Längenbeschränkung haben.
|
||||
(Z.B. Twitter).
|
||||
|
||||
Friendica benutzt zum Erzeugen eines Anreißtextes eine halbwegs intelligente Logik.
|
||||
Es kann aber dennoch von Interesse sein, eine eigene Zusammenfassung zu erstellen, die nur auf dem Fremdnetzwerk dargestellt wird.
|
||||
Dies geschieht mit dem [abstract]-Element.
|
||||
Beispiel:
|
||||
|
||||
<pre>[abstract]Total spannend! Unbedingt diesen Link anklicken![/abstract]
|
||||
Hier erzähle ich euch eine total langweilige Geschichte, die ihr noch
|
||||
nie hören wolltet.</pre>
|
||||
|
||||
Auf Twitter würde das "Total spannend! Unbedingt diesen Link anklicken!" stehen, auf Friendica würde nur der Text nach "Hier erzähle ..." erscheinen.
|
||||
|
||||
Es ist sogar möglich, für einzelne Netzwerke eigene Zusammenfassungen zu erstellen:
|
||||
|
||||
<pre>
|
||||
[abstract]Hallo Leute, hier meine neuesten Bilder![abstract]
|
||||
[abstract=twit]Hallo Twitter-User, hier meine neuesten Bilder![abstract]
|
||||
[abstract=apdn]Hallo App.net-User, hier meine neuesten Bilder![abstract]
|
||||
Ich war heute wieder im Wald unterwegs und habe tolle Bilder geschossen ...
|
||||
</pre>
|
||||
|
||||
Für Twitter und App.net nimmt das System die entsprechenden Texte.
|
||||
Bei anderen Netzwerken, bei denen der Inhalt gekürzt wird (z.B. beim "statusnet"-Connector, der für das Posten nach GNU Social verwendet wird) wird dann die Zusammenfassung unter [abstract] verwendet.
|
||||
|
||||
Wenn man z.B. den "buffer"-Connector verwendet, um nach Facebook oder Google+ zu posten, kann man dieses Element ebenfalls verwenden, wenn man z.B. einen längeren Blogbeitrag erstellt hat, aber ihn nicht komplett in diese Netzwerke posten möchte.
|
||||
|
||||
Netzwerke wie Facebook oder Google+ sind nicht in der Postinglänge beschränkt.
|
||||
Aus diesem Grund greift nicht die [abstract]-Zusammenfassung. Stattdessen muss man das Netzwerk explizit angeben:
|
||||
|
||||
<pre>
|
||||
[abstract]Ich habe neulich wieder etwas erlebt, was ich euch mitteilen möchte.[abstract]
|
||||
[abstract=goog]Hallo meine Google+-Kreislinge. Ich habe neulich wieder
|
||||
etwas erlebt, was ich euch mitteilen möchte.[abstract]
|
||||
[abstract=face]Hallo Facebook-Freunde! Ich habe neulich wieder etwas
|
||||
erlebt, was ich euch mitteilen möchte.[abstract]
|
||||
Beim Bildermachen im Wald habe ich neulich eine interessante Person
|
||||
getroffen ... </pre>
|
||||
|
||||
Das [abstract]-Element greift nicht bei der nativen OStatus-Verbindung oder bei Connectoren, die den HTML-Text posten wie z.B. die Connectoren zu Tumblr, Wordpress oder Pump.io.
|
||||
|
||||
Spezielle Tags
|
||||
-------
|
||||
|
||||
Wenn Du über BBCode Tags in einer Nachricht schreiben möchtest, kannst Du [noparse], [nobb] oder [pre] verwenden um den BBCode Tags vor der Evaluierung zu schützen:
|
||||
|
||||
<pre>[noparse][b]fett[/b][/noparse]</pre> : [b]fett[/b]
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -14,9 +14,6 @@ Friendica erfasst die folgenden Tastaturbefehle:
|
|||
|
||||
* [Pause] - Pausiert die Update-Aktivität via "Ajax". Das ist ein Prozess, der Updates durchführt, ohne die Seite neu zu laden. Du kannst diesen Prozess pausieren, um deine Netzwerkauslastung zu reduzieren und/oder um es in der Javascript-Programmierung zum Debuggen zu nutzen. Ein Pausenzeichen erscheint unten links im Fenster. Klicke die [Pause]-Taste ein weiteres Mal, um die Pause zu beenden.
|
||||
|
||||
* [F8] - Zeigt eine Sprachauswahl an
|
||||
|
||||
|
||||
**Geburtstagsbenachrichtigung**
|
||||
|
||||
Geburtstage erscheinen auf deiner Startseite für alle Freunde, die in den nächsten 6 Tagen Geburtstag haben.
|
||||
|
|
|
|||
|
|
@ -64,9 +64,6 @@ line to your .htconfig.php:
|
|||
* throttle_limit_week - Maximum number of posts that a user can send per week with the API.
|
||||
* throttle_limit_month - Maximum number of posts that a user can send per month with the API.
|
||||
* wall-to-wall_share (Boolean) - Displays forwarded posts like "wall-to-wall" posts.
|
||||
* worker (Boolean) - (Experimental) Use the worker system instead of calling several background processes. Reduces the overall load and speeds up item delivery.
|
||||
* worker_dont_fork (Boolean) - if enabled, the workers are only called from the poller process. Useful on systems that permit the use of "proc_open".
|
||||
* worker_queues - Number of parallel workers. Default value is 10 queues.
|
||||
* xrd_timeout - Timeout for fetching the XRD links. Default value is 20 seconds.
|
||||
|
||||
## service_class ##
|
||||
|
|
|
|||
|
|
@ -129,7 +129,7 @@ function terminate_friendship($user,$self,$contact) {
|
|||
}
|
||||
elseif($contact['network'] === NETWORK_DIASPORA) {
|
||||
require_once('include/diaspora.php');
|
||||
diaspora_unshare($user,$contact);
|
||||
diaspora::send_unshare($user,$contact);
|
||||
}
|
||||
elseif($contact['network'] === NETWORK_DFRN) {
|
||||
require_once('include/dfrn.php');
|
||||
|
|
@ -555,60 +555,6 @@ function posts_from_gcontact($a, $gcontact_id) {
|
|||
return $o;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief set the gcontact-id in all item entries
|
||||
*
|
||||
* This job has to be started multiple times until all entries are set.
|
||||
* It isn't started in the update function since it would consume too much time and can be done in the background.
|
||||
*/
|
||||
function item_set_gcontact() {
|
||||
define ('POST_UPDATE_VERSION', 1192);
|
||||
|
||||
// Was the script completed?
|
||||
if (get_config("system", "post_update_version") >= POST_UPDATE_VERSION)
|
||||
return;
|
||||
|
||||
// Check if the first step is done (Setting "gcontact-id" in the item table)
|
||||
$r = q("SELECT `author-link`, `author-name`, `author-avatar`, `uid`, `network` FROM `item` WHERE `gcontact-id` = 0 LIMIT 1000");
|
||||
if (!$r) {
|
||||
// Are there unfinished entries in the thread table?
|
||||
$r = q("SELECT COUNT(*) AS `total` FROM `thread`
|
||||
INNER JOIN `item` ON `item`.`id` =`thread`.`iid`
|
||||
WHERE `thread`.`gcontact-id` = 0 AND
|
||||
(`thread`.`uid` IN (SELECT `uid` from `user`) OR `thread`.`uid` = 0)");
|
||||
|
||||
if ($r AND ($r[0]["total"] == 0)) {
|
||||
set_config("system", "post_update_version", POST_UPDATE_VERSION);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Update the thread table from the item table
|
||||
q("UPDATE `thread` INNER JOIN `item` ON `item`.`id`=`thread`.`iid`
|
||||
SET `thread`.`gcontact-id` = `item`.`gcontact-id`
|
||||
WHERE `thread`.`gcontact-id` = 0 AND
|
||||
(`thread`.`uid` IN (SELECT `uid` from `user`) OR `thread`.`uid` = 0)");
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
$item_arr = array();
|
||||
foreach ($r AS $item) {
|
||||
$index = $item["author-link"]."-".$item["uid"];
|
||||
$item_arr[$index] = array("author-link" => $item["author-link"],
|
||||
"uid" => $item["uid"],
|
||||
"network" => $item["network"]);
|
||||
}
|
||||
|
||||
// Set the "gcontact-id" in the item table and add a new gcontact entry if needed
|
||||
foreach($item_arr AS $item) {
|
||||
$gcontact_id = get_gcontact_id(array("url" => $item['author-link'], "network" => $item['network'],
|
||||
"photo" => $item['author-avatar'], "name" => $item['author-name']));
|
||||
q("UPDATE `item` SET `gcontact-id` = %d WHERE `uid` = %d AND `author-link` = '%s' AND `gcontact-id` = 0",
|
||||
intval($gcontact_id), intval($item["uid"]), dbesc($item["author-link"]));
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Returns posts from a given contact
|
||||
*
|
||||
|
|
|
|||
|
|
@ -95,12 +95,12 @@ class ForumManager {
|
|||
$selected = (($cid == $contact['id']) ? ' forum-selected' : '');
|
||||
|
||||
$entry = array(
|
||||
'url' => z_root() . '/network?f=&cid=' . $contact['id'],
|
||||
'external_url' => z_root() . '/redir/' . $contact['id'],
|
||||
'url' => 'network?f=&cid=' . $contact['id'],
|
||||
'external_url' => 'redir/' . $contact['id'],
|
||||
'name' => $contact['name'],
|
||||
'cid' => $contact['id'],
|
||||
'selected' => $selected,
|
||||
'micro' => proxy_url($contact['micro'], false, PROXY_SIZE_MICRO),
|
||||
'micro' => App::remove_baseurl(proxy_url($contact['micro'], false, PROXY_SIZE_MICRO)),
|
||||
'id' => ++$id,
|
||||
);
|
||||
$entries[] = $entry;
|
||||
|
|
@ -187,4 +187,4 @@ class ForumManager {
|
|||
return $r;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -23,13 +23,15 @@ function scrape_dfrn($url, $dont_probe = false) {
|
|||
if (is_array($noscrapedata)) {
|
||||
if ($noscrapedata["nick"] != "")
|
||||
return($noscrapedata);
|
||||
else
|
||||
unset($noscrapedata["nick"]);
|
||||
} else
|
||||
$noscrapedata = array();
|
||||
}
|
||||
|
||||
$s = fetch_url($url);
|
||||
|
||||
if(! $s)
|
||||
if (!$s)
|
||||
return $ret;
|
||||
|
||||
if (!$dont_probe) {
|
||||
|
|
@ -356,7 +358,7 @@ function probe_url($url, $mode = PROBE_NORMAL, $level = 1) {
|
|||
|
||||
$result = array();
|
||||
|
||||
if(! $url)
|
||||
if (!$url)
|
||||
return $result;
|
||||
|
||||
$result = Cache::get("probe_url:".$mode.":".$url);
|
||||
|
|
@ -365,6 +367,7 @@ function probe_url($url, $mode = PROBE_NORMAL, $level = 1) {
|
|||
return $result;
|
||||
}
|
||||
|
||||
$original_url = $url;
|
||||
$network = null;
|
||||
$diaspora = false;
|
||||
$diaspora_base = '';
|
||||
|
|
@ -393,7 +396,12 @@ function probe_url($url, $mode = PROBE_NORMAL, $level = 1) {
|
|||
else
|
||||
$links = lrdd($url);
|
||||
|
||||
if(count($links)) {
|
||||
if ((count($links) == 0) AND strstr($url, "/index.php")) {
|
||||
$url = str_replace("/index.php", "", $url);
|
||||
$links = lrdd($url);
|
||||
}
|
||||
|
||||
if (count($links)) {
|
||||
$has_lrdd = true;
|
||||
|
||||
logger('probe_url: found lrdd links: ' . print_r($links,true), LOGGER_DATA);
|
||||
|
|
@ -440,12 +448,21 @@ function probe_url($url, $mode = PROBE_NORMAL, $level = 1) {
|
|||
// aliases, let's hope we're lucky and get one that matches the feed author-uri because
|
||||
// otherwise we're screwed.
|
||||
|
||||
$backup_alias = "";
|
||||
|
||||
foreach($links as $link) {
|
||||
if($link['@attributes']['rel'] === 'alias') {
|
||||
if(strpos($link['@attributes']['href'],'@') === false) {
|
||||
if(isset($profile)) {
|
||||
if($link['@attributes']['href'] !== $profile)
|
||||
$alias = unamp($link['@attributes']['href']);
|
||||
$alias_url = $link['@attributes']['href'];
|
||||
|
||||
if(($alias_url !== $profile) AND ($backup_alias == "") AND
|
||||
($alias_url !== str_replace("/index.php", "", $profile)))
|
||||
$backup_alias = $alias_url;
|
||||
|
||||
if(($alias_url !== $profile) AND !strstr($alias_url, "index.php") AND
|
||||
($alias_url !== str_replace("/index.php", "", $profile)))
|
||||
$alias = $alias_url;
|
||||
}
|
||||
else
|
||||
$profile = unamp($link['@attributes']['href']);
|
||||
|
|
@ -453,6 +470,9 @@ function probe_url($url, $mode = PROBE_NORMAL, $level = 1) {
|
|||
}
|
||||
}
|
||||
|
||||
if ($alias == "")
|
||||
$alias = $backup_alias;
|
||||
|
||||
// If the profile is different from the url then the url is abviously an alias
|
||||
if (($alias == "") AND ($profile != "") AND !$at_addr AND (normalise_link($profile) != normalise_link($url)))
|
||||
$alias = $url;
|
||||
|
|
@ -685,7 +705,14 @@ function probe_url($url, $mode = PROBE_NORMAL, $level = 1) {
|
|||
if (($vcard["nick"] == "") AND ($data["header"]["author-nick"] != ""))
|
||||
$vcard["nick"] = $data["header"]["author-nick"];
|
||||
|
||||
if(!$profile AND ($data["header"]["author-link"] != "") AND !in_array($network, array("", NETWORK_FEED)))
|
||||
if ($network == NETWORK_OSTATUS) {
|
||||
if ($data["header"]["author-id"] != "")
|
||||
$alias = $data["header"]["author-id"];
|
||||
|
||||
if ($data["header"]["author-link"] != "")
|
||||
$profile = $data["header"]["author-link"];
|
||||
|
||||
} elseif(!$profile AND ($data["header"]["author-link"] != "") AND !in_array($network, array("", NETWORK_FEED)))
|
||||
$profile = $data["header"]["author-link"];
|
||||
}
|
||||
}
|
||||
|
|
@ -769,6 +796,9 @@ function probe_url($url, $mode = PROBE_NORMAL, $level = 1) {
|
|||
if (($baseurl == "") AND ($poll != ""))
|
||||
$baseurl = matching_url(normalise_link($profile), normalise_link($poll));
|
||||
|
||||
if (substr($baseurl, -10) == "/index.php")
|
||||
$baseurl = str_replace("/index.php", "", $baseurl);
|
||||
|
||||
$baseurl = rtrim($baseurl, "/");
|
||||
|
||||
if(strpos($url,'@') AND ($addr == "") AND ($network == NETWORK_DFRN))
|
||||
|
|
@ -816,8 +846,28 @@ function probe_url($url, $mode = PROBE_NORMAL, $level = 1) {
|
|||
}
|
||||
|
||||
// Only store into the cache if the value seems to be valid
|
||||
if ($result['network'] != NETWORK_PHANTOM)
|
||||
Cache::set("probe_url:".$mode.":".$url,serialize($result), CACHE_DAY);
|
||||
if ($result['network'] != NETWORK_PHANTOM) {
|
||||
Cache::set("probe_url:".$mode.":".$original_url,serialize($result), CACHE_DAY);
|
||||
|
||||
/// @todo temporary fix - we need a real contact update function that updates only changing fields
|
||||
/// The biggest problem is the avatar picture that could have a reduced image size.
|
||||
/// It should only be updated if the existing picture isn't existing anymore.
|
||||
if (($result['network'] != NETWORK_FEED) AND ($mode == PROBE_NORMAL) AND
|
||||
$result["name"] AND $result["nick"] AND $result["url"] AND $result["addr"] AND $result["poll"])
|
||||
q("UPDATE `contact` SET `name` = '%s', `nick` = '%s', `url` = '%s', `addr` = '%s',
|
||||
`notify` = '%s', `poll` = '%s', `alias` = '%s', `success_update` = '%s'
|
||||
WHERE `nurl` = '%s' AND NOT `self` AND `uid` = 0",
|
||||
dbesc($result["name"]),
|
||||
dbesc($result["nick"]),
|
||||
dbesc($result["url"]),
|
||||
dbesc($result["addr"]),
|
||||
dbesc($result["notify"]),
|
||||
dbesc($result["poll"]),
|
||||
dbesc($result["alias"]),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc(normalise_link($result['url']))
|
||||
);
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -161,10 +161,7 @@
|
|||
if (!isset($_SERVER['PHP_AUTH_USER'])) {
|
||||
logger('API_login: ' . print_r($_SERVER,true), LOGGER_DEBUG);
|
||||
header('WWW-Authenticate: Basic realm="Friendica"');
|
||||
header('HTTP/1.0 401 Unauthorized');
|
||||
die((api_error($a, 'json', "This api requires login")));
|
||||
|
||||
//die('This api requires login');
|
||||
throw new UnauthorizedException("This API requires login");
|
||||
}
|
||||
|
||||
$user = $_SERVER['PHP_AUTH_USER'];
|
||||
|
|
@ -216,8 +213,9 @@
|
|||
if((! $record) || (! count($record))) {
|
||||
logger('API_login failure: ' . print_r($_SERVER,true), LOGGER_DEBUG);
|
||||
header('WWW-Authenticate: Basic realm="Friendica"');
|
||||
header('HTTP/1.0 401 Unauthorized');
|
||||
die('This api requires login');
|
||||
#header('HTTP/1.0 401 Unauthorized');
|
||||
#die('This api requires login');
|
||||
throw new UnauthorizedException("This API requires login");
|
||||
}
|
||||
|
||||
authenticate_success($record); $_SESSION["allow_api"] = true;
|
||||
|
|
@ -332,7 +330,8 @@
|
|||
*
|
||||
* @param Api $a
|
||||
* @param string $type Return type (xml, json, rss, as)
|
||||
* @param string $error Error message
|
||||
* @param HTTPException $error Error object
|
||||
* @return strin error message formatted as $type
|
||||
*/
|
||||
function api_error(&$a, $type, $e) {
|
||||
$error = ($e->getMessage()!==""?$e->getMessage():$e->httpdesc);
|
||||
|
|
@ -904,7 +903,8 @@
|
|||
|
||||
if ($posts_day > $throttle_day) {
|
||||
logger('Daily posting limit reached for user '.api_user(), LOGGER_DEBUG);
|
||||
die(api_error($a, $type, sprintf(t("Daily posting limit of %d posts reached. The post was rejected."), $throttle_day)));
|
||||
#die(api_error($a, $type, sprintf(t("Daily posting limit of %d posts reached. The post was rejected."), $throttle_day)));
|
||||
throw new TooManyRequestsException(sprintf(t("Daily posting limit of %d posts reached. The post was rejected."), $throttle_day));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -923,7 +923,9 @@
|
|||
|
||||
if ($posts_week > $throttle_week) {
|
||||
logger('Weekly posting limit reached for user '.api_user(), LOGGER_DEBUG);
|
||||
die(api_error($a, $type, sprintf(t("Weekly posting limit of %d posts reached. The post was rejected."), $throttle_week)));
|
||||
#die(api_error($a, $type, sprintf(t("Weekly posting limit of %d posts reached. The post was rejected."), $throttle_week)));
|
||||
throw new TooManyRequestsException(sprintf(t("Weekly posting limit of %d posts reached. The post was rejected."), $throttle_week));
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -942,7 +944,8 @@
|
|||
|
||||
if ($posts_month > $throttle_month) {
|
||||
logger('Monthly posting limit reached for user '.api_user(), LOGGER_DEBUG);
|
||||
die(api_error($a, $type, sprintf(t("Monthly posting limit of %d posts reached. The post was rejected."), $throttle_month)));
|
||||
#die(api_error($a, $type, sprintf(t("Monthly posting limit of %d posts reached. The post was rejected."), $throttle_month)));
|
||||
throw new TooManyRequestsException(sprintf(t("Monthly posting limit of %d posts reached. The post was rejected."), $throttle_month));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -1548,6 +1551,7 @@
|
|||
return api_apply_template("timeline", $type, $data);
|
||||
}
|
||||
api_register_func('api/conversation/show','api_conversation_show', true);
|
||||
api_register_func('api/statusnet/conversation','api_conversation_show', true);
|
||||
|
||||
|
||||
/**
|
||||
|
|
@ -1689,13 +1693,13 @@
|
|||
`contact`.`name`, `contact`.`photo`, `contact`.`url`, `contact`.`rel`,
|
||||
`contact`.`network`, `contact`.`thumb`, `contact`.`dfrn-id`, `contact`.`self`,
|
||||
`contact`.`id` AS `cid`, `contact`.`uid` AS `contact-uid`
|
||||
FROM `item`, `contact`
|
||||
FROM `item` FORCE INDEX (`uid_id`), `contact`
|
||||
WHERE `item`.`uid` = %d AND `verb` = '%s'
|
||||
AND NOT (`item`.`author-link` IN ('https://%s', 'http://%s'))
|
||||
AND `item`.`visible` = 1 and `item`.`moderated` = 0 AND `item`.`deleted` = 0
|
||||
AND `item`.`visible` AND NOT `item`.`moderated` AND NOT `item`.`deleted`
|
||||
AND `contact`.`id` = `item`.`contact-id`
|
||||
AND `contact`.`blocked` = 0 AND `contact`.`pending` = 0
|
||||
AND `item`.`parent` IN (SELECT `iid` from thread where uid = %d AND `mention` AND !`ignored`)
|
||||
AND NOT `contact`.`blocked` AND NOT `contact`.`pending`
|
||||
AND `item`.`parent` IN (SELECT `iid` FROM `thread` WHERE `uid` = %d AND `mention` AND !`ignored`)
|
||||
$sql_extra
|
||||
AND `item`.`id`>%d
|
||||
ORDER BY `item`.`id` DESC LIMIT %d ,%d ",
|
||||
|
|
@ -1810,7 +1814,7 @@
|
|||
$action_argv_id=2;
|
||||
if ($a->argv[1]=="1.1") $action_argv_id=3;
|
||||
|
||||
if ($a->argc<=$action_argv_id) die(api_error($a, $type, t("Invalid request.")));
|
||||
if ($a->argc<=$action_argv_id) throw new BadRequestException("Invalid request.");
|
||||
$action = str_replace(".".$type,"",$a->argv[$action_argv_id]);
|
||||
if ($a->argc==$action_argv_id+2) {
|
||||
$itemid = intval($a->argv[$action_argv_id+1]);
|
||||
|
|
|
|||
|
|
@ -311,6 +311,9 @@ function tryoembed($match){
|
|||
|
||||
$o = oembed_fetch_url($url);
|
||||
|
||||
if (!is_object($o))
|
||||
return $match[0];
|
||||
|
||||
if (isset($match[2]))
|
||||
$o->title = $match[2];
|
||||
|
||||
|
|
@ -858,6 +861,8 @@ function bbcode($Text,$preserve_nl = false, $tryoembed = true, $simplehtml = fal
|
|||
$Text = preg_replace_callback("/\[nobb\](.*?)\[\/nobb\]/ism", 'bb_spacefy',$Text);
|
||||
$Text = preg_replace_callback("/\[pre\](.*?)\[\/pre\]/ism", 'bb_spacefy',$Text);
|
||||
|
||||
// Remove the abstract element. It is a non visible element.
|
||||
$Text = remove_abstract($Text);
|
||||
|
||||
// Move all spaces out of the tags
|
||||
$Text = preg_replace("/\[(\w*)\](\s*)/ism", '$2[$1]', $Text);
|
||||
|
|
@ -1300,4 +1305,43 @@ function bbcode($Text,$preserve_nl = false, $tryoembed = true, $simplehtml = fal
|
|||
|
||||
return trim($Text);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Removes the "abstract" element from the text
|
||||
*
|
||||
* @param string $text The text with BBCode
|
||||
* @return string The same text - but without "abstract" element
|
||||
*/
|
||||
function remove_abstract($text) {
|
||||
$text = preg_replace("/[\s|\n]*\[abstract\].*?\[\/abstract\][\s|\n]*/ism", '', $text);
|
||||
$text = preg_replace("/[\s|\n]*\[abstract=.*?\].*?\[\/abstract][\s|\n]*/ism", '', $text);
|
||||
|
||||
return $text;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Returns the value of the "abstract" element
|
||||
*
|
||||
* @param string $text The text that maybe contains the element
|
||||
* @param string $addon The addon for which the abstract is meant for
|
||||
* @return string The abstract
|
||||
*/
|
||||
function fetch_abstract($text, $addon = "") {
|
||||
$abstract = "";
|
||||
$abstracts = array();
|
||||
$addon = strtolower($addon);
|
||||
|
||||
if (preg_match_all("/\[abstract=(.*?)\](.*?)\[\/abstract\]/ism",$text, $results, PREG_SET_ORDER))
|
||||
foreach ($results AS $result)
|
||||
$abstracts[strtolower($result[1])] = $result[2];
|
||||
|
||||
if (isset($abstracts[$addon]))
|
||||
$abstract = $abstracts[$addon];
|
||||
|
||||
if ($abstract == "")
|
||||
if (preg_match("/\[abstract\](.*?)\[\/abstract\]/ism",$text, $result))
|
||||
$abstract = $result[1];
|
||||
|
||||
return $abstract;
|
||||
}
|
||||
?>
|
||||
|
|
|
|||
|
|
@ -99,7 +99,7 @@ function network_to_name($s, $profile = "") {
|
|||
|
||||
$networkname = str_replace($search,$replace,$s);
|
||||
|
||||
if (($s == NETWORK_DIASPORA) AND ($profile != "") AND diaspora_is_redmatrix($profile)) {
|
||||
if (($s == NETWORK_DIASPORA) AND ($profile != "") AND diaspora::is_redmatrix($profile)) {
|
||||
$networkname = t("Hubzilla/Redmatrix");
|
||||
|
||||
$r = q("SELECT `gserver`.`platform` FROM `gcontact`
|
||||
|
|
|
|||
|
|
@ -614,7 +614,7 @@ function conversation(&$a, $items, $mode, $update, $preview = false) {
|
|||
if(($normalised != 'mailbox') && (x($a->contacts[$normalised])))
|
||||
$profile_avatar = $a->contacts[$normalised]['thumb'];
|
||||
else
|
||||
$profile_avatar = ((strlen($item['author-avatar'])) ? $a->get_cached_avatar_image($item['author-avatar']) : $item['thumb']);
|
||||
$profile_avatar = $a->remove_baseurl(((strlen($item['author-avatar'])) ? $item['author-avatar'] : $item['thumb']));
|
||||
|
||||
$locate = array('location' => $item['location'], 'coord' => $item['coord'], 'html' => '');
|
||||
call_hooks('render_location',$locate);
|
||||
|
|
@ -707,8 +707,8 @@ function conversation(&$a, $items, $mode, $update, $preview = false) {
|
|||
'like' => '',
|
||||
'dislike' => '',
|
||||
'comment' => '',
|
||||
//'conv' => (($preview) ? '' : array('href'=> $a->get_baseurl($ssl_state) . '/display/' . $nickname . '/' . $item['id'], 'title'=> t('View in context'))),
|
||||
'conv' => (($preview) ? '' : array('href'=> $a->get_baseurl($ssl_state) . '/display/'.$item['guid'], 'title'=> t('View in context'))),
|
||||
//'conv' => (($preview) ? '' : array('href'=> 'display/' . $nickname . '/' . $item['id'], 'title'=> t('View in context'))),
|
||||
'conv' => (($preview) ? '' : array('href'=> 'display/'.$item['guid'], 'title'=> t('View in context'))),
|
||||
'previewing' => $previewing,
|
||||
'wait' => t('Please wait'),
|
||||
'thread_level' => 1,
|
||||
|
|
@ -868,7 +868,7 @@ function item_photo_menu($item){
|
|||
$status_link = $profile_link . "?url=status";
|
||||
$photos_link = $profile_link . "?url=photos";
|
||||
$profile_link = $profile_link . "?url=profile";
|
||||
$pm_url = $a->get_baseurl($ssl_state) . '/message/new/' . $cid;
|
||||
$pm_url = 'message/new/' . $cid;
|
||||
$zurl = '';
|
||||
}
|
||||
else {
|
||||
|
|
@ -882,23 +882,23 @@ function item_photo_menu($item){
|
|||
$cid = $r[0]["id"];
|
||||
|
||||
if ($r[0]["network"] == NETWORK_DIASPORA)
|
||||
$pm_url = $a->get_baseurl($ssl_state) . '/message/new/' . $cid;
|
||||
$pm_url = 'message/new/' . $cid;
|
||||
|
||||
} else
|
||||
$cid = 0;
|
||||
}
|
||||
}
|
||||
if(($cid) && (! $item['self'])) {
|
||||
$poke_link = $a->get_baseurl($ssl_state) . '/poke/?f=&c=' . $cid;
|
||||
$contact_url = $a->get_baseurl($ssl_state) . '/contacts/' . $cid;
|
||||
$posts_link = $a->get_baseurl($ssl_state) . '/contacts/' . $cid . '/posts';
|
||||
$poke_link = 'poke/?f=&c=' . $cid;
|
||||
$contact_url = 'contacts/' . $cid;
|
||||
$posts_link = 'contacts/' . $cid . '/posts';
|
||||
|
||||
$clean_url = normalise_link($item['author-link']);
|
||||
|
||||
if((local_user()) && (local_user() == $item['uid'])) {
|
||||
if(isset($a->contacts) && x($a->contacts,$clean_url)) {
|
||||
if($a->contacts[$clean_url]['network'] === NETWORK_DIASPORA) {
|
||||
$pm_url = $a->get_baseurl($ssl_state) . '/message/new/' . $cid;
|
||||
$pm_url = 'message/new/' . $cid;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -921,7 +921,7 @@ function item_photo_menu($item){
|
|||
|
||||
if ((($cid == 0) OR ($a->contacts[$clean_url]['rel'] == CONTACT_IS_FOLLOWER)) AND
|
||||
in_array($item['network'], array(NETWORK_DFRN, NETWORK_OSTATUS, NETWORK_DIASPORA)))
|
||||
$menu[t("Connect/Follow")] = $a->get_baseurl($ssl_state)."/follow?url=".urlencode($item['author-link']);
|
||||
$menu[t("Connect/Follow")] = "follow?url=".urlencode($item['author-link']);
|
||||
} else
|
||||
$menu = array(t("View Profile") => $item['author-link']);
|
||||
|
||||
|
|
@ -980,7 +980,7 @@ function builtin_activity_puller($item, &$conv_responses) {
|
|||
if((activity_match($item['verb'], $verb)) && ($item['id'] != $item['parent'])) {
|
||||
$url = $item['author-link'];
|
||||
if((local_user()) && (local_user() == $item['uid']) && ($item['network'] === NETWORK_DFRN) && (! $item['self']) && (link_compare($item['author-link'],$item['url']))) {
|
||||
$url = z_root(true) . '/redir/' . $item['contact-id'];
|
||||
$url = 'redir/' . $item['contact-id'];
|
||||
$sparkle = ' class="sparkle" ';
|
||||
}
|
||||
else
|
||||
|
|
@ -1178,7 +1178,7 @@ function status_editor($a,$x, $notes_cid = 0, $popup=false) {
|
|||
|
||||
$o .= replace_macros($tpl,array(
|
||||
'$return_path' => $query_str,
|
||||
'$action' => $a->get_baseurl(true) . '/item',
|
||||
'$action' => 'item',
|
||||
'$share' => (x($x,'button') ? $x['button'] : t('Share')),
|
||||
'$upload' => t('Upload photo'),
|
||||
'$shortupload' => t('upload photo'),
|
||||
|
|
|
|||
|
|
@ -34,22 +34,18 @@ function cron_run(&$argv, &$argc){
|
|||
require_once('include/Contact.php');
|
||||
require_once('include/email.php');
|
||||
require_once('include/socgraph.php');
|
||||
require_once('include/pidfile.php');
|
||||
require_once('mod/nodeinfo.php');
|
||||
require_once('include/post_update.php');
|
||||
|
||||
load_config('config');
|
||||
load_config('system');
|
||||
|
||||
$maxsysload = intval(get_config('system','maxloadavg'));
|
||||
if($maxsysload < 1)
|
||||
$maxsysload = 50;
|
||||
|
||||
$load = current_load();
|
||||
if($load) {
|
||||
if(intval($load) > $maxsysload) {
|
||||
logger('system: load ' . $load . ' too high. cron deferred to next scheduled run.');
|
||||
// Don't check this stuff if the function is called by the poller
|
||||
if (App::callstack() != "poller_run") {
|
||||
if (App::maxload_reached())
|
||||
return;
|
||||
if (App::is_already_running('cron', 'include/cron.php', 540))
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
$last = get_config('system','last_cron');
|
||||
|
|
@ -66,23 +62,6 @@ function cron_run(&$argv, &$argc){
|
|||
}
|
||||
}
|
||||
|
||||
$lockpath = get_lockpath();
|
||||
if ($lockpath != '') {
|
||||
$pidfile = new pidfile($lockpath, 'cron');
|
||||
if($pidfile->is_already_running()) {
|
||||
logger("cron: Already running");
|
||||
if ($pidfile->running_time() > 9*60) {
|
||||
$pidfile->kill();
|
||||
logger("cron: killed stale process");
|
||||
// Calling a new instance
|
||||
proc_run('php','include/cron.php');
|
||||
}
|
||||
exit;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
$a->set_baseurl(get_config('system','url'));
|
||||
|
||||
load_hooks();
|
||||
|
|
@ -93,10 +72,6 @@ function cron_run(&$argv, &$argc){
|
|||
|
||||
proc_run('php',"include/queue.php");
|
||||
|
||||
// run diaspora photo queue process in the background
|
||||
|
||||
proc_run('php',"include/dsprphotoq.php");
|
||||
|
||||
// run the process to discover global contacts in the background
|
||||
|
||||
proc_run('php',"include/discover_poco.php");
|
||||
|
|
@ -127,13 +102,14 @@ function cron_run(&$argv, &$argc){
|
|||
|
||||
// Check OStatus conversations
|
||||
// Check only conversations with mentions (for a longer time)
|
||||
check_conversations(true);
|
||||
ostatus::check_conversations(true);
|
||||
|
||||
// Check every conversation
|
||||
check_conversations(false);
|
||||
ostatus::check_conversations(false);
|
||||
|
||||
// Set the gcontact-id in the item table if missing
|
||||
item_set_gcontact();
|
||||
// Call possible post update functions
|
||||
// see include/post_update.php for more details
|
||||
post_update();
|
||||
|
||||
// update nodeinfo data
|
||||
nodeinfo_cron();
|
||||
|
|
@ -361,35 +337,37 @@ function cron_clear_cache(&$a) {
|
|||
if ($max_tablesize == 0)
|
||||
$max_tablesize = 100 * 1000000; // Default are 100 MB
|
||||
|
||||
// Minimum fragmentation level in percent
|
||||
$fragmentation_level = intval(get_config('system','optimize_fragmentation')) / 100;
|
||||
if ($fragmentation_level == 0)
|
||||
$fragmentation_level = 0.3; // Default value is 30%
|
||||
if ($max_tablesize > 0) {
|
||||
// Minimum fragmentation level in percent
|
||||
$fragmentation_level = intval(get_config('system','optimize_fragmentation')) / 100;
|
||||
if ($fragmentation_level == 0)
|
||||
$fragmentation_level = 0.3; // Default value is 30%
|
||||
|
||||
// Optimize some tables that need to be optimized
|
||||
$r = q("SHOW TABLE STATUS");
|
||||
foreach($r as $table) {
|
||||
// Optimize some tables that need to be optimized
|
||||
$r = q("SHOW TABLE STATUS");
|
||||
foreach($r as $table) {
|
||||
|
||||
// Don't optimize tables that are too large
|
||||
if ($table["Data_length"] > $max_tablesize)
|
||||
continue;
|
||||
// Don't optimize tables that are too large
|
||||
if ($table["Data_length"] > $max_tablesize)
|
||||
continue;
|
||||
|
||||
// Don't optimize empty tables
|
||||
if ($table["Data_length"] == 0)
|
||||
continue;
|
||||
// Don't optimize empty tables
|
||||
if ($table["Data_length"] == 0)
|
||||
continue;
|
||||
|
||||
// Calculate fragmentation
|
||||
$fragmentation = $table["Data_free"] / $table["Data_length"];
|
||||
// Calculate fragmentation
|
||||
$fragmentation = $table["Data_free"] / ($table["Data_length"] + $table["Index_length"]);
|
||||
|
||||
logger("Table ".$table["Name"]." - Fragmentation level: ".round($fragmentation * 100, 2), LOGGER_DEBUG);
|
||||
logger("Table ".$table["Name"]." - Fragmentation level: ".round($fragmentation * 100, 2), LOGGER_DEBUG);
|
||||
|
||||
// Don't optimize tables that needn't to be optimized
|
||||
if ($fragmentation < $fragmentation_level)
|
||||
continue;
|
||||
// Don't optimize tables that needn't to be optimized
|
||||
if ($fragmentation < $fragmentation_level)
|
||||
continue;
|
||||
|
||||
// So optimize it
|
||||
logger("Optimize Table ".$table["Name"], LOGGER_DEBUG);
|
||||
q("OPTIMIZE TABLE `%s`", dbesc($table["Name"]));
|
||||
// So optimize it
|
||||
logger("Optimize Table ".$table["Name"], LOGGER_DEBUG);
|
||||
q("OPTIMIZE TABLE `%s`", dbesc($table["Name"]));
|
||||
}
|
||||
}
|
||||
|
||||
set_config('system','cache_last_cleared', time());
|
||||
|
|
@ -429,6 +407,9 @@ function cron_repair_database() {
|
|||
// This call is very "cheap" so we can do it at any time without a problem
|
||||
q("UPDATE `item` INNER JOIN `item` AS `parent` ON `parent`.`uri` = `item`.`parent-uri` AND `parent`.`uid` = `item`.`uid` SET `item`.`parent` = `parent`.`id` WHERE `item`.`parent` = 0");
|
||||
|
||||
// There was an issue where the nick vanishes from the contact table
|
||||
q("UPDATE `contact` INNER JOIN `user` ON `contact`.`uid` = `user`.`uid` SET `nick` = `nickname` WHERE `self` AND `nick`=''");
|
||||
|
||||
/// @todo
|
||||
/// - remove thread entries without item
|
||||
/// - remove sign entries without item
|
||||
|
|
|
|||
|
|
@ -19,21 +19,16 @@ function cronhooks_run(&$argv, &$argc){
|
|||
|
||||
require_once('include/session.php');
|
||||
require_once('include/datetime.php');
|
||||
require_once('include/pidfile.php');
|
||||
|
||||
load_config('config');
|
||||
load_config('system');
|
||||
|
||||
$maxsysload = intval(get_config('system','maxloadavg'));
|
||||
if($maxsysload < 1)
|
||||
$maxsysload = 50;
|
||||
|
||||
$load = current_load();
|
||||
if($load) {
|
||||
if(intval($load) > $maxsysload) {
|
||||
logger('system: load ' . $load . ' too high. Cronhooks deferred to next scheduled run.');
|
||||
// Don't check this stuff if the function is called by the poller
|
||||
if (App::callstack() != "poller_run") {
|
||||
if (App::maxload_reached())
|
||||
return;
|
||||
if (App::is_already_running('cronhooks', 'include/cronhooks.php', 1140))
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
$last = get_config('system','last_cronhook');
|
||||
|
|
@ -50,21 +45,6 @@ function cronhooks_run(&$argv, &$argc){
|
|||
}
|
||||
}
|
||||
|
||||
$lockpath = get_lockpath();
|
||||
if ($lockpath != '') {
|
||||
$pidfile = new pidfile($lockpath, 'cronhooks');
|
||||
if($pidfile->is_already_running()) {
|
||||
logger("cronhooks: Already running");
|
||||
if ($pidfile->running_time() > 19*60) {
|
||||
$pidfile->kill();
|
||||
logger("cronhooks: killed stale process");
|
||||
// Calling a new instance
|
||||
proc_run('php','include/cronhooks.php');
|
||||
}
|
||||
exit;
|
||||
}
|
||||
}
|
||||
|
||||
$a->set_baseurl(get_config('system','url'));
|
||||
|
||||
load_hooks();
|
||||
|
|
|
|||
|
|
@ -537,17 +537,6 @@ function db_definition() {
|
|||
"PRIMARY" => array("id"),
|
||||
)
|
||||
);
|
||||
$database["dsprphotoq"] = array(
|
||||
"fields" => array(
|
||||
"id" => array("type" => "int(10) unsigned", "not null" => "1", "extra" => "auto_increment", "primary" => "1"),
|
||||
"uid" => array("type" => "int(11)", "not null" => "1", "default" => "0"),
|
||||
"msg" => array("type" => "mediumtext", "not null" => "1"),
|
||||
"attempt" => array("type" => "tinyint(4)", "not null" => "1", "default" => "0"),
|
||||
),
|
||||
"indexes" => array(
|
||||
"PRIMARY" => array("id"),
|
||||
)
|
||||
);
|
||||
$database["event"] = array(
|
||||
"fields" => array(
|
||||
"id" => array("type" => "int(11)", "not null" => "1", "extra" => "auto_increment", "primary" => "1"),
|
||||
|
|
@ -1246,7 +1235,6 @@ function db_definition() {
|
|||
"fields" => array(
|
||||
"id" => array("type" => "int(10) unsigned", "not null" => "1", "extra" => "auto_increment", "primary" => "1"),
|
||||
"iid" => array("type" => "int(10) unsigned", "not null" => "1", "default" => "0"),
|
||||
"retract_iid" => array("type" => "int(10) unsigned", "not null" => "1", "default" => "0"),
|
||||
"signed_text" => array("type" => "mediumtext", "not null" => "1"),
|
||||
"signature" => array("type" => "text", "not null" => "1"),
|
||||
"signer" => array("type" => "varchar(255)", "not null" => "1", "default" => ""),
|
||||
|
|
@ -1254,7 +1242,6 @@ function db_definition() {
|
|||
"indexes" => array(
|
||||
"PRIMARY" => array("id"),
|
||||
"iid" => array("iid"),
|
||||
"retract_iid" => array("retract_iid"),
|
||||
)
|
||||
);
|
||||
$database["spam"] = array(
|
||||
|
|
|
|||
|
|
@ -10,11 +10,11 @@ require_once("include/dfrn.php");
|
|||
function delivery_run(&$argv, &$argc){
|
||||
global $a, $db;
|
||||
|
||||
if(is_null($a)){
|
||||
if (is_null($a)){
|
||||
$a = new App;
|
||||
}
|
||||
|
||||
if(is_null($db)) {
|
||||
if (is_null($db)) {
|
||||
@include(".htconfig.php");
|
||||
require_once("include/dba.php");
|
||||
$db = new dba($db_host, $db_user, $db_pass, $db_data);
|
||||
|
|
@ -32,12 +32,12 @@ function delivery_run(&$argv, &$argc){
|
|||
|
||||
load_hooks();
|
||||
|
||||
if($argc < 3)
|
||||
if ($argc < 3)
|
||||
return;
|
||||
|
||||
$a->set_baseurl(get_config('system','url'));
|
||||
|
||||
logger('delivery: invoked: ' . print_r($argv,true), LOGGER_DEBUG);
|
||||
logger('delivery: invoked: '. print_r($argv,true), LOGGER_DEBUG);
|
||||
|
||||
$cmd = $argv[1];
|
||||
$item_id = intval($argv[2]);
|
||||
|
|
@ -53,21 +53,12 @@ function delivery_run(&$argv, &$argc){
|
|||
dbesc($item_id),
|
||||
dbesc($contact_id)
|
||||
);
|
||||
if(! count($r)) {
|
||||
if (!count($r)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$maxsysload = intval(get_config('system','maxloadavg'));
|
||||
if($maxsysload < 1)
|
||||
$maxsysload = 50;
|
||||
|
||||
$load = current_load();
|
||||
if($load) {
|
||||
if(intval($load) > $maxsysload) {
|
||||
logger('system: load ' . $load . ' too high. Delivery deferred to next queue run.');
|
||||
return;
|
||||
}
|
||||
}
|
||||
if (App::maxload_reached())
|
||||
return;
|
||||
|
||||
// It's ours to deliver. Remove it from the queue.
|
||||
|
||||
|
|
@ -77,7 +68,7 @@ function delivery_run(&$argv, &$argc){
|
|||
dbesc($contact_id)
|
||||
);
|
||||
|
||||
if((! $item_id) || (! $contact_id))
|
||||
if (!$item_id || !$contact_id)
|
||||
continue;
|
||||
|
||||
$expire = false;
|
||||
|
|
@ -93,20 +84,20 @@ function delivery_run(&$argv, &$argc){
|
|||
|
||||
$recipients[] = $contact_id;
|
||||
|
||||
if($cmd === 'mail') {
|
||||
if ($cmd === 'mail') {
|
||||
$normal_mode = false;
|
||||
$mail = true;
|
||||
$message = q("SELECT * FROM `mail` WHERE `id` = %d LIMIT 1",
|
||||
intval($item_id)
|
||||
);
|
||||
if(! count($message)){
|
||||
if (!count($message)){
|
||||
return;
|
||||
}
|
||||
$uid = $message[0]['uid'];
|
||||
$recipients[] = $message[0]['contact-id'];
|
||||
$item = $message[0];
|
||||
}
|
||||
elseif($cmd === 'expire') {
|
||||
elseif ($cmd === 'expire') {
|
||||
$normal_mode = false;
|
||||
$expire = true;
|
||||
$items = q("SELECT * FROM `item` WHERE `uid` = %d AND `wall` = 1
|
||||
|
|
@ -115,22 +106,22 @@ function delivery_run(&$argv, &$argc){
|
|||
);
|
||||
$uid = $item_id;
|
||||
$item_id = 0;
|
||||
if(! count($items))
|
||||
if (!count($items))
|
||||
continue;
|
||||
}
|
||||
elseif($cmd === 'suggest') {
|
||||
elseif ($cmd === 'suggest') {
|
||||
$normal_mode = false;
|
||||
$fsuggest = true;
|
||||
|
||||
$suggest = q("SELECT * FROM `fsuggest` WHERE `id` = %d LIMIT 1",
|
||||
intval($item_id)
|
||||
);
|
||||
if(! count($suggest))
|
||||
if (!count($suggest))
|
||||
return;
|
||||
$uid = $suggest[0]['uid'];
|
||||
$recipients[] = $suggest[0]['cid'];
|
||||
$item = $suggest[0];
|
||||
} elseif($cmd === 'relocate') {
|
||||
} elseif ($cmd === 'relocate') {
|
||||
$normal_mode = false;
|
||||
$relocate = true;
|
||||
$uid = $item_id;
|
||||
|
|
@ -140,7 +131,7 @@ function delivery_run(&$argv, &$argc){
|
|||
intval($item_id)
|
||||
);
|
||||
|
||||
if((! count($r)) || (! intval($r[0]['parent']))) {
|
||||
if ((!count($r)) || (!intval($r[0]['parent']))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
|
|
@ -154,32 +145,32 @@ function delivery_run(&$argv, &$argc){
|
|||
intval($parent_id)
|
||||
);
|
||||
|
||||
if(! count($items)) {
|
||||
if (!count($items)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$icontacts = null;
|
||||
$contacts_arr = array();
|
||||
foreach($items as $item)
|
||||
if(! in_array($item['contact-id'],$contacts_arr))
|
||||
if (!in_array($item['contact-id'],$contacts_arr))
|
||||
$contacts_arr[] = intval($item['contact-id']);
|
||||
if(count($contacts_arr)) {
|
||||
if (count($contacts_arr)) {
|
||||
$str_contacts = implode(',',$contacts_arr);
|
||||
$icontacts = q("SELECT * FROM `contact`
|
||||
WHERE `id` IN ( $str_contacts ) "
|
||||
);
|
||||
}
|
||||
if( ! ($icontacts && count($icontacts)))
|
||||
if ( !($icontacts && count($icontacts)))
|
||||
continue;
|
||||
|
||||
// avoid race condition with deleting entries
|
||||
|
||||
if($items[0]['deleted']) {
|
||||
if ($items[0]['deleted']) {
|
||||
foreach($items as $item)
|
||||
$item['deleted'] = 1;
|
||||
}
|
||||
|
||||
if((count($items) == 1) && ($items[0]['uri'] === $items[0]['parent-uri'])) {
|
||||
if ((count($items) == 1) && ($items[0]['uri'] === $items[0]['parent-uri'])) {
|
||||
logger('delivery: top level post');
|
||||
$top_level = true;
|
||||
}
|
||||
|
|
@ -193,7 +184,7 @@ function delivery_run(&$argv, &$argc){
|
|||
intval($uid)
|
||||
);
|
||||
|
||||
if(! count($r))
|
||||
if (!count($r))
|
||||
continue;
|
||||
|
||||
$owner = $r[0];
|
||||
|
|
@ -202,7 +193,7 @@ function delivery_run(&$argv, &$argc){
|
|||
|
||||
$public_message = true;
|
||||
|
||||
if(! ($mail || $fsuggest || $relocate)) {
|
||||
if (!($mail || $fsuggest || $relocate)) {
|
||||
require_once('include/group.php');
|
||||
|
||||
$parent = $items[0];
|
||||
|
|
@ -226,7 +217,7 @@ function delivery_run(&$argv, &$argc){
|
|||
|
||||
|
||||
$localhost = $a->get_hostname();
|
||||
if(strpos($localhost,':'))
|
||||
if (strpos($localhost,':'))
|
||||
$localhost = substr($localhost,0,strpos($localhost,':'));
|
||||
|
||||
/**
|
||||
|
|
@ -239,20 +230,21 @@ function delivery_run(&$argv, &$argc){
|
|||
|
||||
$relay_to_owner = false;
|
||||
|
||||
if((! $top_level) && ($parent['wall'] == 0) && (! $expire) && (stristr($target_item['uri'],$localhost))) {
|
||||
if (!$top_level && ($parent['wall'] == 0) && !$expire && stristr($target_item['uri'],$localhost)) {
|
||||
$relay_to_owner = true;
|
||||
}
|
||||
|
||||
if($relay_to_owner) {
|
||||
if ($relay_to_owner) {
|
||||
logger('followup '.$target_item["guid"], LOGGER_DEBUG);
|
||||
// local followup to remote post
|
||||
$followup = true;
|
||||
}
|
||||
|
||||
if((strlen($parent['allow_cid']))
|
||||
if ((strlen($parent['allow_cid']))
|
||||
|| (strlen($parent['allow_gid']))
|
||||
|| (strlen($parent['deny_cid']))
|
||||
|| (strlen($parent['deny_gid']))) {
|
||||
|| (strlen($parent['deny_gid']))
|
||||
|| $parent["private"]) {
|
||||
$public_message = false; // private recipients, not public
|
||||
}
|
||||
|
||||
|
|
@ -262,10 +254,10 @@ function delivery_run(&$argv, &$argc){
|
|||
intval($contact_id)
|
||||
);
|
||||
|
||||
if(count($r))
|
||||
if (count($r))
|
||||
$contact = $r[0];
|
||||
|
||||
if($contact['self'])
|
||||
if ($contact['self'])
|
||||
continue;
|
||||
|
||||
$deliver_status = 0;
|
||||
|
|
@ -275,7 +267,7 @@ function delivery_run(&$argv, &$argc){
|
|||
switch($contact['network']) {
|
||||
|
||||
case NETWORK_DFRN:
|
||||
logger('notifier: '.$target_item["guid"].' dfrndelivery: ' . $contact['name']);
|
||||
logger('notifier: '.$target_item["guid"].' dfrndelivery: '.$contact['name']);
|
||||
|
||||
if ($mail) {
|
||||
$item['body'] = fix_private_photos($item['body'],$owner['uid'],null,$message[0]['contact-id']);
|
||||
|
|
@ -285,13 +277,13 @@ function delivery_run(&$argv, &$argc){
|
|||
q("DELETE FROM `fsuggest` WHERE `id` = %d LIMIT 1", intval($item['id']));
|
||||
} elseif ($relocate)
|
||||
$atom = dfrn::relocate($owner, $uid);
|
||||
elseif($followup) {
|
||||
elseif ($followup) {
|
||||
$msgitems = array();
|
||||
foreach($items as $item) { // there is only one item
|
||||
if(!$item['parent'])
|
||||
if (!$item['parent'])
|
||||
continue;
|
||||
if($item['id'] == $item_id) {
|
||||
logger('followup: item: ' . print_r($item,true), LOGGER_DATA);
|
||||
if ($item['id'] == $item_id) {
|
||||
logger('followup: item: '. print_r($item,true), LOGGER_DATA);
|
||||
$msgitems[] = $item;
|
||||
}
|
||||
}
|
||||
|
|
@ -299,19 +291,19 @@ function delivery_run(&$argv, &$argc){
|
|||
} else {
|
||||
$msgitems = array();
|
||||
foreach($items as $item) {
|
||||
if(!$item['parent'])
|
||||
if (!$item['parent'])
|
||||
continue;
|
||||
|
||||
// private emails may be in included in public conversations. Filter them.
|
||||
if(($public_message) && $item['private'])
|
||||
if ($public_message && $item['private'])
|
||||
continue;
|
||||
|
||||
$item_contact = get_item_contact($item,$icontacts);
|
||||
if(!$item_contact)
|
||||
if (!$item_contact)
|
||||
continue;
|
||||
|
||||
if($normal_mode) {
|
||||
if($item_id == $item['id'] || $item['id'] == $item['parent']) {
|
||||
if ($normal_mode) {
|
||||
if ($item_id == $item['id'] || $item['id'] == $item['parent']) {
|
||||
$item["entry:comment-allow"] = true;
|
||||
$item["entry:cid"] = (($top_level) ? $contact['id'] : 0);
|
||||
$msgitems[] = $item;
|
||||
|
|
@ -326,15 +318,15 @@ function delivery_run(&$argv, &$argc){
|
|||
|
||||
logger('notifier entry: '.$contact["url"].' '.$target_item["guid"].' entry: '.$atom, LOGGER_DEBUG);
|
||||
|
||||
logger('notifier: ' . $atom, LOGGER_DATA);
|
||||
logger('notifier: '.$atom, LOGGER_DATA);
|
||||
$basepath = implode('/', array_slice(explode('/',$contact['url']),0,3));
|
||||
|
||||
// perform local delivery if we are on the same site
|
||||
|
||||
if(link_compare($basepath,$a->get_baseurl())) {
|
||||
if (link_compare($basepath,$a->get_baseurl())) {
|
||||
|
||||
$nickname = basename($contact['url']);
|
||||
if($contact['issued-id'])
|
||||
if ($contact['issued-id'])
|
||||
$sql_extra = sprintf(" AND `dfrn-id` = '%s' ", dbesc($contact['issued-id']));
|
||||
else
|
||||
$sql_extra = sprintf(" AND `issued-id` = '%s' ", dbesc($contact['dfrn-id']));
|
||||
|
|
@ -356,10 +348,10 @@ function delivery_run(&$argv, &$argc){
|
|||
dbesc($nickname)
|
||||
);
|
||||
|
||||
if($x && count($x)) {
|
||||
if ($x && count($x)) {
|
||||
$write_flag = ((($x[0]['rel']) && ($x[0]['rel'] != CONTACT_IS_SHARING)) ? true : false);
|
||||
if((($owner['page-flags'] == PAGE_COMMUNITY) || ($write_flag)) && (! $x[0]['writable'])) {
|
||||
q("update contact set writable = 1 where id = %d",
|
||||
if ((($owner['page-flags'] == PAGE_COMMUNITY) || $write_flag) && !$x[0]['writable']) {
|
||||
q("UPDATE `contact` SET `writable` = 1 WHERE `id` = %d",
|
||||
intval($x[0]['id'])
|
||||
);
|
||||
$x[0]['writable'] = 1;
|
||||
|
|
@ -379,14 +371,14 @@ function delivery_run(&$argv, &$argc){
|
|||
}
|
||||
}
|
||||
|
||||
if(! was_recently_delayed($contact['id']))
|
||||
if (!was_recently_delayed($contact['id']))
|
||||
$deliver_status = dfrn::deliver($owner,$contact,$atom);
|
||||
else
|
||||
$deliver_status = (-1);
|
||||
|
||||
logger('notifier: dfrn_delivery to '.$contact["url"].' with guid '.$target_item["guid"].' returns '.$deliver_status);
|
||||
|
||||
if($deliver_status == (-1)) {
|
||||
if ($deliver_status == (-1)) {
|
||||
logger('notifier: delivery failed: queuing message');
|
||||
add_to_queue($contact['id'],NETWORK_DFRN,$atom);
|
||||
}
|
||||
|
|
@ -394,9 +386,9 @@ function delivery_run(&$argv, &$argc){
|
|||
|
||||
case NETWORK_OSTATUS:
|
||||
// Do not send to otatus if we are not configured to send to public networks
|
||||
if($owner['prvnets'])
|
||||
if ($owner['prvnets'])
|
||||
break;
|
||||
if(get_config('system','ostatus_disabled') || get_config('system','dfrn_only'))
|
||||
if (get_config('system','ostatus_disabled') || get_config('system','dfrn_only'))
|
||||
break;
|
||||
|
||||
// There is currently no code here to distribute anything to OStatus.
|
||||
|
|
@ -406,67 +398,67 @@ function delivery_run(&$argv, &$argc){
|
|||
case NETWORK_MAIL:
|
||||
case NETWORK_MAIL2:
|
||||
|
||||
if(get_config('system','dfrn_only'))
|
||||
if (get_config('system','dfrn_only'))
|
||||
break;
|
||||
// WARNING: does not currently convert to RFC2047 header encodings, etc.
|
||||
|
||||
$addr = $contact['addr'];
|
||||
if(! strlen($addr))
|
||||
if (!strlen($addr))
|
||||
break;
|
||||
|
||||
if($cmd === 'wall-new' || $cmd === 'comment-new') {
|
||||
if ($cmd === 'wall-new' || $cmd === 'comment-new') {
|
||||
|
||||
$it = null;
|
||||
if($cmd === 'wall-new')
|
||||
if ($cmd === 'wall-new')
|
||||
$it = $items[0];
|
||||
else {
|
||||
$r = q("SELECT * FROM `item` WHERE `id` = %d AND `uid` = %d LIMIT 1",
|
||||
intval($argv[2]),
|
||||
intval($uid)
|
||||
);
|
||||
if(count($r))
|
||||
if (count($r))
|
||||
$it = $r[0];
|
||||
}
|
||||
if(! $it)
|
||||
if (!$it)
|
||||
break;
|
||||
|
||||
|
||||
$local_user = q("SELECT * FROM `user` WHERE `uid` = %d LIMIT 1",
|
||||
intval($uid)
|
||||
);
|
||||
if(! count($local_user))
|
||||
if (!count($local_user))
|
||||
break;
|
||||
|
||||
$reply_to = '';
|
||||
$r1 = q("SELECT * FROM `mailacct` WHERE `uid` = %d LIMIT 1",
|
||||
intval($uid)
|
||||
);
|
||||
if($r1 && $r1[0]['reply_to'])
|
||||
if ($r1 && $r1[0]['reply_to'])
|
||||
$reply_to = $r1[0]['reply_to'];
|
||||
|
||||
$subject = (($it['title']) ? email_header_encode($it['title'],'UTF-8') : t("\x28no subject\x29")) ;
|
||||
|
||||
// only expose our real email address to true friends
|
||||
|
||||
if(($contact['rel'] == CONTACT_IS_FRIEND) && (! $contact['blocked'])) {
|
||||
if($reply_to) {
|
||||
if (($contact['rel'] == CONTACT_IS_FRIEND) && !$contact['blocked']) {
|
||||
if ($reply_to) {
|
||||
$headers = 'From: '.email_header_encode($local_user[0]['username'],'UTF-8').' <'.$reply_to.'>'."\n";
|
||||
$headers .= 'Sender: '.$local_user[0]['email']."\n";
|
||||
} else
|
||||
$headers = 'From: '.email_header_encode($local_user[0]['username'],'UTF-8').' <'.$local_user[0]['email'].'>'."\n";
|
||||
} else
|
||||
$headers = 'From: ' . email_header_encode($local_user[0]['username'],'UTF-8') . ' <' . t('noreply') . '@' . $a->get_hostname() . '>' . "\n";
|
||||
$headers = 'From: '. email_header_encode($local_user[0]['username'],'UTF-8') .' <'. t('noreply') .'@'.$a->get_hostname() .'>'. "\n";
|
||||
|
||||
//if($reply_to)
|
||||
// $headers .= 'Reply-to: ' . $reply_to . "\n";
|
||||
//if ($reply_to)
|
||||
// $headers .= 'Reply-to: '.$reply_to . "\n";
|
||||
|
||||
$headers .= 'Message-Id: <' . iri2msgid($it['uri']). '>' . "\n";
|
||||
$headers .= 'Message-Id: <'. iri2msgid($it['uri']).'>'. "\n";
|
||||
|
||||
//logger("Mail: uri: ".$it['uri']." parent-uri ".$it['parent-uri'], LOGGER_DEBUG);
|
||||
//logger("Mail: Data: ".print_r($it, true), LOGGER_DEBUG);
|
||||
//logger("Mail: Data: ".print_r($it, true), LOGGER_DATA);
|
||||
|
||||
if($it['uri'] !== $it['parent-uri']) {
|
||||
if ($it['uri'] !== $it['parent-uri']) {
|
||||
$headers .= "References: <".iri2msgid($it["parent-uri"]).">";
|
||||
|
||||
// If Threading is enabled, write down the correct parent
|
||||
|
|
@ -474,23 +466,23 @@ function delivery_run(&$argv, &$argc){
|
|||
$headers .= " <".iri2msgid($it["thr-parent"]).">";
|
||||
$headers .= "\n";
|
||||
|
||||
if(!$it['title']) {
|
||||
if (!$it['title']) {
|
||||
$r = q("SELECT `title` FROM `item` WHERE `uri` = '%s' AND `uid` = %d LIMIT 1",
|
||||
dbesc($it['parent-uri']),
|
||||
intval($uid));
|
||||
|
||||
if(count($r) AND ($r[0]['title'] != ''))
|
||||
if (count($r) AND ($r[0]['title'] != ''))
|
||||
$subject = $r[0]['title'];
|
||||
else {
|
||||
$r = q("SELECT `title` FROM `item` WHERE `parent-uri` = '%s' AND `uid` = %d LIMIT 1",
|
||||
dbesc($it['parent-uri']),
|
||||
intval($uid));
|
||||
|
||||
if(count($r) AND ($r[0]['title'] != ''))
|
||||
if (count($r) AND ($r[0]['title'] != ''))
|
||||
$subject = $r[0]['title'];
|
||||
}
|
||||
}
|
||||
if(strncasecmp($subject,'RE:',3))
|
||||
if (strncasecmp($subject,'RE:',3))
|
||||
$subject = 'Re: '.$subject;
|
||||
}
|
||||
email_send($addr, $subject, $headers, $it);
|
||||
|
|
@ -498,60 +490,59 @@ function delivery_run(&$argv, &$argc){
|
|||
break;
|
||||
|
||||
case NETWORK_DIASPORA:
|
||||
if($public_message)
|
||||
$loc = 'public batch ' . $contact['batch'];
|
||||
if ($public_message)
|
||||
$loc = 'public batch '.$contact['batch'];
|
||||
else
|
||||
$loc = $contact['name'];
|
||||
|
||||
logger('delivery: diaspora batch deliver: ' . $loc);
|
||||
logger('delivery: diaspora batch deliver: '.$loc);
|
||||
|
||||
if(get_config('system','dfrn_only') || (!get_config('system','diaspora_enabled')))
|
||||
if (get_config('system','dfrn_only') || (!get_config('system','diaspora_enabled')))
|
||||
break;
|
||||
|
||||
if($mail) {
|
||||
diaspora_send_mail($item,$owner,$contact);
|
||||
if ($mail) {
|
||||
diaspora::send_mail($item,$owner,$contact);
|
||||
break;
|
||||
}
|
||||
|
||||
if(!$normal_mode)
|
||||
if (!$normal_mode)
|
||||
break;
|
||||
|
||||
if((! $contact['pubkey']) && (! $public_message))
|
||||
if (!$contact['pubkey'] && !$public_message)
|
||||
break;
|
||||
|
||||
$unsupported_activities = array(ACTIVITY_DISLIKE, ACTIVITY_ATTEND, ACTIVITY_ATTENDNO, ACTIVITY_ATTENDMAYBE);
|
||||
|
||||
//don't transmit activities which are not supported by diaspora
|
||||
foreach($unsupported_activities as $act) {
|
||||
if(activity_match($target_item['verb'],$act)) {
|
||||
if (activity_match($target_item['verb'],$act)) {
|
||||
break 2;
|
||||
}
|
||||
}
|
||||
|
||||
if(($target_item['deleted']) && (($target_item['uri'] === $target_item['parent-uri']) || $followup)) {
|
||||
if (($target_item['deleted']) && (($target_item['uri'] === $target_item['parent-uri']) || $followup)) {
|
||||
// top-level retraction
|
||||
logger('delivery: diaspora retract: ' . $loc);
|
||||
|
||||
diaspora_send_retraction($target_item,$owner,$contact,$public_message);
|
||||
logger('diaspora retract: '.$loc);
|
||||
diaspora::send_retraction($target_item,$owner,$contact,$public_message);
|
||||
break;
|
||||
} elseif($followup) {
|
||||
} elseif ($followup) {
|
||||
// send comments and likes to owner to relay
|
||||
diaspora_send_followup($target_item,$owner,$contact,$public_message);
|
||||
logger('diaspora followup: '.$loc);
|
||||
diaspora::send_followup($target_item,$owner,$contact,$public_message);
|
||||
break;
|
||||
} elseif($target_item['uri'] !== $target_item['parent-uri']) {
|
||||
} elseif ($target_item['uri'] !== $target_item['parent-uri']) {
|
||||
// we are the relay - send comments, likes and relayable_retractions to our conversants
|
||||
logger('delivery: diaspora relay: ' . $loc);
|
||||
|
||||
diaspora_send_relay($target_item,$owner,$contact,$public_message);
|
||||
logger('diaspora relay: '.$loc);
|
||||
diaspora::send_relay($target_item,$owner,$contact,$public_message);
|
||||
break;
|
||||
} elseif(($top_level) && (! $walltowall)) {
|
||||
} elseif ($top_level && !$walltowall) {
|
||||
// currently no workable solution for sending walltowall
|
||||
logger('delivery: diaspora status: ' . $loc);
|
||||
diaspora_send_status($target_item,$owner,$contact,$public_message);
|
||||
logger('diaspora status: '.$loc);
|
||||
diaspora::send_status($target_item,$owner,$contact,$public_message);
|
||||
break;
|
||||
}
|
||||
|
||||
logger('delivery: diaspora unknown mode: ' . $contact['name']);
|
||||
logger('delivery: diaspora unknown mode: '.$contact['name']);
|
||||
|
||||
break;
|
||||
|
||||
|
|
|
|||
244
include/dfrn.php
244
include/dfrn.php
|
|
@ -18,6 +18,8 @@ require_once("include/event.php");
|
|||
require_once("include/text.php");
|
||||
require_once("include/oembed.php");
|
||||
require_once("include/html2bbcode.php");
|
||||
require_once("include/bbcode.php");
|
||||
require_once("include/xml.php");
|
||||
|
||||
/**
|
||||
* @brief This class contain functions to create and send DFRN XML files
|
||||
|
|
@ -84,7 +86,7 @@ class dfrn {
|
|||
$converse = true;
|
||||
if($a->argv[$x] == 'starred')
|
||||
$starred = true;
|
||||
if($a->argv[$x] === 'category' && $a->argc > ($x + 1) && strlen($a->argv[$x+1]))
|
||||
if($a->argv[$x] == 'category' && $a->argc > ($x + 1) && strlen($a->argv[$x+1]))
|
||||
$category = $a->argv[$x+1];
|
||||
}
|
||||
}
|
||||
|
|
@ -243,7 +245,7 @@ class dfrn {
|
|||
foreach($items as $item) {
|
||||
|
||||
// prevent private email from leaking.
|
||||
if($item['network'] === NETWORK_MAIL)
|
||||
if($item['network'] == NETWORK_MAIL)
|
||||
continue;
|
||||
|
||||
// public feeds get html, our own nodes use bbcode
|
||||
|
|
@ -285,17 +287,17 @@ class dfrn {
|
|||
$mail = $doc->createElement("dfrn:mail");
|
||||
$sender = $doc->createElement("dfrn:sender");
|
||||
|
||||
xml_add_element($doc, $sender, "dfrn:name", $owner['name']);
|
||||
xml_add_element($doc, $sender, "dfrn:uri", $owner['url']);
|
||||
xml_add_element($doc, $sender, "dfrn:avatar", $owner['thumb']);
|
||||
xml::add_element($doc, $sender, "dfrn:name", $owner['name']);
|
||||
xml::add_element($doc, $sender, "dfrn:uri", $owner['url']);
|
||||
xml::add_element($doc, $sender, "dfrn:avatar", $owner['thumb']);
|
||||
|
||||
$mail->appendChild($sender);
|
||||
|
||||
xml_add_element($doc, $mail, "dfrn:id", $item['uri']);
|
||||
xml_add_element($doc, $mail, "dfrn:in-reply-to", $item['parent-uri']);
|
||||
xml_add_element($doc, $mail, "dfrn:sentdate", datetime_convert('UTC', 'UTC', $item['created'] . '+00:00' , ATOM_TIME));
|
||||
xml_add_element($doc, $mail, "dfrn:subject", $item['title']);
|
||||
xml_add_element($doc, $mail, "dfrn:content", $item['body']);
|
||||
xml::add_element($doc, $mail, "dfrn:id", $item['uri']);
|
||||
xml::add_element($doc, $mail, "dfrn:in-reply-to", $item['parent-uri']);
|
||||
xml::add_element($doc, $mail, "dfrn:sentdate", datetime_convert('UTC', 'UTC', $item['created'] . '+00:00' , ATOM_TIME));
|
||||
xml::add_element($doc, $mail, "dfrn:subject", $item['title']);
|
||||
xml::add_element($doc, $mail, "dfrn:content", $item['body']);
|
||||
|
||||
$root->appendChild($mail);
|
||||
|
||||
|
|
@ -318,11 +320,11 @@ class dfrn {
|
|||
|
||||
$suggest = $doc->createElement("dfrn:suggest");
|
||||
|
||||
xml_add_element($doc, $suggest, "dfrn:url", $item['url']);
|
||||
xml_add_element($doc, $suggest, "dfrn:name", $item['name']);
|
||||
xml_add_element($doc, $suggest, "dfrn:photo", $item['photo']);
|
||||
xml_add_element($doc, $suggest, "dfrn:request", $item['request']);
|
||||
xml_add_element($doc, $suggest, "dfrn:note", $item['note']);
|
||||
xml::add_element($doc, $suggest, "dfrn:url", $item['url']);
|
||||
xml::add_element($doc, $suggest, "dfrn:name", $item['name']);
|
||||
xml::add_element($doc, $suggest, "dfrn:photo", $item['photo']);
|
||||
xml::add_element($doc, $suggest, "dfrn:request", $item['request']);
|
||||
xml::add_element($doc, $suggest, "dfrn:note", $item['note']);
|
||||
|
||||
$root->appendChild($suggest);
|
||||
|
||||
|
|
@ -364,16 +366,16 @@ class dfrn {
|
|||
|
||||
$relocate = $doc->createElement("dfrn:relocate");
|
||||
|
||||
xml_add_element($doc, $relocate, "dfrn:url", $owner['url']);
|
||||
xml_add_element($doc, $relocate, "dfrn:name", $owner['name']);
|
||||
xml_add_element($doc, $relocate, "dfrn:photo", $photos[4]);
|
||||
xml_add_element($doc, $relocate, "dfrn:thumb", $photos[5]);
|
||||
xml_add_element($doc, $relocate, "dfrn:micro", $photos[6]);
|
||||
xml_add_element($doc, $relocate, "dfrn:request", $owner['request']);
|
||||
xml_add_element($doc, $relocate, "dfrn:confirm", $owner['confirm']);
|
||||
xml_add_element($doc, $relocate, "dfrn:notify", $owner['notify']);
|
||||
xml_add_element($doc, $relocate, "dfrn:poll", $owner['poll']);
|
||||
xml_add_element($doc, $relocate, "dfrn:sitepubkey", get_config('system','site_pubkey'));
|
||||
xml::add_element($doc, $relocate, "dfrn:url", $owner['url']);
|
||||
xml::add_element($doc, $relocate, "dfrn:name", $owner['name']);
|
||||
xml::add_element($doc, $relocate, "dfrn:photo", $photos[4]);
|
||||
xml::add_element($doc, $relocate, "dfrn:thumb", $photos[5]);
|
||||
xml::add_element($doc, $relocate, "dfrn:micro", $photos[6]);
|
||||
xml::add_element($doc, $relocate, "dfrn:request", $owner['request']);
|
||||
xml::add_element($doc, $relocate, "dfrn:confirm", $owner['confirm']);
|
||||
xml::add_element($doc, $relocate, "dfrn:notify", $owner['notify']);
|
||||
xml::add_element($doc, $relocate, "dfrn:poll", $owner['poll']);
|
||||
xml::add_element($doc, $relocate, "dfrn:sitepubkey", get_config('system','site_pubkey'));
|
||||
|
||||
$root->appendChild($relocate);
|
||||
|
||||
|
|
@ -409,39 +411,39 @@ class dfrn {
|
|||
$root->setAttribute("xmlns:ostatus", NAMESPACE_OSTATUS);
|
||||
$root->setAttribute("xmlns:statusnet", NAMESPACE_STATUSNET);
|
||||
|
||||
xml_add_element($doc, $root, "id", app::get_baseurl()."/profile/".$owner["nick"]);
|
||||
xml_add_element($doc, $root, "title", $owner["name"]);
|
||||
xml::add_element($doc, $root, "id", app::get_baseurl()."/profile/".$owner["nick"]);
|
||||
xml::add_element($doc, $root, "title", $owner["name"]);
|
||||
|
||||
$attributes = array("uri" => "https://friendi.ca", "version" => FRIENDICA_VERSION."-".DB_UPDATE_VERSION);
|
||||
xml_add_element($doc, $root, "generator", FRIENDICA_PLATFORM, $attributes);
|
||||
xml::add_element($doc, $root, "generator", FRIENDICA_PLATFORM, $attributes);
|
||||
|
||||
$attributes = array("rel" => "license", "href" => "http://creativecommons.org/licenses/by/3.0/");
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
$attributes = array("rel" => "alternate", "type" => "text/html", "href" => $alternatelink);
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
|
||||
if ($public) {
|
||||
// DFRN itself doesn't uses this. But maybe someone else wants to subscribe to the public feed.
|
||||
ostatus_hublinks($doc, $root);
|
||||
ostatus::hublinks($doc, $root);
|
||||
|
||||
$attributes = array("rel" => "salmon", "href" => app::get_baseurl()."/salmon/".$owner["nick"]);
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
$attributes = array("rel" => "http://salmon-protocol.org/ns/salmon-replies", "href" => app::get_baseurl()."/salmon/".$owner["nick"]);
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
$attributes = array("rel" => "http://salmon-protocol.org/ns/salmon-mention", "href" => app::get_baseurl()."/salmon/".$owner["nick"]);
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
}
|
||||
|
||||
if ($owner['page-flags'] == PAGE_COMMUNITY)
|
||||
xml_add_element($doc, $root, "dfrn:community", 1);
|
||||
xml::add_element($doc, $root, "dfrn:community", 1);
|
||||
|
||||
/// @todo We need a way to transmit the different page flags like "PAGE_PRVGROUP"
|
||||
|
||||
xml_add_element($doc, $root, "updated", datetime_convert("UTC", "UTC", "now", ATOM_TIME));
|
||||
xml::add_element($doc, $root, "updated", datetime_convert("UTC", "UTC", "now", ATOM_TIME));
|
||||
|
||||
$author = self::add_author($doc, $owner, $authorelement, $public);
|
||||
$root->appendChild($author);
|
||||
|
|
@ -467,26 +469,26 @@ class dfrn {
|
|||
$picdate = datetime_convert('UTC', 'UTC', $owner['avatar-date'].'+00:00', ATOM_TIME);
|
||||
|
||||
$attributes = array("dfrn:updated" => $namdate);
|
||||
xml_add_element($doc, $author, "name", $owner["name"], $attributes);
|
||||
xml::add_element($doc, $author, "name", $owner["name"], $attributes);
|
||||
|
||||
$attributes = array("dfrn:updated" => $namdate);
|
||||
xml_add_element($doc, $author, "uri", app::get_baseurl().'/profile/'.$owner["nickname"], $attributes);
|
||||
xml::add_element($doc, $author, "uri", app::get_baseurl().'/profile/'.$owner["nickname"], $attributes);
|
||||
|
||||
$attributes = array("dfrn:updated" => $namdate);
|
||||
xml_add_element($doc, $author, "dfrn:handle", $owner["addr"], $attributes);
|
||||
xml::add_element($doc, $author, "dfrn:handle", $owner["addr"], $attributes);
|
||||
|
||||
$attributes = array("rel" => "photo", "type" => "image/jpeg", "dfrn:updated" => $picdate,
|
||||
"media:width" => 175, "media:height" => 175, "href" => $owner['photo']);
|
||||
xml_add_element($doc, $author, "link", "", $attributes);
|
||||
xml::add_element($doc, $author, "link", "", $attributes);
|
||||
|
||||
$attributes = array("rel" => "avatar", "type" => "image/jpeg", "dfrn:updated" => $picdate,
|
||||
"media:width" => 175, "media:height" => 175, "href" => $owner['photo']);
|
||||
xml_add_element($doc, $author, "link", "", $attributes);
|
||||
xml::add_element($doc, $author, "link", "", $attributes);
|
||||
|
||||
$birthday = feed_birthday($owner['uid'], $owner['timezone']);
|
||||
|
||||
if ($birthday)
|
||||
xml_add_element($doc, $author, "dfrn:birthday", $birthday);
|
||||
xml::add_element($doc, $author, "dfrn:birthday", $birthday);
|
||||
|
||||
// The following fields will only be generated if this isn't for a public feed
|
||||
if ($public)
|
||||
|
|
@ -501,25 +503,25 @@ class dfrn {
|
|||
intval($owner['uid']));
|
||||
if ($r) {
|
||||
$profile = $r[0];
|
||||
xml_add_element($doc, $author, "poco:displayName", $profile["name"]);
|
||||
xml_add_element($doc, $author, "poco:updated", $namdate);
|
||||
xml::add_element($doc, $author, "poco:displayName", $profile["name"]);
|
||||
xml::add_element($doc, $author, "poco:updated", $namdate);
|
||||
|
||||
if (trim($profile["dob"]) != "0000-00-00")
|
||||
xml_add_element($doc, $author, "poco:birthday", "0000-".date("m-d", strtotime($profile["dob"])));
|
||||
xml::add_element($doc, $author, "poco:birthday", "0000-".date("m-d", strtotime($profile["dob"])));
|
||||
|
||||
xml_add_element($doc, $author, "poco:note", $profile["about"]);
|
||||
xml_add_element($doc, $author, "poco:preferredUsername", $profile["nickname"]);
|
||||
xml::add_element($doc, $author, "poco:note", $profile["about"]);
|
||||
xml::add_element($doc, $author, "poco:preferredUsername", $profile["nickname"]);
|
||||
|
||||
$savetz = date_default_timezone_get();
|
||||
date_default_timezone_set($profile["timezone"]);
|
||||
xml_add_element($doc, $author, "poco:utcOffset", date("P"));
|
||||
xml::add_element($doc, $author, "poco:utcOffset", date("P"));
|
||||
date_default_timezone_set($savetz);
|
||||
|
||||
if (trim($profile["homepage"]) != "") {
|
||||
$urls = $doc->createElement("poco:urls");
|
||||
xml_add_element($doc, $urls, "poco:type", "homepage");
|
||||
xml_add_element($doc, $urls, "poco:value", $profile["homepage"]);
|
||||
xml_add_element($doc, $urls, "poco:primary", "true");
|
||||
xml::add_element($doc, $urls, "poco:type", "homepage");
|
||||
xml::add_element($doc, $urls, "poco:value", $profile["homepage"]);
|
||||
xml::add_element($doc, $urls, "poco:primary", "true");
|
||||
$author->appendChild($urls);
|
||||
}
|
||||
|
||||
|
|
@ -527,7 +529,7 @@ class dfrn {
|
|||
$keywords = explode(",", $profile["pub_keywords"]);
|
||||
|
||||
foreach ($keywords AS $keyword)
|
||||
xml_add_element($doc, $author, "poco:tags", trim($keyword));
|
||||
xml::add_element($doc, $author, "poco:tags", trim($keyword));
|
||||
|
||||
}
|
||||
|
||||
|
|
@ -535,25 +537,25 @@ class dfrn {
|
|||
$xmpp = "";
|
||||
if (trim($xmpp) != "") {
|
||||
$ims = $doc->createElement("poco:ims");
|
||||
xml_add_element($doc, $ims, "poco:type", "xmpp");
|
||||
xml_add_element($doc, $ims, "poco:value", $xmpp);
|
||||
xml_add_element($doc, $ims, "poco:primary", "true");
|
||||
xml::add_element($doc, $ims, "poco:type", "xmpp");
|
||||
xml::add_element($doc, $ims, "poco:value", $xmpp);
|
||||
xml::add_element($doc, $ims, "poco:primary", "true");
|
||||
$author->appendChild($ims);
|
||||
}
|
||||
|
||||
if (trim($profile["locality"].$profile["region"].$profile["country-name"]) != "") {
|
||||
$element = $doc->createElement("poco:address");
|
||||
|
||||
xml_add_element($doc, $element, "poco:formatted", formatted_location($profile));
|
||||
xml::add_element($doc, $element, "poco:formatted", formatted_location($profile));
|
||||
|
||||
if (trim($profile["locality"]) != "")
|
||||
xml_add_element($doc, $element, "poco:locality", $profile["locality"]);
|
||||
xml::add_element($doc, $element, "poco:locality", $profile["locality"]);
|
||||
|
||||
if (trim($profile["region"]) != "")
|
||||
xml_add_element($doc, $element, "poco:region", $profile["region"]);
|
||||
xml::add_element($doc, $element, "poco:region", $profile["region"]);
|
||||
|
||||
if (trim($profile["country-name"]) != "")
|
||||
xml_add_element($doc, $element, "poco:country", $profile["country-name"]);
|
||||
xml::add_element($doc, $element, "poco:country", $profile["country-name"]);
|
||||
|
||||
$author->appendChild($element);
|
||||
}
|
||||
|
|
@ -577,9 +579,9 @@ class dfrn {
|
|||
$contact = get_contact_details_by_url($contact_url, $item["uid"]);
|
||||
|
||||
$author = $doc->createElement($element);
|
||||
xml_add_element($doc, $author, "name", $contact["name"]);
|
||||
xml_add_element($doc, $author, "uri", $contact["url"]);
|
||||
xml_add_element($doc, $author, "dfrn:handle", $contact["addr"]);
|
||||
xml::add_element($doc, $author, "name", $contact["name"]);
|
||||
xml::add_element($doc, $author, "uri", $contact["url"]);
|
||||
xml::add_element($doc, $author, "dfrn:handle", $contact["addr"]);
|
||||
|
||||
/// @Todo
|
||||
/// - Check real image type and image size
|
||||
|
|
@ -590,7 +592,7 @@ class dfrn {
|
|||
"media:width" => 80,
|
||||
"media:height" => 80,
|
||||
"href" => $contact["photo"]);
|
||||
xml_add_element($doc, $author, "link", "", $attributes);
|
||||
xml::add_element($doc, $author, "link", "", $attributes);
|
||||
|
||||
$attributes = array(
|
||||
"rel" => "avatar",
|
||||
|
|
@ -598,7 +600,7 @@ class dfrn {
|
|||
"media:width" => 80,
|
||||
"media:height" => 80,
|
||||
"href" => $contact["photo"]);
|
||||
xml_add_element($doc, $author, "link", "", $attributes);
|
||||
xml::add_element($doc, $author, "link", "", $attributes);
|
||||
|
||||
return $author;
|
||||
}
|
||||
|
|
@ -621,13 +623,13 @@ class dfrn {
|
|||
if(!$r)
|
||||
return false;
|
||||
if($r->type)
|
||||
xml_add_element($doc, $entry, "activity:object-type", $r->type);
|
||||
xml::add_element($doc, $entry, "activity:object-type", $r->type);
|
||||
if($r->id)
|
||||
xml_add_element($doc, $entry, "id", $r->id);
|
||||
xml::add_element($doc, $entry, "id", $r->id);
|
||||
if($r->title)
|
||||
xml_add_element($doc, $entry, "title", $r->title);
|
||||
xml::add_element($doc, $entry, "title", $r->title);
|
||||
if($r->link) {
|
||||
if(substr($r->link,0,1) === '<') {
|
||||
if(substr($r->link,0,1) == '<') {
|
||||
if(strstr($r->link,'&') && (! strstr($r->link,'&')))
|
||||
$r->link = str_replace('&','&', $r->link);
|
||||
|
||||
|
|
@ -640,16 +642,16 @@ class dfrn {
|
|||
$attributes = array();
|
||||
foreach ($link->attributes() AS $parameter => $value)
|
||||
$attributes[$parameter] = $value;
|
||||
xml_add_element($doc, $entry, "link", "", $attributes);
|
||||
xml::add_element($doc, $entry, "link", "", $attributes);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
$attributes = array("rel" => "alternate", "type" => "text/html", "href" => $r->link);
|
||||
xml_add_element($doc, $entry, "link", "", $attributes);
|
||||
xml::add_element($doc, $entry, "link", "", $attributes);
|
||||
}
|
||||
}
|
||||
if($r->content)
|
||||
xml_add_element($doc, $entry, "content", bbcode($r->content), array("type" => "html"));
|
||||
xml::add_element($doc, $entry, "content", bbcode($r->content), array("type" => "html"));
|
||||
|
||||
return $entry;
|
||||
}
|
||||
|
|
@ -683,7 +685,7 @@ class dfrn {
|
|||
if(trim($matches[4]) != "")
|
||||
$attributes["title"] = trim($matches[4]);
|
||||
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -710,7 +712,7 @@ class dfrn {
|
|||
|
||||
if($item['deleted']) {
|
||||
$attributes = array("ref" => $item['uri'], "when" => datetime_convert('UTC','UTC',$item['edited'] . '+00:00',ATOM_TIME));
|
||||
return xml_create_element($doc, "at:deleted-entry", "", $attributes);
|
||||
return xml::create_element($doc, "at:deleted-entry", "", $attributes);
|
||||
}
|
||||
|
||||
$entry = $doc->createElement("entry");
|
||||
|
|
@ -720,6 +722,9 @@ class dfrn {
|
|||
else
|
||||
$body = $item['body'];
|
||||
|
||||
// Remove the abstract element. It is only locally important.
|
||||
$body = remove_abstract($body);
|
||||
|
||||
if ($type == 'html') {
|
||||
$htmlbody = $body;
|
||||
|
||||
|
|
@ -741,66 +746,66 @@ class dfrn {
|
|||
$attributes = array("ref" => $parent_item, "type" => "text/html",
|
||||
"href" => app::get_baseurl().'/display/'.$parent[0]['guid'],
|
||||
"dfrn:diaspora_guid" => $parent[0]['guid']);
|
||||
xml_add_element($doc, $entry, "thr:in-reply-to", "", $attributes);
|
||||
xml::add_element($doc, $entry, "thr:in-reply-to", "", $attributes);
|
||||
}
|
||||
|
||||
xml_add_element($doc, $entry, "id", $item["uri"]);
|
||||
xml_add_element($doc, $entry, "title", $item["title"]);
|
||||
xml::add_element($doc, $entry, "id", $item["uri"]);
|
||||
xml::add_element($doc, $entry, "title", $item["title"]);
|
||||
|
||||
xml_add_element($doc, $entry, "published", datetime_convert("UTC","UTC",$item["created"]."+00:00",ATOM_TIME));
|
||||
xml_add_element($doc, $entry, "updated", datetime_convert("UTC","UTC",$item["edited"]."+00:00",ATOM_TIME));
|
||||
xml::add_element($doc, $entry, "published", datetime_convert("UTC","UTC",$item["created"]."+00:00",ATOM_TIME));
|
||||
xml::add_element($doc, $entry, "updated", datetime_convert("UTC","UTC",$item["edited"]."+00:00",ATOM_TIME));
|
||||
|
||||
// "dfrn:env" is used to read the content
|
||||
xml_add_element($doc, $entry, "dfrn:env", base64url_encode($body, true));
|
||||
xml::add_element($doc, $entry, "dfrn:env", base64url_encode($body, true));
|
||||
|
||||
// The "content" field is not read by the receiver. We could remove it when the type is "text"
|
||||
// We keep it at the moment, maybe there is some old version that doesn't read "dfrn:env"
|
||||
xml_add_element($doc, $entry, "content", (($type === 'html') ? $htmlbody : $body), array("type" => $type));
|
||||
xml::add_element($doc, $entry, "content", (($type == 'html') ? $htmlbody : $body), array("type" => $type));
|
||||
|
||||
// We save this value in "plink". Maybe we should read it from there as well?
|
||||
xml_add_element($doc, $entry, "link", "", array("rel" => "alternate", "type" => "text/html",
|
||||
xml::add_element($doc, $entry, "link", "", array("rel" => "alternate", "type" => "text/html",
|
||||
"href" => app::get_baseurl()."/display/".$item["guid"]));
|
||||
|
||||
// "comment-allow" is some old fashioned stuff for old Friendica versions.
|
||||
// It is included in the rewritten code for completeness
|
||||
if ($comment)
|
||||
xml_add_element($doc, $entry, "dfrn:comment-allow", intval($item['last-child']));
|
||||
xml::add_element($doc, $entry, "dfrn:comment-allow", intval($item['last-child']));
|
||||
|
||||
if($item['location'])
|
||||
xml_add_element($doc, $entry, "dfrn:location", $item['location']);
|
||||
xml::add_element($doc, $entry, "dfrn:location", $item['location']);
|
||||
|
||||
if($item['coord'])
|
||||
xml_add_element($doc, $entry, "georss:point", $item['coord']);
|
||||
xml::add_element($doc, $entry, "georss:point", $item['coord']);
|
||||
|
||||
if(($item['private']) || strlen($item['allow_cid']) || strlen($item['allow_gid']) || strlen($item['deny_cid']) || strlen($item['deny_gid']))
|
||||
xml_add_element($doc, $entry, "dfrn:private", (($item['private']) ? $item['private'] : 1));
|
||||
xml::add_element($doc, $entry, "dfrn:private", (($item['private']) ? $item['private'] : 1));
|
||||
|
||||
if($item['extid'])
|
||||
xml_add_element($doc, $entry, "dfrn:extid", $item['extid']);
|
||||
xml::add_element($doc, $entry, "dfrn:extid", $item['extid']);
|
||||
|
||||
if($item['bookmark'])
|
||||
xml_add_element($doc, $entry, "dfrn:bookmark", "true");
|
||||
xml::add_element($doc, $entry, "dfrn:bookmark", "true");
|
||||
|
||||
if($item['app'])
|
||||
xml_add_element($doc, $entry, "statusnet:notice_info", "", array("local_id" => $item['id'], "source" => $item['app']));
|
||||
xml::add_element($doc, $entry, "statusnet:notice_info", "", array("local_id" => $item['id'], "source" => $item['app']));
|
||||
|
||||
xml_add_element($doc, $entry, "dfrn:diaspora_guid", $item["guid"]);
|
||||
xml::add_element($doc, $entry, "dfrn:diaspora_guid", $item["guid"]);
|
||||
|
||||
// The signed text contains the content in Markdown, the sender handle and the signatur for the content
|
||||
// It is needed for relayed comments to Diaspora.
|
||||
if($item['signed_text']) {
|
||||
$sign = base64_encode(json_encode(array('signed_text' => $item['signed_text'],'signature' => $item['signature'],'signer' => $item['signer'])));
|
||||
xml_add_element($doc, $entry, "dfrn:diaspora_signature", $sign);
|
||||
xml::add_element($doc, $entry, "dfrn:diaspora_signature", $sign);
|
||||
}
|
||||
|
||||
xml_add_element($doc, $entry, "activity:verb", construct_verb($item));
|
||||
xml::add_element($doc, $entry, "activity:verb", construct_verb($item));
|
||||
|
||||
if ($item['object-type'] != "")
|
||||
xml_add_element($doc, $entry, "activity:object-type", $item['object-type']);
|
||||
xml::add_element($doc, $entry, "activity:object-type", $item['object-type']);
|
||||
elseif ($item['id'] == $item['parent'])
|
||||
xml_add_element($doc, $entry, "activity:object-type", ACTIVITY_OBJ_NOTE);
|
||||
xml::add_element($doc, $entry, "activity:object-type", ACTIVITY_OBJ_NOTE);
|
||||
else
|
||||
xml_add_element($doc, $entry, "activity:object-type", ACTIVITY_OBJ_COMMENT);
|
||||
xml::add_element($doc, $entry, "activity:object-type", ACTIVITY_OBJ_COMMENT);
|
||||
|
||||
$actobj = self::create_activity($doc, "activity:object", $item['object']);
|
||||
if ($actobj)
|
||||
|
|
@ -815,7 +820,7 @@ class dfrn {
|
|||
if(count($tags)) {
|
||||
foreach($tags as $t)
|
||||
if (($type != 'html') OR ($t[0] != "@"))
|
||||
xml_add_element($doc, $entry, "category", "", array("scheme" => "X-DFRN:".$t[0].":".$t[1], "term" => $t[2]));
|
||||
xml::add_element($doc, $entry, "category", "", array("scheme" => "X-DFRN:".$t[0].":".$t[1], "term" => $t[2]));
|
||||
}
|
||||
|
||||
if(count($tags))
|
||||
|
|
@ -828,11 +833,11 @@ class dfrn {
|
|||
intval($owner["uid"]),
|
||||
dbesc(normalise_link($mention)));
|
||||
if ($r[0]["forum"] OR $r[0]["prv"])
|
||||
xml_add_element($doc, $entry, "link", "", array("rel" => "mentioned",
|
||||
xml::add_element($doc, $entry, "link", "", array("rel" => "mentioned",
|
||||
"ostatus:object-type" => ACTIVITY_OBJ_GROUP,
|
||||
"href" => $mention));
|
||||
else
|
||||
xml_add_element($doc, $entry, "link", "", array("rel" => "mentioned",
|
||||
xml::add_element($doc, $entry, "link", "", array("rel" => "mentioned",
|
||||
"ostatus:object-type" => ACTIVITY_OBJ_PERSON,
|
||||
"href" => $mention));
|
||||
}
|
||||
|
|
@ -1319,7 +1324,7 @@ class dfrn {
|
|||
$obj_element = $obj_doc->createElementNS(NAMESPACE_ATOM1, $element);
|
||||
|
||||
$activity_type = $xpath->query("activity:object-type/text()", $activity)->item(0)->nodeValue;
|
||||
xml_add_element($obj_doc, $obj_element, "type", $activity_type);
|
||||
xml::add_element($obj_doc, $obj_element, "type", $activity_type);
|
||||
|
||||
$id = $xpath->query("atom:id", $activity)->item(0);
|
||||
if (is_object($id))
|
||||
|
|
@ -1769,6 +1774,9 @@ class dfrn {
|
|||
* @return bool Should the processing of the entries be continued?
|
||||
*/
|
||||
private function process_verbs($entrytype, $importer, &$item, &$is_like) {
|
||||
|
||||
logger("Process verb ".$item["verb"]." and object-type ".$item["object-type"]." for entrytype ".$entrytype, LOGGER_DEBUG);
|
||||
|
||||
if (($entrytype == DFRN_TOP_LEVEL)) {
|
||||
// The filling of the the "contact" variable is done for legcy reasons
|
||||
// The functions below are partly used by ostatus.php as well - where we have this variable
|
||||
|
|
@ -1799,11 +1807,11 @@ class dfrn {
|
|||
return false;
|
||||
}
|
||||
} else {
|
||||
if(($item["verb"] === ACTIVITY_LIKE)
|
||||
|| ($item["verb"] === ACTIVITY_DISLIKE)
|
||||
|| ($item["verb"] === ACTIVITY_ATTEND)
|
||||
|| ($item["verb"] === ACTIVITY_ATTENDNO)
|
||||
|| ($item["verb"] === ACTIVITY_ATTENDMAYBE)) {
|
||||
if(($item["verb"] == ACTIVITY_LIKE)
|
||||
|| ($item["verb"] == ACTIVITY_DISLIKE)
|
||||
|| ($item["verb"] == ACTIVITY_ATTEND)
|
||||
|| ($item["verb"] == ACTIVITY_ATTENDNO)
|
||||
|| ($item["verb"] == ACTIVITY_ATTENDMAYBE)) {
|
||||
$is_like = true;
|
||||
$item["type"] = "activity";
|
||||
$item["gravity"] = GRAVITY_LIKE;
|
||||
|
|
@ -1829,7 +1837,7 @@ class dfrn {
|
|||
} else
|
||||
$is_like = false;
|
||||
|
||||
if(($item["verb"] === ACTIVITY_TAG) && ($item["object-type"] === ACTIVITY_OBJ_TAGTERM)) {
|
||||
if(($item["verb"] == ACTIVITY_TAG) && ($item["object-type"] == ACTIVITY_OBJ_TAGTERM)) {
|
||||
|
||||
$xo = parse_xml_string($item["object"],false);
|
||||
$xt = parse_xml_string($item["target"],false);
|
||||
|
|
@ -2018,14 +2026,28 @@ class dfrn {
|
|||
$categories = $xpath->query("atom:category", $entry);
|
||||
if ($categories) {
|
||||
foreach ($categories AS $category) {
|
||||
foreach($category->attributes AS $attributes)
|
||||
if ($attributes->name == "term") {
|
||||
$term = "";
|
||||
$scheme = "";
|
||||
foreach($category->attributes AS $attributes) {
|
||||
if ($attributes->name == "term")
|
||||
$term = $attributes->textContent;
|
||||
|
||||
if ($attributes->name == "scheme")
|
||||
$scheme = $attributes->textContent;
|
||||
}
|
||||
|
||||
if (($term != "") AND ($scheme != "")) {
|
||||
$parts = explode(":", $scheme);
|
||||
if ((count($parts) >= 4) AND (array_shift($parts) == "X-DFRN")) {
|
||||
$termhash = array_shift($parts);
|
||||
$termurl = implode(":", $parts);
|
||||
|
||||
if(strlen($item["tag"]))
|
||||
$item["tag"] .= ",";
|
||||
|
||||
$item["tag"] .= "#[url=".App::get_baseurl()."/search?tag=".$term."]".$term."[/url]";
|
||||
$item["tag"] .= $termhash."[url=".$termurl."]".$term."[/url]";
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -2243,15 +2265,17 @@ class dfrn {
|
|||
else
|
||||
return;
|
||||
|
||||
if($item["object-type"] === ACTIVITY_OBJ_EVENT) {
|
||||
if($item["object-type"] == ACTIVITY_OBJ_EVENT) {
|
||||
logger("Deleting event ".$item["event-id"], LOGGER_DEBUG);
|
||||
event_delete($item["event-id"]);
|
||||
}
|
||||
|
||||
if(($item["verb"] === ACTIVITY_TAG) && ($item["object-type"] === ACTIVITY_OBJ_TAGTERM)) {
|
||||
if(($item["verb"] == ACTIVITY_TAG) && ($item["object-type"] == ACTIVITY_OBJ_TAGTERM)) {
|
||||
|
||||
$xo = parse_xml_string($item["object"],false);
|
||||
$xt = parse_xml_string($item["target"],false);
|
||||
if($xt->type === ACTIVITY_OBJ_NOTE) {
|
||||
|
||||
if($xt->type == ACTIVITY_OBJ_NOTE) {
|
||||
$i = q("SELECT `id`, `contact-id`, `tag` FROM `item` WHERE `uri` = '%s' AND `uid` = %d LIMIT 1",
|
||||
dbesc($xt->id),
|
||||
intval($importer["importer_uid"])
|
||||
|
|
|
|||
5922
include/diaspora.php
5922
include/diaspora.php
|
|
@ -1,1663 +1,1122 @@
|
|||
<?php
|
||||
|
||||
/**
|
||||
* @file include/diaspora.php
|
||||
*
|
||||
* @todo GET /people/9aed8882b9f64896/stream
|
||||
* @brief The implementation of the diaspora protocol
|
||||
*
|
||||
* Checklist:
|
||||
*
|
||||
* Checked:
|
||||
* - send status
|
||||
* - send comment
|
||||
* - send like
|
||||
* - send mail
|
||||
* - send status retraction
|
||||
* - send comment retraction on own post
|
||||
* - send like retraction on own post
|
||||
* - send comment retraction on diaspora post
|
||||
* - send like retraction on diaspora post
|
||||
* - receive status
|
||||
* - receive reshare
|
||||
* - receive comment
|
||||
* - receive like
|
||||
* - receive connect request
|
||||
* - receive profile data
|
||||
* - receive mail
|
||||
* - receive comment retraction
|
||||
* - receive like retraction
|
||||
* - relay comment
|
||||
* - relay like
|
||||
* - relay comment retraction from diaspora
|
||||
* - relay comment retraction from friendica
|
||||
* - relay like retraction from diaspora
|
||||
* - relay like retraction from friendica
|
||||
* - send share
|
||||
*
|
||||
* Should work:
|
||||
* - receive account deletion
|
||||
* - send unshare
|
||||
*
|
||||
* Unchecked:
|
||||
*/
|
||||
|
||||
require_once('include/crypto.php');
|
||||
require_once('include/items.php');
|
||||
require_once('include/bb2diaspora.php');
|
||||
require_once('include/contact_selectors.php');
|
||||
require_once('include/queue_fn.php');
|
||||
require_once('include/lock.php');
|
||||
require_once('include/threads.php');
|
||||
require_once('mod/share.php');
|
||||
require_once('include/enotify.php');
|
||||
require_once("include/items.php");
|
||||
require_once("include/bb2diaspora.php");
|
||||
require_once("include/Scrape.php");
|
||||
require_once("include/Contact.php");
|
||||
require_once("include/Photo.php");
|
||||
require_once("include/socgraph.php");
|
||||
require_once("include/group.php");
|
||||
require_once("include/xml.php");
|
||||
require_once("include/datetime.php");
|
||||
require_once("include/queue_fn.php");
|
||||
|
||||
function diaspora_dispatch_public($msg) {
|
||||
/**
|
||||
* @brief This class contain functions to create and send Diaspora XML files
|
||||
*
|
||||
*/
|
||||
class diaspora {
|
||||
|
||||
$enabled = intval(get_config('system','diaspora_enabled'));
|
||||
if(! $enabled) {
|
||||
logger('mod-diaspora: disabled');
|
||||
return;
|
||||
}
|
||||
/**
|
||||
* @brief Return a list of relay servers
|
||||
*
|
||||
* This is an experimental Diaspora feature.
|
||||
*
|
||||
* @return array of relay servers
|
||||
*/
|
||||
public static function relay_list() {
|
||||
|
||||
// Use a dummy importer to import the data for the public copy
|
||||
$importer = array("uid" => 0, "page-flags" => PAGE_FREELOVE);
|
||||
$result = diaspora_dispatch($importer,$msg);
|
||||
logger("Dispatcher reported ".$result, LOGGER_DEBUG);
|
||||
$serverdata = get_config("system", "relay_server");
|
||||
if ($serverdata == "")
|
||||
return array();
|
||||
|
||||
// Now distribute it to the followers
|
||||
$r = q("SELECT `user`.* FROM `user` WHERE `user`.`uid` IN
|
||||
( SELECT `contact`.`uid` FROM `contact` WHERE `contact`.`network` = '%s' AND `contact`.`addr` = '%s' )
|
||||
AND `account_expired` = 0 AND `account_removed` = 0 ",
|
||||
dbesc(NETWORK_DIASPORA),
|
||||
dbesc($msg['author'])
|
||||
);
|
||||
if(count($r)) {
|
||||
foreach($r as $rr) {
|
||||
logger('diaspora_public: delivering to: ' . $rr['username']);
|
||||
diaspora_dispatch($rr,$msg);
|
||||
$relay = array();
|
||||
|
||||
$servers = explode(",", $serverdata);
|
||||
|
||||
foreach($servers AS $server) {
|
||||
$server = trim($server);
|
||||
$batch = $server."/receive/public";
|
||||
|
||||
$relais = q("SELECT `batch`, `id`, `name`,`network` FROM `contact` WHERE `uid` = 0 AND `batch` = '%s' LIMIT 1", dbesc($batch));
|
||||
|
||||
if (!$relais) {
|
||||
$addr = "relay@".str_replace("http://", "", normalise_link($server));
|
||||
|
||||
$r = q("INSERT INTO `contact` (`uid`, `created`, `name`, `nick`, `addr`, `url`, `nurl`, `batch`, `network`, `rel`, `blocked`, `pending`, `writable`, `name-date`, `uri-date`, `avatar-date`)
|
||||
VALUES (0, '%s', '%s', 'relay', '%s', '%s', '%s', '%s', '%s', %d, 0, 0, 1, '%s', '%s', '%s')",
|
||||
datetime_convert(),
|
||||
dbesc($addr),
|
||||
dbesc($addr),
|
||||
dbesc($server),
|
||||
dbesc(normalise_link($server)),
|
||||
dbesc($batch),
|
||||
dbesc(NETWORK_DIASPORA),
|
||||
intval(CONTACT_IS_FOLLOWER),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc(datetime_convert())
|
||||
);
|
||||
|
||||
$relais = q("SELECT `batch`, `id`, `name`,`network` FROM `contact` WHERE `uid` = 0 AND `batch` = '%s' LIMIT 1", dbesc($batch));
|
||||
if ($relais)
|
||||
$relay[] = $relais[0];
|
||||
} else
|
||||
$relay[] = $relais[0];
|
||||
}
|
||||
}
|
||||
else
|
||||
logger('diaspora_public: no subscribers for '.$msg["author"].' '.print_r($msg, true));
|
||||
}
|
||||
|
||||
|
||||
|
||||
function diaspora_dispatch($importer,$msg,$attempt=1) {
|
||||
|
||||
$ret = 0;
|
||||
|
||||
$enabled = intval(get_config('system','diaspora_enabled'));
|
||||
if(! $enabled) {
|
||||
logger('mod-diaspora: disabled');
|
||||
return;
|
||||
return $relay;
|
||||
}
|
||||
|
||||
// php doesn't like dashes in variable names
|
||||
/**
|
||||
* @brief repairs a signature that was double encoded
|
||||
*
|
||||
* The function is unused at the moment. It was copied from the old implementation.
|
||||
*
|
||||
* @param string $signature The signature
|
||||
* @param string $handle The handle of the signature owner
|
||||
* @param integer $level This value is only set inside this function to avoid endless loops
|
||||
*
|
||||
* @return string the repaired signature
|
||||
*/
|
||||
private function repair_signature($signature, $handle = "", $level = 1) {
|
||||
|
||||
$msg['message'] = str_replace(
|
||||
array('<activity_streams-photo>','</activity_streams-photo>'),
|
||||
array('<asphoto>','</asphoto>'),
|
||||
$msg['message']);
|
||||
if ($signature == "")
|
||||
return ($signature);
|
||||
|
||||
if (base64_encode(base64_decode(base64_decode($signature))) == base64_decode($signature)) {
|
||||
$signature = base64_decode($signature);
|
||||
logger("Repaired double encoded signature from Diaspora/Hubzilla handle ".$handle." - level ".$level, LOGGER_DEBUG);
|
||||
|
||||
$parsed_xml = parse_xml_string($msg['message'],false);
|
||||
|
||||
$xmlbase = $parsed_xml->post;
|
||||
|
||||
logger('diaspora_dispatch: ' . print_r($xmlbase,true), LOGGER_DEBUG);
|
||||
|
||||
|
||||
if($xmlbase->request) {
|
||||
$ret = diaspora_request($importer,$xmlbase->request);
|
||||
}
|
||||
elseif($xmlbase->status_message) {
|
||||
$ret = diaspora_post($importer,$xmlbase->status_message,$msg);
|
||||
}
|
||||
elseif($xmlbase->profile) {
|
||||
$ret = diaspora_profile($importer,$xmlbase->profile,$msg);
|
||||
}
|
||||
elseif($xmlbase->comment) {
|
||||
$ret = diaspora_comment($importer,$xmlbase->comment,$msg);
|
||||
}
|
||||
elseif($xmlbase->like) {
|
||||
$ret = diaspora_like($importer,$xmlbase->like,$msg);
|
||||
}
|
||||
elseif($xmlbase->asphoto) {
|
||||
$ret = diaspora_asphoto($importer,$xmlbase->asphoto,$msg);
|
||||
}
|
||||
elseif($xmlbase->reshare) {
|
||||
$ret = diaspora_reshare($importer,$xmlbase->reshare,$msg);
|
||||
}
|
||||
elseif($xmlbase->retraction) {
|
||||
$ret = diaspora_retraction($importer,$xmlbase->retraction,$msg);
|
||||
}
|
||||
elseif($xmlbase->signed_retraction) {
|
||||
$ret = diaspora_signed_retraction($importer,$xmlbase->signed_retraction,$msg);
|
||||
}
|
||||
elseif($xmlbase->relayable_retraction) {
|
||||
$ret = diaspora_signed_retraction($importer,$xmlbase->relayable_retraction,$msg);
|
||||
}
|
||||
elseif($xmlbase->photo) {
|
||||
$ret = diaspora_photo($importer,$xmlbase->photo,$msg,$attempt);
|
||||
}
|
||||
elseif($xmlbase->conversation) {
|
||||
$ret = diaspora_conversation($importer,$xmlbase->conversation,$msg);
|
||||
}
|
||||
elseif($xmlbase->message) {
|
||||
$ret = diaspora_message($importer,$xmlbase->message,$msg);
|
||||
}
|
||||
elseif($xmlbase->participation) {
|
||||
$ret = diaspora_participation($importer,$xmlbase->participation);
|
||||
}
|
||||
else {
|
||||
logger('diaspora_dispatch: unknown message type: ' . print_r($xmlbase,true));
|
||||
}
|
||||
return $ret;
|
||||
}
|
||||
|
||||
function diaspora_handle_from_contact($contact_id) {
|
||||
$handle = False;
|
||||
|
||||
logger("diaspora_handle_from_contact: contact id is " . $contact_id, LOGGER_DEBUG);
|
||||
|
||||
$r = q("SELECT network, addr, self, url, nick FROM contact WHERE id = %d",
|
||||
intval($contact_id)
|
||||
);
|
||||
if($r) {
|
||||
$contact = $r[0];
|
||||
|
||||
logger("diaspora_handle_from_contact: contact 'self' = " . $contact['self'] . " 'url' = " . $contact['url'], LOGGER_DEBUG);
|
||||
|
||||
if($contact['network'] === NETWORK_DIASPORA) {
|
||||
$handle = $contact['addr'];
|
||||
|
||||
// logger("diaspora_handle_from_contact: contact id is a Diaspora person, handle = " . $handle, LOGGER_DEBUG);
|
||||
// Do a recursive call to be able to fix even multiple levels
|
||||
if ($level < 10)
|
||||
$signature = self::repair_signature($signature, $handle, ++$level);
|
||||
}
|
||||
elseif(($contact['network'] === NETWORK_DFRN) || ($contact['self'] == 1)) {
|
||||
$baseurl_start = strpos($contact['url'],'://') + 3;
|
||||
$baseurl_length = strpos($contact['url'],'/profile') - $baseurl_start; // allows installations in a subdirectory--not sure how Diaspora will handle
|
||||
$baseurl = substr($contact['url'], $baseurl_start, $baseurl_length);
|
||||
$handle = $contact['nick'] . '@' . $baseurl;
|
||||
|
||||
// logger("diaspora_handle_from_contact: contact id is a DFRN person, handle = " . $handle, LOGGER_DEBUG);
|
||||
}
|
||||
return($signature);
|
||||
}
|
||||
|
||||
return $handle;
|
||||
}
|
||||
/**
|
||||
* @brief: Decodes incoming Diaspora message
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param string $xml urldecoded Diaspora salmon
|
||||
*
|
||||
* @return array
|
||||
* 'message' -> decoded Diaspora XML message
|
||||
* 'author' -> author diaspora handle
|
||||
* 'key' -> author public key (converted to pkcs#8)
|
||||
*/
|
||||
public static function decode($importer, $xml) {
|
||||
|
||||
function diaspora_get_contact_by_handle($uid,$handle) {
|
||||
$r = q("SELECT * FROM `contact` WHERE `network` = '%s' AND `uid` = %d AND `addr` = '%s' LIMIT 1",
|
||||
dbesc(NETWORK_DIASPORA),
|
||||
intval($uid),
|
||||
dbesc($handle)
|
||||
);
|
||||
if($r && count($r))
|
||||
return $r[0];
|
||||
$public = false;
|
||||
$basedom = parse_xml_string($xml);
|
||||
|
||||
$handle_parts = explode("@", $handle);
|
||||
$nurl_sql = '%%://' . $handle_parts[1] . '%%/profile/' . $handle_parts[0];
|
||||
$r = q("SELECT * FROM contact WHERE network = '%s' AND uid = %d AND nurl LIKE '%s' LIMIT 1",
|
||||
dbesc(NETWORK_DFRN),
|
||||
intval($uid),
|
||||
dbesc($nurl_sql)
|
||||
);
|
||||
if($r && count($r))
|
||||
return $r[0];
|
||||
if (!is_object($basedom))
|
||||
return false;
|
||||
|
||||
return false;
|
||||
}
|
||||
$children = $basedom->children('https://joindiaspora.com/protocol');
|
||||
|
||||
function find_diaspora_person_by_handle($handle) {
|
||||
if($children->header) {
|
||||
$public = true;
|
||||
$author_link = str_replace('acct:','',$children->header->author_id);
|
||||
} else {
|
||||
|
||||
$person = false;
|
||||
$update = false;
|
||||
$got_lock = false;
|
||||
$encrypted_header = json_decode(base64_decode($children->encrypted_header));
|
||||
|
||||
$endlessloop = 0;
|
||||
$maxloops = 10;
|
||||
$encrypted_aes_key_bundle = base64_decode($encrypted_header->aes_key);
|
||||
$ciphertext = base64_decode($encrypted_header->ciphertext);
|
||||
|
||||
do {
|
||||
$r = q("select * from fcontact where network = '%s' and addr = '%s' limit 1",
|
||||
$outer_key_bundle = '';
|
||||
openssl_private_decrypt($encrypted_aes_key_bundle,$outer_key_bundle,$importer['prvkey']);
|
||||
|
||||
$j_outer_key_bundle = json_decode($outer_key_bundle);
|
||||
|
||||
$outer_iv = base64_decode($j_outer_key_bundle->iv);
|
||||
$outer_key = base64_decode($j_outer_key_bundle->key);
|
||||
|
||||
$decrypted = mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $outer_key, $ciphertext, MCRYPT_MODE_CBC, $outer_iv);
|
||||
|
||||
|
||||
$decrypted = pkcs5_unpad($decrypted);
|
||||
|
||||
logger('decrypted: '.$decrypted, LOGGER_DEBUG);
|
||||
$idom = parse_xml_string($decrypted,false);
|
||||
|
||||
$inner_iv = base64_decode($idom->iv);
|
||||
$inner_aes_key = base64_decode($idom->aes_key);
|
||||
|
||||
$author_link = str_replace('acct:','',$idom->author_id);
|
||||
}
|
||||
|
||||
$dom = $basedom->children(NAMESPACE_SALMON_ME);
|
||||
|
||||
// figure out where in the DOM tree our data is hiding
|
||||
|
||||
if($dom->provenance->data)
|
||||
$base = $dom->provenance;
|
||||
elseif($dom->env->data)
|
||||
$base = $dom->env;
|
||||
elseif($dom->data)
|
||||
$base = $dom;
|
||||
|
||||
if (!$base) {
|
||||
logger('unable to locate salmon data in xml');
|
||||
http_status_exit(400);
|
||||
}
|
||||
|
||||
|
||||
// Stash the signature away for now. We have to find their key or it won't be good for anything.
|
||||
$signature = base64url_decode($base->sig);
|
||||
|
||||
// unpack the data
|
||||
|
||||
// strip whitespace so our data element will return to one big base64 blob
|
||||
$data = str_replace(array(" ","\t","\r","\n"),array("","","",""),$base->data);
|
||||
|
||||
|
||||
// stash away some other stuff for later
|
||||
|
||||
$type = $base->data[0]->attributes()->type[0];
|
||||
$keyhash = $base->sig[0]->attributes()->keyhash[0];
|
||||
$encoding = $base->encoding;
|
||||
$alg = $base->alg;
|
||||
|
||||
|
||||
$signed_data = $data.'.'.base64url_encode($type).'.'.base64url_encode($encoding).'.'.base64url_encode($alg);
|
||||
|
||||
|
||||
// decode the data
|
||||
$data = base64url_decode($data);
|
||||
|
||||
|
||||
if($public)
|
||||
$inner_decrypted = $data;
|
||||
else {
|
||||
|
||||
// Decode the encrypted blob
|
||||
|
||||
$inner_encrypted = base64_decode($data);
|
||||
$inner_decrypted = mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $inner_aes_key, $inner_encrypted, MCRYPT_MODE_CBC, $inner_iv);
|
||||
$inner_decrypted = pkcs5_unpad($inner_decrypted);
|
||||
}
|
||||
|
||||
if (!$author_link) {
|
||||
logger('Could not retrieve author URI.');
|
||||
http_status_exit(400);
|
||||
}
|
||||
// Once we have the author URI, go to the web and try to find their public key
|
||||
// (first this will look it up locally if it is in the fcontact cache)
|
||||
// This will also convert diaspora public key from pkcs#1 to pkcs#8
|
||||
|
||||
logger('Fetching key for '.$author_link);
|
||||
$key = self::key($author_link);
|
||||
|
||||
if (!$key) {
|
||||
logger('Could not retrieve author key.');
|
||||
http_status_exit(400);
|
||||
}
|
||||
|
||||
$verify = rsa_verify($signed_data,$signature,$key);
|
||||
|
||||
if (!$verify) {
|
||||
logger('Message did not verify. Discarding.');
|
||||
http_status_exit(400);
|
||||
}
|
||||
|
||||
logger('Message verified.');
|
||||
|
||||
return array('message' => (string)$inner_decrypted,
|
||||
'author' => unxmlify($author_link),
|
||||
'key' => (string)$key);
|
||||
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @brief Dispatches public messages and find the fitting receivers
|
||||
*
|
||||
* @param array $msg The post that will be dispatched
|
||||
*
|
||||
* @return int The message id of the generated message, "true" or "false" if there was an error
|
||||
*/
|
||||
public static function dispatch_public($msg) {
|
||||
|
||||
$enabled = intval(get_config("system", "diaspora_enabled"));
|
||||
if (!$enabled) {
|
||||
logger("diaspora is disabled");
|
||||
return false;
|
||||
}
|
||||
|
||||
// Use a dummy importer to import the data for the public copy
|
||||
$importer = array("uid" => 0, "page-flags" => PAGE_FREELOVE);
|
||||
$message_id = self::dispatch($importer,$msg);
|
||||
|
||||
// Now distribute it to the followers
|
||||
$r = q("SELECT `user`.* FROM `user` WHERE `user`.`uid` IN
|
||||
(SELECT `contact`.`uid` FROM `contact` WHERE `contact`.`network` = '%s' AND `contact`.`addr` = '%s')
|
||||
AND NOT `account_expired` AND NOT `account_removed`",
|
||||
dbesc(NETWORK_DIASPORA),
|
||||
dbesc($msg["author"])
|
||||
);
|
||||
if($r) {
|
||||
foreach($r as $rr) {
|
||||
logger("delivering to: ".$rr["username"]);
|
||||
self::dispatch($rr,$msg);
|
||||
}
|
||||
} else
|
||||
logger("No subscribers for ".$msg["author"]." ".print_r($msg, true));
|
||||
|
||||
return $message_id;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Dispatches the different message types to the different functions
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param array $msg The post that will be dispatched
|
||||
*
|
||||
* @return int The message id of the generated message, "true" or "false" if there was an error
|
||||
*/
|
||||
public static function dispatch($importer, $msg) {
|
||||
|
||||
// The sender is the handle of the contact that sent the message.
|
||||
// This will often be different with relayed messages (for example "like" and "comment")
|
||||
$sender = $msg["author"];
|
||||
|
||||
if (!diaspora::valid_posting($msg, $fields)) {
|
||||
logger("Invalid posting");
|
||||
return false;
|
||||
}
|
||||
|
||||
$type = $fields->getName();
|
||||
|
||||
logger("Received message type ".$type." from ".$sender." for user ".$importer["uid"], LOGGER_DEBUG);
|
||||
|
||||
switch ($type) {
|
||||
case "account_deletion":
|
||||
return self::receive_account_deletion($importer, $fields);
|
||||
|
||||
case "comment":
|
||||
return self::receive_comment($importer, $sender, $fields, $msg["message"]);
|
||||
|
||||
case "contact":
|
||||
return self::receive_contact_request($importer, $fields);
|
||||
|
||||
case "conversation":
|
||||
return self::receive_conversation($importer, $msg, $fields);
|
||||
|
||||
case "like":
|
||||
return self::receive_like($importer, $sender, $fields);
|
||||
|
||||
case "message":
|
||||
return self::receive_message($importer, $fields);
|
||||
|
||||
case "participation": // Not implemented
|
||||
return self::receive_participation($importer, $fields);
|
||||
|
||||
case "photo": // Not implemented
|
||||
return self::receive_photo($importer, $fields);
|
||||
|
||||
case "poll_participation": // Not implemented
|
||||
return self::receive_poll_participation($importer, $fields);
|
||||
|
||||
case "profile":
|
||||
return self::receive_profile($importer, $fields);
|
||||
|
||||
case "reshare":
|
||||
return self::receive_reshare($importer, $fields, $msg["message"]);
|
||||
|
||||
case "retraction":
|
||||
return self::receive_retraction($importer, $sender, $fields);
|
||||
|
||||
case "status_message":
|
||||
return self::receive_status_message($importer, $fields, $msg["message"]);
|
||||
|
||||
default:
|
||||
logger("Unknown message type ".$type);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Checks if a posting is valid and fetches the data fields.
|
||||
*
|
||||
* This function does not only check the signature.
|
||||
* It also does the conversion between the old and the new diaspora format.
|
||||
*
|
||||
* @param array $msg Array with the XML, the sender handle and the sender signature
|
||||
* @param object $fields SimpleXML object that contains the posting when it is valid
|
||||
*
|
||||
* @return bool Is the posting valid?
|
||||
*/
|
||||
private function valid_posting($msg, &$fields) {
|
||||
|
||||
$data = parse_xml_string($msg["message"], false);
|
||||
|
||||
if (!is_object($data))
|
||||
return false;
|
||||
|
||||
$first_child = $data->getName();
|
||||
|
||||
// Is this the new or the old version?
|
||||
if ($data->getName() == "XML") {
|
||||
$oldXML = true;
|
||||
foreach ($data->post->children() as $child)
|
||||
$element = $child;
|
||||
} else {
|
||||
$oldXML = false;
|
||||
$element = $data;
|
||||
}
|
||||
|
||||
$type = $element->getName();
|
||||
$orig_type = $type;
|
||||
|
||||
// All retractions are handled identically from now on.
|
||||
// In the new version there will only be "retraction".
|
||||
if (in_array($type, array("signed_retraction", "relayable_retraction")))
|
||||
$type = "retraction";
|
||||
|
||||
if ($type == "request")
|
||||
$type = "contact";
|
||||
|
||||
$fields = new SimpleXMLElement("<".$type."/>");
|
||||
|
||||
$signed_data = "";
|
||||
|
||||
foreach ($element->children() AS $fieldname => $entry) {
|
||||
if ($oldXML) {
|
||||
// Translation for the old XML structure
|
||||
if ($fieldname == "diaspora_handle")
|
||||
$fieldname = "author";
|
||||
|
||||
if ($fieldname == "participant_handles")
|
||||
$fieldname = "participants";
|
||||
|
||||
if (in_array($type, array("like", "participation"))) {
|
||||
if ($fieldname == "target_type")
|
||||
$fieldname = "parent_type";
|
||||
}
|
||||
|
||||
if ($fieldname == "sender_handle")
|
||||
$fieldname = "author";
|
||||
|
||||
if ($fieldname == "recipient_handle")
|
||||
$fieldname = "recipient";
|
||||
|
||||
if ($fieldname == "root_diaspora_id")
|
||||
$fieldname = "root_author";
|
||||
|
||||
if ($type == "retraction") {
|
||||
if ($fieldname == "post_guid")
|
||||
$fieldname = "target_guid";
|
||||
|
||||
if ($fieldname == "type")
|
||||
$fieldname = "target_type";
|
||||
}
|
||||
}
|
||||
|
||||
if ($fieldname == "author_signature")
|
||||
$author_signature = base64_decode($entry);
|
||||
elseif ($fieldname == "parent_author_signature")
|
||||
$parent_author_signature = base64_decode($entry);
|
||||
elseif ($fieldname != "target_author_signature") {
|
||||
if ($signed_data != "") {
|
||||
$signed_data .= ";";
|
||||
$signed_data_parent .= ";";
|
||||
}
|
||||
|
||||
$signed_data .= $entry;
|
||||
}
|
||||
if (!in_array($fieldname, array("parent_author_signature", "target_author_signature")) OR
|
||||
($orig_type == "relayable_retraction"))
|
||||
xml::copy($entry, $fields, $fieldname);
|
||||
}
|
||||
|
||||
// This is something that shouldn't happen at all.
|
||||
if (in_array($type, array("status_message", "reshare", "profile")))
|
||||
if ($msg["author"] != $fields->author) {
|
||||
logger("Message handle is not the same as envelope sender. Quitting this message.");
|
||||
return false;
|
||||
}
|
||||
|
||||
// Only some message types have signatures. So we quit here for the other types.
|
||||
if (!in_array($type, array("comment", "message", "like")))
|
||||
return true;
|
||||
|
||||
// No author_signature? This is a must, so we quit.
|
||||
if (!isset($author_signature))
|
||||
return false;
|
||||
|
||||
if (isset($parent_author_signature)) {
|
||||
$key = self::key($msg["author"]);
|
||||
|
||||
if (!rsa_verify($signed_data, $parent_author_signature, $key, "sha256"))
|
||||
return false;
|
||||
}
|
||||
|
||||
$key = self::key($fields->author);
|
||||
|
||||
return rsa_verify($signed_data, $author_signature, $key, "sha256");
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Fetches the public key for a given handle
|
||||
*
|
||||
* @param string $handle The handle
|
||||
*
|
||||
* @return string The public key
|
||||
*/
|
||||
private function key($handle) {
|
||||
$handle = strval($handle);
|
||||
|
||||
logger("Fetching diaspora key for: ".$handle);
|
||||
|
||||
$r = self::person_by_handle($handle);
|
||||
if($r)
|
||||
return $r["pubkey"];
|
||||
|
||||
return "";
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Fetches data for a given handle
|
||||
*
|
||||
* @param string $handle The handle
|
||||
*
|
||||
* @return array the queried data
|
||||
*/
|
||||
private function person_by_handle($handle) {
|
||||
|
||||
$r = q("SELECT * FROM `fcontact` WHERE `network` = '%s' AND `addr` = '%s' LIMIT 1",
|
||||
dbesc(NETWORK_DIASPORA),
|
||||
dbesc($handle)
|
||||
);
|
||||
if(count($r)) {
|
||||
if ($r) {
|
||||
$person = $r[0];
|
||||
logger('find_diaspora_person_by handle: in cache ' . print_r($r,true), LOGGER_DEBUG);
|
||||
logger("In cache ".print_r($r,true), LOGGER_DEBUG);
|
||||
|
||||
// update record occasionally so it doesn't get stale
|
||||
$d = strtotime($person['updated'] . ' +00:00');
|
||||
if($d < strtotime('now - 14 days'))
|
||||
$d = strtotime($person["updated"]." +00:00");
|
||||
if ($d < strtotime("now - 14 days"))
|
||||
$update = true;
|
||||
}
|
||||
|
||||
if (!$person OR $update) {
|
||||
logger("create or refresh", LOGGER_DEBUG);
|
||||
$r = probe_url($handle, PROBE_DIASPORA);
|
||||
|
||||
// FETCHING PERSON INFORMATION FROM REMOTE SERVER
|
||||
//
|
||||
// If the person isn't in our 'fcontact' table, or if he/she is but
|
||||
// his/her information hasn't been updated for more than 14 days, then
|
||||
// we want to fetch the person's information from the remote server.
|
||||
//
|
||||
// Note that $person isn't changed by this block of code unless the
|
||||
// person's information has been successfully fetched from the remote
|
||||
// server. So if $person was 'false' to begin with (because he/she wasn't
|
||||
// in the local cache), it'll stay false, and if $person held the local
|
||||
// cache information to begin with, it'll keep that information. That way
|
||||
// if there's a problem with the remote fetch, we can at least use our
|
||||
// cached information--it's better than nothing.
|
||||
|
||||
if((! $person) || ($update)) {
|
||||
// Lock the function to prevent race conditions if multiple items
|
||||
// come in at the same time from a person who doesn't exist in
|
||||
// fcontact
|
||||
//
|
||||
// Don't loop forever. On the last loop, try to create the contact
|
||||
// whether the function is locked or not. Maybe the locking thread
|
||||
// has died or something. At any rate, a duplicate in 'fcontact'
|
||||
// is a much smaller problem than a deadlocked thread
|
||||
$got_lock = lock_function('find_diaspora_person_by_handle', false);
|
||||
if(($endlessloop + 1) >= $maxloops)
|
||||
$got_lock = true;
|
||||
|
||||
if($got_lock) {
|
||||
logger('find_diaspora_person_by_handle: create or refresh', LOGGER_DEBUG);
|
||||
require_once('include/Scrape.php');
|
||||
$r = probe_url($handle, PROBE_DIASPORA);
|
||||
|
||||
// Note that Friendica contacts can return a "Diaspora person"
|
||||
// if Diaspora connectivity is enabled on their server
|
||||
if((count($r)) && ($r['network'] === NETWORK_DIASPORA)) {
|
||||
add_fcontact($r,$update);
|
||||
$person = ($r);
|
||||
}
|
||||
|
||||
unlock_function('find_diaspora_person_by_handle');
|
||||
}
|
||||
else {
|
||||
logger('find_diaspora_person_by_handle: couldn\'t lock function', LOGGER_DEBUG);
|
||||
if(! $person)
|
||||
block_on_function_lock('find_diaspora_person_by_handle');
|
||||
// Note that Friendica contacts will return a "Diaspora person"
|
||||
// if Diaspora connectivity is enabled on their server
|
||||
if ($r AND ($r["network"] === NETWORK_DIASPORA)) {
|
||||
self::add_fcontact($r, $update);
|
||||
$person = $r;
|
||||
}
|
||||
}
|
||||
} while((! $person) && (! $got_lock) && (++$endlessloop < $maxloops));
|
||||
// We need to try again if the person wasn't in 'fcontact' but the function was locked.
|
||||
// The fact that the function was locked may mean that another process was creating the
|
||||
// person's record. It could also mean another process was creating or updating an unrelated
|
||||
// person.
|
||||
//
|
||||
// At any rate, we need to keep trying until we've either got the person or had a chance to
|
||||
// try to fetch his/her remote information. But we don't want to block on locking the
|
||||
// function, because if the other process is creating the record, then when we acquire the lock
|
||||
// we'll dive right into creating another, duplicate record. We DO want to at least wait
|
||||
// until the lock is released, so we don't flood the database with requests.
|
||||
//
|
||||
// If the person was in the 'fcontact' table, don't try again. It's not worth the time, since
|
||||
// we do have some information for the person
|
||||
|
||||
return $person;
|
||||
}
|
||||
|
||||
|
||||
function get_diaspora_key($uri) {
|
||||
logger('Fetching diaspora key for: ' . $uri);
|
||||
|
||||
$r = find_diaspora_person_by_handle($uri);
|
||||
if($r)
|
||||
return $r['pubkey'];
|
||||
return '';
|
||||
}
|
||||
|
||||
|
||||
function diaspora_pubmsg_build($msg,$user,$contact,$prvkey,$pubkey) {
|
||||
$a = get_app();
|
||||
|
||||
logger('diaspora_pubmsg_build: ' . $msg, LOGGER_DATA);
|
||||
|
||||
|
||||
$handle = $user['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3);
|
||||
|
||||
// $b64_data = base64_encode($msg);
|
||||
// $b64url_data = base64url_encode($b64_data);
|
||||
|
||||
$b64url_data = base64url_encode($msg);
|
||||
|
||||
$data = str_replace(array("\n","\r"," ","\t"),array('','','',''),$b64url_data);
|
||||
|
||||
$type = 'application/xml';
|
||||
$encoding = 'base64url';
|
||||
$alg = 'RSA-SHA256';
|
||||
|
||||
$signable_data = $data . '.' . base64url_encode($type) . '.'
|
||||
. base64url_encode($encoding) . '.' . base64url_encode($alg) ;
|
||||
|
||||
$signature = rsa_sign($signable_data,$prvkey);
|
||||
$sig = base64url_encode($signature);
|
||||
|
||||
$magic_env = <<< EOT
|
||||
<?xml version='1.0' encoding='UTF-8'?>
|
||||
<diaspora xmlns="https://joindiaspora.com/protocol" xmlns:me="http://salmon-protocol.org/ns/magic-env" >
|
||||
<header>
|
||||
<author_id>$handle</author_id>
|
||||
</header>
|
||||
<me:env>
|
||||
<me:encoding>base64url</me:encoding>
|
||||
<me:alg>RSA-SHA256</me:alg>
|
||||
<me:data type="application/xml">$data</me:data>
|
||||
<me:sig>$sig</me:sig>
|
||||
</me:env>
|
||||
</diaspora>
|
||||
EOT;
|
||||
|
||||
logger('diaspora_pubmsg_build: magic_env: ' . $magic_env, LOGGER_DATA);
|
||||
return $magic_env;
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
function diaspora_msg_build($msg,$user,$contact,$prvkey,$pubkey,$public = false) {
|
||||
$a = get_app();
|
||||
|
||||
if($public)
|
||||
return diaspora_pubmsg_build($msg,$user,$contact,$prvkey,$pubkey);
|
||||
|
||||
logger('diaspora_msg_build: ' . $msg, LOGGER_DATA);
|
||||
|
||||
// without a public key nothing will work
|
||||
|
||||
if(! $pubkey) {
|
||||
logger('diaspora_msg_build: pubkey missing: contact id: ' . $contact['id']);
|
||||
return '';
|
||||
return $person;
|
||||
}
|
||||
|
||||
$inner_aes_key = random_string(32);
|
||||
$b_inner_aes_key = base64_encode($inner_aes_key);
|
||||
$inner_iv = random_string(16);
|
||||
$b_inner_iv = base64_encode($inner_iv);
|
||||
/**
|
||||
* @brief Updates the fcontact table
|
||||
*
|
||||
* @param array $arr The fcontact data
|
||||
* @param bool $update Update or insert?
|
||||
*
|
||||
* @return string The id of the fcontact entry
|
||||
*/
|
||||
private function add_fcontact($arr, $update = false) {
|
||||
|
||||
$outer_aes_key = random_string(32);
|
||||
$b_outer_aes_key = base64_encode($outer_aes_key);
|
||||
$outer_iv = random_string(16);
|
||||
$b_outer_iv = base64_encode($outer_iv);
|
||||
|
||||
$handle = $user['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3);
|
||||
|
||||
$padded_data = pkcs5_pad($msg,16);
|
||||
$inner_encrypted = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $inner_aes_key, $padded_data, MCRYPT_MODE_CBC, $inner_iv);
|
||||
|
||||
$b64_data = base64_encode($inner_encrypted);
|
||||
|
||||
|
||||
$b64url_data = base64url_encode($b64_data);
|
||||
$data = str_replace(array("\n","\r"," ","\t"),array('','','',''),$b64url_data);
|
||||
|
||||
$type = 'application/xml';
|
||||
$encoding = 'base64url';
|
||||
$alg = 'RSA-SHA256';
|
||||
|
||||
$signable_data = $data . '.' . base64url_encode($type) . '.'
|
||||
. base64url_encode($encoding) . '.' . base64url_encode($alg) ;
|
||||
|
||||
$signature = rsa_sign($signable_data,$prvkey);
|
||||
$sig = base64url_encode($signature);
|
||||
|
||||
$decrypted_header = <<< EOT
|
||||
<decrypted_header>
|
||||
<iv>$b_inner_iv</iv>
|
||||
<aes_key>$b_inner_aes_key</aes_key>
|
||||
<author_id>$handle</author_id>
|
||||
</decrypted_header>
|
||||
EOT;
|
||||
|
||||
$decrypted_header = pkcs5_pad($decrypted_header,16);
|
||||
|
||||
$ciphertext = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $outer_aes_key, $decrypted_header, MCRYPT_MODE_CBC, $outer_iv);
|
||||
|
||||
$outer_json = json_encode(array('iv' => $b_outer_iv,'key' => $b_outer_aes_key));
|
||||
|
||||
$encrypted_outer_key_bundle = '';
|
||||
openssl_public_encrypt($outer_json,$encrypted_outer_key_bundle,$pubkey);
|
||||
|
||||
$b64_encrypted_outer_key_bundle = base64_encode($encrypted_outer_key_bundle);
|
||||
|
||||
logger('outer_bundle: ' . $b64_encrypted_outer_key_bundle . ' key: ' . $pubkey, LOGGER_DATA);
|
||||
|
||||
$encrypted_header_json_object = json_encode(array('aes_key' => base64_encode($encrypted_outer_key_bundle),
|
||||
'ciphertext' => base64_encode($ciphertext)));
|
||||
$cipher_json = base64_encode($encrypted_header_json_object);
|
||||
|
||||
$encrypted_header = '<encrypted_header>' . $cipher_json . '</encrypted_header>';
|
||||
|
||||
$magic_env = <<< EOT
|
||||
<?xml version='1.0' encoding='UTF-8'?>
|
||||
<diaspora xmlns="https://joindiaspora.com/protocol" xmlns:me="http://salmon-protocol.org/ns/magic-env" >
|
||||
$encrypted_header
|
||||
<me:env>
|
||||
<me:encoding>base64url</me:encoding>
|
||||
<me:alg>RSA-SHA256</me:alg>
|
||||
<me:data type="application/xml">$data</me:data>
|
||||
<me:sig>$sig</me:sig>
|
||||
</me:env>
|
||||
</diaspora>
|
||||
EOT;
|
||||
|
||||
logger('diaspora_msg_build: magic_env: ' . $magic_env, LOGGER_DATA);
|
||||
return $magic_env;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* diaspora_decode($importer,$xml)
|
||||
* array $importer -> from user table
|
||||
* string $xml -> urldecoded Diaspora salmon
|
||||
*
|
||||
* Returns array
|
||||
* 'message' -> decoded Diaspora XML message
|
||||
* 'author' -> author diaspora handle
|
||||
* 'key' -> author public key (converted to pkcs#8)
|
||||
*
|
||||
* Author and key are used elsewhere to save a lookup for verifying replies and likes
|
||||
*/
|
||||
|
||||
|
||||
function diaspora_decode($importer,$xml) {
|
||||
|
||||
$public = false;
|
||||
$basedom = parse_xml_string($xml);
|
||||
|
||||
$children = $basedom->children('https://joindiaspora.com/protocol');
|
||||
|
||||
if($children->header) {
|
||||
$public = true;
|
||||
$author_link = str_replace('acct:','',$children->header->author_id);
|
||||
}
|
||||
else {
|
||||
|
||||
$encrypted_header = json_decode(base64_decode($children->encrypted_header));
|
||||
|
||||
$encrypted_aes_key_bundle = base64_decode($encrypted_header->aes_key);
|
||||
$ciphertext = base64_decode($encrypted_header->ciphertext);
|
||||
|
||||
$outer_key_bundle = '';
|
||||
openssl_private_decrypt($encrypted_aes_key_bundle,$outer_key_bundle,$importer['prvkey']);
|
||||
|
||||
$j_outer_key_bundle = json_decode($outer_key_bundle);
|
||||
|
||||
$outer_iv = base64_decode($j_outer_key_bundle->iv);
|
||||
$outer_key = base64_decode($j_outer_key_bundle->key);
|
||||
|
||||
$decrypted = mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $outer_key, $ciphertext, MCRYPT_MODE_CBC, $outer_iv);
|
||||
|
||||
|
||||
$decrypted = pkcs5_unpad($decrypted);
|
||||
|
||||
/**
|
||||
* $decrypted now contains something like
|
||||
*
|
||||
* <decrypted_header>
|
||||
* <iv>8e+G2+ET8l5BPuW0sVTnQw==</iv>
|
||||
* <aes_key>UvSMb4puPeB14STkcDWq+4QE302Edu15oaprAQSkLKU=</aes_key>
|
||||
|
||||
***** OBSOLETE
|
||||
|
||||
* <author>
|
||||
* <name>Ryan Hughes</name>
|
||||
* <uri>acct:galaxor@diaspora.pirateship.org</uri>
|
||||
* </author>
|
||||
|
||||
***** CURRENT
|
||||
|
||||
* <author_id>galaxor@diaspora.priateship.org</author_id>
|
||||
|
||||
***** END DIFFS
|
||||
|
||||
* </decrypted_header>
|
||||
*/
|
||||
|
||||
logger('decrypted: ' . $decrypted, LOGGER_DEBUG);
|
||||
$idom = parse_xml_string($decrypted,false);
|
||||
|
||||
$inner_iv = base64_decode($idom->iv);
|
||||
$inner_aes_key = base64_decode($idom->aes_key);
|
||||
|
||||
$author_link = str_replace('acct:','',$idom->author_id);
|
||||
if($update) {
|
||||
$r = q("UPDATE `fcontact` SET
|
||||
`name` = '%s',
|
||||
`photo` = '%s',
|
||||
`request` = '%s',
|
||||
`nick` = '%s',
|
||||
`addr` = '%s',
|
||||
`batch` = '%s',
|
||||
`notify` = '%s',
|
||||
`poll` = '%s',
|
||||
`confirm` = '%s',
|
||||
`alias` = '%s',
|
||||
`pubkey` = '%s',
|
||||
`updated` = '%s'
|
||||
WHERE `url` = '%s' AND `network` = '%s'",
|
||||
dbesc($arr["name"]),
|
||||
dbesc($arr["photo"]),
|
||||
dbesc($arr["request"]),
|
||||
dbesc($arr["nick"]),
|
||||
dbesc($arr["addr"]),
|
||||
dbesc($arr["batch"]),
|
||||
dbesc($arr["notify"]),
|
||||
dbesc($arr["poll"]),
|
||||
dbesc($arr["confirm"]),
|
||||
dbesc($arr["alias"]),
|
||||
dbesc($arr["pubkey"]),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc($arr["url"]),
|
||||
dbesc($arr["network"])
|
||||
);
|
||||
} else {
|
||||
$r = q("INSERT INTO `fcontact` (`url`,`name`,`photo`,`request`,`nick`,`addr`,
|
||||
`batch`, `notify`,`poll`,`confirm`,`network`,`alias`,`pubkey`,`updated`)
|
||||
VALUES ('%s','%s','%s','%s','%s','%s','%s','%s','%s','%s','%s','%s','%s','%s')",
|
||||
dbesc($arr["url"]),
|
||||
dbesc($arr["name"]),
|
||||
dbesc($arr["photo"]),
|
||||
dbesc($arr["request"]),
|
||||
dbesc($arr["nick"]),
|
||||
dbesc($arr["addr"]),
|
||||
dbesc($arr["batch"]),
|
||||
dbesc($arr["notify"]),
|
||||
dbesc($arr["poll"]),
|
||||
dbesc($arr["confirm"]),
|
||||
dbesc($arr["network"]),
|
||||
dbesc($arr["alias"]),
|
||||
dbesc($arr["pubkey"]),
|
||||
dbesc(datetime_convert())
|
||||
);
|
||||
}
|
||||
|
||||
return $r;
|
||||
}
|
||||
|
||||
$dom = $basedom->children(NAMESPACE_SALMON_ME);
|
||||
/**
|
||||
* @brief get a handle (user@domain.tld) from a given contact id or gcontact id
|
||||
*
|
||||
* @param int $contact_id The id in the contact table
|
||||
* @param int $gcontact_id The id in the gcontact table
|
||||
*
|
||||
* @return string the handle
|
||||
*/
|
||||
public static function handle_from_contact($contact_id, $gcontact_id = 0) {
|
||||
$handle = False;
|
||||
|
||||
// figure out where in the DOM tree our data is hiding
|
||||
logger("contact id is ".$contact_id." - gcontact id is ".$gcontact_id, LOGGER_DEBUG);
|
||||
|
||||
if($dom->provenance->data)
|
||||
$base = $dom->provenance;
|
||||
elseif($dom->env->data)
|
||||
$base = $dom->env;
|
||||
elseif($dom->data)
|
||||
$base = $dom;
|
||||
if ($gcontact_id != 0) {
|
||||
$r = q("SELECT `addr` FROM `gcontact` WHERE `id` = %d AND `addr` != ''",
|
||||
intval($gcontact_id));
|
||||
if ($r)
|
||||
return $r[0]["addr"];
|
||||
}
|
||||
|
||||
if(! $base) {
|
||||
logger('mod-diaspora: unable to locate salmon data in xml ');
|
||||
http_status_exit(400);
|
||||
$r = q("SELECT `network`, `addr`, `self`, `url`, `nick` FROM `contact` WHERE `id` = %d",
|
||||
intval($contact_id));
|
||||
if ($r) {
|
||||
$contact = $r[0];
|
||||
|
||||
logger("contact 'self' = ".$contact['self']." 'url' = ".$contact['url'], LOGGER_DEBUG);
|
||||
|
||||
if($contact['addr'] != "")
|
||||
$handle = $contact['addr'];
|
||||
else {
|
||||
$baseurl_start = strpos($contact['url'],'://') + 3;
|
||||
$baseurl_length = strpos($contact['url'],'/profile') - $baseurl_start; // allows installations in a subdirectory--not sure how Diaspora will handle
|
||||
$baseurl = substr($contact['url'], $baseurl_start, $baseurl_length);
|
||||
$handle = $contact['nick'].'@'.$baseurl;
|
||||
}
|
||||
}
|
||||
|
||||
return $handle;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Get a contact id for a given handle
|
||||
*
|
||||
* @param int $uid The user id
|
||||
* @param string $handle The handle in the format user@domain.tld
|
||||
*
|
||||
* @return The contact id
|
||||
*/
|
||||
private function contact_by_handle($uid, $handle) {
|
||||
$r = q("SELECT * FROM `contact` WHERE `uid` = %d AND `addr` = '%s' LIMIT 1",
|
||||
intval($uid),
|
||||
dbesc($handle)
|
||||
);
|
||||
|
||||
// Stash the signature away for now. We have to find their key or it won't be good for anything.
|
||||
$signature = base64url_decode($base->sig);
|
||||
if ($r)
|
||||
return $r[0];
|
||||
|
||||
// unpack the data
|
||||
$handle_parts = explode("@", $handle);
|
||||
$nurl_sql = "%%://".$handle_parts[1]."%%/profile/".$handle_parts[0];
|
||||
$r = q("SELECT * FROM `contact` WHERE `network` = '%s' AND `uid` = %d AND `nurl` LIKE '%s' LIMIT 1",
|
||||
dbesc(NETWORK_DFRN),
|
||||
intval($uid),
|
||||
dbesc($nurl_sql)
|
||||
);
|
||||
if($r)
|
||||
return $r[0];
|
||||
|
||||
// strip whitespace so our data element will return to one big base64 blob
|
||||
$data = str_replace(array(" ","\t","\r","\n"),array("","","",""),$base->data);
|
||||
|
||||
|
||||
// stash away some other stuff for later
|
||||
|
||||
$type = $base->data[0]->attributes()->type[0];
|
||||
$keyhash = $base->sig[0]->attributes()->keyhash[0];
|
||||
$encoding = $base->encoding;
|
||||
$alg = $base->alg;
|
||||
|
||||
|
||||
$signed_data = $data . '.' . base64url_encode($type) . '.' . base64url_encode($encoding) . '.' . base64url_encode($alg);
|
||||
|
||||
|
||||
// decode the data
|
||||
$data = base64url_decode($data);
|
||||
|
||||
|
||||
if($public) {
|
||||
$inner_decrypted = $data;
|
||||
}
|
||||
else {
|
||||
|
||||
// Decode the encrypted blob
|
||||
|
||||
$inner_encrypted = base64_decode($data);
|
||||
$inner_decrypted = mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $inner_aes_key, $inner_encrypted, MCRYPT_MODE_CBC, $inner_iv);
|
||||
$inner_decrypted = pkcs5_unpad($inner_decrypted);
|
||||
return false;
|
||||
}
|
||||
|
||||
if(! $author_link) {
|
||||
logger('mod-diaspora: Could not retrieve author URI.');
|
||||
http_status_exit(400);
|
||||
}
|
||||
|
||||
// Once we have the author URI, go to the web and try to find their public key
|
||||
// (first this will look it up locally if it is in the fcontact cache)
|
||||
// This will also convert diaspora public key from pkcs#1 to pkcs#8
|
||||
|
||||
logger('mod-diaspora: Fetching key for ' . $author_link );
|
||||
$key = get_diaspora_key($author_link);
|
||||
|
||||
if(! $key) {
|
||||
logger('mod-diaspora: Could not retrieve author key.');
|
||||
http_status_exit(400);
|
||||
}
|
||||
|
||||
$verify = rsa_verify($signed_data,$signature,$key);
|
||||
|
||||
if(! $verify) {
|
||||
logger('mod-diaspora: Message did not verify. Discarding.');
|
||||
http_status_exit(400);
|
||||
}
|
||||
|
||||
logger('mod-diaspora: Message verified.');
|
||||
|
||||
return array('message' => $inner_decrypted, 'author' => $author_link, 'key' => $key);
|
||||
|
||||
}
|
||||
|
||||
|
||||
function diaspora_request($importer,$xml) {
|
||||
|
||||
$a = get_app();
|
||||
|
||||
$sender_handle = unxmlify($xml->sender_handle);
|
||||
$recipient_handle = unxmlify($xml->recipient_handle);
|
||||
|
||||
if(! $sender_handle || ! $recipient_handle)
|
||||
return;
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$sender_handle);
|
||||
|
||||
if($contact) {
|
||||
/**
|
||||
* @brief Check if posting is allowed for this contact
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param array $contact The contact that is checked
|
||||
* @param bool $is_comment Is the check for a comment?
|
||||
*
|
||||
* @return bool is the contact allowed to post?
|
||||
*/
|
||||
private function post_allow($importer, $contact, $is_comment = false) {
|
||||
|
||||
// perhaps we were already sharing with this person. Now they're sharing with us.
|
||||
// That makes us friends.
|
||||
|
||||
if($contact['rel'] == CONTACT_IS_FOLLOWER && in_array($importer['page-flags'], array(PAGE_FREELOVE))) {
|
||||
// Normally this should have handled by getting a request - but this could get lost
|
||||
if($contact["rel"] == CONTACT_IS_FOLLOWER && in_array($importer["page-flags"], array(PAGE_FREELOVE))) {
|
||||
q("UPDATE `contact` SET `rel` = %d, `writable` = 1 WHERE `id` = %d AND `uid` = %d",
|
||||
intval(CONTACT_IS_FRIEND),
|
||||
intval($contact['id']),
|
||||
intval($importer['uid'])
|
||||
intval($contact["id"]),
|
||||
intval($importer["uid"])
|
||||
);
|
||||
}
|
||||
// send notification
|
||||
|
||||
$r = q("SELECT `hide-friends` FROM `profile` WHERE `uid` = %d AND `is-default` = 1 LIMIT 1",
|
||||
intval($importer['uid'])
|
||||
);
|
||||
|
||||
if((count($r)) && (!$r[0]['hide-friends']) && (!$contact['hidden']) && intval(get_pconfig($importer['uid'],'system','post_newfriend'))) {
|
||||
require_once('include/items.php');
|
||||
|
||||
$self = q("SELECT * FROM `contact` WHERE `self` = 1 AND `uid` = %d LIMIT 1",
|
||||
intval($importer['uid'])
|
||||
);
|
||||
|
||||
// they are not CONTACT_IS_FOLLOWER anymore but that's what we have in the array
|
||||
|
||||
if(count($self) && $contact['rel'] == CONTACT_IS_FOLLOWER) {
|
||||
|
||||
$arr = array();
|
||||
$arr['uri'] = $arr['parent-uri'] = item_new_uri($a->get_hostname(), $importer['uid']);
|
||||
$arr['uid'] = $importer['uid'];
|
||||
$arr['contact-id'] = $self[0]['id'];
|
||||
$arr['wall'] = 1;
|
||||
$arr['type'] = 'wall';
|
||||
$arr['gravity'] = 0;
|
||||
$arr['origin'] = 1;
|
||||
$arr['author-name'] = $arr['owner-name'] = $self[0]['name'];
|
||||
$arr['author-link'] = $arr['owner-link'] = $self[0]['url'];
|
||||
$arr['author-avatar'] = $arr['owner-avatar'] = $self[0]['thumb'];
|
||||
$arr['verb'] = ACTIVITY_FRIEND;
|
||||
$arr['object-type'] = ACTIVITY_OBJ_PERSON;
|
||||
|
||||
$A = '[url=' . $self[0]['url'] . ']' . $self[0]['name'] . '[/url]';
|
||||
$B = '[url=' . $contact['url'] . ']' . $contact['name'] . '[/url]';
|
||||
$BPhoto = '[url=' . $contact['url'] . ']' . '[img]' . $contact['thumb'] . '[/img][/url]';
|
||||
$arr['body'] = sprintf( t('%1$s is now friends with %2$s'), $A, $B)."\n\n\n".$Bphoto;
|
||||
|
||||
$arr['object'] = '<object><type>' . ACTIVITY_OBJ_PERSON . '</type><title>' . $contact['name'] . '</title>'
|
||||
. '<id>' . $contact['url'] . '/' . $contact['name'] . '</id>';
|
||||
$arr['object'] .= '<link>' . xmlify('<link rel="alternate" type="text/html" href="' . $contact['url'] . '" />' . "\n");
|
||||
$arr['object'] .= xmlify('<link rel="photo" type="image/jpeg" href="' . $contact['thumb'] . '" />' . "\n");
|
||||
$arr['object'] .= '</link></object>' . "\n";
|
||||
$arr['last-child'] = 1;
|
||||
|
||||
$arr['allow_cid'] = $user[0]['allow_cid'];
|
||||
$arr['allow_gid'] = $user[0]['allow_gid'];
|
||||
$arr['deny_cid'] = $user[0]['deny_cid'];
|
||||
$arr['deny_gid'] = $user[0]['deny_gid'];
|
||||
|
||||
$i = item_store($arr);
|
||||
if($i)
|
||||
proc_run('php',"include/notifier.php","activity","$i");
|
||||
|
||||
}
|
||||
|
||||
$contact["rel"] = CONTACT_IS_FRIEND;
|
||||
logger("defining user ".$contact["nick"]." as friend");
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
if(($contact["blocked"]) || ($contact["readonly"]) || ($contact["archive"]))
|
||||
return false;
|
||||
if($contact["rel"] == CONTACT_IS_SHARING || $contact["rel"] == CONTACT_IS_FRIEND)
|
||||
return true;
|
||||
if($contact["rel"] == CONTACT_IS_FOLLOWER)
|
||||
if(($importer["page-flags"] == PAGE_COMMUNITY) OR $is_comment)
|
||||
return true;
|
||||
|
||||
$ret = find_diaspora_person_by_handle($sender_handle);
|
||||
|
||||
|
||||
if((! count($ret)) || ($ret['network'] != NETWORK_DIASPORA)) {
|
||||
logger('diaspora_request: Cannot resolve diaspora handle ' . $sender_handle . ' for ' . $recipient_handle);
|
||||
return;
|
||||
}
|
||||
|
||||
$batch = (($ret['batch']) ? $ret['batch'] : implode('/', array_slice(explode('/',$ret['url']),0,3)) . '/receive/public');
|
||||
|
||||
|
||||
|
||||
$r = q("INSERT INTO `contact` (`uid`, `network`,`addr`,`created`,`url`,`nurl`,`batch`,`name`,`nick`,`photo`,`pubkey`,`notify`,`poll`,`blocked`,`priority`)
|
||||
VALUES ( %d, '%s', '%s', '%s', '%s','%s','%s','%s','%s','%s','%s','%s','%s',%d,%d) ",
|
||||
intval($importer['uid']),
|
||||
dbesc($ret['network']),
|
||||
dbesc($ret['addr']),
|
||||
datetime_convert(),
|
||||
dbesc($ret['url']),
|
||||
dbesc(normalise_link($ret['url'])),
|
||||
dbesc($batch),
|
||||
dbesc($ret['name']),
|
||||
dbesc($ret['nick']),
|
||||
dbesc($ret['photo']),
|
||||
dbesc($ret['pubkey']),
|
||||
dbesc($ret['notify']),
|
||||
dbesc($ret['poll']),
|
||||
1,
|
||||
2
|
||||
);
|
||||
|
||||
// find the contact record we just created
|
||||
|
||||
$contact_record = diaspora_get_contact_by_handle($importer['uid'],$sender_handle);
|
||||
|
||||
if(! $contact_record) {
|
||||
logger('diaspora_request: unable to locate newly created contact record.');
|
||||
return;
|
||||
}
|
||||
|
||||
$g = q("select def_gid from user where uid = %d limit 1",
|
||||
intval($importer['uid'])
|
||||
);
|
||||
if($g && intval($g[0]['def_gid'])) {
|
||||
require_once('include/group.php');
|
||||
group_add_member($importer['uid'],'',$contact_record['id'],$g[0]['def_gid']);
|
||||
}
|
||||
|
||||
if($importer['page-flags'] == PAGE_NORMAL) {
|
||||
|
||||
$hash = random_string() . (string) time(); // Generate a confirm_key
|
||||
|
||||
$ret = q("INSERT INTO `intro` ( `uid`, `contact-id`, `blocked`, `knowyou`, `note`, `hash`, `datetime` )
|
||||
VALUES ( %d, %d, %d, %d, '%s', '%s', '%s' )",
|
||||
intval($importer['uid']),
|
||||
intval($contact_record['id']),
|
||||
0,
|
||||
0,
|
||||
dbesc( t('Sharing notification from Diaspora network')),
|
||||
dbesc($hash),
|
||||
dbesc(datetime_convert())
|
||||
);
|
||||
}
|
||||
else {
|
||||
|
||||
// automatic friend approval
|
||||
|
||||
require_once('include/Photo.php');
|
||||
|
||||
update_contact_avatar($contact_record['photo'],$importer['uid'],$contact_record['id']);
|
||||
|
||||
// technically they are sharing with us (CONTACT_IS_SHARING),
|
||||
// but if our page-type is PAGE_COMMUNITY or PAGE_SOAPBOX
|
||||
// we are going to change the relationship and make them a follower.
|
||||
|
||||
if($importer['page-flags'] == PAGE_FREELOVE)
|
||||
$new_relation = CONTACT_IS_FRIEND;
|
||||
else
|
||||
$new_relation = CONTACT_IS_FOLLOWER;
|
||||
|
||||
$r = q("UPDATE `contact` SET `rel` = %d,
|
||||
`name-date` = '%s',
|
||||
`uri-date` = '%s',
|
||||
`blocked` = 0,
|
||||
`pending` = 0,
|
||||
`writable` = 1
|
||||
WHERE `id` = %d
|
||||
",
|
||||
intval($new_relation),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc(datetime_convert()),
|
||||
intval($contact_record['id'])
|
||||
);
|
||||
|
||||
$u = q("select * from user where uid = %d limit 1",intval($importer['uid']));
|
||||
if($u)
|
||||
$ret = diaspora_share($u[0],$contact_record);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
function diaspora_post_allow($importer,$contact, $is_comment = false) {
|
||||
|
||||
// perhaps we were already sharing with this person. Now they're sharing with us.
|
||||
// That makes us friends.
|
||||
// Normally this should have handled by getting a request - but this could get lost
|
||||
if($contact['rel'] == CONTACT_IS_FOLLOWER && in_array($importer['page-flags'], array(PAGE_FREELOVE))) {
|
||||
q("UPDATE `contact` SET `rel` = %d, `writable` = 1 WHERE `id` = %d AND `uid` = %d",
|
||||
intval(CONTACT_IS_FRIEND),
|
||||
intval($contact['id']),
|
||||
intval($importer['uid'])
|
||||
);
|
||||
$contact['rel'] = CONTACT_IS_FRIEND;
|
||||
logger('diaspora_post_allow: defining user '.$contact["nick"].' as friend');
|
||||
}
|
||||
|
||||
if(($contact['blocked']) || ($contact['readonly']) || ($contact['archive']))
|
||||
return false;
|
||||
if($contact['rel'] == CONTACT_IS_SHARING || $contact['rel'] == CONTACT_IS_FRIEND)
|
||||
return true;
|
||||
if($contact['rel'] == CONTACT_IS_FOLLOWER)
|
||||
if(($importer['page-flags'] == PAGE_COMMUNITY) OR $is_comment)
|
||||
// Messages for the global users are always accepted
|
||||
if ($importer["uid"] == 0)
|
||||
return true;
|
||||
|
||||
// Messages for the global users are always accepted
|
||||
if ($importer['uid'] == 0)
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
function diaspora_is_redmatrix($url) {
|
||||
return(strstr($url, "/channel/"));
|
||||
}
|
||||
|
||||
function diaspora_plink($addr, $guid) {
|
||||
$r = q("SELECT `url`, `nick`, `network` FROM `fcontact` WHERE `addr`='%s' LIMIT 1", dbesc($addr));
|
||||
|
||||
// Fallback
|
||||
if (!$r)
|
||||
return 'https://'.substr($addr,strpos($addr,'@')+1).'/posts/'.$guid;
|
||||
|
||||
// Friendica contacts are often detected as Diaspora contacts in the "fcontact" table
|
||||
// So we try another way as well.
|
||||
$s = q("SELECT `network` FROM `gcontact` WHERE `nurl`='%s' LIMIT 1", dbesc(normalise_link($r[0]["url"])));
|
||||
if ($s)
|
||||
$r[0]["network"] = $s[0]["network"];
|
||||
|
||||
if ($r[0]["network"] == NETWORK_DFRN)
|
||||
return(str_replace("/profile/".$r[0]["nick"]."/", "/display/".$guid, $r[0]["url"]."/"));
|
||||
|
||||
if (diaspora_is_redmatrix($r[0]["url"]))
|
||||
return $r[0]["url"]."/?f=&mid=".$guid;
|
||||
|
||||
return 'https://'.substr($addr,strpos($addr,'@')+1).'/posts/'.$guid;
|
||||
}
|
||||
|
||||
function diaspora_repair_signature($signature, $handle = "", $level = 1) {
|
||||
|
||||
if ($signature == "")
|
||||
return($signature);
|
||||
|
||||
if (base64_encode(base64_decode(base64_decode($signature))) == base64_decode($signature)) {
|
||||
$signature = base64_decode($signature);
|
||||
logger("Repaired double encoded signature from Diaspora/Hubzilla handle ".$handle." - level ".$level, LOGGER_DEBUG);
|
||||
|
||||
// Do a recursive call to be able to fix even multiple levels
|
||||
if ($level < 10)
|
||||
$signature = diaspora_repair_signature($signature, $handle, ++$level);
|
||||
}
|
||||
|
||||
return($signature);
|
||||
}
|
||||
|
||||
function diaspora_post($importer,$xml,$msg) {
|
||||
|
||||
$a = get_app();
|
||||
$guid = notags(unxmlify($xml->guid));
|
||||
$diaspora_handle = notags(unxmlify($xml->diaspora_handle));
|
||||
|
||||
if($diaspora_handle != $msg['author']) {
|
||||
logger('diaspora_post: Potential forgery. Message handle is not the same as envelope sender.');
|
||||
return 202;
|
||||
}
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$diaspora_handle);
|
||||
if(! $contact) {
|
||||
logger('diaspora_post: A Contact for handle '.$diaspora_handle.' and user '.$importer['uid'].' was not found');
|
||||
return 203;
|
||||
}
|
||||
|
||||
if(! diaspora_post_allow($importer,$contact, false)) {
|
||||
logger('diaspora_post: Ignoring this author.');
|
||||
return 202;
|
||||
}
|
||||
|
||||
$message_id = $diaspora_handle . ':' . $guid;
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($guid)
|
||||
);
|
||||
if(count($r)) {
|
||||
logger('diaspora_post: message exists: ' . $guid);
|
||||
return 208;
|
||||
}
|
||||
|
||||
$created = unxmlify($xml->created_at);
|
||||
$private = ((unxmlify($xml->public) == 'false') ? 1 : 0);
|
||||
|
||||
$body = diaspora2bb($xml->raw_message);
|
||||
|
||||
$datarray = array();
|
||||
|
||||
$datarray["object"] = json_encode($xml);
|
||||
|
||||
if($xml->photo->remote_photo_path AND $xml->photo->remote_photo_name)
|
||||
$datarray["object-type"] = ACTIVITY_OBJ_PHOTO;
|
||||
else {
|
||||
$datarray['object-type'] = ACTIVITY_OBJ_NOTE;
|
||||
// Add OEmbed and other information to the body
|
||||
if (!diaspora_is_redmatrix($contact['url']))
|
||||
$body = add_page_info_to_body($body, false, true);
|
||||
}
|
||||
|
||||
$str_tags = '';
|
||||
|
||||
$cnt = preg_match_all('/@\[url=(.*?)\[\/url\]/ism',$body,$matches,PREG_SET_ORDER);
|
||||
if($cnt) {
|
||||
foreach($matches as $mtch) {
|
||||
if(strlen($str_tags))
|
||||
$str_tags .= ',';
|
||||
$str_tags .= '@[url=' . $mtch[1] . '[/url]';
|
||||
}
|
||||
}
|
||||
|
||||
$plink = diaspora_plink($diaspora_handle, $guid);
|
||||
|
||||
$datarray['uid'] = $importer['uid'];
|
||||
$datarray['contact-id'] = $contact['id'];
|
||||
$datarray['wall'] = 0;
|
||||
$datarray['network'] = NETWORK_DIASPORA;
|
||||
$datarray['verb'] = ACTIVITY_POST;
|
||||
$datarray['guid'] = $guid;
|
||||
$datarray['uri'] = $datarray['parent-uri'] = $message_id;
|
||||
$datarray['changed'] = $datarray['created'] = $datarray['edited'] = datetime_convert('UTC','UTC',$created);
|
||||
$datarray['private'] = $private;
|
||||
$datarray['parent'] = 0;
|
||||
$datarray['plink'] = $plink;
|
||||
$datarray['owner-name'] = $contact['name'];
|
||||
$datarray['owner-link'] = $contact['url'];
|
||||
//$datarray['owner-avatar'] = $contact['thumb'];
|
||||
$datarray['owner-avatar'] = ((x($contact,'thumb')) ? $contact['thumb'] : $contact['photo']);
|
||||
$datarray['author-name'] = $contact['name'];
|
||||
$datarray['author-link'] = $contact['url'];
|
||||
$datarray['author-avatar'] = $contact['thumb'];
|
||||
$datarray['body'] = $body;
|
||||
$datarray['tag'] = $str_tags;
|
||||
if ($xml->provider_display_name)
|
||||
$datarray["app"] = unxmlify($xml->provider_display_name);
|
||||
else
|
||||
$datarray['app'] = 'Diaspora';
|
||||
|
||||
// if empty content it might be a photo that hasn't arrived yet. If a photo arrives, we'll make it visible.
|
||||
|
||||
$datarray['visible'] = ((strlen($body)) ? 1 : 0);
|
||||
|
||||
DiasporaFetchGuid($datarray);
|
||||
$message_id = item_store($datarray);
|
||||
|
||||
logger("Stored item with message id ".$message_id, LOGGER_DEBUG);
|
||||
|
||||
return 201;
|
||||
|
||||
}
|
||||
|
||||
function DiasporaFetchGuid($item) {
|
||||
preg_replace_callback("&\[url=/posts/([^\[\]]*)\](.*)\[\/url\]&Usi",
|
||||
function ($match) use ($item){
|
||||
return(DiasporaFetchGuidSub($match, $item));
|
||||
},$item["body"]);
|
||||
}
|
||||
|
||||
function DiasporaFetchGuidSub($match, $item) {
|
||||
$a = get_app();
|
||||
|
||||
if (!diaspora_store_by_guid($match[1], $item["author-link"]))
|
||||
diaspora_store_by_guid($match[1], $item["owner-link"]);
|
||||
}
|
||||
|
||||
function diaspora_store_by_guid($guid, $server, $uid = 0) {
|
||||
require_once("include/Contact.php");
|
||||
|
||||
$serverparts = parse_url($server);
|
||||
$server = $serverparts["scheme"]."://".$serverparts["host"];
|
||||
|
||||
logger("Trying to fetch item ".$guid." from ".$server, LOGGER_DEBUG);
|
||||
|
||||
$item = diaspora_fetch_message($guid, $server);
|
||||
|
||||
if (!$item)
|
||||
return false;
|
||||
}
|
||||
|
||||
logger("Successfully fetched item ".$guid." from ".$server, LOGGER_DEBUG);
|
||||
|
||||
$body = $item["body"];
|
||||
$str_tags = $item["tag"];
|
||||
$app = $item["app"];
|
||||
$created = $item["created"];
|
||||
$author = $item["author"];
|
||||
$guid = $item["guid"];
|
||||
$private = $item["private"];
|
||||
$object = $item["object"];
|
||||
$objecttype = $item["object-type"];
|
||||
|
||||
$message_id = $author.':'.$guid;
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($uid),
|
||||
dbesc($guid)
|
||||
);
|
||||
if(count($r))
|
||||
return $r[0]["id"];
|
||||
|
||||
$person = find_diaspora_person_by_handle($author);
|
||||
|
||||
$contact_id = get_contact($person['url'], $uid);
|
||||
|
||||
$contacts = q("SELECT * FROM `contact` WHERE `id` = %d", intval($contact_id));
|
||||
$importers = q("SELECT * FROM `user` WHERE `uid` = %d", intval($uid));
|
||||
|
||||
if ($contacts AND $importers)
|
||||
if(!diaspora_post_allow($importers[0],$contacts[0], false)) {
|
||||
logger('Ignoring author '.$person['url'].' for uid '.$uid);
|
||||
/**
|
||||
* @brief Fetches the contact id for a handle and checks if posting is allowed
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param string $handle The checked handle in the format user@domain.tld
|
||||
* @param bool $is_comment Is the check for a comment?
|
||||
*
|
||||
* @return array The contact data
|
||||
*/
|
||||
private function allowed_contact_by_handle($importer, $handle, $is_comment = false) {
|
||||
$contact = self::contact_by_handle($importer["uid"], $handle);
|
||||
if (!$contact) {
|
||||
logger("A Contact for handle ".$handle." and user ".$importer["uid"]." was not found");
|
||||
return false;
|
||||
} else
|
||||
logger('Author '.$person['url'].' is allowed for uid '.$uid);
|
||||
}
|
||||
|
||||
$datarray = array();
|
||||
$datarray['uid'] = $uid;
|
||||
$datarray['contact-id'] = $contact_id;
|
||||
$datarray['wall'] = 0;
|
||||
$datarray['network'] = NETWORK_DIASPORA;
|
||||
$datarray['guid'] = $guid;
|
||||
$datarray['uri'] = $datarray['parent-uri'] = $message_id;
|
||||
$datarray['changed'] = $datarray['created'] = $datarray['edited'] = datetime_convert('UTC','UTC',$created);
|
||||
$datarray['private'] = $private;
|
||||
$datarray['parent'] = 0;
|
||||
$datarray['plink'] = diaspora_plink($author, $guid);
|
||||
$datarray['author-name'] = $person['name'];
|
||||
$datarray['author-link'] = $person['url'];
|
||||
$datarray['author-avatar'] = ((x($person,'thumb')) ? $person['thumb'] : $person['photo']);
|
||||
$datarray['owner-name'] = $datarray['author-name'];
|
||||
$datarray['owner-link'] = $datarray['author-link'];
|
||||
$datarray['owner-avatar'] = $datarray['author-avatar'];
|
||||
$datarray['body'] = $body;
|
||||
$datarray['tag'] = $str_tags;
|
||||
$datarray['app'] = $app;
|
||||
$datarray['visible'] = ((strlen($body)) ? 1 : 0);
|
||||
$datarray['object'] = $object;
|
||||
$datarray['object-type'] = $objecttype;
|
||||
if (!self::post_allow($importer, $contact, $is_comment)) {
|
||||
logger("The handle: ".$handle." is not allowed to post to user ".$importer["uid"]);
|
||||
return false;
|
||||
}
|
||||
return $contact;
|
||||
}
|
||||
|
||||
if ($datarray['contact-id'] == 0)
|
||||
return false;
|
||||
/**
|
||||
* @brief Does the message already exists on the system?
|
||||
*
|
||||
* @param int $uid The user id
|
||||
* @param string $guid The guid of the message
|
||||
*
|
||||
* @return int|bool message id if the message already was stored into the system - or false.
|
||||
*/
|
||||
private function message_exists($uid, $guid) {
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($uid),
|
||||
dbesc($guid)
|
||||
);
|
||||
|
||||
DiasporaFetchGuid($datarray);
|
||||
$message_id = item_store($datarray);
|
||||
if($r) {
|
||||
logger("message ".$guid." already exists for user ".$uid);
|
||||
return $r[0]["id"];
|
||||
}
|
||||
|
||||
/// @TODO
|
||||
/// Looking if there is some subscribe mechanism in Diaspora to get all comments for this post
|
||||
|
||||
return $message_id;
|
||||
}
|
||||
|
||||
function diaspora_fetch_message($guid, $server, $level = 0) {
|
||||
|
||||
if ($level > 5)
|
||||
return false;
|
||||
|
||||
$a = get_app();
|
||||
|
||||
// This will not work if the server is not a Diaspora server
|
||||
$source_url = $server.'/p/'.$guid.'.xml';
|
||||
$x = fetch_url($source_url);
|
||||
if(!$x)
|
||||
return false;
|
||||
|
||||
$x = str_replace(array('<activity_streams-photo>','</activity_streams-photo>'),array('<asphoto>','</asphoto>'),$x);
|
||||
$source_xml = parse_xml_string($x,false);
|
||||
|
||||
$item = array();
|
||||
$item["app"] = 'Diaspora';
|
||||
$item["guid"] = $guid;
|
||||
$body = "";
|
||||
|
||||
if ($source_xml->post->status_message->created_at)
|
||||
$item["created"] = unxmlify($source_xml->post->status_message->created_at);
|
||||
|
||||
if ($source_xml->post->status_message->provider_display_name)
|
||||
$item["app"] = unxmlify($source_xml->post->status_message->provider_display_name);
|
||||
|
||||
if ($source_xml->post->status_message->diaspora_handle)
|
||||
$item["author"] = unxmlify($source_xml->post->status_message->diaspora_handle);
|
||||
|
||||
if ($source_xml->post->status_message->guid)
|
||||
$item["guid"] = unxmlify($source_xml->post->status_message->guid);
|
||||
|
||||
$item["private"] = (unxmlify($source_xml->post->status_message->public) == 'false');
|
||||
$item["object"] = json_encode($source_xml->post);
|
||||
|
||||
if(strlen($source_xml->post->asphoto->objectId) && ($source_xml->post->asphoto->objectId != 0) && ($source_xml->post->asphoto->image_url)) {
|
||||
$item["object-type"] = ACTIVITY_OBJ_PHOTO;
|
||||
$body = '[url=' . notags(unxmlify($source_xml->post->asphoto->image_url)) . '][img]' . notags(unxmlify($source_xml->post->asphoto->objectId)) . '[/img][/url]' . "\n";
|
||||
$body = scale_external_images($body,false);
|
||||
} elseif($source_xml->post->asphoto->image_url) {
|
||||
$item["object-type"] = ACTIVITY_OBJ_PHOTO;
|
||||
$body = '[img]' . notags(unxmlify($source_xml->post->asphoto->image_url)) . '[/img]' . "\n";
|
||||
$body = scale_external_images($body);
|
||||
} elseif($source_xml->post->status_message) {
|
||||
$body = diaspora2bb($source_xml->post->status_message->raw_message);
|
||||
|
||||
// Checking for embedded pictures
|
||||
if($source_xml->post->status_message->photo->remote_photo_path AND
|
||||
$source_xml->post->status_message->photo->remote_photo_name) {
|
||||
|
||||
$item["object-type"] = ACTIVITY_OBJ_PHOTO;
|
||||
|
||||
$remote_photo_path = notags(unxmlify($source_xml->post->status_message->photo->remote_photo_path));
|
||||
$remote_photo_name = notags(unxmlify($source_xml->post->status_message->photo->remote_photo_name));
|
||||
|
||||
$body = '[img]'.$remote_photo_path.$remote_photo_name.'[/img]'."\n".$body;
|
||||
|
||||
logger('embedded picture link found: '.$body, LOGGER_DEBUG);
|
||||
} else
|
||||
$item["object-type"] = ACTIVITY_OBJ_NOTE;
|
||||
|
||||
$body = scale_external_images($body);
|
||||
|
||||
// Add OEmbed and other information to the body
|
||||
/// @TODO It could be a repeated redmatrix item
|
||||
/// Then we shouldn't add further data to it
|
||||
if ($item["object-type"] == ACTIVITY_OBJ_NOTE)
|
||||
$body = add_page_info_to_body($body, false, true);
|
||||
|
||||
} elseif($source_xml->post->reshare) {
|
||||
// Reshare of a reshare
|
||||
return diaspora_fetch_message($source_xml->post->reshare->root_guid, $server, ++$level);
|
||||
} else {
|
||||
// Maybe it is a reshare of a photo that will be delivered at a later time (testing)
|
||||
logger('no content found: '.print_r($source_xml,true));
|
||||
return false;
|
||||
}
|
||||
|
||||
if (trim($body) == "")
|
||||
return false;
|
||||
|
||||
$item["tag"] = '';
|
||||
$item["body"] = $body;
|
||||
|
||||
return $item;
|
||||
}
|
||||
|
||||
function diaspora_reshare($importer,$xml,$msg) {
|
||||
|
||||
logger('diaspora_reshare: init: ' . print_r($xml,true));
|
||||
|
||||
$a = get_app();
|
||||
$guid = notags(unxmlify($xml->guid));
|
||||
$diaspora_handle = notags(unxmlify($xml->diaspora_handle));
|
||||
|
||||
|
||||
if($diaspora_handle != $msg['author']) {
|
||||
logger('diaspora_post: Potential forgery. Message handle is not the same as envelope sender.');
|
||||
return 202;
|
||||
/**
|
||||
* @brief Checks for links to posts in a message
|
||||
*
|
||||
* @param array $item The item array
|
||||
*/
|
||||
private function fetch_guid($item) {
|
||||
preg_replace_callback("&\[url=/posts/([^\[\]]*)\](.*)\[\/url\]&Usi",
|
||||
function ($match) use ($item){
|
||||
return(self::fetch_guid_sub($match, $item));
|
||||
},$item["body"]);
|
||||
}
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$diaspora_handle);
|
||||
if(! $contact)
|
||||
return;
|
||||
|
||||
if(! diaspora_post_allow($importer,$contact, false)) {
|
||||
logger('diaspora_reshare: Ignoring this author: ' . $diaspora_handle . ' ' . print_r($xml,true));
|
||||
return 202;
|
||||
/**
|
||||
* @brief sub function of "fetch_guid" which checks for links in messages
|
||||
*
|
||||
* @param array $match array containing a link that has to be checked for a message link
|
||||
* @param array $item The item array
|
||||
*/
|
||||
private function fetch_guid_sub($match, $item) {
|
||||
if (!self::store_by_guid($match[1], $item["author-link"]))
|
||||
self::store_by_guid($match[1], $item["owner-link"]);
|
||||
}
|
||||
|
||||
$message_id = $diaspora_handle . ':' . $guid;
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($guid)
|
||||
);
|
||||
if(count($r)) {
|
||||
logger('diaspora_reshare: message exists: ' . $guid);
|
||||
return;
|
||||
/**
|
||||
* @brief Fetches an item with a given guid from a given server
|
||||
*
|
||||
* @param string $guid the message guid
|
||||
* @param string $server The server address
|
||||
* @param int $uid The user id of the user
|
||||
*
|
||||
* @return int the message id of the stored message or false
|
||||
*/
|
||||
private function store_by_guid($guid, $server, $uid = 0) {
|
||||
$serverparts = parse_url($server);
|
||||
$server = $serverparts["scheme"]."://".$serverparts["host"];
|
||||
|
||||
logger("Trying to fetch item ".$guid." from ".$server, LOGGER_DEBUG);
|
||||
|
||||
$msg = self::message($guid, $server);
|
||||
|
||||
if (!$msg)
|
||||
return false;
|
||||
|
||||
logger("Successfully fetched item ".$guid." from ".$server, LOGGER_DEBUG);
|
||||
|
||||
// Now call the dispatcher
|
||||
return self::dispatch_public($msg);
|
||||
}
|
||||
|
||||
$orig_author = notags(unxmlify($xml->root_diaspora_id));
|
||||
$orig_guid = notags(unxmlify($xml->root_guid));
|
||||
$orig_url = $a->get_baseurl()."/display/".$orig_guid;
|
||||
/**
|
||||
* @brief Fetches a message from a server
|
||||
*
|
||||
* @param string $guid message guid
|
||||
* @param string $server The url of the server
|
||||
* @param int $level Endless loop prevention
|
||||
*
|
||||
* @return array
|
||||
* 'message' => The message XML
|
||||
* 'author' => The author handle
|
||||
* 'key' => The public key of the author
|
||||
*/
|
||||
private function message($guid, $server, $level = 0) {
|
||||
|
||||
$create_original_post = false;
|
||||
if ($level > 5)
|
||||
return false;
|
||||
|
||||
// Do we already have this item?
|
||||
$r = q("SELECT `body`, `tag`, `app`, `created`, `plink`, `object`, `object-type`, `uri` FROM `item` WHERE `guid` = '%s' AND `visible` AND NOT `deleted` AND `body` != '' LIMIT 1",
|
||||
dbesc($orig_guid),
|
||||
dbesc(NETWORK_DIASPORA)
|
||||
);
|
||||
if(count($r)) {
|
||||
logger('reshared message '.$orig_guid." reshared by ".$guid.' already exists on system.');
|
||||
// This will work for Diaspora and newer Friendica servers
|
||||
$source_url = $server."/p/".$guid.".xml";
|
||||
$x = fetch_url($source_url);
|
||||
if(!$x)
|
||||
return false;
|
||||
|
||||
// Maybe it is already a reshared item?
|
||||
// Then refetch the content, since there can be many side effects with reshared posts from other networks or reshares from reshares
|
||||
require_once('include/api.php');
|
||||
if (api_share_as_retweet($r[0]))
|
||||
$r = array();
|
||||
else {
|
||||
$body = $r[0]["body"];
|
||||
$str_tags = $r[0]["tag"];
|
||||
$app = $r[0]["app"];
|
||||
$orig_created = $r[0]["created"];
|
||||
$orig_plink = $r[0]["plink"];
|
||||
$orig_uri = $r[0]["uri"];
|
||||
$object = $r[0]["object"];
|
||||
$objecttype = $r[0]["object-type"];
|
||||
$source_xml = parse_xml_string($x, false);
|
||||
|
||||
if (!is_object($source_xml))
|
||||
return false;
|
||||
|
||||
if ($source_xml->post->reshare) {
|
||||
// Reshare of a reshare - old Diaspora version
|
||||
return self::message($source_xml->post->reshare->root_guid, $server, ++$level);
|
||||
} elseif ($source_xml->getName() == "reshare") {
|
||||
// Reshare of a reshare - new Diaspora version
|
||||
return self::message($source_xml->root_guid, $server, ++$level);
|
||||
}
|
||||
|
||||
$author = "";
|
||||
|
||||
// Fetch the author - for the old and the new Diaspora version
|
||||
if ($source_xml->post->status_message->diaspora_handle)
|
||||
$author = (string)$source_xml->post->status_message->diaspora_handle;
|
||||
elseif ($source_xml->author AND ($source_xml->getName() == "status_message"))
|
||||
$author = (string)$source_xml->author;
|
||||
|
||||
// If this isn't a "status_message" then quit
|
||||
if (!$author)
|
||||
return false;
|
||||
|
||||
$msg = array("message" => $x, "author" => $author);
|
||||
|
||||
$msg["key"] = self::key($msg["author"]);
|
||||
|
||||
return $msg;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Fetches the item record of a given guid
|
||||
*
|
||||
* @param int $uid The user id
|
||||
* @param string $guid message guid
|
||||
* @param string $author The handle of the item
|
||||
* @param array $contact The contact of the item owner
|
||||
*
|
||||
* @return array the item record
|
||||
*/
|
||||
private function parent_item($uid, $guid, $author, $contact) {
|
||||
$r = q("SELECT `id`, `body`, `wall`, `uri`, `private`, `origin`,
|
||||
`author-name`, `author-link`, `author-avatar`,
|
||||
`owner-name`, `owner-link`, `owner-avatar`
|
||||
FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($uid), dbesc($guid));
|
||||
|
||||
if(!$r) {
|
||||
$result = self::store_by_guid($guid, $contact["url"], $uid);
|
||||
|
||||
if (!$result) {
|
||||
$person = self::person_by_handle($author);
|
||||
$result = self::store_by_guid($guid, $person["url"], $uid);
|
||||
}
|
||||
|
||||
if ($result) {
|
||||
logger("Fetched missing item ".$guid." - result: ".$result, LOGGER_DEBUG);
|
||||
|
||||
$r = q("SELECT `id`, `body`, `wall`, `uri`, `private`, `origin`,
|
||||
`author-name`, `author-link`, `author-avatar`,
|
||||
`owner-name`, `owner-link`, `owner-avatar`
|
||||
FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($uid), dbesc($guid));
|
||||
}
|
||||
}
|
||||
|
||||
if (!$r) {
|
||||
logger("parent item not found: parent: ".$guid." - user: ".$uid);
|
||||
return false;
|
||||
} else {
|
||||
logger("parent item found: parent: ".$guid." - user: ".$uid);
|
||||
return $r[0];
|
||||
}
|
||||
}
|
||||
|
||||
if (!count($r)) {
|
||||
$body = "";
|
||||
$str_tags = "";
|
||||
$app = "";
|
||||
/**
|
||||
* @brief returns contact details
|
||||
*
|
||||
* @param array $contact The default contact if the person isn't found
|
||||
* @param array $person The record of the person
|
||||
* @param int $uid The user id
|
||||
*
|
||||
* @return array
|
||||
* 'cid' => contact id
|
||||
* 'network' => network type
|
||||
*/
|
||||
private function author_contact_by_url($contact, $person, $uid) {
|
||||
|
||||
$server = 'https://'.substr($orig_author,strpos($orig_author,'@')+1);
|
||||
logger('1st try: reshared message '.$orig_guid." reshared by ".$guid.' will be fetched from original server: '.$server);
|
||||
$item = diaspora_fetch_message($orig_guid, $server);
|
||||
|
||||
if (!$item) {
|
||||
$server = 'https://'.substr($diaspora_handle,strpos($diaspora_handle,'@')+1);
|
||||
logger('2nd try: reshared message '.$orig_guid." reshared by ".$guid." will be fetched from sharer's server: ".$server);
|
||||
$item = diaspora_fetch_message($orig_guid, $server);
|
||||
}
|
||||
if (!$item) {
|
||||
$server = 'http://'.substr($orig_author,strpos($orig_author,'@')+1);
|
||||
logger('3rd try: reshared message '.$orig_guid." reshared by ".$guid.' will be fetched from original server: '.$server);
|
||||
$item = diaspora_fetch_message($orig_guid, $server);
|
||||
}
|
||||
if (!$item) {
|
||||
$server = 'http://'.substr($diaspora_handle,strpos($diaspora_handle,'@')+1);
|
||||
logger('4th try: reshared message '.$orig_guid." reshared by ".$guid." will be fetched from sharer's server: ".$server);
|
||||
$item = diaspora_fetch_message($orig_guid, $server);
|
||||
$r = q("SELECT `id`, `network` FROM `contact` WHERE `nurl` = '%s' AND `uid` = %d LIMIT 1",
|
||||
dbesc(normalise_link($person["url"])), intval($uid));
|
||||
if ($r) {
|
||||
$cid = $r[0]["id"];
|
||||
$network = $r[0]["network"];
|
||||
} else {
|
||||
$cid = $contact["id"];
|
||||
$network = NETWORK_DIASPORA;
|
||||
}
|
||||
|
||||
if ($item) {
|
||||
$body = $item["body"];
|
||||
$str_tags = $item["tag"];
|
||||
$app = $item["app"];
|
||||
$orig_created = $item["created"];
|
||||
$orig_author = $item["author"];
|
||||
$orig_guid = $item["guid"];
|
||||
$orig_plink = diaspora_plink($orig_author, $orig_guid);
|
||||
$orig_uri = $orig_author.':'.$orig_guid;
|
||||
$create_original_post = ($body != "");
|
||||
$object = $item["object"];
|
||||
$objecttype = $item["object-type"];
|
||||
}
|
||||
return (array("cid" => $cid, "network" => $network));
|
||||
}
|
||||
|
||||
$plink = diaspora_plink($diaspora_handle, $guid);
|
||||
|
||||
$person = find_diaspora_person_by_handle($orig_author);
|
||||
|
||||
$created = unxmlify($xml->created_at);
|
||||
$private = ((unxmlify($xml->public) == 'false') ? 1 : 0);
|
||||
|
||||
$datarray = array();
|
||||
|
||||
$datarray['uid'] = $importer['uid'];
|
||||
$datarray['contact-id'] = $contact['id'];
|
||||
$datarray['wall'] = 0;
|
||||
$datarray['network'] = NETWORK_DIASPORA;
|
||||
$datarray['guid'] = $guid;
|
||||
$datarray['uri'] = $datarray['parent-uri'] = $message_id;
|
||||
$datarray['changed'] = $datarray['created'] = $datarray['edited'] = datetime_convert('UTC','UTC',$created);
|
||||
$datarray['private'] = $private;
|
||||
$datarray['parent'] = 0;
|
||||
$datarray['plink'] = $plink;
|
||||
$datarray['owner-name'] = $contact['name'];
|
||||
$datarray['owner-link'] = $contact['url'];
|
||||
$datarray['owner-avatar'] = ((x($contact,'thumb')) ? $contact['thumb'] : $contact['photo']);
|
||||
if (!intval(get_config('system','wall-to-wall_share'))) {
|
||||
$prefix = share_header($person['name'], $person['url'], ((x($person,'thumb')) ? $person['thumb'] : $person['photo']), $orig_guid, $orig_created, $orig_url);
|
||||
|
||||
$datarray['author-name'] = $contact['name'];
|
||||
$datarray['author-link'] = $contact['url'];
|
||||
$datarray['author-avatar'] = $contact['thumb'];
|
||||
$datarray['body'] = $prefix.$body."[/share]";
|
||||
} else {
|
||||
// Let reshared messages look like wall-to-wall posts
|
||||
$datarray['author-name'] = $person['name'];
|
||||
$datarray['author-link'] = $person['url'];
|
||||
$datarray['author-avatar'] = ((x($person,'thumb')) ? $person['thumb'] : $person['photo']);
|
||||
$datarray['body'] = $body;
|
||||
/**
|
||||
* @brief Is the profile a hubzilla profile?
|
||||
*
|
||||
* @param string $url The profile link
|
||||
*
|
||||
* @return bool is it a hubzilla server?
|
||||
*/
|
||||
public static function is_redmatrix($url) {
|
||||
return(strstr($url, "/channel/"));
|
||||
}
|
||||
|
||||
$datarray["object"] = json_encode($xml);
|
||||
$datarray['object-type'] = $objecttype;
|
||||
/**
|
||||
* @brief Generate a post link with a given handle and message guid
|
||||
*
|
||||
* @param string $addr The user handle
|
||||
* @param string $guid message guid
|
||||
*
|
||||
* @return string the post link
|
||||
*/
|
||||
private function plink($addr, $guid) {
|
||||
$r = q("SELECT `url`, `nick`, `network` FROM `fcontact` WHERE `addr`='%s' LIMIT 1", dbesc($addr));
|
||||
|
||||
$datarray['tag'] = $str_tags;
|
||||
$datarray['app'] = $app;
|
||||
// Fallback
|
||||
if (!$r)
|
||||
return "https://".substr($addr,strpos($addr,"@")+1)."/posts/".$guid;
|
||||
|
||||
// if empty content it might be a photo that hasn't arrived yet. If a photo arrives, we'll make it visible. (testing)
|
||||
$datarray['visible'] = ((strlen($body)) ? 1 : 0);
|
||||
// Friendica contacts are often detected as Diaspora contacts in the "fcontact" table
|
||||
// So we try another way as well.
|
||||
$s = q("SELECT `network` FROM `gcontact` WHERE `nurl`='%s' LIMIT 1", dbesc(normalise_link($r[0]["url"])));
|
||||
if ($s)
|
||||
$r[0]["network"] = $s[0]["network"];
|
||||
|
||||
// Store the original item of a reshare
|
||||
if ($create_original_post) {
|
||||
require_once("include/Contact.php");
|
||||
if ($r[0]["network"] == NETWORK_DFRN)
|
||||
return(str_replace("/profile/".$r[0]["nick"]."/", "/display/".$guid, $r[0]["url"]."/"));
|
||||
|
||||
$datarray2 = $datarray;
|
||||
if (self::is_redmatrix($r[0]["url"]))
|
||||
return $r[0]["url"]."/?f=&mid=".$guid;
|
||||
|
||||
$datarray2['uid'] = 0;
|
||||
$datarray2['contact-id'] = get_contact($person['url'], 0);
|
||||
$datarray2['guid'] = $orig_guid;
|
||||
$datarray2['uri'] = $datarray2['parent-uri'] = $orig_uri;
|
||||
$datarray2['changed'] = $datarray2['created'] = $datarray2['edited'] = $datarray2['commented'] = $datarray2['received'] = datetime_convert('UTC','UTC',$orig_created);
|
||||
$datarray2['parent'] = 0;
|
||||
$datarray2['plink'] = $orig_plink;
|
||||
|
||||
$datarray2['author-name'] = $person['name'];
|
||||
$datarray2['author-link'] = $person['url'];
|
||||
$datarray2['author-avatar'] = ((x($person,'thumb')) ? $person['thumb'] : $person['photo']);
|
||||
$datarray2['owner-name'] = $datarray2['author-name'];
|
||||
$datarray2['owner-link'] = $datarray2['author-link'];
|
||||
$datarray2['owner-avatar'] = $datarray2['author-avatar'];
|
||||
$datarray2['body'] = $body;
|
||||
$datarray2["object"] = $object;
|
||||
|
||||
DiasporaFetchGuid($datarray2);
|
||||
$message_id = item_store($datarray2);
|
||||
|
||||
logger("Store original item ".$orig_guid." under message id ".$message_id);
|
||||
return "https://".substr($addr,strpos($addr,"@")+1)."/posts/".$guid;
|
||||
}
|
||||
|
||||
DiasporaFetchGuid($datarray);
|
||||
$message_id = item_store($datarray);
|
||||
/**
|
||||
* @brief Processes an account deletion
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return bool Success
|
||||
*/
|
||||
private function receive_account_deletion($importer, $data) {
|
||||
$author = notags(unxmlify($data->author));
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
|
||||
function diaspora_asphoto($importer,$xml,$msg) {
|
||||
logger('diaspora_asphoto called');
|
||||
|
||||
$a = get_app();
|
||||
$guid = notags(unxmlify($xml->guid));
|
||||
$diaspora_handle = notags(unxmlify($xml->diaspora_handle));
|
||||
|
||||
if($diaspora_handle != $msg['author']) {
|
||||
logger('diaspora_post: Potential forgery. Message handle is not the same as envelope sender.');
|
||||
return 202;
|
||||
}
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$diaspora_handle);
|
||||
if(! $contact)
|
||||
return;
|
||||
|
||||
if(! diaspora_post_allow($importer,$contact, false)) {
|
||||
logger('diaspora_asphoto: Ignoring this author.');
|
||||
return 202;
|
||||
}
|
||||
|
||||
$message_id = $diaspora_handle . ':' . $guid;
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($guid)
|
||||
);
|
||||
if(count($r)) {
|
||||
logger('diaspora_asphoto: message exists: ' . $guid);
|
||||
return;
|
||||
}
|
||||
|
||||
$created = unxmlify($xml->created_at);
|
||||
$private = ((unxmlify($xml->public) == 'false') ? 1 : 0);
|
||||
|
||||
if(strlen($xml->objectId) && ($xml->objectId != 0) && ($xml->image_url)) {
|
||||
$body = '[url=' . notags(unxmlify($xml->image_url)) . '][img]' . notags(unxmlify($xml->objectId)) . '[/img][/url]' . "\n";
|
||||
$body = scale_external_images($body,false);
|
||||
}
|
||||
elseif($xml->image_url) {
|
||||
$body = '[img]' . notags(unxmlify($xml->image_url)) . '[/img]' . "\n";
|
||||
$body = scale_external_images($body);
|
||||
}
|
||||
else {
|
||||
logger('diaspora_asphoto: no photo url found.');
|
||||
return;
|
||||
}
|
||||
|
||||
$plink = diaspora_plink($diaspora_handle, $guid);
|
||||
|
||||
$datarray = array();
|
||||
|
||||
$datarray['uid'] = $importer['uid'];
|
||||
$datarray['contact-id'] = $contact['id'];
|
||||
$datarray['wall'] = 0;
|
||||
$datarray['network'] = NETWORK_DIASPORA;
|
||||
$datarray['guid'] = $guid;
|
||||
$datarray['uri'] = $datarray['parent-uri'] = $message_id;
|
||||
$datarray['changed'] = $datarray['created'] = $datarray['edited'] = datetime_convert('UTC','UTC',$created);
|
||||
$datarray['private'] = $private;
|
||||
$datarray['parent'] = 0;
|
||||
$datarray['plink'] = $plink;
|
||||
$datarray['owner-name'] = $contact['name'];
|
||||
$datarray['owner-link'] = $contact['url'];
|
||||
//$datarray['owner-avatar'] = $contact['thumb'];
|
||||
$datarray['owner-avatar'] = ((x($contact,'thumb')) ? $contact['thumb'] : $contact['photo']);
|
||||
$datarray['author-name'] = $contact['name'];
|
||||
$datarray['author-link'] = $contact['url'];
|
||||
$datarray['author-avatar'] = $contact['thumb'];
|
||||
$datarray['body'] = $body;
|
||||
$datarray["object"] = json_encode($xml);
|
||||
$datarray['object-type'] = ACTIVITY_OBJ_PHOTO;
|
||||
|
||||
$datarray['app'] = 'Diaspora/Cubbi.es';
|
||||
|
||||
DiasporaFetchGuid($datarray);
|
||||
$message_id = item_store($datarray);
|
||||
|
||||
//if($message_id) {
|
||||
// q("update item set plink = '%s' where id = %d",
|
||||
// dbesc($a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $message_id),
|
||||
// intval($message_id)
|
||||
// );
|
||||
//}
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
function diaspora_comment($importer,$xml,$msg) {
|
||||
|
||||
$a = get_app();
|
||||
$guid = notags(unxmlify($xml->guid));
|
||||
$parent_guid = notags(unxmlify($xml->parent_guid));
|
||||
$diaspora_handle = notags(unxmlify($xml->diaspora_handle));
|
||||
$target_type = notags(unxmlify($xml->target_type));
|
||||
$text = unxmlify($xml->text);
|
||||
$author_signature = notags(unxmlify($xml->author_signature));
|
||||
|
||||
$parent_author_signature = (($xml->parent_author_signature) ? notags(unxmlify($xml->parent_author_signature)) : '');
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$msg['author']);
|
||||
if(! $contact) {
|
||||
logger('diaspora_comment: cannot find contact: ' . $msg['author']);
|
||||
return;
|
||||
}
|
||||
|
||||
if(! diaspora_post_allow($importer,$contact, true)) {
|
||||
logger('diaspora_comment: Ignoring this author.');
|
||||
return 202;
|
||||
}
|
||||
|
||||
$r = q("SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($guid)
|
||||
);
|
||||
if(count($r)) {
|
||||
logger('diaspora_comment: our comment just got relayed back to us (or there was a guid collision) : ' . $guid);
|
||||
return;
|
||||
}
|
||||
|
||||
$r = q("SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($parent_guid)
|
||||
);
|
||||
|
||||
if(!count($r)) {
|
||||
$result = diaspora_store_by_guid($parent_guid, $contact['url'], $importer['uid']);
|
||||
|
||||
if (!$result) {
|
||||
$person = find_diaspora_person_by_handle($diaspora_handle);
|
||||
$result = diaspora_store_by_guid($parent_guid, $person['url'], $importer['uid']);
|
||||
$contact = self::contact_by_handle($importer["uid"], $author);
|
||||
if (!$contact) {
|
||||
logger("cannot find contact for author: ".$author);
|
||||
return false;
|
||||
}
|
||||
|
||||
if ($result) {
|
||||
logger("Fetched missing item ".$parent_guid." - result: ".$result, LOGGER_DEBUG);
|
||||
// We now remove the contact
|
||||
contact_remove($contact["id"]);
|
||||
return true;
|
||||
}
|
||||
|
||||
$r = q("SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($parent_guid)
|
||||
/**
|
||||
* @brief Processes an incoming comment
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param string $sender The sender of the message
|
||||
* @param object $data The message object
|
||||
* @param string $xml The original XML of the message
|
||||
*
|
||||
* @return int The message id of the generated comment or "false" if there was an error
|
||||
*/
|
||||
private function receive_comment($importer, $sender, $data, $xml) {
|
||||
$guid = notags(unxmlify($data->guid));
|
||||
$parent_guid = notags(unxmlify($data->parent_guid));
|
||||
$text = unxmlify($data->text);
|
||||
$author = notags(unxmlify($data->author));
|
||||
|
||||
$contact = self::allowed_contact_by_handle($importer, $sender, true);
|
||||
if (!$contact)
|
||||
return false;
|
||||
|
||||
$message_id = self::message_exists($importer["uid"], $guid);
|
||||
if ($message_id)
|
||||
return $message_id;
|
||||
|
||||
$parent_item = self::parent_item($importer["uid"], $parent_guid, $author, $contact);
|
||||
if (!$parent_item)
|
||||
return false;
|
||||
|
||||
$person = self::person_by_handle($author);
|
||||
if (!is_array($person)) {
|
||||
logger("unable to find author details");
|
||||
return false;
|
||||
}
|
||||
|
||||
// Fetch the contact id - if we know this contact
|
||||
$author_contact = self::author_contact_by_url($contact, $person, $importer["uid"]);
|
||||
|
||||
$datarray = array();
|
||||
|
||||
$datarray["uid"] = $importer["uid"];
|
||||
$datarray["contact-id"] = $author_contact["cid"];
|
||||
$datarray["network"] = $author_contact["network"];
|
||||
|
||||
$datarray["author-name"] = $person["name"];
|
||||
$datarray["author-link"] = $person["url"];
|
||||
$datarray["author-avatar"] = ((x($person,"thumb")) ? $person["thumb"] : $person["photo"]);
|
||||
|
||||
$datarray["owner-name"] = $contact["name"];
|
||||
$datarray["owner-link"] = $contact["url"];
|
||||
$datarray["owner-avatar"] = ((x($contact,"thumb")) ? $contact["thumb"] : $contact["photo"]);
|
||||
|
||||
$datarray["guid"] = $guid;
|
||||
$datarray["uri"] = $author.":".$guid;
|
||||
|
||||
$datarray["type"] = "remote-comment";
|
||||
$datarray["verb"] = ACTIVITY_POST;
|
||||
$datarray["gravity"] = GRAVITY_COMMENT;
|
||||
$datarray["parent-uri"] = $parent_item["uri"];
|
||||
|
||||
$datarray["object-type"] = ACTIVITY_OBJ_COMMENT;
|
||||
$datarray["object"] = $xml;
|
||||
|
||||
$datarray["body"] = diaspora2bb($text);
|
||||
|
||||
self::fetch_guid($datarray);
|
||||
|
||||
$message_id = item_store($datarray);
|
||||
|
||||
if ($message_id)
|
||||
logger("Stored comment ".$datarray["guid"]." with message id ".$message_id, LOGGER_DEBUG);
|
||||
|
||||
// If we are the origin of the parent we store the original data and notify our followers
|
||||
if($message_id AND $parent_item["origin"]) {
|
||||
|
||||
// Formerly we stored the signed text, the signature and the author in different fields.
|
||||
// We now store the raw data so that we are more flexible.
|
||||
q("INSERT INTO `sign` (`iid`,`signed_text`) VALUES (%d,'%s')",
|
||||
intval($message_id),
|
||||
dbesc(json_encode($data))
|
||||
);
|
||||
|
||||
// notify others
|
||||
proc_run("php", "include/notifier.php", "comment-import", $message_id);
|
||||
}
|
||||
|
||||
return $message_id;
|
||||
}
|
||||
|
||||
if(! count($r)) {
|
||||
logger('diaspora_comment: parent item not found: parent: ' . $parent_guid . ' item: ' . $guid);
|
||||
return;
|
||||
}
|
||||
$parent_item = $r[0];
|
||||
|
||||
|
||||
/* How Diaspora performs comment signature checking:
|
||||
|
||||
- If an item has been sent by the comment author to the top-level post owner to relay on
|
||||
to the rest of the contacts on the top-level post, the top-level post owner should check
|
||||
the author_signature, then create a parent_author_signature before relaying the comment on
|
||||
- If an item has been relayed on by the top-level post owner, the contacts who receive it
|
||||
check only the parent_author_signature. Basically, they trust that the top-level post
|
||||
owner has already verified the authenticity of anything he/she sends out
|
||||
- In either case, the signature that get checked is the signature created by the person
|
||||
who sent the salmon
|
||||
*/
|
||||
|
||||
$signed_data = $guid . ';' . $parent_guid . ';' . $text . ';' . $diaspora_handle;
|
||||
$key = $msg['key'];
|
||||
|
||||
if($parent_author_signature) {
|
||||
// If a parent_author_signature exists, then we've received the comment
|
||||
// relayed from the top-level post owner. There's no need to check the
|
||||
// author_signature if the parent_author_signature is valid
|
||||
|
||||
$parent_author_signature = base64_decode($parent_author_signature);
|
||||
|
||||
if(! rsa_verify($signed_data,$parent_author_signature,$key,'sha256')) {
|
||||
logger('diaspora_comment: top-level owner verification failed.');
|
||||
return;
|
||||
}
|
||||
}
|
||||
else {
|
||||
// If there's no parent_author_signature, then we've received the comment
|
||||
// from the comment creator. In that case, the person is commenting on
|
||||
// our post, so he/she must be a contact of ours and his/her public key
|
||||
// should be in $msg['key']
|
||||
|
||||
$author_signature = base64_decode($author_signature);
|
||||
|
||||
if(! rsa_verify($signed_data,$author_signature,$key,'sha256')) {
|
||||
logger('diaspora_comment: comment author verification failed.');
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// Phew! Everything checks out. Now create an item.
|
||||
|
||||
// Find the original comment author information.
|
||||
// We need this to make sure we display the comment author
|
||||
// information (name and avatar) correctly.
|
||||
if(strcasecmp($diaspora_handle,$msg['author']) == 0)
|
||||
$person = $contact;
|
||||
else {
|
||||
$person = find_diaspora_person_by_handle($diaspora_handle);
|
||||
|
||||
if(! is_array($person)) {
|
||||
logger('diaspora_comment: unable to find author details');
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// Fetch the contact id - if we know this contact
|
||||
$r = q("SELECT `id`, `network` FROM `contact` WHERE `nurl` = '%s' AND `uid` = %d LIMIT 1",
|
||||
dbesc(normalise_link($person['url'])), intval($importer['uid']));
|
||||
if ($r) {
|
||||
$cid = $r[0]['id'];
|
||||
$network = $r[0]['network'];
|
||||
} else {
|
||||
$cid = $contact['id'];
|
||||
$network = NETWORK_DIASPORA;
|
||||
}
|
||||
|
||||
$body = diaspora2bb($text);
|
||||
$message_id = $diaspora_handle . ':' . $guid;
|
||||
|
||||
$datarray = array();
|
||||
|
||||
$datarray['uid'] = $importer['uid'];
|
||||
$datarray['contact-id'] = $cid;
|
||||
$datarray['type'] = 'remote-comment';
|
||||
$datarray['wall'] = $parent_item['wall'];
|
||||
$datarray['network'] = $network;
|
||||
$datarray['verb'] = ACTIVITY_POST;
|
||||
$datarray['gravity'] = GRAVITY_COMMENT;
|
||||
$datarray['guid'] = $guid;
|
||||
$datarray['uri'] = $message_id;
|
||||
$datarray['parent-uri'] = $parent_item['uri'];
|
||||
|
||||
// No timestamps for comments? OK, we'll the use current time.
|
||||
$datarray['changed'] = $datarray['created'] = $datarray['edited'] = datetime_convert();
|
||||
$datarray['private'] = $parent_item['private'];
|
||||
|
||||
$datarray['owner-name'] = $parent_item['owner-name'];
|
||||
$datarray['owner-link'] = $parent_item['owner-link'];
|
||||
$datarray['owner-avatar'] = $parent_item['owner-avatar'];
|
||||
|
||||
$datarray['author-name'] = $person['name'];
|
||||
$datarray['author-link'] = $person['url'];
|
||||
$datarray['author-avatar'] = ((x($person,'thumb')) ? $person['thumb'] : $person['photo']);
|
||||
$datarray['body'] = $body;
|
||||
$datarray["object"] = json_encode($xml);
|
||||
$datarray["object-type"] = ACTIVITY_OBJ_COMMENT;
|
||||
|
||||
// We can't be certain what the original app is if the message is relayed.
|
||||
if(($parent_item['origin']) && (! $parent_author_signature))
|
||||
$datarray['app'] = 'Diaspora';
|
||||
|
||||
DiasporaFetchGuid($datarray);
|
||||
$message_id = item_store($datarray);
|
||||
|
||||
$datarray['id'] = $message_id;
|
||||
|
||||
//if($message_id) {
|
||||
//q("update item set plink = '%s' where id = %d",
|
||||
// //dbesc($a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $message_id),
|
||||
// dbesc($a->get_baseurl().'/display/'.$datarray['guid']),
|
||||
// intval($message_id)
|
||||
//);
|
||||
//}
|
||||
|
||||
// If we are the origin of the parent we store the original signature and notify our followers
|
||||
if($parent_item['origin']) {
|
||||
$author_signature_base64 = base64_encode($author_signature);
|
||||
$author_signature_base64 = diaspora_repair_signature($author_signature_base64, $diaspora_handle);
|
||||
|
||||
q("insert into sign (`iid`,`signed_text`,`signature`,`signer`) values (%d,'%s','%s','%s') ",
|
||||
intval($message_id),
|
||||
dbesc($signed_data),
|
||||
dbesc($author_signature_base64),
|
||||
dbesc($diaspora_handle)
|
||||
);
|
||||
|
||||
// notify others
|
||||
proc_run('php','include/notifier.php','comment-import',$message_id);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
function diaspora_conversation($importer,$xml,$msg) {
|
||||
|
||||
$a = get_app();
|
||||
|
||||
$guid = notags(unxmlify($xml->guid));
|
||||
$subject = notags(unxmlify($xml->subject));
|
||||
$diaspora_handle = notags(unxmlify($xml->diaspora_handle));
|
||||
$participant_handles = notags(unxmlify($xml->participant_handles));
|
||||
$created_at = datetime_convert('UTC','UTC',notags(unxmlify($xml->created_at)));
|
||||
|
||||
$parent_uri = $diaspora_handle . ':' . $guid;
|
||||
|
||||
$messages = $xml->message;
|
||||
|
||||
if(! count($messages)) {
|
||||
logger('diaspora_conversation: empty conversation');
|
||||
return;
|
||||
}
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$msg['author']);
|
||||
if(! $contact) {
|
||||
logger('diaspora_conversation: cannot find contact: ' . $msg['author']);
|
||||
return;
|
||||
}
|
||||
|
||||
if(($contact['rel'] == CONTACT_IS_FOLLOWER) || ($contact['blocked']) || ($contact['readonly'])) {
|
||||
logger('diaspora_conversation: Ignoring this author.');
|
||||
return 202;
|
||||
}
|
||||
|
||||
$conversation = null;
|
||||
|
||||
$c = q("select * from conv where uid = %d and guid = '%s' limit 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($guid)
|
||||
);
|
||||
if(count($c))
|
||||
$conversation = $c[0];
|
||||
else {
|
||||
$r = q("insert into conv (uid,guid,creator,created,updated,subject,recips) values(%d, '%s', '%s', '%s', '%s', '%s', '%s') ",
|
||||
intval($importer['uid']),
|
||||
dbesc($guid),
|
||||
dbesc($diaspora_handle),
|
||||
dbesc(datetime_convert('UTC','UTC',$created_at)),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc($subject),
|
||||
dbesc($participant_handles)
|
||||
);
|
||||
if($r)
|
||||
$c = q("select * from conv where uid = %d and guid = '%s' limit 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($guid)
|
||||
);
|
||||
if(count($c))
|
||||
$conversation = $c[0];
|
||||
}
|
||||
if(! $conversation) {
|
||||
logger('diaspora_conversation: unable to create conversation.');
|
||||
return;
|
||||
}
|
||||
|
||||
foreach($messages as $mesg) {
|
||||
/**
|
||||
* @brief processes and stores private messages
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param array $contact The contact of the message
|
||||
* @param object $data The message object
|
||||
* @param array $msg Array of the processed message, author handle and key
|
||||
* @param object $mesg The private message
|
||||
* @param array $conversation The conversation record to which this message belongs
|
||||
*
|
||||
* @return bool "true" if it was successful
|
||||
*/
|
||||
private function receive_conversation_message($importer, $contact, $data, $msg, $mesg, $conversation) {
|
||||
$guid = notags(unxmlify($data->guid));
|
||||
$subject = notags(unxmlify($data->subject));
|
||||
$author = notags(unxmlify($data->author));
|
||||
|
||||
$reply = 0;
|
||||
|
||||
|
|
@ -1666,1469 +1125,2102 @@ function diaspora_conversation($importer,$xml,$msg) {
|
|||
$msg_parent_author_signature = notags(unxmlify($mesg->parent_author_signature));
|
||||
$msg_author_signature = notags(unxmlify($mesg->author_signature));
|
||||
$msg_text = unxmlify($mesg->text);
|
||||
$msg_created_at = datetime_convert('UTC','UTC',notags(unxmlify($mesg->created_at)));
|
||||
$msg_diaspora_handle = notags(unxmlify($mesg->diaspora_handle));
|
||||
$msg_created_at = datetime_convert("UTC", "UTC", notags(unxmlify($mesg->created_at)));
|
||||
|
||||
// "diaspora_handle" is the element name from the old version
|
||||
// "author" is the element name from the new version
|
||||
if ($mesg->author)
|
||||
$msg_author = notags(unxmlify($mesg->author));
|
||||
elseif ($mesg->diaspora_handle)
|
||||
$msg_author = notags(unxmlify($mesg->diaspora_handle));
|
||||
else
|
||||
return false;
|
||||
|
||||
$msg_conversation_guid = notags(unxmlify($mesg->conversation_guid));
|
||||
|
||||
if($msg_conversation_guid != $guid) {
|
||||
logger('diaspora_conversation: message conversation guid does not belong to the current conversation. ' . $xml);
|
||||
continue;
|
||||
logger("message conversation guid does not belong to the current conversation.");
|
||||
return false;
|
||||
}
|
||||
|
||||
$body = diaspora2bb($msg_text);
|
||||
$message_id = $msg_diaspora_handle . ':' . $msg_guid;
|
||||
$message_uri = $msg_author.":".$msg_guid;
|
||||
|
||||
$author_signed_data = $msg_guid . ';' . $msg_parent_guid . ';' . $msg_text . ';' . unxmlify($mesg->created_at) . ';' . $msg_diaspora_handle . ';' . $msg_conversation_guid;
|
||||
$author_signed_data = $msg_guid.";".$msg_parent_guid.";".$msg_text.";".unxmlify($mesg->created_at).";".$msg_author.";".$msg_conversation_guid;
|
||||
|
||||
$author_signature = base64_decode($msg_author_signature);
|
||||
|
||||
if(strcasecmp($msg_diaspora_handle,$msg['author']) == 0) {
|
||||
if(strcasecmp($msg_author,$msg["author"]) == 0) {
|
||||
$person = $contact;
|
||||
$key = $msg['key'];
|
||||
}
|
||||
else {
|
||||
$person = find_diaspora_person_by_handle($msg_diaspora_handle);
|
||||
$key = $msg["key"];
|
||||
} else {
|
||||
$person = self::person_by_handle($msg_author);
|
||||
|
||||
if(is_array($person) && x($person,'pubkey'))
|
||||
$key = $person['pubkey'];
|
||||
if (is_array($person) && x($person, "pubkey"))
|
||||
$key = $person["pubkey"];
|
||||
else {
|
||||
logger('diaspora_conversation: unable to find author details');
|
||||
continue;
|
||||
logger("unable to find author details");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
if(! rsa_verify($author_signed_data,$author_signature,$key,'sha256')) {
|
||||
logger('diaspora_conversation: verification failed.');
|
||||
continue;
|
||||
if (!rsa_verify($author_signed_data, $author_signature, $key, "sha256")) {
|
||||
logger("verification failed.");
|
||||
return false;
|
||||
}
|
||||
|
||||
if($msg_parent_author_signature) {
|
||||
$owner_signed_data = $msg_guid . ';' . $msg_parent_guid . ';' . $msg_text . ';' . unxmlify($mesg->created_at) . ';' . $msg_diaspora_handle . ';' . $msg_conversation_guid;
|
||||
$owner_signed_data = $msg_guid.";".$msg_parent_guid.";".$msg_text.";".unxmlify($mesg->created_at).";".$msg_author.";".$msg_conversation_guid;
|
||||
|
||||
$parent_author_signature = base64_decode($msg_parent_author_signature);
|
||||
|
||||
$key = $msg['key'];
|
||||
$key = $msg["key"];
|
||||
|
||||
if(! rsa_verify($owner_signed_data,$parent_author_signature,$key,'sha256')) {
|
||||
logger('diaspora_conversation: owner verification failed.');
|
||||
continue;
|
||||
if (!rsa_verify($owner_signed_data, $parent_author_signature, $key, "sha256")) {
|
||||
logger("owner verification failed.");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
$r = q("select id from mail where `uri` = '%s' limit 1",
|
||||
dbesc($message_id)
|
||||
$r = q("SELECT `id` FROM `mail` WHERE `uri` = '%s' LIMIT 1",
|
||||
dbesc($message_uri)
|
||||
);
|
||||
if(count($r)) {
|
||||
logger('diaspora_conversation: duplicate message already delivered.', LOGGER_DEBUG);
|
||||
continue;
|
||||
if($r) {
|
||||
logger("duplicate message already delivered.", LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
|
||||
q("insert into mail ( `uid`, `guid`, `convid`, `from-name`,`from-photo`,`from-url`,`contact-id`,`title`,`body`,`seen`,`reply`,`uri`,`parent-uri`,`created`) values ( %d, '%s', %d, '%s', '%s', '%s', %d, '%s', '%s', %d, %d, '%s','%s','%s')",
|
||||
intval($importer['uid']),
|
||||
q("INSERT INTO `mail` (`uid`, `guid`, `convid`, `from-name`,`from-photo`,`from-url`,`contact-id`,`title`,`body`,`seen`,`reply`,`uri`,`parent-uri`,`created`)
|
||||
VALUES (%d, '%s', %d, '%s', '%s', '%s', %d, '%s', '%s', %d, %d, '%s','%s','%s')",
|
||||
intval($importer["uid"]),
|
||||
dbesc($msg_guid),
|
||||
intval($conversation['id']),
|
||||
dbesc($person['name']),
|
||||
dbesc($person['photo']),
|
||||
dbesc($person['url']),
|
||||
intval($contact['id']),
|
||||
intval($conversation["id"]),
|
||||
dbesc($person["name"]),
|
||||
dbesc($person["photo"]),
|
||||
dbesc($person["url"]),
|
||||
intval($contact["id"]),
|
||||
dbesc($subject),
|
||||
dbesc($body),
|
||||
0,
|
||||
0,
|
||||
dbesc($message_id),
|
||||
dbesc($parent_uri),
|
||||
dbesc($message_uri),
|
||||
dbesc($author.":".$guid),
|
||||
dbesc($msg_created_at)
|
||||
);
|
||||
|
||||
q("update conv set updated = '%s' where id = %d",
|
||||
q("UPDATE `conv` SET `updated` = '%s' WHERE `id` = %d",
|
||||
dbesc(datetime_convert()),
|
||||
intval($conversation['id'])
|
||||
intval($conversation["id"])
|
||||
);
|
||||
|
||||
notification(array(
|
||||
'type' => NOTIFY_MAIL,
|
||||
'notify_flags' => $importer['notify-flags'],
|
||||
'language' => $importer['language'],
|
||||
'to_name' => $importer['username'],
|
||||
'to_email' => $importer['email'],
|
||||
'uid' =>$importer['uid'],
|
||||
'item' => array('subject' => $subject, 'body' => $body),
|
||||
'source_name' => $person['name'],
|
||||
'source_link' => $person['url'],
|
||||
'source_photo' => $person['thumb'],
|
||||
'verb' => ACTIVITY_POST,
|
||||
'otype' => 'mail'
|
||||
"type" => NOTIFY_MAIL,
|
||||
"notify_flags" => $importer["notify-flags"],
|
||||
"language" => $importer["language"],
|
||||
"to_name" => $importer["username"],
|
||||
"to_email" => $importer["email"],
|
||||
"uid" =>$importer["uid"],
|
||||
"item" => array("subject" => $subject, "body" => $body),
|
||||
"source_name" => $person["name"],
|
||||
"source_link" => $person["url"],
|
||||
"source_photo" => $person["thumb"],
|
||||
"verb" => ACTIVITY_POST,
|
||||
"otype" => "mail"
|
||||
));
|
||||
return true;
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
/**
|
||||
* @brief Processes new private messages (answers to private messages are processed elsewhere)
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param array $msg Array of the processed message, author handle and key
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return bool Success
|
||||
*/
|
||||
private function receive_conversation($importer, $msg, $data) {
|
||||
$guid = notags(unxmlify($data->guid));
|
||||
$subject = notags(unxmlify($data->subject));
|
||||
$created_at = datetime_convert("UTC", "UTC", notags(unxmlify($data->created_at)));
|
||||
$author = notags(unxmlify($data->author));
|
||||
$participants = notags(unxmlify($data->participants));
|
||||
|
||||
function diaspora_message($importer,$xml,$msg) {
|
||||
$messages = $data->message;
|
||||
|
||||
$a = get_app();
|
||||
|
||||
$msg_guid = notags(unxmlify($xml->guid));
|
||||
$msg_parent_guid = notags(unxmlify($xml->parent_guid));
|
||||
$msg_parent_author_signature = notags(unxmlify($xml->parent_author_signature));
|
||||
$msg_author_signature = notags(unxmlify($xml->author_signature));
|
||||
$msg_text = unxmlify($xml->text);
|
||||
$msg_created_at = datetime_convert('UTC','UTC',notags(unxmlify($xml->created_at)));
|
||||
$msg_diaspora_handle = notags(unxmlify($xml->diaspora_handle));
|
||||
$msg_conversation_guid = notags(unxmlify($xml->conversation_guid));
|
||||
|
||||
$parent_uri = $msg_diaspora_handle . ':' . $msg_parent_guid;
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$msg_diaspora_handle);
|
||||
if(! $contact) {
|
||||
logger('diaspora_message: cannot find contact: ' . $msg_diaspora_handle);
|
||||
return;
|
||||
}
|
||||
|
||||
if(($contact['rel'] == CONTACT_IS_FOLLOWER) || ($contact['blocked']) || ($contact['readonly'])) {
|
||||
logger('diaspora_message: Ignoring this author.');
|
||||
return 202;
|
||||
}
|
||||
|
||||
$conversation = null;
|
||||
|
||||
$c = q("select * from conv where uid = %d and guid = '%s' limit 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($msg_conversation_guid)
|
||||
);
|
||||
if(count($c))
|
||||
$conversation = $c[0];
|
||||
else {
|
||||
logger('diaspora_message: conversation not available.');
|
||||
return;
|
||||
}
|
||||
|
||||
$reply = 0;
|
||||
|
||||
$body = diaspora2bb($msg_text);
|
||||
$message_id = $msg_diaspora_handle . ':' . $msg_guid;
|
||||
|
||||
$author_signed_data = $msg_guid . ';' . $msg_parent_guid . ';' . $msg_text . ';' . unxmlify($xml->created_at) . ';' . $msg_diaspora_handle . ';' . $msg_conversation_guid;
|
||||
|
||||
|
||||
$author_signature = base64_decode($msg_author_signature);
|
||||
|
||||
$person = find_diaspora_person_by_handle($msg_diaspora_handle);
|
||||
if(is_array($person) && x($person,'pubkey'))
|
||||
$key = $person['pubkey'];
|
||||
else {
|
||||
logger('diaspora_message: unable to find author details');
|
||||
return;
|
||||
}
|
||||
|
||||
if(! rsa_verify($author_signed_data,$author_signature,$key,'sha256')) {
|
||||
logger('diaspora_message: verification failed.');
|
||||
return;
|
||||
}
|
||||
|
||||
$r = q("select id from mail where `uri` = '%s' and uid = %d limit 1",
|
||||
dbesc($message_id),
|
||||
intval($importer['uid'])
|
||||
);
|
||||
if(count($r)) {
|
||||
logger('diaspora_message: duplicate message already delivered.', LOGGER_DEBUG);
|
||||
return;
|
||||
}
|
||||
|
||||
q("insert into mail ( `uid`, `guid`, `convid`, `from-name`,`from-photo`,`from-url`,`contact-id`,`title`,`body`,`seen`,`reply`,`uri`,`parent-uri`,`created`) values ( %d, '%s', %d, '%s', '%s', '%s', %d, '%s', '%s', %d, %d, '%s','%s','%s')",
|
||||
intval($importer['uid']),
|
||||
dbesc($msg_guid),
|
||||
intval($conversation['id']),
|
||||
dbesc($person['name']),
|
||||
dbesc($person['photo']),
|
||||
dbesc($person['url']),
|
||||
intval($contact['id']),
|
||||
dbesc($conversation['subject']),
|
||||
dbesc($body),
|
||||
0,
|
||||
1,
|
||||
dbesc($message_id),
|
||||
dbesc($parent_uri),
|
||||
dbesc($msg_created_at)
|
||||
);
|
||||
|
||||
q("update conv set updated = '%s' where id = %d",
|
||||
dbesc(datetime_convert()),
|
||||
intval($conversation['id'])
|
||||
);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
function diaspora_participation($importer,$xml) {
|
||||
logger("Unsupported message type 'participation' ".print_r($xml, true));
|
||||
}
|
||||
|
||||
function diaspora_photo($importer,$xml,$msg,$attempt=1) {
|
||||
|
||||
$a = get_app();
|
||||
|
||||
logger('diaspora_photo: init',LOGGER_DEBUG);
|
||||
|
||||
$remote_photo_path = notags(unxmlify($xml->remote_photo_path));
|
||||
|
||||
$remote_photo_name = notags(unxmlify($xml->remote_photo_name));
|
||||
|
||||
$status_message_guid = notags(unxmlify($xml->status_message_guid));
|
||||
|
||||
$guid = notags(unxmlify($xml->guid));
|
||||
|
||||
$diaspora_handle = notags(unxmlify($xml->diaspora_handle));
|
||||
|
||||
$public = notags(unxmlify($xml->public));
|
||||
|
||||
$created_at = notags(unxmlify($xml_created_at));
|
||||
|
||||
logger('diaspora_photo: status_message_guid: ' . $status_message_guid, LOGGER_DEBUG);
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$msg['author']);
|
||||
if(! $contact) {
|
||||
logger('diaspora_photo: contact record not found: ' . $msg['author'] . ' handle: ' . $diaspora_handle);
|
||||
return;
|
||||
}
|
||||
|
||||
if(! diaspora_post_allow($importer,$contact, false)) {
|
||||
logger('diaspora_photo: Ignoring this author.');
|
||||
return 202;
|
||||
}
|
||||
|
||||
$r = q("SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($status_message_guid)
|
||||
);
|
||||
|
||||
/* deactivated by now since it can lead to multiplicated pictures in posts.
|
||||
if(!count($r)) {
|
||||
$result = diaspora_store_by_guid($status_message_guid, $contact['url'], $importer['uid']);
|
||||
|
||||
if (!$result) {
|
||||
$person = find_diaspora_person_by_handle($diaspora_handle);
|
||||
$result = diaspora_store_by_guid($status_message_guid, $person['url'], $importer['uid']);
|
||||
if (!count($messages)) {
|
||||
logger("empty conversation");
|
||||
return false;
|
||||
}
|
||||
|
||||
if ($result) {
|
||||
logger("Fetched missing item ".$status_message_guid." - result: ".$result, LOGGER_DEBUG);
|
||||
$contact = self::allowed_contact_by_handle($importer, $msg["author"], true);
|
||||
if (!$contact)
|
||||
return false;
|
||||
|
||||
$r = q("SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($status_message_guid)
|
||||
$conversation = null;
|
||||
|
||||
$c = q("SELECT * FROM `conv` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer["uid"]),
|
||||
dbesc($guid)
|
||||
);
|
||||
if($c)
|
||||
$conversation = $c[0];
|
||||
else {
|
||||
$r = q("INSERT INTO `conv` (`uid`, `guid`, `creator`, `created`, `updated`, `subject`, `recips`)
|
||||
VALUES (%d, '%s', '%s', '%s', '%s', '%s', '%s')",
|
||||
intval($importer["uid"]),
|
||||
dbesc($guid),
|
||||
dbesc($author),
|
||||
dbesc(datetime_convert("UTC", "UTC", $created_at)),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc($subject),
|
||||
dbesc($participants)
|
||||
);
|
||||
if($r)
|
||||
$c = q("SELECT * FROM `conv` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer["uid"]),
|
||||
dbesc($guid)
|
||||
);
|
||||
|
||||
if($c)
|
||||
$conversation = $c[0];
|
||||
}
|
||||
if (!$conversation) {
|
||||
logger("unable to create conversation.");
|
||||
return;
|
||||
}
|
||||
|
||||
foreach($messages as $mesg)
|
||||
self::receive_conversation_message($importer, $contact, $data, $msg, $mesg, $conversation);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Creates the body for a "like" message
|
||||
*
|
||||
* @param array $contact The contact that send us the "like"
|
||||
* @param array $parent_item The item array of the parent item
|
||||
* @param string $guid message guid
|
||||
*
|
||||
* @return string the body
|
||||
*/
|
||||
private function construct_like_body($contact, $parent_item, $guid) {
|
||||
$bodyverb = t('%1$s likes %2$s\'s %3$s');
|
||||
|
||||
$ulink = "[url=".$contact["url"]."]".$contact["name"]."[/url]";
|
||||
$alink = "[url=".$parent_item["author-link"]."]".$parent_item["author-name"]."[/url]";
|
||||
$plink = "[url=".App::get_baseurl()."/display/".urlencode($guid)."]".t("status")."[/url]";
|
||||
|
||||
return sprintf($bodyverb, $ulink, $alink, $plink);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Creates a XML object for a "like"
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param array $parent_item The item array of the parent item
|
||||
*
|
||||
* @return string The XML
|
||||
*/
|
||||
private function construct_like_object($importer, $parent_item) {
|
||||
$objtype = ACTIVITY_OBJ_NOTE;
|
||||
$link = '<link rel="alternate" type="text/html" href="'.App::get_baseurl()."/display/".$importer["nickname"]."/".$parent_item["id"].'" />';
|
||||
$parent_body = $parent_item["body"];
|
||||
|
||||
$xmldata = array("object" => array("type" => $objtype,
|
||||
"local" => "1",
|
||||
"id" => $parent_item["uri"],
|
||||
"link" => $link,
|
||||
"title" => "",
|
||||
"content" => $parent_body));
|
||||
|
||||
return xml::from_array($xmldata, $xml, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Processes "like" messages
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param string $sender The sender of the message
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return int The message id of the generated like or "false" if there was an error
|
||||
*/
|
||||
private function receive_like($importer, $sender, $data) {
|
||||
$positive = notags(unxmlify($data->positive));
|
||||
$guid = notags(unxmlify($data->guid));
|
||||
$parent_type = notags(unxmlify($data->parent_type));
|
||||
$parent_guid = notags(unxmlify($data->parent_guid));
|
||||
$author = notags(unxmlify($data->author));
|
||||
|
||||
// likes on comments aren't supported by Diaspora - only on posts
|
||||
// But maybe this will be supported in the future, so we will accept it.
|
||||
if (!in_array($parent_type, array("Post", "Comment")))
|
||||
return false;
|
||||
|
||||
$contact = self::allowed_contact_by_handle($importer, $sender, true);
|
||||
if (!$contact)
|
||||
return false;
|
||||
|
||||
$message_id = self::message_exists($importer["uid"], $guid);
|
||||
if ($message_id)
|
||||
return $message_id;
|
||||
|
||||
$parent_item = self::parent_item($importer["uid"], $parent_guid, $author, $contact);
|
||||
if (!$parent_item)
|
||||
return false;
|
||||
|
||||
$person = self::person_by_handle($author);
|
||||
if (!is_array($person)) {
|
||||
logger("unable to find author details");
|
||||
return false;
|
||||
}
|
||||
|
||||
// Fetch the contact id - if we know this contact
|
||||
$author_contact = self::author_contact_by_url($contact, $person, $importer["uid"]);
|
||||
|
||||
// "positive" = "false" would be a Dislike - wich isn't currently supported by Diaspora
|
||||
// We would accept this anyhow.
|
||||
if ($positive == "true")
|
||||
$verb = ACTIVITY_LIKE;
|
||||
else
|
||||
$verb = ACTIVITY_DISLIKE;
|
||||
|
||||
$datarray = array();
|
||||
|
||||
$datarray["uid"] = $importer["uid"];
|
||||
$datarray["contact-id"] = $author_contact["cid"];
|
||||
$datarray["network"] = $author_contact["network"];
|
||||
|
||||
$datarray["author-name"] = $person["name"];
|
||||
$datarray["author-link"] = $person["url"];
|
||||
$datarray["author-avatar"] = ((x($person,"thumb")) ? $person["thumb"] : $person["photo"]);
|
||||
|
||||
$datarray["owner-name"] = $contact["name"];
|
||||
$datarray["owner-link"] = $contact["url"];
|
||||
$datarray["owner-avatar"] = ((x($contact,"thumb")) ? $contact["thumb"] : $contact["photo"]);
|
||||
|
||||
$datarray["guid"] = $guid;
|
||||
$datarray["uri"] = $author.":".$guid;
|
||||
|
||||
$datarray["type"] = "activity";
|
||||
$datarray["verb"] = $verb;
|
||||
$datarray["gravity"] = GRAVITY_LIKE;
|
||||
$datarray["parent-uri"] = $parent_item["uri"];
|
||||
|
||||
$datarray["object-type"] = ACTIVITY_OBJ_NOTE;
|
||||
$datarray["object"] = self::construct_like_object($importer, $parent_item);
|
||||
|
||||
$datarray["body"] = self::construct_like_body($contact, $parent_item, $guid);
|
||||
|
||||
$message_id = item_store($datarray);
|
||||
|
||||
if ($message_id)
|
||||
logger("Stored like ".$datarray["guid"]." with message id ".$message_id, LOGGER_DEBUG);
|
||||
|
||||
// If we are the origin of the parent we store the original data and notify our followers
|
||||
if($message_id AND $parent_item["origin"]) {
|
||||
|
||||
// Formerly we stored the signed text, the signature and the author in different fields.
|
||||
// We now store the raw data so that we are more flexible.
|
||||
q("INSERT INTO `sign` (`iid`,`signed_text`) VALUES (%d,'%s')",
|
||||
intval($message_id),
|
||||
dbesc(json_encode($data))
|
||||
);
|
||||
|
||||
// notify others
|
||||
proc_run("php", "include/notifier.php", "comment-import", $message_id);
|
||||
}
|
||||
|
||||
return $message_id;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Processes private messages
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return bool Success?
|
||||
*/
|
||||
private function receive_message($importer, $data) {
|
||||
$guid = notags(unxmlify($data->guid));
|
||||
$parent_guid = notags(unxmlify($data->parent_guid));
|
||||
$text = unxmlify($data->text);
|
||||
$created_at = datetime_convert("UTC", "UTC", notags(unxmlify($data->created_at)));
|
||||
$author = notags(unxmlify($data->author));
|
||||
$conversation_guid = notags(unxmlify($data->conversation_guid));
|
||||
|
||||
$contact = self::allowed_contact_by_handle($importer, $author, true);
|
||||
if (!$contact)
|
||||
return false;
|
||||
|
||||
$conversation = null;
|
||||
|
||||
$c = q("SELECT * FROM `conv` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer["uid"]),
|
||||
dbesc($conversation_guid)
|
||||
);
|
||||
if($c)
|
||||
$conversation = $c[0];
|
||||
else {
|
||||
logger("conversation not available.");
|
||||
return false;
|
||||
}
|
||||
|
||||
$reply = 0;
|
||||
|
||||
$body = diaspora2bb($text);
|
||||
$message_uri = $author.":".$guid;
|
||||
|
||||
$person = self::person_by_handle($author);
|
||||
if (!$person) {
|
||||
logger("unable to find author details");
|
||||
return false;
|
||||
}
|
||||
|
||||
$r = q("SELECT `id` FROM `mail` WHERE `uri` = '%s' AND `uid` = %d LIMIT 1",
|
||||
dbesc($message_uri),
|
||||
intval($importer["uid"])
|
||||
);
|
||||
if($r) {
|
||||
logger("duplicate message already delivered.", LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
|
||||
q("INSERT INTO `mail` (`uid`, `guid`, `convid`, `from-name`,`from-photo`,`from-url`,`contact-id`,`title`,`body`,`seen`,`reply`,`uri`,`parent-uri`,`created`)
|
||||
VALUES ( %d, '%s', %d, '%s', '%s', '%s', %d, '%s', '%s', %d, %d, '%s','%s','%s')",
|
||||
intval($importer["uid"]),
|
||||
dbesc($guid),
|
||||
intval($conversation["id"]),
|
||||
dbesc($person["name"]),
|
||||
dbesc($person["photo"]),
|
||||
dbesc($person["url"]),
|
||||
intval($contact["id"]),
|
||||
dbesc($conversation["subject"]),
|
||||
dbesc($body),
|
||||
0,
|
||||
1,
|
||||
dbesc($message_uri),
|
||||
dbesc($author.":".$parent_guid),
|
||||
dbesc($created_at)
|
||||
);
|
||||
|
||||
q("UPDATE `conv` SET `updated` = '%s' WHERE `id` = %d",
|
||||
dbesc(datetime_convert()),
|
||||
intval($conversation["id"])
|
||||
);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Processes participations - unsupported by now
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return bool always true
|
||||
*/
|
||||
private function receive_participation($importer, $data) {
|
||||
// I'm not sure if we can fully support this message type
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Processes photos - unneeded
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return bool always true
|
||||
*/
|
||||
private function receive_photo($importer, $data) {
|
||||
// There doesn't seem to be a reason for this function, since the photo data is transmitted in the status message as well
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Processes poll participations - unssupported
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return bool always true
|
||||
*/
|
||||
private function receive_poll_participation($importer, $data) {
|
||||
// We don't support polls by now
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Processes incoming profile updates
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return bool Success
|
||||
*/
|
||||
private function receive_profile($importer, $data) {
|
||||
$author = notags(unxmlify($data->author));
|
||||
|
||||
$contact = self::contact_by_handle($importer["uid"], $author);
|
||||
if (!$contact)
|
||||
return false;
|
||||
|
||||
$name = unxmlify($data->first_name).((strlen($data->last_name)) ? " ".unxmlify($data->last_name) : "");
|
||||
$image_url = unxmlify($data->image_url);
|
||||
$birthday = unxmlify($data->birthday);
|
||||
$location = diaspora2bb(unxmlify($data->location));
|
||||
$about = diaspora2bb(unxmlify($data->bio));
|
||||
$gender = unxmlify($data->gender);
|
||||
$searchable = (unxmlify($data->searchable) == "true");
|
||||
$nsfw = (unxmlify($data->nsfw) == "true");
|
||||
$tags = unxmlify($data->tag_string);
|
||||
|
||||
$tags = explode("#", $tags);
|
||||
|
||||
$keywords = array();
|
||||
foreach ($tags as $tag) {
|
||||
$tag = trim(strtolower($tag));
|
||||
if ($tag != "")
|
||||
$keywords[] = $tag;
|
||||
}
|
||||
|
||||
$keywords = implode(", ", $keywords);
|
||||
|
||||
$handle_parts = explode("@", $author);
|
||||
$nick = $handle_parts[0];
|
||||
|
||||
if($name === "")
|
||||
$name = $handle_parts[0];
|
||||
|
||||
if( preg_match("|^https?://|", $image_url) === 0)
|
||||
$image_url = "http://".$handle_parts[1].$image_url;
|
||||
|
||||
update_contact_avatar($image_url, $importer["uid"], $contact["id"]);
|
||||
|
||||
// Generic birthday. We don't know the timezone. The year is irrelevant.
|
||||
|
||||
$birthday = str_replace("1000", "1901", $birthday);
|
||||
|
||||
if ($birthday != "")
|
||||
$birthday = datetime_convert("UTC", "UTC", $birthday, "Y-m-d");
|
||||
|
||||
// this is to prevent multiple birthday notifications in a single year
|
||||
// if we already have a stored birthday and the 'm-d' part hasn't changed, preserve the entry, which will preserve the notify year
|
||||
|
||||
if(substr($birthday,5) === substr($contact["bd"],5))
|
||||
$birthday = $contact["bd"];
|
||||
|
||||
$r = q("UPDATE `contact` SET `name` = '%s', `nick` = '%s', `addr` = '%s', `name-date` = '%s', `bd` = '%s',
|
||||
`location` = '%s', `about` = '%s', `keywords` = '%s', `gender` = '%s' WHERE `id` = %d AND `uid` = %d",
|
||||
dbesc($name),
|
||||
dbesc($nick),
|
||||
dbesc($author),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc($birthday),
|
||||
dbesc($location),
|
||||
dbesc($about),
|
||||
dbesc($keywords),
|
||||
dbesc($gender),
|
||||
intval($contact["id"]),
|
||||
intval($importer["uid"])
|
||||
);
|
||||
|
||||
if ($searchable) {
|
||||
poco_check($contact["url"], $name, NETWORK_DIASPORA, $image_url, $about, $location, $gender, $keywords, "",
|
||||
datetime_convert(), 2, $contact["id"], $importer["uid"]);
|
||||
}
|
||||
|
||||
$gcontact = array("url" => $contact["url"], "network" => NETWORK_DIASPORA, "generation" => 2,
|
||||
"photo" => $image_url, "name" => $name, "location" => $location,
|
||||
"about" => $about, "birthday" => $birthday, "gender" => $gender,
|
||||
"addr" => $author, "nick" => $nick, "keywords" => $keywords,
|
||||
"hide" => !$searchable, "nsfw" => $nsfw);
|
||||
|
||||
update_gcontact($gcontact);
|
||||
|
||||
logger("Profile of contact ".$contact["id"]." stored for user ".$importer["uid"], LOGGER_DEBUG);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Processes incoming friend requests
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param array $contact The contact that send the request
|
||||
*/
|
||||
private function receive_request_make_friend($importer, $contact) {
|
||||
|
||||
$a = get_app();
|
||||
|
||||
if($contact["rel"] == CONTACT_IS_FOLLOWER && in_array($importer["page-flags"], array(PAGE_FREELOVE))) {
|
||||
q("UPDATE `contact` SET `rel` = %d, `writable` = 1 WHERE `id` = %d AND `uid` = %d",
|
||||
intval(CONTACT_IS_FRIEND),
|
||||
intval($contact["id"]),
|
||||
intval($importer["uid"])
|
||||
);
|
||||
}
|
||||
// send notification
|
||||
|
||||
$r = q("SELECT `hide-friends` FROM `profile` WHERE `uid` = %d AND `is-default` = 1 LIMIT 1",
|
||||
intval($importer["uid"])
|
||||
);
|
||||
|
||||
if($r && !$r[0]["hide-friends"] && !$contact["hidden"] && intval(get_pconfig($importer["uid"], "system", "post_newfriend"))) {
|
||||
|
||||
$self = q("SELECT * FROM `contact` WHERE `self` AND `uid` = %d LIMIT 1",
|
||||
intval($importer["uid"])
|
||||
);
|
||||
|
||||
// they are not CONTACT_IS_FOLLOWER anymore but that's what we have in the array
|
||||
|
||||
if($self && $contact["rel"] == CONTACT_IS_FOLLOWER) {
|
||||
|
||||
$arr = array();
|
||||
$arr["uri"] = $arr["parent-uri"] = item_new_uri($a->get_hostname(), $importer["uid"]);
|
||||
$arr["uid"] = $importer["uid"];
|
||||
$arr["contact-id"] = $self[0]["id"];
|
||||
$arr["wall"] = 1;
|
||||
$arr["type"] = 'wall';
|
||||
$arr["gravity"] = 0;
|
||||
$arr["origin"] = 1;
|
||||
$arr["author-name"] = $arr["owner-name"] = $self[0]["name"];
|
||||
$arr["author-link"] = $arr["owner-link"] = $self[0]["url"];
|
||||
$arr["author-avatar"] = $arr["owner-avatar"] = $self[0]["thumb"];
|
||||
$arr["verb"] = ACTIVITY_FRIEND;
|
||||
$arr["object-type"] = ACTIVITY_OBJ_PERSON;
|
||||
|
||||
$A = "[url=".$self[0]["url"]."]".$self[0]["name"]."[/url]";
|
||||
$B = "[url=".$contact["url"]."]".$contact["name"]."[/url]";
|
||||
$BPhoto = "[url=".$contact["url"]."][img]".$contact["thumb"]."[/img][/url]";
|
||||
$arr["body"] = sprintf(t("%1$s is now friends with %2$s"), $A, $B)."\n\n\n".$Bphoto;
|
||||
|
||||
$arr["object"] = self::construct_new_friend_object($contact);
|
||||
|
||||
$arr["last-child"] = 1;
|
||||
|
||||
$arr["allow_cid"] = $user[0]["allow_cid"];
|
||||
$arr["allow_gid"] = $user[0]["allow_gid"];
|
||||
$arr["deny_cid"] = $user[0]["deny_cid"];
|
||||
$arr["deny_gid"] = $user[0]["deny_gid"];
|
||||
|
||||
$i = item_store($arr);
|
||||
if($i)
|
||||
proc_run("php", "include/notifier.php", "activity", $i);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Creates a XML object for a "new friend" message
|
||||
*
|
||||
* @param array $contact Array of the contact
|
||||
*
|
||||
* @return string The XML
|
||||
*/
|
||||
private function construct_new_friend_object($contact) {
|
||||
$objtype = ACTIVITY_OBJ_PERSON;
|
||||
$link = '<link rel="alternate" type="text/html" href="'.$contact["url"].'" />'."\n".
|
||||
'<link rel="photo" type="image/jpeg" href="'.$contact["thumb"].'" />'."\n";
|
||||
|
||||
$xmldata = array("object" => array("type" => $objtype,
|
||||
"title" => $contact["name"],
|
||||
"id" => $contact["url"]."/".$contact["name"],
|
||||
"link" => $link));
|
||||
|
||||
return xml::from_array($xmldata, $xml, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Processes incoming sharing notification
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return bool Success
|
||||
*/
|
||||
private function receive_contact_request($importer, $data) {
|
||||
$author = unxmlify($data->author);
|
||||
$recipient = unxmlify($data->recipient);
|
||||
|
||||
if (!$author || !$recipient)
|
||||
return false;
|
||||
|
||||
// the current protocol version doesn't know these fields
|
||||
// That means that we will assume their existance
|
||||
if (isset($data->following))
|
||||
$following = (unxmlify($data->following) == "true");
|
||||
else
|
||||
$following = true;
|
||||
|
||||
if (isset($data->sharing))
|
||||
$sharing = (unxmlify($data->sharing) == "true");
|
||||
else
|
||||
$sharing = true;
|
||||
|
||||
$contact = self::contact_by_handle($importer["uid"],$author);
|
||||
|
||||
// perhaps we were already sharing with this person. Now they're sharing with us.
|
||||
// That makes us friends.
|
||||
if ($contact) {
|
||||
if ($following AND $sharing) {
|
||||
self::receive_request_make_friend($importer, $contact);
|
||||
return true;
|
||||
} else /// @todo Handle all possible variations of adding and retracting of permissions
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!$following AND $sharing AND in_array($importer["page-flags"], array(PAGE_SOAPBOX, PAGE_NORMAL))) {
|
||||
logger("Author ".$author." wants to share with us - but doesn't want to listen. Request is ignored.", LOGGER_DEBUG);
|
||||
return false;
|
||||
} elseif (!$following AND !$sharing) {
|
||||
logger("Author ".$author." doesn't want anything - and we don't know the author. Request is ignored.", LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
|
||||
$ret = self::person_by_handle($author);
|
||||
|
||||
if (!$ret || ($ret["network"] != NETWORK_DIASPORA)) {
|
||||
logger("Cannot resolve diaspora handle ".$author." for ".$recipient);
|
||||
return false;
|
||||
}
|
||||
|
||||
$batch = (($ret["batch"]) ? $ret["batch"] : implode("/", array_slice(explode("/", $ret["url"]), 0, 3))."/receive/public");
|
||||
|
||||
$r = q("INSERT INTO `contact` (`uid`, `network`,`addr`,`created`,`url`,`nurl`,`batch`,`name`,`nick`,`photo`,`pubkey`,`notify`,`poll`,`blocked`,`priority`)
|
||||
VALUES (%d, '%s', '%s', '%s', '%s','%s','%s','%s','%s','%s','%s','%s','%s',%d,%d)",
|
||||
intval($importer["uid"]),
|
||||
dbesc($ret["network"]),
|
||||
dbesc($ret["addr"]),
|
||||
datetime_convert(),
|
||||
dbesc($ret["url"]),
|
||||
dbesc(normalise_link($ret["url"])),
|
||||
dbesc($batch),
|
||||
dbesc($ret["name"]),
|
||||
dbesc($ret["nick"]),
|
||||
dbesc($ret["photo"]),
|
||||
dbesc($ret["pubkey"]),
|
||||
dbesc($ret["notify"]),
|
||||
dbesc($ret["poll"]),
|
||||
1,
|
||||
2
|
||||
);
|
||||
|
||||
// find the contact record we just created
|
||||
|
||||
$contact_record = self::contact_by_handle($importer["uid"],$author);
|
||||
|
||||
if (!$contact_record) {
|
||||
logger("unable to locate newly created contact record.");
|
||||
return;
|
||||
}
|
||||
|
||||
$g = q("SELECT `def_gid` FROM `user` WHERE `uid` = %d LIMIT 1",
|
||||
intval($importer["uid"])
|
||||
);
|
||||
|
||||
if($g && intval($g[0]["def_gid"]))
|
||||
group_add_member($importer["uid"], "", $contact_record["id"], $g[0]["def_gid"]);
|
||||
|
||||
if($importer["page-flags"] == PAGE_NORMAL) {
|
||||
|
||||
$hash = random_string().(string)time(); // Generate a confirm_key
|
||||
|
||||
$ret = q("INSERT INTO `intro` (`uid`, `contact-id`, `blocked`, `knowyou`, `note`, `hash`, `datetime`)
|
||||
VALUES (%d, %d, %d, %d, '%s', '%s', '%s')",
|
||||
intval($importer["uid"]),
|
||||
intval($contact_record["id"]),
|
||||
0,
|
||||
0,
|
||||
dbesc(t("Sharing notification from Diaspora network")),
|
||||
dbesc($hash),
|
||||
dbesc(datetime_convert())
|
||||
);
|
||||
} else {
|
||||
|
||||
// automatic friend approval
|
||||
|
||||
update_contact_avatar($contact_record["photo"],$importer["uid"],$contact_record["id"]);
|
||||
|
||||
// technically they are sharing with us (CONTACT_IS_SHARING),
|
||||
// but if our page-type is PAGE_COMMUNITY or PAGE_SOAPBOX
|
||||
// we are going to change the relationship and make them a follower.
|
||||
|
||||
if (($importer["page-flags"] == PAGE_FREELOVE) AND $sharing AND $following)
|
||||
$new_relation = CONTACT_IS_FRIEND;
|
||||
elseif (($importer["page-flags"] == PAGE_FREELOVE) AND $sharing)
|
||||
$new_relation = CONTACT_IS_SHARING;
|
||||
else
|
||||
$new_relation = CONTACT_IS_FOLLOWER;
|
||||
|
||||
$r = q("UPDATE `contact` SET `rel` = %d,
|
||||
`name-date` = '%s',
|
||||
`uri-date` = '%s',
|
||||
`blocked` = 0,
|
||||
`pending` = 0,
|
||||
`writable` = 1
|
||||
WHERE `id` = %d
|
||||
",
|
||||
intval($new_relation),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc(datetime_convert()),
|
||||
intval($contact_record["id"])
|
||||
);
|
||||
|
||||
$u = q("SELECT * FROM `user` WHERE `uid` = %d LIMIT 1", intval($importer["uid"]));
|
||||
if($u)
|
||||
$ret = self::send_share($u[0], $contact_record);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Fetches a message with a given guid
|
||||
*
|
||||
* @param string $guid message guid
|
||||
* @param string $orig_author handle of the original post
|
||||
* @param string $author handle of the sharer
|
||||
*
|
||||
* @return array The fetched item
|
||||
*/
|
||||
private function original_item($guid, $orig_author, $author) {
|
||||
|
||||
// Do we already have this item?
|
||||
$r = q("SELECT `body`, `tag`, `app`, `created`, `object-type`, `uri`, `guid`,
|
||||
`author-name`, `author-link`, `author-avatar`
|
||||
FROM `item` WHERE `guid` = '%s' AND `visible` AND NOT `deleted` AND `body` != '' LIMIT 1",
|
||||
dbesc($guid));
|
||||
|
||||
if($r) {
|
||||
logger("reshared message ".$guid." already exists on system.");
|
||||
|
||||
// Maybe it is already a reshared item?
|
||||
// Then refetch the content, if it is a reshare from a reshare.
|
||||
// If it is a reshared post from another network then reformat to avoid display problems with two share elements
|
||||
if (self::is_reshare($r[0]["body"], true))
|
||||
$r = array();
|
||||
elseif (self::is_reshare($r[0]["body"], false)) {
|
||||
$r[0]["body"] = diaspora2bb(bb2diaspora($r[0]["body"]));
|
||||
|
||||
// Add OEmbed and other information to the body
|
||||
$r[0]["body"] = add_page_info_to_body($r[0]["body"], false, true);
|
||||
|
||||
return $r[0];
|
||||
} else
|
||||
return $r[0];
|
||||
}
|
||||
|
||||
if (!$r) {
|
||||
$server = "https://".substr($orig_author, strpos($orig_author, "@") + 1);
|
||||
logger("1st try: reshared message ".$guid." will be fetched from original server: ".$server);
|
||||
$item_id = self::store_by_guid($guid, $server);
|
||||
|
||||
if (!$item_id) {
|
||||
$server = "http://".substr($orig_author, strpos($orig_author, "@") + 1);
|
||||
logger("2nd try: reshared message ".$guid." will be fetched from original server: ".$server);
|
||||
$item_id = self::store_by_guid($guid, $server);
|
||||
}
|
||||
|
||||
// Deactivated by now since there is a risk that someone could manipulate postings through this method
|
||||
/* if (!$item_id) {
|
||||
$server = "https://".substr($author, strpos($author, "@") + 1);
|
||||
logger("3rd try: reshared message ".$guid." will be fetched from sharer's server: ".$server);
|
||||
$item_id = self::store_by_guid($guid, $server);
|
||||
}
|
||||
if (!$item_id) {
|
||||
$server = "http://".substr($author, strpos($author, "@") + 1);
|
||||
logger("4th try: reshared message ".$guid." will be fetched from sharer's server: ".$server);
|
||||
$item_id = self::store_by_guid($guid, $server);
|
||||
}
|
||||
*/
|
||||
if(!count($r)) {
|
||||
if($attempt <= 3) {
|
||||
q("INSERT INTO dsprphotoq (uid, msg, attempt) VALUES (%d, '%s', %d)",
|
||||
intval($importer['uid']),
|
||||
dbesc(serialize($msg)),
|
||||
intval($attempt + 1)
|
||||
);
|
||||
}
|
||||
if ($item_id) {
|
||||
$r = q("SELECT `body`, `tag`, `app`, `created`, `object-type`, `uri`, `guid`,
|
||||
`author-name`, `author-link`, `author-avatar`
|
||||
FROM `item` WHERE `id` = %d AND `visible` AND NOT `deleted` AND `body` != '' LIMIT 1",
|
||||
intval($item_id));
|
||||
|
||||
logger('diaspora_photo: attempt = ' . $attempt . '; status message not found: ' . $status_message_guid . ' for photo: ' . $guid);
|
||||
return;
|
||||
}
|
||||
if ($r)
|
||||
return $r[0];
|
||||
|
||||
$parent_item = $r[0];
|
||||
|
||||
$link_text = '[img]' . $remote_photo_path . $remote_photo_name . '[/img]' . "\n";
|
||||
|
||||
$link_text = scale_external_images($link_text, true,
|
||||
array($remote_photo_name, 'scaled_full_' . $remote_photo_name));
|
||||
|
||||
if(strpos($parent_item['body'],$link_text) === false) {
|
||||
|
||||
$parent_item['body'] = $link_text . $parent_item['body'];
|
||||
|
||||
$r = q("UPDATE `item` SET `body` = '%s', `visible` = 1 WHERE `id` = %d AND `uid` = %d",
|
||||
dbesc($parent_item['body']),
|
||||
intval($parent_item['id']),
|
||||
intval($parent_item['uid'])
|
||||
);
|
||||
put_item_in_cache($parent_item, true);
|
||||
update_thread($parent_item['id']);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
function diaspora_like($importer,$xml,$msg) {
|
||||
|
||||
$a = get_app();
|
||||
$guid = notags(unxmlify($xml->guid));
|
||||
$parent_guid = notags(unxmlify($xml->parent_guid));
|
||||
$diaspora_handle = notags(unxmlify($xml->diaspora_handle));
|
||||
$target_type = notags(unxmlify($xml->target_type));
|
||||
$positive = notags(unxmlify($xml->positive));
|
||||
$author_signature = notags(unxmlify($xml->author_signature));
|
||||
|
||||
$parent_author_signature = (($xml->parent_author_signature) ? notags(unxmlify($xml->parent_author_signature)) : '');
|
||||
|
||||
// likes on comments not supported here and likes on photos not supported by Diaspora
|
||||
|
||||
// if($target_type !== 'Post')
|
||||
// return;
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$msg['author']);
|
||||
if(! $contact) {
|
||||
logger('diaspora_like: cannot find contact: ' . $msg['author']);
|
||||
return;
|
||||
}
|
||||
|
||||
if(! diaspora_post_allow($importer,$contact, false)) {
|
||||
logger('diaspora_like: Ignoring this author.');
|
||||
return 202;
|
||||
}
|
||||
|
||||
$r = q("SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($parent_guid)
|
||||
);
|
||||
|
||||
if(!count($r)) {
|
||||
$result = diaspora_store_by_guid($parent_guid, $contact['url'], $importer['uid']);
|
||||
|
||||
if (!$result) {
|
||||
$person = find_diaspora_person_by_handle($diaspora_handle);
|
||||
$result = diaspora_store_by_guid($parent_guid, $person['url'], $importer['uid']);
|
||||
}
|
||||
|
||||
if ($result) {
|
||||
logger("Fetched missing item ".$parent_guid." - result: ".$result, LOGGER_DEBUG);
|
||||
|
||||
$r = q("SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($parent_guid)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
if(! count($r)) {
|
||||
logger('diaspora_like: parent item not found: ' . $guid);
|
||||
return;
|
||||
}
|
||||
|
||||
$parent_item = $r[0];
|
||||
|
||||
$r = q("SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($importer['uid']),
|
||||
dbesc($guid)
|
||||
);
|
||||
if(count($r)) {
|
||||
if($positive === 'true') {
|
||||
logger('diaspora_like: duplicate like: ' . $guid);
|
||||
return;
|
||||
}
|
||||
// Note: I don't think "Like" objects with positive = "false" are ever actually used
|
||||
// It looks like "RelayableRetractions" are used for "unlike" instead
|
||||
if($positive === 'false') {
|
||||
logger('diaspora_like: received a like with positive set to "false"...ignoring');
|
||||
/* q("UPDATE `item` SET `deleted` = 1 WHERE `id` = %d AND `uid` = %d",
|
||||
intval($r[0]['id']),
|
||||
intval($importer['uid'])
|
||||
);*/
|
||||
// FIXME--actually don't unless it turns out that Diaspora does indeed send out "false" likes
|
||||
// send notification via proc_run()
|
||||
return;
|
||||
}
|
||||
}
|
||||
// Note: I don't think "Like" objects with positive = "false" are ever actually used
|
||||
// It looks like "RelayableRetractions" are used for "unlike" instead
|
||||
if($positive === 'false') {
|
||||
logger('diaspora_like: received a like with positive set to "false"');
|
||||
logger('diaspora_like: unlike received with no corresponding like...ignoring');
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
/* How Diaspora performs "like" signature checking:
|
||||
|
||||
- If an item has been sent by the like author to the top-level post owner to relay on
|
||||
to the rest of the contacts on the top-level post, the top-level post owner should check
|
||||
the author_signature, then create a parent_author_signature before relaying the like on
|
||||
- If an item has been relayed on by the top-level post owner, the contacts who receive it
|
||||
check only the parent_author_signature. Basically, they trust that the top-level post
|
||||
owner has already verified the authenticity of anything he/she sends out
|
||||
- In either case, the signature that get checked is the signature created by the person
|
||||
who sent the salmon
|
||||
*/
|
||||
|
||||
// Diaspora has changed the way they are signing the likes.
|
||||
// Just to make sure that we don't miss any likes we will check the old and the current way.
|
||||
$old_signed_data = $guid . ';' . $target_type . ';' . $parent_guid . ';' . $positive . ';' . $diaspora_handle;
|
||||
|
||||
$signed_data = $positive . ';' . $guid . ';' . $target_type . ';' . $parent_guid . ';' . $diaspora_handle;
|
||||
|
||||
$key = $msg['key'];
|
||||
|
||||
if ($parent_author_signature) {
|
||||
// If a parent_author_signature exists, then we've received the like
|
||||
// relayed from the top-level post owner. There's no need to check the
|
||||
// author_signature if the parent_author_signature is valid
|
||||
|
||||
$parent_author_signature = base64_decode($parent_author_signature);
|
||||
|
||||
if (!rsa_verify($signed_data,$parent_author_signature,$key,'sha256') AND
|
||||
!rsa_verify($old_signed_data,$parent_author_signature,$key,'sha256')) {
|
||||
|
||||
logger('diaspora_like: top-level owner verification failed.');
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
// If there's no parent_author_signature, then we've received the like
|
||||
// from the like creator. In that case, the person is "like"ing
|
||||
// our post, so he/she must be a contact of ours and his/her public key
|
||||
// should be in $msg['key']
|
||||
|
||||
$author_signature = base64_decode($author_signature);
|
||||
|
||||
if (!rsa_verify($signed_data,$author_signature,$key,'sha256') AND
|
||||
!rsa_verify($old_signed_data,$author_signature,$key,'sha256')) {
|
||||
|
||||
logger('diaspora_like: like creator verification failed.');
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// Phew! Everything checks out. Now create an item.
|
||||
|
||||
// Find the original comment author information.
|
||||
// We need this to make sure we display the comment author
|
||||
// information (name and avatar) correctly.
|
||||
if(strcasecmp($diaspora_handle,$msg['author']) == 0)
|
||||
$person = $contact;
|
||||
else {
|
||||
$person = find_diaspora_person_by_handle($diaspora_handle);
|
||||
|
||||
if(! is_array($person)) {
|
||||
logger('diaspora_like: unable to find author details');
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
$uri = $diaspora_handle . ':' . $guid;
|
||||
|
||||
$activity = ACTIVITY_LIKE;
|
||||
$post_type = (($parent_item['resource-id']) ? t('photo') : t('status'));
|
||||
$objtype = (($parent_item['resource-id']) ? ACTIVITY_OBJ_PHOTO : ACTIVITY_OBJ_NOTE );
|
||||
$link = xmlify('<link rel="alternate" type="text/html" href="' . $a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $parent_item['id'] . '" />' . "\n") ;
|
||||
$body = $parent_item['body'];
|
||||
|
||||
$obj = <<< EOT
|
||||
|
||||
<object>
|
||||
<type>$objtype</type>
|
||||
<local>1</local>
|
||||
<id>{$parent_item['uri']}</id>
|
||||
<link>$link</link>
|
||||
<title></title>
|
||||
<content>$body</content>
|
||||
</object>
|
||||
EOT;
|
||||
$bodyverb = t('%1$s likes %2$s\'s %3$s');
|
||||
|
||||
// Fetch the contact id - if we know this contact
|
||||
$r = q("SELECT `id`, `network` FROM `contact` WHERE `nurl` = '%s' AND `uid` = %d LIMIT 1",
|
||||
dbesc(normalise_link($person['url'])), intval($importer['uid']));
|
||||
if ($r) {
|
||||
$cid = $r[0]['id'];
|
||||
$network = $r[0]['network'];
|
||||
} else {
|
||||
$cid = $contact['id'];
|
||||
$network = NETWORK_DIASPORA;
|
||||
}
|
||||
|
||||
$arr = array();
|
||||
|
||||
$arr['uri'] = $uri;
|
||||
$arr['uid'] = $importer['uid'];
|
||||
$arr['guid'] = $guid;
|
||||
$arr['network'] = $network;
|
||||
$arr['contact-id'] = $cid;
|
||||
$arr['type'] = 'activity';
|
||||
$arr['wall'] = $parent_item['wall'];
|
||||
$arr['gravity'] = GRAVITY_LIKE;
|
||||
$arr['parent'] = $parent_item['id'];
|
||||
$arr['parent-uri'] = $parent_item['uri'];
|
||||
|
||||
$arr['owner-name'] = $parent_item['name'];
|
||||
$arr['owner-link'] = $parent_item['url'];
|
||||
//$arr['owner-avatar'] = $parent_item['thumb'];
|
||||
$arr['owner-avatar'] = ((x($parent_item,'thumb')) ? $parent_item['thumb'] : $parent_item['photo']);
|
||||
|
||||
$arr['author-name'] = $person['name'];
|
||||
$arr['author-link'] = $person['url'];
|
||||
$arr['author-avatar'] = ((x($person,'thumb')) ? $person['thumb'] : $person['photo']);
|
||||
|
||||
$ulink = '[url=' . $contact['url'] . ']' . $contact['name'] . '[/url]';
|
||||
$alink = '[url=' . $parent_item['author-link'] . ']' . $parent_item['author-name'] . '[/url]';
|
||||
//$plink = '[url=' . $a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $parent_item['id'] . ']' . $post_type . '[/url]';
|
||||
$plink = '[url='.$a->get_baseurl().'/display/'.urlencode($guid).']'.$post_type.'[/url]';
|
||||
$arr['body'] = sprintf( $bodyverb, $ulink, $alink, $plink );
|
||||
|
||||
$arr['app'] = 'Diaspora';
|
||||
|
||||
$arr['private'] = $parent_item['private'];
|
||||
$arr['verb'] = $activity;
|
||||
$arr['object-type'] = $objtype;
|
||||
$arr['object'] = $obj;
|
||||
$arr['visible'] = 1;
|
||||
$arr['unseen'] = 1;
|
||||
$arr['last-child'] = 0;
|
||||
|
||||
$message_id = item_store($arr);
|
||||
|
||||
|
||||
//if($message_id) {
|
||||
// q("update item set plink = '%s' where id = %d",
|
||||
// //dbesc($a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $message_id),
|
||||
// dbesc($a->get_baseurl().'/display/'.$guid),
|
||||
// intval($message_id)
|
||||
// );
|
||||
//}
|
||||
|
||||
// If we are the origin of the parent we store the original signature and notify our followers
|
||||
if($parent_item['origin']) {
|
||||
$author_signature_base64 = base64_encode($author_signature);
|
||||
$author_signature_base64 = diaspora_repair_signature($author_signature_base64, $diaspora_handle);
|
||||
|
||||
q("insert into sign (`iid`,`signed_text`,`signature`,`signer`) values (%d,'%s','%s','%s') ",
|
||||
intval($message_id),
|
||||
dbesc($signed_data),
|
||||
dbesc($author_signature_base64),
|
||||
dbesc($diaspora_handle)
|
||||
);
|
||||
|
||||
// notify others
|
||||
proc_run('php','include/notifier.php','comment-import',$message_id);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
function diaspora_retraction($importer,$xml) {
|
||||
|
||||
|
||||
$guid = notags(unxmlify($xml->guid));
|
||||
$diaspora_handle = notags(unxmlify($xml->diaspora_handle));
|
||||
$type = notags(unxmlify($xml->type));
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$diaspora_handle);
|
||||
if(! $contact)
|
||||
return;
|
||||
|
||||
if($type === 'Person') {
|
||||
require_once('include/Contact.php');
|
||||
contact_remove($contact['id']);
|
||||
} elseif($type === 'StatusMessage') {
|
||||
$guid = notags(unxmlify($xml->post_guid));
|
||||
|
||||
$r = q("SELECT * FROM `item` WHERE `guid` = '%s' AND `uid` = %d AND NOT `file` LIKE '%%[%%' LIMIT 1",
|
||||
dbesc($guid),
|
||||
intval($importer['uid'])
|
||||
);
|
||||
if(count($r)) {
|
||||
if(link_compare($r[0]['author-link'],$contact['url'])) {
|
||||
q("UPDATE `item` SET `deleted` = 1, `changed` = '%s' WHERE `id` = %d",
|
||||
dbesc(datetime_convert()),
|
||||
intval($r[0]['id'])
|
||||
);
|
||||
delete_thread($r[0]['id'], $r[0]['parent-uri']);
|
||||
}
|
||||
}
|
||||
} elseif($type === 'Post') {
|
||||
$r = q("select * from item where guid = '%s' and uid = %d and not file like '%%[%%' limit 1",
|
||||
dbesc('guid'),
|
||||
intval($importer['uid'])
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Processes a reshare message
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param object $data The message object
|
||||
* @param string $xml The original XML of the message
|
||||
*
|
||||
* @return int the message id
|
||||
*/
|
||||
private function receive_reshare($importer, $data, $xml) {
|
||||
$root_author = notags(unxmlify($data->root_author));
|
||||
$root_guid = notags(unxmlify($data->root_guid));
|
||||
$guid = notags(unxmlify($data->guid));
|
||||
$author = notags(unxmlify($data->author));
|
||||
$public = notags(unxmlify($data->public));
|
||||
$created_at = notags(unxmlify($data->created_at));
|
||||
|
||||
$contact = self::allowed_contact_by_handle($importer, $author, false);
|
||||
if (!$contact)
|
||||
return false;
|
||||
|
||||
$message_id = self::message_exists($importer["uid"], $guid);
|
||||
if ($message_id)
|
||||
return $message_id;
|
||||
|
||||
$original_item = self::original_item($root_guid, $root_author, $author);
|
||||
if (!$original_item)
|
||||
return false;
|
||||
|
||||
$orig_url = App::get_baseurl()."/display/".$original_item["guid"];
|
||||
|
||||
$datarray = array();
|
||||
|
||||
$datarray["uid"] = $importer["uid"];
|
||||
$datarray["contact-id"] = $contact["id"];
|
||||
$datarray["network"] = NETWORK_DIASPORA;
|
||||
|
||||
$datarray["author-name"] = $contact["name"];
|
||||
$datarray["author-link"] = $contact["url"];
|
||||
$datarray["author-avatar"] = ((x($contact,"thumb")) ? $contact["thumb"] : $contact["photo"]);
|
||||
|
||||
$datarray["owner-name"] = $datarray["author-name"];
|
||||
$datarray["owner-link"] = $datarray["author-link"];
|
||||
$datarray["owner-avatar"] = $datarray["author-avatar"];
|
||||
|
||||
$datarray["guid"] = $guid;
|
||||
$datarray["uri"] = $datarray["parent-uri"] = $author.":".$guid;
|
||||
|
||||
$datarray["verb"] = ACTIVITY_POST;
|
||||
$datarray["gravity"] = GRAVITY_PARENT;
|
||||
|
||||
$datarray["object"] = $xml;
|
||||
|
||||
$prefix = share_header($original_item["author-name"], $original_item["author-link"], $original_item["author-avatar"],
|
||||
$original_item["guid"], $original_item["created"], $orig_url);
|
||||
$datarray["body"] = $prefix.$original_item["body"]."[/share]";
|
||||
|
||||
$datarray["tag"] = $original_item["tag"];
|
||||
$datarray["app"] = $original_item["app"];
|
||||
|
||||
$datarray["plink"] = self::plink($author, $guid);
|
||||
$datarray["private"] = (($public == "false") ? 1 : 0);
|
||||
$datarray["changed"] = $datarray["created"] = $datarray["edited"] = datetime_convert("UTC", "UTC", $created_at);
|
||||
|
||||
$datarray["object-type"] = $original_item["object-type"];
|
||||
|
||||
self::fetch_guid($datarray);
|
||||
$message_id = item_store($datarray);
|
||||
|
||||
if ($message_id)
|
||||
logger("Stored reshare ".$datarray["guid"]." with message id ".$message_id, LOGGER_DEBUG);
|
||||
|
||||
return $message_id;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Processes retractions
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param array $contact The contact of the item owner
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return bool success
|
||||
*/
|
||||
private function item_retraction($importer, $contact, $data) {
|
||||
$target_type = notags(unxmlify($data->target_type));
|
||||
$target_guid = notags(unxmlify($data->target_guid));
|
||||
$author = notags(unxmlify($data->author));
|
||||
|
||||
$person = self::person_by_handle($author);
|
||||
if (!is_array($person)) {
|
||||
logger("unable to find author detail for ".$author);
|
||||
return false;
|
||||
}
|
||||
|
||||
$r = q("SELECT `id`, `parent`, `parent-uri`, `author-link` FROM `item` WHERE `guid` = '%s' AND `uid` = %d AND NOT `file` LIKE '%%[%%' LIMIT 1",
|
||||
dbesc($target_guid),
|
||||
intval($importer["uid"])
|
||||
);
|
||||
if(count($r)) {
|
||||
if(link_compare($r[0]['author-link'],$contact['url'])) {
|
||||
q("update item set `deleted` = 1, `changed` = '%s' where `id` = %d",
|
||||
dbesc(datetime_convert()),
|
||||
intval($r[0]['id'])
|
||||
);
|
||||
delete_thread($r[0]['id'], $r[0]['parent-uri']);
|
||||
if (!$r)
|
||||
return false;
|
||||
|
||||
// Only delete it if the author really fits
|
||||
if (!link_compare($r[0]["author-link"], $person["url"])) {
|
||||
logger("Item author ".$r[0]["author-link"]." doesn't fit to expected contact ".$person["url"], LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Check if the sender is the thread owner
|
||||
$p = q("SELECT `id`, `author-link`, `origin` FROM `item` WHERE `id` = %d",
|
||||
intval($r[0]["parent"]));
|
||||
|
||||
// Only delete it if the parent author really fits
|
||||
if (!link_compare($p[0]["author-link"], $contact["url"]) AND !link_compare($r[0]["author-link"], $contact["url"])) {
|
||||
logger("Thread author ".$p[0]["author-link"]." and item author ".$r[0]["author-link"]." don't fit to expected contact ".$contact["url"], LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Currently we don't have a central deletion function that we could use in this case. The function "item_drop" doesn't work for that case
|
||||
q("UPDATE `item` SET `deleted` = 1, `edited` = '%s', `changed` = '%s', `body` = '' , `title` = '' WHERE `id` = %d",
|
||||
dbesc(datetime_convert()),
|
||||
dbesc(datetime_convert()),
|
||||
intval($r[0]["id"])
|
||||
);
|
||||
delete_thread($r[0]["id"], $r[0]["parent-uri"]);
|
||||
|
||||
logger("Deleted target ".$target_guid." (".$r[0]["id"].") from user ".$importer["uid"]." parent: ".$p[0]["id"], LOGGER_DEBUG);
|
||||
|
||||
// Now check if the retraction needs to be relayed by us
|
||||
if($p[0]["origin"]) {
|
||||
// notify others
|
||||
proc_run("php", "include/notifier.php", "drop", $r[0]["id"]);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Receives retraction messages
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param string $sender The sender of the message
|
||||
* @param object $data The message object
|
||||
*
|
||||
* @return bool Success
|
||||
*/
|
||||
private function receive_retraction($importer, $sender, $data) {
|
||||
$target_type = notags(unxmlify($data->target_type));
|
||||
|
||||
$contact = self::contact_by_handle($importer["uid"], $sender);
|
||||
if (!$contact) {
|
||||
logger("cannot find contact for sender: ".$sender." and user ".$importer["uid"]);
|
||||
return false;
|
||||
}
|
||||
|
||||
logger("Got retraction for ".$target_type.", sender ".$sender." and user ".$importer["uid"], LOGGER_DEBUG);
|
||||
|
||||
switch ($target_type) {
|
||||
case "Comment":
|
||||
case "Like":
|
||||
case "Post": // "Post" will be supported in a future version
|
||||
case "Reshare":
|
||||
case "StatusMessage":
|
||||
return self::item_retraction($importer, $contact, $data);;
|
||||
|
||||
case "Person":
|
||||
/// @todo What should we do with an "unshare"?
|
||||
// Removing the contact isn't correct since we still can read the public items
|
||||
//contact_remove($contact["id"]);
|
||||
return true;
|
||||
|
||||
default:
|
||||
logger("Unknown target type ".$target_type);
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Receives status messages
|
||||
*
|
||||
* @param array $importer Array of the importer user
|
||||
* @param object $data The message object
|
||||
* @param string $xml The original XML of the message
|
||||
*
|
||||
* @return int The message id of the newly created item
|
||||
*/
|
||||
private function receive_status_message($importer, $data, $xml) {
|
||||
|
||||
$raw_message = unxmlify($data->raw_message);
|
||||
$guid = notags(unxmlify($data->guid));
|
||||
$author = notags(unxmlify($data->author));
|
||||
$public = notags(unxmlify($data->public));
|
||||
$created_at = notags(unxmlify($data->created_at));
|
||||
$provider_display_name = notags(unxmlify($data->provider_display_name));
|
||||
|
||||
/// @todo enable support for polls
|
||||
//if ($data->poll) {
|
||||
// foreach ($data->poll AS $poll)
|
||||
// print_r($poll);
|
||||
// die("poll!\n");
|
||||
//}
|
||||
$contact = self::allowed_contact_by_handle($importer, $author, false);
|
||||
if (!$contact)
|
||||
return false;
|
||||
|
||||
$message_id = self::message_exists($importer["uid"], $guid);
|
||||
if ($message_id)
|
||||
return $message_id;
|
||||
|
||||
$address = array();
|
||||
if ($data->location)
|
||||
foreach ($data->location->children() AS $fieldname => $data)
|
||||
$address[$fieldname] = notags(unxmlify($data));
|
||||
|
||||
$body = diaspora2bb($raw_message);
|
||||
|
||||
$datarray = array();
|
||||
|
||||
// Attach embedded pictures to the body
|
||||
if ($data->photo) {
|
||||
foreach ($data->photo AS $photo)
|
||||
$body = "[img]".unxmlify($photo->remote_photo_path).
|
||||
unxmlify($photo->remote_photo_name)."[/img]\n".$body;
|
||||
|
||||
$datarray["object-type"] = ACTIVITY_OBJ_PHOTO;
|
||||
} else {
|
||||
$datarray["object-type"] = ACTIVITY_OBJ_NOTE;
|
||||
|
||||
// Add OEmbed and other information to the body
|
||||
if (!self::is_redmatrix($contact["url"]))
|
||||
$body = add_page_info_to_body($body, false, true);
|
||||
}
|
||||
|
||||
$datarray["uid"] = $importer["uid"];
|
||||
$datarray["contact-id"] = $contact["id"];
|
||||
$datarray["network"] = NETWORK_DIASPORA;
|
||||
|
||||
$datarray["author-name"] = $contact["name"];
|
||||
$datarray["author-link"] = $contact["url"];
|
||||
$datarray["author-avatar"] = ((x($contact,"thumb")) ? $contact["thumb"] : $contact["photo"]);
|
||||
|
||||
$datarray["owner-name"] = $datarray["author-name"];
|
||||
$datarray["owner-link"] = $datarray["author-link"];
|
||||
$datarray["owner-avatar"] = $datarray["author-avatar"];
|
||||
|
||||
$datarray["guid"] = $guid;
|
||||
$datarray["uri"] = $datarray["parent-uri"] = $author.":".$guid;
|
||||
|
||||
$datarray["verb"] = ACTIVITY_POST;
|
||||
$datarray["gravity"] = GRAVITY_PARENT;
|
||||
|
||||
$datarray["object"] = $xml;
|
||||
|
||||
$datarray["body"] = $body;
|
||||
|
||||
if ($provider_display_name != "")
|
||||
$datarray["app"] = $provider_display_name;
|
||||
|
||||
$datarray["plink"] = self::plink($author, $guid);
|
||||
$datarray["private"] = (($public == "false") ? 1 : 0);
|
||||
$datarray["changed"] = $datarray["created"] = $datarray["edited"] = datetime_convert("UTC", "UTC", $created_at);
|
||||
|
||||
if (isset($address["address"]))
|
||||
$datarray["location"] = $address["address"];
|
||||
|
||||
if (isset($address["lat"]) AND isset($address["lng"]))
|
||||
$datarray["coord"] = $address["lat"]." ".$address["lng"];
|
||||
|
||||
self::fetch_guid($datarray);
|
||||
$message_id = item_store($datarray);
|
||||
|
||||
if ($message_id)
|
||||
logger("Stored item ".$datarray["guid"]." with message id ".$message_id, LOGGER_DEBUG);
|
||||
|
||||
return $message_id;
|
||||
}
|
||||
|
||||
/* ************************************************************************************** *
|
||||
* Here are all the functions that are needed to transmit data with the Diaspora protocol *
|
||||
* ************************************************************************************** */
|
||||
|
||||
/**
|
||||
* @brief returnes the handle of a contact
|
||||
*
|
||||
* @param array $me contact array
|
||||
*
|
||||
* @return string the handle in the format user@domain.tld
|
||||
*/
|
||||
private function my_handle($contact) {
|
||||
if ($contact["addr"] != "")
|
||||
return $contact["addr"];
|
||||
|
||||
// Normally we should have a filled "addr" field - but in the past this wasn't the case
|
||||
// So - just in case - we build the the address here.
|
||||
if ($contact["nickname"] != "")
|
||||
$nick = $contact["nickname"];
|
||||
else
|
||||
$nick = $contact["nick"];
|
||||
|
||||
return $nick."@".substr(App::get_baseurl(), strpos(App::get_baseurl(),"://") + 3);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Creates the envelope for a public message
|
||||
*
|
||||
* @param string $msg The message that is to be transmitted
|
||||
* @param array $user The record of the sender
|
||||
* @param array $contact Target of the communication
|
||||
* @param string $prvkey The private key of the sender
|
||||
* @param string $pubkey The public key of the receiver
|
||||
*
|
||||
* @return string The envelope
|
||||
*/
|
||||
private function build_public_message($msg, $user, $contact, $prvkey, $pubkey) {
|
||||
|
||||
logger("Message: ".$msg, LOGGER_DATA);
|
||||
|
||||
$handle = self::my_handle($user);
|
||||
|
||||
$b64url_data = base64url_encode($msg);
|
||||
|
||||
$data = str_replace(array("\n", "\r", " ", "\t"), array("", "", "", ""), $b64url_data);
|
||||
|
||||
$type = "application/xml";
|
||||
$encoding = "base64url";
|
||||
$alg = "RSA-SHA256";
|
||||
|
||||
$signable_data = $data.".".base64url_encode($type).".".base64url_encode($encoding).".".base64url_encode($alg);
|
||||
|
||||
$signature = rsa_sign($signable_data,$prvkey);
|
||||
$sig = base64url_encode($signature);
|
||||
|
||||
$xmldata = array("diaspora" => array("header" => array("author_id" => $handle),
|
||||
"me:env" => array("me:encoding" => "base64url",
|
||||
"me:alg" => "RSA-SHA256",
|
||||
"me:data" => $data,
|
||||
"@attributes" => array("type" => "application/xml"),
|
||||
"me:sig" => $sig)));
|
||||
|
||||
$namespaces = array("" => "https://joindiaspora.com/protocol",
|
||||
"me" => "http://salmon-protocol.org/ns/magic-env");
|
||||
|
||||
$magic_env = xml::from_array($xmldata, $xml, false, $namespaces);
|
||||
|
||||
logger("magic_env: ".$magic_env, LOGGER_DATA);
|
||||
return $magic_env;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Creates the envelope for a private message
|
||||
*
|
||||
* @param string $msg The message that is to be transmitted
|
||||
* @param array $user The record of the sender
|
||||
* @param array $contact Target of the communication
|
||||
* @param string $prvkey The private key of the sender
|
||||
* @param string $pubkey The public key of the receiver
|
||||
*
|
||||
* @return string The envelope
|
||||
*/
|
||||
private function build_private_message($msg, $user, $contact, $prvkey, $pubkey) {
|
||||
|
||||
logger("Message: ".$msg, LOGGER_DATA);
|
||||
|
||||
// without a public key nothing will work
|
||||
|
||||
if (!$pubkey) {
|
||||
logger("pubkey missing: contact id: ".$contact["id"]);
|
||||
return false;
|
||||
}
|
||||
|
||||
$inner_aes_key = random_string(32);
|
||||
$b_inner_aes_key = base64_encode($inner_aes_key);
|
||||
$inner_iv = random_string(16);
|
||||
$b_inner_iv = base64_encode($inner_iv);
|
||||
|
||||
$outer_aes_key = random_string(32);
|
||||
$b_outer_aes_key = base64_encode($outer_aes_key);
|
||||
$outer_iv = random_string(16);
|
||||
$b_outer_iv = base64_encode($outer_iv);
|
||||
|
||||
$handle = self::my_handle($user);
|
||||
|
||||
$padded_data = pkcs5_pad($msg,16);
|
||||
$inner_encrypted = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $inner_aes_key, $padded_data, MCRYPT_MODE_CBC, $inner_iv);
|
||||
|
||||
$b64_data = base64_encode($inner_encrypted);
|
||||
|
||||
|
||||
$b64url_data = base64url_encode($b64_data);
|
||||
$data = str_replace(array("\n", "\r", " ", "\t"), array("", "", "", ""), $b64url_data);
|
||||
|
||||
$type = "application/xml";
|
||||
$encoding = "base64url";
|
||||
$alg = "RSA-SHA256";
|
||||
|
||||
$signable_data = $data.".".base64url_encode($type).".".base64url_encode($encoding).".".base64url_encode($alg);
|
||||
|
||||
$signature = rsa_sign($signable_data,$prvkey);
|
||||
$sig = base64url_encode($signature);
|
||||
|
||||
$xmldata = array("decrypted_header" => array("iv" => $b_inner_iv,
|
||||
"aes_key" => $b_inner_aes_key,
|
||||
"author_id" => $handle));
|
||||
|
||||
$decrypted_header = xml::from_array($xmldata, $xml, true);
|
||||
$decrypted_header = pkcs5_pad($decrypted_header,16);
|
||||
|
||||
$ciphertext = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $outer_aes_key, $decrypted_header, MCRYPT_MODE_CBC, $outer_iv);
|
||||
|
||||
$outer_json = json_encode(array("iv" => $b_outer_iv, "key" => $b_outer_aes_key));
|
||||
|
||||
$encrypted_outer_key_bundle = "";
|
||||
openssl_public_encrypt($outer_json, $encrypted_outer_key_bundle, $pubkey);
|
||||
|
||||
$b64_encrypted_outer_key_bundle = base64_encode($encrypted_outer_key_bundle);
|
||||
|
||||
logger("outer_bundle: ".$b64_encrypted_outer_key_bundle." key: ".$pubkey, LOGGER_DATA);
|
||||
|
||||
$encrypted_header_json_object = json_encode(array("aes_key" => base64_encode($encrypted_outer_key_bundle),
|
||||
"ciphertext" => base64_encode($ciphertext)));
|
||||
$cipher_json = base64_encode($encrypted_header_json_object);
|
||||
|
||||
$xmldata = array("diaspora" => array("encrypted_header" => $cipher_json,
|
||||
"me:env" => array("me:encoding" => "base64url",
|
||||
"me:alg" => "RSA-SHA256",
|
||||
"me:data" => $data,
|
||||
"@attributes" => array("type" => "application/xml"),
|
||||
"me:sig" => $sig)));
|
||||
|
||||
$namespaces = array("" => "https://joindiaspora.com/protocol",
|
||||
"me" => "http://salmon-protocol.org/ns/magic-env");
|
||||
|
||||
$magic_env = xml::from_array($xmldata, $xml, false, $namespaces);
|
||||
|
||||
logger("magic_env: ".$magic_env, LOGGER_DATA);
|
||||
return $magic_env;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Create the envelope for a message
|
||||
*
|
||||
* @param string $msg The message that is to be transmitted
|
||||
* @param array $user The record of the sender
|
||||
* @param array $contact Target of the communication
|
||||
* @param string $prvkey The private key of the sender
|
||||
* @param string $pubkey The public key of the receiver
|
||||
* @param bool $public Is the message public?
|
||||
*
|
||||
* @return string The message that will be transmitted to other servers
|
||||
*/
|
||||
private function build_message($msg, $user, $contact, $prvkey, $pubkey, $public = false) {
|
||||
|
||||
if ($public)
|
||||
$magic_env = self::build_public_message($msg,$user,$contact,$prvkey,$pubkey);
|
||||
else
|
||||
$magic_env = self::build_private_message($msg,$user,$contact,$prvkey,$pubkey);
|
||||
|
||||
// The data that will be transmitted is double encoded via "urlencode", strange ...
|
||||
$slap = "xml=".urlencode(urlencode($magic_env));
|
||||
return $slap;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Creates a signature for a message
|
||||
*
|
||||
* @param array $owner the array of the owner of the message
|
||||
* @param array $message The message that is to be signed
|
||||
*
|
||||
* @return string The signature
|
||||
*/
|
||||
private function signature($owner, $message) {
|
||||
$sigmsg = $message;
|
||||
unset($sigmsg["author_signature"]);
|
||||
unset($sigmsg["parent_author_signature"]);
|
||||
|
||||
$signed_text = implode(";", $sigmsg);
|
||||
|
||||
return base64_encode(rsa_sign($signed_text, $owner["uprvkey"], "sha256"));
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Transmit a message to a target server
|
||||
*
|
||||
* @param array $owner the array of the item owner
|
||||
* @param array $contact Target of the communication
|
||||
* @param string $slap The message that is to be transmitted
|
||||
* @param bool $public_batch Is it a public post?
|
||||
* @param bool $queue_run Is the transmission called from the queue?
|
||||
* @param string $guid message guid
|
||||
*
|
||||
* @return int Result of the transmission
|
||||
*/
|
||||
public static function transmit($owner, $contact, $slap, $public_batch, $queue_run=false, $guid = "") {
|
||||
|
||||
$a = get_app();
|
||||
|
||||
$enabled = intval(get_config("system", "diaspora_enabled"));
|
||||
if(!$enabled)
|
||||
return 200;
|
||||
|
||||
$logid = random_string(4);
|
||||
$dest_url = (($public_batch) ? $contact["batch"] : $contact["notify"]);
|
||||
if (!$dest_url) {
|
||||
logger("no url for contact: ".$contact["id"]." batch mode =".$public_batch);
|
||||
return 0;
|
||||
}
|
||||
|
||||
logger("transmit: ".$logid."-".$guid." ".$dest_url);
|
||||
|
||||
if (!$queue_run && was_recently_delayed($contact["id"])) {
|
||||
$return_code = 0;
|
||||
} else {
|
||||
if (!intval(get_config("system", "diaspora_test"))) {
|
||||
post_url($dest_url."/", $slap);
|
||||
$return_code = $a->get_curl_code();
|
||||
} else {
|
||||
logger("test_mode");
|
||||
return 200;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 202;
|
||||
// NOTREACHED
|
||||
}
|
||||
logger("transmit: ".$logid."-".$guid." returns: ".$return_code);
|
||||
|
||||
function diaspora_signed_retraction($importer,$xml,$msg) {
|
||||
if(!$return_code || (($return_code == 503) && (stristr($a->get_curl_headers(), "retry-after")))) {
|
||||
logger("queue message");
|
||||
|
||||
|
||||
$guid = notags(unxmlify($xml->target_guid));
|
||||
$diaspora_handle = notags(unxmlify($xml->sender_handle));
|
||||
$type = notags(unxmlify($xml->target_type));
|
||||
$sig = notags(unxmlify($xml->target_author_signature));
|
||||
|
||||
$parent_author_signature = (($xml->parent_author_signature) ? notags(unxmlify($xml->parent_author_signature)) : '');
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$diaspora_handle);
|
||||
if(! $contact) {
|
||||
logger('diaspora_signed_retraction: no contact ' . $diaspora_handle . ' for ' . $importer['uid']);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
$signed_data = $guid . ';' . $type ;
|
||||
$key = $msg['key'];
|
||||
|
||||
/* How Diaspora performs relayable_retraction signature checking:
|
||||
|
||||
- If an item has been sent by the item author to the top-level post owner to relay on
|
||||
to the rest of the contacts on the top-level post, the top-level post owner checks
|
||||
the author_signature, then creates a parent_author_signature before relaying the item on
|
||||
- If an item has been relayed on by the top-level post owner, the contacts who receive it
|
||||
check only the parent_author_signature. Basically, they trust that the top-level post
|
||||
owner has already verified the authenticity of anything he/she sends out
|
||||
- In either case, the signature that get checked is the signature created by the person
|
||||
who sent the salmon
|
||||
*/
|
||||
|
||||
if($parent_author_signature) {
|
||||
|
||||
$parent_author_signature = base64_decode($parent_author_signature);
|
||||
|
||||
if(! rsa_verify($signed_data,$parent_author_signature,$key,'sha256')) {
|
||||
logger('diaspora_signed_retraction: top-level post owner verification failed');
|
||||
return;
|
||||
$r = q("SELECT `id` FROM `queue` WHERE `cid` = %d AND `network` = '%s' AND `content` = '%s' AND `batch` = %d LIMIT 1",
|
||||
intval($contact["id"]),
|
||||
dbesc(NETWORK_DIASPORA),
|
||||
dbesc($slap),
|
||||
intval($public_batch)
|
||||
);
|
||||
if($r) {
|
||||
logger("add_to_queue ignored - identical item already in queue");
|
||||
} else {
|
||||
// queue message for redelivery
|
||||
add_to_queue($contact["id"], NETWORK_DIASPORA, $slap, $public_batch);
|
||||
}
|
||||
}
|
||||
|
||||
} else {
|
||||
|
||||
$sig_decode = base64_decode($sig);
|
||||
|
||||
if(! rsa_verify($signed_data,$sig_decode,$key,'sha256')) {
|
||||
logger('diaspora_signed_retraction: retraction owner verification failed.' . print_r($msg,true));
|
||||
return;
|
||||
}
|
||||
return(($return_code) ? $return_code : (-1));
|
||||
}
|
||||
|
||||
if($type === 'StatusMessage' || $type === 'Comment' || $type === 'Like') {
|
||||
$r = q("select * from item where guid = '%s' and uid = %d and not file like '%%[%%' limit 1",
|
||||
dbesc($guid),
|
||||
intval($importer['uid'])
|
||||
|
||||
/**
|
||||
* @brief Builds and transmit messages
|
||||
*
|
||||
* @param array $owner the array of the item owner
|
||||
* @param array $contact Target of the communication
|
||||
* @param string $type The message type
|
||||
* @param array $message The message data
|
||||
* @param bool $public_batch Is it a public post?
|
||||
* @param string $guid message guid
|
||||
* @param bool $spool Should the transmission be spooled or transmitted?
|
||||
*
|
||||
* @return int Result of the transmission
|
||||
*/
|
||||
private function build_and_transmit($owner, $contact, $type, $message, $public_batch = false, $guid = "", $spool = false) {
|
||||
|
||||
$data = array("XML" => array("post" => array($type => $message)));
|
||||
|
||||
$msg = xml::from_array($data, $xml);
|
||||
|
||||
logger('message: '.$msg, LOGGER_DATA);
|
||||
logger('send guid '.$guid, LOGGER_DEBUG);
|
||||
|
||||
$slap = self::build_message($msg, $owner, $contact, $owner['uprvkey'], $contact['pubkey'], $public_batch);
|
||||
|
||||
if ($spool) {
|
||||
add_to_queue($contact['id'], NETWORK_DIASPORA, $slap, $public_batch);
|
||||
return true;
|
||||
} else
|
||||
$return_code = self::transmit($owner, $contact, $slap, $public_batch, false, $guid);
|
||||
|
||||
logger("guid: ".$item["guid"]." result ".$return_code, LOGGER_DEBUG);
|
||||
|
||||
return $return_code;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Sends a "share" message
|
||||
*
|
||||
* @param array $owner the array of the item owner
|
||||
* @param array $contact Target of the communication
|
||||
*
|
||||
* @return int The result of the transmission
|
||||
*/
|
||||
public static function send_share($owner,$contact) {
|
||||
|
||||
$message = array("sender_handle" => self::my_handle($owner),
|
||||
"recipient_handle" => $contact["addr"]);
|
||||
|
||||
return self::build_and_transmit($owner, $contact, "request", $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief sends an "unshare"
|
||||
*
|
||||
* @param array $owner the array of the item owner
|
||||
* @param array $contact Target of the communication
|
||||
*
|
||||
* @return int The result of the transmission
|
||||
*/
|
||||
public static function send_unshare($owner,$contact) {
|
||||
|
||||
$message = array("post_guid" => $owner["guid"],
|
||||
"diaspora_handle" => self::my_handle($owner),
|
||||
"type" => "Person");
|
||||
|
||||
return self::build_and_transmit($owner, $contact, "retraction", $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Checks a message body if it is a reshare
|
||||
*
|
||||
* @param string $body The message body that is to be check
|
||||
* @param bool $complete Should it be a complete check or a simple check?
|
||||
*
|
||||
* @return array|bool Reshare details or "false" if no reshare
|
||||
*/
|
||||
public static function is_reshare($body, $complete = true) {
|
||||
$body = trim($body);
|
||||
|
||||
// Skip if it isn't a pure repeated messages
|
||||
// Does it start with a share?
|
||||
if (strpos($body, "[share") > 0)
|
||||
return(false);
|
||||
|
||||
// Does it end with a share?
|
||||
if (strlen($body) > (strrpos($body, "[/share]") + 8))
|
||||
return(false);
|
||||
|
||||
$attributes = preg_replace("/\[share(.*?)\]\s?(.*?)\s?\[\/share\]\s?/ism","$1",$body);
|
||||
// Skip if there is no shared message in there
|
||||
if ($body == $attributes)
|
||||
return(false);
|
||||
|
||||
// If we don't do the complete check we quit here
|
||||
if (!$complete)
|
||||
return true;
|
||||
|
||||
$guid = "";
|
||||
preg_match("/guid='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$guid = $matches[1];
|
||||
|
||||
preg_match('/guid="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$guid = $matches[1];
|
||||
|
||||
if ($guid != "") {
|
||||
$r = q("SELECT `contact-id` FROM `item` WHERE `guid` = '%s' AND `network` IN ('%s', '%s') LIMIT 1",
|
||||
dbesc($guid), NETWORK_DFRN, NETWORK_DIASPORA);
|
||||
if ($r) {
|
||||
$ret= array();
|
||||
$ret["root_handle"] = self::handle_from_contact($r[0]["contact-id"]);
|
||||
$ret["root_guid"] = $guid;
|
||||
return($ret);
|
||||
}
|
||||
}
|
||||
|
||||
$profile = "";
|
||||
preg_match("/profile='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$profile = $matches[1];
|
||||
|
||||
preg_match('/profile="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$profile = $matches[1];
|
||||
|
||||
$ret= array();
|
||||
|
||||
$ret["root_handle"] = preg_replace("=https?://(.*)/u/(.*)=ism", "$2@$1", $profile);
|
||||
if (($ret["root_handle"] == $profile) OR ($ret["root_handle"] == ""))
|
||||
return(false);
|
||||
|
||||
$link = "";
|
||||
preg_match("/link='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$link = $matches[1];
|
||||
|
||||
preg_match('/link="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$link = $matches[1];
|
||||
|
||||
$ret["root_guid"] = preg_replace("=https?://(.*)/posts/(.*)=ism", "$2", $link);
|
||||
if (($ret["root_guid"] == $link) OR (trim($ret["root_guid"]) == ""))
|
||||
return(false);
|
||||
|
||||
return($ret);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Sends a post
|
||||
*
|
||||
* @param array $item The item that will be exported
|
||||
* @param array $owner the array of the item owner
|
||||
* @param array $contact Target of the communication
|
||||
* @param bool $public_batch Is it a public post?
|
||||
*
|
||||
* @return int The result of the transmission
|
||||
*/
|
||||
public static function send_status($item, $owner, $contact, $public_batch = false) {
|
||||
|
||||
$myaddr = self::my_handle($owner);
|
||||
|
||||
$public = (($item["private"]) ? "false" : "true");
|
||||
|
||||
$created = datetime_convert("UTC", "UTC", $item["created"], 'Y-m-d H:i:s \U\T\C');
|
||||
|
||||
// Detect a share element and do a reshare
|
||||
if (!$item['private'] AND ($ret = self::is_reshare($item["body"]))) {
|
||||
$message = array("root_diaspora_id" => $ret["root_handle"],
|
||||
"root_guid" => $ret["root_guid"],
|
||||
"guid" => $item["guid"],
|
||||
"diaspora_handle" => $myaddr,
|
||||
"public" => $public,
|
||||
"created_at" => $created,
|
||||
"provider_display_name" => $item["app"]);
|
||||
|
||||
$type = "reshare";
|
||||
} else {
|
||||
$title = $item["title"];
|
||||
$body = $item["body"];
|
||||
|
||||
// convert to markdown
|
||||
$body = html_entity_decode(bb2diaspora($body));
|
||||
|
||||
// Adding the title
|
||||
if(strlen($title))
|
||||
$body = "## ".html_entity_decode($title)."\n\n".$body;
|
||||
|
||||
if ($item["attach"]) {
|
||||
$cnt = preg_match_all('/href=\"(.*?)\"(.*?)title=\"(.*?)\"/ism', $item["attach"], $matches, PREG_SET_ORDER);
|
||||
if(cnt) {
|
||||
$body .= "\n".t("Attachments:")."\n";
|
||||
foreach($matches as $mtch)
|
||||
$body .= "[".$mtch[3]."](".$mtch[1].")\n";
|
||||
}
|
||||
}
|
||||
|
||||
$location = array();
|
||||
|
||||
if ($item["location"] != "")
|
||||
$location["address"] = $item["location"];
|
||||
|
||||
if ($item["coord"] != "") {
|
||||
$coord = explode(" ", $item["coord"]);
|
||||
$location["lat"] = $coord[0];
|
||||
$location["lng"] = $coord[1];
|
||||
}
|
||||
|
||||
$message = array("raw_message" => $body,
|
||||
"location" => $location,
|
||||
"guid" => $item["guid"],
|
||||
"diaspora_handle" => $myaddr,
|
||||
"public" => $public,
|
||||
"created_at" => $created,
|
||||
"provider_display_name" => $item["app"]);
|
||||
|
||||
if (count($location) == 0)
|
||||
unset($message["location"]);
|
||||
|
||||
$type = "status_message";
|
||||
}
|
||||
|
||||
return self::build_and_transmit($owner, $contact, $type, $message, $public_batch, $item["guid"]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Creates a "like" object
|
||||
*
|
||||
* @param array $item The item that will be exported
|
||||
* @param array $owner the array of the item owner
|
||||
*
|
||||
* @return array The data for a "like"
|
||||
*/
|
||||
private function construct_like($item, $owner) {
|
||||
|
||||
$p = q("SELECT `guid`, `uri`, `parent-uri` FROM `item` WHERE `uri` = '%s' LIMIT 1",
|
||||
dbesc($item["thr-parent"]));
|
||||
if(!$p)
|
||||
return false;
|
||||
|
||||
$parent = $p[0];
|
||||
|
||||
$target_type = ($parent["uri"] === $parent["parent-uri"] ? "Post" : "Comment");
|
||||
$positive = "true";
|
||||
|
||||
return(array("positive" => $positive,
|
||||
"guid" => $item["guid"],
|
||||
"target_type" => $target_type,
|
||||
"parent_guid" => $parent["guid"],
|
||||
"author_signature" => "",
|
||||
"diaspora_handle" => self::my_handle($owner)));
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Creates the object for a comment
|
||||
*
|
||||
* @param array $item The item that will be exported
|
||||
* @param array $owner the array of the item owner
|
||||
*
|
||||
* @return array The data for a comment
|
||||
*/
|
||||
private function construct_comment($item, $owner) {
|
||||
|
||||
$p = q("SELECT `guid` FROM `item` WHERE `parent` = %d AND `id` = %d LIMIT 1",
|
||||
intval($item["parent"]),
|
||||
intval($item["parent"])
|
||||
);
|
||||
if(count($r)) {
|
||||
if(link_compare($r[0]['author-link'],$contact['url'])) {
|
||||
q("update item set `deleted` = 1, `edited` = '%s', `changed` = '%s', `body` = '' , `title` = '' where `id` = %d",
|
||||
dbesc(datetime_convert()),
|
||||
dbesc(datetime_convert()),
|
||||
intval($r[0]['id'])
|
||||
);
|
||||
delete_thread($r[0]['id'], $r[0]['parent-uri']);
|
||||
|
||||
// Now check if the retraction needs to be relayed by us
|
||||
//
|
||||
// The first item in the `item` table with the parent id is the parent. However, MySQL doesn't always
|
||||
// return the items ordered by `item`.`id`, in which case the wrong item is chosen as the parent.
|
||||
// The only item with `parent` and `id` as the parent id is the parent item.
|
||||
$p = q("SELECT `origin` FROM `item` WHERE `parent` = %d AND `id` = %d LIMIT 1",
|
||||
intval($r[0]['parent']),
|
||||
intval($r[0]['parent'])
|
||||
);
|
||||
if(count($p)) {
|
||||
if($p[0]['origin']) {
|
||||
q("insert into sign (`retract_iid`,`signed_text`,`signature`,`signer`) values (%d,'%s','%s','%s') ",
|
||||
$r[0]['id'],
|
||||
dbesc($signed_data),
|
||||
dbesc($sig),
|
||||
dbesc($diaspora_handle)
|
||||
);
|
||||
if (!$p)
|
||||
return false;
|
||||
|
||||
// the existence of parent_author_signature would have meant the parent_author or owner
|
||||
// is already relaying.
|
||||
logger('diaspora_signed_retraction: relaying relayable_retraction');
|
||||
$parent = $p[0];
|
||||
|
||||
proc_run('php','include/notifier.php','drop',$r[0]['id']);
|
||||
$text = html_entity_decode(bb2diaspora($item["body"]));
|
||||
|
||||
return(array("guid" => $item["guid"],
|
||||
"parent_guid" => $parent["guid"],
|
||||
"author_signature" => "",
|
||||
"text" => $text,
|
||||
"diaspora_handle" => self::my_handle($owner)));
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Send a like or a comment
|
||||
*
|
||||
* @param array $item The item that will be exported
|
||||
* @param array $owner the array of the item owner
|
||||
* @param array $contact Target of the communication
|
||||
* @param bool $public_batch Is it a public post?
|
||||
*
|
||||
* @return int The result of the transmission
|
||||
*/
|
||||
public static function send_followup($item,$owner,$contact,$public_batch = false) {
|
||||
|
||||
if($item['verb'] === ACTIVITY_LIKE) {
|
||||
$message = self::construct_like($item, $owner);
|
||||
$type = "like";
|
||||
} else {
|
||||
$message = self::construct_comment($item, $owner);
|
||||
$type = "comment";
|
||||
}
|
||||
|
||||
if (!$message)
|
||||
return false;
|
||||
|
||||
$message["author_signature"] = self::signature($owner, $message);
|
||||
|
||||
return self::build_and_transmit($owner, $contact, $type, $message, $public_batch, $item["guid"]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Creates a message from a signature record entry
|
||||
*
|
||||
* @param array $item The item that will be exported
|
||||
* @param array $signature The entry of the "sign" record
|
||||
*
|
||||
* @return string The message
|
||||
*/
|
||||
private function message_from_signature($item, $signature) {
|
||||
|
||||
// Split the signed text
|
||||
$signed_parts = explode(";", $signature['signed_text']);
|
||||
|
||||
if ($item["deleted"])
|
||||
$message = array("parent_author_signature" => "",
|
||||
"target_guid" => $signed_parts[0],
|
||||
"target_type" => $signed_parts[1],
|
||||
"sender_handle" => $signature['signer'],
|
||||
"target_author_signature" => $signature['signature']);
|
||||
elseif ($item['verb'] === ACTIVITY_LIKE)
|
||||
$message = array("positive" => $signed_parts[0],
|
||||
"guid" => $signed_parts[1],
|
||||
"target_type" => $signed_parts[2],
|
||||
"parent_guid" => $signed_parts[3],
|
||||
"parent_author_signature" => "",
|
||||
"author_signature" => $signature['signature'],
|
||||
"diaspora_handle" => $signed_parts[4]);
|
||||
else {
|
||||
// Remove the comment guid
|
||||
$guid = array_shift($signed_parts);
|
||||
|
||||
// Remove the parent guid
|
||||
$parent_guid = array_shift($signed_parts);
|
||||
|
||||
// Remove the handle
|
||||
$handle = array_pop($signed_parts);
|
||||
|
||||
// Glue the parts together
|
||||
$text = implode(";", $signed_parts);
|
||||
|
||||
$message = array("guid" => $guid,
|
||||
"parent_guid" => $parent_guid,
|
||||
"parent_author_signature" => "",
|
||||
"author_signature" => $signature['signature'],
|
||||
"text" => implode(";", $signed_parts),
|
||||
"diaspora_handle" => $handle);
|
||||
}
|
||||
return $message;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Relays messages (like, comment, retraction) to other servers if we are the thread owner
|
||||
*
|
||||
* @param array $item The item that will be exported
|
||||
* @param array $owner the array of the item owner
|
||||
* @param array $contact Target of the communication
|
||||
* @param bool $public_batch Is it a public post?
|
||||
*
|
||||
* @return int The result of the transmission
|
||||
*/
|
||||
public static function send_relay($item, $owner, $contact, $public_batch = false) {
|
||||
|
||||
if ($item["deleted"])
|
||||
return self::send_retraction($item, $owner, $contact, $public_batch, true);
|
||||
elseif ($item['verb'] === ACTIVITY_LIKE)
|
||||
$type = "like";
|
||||
else
|
||||
$type = "comment";
|
||||
|
||||
logger("Got relayable data ".$type." for item ".$item["guid"]." (".$item["id"].")", LOGGER_DEBUG);
|
||||
|
||||
// fetch the original signature
|
||||
|
||||
$r = q("SELECT `signed_text`, `signature`, `signer` FROM `sign` WHERE `iid` = %d LIMIT 1",
|
||||
intval($item["id"]));
|
||||
|
||||
if (!$r) {
|
||||
logger("Couldn't fetch signatur for item ".$item["guid"]." (".$item["id"].")", LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
|
||||
$signature = $r[0];
|
||||
|
||||
// Old way - is used by the internal Friendica functions
|
||||
/// @todo Change all signatur storing functions to the new format
|
||||
if ($signature['signed_text'] AND $signature['signature'] AND $signature['signer'])
|
||||
$message = self::message_from_signature($item, $signature);
|
||||
else {// New way
|
||||
$msg = json_decode($signature['signed_text'], true);
|
||||
|
||||
$message = array();
|
||||
if (is_array($msg)) {
|
||||
foreach ($msg AS $field => $data) {
|
||||
if (!$item["deleted"]) {
|
||||
if ($field == "author")
|
||||
$field = "diaspora_handle";
|
||||
if ($field == "parent_type")
|
||||
$field = "target_type";
|
||||
}
|
||||
|
||||
$message[$field] = $data;
|
||||
}
|
||||
} else
|
||||
logger("Signature text for item ".$item["guid"]." (".$item["id"].") couldn't be extracted: ".$signature['signed_text'], LOGGER_DEBUG);
|
||||
}
|
||||
|
||||
$message["parent_author_signature"] = self::signature($owner, $message);
|
||||
|
||||
logger("Relayed data ".print_r($message, true), LOGGER_DEBUG);
|
||||
|
||||
return self::build_and_transmit($owner, $contact, $type, $message, $public_batch, $item["guid"]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Sends a retraction (deletion) of a message, like or comment
|
||||
*
|
||||
* @param array $item The item that will be exported
|
||||
* @param array $owner the array of the item owner
|
||||
* @param array $contact Target of the communication
|
||||
* @param bool $public_batch Is it a public post?
|
||||
* @param bool $relay Is the retraction transmitted from a relay?
|
||||
*
|
||||
* @return int The result of the transmission
|
||||
*/
|
||||
public static function send_retraction($item, $owner, $contact, $public_batch = false, $relay = false) {
|
||||
|
||||
$itemaddr = self::handle_from_contact($item["contact-id"], $item["gcontact-id"]);
|
||||
|
||||
// Check whether the retraction is for a top-level post or whether it's a relayable
|
||||
if ($item["uri"] !== $item["parent-uri"]) {
|
||||
$msg_type = "relayable_retraction";
|
||||
$target_type = (($item["verb"] === ACTIVITY_LIKE) ? "Like" : "Comment");
|
||||
} else {
|
||||
$msg_type = "signed_retraction";
|
||||
$target_type = "StatusMessage";
|
||||
}
|
||||
|
||||
if ($relay AND ($item["uri"] !== $item["parent-uri"]))
|
||||
$signature = "parent_author_signature";
|
||||
else
|
||||
$signature = "target_author_signature";
|
||||
|
||||
$signed_text = $item["guid"].";".$target_type;
|
||||
|
||||
$message = array("target_guid" => $item['guid'],
|
||||
"target_type" => $target_type,
|
||||
"sender_handle" => $itemaddr,
|
||||
$signature => base64_encode(rsa_sign($signed_text,$owner['uprvkey'],'sha256')));
|
||||
|
||||
logger("Got message ".print_r($message, true), LOGGER_DEBUG);
|
||||
|
||||
return self::build_and_transmit($owner, $contact, $msg_type, $message, $public_batch, $item["guid"]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Sends a mail
|
||||
*
|
||||
* @param array $item The item that will be exported
|
||||
* @param array $owner The owner
|
||||
* @param array $contact Target of the communication
|
||||
*
|
||||
* @return int The result of the transmission
|
||||
*/
|
||||
public static function send_mail($item, $owner, $contact) {
|
||||
|
||||
$myaddr = self::my_handle($owner);
|
||||
|
||||
$r = q("SELECT * FROM `conv` WHERE `id` = %d AND `uid` = %d LIMIT 1",
|
||||
intval($item["convid"]),
|
||||
intval($item["uid"])
|
||||
);
|
||||
|
||||
if (!$r) {
|
||||
logger("conversation not found.");
|
||||
return;
|
||||
}
|
||||
$cnv = $r[0];
|
||||
|
||||
$conv = array(
|
||||
"guid" => $cnv["guid"],
|
||||
"subject" => $cnv["subject"],
|
||||
"created_at" => datetime_convert("UTC", "UTC", $cnv['created'], 'Y-m-d H:i:s \U\T\C'),
|
||||
"diaspora_handle" => $cnv["creator"],
|
||||
"participant_handles" => $cnv["recips"]
|
||||
);
|
||||
|
||||
$body = bb2diaspora($item["body"]);
|
||||
$created = datetime_convert("UTC", "UTC", $item["created"], 'Y-m-d H:i:s \U\T\C');
|
||||
|
||||
$signed_text = $item["guid"].";".$cnv["guid"].";".$body.";".$created.";".$myaddr.";".$cnv['guid'];
|
||||
$sig = base64_encode(rsa_sign($signed_text, $owner["uprvkey"], "sha256"));
|
||||
|
||||
$msg = array(
|
||||
"guid" => $item["guid"],
|
||||
"parent_guid" => $cnv["guid"],
|
||||
"parent_author_signature" => $sig,
|
||||
"author_signature" => $sig,
|
||||
"text" => $body,
|
||||
"created_at" => $created,
|
||||
"diaspora_handle" => $myaddr,
|
||||
"conversation_guid" => $cnv["guid"]
|
||||
);
|
||||
|
||||
if ($item["reply"]) {
|
||||
$message = $msg;
|
||||
$type = "message";
|
||||
} else {
|
||||
$message = array("guid" => $cnv["guid"],
|
||||
"subject" => $cnv["subject"],
|
||||
"created_at" => datetime_convert("UTC", "UTC", $cnv['created'], 'Y-m-d H:i:s \U\T\C'),
|
||||
"message" => $msg,
|
||||
"diaspora_handle" => $cnv["creator"],
|
||||
"participant_handles" => $cnv["recips"]);
|
||||
|
||||
$type = "conversation";
|
||||
}
|
||||
|
||||
return self::build_and_transmit($owner, $contact, $type, $message, false, $item["guid"]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Sends profile data
|
||||
*
|
||||
* @param int $uid The user id
|
||||
*/
|
||||
public static function send_profile($uid) {
|
||||
|
||||
if (!$uid)
|
||||
return;
|
||||
|
||||
$recips = q("SELECT `id`,`name`,`network`,`pubkey`,`notify` FROM `contact` WHERE `network` = '%s'
|
||||
AND `uid` = %d AND `rel` != %d",
|
||||
dbesc(NETWORK_DIASPORA),
|
||||
intval($uid),
|
||||
intval(CONTACT_IS_SHARING)
|
||||
);
|
||||
if (!$recips)
|
||||
return;
|
||||
|
||||
$r = q("SELECT `profile`.`uid` AS `profile_uid`, `profile`.* , `user`.*, `user`.`prvkey` AS `uprvkey`, `contact`.`addr`
|
||||
FROM `profile`
|
||||
INNER JOIN `user` ON `profile`.`uid` = `user`.`uid`
|
||||
INNER JOIN `contact` ON `profile`.`uid` = `contact`.`uid`
|
||||
WHERE `user`.`uid` = %d AND `profile`.`is-default` AND `contact`.`self` LIMIT 1",
|
||||
intval($uid)
|
||||
);
|
||||
|
||||
if (!$r)
|
||||
return;
|
||||
|
||||
$profile = $r[0];
|
||||
|
||||
$handle = $profile["addr"];
|
||||
$first = ((strpos($profile['name'],' ')
|
||||
? trim(substr($profile['name'],0,strpos($profile['name'],' '))) : $profile['name']));
|
||||
$last = (($first === $profile['name']) ? '' : trim(substr($profile['name'], strlen($first))));
|
||||
$large = App::get_baseurl().'/photo/custom/300/'.$profile['uid'].'.jpg';
|
||||
$medium = App::get_baseurl().'/photo/custom/100/'.$profile['uid'].'.jpg';
|
||||
$small = App::get_baseurl().'/photo/custom/50/' .$profile['uid'].'.jpg';
|
||||
$searchable = (($profile['publish'] && $profile['net-publish']) ? 'true' : 'false');
|
||||
|
||||
if ($searchable === 'true') {
|
||||
$dob = '1000-00-00';
|
||||
|
||||
if (($profile['dob']) && ($profile['dob'] != '0000-00-00'))
|
||||
$dob = ((intval($profile['dob'])) ? intval($profile['dob']) : '1000') .'-'. datetime_convert('UTC','UTC',$profile['dob'],'m-d');
|
||||
|
||||
$about = $profile['about'];
|
||||
$about = strip_tags(bbcode($about));
|
||||
|
||||
$location = formatted_location($profile);
|
||||
$tags = '';
|
||||
if ($profile['pub_keywords']) {
|
||||
$kw = str_replace(',',' ',$profile['pub_keywords']);
|
||||
$kw = str_replace(' ',' ',$kw);
|
||||
$arr = explode(' ',$profile['pub_keywords']);
|
||||
if (count($arr)) {
|
||||
for($x = 0; $x < 5; $x ++) {
|
||||
if (trim($arr[$x]))
|
||||
$tags .= '#'. trim($arr[$x]) .' ';
|
||||
}
|
||||
}
|
||||
}
|
||||
$tags = trim($tags);
|
||||
}
|
||||
}
|
||||
else
|
||||
logger('diaspora_signed_retraction: unknown type: ' . $type);
|
||||
|
||||
return 202;
|
||||
// NOTREACHED
|
||||
}
|
||||
$message = array("diaspora_handle" => $handle,
|
||||
"first_name" => $first,
|
||||
"last_name" => $last,
|
||||
"image_url" => $large,
|
||||
"image_url_medium" => $medium,
|
||||
"image_url_small" => $small,
|
||||
"birthday" => $dob,
|
||||
"gender" => $profile['gender'],
|
||||
"bio" => $about,
|
||||
"location" => $location,
|
||||
"searchable" => $searchable,
|
||||
"tag_string" => $tags);
|
||||
|
||||
function diaspora_profile($importer,$xml,$msg) {
|
||||
|
||||
$a = get_app();
|
||||
$diaspora_handle = notags(unxmlify($xml->diaspora_handle));
|
||||
|
||||
|
||||
if($diaspora_handle != $msg['author']) {
|
||||
logger('diaspora_post: Potential forgery. Message handle is not the same as envelope sender.');
|
||||
return 202;
|
||||
foreach($recips as $recip)
|
||||
self::build_and_transmit($profile, $recip, "profile", $message, false, "", true);
|
||||
}
|
||||
|
||||
$contact = diaspora_get_contact_by_handle($importer['uid'],$diaspora_handle);
|
||||
if(! $contact)
|
||||
return;
|
||||
/**
|
||||
* @brief Stores the signature for likes that are created on our system
|
||||
*
|
||||
* @param array $contact The contact array of the "like"
|
||||
* @param int $post_id The post id of the "like"
|
||||
*
|
||||
* @return bool Success
|
||||
*/
|
||||
public static function store_like_signature($contact, $post_id) {
|
||||
|
||||
//if($contact['blocked']) {
|
||||
// logger('diaspora_post: Ignoring this author.');
|
||||
// return 202;
|
||||
//}
|
||||
|
||||
$name = unxmlify($xml->first_name) . ((strlen($xml->last_name)) ? ' ' . unxmlify($xml->last_name) : '');
|
||||
$image_url = unxmlify($xml->image_url);
|
||||
$birthday = unxmlify($xml->birthday);
|
||||
$location = diaspora2bb(unxmlify($xml->location));
|
||||
$about = diaspora2bb(unxmlify($xml->bio));
|
||||
$gender = unxmlify($xml->gender);
|
||||
$searchable = (unxmlify($xml->searchable) == "true");
|
||||
$nsfw = (unxmlify($xml->nsfw) == "true");
|
||||
$tags = unxmlify($xml->tag_string);
|
||||
|
||||
$tags = explode("#", $tags);
|
||||
|
||||
$keywords = array();
|
||||
foreach ($tags as $tag) {
|
||||
$tag = trim(strtolower($tag));
|
||||
if ($tag != "")
|
||||
$keywords[] = $tag;
|
||||
}
|
||||
|
||||
$keywords = implode(", ", $keywords);
|
||||
|
||||
$handle_parts = explode("@", $diaspora_handle);
|
||||
$nick = $handle_parts[0];
|
||||
|
||||
if($name === '') {
|
||||
$name = $handle_parts[0];
|
||||
}
|
||||
|
||||
if( preg_match("|^https?://|", $image_url) === 0) {
|
||||
$image_url = "http://" . $handle_parts[1] . $image_url;
|
||||
}
|
||||
|
||||
/* $r = q("SELECT DISTINCT ( `resource-id` ) FROM `photo` WHERE `uid` = %d AND `contact-id` = %d AND `album` = 'Contact Photos' ",
|
||||
intval($importer['uid']),
|
||||
intval($contact['id'])
|
||||
);
|
||||
$oldphotos = ((count($r)) ? $r : null);*/
|
||||
|
||||
require_once('include/Photo.php');
|
||||
|
||||
update_contact_avatar($image_url,$importer['uid'],$contact['id']);
|
||||
|
||||
// Generic birthday. We don't know the timezone. The year is irrelevant.
|
||||
|
||||
$birthday = str_replace('1000','1901',$birthday);
|
||||
|
||||
if ($birthday != "")
|
||||
$birthday = datetime_convert('UTC','UTC',$birthday,'Y-m-d');
|
||||
|
||||
// this is to prevent multiple birthday notifications in a single year
|
||||
// if we already have a stored birthday and the 'm-d' part hasn't changed, preserve the entry, which will preserve the notify year
|
||||
|
||||
if(substr($birthday,5) === substr($contact['bd'],5))
|
||||
$birthday = $contact['bd'];
|
||||
|
||||
/// @TODO Update name on item['author-name'] if the name changed. See consume_feed()
|
||||
/// (Not doing this currently because D* protocol is scheduled for revision soon).
|
||||
|
||||
$r = q("UPDATE `contact` SET `name` = '%s', `nick` = '%s', `addr` = '%s', `name-date` = '%s', `bd` = '%s',
|
||||
`location` = '%s', `about` = '%s', `keywords` = '%s', `gender` = '%s' WHERE `id` = %d AND `uid` = %d",
|
||||
dbesc($name),
|
||||
dbesc($nick),
|
||||
dbesc($diaspora_handle),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc($birthday),
|
||||
dbesc($location),
|
||||
dbesc($about),
|
||||
dbesc($keywords),
|
||||
dbesc($gender),
|
||||
intval($contact['id']),
|
||||
intval($importer['uid'])
|
||||
);
|
||||
|
||||
if ($searchable) {
|
||||
require_once('include/socgraph.php');
|
||||
poco_check($contact['url'], $name, NETWORK_DIASPORA, $image_url, $about, $location, $gender, $keywords, "",
|
||||
datetime_convert(), 2, $contact['id'], $importer['uid']);
|
||||
}
|
||||
|
||||
update_gcontact(array("url" => $contact['url'], "network" => NETWORK_DIASPORA, "generation" => 2,
|
||||
"photo" => $image_url, "name" => $name, "location" => $location,
|
||||
"about" => $about, "birthday" => $birthday, "gender" => $gender,
|
||||
"addr" => $diaspora_handle, "nick" => $nick, "keywords" => $keywords,
|
||||
"hide" => !$searchable, "nsfw" => $nsfw));
|
||||
|
||||
/* if($r) {
|
||||
if($oldphotos) {
|
||||
foreach($oldphotos as $ph) {
|
||||
q("DELETE FROM `photo` WHERE `uid` = %d AND `contact-id` = %d AND `album` = 'Contact Photos' AND `resource-id` = '%s' ",
|
||||
intval($importer['uid']),
|
||||
intval($contact['id']),
|
||||
dbesc($ph['resource-id'])
|
||||
);
|
||||
}
|
||||
$enabled = intval(get_config('system','diaspora_enabled'));
|
||||
if (!$enabled) {
|
||||
logger('Diaspora support disabled, not storing like signature', LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
} */
|
||||
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
function diaspora_share($me,$contact) {
|
||||
$a = get_app();
|
||||
$myaddr = $me['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3);
|
||||
$theiraddr = $contact['addr'];
|
||||
|
||||
$tpl = get_markup_template('diaspora_share.tpl');
|
||||
$msg = replace_macros($tpl, array(
|
||||
'$sender' => $myaddr,
|
||||
'$recipient' => $theiraddr
|
||||
));
|
||||
|
||||
$slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$me,$contact,$me['prvkey'],$contact['pubkey'])));
|
||||
//$slap = 'xml=' . urlencode(diaspora_msg_build($msg,$me,$contact,$me['prvkey'],$contact['pubkey']));
|
||||
|
||||
return(diaspora_transmit($owner,$contact,$slap, false));
|
||||
}
|
||||
|
||||
function diaspora_unshare($me,$contact) {
|
||||
|
||||
$a = get_app();
|
||||
$myaddr = $me['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3);
|
||||
|
||||
$tpl = get_markup_template('diaspora_retract.tpl');
|
||||
$msg = replace_macros($tpl, array(
|
||||
'$guid' => $me['guid'],
|
||||
'$type' => 'Person',
|
||||
'$handle' => $myaddr
|
||||
));
|
||||
|
||||
$slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$me,$contact,$me['prvkey'],$contact['pubkey'])));
|
||||
//$slap = 'xml=' . urlencode(diaspora_msg_build($msg,$me,$contact,$me['prvkey'],$contact['pubkey']));
|
||||
|
||||
return(diaspora_transmit($owner,$contact,$slap, false));
|
||||
|
||||
}
|
||||
|
||||
|
||||
function diaspora_send_status($item,$owner,$contact,$public_batch = false) {
|
||||
|
||||
$a = get_app();
|
||||
$myaddr = $owner['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3);
|
||||
$theiraddr = $contact['addr'];
|
||||
|
||||
$images = array();
|
||||
|
||||
$title = $item['title'];
|
||||
$body = $item['body'];
|
||||
|
||||
/*
|
||||
// We're trying to match Diaspora's split message/photo protocol but
|
||||
// all the photos are displayed on D* as links and not img's - even
|
||||
// though we're sending pretty much precisely what they send us when
|
||||
// doing the same operation.
|
||||
// Commented out for now, we'll use bb2diaspora to convert photos to markdown
|
||||
// which seems to get through intact.
|
||||
|
||||
$cnt = preg_match_all('|\[img\](.*?)\[\/img\]|',$body,$matches,PREG_SET_ORDER);
|
||||
if($cnt) {
|
||||
foreach($matches as $mtch) {
|
||||
$detail = array();
|
||||
$detail['str'] = $mtch[0];
|
||||
$detail['path'] = dirname($mtch[1]) . '/';
|
||||
$detail['file'] = basename($mtch[1]);
|
||||
$detail['guid'] = $item['guid'];
|
||||
$detail['handle'] = $myaddr;
|
||||
$images[] = $detail;
|
||||
$body = str_replace($detail['str'],$mtch[1],$body);
|
||||
// Is the contact the owner? Then fetch the private key
|
||||
if (!$contact['self'] OR ($contact['uid'] == 0)) {
|
||||
logger("No owner post, so not storing signature", LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
*/
|
||||
|
||||
//if(strlen($title))
|
||||
// $body = "[b]".html_entity_decode($title)."[/b]\n\n".$body;
|
||||
$r = q("SELECT `prvkey` FROM `user` WHERE `uid` = %d LIMIT 1", intval($contact['uid']));
|
||||
if(!$r)
|
||||
return false;
|
||||
|
||||
// convert to markdown
|
||||
$body = xmlify(html_entity_decode(bb2diaspora($body)));
|
||||
//$body = bb2diaspora($body);
|
||||
$contact["uprvkey"] = $r[0]['prvkey'];
|
||||
|
||||
// Adding the title
|
||||
if(strlen($title))
|
||||
$body = "## ".html_entity_decode($title)."\n\n".$body;
|
||||
$r = q("SELECT * FROM `item` WHERE `id` = %d LIMIT 1", intval($post_id));
|
||||
if (!$r)
|
||||
return false;
|
||||
|
||||
if($item['attach']) {
|
||||
$cnt = preg_match_all('/href=\"(.*?)\"(.*?)title=\"(.*?)\"/ism',$item['attach'],$matches,PREG_SET_ORDER);
|
||||
if(cnt) {
|
||||
$body .= "\n" . t('Attachments:') . "\n";
|
||||
foreach($matches as $mtch) {
|
||||
$body .= '[' . $mtch[3] . '](' . $mtch[1] . ')' . "\n";
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!in_array($r[0]["verb"], array(ACTIVITY_LIKE, ACTIVITY_DISLIKE)))
|
||||
return false;
|
||||
|
||||
$message = self::construct_like($r[0], $contact);
|
||||
$message["author_signature"] = self::signature($contact, $message);
|
||||
|
||||
$public = (($item['private']) ? 'false' : 'true');
|
||||
// In the future we will store the signature more flexible to support new fields.
|
||||
// Right now we cannot change this since old Friendica versions (prior to 3.5) can only handle this format.
|
||||
// (We are transmitting this data here via DFRN)
|
||||
|
||||
require_once('include/datetime.php');
|
||||
$created = datetime_convert('UTC','UTC',$item['created'],'Y-m-d H:i:s \U\T\C');
|
||||
$signed_text = $message["positive"].";".$message["guid"].";".$message["target_type"].";".
|
||||
$message["parent_guid"].";".$message["diaspora_handle"];
|
||||
|
||||
// Detect a share element and do a reshare
|
||||
// see: https://github.com/Raven24/diaspora-federation/blob/master/lib/diaspora-federation/entities/reshare.rb
|
||||
if (!$item['private'] AND ($ret = diaspora_is_reshare($item["body"]))) {
|
||||
$tpl = get_markup_template('diaspora_reshare.tpl');
|
||||
$msg = replace_macros($tpl, array(
|
||||
'$root_handle' => xmlify($ret['root_handle']),
|
||||
'$root_guid' => $ret['root_guid'],
|
||||
'$guid' => $item['guid'],
|
||||
'$handle' => xmlify($myaddr),
|
||||
'$public' => $public,
|
||||
'$created' => $created,
|
||||
'$provider' => $item["app"]
|
||||
));
|
||||
} else {
|
||||
$tpl = get_markup_template('diaspora_post.tpl');
|
||||
$msg = replace_macros($tpl, array(
|
||||
'$body' => $body,
|
||||
'$guid' => $item['guid'],
|
||||
'$handle' => xmlify($myaddr),
|
||||
'$public' => $public,
|
||||
'$created' => $created,
|
||||
'$provider' => $item["app"]
|
||||
));
|
||||
}
|
||||
|
||||
logger('diaspora_send_status: '.$owner['username'].' -> '.$contact['name'].' base message: '.$msg, LOGGER_DATA);
|
||||
logger('send guid '.$item['guid'], LOGGER_DEBUG);
|
||||
|
||||
$slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch)));
|
||||
//$slap = 'xml=' . urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch));
|
||||
|
||||
$return_code = diaspora_transmit($owner,$contact,$slap,$public_batch,false,$item['guid']);
|
||||
|
||||
logger('diaspora_send_status: guid: '.$item['guid'].' result '.$return_code, LOGGER_DEBUG);
|
||||
|
||||
if(count($images)) {
|
||||
diaspora_send_images($item,$owner,$contact,$images,$public_batch);
|
||||
}
|
||||
|
||||
return $return_code;
|
||||
}
|
||||
|
||||
function diaspora_is_reshare($body) {
|
||||
$body = trim($body);
|
||||
|
||||
// Skip if it isn't a pure repeated messages
|
||||
// Does it start with a share?
|
||||
if (strpos($body, "[share") > 0)
|
||||
return(false);
|
||||
|
||||
// Does it end with a share?
|
||||
if (strlen($body) > (strrpos($body, "[/share]") + 8))
|
||||
return(false);
|
||||
|
||||
$attributes = preg_replace("/\[share(.*?)\]\s?(.*?)\s?\[\/share\]\s?/ism","$1",$body);
|
||||
// Skip if there is no shared message in there
|
||||
if ($body == $attributes)
|
||||
return(false);
|
||||
|
||||
$guid = "";
|
||||
preg_match("/guid='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$guid = $matches[1];
|
||||
|
||||
preg_match('/guid="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$guid = $matches[1];
|
||||
|
||||
if ($guid != "") {
|
||||
$r = q("SELECT `contact-id` FROM `item` WHERE `guid` = '%s' AND `network` IN ('%s', '%s') LIMIT 1",
|
||||
dbesc($guid), NETWORK_DFRN, NETWORK_DIASPORA);
|
||||
if ($r) {
|
||||
$ret= array();
|
||||
$ret["root_handle"] = diaspora_handle_from_contact($r[0]["contact-id"]);
|
||||
$ret["root_guid"] = $guid;
|
||||
return($ret);
|
||||
}
|
||||
}
|
||||
|
||||
$profile = "";
|
||||
preg_match("/profile='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$profile = $matches[1];
|
||||
|
||||
preg_match('/profile="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$profile = $matches[1];
|
||||
|
||||
$ret= array();
|
||||
|
||||
$ret["root_handle"] = preg_replace("=https?://(.*)/u/(.*)=ism", "$2@$1", $profile);
|
||||
if (($ret["root_handle"] == $profile) OR ($ret["root_handle"] == ""))
|
||||
return(false);
|
||||
|
||||
$link = "";
|
||||
preg_match("/link='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$link = $matches[1];
|
||||
|
||||
preg_match('/link="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$link = $matches[1];
|
||||
|
||||
$ret["root_guid"] = preg_replace("=https?://(.*)/posts/(.*)=ism", "$2", $link);
|
||||
if (($ret["root_guid"] == $link) OR ($ret["root_guid"] == ""))
|
||||
return(false);
|
||||
|
||||
return($ret);
|
||||
}
|
||||
|
||||
function diaspora_send_images($item,$owner,$contact,$images,$public_batch = false) {
|
||||
$a = get_app();
|
||||
if(! count($images))
|
||||
return;
|
||||
$mysite = substr($a->get_baseurl(),strpos($a->get_baseurl(),'://') + 3) . '/photo';
|
||||
|
||||
$tpl = get_markup_template('diaspora_photo.tpl');
|
||||
foreach($images as $image) {
|
||||
if(! stristr($image['path'],$mysite))
|
||||
continue;
|
||||
$resource = str_replace('.jpg','',$image['file']);
|
||||
$resource = substr($resource,0,strpos($resource,'-'));
|
||||
|
||||
$r = q("select * from photo where `resource-id` = '%s' and `uid` = %d limit 1",
|
||||
dbesc($resource),
|
||||
intval($owner['uid'])
|
||||
q("INSERT INTO `sign` (`iid`,`signed_text`,`signature`,`signer`) VALUES (%d,'%s','%s','%s')",
|
||||
intval($post_id),
|
||||
dbesc($signed_text),
|
||||
dbesc($message["author_signature"]),
|
||||
dbesc($message["diaspora_handle"])
|
||||
);
|
||||
if(! count($r))
|
||||
continue;
|
||||
$public = (($r[0]['allow_cid'] || $r[0]['allow_gid'] || $r[0]['deny_cid'] || $r[0]['deny_gid']) ? 'false' : 'true' );
|
||||
$msg = replace_macros($tpl,array(
|
||||
'$path' => xmlify($image['path']),
|
||||
'$filename' => xmlify($image['file']),
|
||||
'$msg_guid' => xmlify($image['guid']),
|
||||
'$guid' => xmlify($r[0]['guid']),
|
||||
'$handle' => xmlify($image['handle']),
|
||||
'$public' => xmlify($public),
|
||||
'$created_at' => xmlify(datetime_convert('UTC','UTC',$r[0]['created'],'Y-m-d H:i:s \U\T\C'))
|
||||
));
|
||||
|
||||
// This here will replace the lines above, once Diaspora changed its protocol
|
||||
//q("INSERT INTO `sign` (`iid`,`signed_text`) VALUES (%d,'%s')",
|
||||
// intval($message_id),
|
||||
// dbesc(json_encode($message))
|
||||
//);
|
||||
|
||||
logger('diaspora_send_photo: base message: ' . $msg, LOGGER_DATA);
|
||||
logger('send guid '.$r[0]['guid'], LOGGER_DEBUG);
|
||||
|
||||
$slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch)));
|
||||
//$slap = 'xml=' . urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch));
|
||||
|
||||
diaspora_transmit($owner,$contact,$slap,$public_batch,false,$r[0]['guid']);
|
||||
logger('Stored diaspora like signature');
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
/**
|
||||
* @brief Stores the signature for comments that are created on our system
|
||||
*
|
||||
* @param array $item The item array of the comment
|
||||
* @param array $contact The contact array of the item owner
|
||||
* @param string $uprvkey The private key of the sender
|
||||
* @param int $message_id The message id of the comment
|
||||
*
|
||||
* @return bool Success
|
||||
*/
|
||||
public static function store_comment_signature($item, $contact, $uprvkey, $message_id) {
|
||||
|
||||
function diaspora_send_followup($item,$owner,$contact,$public_batch = false) {
|
||||
if ($uprvkey == "") {
|
||||
logger('No private key, so not storing comment signature', LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
|
||||
$a = get_app();
|
||||
$myaddr = $owner['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3);
|
||||
// $theiraddr = $contact['addr'];
|
||||
$enabled = intval(get_config('system','diaspora_enabled'));
|
||||
if (!$enabled) {
|
||||
logger('Diaspora support disabled, not storing comment signature', LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Diaspora doesn't support threaded comments, but some
|
||||
// versions of Diaspora (i.e. Diaspora-pistos) support
|
||||
// likes on comments
|
||||
if($item['verb'] === ACTIVITY_LIKE && $item['thr-parent']) {
|
||||
$p = q("select guid, type, uri, `parent-uri` from item where uri = '%s' limit 1",
|
||||
dbesc($item['thr-parent'])
|
||||
);
|
||||
}
|
||||
else {
|
||||
// The first item in the `item` table with the parent id is the parent. However, MySQL doesn't always
|
||||
// return the items ordered by `item`.`id`, in which case the wrong item is chosen as the parent.
|
||||
// The only item with `parent` and `id` as the parent id is the parent item.
|
||||
$p = q("select guid, type, uri, `parent-uri` from item where parent = %d and id = %d limit 1",
|
||||
intval($item['parent']),
|
||||
intval($item['parent'])
|
||||
$contact["uprvkey"] = $uprvkey;
|
||||
|
||||
$message = self::construct_comment($item, $contact);
|
||||
$message["author_signature"] = self::signature($contact, $message);
|
||||
|
||||
// In the future we will store the signature more flexible to support new fields.
|
||||
// Right now we cannot change this since old Friendica versions (prior to 3.5) can only handle this format.
|
||||
// (We are transmitting this data here via DFRN)
|
||||
$signed_text = $message["guid"].";".$message["parent_guid"].";".
|
||||
$message["text"].";".$message["diaspora_handle"];
|
||||
|
||||
q("INSERT INTO `sign` (`iid`,`signed_text`,`signature`,`signer`) VALUES (%d,'%s','%s','%s')",
|
||||
intval($message_id),
|
||||
dbesc($signed_text),
|
||||
dbesc($message["author_signature"]),
|
||||
dbesc($message["diaspora_handle"])
|
||||
);
|
||||
|
||||
// This here will replace the lines above, once Diaspora changed its protocol
|
||||
//q("INSERT INTO `sign` (`iid`,`signed_text`) VALUES (%d,'%s')",
|
||||
// intval($message_id),
|
||||
// dbesc(json_encode($message))
|
||||
//);
|
||||
|
||||
logger('Stored diaspora comment signature');
|
||||
return true;
|
||||
}
|
||||
if(count($p))
|
||||
$parent = $p[0];
|
||||
else
|
||||
return;
|
||||
|
||||
if($item['verb'] === ACTIVITY_LIKE) {
|
||||
$tpl = get_markup_template('diaspora_like.tpl');
|
||||
$like = true;
|
||||
$target_type = ( $parent['uri'] === $parent['parent-uri'] ? 'Post' : 'Comment');
|
||||
// $target_type = (strpos($parent['type'], 'comment') ? 'Comment' : 'Post');
|
||||
// $positive = (($item['deleted']) ? 'false' : 'true');
|
||||
$positive = 'true';
|
||||
|
||||
if(($item['deleted']))
|
||||
logger('diaspora_send_followup: received deleted "like". Those should go to diaspora_send_retraction');
|
||||
}
|
||||
else {
|
||||
$tpl = get_markup_template('diaspora_comment.tpl');
|
||||
$like = false;
|
||||
}
|
||||
|
||||
$text = html_entity_decode(bb2diaspora($item['body']));
|
||||
|
||||
// sign it
|
||||
|
||||
if($like)
|
||||
$signed_text = $positive . ';' . $item['guid'] . ';' . $target_type . ';' . $parent['guid'] . ';' . $myaddr;
|
||||
else
|
||||
$signed_text = $item['guid'] . ';' . $parent['guid'] . ';' . $text . ';' . $myaddr;
|
||||
|
||||
$authorsig = base64_encode(rsa_sign($signed_text,$owner['uprvkey'],'sha256'));
|
||||
|
||||
$msg = replace_macros($tpl,array(
|
||||
'$guid' => xmlify($item['guid']),
|
||||
'$parent_guid' => xmlify($parent['guid']),
|
||||
'$target_type' =>xmlify($target_type),
|
||||
'$authorsig' => xmlify($authorsig),
|
||||
'$body' => xmlify($text),
|
||||
'$positive' => xmlify($positive),
|
||||
'$handle' => xmlify($myaddr)
|
||||
));
|
||||
|
||||
logger('diaspora_followup: base message: ' . $msg, LOGGER_DATA);
|
||||
logger('send guid '.$item['guid'], LOGGER_DEBUG);
|
||||
|
||||
$slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch)));
|
||||
//$slap = 'xml=' . urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch));
|
||||
|
||||
return(diaspora_transmit($owner,$contact,$slap,$public_batch,false,$item['guid']));
|
||||
}
|
||||
|
||||
|
||||
function diaspora_send_relay($item,$owner,$contact,$public_batch = false) {
|
||||
|
||||
|
||||
$a = get_app();
|
||||
$myaddr = $owner['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3);
|
||||
// $theiraddr = $contact['addr'];
|
||||
|
||||
// Diaspora doesn't support threaded comments, but some
|
||||
// versions of Diaspora (i.e. Diaspora-pistos) support
|
||||
// likes on comments
|
||||
if($item['verb'] === ACTIVITY_LIKE && $item['thr-parent']) {
|
||||
$p = q("select guid, type, uri, `parent-uri` from item where uri = '%s' limit 1",
|
||||
dbesc($item['thr-parent'])
|
||||
);
|
||||
}
|
||||
else {
|
||||
// The first item in the `item` table with the parent id is the parent. However, MySQL doesn't always
|
||||
// return the items ordered by `item`.`id`, in which case the wrong item is chosen as the parent.
|
||||
// The only item with `parent` and `id` as the parent id is the parent item.
|
||||
$p = q("select guid, type, uri, `parent-uri` from item where parent = %d and id = %d limit 1",
|
||||
intval($item['parent']),
|
||||
intval($item['parent'])
|
||||
);
|
||||
}
|
||||
if(count($p))
|
||||
$parent = $p[0];
|
||||
else
|
||||
return;
|
||||
|
||||
$like = false;
|
||||
$relay_retract = false;
|
||||
$sql_sign_id = 'iid';
|
||||
if( $item['deleted']) {
|
||||
$relay_retract = true;
|
||||
|
||||
$target_type = ( ($item['verb'] === ACTIVITY_LIKE) ? 'Like' : 'Comment');
|
||||
|
||||
$sql_sign_id = 'retract_iid';
|
||||
$tpl = get_markup_template('diaspora_relayable_retraction.tpl');
|
||||
}
|
||||
elseif($item['verb'] === ACTIVITY_LIKE) {
|
||||
$like = true;
|
||||
|
||||
$target_type = ( $parent['uri'] === $parent['parent-uri'] ? 'Post' : 'Comment');
|
||||
// $positive = (($item['deleted']) ? 'false' : 'true');
|
||||
$positive = 'true';
|
||||
|
||||
$tpl = get_markup_template('diaspora_like_relay.tpl');
|
||||
}
|
||||
else { // item is a comment
|
||||
$tpl = get_markup_template('diaspora_comment_relay.tpl');
|
||||
}
|
||||
|
||||
|
||||
// fetch the original signature if the relayable was created by a Diaspora
|
||||
// or DFRN user. Relayables for other networks are not supported.
|
||||
|
||||
$r = q("SELECT `signed_text`, `signature`, `signer` FROM `sign` WHERE " . $sql_sign_id . " = %d LIMIT 1",
|
||||
intval($item['id'])
|
||||
);
|
||||
if(count($r)) {
|
||||
$orig_sign = $r[0];
|
||||
$signed_text = $orig_sign['signed_text'];
|
||||
$authorsig = $orig_sign['signature'];
|
||||
$handle = $orig_sign['signer'];
|
||||
|
||||
// Split the signed text
|
||||
$signed_parts = explode(";", $signed_text);
|
||||
|
||||
// Remove the parent guid
|
||||
array_shift($signed_parts);
|
||||
|
||||
// Remove the comment guid
|
||||
array_shift($signed_parts);
|
||||
|
||||
// Remove the handle
|
||||
array_pop($signed_parts);
|
||||
|
||||
// Glue the parts together
|
||||
$text = implode(";", $signed_parts);
|
||||
}
|
||||
else {
|
||||
// This part is meant for cases where we don't have the signatur. (Which shouldn't happen with posts from Diaspora and Friendica)
|
||||
// This means that the comment won't be accepted by newer Diaspora servers
|
||||
|
||||
$body = $item['body'];
|
||||
$text = html_entity_decode(bb2diaspora($body));
|
||||
|
||||
$handle = diaspora_handle_from_contact($item['contact-id']);
|
||||
if(! $handle)
|
||||
return;
|
||||
|
||||
if($relay_retract)
|
||||
$signed_text = $item['guid'] . ';' . $target_type;
|
||||
elseif($like)
|
||||
$signed_text = $item['guid'] . ';' . $target_type . ';' . $parent['guid'] . ';' . $positive . ';' . $handle;
|
||||
else
|
||||
$signed_text = $item['guid'] . ';' . $parent['guid'] . ';' . $text . ';' . $handle;
|
||||
|
||||
$authorsig = base64_encode(rsa_sign($signed_text,$owner['uprvkey'],'sha256'));
|
||||
}
|
||||
|
||||
// Sign the relayable with the top-level owner's signature
|
||||
$parentauthorsig = base64_encode(rsa_sign($signed_text,$owner['uprvkey'],'sha256'));
|
||||
|
||||
$msg = replace_macros($tpl,array(
|
||||
'$guid' => xmlify($item['guid']),
|
||||
'$parent_guid' => xmlify($parent['guid']),
|
||||
'$target_type' =>xmlify($target_type),
|
||||
'$authorsig' => xmlify($authorsig),
|
||||
'$parentsig' => xmlify($parentauthorsig),
|
||||
'$body' => xmlify($text),
|
||||
'$positive' => xmlify($positive),
|
||||
'$handle' => xmlify($handle)
|
||||
));
|
||||
|
||||
logger('diaspora_send_relay: base message: ' . $msg, LOGGER_DATA);
|
||||
logger('send guid '.$item['guid'], LOGGER_DEBUG);
|
||||
|
||||
$slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch)));
|
||||
//$slap = 'xml=' . urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch));
|
||||
|
||||
return(diaspora_transmit($owner,$contact,$slap,$public_batch,false,$item['guid']));
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
function diaspora_send_retraction($item,$owner,$contact,$public_batch = false) {
|
||||
|
||||
$a = get_app();
|
||||
$myaddr = $owner['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3);
|
||||
|
||||
// Check whether the retraction is for a top-level post or whether it's a relayable
|
||||
if( $item['uri'] !== $item['parent-uri'] ) {
|
||||
|
||||
$tpl = get_markup_template('diaspora_relay_retraction.tpl');
|
||||
$target_type = (($item['verb'] === ACTIVITY_LIKE) ? 'Like' : 'Comment');
|
||||
}
|
||||
else {
|
||||
|
||||
$tpl = get_markup_template('diaspora_signed_retract.tpl');
|
||||
$target_type = 'StatusMessage';
|
||||
}
|
||||
|
||||
$signed_text = $item['guid'] . ';' . $target_type;
|
||||
|
||||
$msg = replace_macros($tpl, array(
|
||||
'$guid' => xmlify($item['guid']),
|
||||
'$type' => xmlify($target_type),
|
||||
'$handle' => xmlify($myaddr),
|
||||
'$signature' => xmlify(base64_encode(rsa_sign($signed_text,$owner['uprvkey'],'sha256')))
|
||||
));
|
||||
|
||||
logger('send guid '.$item['guid'], LOGGER_DEBUG);
|
||||
|
||||
$slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch)));
|
||||
//$slap = 'xml=' . urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch));
|
||||
|
||||
return(diaspora_transmit($owner,$contact,$slap,$public_batch,false,$item['guid']));
|
||||
}
|
||||
|
||||
function diaspora_send_mail($item,$owner,$contact) {
|
||||
|
||||
$a = get_app();
|
||||
$myaddr = $owner['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3);
|
||||
|
||||
$r = q("select * from conv where id = %d and uid = %d limit 1",
|
||||
intval($item['convid']),
|
||||
intval($item['uid'])
|
||||
);
|
||||
|
||||
if(! count($r)) {
|
||||
logger('diaspora_send_mail: conversation not found.');
|
||||
return;
|
||||
}
|
||||
$cnv = $r[0];
|
||||
|
||||
$conv = array(
|
||||
'guid' => xmlify($cnv['guid']),
|
||||
'subject' => xmlify($cnv['subject']),
|
||||
'created_at' => xmlify(datetime_convert('UTC','UTC',$cnv['created'],'Y-m-d H:i:s \U\T\C')),
|
||||
'diaspora_handle' => xmlify($cnv['creator']),
|
||||
'participant_handles' => xmlify($cnv['recips'])
|
||||
);
|
||||
|
||||
$body = bb2diaspora($item['body']);
|
||||
$created = datetime_convert('UTC','UTC',$item['created'],'Y-m-d H:i:s \U\T\C');
|
||||
|
||||
$signed_text = $item['guid'] . ';' . $cnv['guid'] . ';' . $body . ';'
|
||||
. $created . ';' . $myaddr . ';' . $cnv['guid'];
|
||||
|
||||
$sig = base64_encode(rsa_sign($signed_text,$owner['uprvkey'],'sha256'));
|
||||
|
||||
$msg = array(
|
||||
'guid' => xmlify($item['guid']),
|
||||
'parent_guid' => xmlify($cnv['guid']),
|
||||
'parent_author_signature' => xmlify($sig),
|
||||
'author_signature' => xmlify($sig),
|
||||
'text' => xmlify($body),
|
||||
'created_at' => xmlify($created),
|
||||
'diaspora_handle' => xmlify($myaddr),
|
||||
'conversation_guid' => xmlify($cnv['guid'])
|
||||
);
|
||||
|
||||
if($item['reply']) {
|
||||
$tpl = get_markup_template('diaspora_message.tpl');
|
||||
$xmsg = replace_macros($tpl, array('$msg' => $msg));
|
||||
}
|
||||
else {
|
||||
$conv['messages'] = array($msg);
|
||||
$tpl = get_markup_template('diaspora_conversation.tpl');
|
||||
$xmsg = replace_macros($tpl, array('$conv' => $conv));
|
||||
}
|
||||
|
||||
logger('diaspora_conversation: ' . print_r($xmsg,true), LOGGER_DATA);
|
||||
logger('send guid '.$item['guid'], LOGGER_DEBUG);
|
||||
|
||||
$slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($xmsg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],false)));
|
||||
//$slap = 'xml=' . urlencode(diaspora_msg_build($xmsg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],false));
|
||||
|
||||
return(diaspora_transmit($owner,$contact,$slap,false,false,$item['guid']));
|
||||
|
||||
|
||||
}
|
||||
|
||||
function diaspora_transmit($owner,$contact,$slap,$public_batch,$queue_run=false,$guid = "") {
|
||||
|
||||
$enabled = intval(get_config('system','diaspora_enabled'));
|
||||
if(! $enabled) {
|
||||
return 200;
|
||||
}
|
||||
|
||||
$a = get_app();
|
||||
$logid = random_string(4);
|
||||
$dest_url = (($public_batch) ? $contact['batch'] : $contact['notify']);
|
||||
if(! $dest_url) {
|
||||
logger('diaspora_transmit: no url for contact: ' . $contact['id'] . ' batch mode =' . $public_batch);
|
||||
return 0;
|
||||
}
|
||||
|
||||
logger('diaspora_transmit: '.$logid.'-'.$guid.' '.$dest_url);
|
||||
|
||||
if( (! $queue_run) && (was_recently_delayed($contact['id'])) ) {
|
||||
$return_code = 0;
|
||||
}
|
||||
else {
|
||||
if (!intval(get_config('system','diaspora_test'))) {
|
||||
post_url($dest_url . '/', $slap);
|
||||
$return_code = $a->get_curl_code();
|
||||
} else {
|
||||
logger('diaspora_transmit: test_mode');
|
||||
return 200;
|
||||
}
|
||||
}
|
||||
|
||||
logger('diaspora_transmit: '.$logid.'-'.$guid.' returns: '.$return_code);
|
||||
|
||||
if((! $return_code) || (($return_code == 503) && (stristr($a->get_curl_headers(),'retry-after')))) {
|
||||
logger('diaspora_transmit: queue message');
|
||||
|
||||
$r = q("SELECT id from queue where cid = %d and network = '%s' and content = '%s' and batch = %d limit 1",
|
||||
intval($contact['id']),
|
||||
dbesc(NETWORK_DIASPORA),
|
||||
dbesc($slap),
|
||||
intval($public_batch)
|
||||
);
|
||||
if(count($r)) {
|
||||
logger('diaspora_transmit: add_to_queue ignored - identical item already in queue');
|
||||
}
|
||||
else {
|
||||
// queue message for redelivery
|
||||
add_to_queue($contact['id'],NETWORK_DIASPORA,$slap,$public_batch);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
return(($return_code) ? $return_code : (-1));
|
||||
}
|
||||
|
||||
function diaspora_fetch_relay() {
|
||||
|
||||
$serverdata = get_config("system", "relay_server");
|
||||
if ($serverdata == "")
|
||||
return array();
|
||||
|
||||
$relay = array();
|
||||
|
||||
$servers = explode(",", $serverdata);
|
||||
|
||||
foreach($servers AS $server) {
|
||||
$server = trim($server);
|
||||
$batch = $server."/receive/public";
|
||||
|
||||
$relais = q("SELECT `batch`, `id`, `name`,`network` FROM `contact` WHERE `uid` = 0 AND `batch` = '%s' LIMIT 1", dbesc($batch));
|
||||
|
||||
if (!$relais) {
|
||||
$addr = "relay@".str_replace("http://", "", normalise_link($server));
|
||||
|
||||
$r = q("INSERT INTO `contact` (`uid`, `created`, `name`, `nick`, `addr`, `url`, `nurl`, `batch`, `network`, `rel`, `blocked`, `pending`, `writable`, `name-date`, `uri-date`, `avatar-date`)
|
||||
VALUES (0, '%s', '%s', 'relay', '%s', '%s', '%s', '%s', '%s', %d, 0, 0, 1, '%s', '%s', '%s')",
|
||||
datetime_convert(),
|
||||
dbesc($addr),
|
||||
dbesc($addr),
|
||||
dbesc($server),
|
||||
dbesc(normalise_link($server)),
|
||||
dbesc($batch),
|
||||
dbesc(NETWORK_DIASPORA),
|
||||
intval(CONTACT_IS_FOLLOWER),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc(datetime_convert())
|
||||
);
|
||||
|
||||
$relais = q("SELECT `batch`, `id`, `name`,`network` FROM `contact` WHERE `uid` = 0 AND `batch` = '%s' LIMIT 1", dbesc($batch));
|
||||
if ($relais)
|
||||
$relay[] = $relais[0];
|
||||
} else
|
||||
$relay[] = $relais[0];
|
||||
}
|
||||
|
||||
return $relay;
|
||||
}
|
||||
?>
|
||||
|
|
|
|||
|
|
@ -20,22 +20,14 @@ function discover_poco_run(&$argv, &$argc){
|
|||
|
||||
require_once('include/session.php');
|
||||
require_once('include/datetime.php');
|
||||
require_once('include/pidfile.php');
|
||||
|
||||
load_config('config');
|
||||
load_config('system');
|
||||
|
||||
$maxsysload = intval(get_config('system','maxloadavg'));
|
||||
if($maxsysload < 1)
|
||||
$maxsysload = 50;
|
||||
|
||||
$load = current_load();
|
||||
if($load) {
|
||||
if(intval($load) > $maxsysload) {
|
||||
logger('system: load ' . $load . ' too high. discover_poco deferred to next scheduled run.');
|
||||
// Don't check this stuff if the function is called by the poller
|
||||
if (App::callstack() != "poller_run")
|
||||
if (App::maxload_reached())
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if(($argc > 2) && ($argv[1] == "dirsearch")) {
|
||||
$search = urldecode($argv[2]);
|
||||
|
|
@ -50,21 +42,10 @@ function discover_poco_run(&$argv, &$argc){
|
|||
} else
|
||||
die("Unknown or missing parameter ".$argv[1]."\n");
|
||||
|
||||
$lockpath = get_lockpath();
|
||||
if ($lockpath != '') {
|
||||
$pidfile = new pidfile($lockpath, 'discover_poco'.$mode.urlencode($search));
|
||||
if($pidfile->is_already_running()) {
|
||||
logger("discover_poco: Already running");
|
||||
if ($pidfile->running_time() > 19*60) {
|
||||
$pidfile->kill();
|
||||
logger("discover_poco: killed stale process");
|
||||
// Calling a new instance
|
||||
if ($mode == 0)
|
||||
proc_run('php','include/discover_poco.php');
|
||||
}
|
||||
exit;
|
||||
}
|
||||
}
|
||||
// Don't check this stuff if the function is called by the poller
|
||||
if (App::callstack() != "poller_run")
|
||||
if (App::is_already_running('discover_poco'.$mode.urlencode($search), 'include/discover_poco.php', 1140))
|
||||
return;
|
||||
|
||||
$a->set_baseurl(get_config('system','url'));
|
||||
|
||||
|
|
|
|||
|
|
@ -1,55 +0,0 @@
|
|||
<?php
|
||||
require_once("boot.php");
|
||||
require_once('include/diaspora.php');
|
||||
|
||||
function dsprphotoq_run($argv, $argc){
|
||||
global $a, $db;
|
||||
|
||||
if(is_null($a)){
|
||||
$a = new App;
|
||||
}
|
||||
|
||||
if(is_null($db)){
|
||||
@include(".htconfig.php");
|
||||
require_once("include/dba.php");
|
||||
$db = new dba($db_host, $db_user, $db_pass, $db_data);
|
||||
unset($db_host, $db_user, $db_pass, $db_data);
|
||||
};
|
||||
|
||||
logger("diaspora photo queue: running", LOGGER_DEBUG);
|
||||
|
||||
$r = q("SELECT * FROM dsprphotoq");
|
||||
if(!$r)
|
||||
return;
|
||||
|
||||
$dphotos = $r;
|
||||
|
||||
logger("diaspora photo queue: processing " . count($dphotos) . " photos");
|
||||
|
||||
foreach($dphotos as $dphoto) {
|
||||
|
||||
$r = array();
|
||||
|
||||
if ($dphoto['uid'] == 0)
|
||||
$r[0] = array("uid" => 0, "page-flags" => PAGE_FREELOVE);
|
||||
else
|
||||
$r = q("SELECT * FROM user WHERE uid = %d",
|
||||
intval($dphoto['uid']));
|
||||
|
||||
if(!$r) {
|
||||
logger("diaspora photo queue: user " . $dphoto['uid'] . " not found");
|
||||
return;
|
||||
}
|
||||
|
||||
$ret = diaspora_dispatch($r[0],unserialize($dphoto['msg']),$dphoto['attempt']);
|
||||
q("DELETE FROM dsprphotoq WHERE id = %d",
|
||||
intval($dphoto['id'])
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (array_search(__file__,get_included_files())===0){
|
||||
dsprphotoq_run($_SERVER["argv"],$_SERVER["argc"]);
|
||||
killme();
|
||||
}
|
||||
|
|
@ -54,8 +54,10 @@ function feed_import($xml,$importer,&$contact, &$hub, $simulate = false) {
|
|||
if ($attributes->name == "href")
|
||||
$author["author-link"] = $attributes->textContent;
|
||||
|
||||
$author["author-id"] = $xpath->evaluate('/atom:feed/atom:author/atom:uri/text()')->item(0)->nodeValue;
|
||||
|
||||
if ($author["author-link"] == "")
|
||||
$author["author-link"] = $xpath->evaluate('/atom:feed/atom:author/atom:uri/text()')->item(0)->nodeValue;
|
||||
$author["author-link"] = $author["author-id"];
|
||||
|
||||
if ($author["author-link"] == "") {
|
||||
$self = $xpath->query("atom:link[@rel='self']")->item(0)->attributes;
|
||||
|
|
@ -127,6 +129,7 @@ function feed_import($xml,$importer,&$contact, &$hub, $simulate = false) {
|
|||
|
||||
// This is no field in the item table. So we have to unset it.
|
||||
unset($author["author-nick"]);
|
||||
unset($author["author-id"]);
|
||||
}
|
||||
|
||||
$header = array();
|
||||
|
|
|
|||
|
|
@ -258,12 +258,10 @@ function new_contact($uid,$url,$interactive = false) {
|
|||
$contact_id = $r[0]['id'];
|
||||
$result['cid'] = $contact_id;
|
||||
|
||||
$g = q("select def_gid from user where uid = %d limit 1",
|
||||
intval($uid)
|
||||
);
|
||||
if($g && intval($g[0]['def_gid'])) {
|
||||
$def_gid = get_default_group($uid, $contact["network"]);
|
||||
if (intval($def_gid)) {
|
||||
require_once('include/group.php');
|
||||
group_add_member($uid,'',$contact_id,$g[0]['def_gid']);
|
||||
group_add_member($uid, '', $contact_id, $def_gid);
|
||||
}
|
||||
|
||||
require_once("include/Photo.php");
|
||||
|
|
@ -305,8 +303,8 @@ function new_contact($uid,$url,$interactive = false) {
|
|||
}
|
||||
if($contact['network'] == NETWORK_DIASPORA) {
|
||||
require_once('include/diaspora.php');
|
||||
$ret = diaspora_share($a->user,$contact);
|
||||
logger('mod_follow: diaspora_share returns: ' . $ret);
|
||||
$ret = diaspora::send_share($a->user,$contact);
|
||||
logger('share returns: '.$ret);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -188,7 +188,7 @@ function group_public_members($gid) {
|
|||
}
|
||||
|
||||
|
||||
function mini_group_select($uid,$gid = 0) {
|
||||
function mini_group_select($uid,$gid = 0, $label = "") {
|
||||
|
||||
$grps = array();
|
||||
$o = '';
|
||||
|
|
@ -205,8 +205,11 @@ function mini_group_select($uid,$gid = 0) {
|
|||
}
|
||||
logger('groups: ' . print_r($grps,true));
|
||||
|
||||
if ($label == "")
|
||||
$label = t('Default privacy group for new contacts');
|
||||
|
||||
$o = replace_macros(get_markup_template('group_selection.tpl'), array(
|
||||
'$label' => t('Default privacy group for new contacts'),
|
||||
'$label' => $label,
|
||||
'$groups' => $grps
|
||||
));
|
||||
return $o;
|
||||
|
|
@ -375,3 +378,28 @@ function groups_count_unseen() {
|
|||
|
||||
return $r;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Returns the default group for a given user and network
|
||||
*
|
||||
* @param int $uid User id
|
||||
* @param string $network network name
|
||||
*
|
||||
* @return int group id
|
||||
*/
|
||||
function get_default_group($uid, $network = "") {
|
||||
|
||||
$default_group = 0;
|
||||
|
||||
if ($network == NETWORK_OSTATUS)
|
||||
$default_group = get_pconfig($uid, "ostatus", "default_group");
|
||||
|
||||
if ($default_group != 0)
|
||||
return $default_group;
|
||||
|
||||
$g = q("SELECT `def_gid` FROM `user` WHERE `uid` = %d LIMIT 1", intval($uid));
|
||||
if($g && intval($g[0]["def_gid"]))
|
||||
$default_group = $g[0]["def_gid"];
|
||||
|
||||
return $default_group;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -237,6 +237,7 @@ function profile_sidebar($profile, $block = 0) {
|
|||
if ($connect AND ($profile['network'] != NETWORK_DFRN) AND !isset($profile['remoteconnect']))
|
||||
$connect = false;
|
||||
|
||||
$remoteconnect = NULL;
|
||||
if (isset($profile['remoteconnect']))
|
||||
$remoteconnect = $profile['remoteconnect'];
|
||||
|
||||
|
|
@ -292,9 +293,9 @@ function profile_sidebar($profile, $block = 0) {
|
|||
// check if profile is a forum
|
||||
if((intval($profile['page-flags']) == PAGE_COMMUNITY)
|
||||
|| (intval($profile['page-flags']) == PAGE_PRVGROUP)
|
||||
|| (intval($profile['forum']))
|
||||
|| (intval($profile['prv']))
|
||||
|| (intval($profile['community'])))
|
||||
|| (isset($profile['forum']) && intval($profile['forum']))
|
||||
|| (isset($profile['prv']) && intval($profile['prv']))
|
||||
|| (isset($profile['community']) && intval($profile['community'])))
|
||||
$account_type = t('Forum');
|
||||
else
|
||||
$account_type = "";
|
||||
|
|
@ -332,9 +333,9 @@ function profile_sidebar($profile, $block = 0) {
|
|||
'fullname' => $profile['name'],
|
||||
'firstname' => $firstname,
|
||||
'lastname' => $lastname,
|
||||
'photo300' => $a->get_cached_avatar_image($a->get_baseurl() . '/photo/custom/300/' . $profile['uid'] . '.jpg'),
|
||||
'photo100' => $a->get_cached_avatar_image($a->get_baseurl() . '/photo/custom/100/' . $profile['uid'] . '.jpg'),
|
||||
'photo50' => $a->get_cached_avatar_image($a->get_baseurl() . '/photo/custom/50/' . $profile['uid'] . '.jpg'),
|
||||
'photo300' => $a->get_baseurl() . '/photo/custom/300/' . $profile['uid'] . '.jpg',
|
||||
'photo100' => $a->get_baseurl() . '/photo/custom/100/' . $profile['uid'] . '.jpg',
|
||||
'photo50' => $a->get_baseurl() . '/photo/custom/50/' . $profile['uid'] . '.jpg',
|
||||
);
|
||||
|
||||
if (!$block){
|
||||
|
|
|
|||
|
|
@ -383,9 +383,9 @@ function item_store($arr,$force_parent = false, $notify = false, $dontcache = fa
|
|||
// Converting the plink
|
||||
if ($arr['network'] == NETWORK_OSTATUS) {
|
||||
if (isset($arr['plink']))
|
||||
$arr['plink'] = ostatus_convert_href($arr['plink']);
|
||||
$arr['plink'] = ostatus::convert_href($arr['plink']);
|
||||
elseif (isset($arr['uri']))
|
||||
$arr['plink'] = ostatus_convert_href($arr['uri']);
|
||||
$arr['plink'] = ostatus::convert_href($arr['uri']);
|
||||
}
|
||||
|
||||
if(x($arr, 'gravity'))
|
||||
|
|
@ -707,9 +707,9 @@ function item_store($arr,$force_parent = false, $notify = false, $dontcache = fa
|
|||
if ($arr["uid"] == 0) {
|
||||
$arr["global"] = true;
|
||||
|
||||
q("UPDATE `item` SET `global` = 1 WHERE `guid` = '%s'", dbesc($arr["guid"]));
|
||||
q("UPDATE `item` SET `global` = 1 WHERE `uri` = '%s'", dbesc($arr["uri"]));
|
||||
} else {
|
||||
$isglobal = q("SELECT `global` FROM `item` WHERE `uid` = 0 AND `guid` = '%s'", dbesc($arr["guid"]));
|
||||
$isglobal = q("SELECT `global` FROM `item` WHERE `uid` = 0 AND `uri` = '%s'", dbesc($arr["uri"]));
|
||||
|
||||
$arr["global"] = (count($isglobal) > 0);
|
||||
}
|
||||
|
|
@ -1243,7 +1243,7 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0)
|
|||
//$tempfile = tempnam(get_temppath(), "ostatus2");
|
||||
//file_put_contents($tempfile, $xml);
|
||||
logger("Consume OStatus messages ", LOGGER_DEBUG);
|
||||
ostatus_import($xml,$importer,$contact, $hub);
|
||||
ostatus::import($xml,$importer,$contact, $hub);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
|
@ -1980,9 +1980,6 @@ function drop_item($id,$interactive = true) {
|
|||
intval($r[0]['id'])
|
||||
);
|
||||
}
|
||||
|
||||
// Add a relayable_retraction signature for Diaspora.
|
||||
store_diaspora_retract_sig($item, $a->user, $a->get_baseurl());
|
||||
}
|
||||
|
||||
$drop_id = intval($item['id']);
|
||||
|
|
@ -2115,51 +2112,3 @@ function posted_date_widget($url,$uid,$wall) {
|
|||
));
|
||||
return $o;
|
||||
}
|
||||
|
||||
function store_diaspora_retract_sig($item, $user, $baseurl) {
|
||||
// Note that we can't add a target_author_signature
|
||||
// if the comment was deleted by a remote user. That should be ok, because if a remote user is deleting
|
||||
// the comment, that means we're the home of the post, and Diaspora will only
|
||||
// check the parent_author_signature of retractions that it doesn't have to relay further
|
||||
//
|
||||
// I don't think this function gets called for an "unlike," but I'll check anyway
|
||||
|
||||
$enabled = intval(get_config('system','diaspora_enabled'));
|
||||
if(! $enabled) {
|
||||
logger('drop_item: diaspora support disabled, not storing retraction signature', LOGGER_DEBUG);
|
||||
return;
|
||||
}
|
||||
|
||||
logger('drop_item: storing diaspora retraction signature');
|
||||
|
||||
$signed_text = $item['guid'] . ';' . ( ($item['verb'] === ACTIVITY_LIKE) ? 'Like' : 'Comment');
|
||||
|
||||
if(local_user() == $item['uid']) {
|
||||
|
||||
$handle = $user['nickname'] . '@' . substr($baseurl, strpos($baseurl,'://') + 3);
|
||||
$authorsig = base64_encode(rsa_sign($signed_text,$user['prvkey'],'sha256'));
|
||||
}
|
||||
else {
|
||||
$r = q("SELECT `nick`, `url` FROM `contact` WHERE `id` = '%d' LIMIT 1",
|
||||
$item['contact-id'] // If this function gets called, drop_item() has already checked remote_user() == $item['contact-id']
|
||||
);
|
||||
if(count($r)) {
|
||||
// The below handle only works for NETWORK_DFRN. I think that's ok, because this function
|
||||
// only handles DFRN deletes
|
||||
$handle_baseurl_start = strpos($r['url'],'://') + 3;
|
||||
$handle_baseurl_length = strpos($r['url'],'/profile') - $handle_baseurl_start;
|
||||
$handle = $r['nick'] . '@' . substr($r['url'], $handle_baseurl_start, $handle_baseurl_length);
|
||||
$authorsig = '';
|
||||
}
|
||||
}
|
||||
|
||||
if(isset($handle))
|
||||
q("insert into sign (`retract_iid`,`signed_text`,`signature`,`signer`) values (%d,'%s','%s','%s') ",
|
||||
intval($item['id']),
|
||||
dbesc($signed_text),
|
||||
dbesc($authorsig),
|
||||
dbesc($handle)
|
||||
);
|
||||
|
||||
return;
|
||||
}
|
||||
|
|
|
|||
153
include/like.php
153
include/like.php
|
|
@ -1,4 +1,5 @@
|
|||
<?php
|
||||
require_once("include/diaspora.php");
|
||||
|
||||
/**
|
||||
* @brief add/remove activity to an item
|
||||
|
|
@ -151,9 +152,6 @@ function do_like($item_id, $verb) {
|
|||
intval($like_item['id'])
|
||||
);
|
||||
|
||||
// Save the author information for the unlike in case we need to relay to Diaspora
|
||||
store_diaspora_like_retract_sig($activity, $item, $like_item, $contact);
|
||||
|
||||
$like_item_id = $like_item['id'];
|
||||
proc_run('php',"include/notifier.php","like","$like_item_id");
|
||||
|
||||
|
|
@ -196,6 +194,7 @@ EOT;
|
|||
|
||||
$arr = array();
|
||||
|
||||
$arr['guid'] = get_guid(32);
|
||||
$arr['uri'] = $uri;
|
||||
$arr['uid'] = $owner_uid;
|
||||
$arr['contact-id'] = $contact['id'];
|
||||
|
|
@ -240,7 +239,7 @@ EOT;
|
|||
|
||||
|
||||
// Save the author information for the like in case we need to relay to Diaspora
|
||||
store_diaspora_like_sig($activity, $post_type, $contact, $post_id);
|
||||
diaspora::store_like_signature($contact, $post_id);
|
||||
|
||||
$arr['id'] = $post_id;
|
||||
|
||||
|
|
@ -250,149 +249,3 @@ EOT;
|
|||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
|
||||
function store_diaspora_like_retract_sig($activity, $item, $like_item, $contact) {
|
||||
// Note that we can only create a signature for a user of the local server. We don't have
|
||||
// a key for remote users. That is ok, because if a remote user is "unlike"ing a post, it
|
||||
// means we are the relay, and for relayable_retractions, Diaspora
|
||||
// only checks the parent_author_signature if it doesn't have to relay further
|
||||
//
|
||||
// If $item['resource-id'] exists, it means the item is a photo. Diaspora doesn't support
|
||||
// likes on photos, so don't bother.
|
||||
|
||||
$enabled = intval(get_config('system','diaspora_enabled'));
|
||||
if(! $enabled) {
|
||||
logger('mod_like: diaspora support disabled, not storing like retraction signature', LOGGER_DEBUG);
|
||||
return;
|
||||
}
|
||||
|
||||
logger('mod_like: storing diaspora like retraction signature');
|
||||
|
||||
if(($activity === ACTIVITY_LIKE) && (! $item['resource-id'])) {
|
||||
$signed_text = $like_item['guid'] . ';' . 'Like';
|
||||
|
||||
// Only works for NETWORK_DFRN
|
||||
$contact_baseurl_start = strpos($contact['url'],'://') + 3;
|
||||
$contact_baseurl_length = strpos($contact['url'],'/profile') - $contact_baseurl_start;
|
||||
$contact_baseurl = substr($contact['url'], $contact_baseurl_start, $contact_baseurl_length);
|
||||
$diaspora_handle = $contact['nick'] . '@' . $contact_baseurl;
|
||||
|
||||
// This code could never had worked (the return values form the queries were used in a wrong way.
|
||||
// Additionally it is needlessly complicated. Either the contact is owner or not. And we have this data already.
|
||||
/*
|
||||
// Get contact's private key if he's a user of the local Friendica server
|
||||
$r = q("SELECT `contact`.`uid` FROM `contact` WHERE `url` = '%s' AND `self` = 1 LIMIT 1",
|
||||
dbesc($contact['url'])
|
||||
);
|
||||
|
||||
if( $r) {
|
||||
$contact_uid = $r['uid'];
|
||||
$r = q("SELECT prvkey FROM user WHERE uid = %d LIMIT 1",
|
||||
intval($contact_uid)
|
||||
);
|
||||
*/
|
||||
// Is the contact the owner? Then fetch the private key
|
||||
if ($contact['self'] AND ($contact['uid'] > 0)) {
|
||||
$r = q("SELECT prvkey FROM user WHERE uid = %d LIMIT 1",
|
||||
intval($contact['uid'])
|
||||
);
|
||||
|
||||
if($r)
|
||||
$authorsig = base64_encode(rsa_sign($signed_text,$r[0]['prvkey'],'sha256'));
|
||||
}
|
||||
|
||||
if(! isset($authorsig))
|
||||
$authorsig = '';
|
||||
|
||||
q("insert into sign (`retract_iid`,`signed_text`,`signature`,`signer`) values (%d,'%s','%s','%s') ",
|
||||
intval($like_item['id']),
|
||||
dbesc($signed_text),
|
||||
dbesc($authorsig),
|
||||
dbesc($diaspora_handle)
|
||||
);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
function store_diaspora_like_sig($activity, $post_type, $contact, $post_id) {
|
||||
// Note that we can only create a signature for a user of the local server. We don't have
|
||||
// a key for remote users. That is ok, because if a remote user is "unlike"ing a post, it
|
||||
// means we are the relay, and for relayable_retractions, Diaspora
|
||||
// only checks the parent_author_signature if it doesn't have to relay further
|
||||
|
||||
$enabled = intval(get_config('system','diaspora_enabled'));
|
||||
if(! $enabled) {
|
||||
logger('mod_like: diaspora support disabled, not storing like signature', LOGGER_DEBUG);
|
||||
return;
|
||||
}
|
||||
|
||||
logger('mod_like: storing diaspora like signature');
|
||||
|
||||
if(($activity === ACTIVITY_LIKE) && ($post_type === t('status'))) {
|
||||
// Only works for NETWORK_DFRN
|
||||
$contact_baseurl_start = strpos($contact['url'],'://') + 3;
|
||||
$contact_baseurl_length = strpos($contact['url'],'/profile') - $contact_baseurl_start;
|
||||
$contact_baseurl = substr($contact['url'], $contact_baseurl_start, $contact_baseurl_length);
|
||||
$diaspora_handle = $contact['nick'] . '@' . $contact_baseurl;
|
||||
|
||||
|
||||
// This code could never had worked (the return values form the queries were used in a wrong way.
|
||||
// Additionally it is needlessly complicated. Either the contact is owner or not. And we have this data already.
|
||||
/*
|
||||
// Get contact's private key if he's a user of the local Friendica server
|
||||
$r = q("SELECT `contact`.`uid` FROM `contact` WHERE `url` = '%s' AND `self` = 1 LIMIT 1",
|
||||
dbesc($contact['url'])
|
||||
);
|
||||
|
||||
if( $r) {
|
||||
$contact_uid = $r['uid'];
|
||||
$r = q("SELECT prvkey FROM user WHERE uid = %d LIMIT 1",
|
||||
intval($contact_uid)
|
||||
);
|
||||
|
||||
if( $r)
|
||||
$contact_uprvkey = $r['prvkey'];
|
||||
}
|
||||
*/
|
||||
|
||||
// Is the contact the owner? Then fetch the private key
|
||||
if ($contact['self'] AND ($contact['uid'] > 0)) {
|
||||
$r = q("SELECT prvkey FROM user WHERE uid = %d LIMIT 1",
|
||||
intval($contact['uid'])
|
||||
);
|
||||
|
||||
if($r)
|
||||
$contact_uprvkey = $r[0]['prvkey'];
|
||||
}
|
||||
|
||||
$r = q("SELECT guid, parent FROM `item` WHERE id = %d LIMIT 1",
|
||||
intval($post_id)
|
||||
);
|
||||
if( $r) {
|
||||
$p = q("SELECT guid FROM `item` WHERE id = %d AND parent = %d LIMIT 1",
|
||||
intval($r[0]['parent']),
|
||||
intval($r[0]['parent'])
|
||||
);
|
||||
if( $p) {
|
||||
$signed_text = 'true;'.$r[0]['guid'].';Post;'.$p[0]['guid'].';'.$diaspora_handle;
|
||||
|
||||
if(isset($contact_uprvkey))
|
||||
$authorsig = base64_encode(rsa_sign($signed_text,$contact_uprvkey,'sha256'));
|
||||
else
|
||||
$authorsig = '';
|
||||
|
||||
q("insert into sign (`iid`,`signed_text`,`signature`,`signer`) values (%d,'%s','%s','%s') ",
|
||||
intval($post_id),
|
||||
dbesc($signed_text),
|
||||
dbesc($authorsig),
|
||||
dbesc($diaspora_handle)
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -82,7 +82,7 @@ function nav_info(&$a) {
|
|||
// user info
|
||||
$r = q("SELECT micro FROM contact WHERE uid=%d AND self=1", intval($a->user['uid']));
|
||||
$userinfo = array(
|
||||
'icon' => (count($r) ? $a->get_cached_avatar_image($r[0]['micro']) : $a->get_baseurl($ssl_state)."/images/person-48.jpg"),
|
||||
'icon' => (count($r) ? $a->remove_baseurl($r[0]['micro']) : "images/person-48.jpg"),
|
||||
'name' => $a->user['username'],
|
||||
);
|
||||
|
||||
|
|
@ -107,7 +107,7 @@ function nav_info(&$a) {
|
|||
if(($a->config['register_policy'] == REGISTER_OPEN) && (! local_user()) && (! remote_user()))
|
||||
$nav['register'] = array('register',t('Register'), "", t('Create an account'));
|
||||
|
||||
$help_url = $a->get_baseurl($ssl_state) . '/help';
|
||||
$help_url = 'help';
|
||||
|
||||
if(! get_config('system','hide_help'))
|
||||
$nav['help'] = array($help_url, t('Help'), "", t('Help and documentation'));
|
||||
|
|
|
|||
|
|
@ -862,64 +862,6 @@ function parse_xml_string($s,$strict = true) {
|
|||
return $x;
|
||||
}}
|
||||
|
||||
function add_fcontact($arr,$update = false) {
|
||||
|
||||
if($update) {
|
||||
$r = q("UPDATE `fcontact` SET
|
||||
`name` = '%s',
|
||||
`photo` = '%s',
|
||||
`request` = '%s',
|
||||
`nick` = '%s',
|
||||
`addr` = '%s',
|
||||
`batch` = '%s',
|
||||
`notify` = '%s',
|
||||
`poll` = '%s',
|
||||
`confirm` = '%s',
|
||||
`alias` = '%s',
|
||||
`pubkey` = '%s',
|
||||
`updated` = '%s'
|
||||
WHERE `url` = '%s' AND `network` = '%s'",
|
||||
dbesc($arr['name']),
|
||||
dbesc($arr['photo']),
|
||||
dbesc($arr['request']),
|
||||
dbesc($arr['nick']),
|
||||
dbesc($arr['addr']),
|
||||
dbesc($arr['batch']),
|
||||
dbesc($arr['notify']),
|
||||
dbesc($arr['poll']),
|
||||
dbesc($arr['confirm']),
|
||||
dbesc($arr['alias']),
|
||||
dbesc($arr['pubkey']),
|
||||
dbesc(datetime_convert()),
|
||||
dbesc($arr['url']),
|
||||
dbesc($arr['network'])
|
||||
);
|
||||
}
|
||||
else {
|
||||
$r = q("insert into fcontact ( `url`,`name`,`photo`,`request`,`nick`,`addr`,
|
||||
`batch`, `notify`,`poll`,`confirm`,`network`,`alias`,`pubkey`,`updated` )
|
||||
values('%s','%s','%s','%s','%s','%s','%s','%s','%s','%s','%s','%s','%s','%s')",
|
||||
dbesc($arr['url']),
|
||||
dbesc($arr['name']),
|
||||
dbesc($arr['photo']),
|
||||
dbesc($arr['request']),
|
||||
dbesc($arr['nick']),
|
||||
dbesc($arr['addr']),
|
||||
dbesc($arr['batch']),
|
||||
dbesc($arr['notify']),
|
||||
dbesc($arr['poll']),
|
||||
dbesc($arr['confirm']),
|
||||
dbesc($arr['network']),
|
||||
dbesc($arr['alias']),
|
||||
dbesc($arr['pubkey']),
|
||||
dbesc(datetime_convert())
|
||||
);
|
||||
}
|
||||
|
||||
return $r;
|
||||
}
|
||||
|
||||
|
||||
function scale_external_images($srctext, $include_link = true, $scale_replace = false) {
|
||||
|
||||
// Suppress "view full size"
|
||||
|
|
|
|||
|
|
@ -223,13 +223,13 @@ function notifier_run(&$argv, &$argc){
|
|||
|
||||
if(! ($mail || $fsuggest || $relocate)) {
|
||||
|
||||
$slap = ostatus_salmon($target_item,$owner);
|
||||
$slap = ostatus::salmon($target_item,$owner);
|
||||
|
||||
require_once('include/group.php');
|
||||
|
||||
$parent = $items[0];
|
||||
|
||||
$thr_parent = q("SELECT `network` FROM `item` WHERE `uri` = '%s' AND `uid` = %d",
|
||||
$thr_parent = q("SELECT `network`, `author-link`, `owner-link` FROM `item` WHERE `uri` = '%s' AND `uid` = %d",
|
||||
dbesc($target_item["thr-parent"]), intval($target_item["uid"]));
|
||||
|
||||
logger('Parent is '.$parent['network'].'. Thread parent is '.$thr_parent[0]['network'], LOGGER_DEBUG);
|
||||
|
|
@ -390,6 +390,20 @@ function notifier_run(&$argv, &$argc){
|
|||
|
||||
logger('Some parent is OStatus for '.$target_item["guid"], LOGGER_DEBUG);
|
||||
|
||||
// Send a salmon to the parent author
|
||||
$probed_contact = probe_url($thr_parent[0]['author-link']);
|
||||
if ($probed_contact["notify"] != "") {
|
||||
logger('Notify parent author '.$probed_contact["url"].': '.$probed_contact["notify"]);
|
||||
$url_recipients[$probed_contact["notify"]] = $probed_contact["notify"];
|
||||
}
|
||||
|
||||
// Send a salmon to the parent owner
|
||||
$probed_contact = probe_url($thr_parent[0]['owner-link']);
|
||||
if ($probed_contact["notify"] != "") {
|
||||
logger('Notify parent owner '.$probed_contact["url"].': '.$probed_contact["notify"]);
|
||||
$url_recipients[$probed_contact["notify"]] = $probed_contact["notify"];
|
||||
}
|
||||
|
||||
// Send a salmon notification to every person we mentioned in the post
|
||||
$arr = explode(',',$target_item['tag']);
|
||||
foreach($arr as $x) {
|
||||
|
|
@ -536,7 +550,7 @@ function notifier_run(&$argv, &$argc){
|
|||
if($public_message) {
|
||||
|
||||
if (!$followup AND $top_level)
|
||||
$r0 = diaspora_fetch_relay();
|
||||
$r0 = diaspora::relay_list();
|
||||
else
|
||||
$r0 = array();
|
||||
|
||||
|
|
@ -628,13 +642,6 @@ function notifier_run(&$argv, &$argc){
|
|||
proc_run('php','include/pubsubpublish.php');
|
||||
}
|
||||
|
||||
// If the item was deleted, clean up the `sign` table
|
||||
if($target_item['deleted']) {
|
||||
$r = q("DELETE FROM sign where `retract_iid` = %d",
|
||||
intval($target_item['id'])
|
||||
);
|
||||
}
|
||||
|
||||
logger('notifier: calling hooks', LOGGER_DEBUG);
|
||||
|
||||
if($normal_mode)
|
||||
|
|
|
|||
|
|
@ -31,7 +31,6 @@ function onepoll_run(&$argv, &$argc){
|
|||
require_once('include/Contact.php');
|
||||
require_once('include/email.php');
|
||||
require_once('include/socgraph.php');
|
||||
require_once('include/pidfile.php');
|
||||
require_once('include/queue_fn.php');
|
||||
|
||||
load_config('config');
|
||||
|
|
@ -60,18 +59,10 @@ function onepoll_run(&$argv, &$argc){
|
|||
return;
|
||||
}
|
||||
|
||||
$lockpath = get_lockpath();
|
||||
if ($lockpath != '') {
|
||||
$pidfile = new pidfile($lockpath, 'onepoll'.$contact_id);
|
||||
if ($pidfile->is_already_running()) {
|
||||
logger("onepoll: Already running for contact ".$contact_id);
|
||||
if ($pidfile->running_time() > 9*60) {
|
||||
$pidfile->kill();
|
||||
logger("killed stale process");
|
||||
}
|
||||
exit;
|
||||
}
|
||||
}
|
||||
// Don't check this stuff if the function is called by the poller
|
||||
if (App::callstack() != "poller_run")
|
||||
if (App::is_already_running('onepoll'.$contact_id, '', 540))
|
||||
return;
|
||||
|
||||
$d = datetime_convert();
|
||||
|
||||
|
|
|
|||
3213
include/ostatus.php
3213
include/ostatus.php
|
|
@ -1,4 +1,8 @@
|
|||
<?php
|
||||
/**
|
||||
* @file include/ostatus.php
|
||||
*/
|
||||
|
||||
require_once("include/Contact.php");
|
||||
require_once("include/threads.php");
|
||||
require_once("include/html2bbcode.php");
|
||||
|
|
@ -12,484 +16,486 @@ require_once("include/Scrape.php");
|
|||
require_once("include/follow.php");
|
||||
require_once("include/api.php");
|
||||
require_once("mod/proxy.php");
|
||||
require_once("include/xml.php");
|
||||
|
||||
define('OSTATUS_DEFAULT_POLL_INTERVAL', 30); // given in minutes
|
||||
define('OSTATUS_DEFAULT_POLL_TIMEFRAME', 1440); // given in minutes
|
||||
define('OSTATUS_DEFAULT_POLL_TIMEFRAME_MENTIONS', 14400); // given in minutes
|
||||
/**
|
||||
* @brief This class contain functions for the OStatus protocol
|
||||
*
|
||||
*/
|
||||
class ostatus {
|
||||
const OSTATUS_DEFAULT_POLL_INTERVAL = 30; // given in minutes
|
||||
const OSTATUS_DEFAULT_POLL_TIMEFRAME = 1440; // given in minutes
|
||||
const OSTATUS_DEFAULT_POLL_TIMEFRAME_MENTIONS = 14400; // given in minutes
|
||||
|
||||
function ostatus_check_follow_friends() {
|
||||
$r = q("SELECT `uid`,`v` FROM `pconfig` WHERE `cat`='system' AND `k`='ostatus_legacy_contact' AND `v` != ''");
|
||||
/**
|
||||
* @brief Fetches author data
|
||||
*
|
||||
* @param object $xpath The xpath object
|
||||
* @param object $context The xml context of the author detals
|
||||
* @param array $importer user record of the importing user
|
||||
* @param array $contact Called by reference, will contain the fetched contact
|
||||
* @param bool $onlyfetch Only fetch the header without updating the contact entries
|
||||
*
|
||||
* @return array Array of author related entries for the item
|
||||
*/
|
||||
private function fetchauthor($xpath, $context, $importer, &$contact, $onlyfetch) {
|
||||
|
||||
if (!$r)
|
||||
return;
|
||||
$author = array();
|
||||
$author["author-link"] = $xpath->evaluate('atom:author/atom:uri/text()', $context)->item(0)->nodeValue;
|
||||
$author["author-name"] = $xpath->evaluate('atom:author/atom:name/text()', $context)->item(0)->nodeValue;
|
||||
|
||||
foreach ($r AS $contact) {
|
||||
ostatus_follow_friends($contact["uid"], $contact["v"]);
|
||||
set_pconfig($contact["uid"], "system", "ostatus_legacy_contact", "");
|
||||
}
|
||||
}
|
||||
$aliaslink = $author["author-link"];
|
||||
|
||||
// This function doesn't work reliable by now.
|
||||
function ostatus_follow_friends($uid, $url) {
|
||||
$contact = probe_url($url);
|
||||
$alternate = $xpath->query("atom:author/atom:link[@rel='alternate']", $context)->item(0)->attributes;
|
||||
if (is_object($alternate))
|
||||
foreach($alternate AS $attributes)
|
||||
if ($attributes->name == "href")
|
||||
$author["author-link"] = $attributes->textContent;
|
||||
|
||||
if (!$contact)
|
||||
return;
|
||||
$r = q("SELECT * FROM `contact` WHERE `uid` = %d AND `nurl` IN ('%s', '%s') AND `network` != '%s'",
|
||||
intval($importer["uid"]), dbesc(normalise_link($author["author-link"])),
|
||||
dbesc(normalise_link($aliaslink)), dbesc(NETWORK_STATUSNET));
|
||||
if ($r) {
|
||||
$contact = $r[0];
|
||||
$author["contact-id"] = $r[0]["id"];
|
||||
} else
|
||||
$author["contact-id"] = $contact["id"];
|
||||
|
||||
$api = $contact["baseurl"]."/api/";
|
||||
|
||||
// Fetching friends
|
||||
$data = z_fetch_url($api."statuses/friends.json?screen_name=".$contact["nick"]);
|
||||
|
||||
if (!$data["success"])
|
||||
return;
|
||||
|
||||
$friends = json_decode($data["body"]);
|
||||
|
||||
foreach ($friends AS $friend) {
|
||||
$url = $friend->statusnet_profile_url;
|
||||
$r = q("SELECT `url` FROM `contact` WHERE `uid` = %d AND
|
||||
(`nurl` = '%s' OR `alias` = '%s' OR `alias` = '%s') AND
|
||||
`network` != '%s' LIMIT 1",
|
||||
intval($uid), dbesc(normalise_link($url)),
|
||||
dbesc(normalise_link($url)), dbesc($url), dbesc(NETWORK_STATUSNET));
|
||||
if (!$r) {
|
||||
$data = probe_url($friend->statusnet_profile_url);
|
||||
if ($data["network"] == NETWORK_OSTATUS) {
|
||||
$result = new_contact($uid,$friend->statusnet_profile_url);
|
||||
if ($result["success"])
|
||||
logger($friend->name." ".$url." - success", LOGGER_DEBUG);
|
||||
else
|
||||
logger($friend->name." ".$url." - failed", LOGGER_DEBUG);
|
||||
} else
|
||||
logger($friend->name." ".$url." - not OStatus", LOGGER_DEBUG);
|
||||
$avatarlist = array();
|
||||
$avatars = $xpath->query("atom:author/atom:link[@rel='avatar']", $context);
|
||||
foreach($avatars AS $avatar) {
|
||||
$href = "";
|
||||
$width = 0;
|
||||
foreach($avatar->attributes AS $attributes) {
|
||||
if ($attributes->name == "href")
|
||||
$href = $attributes->textContent;
|
||||
if ($attributes->name == "width")
|
||||
$width = $attributes->textContent;
|
||||
}
|
||||
if (($width > 0) AND ($href != ""))
|
||||
$avatarlist[$width] = $href;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function ostatus_fetchauthor($xpath, $context, $importer, &$contact, $onlyfetch) {
|
||||
|
||||
$author = array();
|
||||
$author["author-link"] = $xpath->evaluate('atom:author/atom:uri/text()', $context)->item(0)->nodeValue;
|
||||
$author["author-name"] = $xpath->evaluate('atom:author/atom:name/text()', $context)->item(0)->nodeValue;
|
||||
|
||||
// Preserve the value
|
||||
$authorlink = $author["author-link"];
|
||||
|
||||
$alternate = $xpath->query("atom:author/atom:link[@rel='alternate']", $context)->item(0)->attributes;
|
||||
if (is_object($alternate))
|
||||
foreach($alternate AS $attributes)
|
||||
if ($attributes->name == "href")
|
||||
$author["author-link"] = $attributes->textContent;
|
||||
|
||||
$r = q("SELECT * FROM `contact` WHERE `uid` = %d AND `nurl` IN ('%s', '%s') AND `network` != '%s'",
|
||||
intval($importer["uid"]), dbesc(normalise_link($author["author-link"])),
|
||||
dbesc(normalise_link($authorlink)), dbesc(NETWORK_STATUSNET));
|
||||
if ($r) {
|
||||
$contact = $r[0];
|
||||
$author["contact-id"] = $r[0]["id"];
|
||||
} else
|
||||
$author["contact-id"] = $contact["id"];
|
||||
|
||||
$avatarlist = array();
|
||||
$avatars = $xpath->query("atom:author/atom:link[@rel='avatar']", $context);
|
||||
foreach($avatars AS $avatar) {
|
||||
$href = "";
|
||||
$width = 0;
|
||||
foreach($avatar->attributes AS $attributes) {
|
||||
if ($attributes->name == "href")
|
||||
$href = $attributes->textContent;
|
||||
if ($attributes->name == "width")
|
||||
$width = $attributes->textContent;
|
||||
}
|
||||
if (($width > 0) AND ($href != ""))
|
||||
$avatarlist[$width] = $href;
|
||||
}
|
||||
if (count($avatarlist) > 0) {
|
||||
krsort($avatarlist);
|
||||
$author["author-avatar"] = current($avatarlist);
|
||||
}
|
||||
|
||||
$displayname = $xpath->evaluate('atom:author/poco:displayName/text()', $context)->item(0)->nodeValue;
|
||||
if ($displayname != "")
|
||||
$author["author-name"] = $displayname;
|
||||
|
||||
$author["owner-name"] = $author["author-name"];
|
||||
$author["owner-link"] = $author["author-link"];
|
||||
$author["owner-avatar"] = $author["author-avatar"];
|
||||
|
||||
// Only update the contacts if it is an OStatus contact
|
||||
if ($r AND !$onlyfetch AND ($contact["network"] == NETWORK_OSTATUS)) {
|
||||
// Update contact data
|
||||
|
||||
$value = $xpath->query("atom:link[@rel='salmon']", $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["notify"] = $value;
|
||||
|
||||
$value = $xpath->evaluate('atom:author/uri/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["alias"] = $value;
|
||||
|
||||
$value = $xpath->evaluate('atom:author/poco:displayName/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["name"] = $value;
|
||||
|
||||
$value = $xpath->evaluate('atom:author/poco:preferredUsername/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["nick"] = $value;
|
||||
|
||||
$value = $xpath->evaluate('atom:author/poco:note/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["about"] = html2bbcode($value);
|
||||
|
||||
$value = $xpath->evaluate('atom:author/poco:address/poco:formatted/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["location"] = $value;
|
||||
|
||||
if (($contact["name"] != $r[0]["name"]) OR ($contact["nick"] != $r[0]["nick"]) OR ($contact["about"] != $r[0]["about"]) OR ($contact["location"] != $r[0]["location"])) {
|
||||
|
||||
logger("Update contact data for contact ".$contact["id"], LOGGER_DEBUG);
|
||||
|
||||
q("UPDATE `contact` SET `name` = '%s', `nick` = '%s', `about` = '%s', `location` = '%s', `name-date` = '%s' WHERE `id` = %d",
|
||||
dbesc($contact["name"]), dbesc($contact["nick"]), dbesc($contact["about"]), dbesc($contact["location"]),
|
||||
dbesc(datetime_convert()), intval($contact["id"]));
|
||||
|
||||
poco_check($contact["url"], $contact["name"], $contact["network"], $author["author-avatar"], $contact["about"], $contact["location"],
|
||||
"", "", "", datetime_convert(), 2, $contact["id"], $contact["uid"]);
|
||||
if (count($avatarlist) > 0) {
|
||||
krsort($avatarlist);
|
||||
$author["author-avatar"] = current($avatarlist);
|
||||
}
|
||||
|
||||
if (isset($author["author-avatar"]) AND ($author["author-avatar"] != $r[0]['avatar'])) {
|
||||
logger("Update profile picture for contact ".$contact["id"], LOGGER_DEBUG);
|
||||
$displayname = $xpath->evaluate('atom:author/poco:displayName/text()', $context)->item(0)->nodeValue;
|
||||
if ($displayname != "")
|
||||
$author["author-name"] = $displayname;
|
||||
|
||||
update_contact_avatar($author["author-avatar"], $importer["uid"], $contact["id"]);
|
||||
}
|
||||
$author["owner-name"] = $author["author-name"];
|
||||
$author["owner-link"] = $author["author-link"];
|
||||
$author["owner-avatar"] = $author["author-avatar"];
|
||||
|
||||
$contact["generation"] = 2;
|
||||
$contact["photo"] = $author["author-avatar"];
|
||||
update_gcontact($contact);
|
||||
}
|
||||
// Only update the contacts if it is an OStatus contact
|
||||
if ($r AND !$onlyfetch AND ($contact["network"] == NETWORK_OSTATUS)) {
|
||||
|
||||
return($author);
|
||||
}
|
||||
// Update contact data
|
||||
|
||||
function ostatus_salmon_author($xml, $importer) {
|
||||
$a = get_app();
|
||||
// This query doesn't seem to work
|
||||
// $value = $xpath->query("atom:link[@rel='salmon']", $context)->item(0)->nodeValue;
|
||||
// if ($value != "")
|
||||
// $contact["notify"] = $value;
|
||||
|
||||
if ($xml == "")
|
||||
return;
|
||||
// This query doesn't seem to work as well - I hate these queries
|
||||
// $value = $xpath->query("atom:link[@rel='self' and @type='application/atom+xml']", $context)->item(0)->nodeValue;
|
||||
// if ($value != "")
|
||||
// $contact["poll"] = $value;
|
||||
|
||||
$doc = new DOMDocument();
|
||||
@$doc->loadXML($xml);
|
||||
$value = $xpath->evaluate('atom:author/atom:uri/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["alias"] = $value;
|
||||
|
||||
$xpath = new DomXPath($doc);
|
||||
$xpath->registerNamespace('atom', NAMESPACE_ATOM1);
|
||||
$xpath->registerNamespace('thr', NAMESPACE_THREAD);
|
||||
$xpath->registerNamespace('georss', NAMESPACE_GEORSS);
|
||||
$xpath->registerNamespace('activity', NAMESPACE_ACTIVITY);
|
||||
$xpath->registerNamespace('media', NAMESPACE_MEDIA);
|
||||
$xpath->registerNamespace('poco', NAMESPACE_POCO);
|
||||
$xpath->registerNamespace('ostatus', NAMESPACE_OSTATUS);
|
||||
$xpath->registerNamespace('statusnet', NAMESPACE_STATUSNET);
|
||||
$value = $xpath->evaluate('atom:author/poco:displayName/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["name"] = $value;
|
||||
|
||||
$entries = $xpath->query('/atom:entry');
|
||||
$value = $xpath->evaluate('atom:author/poco:preferredUsername/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["nick"] = $value;
|
||||
|
||||
foreach ($entries AS $entry) {
|
||||
// fetch the author
|
||||
$author = ostatus_fetchauthor($xpath, $entry, $importer, $contact, true);
|
||||
return $author;
|
||||
}
|
||||
}
|
||||
$value = $xpath->evaluate('atom:author/poco:note/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["about"] = html2bbcode($value);
|
||||
|
||||
function ostatus_import($xml,$importer,&$contact, &$hub) {
|
||||
$value = $xpath->evaluate('atom:author/poco:address/poco:formatted/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$contact["location"] = $value;
|
||||
|
||||
$a = get_app();
|
||||
if (($contact["name"] != $r[0]["name"]) OR ($contact["nick"] != $r[0]["nick"]) OR ($contact["about"] != $r[0]["about"]) OR
|
||||
($contact["alias"] != $r[0]["alias"]) OR ($contact["location"] != $r[0]["location"])) {
|
||||
|
||||
logger("Import OStatus message", LOGGER_DEBUG);
|
||||
logger("Update contact data for contact ".$contact["id"], LOGGER_DEBUG);
|
||||
|
||||
if ($xml == "")
|
||||
return;
|
||||
q("UPDATE `contact` SET `name` = '%s', `nick` = '%s', `alias` = '%s', `about` = '%s', `location` = '%s', `name-date` = '%s' WHERE `id` = %d",
|
||||
dbesc($contact["name"]), dbesc($contact["nick"]), dbesc($contact["alias"]),
|
||||
dbesc($contact["about"]), dbesc($contact["location"]),
|
||||
dbesc(datetime_convert()), intval($contact["id"]));
|
||||
|
||||
$doc = new DOMDocument();
|
||||
@$doc->loadXML($xml);
|
||||
|
||||
$xpath = new DomXPath($doc);
|
||||
$xpath->registerNamespace('atom', NAMESPACE_ATOM1);
|
||||
$xpath->registerNamespace('thr', NAMESPACE_THREAD);
|
||||
$xpath->registerNamespace('georss', NAMESPACE_GEORSS);
|
||||
$xpath->registerNamespace('activity', NAMESPACE_ACTIVITY);
|
||||
$xpath->registerNamespace('media', NAMESPACE_MEDIA);
|
||||
$xpath->registerNamespace('poco', NAMESPACE_POCO);
|
||||
$xpath->registerNamespace('ostatus', NAMESPACE_OSTATUS);
|
||||
$xpath->registerNamespace('statusnet', NAMESPACE_STATUSNET);
|
||||
|
||||
$gub = "";
|
||||
$hub_attributes = $xpath->query("/atom:feed/atom:link[@rel='hub']")->item(0)->attributes;
|
||||
if (is_object($hub_attributes))
|
||||
foreach($hub_attributes AS $hub_attribute)
|
||||
if ($hub_attribute->name == "href") {
|
||||
$hub = $hub_attribute->textContent;
|
||||
logger("Found hub ".$hub, LOGGER_DEBUG);
|
||||
poco_check($contact["url"], $contact["name"], $contact["network"], $author["author-avatar"], $contact["about"], $contact["location"],
|
||||
"", "", "", datetime_convert(), 2, $contact["id"], $contact["uid"]);
|
||||
}
|
||||
|
||||
$header = array();
|
||||
$header["uid"] = $importer["uid"];
|
||||
$header["network"] = NETWORK_OSTATUS;
|
||||
$header["type"] = "remote";
|
||||
$header["wall"] = 0;
|
||||
$header["origin"] = 0;
|
||||
$header["gravity"] = GRAVITY_PARENT;
|
||||
if (isset($author["author-avatar"]) AND ($author["author-avatar"] != $r[0]['avatar'])) {
|
||||
logger("Update profile picture for contact ".$contact["id"], LOGGER_DEBUG);
|
||||
|
||||
// it could either be a received post or a post we fetched by ourselves
|
||||
// depending on that, the first node is different
|
||||
$first_child = $doc->firstChild->tagName;
|
||||
update_contact_avatar($author["author-avatar"], $importer["uid"], $contact["id"]);
|
||||
}
|
||||
|
||||
// Ensure that we are having this contact (with uid=0)
|
||||
$cid = get_contact($author["author-link"], 0);
|
||||
|
||||
if ($cid) {
|
||||
// Update it with the current values
|
||||
q("UPDATE `contact` SET `url` = '%s', `name` = '%s', `nick` = '%s', `alias` = '%s',
|
||||
`about` = '%s', `location` = '%s',
|
||||
`success_update` = '%s', `last-update` = '%s'
|
||||
WHERE `id` = %d",
|
||||
dbesc($author["author-link"]), dbesc($contact["name"]), dbesc($contact["nick"]),
|
||||
dbesc($contact["alias"]), dbesc($contact["about"]), dbesc($contact["location"]),
|
||||
dbesc(datetime_convert()), dbesc(datetime_convert()), intval($cid));
|
||||
|
||||
// Update the avatar
|
||||
update_contact_avatar($author["author-avatar"], 0, $cid);
|
||||
}
|
||||
|
||||
$contact["generation"] = 2;
|
||||
$contact["photo"] = $author["author-avatar"];
|
||||
update_gcontact($contact);
|
||||
}
|
||||
|
||||
return($author);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Fetches author data from a given XML string
|
||||
*
|
||||
* @param string $xml The XML
|
||||
* @param array $importer user record of the importing user
|
||||
*
|
||||
* @return array Array of author related entries for the item
|
||||
*/
|
||||
public static function salmon_author($xml, $importer) {
|
||||
|
||||
if ($xml == "")
|
||||
return;
|
||||
|
||||
$doc = new DOMDocument();
|
||||
@$doc->loadXML($xml);
|
||||
|
||||
$xpath = new DomXPath($doc);
|
||||
$xpath->registerNamespace('atom', NAMESPACE_ATOM1);
|
||||
$xpath->registerNamespace('thr', NAMESPACE_THREAD);
|
||||
$xpath->registerNamespace('georss', NAMESPACE_GEORSS);
|
||||
$xpath->registerNamespace('activity', NAMESPACE_ACTIVITY);
|
||||
$xpath->registerNamespace('media', NAMESPACE_MEDIA);
|
||||
$xpath->registerNamespace('poco', NAMESPACE_POCO);
|
||||
$xpath->registerNamespace('ostatus', NAMESPACE_OSTATUS);
|
||||
$xpath->registerNamespace('statusnet', NAMESPACE_STATUSNET);
|
||||
|
||||
if ($first_child == "feed")
|
||||
$entries = $xpath->query('/atom:feed/atom:entry');
|
||||
else
|
||||
$entries = $xpath->query('/atom:entry');
|
||||
|
||||
$conversation = "";
|
||||
$conversationlist = array();
|
||||
$item_id = 0;
|
||||
|
||||
// Reverse the order of the entries
|
||||
$entrylist = array();
|
||||
|
||||
foreach ($entries AS $entry)
|
||||
$entrylist[] = $entry;
|
||||
|
||||
foreach (array_reverse($entrylist) AS $entry) {
|
||||
|
||||
$mention = false;
|
||||
|
||||
// fetch the author
|
||||
if ($first_child == "feed")
|
||||
$author = ostatus_fetchauthor($xpath, $doc->firstChild, $importer, $contact, false);
|
||||
else
|
||||
$author = ostatus_fetchauthor($xpath, $entry, $importer, $contact, false);
|
||||
|
||||
$value = $xpath->evaluate('atom:author/poco:preferredUsername/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$nickname = $value;
|
||||
else
|
||||
$nickname = $author["author-name"];
|
||||
|
||||
$item = array_merge($header, $author);
|
||||
|
||||
// Now get the item
|
||||
$item["uri"] = $xpath->query('atom:id/text()', $entry)->item(0)->nodeValue;
|
||||
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s'",
|
||||
intval($importer["uid"]), dbesc($item["uri"]));
|
||||
if ($r) {
|
||||
logger("Item with uri ".$item["uri"]." for user ".$importer["uid"]." already existed under id ".$r[0]["id"], LOGGER_DEBUG);
|
||||
continue;
|
||||
foreach ($entries AS $entry) {
|
||||
// fetch the author
|
||||
$author = self::fetchauthor($xpath, $entry, $importer, $contact, true);
|
||||
return $author;
|
||||
}
|
||||
}
|
||||
|
||||
$item["body"] = add_page_info_to_body(html2bbcode($xpath->query('atom:content/text()', $entry)->item(0)->nodeValue));
|
||||
$item["object-type"] = $xpath->query('activity:object-type/text()', $entry)->item(0)->nodeValue;
|
||||
/**
|
||||
* @brief Imports an XML string containing OStatus elements
|
||||
*
|
||||
* @param string $xml The XML
|
||||
* @param array $importer user record of the importing user
|
||||
* @param $contact
|
||||
* @param array $hub Called by reference, returns the fetched hub data
|
||||
*/
|
||||
public static function import($xml,$importer,&$contact, &$hub) {
|
||||
/// @todo this function is too long. It has to be split in many parts
|
||||
|
||||
if (($item["object-type"] == ACTIVITY_OBJ_BOOKMARK) OR ($item["object-type"] == ACTIVITY_OBJ_EVENT)) {
|
||||
$item["title"] = $xpath->query('atom:title/text()', $entry)->item(0)->nodeValue;
|
||||
$item["body"] = $xpath->query('atom:summary/text()', $entry)->item(0)->nodeValue;
|
||||
} elseif ($item["object-type"] == ACTIVITY_OBJ_QUESTION)
|
||||
$item["title"] = $xpath->query('atom:title/text()', $entry)->item(0)->nodeValue;
|
||||
logger("Import OStatus message", LOGGER_DEBUG);
|
||||
|
||||
$item["object"] = $xml;
|
||||
$item["verb"] = $xpath->query('activity:verb/text()', $entry)->item(0)->nodeValue;
|
||||
if ($xml == "")
|
||||
return;
|
||||
|
||||
/// @TODO
|
||||
/// Delete a message
|
||||
if ($item["verb"] == "qvitter-delete-notice") {
|
||||
// ignore "Delete" messages (by now)
|
||||
logger("Ignore delete message ".print_r($item, true));
|
||||
continue;
|
||||
}
|
||||
//$tempfile = tempnam(get_temppath(), "import");
|
||||
//file_put_contents($tempfile, $xml);
|
||||
|
||||
if ($item["verb"] == ACTIVITY_JOIN) {
|
||||
// ignore "Join" messages
|
||||
logger("Ignore join message ".print_r($item, true));
|
||||
continue;
|
||||
}
|
||||
$doc = new DOMDocument();
|
||||
@$doc->loadXML($xml);
|
||||
|
||||
if ($item["verb"] == ACTIVITY_FOLLOW) {
|
||||
new_follower($importer, $contact, $item, $nickname);
|
||||
continue;
|
||||
}
|
||||
$xpath = new DomXPath($doc);
|
||||
$xpath->registerNamespace('atom', NAMESPACE_ATOM1);
|
||||
$xpath->registerNamespace('thr', NAMESPACE_THREAD);
|
||||
$xpath->registerNamespace('georss', NAMESPACE_GEORSS);
|
||||
$xpath->registerNamespace('activity', NAMESPACE_ACTIVITY);
|
||||
$xpath->registerNamespace('media', NAMESPACE_MEDIA);
|
||||
$xpath->registerNamespace('poco', NAMESPACE_POCO);
|
||||
$xpath->registerNamespace('ostatus', NAMESPACE_OSTATUS);
|
||||
$xpath->registerNamespace('statusnet', NAMESPACE_STATUSNET);
|
||||
|
||||
if ($item["verb"] == NAMESPACE_OSTATUS."/unfollow") {
|
||||
lose_follower($importer, $contact, $item, $dummy);
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($item["verb"] == ACTIVITY_FAVORITE) {
|
||||
$orig_uri = $xpath->query("activity:object/atom:id", $entry)->item(0)->nodeValue;
|
||||
logger("Favorite ".$orig_uri." ".print_r($item, true));
|
||||
|
||||
$item["verb"] = ACTIVITY_LIKE;
|
||||
$item["parent-uri"] = $orig_uri;
|
||||
$item["gravity"] = GRAVITY_LIKE;
|
||||
}
|
||||
|
||||
if ($item["verb"] == NAMESPACE_OSTATUS."/unfavorite") {
|
||||
// Ignore "Unfavorite" message
|
||||
logger("Ignore unfavorite message ".print_r($item, true));
|
||||
continue;
|
||||
}
|
||||
|
||||
// http://activitystrea.ms/schema/1.0/rsvp-yes
|
||||
if (!in_array($item["verb"], array(ACTIVITY_POST, ACTIVITY_LIKE, ACTIVITY_SHARE)))
|
||||
logger("Unhandled verb ".$item["verb"]." ".print_r($item, true));
|
||||
|
||||
$item["created"] = $xpath->query('atom:published/text()', $entry)->item(0)->nodeValue;
|
||||
$item["edited"] = $xpath->query('atom:updated/text()', $entry)->item(0)->nodeValue;
|
||||
$conversation = $xpath->query('ostatus:conversation/text()', $entry)->item(0)->nodeValue;
|
||||
|
||||
$related = "";
|
||||
|
||||
$inreplyto = $xpath->query('thr:in-reply-to', $entry);
|
||||
if (is_object($inreplyto->item(0))) {
|
||||
foreach($inreplyto->item(0)->attributes AS $attributes) {
|
||||
if ($attributes->name == "ref")
|
||||
$item["parent-uri"] = $attributes->textContent;
|
||||
if ($attributes->name == "href")
|
||||
$related = $attributes->textContent;
|
||||
}
|
||||
}
|
||||
|
||||
$georsspoint = $xpath->query('georss:point', $entry);
|
||||
if ($georsspoint)
|
||||
$item["coord"] = $georsspoint->item(0)->nodeValue;
|
||||
|
||||
/// @TODO
|
||||
/// $item["location"] =
|
||||
|
||||
$categories = $xpath->query('atom:category', $entry);
|
||||
if ($categories) {
|
||||
foreach ($categories AS $category) {
|
||||
foreach($category->attributes AS $attributes)
|
||||
if ($attributes->name == "term") {
|
||||
$term = $attributes->textContent;
|
||||
if(strlen($item["tag"]))
|
||||
$item["tag"] .= ',';
|
||||
$item["tag"] .= "#[url=".$a->get_baseurl()."/search?tag=".$term."]".$term."[/url]";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$self = "";
|
||||
$enclosure = "";
|
||||
|
||||
$links = $xpath->query('atom:link', $entry);
|
||||
if ($links) {
|
||||
$rel = "";
|
||||
$href = "";
|
||||
$type = "";
|
||||
$length = "0";
|
||||
$title = "";
|
||||
foreach ($links AS $link) {
|
||||
foreach($link->attributes AS $attributes) {
|
||||
if ($attributes->name == "href")
|
||||
$href = $attributes->textContent;
|
||||
if ($attributes->name == "rel")
|
||||
$rel = $attributes->textContent;
|
||||
if ($attributes->name == "type")
|
||||
$type = $attributes->textContent;
|
||||
if ($attributes->name == "length")
|
||||
$length = $attributes->textContent;
|
||||
if ($attributes->name == "title")
|
||||
$title = $attributes->textContent;
|
||||
$gub = "";
|
||||
$hub_attributes = $xpath->query("/atom:feed/atom:link[@rel='hub']")->item(0)->attributes;
|
||||
if (is_object($hub_attributes))
|
||||
foreach($hub_attributes AS $hub_attribute)
|
||||
if ($hub_attribute->name == "href") {
|
||||
$hub = $hub_attribute->textContent;
|
||||
logger("Found hub ".$hub, LOGGER_DEBUG);
|
||||
}
|
||||
if (($rel != "") AND ($href != ""))
|
||||
switch($rel) {
|
||||
case "alternate":
|
||||
$item["plink"] = $href;
|
||||
if (($item["object-type"] == ACTIVITY_OBJ_QUESTION) OR
|
||||
($item["object-type"] == ACTIVITY_OBJ_EVENT))
|
||||
$item["body"] .= add_page_info($href);
|
||||
break;
|
||||
case "ostatus:conversation":
|
||||
$conversation = $href;
|
||||
break;
|
||||
case "enclosure":
|
||||
$enclosure = $href;
|
||||
if(strlen($item["attach"]))
|
||||
$item["attach"] .= ',';
|
||||
|
||||
$item["attach"] .= '[attach]href="'.$href.'" length="'.$length.'" type="'.$type.'" title="'.$title.'"[/attach]';
|
||||
break;
|
||||
case "related":
|
||||
if ($item["object-type"] != ACTIVITY_OBJ_BOOKMARK) {
|
||||
if (!isset($item["parent-uri"]))
|
||||
$item["parent-uri"] = $href;
|
||||
$header = array();
|
||||
$header["uid"] = $importer["uid"];
|
||||
$header["network"] = NETWORK_OSTATUS;
|
||||
$header["type"] = "remote";
|
||||
$header["wall"] = 0;
|
||||
$header["origin"] = 0;
|
||||
$header["gravity"] = GRAVITY_PARENT;
|
||||
|
||||
if ($related == "")
|
||||
$related = $href;
|
||||
} else
|
||||
$item["body"] .= add_page_info($href);
|
||||
break;
|
||||
case "self":
|
||||
$self = $href;
|
||||
break;
|
||||
case "mentioned":
|
||||
// Notification check
|
||||
if ($importer["nurl"] == normalise_link($href))
|
||||
$mention = true;
|
||||
break;
|
||||
}
|
||||
// it could either be a received post or a post we fetched by ourselves
|
||||
// depending on that, the first node is different
|
||||
$first_child = $doc->firstChild->tagName;
|
||||
|
||||
if ($first_child == "feed")
|
||||
$entries = $xpath->query('/atom:feed/atom:entry');
|
||||
else
|
||||
$entries = $xpath->query('/atom:entry');
|
||||
|
||||
$conversation = "";
|
||||
$conversationlist = array();
|
||||
$item_id = 0;
|
||||
|
||||
// Reverse the order of the entries
|
||||
$entrylist = array();
|
||||
|
||||
foreach ($entries AS $entry)
|
||||
$entrylist[] = $entry;
|
||||
|
||||
foreach (array_reverse($entrylist) AS $entry) {
|
||||
|
||||
$mention = false;
|
||||
|
||||
// fetch the author
|
||||
if ($first_child == "feed")
|
||||
$author = self::fetchauthor($xpath, $doc->firstChild, $importer, $contact, false);
|
||||
else
|
||||
$author = self::fetchauthor($xpath, $entry, $importer, $contact, false);
|
||||
|
||||
$value = $xpath->evaluate('atom:author/poco:preferredUsername/text()', $context)->item(0)->nodeValue;
|
||||
if ($value != "")
|
||||
$nickname = $value;
|
||||
else
|
||||
$nickname = $author["author-name"];
|
||||
|
||||
$item = array_merge($header, $author);
|
||||
|
||||
// Now get the item
|
||||
$item["uri"] = $xpath->query('atom:id/text()', $entry)->item(0)->nodeValue;
|
||||
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s'",
|
||||
intval($importer["uid"]), dbesc($item["uri"]));
|
||||
if ($r) {
|
||||
logger("Item with uri ".$item["uri"]." for user ".$importer["uid"]." already existed under id ".$r[0]["id"], LOGGER_DEBUG);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
$local_id = "";
|
||||
$repeat_of = "";
|
||||
$item["body"] = add_page_info_to_body(html2bbcode($xpath->query('atom:content/text()', $entry)->item(0)->nodeValue));
|
||||
$item["object-type"] = $xpath->query('activity:object-type/text()', $entry)->item(0)->nodeValue;
|
||||
|
||||
$notice_info = $xpath->query('statusnet:notice_info', $entry);
|
||||
if ($notice_info AND ($notice_info->length > 0)) {
|
||||
foreach($notice_info->item(0)->attributes AS $attributes) {
|
||||
if ($attributes->name == "source")
|
||||
$item["app"] = strip_tags($attributes->textContent);
|
||||
if ($attributes->name == "local_id")
|
||||
$local_id = $attributes->textContent;
|
||||
if ($attributes->name == "repeat_of")
|
||||
$repeat_of = $attributes->textContent;
|
||||
if (($item["object-type"] == ACTIVITY_OBJ_BOOKMARK) OR ($item["object-type"] == ACTIVITY_OBJ_EVENT)) {
|
||||
$item["title"] = $xpath->query('atom:title/text()', $entry)->item(0)->nodeValue;
|
||||
$item["body"] = $xpath->query('atom:summary/text()', $entry)->item(0)->nodeValue;
|
||||
} elseif ($item["object-type"] == ACTIVITY_OBJ_QUESTION)
|
||||
$item["title"] = $xpath->query('atom:title/text()', $entry)->item(0)->nodeValue;
|
||||
|
||||
$item["object"] = $xml;
|
||||
$item["verb"] = $xpath->query('activity:verb/text()', $entry)->item(0)->nodeValue;
|
||||
|
||||
/// @TODO
|
||||
/// Delete a message
|
||||
if ($item["verb"] == "qvitter-delete-notice") {
|
||||
// ignore "Delete" messages (by now)
|
||||
logger("Ignore delete message ".print_r($item, true));
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
// Is it a repeated post?
|
||||
if ($repeat_of != "") {
|
||||
$activityobjects = $xpath->query('activity:object', $entry)->item(0);
|
||||
if ($item["verb"] == ACTIVITY_JOIN) {
|
||||
// ignore "Join" messages
|
||||
logger("Ignore join message ".print_r($item, true));
|
||||
continue;
|
||||
}
|
||||
|
||||
if (is_object($activityobjects)) {
|
||||
if ($item["verb"] == ACTIVITY_FOLLOW) {
|
||||
new_follower($importer, $contact, $item, $nickname);
|
||||
continue;
|
||||
}
|
||||
|
||||
$orig_uri = $xpath->query("activity:object/atom:id", $activityobjects)->item(0)->nodeValue;
|
||||
if (!isset($orig_uri))
|
||||
$orig_uri = $xpath->query('atom:id/text()', $activityobjects)->item(0)->nodeValue;
|
||||
if ($item["verb"] == NAMESPACE_OSTATUS."/unfollow") {
|
||||
lose_follower($importer, $contact, $item, $dummy);
|
||||
continue;
|
||||
}
|
||||
|
||||
$orig_links = $xpath->query("activity:object/atom:link[@rel='alternate']", $activityobjects);
|
||||
if ($orig_links AND ($orig_links->length > 0))
|
||||
foreach($orig_links->item(0)->attributes AS $attributes)
|
||||
if ($item["verb"] == ACTIVITY_FAVORITE) {
|
||||
$orig_uri = $xpath->query("activity:object/atom:id", $entry)->item(0)->nodeValue;
|
||||
logger("Favorite ".$orig_uri." ".print_r($item, true));
|
||||
|
||||
$item["verb"] = ACTIVITY_LIKE;
|
||||
$item["parent-uri"] = $orig_uri;
|
||||
$item["gravity"] = GRAVITY_LIKE;
|
||||
}
|
||||
|
||||
if ($item["verb"] == NAMESPACE_OSTATUS."/unfavorite") {
|
||||
// Ignore "Unfavorite" message
|
||||
logger("Ignore unfavorite message ".print_r($item, true));
|
||||
continue;
|
||||
}
|
||||
|
||||
// http://activitystrea.ms/schema/1.0/rsvp-yes
|
||||
if (!in_array($item["verb"], array(ACTIVITY_POST, ACTIVITY_LIKE, ACTIVITY_SHARE)))
|
||||
logger("Unhandled verb ".$item["verb"]." ".print_r($item, true));
|
||||
|
||||
$item["created"] = $xpath->query('atom:published/text()', $entry)->item(0)->nodeValue;
|
||||
$item["edited"] = $xpath->query('atom:updated/text()', $entry)->item(0)->nodeValue;
|
||||
$conversation = $xpath->query('ostatus:conversation/text()', $entry)->item(0)->nodeValue;
|
||||
|
||||
$related = "";
|
||||
|
||||
$inreplyto = $xpath->query('thr:in-reply-to', $entry);
|
||||
if (is_object($inreplyto->item(0))) {
|
||||
foreach($inreplyto->item(0)->attributes AS $attributes) {
|
||||
if ($attributes->name == "ref")
|
||||
$item["parent-uri"] = $attributes->textContent;
|
||||
if ($attributes->name == "href")
|
||||
$related = $attributes->textContent;
|
||||
}
|
||||
}
|
||||
|
||||
$georsspoint = $xpath->query('georss:point', $entry);
|
||||
if ($georsspoint)
|
||||
$item["coord"] = $georsspoint->item(0)->nodeValue;
|
||||
|
||||
$categories = $xpath->query('atom:category', $entry);
|
||||
if ($categories) {
|
||||
foreach ($categories AS $category) {
|
||||
foreach($category->attributes AS $attributes)
|
||||
if ($attributes->name == "term") {
|
||||
$term = $attributes->textContent;
|
||||
if(strlen($item["tag"]))
|
||||
$item["tag"] .= ',';
|
||||
$item["tag"] .= "#[url=".App::get_baseurl()."/search?tag=".$term."]".$term."[/url]";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$self = "";
|
||||
$enclosure = "";
|
||||
|
||||
$links = $xpath->query('atom:link', $entry);
|
||||
if ($links) {
|
||||
$rel = "";
|
||||
$href = "";
|
||||
$type = "";
|
||||
$length = "0";
|
||||
$title = "";
|
||||
foreach ($links AS $link) {
|
||||
foreach($link->attributes AS $attributes) {
|
||||
if ($attributes->name == "href")
|
||||
$orig_link = $attributes->textContent;
|
||||
$href = $attributes->textContent;
|
||||
if ($attributes->name == "rel")
|
||||
$rel = $attributes->textContent;
|
||||
if ($attributes->name == "type")
|
||||
$type = $attributes->textContent;
|
||||
if ($attributes->name == "length")
|
||||
$length = $attributes->textContent;
|
||||
if ($attributes->name == "title")
|
||||
$title = $attributes->textContent;
|
||||
}
|
||||
if (($rel != "") AND ($href != ""))
|
||||
switch($rel) {
|
||||
case "alternate":
|
||||
$item["plink"] = $href;
|
||||
if (($item["object-type"] == ACTIVITY_OBJ_QUESTION) OR
|
||||
($item["object-type"] == ACTIVITY_OBJ_EVENT))
|
||||
$item["body"] .= add_page_info($href);
|
||||
break;
|
||||
case "ostatus:conversation":
|
||||
$conversation = $href;
|
||||
break;
|
||||
case "enclosure":
|
||||
$enclosure = $href;
|
||||
if(strlen($item["attach"]))
|
||||
$item["attach"] .= ',';
|
||||
|
||||
if (!isset($orig_link))
|
||||
$orig_link = $xpath->query("atom:link[@rel='alternate']", $activityobjects)->item(0)->nodeValue;
|
||||
$item["attach"] .= '[attach]href="'.$href.'" length="'.$length.'" type="'.$type.'" title="'.$title.'"[/attach]';
|
||||
break;
|
||||
case "related":
|
||||
if ($item["object-type"] != ACTIVITY_OBJ_BOOKMARK) {
|
||||
if (!isset($item["parent-uri"]))
|
||||
$item["parent-uri"] = $href;
|
||||
|
||||
if (!isset($orig_link))
|
||||
$orig_link = ostatus_convert_href($orig_uri);
|
||||
if ($related == "")
|
||||
$related = $href;
|
||||
} else
|
||||
$item["body"] .= add_page_info($href);
|
||||
break;
|
||||
case "self":
|
||||
$self = $href;
|
||||
break;
|
||||
case "mentioned":
|
||||
// Notification check
|
||||
if ($importer["nurl"] == normalise_link($href))
|
||||
$mention = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
$orig_body = $xpath->query('activity:object/atom:content/text()', $activityobjects)->item(0)->nodeValue;
|
||||
if (!isset($orig_body))
|
||||
$orig_body = $xpath->query('atom:content/text()', $activityobjects)->item(0)->nodeValue;
|
||||
$local_id = "";
|
||||
$repeat_of = "";
|
||||
|
||||
$orig_created = $xpath->query('atom:published/text()', $activityobjects)->item(0)->nodeValue;
|
||||
$notice_info = $xpath->query('statusnet:notice_info', $entry);
|
||||
if ($notice_info AND ($notice_info->length > 0)) {
|
||||
foreach($notice_info->item(0)->attributes AS $attributes) {
|
||||
if ($attributes->name == "source")
|
||||
$item["app"] = strip_tags($attributes->textContent);
|
||||
if ($attributes->name == "local_id")
|
||||
$local_id = $attributes->textContent;
|
||||
if ($attributes->name == "repeat_of")
|
||||
$repeat_of = $attributes->textContent;
|
||||
}
|
||||
}
|
||||
|
||||
$orig_contact = $contact;
|
||||
$orig_author = ostatus_fetchauthor($xpath, $activityobjects, $importer, $orig_contact, false);
|
||||
// Is it a repeated post?
|
||||
if ($repeat_of != "") {
|
||||
$activityobjects = $xpath->query('activity:object', $entry)->item(0);
|
||||
|
||||
if (is_object($activityobjects)) {
|
||||
|
||||
$orig_uri = $xpath->query("activity:object/atom:id", $activityobjects)->item(0)->nodeValue;
|
||||
if (!isset($orig_uri))
|
||||
$orig_uri = $xpath->query('atom:id/text()', $activityobjects)->item(0)->nodeValue;
|
||||
|
||||
$orig_links = $xpath->query("activity:object/atom:link[@rel='alternate']", $activityobjects);
|
||||
if ($orig_links AND ($orig_links->length > 0))
|
||||
foreach($orig_links->item(0)->attributes AS $attributes)
|
||||
if ($attributes->name == "href")
|
||||
$orig_link = $attributes->textContent;
|
||||
|
||||
if (!isset($orig_link))
|
||||
$orig_link = $xpath->query("atom:link[@rel='alternate']", $activityobjects)->item(0)->nodeValue;
|
||||
|
||||
if (!isset($orig_link))
|
||||
$orig_link = self::convert_href($orig_uri);
|
||||
|
||||
$orig_body = $xpath->query('activity:object/atom:content/text()', $activityobjects)->item(0)->nodeValue;
|
||||
if (!isset($orig_body))
|
||||
$orig_body = $xpath->query('atom:content/text()', $activityobjects)->item(0)->nodeValue;
|
||||
|
||||
$orig_created = $xpath->query('atom:published/text()', $activityobjects)->item(0)->nodeValue;
|
||||
|
||||
$orig_contact = $contact;
|
||||
$orig_author = self::fetchauthor($xpath, $activityobjects, $importer, $orig_contact, false);
|
||||
|
||||
//if (!intval(get_config('system','wall-to-wall_share'))) {
|
||||
// $prefix = share_header($orig_author['author-name'], $orig_author['author-link'], $orig_author['author-avatar'], "", $orig_created, $orig_link);
|
||||
// $item["body"] = $prefix.add_page_info_to_body(html2bbcode($orig_body))."[/share]";
|
||||
//} else {
|
||||
$item["author-name"] = $orig_author["author-name"];
|
||||
$item["author-link"] = $orig_author["author-link"];
|
||||
$item["author-avatar"] = $orig_author["author-avatar"];
|
||||
|
|
@ -498,1146 +504,1511 @@ function ostatus_import($xml,$importer,&$contact, &$hub) {
|
|||
|
||||
$item["uri"] = $orig_uri;
|
||||
$item["plink"] = $orig_link;
|
||||
//}
|
||||
|
||||
$item["verb"] = $xpath->query('activity:verb/text()', $activityobjects)->item(0)->nodeValue;
|
||||
$item["verb"] = $xpath->query('activity:verb/text()', $activityobjects)->item(0)->nodeValue;
|
||||
|
||||
$item["object-type"] = $xpath->query('activity:object/activity:object-type/text()', $activityobjects)->item(0)->nodeValue;
|
||||
if (!isset($item["object-type"]))
|
||||
$item["object-type"] = $xpath->query('activity:object-type/text()', $activityobjects)->item(0)->nodeValue;
|
||||
}
|
||||
}
|
||||
|
||||
//if ($enclosure != "")
|
||||
// $item["body"] .= add_page_info($enclosure);
|
||||
|
||||
if (isset($item["parent-uri"])) {
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s'",
|
||||
intval($importer["uid"]), dbesc($item["parent-uri"]));
|
||||
|
||||
if (!$r AND ($related != "")) {
|
||||
$reply_path = str_replace("/notice/", "/api/statuses/show/", $related).".atom";
|
||||
|
||||
if ($reply_path != $related) {
|
||||
logger("Fetching related items for user ".$importer["uid"]." from ".$reply_path, LOGGER_DEBUG);
|
||||
$reply_xml = fetch_url($reply_path);
|
||||
|
||||
$reply_contact = $contact;
|
||||
ostatus_import($reply_xml,$importer,$reply_contact, $reply_hub);
|
||||
|
||||
// After the import try to fetch the parent item again
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s'",
|
||||
intval($importer["uid"]), dbesc($item["parent-uri"]));
|
||||
$item["object-type"] = $xpath->query('activity:object/activity:object-type/text()', $activityobjects)->item(0)->nodeValue;
|
||||
if (!isset($item["object-type"]))
|
||||
$item["object-type"] = $xpath->query('activity:object-type/text()', $activityobjects)->item(0)->nodeValue;
|
||||
}
|
||||
}
|
||||
if ($r) {
|
||||
$item["type"] = 'remote-comment';
|
||||
$item["gravity"] = GRAVITY_COMMENT;
|
||||
}
|
||||
} else
|
||||
$item["parent-uri"] = $item["uri"];
|
||||
|
||||
$item_id = ostatus_completion($conversation, $importer["uid"], $item);
|
||||
//if ($enclosure != "")
|
||||
// $item["body"] .= add_page_info($enclosure);
|
||||
|
||||
if (!$item_id) {
|
||||
logger("Error storing item", LOGGER_DEBUG);
|
||||
continue;
|
||||
}
|
||||
if (isset($item["parent-uri"])) {
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s'",
|
||||
intval($importer["uid"]), dbesc($item["parent-uri"]));
|
||||
|
||||
logger("Item was stored with id ".$item_id, LOGGER_DEBUG);
|
||||
}
|
||||
}
|
||||
if (!$r AND ($related != "")) {
|
||||
$reply_path = str_replace("/notice/", "/api/statuses/show/", $related).".atom";
|
||||
|
||||
function ostatus_convert_href($href) {
|
||||
$elements = explode(":",$href);
|
||||
if ($reply_path != $related) {
|
||||
logger("Fetching related items for user ".$importer["uid"]." from ".$reply_path, LOGGER_DEBUG);
|
||||
$reply_xml = fetch_url($reply_path);
|
||||
|
||||
if ((count($elements) <= 2) OR ($elements[0] != "tag"))
|
||||
return $href;
|
||||
$reply_contact = $contact;
|
||||
self::import($reply_xml,$importer,$reply_contact, $reply_hub);
|
||||
|
||||
$server = explode(",", $elements[1]);
|
||||
$conversation = explode("=", $elements[2]);
|
||||
|
||||
if ((count($elements) == 4) AND ($elements[2] == "post"))
|
||||
return "http://".$server[0]."/notice/".$elements[3];
|
||||
|
||||
if ((count($conversation) != 2) OR ($conversation[1] ==""))
|
||||
return $href;
|
||||
|
||||
if ($elements[3] == "objectType=thread")
|
||||
return "http://".$server[0]."/conversation/".$conversation[1];
|
||||
else
|
||||
return "http://".$server[0]."/notice/".$conversation[1];
|
||||
|
||||
return $href;
|
||||
}
|
||||
|
||||
function check_conversations($mentions = false, $override = false) {
|
||||
$last = get_config('system','ostatus_last_poll');
|
||||
|
||||
$poll_interval = intval(get_config('system','ostatus_poll_interval'));
|
||||
if(! $poll_interval)
|
||||
$poll_interval = OSTATUS_DEFAULT_POLL_INTERVAL;
|
||||
|
||||
// Don't poll if the interval is set negative
|
||||
if (($poll_interval < 0) AND !$override)
|
||||
return;
|
||||
|
||||
if (!$mentions) {
|
||||
$poll_timeframe = intval(get_config('system','ostatus_poll_timeframe'));
|
||||
if (!$poll_timeframe)
|
||||
$poll_timeframe = OSTATUS_DEFAULT_POLL_TIMEFRAME;
|
||||
} else {
|
||||
$poll_timeframe = intval(get_config('system','ostatus_poll_timeframe'));
|
||||
if (!$poll_timeframe)
|
||||
$poll_timeframe = OSTATUS_DEFAULT_POLL_TIMEFRAME_MENTIONS;
|
||||
}
|
||||
|
||||
|
||||
if ($last AND !$override) {
|
||||
$next = $last + ($poll_interval * 60);
|
||||
if ($next > time()) {
|
||||
logger('poll interval not reached');
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
logger('cron_start');
|
||||
|
||||
$start = date("Y-m-d H:i:s", time() - ($poll_timeframe * 60));
|
||||
|
||||
if ($mentions)
|
||||
$conversations = q("SELECT `term`.`oid`, `term`.`url`, `term`.`uid` FROM `term`
|
||||
STRAIGHT_JOIN `thread` ON `thread`.`iid` = `term`.`oid` AND `thread`.`uid` = `term`.`uid`
|
||||
WHERE `term`.`type` = 7 AND `term`.`term` > '%s' AND `thread`.`mention`
|
||||
GROUP BY `term`.`url`, `term`.`uid` ORDER BY `term`.`term` DESC", dbesc($start));
|
||||
else
|
||||
$conversations = q("SELECT `oid`, `url`, `uid` FROM `term`
|
||||
WHERE `type` = 7 AND `term` > '%s'
|
||||
GROUP BY `url`, `uid` ORDER BY `term` DESC", dbesc($start));
|
||||
|
||||
foreach ($conversations AS $conversation) {
|
||||
ostatus_completion($conversation['url'], $conversation['uid']);
|
||||
}
|
||||
|
||||
logger('cron_end');
|
||||
|
||||
set_config('system','ostatus_last_poll', time());
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Updates the gcontact table with actor data from the conversation
|
||||
*
|
||||
* @param object $actor The actor object that contains the contact data
|
||||
*/
|
||||
function ostatus_conv_fetch_actor($actor) {
|
||||
|
||||
// We set the generation to "3" since the data here is not as reliable as the data we get on other occasions
|
||||
$contact = array("network" => NETWORK_OSTATUS, "generation" => 3);
|
||||
|
||||
if (isset($actor->url))
|
||||
$contact["url"] = $actor->url;
|
||||
|
||||
if (isset($actor->displayName))
|
||||
$contact["name"] = $actor->displayName;
|
||||
|
||||
if (isset($actor->portablecontacts_net->displayName))
|
||||
$contact["name"] = $actor->portablecontacts_net->displayName;
|
||||
|
||||
if (isset($actor->portablecontacts_net->preferredUsername))
|
||||
$contact["nick"] = $actor->portablecontacts_net->preferredUsername;
|
||||
|
||||
if (isset($actor->id))
|
||||
$contact["alias"] = $actor->id;
|
||||
|
||||
if (isset($actor->summary))
|
||||
$contact["about"] = $actor->summary;
|
||||
|
||||
if (isset($actor->portablecontacts_net->note))
|
||||
$contact["about"] = $actor->portablecontacts_net->note;
|
||||
|
||||
if (isset($actor->portablecontacts_net->addresses->formatted))
|
||||
$contact["location"] = $actor->portablecontacts_net->addresses->formatted;
|
||||
|
||||
|
||||
if (isset($actor->image->url))
|
||||
$contact["photo"] = $actor->image->url;
|
||||
|
||||
if (isset($actor->image->width))
|
||||
$avatarwidth = $actor->image->width;
|
||||
|
||||
if (is_array($actor->status_net->avatarLinks))
|
||||
foreach ($actor->status_net->avatarLinks AS $avatar) {
|
||||
if ($avatarsize < $avatar->width) {
|
||||
$contact["photo"] = $avatar->url;
|
||||
$avatarsize = $avatar->width;
|
||||
}
|
||||
}
|
||||
|
||||
update_gcontact($contact);
|
||||
}
|
||||
|
||||
|
||||
function ostatus_completion($conversation_url, $uid, $item = array()) {
|
||||
|
||||
$a = get_app();
|
||||
|
||||
$item_stored = -1;
|
||||
|
||||
$conversation_url = ostatus_convert_href($conversation_url);
|
||||
|
||||
// If the thread shouldn't be completed then store the item and go away
|
||||
if ((intval(get_config('system','ostatus_poll_interval')) == -2) AND (count($item) > 0)) {
|
||||
//$arr["app"] .= " (OStatus-NoCompletion)";
|
||||
$item_stored = item_store($item, true);
|
||||
return($item_stored);
|
||||
}
|
||||
|
||||
// Get the parent
|
||||
$parents = q("SELECT `id`, `parent`, `uri`, `contact-id`, `type`, `verb`, `visible` FROM `item` WHERE `id` IN
|
||||
(SELECT `parent` FROM `item` WHERE `id` IN
|
||||
(SELECT `oid` FROM `term` WHERE `uid` = %d AND `otype` = %d AND `type` = %d AND `url` = '%s'))",
|
||||
intval($uid), intval(TERM_OBJ_POST), intval(TERM_CONVERSATION), dbesc($conversation_url));
|
||||
|
||||
if ($parents)
|
||||
$parent = $parents[0];
|
||||
elseif (count($item) > 0) {
|
||||
$parent = $item;
|
||||
$parent["type"] = "remote";
|
||||
$parent["verb"] = ACTIVITY_POST;
|
||||
$parent["visible"] = 1;
|
||||
} else {
|
||||
// Preset the parent
|
||||
$r = q("SELECT `id` FROM `contact` WHERE `self` AND `uid`=%d", $uid);
|
||||
if (!$r)
|
||||
return(-2);
|
||||
|
||||
$parent = array();
|
||||
$parent["id"] = 0;
|
||||
$parent["parent"] = 0;
|
||||
$parent["uri"] = "";
|
||||
$parent["contact-id"] = $r[0]["id"];
|
||||
$parent["type"] = "remote";
|
||||
$parent["verb"] = ACTIVITY_POST;
|
||||
$parent["visible"] = 1;
|
||||
}
|
||||
|
||||
$conv = str_replace("/conversation/", "/api/statusnet/conversation/", $conversation_url).".as";
|
||||
$pageno = 1;
|
||||
$items = array();
|
||||
|
||||
logger('fetching conversation url '.$conv.' for user '.$uid);
|
||||
|
||||
do {
|
||||
$conv_arr = z_fetch_url($conv."?page=".$pageno);
|
||||
|
||||
// If it is a non-ssl site and there is an error, then try ssl or vice versa
|
||||
if (!$conv_arr["success"] AND (substr($conv, 0, 7) == "http://")) {
|
||||
$conv = str_replace("http://", "https://", $conv);
|
||||
$conv_as = fetch_url($conv."?page=".$pageno);
|
||||
} elseif (!$conv_arr["success"] AND (substr($conv, 0, 8) == "https://")) {
|
||||
$conv = str_replace("https://", "http://", $conv);
|
||||
$conv_as = fetch_url($conv."?page=".$pageno);
|
||||
} else
|
||||
$conv_as = $conv_arr["body"];
|
||||
|
||||
$conv_as = str_replace(',"statusnet:notice_info":', ',"statusnet_notice_info":', $conv_as);
|
||||
$conv_as = json_decode($conv_as);
|
||||
|
||||
$no_of_items = sizeof($items);
|
||||
|
||||
if (@is_array($conv_as->items))
|
||||
foreach ($conv_as->items AS $single_item)
|
||||
$items[$single_item->id] = $single_item;
|
||||
|
||||
if ($no_of_items == sizeof($items))
|
||||
break;
|
||||
|
||||
$pageno++;
|
||||
|
||||
} while (true);
|
||||
|
||||
logger('fetching conversation done. Found '.count($items).' items');
|
||||
|
||||
if (!sizeof($items)) {
|
||||
if (count($item) > 0) {
|
||||
//$arr["app"] .= " (OStatus-NoConvFetched)";
|
||||
$item_stored = item_store($item, true);
|
||||
|
||||
if ($item_stored) {
|
||||
logger("Conversation ".$conversation_url." couldn't be fetched. Item uri ".$item["uri"]." stored: ".$item_stored, LOGGER_DEBUG);
|
||||
ostatus_store_conversation($item_id, $conversation_url);
|
||||
}
|
||||
|
||||
return($item_stored);
|
||||
} else
|
||||
return(-3);
|
||||
}
|
||||
|
||||
$items = array_reverse($items);
|
||||
|
||||
$r = q("SELECT `nurl` FROM `contact` WHERE `uid` = %d AND `self`", intval($uid));
|
||||
$importer = $r[0];
|
||||
|
||||
foreach ($items as $single_conv) {
|
||||
|
||||
// Update the gcontact table
|
||||
ostatus_conv_fetch_actor($single_conv->actor);
|
||||
|
||||
// Test - remove before flight
|
||||
//$tempfile = tempnam(get_temppath(), "conversation");
|
||||
//file_put_contents($tempfile, json_encode($single_conv));
|
||||
|
||||
$mention = false;
|
||||
|
||||
if (isset($single_conv->object->id))
|
||||
$single_conv->id = $single_conv->object->id;
|
||||
|
||||
$plink = ostatus_convert_href($single_conv->id);
|
||||
if (isset($single_conv->object->url))
|
||||
$plink = ostatus_convert_href($single_conv->object->url);
|
||||
|
||||
if (@!$single_conv->id)
|
||||
continue;
|
||||
|
||||
logger("Got id ".$single_conv->id, LOGGER_DEBUG);
|
||||
|
||||
if ($first_id == "") {
|
||||
$first_id = $single_conv->id;
|
||||
|
||||
// The first post of the conversation isn't our first post. There are three options:
|
||||
// 1. Our conversation hasn't the "real" thread starter
|
||||
// 2. This first post is a post inside our thread
|
||||
// 3. This first post is a post inside another thread
|
||||
if (($first_id != $parent["uri"]) AND ($parent["uri"] != "")) {
|
||||
$new_parents = q("SELECT `id`, `parent`, `uri`, `contact-id`, `type`, `verb`, `visible` FROM `item` WHERE `id` IN
|
||||
(SELECT `parent` FROM `item`
|
||||
WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s')) LIMIT 1",
|
||||
intval($uid), dbesc($first_id), dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN));
|
||||
if ($new_parents) {
|
||||
if ($new_parents[0]["parent"] == $parent["parent"]) {
|
||||
// Option 2: This post is already present inside our thread - but not as thread starter
|
||||
logger("Option 2: uri present in our thread: ".$first_id, LOGGER_DEBUG);
|
||||
$first_id = $parent["uri"];
|
||||
} else {
|
||||
// Option 3: Not so good. We have mixed parents. We have to see how to clean this up.
|
||||
// For now just take the new parent.
|
||||
$parent = $new_parents[0];
|
||||
$first_id = $parent["uri"];
|
||||
logger("Option 3: mixed parents for uri ".$first_id, LOGGER_DEBUG);
|
||||
// After the import try to fetch the parent item again
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s'",
|
||||
intval($importer["uid"]), dbesc($item["parent-uri"]));
|
||||
}
|
||||
} else {
|
||||
// Option 1: We hadn't got the real thread starter
|
||||
// We have to clean up our existing messages.
|
||||
$parent["id"] = 0;
|
||||
$parent["uri"] = $first_id;
|
||||
logger("Option 1: we have a new parent: ".$first_id, LOGGER_DEBUG);
|
||||
}
|
||||
} elseif ($parent["uri"] == "") {
|
||||
$parent["id"] = 0;
|
||||
$parent["uri"] = $first_id;
|
||||
}
|
||||
}
|
||||
|
||||
$parent_uri = $parent["uri"];
|
||||
|
||||
// "context" only seems to exist on older servers
|
||||
if (isset($single_conv->context->inReplyTo->id)) {
|
||||
$parent_exists = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s') LIMIT 1",
|
||||
intval($uid), dbesc($single_conv->context->inReplyTo->id), dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN));
|
||||
if ($parent_exists)
|
||||
$parent_uri = $single_conv->context->inReplyTo->id;
|
||||
}
|
||||
|
||||
// This is the current way
|
||||
if (isset($single_conv->object->inReplyTo->id)) {
|
||||
$parent_exists = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s') LIMIT 1",
|
||||
intval($uid), dbesc($single_conv->object->inReplyTo->id), dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN));
|
||||
if ($parent_exists)
|
||||
$parent_uri = $single_conv->object->inReplyTo->id;
|
||||
}
|
||||
|
||||
$message_exists = q("SELECT `id`, `parent`, `uri` FROM `item` WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s') LIMIT 1",
|
||||
intval($uid), dbesc($single_conv->id),
|
||||
dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN));
|
||||
if ($message_exists) {
|
||||
logger("Message ".$single_conv->id." already existed on the system", LOGGER_DEBUG);
|
||||
|
||||
if ($parent["id"] != 0) {
|
||||
$existing_message = $message_exists[0];
|
||||
|
||||
// We improved the way we fetch OStatus messages, this shouldn't happen very often now
|
||||
/// @TODO We have to change the shadow copies as well. This way here is really ugly.
|
||||
if ($existing_message["parent"] != $parent["id"]) {
|
||||
logger('updating id '.$existing_message["id"].' with parent '.$existing_message["parent"].' to parent '.$parent["id"].' uri '.$parent["uri"].' thread '.$parent_uri, LOGGER_DEBUG);
|
||||
|
||||
// Update the parent id of the selected item
|
||||
$r = q("UPDATE `item` SET `parent` = %d, `parent-uri` = '%s' WHERE `id` = %d",
|
||||
intval($parent["id"]), dbesc($parent["uri"]), intval($existing_message["id"]));
|
||||
|
||||
// Update the parent uri in the thread - but only if it points to itself
|
||||
$r = q("UPDATE `item` SET `thr-parent` = '%s' WHERE `id` = %d AND `uri` = `thr-parent`",
|
||||
dbesc($parent_uri), intval($existing_message["id"]));
|
||||
|
||||
// try to change all items of the same parent
|
||||
$r = q("UPDATE `item` SET `parent` = %d, `parent-uri` = '%s' WHERE `parent` = %d",
|
||||
intval($parent["id"]), dbesc($parent["uri"]), intval($existing_message["parent"]));
|
||||
|
||||
// Update the parent uri in the thread - but only if it points to itself
|
||||
$r = q("UPDATE `item` SET `thr-parent` = '%s' WHERE (`parent` = %d) AND (`uri` = `thr-parent`)",
|
||||
dbesc($parent["uri"]), intval($existing_message["parent"]));
|
||||
|
||||
// Now delete the thread
|
||||
delete_thread($existing_message["parent"]);
|
||||
if ($r) {
|
||||
$item["type"] = 'remote-comment';
|
||||
$item["gravity"] = GRAVITY_COMMENT;
|
||||
}
|
||||
} else
|
||||
$item["parent-uri"] = $item["uri"];
|
||||
|
||||
$item_id = self::completion($conversation, $importer["uid"], $item, $self);
|
||||
|
||||
if (!$item_id) {
|
||||
logger("Error storing item", LOGGER_DEBUG);
|
||||
continue;
|
||||
}
|
||||
|
||||
// The item we are having on the system is the one that we wanted to store via the item array
|
||||
if (isset($item["uri"]) AND ($item["uri"] == $existing_message["uri"])) {
|
||||
$item = array();
|
||||
$item_stored = 0;
|
||||
}
|
||||
|
||||
continue;
|
||||
logger("Item was stored with id ".$item_id, LOGGER_DEBUG);
|
||||
}
|
||||
}
|
||||
|
||||
if (is_array($single_conv->to))
|
||||
foreach($single_conv->to AS $to)
|
||||
if ($importer["nurl"] == normalise_link($to->id))
|
||||
$mention = true;
|
||||
/**
|
||||
* @brief Create an url out of an uri
|
||||
*
|
||||
* @param string $href URI in the format "parameter1:parameter1:..."
|
||||
*
|
||||
* @return string URL in the format http(s)://....
|
||||
*/
|
||||
public static function convert_href($href) {
|
||||
$elements = explode(":",$href);
|
||||
|
||||
$actor = $single_conv->actor->id;
|
||||
if (isset($single_conv->actor->url))
|
||||
$actor = $single_conv->actor->url;
|
||||
if ((count($elements) <= 2) OR ($elements[0] != "tag"))
|
||||
return $href;
|
||||
|
||||
$contact = q("SELECT `id` FROM `contact` WHERE `uid` = %d AND `nurl` = '%s' AND `network` != '%s'",
|
||||
$uid, normalise_link($actor), NETWORK_STATUSNET);
|
||||
$server = explode(",", $elements[1]);
|
||||
$conversation = explode("=", $elements[2]);
|
||||
|
||||
if (count($contact)) {
|
||||
logger("Found contact for url ".$actor, LOGGER_DEBUG);
|
||||
$contact_id = $contact[0]["id"];
|
||||
if ((count($elements) == 4) AND ($elements[2] == "post"))
|
||||
return "http://".$server[0]."/notice/".$elements[3];
|
||||
|
||||
if ((count($conversation) != 2) OR ($conversation[1] ==""))
|
||||
return $href;
|
||||
|
||||
if ($elements[3] == "objectType=thread")
|
||||
return "http://".$server[0]."/conversation/".$conversation[1];
|
||||
else
|
||||
return "http://".$server[0]."/notice/".$conversation[1];
|
||||
|
||||
return $href;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Checks if there are entries in conversations that aren't present on our side
|
||||
*
|
||||
* @param bool $mentions Fetch conversations where we are mentioned
|
||||
* @param bool $override Override the interval setting
|
||||
*/
|
||||
public static function check_conversations($mentions = false, $override = false) {
|
||||
$last = get_config('system','ostatus_last_poll');
|
||||
|
||||
$poll_interval = intval(get_config('system','ostatus_poll_interval'));
|
||||
if(! $poll_interval)
|
||||
$poll_interval = OSTATUS_DEFAULT_POLL_INTERVAL;
|
||||
|
||||
// Don't poll if the interval is set negative
|
||||
if (($poll_interval < 0) AND !$override)
|
||||
return;
|
||||
|
||||
if (!$mentions) {
|
||||
$poll_timeframe = intval(get_config('system','ostatus_poll_timeframe'));
|
||||
if (!$poll_timeframe)
|
||||
$poll_timeframe = OSTATUS_DEFAULT_POLL_TIMEFRAME;
|
||||
} else {
|
||||
logger("No contact found for url ".$actor, LOGGER_DEBUG);
|
||||
$poll_timeframe = intval(get_config('system','ostatus_poll_timeframe'));
|
||||
if (!$poll_timeframe)
|
||||
$poll_timeframe = OSTATUS_DEFAULT_POLL_TIMEFRAME_MENTIONS;
|
||||
}
|
||||
|
||||
|
||||
if ($last AND !$override) {
|
||||
$next = $last + ($poll_interval * 60);
|
||||
if ($next > time()) {
|
||||
logger('poll interval not reached');
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
logger('cron_start');
|
||||
|
||||
$start = date("Y-m-d H:i:s", time() - ($poll_timeframe * 60));
|
||||
|
||||
if ($mentions)
|
||||
$conversations = q("SELECT `term`.`oid`, `term`.`url`, `term`.`uid` FROM `term`
|
||||
STRAIGHT_JOIN `thread` ON `thread`.`iid` = `term`.`oid` AND `thread`.`uid` = `term`.`uid`
|
||||
WHERE `term`.`type` = 7 AND `term`.`term` > '%s' AND `thread`.`mention`
|
||||
GROUP BY `term`.`url`, `term`.`uid` ORDER BY `term`.`term` DESC", dbesc($start));
|
||||
else
|
||||
$conversations = q("SELECT `oid`, `url`, `uid` FROM `term`
|
||||
WHERE `type` = 7 AND `term` > '%s'
|
||||
GROUP BY `url`, `uid` ORDER BY `term` DESC", dbesc($start));
|
||||
|
||||
foreach ($conversations AS $conversation) {
|
||||
self::completion($conversation['url'], $conversation['uid']);
|
||||
}
|
||||
|
||||
logger('cron_end');
|
||||
|
||||
set_config('system','ostatus_last_poll', time());
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Updates the gcontact table with actor data from the conversation
|
||||
*
|
||||
* @param object $actor The actor object that contains the contact data
|
||||
*/
|
||||
private function conv_fetch_actor($actor) {
|
||||
|
||||
// We set the generation to "3" since the data here is not as reliable as the data we get on other occasions
|
||||
$contact = array("network" => NETWORK_OSTATUS, "generation" => 3);
|
||||
|
||||
if (isset($actor->url))
|
||||
$contact["url"] = $actor->url;
|
||||
|
||||
if (isset($actor->displayName))
|
||||
$contact["name"] = $actor->displayName;
|
||||
|
||||
if (isset($actor->portablecontacts_net->displayName))
|
||||
$contact["name"] = $actor->portablecontacts_net->displayName;
|
||||
|
||||
if (isset($actor->portablecontacts_net->preferredUsername))
|
||||
$contact["nick"] = $actor->portablecontacts_net->preferredUsername;
|
||||
|
||||
if (isset($actor->id))
|
||||
$contact["alias"] = $actor->id;
|
||||
|
||||
if (isset($actor->summary))
|
||||
$contact["about"] = $actor->summary;
|
||||
|
||||
if (isset($actor->portablecontacts_net->note))
|
||||
$contact["about"] = $actor->portablecontacts_net->note;
|
||||
|
||||
if (isset($actor->portablecontacts_net->addresses->formatted))
|
||||
$contact["location"] = $actor->portablecontacts_net->addresses->formatted;
|
||||
|
||||
|
||||
if (isset($actor->image->url))
|
||||
$contact["photo"] = $actor->image->url;
|
||||
|
||||
if (isset($actor->image->width))
|
||||
$avatarwidth = $actor->image->width;
|
||||
|
||||
if (is_array($actor->status_net->avatarLinks))
|
||||
foreach ($actor->status_net->avatarLinks AS $avatar) {
|
||||
if ($avatarsize < $avatar->width) {
|
||||
$contact["photo"] = $avatar->url;
|
||||
$avatarsize = $avatar->width;
|
||||
}
|
||||
}
|
||||
|
||||
update_gcontact($contact);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Fetches the conversation url for a given item link or conversation id
|
||||
*
|
||||
* @param string $self The link to the posting
|
||||
* @param string $conversation_id The conversation id
|
||||
*
|
||||
* @return string The conversation url
|
||||
*/
|
||||
private function fetch_conversation($self, $conversation_id = "") {
|
||||
|
||||
if ($conversation_id != "") {
|
||||
$elements = explode(":", $conversation_id);
|
||||
|
||||
if ((count($elements) <= 2) OR ($elements[0] != "tag"))
|
||||
return $conversation_id;
|
||||
}
|
||||
|
||||
if ($self == "")
|
||||
return "";
|
||||
|
||||
$json = str_replace(".atom", ".json", $self);
|
||||
|
||||
$raw = fetch_url($json);
|
||||
if ($raw == "")
|
||||
return "";
|
||||
|
||||
$data = json_decode($raw);
|
||||
if (!is_object($data))
|
||||
return "";
|
||||
|
||||
$conversation_id = $data->statusnet_conversation_id;
|
||||
|
||||
$pos = strpos($self, "/api/statuses/show/");
|
||||
$base_url = substr($self, 0, $pos);
|
||||
|
||||
return $base_url."/conversation/".$conversation_id;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Fetches actor details of a given actor and user id
|
||||
*
|
||||
* @param string $actor The actor url
|
||||
* @param int $uid The user id
|
||||
* @param int $contact_id The default contact-id
|
||||
*
|
||||
* @return array Array with actor details
|
||||
*/
|
||||
private function get_actor_details($actor, $uid, $contact_id) {
|
||||
|
||||
$details = array();
|
||||
|
||||
$contact = q("SELECT `id`, `rel`, `network` FROM `contact` WHERE `uid` = %d AND `nurl` = '%s' AND `network` != '%s'",
|
||||
$uid, normalise_link($actor), NETWORK_STATUSNET);
|
||||
|
||||
if (!$contact)
|
||||
$contact = q("SELECT `id`, `rel`, `network` FROM `contact` WHERE `uid` = %d AND `alias` IN ('%s', '%s') AND `network` != '%s'",
|
||||
$uid, $actor, normalise_link($actor), NETWORK_STATUSNET);
|
||||
|
||||
if ($contact) {
|
||||
logger("Found contact for url ".$actor, LOGGER_DEBUG);
|
||||
$details["contact_id"] = $contact[0]["id"];
|
||||
$details["network"] = $contact[0]["network"];
|
||||
|
||||
$details["not_following"] = !in_array($contact[0]["rel"], array(CONTACT_IS_SHARING, CONTACT_IS_FRIEND));
|
||||
} else {
|
||||
logger("No contact found for user ".$uid." and url ".$actor, LOGGER_DEBUG);
|
||||
|
||||
// Adding a global contact
|
||||
/// @TODO Use this data for the post
|
||||
$global_contact_id = get_contact($actor, 0);
|
||||
$details["global_contact_id"] = get_contact($actor, 0);
|
||||
|
||||
logger("Global contact ".$global_contact_id." found for url ".$actor, LOGGER_DEBUG);
|
||||
|
||||
$contact_id = $parent["contact-id"];
|
||||
$details["contact_id"] = $contact_id;
|
||||
$details["network"] = NETWORK_OSTATUS;
|
||||
|
||||
$details["not_following"] = true;
|
||||
}
|
||||
|
||||
$arr = array();
|
||||
$arr["network"] = NETWORK_OSTATUS;
|
||||
$arr["uri"] = $single_conv->id;
|
||||
$arr["plink"] = $plink;
|
||||
$arr["uid"] = $uid;
|
||||
$arr["contact-id"] = $contact_id;
|
||||
$arr["parent-uri"] = $parent_uri;
|
||||
$arr["created"] = $single_conv->published;
|
||||
$arr["edited"] = $single_conv->published;
|
||||
$arr["owner-name"] = $single_conv->actor->displayName;
|
||||
if ($arr["owner-name"] == '')
|
||||
$arr["owner-name"] = $single_conv->actor->contact->displayName;
|
||||
if ($arr["owner-name"] == '')
|
||||
$arr["owner-name"] = $single_conv->actor->portablecontacts_net->displayName;
|
||||
return $details;
|
||||
}
|
||||
|
||||
$arr["owner-link"] = $actor;
|
||||
$arr["owner-avatar"] = $single_conv->actor->image->url;
|
||||
$arr["author-name"] = $arr["owner-name"];
|
||||
$arr["author-link"] = $actor;
|
||||
$arr["author-avatar"] = $single_conv->actor->image->url;
|
||||
$arr["body"] = add_page_info_to_body(html2bbcode($single_conv->content));
|
||||
/**
|
||||
* @brief Stores an item and completes the thread
|
||||
*
|
||||
* @param string $conversation_url The URI of the conversation
|
||||
* @param integer $uid The user id
|
||||
* @param array $item Data of the item that is to be posted
|
||||
*
|
||||
* @return integer The item id of the posted item array
|
||||
*/
|
||||
private function completion($conversation_url, $uid, $item = array(), $self = "") {
|
||||
|
||||
if (isset($single_conv->status_net->notice_info->source))
|
||||
$arr["app"] = strip_tags($single_conv->status_net->notice_info->source);
|
||||
elseif (isset($single_conv->statusnet->notice_info->source))
|
||||
$arr["app"] = strip_tags($single_conv->statusnet->notice_info->source);
|
||||
elseif (isset($single_conv->statusnet_notice_info->source))
|
||||
$arr["app"] = strip_tags($single_conv->statusnet_notice_info->source);
|
||||
elseif (isset($single_conv->provider->displayName))
|
||||
$arr["app"] = $single_conv->provider->displayName;
|
||||
else
|
||||
$arr["app"] = "OStatus";
|
||||
/// @todo This function is totally ugly and has to be rewritten totally
|
||||
|
||||
//$arr["app"] .= " (Conversation)";
|
||||
$item_stored = -1;
|
||||
|
||||
$arr["object"] = json_encode($single_conv);
|
||||
$arr["verb"] = $parent["verb"];
|
||||
$arr["visible"] = $parent["visible"];
|
||||
$arr["location"] = $single_conv->location->displayName;
|
||||
$arr["coord"] = trim($single_conv->location->lat." ".$single_conv->location->lon);
|
||||
$conversation_url = self::fetch_conversation($self, $conversation_url);
|
||||
|
||||
// Is it a reshared item?
|
||||
if (isset($single_conv->verb) AND ($single_conv->verb == "share") AND isset($single_conv->object)) {
|
||||
if (is_array($single_conv->object))
|
||||
$single_conv->object = $single_conv->object[0];
|
||||
// If the thread shouldn't be completed then store the item and go away
|
||||
// Don't do a completion on liked content
|
||||
if (((intval(get_config('system','ostatus_poll_interval')) == -2) AND (count($item) > 0)) OR
|
||||
($item["verb"] == ACTIVITY_LIKE) OR ($conversation_url == "")) {
|
||||
$item_stored = item_store($item, true);
|
||||
return($item_stored);
|
||||
}
|
||||
|
||||
logger("Found reshared item ".$single_conv->object->id);
|
||||
// Get the parent
|
||||
$parents = q("SELECT `id`, `parent`, `uri`, `contact-id`, `type`, `verb`, `visible` FROM `item` WHERE `id` IN
|
||||
(SELECT `parent` FROM `item` WHERE `id` IN
|
||||
(SELECT `oid` FROM `term` WHERE `uid` = %d AND `otype` = %d AND `type` = %d AND `url` = '%s'))",
|
||||
intval($uid), intval(TERM_OBJ_POST), intval(TERM_CONVERSATION), dbesc($conversation_url));
|
||||
|
||||
// $single_conv->object->context->conversation;
|
||||
if ($parents)
|
||||
$parent = $parents[0];
|
||||
elseif (count($item) > 0) {
|
||||
$parent = $item;
|
||||
$parent["type"] = "remote";
|
||||
$parent["verb"] = ACTIVITY_POST;
|
||||
$parent["visible"] = 1;
|
||||
} else {
|
||||
// Preset the parent
|
||||
$r = q("SELECT `id` FROM `contact` WHERE `self` AND `uid`=%d", $uid);
|
||||
if (!$r)
|
||||
return(-2);
|
||||
|
||||
if (isset($single_conv->object->object->id))
|
||||
$arr["uri"] = $single_conv->object->object->id;
|
||||
else
|
||||
$arr["uri"] = $single_conv->object->id;
|
||||
$parent = array();
|
||||
$parent["id"] = 0;
|
||||
$parent["parent"] = 0;
|
||||
$parent["uri"] = "";
|
||||
$parent["contact-id"] = $r[0]["id"];
|
||||
$parent["type"] = "remote";
|
||||
$parent["verb"] = ACTIVITY_POST;
|
||||
$parent["visible"] = 1;
|
||||
}
|
||||
|
||||
if (isset($single_conv->object->object->url))
|
||||
$plink = ostatus_convert_href($single_conv->object->object->url);
|
||||
else
|
||||
$plink = ostatus_convert_href($single_conv->object->url);
|
||||
$conv = str_replace("/conversation/", "/api/statusnet/conversation/", $conversation_url).".as";
|
||||
$pageno = 1;
|
||||
$items = array();
|
||||
|
||||
if (isset($single_conv->object->object->content))
|
||||
$arr["body"] = add_page_info_to_body(html2bbcode($single_conv->object->object->content));
|
||||
else
|
||||
$arr["body"] = add_page_info_to_body(html2bbcode($single_conv->object->content));
|
||||
logger('fetching conversation url '.$conv.' (Self: '.$self.') for user '.$uid);
|
||||
|
||||
do {
|
||||
$conv_arr = z_fetch_url($conv."?page=".$pageno);
|
||||
|
||||
// If it is a non-ssl site and there is an error, then try ssl or vice versa
|
||||
if (!$conv_arr["success"] AND (substr($conv, 0, 7) == "http://")) {
|
||||
$conv = str_replace("http://", "https://", $conv);
|
||||
$conv_as = fetch_url($conv."?page=".$pageno);
|
||||
} elseif (!$conv_arr["success"] AND (substr($conv, 0, 8) == "https://")) {
|
||||
$conv = str_replace("https://", "http://", $conv);
|
||||
$conv_as = fetch_url($conv."?page=".$pageno);
|
||||
} else
|
||||
$conv_as = $conv_arr["body"];
|
||||
|
||||
$conv_as = str_replace(',"statusnet:notice_info":', ',"statusnet_notice_info":', $conv_as);
|
||||
$conv_as = json_decode($conv_as);
|
||||
|
||||
$no_of_items = sizeof($items);
|
||||
|
||||
if (@is_array($conv_as->items))
|
||||
foreach ($conv_as->items AS $single_item)
|
||||
$items[$single_item->id] = $single_item;
|
||||
|
||||
if ($no_of_items == sizeof($items))
|
||||
break;
|
||||
|
||||
$pageno++;
|
||||
|
||||
} while (true);
|
||||
|
||||
logger('fetching conversation done. Found '.count($items).' items');
|
||||
|
||||
if (!sizeof($items)) {
|
||||
if (count($item) > 0) {
|
||||
$item_stored = item_store($item, true);
|
||||
|
||||
if ($item_stored) {
|
||||
logger("Conversation ".$conversation_url." couldn't be fetched. Item uri ".$item["uri"]." stored: ".$item_stored, LOGGER_DEBUG);
|
||||
self::store_conversation($item_id, $conversation_url);
|
||||
}
|
||||
|
||||
return($item_stored);
|
||||
} else
|
||||
return(-3);
|
||||
}
|
||||
|
||||
$items = array_reverse($items);
|
||||
|
||||
$r = q("SELECT `nurl` FROM `contact` WHERE `uid` = %d AND `self`", intval($uid));
|
||||
$importer = $r[0];
|
||||
|
||||
$new_parent = true;
|
||||
|
||||
foreach ($items as $single_conv) {
|
||||
|
||||
// Update the gcontact table
|
||||
self::conv_fetch_actor($single_conv->actor);
|
||||
|
||||
// Test - remove before flight
|
||||
//$tempfile = tempnam(get_temppath(), "conversation");
|
||||
//file_put_contents($tempfile, json_encode($single_conv));
|
||||
|
||||
$mention = false;
|
||||
|
||||
if (isset($single_conv->object->id))
|
||||
$single_conv->id = $single_conv->object->id;
|
||||
|
||||
$plink = self::convert_href($single_conv->id);
|
||||
if (isset($single_conv->object->url))
|
||||
$plink = self::convert_href($single_conv->object->url);
|
||||
|
||||
if (@!$single_conv->id)
|
||||
continue;
|
||||
|
||||
logger("Got id ".$single_conv->id, LOGGER_DEBUG);
|
||||
|
||||
if ($first_id == "") {
|
||||
$first_id = $single_conv->id;
|
||||
|
||||
// The first post of the conversation isn't our first post. There are three options:
|
||||
// 1. Our conversation hasn't the "real" thread starter
|
||||
// 2. This first post is a post inside our thread
|
||||
// 3. This first post is a post inside another thread
|
||||
if (($first_id != $parent["uri"]) AND ($parent["uri"] != "")) {
|
||||
|
||||
$new_parent = true;
|
||||
|
||||
$new_parents = q("SELECT `id`, `parent`, `uri`, `contact-id`, `type`, `verb`, `visible` FROM `item` WHERE `id` IN
|
||||
(SELECT `parent` FROM `item`
|
||||
WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s')) LIMIT 1",
|
||||
intval($uid), dbesc($first_id), dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN));
|
||||
if ($new_parents) {
|
||||
if ($new_parents[0]["parent"] == $parent["parent"]) {
|
||||
// Option 2: This post is already present inside our thread - but not as thread starter
|
||||
logger("Option 2: uri present in our thread: ".$first_id, LOGGER_DEBUG);
|
||||
$first_id = $parent["uri"];
|
||||
} else {
|
||||
// Option 3: Not so good. We have mixed parents. We have to see how to clean this up.
|
||||
// For now just take the new parent.
|
||||
$parent = $new_parents[0];
|
||||
$first_id = $parent["uri"];
|
||||
logger("Option 3: mixed parents for uri ".$first_id, LOGGER_DEBUG);
|
||||
}
|
||||
} else {
|
||||
// Option 1: We hadn't got the real thread starter
|
||||
// We have to clean up our existing messages.
|
||||
$parent["id"] = 0;
|
||||
$parent["uri"] = $first_id;
|
||||
logger("Option 1: we have a new parent: ".$first_id, LOGGER_DEBUG);
|
||||
}
|
||||
} elseif ($parent["uri"] == "") {
|
||||
$parent["id"] = 0;
|
||||
$parent["uri"] = $first_id;
|
||||
}
|
||||
}
|
||||
|
||||
$parent_uri = $parent["uri"];
|
||||
|
||||
// "context" only seems to exist on older servers
|
||||
if (isset($single_conv->context->inReplyTo->id)) {
|
||||
$parent_exists = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s') LIMIT 1",
|
||||
intval($uid), dbesc($single_conv->context->inReplyTo->id), dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN));
|
||||
if ($parent_exists)
|
||||
$parent_uri = $single_conv->context->inReplyTo->id;
|
||||
}
|
||||
|
||||
// This is the current way
|
||||
if (isset($single_conv->object->inReplyTo->id)) {
|
||||
$parent_exists = q("SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s') LIMIT 1",
|
||||
intval($uid), dbesc($single_conv->object->inReplyTo->id), dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN));
|
||||
if ($parent_exists)
|
||||
$parent_uri = $single_conv->object->inReplyTo->id;
|
||||
}
|
||||
|
||||
$message_exists = q("SELECT `id`, `parent`, `uri` FROM `item` WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s') LIMIT 1",
|
||||
intval($uid), dbesc($single_conv->id),
|
||||
dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN));
|
||||
if ($message_exists) {
|
||||
logger("Message ".$single_conv->id." already existed on the system", LOGGER_DEBUG);
|
||||
|
||||
if ($parent["id"] != 0) {
|
||||
$existing_message = $message_exists[0];
|
||||
|
||||
// We improved the way we fetch OStatus messages, this shouldn't happen very often now
|
||||
/// @TODO We have to change the shadow copies as well. This way here is really ugly.
|
||||
if ($existing_message["parent"] != $parent["id"]) {
|
||||
logger('updating id '.$existing_message["id"].' with parent '.$existing_message["parent"].' to parent '.$parent["id"].' uri '.$parent["uri"].' thread '.$parent_uri, LOGGER_DEBUG);
|
||||
|
||||
// Update the parent id of the selected item
|
||||
$r = q("UPDATE `item` SET `parent` = %d, `parent-uri` = '%s' WHERE `id` = %d",
|
||||
intval($parent["id"]), dbesc($parent["uri"]), intval($existing_message["id"]));
|
||||
|
||||
// Update the parent uri in the thread - but only if it points to itself
|
||||
$r = q("UPDATE `item` SET `thr-parent` = '%s' WHERE `id` = %d AND `uri` = `thr-parent`",
|
||||
dbesc($parent_uri), intval($existing_message["id"]));
|
||||
|
||||
// try to change all items of the same parent
|
||||
$r = q("UPDATE `item` SET `parent` = %d, `parent-uri` = '%s' WHERE `parent` = %d",
|
||||
intval($parent["id"]), dbesc($parent["uri"]), intval($existing_message["parent"]));
|
||||
|
||||
// Update the parent uri in the thread - but only if it points to itself
|
||||
$r = q("UPDATE `item` SET `thr-parent` = '%s' WHERE (`parent` = %d) AND (`uri` = `thr-parent`)",
|
||||
dbesc($parent["uri"]), intval($existing_message["parent"]));
|
||||
|
||||
// Now delete the thread
|
||||
delete_thread($existing_message["parent"]);
|
||||
}
|
||||
}
|
||||
|
||||
// The item we are having on the system is the one that we wanted to store via the item array
|
||||
if (isset($item["uri"]) AND ($item["uri"] == $existing_message["uri"])) {
|
||||
$item = array();
|
||||
$item_stored = 0;
|
||||
}
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
if (is_array($single_conv->to))
|
||||
foreach($single_conv->to AS $to)
|
||||
if ($importer["nurl"] == normalise_link($to->id))
|
||||
$mention = true;
|
||||
|
||||
$actor = $single_conv->actor->id;
|
||||
if (isset($single_conv->actor->url))
|
||||
$actor = $single_conv->actor->url;
|
||||
|
||||
$details = self::get_actor_details($actor, $uid, $parent["contact-id"]);
|
||||
|
||||
// Do we only want to import threads that were started by our contacts?
|
||||
if ($details["not_following"] AND $new_parent AND get_config('system','ostatus_full_threads')) {
|
||||
logger("Don't import uri ".$first_id." because user ".$uid." doesn't follow the person ".$actor, LOGGER_DEBUG);
|
||||
continue;
|
||||
}
|
||||
|
||||
$arr = array();
|
||||
$arr["network"] = $details["network"];
|
||||
$arr["uri"] = $single_conv->id;
|
||||
$arr["plink"] = $plink;
|
||||
|
||||
$arr["created"] = $single_conv->object->published;
|
||||
$arr["edited"] = $single_conv->object->published;
|
||||
|
||||
$arr["author-name"] = $single_conv->object->actor->displayName;
|
||||
$arr["uid"] = $uid;
|
||||
$arr["contact-id"] = $details["contact_id"];
|
||||
$arr["parent-uri"] = $parent_uri;
|
||||
$arr["created"] = $single_conv->published;
|
||||
$arr["edited"] = $single_conv->published;
|
||||
$arr["owner-name"] = $single_conv->actor->displayName;
|
||||
if ($arr["owner-name"] == '')
|
||||
$arr["author-name"] = $single_conv->object->actor->contact->displayName;
|
||||
$arr["owner-name"] = $single_conv->actor->contact->displayName;
|
||||
if ($arr["owner-name"] == '')
|
||||
$arr["owner-name"] = $single_conv->actor->portablecontacts_net->displayName;
|
||||
|
||||
$arr["author-link"] = $single_conv->object->actor->url;
|
||||
$arr["author-avatar"] = $single_conv->object->actor->image->url;
|
||||
$arr["owner-link"] = $actor;
|
||||
$arr["owner-avatar"] = $single_conv->actor->image->url;
|
||||
$arr["author-name"] = $arr["owner-name"];
|
||||
$arr["author-link"] = $actor;
|
||||
$arr["author-avatar"] = $single_conv->actor->image->url;
|
||||
$arr["body"] = add_page_info_to_body(html2bbcode($single_conv->content));
|
||||
|
||||
$arr["app"] = $single_conv->object->provider->displayName."#";
|
||||
//$arr["verb"] = $single_conv->object->verb;
|
||||
if (isset($single_conv->status_net->notice_info->source))
|
||||
$arr["app"] = strip_tags($single_conv->status_net->notice_info->source);
|
||||
elseif (isset($single_conv->statusnet->notice_info->source))
|
||||
$arr["app"] = strip_tags($single_conv->statusnet->notice_info->source);
|
||||
elseif (isset($single_conv->statusnet_notice_info->source))
|
||||
$arr["app"] = strip_tags($single_conv->statusnet_notice_info->source);
|
||||
elseif (isset($single_conv->provider->displayName))
|
||||
$arr["app"] = $single_conv->provider->displayName;
|
||||
else
|
||||
$arr["app"] = "OStatus";
|
||||
|
||||
$arr["location"] = $single_conv->object->location->displayName;
|
||||
$arr["coord"] = trim($single_conv->object->location->lat." ".$single_conv->object->location->lon);
|
||||
|
||||
$arr["object"] = json_encode($single_conv);
|
||||
$arr["verb"] = $parent["verb"];
|
||||
$arr["visible"] = $parent["visible"];
|
||||
$arr["location"] = $single_conv->location->displayName;
|
||||
$arr["coord"] = trim($single_conv->location->lat." ".$single_conv->location->lon);
|
||||
|
||||
// Is it a reshared item?
|
||||
if (isset($single_conv->verb) AND ($single_conv->verb == "share") AND isset($single_conv->object)) {
|
||||
if (is_array($single_conv->object))
|
||||
$single_conv->object = $single_conv->object[0];
|
||||
|
||||
logger("Found reshared item ".$single_conv->object->id);
|
||||
|
||||
// $single_conv->object->context->conversation;
|
||||
|
||||
if (isset($single_conv->object->object->id))
|
||||
$arr["uri"] = $single_conv->object->object->id;
|
||||
else
|
||||
$arr["uri"] = $single_conv->object->id;
|
||||
|
||||
if (isset($single_conv->object->object->url))
|
||||
$plink = self::convert_href($single_conv->object->object->url);
|
||||
else
|
||||
$plink = self::convert_href($single_conv->object->url);
|
||||
|
||||
if (isset($single_conv->object->object->content))
|
||||
$arr["body"] = add_page_info_to_body(html2bbcode($single_conv->object->object->content));
|
||||
else
|
||||
$arr["body"] = add_page_info_to_body(html2bbcode($single_conv->object->content));
|
||||
|
||||
$arr["plink"] = $plink;
|
||||
|
||||
$arr["created"] = $single_conv->object->published;
|
||||
$arr["edited"] = $single_conv->object->published;
|
||||
|
||||
$arr["author-name"] = $single_conv->object->actor->displayName;
|
||||
if ($arr["owner-name"] == '')
|
||||
$arr["author-name"] = $single_conv->object->actor->contact->displayName;
|
||||
|
||||
$arr["author-link"] = $single_conv->object->actor->url;
|
||||
$arr["author-avatar"] = $single_conv->object->actor->image->url;
|
||||
|
||||
$arr["app"] = $single_conv->object->provider->displayName."#";
|
||||
//$arr["verb"] = $single_conv->object->verb;
|
||||
|
||||
$arr["location"] = $single_conv->object->location->displayName;
|
||||
$arr["coord"] = trim($single_conv->object->location->lat." ".$single_conv->object->location->lon);
|
||||
}
|
||||
|
||||
if ($arr["location"] == "")
|
||||
unset($arr["location"]);
|
||||
|
||||
if ($arr["coord"] == "")
|
||||
unset($arr["coord"]);
|
||||
|
||||
// Copy fields from given item array
|
||||
if (isset($item["uri"]) AND (($item["uri"] == $arr["uri"]) OR ($item["uri"] == $single_conv->id))) {
|
||||
$copy_fields = array("owner-name", "owner-link", "owner-avatar", "author-name", "author-link", "author-avatar",
|
||||
"gravity", "body", "object-type", "object", "verb", "created", "edited", "coord", "tag",
|
||||
"title", "attach", "app", "type", "location", "contact-id", "uri");
|
||||
foreach ($copy_fields AS $field)
|
||||
if (isset($item[$field]))
|
||||
$arr[$field] = $item[$field];
|
||||
|
||||
}
|
||||
|
||||
$newitem = item_store($arr);
|
||||
if (!$newitem) {
|
||||
logger("Item wasn't stored ".print_r($arr, true), LOGGER_DEBUG);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (isset($item["uri"]) AND ($item["uri"] == $arr["uri"])) {
|
||||
$item = array();
|
||||
$item_stored = $newitem;
|
||||
}
|
||||
|
||||
logger('Stored new item '.$plink.' for parent '.$arr["parent-uri"].' under id '.$newitem, LOGGER_DEBUG);
|
||||
|
||||
// Add the conversation entry (but don't fetch the whole conversation)
|
||||
self::store_conversation($newitem, $conversation_url);
|
||||
|
||||
// If the newly created item is the top item then change the parent settings of the thread
|
||||
// This shouldn't happen anymore. This is supposed to be absolote.
|
||||
if ($arr["uri"] == $first_id) {
|
||||
logger('setting new parent to id '.$newitem);
|
||||
$new_parents = q("SELECT `id`, `uri`, `contact-id`, `type`, `verb`, `visible` FROM `item` WHERE `uid` = %d AND `id` = %d LIMIT 1",
|
||||
intval($uid), intval($newitem));
|
||||
if ($new_parents)
|
||||
$parent = $new_parents[0];
|
||||
}
|
||||
}
|
||||
|
||||
if ($arr["location"] == "")
|
||||
unset($arr["location"]);
|
||||
if (($item_stored < 0) AND (count($item) > 0)) {
|
||||
|
||||
if ($arr["coord"] == "")
|
||||
unset($arr["coord"]);
|
||||
if (get_config('system','ostatus_full_threads')) {
|
||||
$details = self::get_actor_details($item["owner-link"], $uid, $item["contact-id"]);
|
||||
if ($details["not_following"]) {
|
||||
logger("Don't import uri ".$item["uri"]." because user ".$uid." doesn't follow the person ".$item["owner-link"], LOGGER_DEBUG);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// Copy fields from given item array
|
||||
if (isset($item["uri"]) AND (($item["uri"] == $arr["uri"]) OR ($item["uri"] == $single_conv->id))) {
|
||||
$copy_fields = array("owner-name", "owner-link", "owner-avatar", "author-name", "author-link", "author-avatar",
|
||||
"gravity", "body", "object-type", "object", "verb", "created", "edited", "coord", "tag",
|
||||
"title", "attach", "app", "type", "location", "contact-id", "uri");
|
||||
foreach ($copy_fields AS $field)
|
||||
if (isset($item[$field]))
|
||||
$arr[$field] = $item[$field];
|
||||
|
||||
//$arr["app"] .= " (OStatus)";
|
||||
$item_stored = item_store($item, true);
|
||||
if ($item_stored) {
|
||||
logger("Uri ".$item["uri"]." wasn't found in conversation ".$conversation_url, LOGGER_DEBUG);
|
||||
self::store_conversation($item_stored, $conversation_url);
|
||||
}
|
||||
}
|
||||
|
||||
$newitem = item_store($arr);
|
||||
if (!$newitem) {
|
||||
logger("Item wasn't stored ".print_r($arr, true), LOGGER_DEBUG);
|
||||
continue;
|
||||
}
|
||||
return($item_stored);
|
||||
}
|
||||
|
||||
if (isset($item["uri"]) AND ($item["uri"] == $arr["uri"])) {
|
||||
$item = array();
|
||||
$item_stored = $newitem;
|
||||
}
|
||||
/**
|
||||
* @brief Stores conversation data into the database
|
||||
*
|
||||
* @param integer $itemid The id of the item
|
||||
* @param string $conversation_url The uri of the conversation
|
||||
*/
|
||||
private function store_conversation($itemid, $conversation_url) {
|
||||
|
||||
logger('Stored new item '.$plink.' for parent '.$arr["parent-uri"].' under id '.$newitem, LOGGER_DEBUG);
|
||||
$conversation_url = self::convert_href($conversation_url);
|
||||
|
||||
// Add the conversation entry (but don't fetch the whole conversation)
|
||||
ostatus_store_conversation($newitem, $conversation_url);
|
||||
$messages = q("SELECT `uid`, `parent`, `created`, `received`, `guid` FROM `item` WHERE `id` = %d LIMIT 1", intval($itemid));
|
||||
if (!$messages)
|
||||
return;
|
||||
$message = $messages[0];
|
||||
|
||||
// If the newly created item is the top item then change the parent settings of the thread
|
||||
// This shouldn't happen anymore. This is supposed to be absolote.
|
||||
if ($arr["uri"] == $first_id) {
|
||||
logger('setting new parent to id '.$newitem);
|
||||
$new_parents = q("SELECT `id`, `uri`, `contact-id`, `type`, `verb`, `visible` FROM `item` WHERE `uid` = %d AND `id` = %d LIMIT 1",
|
||||
intval($uid), intval($newitem));
|
||||
if ($new_parents)
|
||||
$parent = $new_parents[0];
|
||||
// Store conversation url if not done before
|
||||
$conversation = q("SELECT `url` FROM `term` WHERE `uid` = %d AND `oid` = %d AND `otype` = %d AND `type` = %d",
|
||||
intval($message["uid"]), intval($itemid), intval(TERM_OBJ_POST), intval(TERM_CONVERSATION));
|
||||
|
||||
if (!$conversation) {
|
||||
$r = q("INSERT INTO `term` (`uid`, `oid`, `otype`, `type`, `term`, `url`, `created`, `received`, `guid`) VALUES (%d, %d, %d, %d, '%s', '%s', '%s', '%s', '%s')",
|
||||
intval($message["uid"]), intval($itemid), intval(TERM_OBJ_POST), intval(TERM_CONVERSATION),
|
||||
dbesc($message["created"]), dbesc($conversation_url), dbesc($message["created"]), dbesc($message["received"]), dbesc($message["guid"]));
|
||||
logger('Storing conversation url '.$conversation_url.' for id '.$itemid);
|
||||
}
|
||||
}
|
||||
|
||||
if (($item_stored < 0) AND (count($item) > 0)) {
|
||||
//$arr["app"] .= " (OStatus-NoConvFound)";
|
||||
$item_stored = item_store($item, true);
|
||||
if ($item_stored) {
|
||||
logger("Uri ".$item["uri"]." wasn't found in conversation ".$conversation_url, LOGGER_DEBUG);
|
||||
ostatus_store_conversation($item_stored, $conversation_url);
|
||||
/**
|
||||
* @brief Checks if the current post is a reshare
|
||||
*
|
||||
* @param array $item The item array of thw post
|
||||
*
|
||||
* @return string The guid if the post is a reshare
|
||||
*/
|
||||
private function get_reshared_guid($item) {
|
||||
$body = trim($item["body"]);
|
||||
|
||||
// Skip if it isn't a pure repeated messages
|
||||
// Does it start with a share?
|
||||
if (strpos($body, "[share") > 0)
|
||||
return("");
|
||||
|
||||
// Does it end with a share?
|
||||
if (strlen($body) > (strrpos($body, "[/share]") + 8))
|
||||
return("");
|
||||
|
||||
$attributes = preg_replace("/\[share(.*?)\]\s?(.*?)\s?\[\/share\]\s?/ism","$1",$body);
|
||||
// Skip if there is no shared message in there
|
||||
if ($body == $attributes)
|
||||
return(false);
|
||||
|
||||
$guid = "";
|
||||
preg_match("/guid='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$guid = $matches[1];
|
||||
|
||||
preg_match('/guid="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$guid = $matches[1];
|
||||
|
||||
return $guid;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Cleans the body of a post if it contains picture links
|
||||
*
|
||||
* @param string $body The body
|
||||
*
|
||||
* @return string The cleaned body
|
||||
*/
|
||||
private function format_picture_post($body) {
|
||||
$siteinfo = get_attached_data($body);
|
||||
|
||||
if (($siteinfo["type"] == "photo")) {
|
||||
if (isset($siteinfo["preview"]))
|
||||
$preview = $siteinfo["preview"];
|
||||
else
|
||||
$preview = $siteinfo["image"];
|
||||
|
||||
// Is it a remote picture? Then make a smaller preview here
|
||||
$preview = proxy_url($preview, false, PROXY_SIZE_SMALL);
|
||||
|
||||
// Is it a local picture? Then make it smaller here
|
||||
$preview = str_replace(array("-0.jpg", "-0.png"), array("-2.jpg", "-2.png"), $preview);
|
||||
$preview = str_replace(array("-1.jpg", "-1.png"), array("-2.jpg", "-2.png"), $preview);
|
||||
|
||||
if (isset($siteinfo["url"]))
|
||||
$url = $siteinfo["url"];
|
||||
else
|
||||
$url = $siteinfo["image"];
|
||||
|
||||
$body = trim($siteinfo["text"])." [url]".$url."[/url]\n[img]".$preview."[/img]";
|
||||
}
|
||||
|
||||
return $body;
|
||||
}
|
||||
|
||||
return($item_stored);
|
||||
}
|
||||
/**
|
||||
* @brief Adds the header elements to the XML document
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param array $owner Contact data of the poster
|
||||
*
|
||||
* @return object header root element
|
||||
*/
|
||||
private function add_header($doc, $owner) {
|
||||
|
||||
function ostatus_store_conversation($itemid, $conversation_url) {
|
||||
global $a;
|
||||
$a = get_app();
|
||||
|
||||
$conversation_url = ostatus_convert_href($conversation_url);
|
||||
$root = $doc->createElementNS(NAMESPACE_ATOM1, 'feed');
|
||||
$doc->appendChild($root);
|
||||
|
||||
$messages = q("SELECT `uid`, `parent`, `created`, `received`, `guid` FROM `item` WHERE `id` = %d LIMIT 1", intval($itemid));
|
||||
if (!$messages)
|
||||
return;
|
||||
$message = $messages[0];
|
||||
$root->setAttribute("xmlns:thr", NAMESPACE_THREAD);
|
||||
$root->setAttribute("xmlns:georss", NAMESPACE_GEORSS);
|
||||
$root->setAttribute("xmlns:activity", NAMESPACE_ACTIVITY);
|
||||
$root->setAttribute("xmlns:media", NAMESPACE_MEDIA);
|
||||
$root->setAttribute("xmlns:poco", NAMESPACE_POCO);
|
||||
$root->setAttribute("xmlns:ostatus", NAMESPACE_OSTATUS);
|
||||
$root->setAttribute("xmlns:statusnet", NAMESPACE_STATUSNET);
|
||||
|
||||
// Store conversation url if not done before
|
||||
$conversation = q("SELECT `url` FROM `term` WHERE `uid` = %d AND `oid` = %d AND `otype` = %d AND `type` = %d",
|
||||
intval($message["uid"]), intval($itemid), intval(TERM_OBJ_POST), intval(TERM_CONVERSATION));
|
||||
$attributes = array("uri" => "https://friendi.ca", "version" => FRIENDICA_VERSION."-".DB_UPDATE_VERSION);
|
||||
xml::add_element($doc, $root, "generator", FRIENDICA_PLATFORM, $attributes);
|
||||
xml::add_element($doc, $root, "id", App::get_baseurl()."/profile/".$owner["nick"]);
|
||||
xml::add_element($doc, $root, "title", sprintf("%s timeline", $owner["name"]));
|
||||
xml::add_element($doc, $root, "subtitle", sprintf("Updates from %s on %s", $owner["name"], $a->config["sitename"]));
|
||||
xml::add_element($doc, $root, "logo", $owner["photo"]);
|
||||
xml::add_element($doc, $root, "updated", datetime_convert("UTC", "UTC", "now", ATOM_TIME));
|
||||
|
||||
if (!$conversation) {
|
||||
$r = q("INSERT INTO `term` (`uid`, `oid`, `otype`, `type`, `term`, `url`, `created`, `received`, `guid`) VALUES (%d, %d, %d, %d, '%s', '%s', '%s', '%s', '%s')",
|
||||
intval($message["uid"]), intval($itemid), intval(TERM_OBJ_POST), intval(TERM_CONVERSATION),
|
||||
dbesc($message["created"]), dbesc($conversation_url), dbesc($message["created"]), dbesc($message["received"]), dbesc($message["guid"]));
|
||||
logger('Storing conversation url '.$conversation_url.' for id '.$itemid);
|
||||
}
|
||||
}
|
||||
$author = self::add_author($doc, $owner);
|
||||
$root->appendChild($author);
|
||||
|
||||
function get_reshared_guid($item) {
|
||||
$body = trim($item["body"]);
|
||||
$attributes = array("href" => $owner["url"], "rel" => "alternate", "type" => "text/html");
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
// Skip if it isn't a pure repeated messages
|
||||
// Does it start with a share?
|
||||
if (strpos($body, "[share") > 0)
|
||||
return("");
|
||||
/// @TODO We have to find out what this is
|
||||
/// $attributes = array("href" => App::get_baseurl()."/sup",
|
||||
/// "rel" => "http://api.friendfeed.com/2008/03#sup",
|
||||
/// "type" => "application/json");
|
||||
/// xml::add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
// Does it end with a share?
|
||||
if (strlen($body) > (strrpos($body, "[/share]") + 8))
|
||||
return("");
|
||||
self::hublinks($doc, $root);
|
||||
|
||||
$attributes = preg_replace("/\[share(.*?)\]\s?(.*?)\s?\[\/share\]\s?/ism","$1",$body);
|
||||
// Skip if there is no shared message in there
|
||||
if ($body == $attributes)
|
||||
return(false);
|
||||
$attributes = array("href" => App::get_baseurl()."/salmon/".$owner["nick"], "rel" => "salmon");
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
$guid = "";
|
||||
preg_match("/guid='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$guid = $matches[1];
|
||||
$attributes = array("href" => App::get_baseurl()."/salmon/".$owner["nick"], "rel" => "http://salmon-protocol.org/ns/salmon-replies");
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
preg_match('/guid="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$guid = $matches[1];
|
||||
$attributes = array("href" => App::get_baseurl()."/salmon/".$owner["nick"], "rel" => "http://salmon-protocol.org/ns/salmon-mention");
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
return $guid;
|
||||
}
|
||||
$attributes = array("href" => App::get_baseurl()."/api/statuses/user_timeline/".$owner["nick"].".atom",
|
||||
"rel" => "self", "type" => "application/atom+xml");
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
function xml_create_element($doc, $element, $value = "", $attributes = array()) {
|
||||
$element = $doc->createElement($element, xmlify($value));
|
||||
|
||||
foreach ($attributes AS $key => $value) {
|
||||
$attribute = $doc->createAttribute($key);
|
||||
$attribute->value = xmlify($value);
|
||||
$element->appendChild($attribute);
|
||||
}
|
||||
return $element;
|
||||
}
|
||||
|
||||
function xml_add_element($doc, $parent, $element, $value = "", $attributes = array()) {
|
||||
$element = xml_create_element($doc, $element, $value, $attributes);
|
||||
$parent->appendChild($element);
|
||||
}
|
||||
|
||||
function ostatus_format_picture_post($body) {
|
||||
$siteinfo = get_attached_data($body);
|
||||
|
||||
if (($siteinfo["type"] == "photo")) {
|
||||
if (isset($siteinfo["preview"]))
|
||||
$preview = $siteinfo["preview"];
|
||||
else
|
||||
$preview = $siteinfo["image"];
|
||||
|
||||
// Is it a remote picture? Then make a smaller preview here
|
||||
$preview = proxy_url($preview, false, PROXY_SIZE_SMALL);
|
||||
|
||||
// Is it a local picture? Then make it smaller here
|
||||
$preview = str_replace(array("-0.jpg", "-0.png"), array("-2.jpg", "-2.png"), $preview);
|
||||
$preview = str_replace(array("-1.jpg", "-1.png"), array("-2.jpg", "-2.png"), $preview);
|
||||
|
||||
if (isset($siteinfo["url"]))
|
||||
$url = $siteinfo["url"];
|
||||
else
|
||||
$url = $siteinfo["image"];
|
||||
|
||||
$body = trim($siteinfo["text"])." [url]".$url."[/url]\n[img]".$preview."[/img]";
|
||||
return $root;
|
||||
}
|
||||
|
||||
return $body;
|
||||
}
|
||||
/**
|
||||
* @brief Add the link to the push hubs to the XML document
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param object $root XML root element where the hub links are added
|
||||
*/
|
||||
public static function hublinks($doc, $root) {
|
||||
$hub = get_config('system','huburl');
|
||||
|
||||
function ostatus_add_header($doc, $owner) {
|
||||
$a = get_app();
|
||||
|
||||
$root = $doc->createElementNS(NAMESPACE_ATOM1, 'feed');
|
||||
$doc->appendChild($root);
|
||||
|
||||
$root->setAttribute("xmlns:thr", NAMESPACE_THREAD);
|
||||
$root->setAttribute("xmlns:georss", NAMESPACE_GEORSS);
|
||||
$root->setAttribute("xmlns:activity", NAMESPACE_ACTIVITY);
|
||||
$root->setAttribute("xmlns:media", NAMESPACE_MEDIA);
|
||||
$root->setAttribute("xmlns:poco", NAMESPACE_POCO);
|
||||
$root->setAttribute("xmlns:ostatus", NAMESPACE_OSTATUS);
|
||||
$root->setAttribute("xmlns:statusnet", NAMESPACE_STATUSNET);
|
||||
|
||||
$attributes = array("uri" => "https://friendi.ca", "version" => FRIENDICA_VERSION."-".DB_UPDATE_VERSION);
|
||||
xml_add_element($doc, $root, "generator", FRIENDICA_PLATFORM, $attributes);
|
||||
xml_add_element($doc, $root, "id", $a->get_baseurl()."/profile/".$owner["nick"]);
|
||||
xml_add_element($doc, $root, "title", sprintf("%s timeline", $owner["name"]));
|
||||
xml_add_element($doc, $root, "subtitle", sprintf("Updates from %s on %s", $owner["name"], $a->config["sitename"]));
|
||||
xml_add_element($doc, $root, "logo", $owner["photo"]);
|
||||
xml_add_element($doc, $root, "updated", datetime_convert("UTC", "UTC", "now", ATOM_TIME));
|
||||
|
||||
$author = ostatus_add_author($doc, $owner);
|
||||
$root->appendChild($author);
|
||||
|
||||
$attributes = array("href" => $owner["url"], "rel" => "alternate", "type" => "text/html");
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
/// @TODO We have to find out what this is
|
||||
/// $attributes = array("href" => $a->get_baseurl()."/sup",
|
||||
/// "rel" => "http://api.friendfeed.com/2008/03#sup",
|
||||
/// "type" => "application/json");
|
||||
/// xml_add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
ostatus_hublinks($doc, $root);
|
||||
|
||||
$attributes = array("href" => $a->get_baseurl()."/salmon/".$owner["nick"], "rel" => "salmon");
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
$attributes = array("href" => $a->get_baseurl()."/salmon/".$owner["nick"], "rel" => "http://salmon-protocol.org/ns/salmon-replies");
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
$attributes = array("href" => $a->get_baseurl()."/salmon/".$owner["nick"], "rel" => "http://salmon-protocol.org/ns/salmon-mention");
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
$attributes = array("href" => $a->get_baseurl()."/api/statuses/user_timeline/".$owner["nick"].".atom",
|
||||
"rel" => "self", "type" => "application/atom+xml");
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
return $root;
|
||||
}
|
||||
|
||||
function ostatus_hublinks($doc, $root) {
|
||||
$a = get_app();
|
||||
$hub = get_config('system','huburl');
|
||||
|
||||
$hubxml = '';
|
||||
if(strlen($hub)) {
|
||||
$hubs = explode(',', $hub);
|
||||
if(count($hubs)) {
|
||||
foreach($hubs as $h) {
|
||||
$h = trim($h);
|
||||
if(! strlen($h))
|
||||
continue;
|
||||
if ($h === '[internal]')
|
||||
$h = $a->get_baseurl() . '/pubsubhubbub';
|
||||
xml_add_element($doc, $root, "link", "", array("href" => $h, "rel" => "hub"));
|
||||
$hubxml = '';
|
||||
if(strlen($hub)) {
|
||||
$hubs = explode(',', $hub);
|
||||
if(count($hubs)) {
|
||||
foreach($hubs as $h) {
|
||||
$h = trim($h);
|
||||
if(! strlen($h))
|
||||
continue;
|
||||
if ($h === '[internal]')
|
||||
$h = App::get_baseurl() . '/pubsubhubbub';
|
||||
xml::add_element($doc, $root, "link", "", array("href" => $h, "rel" => "hub"));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function ostatus_get_attachment($doc, $root, $item) {
|
||||
$o = "";
|
||||
$siteinfo = get_attached_data($item["body"]);
|
||||
/**
|
||||
* @brief Adds attachement data to the XML document
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param object $root XML root element where the hub links are added
|
||||
* @param array $item Data of the item that is to be posted
|
||||
*/
|
||||
private function get_attachment($doc, $root, $item) {
|
||||
$o = "";
|
||||
$siteinfo = get_attached_data($item["body"]);
|
||||
|
||||
switch($siteinfo["type"]) {
|
||||
case 'link':
|
||||
$attributes = array("rel" => "enclosure",
|
||||
"href" => $siteinfo["url"],
|
||||
"type" => "text/html; charset=UTF-8",
|
||||
"length" => "",
|
||||
"title" => $siteinfo["title"]);
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
break;
|
||||
case 'photo':
|
||||
$imgdata = get_photo_info($siteinfo["image"]);
|
||||
$attributes = array("rel" => "enclosure",
|
||||
"href" => $siteinfo["image"],
|
||||
"type" => $imgdata["mime"],
|
||||
"length" => intval($imgdata["size"]));
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
break;
|
||||
case 'video':
|
||||
$attributes = array("rel" => "enclosure",
|
||||
"href" => $siteinfo["url"],
|
||||
"type" => "text/html; charset=UTF-8",
|
||||
"length" => "",
|
||||
"title" => $siteinfo["title"]);
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if (($siteinfo["type"] != "photo") AND isset($siteinfo["image"])) {
|
||||
$photodata = get_photo_info($siteinfo["image"]);
|
||||
|
||||
$attributes = array("rel" => "preview", "href" => $siteinfo["image"], "media:width" => $photodata[0], "media:height" => $photodata[1]);
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
}
|
||||
|
||||
|
||||
$arr = explode('[/attach],',$item['attach']);
|
||||
if(count($arr)) {
|
||||
foreach($arr as $r) {
|
||||
$matches = false;
|
||||
$cnt = preg_match('|\[attach\]href=\"(.*?)\" length=\"(.*?)\" type=\"(.*?)\" title=\"(.*?)\"|',$r,$matches);
|
||||
if($cnt) {
|
||||
switch($siteinfo["type"]) {
|
||||
case 'link':
|
||||
$attributes = array("rel" => "enclosure",
|
||||
"href" => $matches[1],
|
||||
"type" => $matches[3]);
|
||||
"href" => $siteinfo["url"],
|
||||
"type" => "text/html; charset=UTF-8",
|
||||
"length" => "",
|
||||
"title" => $siteinfo["title"]);
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
break;
|
||||
case 'photo':
|
||||
$imgdata = get_photo_info($siteinfo["image"]);
|
||||
$attributes = array("rel" => "enclosure",
|
||||
"href" => $siteinfo["image"],
|
||||
"type" => $imgdata["mime"],
|
||||
"length" => intval($imgdata["size"]));
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
break;
|
||||
case 'video':
|
||||
$attributes = array("rel" => "enclosure",
|
||||
"href" => $siteinfo["url"],
|
||||
"type" => "text/html; charset=UTF-8",
|
||||
"length" => "",
|
||||
"title" => $siteinfo["title"]);
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if(intval($matches[2]))
|
||||
$attributes["length"] = intval($matches[2]);
|
||||
if (($siteinfo["type"] != "photo") AND isset($siteinfo["image"])) {
|
||||
$photodata = get_photo_info($siteinfo["image"]);
|
||||
|
||||
if(trim($matches[4]) != "")
|
||||
$attributes["title"] = trim($matches[4]);
|
||||
$attributes = array("rel" => "preview", "href" => $siteinfo["image"], "media:width" => $photodata[0], "media:height" => $photodata[1]);
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
}
|
||||
|
||||
xml_add_element($doc, $root, "link", "", $attributes);
|
||||
|
||||
$arr = explode('[/attach],',$item['attach']);
|
||||
if(count($arr)) {
|
||||
foreach($arr as $r) {
|
||||
$matches = false;
|
||||
$cnt = preg_match('|\[attach\]href=\"(.*?)\" length=\"(.*?)\" type=\"(.*?)\" title=\"(.*?)\"|',$r,$matches);
|
||||
if($cnt) {
|
||||
$attributes = array("rel" => "enclosure",
|
||||
"href" => $matches[1],
|
||||
"type" => $matches[3]);
|
||||
|
||||
if(intval($matches[2]))
|
||||
$attributes["length"] = intval($matches[2]);
|
||||
|
||||
if(trim($matches[4]) != "")
|
||||
$attributes["title"] = trim($matches[4]);
|
||||
|
||||
xml::add_element($doc, $root, "link", "", $attributes);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function ostatus_add_author($doc, $owner) {
|
||||
$a = get_app();
|
||||
/**
|
||||
* @brief Adds the author element to the XML document
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param array $owner Contact data of the poster
|
||||
*
|
||||
* @return object author element
|
||||
*/
|
||||
private function add_author($doc, $owner) {
|
||||
|
||||
$r = q("SELECT `homepage` FROM `profile` WHERE `uid` = %d AND `is-default` LIMIT 1", intval($owner["uid"]));
|
||||
if ($r)
|
||||
$profile = $r[0];
|
||||
$r = q("SELECT `homepage` FROM `profile` WHERE `uid` = %d AND `is-default` LIMIT 1", intval($owner["uid"]));
|
||||
if ($r)
|
||||
$profile = $r[0];
|
||||
|
||||
$author = $doc->createElement("author");
|
||||
xml_add_element($doc, $author, "activity:object-type", ACTIVITY_OBJ_PERSON);
|
||||
xml_add_element($doc, $author, "uri", $owner["url"]);
|
||||
xml_add_element($doc, $author, "name", $owner["name"]);
|
||||
$author = $doc->createElement("author");
|
||||
xml::add_element($doc, $author, "activity:object-type", ACTIVITY_OBJ_PERSON);
|
||||
xml::add_element($doc, $author, "uri", $owner["url"]);
|
||||
xml::add_element($doc, $author, "name", $owner["name"]);
|
||||
xml::add_element($doc, $author, "summary", bbcode($owner["about"], false, false, 7));
|
||||
|
||||
$attributes = array("rel" => "alternate", "type" => "text/html", "href" => $owner["url"]);
|
||||
xml_add_element($doc, $author, "link", "", $attributes);
|
||||
$attributes = array("rel" => "alternate", "type" => "text/html", "href" => $owner["url"]);
|
||||
xml::add_element($doc, $author, "link", "", $attributes);
|
||||
|
||||
$attributes = array(
|
||||
"rel" => "avatar",
|
||||
"type" => "image/jpeg", // To-Do?
|
||||
"media:width" => 175,
|
||||
"media:height" => 175,
|
||||
"href" => $owner["photo"]);
|
||||
xml_add_element($doc, $author, "link", "", $attributes);
|
||||
|
||||
if (isset($owner["thumb"])) {
|
||||
$attributes = array(
|
||||
"rel" => "avatar",
|
||||
"type" => "image/jpeg", // To-Do?
|
||||
"media:width" => 80,
|
||||
"media:height" => 80,
|
||||
"href" => $owner["thumb"]);
|
||||
xml_add_element($doc, $author, "link", "", $attributes);
|
||||
"media:width" => 175,
|
||||
"media:height" => 175,
|
||||
"href" => $owner["photo"]);
|
||||
xml::add_element($doc, $author, "link", "", $attributes);
|
||||
|
||||
if (isset($owner["thumb"])) {
|
||||
$attributes = array(
|
||||
"rel" => "avatar",
|
||||
"type" => "image/jpeg", // To-Do?
|
||||
"media:width" => 80,
|
||||
"media:height" => 80,
|
||||
"href" => $owner["thumb"]);
|
||||
xml::add_element($doc, $author, "link", "", $attributes);
|
||||
}
|
||||
|
||||
xml::add_element($doc, $author, "poco:preferredUsername", $owner["nick"]);
|
||||
xml::add_element($doc, $author, "poco:displayName", $owner["name"]);
|
||||
xml::add_element($doc, $author, "poco:note", bbcode($owner["about"], false, false, 7));
|
||||
|
||||
if (trim($owner["location"]) != "") {
|
||||
$element = $doc->createElement("poco:address");
|
||||
xml::add_element($doc, $element, "poco:formatted", $owner["location"]);
|
||||
$author->appendChild($element);
|
||||
}
|
||||
|
||||
if (trim($profile["homepage"]) != "") {
|
||||
$urls = $doc->createElement("poco:urls");
|
||||
xml::add_element($doc, $urls, "poco:type", "homepage");
|
||||
xml::add_element($doc, $urls, "poco:value", $profile["homepage"]);
|
||||
xml::add_element($doc, $urls, "poco:primary", "true");
|
||||
$author->appendChild($urls);
|
||||
}
|
||||
|
||||
if (count($profile)) {
|
||||
xml::add_element($doc, $author, "followers", "", array("url" => App::get_baseurl()."/viewcontacts/".$owner["nick"]));
|
||||
xml::add_element($doc, $author, "statusnet:profile_info", "", array("local_id" => $owner["uid"]));
|
||||
}
|
||||
|
||||
return $author;
|
||||
}
|
||||
|
||||
xml_add_element($doc, $author, "poco:preferredUsername", $owner["nick"]);
|
||||
xml_add_element($doc, $author, "poco:displayName", $owner["name"]);
|
||||
xml_add_element($doc, $author, "poco:note", $owner["about"]);
|
||||
/**
|
||||
* @TODO Picture attachments should look like this:
|
||||
* <a href="https://status.pirati.ca/attachment/572819" title="https://status.pirati.ca/file/heluecht-20151202T222602-rd3u49p.gif"
|
||||
* class="attachment thumbnail" id="attachment-572819" rel="nofollow external">https://status.pirati.ca/attachment/572819</a>
|
||||
*
|
||||
*/
|
||||
|
||||
if (trim($owner["location"]) != "") {
|
||||
$element = $doc->createElement("poco:address");
|
||||
xml_add_element($doc, $element, "poco:formatted", $owner["location"]);
|
||||
$author->appendChild($element);
|
||||
/**
|
||||
* @brief Returns the given activity if present - otherwise returns the "post" activity
|
||||
*
|
||||
* @param array $item Data of the item that is to be posted
|
||||
*
|
||||
* @return string activity
|
||||
*/
|
||||
function construct_verb($item) {
|
||||
if ($item['verb'])
|
||||
return $item['verb'];
|
||||
return ACTIVITY_POST;
|
||||
}
|
||||
|
||||
if (trim($profile["homepage"]) != "") {
|
||||
$urls = $doc->createElement("poco:urls");
|
||||
xml_add_element($doc, $urls, "poco:type", "homepage");
|
||||
xml_add_element($doc, $urls, "poco:value", $profile["homepage"]);
|
||||
xml_add_element($doc, $urls, "poco:primary", "true");
|
||||
$author->appendChild($urls);
|
||||
/**
|
||||
* @brief Returns the given object type if present - otherwise returns the "note" object type
|
||||
*
|
||||
* @param array $item Data of the item that is to be posted
|
||||
*
|
||||
* @return string Object type
|
||||
*/
|
||||
function construct_objecttype($item) {
|
||||
if (in_array($item['object-type'], array(ACTIVITY_OBJ_NOTE, ACTIVITY_OBJ_COMMENT)))
|
||||
return $item['object-type'];
|
||||
return ACTIVITY_OBJ_NOTE;
|
||||
}
|
||||
|
||||
if (count($profile)) {
|
||||
xml_add_element($doc, $author, "followers", "", array("url" => $a->get_baseurl()."/viewcontacts/".$owner["nick"]));
|
||||
xml_add_element($doc, $author, "statusnet:profile_info", "", array("local_id" => $owner["uid"]));
|
||||
/**
|
||||
* @brief Adds an entry element to the XML document
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param array $item Data of the item that is to be posted
|
||||
* @param array $owner Contact data of the poster
|
||||
* @param bool $toplevel
|
||||
*
|
||||
* @return object Entry element
|
||||
*/
|
||||
private function entry($doc, $item, $owner, $toplevel = false) {
|
||||
$repeated_guid = self::get_reshared_guid($item);
|
||||
if ($repeated_guid != "")
|
||||
$xml = self::reshare_entry($doc, $item, $owner, $repeated_guid, $toplevel);
|
||||
|
||||
if ($xml)
|
||||
return $xml;
|
||||
|
||||
if ($item["verb"] == ACTIVITY_LIKE)
|
||||
return self::like_entry($doc, $item, $owner, $toplevel);
|
||||
else
|
||||
return self::note_entry($doc, $item, $owner, $toplevel);
|
||||
}
|
||||
|
||||
return $author;
|
||||
}
|
||||
/**
|
||||
* @brief Adds a source entry to the XML document
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param array $contact Array of the contact that is added
|
||||
*
|
||||
* @return object Source element
|
||||
*/
|
||||
private function source_entry($doc, $contact) {
|
||||
$source = $doc->createElement("source");
|
||||
xml::add_element($doc, $source, "id", $contact["poll"]);
|
||||
xml::add_element($doc, $source, "title", $contact["name"]);
|
||||
xml::add_element($doc, $source, "link", "", array("rel" => "alternate",
|
||||
"type" => "text/html",
|
||||
"href" => $contact["alias"]));
|
||||
xml::add_element($doc, $source, "link", "", array("rel" => "self",
|
||||
"type" => "application/atom+xml",
|
||||
"href" => $contact["poll"]));
|
||||
xml::add_element($doc, $source, "icon", $contact["photo"]);
|
||||
xml::add_element($doc, $source, "updated", datetime_convert("UTC","UTC",$contact["success_update"]."+00:00",ATOM_TIME));
|
||||
|
||||
/**
|
||||
* @TODO Picture attachments should look like this:
|
||||
* <a href="https://status.pirati.ca/attachment/572819" title="https://status.pirati.ca/file/heluecht-20151202T222602-rd3u49p.gif"
|
||||
* class="attachment thumbnail" id="attachment-572819" rel="nofollow external">https://status.pirati.ca/attachment/572819</a>
|
||||
*
|
||||
*/
|
||||
|
||||
function ostatus_entry($doc, $item, $owner, $toplevel = false, $repeat = false) {
|
||||
$a = get_app();
|
||||
|
||||
if (($item["id"] != $item["parent"]) AND (normalise_link($item["author-link"]) != normalise_link($owner["url"]))) {
|
||||
logger("OStatus entry is from author ".$owner["url"]." - not from ".$item["author-link"].". Quitting.", LOGGER_DEBUG);
|
||||
return $source;
|
||||
}
|
||||
|
||||
$is_repeat = false;
|
||||
/**
|
||||
* @brief Fetches contact data from the contact or the gcontact table
|
||||
*
|
||||
* @param string $url URL of the contact
|
||||
* @param array $owner Contact data of the poster
|
||||
*
|
||||
* @return array Contact array
|
||||
*/
|
||||
private function contact_entry($url, $owner) {
|
||||
|
||||
/* if (!$repeat) {
|
||||
$repeated_guid = get_reshared_guid($item);
|
||||
$r = q("SELECT * FROM `contact` WHERE `nurl` = '%s' AND `uid` IN (0, %d) ORDER BY `uid` DESC LIMIT 1",
|
||||
dbesc(normalise_link($url)), intval($owner["uid"]));
|
||||
if ($r) {
|
||||
$contact = $r[0];
|
||||
$contact["uid"] = -1;
|
||||
}
|
||||
|
||||
if ($repeated_guid != "") {
|
||||
$r = q("SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1",
|
||||
intval($owner["uid"]), dbesc($repeated_guid));
|
||||
if (!$r) {
|
||||
$r = q("SELECT * FROM `gcontact` WHERE `nurl` = '%s' LIMIT 1",
|
||||
dbesc(normalise_link($url)));
|
||||
if ($r) {
|
||||
$repeated_item = $r[0];
|
||||
$is_repeat = true;
|
||||
$contact = $r[0];
|
||||
$contact["uid"] = -1;
|
||||
$contact["success_update"] = $contact["updated"];
|
||||
}
|
||||
}
|
||||
}
|
||||
*/
|
||||
if (!$toplevel AND !$repeat) {
|
||||
$entry = $doc->createElement("entry");
|
||||
$title = sprintf("New note by %s", $owner["nick"]);
|
||||
} elseif (!$toplevel AND $repeat) {
|
||||
$entry = $doc->createElement("activity:object");
|
||||
$title = sprintf("New note by %s", $owner["nick"]);
|
||||
} else {
|
||||
$entry = $doc->createElementNS(NAMESPACE_ATOM1, "entry");
|
||||
|
||||
$entry->setAttribute("xmlns:thr", NAMESPACE_THREAD);
|
||||
$entry->setAttribute("xmlns:georss", NAMESPACE_GEORSS);
|
||||
$entry->setAttribute("xmlns:activity", NAMESPACE_ACTIVITY);
|
||||
$entry->setAttribute("xmlns:media", NAMESPACE_MEDIA);
|
||||
$entry->setAttribute("xmlns:poco", NAMESPACE_POCO);
|
||||
$entry->setAttribute("xmlns:ostatus", NAMESPACE_OSTATUS);
|
||||
$entry->setAttribute("xmlns:statusnet", NAMESPACE_STATUSNET);
|
||||
if (!$r)
|
||||
$contact = owner;
|
||||
|
||||
$author = ostatus_add_author($doc, $owner);
|
||||
$entry->appendChild($author);
|
||||
if (!isset($contact["poll"])) {
|
||||
$data = probe_url($url);
|
||||
$contact["poll"] = $data["poll"];
|
||||
|
||||
$title = sprintf("New comment by %s", $owner["nick"]);
|
||||
}
|
||||
|
||||
// To use the object-type "bookmark" we have to implement these elements:
|
||||
//
|
||||
// <activity:object-type>http://activitystrea.ms/schema/1.0/bookmark</activity:object-type>
|
||||
// <title>Historic Rocket Landing</title>
|
||||
// <summary>Nur ein Testbeitrag.</summary>
|
||||
// <link rel="related" href="https://www.youtube.com/watch?v=9pillaOxGCo"/>
|
||||
// <link rel="preview" href="https://pirati.cc/file/thumb-4526-450x338-b48c8055f0c2fed0c3f67adc234c4b99484a90c42ed3cac73dc1081a4d0a7bc1.jpg.jpg" media:width="450" media:height="338"/>
|
||||
//
|
||||
// But: it seems as if it doesn't federate well between the GS servers
|
||||
// So we just set it to "note" to be sure that it reaches their target systems
|
||||
|
||||
if (!$repeat)
|
||||
xml_add_element($doc, $entry, "activity:object-type", ACTIVITY_OBJ_NOTE);
|
||||
else
|
||||
xml_add_element($doc, $entry, "activity:object-type", NAMESPACE_ACTIVITY_SCHEMA.'activity');
|
||||
|
||||
xml_add_element($doc, $entry, "id", $item["uri"]);
|
||||
xml_add_element($doc, $entry, "title", $title);
|
||||
|
||||
if($item['allow_cid'] || $item['allow_gid'] || $item['deny_cid'] || $item['deny_gid'])
|
||||
$body = fix_private_photos($item['body'],$owner['uid'],$item, 0);
|
||||
else
|
||||
$body = $item['body'];
|
||||
|
||||
$body = ostatus_format_picture_post($body);
|
||||
|
||||
if ($item['title'] != "")
|
||||
$body = "[b]".$item['title']."[/b]\n\n".$body;
|
||||
|
||||
//$body = bb_remove_share_information($body);
|
||||
$body = bbcode($body, false, false, 7);
|
||||
|
||||
xml_add_element($doc, $entry, "content", $body, array("type" => "html"));
|
||||
|
||||
xml_add_element($doc, $entry, "link", "", array("rel" => "alternate", "type" => "text/html",
|
||||
"href" => $a->get_baseurl()."/display/".$item["guid"]));
|
||||
|
||||
xml_add_element($doc, $entry, "status_net", "", array("notice_id" => $item["id"]));
|
||||
|
||||
if (!$is_repeat)
|
||||
xml_add_element($doc, $entry, "activity:verb", construct_verb($item));
|
||||
else
|
||||
xml_add_element($doc, $entry, "activity:verb", ACTIVITY_SHARE);
|
||||
|
||||
xml_add_element($doc, $entry, "published", datetime_convert("UTC","UTC",$item["created"]."+00:00",ATOM_TIME));
|
||||
xml_add_element($doc, $entry, "updated", datetime_convert("UTC","UTC",$item["edited"]."+00:00",ATOM_TIME));
|
||||
|
||||
if ($is_repeat) {
|
||||
$repeated_owner = array();
|
||||
$repeated_owner["name"] = $repeated_item["author-name"];
|
||||
$repeated_owner["url"] = $repeated_item["author-link"];
|
||||
$repeated_owner["photo"] = $repeated_item["author-avatar"];
|
||||
$repeated_owner["nick"] = $repeated_owner["name"];
|
||||
$repeated_owner["location"] = "";
|
||||
$repeated_owner["about"] = "";
|
||||
$repeated_owner["uid"] = 0;
|
||||
|
||||
// Fetch the missing data from the global contacts
|
||||
$r =q("SELECT * FROM `gcontact` WHERE `nurl` = '%s'", normalise_link($repeated_item["author-link"]));
|
||||
if ($r) {
|
||||
if ($r[0]["nick"] != "")
|
||||
$repeated_owner["nick"] = $r[0]["nick"];
|
||||
|
||||
$repeated_owner["location"] = $r[0]["location"];
|
||||
$repeated_owner["about"] = $r[0]["about"];
|
||||
if (!$contact["alias"])
|
||||
$contact["alias"] = $data["alias"];
|
||||
}
|
||||
|
||||
$entry_repeat = ostatus_entry($doc, $repeated_item, $repeated_owner, false, true);
|
||||
$entry->appendChild($entry_repeat);
|
||||
} elseif ($repeat) {
|
||||
$author = ostatus_add_author($doc, $owner);
|
||||
$entry->appendChild($author);
|
||||
if (!isset($contact["alias"]))
|
||||
$contact["alias"] = $contact["url"];
|
||||
|
||||
return $contact;
|
||||
}
|
||||
|
||||
$mentioned = array();
|
||||
/**
|
||||
* @brief Adds an entry element with reshared content
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param array $item Data of the item that is to be posted
|
||||
* @param array $owner Contact data of the poster
|
||||
* @param $repeated_guid
|
||||
* @param bool $toplevel Is it for en entry element (false) or a feed entry (true)?
|
||||
*
|
||||
* @return object Entry element
|
||||
*/
|
||||
private function reshare_entry($doc, $item, $owner, $repeated_guid, $toplevel) {
|
||||
|
||||
if (($item["id"] != $item["parent"]) AND (normalise_link($item["author-link"]) != normalise_link($owner["url"]))) {
|
||||
logger("OStatus entry is from author ".$owner["url"]." - not from ".$item["author-link"].". Quitting.", LOGGER_DEBUG);
|
||||
}
|
||||
|
||||
$title = self::entry_header($doc, $entry, $owner, $toplevel);
|
||||
|
||||
$r = q("SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' AND NOT `private` AND `network` IN ('%s', '%s', '%s') LIMIT 1",
|
||||
intval($owner["uid"]), dbesc($repeated_guid),
|
||||
dbesc(NETWORK_DFRN), dbesc(NETWORK_DIASPORA), dbesc(NETWORK_OSTATUS));
|
||||
if ($r)
|
||||
$repeated_item = $r[0];
|
||||
else
|
||||
return false;
|
||||
|
||||
$contact = self::contact_entry($repeated_item['author-link'], $owner);
|
||||
|
||||
if (($item['parent'] != $item['id']) || ($item['parent-uri'] !== $item['uri']) || (($item['thr-parent'] !== '') && ($item['thr-parent'] !== $item['uri']))) {
|
||||
$parent = q("SELECT `guid`, `author-link`, `owner-link` FROM `item` WHERE `id` = %d", intval($item["parent"]));
|
||||
$parent_item = (($item['thr-parent']) ? $item['thr-parent'] : $item['parent-uri']);
|
||||
|
||||
$attributes = array(
|
||||
"ref" => $parent_item,
|
||||
"type" => "text/html",
|
||||
"href" => $a->get_baseurl()."/display/".$parent[0]["guid"]);
|
||||
xml_add_element($doc, $entry, "thr:in-reply-to", "", $attributes);
|
||||
$title = $owner["nick"]." repeated a notice by ".$contact["nick"];
|
||||
|
||||
$attributes = array(
|
||||
"rel" => "related",
|
||||
"href" => $a->get_baseurl()."/display/".$parent[0]["guid"]);
|
||||
xml_add_element($doc, $entry, "link", "", $attributes);
|
||||
self::entry_content($doc, $entry, $item, $owner, $title, ACTIVITY_SHARE, false);
|
||||
|
||||
$mentioned[$parent[0]["author-link"]] = $parent[0]["author-link"];
|
||||
$mentioned[$parent[0]["owner-link"]] = $parent[0]["owner-link"];
|
||||
$as_object = $doc->createElement("activity:object");
|
||||
|
||||
$thrparent = q("SELECT `guid`, `author-link`, `owner-link` FROM `item` WHERE `uid` = %d AND `uri` = '%s'",
|
||||
xml::add_element($doc, $as_object, "activity:object-type", NAMESPACE_ACTIVITY_SCHEMA."activity");
|
||||
|
||||
self::entry_content($doc, $as_object, $repeated_item, $owner, "", "", false);
|
||||
|
||||
$author = self::add_author($doc, $contact);
|
||||
$as_object->appendChild($author);
|
||||
|
||||
$as_object2 = $doc->createElement("activity:object");
|
||||
|
||||
xml::add_element($doc, $as_object2, "activity:object-type", self::construct_objecttype($repeated_item));
|
||||
|
||||
$title = sprintf("New comment by %s", $contact["nick"]);
|
||||
|
||||
self::entry_content($doc, $as_object2, $repeated_item, $owner, $title);
|
||||
|
||||
$as_object->appendChild($as_object2);
|
||||
|
||||
self::entry_footer($doc, $as_object, $item, $owner, false);
|
||||
|
||||
$source = self::source_entry($doc, $contact);
|
||||
|
||||
$as_object->appendChild($source);
|
||||
|
||||
$entry->appendChild($as_object);
|
||||
|
||||
self::entry_footer($doc, $entry, $item, $owner);
|
||||
|
||||
return $entry;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Adds an entry element with a "like"
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param array $item Data of the item that is to be posted
|
||||
* @param array $owner Contact data of the poster
|
||||
* @param bool $toplevel Is it for en entry element (false) or a feed entry (true)?
|
||||
*
|
||||
* @return object Entry element with "like"
|
||||
*/
|
||||
private function like_entry($doc, $item, $owner, $toplevel) {
|
||||
|
||||
if (($item["id"] != $item["parent"]) AND (normalise_link($item["author-link"]) != normalise_link($owner["url"]))) {
|
||||
logger("OStatus entry is from author ".$owner["url"]." - not from ".$item["author-link"].". Quitting.", LOGGER_DEBUG);
|
||||
}
|
||||
|
||||
$title = self::entry_header($doc, $entry, $owner, $toplevel);
|
||||
|
||||
$verb = NAMESPACE_ACTIVITY_SCHEMA."favorite";
|
||||
self::entry_content($doc, $entry, $item, $owner, "Favorite", $verb, false);
|
||||
|
||||
$as_object = $doc->createElement("activity:object");
|
||||
|
||||
$parent = q("SELECT * FROM `item` WHERE `uri` = '%s' AND `uid` = %d",
|
||||
dbesc($item["thr-parent"]), intval($item["uid"]));
|
||||
$parent_item = (($item['thr-parent']) ? $item['thr-parent'] : $item['parent-uri']);
|
||||
|
||||
xml::add_element($doc, $as_object, "activity:object-type", self::construct_objecttype($parent[0]));
|
||||
|
||||
self::entry_content($doc, $as_object, $parent[0], $owner, "New entry");
|
||||
|
||||
$entry->appendChild($as_object);
|
||||
|
||||
self::entry_footer($doc, $entry, $item, $owner);
|
||||
|
||||
return $entry;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Adds a regular entry element
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param array $item Data of the item that is to be posted
|
||||
* @param array $owner Contact data of the poster
|
||||
* @param bool $toplevel Is it for en entry element (false) or a feed entry (true)?
|
||||
*
|
||||
* @return object Entry element
|
||||
*/
|
||||
private function note_entry($doc, $item, $owner, $toplevel) {
|
||||
|
||||
if (($item["id"] != $item["parent"]) AND (normalise_link($item["author-link"]) != normalise_link($owner["url"]))) {
|
||||
logger("OStatus entry is from author ".$owner["url"]." - not from ".$item["author-link"].". Quitting.", LOGGER_DEBUG);
|
||||
}
|
||||
|
||||
$title = self::entry_header($doc, $entry, $owner, $toplevel);
|
||||
|
||||
xml::add_element($doc, $entry, "activity:object-type", ACTIVITY_OBJ_NOTE);
|
||||
|
||||
self::entry_content($doc, $entry, $item, $owner, $title);
|
||||
|
||||
self::entry_footer($doc, $entry, $item, $owner);
|
||||
|
||||
return $entry;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Adds a header element to the XML document
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param object $entry The entry element where the elements are added
|
||||
* @param array $owner Contact data of the poster
|
||||
* @param bool $toplevel Is it for en entry element (false) or a feed entry (true)?
|
||||
*
|
||||
* @return string The title for the element
|
||||
*/
|
||||
private function entry_header($doc, &$entry, $owner, $toplevel) {
|
||||
/// @todo Check if this title stuff is really needed (I guess not)
|
||||
if (!$toplevel) {
|
||||
$entry = $doc->createElement("entry");
|
||||
$title = sprintf("New note by %s", $owner["nick"]);
|
||||
} else {
|
||||
$entry = $doc->createElementNS(NAMESPACE_ATOM1, "entry");
|
||||
|
||||
$entry->setAttribute("xmlns:thr", NAMESPACE_THREAD);
|
||||
$entry->setAttribute("xmlns:georss", NAMESPACE_GEORSS);
|
||||
$entry->setAttribute("xmlns:activity", NAMESPACE_ACTIVITY);
|
||||
$entry->setAttribute("xmlns:media", NAMESPACE_MEDIA);
|
||||
$entry->setAttribute("xmlns:poco", NAMESPACE_POCO);
|
||||
$entry->setAttribute("xmlns:ostatus", NAMESPACE_OSTATUS);
|
||||
$entry->setAttribute("xmlns:statusnet", NAMESPACE_STATUSNET);
|
||||
|
||||
$author = self::add_author($doc, $owner);
|
||||
$entry->appendChild($author);
|
||||
|
||||
$title = sprintf("New comment by %s", $owner["nick"]);
|
||||
}
|
||||
return $title;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Adds elements to the XML document
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param object $entry Entry element where the content is added
|
||||
* @param array $item Data of the item that is to be posted
|
||||
* @param array $owner Contact data of the poster
|
||||
* @param string $title Title for the post
|
||||
* @param string $verb The activity verb
|
||||
* @param bool $complete Add the "status_net" element?
|
||||
*/
|
||||
private function entry_content($doc, $entry, $item, $owner, $title, $verb = "", $complete = true) {
|
||||
|
||||
if ($verb == "")
|
||||
$verb = self::construct_verb($item);
|
||||
|
||||
xml::add_element($doc, $entry, "id", $item["uri"]);
|
||||
xml::add_element($doc, $entry, "title", $title);
|
||||
|
||||
$body = self::format_picture_post($item['body']);
|
||||
|
||||
if ($item['title'] != "")
|
||||
$body = "[b]".$item['title']."[/b]\n\n".$body;
|
||||
|
||||
$body = bbcode($body, false, false, 7);
|
||||
|
||||
xml::add_element($doc, $entry, "content", $body, array("type" => "html"));
|
||||
|
||||
xml::add_element($doc, $entry, "link", "", array("rel" => "alternate", "type" => "text/html",
|
||||
"href" => App::get_baseurl()."/display/".$item["guid"]));
|
||||
|
||||
if ($complete)
|
||||
xml::add_element($doc, $entry, "status_net", "", array("notice_id" => $item["id"]));
|
||||
|
||||
xml::add_element($doc, $entry, "activity:verb", $verb);
|
||||
|
||||
xml::add_element($doc, $entry, "published", datetime_convert("UTC","UTC",$item["created"]."+00:00",ATOM_TIME));
|
||||
xml::add_element($doc, $entry, "updated", datetime_convert("UTC","UTC",$item["edited"]."+00:00",ATOM_TIME));
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Adds the elements at the foot of an entry to the XML document
|
||||
*
|
||||
* @param object $doc XML document
|
||||
* @param object $entry The entry element where the elements are added
|
||||
* @param array $item Data of the item that is to be posted
|
||||
* @param array $owner Contact data of the poster
|
||||
* @param $complete
|
||||
*/
|
||||
private function entry_footer($doc, $entry, $item, $owner, $complete = true) {
|
||||
|
||||
$mentioned = array();
|
||||
|
||||
if (($item['parent'] != $item['id']) || ($item['parent-uri'] !== $item['uri']) || (($item['thr-parent'] !== '') && ($item['thr-parent'] !== $item['uri']))) {
|
||||
$parent = q("SELECT `guid`, `author-link`, `owner-link` FROM `item` WHERE `id` = %d", intval($item["parent"]));
|
||||
$parent_item = (($item['thr-parent']) ? $item['thr-parent'] : $item['parent-uri']);
|
||||
|
||||
$attributes = array(
|
||||
"ref" => $parent_item,
|
||||
"type" => "text/html",
|
||||
"href" => App::get_baseurl()."/display/".$parent[0]["guid"]);
|
||||
xml::add_element($doc, $entry, "thr:in-reply-to", "", $attributes);
|
||||
|
||||
$attributes = array(
|
||||
"rel" => "related",
|
||||
"href" => App::get_baseurl()."/display/".$parent[0]["guid"]);
|
||||
xml::add_element($doc, $entry, "link", "", $attributes);
|
||||
|
||||
$mentioned[$parent[0]["author-link"]] = $parent[0]["author-link"];
|
||||
$mentioned[$parent[0]["owner-link"]] = $parent[0]["owner-link"];
|
||||
|
||||
$thrparent = q("SELECT `guid`, `author-link`, `owner-link` FROM `item` WHERE `uid` = %d AND `uri` = '%s'",
|
||||
intval($owner["uid"]),
|
||||
dbesc($parent_item));
|
||||
if ($thrparent) {
|
||||
$mentioned[$thrparent[0]["author-link"]] = $thrparent[0]["author-link"];
|
||||
$mentioned[$thrparent[0]["owner-link"]] = $thrparent[0]["owner-link"];
|
||||
}
|
||||
}
|
||||
|
||||
xml::add_element($doc, $entry, "link", "", array("rel" => "ostatus:conversation",
|
||||
"href" => App::get_baseurl()."/display/".$owner["nick"]."/".$item["parent"]));
|
||||
xml::add_element($doc, $entry, "ostatus:conversation", App::get_baseurl()."/display/".$owner["nick"]."/".$item["parent"]);
|
||||
|
||||
$tags = item_getfeedtags($item);
|
||||
|
||||
if(count($tags))
|
||||
foreach($tags as $t)
|
||||
if ($t[0] == "@")
|
||||
$mentioned[$t[1]] = $t[1];
|
||||
|
||||
// Make sure that mentions are accepted (GNU Social has problems with mixing HTTP and HTTPS)
|
||||
$newmentions = array();
|
||||
foreach ($mentioned AS $mention) {
|
||||
$newmentions[str_replace("http://", "https://", $mention)] = str_replace("http://", "https://", $mention);
|
||||
$newmentions[str_replace("https://", "http://", $mention)] = str_replace("https://", "http://", $mention);
|
||||
}
|
||||
$mentioned = $newmentions;
|
||||
|
||||
foreach ($mentioned AS $mention) {
|
||||
$r = q("SELECT `forum`, `prv` FROM `contact` WHERE `uid` = %d AND `nurl` = '%s'",
|
||||
intval($owner["uid"]),
|
||||
dbesc($parent_item));
|
||||
if ($thrparent) {
|
||||
$mentioned[$thrparent[0]["author-link"]] = $thrparent[0]["author-link"];
|
||||
$mentioned[$thrparent[0]["owner-link"]] = $thrparent[0]["owner-link"];
|
||||
dbesc(normalise_link($mention)));
|
||||
if ($r[0]["forum"] OR $r[0]["prv"])
|
||||
xml::add_element($doc, $entry, "link", "", array("rel" => "mentioned",
|
||||
"ostatus:object-type" => ACTIVITY_OBJ_GROUP,
|
||||
"href" => $mention));
|
||||
else
|
||||
xml::add_element($doc, $entry, "link", "", array("rel" => "mentioned",
|
||||
"ostatus:object-type" => ACTIVITY_OBJ_PERSON,
|
||||
"href" => $mention));
|
||||
}
|
||||
|
||||
if (!$item["private"]) {
|
||||
xml::add_element($doc, $entry, "link", "", array("rel" => "ostatus:attention",
|
||||
"href" => "http://activityschema.org/collection/public"));
|
||||
xml::add_element($doc, $entry, "link", "", array("rel" => "mentioned",
|
||||
"ostatus:object-type" => "http://activitystrea.ms/schema/1.0/collection",
|
||||
"href" => "http://activityschema.org/collection/public"));
|
||||
}
|
||||
|
||||
if(count($tags))
|
||||
foreach($tags as $t)
|
||||
if ($t[0] != "@")
|
||||
xml::add_element($doc, $entry, "category", "", array("term" => $t[2]));
|
||||
|
||||
self::get_attachment($doc, $entry, $item);
|
||||
|
||||
if ($complete) {
|
||||
$app = $item["app"];
|
||||
if ($app == "")
|
||||
$app = "web";
|
||||
|
||||
$attributes = array("local_id" => $item["id"], "source" => $app);
|
||||
|
||||
if (isset($parent["id"]))
|
||||
$attributes["repeat_of"] = $parent["id"];
|
||||
|
||||
if ($item["coord"] != "")
|
||||
xml::add_element($doc, $entry, "georss:point", $item["coord"]);
|
||||
|
||||
xml::add_element($doc, $entry, "statusnet:notice_info", "", $attributes);
|
||||
}
|
||||
}
|
||||
|
||||
xml_add_element($doc, $entry, "link", "", array("rel" => "ostatus:conversation",
|
||||
"href" => $a->get_baseurl()."/display/".$owner["nick"]."/".$item["parent"]));
|
||||
xml_add_element($doc, $entry, "ostatus:conversation", $a->get_baseurl()."/display/".$owner["nick"]."/".$item["parent"]);
|
||||
/**
|
||||
* @brief Creates the XML feed for a given nickname
|
||||
*
|
||||
* @param app $a The application class
|
||||
* @param string $owner_nick Nickname of the feed owner
|
||||
* @param string $last_update Date of the last update
|
||||
*
|
||||
* @return string XML feed
|
||||
*/
|
||||
public static function feed(&$a, $owner_nick, $last_update) {
|
||||
|
||||
$tags = item_getfeedtags($item);
|
||||
$r = q("SELECT `contact`.*, `user`.`nickname`, `user`.`timezone`, `user`.`page-flags`
|
||||
FROM `contact` INNER JOIN `user` ON `user`.`uid` = `contact`.`uid`
|
||||
WHERE `contact`.`self` AND `user`.`nickname` = '%s' LIMIT 1",
|
||||
dbesc($owner_nick));
|
||||
if (!$r)
|
||||
return;
|
||||
|
||||
if(count($tags))
|
||||
foreach($tags as $t)
|
||||
if ($t[0] == "@")
|
||||
$mentioned[$t[1]] = $t[1];
|
||||
$owner = $r[0];
|
||||
|
||||
// Make sure that mentions are accepted (GNU Social has problems with mixing HTTP and HTTPS)
|
||||
$newmentions = array();
|
||||
foreach ($mentioned AS $mention) {
|
||||
$newmentions[str_replace("http://", "https://", $mention)] = str_replace("http://", "https://", $mention);
|
||||
$newmentions[str_replace("https://", "http://", $mention)] = str_replace("https://", "http://", $mention);
|
||||
}
|
||||
$mentioned = $newmentions;
|
||||
if(!strlen($last_update))
|
||||
$last_update = 'now -30 days';
|
||||
|
||||
foreach ($mentioned AS $mention) {
|
||||
$r = q("SELECT `forum`, `prv` FROM `contact` WHERE `uid` = %d AND `nurl` = '%s'",
|
||||
intval($owner["uid"]),
|
||||
dbesc(normalise_link($mention)));
|
||||
if ($r[0]["forum"] OR $r[0]["prv"])
|
||||
xml_add_element($doc, $entry, "link", "", array("rel" => "mentioned",
|
||||
"ostatus:object-type" => ACTIVITY_OBJ_GROUP,
|
||||
"href" => $mention));
|
||||
else
|
||||
xml_add_element($doc, $entry, "link", "", array("rel" => "mentioned",
|
||||
"ostatus:object-type" => ACTIVITY_OBJ_PERSON,
|
||||
"href" => $mention));
|
||||
$check_date = datetime_convert('UTC','UTC',$last_update,'Y-m-d H:i:s');
|
||||
|
||||
$items = q("SELECT STRAIGHT_JOIN `item`.*, `item`.`id` AS `item_id` FROM `item`
|
||||
INNER JOIN `thread` ON `thread`.`iid` = `item`.`parent`
|
||||
LEFT JOIN `item` AS `thritem` ON `thritem`.`uri`=`item`.`thr-parent` AND `thritem`.`uid`=`item`.`uid`
|
||||
WHERE `item`.`uid` = %d AND `item`.`received` > '%s' AND NOT `item`.`private` AND NOT `item`.`deleted`
|
||||
AND `item`.`allow_cid` = '' AND `item`.`allow_gid` = '' AND `item`.`deny_cid` = '' AND `item`.`deny_gid` = ''
|
||||
AND ((`item`.`wall` AND (`item`.`parent` = `item`.`id`))
|
||||
OR (`item`.`network` = '%s' AND ((`thread`.`network` IN ('%s', '%s')) OR (`thritem`.`network` IN ('%s', '%s')))) AND `thread`.`mention`)
|
||||
AND ((`item`.`owner-link` IN ('%s', '%s') AND (`item`.`parent` = `item`.`id`))
|
||||
OR (`item`.`author-link` IN ('%s', '%s')))
|
||||
ORDER BY `item`.`received` DESC
|
||||
LIMIT 0, 300",
|
||||
intval($owner["uid"]), dbesc($check_date), dbesc(NETWORK_DFRN),
|
||||
//dbesc(NETWORK_OSTATUS), dbesc(NETWORK_OSTATUS),
|
||||
//dbesc(NETWORK_OSTATUS), dbesc(NETWORK_OSTATUS),
|
||||
dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN),
|
||||
dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN),
|
||||
dbesc($owner["nurl"]), dbesc(str_replace("http://", "https://", $owner["nurl"])),
|
||||
dbesc($owner["nurl"]), dbesc(str_replace("http://", "https://", $owner["nurl"]))
|
||||
);
|
||||
|
||||
$doc = new DOMDocument('1.0', 'utf-8');
|
||||
$doc->formatOutput = true;
|
||||
|
||||
$root = self::add_header($doc, $owner);
|
||||
|
||||
foreach ($items AS $item) {
|
||||
$entry = self::entry($doc, $item, $owner);
|
||||
$root->appendChild($entry);
|
||||
}
|
||||
|
||||
return(trim($doc->saveXML()));
|
||||
}
|
||||
|
||||
if (!$item["private"])
|
||||
xml_add_element($doc, $entry, "link", "", array("rel" => "mentioned",
|
||||
"ostatus:object-type" => "http://activitystrea.ms/schema/1.0/collection",
|
||||
"href" => "http://activityschema.org/collection/public"));
|
||||
/**
|
||||
* @brief Creates the XML for a salmon message
|
||||
*
|
||||
* @param array $item Data of the item that is to be posted
|
||||
* @param array $owner Contact data of the poster
|
||||
*
|
||||
* @return string XML for the salmon
|
||||
*/
|
||||
public static function salmon($item,$owner) {
|
||||
|
||||
if(count($tags))
|
||||
foreach($tags as $t)
|
||||
if ($t[0] != "@")
|
||||
xml_add_element($doc, $entry, "category", "", array("term" => $t[2]));
|
||||
$doc = new DOMDocument('1.0', 'utf-8');
|
||||
$doc->formatOutput = true;
|
||||
|
||||
ostatus_get_attachment($doc, $entry, $item);
|
||||
$entry = self::entry($doc, $item, $owner, true);
|
||||
|
||||
/// @TODO
|
||||
/// The API call has yet to be implemented
|
||||
//$attributes = array("href" => $a->get_baseurl()."/api/statuses/show/".$item["id"].".atom",
|
||||
// "rel" => "self", "type" => "application/atom+xml");
|
||||
//xml_add_element($doc, $entry, "link", "", $attributes);
|
||||
$doc->appendChild($entry);
|
||||
|
||||
//$attributes = array("href" => $a->get_baseurl()."/api/statuses/show/".$item["id"].".atom",
|
||||
// "rel" => "edit", "type" => "application/atom+xml");
|
||||
//xml_add_element($doc, $entry, "link", "", $attributes);
|
||||
|
||||
$app = $item["app"];
|
||||
if ($app == "")
|
||||
$app = "web";
|
||||
|
||||
|
||||
$attributes = array("local_id" => $item["id"], "source" => $app);
|
||||
if ($is_repeat)
|
||||
$attributes["repeat_of"] = $repeated_item["id"];
|
||||
|
||||
xml_add_element($doc, $entry, "statusnet:notice_info", "", $attributes);
|
||||
|
||||
return $entry;
|
||||
}
|
||||
|
||||
function ostatus_feed(&$a, $owner_nick, $last_update) {
|
||||
|
||||
$r = q("SELECT `contact`.*, `user`.`nickname`, `user`.`timezone`, `user`.`page-flags`
|
||||
FROM `contact` INNER JOIN `user` ON `user`.`uid` = `contact`.`uid`
|
||||
WHERE `contact`.`self` AND `user`.`nickname` = '%s' LIMIT 1",
|
||||
dbesc($owner_nick));
|
||||
if (!$r)
|
||||
return;
|
||||
|
||||
$owner = $r[0];
|
||||
|
||||
if(!strlen($last_update))
|
||||
$last_update = 'now -30 days';
|
||||
|
||||
$check_date = datetime_convert('UTC','UTC',$last_update,'Y-m-d H:i:s');
|
||||
|
||||
$items = q("SELECT STRAIGHT_JOIN `item`.*, `item`.`id` AS `item_id` FROM `item`
|
||||
INNER JOIN `thread` ON `thread`.`iid` = `item`.`parent`
|
||||
LEFT JOIN `item` AS `thritem` ON `thritem`.`uri`=`item`.`thr-parent` AND `thritem`.`uid`=`item`.`uid`
|
||||
WHERE `item`.`uid` = %d AND `item`.`received` > '%s' AND NOT `item`.`private` AND NOT `item`.`deleted`
|
||||
AND `item`.`allow_cid` = '' AND `item`.`allow_gid` = '' AND `item`.`deny_cid` = '' AND `item`.`deny_gid` = ''
|
||||
AND ((`item`.`wall` AND (`item`.`parent` = `item`.`id`))
|
||||
OR (`item`.`network` = '%s' AND ((`thread`.`network` IN ('%s', '%s')) OR (`thritem`.`network` IN ('%s', '%s')))) AND `thread`.`mention`)
|
||||
AND ((`item`.`owner-link` IN ('%s', '%s') AND (`item`.`parent` = `item`.`id`))
|
||||
OR (`item`.`author-link` IN ('%s', '%s')))
|
||||
ORDER BY `item`.`received` DESC
|
||||
LIMIT 0, 300",
|
||||
intval($owner["uid"]), dbesc($check_date), dbesc(NETWORK_DFRN),
|
||||
//dbesc(NETWORK_OSTATUS), dbesc(NETWORK_OSTATUS),
|
||||
//dbesc(NETWORK_OSTATUS), dbesc(NETWORK_OSTATUS),
|
||||
dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN),
|
||||
dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DFRN),
|
||||
dbesc($owner["nurl"]), dbesc(str_replace("http://", "https://", $owner["nurl"])),
|
||||
dbesc($owner["nurl"]), dbesc(str_replace("http://", "https://", $owner["nurl"]))
|
||||
);
|
||||
|
||||
$doc = new DOMDocument('1.0', 'utf-8');
|
||||
$doc->formatOutput = true;
|
||||
|
||||
$root = ostatus_add_header($doc, $owner);
|
||||
|
||||
foreach ($items AS $item) {
|
||||
$entry = ostatus_entry($doc, $item, $owner);
|
||||
$root->appendChild($entry);
|
||||
return(trim($doc->saveXML()));
|
||||
}
|
||||
|
||||
return(trim($doc->saveXML()));
|
||||
}
|
||||
|
||||
function ostatus_salmon($item,$owner) {
|
||||
|
||||
$doc = new DOMDocument('1.0', 'utf-8');
|
||||
$doc->formatOutput = true;
|
||||
|
||||
$entry = ostatus_entry($doc, $item, $owner, true);
|
||||
|
||||
$doc->appendChild($entry);
|
||||
|
||||
return(trim($doc->saveXML()));
|
||||
}
|
||||
?>
|
||||
|
|
|
|||
|
|
@ -132,7 +132,19 @@ function shortenmsg($msg, $limit, $twitter = false) {
|
|||
return($msg);
|
||||
}
|
||||
|
||||
function plaintext($a, $b, $limit = 0, $includedlinks = false, $htmlmode = 2) {
|
||||
/**
|
||||
* @brief Convert a message into plaintext for connectors to other networks
|
||||
*
|
||||
* @param App $a The application class
|
||||
* @param array $b The message array that is about to be posted
|
||||
* @param int $limit The maximum number of characters when posting to that network
|
||||
* @param bool $includedlinks Has an attached link to be included into the message?
|
||||
* @param int $htmlmode This triggers the behaviour of the bbcode conversion
|
||||
* @param string $target_network Name of the network where the post should go to.
|
||||
*
|
||||
* @return string The converted message
|
||||
*/
|
||||
function plaintext($a, $b, $limit = 0, $includedlinks = false, $htmlmode = 2, $target_network = "") {
|
||||
require_once("include/bbcode.php");
|
||||
require_once("include/html2plain.php");
|
||||
require_once("include/network.php");
|
||||
|
|
@ -144,6 +156,9 @@ function plaintext($a, $b, $limit = 0, $includedlinks = false, $htmlmode = 2) {
|
|||
// Add an URL element if the text contains a raw link
|
||||
$body = preg_replace("/([^\]\='".'"'."]|^)(https?\:\/\/[a-zA-Z0-9\:\/\-\?\&\;\.\=\_\~\#\%\$\!\+\,]+)/ism", '$1[url]$2[/url]', $body);
|
||||
|
||||
// Remove the abstract
|
||||
$body = remove_abstract($body);
|
||||
|
||||
// At first look at data that is attached via "type-..." stuff
|
||||
// This will hopefully replaced with a dedicated bbcode later
|
||||
//$post = get_attached_data($b["body"]);
|
||||
|
|
@ -154,6 +169,44 @@ function plaintext($a, $b, $limit = 0, $includedlinks = false, $htmlmode = 2) {
|
|||
elseif ($b["title"] != "")
|
||||
$post["text"] = trim($b["title"]);
|
||||
|
||||
$abstract = "";
|
||||
|
||||
// Fetch the abstract from the given target network
|
||||
if ($target_network != "") {
|
||||
$default_abstract = fetch_abstract($b["body"]);
|
||||
$abstract = fetch_abstract($b["body"], $target_network);
|
||||
|
||||
// If we post to a network with no limit we only fetch
|
||||
// an abstract exactly for this network
|
||||
if (($limit == 0) AND ($abstract == $default_abstract))
|
||||
$abstract = "";
|
||||
|
||||
} else // Try to guess the correct target network
|
||||
switch ($htmlmode) {
|
||||
case 8:
|
||||
$abstract = fetch_abstract($b["body"], NETWORK_TWITTER);
|
||||
break;
|
||||
case 7:
|
||||
$abstract = fetch_abstract($b["body"], NETWORK_STATUSNET);
|
||||
break;
|
||||
case 6:
|
||||
$abstract = fetch_abstract($b["body"], NETWORK_APPNET);
|
||||
break;
|
||||
default: // We don't know the exact target.
|
||||
// We fetch an abstract since there is a posting limit.
|
||||
if ($limit > 0)
|
||||
$abstract = fetch_abstract($b["body"]);
|
||||
}
|
||||
|
||||
if ($abstract != "") {
|
||||
$post["text"] = $abstract;
|
||||
|
||||
if ($post["type"] == "text") {
|
||||
$post["type"] = "link";
|
||||
$post["url"] = $b["plink"];
|
||||
}
|
||||
}
|
||||
|
||||
$html = bbcode($post["text"], false, false, $htmlmode);
|
||||
$msg = html2plain($html, 0, true);
|
||||
$msg = trim(html_entity_decode($msg,ENT_QUOTES,'UTF-8'));
|
||||
|
|
|
|||
|
|
@ -29,17 +29,8 @@ function poller_run(&$argv, &$argc){
|
|||
if (poller_max_connections_reached())
|
||||
return;
|
||||
|
||||
$load = current_load();
|
||||
if($load) {
|
||||
$maxsysload = intval(get_config('system','maxloadavg'));
|
||||
if($maxsysload < 1)
|
||||
$maxsysload = 50;
|
||||
|
||||
if(intval($load) > $maxsysload) {
|
||||
logger('system: load ' . $load . ' too high. poller deferred to next scheduled run.');
|
||||
return;
|
||||
}
|
||||
}
|
||||
if (App::maxload_reached())
|
||||
return;
|
||||
|
||||
// Checking the number of workers
|
||||
if (poller_too_much_workers(1)) {
|
||||
|
|
@ -205,6 +196,12 @@ function poller_max_connections_reached() {
|
|||
*/
|
||||
function poller_kill_stale_workers() {
|
||||
$r = q("SELECT `pid`, `executed` FROM `workerqueue` WHERE `executed` != '0000-00-00 00:00:00'");
|
||||
|
||||
if (!is_array($r) || count($r) == 0) {
|
||||
// No processing here needed
|
||||
return;
|
||||
}
|
||||
|
||||
foreach($r AS $pid)
|
||||
if (!posix_kill($pid["pid"], 0))
|
||||
q("UPDATE `workerqueue` SET `executed` = '0000-00-00 00:00:00', `pid` = 0 WHERE `pid` = %d",
|
||||
|
|
|
|||
141
include/post_update.php
Normal file
141
include/post_update.php
Normal file
|
|
@ -0,0 +1,141 @@
|
|||
<?php
|
||||
/**
|
||||
* @file include/post_update.php
|
||||
*/
|
||||
|
||||
/**
|
||||
* @brief Calls the post update functions
|
||||
*/
|
||||
function post_update() {
|
||||
|
||||
if (!post_update_1192())
|
||||
return;
|
||||
|
||||
if (!post_update_1194())
|
||||
return;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief set the gcontact-id in all item entries
|
||||
*
|
||||
* This job has to be started multiple times until all entries are set.
|
||||
* It isn't started in the update function since it would consume too much time and can be done in the background.
|
||||
*
|
||||
* @return bool "true" when the job is done
|
||||
*/
|
||||
function post_update_1192() {
|
||||
|
||||
// Was the script completed?
|
||||
if (get_config("system", "post_update_version") >= 1192)
|
||||
return true;
|
||||
|
||||
// Check if the first step is done (Setting "gcontact-id" in the item table)
|
||||
$r = q("SELECT `author-link`, `author-name`, `author-avatar`, `uid`, `network` FROM `item` WHERE `gcontact-id` = 0 LIMIT 1000");
|
||||
if (!$r) {
|
||||
// Are there unfinished entries in the thread table?
|
||||
$r = q("SELECT COUNT(*) AS `total` FROM `thread`
|
||||
INNER JOIN `item` ON `item`.`id` =`thread`.`iid`
|
||||
WHERE `thread`.`gcontact-id` = 0 AND
|
||||
(`thread`.`uid` IN (SELECT `uid` from `user`) OR `thread`.`uid` = 0)");
|
||||
|
||||
if ($r AND ($r[0]["total"] == 0)) {
|
||||
set_config("system", "post_update_version", 1192);
|
||||
return true;
|
||||
}
|
||||
|
||||
// Update the thread table from the item table
|
||||
q("UPDATE `thread` INNER JOIN `item` ON `item`.`id`=`thread`.`iid`
|
||||
SET `thread`.`gcontact-id` = `item`.`gcontact-id`
|
||||
WHERE `thread`.`gcontact-id` = 0 AND
|
||||
(`thread`.`uid` IN (SELECT `uid` from `user`) OR `thread`.`uid` = 0)");
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
$item_arr = array();
|
||||
foreach ($r AS $item) {
|
||||
$index = $item["author-link"]."-".$item["uid"];
|
||||
$item_arr[$index] = array("author-link" => $item["author-link"],
|
||||
"uid" => $item["uid"],
|
||||
"network" => $item["network"]);
|
||||
}
|
||||
|
||||
// Set the "gcontact-id" in the item table and add a new gcontact entry if needed
|
||||
foreach($item_arr AS $item) {
|
||||
$gcontact_id = get_gcontact_id(array("url" => $item['author-link'], "network" => $item['network'],
|
||||
"photo" => $item['author-avatar'], "name" => $item['author-name']));
|
||||
q("UPDATE `item` SET `gcontact-id` = %d WHERE `uid` = %d AND `author-link` = '%s' AND `gcontact-id` = 0",
|
||||
intval($gcontact_id), intval($item["uid"]), dbesc($item["author-link"]));
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Updates the "global" field in the item table
|
||||
*
|
||||
* @return bool "true" when the job is done
|
||||
*/
|
||||
function post_update_1194() {
|
||||
|
||||
// Was the script completed?
|
||||
if (get_config("system", "post_update_version") >= 1194)
|
||||
return true;
|
||||
|
||||
logger("Start", LOGGER_DEBUG);
|
||||
|
||||
$end_id = get_config("system", "post_update_1194_end");
|
||||
if (!$end_id) {
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uid` != 0 ORDER BY `id` DESC LIMIT 1");
|
||||
if ($r) {
|
||||
set_config("system", "post_update_1194_end", $r[0]["id"]);
|
||||
$end_id = get_config("system", "post_update_1194_end");
|
||||
}
|
||||
}
|
||||
|
||||
logger("End ID: ".$end_id, LOGGER_DEBUG);
|
||||
|
||||
$start_id = get_config("system", "post_update_1194_start");
|
||||
|
||||
$query1 = "SELECT `item`.`id` FROM `item` ";
|
||||
|
||||
$query2 = "INNER JOIN `item` AS `shadow` ON `item`.`uri` = `shadow`.`uri` AND `shadow`.`uid` = 0 ";
|
||||
|
||||
$query3 = "WHERE `item`.`uid` != 0 AND `item`.`id` >= %d AND `item`.`id` <= %d
|
||||
AND `item`.`visible` AND NOT `item`.`private`
|
||||
AND NOT `item`.`deleted` AND NOT `item`.`moderated`
|
||||
AND `item`.`network` IN ('%s', '%s', '%s', '')
|
||||
AND `item`.`allow_cid` = '' AND `item`.`allow_gid` = ''
|
||||
AND `item`.`deny_cid` = '' AND `item`.`deny_gid` = ''
|
||||
AND NOT `item`.`global`";
|
||||
|
||||
$r = q($query1.$query2.$query3." ORDER BY `item`.`id` LIMIT 1",
|
||||
intval($start_id), intval($end_id),
|
||||
dbesc(NETWORK_DFRN), dbesc(NETWORK_DIASPORA), dbesc(NETWORK_OSTATUS));
|
||||
if (!$r) {
|
||||
set_config("system", "post_update_version", 1194);
|
||||
logger("Update is done", LOGGER_DEBUG);
|
||||
return true;
|
||||
} else {
|
||||
set_config("system", "post_update_1194_start", $r[0]["id"]);
|
||||
$start_id = get_config("system", "post_update_1194_start");
|
||||
}
|
||||
|
||||
logger("Start ID: ".$start_id, LOGGER_DEBUG);
|
||||
|
||||
$r = q($query1.$query2.$query3." ORDER BY `item`.`id` LIMIT 1000,1",
|
||||
intval($start_id), intval($end_id),
|
||||
dbesc(NETWORK_DFRN), dbesc(NETWORK_DIASPORA), dbesc(NETWORK_OSTATUS));
|
||||
if ($r)
|
||||
$pos_id = $r[0]["id"];
|
||||
else
|
||||
$pos_id = $end_id;
|
||||
|
||||
logger("Progress: Start: ".$start_id." position: ".$pos_id." end: ".$end_id, LOGGER_DEBUG);
|
||||
|
||||
$r = q("UPDATE `item` ".$query2." SET `item`.`global` = 1 ".$query3,
|
||||
intval($start_id), intval($pos_id),
|
||||
dbesc(NETWORK_DFRN), dbesc(NETWORK_DIASPORA), dbesc(NETWORK_OSTATUS));
|
||||
|
||||
logger("Done", LOGGER_DEBUG);
|
||||
}
|
||||
?>
|
||||
|
|
@ -1,96 +1,6 @@
|
|||
<?php
|
||||
|
||||
require_once('include/datetime.php');
|
||||
require_once('include/diaspora.php');
|
||||
require_once('include/queue_fn.php');
|
||||
require_once('include/Contact.php');
|
||||
|
||||
function profile_change() {
|
||||
|
||||
$a = get_app();
|
||||
|
||||
if(! local_user())
|
||||
return;
|
||||
|
||||
// $url = $a->get_baseurl() . '/profile/' . $a->user['nickname'];
|
||||
// if($url && strlen(get_config('system','directory')))
|
||||
// proc_run('php',"include/directory.php","$url");
|
||||
|
||||
$recips = q("SELECT `id`,`name`,`network`,`pubkey`,`notify` FROM `contact` WHERE `network` = '%s'
|
||||
AND `uid` = %d AND `rel` != %d ",
|
||||
dbesc(NETWORK_DIASPORA),
|
||||
intval(local_user()),
|
||||
intval(CONTACT_IS_SHARING)
|
||||
);
|
||||
if(! count($recips))
|
||||
return;
|
||||
|
||||
$r = q("SELECT `profile`.`uid` AS `profile_uid`, `profile`.* , `user`.* FROM `profile`
|
||||
INNER JOIN `user` ON `profile`.`uid` = `user`.`uid`
|
||||
WHERE `user`.`uid` = %d AND `profile`.`is-default` = 1 LIMIT 1",
|
||||
intval(local_user())
|
||||
);
|
||||
|
||||
if(! count($r))
|
||||
return;
|
||||
$profile = $r[0];
|
||||
|
||||
$handle = xmlify($a->user['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3));
|
||||
$first = xmlify(((strpos($profile['name'],' '))
|
||||
? trim(substr($profile['name'],0,strpos($profile['name'],' '))) : $profile['name']));
|
||||
$last = xmlify((($first === $profile['name']) ? '' : trim(substr($profile['name'],strlen($first)))));
|
||||
$large = xmlify($a->get_baseurl() . '/photo/custom/300/' . $profile['uid'] . '.jpg');
|
||||
$medium = xmlify($a->get_baseurl() . '/photo/custom/100/' . $profile['uid'] . '.jpg');
|
||||
$small = xmlify($a->get_baseurl() . '/photo/custom/50/' . $profile['uid'] . '.jpg');
|
||||
$searchable = xmlify((($profile['publish'] && $profile['net-publish']) ? 'true' : 'false' ));
|
||||
// $searchable = 'true';
|
||||
|
||||
if($searchable === 'true') {
|
||||
$dob = '1000-00-00';
|
||||
|
||||
if(($profile['dob']) && ($profile['dob'] != '0000-00-00'))
|
||||
$dob = ((intval($profile['dob'])) ? intval($profile['dob']) : '1000') . '-' . datetime_convert('UTC','UTC',$profile['dob'],'m-d');
|
||||
$gender = xmlify($profile['gender']);
|
||||
$about = xmlify($profile['about']);
|
||||
require_once('include/bbcode.php');
|
||||
$about = xmlify(strip_tags(bbcode($about)));
|
||||
$location = formatted_location($profile);
|
||||
$location = xmlify($location);
|
||||
$tags = '';
|
||||
if($profile['pub_keywords']) {
|
||||
$kw = str_replace(',',' ',$profile['pub_keywords']);
|
||||
$kw = str_replace(' ',' ',$kw);
|
||||
$arr = explode(' ',$profile['pub_keywords']);
|
||||
if(count($arr)) {
|
||||
for($x = 0; $x < 5; $x ++) {
|
||||
if(trim($arr[$x]))
|
||||
$tags .= '#' . trim($arr[$x]) . ' ';
|
||||
}
|
||||
}
|
||||
}
|
||||
$tags = xmlify(trim($tags));
|
||||
}
|
||||
|
||||
$tpl = get_markup_template('diaspora_profile.tpl');
|
||||
|
||||
$msg = replace_macros($tpl,array(
|
||||
'$handle' => $handle,
|
||||
'$first' => $first,
|
||||
'$last' => $last,
|
||||
'$large' => $large,
|
||||
'$medium' => $medium,
|
||||
'$small' => $small,
|
||||
'$dob' => $dob,
|
||||
'$gender' => $gender,
|
||||
'$about' => $about,
|
||||
'$location' => $location,
|
||||
'$searchable' => $searchable,
|
||||
'$tags' => $tags
|
||||
));
|
||||
logger('profile_change: ' . $msg, LOGGER_ALL);
|
||||
|
||||
foreach($recips as $recip) {
|
||||
$msgtosend = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$a->user,$recip,$a->user['prvkey'],$recip['pubkey'],false)));
|
||||
add_to_queue($recip['id'],NETWORK_DIASPORA,$msgtosend,false);
|
||||
}
|
||||
diaspora::send_profile(local_user());
|
||||
}
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ function handle_pubsubhubbub() {
|
|||
|
||||
logger("Generate feed for user ".$rr['nickname']." - last updated ".$rr['last_update'], LOGGER_DEBUG);
|
||||
|
||||
$params = ostatus_feed($a, $rr['nickname'], $rr['last_update']);
|
||||
$params = ostatus::feed($a, $rr['nickname'], $rr['last_update']);
|
||||
$hmac_sig = hash_hmac("sha1", $params, $rr['secret']);
|
||||
|
||||
$headers = array("Content-type: application/atom+xml",
|
||||
|
|
@ -74,25 +74,14 @@ function pubsubpublish_run(&$argv, &$argc){
|
|||
};
|
||||
|
||||
require_once('include/items.php');
|
||||
require_once('include/pidfile.php');
|
||||
|
||||
load_config('config');
|
||||
load_config('system');
|
||||
|
||||
$lockpath = get_lockpath();
|
||||
if ($lockpath != '') {
|
||||
$pidfile = new pidfile($lockpath, 'pubsubpublish');
|
||||
if($pidfile->is_already_running()) {
|
||||
logger("Already running");
|
||||
if ($pidfile->running_time() > 9*60) {
|
||||
$pidfile->kill();
|
||||
logger("killed stale process");
|
||||
// Calling a new instance
|
||||
proc_run('php',"include/pubsubpublish.php");
|
||||
}
|
||||
// Don't check this stuff if the function is called by the poller
|
||||
if (App::callstack() != "poller_run")
|
||||
if (App::is_already_running("pubsubpublish", "include/pubsubpublish.php", 540))
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
$a->set_baseurl(get_config('system','url'));
|
||||
|
||||
|
|
|
|||
|
|
@ -22,26 +22,15 @@ function queue_run(&$argv, &$argc){
|
|||
require_once("include/datetime.php");
|
||||
require_once('include/items.php');
|
||||
require_once('include/bbcode.php');
|
||||
require_once('include/pidfile.php');
|
||||
require_once('include/socgraph.php');
|
||||
|
||||
load_config('config');
|
||||
load_config('system');
|
||||
|
||||
$lockpath = get_lockpath();
|
||||
if ($lockpath != '') {
|
||||
$pidfile = new pidfile($lockpath, 'queue');
|
||||
if($pidfile->is_already_running()) {
|
||||
logger("queue: Already running");
|
||||
if ($pidfile->running_time() > 9*60) {
|
||||
$pidfile->kill();
|
||||
logger("queue: killed stale process");
|
||||
// Calling a new instance
|
||||
proc_run('php',"include/queue.php");
|
||||
}
|
||||
// Don't check this stuff if the function is called by the poller
|
||||
if (App::callstack() != "poller_run")
|
||||
if (App::is_already_running('queue', 'include/queue.php', 540))
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
$a->set_baseurl(get_config('system','url'));
|
||||
|
||||
|
|
@ -204,7 +193,7 @@ function queue_run(&$argv, &$argc){
|
|||
case NETWORK_DIASPORA:
|
||||
if($contact['notify']) {
|
||||
logger('queue: diaspora_delivery: item '.$q_item['id'].' for '.$contact['name'].' <'.$contact['url'].'>');
|
||||
$deliver_status = diaspora_transmit($owner,$contact,$data,$public,true);
|
||||
$deliver_status = diaspora::transmit($owner,$contact,$data,$public,true);
|
||||
|
||||
if($deliver_status == (-1)) {
|
||||
update_queue_time($q_item['id']);
|
||||
|
|
|
|||
|
|
@ -69,7 +69,7 @@ function ref_session_destroy ($id) {
|
|||
if(! function_exists('ref_session_gc')) {
|
||||
function ref_session_gc($expire) {
|
||||
q("DELETE FROM `session` WHERE `expire` < %d", dbesc(time()));
|
||||
q("OPTIMIZE TABLE `sess_data`");
|
||||
//q("OPTIMIZE TABLE `sess_data`");
|
||||
return true;
|
||||
}}
|
||||
|
||||
|
|
|
|||
|
|
@ -438,44 +438,47 @@ function poco_last_updated($profile, $force = false) {
|
|||
|
||||
$noscrape = json_decode($noscraperet["body"], true);
|
||||
|
||||
$contact = array("url" => $profile,
|
||||
"network" => $server[0]["network"],
|
||||
"generation" => $gcontacts[0]["generation"]);
|
||||
if (is_array($noscrape)) {
|
||||
$contact = array("url" => $profile,
|
||||
"network" => $server[0]["network"],
|
||||
"generation" => $gcontacts[0]["generation"]);
|
||||
|
||||
$contact["name"] = $noscrape["fn"];
|
||||
$contact["community"] = $noscrape["comm"];
|
||||
$contact["name"] = $noscrape["fn"];
|
||||
$contact["community"] = $noscrape["comm"];
|
||||
|
||||
if (isset($noscrape["tags"])) {
|
||||
$keywords = implode(" ", $noscrape["tags"]);
|
||||
if ($keywords != "")
|
||||
$contact["keywords"] = $keywords;
|
||||
if (isset($noscrape["tags"])) {
|
||||
$keywords = implode(" ", $noscrape["tags"]);
|
||||
if ($keywords != "")
|
||||
$contact["keywords"] = $keywords;
|
||||
}
|
||||
|
||||
$location = formatted_location($noscrape);
|
||||
if ($location)
|
||||
$contact["location"] = $location;
|
||||
|
||||
$contact["notify"] = $noscrape["dfrn-notify"];
|
||||
|
||||
// Remove all fields that are not present in the gcontact table
|
||||
unset($noscrape["fn"]);
|
||||
unset($noscrape["key"]);
|
||||
unset($noscrape["homepage"]);
|
||||
unset($noscrape["comm"]);
|
||||
unset($noscrape["tags"]);
|
||||
unset($noscrape["locality"]);
|
||||
unset($noscrape["region"]);
|
||||
unset($noscrape["country-name"]);
|
||||
unset($noscrape["contacts"]);
|
||||
unset($noscrape["dfrn-request"]);
|
||||
unset($noscrape["dfrn-confirm"]);
|
||||
unset($noscrape["dfrn-notify"]);
|
||||
unset($noscrape["dfrn-poll"]);
|
||||
|
||||
$contact = array_merge($contact, $noscrape);
|
||||
|
||||
update_gcontact($contact);
|
||||
|
||||
return $noscrape["updated"];
|
||||
}
|
||||
|
||||
$location = formatted_location($noscrape);
|
||||
if ($location)
|
||||
$contact["location"] = $location;
|
||||
|
||||
$contact["notify"] = $noscrape["dfrn-notify"];
|
||||
|
||||
// Remove all fields that are not present in the gcontact table
|
||||
unset($noscrape["fn"]);
|
||||
unset($noscrape["key"]);
|
||||
unset($noscrape["homepage"]);
|
||||
unset($noscrape["comm"]);
|
||||
unset($noscrape["tags"]);
|
||||
unset($noscrape["locality"]);
|
||||
unset($noscrape["region"]);
|
||||
unset($noscrape["country-name"]);
|
||||
unset($noscrape["contacts"]);
|
||||
unset($noscrape["dfrn-request"]);
|
||||
unset($noscrape["dfrn-confirm"]);
|
||||
unset($noscrape["dfrn-notify"]);
|
||||
unset($noscrape["dfrn-poll"]);
|
||||
|
||||
$contact = array_merge($contact, $noscrape);
|
||||
update_gcontact($contact);
|
||||
|
||||
return $noscrape["updated"];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -719,7 +722,8 @@ function poco_check_server($server_url, $network = "", $force = false) {
|
|||
// Will also return data for Friendica and GNU Social - but it will be overwritten later
|
||||
// The "not implemented" is a special treatment for really, really old Friendica versions
|
||||
$serverret = z_fetch_url($server_url."/api/statusnet/version.json");
|
||||
if ($serverret["success"] AND ($serverret["body"] != '{"error":"not implemented"}') AND ($serverret["body"] != '') AND (strlen($serverret["body"]) < 250)) {
|
||||
if ($serverret["success"] AND ($serverret["body"] != '{"error":"not implemented"}') AND
|
||||
($serverret["body"] != '') AND (strlen($serverret["body"]) < 30)) {
|
||||
$platform = "StatusNet";
|
||||
$version = trim($serverret["body"], '"');
|
||||
$network = NETWORK_OSTATUS;
|
||||
|
|
@ -727,7 +731,8 @@ function poco_check_server($server_url, $network = "", $force = false) {
|
|||
|
||||
// Test for GNU Social
|
||||
$serverret = z_fetch_url($server_url."/api/gnusocial/version.json");
|
||||
if ($serverret["success"] AND ($serverret["body"] != '{"error":"not implemented"}') AND ($serverret["body"] != '') AND (strlen($serverret["body"]) < 250)) {
|
||||
if ($serverret["success"] AND ($serverret["body"] != '{"error":"not implemented"}') AND
|
||||
($serverret["body"] != '') AND (strlen($serverret["body"]) < 30)) {
|
||||
$platform = "GNU Social";
|
||||
$version = trim($serverret["body"], '"');
|
||||
$network = NETWORK_OSTATUS;
|
||||
|
|
@ -854,6 +859,11 @@ function poco_check_server($server_url, $network = "", $force = false) {
|
|||
// Check again if the server exists
|
||||
$servers = q("SELECT `nurl` FROM `gserver` WHERE `nurl` = '%s'", dbesc(normalise_link($server_url)));
|
||||
|
||||
$version = strip_tags($version);
|
||||
$site_name = strip_tags($site_name);
|
||||
$info = strip_tags($info);
|
||||
$platform = strip_tags($platform);
|
||||
|
||||
if ($servers)
|
||||
q("UPDATE `gserver` SET `url` = '%s', `version` = '%s', `site_name` = '%s', `info` = '%s', `register_policy` = %d, `poco` = '%s', `noscrape` = '%s',
|
||||
`network` = '%s', `platform` = '%s', `last_contact` = '%s', `last_failure` = '%s' WHERE `nurl` = '%s'",
|
||||
|
|
|
|||
|
|
@ -285,7 +285,7 @@ function paginate_data(&$a, $count=null) {
|
|||
if (($a->page_offset != "") AND !preg_match('/[?&].offset=/', $stripped))
|
||||
$stripped .= "&offset=".urlencode($a->page_offset);
|
||||
|
||||
$url = z_root() . '/' . $stripped;
|
||||
$url = $stripped;
|
||||
|
||||
$data = array();
|
||||
function _l(&$d, $name, $url, $text, $class="") {
|
||||
|
|
@ -923,7 +923,7 @@ function micropro($contact, $redirect = false, $class = '', $textmode = false) {
|
|||
|
||||
if($redirect) {
|
||||
$a = get_app();
|
||||
$redirect_url = z_root() . '/redir/' . $contact['id'];
|
||||
$redirect_url = 'redir/' . $contact['id'];
|
||||
if(local_user() && ($contact['uid'] == local_user()) && ($contact['network'] === NETWORK_DFRN)) {
|
||||
$redir = true;
|
||||
$url = $redirect_url;
|
||||
|
|
@ -964,13 +964,13 @@ if(! function_exists('search')) {
|
|||
* @param string $url search url
|
||||
* @param boolean $savedsearch show save search button
|
||||
*/
|
||||
function search($s,$id='search-box',$url='/search',$save = false, $aside = true) {
|
||||
function search($s,$id='search-box',$url='search',$save = false, $aside = true) {
|
||||
$a = get_app();
|
||||
|
||||
$values = array(
|
||||
'$s' => $s,
|
||||
'$id' => $id,
|
||||
'$action_url' => $a->get_baseurl((stristr($url,'network')) ? true : false) . $url,
|
||||
'$action_url' => $url,
|
||||
'$search_label' => t('Search'),
|
||||
'$save_label' => t('Save'),
|
||||
'$savedsearch' => feature_enabled(local_user(),'savedsearch'),
|
||||
|
|
@ -1148,41 +1148,41 @@ function smilies($s, $sample = false) {
|
|||
);
|
||||
|
||||
$icons = array(
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-heart.gif" alt="<3" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-brokenheart.gif" alt="</3" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-brokenheart.gif" alt="<\\3" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-smile.gif" alt=":-)" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-wink.gif" alt=";-)" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-frown.gif" alt=":-(" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-tongue-out.gif" alt=":-P" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-tongue-out.gif" alt=":-p" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-kiss.gif" alt=":-\"" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-kiss.gif" alt=":-\"" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-kiss.gif" alt=":-x" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-kiss.gif" alt=":-X" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-laughing.gif" alt=":-D" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-surprised.gif" alt="8-|" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-surprised.gif" alt="8-O" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-surprised.gif" alt=":-O" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-thumbsup.gif" alt="\\o/" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-Oo.gif" alt="o.O" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-Oo.gif" alt="O.o" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-Oo.gif" alt="o_O" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-Oo.gif" alt="O_o" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-cry.gif" alt=":\'(" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-foot-in-mouth.gif" alt=":-!" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-undecided.gif" alt=":-/" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-embarassed.gif" alt=":-[" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-cool.gif" alt="8-)" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/beer_mug.gif" alt=":beer" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/beer_mug.gif" alt=":homebrew" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/coffee.gif" alt=":coffee" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-facepalm.gif" alt=":facepalm" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/like.gif" alt=":like" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/dislike.gif" alt=":dislike" />',
|
||||
'<a href="http://friendica.com">~friendica <img class="smiley" src="' . z_root() . '/images/friendica-16.png" alt="~friendica" /></a>',
|
||||
'<a href="http://redmatrix.me/">red<img class="smiley" src="' . z_root() . '/images/rm-16.png" alt="red" />matrix</a>',
|
||||
'<a href="http://redmatrix.me/">red<img class="smiley" src="' . z_root() . '/images/rm-16.png" alt="red" />matrix</a>'
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-heart.gif" alt="<3" title="<3" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-brokenheart.gif" alt="</3" title="</3" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-brokenheart.gif" alt="<\\3" title="<\\3" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-smile.gif" alt=":-)" title=":-)" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-wink.gif" alt=";-)" title=";-)" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-frown.gif" alt=":-(" title=":-(" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-tongue-out.gif" alt=":-P" title=":-P" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-tongue-out.gif" alt=":-p" title=":-P" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-kiss.gif" alt=":-\" title=":-\" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-kiss.gif" alt=":-\" title=":-\" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-kiss.gif" alt=":-x" title=":-x" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-kiss.gif" alt=":-X" title=":-X" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-laughing.gif" alt=":-D" title=":-D" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-surprised.gif" alt="8-|" title="8-|" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-surprised.gif" alt="8-O" title="8-O" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-surprised.gif" alt=":-O" title="8-O" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-thumbsup.gif" alt="\\o/" title="\\o/" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-Oo.gif" alt="o.O" title="o.O" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-Oo.gif" alt="O.o" title="O.o" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-Oo.gif" alt="o_O" title="o_O" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-Oo.gif" alt="O_o" title="O_o" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-cry.gif" alt=":\'(" title=":\'("/>',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-foot-in-mouth.gif" alt=":-!" title=":-!" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-undecided.gif" alt=":-/" title=":-/" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-embarassed.gif" alt=":-[" title=":-[" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-cool.gif" alt="8-)" title="8-)" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/beer_mug.gif" alt=":beer" title=":beer" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/beer_mug.gif" alt=":homebrew" title=":homebrew" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/coffee.gif" alt=":coffee" title=":coffee" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/smiley-facepalm.gif" alt=":facepalm" title=":facepalm" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/like.gif" alt=":like" title=":like" />',
|
||||
'<img class="smiley" src="' . z_root() . '/images/dislike.gif" alt=":dislike" title=":dislike" />',
|
||||
'<a href="http://friendica.com">~friendica <img class="smiley" src="' . z_root() . '/images/friendica-16.png" alt="~friendica" title="~friendica" /></a>',
|
||||
'<a href="http://redmatrix.me/">red<img class="smiley" src="' . z_root() . '/images/rm-16.png" alt="red#" title="red#" />matrix</a>',
|
||||
'<a href="http://redmatrix.me/">red<img class="smiley" src="' . z_root() . '/images/rm-16.png" alt="red#matrix" title="red#matrix" />matrix</a>'
|
||||
);
|
||||
|
||||
$params = array('texts' => $texts, 'icons' => $icons, 'string' => $s);
|
||||
|
|
@ -1305,7 +1305,7 @@ function redir_private_images($a, &$item) {
|
|||
|
||||
if((local_user() == $item['uid']) && ($item['private'] != 0) && ($item['contact-id'] != $a->contact['id']) && ($item['network'] == NETWORK_DFRN)) {
|
||||
//logger("redir_private_images: redir");
|
||||
$img_url = z_root() . '/redir?f=1&quiet=1&url=' . $mtch[1] . '&conurl=' . $item['author-link'];
|
||||
$img_url = 'redir?f=1&quiet=1&url=' . $mtch[1] . '&conurl=' . $item['author-link'];
|
||||
$item['body'] = str_replace($mtch[0], "[img]".$img_url."[/img]", $item['body']);
|
||||
}
|
||||
}
|
||||
|
|
@ -1421,7 +1421,7 @@ function prepare_body(&$item,$attach = false, $preview = false) {
|
|||
$mime = $mtch[3];
|
||||
|
||||
if((local_user() == $item['uid']) && ($item['contact-id'] != $a->contact['id']) && ($item['network'] == NETWORK_DFRN))
|
||||
$the_url = z_root() . '/redir/' . $item['contact-id'] . '?f=1&url=' . $mtch[1];
|
||||
$the_url = 'redir/' . $item['contact-id'] . '?f=1&url=' . $mtch[1];
|
||||
else
|
||||
$the_url = $mtch[1];
|
||||
|
||||
|
|
@ -1596,7 +1596,7 @@ function get_cats_and_terms($item) {
|
|||
$categories[] = array(
|
||||
'name' => xmlify(file_tag_decode($mtch[1])),
|
||||
'url' => "#",
|
||||
'removeurl' => ((local_user() == $item['uid'])?z_root() . '/filerm/' . $item['id'] . '?f=&cat=' . xmlify(file_tag_decode($mtch[1])):""),
|
||||
'removeurl' => ((local_user() == $item['uid'])?'filerm/' . $item['id'] . '?f=&cat=' . xmlify(file_tag_decode($mtch[1])):""),
|
||||
'first' => $first,
|
||||
'last' => false
|
||||
);
|
||||
|
|
@ -1614,7 +1614,7 @@ function get_cats_and_terms($item) {
|
|||
$folders[] = array(
|
||||
'name' => xmlify(file_tag_decode($mtch[1])),
|
||||
'url' => "#",
|
||||
'removeurl' => ((local_user() == $item['uid'])?z_root() . '/filerm/' . $item['id'] . '?f=&term=' . xmlify(file_tag_decode($mtch[1])):""),
|
||||
'removeurl' => ((local_user() == $item['uid'])?'filerm/' . $item['id'] . '?f=&term=' . xmlify(file_tag_decode($mtch[1])):""),
|
||||
'first' => $first,
|
||||
'last' => false
|
||||
);
|
||||
|
|
@ -1639,15 +1639,15 @@ function get_plink($item) {
|
|||
|
||||
if ($a->user['nickname'] != "") {
|
||||
$ret = array(
|
||||
//'href' => z_root()."/display/".$a->user['nickname']."/".$item['id'],
|
||||
'href' => z_root()."/display/".$item['guid'],
|
||||
'orig' => z_root()."/display/".$item['guid'],
|
||||
//'href' => "display/".$a->user['nickname']."/".$item['id'],
|
||||
'href' => "display/".$item['guid'],
|
||||
'orig' => "display/".$item['guid'],
|
||||
'title' => t('View on separate page'),
|
||||
'orig_title' => t('view on separate page'),
|
||||
);
|
||||
|
||||
if (x($item,'plink')) {
|
||||
$ret["href"] = $item['plink'];
|
||||
$ret["href"] = $a->remove_baseurl($item['plink']);
|
||||
$ret["title"] = t('link to source');
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -16,7 +16,6 @@ function update_gcontact_run(&$argv, &$argc){
|
|||
unset($db_host, $db_user, $db_pass, $db_data);
|
||||
};
|
||||
|
||||
require_once('include/pidfile.php');
|
||||
require_once('include/Scrape.php');
|
||||
require_once("include/socgraph.php");
|
||||
|
||||
|
|
@ -37,18 +36,10 @@ function update_gcontact_run(&$argv, &$argc){
|
|||
return;
|
||||
}
|
||||
|
||||
$lockpath = get_lockpath();
|
||||
if ($lockpath != '') {
|
||||
$pidfile = new pidfile($lockpath, 'update_gcontact'.$contact_id);
|
||||
if ($pidfile->is_already_running()) {
|
||||
logger("update_gcontact: Already running for contact ".$contact_id);
|
||||
if ($pidfile->running_time() > 9*60) {
|
||||
$pidfile->kill();
|
||||
logger("killed stale process");
|
||||
}
|
||||
exit;
|
||||
}
|
||||
}
|
||||
// Don't check this stuff if the function is called by the poller
|
||||
if (App::callstack() != "poller_run")
|
||||
if (App::is_already_running('update_gcontact'.$contact_id, '', 540))
|
||||
return;
|
||||
|
||||
$r = q("SELECT * FROM `gcontact` WHERE `id` = %d", intval($contact_id));
|
||||
|
||||
|
|
|
|||
131
include/xml.php
Normal file
131
include/xml.php
Normal file
|
|
@ -0,0 +1,131 @@
|
|||
<?php
|
||||
/**
|
||||
* @file include/xml.php
|
||||
*/
|
||||
|
||||
|
||||
/**
|
||||
* @brief This class contain functions to work with XML data
|
||||
*
|
||||
*/
|
||||
class xml {
|
||||
/**
|
||||
* @brief Creates an XML structure out of a given array
|
||||
*
|
||||
* @param array $array The array of the XML structure that will be generated
|
||||
* @param object $xml The createdXML will be returned by reference
|
||||
* @param bool $remove_header Should the XML header be removed or not?
|
||||
* @param array $namespaces List of namespaces
|
||||
* @param bool $root - interally used parameter. Mustn't be used from outside.
|
||||
*
|
||||
* @return string The created XML
|
||||
*/
|
||||
public static function from_array($array, &$xml, $remove_header = false, $namespaces = array(), $root = true) {
|
||||
|
||||
if ($root) {
|
||||
foreach($array as $key => $value) {
|
||||
foreach ($namespaces AS $nskey => $nsvalue)
|
||||
$key .= " xmlns".($nskey == "" ? "":":").$nskey.'="'.$nsvalue.'"';
|
||||
|
||||
$root = new SimpleXMLElement("<".$key."/>");
|
||||
self::from_array($value, $root, $remove_header, $namespaces, false);
|
||||
|
||||
$dom = dom_import_simplexml($root)->ownerDocument;
|
||||
$dom->formatOutput = true;
|
||||
$xml = $dom;
|
||||
|
||||
$xml_text = $dom->saveXML();
|
||||
|
||||
if ($remove_header)
|
||||
$xml_text = trim(substr($xml_text, 21));
|
||||
|
||||
return $xml_text;
|
||||
}
|
||||
}
|
||||
|
||||
foreach($array as $key => $value) {
|
||||
if ($key == "@attributes") {
|
||||
if (!isset($element) OR !is_array($value))
|
||||
continue;
|
||||
|
||||
foreach ($value as $attr_key => $attr_value) {
|
||||
$element_parts = explode(":", $attr_key);
|
||||
if ((count($element_parts) > 1) AND isset($namespaces[$element_parts[0]]))
|
||||
$namespace = $namespaces[$element_parts[0]];
|
||||
else
|
||||
$namespace = NULL;
|
||||
|
||||
$element->addAttribute ($attr_key, $attr_value, $namespace);
|
||||
}
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
$element_parts = explode(":", $key);
|
||||
if ((count($element_parts) > 1) AND isset($namespaces[$element_parts[0]]))
|
||||
$namespace = $namespaces[$element_parts[0]];
|
||||
else
|
||||
$namespace = NULL;
|
||||
|
||||
if (!is_array($value))
|
||||
$element = $xml->addChild($key, xmlify($value), $namespace);
|
||||
elseif (is_array($value)) {
|
||||
$element = $xml->addChild($key, NULL, $namespace);
|
||||
self::from_array($value, $element, $remove_header, $namespaces, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Copies an XML object
|
||||
*
|
||||
* @param object $source The XML source
|
||||
* @param object $target The XML target
|
||||
* @param string $elementname Name of the XML element of the target
|
||||
*/
|
||||
public static function copy(&$source, &$target, $elementname) {
|
||||
if (count($source->children()) == 0)
|
||||
$target->addChild($elementname, xmlify($source));
|
||||
else {
|
||||
$child = $target->addChild($elementname);
|
||||
foreach ($source->children() AS $childfield => $childentry)
|
||||
self::copy($childentry, $child, $childfield);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Create an XML element
|
||||
*
|
||||
* @param object $doc XML root
|
||||
* @param string $element XML element name
|
||||
* @param string $value XML value
|
||||
* @param array $attributes array containing the attributes
|
||||
*
|
||||
* @return object XML element object
|
||||
*/
|
||||
public static function create_element($doc, $element, $value = "", $attributes = array()) {
|
||||
$element = $doc->createElement($element, xmlify($value));
|
||||
|
||||
foreach ($attributes AS $key => $value) {
|
||||
$attribute = $doc->createAttribute($key);
|
||||
$attribute->value = xmlify($value);
|
||||
$element->appendChild($attribute);
|
||||
}
|
||||
return $element;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Create an XML and append it to the parent object
|
||||
*
|
||||
* @param object $doc XML root
|
||||
* @param object $parent parent object
|
||||
* @param string $element XML element name
|
||||
* @param string $value XML value
|
||||
* @param array $attributes array containing the attributes
|
||||
*/
|
||||
public static function add_element($doc, $parent, $element, $value = "", $attributes = array()) {
|
||||
$element = self::create_element($doc, $element, $value, $attributes);
|
||||
$parent->appendChild($element);
|
||||
}
|
||||
}
|
||||
?>
|
||||
|
|
@ -72,7 +72,8 @@ if(!$install) {
|
|||
(intval(get_config('system','ssl_policy')) == SSL_POLICY_FULL) AND
|
||||
(substr($a->get_baseurl(), 0, 8) == "https://")) {
|
||||
header("HTTP/1.1 302 Moved Temporarily");
|
||||
header("location: ".$a->get_baseurl()."/".$a->query_string);
|
||||
header("Location: ".$a->get_baseurl()."/".$a->query_string);
|
||||
exit();
|
||||
}
|
||||
|
||||
require_once("include/session.php");
|
||||
|
|
@ -371,7 +372,7 @@ $a->init_page_end();
|
|||
if(x($_SESSION,'visitor_home'))
|
||||
$homebase = $_SESSION['visitor_home'];
|
||||
elseif(local_user())
|
||||
$homebase = $a->get_baseurl() . '/profile/' . $a->user['nickname'];
|
||||
$homebase = 'profile/' . $a->user['nickname'];
|
||||
|
||||
if(isset($homebase))
|
||||
$a->page['content'] .= '<script>var homebase="' . $homebase . '" ; </script>';
|
||||
|
|
@ -423,10 +424,10 @@ if($a->module != 'install' && $a->module != 'maintenance') {
|
|||
|
||||
if($a->is_mobile || $a->is_tablet) {
|
||||
if(isset($_SESSION['show-mobile']) && !$_SESSION['show-mobile']) {
|
||||
$link = $a->get_baseurl() . '/toggle_mobile?address=' . curPageURL();
|
||||
$link = 'toggle_mobile?address=' . curPageURL();
|
||||
}
|
||||
else {
|
||||
$link = $a->get_baseurl() . '/toggle_mobile?off=1&address=' . curPageURL();
|
||||
$link = 'toggle_mobile?off=1&address=' . curPageURL();
|
||||
}
|
||||
$a->page['footer'] = replace_macros(get_markup_template("toggle_mobile_footer.tpl"), array(
|
||||
'$toggle_link' => $link,
|
||||
|
|
|
|||
231
mod/admin.php
231
mod/admin.php
|
|
@ -55,13 +55,13 @@ function admin_post(&$a){
|
|||
$func($a);
|
||||
}
|
||||
}
|
||||
goaway($a->get_baseurl(true) . '/admin/plugins/' . $a->argv[2] );
|
||||
goaway('admin/plugins/'.$a->argv[2]);
|
||||
return; // NOTREACHED
|
||||
break;
|
||||
case 'themes':
|
||||
if($a->argc < 2) {
|
||||
if(is_ajax()) return;
|
||||
goaway($a->get_baseurl(true) . '/admin/' );
|
||||
goaway('admin/');
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
@ -92,7 +92,7 @@ function admin_post(&$a){
|
|||
info(t('Theme settings updated.'));
|
||||
if(is_ajax()) return;
|
||||
|
||||
goaway($a->get_baseurl(true) . '/admin/themes/' . $theme );
|
||||
goaway('admin/themes/'.$theme);
|
||||
return;
|
||||
break;
|
||||
case 'features':
|
||||
|
|
@ -107,7 +107,7 @@ function admin_post(&$a){
|
|||
}
|
||||
}
|
||||
|
||||
goaway($a->get_baseurl(true) . '/admin' );
|
||||
goaway('admin');
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -150,17 +150,17 @@ function admin_content(&$a) {
|
|||
* Side bar links
|
||||
*/
|
||||
$aside_tools = array();
|
||||
// array( url, name, extra css classes )
|
||||
// array(url, name, extra css classes)
|
||||
// not part of $aside to make the template more adjustable
|
||||
$aside_sub = array(
|
||||
'site' => array($a->get_baseurl(true)."/admin/site/", t("Site") , "site"),
|
||||
'users' => array($a->get_baseurl(true)."/admin/users/", t("Users") , "users"),
|
||||
'plugins'=> array($a->get_baseurl(true)."/admin/plugins/", t("Plugins") , "plugins"),
|
||||
'themes' => array($a->get_baseurl(true)."/admin/themes/", t("Themes") , "themes"),
|
||||
'features' => array($a->get_baseurl(true)."/admin/features/", t("Additional features") , "features"),
|
||||
'dbsync' => array($a->get_baseurl(true)."/admin/dbsync/", t('DB updates'), "dbsync"),
|
||||
'queue' => array($a->get_baseurl(true)."/admin/queue/", t('Inspect Queue'), "queue"),
|
||||
'federation' => array($a->get_baseurl(true)."/admin/federation/", t('Federation Statistics'), "federation"),
|
||||
'site' => array("admin/site/", t("Site") , "site"),
|
||||
'users' => array("admin/users/", t("Users") , "users"),
|
||||
'plugins'=> array("admin/plugins/", t("Plugins") , "plugins"),
|
||||
'themes' => array("admin/themes/", t("Themes") , "themes"),
|
||||
'features' => array("admin/features/", t("Additional features") , "features"),
|
||||
'dbsync' => array("admin/dbsync/", t('DB updates'), "dbsync"),
|
||||
'queue' => array("admin/queue/", t('Inspect Queue'), "queue"),
|
||||
'federation' => array("admin/federation/", t('Federation Statistics'), "federation"),
|
||||
);
|
||||
|
||||
/* get plugins admin page */
|
||||
|
|
@ -169,18 +169,18 @@ function admin_content(&$a) {
|
|||
$aside_tools['plugins_admin']=array();
|
||||
foreach ($r as $h){
|
||||
$plugin =$h['name'];
|
||||
$aside_tools['plugins_admin'][] = array($a->get_baseurl(true)."/admin/plugins/".$plugin, $plugin, "plugin");
|
||||
$aside_tools['plugins_admin'][] = array("admin/plugins/".$plugin, $plugin, "plugin");
|
||||
// temp plugins with admin
|
||||
$a->plugins_admin[] = $plugin;
|
||||
}
|
||||
|
||||
$aside_tools['logs'] = array($a->get_baseurl(true)."/admin/logs/", t("Logs"), "logs");
|
||||
$aside_tools['viewlogs'] = array($a->get_baseurl(true)."/admin/viewlogs/", t("View Logs"), 'viewlogs');
|
||||
$aside_tools['diagnostics_probe'] = array($a->get_baseurl(true).'/probe/', t('probe address'), 'probe');
|
||||
$aside_tools['diagnostics_webfinger'] = array($a->get_baseurl(true).'/webfinger/', t('check webfinger'), 'webfinger');
|
||||
$aside_tools['logs'] = array("admin/logs/", t("Logs"), "logs");
|
||||
$aside_tools['viewlogs'] = array("admin/viewlogs/", t("View Logs"), 'viewlogs');
|
||||
$aside_tools['diagnostics_probe'] = array('probe/', t('probe address'), 'probe');
|
||||
$aside_tools['diagnostics_webfinger'] = array('webfinger/', t('check webfinger'), 'webfinger');
|
||||
|
||||
$t = get_markup_template("admin_aside.tpl");
|
||||
$a->page['aside'] .= replace_macros( $t, array(
|
||||
$a->page['aside'] .= replace_macros($t, array(
|
||||
'$admin' => $aside_tools,
|
||||
'$subpages' => $aside_sub,
|
||||
'$admtxt' => t('Admin'),
|
||||
|
|
@ -188,7 +188,7 @@ function admin_content(&$a) {
|
|||
'$logtxt' => t('Logs'),
|
||||
'$diagnosticstxt' => t('diagnostics'),
|
||||
'$h_pending' => t('User registrations waiting for confirmation'),
|
||||
'$admurl'=> $a->get_baseurl(true)."/admin/"
|
||||
'$admurl'=> "admin/"
|
||||
));
|
||||
|
||||
|
||||
|
|
@ -231,7 +231,7 @@ function admin_content(&$a) {
|
|||
$o = admin_page_federation($a);
|
||||
break;
|
||||
default:
|
||||
notice( t("Item not found.") );
|
||||
notice(t("Item not found."));
|
||||
}
|
||||
} else {
|
||||
$o = admin_page_summary($a);
|
||||
|
|
@ -270,6 +270,12 @@ function admin_page_federation(&$a) {
|
|||
// Add more platforms if you like, when one returns 0 known nodes it is not
|
||||
// displayed on the stats page.
|
||||
$platforms = array('Friendica', 'Diaspora', '%%red%%', 'Hubzilla', 'GNU Social', 'StatusNet');
|
||||
$colors = array('Friendica' => '#ffc018', // orange from the logo
|
||||
'Diaspora' => '#a1a1a1', // logo is black and white, makes a gray
|
||||
'%%red%%' => '#c50001', // fire red from the logo
|
||||
'Hubzilla' => '#43488a', // blue from the logo
|
||||
'GNU Social'=> '#a22430', // dark red from the logo
|
||||
'StatusNet' => '#789240'); // the green from the logo (red and blue have already others
|
||||
$counts = array();
|
||||
$total = 0;
|
||||
|
||||
|
|
@ -277,14 +283,14 @@ function admin_page_federation(&$a) {
|
|||
// get a total count for the platform, the name and version of the
|
||||
// highest version and the protocol tpe
|
||||
$c = q('SELECT count(*) AS total, platform, network, version FROM gserver
|
||||
WHERE platform LIKE "%s" AND last_contact > last_failure
|
||||
WHERE platform LIKE "%s" AND last_contact > last_failure AND `version` != ""
|
||||
ORDER BY version ASC;', $p);
|
||||
$total = $total + $c[0]['total'];
|
||||
|
||||
// what versions for that platform do we know at all?
|
||||
// again only the active nodes
|
||||
$v = q('SELECT count(*) AS total, version FROM gserver
|
||||
WHERE last_contact > last_failure AND platform LIKE "%s"
|
||||
WHERE last_contact > last_failure AND platform LIKE "%s" AND `version` != ""
|
||||
GROUP BY version
|
||||
ORDER BY version;', $p);
|
||||
|
||||
|
|
@ -338,9 +344,12 @@ function admin_page_federation(&$a) {
|
|||
$v = $newVv;
|
||||
}
|
||||
|
||||
foreach ($v as $key => $vv)
|
||||
$v[$key]["version"] = trim(strip_tags($vv["version"]));
|
||||
|
||||
// the 3rd array item is needed for the JavaScript graphs as JS does
|
||||
// not like some characters in the names of variables...
|
||||
$counts[$p]=array($c[0], $v, str_replace(array(' ','%'),'',$p));
|
||||
$counts[$p]=array($c[0], $v, str_replace(array(' ','%'),'',$p), $colors[$p]);
|
||||
}
|
||||
|
||||
// some helpful text
|
||||
|
|
@ -409,18 +418,18 @@ function admin_page_queue(&$a) {
|
|||
function admin_page_summary(&$a) {
|
||||
$r = q("SELECT `page-flags`, COUNT(uid) as `count` FROM `user` GROUP BY `page-flags`");
|
||||
$accounts = array(
|
||||
array( t('Normal Account'), 0),
|
||||
array( t('Soapbox Account'), 0),
|
||||
array( t('Community/Celebrity Account'), 0),
|
||||
array( t('Automatic Friend Account'), 0),
|
||||
array( t('Blog Account'), 0),
|
||||
array( t('Private Forum'), 0)
|
||||
array(t('Normal Account'), 0),
|
||||
array(t('Soapbox Account'), 0),
|
||||
array(t('Community/Celebrity Account'), 0),
|
||||
array(t('Automatic Friend Account'), 0),
|
||||
array(t('Blog Account'), 0),
|
||||
array(t('Private Forum'), 0)
|
||||
);
|
||||
|
||||
$users=0;
|
||||
foreach ($r as $u){ $accounts[$u['page-flags']][1] = $u['count']; $users+= $u['count']; }
|
||||
|
||||
logger('accounts: ' . print_r($accounts,true),LOGGER_DATA);
|
||||
logger('accounts: '.print_r($accounts,true),LOGGER_DATA);
|
||||
|
||||
$r = q("SELECT COUNT(id) as `count` FROM `register`");
|
||||
$pending = $r[0]['count'];
|
||||
|
|
@ -433,7 +442,7 @@ function admin_page_summary(&$a) {
|
|||
|
||||
// We can do better, but this is a quick queue status
|
||||
|
||||
$queues = array( 'label' => t('Message queues'), 'deliverq' => $deliverq, 'queue' => $queue );
|
||||
$queues = array('label' => t('Message queues'), 'deliverq' => $deliverq, 'queue' => $queue);
|
||||
|
||||
|
||||
$t = get_markup_template("admin_summary.tpl");
|
||||
|
|
@ -441,15 +450,15 @@ function admin_page_summary(&$a) {
|
|||
'$title' => t('Administration'),
|
||||
'$page' => t('Summary'),
|
||||
'$queues' => $queues,
|
||||
'$users' => array( t('Registered users'), $users),
|
||||
'$users' => array(t('Registered users'), $users),
|
||||
'$accounts' => $accounts,
|
||||
'$pending' => array( t('Pending registrations'), $pending),
|
||||
'$version' => array( t('Version'), FRIENDICA_VERSION),
|
||||
'$pending' => array(t('Pending registrations'), $pending),
|
||||
'$version' => array(t('Version'), FRIENDICA_VERSION),
|
||||
'$baseurl' => $a->get_baseurl(),
|
||||
'$platform' => FRIENDICA_PLATFORM,
|
||||
'$codename' => FRIENDICA_CODENAME,
|
||||
'$build' => get_config('system','build'),
|
||||
'$plugins' => array( t('Active plugins'), $a->plugins )
|
||||
'$plugins' => array(t('Active plugins'), $a->plugins)
|
||||
));
|
||||
}
|
||||
|
||||
|
|
@ -473,7 +482,7 @@ function admin_page_site_post(&$a) {
|
|||
$parsed = @parse_url($new_url);
|
||||
if(!$parsed || (!x($parsed,'host') || !x($parsed,'scheme'))) {
|
||||
notice(t("Can not parse base url. Must have at least <scheme>://<domain>"));
|
||||
goaway($a->get_baseurl(true) . '/admin/site' );
|
||||
goaway('admin/site');
|
||||
}
|
||||
|
||||
/* steps:
|
||||
|
|
@ -483,6 +492,10 @@ function admin_page_site_post(&$a) {
|
|||
|
||||
$old_url = $a->get_baseurl(true);
|
||||
|
||||
// Generate host names for relocation the addresses in the format user@address.tld
|
||||
$new_host = str_replace("http://", "@", normalise_link($new_url));
|
||||
$old_host = str_replace("http://", "@", normalise_link($old_url));
|
||||
|
||||
function update_table($table_name, $fields, $old_url, $new_url) {
|
||||
global $db, $a;
|
||||
|
||||
|
|
@ -501,17 +514,22 @@ function admin_page_site_post(&$a) {
|
|||
$q = sprintf("UPDATE %s SET %s;", $table_name, $upds);
|
||||
$r = q($q);
|
||||
if(!$r) {
|
||||
notice( "Failed updating '$table_name': " . $db->error );
|
||||
goaway($a->get_baseurl(true) . '/admin/site' );
|
||||
notice("Failed updating '$table_name': ".$db->error);
|
||||
goaway('admin/site');
|
||||
}
|
||||
}
|
||||
|
||||
// update tables
|
||||
// update profile links in the format "http://server.tld"
|
||||
update_table("profile", array('photo', 'thumb'), $old_url, $new_url);
|
||||
update_table("term", array('url'), $old_url, $new_url);
|
||||
update_table("contact", array('photo','thumb','micro','url','nurl','request','notify','poll','confirm','poco'), $old_url, $new_url);
|
||||
update_table("gcontact", array('photo','url','nurl','server_url'), $old_url, $new_url);
|
||||
update_table("item", array('owner-link','owner-avatar','author-name','author-link','author-avatar','body','plink','tag'), $old_url, $new_url);
|
||||
update_table("contact", array('photo','thumb','micro','url','nurl','alias','request','notify','poll','confirm','poco', 'avatar'), $old_url, $new_url);
|
||||
update_table("gcontact", array('url','nurl','photo','server_url','notify','alias'), $old_url, $new_url);
|
||||
update_table("item", array('owner-link','owner-avatar','author-link','author-avatar','body','plink','tag'), $old_url, $new_url);
|
||||
|
||||
// update profile addresses in the format "user@server.tld"
|
||||
update_table("contact", array('addr'), $old_host, $new_host);
|
||||
update_table("gcontact", array('connect','addr'), $old_host, $new_host);
|
||||
|
||||
// update config
|
||||
$a->set_baseurl($new_url);
|
||||
|
|
@ -526,7 +544,7 @@ function admin_page_site_post(&$a) {
|
|||
|
||||
info("Relocation started. Could take a while to complete.");
|
||||
|
||||
goaway($a->get_baseurl(true) . '/admin/site' );
|
||||
goaway('admin/site');
|
||||
}
|
||||
// end relocate
|
||||
|
||||
|
|
@ -589,6 +607,7 @@ function admin_page_site_post(&$a) {
|
|||
$dfrn_only = ((x($_POST,'dfrn_only')) ? True : False);
|
||||
$ostatus_disabled = !((x($_POST,'ostatus_disabled')) ? True : False);
|
||||
$ostatus_poll_interval = ((x($_POST,'ostatus_poll_interval')) ? intval(trim($_POST['ostatus_poll_interval'])) : 0);
|
||||
$ostatus_full_threads = ((x($_POST,'ostatus_full_threads')) ? True : False);
|
||||
$diaspora_enabled = ((x($_POST,'diaspora_enabled')) ? True : False);
|
||||
$ssl_policy = ((x($_POST,'ssl_policy')) ? intval($_POST['ssl_policy']) : 0);
|
||||
$force_ssl = ((x($_POST,'force_ssl')) ? True : False);
|
||||
|
|
@ -609,6 +628,9 @@ function admin_page_site_post(&$a) {
|
|||
$only_tag_search = ((x($_POST,'only_tag_search')) ? True : False);
|
||||
$rino = ((x($_POST,'rino')) ? intval($_POST['rino']) : 0);
|
||||
$embedly = ((x($_POST,'embedly')) ? notags(trim($_POST['embedly'])) : '');
|
||||
$worker = ((x($_POST,'worker')) ? True : False);
|
||||
$worker_queues = ((x($_POST,'worker_queues')) ? intval($_POST['worker_queues']) : 4);
|
||||
$worker_dont_fork = ((x($_POST,'worker_dont_fork')) ? True : False);
|
||||
|
||||
if($a->get_path() != "")
|
||||
$diaspora_enabled = false;
|
||||
|
|
@ -695,12 +717,12 @@ function admin_page_site_post(&$a) {
|
|||
set_config('system','language', $language);
|
||||
set_config('system','theme', $theme);
|
||||
|
||||
if( $theme_mobile === '---' ) {
|
||||
if($theme_mobile === '---') {
|
||||
del_config('system','mobile-theme');
|
||||
} else {
|
||||
set_config('system','mobile-theme', $theme_mobile);
|
||||
}
|
||||
if( $singleuser === '---' ) {
|
||||
if($singleuser === '---') {
|
||||
del_config('system','singleuser');
|
||||
} else {
|
||||
set_config('system','singleuser', $singleuser);
|
||||
|
|
@ -737,6 +759,7 @@ function admin_page_site_post(&$a) {
|
|||
set_config('system','dfrn_only', $dfrn_only);
|
||||
set_config('system','ostatus_disabled', $ostatus_disabled);
|
||||
set_config('system','ostatus_poll_interval', $ostatus_poll_interval);
|
||||
set_config('system','ostatus_full_threads', $ostatus_full_threads);
|
||||
set_config('system','diaspora_enabled', $diaspora_enabled);
|
||||
|
||||
set_config('config','private_addons', $private_addons);
|
||||
|
|
@ -754,7 +777,9 @@ function admin_page_site_post(&$a) {
|
|||
set_config('system','proxy_disabled', $proxy_disabled);
|
||||
set_config('system','old_pager', $old_pager);
|
||||
set_config('system','only_tag_search', $only_tag_search);
|
||||
|
||||
set_config('system','worker', $worker);
|
||||
set_config('system','worker_queues', $worker_queues);
|
||||
set_config('system','worker_dont_fork', $worker_dont_fork);
|
||||
|
||||
if($rino==2 and !function_exists('mcrypt_create_iv')) {
|
||||
notice(t("RINO2 needs mcrypt php extension to work."));
|
||||
|
|
@ -765,8 +790,8 @@ function admin_page_site_post(&$a) {
|
|||
set_config('system','embedly', $embedly);
|
||||
|
||||
|
||||
info( t('Site settings updated.') . EOL);
|
||||
goaway($a->get_baseurl(true) . '/admin/site' );
|
||||
info(t('Site settings updated.').EOL);
|
||||
goaway('admin/site');
|
||||
return; // NOTREACHED
|
||||
|
||||
}
|
||||
|
|
@ -797,12 +822,12 @@ function admin_page_site(&$a) {
|
|||
$files = glob('view/theme/*');
|
||||
if($files) {
|
||||
foreach($files as $file) {
|
||||
if(intval(file_exists($file . '/unsupported')))
|
||||
if(intval(file_exists($file.'/unsupported')))
|
||||
continue;
|
||||
|
||||
$f = basename($file);
|
||||
$theme_name = ((file_exists($file . '/experimental')) ? sprintf("%s - \x28Experimental\x29", $f) : $f);
|
||||
if(file_exists($file . '/mobile')) {
|
||||
$theme_name = ((file_exists($file.'/experimental')) ? sprintf("%s - \x28Experimental\x29", $f) : $f);
|
||||
if(file_exists($file.'/mobile')) {
|
||||
$theme_choices_mobile[$f] = $theme_name;
|
||||
} else {
|
||||
$theme_choices[$f] = $theme_name;
|
||||
|
|
@ -893,6 +918,7 @@ function admin_page_site(&$a) {
|
|||
'$advanced' => t('Advanced'),
|
||||
'$portable_contacts' => t('Auto Discovered Contact Directory'),
|
||||
'$performance' => t('Performance'),
|
||||
'$worker_title' => t('Worker'),
|
||||
'$relocate'=> t('Relocate - WARNING: advanced function. Could make this server unreachable.'),
|
||||
'$baseurl' => $a->get_baseurl(true),
|
||||
// name, label, value, help string, extra data...
|
||||
|
|
@ -938,6 +964,7 @@ function admin_page_site(&$a) {
|
|||
'$max_author_posts_community_page' => array('max_author_posts_community_page', t("Posts per user on community page"), get_config('system','max_author_posts_community_page'), t("The maximum number of posts per user on the community page. (Not valid for 'Global Community')")),
|
||||
'$ostatus_disabled' => array('ostatus_disabled', t("Enable OStatus support"), !get_config('system','ostatus_disabled'), t("Provide built-in OStatus \x28StatusNet, GNU Social etc.\x29 compatibility. All communications in OStatus are public, so privacy warnings will be occasionally displayed.")),
|
||||
'$ostatus_poll_interval' => array('ostatus_poll_interval', t("OStatus conversation completion interval"), (string) intval(get_config('system','ostatus_poll_interval')), t("How often shall the poller check for new entries in OStatus conversations? This can be a very ressource task."), $ostatus_poll_choices),
|
||||
'$ostatus_full_threads' => array('ostatus_full_threads', t("Only import OStatus threads from our contacts"), get_config('system','ostatus_full_threads'), t("Normally we import every content from our OStatus contacts. With this option we only store threads that are started by a contact that is known on our system.")),
|
||||
'$ostatus_not_able' => t("OStatus support can only be enabled if threading is enabled."),
|
||||
'$diaspora_able' => $diaspora_able,
|
||||
'$diaspora_not_able' => t("Diaspora support can't be enabled because Friendica was installed into a sub directory."),
|
||||
|
|
@ -980,6 +1007,10 @@ function admin_page_site(&$a) {
|
|||
'$rino' => array('rino', t("RINO Encryption"), intval(get_config('system','rino_encrypt')), t("Encryption layer between nodes."), array("Disabled", "RINO1 (deprecated)", "RINO2")),
|
||||
'$embedly' => array('embedly', t("Embedly API key"), get_config('system','embedly'), t("<a href='http://embed.ly'>Embedly</a> is used to fetch additional data for web pages. This is an optional parameter.")),
|
||||
|
||||
'$worker' => array('worker', t("Enable 'worker' background processing"), get_config('system','worker'), t("The worker background processing limits the number of parallel background jobs to a maximum number and respects the system load.")),
|
||||
'$worker_queues' => array('worker_queues', t("Maximum number of parallel workers"), get_config('system','worker_queues'), t("On shared hosters set this to 2. On larger systems, values of 10 are great. Default value is 4.")),
|
||||
'$worker_dont_fork' => array('worker_dont_fork', t("Don't use 'proc_open' with the worker"), get_config('system','worker_dont_fork'), t("Enable this if your system doesn't allow the use of 'proc_open'. This can happen on shared hosters. If this is enabled you should increase the frequency of poller calls in your crontab.")),
|
||||
|
||||
'$form_security_token' => get_form_security_token("admin_site")
|
||||
|
||||
));
|
||||
|
|
@ -1003,12 +1034,12 @@ function admin_page_dbsync(&$a) {
|
|||
$o = '';
|
||||
|
||||
if($a->argc > 3 && intval($a->argv[3]) && $a->argv[2] === 'mark') {
|
||||
set_config('database', 'update_' . intval($a->argv[3]), 'success');
|
||||
set_config('database', 'update_'.intval($a->argv[3]), 'success');
|
||||
$curr = get_config('system','build');
|
||||
if(intval($curr) == intval($a->argv[3]))
|
||||
set_config('system','build',intval($curr) + 1);
|
||||
info( t('Update has been marked successful') . EOL);
|
||||
goaway($a->get_baseurl(true) . '/admin/dbsync');
|
||||
info(t('Update has been marked successful').EOL);
|
||||
goaway('admin/dbsync');
|
||||
}
|
||||
|
||||
if(($a->argc > 2) AND (intval($a->argv[2]) OR ($a->argv[2] === 'check'))) {
|
||||
|
|
@ -1026,7 +1057,7 @@ function admin_page_dbsync(&$a) {
|
|||
|
||||
if($a->argc > 2 && intval($a->argv[2])) {
|
||||
require_once('update.php');
|
||||
$func = 'update_' . intval($a->argv[2]);
|
||||
$func = 'update_'.intval($a->argv[2]);
|
||||
if(function_exists($func)) {
|
||||
$retval = $func();
|
||||
if($retval === UPDATE_FAILED) {
|
||||
|
|
@ -1082,18 +1113,18 @@ function admin_page_dbsync(&$a) {
|
|||
* @param App $a
|
||||
*/
|
||||
function admin_page_users_post(&$a){
|
||||
$pending = ( x($_POST, 'pending') ? $_POST['pending'] : array() );
|
||||
$users = ( x($_POST, 'user') ? $_POST['user'] : array() );
|
||||
$nu_name = ( x($_POST, 'new_user_name') ? $_POST['new_user_name'] : '');
|
||||
$nu_nickname = ( x($_POST, 'new_user_nickname') ? $_POST['new_user_nickname'] : '');
|
||||
$nu_email = ( x($_POST, 'new_user_email') ? $_POST['new_user_email'] : '');
|
||||
$pending = (x($_POST, 'pending') ? $_POST['pending'] : array());
|
||||
$users = (x($_POST, 'user') ? $_POST['user'] : array());
|
||||
$nu_name = (x($_POST, 'new_user_name') ? $_POST['new_user_name'] : '');
|
||||
$nu_nickname = (x($_POST, 'new_user_nickname') ? $_POST['new_user_nickname'] : '');
|
||||
$nu_email = (x($_POST, 'new_user_email') ? $_POST['new_user_email'] : '');
|
||||
|
||||
check_form_security_token_redirectOnErr('/admin/users', 'admin_users');
|
||||
|
||||
if(!($nu_name==="") && !($nu_email==="") && !($nu_nickname==="")) {
|
||||
require_once('include/user.php');
|
||||
|
||||
$result = create_user( array('username'=>$nu_name, 'email'=>$nu_email, 'nickname'=>$nu_nickname, 'verified'=>1) );
|
||||
$result = create_user(array('username'=>$nu_name, 'email'=>$nu_email, 'nickname'=>$nu_nickname, 'verified'=>1));
|
||||
if(! $result['success']) {
|
||||
notice($result['message']);
|
||||
return;
|
||||
|
|
@ -1134,7 +1165,7 @@ function admin_page_users_post(&$a){
|
|||
notification(array(
|
||||
'type' => "SYSTEM_EMAIL",
|
||||
'to_email' => $nu['email'],
|
||||
'subject'=> sprintf( t('Registration details for %s'), $a->config['sitename']),
|
||||
'subject'=> sprintf(t('Registration details for %s'), $a->config['sitename']),
|
||||
'preamble'=> $preamble,
|
||||
'body' => $body));
|
||||
|
||||
|
|
@ -1143,17 +1174,17 @@ function admin_page_users_post(&$a){
|
|||
if(x($_POST,'page_users_block')) {
|
||||
foreach($users as $uid){
|
||||
q("UPDATE `user` SET `blocked`=1-`blocked` WHERE `uid`=%s",
|
||||
intval( $uid )
|
||||
intval($uid)
|
||||
);
|
||||
}
|
||||
notice( sprintf( tt("%s user blocked/unblocked", "%s users blocked/unblocked", count($users)), count($users)) );
|
||||
notice(sprintf(tt("%s user blocked/unblocked", "%s users blocked/unblocked", count($users)), count($users)));
|
||||
}
|
||||
if(x($_POST,'page_users_delete')) {
|
||||
require_once("include/Contact.php");
|
||||
foreach($users as $uid){
|
||||
user_remove($uid);
|
||||
}
|
||||
notice( sprintf( tt("%s user deleted", "%s users deleted", count($users)), count($users)) );
|
||||
notice(sprintf(tt("%s user deleted", "%s users deleted", count($users)), count($users)));
|
||||
}
|
||||
|
||||
if(x($_POST,'page_users_approve')) {
|
||||
|
|
@ -1168,7 +1199,7 @@ function admin_page_users_post(&$a){
|
|||
user_deny($hash);
|
||||
}
|
||||
}
|
||||
goaway($a->get_baseurl(true) . '/admin/users' );
|
||||
goaway('admin/users');
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -1189,8 +1220,8 @@ function admin_page_users(&$a){
|
|||
$uid = $a->argv[3];
|
||||
$user = q("SELECT username, blocked FROM `user` WHERE `uid`=%d", intval($uid));
|
||||
if(count($user)==0) {
|
||||
notice( 'User not found' . EOL);
|
||||
goaway($a->get_baseurl(true) . '/admin/users' );
|
||||
notice('User not found'.EOL);
|
||||
goaway('admin/users');
|
||||
return ''; // NOTREACHED
|
||||
}
|
||||
switch($a->argv[2]){
|
||||
|
|
@ -1200,18 +1231,18 @@ function admin_page_users(&$a){
|
|||
require_once("include/Contact.php");
|
||||
user_remove($uid);
|
||||
|
||||
notice( sprintf(t("User '%s' deleted"), $user[0]['username']) . EOL);
|
||||
notice(sprintf(t("User '%s' deleted"), $user[0]['username']).EOL);
|
||||
}; break;
|
||||
case "block":{
|
||||
check_form_security_token_redirectOnErr('/admin/users', 'admin_users', 't');
|
||||
q("UPDATE `user` SET `blocked`=%d WHERE `uid`=%s",
|
||||
intval( 1-$user[0]['blocked'] ),
|
||||
intval( $uid )
|
||||
intval(1-$user[0]['blocked']),
|
||||
intval($uid)
|
||||
);
|
||||
notice( sprintf( ($user[0]['blocked']?t("User '%s' unblocked"):t("User '%s' blocked")) , $user[0]['username']) . EOL);
|
||||
notice(sprintf(($user[0]['blocked']?t("User '%s' unblocked"):t("User '%s' blocked")) , $user[0]['username']).EOL);
|
||||
}; break;
|
||||
}
|
||||
goaway($a->get_baseurl(true) . '/admin/users' );
|
||||
goaway('admin/users');
|
||||
return ''; // NOTREACHED
|
||||
|
||||
}
|
||||
|
|
@ -1230,7 +1261,7 @@ function admin_page_users(&$a){
|
|||
$a->set_pager_itemspage(100);
|
||||
}
|
||||
|
||||
$users = q("SELECT `user` . * , `contact`.`name` , `contact`.`url` , `contact`.`micro`, `lastitem`.`lastitem_date`, `user`.`account_expired`
|
||||
$users = q("SELECT `user`.* , `contact`.`name` , `contact`.`url` , `contact`.`micro`, `lastitem`.`lastitem_date`, `user`.`account_expired`
|
||||
FROM
|
||||
(SELECT MAX(`item`.`changed`) as `lastitem_date`, `item`.`uid`
|
||||
FROM `item`
|
||||
|
|
@ -1277,7 +1308,7 @@ function admin_page_users(&$a){
|
|||
|
||||
while(count($users)) {
|
||||
$new_user = array();
|
||||
foreach( array_pop($users) as $k => $v) {
|
||||
foreach(array_pop($users) as $k => $v) {
|
||||
$k = str_replace('-','_',$k);
|
||||
$new_user[$k] = $v;
|
||||
}
|
||||
|
|
@ -1303,7 +1334,7 @@ function admin_page_users(&$a){
|
|||
'$select_all' => t('select all'),
|
||||
'$h_pending' => t('User registrations waiting for confirm'),
|
||||
'$h_deleted' => t('User waiting for permanent deletion'),
|
||||
'$th_pending' => array( t('Request date'), t('Name'), t('Email') ),
|
||||
'$th_pending' => array(t('Request date'), t('Name'), t('Email')),
|
||||
'$no_pending' => t('No registrations.'),
|
||||
'$approve' => t('Approve'),
|
||||
'$deny' => t('Deny'),
|
||||
|
|
@ -1315,8 +1346,8 @@ function admin_page_users(&$a){
|
|||
|
||||
'$h_users' => t('Users'),
|
||||
'$h_newuser' => t('New User'),
|
||||
'$th_deleted' => array( t('Name'), t('Email'), t('Register date'), t('Last login'), t('Last item'), t('Deleted since') ),
|
||||
'$th_users' => array( t('Name'), t('Email'), t('Register date'), t('Last login'), t('Last item'), t('Account') ),
|
||||
'$th_deleted' => array(t('Name'), t('Email'), t('Register date'), t('Last login'), t('Last item'), t('Deleted since')),
|
||||
'$th_users' => array(t('Name'), t('Email'), t('Register date'), t('Last login'), t('Last item'), t('Account')),
|
||||
|
||||
'$confirm_delete_multi' => t('Selected users will be deleted!\n\nEverything these users had posted on this site will be permanently deleted!\n\nAre you sure?'),
|
||||
'$confirm_delete' => t('The user {0} will be deleted!\n\nEverything this user has posted on this site will be permanently deleted!\n\nAre you sure?'),
|
||||
|
|
@ -1362,7 +1393,7 @@ function admin_page_plugins(&$a){
|
|||
if($a->argc == 3) {
|
||||
$plugin = $a->argv[2];
|
||||
if(!is_file("addon/$plugin/$plugin.php")) {
|
||||
notice( t("Item not found.") );
|
||||
notice(t("Item not found."));
|
||||
return '';
|
||||
}
|
||||
|
||||
|
|
@ -1374,14 +1405,14 @@ function admin_page_plugins(&$a){
|
|||
if($idx !== false) {
|
||||
unset($a->plugins[$idx]);
|
||||
uninstall_plugin($plugin);
|
||||
info( sprintf( t("Plugin %s disabled."), $plugin ) );
|
||||
info(sprintf(t("Plugin %s disabled."), $plugin));
|
||||
} else {
|
||||
$a->plugins[] = $plugin;
|
||||
install_plugin($plugin);
|
||||
info( sprintf( t("Plugin %s enabled."), $plugin ) );
|
||||
info(sprintf(t("Plugin %s enabled."), $plugin));
|
||||
}
|
||||
set_config("system","addon", implode(", ",$a->plugins));
|
||||
goaway($a->get_baseurl(true) . '/admin/plugins' );
|
||||
goaway('admin/plugins');
|
||||
return ''; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -1480,7 +1511,7 @@ function admin_page_plugins(&$a){
|
|||
'$function' => 'plugins',
|
||||
'$plugins' => $plugins,
|
||||
'$pcount' => count($plugins),
|
||||
'$noplugshint' => sprintf( t('There are currently no plugins available on your node. You can find the official plugin repository at %1$s and might find other interesting plugins in the open plugin registry at %2$s'), 'https://github.com/friendica/friendica-addons', 'http://addons.friendi.ca'),
|
||||
'$noplugshint' => sprintf(t('There are currently no plugins available on your node. You can find the official plugin repository at %1$s and might find other interesting plugins in the open plugin registry at %2$s'), 'https://github.com/friendica/friendica-addons', 'http://addons.friendi.ca'),
|
||||
'$form_security_token' => get_form_security_token("admin_themes"),
|
||||
));
|
||||
}
|
||||
|
|
@ -1575,8 +1606,8 @@ function admin_page_themes(&$a){
|
|||
if($files) {
|
||||
foreach($files as $file) {
|
||||
$f = basename($file);
|
||||
$is_experimental = intval(file_exists($file . '/experimental'));
|
||||
$is_supported = 1-(intval(file_exists($file . '/unsupported')));
|
||||
$is_experimental = intval(file_exists($file.'/experimental'));
|
||||
$is_supported = 1-(intval(file_exists($file.'/unsupported')));
|
||||
$is_allowed = intval(in_array($f,$allowed_themes));
|
||||
|
||||
if($is_allowed OR $is_supported OR get_config("system", "show_unsupported_themes"))
|
||||
|
|
@ -1585,7 +1616,7 @@ function admin_page_themes(&$a){
|
|||
}
|
||||
|
||||
if(! count($themes)) {
|
||||
notice( t('No themes found.'));
|
||||
notice(t('No themes found.'));
|
||||
return '';
|
||||
}
|
||||
|
||||
|
|
@ -1596,7 +1627,7 @@ function admin_page_themes(&$a){
|
|||
if($a->argc == 3) {
|
||||
$theme = $a->argv[2];
|
||||
if(! is_dir("view/theme/$theme")) {
|
||||
notice( t("Item not found.") );
|
||||
notice(t("Item not found."));
|
||||
return '';
|
||||
}
|
||||
|
||||
|
|
@ -1609,15 +1640,15 @@ function admin_page_themes(&$a){
|
|||
$s = rebuild_theme_table($themes);
|
||||
if($result) {
|
||||
install_theme($theme);
|
||||
info( sprintf('Theme %s enabled.',$theme));
|
||||
info(sprintf('Theme %s enabled.',$theme));
|
||||
}
|
||||
else {
|
||||
uninstall_theme($theme);
|
||||
info( sprintf('Theme %s disabled.',$theme));
|
||||
info(sprintf('Theme %s disabled.',$theme));
|
||||
}
|
||||
|
||||
set_config('system','allowed_themes',$s);
|
||||
goaway($a->get_baseurl(true) . '/admin/themes' );
|
||||
goaway('admin/themes');
|
||||
return ''; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -1663,7 +1694,7 @@ function admin_page_themes(&$a){
|
|||
$admin_form = __get_theme_admin_form($a, $theme);
|
||||
}
|
||||
|
||||
$screenshot = array( get_theme_screenshot($theme), t('Screenshot'));
|
||||
$screenshot = array(get_theme_screenshot($theme), t('Screenshot'));
|
||||
if(! stristr($screenshot[0],$theme))
|
||||
$screenshot = null;
|
||||
|
||||
|
|
@ -1754,8 +1785,8 @@ function admin_page_logs_post(&$a) {
|
|||
set_config('system','loglevel', $loglevel);
|
||||
}
|
||||
|
||||
info( t("Log settings updated.") );
|
||||
goaway($a->get_baseurl(true) . '/admin/logs' );
|
||||
info(t("Log settings updated."));
|
||||
goaway('admin/logs');
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -1803,7 +1834,7 @@ function admin_page_logs(&$a){
|
|||
'$form_security_token' => get_form_security_token("admin_logs"),
|
||||
'$phpheader' => t("PHP logging"),
|
||||
'$phphint' => t("To enable logging of PHP errors and warnings you can add the following to the .htconfig.php file of your installation. The filename set in the 'error_log' line is relative to the friendica top-level directory and must be writeable by the web server. The option '1' for 'log_errors' and 'display_errors' is to enable these options, set to '0' to disable them."),
|
||||
'$phplogcode' => "error_reporting(E_ERROR | E_WARNING | E_PARSE );\nini_set('error_log','php.out');\nini_set('log_errors','1');\nini_set('display_errors', '1');",
|
||||
'$phplogcode' => "error_reporting(E_ERROR | E_WARNING | E_PARSE);\nini_set('error_log','php.out');\nini_set('log_errors','1');\nini_set('display_errors', '1');",
|
||||
));
|
||||
}
|
||||
|
||||
|
|
@ -1871,7 +1902,7 @@ function admin_page_features_post(&$a) {
|
|||
|
||||
check_form_security_token_redirectOnErr('/admin/features', 'admin_manage_features');
|
||||
|
||||
logger('postvars: ' . print_r($_POST,true),LOGGER_DATA);
|
||||
logger('postvars: '.print_r($_POST,true),LOGGER_DATA);
|
||||
|
||||
$arr = array();
|
||||
$features = get_features(false);
|
||||
|
|
@ -1879,11 +1910,11 @@ function admin_page_features_post(&$a) {
|
|||
foreach($features as $fname => $fdata) {
|
||||
foreach(array_slice($fdata,1) as $f) {
|
||||
$feature = $f[0];
|
||||
$feature_state = 'feature_' . $feature;
|
||||
$featurelock = 'featurelock_' . $feature;
|
||||
$feature_state = 'feature_'.$feature;
|
||||
$featurelock = 'featurelock_'.$feature;
|
||||
|
||||
if(x($_POST[$feature_state]))
|
||||
$val = intval($_POST['feature_' . $feature]);
|
||||
$val = intval($_POST['feature_'.$feature]);
|
||||
else
|
||||
$val = 0;
|
||||
set_config('feature',$feature,$val);
|
||||
|
|
@ -1895,7 +1926,7 @@ function admin_page_features_post(&$a) {
|
|||
}
|
||||
}
|
||||
|
||||
goaway($a->get_baseurl(true) . '/admin/features' );
|
||||
goaway('admin/features');
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -1929,7 +1960,7 @@ function admin_page_features(&$a) {
|
|||
$set = $f[3];
|
||||
$arr[$fname][1][] = array(
|
||||
array('feature_' .$f[0],$f[1],$set,$f[2],array(t('Off'),t('On'))),
|
||||
array('featurelock_' .$f[0],sprintf( t('Lock feature %s'),$f[1]),(($f[4] !== false) ? "1" : ''),'',array(t('Off'),t('On')))
|
||||
array('featurelock_' .$f[0],sprintf(t('Lock feature %s'),$f[1]),(($f[4] !== false) ? "1" : ''),'',array(t('Off'),t('On')))
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -40,7 +40,7 @@ function common_content(&$a) {
|
|||
$vcard_widget .= replace_macros(get_markup_template("vcard-widget.tpl"),array(
|
||||
'$name' => htmlentities($c[0]['name']),
|
||||
'$photo' => $c[0]['photo'],
|
||||
'url' => z_root() . '/contacts/' . $cid
|
||||
'url' => 'contacts/' . $cid
|
||||
));
|
||||
|
||||
if(! x($a->page,'aside'))
|
||||
|
|
|
|||
165
mod/contacts.php
165
mod/contacts.php
|
|
@ -44,7 +44,7 @@ function contacts_init(&$a) {
|
|||
$vcard_widget = replace_macros(get_markup_template("vcard-widget.tpl"),array(
|
||||
'$name' => htmlentities($a->data['contact']['name']),
|
||||
'$photo' => $a->data['contact']['photo'],
|
||||
'$url' => ($a->data['contact']['network'] == NETWORK_DFRN) ? z_root()."/redir/".$a->data['contact']['id'] : $a->data['contact']['url'],
|
||||
'$url' => ($a->data['contact']['network'] == NETWORK_DFRN) ? "redir/".$a->data['contact']['id'] : $a->data['contact']['url'],
|
||||
'$addr' => (($a->data['contact']['addr'] != "") ? ($a->data['contact']['addr']) : ""),
|
||||
'$network_name' => $networkname,
|
||||
'$network' => t('Network:'),
|
||||
|
|
@ -129,9 +129,9 @@ function contacts_batch_actions(&$a){
|
|||
}
|
||||
|
||||
if(x($_SESSION,'return_url'))
|
||||
goaway($a->get_baseurl(true) . '/' . $_SESSION['return_url']);
|
||||
goaway('' . $_SESSION['return_url']);
|
||||
else
|
||||
goaway($a->get_baseurl(true) . '/contacts');
|
||||
goaway('contacts');
|
||||
|
||||
}
|
||||
|
||||
|
|
@ -157,7 +157,7 @@ function contacts_post(&$a) {
|
|||
|
||||
if(! count($orig_record)) {
|
||||
notice( t('Could not access contact record.') . EOL);
|
||||
goaway($a->get_baseurl(true) . '/contacts');
|
||||
goaway('contacts');
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -366,19 +366,19 @@ function contacts_content(&$a) {
|
|||
|
||||
if(! count($orig_record)) {
|
||||
notice( t('Could not access contact record.') . EOL);
|
||||
goaway($a->get_baseurl(true) . '/contacts');
|
||||
goaway('contacts');
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
if($cmd === 'update') {
|
||||
_contact_update($contact_id);
|
||||
goaway($a->get_baseurl(true) . '/contacts/' . $contact_id);
|
||||
goaway('contacts/' . $contact_id);
|
||||
// NOTREACHED
|
||||
}
|
||||
|
||||
if($cmd === 'updateprofile') {
|
||||
_contact_update_profile($contact_id);
|
||||
goaway($a->get_baseurl(true) . '/crepair/' . $contact_id);
|
||||
goaway('crepair/' . $contact_id);
|
||||
// NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -389,7 +389,7 @@ function contacts_content(&$a) {
|
|||
info((($blocked) ? t('Contact has been blocked') : t('Contact has been unblocked')).EOL);
|
||||
}
|
||||
|
||||
goaway($a->get_baseurl(true) . '/contacts/' . $contact_id);
|
||||
goaway('contacts/' . $contact_id);
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -400,7 +400,7 @@ function contacts_content(&$a) {
|
|||
info((($readonly) ? t('Contact has been ignored') : t('Contact has been unignored')).EOL);
|
||||
}
|
||||
|
||||
goaway($a->get_baseurl(true) . '/contacts/' . $contact_id);
|
||||
goaway('contacts/' . $contact_id);
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -412,7 +412,7 @@ function contacts_content(&$a) {
|
|||
info((($archived) ? t('Contact has been archived') : t('Contact has been unarchived')).EOL);
|
||||
}
|
||||
|
||||
goaway($a->get_baseurl(true) . '/contacts/' . $contact_id);
|
||||
goaway('contacts/' . $contact_id);
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -447,17 +447,17 @@ function contacts_content(&$a) {
|
|||
// Now check how the user responded to the confirmation query
|
||||
if($_REQUEST['canceled']) {
|
||||
if(x($_SESSION,'return_url'))
|
||||
goaway($a->get_baseurl(true) . '/' . $_SESSION['return_url']);
|
||||
goaway('' . $_SESSION['return_url']);
|
||||
else
|
||||
goaway($a->get_baseurl(true) . '/contacts');
|
||||
goaway('contacts');
|
||||
}
|
||||
|
||||
_contact_drop($contact_id, $orig_record[0]);
|
||||
info( t('Contact has been removed.') . EOL );
|
||||
if(x($_SESSION,'return_url'))
|
||||
goaway($a->get_baseurl(true) . '/' . $_SESSION['return_url']);
|
||||
goaway('' . $_SESSION['return_url']);
|
||||
else
|
||||
goaway($a->get_baseurl(true) . '/contacts');
|
||||
goaway('contacts');
|
||||
return; // NOTREACHED
|
||||
}
|
||||
if($cmd === 'posts') {
|
||||
|
|
@ -565,6 +565,9 @@ function contacts_content(&$a) {
|
|||
($contact['rel'] == CONTACT_IS_FOLLOWER))
|
||||
$follow = $a->get_baseurl(true)."/follow?url=".urlencode($contact["url"]);
|
||||
|
||||
// Load contactact related actions like hide, suggest, delete and others
|
||||
$contact_actions = contact_actions($contact);
|
||||
|
||||
|
||||
$o .= replace_macros($tpl, array(
|
||||
//'$header' => t('Contact Editor'),
|
||||
|
|
@ -575,7 +578,7 @@ function contacts_content(&$a) {
|
|||
'$lbl_info1' => t('Contact Information / Notes'),
|
||||
'$infedit' => t('Edit contact notes'),
|
||||
'$common_text' => $common_text,
|
||||
'$common_link' => $a->get_baseurl(true) . '/common/loc/' . local_user() . '/' . $contact['id'],
|
||||
'$common_link' => 'common/loc/' . local_user() . '/' . $contact['id'],
|
||||
'$all_friends' => $all_friends,
|
||||
'$relation_text' => $relation_text,
|
||||
'$visit' => sprintf( t('Visit %s\'s profile [%s]'),$contact['name'],$contact['url']),
|
||||
|
|
@ -584,7 +587,7 @@ function contacts_content(&$a) {
|
|||
'$lblcrepair' => t("Repair URL settings"),
|
||||
'$lblrecent' => t('View conversations'),
|
||||
'$lblsuggest' => $lblsuggest,
|
||||
'$delete' => t('Delete contact'),
|
||||
//'$delete' => t('Delete contact'),
|
||||
'$nettype' => $nettype,
|
||||
'$poll_interval' => $poll_interval,
|
||||
'$poll_enabled' => $poll_enabled,
|
||||
|
|
@ -622,7 +625,11 @@ function contacts_content(&$a) {
|
|||
'$about' => bbcode($contact["about"], false, false),
|
||||
'$about_label' => t("About:"),
|
||||
'$keywords' => $contact["keywords"],
|
||||
'$keywords_label' => t("Tags:")
|
||||
'$keywords_label' => t("Tags:"),
|
||||
'$contact_action_button' => t("Actions"),
|
||||
'$contact_actions' => $contact_actions,
|
||||
'$contact_status' => t("Status"),
|
||||
'$contact_settings_label' => t('Contact Settings'),
|
||||
|
||||
));
|
||||
|
||||
|
|
@ -668,7 +675,7 @@ function contacts_content(&$a) {
|
|||
$tabs = array(
|
||||
array(
|
||||
'label' => t('Suggestions'),
|
||||
'url' => $a->get_baseurl(true) . '/suggest',
|
||||
'url' => 'suggest',
|
||||
'sel' => '',
|
||||
'title' => t('Suggest potential friends'),
|
||||
'id' => 'suggestions-tab',
|
||||
|
|
@ -676,7 +683,7 @@ function contacts_content(&$a) {
|
|||
),
|
||||
array(
|
||||
'label' => t('All Contacts'),
|
||||
'url' => $a->get_baseurl(true) . '/contacts/all',
|
||||
'url' => 'contacts/all',
|
||||
'sel' => ($all) ? 'active' : '',
|
||||
'title' => t('Show all contacts'),
|
||||
'id' => 'showall-tab',
|
||||
|
|
@ -684,7 +691,7 @@ function contacts_content(&$a) {
|
|||
),
|
||||
array(
|
||||
'label' => t('Unblocked'),
|
||||
'url' => $a->get_baseurl(true) . '/contacts',
|
||||
'url' => 'contacts',
|
||||
'sel' => ((! $all) && (! $blocked) && (! $hidden) && (! $search) && (! $nets) && (! $ignored) && (! $archived)) ? 'active' : '',
|
||||
'title' => t('Only show unblocked contacts'),
|
||||
'id' => 'showunblocked-tab',
|
||||
|
|
@ -693,7 +700,7 @@ function contacts_content(&$a) {
|
|||
|
||||
array(
|
||||
'label' => t('Blocked'),
|
||||
'url' => $a->get_baseurl(true) . '/contacts/blocked',
|
||||
'url' => 'contacts/blocked',
|
||||
'sel' => ($blocked) ? 'active' : '',
|
||||
'title' => t('Only show blocked contacts'),
|
||||
'id' => 'showblocked-tab',
|
||||
|
|
@ -702,7 +709,7 @@ function contacts_content(&$a) {
|
|||
|
||||
array(
|
||||
'label' => t('Ignored'),
|
||||
'url' => $a->get_baseurl(true) . '/contacts/ignored',
|
||||
'url' => 'contacts/ignored',
|
||||
'sel' => ($ignored) ? 'active' : '',
|
||||
'title' => t('Only show ignored contacts'),
|
||||
'id' => 'showignored-tab',
|
||||
|
|
@ -711,7 +718,7 @@ function contacts_content(&$a) {
|
|||
|
||||
array(
|
||||
'label' => t('Archived'),
|
||||
'url' => $a->get_baseurl(true) . '/contacts/archived',
|
||||
'url' => 'contacts/archived',
|
||||
'sel' => ($archived) ? 'active' : '',
|
||||
'title' => t('Only show archived contacts'),
|
||||
'id' => 'showarchived-tab',
|
||||
|
|
@ -720,7 +727,7 @@ function contacts_content(&$a) {
|
|||
|
||||
array(
|
||||
'label' => t('Hidden'),
|
||||
'url' => $a->get_baseurl(true) . '/contacts/hidden',
|
||||
'url' => 'contacts/hidden',
|
||||
'sel' => ($hidden) ? 'active' : '',
|
||||
'title' => t('Only show hidden contacts'),
|
||||
'id' => 'showhidden-tab',
|
||||
|
|
@ -800,6 +807,17 @@ function contacts_content(&$a) {
|
|||
return $o;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief List of pages for the Contact TabBar
|
||||
*
|
||||
* Available Pages are 'Status', 'Profile', 'Contacts' and 'Common Friends'
|
||||
*
|
||||
* @param app $a
|
||||
* @param int $contact_id The ID of the contact
|
||||
* @param int $active_tab 1 if tab should be marked as active
|
||||
*
|
||||
* @return array with with contact TabBar data
|
||||
*/
|
||||
function contacts_tab($a, $contact_id, $active_tab) {
|
||||
// tabs
|
||||
$tabs = array(
|
||||
|
|
@ -821,6 +839,7 @@ function contacts_tab($a, $contact_id, $active_tab) {
|
|||
)
|
||||
);
|
||||
|
||||
// Show this tab only if there is visible friend list
|
||||
$x = count_all_friends(local_user(), $contact_id);
|
||||
if ($x)
|
||||
$tabs[] = array('label'=>t('Contacts'),
|
||||
|
|
@ -830,6 +849,7 @@ function contacts_tab($a, $contact_id, $active_tab) {
|
|||
'id' => 'allfriends-tab',
|
||||
'accesskey' => 't');
|
||||
|
||||
// Show this tab only if there is visible common friend list
|
||||
$common = count_common_friends(local_user(),$contact_id);
|
||||
if ($common)
|
||||
$tabs[] = array('label'=>t('Common Friends'),
|
||||
|
|
@ -839,35 +859,13 @@ function contacts_tab($a, $contact_id, $active_tab) {
|
|||
'id' => 'common-loc-tab',
|
||||
'accesskey' => 'd');
|
||||
|
||||
$tabs[] = array('label' => t('Repair'),
|
||||
'url' => $a->get_baseurl(true) . '/crepair/' . $contact_id,
|
||||
$tabs[] = array('label' => t('Advanced'),
|
||||
'url' => 'crepair/' . $contact_id,
|
||||
'sel' => (($active_tab == 5)?'active':''),
|
||||
'title' => t('Advanced Contact Settings'),
|
||||
'id' => 'repair-tab',
|
||||
'id' => 'advanced-tab',
|
||||
'accesskey' => 'r');
|
||||
|
||||
|
||||
$tabs[] = array('label' => (($contact['blocked']) ? t('Unblock') : t('Block') ),
|
||||
'url' => $a->get_baseurl(true) . '/contacts/' . $contact_id . '/block',
|
||||
'sel' => '',
|
||||
'title' => t('Toggle Blocked status'),
|
||||
'id' => 'toggle-block-tab',
|
||||
'accesskey' => 'b');
|
||||
|
||||
$tabs[] = array('label' => (($contact['readonly']) ? t('Unignore') : t('Ignore') ),
|
||||
'url' => $a->get_baseurl(true) . '/contacts/' . $contact_id . '/ignore',
|
||||
'sel' => '',
|
||||
'title' => t('Toggle Ignored status'),
|
||||
'id' => 'toggle-ignore-tab',
|
||||
'accesskey' => 'i');
|
||||
|
||||
$tabs[] = array('label' => (($contact['archive']) ? t('Unarchive') : t('Archive') ),
|
||||
'url' => $a->get_baseurl(true) . '/contacts/' . $contact_id . '/archive',
|
||||
'sel' => '',
|
||||
'title' => t('Toggle Archive status'),
|
||||
'id' => 'toggle-archive-tab',
|
||||
'accesskey' => 'v');
|
||||
|
||||
$tab_tpl = get_markup_template('common_tabs.tpl');
|
||||
$tab_str = replace_macros($tab_tpl, array('$tabs' => $tabs));
|
||||
|
||||
|
|
@ -954,3 +952,72 @@ function _contact_detail_for_template($rr){
|
|||
);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Gives a array with actions which can performed to a given contact
|
||||
*
|
||||
* This includes actions like e.g. 'block', 'hide', 'archive', 'delete' and others
|
||||
*
|
||||
* @param array $contact Data about the Contact
|
||||
* @return array with contact related actions
|
||||
*/
|
||||
function contact_actions($contact) {
|
||||
|
||||
$poll_enabled = in_array($contact['network'], array(NETWORK_DFRN, NETWORK_OSTATUS, NETWORK_FEED, NETWORK_MAIL, NETWORK_MAIL2));
|
||||
$contact_action = array();
|
||||
|
||||
// Provide friend suggestion only for Friendica contacts
|
||||
if($contact['network'] === NETWORK_DFRN) {
|
||||
$contact_actions['suggest'] = array(
|
||||
'label' => t('Suggest friends'),
|
||||
'url' => 'fsuggest/' . $contact['id'],
|
||||
'title' => '',
|
||||
'sel' => '',
|
||||
'id' => 'suggest',
|
||||
);
|
||||
}
|
||||
|
||||
if($poll_enabled) {
|
||||
$contact_actions['update'] = array(
|
||||
'label' => t('Update now'),
|
||||
'url' => 'contacts/' . $contact['id'] . '/update',
|
||||
'title' => '',
|
||||
'sel' => '',
|
||||
'id' => 'update',
|
||||
);
|
||||
}
|
||||
|
||||
$contact_actions['block'] = array(
|
||||
'label' => (intval($contact['blocked']) ? t('Unblock') : t('Block') ),
|
||||
'url' => 'contacts/' . $contact['id'] . '/block',
|
||||
'title' => t('Toggle Blocked status'),
|
||||
'sel' => (intval($contact['blocked']) ? 'active' : ''),
|
||||
'id' => 'toggle-block',
|
||||
);
|
||||
|
||||
$contact_actions['ignore'] = array(
|
||||
'label' => (intval($contact['readonly']) ? t('Unignore') : t('Ignore') ),
|
||||
'url' => 'contacts/' . $contact['id'] . '/ignore',
|
||||
'title' => t('Toggle Ignored status'),
|
||||
'sel' => (intval($contact['readonly']) ? 'active' : ''),
|
||||
'id' => 'toggle-ignore',
|
||||
);
|
||||
|
||||
$contact_actions['archive'] = array(
|
||||
'label' => (intval($contact['archive']) ? t('Unarchive') : t('Archive') ),
|
||||
'url' => 'contacts/' . $contact['id'] . '/archive',
|
||||
'title' => t('Toggle Archive status'),
|
||||
'sel' => (intval($contact['archive']) ? 'active' : ''),
|
||||
'id' => 'toggle-archive',
|
||||
);
|
||||
|
||||
$contact_actions['delete'] = array(
|
||||
'label' => t('Delete'),
|
||||
'url' => 'contacts/' . $contact['id'] . '/drop',
|
||||
'title' => t('Delete contact'),
|
||||
'sel' => '',
|
||||
'id' => 'delete',
|
||||
);
|
||||
|
||||
return $contact_actions;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -420,7 +420,7 @@ function render_content(&$a, $items, $mode, $update, $preview = false) {
|
|||
if(($normalised != 'mailbox') && (x($a->contacts[$normalised])))
|
||||
$profile_avatar = $a->contacts[$normalised]['thumb'];
|
||||
else
|
||||
$profile_avatar = ((strlen($item['author-avatar'])) ? $a->get_cached_avatar_image($item['author-avatar']) : $item['thumb']);
|
||||
$profile_avatar = $a->remove_baseurl(((strlen($item['author-avatar'])) ? $item['author-avatar'] : $item['thumb']));
|
||||
|
||||
$locate = array('location' => $item['location'], 'coord' => $item['coord'], 'html' => '');
|
||||
call_hooks('render_location',$locate);
|
||||
|
|
@ -615,7 +615,7 @@ function render_content(&$a, $items, $mode, $update, $preview = false) {
|
|||
$comment_lastcollapsed = true;
|
||||
}
|
||||
|
||||
$redirect_url = $a->get_baseurl($ssl_state) . '/redir/' . $item['cid'] ;
|
||||
$redirect_url = 'redir/' . $item['cid'] ;
|
||||
|
||||
$lock = ((($item['private'] == 1) || (($item['uid'] == local_user()) && (strlen($item['allow_cid']) || strlen($item['allow_gid'])
|
||||
|| strlen($item['deny_cid']) || strlen($item['deny_gid']))))
|
||||
|
|
@ -791,7 +791,7 @@ function render_content(&$a, $items, $mode, $update, $preview = false) {
|
|||
if(($normalised != 'mailbox') && (x($a->contacts,$normalised)))
|
||||
$profile_avatar = $a->contacts[$normalised]['thumb'];
|
||||
else
|
||||
$profile_avatar = (((strlen($item['author-avatar'])) && $diff_author) ? $item['author-avatar'] : $a->get_cached_avatar_image($thumb));
|
||||
$profile_avatar = $a->remove_baseurl(((strlen($item['author-avatar']) && $diff_author) ? $item['author-avatar'] : $thumb));
|
||||
|
||||
$like = ((x($alike,$item['uri'])) ? format_like($alike[$item['uri']],$alike[$item['uri'] . '-l'],'like',$item['uri']) : '');
|
||||
$dislike = ((x($dlike,$item['uri'])) ? format_like($dlike[$item['uri']],$dlike[$item['uri'] . '-l'],'dislike',$item['uri']) : '');
|
||||
|
|
|
|||
|
|
@ -427,8 +427,8 @@ function dfrn_confirm_post(&$a,$handsfree = null) {
|
|||
|
||||
if(($contact) && ($contact['network'] === NETWORK_DIASPORA)) {
|
||||
require_once('include/diaspora.php');
|
||||
$ret = diaspora_share($user[0],$r[0]);
|
||||
logger('mod_follow: diaspora_share returns: ' . $ret);
|
||||
$ret = diaspora::send_share($user[0],$r[0]);
|
||||
logger('share returns: ' . $ret);
|
||||
}
|
||||
|
||||
// Send a new friend post if we are allowed to...
|
||||
|
|
@ -448,6 +448,7 @@ function dfrn_confirm_post(&$a,$handsfree = null) {
|
|||
if(count($self)) {
|
||||
|
||||
$arr = array();
|
||||
$arr['guid'] = get_guid(32);
|
||||
$arr['uri'] = $arr['parent-uri'] = item_new_uri($a->get_hostname(), $uid);
|
||||
$arr['uid'] = $uid;
|
||||
$arr['contact-id'] = $self[0]['id'];
|
||||
|
|
@ -466,7 +467,7 @@ function dfrn_confirm_post(&$a,$handsfree = null) {
|
|||
$BPhoto = '[url=' . $contact['url'] . ']' . '[img]' . $contact['thumb'] . '[/img][/url]';
|
||||
|
||||
$arr['verb'] = ACTIVITY_FRIEND;
|
||||
$arr['object-type'] = ACTIVITY_OBJ_PERSON;
|
||||
$arr['object-type'] = ACTIVITY_OBJ_PERSON;
|
||||
$arr['body'] = sprintf( t('%1$s is now friends with %2$s'), $A, $B)."\n\n\n".$BPhoto;
|
||||
|
||||
$arr['object'] = '<object><type>' . ACTIVITY_OBJ_PERSON . '</type><title>' . $contact['name'] . '</title>'
|
||||
|
|
@ -489,13 +490,10 @@ function dfrn_confirm_post(&$a,$handsfree = null) {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
$g = q("select def_gid from user where uid = %d limit 1",
|
||||
intval($uid)
|
||||
);
|
||||
if($contact && $g && intval($g[0]['def_gid'])) {
|
||||
$def_gid = get_default_group($uid, $contact["network"]);
|
||||
if($contact && intval($def_gid)) {
|
||||
require_once('include/group.php');
|
||||
group_add_member($uid,'',$contact['id'],$g[0]['def_gid']);
|
||||
group_add_member($uid, '', $contact['id'], $def_gid);
|
||||
}
|
||||
|
||||
// Let's send our user to the contact editor in case they want to
|
||||
|
|
|
|||
|
|
@ -42,8 +42,10 @@ function dfrn_request_init(&$a) {
|
|||
if(! function_exists('dfrn_request_post')) {
|
||||
function dfrn_request_post(&$a) {
|
||||
|
||||
if(($a->argc != 2) || (! count($a->profile)))
|
||||
if(($a->argc != 2) || (! count($a->profile))) {
|
||||
logger('Wrong count of argc or profiles: argc=' . $a->argc . ',profile()=' . count($a->profile));
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
if(x($_POST, 'cancel')) {
|
||||
|
|
@ -172,18 +174,16 @@ function dfrn_request_post(&$a) {
|
|||
info( t("Introduction complete.") . EOL);
|
||||
}
|
||||
|
||||
$r = q("select id from contact where uid = %d and url = '%s' and `site-pubkey` = '%s' limit 1",
|
||||
$r = q("SELECT `id`, `network` FROM `contact` WHERE `uid` = %d AND `url` = '%s' AND `site-pubkey` = '%s' LIMIT 1",
|
||||
intval(local_user()),
|
||||
dbesc($dfrn_url),
|
||||
$parms['key'] // this was already escaped
|
||||
);
|
||||
if(count($r)) {
|
||||
$g = q("select def_gid from user where uid = %d limit 1",
|
||||
intval(local_user())
|
||||
);
|
||||
if($g && intval($g[0]['def_gid'])) {
|
||||
$def_gid = get_default_group(local_user(), $r[0]["network"]);
|
||||
if(intval($def_gid)) {
|
||||
require_once('include/group.php');
|
||||
group_add_member(local_user(),'',$r[0]['id'],$g[0]['def_gid']);
|
||||
group_add_member(local_user(), '', $r[0]['id'], $def_gid);
|
||||
}
|
||||
$forwardurl = $a->get_baseurl()."/contacts/".$r[0]['id'];
|
||||
} else
|
||||
|
|
@ -386,19 +386,17 @@ function dfrn_request_post(&$a) {
|
|||
intval($rel)
|
||||
);
|
||||
|
||||
$r = q("select id from contact where poll = '%s' and uid = %d limit 1",
|
||||
$r = q("SELECT `id`, `network` FROM `contact` WHERE `poll` = '%s' AND `uid` = %d LIMIT 1",
|
||||
dbesc($poll),
|
||||
intval($uid)
|
||||
);
|
||||
if(count($r)) {
|
||||
$contact_id = $r[0]['id'];
|
||||
|
||||
$g = q("select def_gid from user where uid = %d limit 1",
|
||||
intval($uid)
|
||||
);
|
||||
if($g && intval($g[0]['def_gid'])) {
|
||||
$def_gid = get_default_group($uid, $r[0]["network"]);
|
||||
if (intval($def_gid)) {
|
||||
require_once('include/group.php');
|
||||
group_add_member($uid,'',$contact_id,$g[0]['def_gid']);
|
||||
group_add_member($uid, '', $contact_id, $def_gid);
|
||||
}
|
||||
|
||||
$photo = avatar_img($addr);
|
||||
|
|
@ -461,7 +459,7 @@ function dfrn_request_post(&$a) {
|
|||
$network = NETWORK_DFRN;
|
||||
}
|
||||
|
||||
logger('dfrn_request: url: ' . $url);
|
||||
logger('dfrn_request: url: ' . $url . ',network=' . $network, LOGGER_DEBUG);
|
||||
|
||||
if($network === NETWORK_DFRN) {
|
||||
$ret = q("SELECT * FROM `contact` WHERE `uid` = %d AND `url` = '%s' AND `self` = 0 LIMIT 1",
|
||||
|
|
@ -825,7 +823,7 @@ function dfrn_request_content(&$a) {
|
|||
else
|
||||
$tpl = get_markup_template('auto_request.tpl');
|
||||
|
||||
$page_desc .= t("Please enter your 'Identity Address' from one of the following supported communications networks:");
|
||||
$page_desc = t("Please enter your 'Identity Address' from one of the following supported communications networks:");
|
||||
|
||||
// see if we are allowed to have NETWORK_MAIL2 contacts
|
||||
|
||||
|
|
@ -850,7 +848,7 @@ function dfrn_request_content(&$a) {
|
|||
get_server()
|
||||
);
|
||||
|
||||
$o .= replace_macros($tpl,array(
|
||||
$o = replace_macros($tpl,array(
|
||||
'$header' => t('Friend/Connection Request'),
|
||||
'$desc' => t('Examples: jojo@demo.friendica.com, http://demo.friendica.com/profile/jojo, testuser@identi.ca'),
|
||||
'$pls_answer' => t('Please answer the following:'),
|
||||
|
|
|
|||
|
|
@ -104,7 +104,7 @@ function directory_content(&$a) {
|
|||
|
||||
$itemurl = (($rr['addr'] != "") ? $rr['addr'] : $rr['profile_url']);
|
||||
|
||||
$profile_link = z_root() . '/profile/' . ((strlen($rr['nickname'])) ? $rr['nickname'] : $rr['profile_uid']);
|
||||
$profile_link = 'profile/' . ((strlen($rr['nickname'])) ? $rr['nickname'] : $rr['profile_uid']);
|
||||
|
||||
$pdesc = (($rr['pdesc']) ? $rr['pdesc'] . '<br />' : '');
|
||||
|
||||
|
|
@ -158,14 +158,14 @@ function directory_content(&$a) {
|
|||
else {
|
||||
$location_e = $location;
|
||||
}
|
||||
|
||||
|
||||
$photo_menu = array(array(t("View Profile"), zrl($profile_link)));
|
||||
|
||||
$entry = array(
|
||||
'id' => $rr['id'],
|
||||
'url' => $profile_link,
|
||||
'itemurl' => $itemurl,
|
||||
'thumb' => proxy_url($a->get_cached_avatar_image($rr[$photo]), false, PROXY_SIZE_THUMB),
|
||||
'thumb' => proxy_url($rr[$photo], false, PROXY_SIZE_THUMB),
|
||||
'img_hover' => $rr['name'],
|
||||
'name' => $rr['name'],
|
||||
'details' => $details,
|
||||
|
|
|
|||
122
mod/display.php
122
mod/display.php
|
|
@ -17,7 +17,7 @@ function display_init(&$a) {
|
|||
// Does the local user have this item?
|
||||
if (local_user()) {
|
||||
$r = q("SELECT `id`, `parent`, `author-name`, `author-link`, `author-avatar`, `network`, `body`, `uid` FROM `item`
|
||||
WHERE `item`.`visible` = 1 AND `item`.`deleted` = 0 and `item`.`moderated` = 0
|
||||
WHERE `item`.`visible` AND NOT `item`.`deleted` AND NOT `item`.`moderated`
|
||||
AND `guid` = '%s' AND `uid` = %d", dbesc($a->argv[1]), local_user());
|
||||
if (count($r)) {
|
||||
$nick = $a->user["nickname"];
|
||||
|
|
@ -30,12 +30,12 @@ function display_init(&$a) {
|
|||
$r = q("SELECT `user`.`nickname`, `item`.`id`, `item`.`parent`, `item`.`author-name`,
|
||||
`item`.`author-link`, `item`.`author-avatar`, `item`.`network`, `item`.`uid`, `item`.`body`
|
||||
FROM `item` INNER JOIN `user` ON `user`.`uid` = `item`.`uid`
|
||||
WHERE `item`.`visible` = 1 AND `item`.`deleted` = 0 and `item`.`moderated` = 0
|
||||
WHERE `item`.`visible` AND NOT `item`.`deleted` AND NOT `item`.`moderated`
|
||||
AND `item`.`allow_cid` = '' AND `item`.`allow_gid` = ''
|
||||
AND `item`.`deny_cid` = '' AND `item`.`deny_gid` = ''
|
||||
AND `item`.`private` = 0 AND NOT `user`.`hidewall`
|
||||
AND NOT `item`.`private` AND NOT `user`.`hidewall`
|
||||
AND `item`.`guid` = '%s'", dbesc($a->argv[1]));
|
||||
// AND `item`.`private` = 0 AND `item`.`wall` = 1
|
||||
// AND NOT `item`.`private` AND `item`.`wall`
|
||||
if (count($r)) {
|
||||
$nick = $r[0]["nickname"];
|
||||
$itemuid = $r[0]["uid"];
|
||||
|
|
@ -46,17 +46,17 @@ function display_init(&$a) {
|
|||
if ($nick == "") {
|
||||
$r = q("SELECT `item`.`id`, `item`.`parent`, `item`.`author-name`,
|
||||
`item`.`author-link`, `item`.`author-avatar`, `item`.`network`, `item`.`uid`, `item`.`body`
|
||||
FROM `item` WHERE `item`.`visible` = 1 AND `item`.`deleted` = 0 and `item`.`moderated` = 0
|
||||
FROM `item` WHERE `item`.`visible` AND NOT `item`.`deleted` AND NOT `item`.`moderated`
|
||||
AND `item`.`allow_cid` = '' AND `item`.`allow_gid` = ''
|
||||
AND `item`.`deny_cid` = '' AND `item`.`deny_gid` = ''
|
||||
AND `item`.`private` = 0 AND `item`.`uid` = 0
|
||||
AND NOT `item`.`private` AND `item`.`uid` = 0
|
||||
AND `item`.`guid` = '%s'", dbesc($a->argv[1]));
|
||||
// AND `item`.`private` = 0 AND `item`.`wall` = 1
|
||||
// AND NOT `item`.`private` AND `item`.`wall`
|
||||
}
|
||||
if (count($r)) {
|
||||
if ($r[0]["id"] != $r[0]["parent"])
|
||||
$r = q("SELECT `id`, `author-name`, `author-link`, `author-avatar`, `network`, `body`, `uid` FROM `item`
|
||||
WHERE `item`.`visible` = 1 AND `item`.`deleted` = 0 and `item`.`moderated` = 0
|
||||
WHERE `item`.`visible` AND NOT `item`.`deleted` AND NOT `item`.`moderated`
|
||||
AND `id` = %d", $r[0]["parent"]);
|
||||
|
||||
$profiledata = display_fetchauthor($a, $r[0]);
|
||||
|
|
@ -67,7 +67,7 @@ function display_init(&$a) {
|
|||
if (($nickname != $a->user["nickname"])) {
|
||||
$r = q("SELECT `profile`.`uid` AS `profile_uid`, `profile`.* , `contact`.`avatar-date` AS picdate, `user`.* FROM `profile`
|
||||
INNER JOIN `contact` on `contact`.`uid` = `profile`.`uid` INNER JOIN `user` ON `profile`.`uid` = `user`.`uid`
|
||||
WHERE `user`.`nickname` = '%s' AND `profile`.`is-default` = 1 and `contact`.`self` = 1 LIMIT 1",
|
||||
WHERE `user`.`nickname` = '%s' AND `profile`.`is-default` AND `contact`.`self` LIMIT 1",
|
||||
dbesc($nickname)
|
||||
);
|
||||
if (count($r))
|
||||
|
|
@ -120,27 +120,27 @@ function display_fetchauthor($a, $item) {
|
|||
}
|
||||
|
||||
if (!$skip) {
|
||||
$author = "";
|
||||
preg_match("/author='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$author = "";
|
||||
preg_match("/author='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$profiledata["name"] = html_entity_decode($matches[1],ENT_QUOTES,'UTF-8');
|
||||
|
||||
preg_match('/author="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
preg_match('/author="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$profiledata["name"] = html_entity_decode($matches[1],ENT_QUOTES,'UTF-8');
|
||||
|
||||
$profile = "";
|
||||
preg_match("/profile='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$profile = "";
|
||||
preg_match("/profile='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$profiledata["url"] = $matches[1];
|
||||
|
||||
preg_match('/profile="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
preg_match('/profile="(.*?)"/ism', $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$profiledata["url"] = $matches[1];
|
||||
|
||||
$avatar = "";
|
||||
preg_match("/avatar='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$avatar = "";
|
||||
preg_match("/avatar='(.*?)'/ism", $attributes, $matches);
|
||||
if ($matches[1] != "")
|
||||
$profiledata["photo"] = $matches[1];
|
||||
|
||||
preg_match('/avatar="(.*?)"/ism', $attributes, $matches);
|
||||
|
|
@ -257,7 +257,7 @@ function display_content(&$a, $update = 0) {
|
|||
|
||||
if (local_user()) {
|
||||
$r = q("SELECT `id` FROM `item`
|
||||
WHERE `item`.`visible` = 1 AND `item`.`deleted` = 0 and `item`.`moderated` = 0
|
||||
WHERE `item`.`visible` AND NOT `item`.`deleted` AND NOT `item`.`moderated`
|
||||
AND `guid` = '%s' AND `uid` = %d", dbesc($a->argv[1]), local_user());
|
||||
if (count($r)) {
|
||||
$item_id = $r[0]["id"];
|
||||
|
|
@ -267,12 +267,12 @@ function display_content(&$a, $update = 0) {
|
|||
|
||||
if ($nick == "") {
|
||||
$r = q("SELECT `user`.`nickname`, `item`.`id` FROM `item` INNER JOIN `user` ON `user`.`uid` = `item`.`uid`
|
||||
WHERE `item`.`visible` = 1 AND `item`.`deleted` = 0 and `item`.`moderated` = 0
|
||||
WHERE `item`.`visible` AND NOT `item`.`deleted` AND NOT `item`.`moderated`
|
||||
AND `item`.`allow_cid` = '' AND `item`.`allow_gid` = ''
|
||||
AND `item`.`deny_cid` = '' AND `item`.`deny_gid` = ''
|
||||
AND `item`.`private` = 0 AND NOT `user`.`hidewall`
|
||||
AND NOT `item`.`private` AND NOT `user`.`hidewall`
|
||||
AND `item`.`guid` = '%s'", dbesc($a->argv[1]));
|
||||
// AND `item`.`private` = 0 AND `item`.`wall` = 1
|
||||
// AND NOT `item`.`private` AND `item`.`wall`
|
||||
if (count($r)) {
|
||||
$item_id = $r[0]["id"];
|
||||
$nick = $r[0]["nickname"];
|
||||
|
|
@ -280,12 +280,12 @@ function display_content(&$a, $update = 0) {
|
|||
}
|
||||
if ($nick == "") {
|
||||
$r = q("SELECT `item`.`id` FROM `item`
|
||||
WHERE `item`.`visible` = 1 AND `item`.`deleted` = 0 and `item`.`moderated` = 0
|
||||
WHERE `item`.`visible` AND NOT `item`.`deleted` AND NOT `item`.`moderated`
|
||||
AND `item`.`allow_cid` = '' AND `item`.`allow_gid` = ''
|
||||
AND `item`.`deny_cid` = '' AND `item`.`deny_gid` = ''
|
||||
AND `item`.`private` = 0 AND `item`.`uid` = 0
|
||||
AND NOT `item`.`private` AND `item`.`uid` = 0
|
||||
AND `item`.`guid` = '%s'", dbesc($a->argv[1]));
|
||||
// AND `item`.`private` = 0 AND `item`.`wall` = 1
|
||||
// AND NOT `item`.`private` AND `item`.`wall`
|
||||
if (count($r)) {
|
||||
$item_id = $r[0]["id"];
|
||||
}
|
||||
|
|
@ -293,12 +293,22 @@ function display_content(&$a, $update = 0) {
|
|||
}
|
||||
}
|
||||
|
||||
if(! $item_id) {
|
||||
if ($item_id AND !is_numeric($item_id)) {
|
||||
$r = q("SELECT `id` FROM `item` WHERE `uri` = '%s' AND `uid` = %d LIMIT 1",
|
||||
dbesc($item_id), intval($a->profile['uid']));
|
||||
if ($r)
|
||||
$item_id = $r[0]["id"];
|
||||
else
|
||||
$item_id = false;
|
||||
}
|
||||
|
||||
if (!$item_id) {
|
||||
$a->error = 404;
|
||||
notice( t('Item not found.') . EOL);
|
||||
notice(t('Item not found.').EOL);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
$groups = array();
|
||||
|
||||
$contact = null;
|
||||
|
|
@ -334,7 +344,7 @@ function display_content(&$a, $update = 0) {
|
|||
}
|
||||
}
|
||||
|
||||
$r = q("SELECT * FROM `contact` WHERE `uid` = %d AND `self` = 1 LIMIT 1",
|
||||
$r = q("SELECT * FROM `contact` WHERE `uid` = %d AND `self` LIMIT 1",
|
||||
intval($a->profile['uid'])
|
||||
);
|
||||
if(count($r))
|
||||
|
|
@ -347,10 +357,8 @@ function display_content(&$a, $update = 0) {
|
|||
return;
|
||||
}
|
||||
|
||||
// Why do we need this on the display page? We don't have the possibility to write new content here.
|
||||
// Ad editing of posts work without this as well.
|
||||
// We should remove this completely for the 3.5.1 release.
|
||||
/*
|
||||
// We need the editor here to be able to reshare an item.
|
||||
|
||||
if ($is_owner) {
|
||||
$x = array(
|
||||
'is_owner' => true,
|
||||
|
|
@ -366,66 +374,56 @@ function display_content(&$a, $update = 0) {
|
|||
);
|
||||
$o .= status_editor($a,$x,0,true);
|
||||
}
|
||||
*/
|
||||
|
||||
$sql_extra = item_permissions_sql($a->profile['uid'],$remote_contact,$groups);
|
||||
|
||||
// AND `item`.`parent` = ( SELECT `parent` FROM `item` FORCE INDEX (PRIMARY, `uri`) WHERE ( `id` = '%s' OR `uri` = '%s' ))
|
||||
|
||||
if($update) {
|
||||
|
||||
$r = q("SELECT id FROM item WHERE item.uid = %d
|
||||
AND `item`.`parent` = (SELECT `parent` FROM `item` WHERE (`id` = '%s' OR `uri` = '%s'))
|
||||
$sql_extra AND unseen = 1",
|
||||
intval($a->profile['uid']),
|
||||
dbesc($item_id),
|
||||
dbesc($item_id)
|
||||
$r = q("SELECT `id` FROM `item` WHERE `item`.`uid` = %d
|
||||
AND `item`.`parent` = (SELECT `parent` FROM `item` WHERE `id` = %d)
|
||||
$sql_extra AND `unseen`",
|
||||
intval($a->profile['uid']),
|
||||
intval($item_id)
|
||||
);
|
||||
|
||||
if(!$r)
|
||||
return '';
|
||||
}
|
||||
|
||||
// AND `item`.`parent` = ( SELECT `parent` FROM `item` FORCE INDEX (PRIMARY, `uri`) WHERE ( `id` = '%s' OR `uri` = '%s' )
|
||||
|
||||
$r = q("SELECT `item`.*, `item`.`id` AS `item_id`, `item`.`network` AS `item_network`,
|
||||
`contact`.`name`, `contact`.`photo`, `contact`.`url`, `contact`.`rel`,
|
||||
`contact`.`network`, `contact`.`thumb`, `contact`.`self`, `contact`.`writable`,
|
||||
`contact`.`id` AS `cid`, `contact`.`uid` AS `contact-uid`
|
||||
FROM `item` INNER JOIN `contact` ON `contact`.`id` = `item`.`contact-id`
|
||||
AND `contact`.`blocked` = 0 AND `contact`.`pending` = 0
|
||||
WHERE `item`.`uid` = %d AND `item`.`visible` = 1 AND `item`.`deleted` = 0
|
||||
and `item`.`moderated` = 0
|
||||
AND `item`.`parent` = (SELECT `parent` FROM `item` WHERE (`id` = '%s' OR `uri` = '%s')
|
||||
AND uid = %d)
|
||||
AND NOT `contact`.`blocked` AND NOT `contact`.`pending`
|
||||
WHERE `item`.`uid` = %d AND `item`.`visible` AND NOT `item`.`deleted`
|
||||
AND NOT `item`.`moderated`
|
||||
AND `item`.`parent` = (SELECT `parent` FROM `item` WHERE `id` = %d)
|
||||
$sql_extra
|
||||
ORDER BY `parent` DESC, `gravity` ASC, `id` ASC",
|
||||
intval($a->profile['uid']),
|
||||
dbesc($item_id),
|
||||
dbesc($item_id),
|
||||
intval($a->profile['uid'])
|
||||
intval($item_id)
|
||||
);
|
||||
|
||||
if(!$r && local_user()) {
|
||||
// Check if this is another person's link to a post that we have
|
||||
$r = q("SELECT `item`.uri FROM `item`
|
||||
WHERE (`item`.`id` = '%s' OR `item`.`uri` = '%s' )
|
||||
WHERE (`item`.`id` = %d OR `item`.`uri` = '%s')
|
||||
LIMIT 1",
|
||||
dbesc($item_id),
|
||||
intval($item_id),
|
||||
dbesc($item_id)
|
||||
);
|
||||
if($r) {
|
||||
$item_uri = $r[0]['uri'];
|
||||
// AND `item`.`parent` = ( SELECT `parent` FROM `item` FORCE INDEX (PRIMARY, `uri`) WHERE `uri` = '%s' AND uid = %d )
|
||||
|
||||
$r = q("SELECT `item`.*, `item`.`id` AS `item_id`, `item`.`network` AS `item_network`,
|
||||
`contact`.`name`, `contact`.`photo`, `contact`.`url`, `contact`.`rel`,
|
||||
`contact`.`network`, `contact`.`thumb`, `contact`.`self`, `contact`.`writable`,
|
||||
`contact`.`id` AS `cid`, `contact`.`uid` AS `contact-uid`
|
||||
FROM `item` INNER JOIN `contact` ON `contact`.`id` = `item`.`contact-id`
|
||||
AND `contact`.`blocked` = 0 AND `contact`.`pending` = 0
|
||||
WHERE `item`.`uid` = %d AND `item`.`visible` = 1 AND `item`.`deleted` = 0
|
||||
and `item`.`moderated` = 0
|
||||
AND NOT `contact`.`blocked` AND NOT `contact`.`pending`
|
||||
WHERE `item`.`uid` = %d AND `item`.`visible` AND NOT `item`.`deleted`
|
||||
AND NOT `item`.`moderated`
|
||||
AND `item`.`parent` = (SELECT `parent` FROM `item` WHERE `uri` = '%s' AND uid = %d)
|
||||
ORDER BY `parent` DESC, `gravity` ASC, `id` ASC ",
|
||||
intval(local_user()),
|
||||
|
|
@ -440,7 +438,7 @@ function display_content(&$a, $update = 0) {
|
|||
|
||||
if((local_user()) && (local_user() == $a->profile['uid'])) {
|
||||
q("UPDATE `item` SET `unseen` = 0
|
||||
WHERE `parent` = %d AND `unseen` = 1",
|
||||
WHERE `parent` = %d AND `unseen`",
|
||||
intval($r[0]['parent'])
|
||||
);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -74,10 +74,18 @@ function fbrowser_content($a){
|
|||
$filename_e = $rr['filename'];
|
||||
}
|
||||
|
||||
// Take the second largest picture as preview
|
||||
$p = q("SELECT `scale` FROM `photo` WHERE `resource-id` = '%s' AND `scale` > %d ORDER BY `resource-id`, `scale` LIMIT 1",
|
||||
dbesc($rr['resource-id']), intval($rr['hiq']));
|
||||
if ($p)
|
||||
$scale = $p[0]["scale"];
|
||||
else
|
||||
$scale = $rr['loq'];
|
||||
|
||||
return array(
|
||||
$a->get_baseurl() . '/photos/' . $a->user['nickname'] . '/image/' . $rr['resource-id'],
|
||||
$filename_e,
|
||||
$a->get_baseurl() . '/photo/' . $rr['resource-id'] . '-' . $rr['loq'] . '.'. $ext
|
||||
$a->get_baseurl() . '/photo/' . $rr['resource-id'] . '-' . $scale . '.'. $ext
|
||||
);
|
||||
}
|
||||
$files = array_map("_map_files1", $r);
|
||||
|
|
|
|||
42
mod/item.php
42
mod/item.php
|
|
@ -24,6 +24,7 @@ require_once('include/threads.php');
|
|||
require_once('include/text.php');
|
||||
require_once('include/items.php');
|
||||
require_once('include/Scrape.php');
|
||||
require_once('include/diaspora.php');
|
||||
|
||||
function item_post(&$a) {
|
||||
|
||||
|
|
@ -900,7 +901,7 @@ function item_post(&$a) {
|
|||
|
||||
|
||||
// Store the comment signature information in case we need to relay to Diaspora
|
||||
store_diaspora_comment_sig($datarray, $author, ($self ? $user['prvkey'] : false), $parent_item, $post_id);
|
||||
diaspora::store_comment_signature($datarray, $author, ($self ? $user['prvkey'] : false), $post_id);
|
||||
|
||||
} else {
|
||||
$parent = $post_id;
|
||||
|
|
@ -1245,42 +1246,3 @@ function handle_tag($a, &$body, &$inform, &$str_tags, $profile_uid, $tag, $netwo
|
|||
|
||||
return array('replaced' => $replaced, 'contact' => $r[0]);
|
||||
}
|
||||
|
||||
|
||||
function store_diaspora_comment_sig($datarray, $author, $uprvkey, $parent_item, $post_id) {
|
||||
// We won't be able to sign Diaspora comments for authenticated visitors - we don't have their private key
|
||||
|
||||
$enabled = intval(get_config('system','diaspora_enabled'));
|
||||
if(! $enabled) {
|
||||
logger('mod_item: diaspora support disabled, not storing comment signature', LOGGER_DEBUG);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
logger('mod_item: storing diaspora comment signature');
|
||||
|
||||
require_once('include/bb2diaspora.php');
|
||||
$signed_body = html_entity_decode(bb2diaspora($datarray['body']));
|
||||
|
||||
// Only works for NETWORK_DFRN
|
||||
$contact_baseurl_start = strpos($author['url'],'://') + 3;
|
||||
$contact_baseurl_length = strpos($author['url'],'/profile') - $contact_baseurl_start;
|
||||
$contact_baseurl = substr($author['url'], $contact_baseurl_start, $contact_baseurl_length);
|
||||
$diaspora_handle = $author['nick'] . '@' . $contact_baseurl;
|
||||
|
||||
$signed_text = $datarray['guid'] . ';' . $parent_item['guid'] . ';' . $signed_body . ';' . $diaspora_handle;
|
||||
|
||||
if( $uprvkey !== false )
|
||||
$authorsig = rsa_sign($signed_text,$uprvkey,'sha256');
|
||||
else
|
||||
$authorsig = '';
|
||||
|
||||
q("insert into sign (`iid`,`signed_text`,`signature`,`signer`) values (%d,'%s','%s','%s') ",
|
||||
intval($post_id),
|
||||
dbesc($signed_text),
|
||||
dbesc(base64_encode($authorsig)),
|
||||
dbesc($diaspora_handle)
|
||||
);
|
||||
|
||||
return;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ function message_init(&$a) {
|
|||
|
||||
$new = array(
|
||||
'label' => t('New Message'),
|
||||
'url' => $a->get_baseurl(true) . '/message/new',
|
||||
'url' => 'message/new',
|
||||
'sel'=> ($a->argv[1] == 'new'),
|
||||
'accesskey' => 'm',
|
||||
);
|
||||
|
|
@ -90,7 +90,7 @@ function message_post(&$a) {
|
|||
$a->argv[1] = 'new';
|
||||
}
|
||||
else
|
||||
goaway($a->get_baseurl(true) . '/' . $_SESSION['return_url']);
|
||||
goaway($_SESSION['return_url']);
|
||||
|
||||
}
|
||||
|
||||
|
|
@ -182,7 +182,7 @@ function message_content(&$a) {
|
|||
return;
|
||||
}
|
||||
|
||||
$myprofile = $a->get_baseurl(true) . '/profile/' . $a->user['nickname'];
|
||||
$myprofile = 'profile/' . $a->user['nickname'];
|
||||
|
||||
$tpl = get_markup_template('mail_head.tpl');
|
||||
$header = replace_macros($tpl, array(
|
||||
|
|
@ -221,7 +221,7 @@ function message_content(&$a) {
|
|||
}
|
||||
// Now check how the user responded to the confirmation query
|
||||
if($_REQUEST['canceled']) {
|
||||
goaway($a->get_baseurl(true) . '/' . $_SESSION['return_url']);
|
||||
goaway($_SESSION['return_url']);
|
||||
}
|
||||
|
||||
$cmd = $a->argv[1];
|
||||
|
|
@ -234,7 +234,7 @@ function message_content(&$a) {
|
|||
info( t('Message deleted.') . EOL );
|
||||
}
|
||||
//goaway($a->get_baseurl(true) . '/message' );
|
||||
goaway($a->get_baseurl(true) . '/' . $_SESSION['return_url']);
|
||||
goaway($_SESSION['return_url']);
|
||||
}
|
||||
else {
|
||||
$r = q("SELECT `parent-uri`,`convid` FROM `mail` WHERE `id` = %d AND `uid` = %d LIMIT 1",
|
||||
|
|
@ -265,7 +265,7 @@ function message_content(&$a) {
|
|||
info( t('Conversation removed.') . EOL );
|
||||
}
|
||||
//goaway($a->get_baseurl(true) . '/message' );
|
||||
goaway($a->get_baseurl(true) . '/' . $_SESSION['return_url']);
|
||||
goaway($_SESSION['return_url']);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -448,7 +448,7 @@ function message_content(&$a) {
|
|||
$sparkle = '';
|
||||
}
|
||||
else {
|
||||
$from_url = $a->get_baseurl(true) . '/redir/' . $message['contact-id'];
|
||||
$from_url = 'redir/' . $message['contact-id'];
|
||||
$sparkle = ' sparkle';
|
||||
}
|
||||
|
||||
|
|
@ -549,7 +549,7 @@ function render_messages($msg, $t) {
|
|||
$tpl = get_markup_template($t);
|
||||
$rslt = '';
|
||||
|
||||
$myprofile = $a->get_baseurl(true) . '/profile/' . $a->user['nickname'];
|
||||
$myprofile = 'profile/' . $a->user['nickname'];
|
||||
|
||||
foreach($msg as $rr) {
|
||||
|
||||
|
|
@ -577,7 +577,7 @@ function render_messages($msg, $t) {
|
|||
$rslt .= replace_macros($tpl, array(
|
||||
'$id' => $rr['id'],
|
||||
'$from_name' => $participants,
|
||||
'$from_url' => (($rr['network'] === NETWORK_DFRN) ? $a->get_baseurl(true) . '/redir/' . $rr['contact-id'] : $rr['url']),
|
||||
'$from_url' => (($rr['network'] === NETWORK_DFRN) ? 'redir/' . $rr['contact-id'] : $rr['url']),
|
||||
'$sparkle' => ' sparkle',
|
||||
'$from_photo' => (($rr['thumb']) ? $rr['thumb'] : $rr['from-photo']),
|
||||
'$subject' => $subject_e,
|
||||
|
|
|
|||
|
|
@ -62,7 +62,7 @@ function mood_init(&$a) {
|
|||
$action = sprintf( t('%1$s is currently %2$s'), '[url=' . $poster['url'] . ']' . $poster['name'] . '[/url]' , $verbs[$verb]);
|
||||
|
||||
$arr = array();
|
||||
|
||||
$arr['guid'] = get_guid(32);
|
||||
$arr['uid'] = $uid;
|
||||
$arr['uri'] = $uri;
|
||||
$arr['parent-uri'] = (($parent_uri) ? $parent_uri : $uri);
|
||||
|
|
|
|||
|
|
@ -149,10 +149,10 @@ function network_init(&$a) {
|
|||
|
||||
$a->page['aside'] .= (feature_enabled(local_user(),'groups') ? group_side('network/0','network','standard',$group_id) : '');
|
||||
$a->page['aside'] .= (feature_enabled(local_user(),'forumlist_widget') ? ForumManager::widget(local_user(),$cid) : '');
|
||||
$a->page['aside'] .= posted_date_widget($a->get_baseurl() . '/network',local_user(),false);
|
||||
$a->page['aside'] .= networks_widget($a->get_baseurl(true) . '/network',(x($_GET, 'nets') ? $_GET['nets'] : ''));
|
||||
$a->page['aside'] .= posted_date_widget('network',local_user(),false);
|
||||
$a->page['aside'] .= networks_widget('network',(x($_GET, 'nets') ? $_GET['nets'] : ''));
|
||||
$a->page['aside'] .= saved_searches($search);
|
||||
$a->page['aside'] .= fileas_widget($a->get_baseurl(true) . '/network',(x($_GET, 'file') ? $_GET['file'] : ''));
|
||||
$a->page['aside'] .= fileas_widget('network',(x($_GET, 'file') ? $_GET['file'] : ''));
|
||||
|
||||
}
|
||||
|
||||
|
|
@ -363,7 +363,7 @@ function network_content(&$a, $update = 0) {
|
|||
$tabs = array(
|
||||
array(
|
||||
'label' => t('Commented Order'),
|
||||
'url' => $a->get_baseurl(true) . '/' . str_replace('/new', '', $cmd) . '?f=&order=comment' . ((x($_GET,'cid')) ? '&cid=' . $_GET['cid'] : ''),
|
||||
'url' => str_replace('/new', '', $cmd) . '?f=&order=comment' . ((x($_GET,'cid')) ? '&cid=' . $_GET['cid'] : ''),
|
||||
'sel' => $all_active,
|
||||
'title' => t('Sort by Comment Date'),
|
||||
'id' => 'commented-order-tab',
|
||||
|
|
@ -371,7 +371,7 @@ function network_content(&$a, $update = 0) {
|
|||
),
|
||||
array(
|
||||
'label' => t('Posted Order'),
|
||||
'url' => $a->get_baseurl(true) . '/' . str_replace('/new', '', $cmd) . '?f=&order=post' . ((x($_GET,'cid')) ? '&cid=' . $_GET['cid'] : ''),
|
||||
'url' => str_replace('/new', '', $cmd) . '?f=&order=post' . ((x($_GET,'cid')) ? '&cid=' . $_GET['cid'] : ''),
|
||||
'sel' => $postord_active,
|
||||
'title' => t('Sort by Post Date'),
|
||||
'id' => 'posted-order-tab',
|
||||
|
|
@ -382,7 +382,7 @@ function network_content(&$a, $update = 0) {
|
|||
if(feature_enabled(local_user(),'personal_tab')) {
|
||||
$tabs[] = array(
|
||||
'label' => t('Personal'),
|
||||
'url' => $a->get_baseurl(true) . '/' . str_replace('/new', '', $cmd) . ((x($_GET,'cid')) ? '/?f=&cid=' . $_GET['cid'] : '/?f=') . '&conv=1',
|
||||
'url' => str_replace('/new', '', $cmd) . ((x($_GET,'cid')) ? '/?f=&cid=' . $_GET['cid'] : '/?f=') . '&conv=1',
|
||||
'sel' => $conv_active,
|
||||
'title' => t('Posts that mention or involve you'),
|
||||
'id' => 'personal-tab',
|
||||
|
|
@ -393,7 +393,7 @@ function network_content(&$a, $update = 0) {
|
|||
if(feature_enabled(local_user(),'new_tab')) {
|
||||
$tabs[] = array(
|
||||
'label' => t('New'),
|
||||
'url' => $a->get_baseurl(true) . '/' . str_replace('/new', '', $cmd) . ($len_naked_cmd ? '/' : '') . 'new' . ((x($_GET,'cid')) ? '/?f=&cid=' . $_GET['cid'] : ''),
|
||||
'url' => str_replace('/new', '', $cmd) . ($len_naked_cmd ? '/' : '') . 'new' . ((x($_GET,'cid')) ? '/?f=&cid=' . $_GET['cid'] : ''),
|
||||
'sel' => $new_active,
|
||||
'title' => t('Activity Stream - by date'),
|
||||
'id' => 'activitiy-by-date-tab',
|
||||
|
|
@ -404,7 +404,7 @@ function network_content(&$a, $update = 0) {
|
|||
if(feature_enabled(local_user(),'link_tab')) {
|
||||
$tabs[] = array(
|
||||
'label' => t('Shared Links'),
|
||||
'url' => $a->get_baseurl(true) . '/' . str_replace('/new', '', $cmd) . ((x($_GET,'cid')) ? '/?f=&cid=' . $_GET['cid'] : '/?f=') . '&bmark=1',
|
||||
'url' => str_replace('/new', '', $cmd) . ((x($_GET,'cid')) ? '/?f=&cid=' . $_GET['cid'] : '/?f=') . '&bmark=1',
|
||||
'sel' => $bookmarked_active,
|
||||
'title' => t('Interesting Links'),
|
||||
'id' => 'shared-links-tab',
|
||||
|
|
@ -415,7 +415,7 @@ function network_content(&$a, $update = 0) {
|
|||
if(feature_enabled(local_user(),'star_posts')) {
|
||||
$tabs[] = array(
|
||||
'label' => t('Starred'),
|
||||
'url' => $a->get_baseurl(true) . '/' . str_replace('/new', '', $cmd) . ((x($_GET,'cid')) ? '/?f=&cid=' . $_GET['cid'] : '/?f=') . '&star=1',
|
||||
'url' => str_replace('/new', '', $cmd) . ((x($_GET,'cid')) ? '/?f=&cid=' . $_GET['cid'] : '/?f=') . '&star=1',
|
||||
'sel' => $starred_active,
|
||||
'title' => t('Favourite Posts'),
|
||||
'id' => 'starred-posts-tab',
|
||||
|
|
@ -547,7 +547,7 @@ function network_content(&$a, $update = 0) {
|
|||
if($update)
|
||||
killme();
|
||||
notice( t('No such group') . EOL );
|
||||
goaway($a->get_baseurl(true) . '/network/0');
|
||||
goaway('network/0');
|
||||
// NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -611,7 +611,7 @@ function network_content(&$a, $update = 0) {
|
|||
}
|
||||
else {
|
||||
notice( t('Invalid contact.') . EOL);
|
||||
goaway($a->get_baseurl(true) . '/network');
|
||||
goaway('network');
|
||||
// NOTREACHED
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -28,7 +28,7 @@ function noscrape_init(&$a) {
|
|||
$json_info = array(
|
||||
'fn' => $a->profile['name'],
|
||||
'addr' => $a->profile['addr'],
|
||||
'nick' => $a->user['nickname'],
|
||||
'nick' => $which,
|
||||
'key' => $a->profile['pubkey'],
|
||||
'homepage' => $a->get_baseurl()."/profile/{$which}",
|
||||
'comm' => (x($a->profile,'page-flags')) && ($a->profile['page-flags'] == PAGE_COMMUNITY),
|
||||
|
|
|
|||
|
|
@ -49,12 +49,12 @@ function notifications_post(&$a) {
|
|||
intval(local_user())
|
||||
);
|
||||
}
|
||||
goaway($a->get_baseurl(true) . '/notifications/intros');
|
||||
goaway('notifications/intros');
|
||||
}
|
||||
if($_POST['submit'] == t('Ignore')) {
|
||||
$r = q("UPDATE `intro` SET `ignore` = 1 WHERE `id` = %d",
|
||||
intval($intro_id));
|
||||
goaway($a->get_baseurl(true) . '/notifications/intros');
|
||||
goaway('notifications/intros');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -79,37 +79,37 @@ function notifications_content(&$a) {
|
|||
$tabs = array(
|
||||
array(
|
||||
'label' => t('System'),
|
||||
'url'=>$a->get_baseurl(true) . '/notifications/system',
|
||||
'url'=>'notifications/system',
|
||||
'sel'=> (($a->argv[1] == 'system') ? 'active' : ''),
|
||||
'accesskey' => 'y',
|
||||
),
|
||||
array(
|
||||
'label' => t('Network'),
|
||||
'url'=>$a->get_baseurl(true) . '/notifications/network',
|
||||
'url'=>'notifications/network',
|
||||
'sel'=> (($a->argv[1] == 'network') ? 'active' : ''),
|
||||
'accesskey' => 'w',
|
||||
),
|
||||
array(
|
||||
'label' => t('Personal'),
|
||||
'url'=>$a->get_baseurl(true) . '/notifications/personal',
|
||||
'url'=>'notifications/personal',
|
||||
'sel'=> (($a->argv[1] == 'personal') ? 'active' : ''),
|
||||
'accesskey' => 'r',
|
||||
),
|
||||
array(
|
||||
'label' => t('Home'),
|
||||
'url' => $a->get_baseurl(true) . '/notifications/home',
|
||||
'url' => 'notifications/home',
|
||||
'sel'=> (($a->argv[1] == 'home') ? 'active' : ''),
|
||||
'accesskey' => 'h',
|
||||
),
|
||||
array(
|
||||
'label' => t('Introductions'),
|
||||
'url' => $a->get_baseurl(true) . '/notifications/intros',
|
||||
'url' => 'notifications/intros',
|
||||
'sel'=> (($a->argv[1] == 'intros') ? 'active' : ''),
|
||||
'accesskey' => 'i',
|
||||
),
|
||||
/*array(
|
||||
'label' => t('Messages'),
|
||||
'url' => $a->get_baseurl(true) . '/message',
|
||||
'url' => 'message',
|
||||
'sel'=> '',
|
||||
),*/ /*while I can have notifications for messages, this tablist is not place for message page link */
|
||||
);
|
||||
|
|
|
|||
|
|
@ -28,14 +28,14 @@ function p_init($a){
|
|||
|
||||
$post = array();
|
||||
|
||||
$reshared = diaspora_is_reshare($item[0]["body"]);
|
||||
$reshared = diaspora::is_reshare($item[0]["body"]);
|
||||
|
||||
if ($reshared) {
|
||||
$nodename = "reshare";
|
||||
$post["root_diaspora_id"] = $reshared["root_handle"];
|
||||
$post["root_guid"] = $reshared["root_guid"];
|
||||
$post["guid"] = $item[0]["guid"];
|
||||
$post["diaspora_handle"] = diaspora_handle_from_contact($item[0]["contact-id"]);
|
||||
$post["diaspora_handle"] = diaspora::handle_from_contact($item[0]["contact-id"]);
|
||||
$post["public"] = (!$item[0]["private"] ? 'true':'false');
|
||||
$post["created_at"] = datetime_convert('UTC','UTC',$item[0]["created"]);
|
||||
} else {
|
||||
|
|
@ -48,7 +48,7 @@ function p_init($a){
|
|||
$nodename = "status_message";
|
||||
$post["raw_message"] = str_replace("&", "&", $body);
|
||||
$post["guid"] = $item[0]["guid"];
|
||||
$post["diaspora_handle"] = diaspora_handle_from_contact($item[0]["contact-id"]);
|
||||
$post["diaspora_handle"] = diaspora::handle_from_contact($item[0]["contact-id"]);
|
||||
$post["public"] = (!$item[0]["private"] ? 'true':'false');
|
||||
$post["created_at"] = datetime_convert('UTC','UTC',$item[0]["created"]);
|
||||
$post["provider_display_name"] = $item[0]["app"];
|
||||
|
|
|
|||
|
|
@ -80,7 +80,7 @@ function photos_init(&$a) {
|
|||
$entry = array(
|
||||
'text' => $album['album'],
|
||||
'total' => $album['total'],
|
||||
'url' => z_root() . '/photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($album['album']),
|
||||
'url' => 'photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($album['album']),
|
||||
'urlencode' => urlencode($album['album']),
|
||||
'bin2hex' => bin2hex($album['album'])
|
||||
);
|
||||
|
|
@ -100,7 +100,7 @@ function photos_init(&$a) {
|
|||
'$recent' => t('Recent Photos'),
|
||||
'$albums' => $albums['albums'],
|
||||
'$baseurl' => z_root(),
|
||||
'$upload' => array( t('Upload New Photos'), $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/upload'),
|
||||
'$upload' => array( t('Upload New Photos'), 'photos/' . $a->data['user']['nickname'] . '/upload'),
|
||||
'$can_post' => $can_post
|
||||
));
|
||||
}
|
||||
|
|
@ -190,7 +190,7 @@ function photos_post(&$a) {
|
|||
$album = hex2bin($a->argv[3]);
|
||||
|
||||
if($album === t('Profile Photos') || $album === 'Contact Photos' || $album === t('Contact Photos')) {
|
||||
goaway($a->get_baseurl() . '/' . $_SESSION['photo_return']);
|
||||
goaway($_SESSION['photo_return']);
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -200,13 +200,13 @@ function photos_post(&$a) {
|
|||
);
|
||||
if(! count($r)) {
|
||||
notice( t('Album not found.') . EOL);
|
||||
goaway($a->get_baseurl() . '/' . $_SESSION['photo_return']);
|
||||
goaway($_SESSION['photo_return']);
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
// Check if the user has responded to a delete confirmation query
|
||||
if($_REQUEST['canceled']) {
|
||||
goaway($a->get_baseurl() . '/' . $_SESSION['photo_return']);
|
||||
goaway($_SESSION['photo_return']);
|
||||
}
|
||||
|
||||
/*
|
||||
|
|
@ -221,7 +221,7 @@ function photos_post(&$a) {
|
|||
intval($page_owner_uid)
|
||||
);
|
||||
$newurl = str_replace(bin2hex($album),bin2hex($newalbum),$_SESSION['photo_return']);
|
||||
goaway($a->get_baseurl() . '/' . $newurl);
|
||||
goaway($newurl);
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -273,7 +273,7 @@ function photos_post(&$a) {
|
|||
}
|
||||
}
|
||||
else {
|
||||
goaway($a->get_baseurl() . '/' . $_SESSION['photo_return']);
|
||||
goaway($_SESSION['photo_return']);
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -309,14 +309,14 @@ function photos_post(&$a) {
|
|||
}
|
||||
}
|
||||
}
|
||||
goaway($a->get_baseurl() . '/photos/' . $a->data['user']['nickname']);
|
||||
goaway('photos/' . $a->data['user']['nickname']);
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
||||
// Check if the user has responded to a delete confirmation query for a single photo
|
||||
if(($a->argc > 2) && $_REQUEST['canceled']) {
|
||||
goaway($a->get_baseurl() . '/' . $_SESSION['photo_return']);
|
||||
goaway($_SESSION['photo_return']);
|
||||
}
|
||||
|
||||
if(($a->argc > 2) && (x($_POST,'delete')) && ($_POST['delete'] == t('Delete Photo'))) {
|
||||
|
|
@ -379,7 +379,7 @@ function photos_post(&$a) {
|
|||
}
|
||||
}
|
||||
|
||||
goaway($a->get_baseurl() . '/photos/' . $a->data['user']['nickname']);
|
||||
goaway('photos/' . $a->data['user']['nickname']);
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -488,7 +488,7 @@ function photos_post(&$a) {
|
|||
$uri = item_new_uri($a->get_hostname(),$page_owner_uid);
|
||||
|
||||
$arr = array();
|
||||
|
||||
$arr['guid'] = get_guid(32);
|
||||
$arr['uid'] = $page_owner_uid;
|
||||
$arr['uri'] = $uri;
|
||||
$arr['parent-uri'] = $uri;
|
||||
|
|
@ -677,7 +677,7 @@ function photos_post(&$a) {
|
|||
$uri = item_new_uri($a->get_hostname(),$page_owner_uid);
|
||||
|
||||
$arr = array();
|
||||
|
||||
$arr['guid'] = get_guid(32);
|
||||
$arr['uid'] = $page_owner_uid;
|
||||
$arr['uri'] = $uri;
|
||||
$arr['parent-uri'] = $uri;
|
||||
|
|
@ -718,12 +718,6 @@ function photos_post(&$a) {
|
|||
|
||||
$item_id = item_store($arr);
|
||||
if($item_id) {
|
||||
//q("UPDATE `item` SET `plink` = '%s' WHERE `uid` = %d AND `id` = %d",
|
||||
// dbesc($a->get_baseurl() . '/display/' . $owner_record['nickname'] . '/' . $item_id),
|
||||
// intval($page_owner_uid),
|
||||
// intval($item_id)
|
||||
//);
|
||||
|
||||
proc_run('php',"include/notifier.php","tag","$item_id");
|
||||
}
|
||||
}
|
||||
|
|
@ -731,7 +725,7 @@ function photos_post(&$a) {
|
|||
}
|
||||
|
||||
}
|
||||
goaway($a->get_baseurl() . '/' . $_SESSION['photo_return']);
|
||||
goaway($_SESSION['photo_return']);
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -910,6 +904,7 @@ function photos_post(&$a) {
|
|||
if($lat && $lon)
|
||||
$arr['coord'] = $lat . ' ' . $lon;
|
||||
|
||||
$arr['guid'] = get_guid(32);
|
||||
$arr['uid'] = $page_owner_uid;
|
||||
$arr['uri'] = $uri;
|
||||
$arr['parent-uri'] = $uri;
|
||||
|
|
@ -938,14 +933,6 @@ function photos_post(&$a) {
|
|||
|
||||
$item_id = item_store($arr);
|
||||
|
||||
//if($item_id) {
|
||||
// q("UPDATE `item` SET `plink` = '%s' WHERE `uid` = %d AND `id` = %d",
|
||||
// dbesc($a->get_baseurl() . '/display/' . $owner_record['nickname'] . '/' . $item_id),
|
||||
// intval($page_owner_uid),
|
||||
// intval($item_id)
|
||||
// );
|
||||
//}
|
||||
|
||||
if($visible)
|
||||
proc_run('php', "include/notifier.php", 'wall-new', $item_id);
|
||||
|
||||
|
|
@ -954,7 +941,7 @@ function photos_post(&$a) {
|
|||
// addon uploaders should call "killme()" [e.g. exit] within the photo_post_end hook
|
||||
// if they do not wish to be redirected
|
||||
|
||||
goaway($a->get_baseurl() . '/' . $_SESSION['photo_return']);
|
||||
goaway($_SESSION['photo_return']);
|
||||
// NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -1125,7 +1112,7 @@ function photos_content(&$a) {
|
|||
|
||||
$uploader = '';
|
||||
|
||||
$ret = array('post_url' => $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'],
|
||||
$ret = array('post_url' => 'photos/' . $a->data['user']['nickname'],
|
||||
'addon_text' => $uploader,
|
||||
'default_upload' => true);
|
||||
|
||||
|
|
@ -1267,15 +1254,15 @@ function photos_content(&$a) {
|
|||
else {
|
||||
if(($album !== t('Profile Photos')) && ($album !== 'Contact Photos') && ($album !== t('Contact Photos'))) {
|
||||
if($can_post) {
|
||||
$edit = array(t('Edit Album'), $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($album) . '/edit');
|
||||
$edit = array(t('Edit Album'), 'photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($album) . '/edit');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if($_GET['order'] === 'posted')
|
||||
$order = array(t('Show Newest First'), $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($album));
|
||||
$order = array(t('Show Newest First'), 'photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($album));
|
||||
else
|
||||
$order = array(t('Show Oldest First'), $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($album) . '?f=&order=posted');
|
||||
$order = array(t('Show Oldest First'), 'photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($album) . '?f=&order=posted');
|
||||
|
||||
$photos = array();
|
||||
|
||||
|
|
@ -1301,10 +1288,10 @@ function photos_content(&$a) {
|
|||
$photos[] = array(
|
||||
'id' => $rr['id'],
|
||||
'twist' => ' ' . $twist . rand(2,4),
|
||||
'link' => $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/image/' . $rr['resource-id']
|
||||
'link' => 'photos/' . $a->data['user']['nickname'] . '/image/' . $rr['resource-id']
|
||||
. (($_GET['order'] === 'posted') ? '?f=&order=posted' : ''),
|
||||
'title' => t('View Photo'),
|
||||
'src' => $a->get_baseurl() . '/photo/' . $rr['resource-id'] . '-' . $rr['scale'] . '.' .$ext,
|
||||
'src' => 'photo/' . $rr['resource-id'] . '-' . $rr['scale'] . '.' .$ext,
|
||||
'alt' => $imgalt_e,
|
||||
'desc'=> $desc_e,
|
||||
'ext' => $ext,
|
||||
|
|
@ -1317,7 +1304,7 @@ function photos_content(&$a) {
|
|||
'$photos' => $photos,
|
||||
'$album' => $album,
|
||||
'$can_post' => $can_post,
|
||||
'$upload' => array(t('Upload New Photos'), $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/upload/' . bin2hex($album)),
|
||||
'$upload' => array(t('Upload New Photos'), 'photos/' . $a->data['user']['nickname'] . '/upload/' . bin2hex($album)),
|
||||
'$order' => $order,
|
||||
'$edit' => $edit
|
||||
));
|
||||
|
|
@ -1384,8 +1371,8 @@ function photos_content(&$a) {
|
|||
}
|
||||
}
|
||||
$edit_suffix = ((($cmd === 'edit') && ($can_post)) ? '/edit' : '');
|
||||
$prevlink = $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/image/' . $prvnxt[$prv]['resource-id'] . $edit_suffix . (($_GET['order'] === 'posted') ? '?f=&order=posted' : '');
|
||||
$nextlink = $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/image/' . $prvnxt[$nxt]['resource-id'] . $edit_suffix . (($_GET['order'] === 'posted') ? '?f=&order=posted' : '');
|
||||
$prevlink = 'photos/' . $a->data['user']['nickname'] . '/image/' . $prvnxt[$prv]['resource-id'] . $edit_suffix . (($_GET['order'] === 'posted') ? '?f=&order=posted' : '');
|
||||
$nextlink = 'photos/' . $a->data['user']['nickname'] . '/image/' . $prvnxt[$nxt]['resource-id'] . $edit_suffix . (($_GET['order'] === 'posted') ? '?f=&order=posted' : '');
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -1402,14 +1389,14 @@ function photos_content(&$a) {
|
|||
}
|
||||
}
|
||||
|
||||
$album_link = $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($ph[0]['album']);
|
||||
$album_link = 'photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($ph[0]['album']);
|
||||
$tools = Null;
|
||||
$lock = Null;
|
||||
|
||||
if($can_post && ($ph[0]['uid'] == $owner_uid)) {
|
||||
$tools = array(
|
||||
'edit' => array($a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/image/' . $datum . (($cmd === 'edit') ? '' : '/edit'), (($cmd === 'edit') ? t('View photo') : t('Edit photo'))),
|
||||
'profile'=>array($a->get_baseurl() . '/profile_photo/use/'.$ph[0]['resource-id'], t('Use as profile photo')),
|
||||
'edit' => array('photos/' . $a->data['user']['nickname'] . '/image/' . $datum . (($cmd === 'edit') ? '' : '/edit'), (($cmd === 'edit') ? t('View photo') : t('Edit photo'))),
|
||||
'profile'=>array('profile_photo/use/'.$ph[0]['resource-id'], t('Use as profile photo')),
|
||||
);
|
||||
|
||||
// lock
|
||||
|
|
@ -1433,9 +1420,9 @@ function photos_content(&$a) {
|
|||
$prevlink = array($prevlink, '<div class="icon prev"></div>') ;
|
||||
|
||||
$photo = array(
|
||||
'href' => $a->get_baseurl() . '/photo/' . $hires['resource-id'] . '-' . $hires['scale'] . '.' . $phototypes[$hires['type']],
|
||||
'href' => 'photo/' . $hires['resource-id'] . '-' . $hires['scale'] . '.' . $phototypes[$hires['type']],
|
||||
'title'=> t('View Full Size'),
|
||||
'src' => $a->get_baseurl() . '/photo/' . $lores['resource-id'] . '-' . $lores['scale'] . '.' . $phototypes[$lores['type']] . '?f=&_u=' . datetime_convert('','','','ymdhis'),
|
||||
'src' => 'photo/' . $lores['resource-id'] . '-' . $lores['scale'] . '.' . $phototypes[$lores['type']] . '?f=&_u=' . datetime_convert('','','','ymdhis'),
|
||||
'height' => $hires['height'],
|
||||
'width' => $hires['width'],
|
||||
'album' => $hires['album'],
|
||||
|
|
@ -1522,7 +1509,7 @@ function photos_content(&$a) {
|
|||
}
|
||||
$tags = array(t('Tags: '), $tag_str);
|
||||
if($cmd === 'edit') {
|
||||
$tags[] = $a->get_baseurl() . '/tagrm/' . $link_item['id'];
|
||||
$tags[] = 'tagrm/' . $link_item['id'];
|
||||
$tags[] = t('[Remove any tag]');
|
||||
}
|
||||
}
|
||||
|
|
@ -1693,7 +1680,7 @@ function photos_content(&$a) {
|
|||
if(((activity_match($item['verb'],ACTIVITY_LIKE)) || (activity_match($item['verb'],ACTIVITY_DISLIKE))) && ($item['id'] != $item['parent']))
|
||||
continue;
|
||||
|
||||
$redirect_url = $a->get_baseurl() . '/redir/' . $item['cid'] ;
|
||||
$redirect_url = 'redir/' . $item['cid'] ;
|
||||
|
||||
|
||||
if(local_user() && ($item['contact-uid'] == local_user())
|
||||
|
|
@ -1880,12 +1867,12 @@ function photos_content(&$a) {
|
|||
$photos[] = array(
|
||||
'id' => $rr['id'],
|
||||
'twist' => ' ' . $twist . rand(2,4),
|
||||
'link' => $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/image/' . $rr['resource-id'],
|
||||
'link' => 'photos/' . $a->data['user']['nickname'] . '/image/' . $rr['resource-id'],
|
||||
'title' => t('View Photo'),
|
||||
'src' => $a->get_baseurl() . '/photo/' . $rr['resource-id'] . '-' . ((($rr['scale']) == 6) ? 4 : $rr['scale']) . '.' . $ext,
|
||||
'src' => 'photo/' . $rr['resource-id'] . '-' . ((($rr['scale']) == 6) ? 4 : $rr['scale']) . '.' . $ext,
|
||||
'alt' => $alt_e,
|
||||
'album' => array(
|
||||
'link' => $a->get_baseurl() . '/photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($rr['album']),
|
||||
'link' => 'photos/' . $a->data['user']['nickname'] . '/album/' . bin2hex($rr['album']),
|
||||
'name' => $name_e,
|
||||
'alt' => t('View Album'),
|
||||
),
|
||||
|
|
@ -1898,7 +1885,7 @@ function photos_content(&$a) {
|
|||
$o .= replace_macros($tpl, array(
|
||||
'$title' => t('Recent Photos'),
|
||||
'$can_post' => $can_post,
|
||||
'$upload' => array(t('Upload New Photos'), $a->get_baseurl().'/photos/'.$a->data['user']['nickname'].'/upload'),
|
||||
'$upload' => array(t('Upload New Photos'), 'photos/'.$a->data['user']['nickname'].'/upload'),
|
||||
'$photos' => $photos,
|
||||
));
|
||||
|
||||
|
|
|
|||
|
|
@ -207,7 +207,7 @@ function ping_init(&$a) {
|
|||
call_hooks('ping_xmlize', $n);
|
||||
$notsxml = '<note id="%d" href="%s" name="%s" url="%s" photo="%s" date="%s" seen="%s" timestamp="%s" >%s</note>'."\n";
|
||||
return sprintf ( $notsxml, intval($n['id']),
|
||||
xmlify($n['href']), xmlify($n['name']), xmlify($n['url']), xmlify($n['photo']),
|
||||
xmlify($n['href']), xmlify(xmlify($n['name'])), xmlify($n['url']), xmlify($n['photo']),
|
||||
xmlify(relative_date($n['date'])), xmlify($n['seen']), xmlify(strtotime($local_time)),
|
||||
xmlify($n['message'])
|
||||
);
|
||||
|
|
|
|||
|
|
@ -91,6 +91,7 @@ function poke_init(&$a) {
|
|||
|
||||
$arr = array();
|
||||
|
||||
$arr['guid'] = get_guid(32);
|
||||
$arr['uid'] = $uid;
|
||||
$arr['uri'] = $uri;
|
||||
$arr['parent-uri'] = (($parent_uri) ? $parent_uri : $uri);
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ function profiles_init(&$a) {
|
|||
);
|
||||
if(! count($r)) {
|
||||
notice( t('Profile not found.') . EOL);
|
||||
goaway($a->get_baseurl(true) . '/profiles');
|
||||
goaway('profiles');
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -34,9 +34,9 @@ function profiles_init(&$a) {
|
|||
intval(local_user())
|
||||
);
|
||||
if($r)
|
||||
info( t('Profile deleted.') . EOL);
|
||||
info(t('Profile deleted.').EOL);
|
||||
|
||||
goaway($a->get_baseurl(true) . '/profiles');
|
||||
goaway('profiles');
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -73,9 +73,9 @@ function profiles_init(&$a) {
|
|||
|
||||
info( t('New profile created.') . EOL);
|
||||
if(count($r3) == 1)
|
||||
goaway($a->get_baseurl(true) . '/profiles/' . $r3[0]['id']);
|
||||
goaway('profiles/'.$r3[0]['id']);
|
||||
|
||||
goaway($a->get_baseurl(true) . '/profiles');
|
||||
goaway('profiles');
|
||||
}
|
||||
|
||||
if(($a->argc > 2) && ($a->argv[1] === 'clone')) {
|
||||
|
|
@ -116,9 +116,9 @@ function profiles_init(&$a) {
|
|||
);
|
||||
info( t('New profile created.') . EOL);
|
||||
if(count($r3) == 1)
|
||||
goaway($a->get_baseurl(true) . '/profiles/' . $r3[0]['id']);
|
||||
goaway('profiles/'.$r3[0]['id']);
|
||||
|
||||
goaway($a->get_baseurl(true) . '/profiles');
|
||||
goaway('profiles');
|
||||
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
|
@ -526,6 +526,8 @@ function profile_activity($changed, $value) {
|
|||
return;
|
||||
|
||||
$arr = array();
|
||||
|
||||
$arr['guid'] = get_guid(32);
|
||||
$arr['uri'] = $arr['parent-uri'] = item_new_uri($a->get_hostname(), local_user());
|
||||
$arr['uid'] = local_user();
|
||||
$arr['contact-id'] = $self[0]['id'];
|
||||
|
|
@ -582,15 +584,7 @@ function profile_activity($changed, $value) {
|
|||
|
||||
$i = item_store($arr);
|
||||
if($i) {
|
||||
|
||||
// give it a permanent link
|
||||
//q("update item set plink = '%s' where id = %d",
|
||||
// dbesc($a->get_baseurl() . '/display/' . $a->user['nickname'] . '/' . $i),
|
||||
// intval($i)
|
||||
//);
|
||||
|
||||
proc_run('php',"include/notifier.php","activity","$i");
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -786,7 +780,7 @@ function profiles_content(&$a) {
|
|||
);
|
||||
if(count($r)){
|
||||
//Go to the default profile.
|
||||
goaway($a->get_baseurl(true) . '/profiles/'.$r[0]['id']);
|
||||
goaway('profiles/'.$r[0]['id']);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -807,12 +801,12 @@ function profiles_content(&$a) {
|
|||
|
||||
foreach($r as $rr) {
|
||||
$o .= replace_macros($tpl, array(
|
||||
'$photo' => $a->get_cached_avatar_image($rr['thumb']),
|
||||
'$photo' => $a->remove_baseurl($rr['thumb']),
|
||||
'$id' => $rr['id'],
|
||||
'$alt' => t('Profile Image'),
|
||||
'$profile_name' => $rr['profile-name'],
|
||||
'$visible' => (($rr['is-default']) ? '<strong>' . t('visible to everybody') . '</strong>'
|
||||
: '<a href="' . $a->get_baseurl(true) . '/profperm/' . $rr['id'] . '" />' . t('Edit visibility') . '</a>')
|
||||
: '<a href="'.'profperm/'.$rr['id'].'" />' . t('Edit visibility') . '</a>')
|
||||
));
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -53,7 +53,7 @@ function receive_post(&$a) {
|
|||
|
||||
logger('mod-diaspora: message is okay', LOGGER_DEBUG);
|
||||
|
||||
$msg = diaspora_decode($importer,$xml);
|
||||
$msg = diaspora::decode($importer,$xml);
|
||||
|
||||
logger('mod-diaspora: decoded', LOGGER_DEBUG);
|
||||
|
||||
|
|
@ -65,10 +65,11 @@ function receive_post(&$a) {
|
|||
logger('mod-diaspora: dispatching', LOGGER_DEBUG);
|
||||
|
||||
$ret = 0;
|
||||
if($public)
|
||||
diaspora_dispatch_public($msg);
|
||||
else
|
||||
$ret = diaspora_dispatch($importer,$msg);
|
||||
if($public) {
|
||||
diaspora::dispatch_public($msg);
|
||||
} else {
|
||||
$ret = diaspora::dispatch($importer,$msg);
|
||||
}
|
||||
|
||||
http_status_exit(($ret) ? $ret : 200);
|
||||
// NOTREACHED
|
||||
|
|
|
|||
|
|
@ -84,7 +84,7 @@ function salmon_post(&$a) {
|
|||
// decode the data
|
||||
$data = base64url_decode($data);
|
||||
|
||||
$author = ostatus_salmon_author($data,$importer);
|
||||
$author = ostatus::salmon_author($data,$importer);
|
||||
$author_link = $author["author-link"];
|
||||
|
||||
if(! $author_link) {
|
||||
|
|
@ -181,7 +181,7 @@ function salmon_post(&$a) {
|
|||
|
||||
$contact_rec = ((count($r)) ? $r[0] : null);
|
||||
|
||||
ostatus_import($data,$importer,$contact_rec, $hub);
|
||||
ostatus::import($data,$importer,$contact_rec, $hub);
|
||||
|
||||
http_status_exit(200);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -147,7 +147,7 @@ function search_content(&$a) {
|
|||
}
|
||||
|
||||
|
||||
$o .= search($search,'search-box','/search',((local_user()) ? true : false), false);
|
||||
$o .= search($search,'search-box','search',((local_user()) ? true : false), false);
|
||||
|
||||
if(strpos($search,'#') === 0) {
|
||||
$tag = true;
|
||||
|
|
@ -217,11 +217,10 @@ function search_content(&$a) {
|
|||
FROM `item`
|
||||
INNER JOIN `contact` ON `contact`.`id` = `item`.`contact-id` AND NOT `contact`.`blocked` AND NOT `contact`.`pending`
|
||||
WHERE `item`.`visible` AND NOT `item`.`deleted` AND NOT `item`.`moderated`
|
||||
AND (`item`.`uid` = 0 OR (`item`.`uid` = %s AND (`item`.`private` OR NOT `item`.`network` IN ('%s', '%s', '%s'))))
|
||||
AND (`item`.`uid` = 0 OR (`item`.`uid` = %s AND NOT `item`.`global`))
|
||||
$sql_extra
|
||||
GROUP BY `item`.`uri` ORDER BY `item`.`id` DESC LIMIT %d , %d ",
|
||||
intval(local_user()), dbesc(NETWORK_DFRN), dbesc(NETWORK_OSTATUS), dbesc(NETWORK_DIASPORA),
|
||||
intval($a->pager['start']), intval($a->pager['itemspage']));
|
||||
intval(local_user()), intval($a->pager['start']), intval($a->pager['itemspage']));
|
||||
}
|
||||
|
||||
if(! count($r)) {
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
<?php
|
||||
|
||||
require_once('include/group.php');
|
||||
|
||||
function get_theme_config_file($theme){
|
||||
$a = get_app();
|
||||
|
|
@ -39,7 +40,7 @@ function settings_init(&$a) {
|
|||
$tabs = array(
|
||||
array(
|
||||
'label' => t('Account'),
|
||||
'url' => $a->get_baseurl(true).'/settings',
|
||||
'url' => 'settings',
|
||||
'selected' => (($a->argc == 1) && ($a->argv[0] === 'settings')?'active':''),
|
||||
'accesskey' => 'o',
|
||||
),
|
||||
|
|
@ -48,7 +49,7 @@ function settings_init(&$a) {
|
|||
if(get_features()) {
|
||||
$tabs[] = array(
|
||||
'label' => t('Additional features'),
|
||||
'url' => $a->get_baseurl(true).'/settings/features',
|
||||
'url' => 'settings/features',
|
||||
'selected' => (($a->argc > 1) && ($a->argv[1] === 'features') ? 'active' : ''),
|
||||
'accesskey' => 't',
|
||||
);
|
||||
|
|
@ -56,49 +57,49 @@ function settings_init(&$a) {
|
|||
|
||||
$tabs[] = array(
|
||||
'label' => t('Display'),
|
||||
'url' => $a->get_baseurl(true).'/settings/display',
|
||||
'url' => 'settings/display',
|
||||
'selected' => (($a->argc > 1) && ($a->argv[1] === 'display')?'active':''),
|
||||
'accesskey' => 'i',
|
||||
);
|
||||
|
||||
$tabs[] = array(
|
||||
'label' => t('Social Networks'),
|
||||
'url' => $a->get_baseurl(true).'/settings/connectors',
|
||||
'url' => 'settings/connectors',
|
||||
'selected' => (($a->argc > 1) && ($a->argv[1] === 'connectors')?'active':''),
|
||||
'accesskey' => 'w',
|
||||
);
|
||||
|
||||
$tabs[] = array(
|
||||
'label' => t('Plugins'),
|
||||
'url' => $a->get_baseurl(true).'/settings/addon',
|
||||
'url' => 'settings/addon',
|
||||
'selected' => (($a->argc > 1) && ($a->argv[1] === 'addon')?'active':''),
|
||||
'accesskey' => 'l',
|
||||
);
|
||||
|
||||
$tabs[] = array(
|
||||
'label' => t('Delegations'),
|
||||
'url' => $a->get_baseurl(true).'/delegate',
|
||||
'url' => 'delegate',
|
||||
'selected' => (($a->argc == 1) && ($a->argv[0] === 'delegate')?'active':''),
|
||||
'accesskey' => 'd',
|
||||
);
|
||||
|
||||
$tabs[] = array(
|
||||
'label' => t('Connected apps'),
|
||||
'url' => $a->get_baseurl(true) . '/settings/oauth',
|
||||
'url' => 'settings/oauth',
|
||||
'selected' => (($a->argc > 1) && ($a->argv[1] === 'oauth')?'active':''),
|
||||
'accesskey' => 'b',
|
||||
);
|
||||
|
||||
$tabs[] = array(
|
||||
'label' => t('Export personal data'),
|
||||
'url' => $a->get_baseurl(true) . '/uexport',
|
||||
'url' => 'uexport',
|
||||
'selected' => (($a->argc == 1) && ($a->argv[0] === 'uexport')?'active':''),
|
||||
'accesskey' => 'e',
|
||||
);
|
||||
|
||||
$tabs[] = array(
|
||||
'label' => t('Remove account'),
|
||||
'url' => $a->get_baseurl(true) . '/removeme',
|
||||
'url' => 'removeme',
|
||||
'selected' => (($a->argc == 1) && ($a->argv[0] === 'removeme')?'active':''),
|
||||
'accesskey' => 'r',
|
||||
);
|
||||
|
|
@ -199,6 +200,7 @@ function settings_post(&$a) {
|
|||
if(x($_POST, 'general-submit')) {
|
||||
set_pconfig(local_user(), 'system', 'no_intelligent_shortening', intval($_POST['no_intelligent_shortening']));
|
||||
set_pconfig(local_user(), 'system', 'ostatus_autofriend', intval($_POST['snautofollow']));
|
||||
set_pconfig(local_user(), 'ostatus', 'default_group', $_POST['group-selection']);
|
||||
set_pconfig(local_user(), 'ostatus', 'legacy_contact', $_POST['legacy_contact']);
|
||||
} elseif(x($_POST, 'imap-submit')) {
|
||||
|
||||
|
|
@ -342,7 +344,7 @@ function settings_post(&$a) {
|
|||
);
|
||||
|
||||
call_hooks('display_settings_post', $_POST);
|
||||
goaway($a->get_baseurl(true) . '/settings/display' );
|
||||
goaway('settings/display' );
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -351,7 +353,7 @@ function settings_post(&$a) {
|
|||
if (x($_POST,'resend_relocate')) {
|
||||
proc_run('php', 'include/notifier.php', 'relocate', local_user());
|
||||
info(t("Relocate message has been send to your contacts"));
|
||||
goaway($a->get_baseurl(true) . '/settings');
|
||||
goaway('settings');
|
||||
}
|
||||
|
||||
call_hooks('settings_post', $_POST);
|
||||
|
|
@ -627,7 +629,7 @@ function settings_post(&$a) {
|
|||
|
||||
}
|
||||
|
||||
goaway($a->get_baseurl(true) . '/settings' );
|
||||
goaway('settings' );
|
||||
return; // NOTREACHED
|
||||
}
|
||||
|
||||
|
|
@ -797,8 +799,11 @@ function settings_content(&$a) {
|
|||
$settings_connectors .= '<span class="field_help">'.t('If you receive a message from an unknown OStatus user, this option decides what to do. If it is checked, a new contact will be created for every unknown user.').'</span>';
|
||||
$settings_connectors .= '</div>';
|
||||
|
||||
$default_group = get_pconfig(local_user(), 'ostatus', 'default_group');
|
||||
$legacy_contact = get_pconfig(local_user(), 'ostatus', 'legacy_contact');
|
||||
|
||||
$settings_connectors .= mini_group_select(local_user(), $default_group, t("Default group for OStatus contacts"));
|
||||
|
||||
if ($legacy_contact != "")
|
||||
$a->page['htmlhead'] = '<meta http-equiv="refresh" content="0; URL='.$a->get_baseurl().'/ostatus_subscribe?url='.urlencode($legacy_contact).'">';
|
||||
|
||||
|
|
@ -1152,7 +1157,7 @@ function settings_content(&$a) {
|
|||
info( t('Profile is <strong>not published</strong>.') . EOL );
|
||||
|
||||
|
||||
//$subdir = ((strlen($a->get_path())) ? '<br />' . t('or') . ' ' . $a->get_baseurl(true) . '/profile/' . $nickname : '');
|
||||
//$subdir = ((strlen($a->get_path())) ? '<br />' . t('or') . ' ' . 'profile/' . $nickname : '');
|
||||
|
||||
$tpl_addr = get_markup_template("settings_nick_set.tpl");
|
||||
|
||||
|
|
|
|||
|
|
@ -103,10 +103,11 @@ EOT;
|
|||
$bodyverb = t('%1$s is following %2$s\'s %3$s');
|
||||
|
||||
if(! isset($bodyverb))
|
||||
return;
|
||||
return;
|
||||
|
||||
$arr = array();
|
||||
|
||||
$arr['guid'] = get_guid(32);
|
||||
$arr['uri'] = $uri;
|
||||
$arr['uid'] = $owner_uid;
|
||||
$arr['contact-id'] = $contact['id'];
|
||||
|
|
@ -123,7 +124,7 @@ EOT;
|
|||
$arr['author-name'] = $contact['name'];
|
||||
$arr['author-link'] = $contact['url'];
|
||||
$arr['author-avatar'] = $contact['thumb'];
|
||||
|
||||
|
||||
$ulink = '[url=' . $contact['url'] . ']' . $contact['name'] . '[/url]';
|
||||
$alink = '[url=' . $item['author-link'] . ']' . $item['author-name'] . '[/url]';
|
||||
$plink = '[url=' . $a->get_baseurl() . '/display/' . $owner['nickname'] . '/' . $item['id'] . ']' . $post_type . '[/url]';
|
||||
|
|
|
|||
|
|
@ -95,12 +95,13 @@ EOT;
|
|||
$bodyverb = t('%1$s tagged %2$s\'s %3$s with %4$s');
|
||||
|
||||
if(! isset($bodyverb))
|
||||
return;
|
||||
return;
|
||||
|
||||
$termlink = html_entity_decode('⌗') . '[url=' . $a->get_baseurl() . '/search?tag=' . urlencode($term) . ']'. $term . '[/url]';
|
||||
|
||||
$arr = array();
|
||||
|
||||
$arr['guid'] = get_guid(32);
|
||||
$arr['uri'] = $uri;
|
||||
$arr['uid'] = $owner_uid;
|
||||
$arr['contact-id'] = $contact['id'];
|
||||
|
|
@ -115,7 +116,7 @@ EOT;
|
|||
$arr['author-name'] = $contact['name'];
|
||||
$arr['author-link'] = $contact['url'];
|
||||
$arr['author-avatar'] = $contact['thumb'];
|
||||
|
||||
|
||||
$ulink = '[url=' . $contact['url'] . ']' . $contact['name'] . '[/url]';
|
||||
$alink = '[url=' . $item['author-link'] . ']' . $item['author-name'] . '[/url]';
|
||||
$plink = '[url=' . $item['plink'] . ']' . $post_type . '[/url]';
|
||||
|
|
|
|||
|
|
@ -6,54 +6,6 @@ function uexport_init(&$a){
|
|||
|
||||
require_once("mod/settings.php");
|
||||
settings_init($a);
|
||||
|
||||
/*
|
||||
$tabs = array(
|
||||
array(
|
||||
'label' => t('Account settings'),
|
||||
'url' => $a->get_baseurl(true).'/settings',
|
||||
'selected' => '',
|
||||
),
|
||||
array(
|
||||
'label' => t('Display settings'),
|
||||
'url' => $a->get_baseurl(true).'/settings/display',
|
||||
'selected' =>'',
|
||||
),
|
||||
|
||||
array(
|
||||
'label' => t('Connector settings'),
|
||||
'url' => $a->get_baseurl(true).'/settings/connectors',
|
||||
'selected' => '',
|
||||
),
|
||||
array(
|
||||
'label' => t('Plugin settings'),
|
||||
'url' => $a->get_baseurl(true).'/settings/addon',
|
||||
'selected' => '',
|
||||
),
|
||||
array(
|
||||
'label' => t('Connected apps'),
|
||||
'url' => $a->get_baseurl(true) . '/settings/oauth',
|
||||
'selected' => '',
|
||||
),
|
||||
array(
|
||||
'label' => t('Export personal data'),
|
||||
'url' => $a->get_baseurl(true) . '/uexport',
|
||||
'selected' => 'active'
|
||||
),
|
||||
array(
|
||||
'label' => t('Remove account'),
|
||||
'url' => $a->get_baseurl(true) . '/removeme',
|
||||
'selected' => ''
|
||||
)
|
||||
);
|
||||
|
||||
$tabtpl = get_markup_template("generic_links_widget.tpl");
|
||||
$a->page['aside'] = replace_macros($tabtpl, array(
|
||||
'$title' => t('Settings'),
|
||||
'$class' => 'settings-widget',
|
||||
'$items' => $tabs,
|
||||
));
|
||||
*/
|
||||
}
|
||||
|
||||
function uexport_content(&$a){
|
||||
|
|
@ -74,8 +26,8 @@ function uexport_content(&$a){
|
|||
* list of array( 'link url', 'link text', 'help text' )
|
||||
*/
|
||||
$options = array(
|
||||
array('/uexport/account',t('Export account'),t('Export your account info and contacts. Use this to make a backup of your account and/or to move it to another server.')),
|
||||
array('/uexport/backup',t('Export all'),t('Export your accout info, contacts and all your items as json. Could be a very big file, and could take a lot of time. Use this to make a full backup of your account (photos are not exported)')),
|
||||
array('uexport/account',t('Export account'),t('Export your account info and contacts. Use this to make a backup of your account and/or to move it to another server.')),
|
||||
array('uexport/backup',t('Export all'),t('Export your accout info, contacts and all your items as json. Could be a very big file, and could take a lot of time. Use this to make a full backup of your account (photos are not exported)')),
|
||||
);
|
||||
call_hooks('uexport_options', $options);
|
||||
|
||||
|
|
@ -153,9 +105,9 @@ function uexport_account($a){
|
|||
'version' => FRIENDICA_VERSION,
|
||||
'schema' => DB_UPDATE_VERSION,
|
||||
'baseurl' => $a->get_baseurl(),
|
||||
'user' => $user,
|
||||
'contact' => $contact,
|
||||
'profile' => $profile,
|
||||
'user' => $user,
|
||||
'contact' => $contact,
|
||||
'profile' => $profile,
|
||||
'photo' => $photo,
|
||||
'pconfig' => $pconfig,
|
||||
'group' => $group,
|
||||
|
|
@ -171,8 +123,8 @@ function uexport_account($a){
|
|||
* echoes account data and items as separated json, one per line
|
||||
*/
|
||||
function uexport_all(&$a) {
|
||||
|
||||
uexport_account($a);
|
||||
|
||||
uexport_account($a);
|
||||
echo "\n";
|
||||
|
||||
$r = q("SELECT count(*) as `total` FROM `item` WHERE `uid` = %d ",
|
||||
|
|
|
|||
|
|
@ -50,7 +50,7 @@ class Item extends BaseObject {
|
|||
$this->writable = ($this->get_data_value('writable') || $this->get_data_value('self'));
|
||||
|
||||
$ssl_state = ((local_user()) ? true : false);
|
||||
$this->redirect_url = $a->get_baseurl($ssl_state) . '/redir/' . $this->get_data_value('cid') ;
|
||||
$this->redirect_url = 'redir/' . $this->get_data_value('cid') ;
|
||||
|
||||
if(get_config('system','thread_allow') && $a->theme_thread_allow && !$this->is_toplevel())
|
||||
$this->threaded = true;
|
||||
|
|
@ -119,9 +119,9 @@ class Item extends BaseObject {
|
|||
$shareable = ((($conv->get_profile_owner() == local_user()) && ($item['private'] != 1)) ? true : false);
|
||||
if(local_user() && link_compare($a->contact['url'],$item['author-link'])) {
|
||||
if ($item["event-id"] != 0)
|
||||
$edpost = array($a->get_baseurl($ssl_state)."/events/event/".$item['event-id'], t("Edit"));
|
||||
$edpost = array("events/event/".$item['event-id'], t("Edit"));
|
||||
else
|
||||
$edpost = array($a->get_baseurl($ssl_state)."/editpost/".$item['id'], t("Edit"));
|
||||
$edpost = array("editpost/".$item['id'], t("Edit"));
|
||||
} else
|
||||
$edpost = false;
|
||||
if(($this->get_data_value('uid') == local_user()) || $this->is_visiting())
|
||||
|
|
@ -154,13 +154,13 @@ class Item extends BaseObject {
|
|||
if(($normalised != 'mailbox') && (x($a->contacts,$normalised)))
|
||||
$profile_avatar = $a->contacts[$normalised]['thumb'];
|
||||
else
|
||||
$profile_avatar = (((strlen($item['author-avatar'])) && $diff_author) ? $item['author-avatar'] : $a->get_cached_avatar_image($this->get_data_value('thumb')));
|
||||
$profile_avatar = (((strlen($item['author-avatar'])) && $diff_author) ? $item['author-avatar'] : $a->remove_baseurl($this->get_data_value('thumb')));
|
||||
|
||||
$locate = array('location' => $item['location'], 'coord' => $item['coord'], 'html' => '');
|
||||
call_hooks('render_location',$locate);
|
||||
$location = ((strlen($locate['html'])) ? $locate['html'] : render_location_dummy($locate));
|
||||
|
||||
$searchpath = $a->get_baseurl()."/search?tag=";
|
||||
$searchpath = "search?tag=";
|
||||
$tags=array();
|
||||
$hashtags = array();
|
||||
$mentions = array();
|
||||
|
|
@ -324,7 +324,7 @@ class Item extends BaseObject {
|
|||
|
||||
// Diaspora isn't able to do likes on comments - but red does
|
||||
if (($item["item_network"] == NETWORK_DIASPORA) AND ($indent == 'comment') AND
|
||||
!diaspora_is_redmatrix($item["owner-link"]) AND isset($buttons["like"]))
|
||||
!diaspora::is_redmatrix($item["owner-link"]) AND isset($buttons["like"]))
|
||||
unset($buttons["like"]);
|
||||
|
||||
// Diaspora doesn't has multithreaded comments
|
||||
|
|
@ -703,9 +703,9 @@ class Item extends BaseObject {
|
|||
'$parent' => $this->get_id(),
|
||||
'$qcomment' => $qcomment,
|
||||
'$profile_uid' => $conv->get_profile_owner(),
|
||||
'$mylink' => $a->contact['url'],
|
||||
'$mylink' => $a->remove_baseurl($a->contact['url']),
|
||||
'$mytitle' => t('This is you'),
|
||||
'$myphoto' => $a->contact['thumb'],
|
||||
'$myphoto' => $a->remove_baseurl($a->contact['thumb']),
|
||||
'$comment' => t('Comment'),
|
||||
'$submit' => t('Submit'),
|
||||
'$edbold' => t('Bold'),
|
||||
|
|
|
|||
94
util/createdoxygen.php
Normal file
94
util/createdoxygen.php
Normal file
|
|
@ -0,0 +1,94 @@
|
|||
#!/usr/bin/php
|
||||
<?php
|
||||
/**
|
||||
* @file util/createdoxygen.php
|
||||
* @brief Adds a doxygen header to functions
|
||||
*/
|
||||
|
||||
if (count($_SERVER["argv"]) < 2)
|
||||
die("usage: createdoxygen.php file\n");
|
||||
|
||||
$file = $_SERVER["argv"][1];
|
||||
$data = file_get_contents($file);
|
||||
|
||||
$lines = explode("\n", $data);
|
||||
|
||||
$previous = "";
|
||||
|
||||
foreach ($lines AS $line) {
|
||||
$line = rtrim(trim($line, "\r"));
|
||||
|
||||
if (strstr(strtolower($line), "function")) {
|
||||
$detect = strtolower(trim($line));
|
||||
$detect = implode(" ", explode(" ", $detect));
|
||||
|
||||
$found = false;
|
||||
|
||||
if (substr($detect, 0, 9) == "function ")
|
||||
$found = true;
|
||||
|
||||
if (substr($detect, 0, 17) == "private function ")
|
||||
$found = true;
|
||||
|
||||
if (substr($detect, 0, 23) == "public static function ")
|
||||
$found = true;
|
||||
|
||||
if (substr($detect, 0, 10) == "function (")
|
||||
$found = false;
|
||||
|
||||
if ($found and (trim($previous) == "*/"))
|
||||
$found = false;
|
||||
|
||||
if ($found and !strstr($detect, "{"))
|
||||
$found = false;
|
||||
|
||||
if ($found) {
|
||||
echo add_documentation($line);
|
||||
}
|
||||
}
|
||||
echo $line."\n";
|
||||
$previous = $line;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Adds a doxygen header
|
||||
*
|
||||
* @param string $line The current line of the document
|
||||
*
|
||||
* @return string added doxygen header
|
||||
*/
|
||||
function add_documentation($line) {
|
||||
|
||||
$trimmed = ltrim($line);
|
||||
$length = strlen($line) - strlen($trimmed);
|
||||
$space = substr($line, 0, $length);
|
||||
|
||||
$block = $space."/**\n".
|
||||
$space." * @brief \n".
|
||||
$space." *\n"; /**/
|
||||
|
||||
|
||||
$left = strpos($line, "(");
|
||||
$line = substr($line, $left + 1);
|
||||
|
||||
$right = strpos($line, ")");
|
||||
$line = trim(substr($line, 0, $right));
|
||||
|
||||
if ($line != "") {
|
||||
$parameters = explode(",", $line);
|
||||
foreach ($parameters AS $parameter) {
|
||||
$parameter = trim($parameter);
|
||||
$splitted = explode("=", $parameter);
|
||||
|
||||
$block .= $space." * @param ".trim($splitted[0], "& ")."\n";
|
||||
}
|
||||
if (count($parameters) > 0)
|
||||
$block .= $space." *\n";
|
||||
}
|
||||
|
||||
$block .= $space." * @return \n".
|
||||
$space." */\n";
|
||||
|
||||
return $block;
|
||||
}
|
||||
?>
|
||||
2187
util/messages.po
2187
util/messages.po
|
|
@ -8,7 +8,7 @@ msgid ""
|
|||
msgstr ""
|
||||
"Project-Id-Version: \n"
|
||||
"Report-Msgid-Bugs-To: \n"
|
||||
"POT-Creation-Date: 2016-01-24 06:49+0100\n"
|
||||
"POT-Creation-Date: 2016-03-12 07:34+0100\n"
|
||||
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
|
||||
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
|
||||
"Language-Team: LANGUAGE <LL@li.org>\n"
|
||||
|
|
@ -18,15 +18,15 @@ msgstr ""
|
|||
"Content-Transfer-Encoding: 8bit\n"
|
||||
|
||||
|
||||
#: mod/contacts.php:50 include/identity.php:395
|
||||
#: mod/contacts.php:50 include/identity.php:396
|
||||
msgid "Network:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:51 mod/contacts.php:961 mod/videos.php:37
|
||||
#: mod/contacts.php:51 mod/contacts.php:947 mod/videos.php:37
|
||||
#: mod/viewcontacts.php:105 mod/dirfind.php:214 mod/network.php:598
|
||||
#: mod/allfriends.php:77 mod/match.php:82 mod/directory.php:172
|
||||
#: mod/common.php:123 mod/suggest.php:95 mod/photos.php:41
|
||||
#: include/identity.php:298
|
||||
#: include/identity.php:299
|
||||
msgid "Forum"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -37,7 +37,7 @@ msgid_plural "%d contacts edited."
|
|||
msgstr[0] ""
|
||||
msgstr[1] ""
|
||||
|
||||
#: mod/contacts.php:159 mod/contacts.php:383
|
||||
#: mod/contacts.php:159 mod/contacts.php:368
|
||||
msgid "Could not access contact record."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -49,150 +49,150 @@ msgstr ""
|
|||
msgid "Contact updated."
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:208 mod/dfrn_request.php:575
|
||||
#: mod/contacts.php:208 mod/dfrn_request.php:573
|
||||
msgid "Failed to update contact record."
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:365 mod/manage.php:96 mod/display.php:509
|
||||
#: mod/contacts.php:350 mod/manage.php:96 mod/display.php:513
|
||||
#: mod/profile_photo.php:19 mod/profile_photo.php:175 mod/profile_photo.php:186
|
||||
#: mod/profile_photo.php:199 mod/ostatus_subscribe.php:9 mod/follow.php:11
|
||||
#: mod/follow.php:73 mod/follow.php:155 mod/item.php:180 mod/item.php:192
|
||||
#: mod/follow.php:73 mod/follow.php:155 mod/item.php:183 mod/item.php:195
|
||||
#: mod/group.php:19 mod/dfrn_confirm.php:55 mod/fsuggest.php:78
|
||||
#: mod/wall_upload.php:77 mod/wall_upload.php:80 mod/viewcontacts.php:40
|
||||
#: mod/notifications.php:69 mod/message.php:45 mod/message.php:181
|
||||
#: mod/crepair.php:117 mod/dirfind.php:11 mod/nogroup.php:25 mod/network.php:4
|
||||
#: mod/crepair.php:100 mod/dirfind.php:11 mod/nogroup.php:25 mod/network.php:4
|
||||
#: mod/allfriends.php:12 mod/events.php:165 mod/wallmessage.php:9
|
||||
#: mod/wallmessage.php:33 mod/wallmessage.php:79 mod/wallmessage.php:103
|
||||
#: mod/wall_attach.php:67 mod/wall_attach.php:70 mod/settings.php:20
|
||||
#: mod/settings.php:126 mod/settings.php:646 mod/register.php:42
|
||||
#: mod/settings.php:126 mod/settings.php:647 mod/register.php:42
|
||||
#: mod/delegate.php:12 mod/common.php:18 mod/mood.php:114 mod/suggest.php:58
|
||||
#: mod/profiles.php:165 mod/profiles.php:615 mod/editpost.php:10 mod/api.php:26
|
||||
#: mod/profiles.php:165 mod/profiles.php:593 mod/editpost.php:10 mod/api.php:26
|
||||
#: mod/api.php:31 mod/notes.php:22 mod/poke.php:149 mod/repair_ostatus.php:9
|
||||
#: mod/invite.php:15 mod/invite.php:101 mod/photos.php:171 mod/photos.php:1105
|
||||
#: mod/invite.php:15 mod/invite.php:101 mod/photos.php:171 mod/photos.php:1091
|
||||
#: mod/regmod.php:110 mod/uimport.php:23 mod/attach.php:33
|
||||
#: include/items.php:5096 index.php:383
|
||||
#: include/items.php:2002 index.php:384
|
||||
msgid "Permission denied."
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:404
|
||||
#: mod/contacts.php:389
|
||||
msgid "Contact has been blocked"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:404
|
||||
#: mod/contacts.php:389
|
||||
msgid "Contact has been unblocked"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:415
|
||||
#: mod/contacts.php:400
|
||||
msgid "Contact has been ignored"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:415
|
||||
#: mod/contacts.php:400
|
||||
msgid "Contact has been unignored"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:427
|
||||
#: mod/contacts.php:412
|
||||
msgid "Contact has been archived"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:427
|
||||
#: mod/contacts.php:412
|
||||
msgid "Contact has been unarchived"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:454 mod/contacts.php:802
|
||||
#: mod/contacts.php:439 mod/contacts.php:794
|
||||
msgid "Do you really want to delete this contact?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:456 mod/follow.php:110 mod/message.php:216
|
||||
#: mod/settings.php:1103 mod/settings.php:1109 mod/settings.php:1117
|
||||
#: mod/settings.php:1121 mod/settings.php:1126 mod/settings.php:1132
|
||||
#: mod/settings.php:1138 mod/settings.php:1144 mod/settings.php:1170
|
||||
#: mod/settings.php:1171 mod/settings.php:1172 mod/settings.php:1173
|
||||
#: mod/settings.php:1174 mod/dfrn_request.php:857 mod/register.php:238
|
||||
#: mod/suggest.php:29 mod/profiles.php:658 mod/profiles.php:661
|
||||
#: mod/profiles.php:687 mod/api.php:105 include/items.php:4928
|
||||
#: mod/contacts.php:441 mod/follow.php:110 mod/message.php:216
|
||||
#: mod/settings.php:1107 mod/settings.php:1113 mod/settings.php:1121
|
||||
#: mod/settings.php:1125 mod/settings.php:1130 mod/settings.php:1136
|
||||
#: mod/settings.php:1142 mod/settings.php:1148 mod/settings.php:1174
|
||||
#: mod/settings.php:1175 mod/settings.php:1176 mod/settings.php:1177
|
||||
#: mod/settings.php:1178 mod/dfrn_request.php:855 mod/register.php:238
|
||||
#: mod/suggest.php:29 mod/profiles.php:636 mod/profiles.php:639
|
||||
#: mod/profiles.php:665 mod/api.php:105 include/items.php:1834
|
||||
msgid "Yes"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:459 mod/tagrm.php:11 mod/tagrm.php:94 mod/follow.php:121
|
||||
#: mod/contacts.php:444 mod/tagrm.php:11 mod/tagrm.php:94 mod/follow.php:121
|
||||
#: mod/videos.php:131 mod/message.php:219 mod/fbrowser.php:93
|
||||
#: mod/fbrowser.php:128 mod/settings.php:660 mod/settings.php:686
|
||||
#: mod/dfrn_request.php:871 mod/suggest.php:32 mod/editpost.php:148
|
||||
#: mod/fbrowser.php:128 mod/settings.php:661 mod/settings.php:687
|
||||
#: mod/dfrn_request.php:869 mod/suggest.php:32 mod/editpost.php:148
|
||||
#: mod/photos.php:247 mod/photos.php:336 include/conversation.php:1220
|
||||
#: include/items.php:4931
|
||||
#: include/items.php:1837
|
||||
msgid "Cancel"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:471
|
||||
#: mod/contacts.php:456
|
||||
msgid "Contact has been removed."
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:512
|
||||
#: mod/contacts.php:497
|
||||
#, php-format
|
||||
msgid "You are mutual friends with %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:516
|
||||
#: mod/contacts.php:501
|
||||
#, php-format
|
||||
msgid "You are sharing with %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:521
|
||||
#: mod/contacts.php:506
|
||||
#, php-format
|
||||
msgid "%s is sharing with you"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:541
|
||||
#: mod/contacts.php:526
|
||||
msgid "Private communications are not available for this contact."
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:544 mod/admin.php:822
|
||||
#: mod/contacts.php:529 mod/admin.php:838
|
||||
msgid "Never"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:548
|
||||
#: mod/contacts.php:533
|
||||
msgid "(Update was successful)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:548
|
||||
#: mod/contacts.php:533
|
||||
msgid "(Update was not successful)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:550
|
||||
#: mod/contacts.php:535 mod/contacts.php:972
|
||||
msgid "Suggest friends"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:554
|
||||
#: mod/contacts.php:539
|
||||
#, php-format
|
||||
msgid "Network type: %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:567
|
||||
#: mod/contacts.php:552
|
||||
msgid "Communications lost with this contact!"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:570
|
||||
#: mod/contacts.php:555
|
||||
msgid "Fetch further information for feeds"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:571 mod/admin.php:831
|
||||
#: mod/contacts.php:556 mod/admin.php:847
|
||||
msgid "Disabled"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:571
|
||||
#: mod/contacts.php:556
|
||||
msgid "Fetch information"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:571
|
||||
#: mod/contacts.php:556
|
||||
msgid "Fetch information and keywords"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:587 mod/manage.php:143 mod/fsuggest.php:107
|
||||
#: mod/message.php:342 mod/message.php:525 mod/crepair.php:196
|
||||
#: mod/contacts.php:575 mod/manage.php:143 mod/fsuggest.php:107
|
||||
#: mod/message.php:342 mod/message.php:525 mod/crepair.php:179
|
||||
#: mod/events.php:574 mod/content.php:712 mod/install.php:261
|
||||
#: mod/install.php:299 mod/mood.php:137 mod/profiles.php:696
|
||||
#: mod/localtime.php:45 mod/poke.php:198 mod/invite.php:140 mod/photos.php:1137
|
||||
#: mod/photos.php:1261 mod/photos.php:1579 mod/photos.php:1630
|
||||
#: mod/photos.php:1678 mod/photos.php:1766 object/Item.php:710
|
||||
#: mod/install.php:299 mod/mood.php:137 mod/profiles.php:674
|
||||
#: mod/localtime.php:45 mod/poke.php:198 mod/invite.php:140 mod/photos.php:1123
|
||||
#: mod/photos.php:1247 mod/photos.php:1565 mod/photos.php:1616
|
||||
#: mod/photos.php:1664 mod/photos.php:1752 object/Item.php:710
|
||||
#: view/theme/cleanzero/config.php:80 view/theme/dispy/config.php:70
|
||||
#: view/theme/quattro/config.php:64 view/theme/diabook/config.php:148
|
||||
#: view/theme/diabook/theme.php:633 view/theme/vier/config.php:107
|
||||
|
|
@ -200,306 +200,316 @@ msgstr ""
|
|||
msgid "Submit"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:588
|
||||
#: mod/contacts.php:576
|
||||
msgid "Profile Visibility"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:589
|
||||
#: mod/contacts.php:577
|
||||
#, php-format
|
||||
msgid ""
|
||||
"Please choose the profile you would like to display to %s when viewing your "
|
||||
"profile securely."
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:590
|
||||
#: mod/contacts.php:578
|
||||
msgid "Contact Information / Notes"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:591
|
||||
#: mod/contacts.php:579
|
||||
msgid "Edit contact notes"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:596 mod/contacts.php:952 mod/viewcontacts.php:97
|
||||
#: mod/contacts.php:584 mod/contacts.php:938 mod/viewcontacts.php:97
|
||||
#: mod/nogroup.php:41
|
||||
#, php-format
|
||||
msgid "Visit %s's profile [%s]"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:597
|
||||
#: mod/contacts.php:585
|
||||
msgid "Block/Unblock contact"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:598
|
||||
#: mod/contacts.php:586
|
||||
msgid "Ignore contact"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:599
|
||||
#: mod/contacts.php:587
|
||||
msgid "Repair URL settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:600
|
||||
#: mod/contacts.php:588
|
||||
msgid "View conversations"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:602
|
||||
msgid "Delete contact"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:606
|
||||
#: mod/contacts.php:594
|
||||
msgid "Last update:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:608
|
||||
#: mod/contacts.php:596
|
||||
msgid "Update public posts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:610
|
||||
#: mod/contacts.php:598 mod/contacts.php:982
|
||||
msgid "Update now"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:612 mod/follow.php:103 mod/dirfind.php:196
|
||||
#: mod/contacts.php:600 mod/follow.php:103 mod/dirfind.php:196
|
||||
#: mod/allfriends.php:65 mod/match.php:71 mod/suggest.php:82
|
||||
#: include/contact_widgets.php:32 include/Contact.php:297
|
||||
#: include/contact_widgets.php:32 include/Contact.php:299
|
||||
#: include/conversation.php:924
|
||||
msgid "Connect/Follow"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:615 mod/contacts.php:806 mod/contacts.php:865
|
||||
#: mod/admin.php:1312
|
||||
#: mod/contacts.php:603 mod/contacts.php:798 mod/contacts.php:991
|
||||
#: mod/admin.php:1334
|
||||
msgid "Unblock"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:615 mod/contacts.php:806 mod/contacts.php:865
|
||||
#: mod/admin.php:1311
|
||||
#: mod/contacts.php:603 mod/contacts.php:798 mod/contacts.php:991
|
||||
#: mod/admin.php:1333
|
||||
msgid "Block"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:616 mod/contacts.php:807 mod/contacts.php:872
|
||||
#: mod/contacts.php:604 mod/contacts.php:799 mod/contacts.php:999
|
||||
msgid "Unignore"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:616 mod/contacts.php:807 mod/contacts.php:872
|
||||
#: mod/contacts.php:604 mod/contacts.php:799 mod/contacts.php:999
|
||||
#: mod/notifications.php:54 mod/notifications.php:179 mod/notifications.php:259
|
||||
msgid "Ignore"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:619
|
||||
#: mod/contacts.php:607
|
||||
msgid "Currently blocked"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:620
|
||||
#: mod/contacts.php:608
|
||||
msgid "Currently ignored"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:621
|
||||
#: mod/contacts.php:609
|
||||
msgid "Currently archived"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:622 mod/notifications.php:172 mod/notifications.php:251
|
||||
#: mod/contacts.php:610 mod/notifications.php:172 mod/notifications.php:251
|
||||
msgid "Hide this contact from others"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:622
|
||||
#: mod/contacts.php:610
|
||||
msgid ""
|
||||
"Replies/likes to your public posts <strong>may</strong> still be visible"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:623
|
||||
#: mod/contacts.php:611
|
||||
msgid "Notification for new posts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:623
|
||||
#: mod/contacts.php:611
|
||||
msgid "Send a notification of every new post of this contact"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:626
|
||||
#: mod/contacts.php:614
|
||||
msgid "Blacklisted keywords"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:626
|
||||
#: mod/contacts.php:614
|
||||
msgid ""
|
||||
"Comma separated list of keywords that should not be converted to hashtags, "
|
||||
"when \"Fetch information and keywords\" is selected"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:633 mod/follow.php:126 mod/notifications.php:255
|
||||
#: mod/contacts.php:621 mod/follow.php:126 mod/notifications.php:255
|
||||
msgid "Profile URL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:636 mod/notifications.php:244 mod/events.php:566
|
||||
#: mod/directory.php:145 include/identity.php:308 include/bb2diaspora.php:170
|
||||
#: mod/contacts.php:624 mod/notifications.php:244 mod/events.php:566
|
||||
#: mod/directory.php:145 include/identity.php:309 include/bb2diaspora.php:170
|
||||
#: include/event.php:36 include/event.php:60
|
||||
msgid "Location:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:638 mod/notifications.php:246 mod/directory.php:153
|
||||
#: include/identity.php:317 include/identity.php:631
|
||||
#: mod/contacts.php:626 mod/notifications.php:246 mod/directory.php:153
|
||||
#: include/identity.php:318 include/identity.php:632
|
||||
msgid "About:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:640 mod/follow.php:134 mod/notifications.php:248
|
||||
#: include/identity.php:625
|
||||
#: mod/contacts.php:628 mod/follow.php:134 mod/notifications.php:248
|
||||
#: include/identity.php:626
|
||||
msgid "Tags:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:685
|
||||
#: mod/contacts.php:629
|
||||
msgid "Actions"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:631 mod/contacts.php:825 include/identity.php:687
|
||||
#: include/nav.php:75
|
||||
msgid "Status"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:632
|
||||
msgid "Contact Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:677
|
||||
msgid "Suggestions"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:688
|
||||
#: mod/contacts.php:680
|
||||
msgid "Suggest potential friends"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:693 mod/group.php:192
|
||||
#: mod/contacts.php:685 mod/group.php:192
|
||||
msgid "All Contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:696
|
||||
#: mod/contacts.php:688
|
||||
msgid "Show all contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:701
|
||||
#: mod/contacts.php:693
|
||||
msgid "Unblocked"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:704
|
||||
#: mod/contacts.php:696
|
||||
msgid "Only show unblocked contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:710
|
||||
#: mod/contacts.php:702
|
||||
msgid "Blocked"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:713
|
||||
#: mod/contacts.php:705
|
||||
msgid "Only show blocked contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:719
|
||||
#: mod/contacts.php:711
|
||||
msgid "Ignored"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:722
|
||||
#: mod/contacts.php:714
|
||||
msgid "Only show ignored contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:728
|
||||
#: mod/contacts.php:720
|
||||
msgid "Archived"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:731
|
||||
#: mod/contacts.php:723
|
||||
msgid "Only show archived contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:737
|
||||
#: mod/contacts.php:729
|
||||
msgid "Hidden"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:740
|
||||
#: mod/contacts.php:732
|
||||
msgid "Only show hidden contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:793 mod/contacts.php:841 mod/viewcontacts.php:116
|
||||
#: include/identity.php:741 include/identity.php:744 include/text.php:1012
|
||||
#: mod/contacts.php:785 mod/contacts.php:845 mod/viewcontacts.php:116
|
||||
#: include/identity.php:742 include/identity.php:745 include/text.php:983
|
||||
#: include/nav.php:123 include/nav.php:187 view/theme/diabook/theme.php:125
|
||||
msgid "Contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:797
|
||||
#: mod/contacts.php:789
|
||||
msgid "Search your contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:798
|
||||
#: mod/contacts.php:790
|
||||
msgid "Finding: "
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:799 mod/directory.php:210 include/contact_widgets.php:34
|
||||
#: mod/contacts.php:791 mod/directory.php:210 include/contact_widgets.php:34
|
||||
msgid "Find"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:805 mod/settings.php:156 mod/settings.php:685
|
||||
#: mod/contacts.php:797 mod/settings.php:156 mod/settings.php:686
|
||||
msgid "Update"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:808 mod/contacts.php:879
|
||||
#: mod/contacts.php:800 mod/contacts.php:1007
|
||||
msgid "Archive"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:808 mod/contacts.php:879
|
||||
#: mod/contacts.php:800 mod/contacts.php:1007
|
||||
msgid "Unarchive"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:809 mod/group.php:171 mod/admin.php:1310
|
||||
#: mod/content.php:440 mod/content.php:743 mod/settings.php:722
|
||||
#: mod/photos.php:1723 object/Item.php:134 include/conversation.php:635
|
||||
#: mod/contacts.php:801 mod/contacts.php:1015 mod/group.php:171
|
||||
#: mod/admin.php:1332 mod/content.php:440 mod/content.php:743
|
||||
#: mod/settings.php:723 mod/photos.php:1709 object/Item.php:134
|
||||
#: include/conversation.php:635
|
||||
msgid "Delete"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:822 include/identity.php:686 include/nav.php:75
|
||||
msgid "Status"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:825 mod/follow.php:143 include/identity.php:689
|
||||
#: mod/contacts.php:828 mod/follow.php:143 include/identity.php:690
|
||||
msgid "Status Messages and Posts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:830 mod/profperm.php:104 mod/newmember.php:32
|
||||
#: include/identity.php:579 include/identity.php:665 include/identity.php:694
|
||||
#: mod/contacts.php:833 mod/profperm.php:104 mod/newmember.php:32
|
||||
#: include/identity.php:580 include/identity.php:666 include/identity.php:695
|
||||
#: include/nav.php:76 view/theme/diabook/theme.php:124
|
||||
msgid "Profile"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:833 include/identity.php:697
|
||||
#: mod/contacts.php:836 include/identity.php:698
|
||||
msgid "Profile Details"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:844
|
||||
#: mod/contacts.php:848
|
||||
msgid "View all contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:850 mod/common.php:134
|
||||
#: mod/contacts.php:855 mod/common.php:134
|
||||
msgid "Common Friends"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:853
|
||||
#: mod/contacts.php:858
|
||||
msgid "View all common friends"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:857
|
||||
msgid "Repair"
|
||||
#: mod/contacts.php:862 mod/admin.php:909
|
||||
msgid "Advanced"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:860
|
||||
#: mod/contacts.php:865
|
||||
msgid "Advanced Contact Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:868
|
||||
msgid "Toggle Blocked status"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:875
|
||||
msgid "Toggle Ignored status"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:882
|
||||
msgid "Toggle Archive status"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:924
|
||||
#: mod/contacts.php:910
|
||||
msgid "Mutual Friendship"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:928
|
||||
#: mod/contacts.php:914
|
||||
msgid "is a fan of yours"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:932
|
||||
#: mod/contacts.php:918
|
||||
msgid "you are a fan of"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:953 mod/nogroup.php:42
|
||||
#: mod/contacts.php:939 mod/nogroup.php:42
|
||||
msgid "Edit contact"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:993
|
||||
msgid "Toggle Blocked status"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:1001
|
||||
msgid "Toggle Ignored status"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:1009
|
||||
msgid "Toggle Archive status"
|
||||
msgstr ""
|
||||
|
||||
#: mod/contacts.php:1017
|
||||
msgid "Delete contact"
|
||||
msgstr ""
|
||||
|
||||
#: mod/hcard.php:10
|
||||
msgid "No profile"
|
||||
msgstr ""
|
||||
|
|
@ -522,7 +532,7 @@ msgstr ""
|
|||
msgid "Post successful."
|
||||
msgstr ""
|
||||
|
||||
#: mod/profperm.php:19 mod/group.php:72 index.php:382
|
||||
#: mod/profperm.php:19 mod/group.php:72 index.php:383
|
||||
msgid "Permission denied"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -546,23 +556,23 @@ msgstr ""
|
|||
msgid "All Contacts (with secure profile access)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/display.php:82 mod/display.php:291 mod/display.php:513
|
||||
#: mod/viewsrc.php:15 mod/admin.php:234 mod/admin.php:1365 mod/admin.php:1599
|
||||
#: mod/notice.php:15 include/items.php:4887
|
||||
#: mod/display.php:82 mod/display.php:298 mod/display.php:517
|
||||
#: mod/viewsrc.php:15 mod/admin.php:234 mod/admin.php:1387 mod/admin.php:1621
|
||||
#: mod/notice.php:15 include/items.php:1793
|
||||
msgid "Item not found."
|
||||
msgstr ""
|
||||
|
||||
#: mod/display.php:220 mod/videos.php:197 mod/viewcontacts.php:35
|
||||
#: mod/community.php:22 mod/dfrn_request.php:786 mod/search.php:93
|
||||
#: mod/search.php:99 mod/directory.php:37 mod/photos.php:976
|
||||
#: mod/display.php:227 mod/videos.php:197 mod/viewcontacts.php:35
|
||||
#: mod/community.php:22 mod/dfrn_request.php:784 mod/search.php:93
|
||||
#: mod/search.php:99 mod/directory.php:37 mod/photos.php:962
|
||||
msgid "Public access denied."
|
||||
msgstr ""
|
||||
|
||||
#: mod/display.php:339 mod/profile.php:155
|
||||
#: mod/display.php:346 mod/profile.php:155
|
||||
msgid "Access to this profile has been restricted."
|
||||
msgstr ""
|
||||
|
||||
#: mod/display.php:506
|
||||
#: mod/display.php:510
|
||||
msgid "Item has been removed."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -597,7 +607,7 @@ msgid ""
|
|||
"join."
|
||||
msgstr ""
|
||||
|
||||
#: mod/newmember.php:22 mod/admin.php:1418 mod/admin.php:1676
|
||||
#: mod/newmember.php:22 mod/admin.php:1440 mod/admin.php:1698
|
||||
#: mod/settings.php:109 include/nav.php:182 view/theme/diabook/theme.php:544
|
||||
#: view/theme/diabook/theme.php:648
|
||||
msgid "Settings"
|
||||
|
|
@ -622,7 +632,7 @@ msgid ""
|
|||
"potential friends know exactly how to find you."
|
||||
msgstr ""
|
||||
|
||||
#: mod/newmember.php:36 mod/profile_photo.php:250 mod/profiles.php:709
|
||||
#: mod/newmember.php:36 mod/profile_photo.php:250 mod/profiles.php:687
|
||||
msgid "Upload Profile Photo"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -705,7 +715,7 @@ msgid ""
|
|||
"hours."
|
||||
msgstr ""
|
||||
|
||||
#: mod/newmember.php:61 include/group.php:283
|
||||
#: mod/newmember.php:61 include/group.php:286
|
||||
msgid "Groups"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -765,8 +775,8 @@ msgstr ""
|
|||
#: mod/profile_photo.php:74 mod/profile_photo.php:81 mod/profile_photo.php:88
|
||||
#: mod/profile_photo.php:210 mod/profile_photo.php:302
|
||||
#: mod/profile_photo.php:311 mod/photos.php:78 mod/photos.php:192
|
||||
#: mod/photos.php:775 mod/photos.php:1245 mod/photos.php:1268
|
||||
#: mod/photos.php:1862 include/user.php:345 include/user.php:352
|
||||
#: mod/photos.php:769 mod/photos.php:1231 mod/photos.php:1254
|
||||
#: mod/photos.php:1848 include/user.php:345 include/user.php:352
|
||||
#: include/user.php:359 view/theme/diabook/theme.php:500
|
||||
msgid "Profile Photos"
|
||||
msgstr ""
|
||||
|
|
@ -787,12 +797,12 @@ msgstr ""
|
|||
msgid "Unable to process image"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profile_photo.php:150 mod/wall_upload.php:151 mod/photos.php:811
|
||||
#: mod/profile_photo.php:150 mod/wall_upload.php:151 mod/photos.php:805
|
||||
#, php-format
|
||||
msgid "Image exceeds size limit of %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profile_photo.php:159 mod/wall_upload.php:183 mod/photos.php:851
|
||||
#: mod/profile_photo.php:159 mod/wall_upload.php:188 mod/photos.php:845
|
||||
msgid "Unable to process image."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -836,13 +846,13 @@ msgstr ""
|
|||
msgid "Image uploaded successfully."
|
||||
msgstr ""
|
||||
|
||||
#: mod/profile_photo.php:307 mod/wall_upload.php:216 mod/photos.php:878
|
||||
#: mod/profile_photo.php:307 mod/wall_upload.php:221 mod/photos.php:872
|
||||
msgid "Image upload failed."
|
||||
msgstr ""
|
||||
|
||||
#: mod/subthread.php:87 mod/tagger.php:62 include/like.php:165
|
||||
#: include/conversation.php:130 include/conversation.php:266
|
||||
#: include/text.php:2000 include/diaspora.php:2169
|
||||
#: include/text.php:1923 include/diaspora.php:2117
|
||||
#: view/theme/diabook/theme.php:471
|
||||
msgid "photo"
|
||||
msgstr ""
|
||||
|
|
@ -850,7 +860,7 @@ msgstr ""
|
|||
#: mod/subthread.php:87 mod/tagger.php:62 include/like.php:165
|
||||
#: include/like.php:334 include/conversation.php:125
|
||||
#: include/conversation.php:134 include/conversation.php:261
|
||||
#: include/conversation.php:270 include/diaspora.php:2169
|
||||
#: include/conversation.php:270 include/diaspora.php:2117
|
||||
#: view/theme/diabook/theme.php:466 view/theme/diabook/theme.php:475
|
||||
msgid "status"
|
||||
msgstr ""
|
||||
|
|
@ -920,11 +930,11 @@ msgstr ""
|
|||
msgid "- select -"
|
||||
msgstr ""
|
||||
|
||||
#: mod/filer.php:31 mod/editpost.php:109 mod/notes.php:61 include/text.php:1004
|
||||
#: mod/filer.php:31 mod/editpost.php:109 mod/notes.php:61 include/text.php:975
|
||||
msgid "Save"
|
||||
msgstr ""
|
||||
|
||||
#: mod/follow.php:19 mod/dfrn_request.php:870
|
||||
#: mod/follow.php:19 mod/dfrn_request.php:868
|
||||
msgid "Submit Request"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -944,30 +954,30 @@ msgstr ""
|
|||
msgid "The network type couldn't be detected. Contact can't be added."
|
||||
msgstr ""
|
||||
|
||||
#: mod/follow.php:109 mod/dfrn_request.php:856
|
||||
#: mod/follow.php:109 mod/dfrn_request.php:854
|
||||
msgid "Please answer the following:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/follow.php:110 mod/dfrn_request.php:857
|
||||
#: mod/follow.php:110 mod/dfrn_request.php:855
|
||||
#, php-format
|
||||
msgid "Does %s know you?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/follow.php:110 mod/settings.php:1103 mod/settings.php:1109
|
||||
#: mod/settings.php:1117 mod/settings.php:1121 mod/settings.php:1126
|
||||
#: mod/settings.php:1132 mod/settings.php:1138 mod/settings.php:1144
|
||||
#: mod/settings.php:1170 mod/settings.php:1171 mod/settings.php:1172
|
||||
#: mod/settings.php:1173 mod/settings.php:1174 mod/dfrn_request.php:857
|
||||
#: mod/register.php:239 mod/profiles.php:658 mod/profiles.php:662
|
||||
#: mod/profiles.php:687 mod/api.php:106
|
||||
#: mod/follow.php:110 mod/settings.php:1107 mod/settings.php:1113
|
||||
#: mod/settings.php:1121 mod/settings.php:1125 mod/settings.php:1130
|
||||
#: mod/settings.php:1136 mod/settings.php:1142 mod/settings.php:1148
|
||||
#: mod/settings.php:1174 mod/settings.php:1175 mod/settings.php:1176
|
||||
#: mod/settings.php:1177 mod/settings.php:1178 mod/dfrn_request.php:855
|
||||
#: mod/register.php:239 mod/profiles.php:636 mod/profiles.php:640
|
||||
#: mod/profiles.php:665 mod/api.php:106
|
||||
msgid "No"
|
||||
msgstr ""
|
||||
|
||||
#: mod/follow.php:111 mod/dfrn_request.php:861
|
||||
#: mod/follow.php:111 mod/dfrn_request.php:859
|
||||
msgid "Add a personal note:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/follow.php:117 mod/dfrn_request.php:867
|
||||
#: mod/follow.php:117 mod/dfrn_request.php:865
|
||||
msgid "Your Identity Address:"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -979,17 +989,17 @@ msgstr ""
|
|||
msgid "Unable to locate original post."
|
||||
msgstr ""
|
||||
|
||||
#: mod/item.php:329
|
||||
#: mod/item.php:332
|
||||
msgid "Empty post discarded."
|
||||
msgstr ""
|
||||
|
||||
#: mod/item.php:467 mod/wall_upload.php:213 mod/wall_upload.php:227
|
||||
#: mod/wall_upload.php:234 include/Photo.php:958 include/Photo.php:973
|
||||
#: include/Photo.php:980 include/Photo.php:1002 include/message.php:145
|
||||
#: mod/item.php:470 mod/wall_upload.php:218 mod/wall_upload.php:232
|
||||
#: mod/wall_upload.php:239 include/Photo.php:994 include/Photo.php:1009
|
||||
#: include/Photo.php:1016 include/Photo.php:1038 include/message.php:145
|
||||
msgid "Wall Photos"
|
||||
msgstr ""
|
||||
|
||||
#: mod/item.php:842
|
||||
#: mod/item.php:845
|
||||
msgid "System error. Post not saved."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1039,7 +1049,7 @@ msgstr ""
|
|||
msgid "Create a group of contacts/friends."
|
||||
msgstr ""
|
||||
|
||||
#: mod/group.php:94 mod/group.php:178 include/group.php:289
|
||||
#: mod/group.php:94 mod/group.php:178 include/group.php:292
|
||||
msgid "Group Name: "
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1063,7 +1073,7 @@ msgstr ""
|
|||
msgid "Group is empty"
|
||||
msgstr ""
|
||||
|
||||
#: mod/apps.php:7 index.php:226
|
||||
#: mod/apps.php:7 index.php:227
|
||||
msgid "You must be logged in to use addons. "
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1076,12 +1086,12 @@ msgid "No installed applications."
|
|||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:64 mod/profiles.php:18 mod/profiles.php:133
|
||||
#: mod/profiles.php:179 mod/profiles.php:627
|
||||
#: mod/profiles.php:179 mod/profiles.php:605
|
||||
msgid "Profile not found."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:120 mod/fsuggest.php:20 mod/fsuggest.php:92
|
||||
#: mod/crepair.php:131
|
||||
#: mod/crepair.php:114
|
||||
msgid "Contact not found."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1115,57 +1125,57 @@ msgstr ""
|
|||
msgid "Introduction failed or was revoked."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:430
|
||||
#: mod/dfrn_confirm.php:413
|
||||
msgid "Unable to set contact photo."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:487 include/conversation.php:185
|
||||
#: include/diaspora.php:637
|
||||
#: mod/dfrn_confirm.php:470 include/conversation.php:185
|
||||
#: include/diaspora.php:638
|
||||
#, php-format
|
||||
msgid "%1$s is now friends with %2$s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:572
|
||||
#: mod/dfrn_confirm.php:552
|
||||
#, php-format
|
||||
msgid "No user record found for '%s' "
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:582
|
||||
#: mod/dfrn_confirm.php:562
|
||||
msgid "Our site encryption key is apparently messed up."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:593
|
||||
#: mod/dfrn_confirm.php:573
|
||||
msgid "Empty site URL was provided or URL could not be decrypted by us."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:614
|
||||
#: mod/dfrn_confirm.php:594
|
||||
msgid "Contact record was not found for you on our site."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:628
|
||||
#: mod/dfrn_confirm.php:608
|
||||
#, php-format
|
||||
msgid "Site public key not available in contact record for URL %s."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:648
|
||||
#: mod/dfrn_confirm.php:628
|
||||
msgid ""
|
||||
"The ID provided by your system is a duplicate on our system. It should work "
|
||||
"if you try again."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:659
|
||||
#: mod/dfrn_confirm.php:639
|
||||
msgid "Unable to set your contact credentials on our system."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:726
|
||||
#: mod/dfrn_confirm.php:698
|
||||
msgid "Unable to update your contact profile details on our system"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:753 mod/dfrn_request.php:741 include/items.php:4299
|
||||
#: mod/dfrn_confirm.php:725 mod/dfrn_request.php:739 include/items.php:1434
|
||||
msgid "[Name Withheld]"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_confirm.php:798
|
||||
#: mod/dfrn_confirm.php:770
|
||||
#, php-format
|
||||
msgid "%1$s has joined %2$s"
|
||||
msgstr ""
|
||||
|
|
@ -1190,15 +1200,15 @@ msgstr ""
|
|||
msgid "No videos selected"
|
||||
msgstr ""
|
||||
|
||||
#: mod/videos.php:308 mod/photos.php:1087
|
||||
#: mod/videos.php:308 mod/photos.php:1073
|
||||
msgid "Access to this item is restricted."
|
||||
msgstr ""
|
||||
|
||||
#: mod/videos.php:383 include/text.php:1472
|
||||
#: mod/videos.php:383 include/text.php:1443
|
||||
msgid "View Video"
|
||||
msgstr ""
|
||||
|
||||
#: mod/videos.php:390 mod/photos.php:1890
|
||||
#: mod/videos.php:390 mod/photos.php:1876
|
||||
msgid "View Album"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1230,7 +1240,7 @@ msgstr ""
|
|||
|
||||
#: mod/wall_upload.php:20 mod/wall_upload.php:33 mod/wall_upload.php:86
|
||||
#: mod/wall_upload.php:122 mod/wall_upload.php:125 mod/wall_attach.php:17
|
||||
#: mod/wall_attach.php:25 mod/wall_attach.php:76 include/api.php:1781
|
||||
#: mod/wall_attach.php:25 mod/wall_attach.php:76
|
||||
msgid "Invalid request."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1288,7 +1298,7 @@ msgid ""
|
|||
"Password reset failed."
|
||||
msgstr ""
|
||||
|
||||
#: mod/lostpass.php:109 boot.php:1444
|
||||
#: mod/lostpass.php:109 boot.php:1534
|
||||
msgid "Password Reset"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1364,15 +1374,15 @@ msgstr ""
|
|||
msgid "Reset"
|
||||
msgstr ""
|
||||
|
||||
#: mod/ping.php:265
|
||||
#: mod/ping.php:267
|
||||
msgid "{0} wants to be your friend"
|
||||
msgstr ""
|
||||
|
||||
#: mod/ping.php:280
|
||||
#: mod/ping.php:282
|
||||
msgid "{0} sent you a message"
|
||||
msgstr ""
|
||||
|
||||
#: mod/ping.php:295
|
||||
#: mod/ping.php:297
|
||||
msgid "{0} requested registration"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1392,7 +1402,7 @@ msgstr ""
|
|||
msgid "System"
|
||||
msgstr ""
|
||||
|
||||
#: mod/notifications.php:87 mod/admin.php:390 include/nav.php:154
|
||||
#: mod/notifications.php:87 mod/admin.php:399 include/nav.php:154
|
||||
msgid "Network"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1438,7 +1448,7 @@ msgstr ""
|
|||
msgid "if applicable"
|
||||
msgstr ""
|
||||
|
||||
#: mod/notifications.php:176 mod/notifications.php:257 mod/admin.php:1308
|
||||
#: mod/notifications.php:176 mod/notifications.php:257 mod/admin.php:1330
|
||||
msgid "Approve"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1488,8 +1498,8 @@ msgstr ""
|
|||
msgid "New Follower"
|
||||
msgstr ""
|
||||
|
||||
#: mod/notifications.php:250 mod/directory.php:147 include/identity.php:310
|
||||
#: include/identity.php:590
|
||||
#: mod/notifications.php:250 mod/directory.php:147 include/identity.php:311
|
||||
#: include/identity.php:591
|
||||
msgid "Gender:"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1538,11 +1548,11 @@ msgstr ""
|
|||
msgid "Network Notifications"
|
||||
msgstr ""
|
||||
|
||||
#: mod/notifications.php:385 mod/notify.php:72
|
||||
#: mod/notifications.php:385 mod/notify.php:60
|
||||
msgid "No more system notifications."
|
||||
msgstr ""
|
||||
|
||||
#: mod/notifications.php:389 mod/notify.php:76
|
||||
#: mod/notifications.php:389 mod/notify.php:64
|
||||
msgid "System Notifications"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1693,7 +1703,7 @@ msgstr ""
|
|||
|
||||
#: mod/message.php:341 mod/message.php:526 mod/content.php:501
|
||||
#: mod/content.php:885 mod/wallmessage.php:156 mod/editpost.php:124
|
||||
#: mod/photos.php:1610 object/Item.php:396 include/conversation.php:713
|
||||
#: mod/photos.php:1596 object/Item.php:396 include/conversation.php:713
|
||||
#: include/conversation.php:1201
|
||||
msgid "Please wait"
|
||||
msgstr ""
|
||||
|
|
@ -1755,98 +1765,98 @@ msgstr[1] ""
|
|||
msgid "[Embedded content - reload page to view]"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:104
|
||||
#: mod/crepair.php:87
|
||||
msgid "Contact settings applied."
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:106
|
||||
#: mod/crepair.php:89
|
||||
msgid "Contact update failed."
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:137
|
||||
#: mod/crepair.php:120
|
||||
msgid ""
|
||||
"<strong>WARNING: This is highly advanced</strong> and if you enter incorrect "
|
||||
"information your communications with this contact may stop working."
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:138
|
||||
#: mod/crepair.php:121
|
||||
msgid ""
|
||||
"Please use your browser 'Back' button <strong>now</strong> if you are "
|
||||
"uncertain what to do on this page."
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:151 mod/crepair.php:153
|
||||
#: mod/crepair.php:134 mod/crepair.php:136
|
||||
msgid "No mirroring"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:151
|
||||
#: mod/crepair.php:134
|
||||
msgid "Mirror as forwarded posting"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:151 mod/crepair.php:153
|
||||
#: mod/crepair.php:134 mod/crepair.php:136
|
||||
msgid "Mirror as my own posting"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:167
|
||||
#: mod/crepair.php:150
|
||||
msgid "Return to contact editor"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:169
|
||||
#: mod/crepair.php:152
|
||||
msgid "Refetch contact data"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:170 mod/admin.php:1306 mod/admin.php:1318 mod/admin.php:1319
|
||||
#: mod/admin.php:1332 mod/settings.php:661 mod/settings.php:687
|
||||
#: mod/crepair.php:153 mod/admin.php:1328 mod/admin.php:1340 mod/admin.php:1341
|
||||
#: mod/admin.php:1354 mod/settings.php:662 mod/settings.php:688
|
||||
msgid "Name"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:171
|
||||
#: mod/crepair.php:154
|
||||
msgid "Account Nickname"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:172
|
||||
#: mod/crepair.php:155
|
||||
msgid "@Tagname - overrides Name/Nickname"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:173
|
||||
#: mod/crepair.php:156
|
||||
msgid "Account URL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:174
|
||||
#: mod/crepair.php:157
|
||||
msgid "Friend Request URL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:175
|
||||
#: mod/crepair.php:158
|
||||
msgid "Friend Confirm URL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:176
|
||||
#: mod/crepair.php:159
|
||||
msgid "Notification Endpoint URL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:177
|
||||
#: mod/crepair.php:160
|
||||
msgid "Poll/Feed URL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:178
|
||||
#: mod/crepair.php:161
|
||||
msgid "New photo from this URL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:179
|
||||
#: mod/crepair.php:162
|
||||
msgid "Remote Self"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:182
|
||||
#: mod/crepair.php:165
|
||||
msgid "Mirror postings from this contact"
|
||||
msgstr ""
|
||||
|
||||
#: mod/crepair.php:184
|
||||
#: mod/crepair.php:167
|
||||
msgid ""
|
||||
"Mark this contact as remote_self, this will cause friendica to repost new "
|
||||
"entries from this contact."
|
||||
msgstr ""
|
||||
|
||||
#: mod/bookmarklet.php:12 boot.php:1430 include/nav.php:91
|
||||
#: mod/bookmarklet.php:12 boot.php:1520 include/nav.php:91
|
||||
msgid "Login"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1864,8 +1874,8 @@ msgid "Connect"
|
|||
msgstr ""
|
||||
|
||||
#: mod/dirfind.php:195 mod/allfriends.php:64 mod/match.php:70
|
||||
#: mod/directory.php:162 mod/suggest.php:81 include/Contact.php:283
|
||||
#: include/Contact.php:296 include/Contact.php:338 include/conversation.php:912
|
||||
#: mod/directory.php:162 mod/suggest.php:81 include/Contact.php:285
|
||||
#: include/Contact.php:298 include/Contact.php:340 include/conversation.php:912
|
||||
#: include/conversation.php:926
|
||||
msgid "View Profile"
|
||||
msgstr ""
|
||||
|
|
@ -1879,14 +1889,14 @@ msgstr ""
|
|||
msgid "No matches"
|
||||
msgstr ""
|
||||
|
||||
#: mod/fbrowser.php:32 include/identity.php:702 include/nav.php:77
|
||||
#: mod/fbrowser.php:32 include/identity.php:703 include/nav.php:77
|
||||
#: view/theme/diabook/theme.php:126
|
||||
msgid "Photos"
|
||||
msgstr ""
|
||||
|
||||
#: mod/fbrowser.php:41 mod/fbrowser.php:62 mod/photos.php:62 mod/photos.php:192
|
||||
#: mod/photos.php:1119 mod/photos.php:1245 mod/photos.php:1268
|
||||
#: mod/photos.php:1838 mod/photos.php:1850 view/theme/diabook/theme.php:499
|
||||
#: mod/photos.php:1105 mod/photos.php:1231 mod/photos.php:1254
|
||||
#: mod/photos.php:1824 mod/photos.php:1836 view/theme/diabook/theme.php:499
|
||||
msgid "Contact Photos"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1902,19 +1912,19 @@ msgstr ""
|
|||
msgid "Theme settings updated."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:156 mod/admin.php:888
|
||||
#: mod/admin.php:156 mod/admin.php:904
|
||||
msgid "Site"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:157 mod/admin.php:832 mod/admin.php:1301 mod/admin.php:1316
|
||||
#: mod/admin.php:157 mod/admin.php:848 mod/admin.php:1323 mod/admin.php:1338
|
||||
msgid "Users"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:158 mod/admin.php:1416 mod/admin.php:1476 mod/settings.php:72
|
||||
#: mod/admin.php:158 mod/admin.php:1438 mod/admin.php:1498 mod/settings.php:72
|
||||
msgid "Plugins"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:159 mod/admin.php:1674 mod/admin.php:1724
|
||||
#: mod/admin.php:159 mod/admin.php:1696 mod/admin.php:1746
|
||||
msgid "Themes"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1926,19 +1936,19 @@ msgstr ""
|
|||
msgid "DB updates"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:162 mod/admin.php:385
|
||||
#: mod/admin.php:162 mod/admin.php:394
|
||||
msgid "Inspect Queue"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:163 mod/admin.php:354
|
||||
#: mod/admin.php:163 mod/admin.php:363
|
||||
msgid "Federation Statistics"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:177 mod/admin.php:188 mod/admin.php:1792
|
||||
#: mod/admin.php:177 mod/admin.php:188 mod/admin.php:1814
|
||||
msgid "Logs"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:178 mod/admin.php:1859
|
||||
#: mod/admin.php:178 mod/admin.php:1881
|
||||
msgid "View Logs"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -1966,739 +1976,750 @@ msgstr ""
|
|||
msgid "User registrations waiting for confirmation"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:347
|
||||
#: mod/admin.php:356
|
||||
msgid ""
|
||||
"This page offers you some numbers to the known part of the federated social "
|
||||
"network your Friendica node is part of. These numbers are not complete but "
|
||||
"only reflect the part of the network your node is aware of."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:348
|
||||
#: mod/admin.php:357
|
||||
msgid ""
|
||||
"The <em>Auto Discovered Contact Directory</em> feature is not enabled, it "
|
||||
"will improve the data displayed here."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:353 mod/admin.php:384 mod/admin.php:441 mod/admin.php:887
|
||||
#: mod/admin.php:1300 mod/admin.php:1415 mod/admin.php:1475 mod/admin.php:1673
|
||||
#: mod/admin.php:1723 mod/admin.php:1791 mod/admin.php:1858
|
||||
#: mod/admin.php:362 mod/admin.php:393 mod/admin.php:450 mod/admin.php:903
|
||||
#: mod/admin.php:1322 mod/admin.php:1437 mod/admin.php:1497 mod/admin.php:1695
|
||||
#: mod/admin.php:1745 mod/admin.php:1813 mod/admin.php:1880
|
||||
msgid "Administration"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:360
|
||||
#: mod/admin.php:369
|
||||
#, php-format
|
||||
msgid "Currently this node is aware of %d nodes from the following platforms:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:387
|
||||
#: mod/admin.php:396
|
||||
msgid "ID"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:388
|
||||
#: mod/admin.php:397
|
||||
msgid "Recipient Name"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:389
|
||||
#: mod/admin.php:398
|
||||
msgid "Recipient Profile"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:391
|
||||
#: mod/admin.php:400
|
||||
msgid "Created"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:392
|
||||
#: mod/admin.php:401
|
||||
msgid "Last Tried"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:393
|
||||
#: mod/admin.php:402
|
||||
msgid ""
|
||||
"This page lists the content of the queue for outgoing postings. These are "
|
||||
"postings the initial delivery failed for. They will be resend later and "
|
||||
"eventually deleted if the delivery fails permanently."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:412 mod/admin.php:1254
|
||||
#: mod/admin.php:421 mod/admin.php:1276
|
||||
msgid "Normal Account"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:413 mod/admin.php:1255
|
||||
#: mod/admin.php:422 mod/admin.php:1277
|
||||
msgid "Soapbox Account"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:414 mod/admin.php:1256
|
||||
#: mod/admin.php:423 mod/admin.php:1278
|
||||
msgid "Community/Celebrity Account"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:415 mod/admin.php:1257
|
||||
#: mod/admin.php:424 mod/admin.php:1279
|
||||
msgid "Automatic Friend Account"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:416
|
||||
#: mod/admin.php:425
|
||||
msgid "Blog Account"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:417
|
||||
#: mod/admin.php:426
|
||||
msgid "Private Forum"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:436
|
||||
#: mod/admin.php:445
|
||||
msgid "Message queues"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:442
|
||||
#: mod/admin.php:451
|
||||
msgid "Summary"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:444
|
||||
#: mod/admin.php:453
|
||||
msgid "Registered users"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:446
|
||||
#: mod/admin.php:455
|
||||
msgid "Pending registrations"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:447
|
||||
#: mod/admin.php:456
|
||||
msgid "Version"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:452
|
||||
#: mod/admin.php:461
|
||||
msgid "Active plugins"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:475
|
||||
#: mod/admin.php:484
|
||||
msgid "Can not parse base url. Must have at least <scheme>://<domain>"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:760
|
||||
#: mod/admin.php:776
|
||||
msgid "RINO2 needs mcrypt php extension to work."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:768
|
||||
#: mod/admin.php:784
|
||||
msgid "Site settings updated."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:796 mod/settings.php:912
|
||||
#: mod/admin.php:812 mod/settings.php:916
|
||||
msgid "No special theme for mobile devices"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:815
|
||||
#: mod/admin.php:831
|
||||
msgid "No community page"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:816
|
||||
#: mod/admin.php:832
|
||||
msgid "Public postings from users of this site"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:817
|
||||
#: mod/admin.php:833
|
||||
msgid "Global community page"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:823
|
||||
#: mod/admin.php:839
|
||||
msgid "At post arrival"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:824 include/contact_selectors.php:56
|
||||
#: mod/admin.php:840 include/contact_selectors.php:56
|
||||
msgid "Frequently"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:825 include/contact_selectors.php:57
|
||||
#: mod/admin.php:841 include/contact_selectors.php:57
|
||||
msgid "Hourly"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:826 include/contact_selectors.php:58
|
||||
#: mod/admin.php:842 include/contact_selectors.php:58
|
||||
msgid "Twice daily"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:827 include/contact_selectors.php:59
|
||||
#: mod/admin.php:843 include/contact_selectors.php:59
|
||||
msgid "Daily"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:833
|
||||
#: mod/admin.php:849
|
||||
msgid "Users, Global Contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:834
|
||||
#: mod/admin.php:850
|
||||
msgid "Users, Global Contacts/fallback"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:838
|
||||
#: mod/admin.php:854
|
||||
msgid "One month"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:839
|
||||
#: mod/admin.php:855
|
||||
msgid "Three months"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:840
|
||||
#: mod/admin.php:856
|
||||
msgid "Half a year"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:841
|
||||
#: mod/admin.php:857
|
||||
msgid "One year"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:846
|
||||
#: mod/admin.php:862
|
||||
msgid "Multi user instance"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:869
|
||||
#: mod/admin.php:885
|
||||
msgid "Closed"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:870
|
||||
#: mod/admin.php:886
|
||||
msgid "Requires approval"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:871
|
||||
#: mod/admin.php:887
|
||||
msgid "Open"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:875
|
||||
#: mod/admin.php:891
|
||||
msgid "No SSL policy, links will track page SSL state"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:876
|
||||
#: mod/admin.php:892
|
||||
msgid "Force all links to use SSL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:877
|
||||
#: mod/admin.php:893
|
||||
msgid "Self-signed certificate, use SSL for local links only (discouraged)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:889 mod/admin.php:1477 mod/admin.php:1725 mod/admin.php:1793
|
||||
#: mod/admin.php:1942 mod/settings.php:659 mod/settings.php:769
|
||||
#: mod/settings.php:813 mod/settings.php:882 mod/settings.php:969
|
||||
#: mod/settings.php:1204
|
||||
#: mod/admin.php:905 mod/admin.php:1499 mod/admin.php:1747 mod/admin.php:1815
|
||||
#: mod/admin.php:1964 mod/settings.php:660 mod/settings.php:770
|
||||
#: mod/settings.php:817 mod/settings.php:886 mod/settings.php:973
|
||||
#: mod/settings.php:1208
|
||||
msgid "Save Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:890 mod/register.php:263
|
||||
#: mod/admin.php:906 mod/register.php:263
|
||||
msgid "Registration"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:891
|
||||
#: mod/admin.php:907
|
||||
msgid "File upload"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:892
|
||||
#: mod/admin.php:908
|
||||
msgid "Policies"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:893
|
||||
msgid "Advanced"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:894
|
||||
#: mod/admin.php:910
|
||||
msgid "Auto Discovered Contact Directory"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:895
|
||||
#: mod/admin.php:911
|
||||
msgid "Performance"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:896
|
||||
#: mod/admin.php:912
|
||||
msgid "Worker"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:913
|
||||
msgid ""
|
||||
"Relocate - WARNING: advanced function. Could make this server unreachable."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:899
|
||||
#: mod/admin.php:916
|
||||
msgid "Site name"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:900
|
||||
#: mod/admin.php:917
|
||||
msgid "Host name"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:901
|
||||
#: mod/admin.php:918
|
||||
msgid "Sender Email"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:901
|
||||
#: mod/admin.php:918
|
||||
msgid ""
|
||||
"The email address your server shall use to send notification emails from."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:902
|
||||
#: mod/admin.php:919
|
||||
msgid "Banner/Logo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:903
|
||||
#: mod/admin.php:920
|
||||
msgid "Shortcut icon"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:903
|
||||
#: mod/admin.php:920
|
||||
msgid "Link to an icon that will be used for browsers."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:904
|
||||
#: mod/admin.php:921
|
||||
msgid "Touch icon"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:904
|
||||
#: mod/admin.php:921
|
||||
msgid "Link to an icon that will be used for tablets and mobiles."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:905
|
||||
#: mod/admin.php:922
|
||||
msgid "Additional Info"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:905
|
||||
#: mod/admin.php:922
|
||||
#, php-format
|
||||
msgid ""
|
||||
"For public servers: you can add additional information here that will be "
|
||||
"listed at %s/siteinfo."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:906
|
||||
#: mod/admin.php:923
|
||||
msgid "System language"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:907
|
||||
#: mod/admin.php:924
|
||||
msgid "System theme"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:907
|
||||
#: mod/admin.php:924
|
||||
msgid ""
|
||||
"Default system theme - may be over-ridden by user profiles - <a href='#' "
|
||||
"id='cnftheme'>change theme settings</a>"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:908
|
||||
#: mod/admin.php:925
|
||||
msgid "Mobile system theme"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:908
|
||||
#: mod/admin.php:925
|
||||
msgid "Theme for mobile devices"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:909
|
||||
#: mod/admin.php:926
|
||||
msgid "SSL link policy"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:909
|
||||
#: mod/admin.php:926
|
||||
msgid "Determines whether generated links should be forced to use SSL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:910
|
||||
#: mod/admin.php:927
|
||||
msgid "Force SSL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:910
|
||||
#: mod/admin.php:927
|
||||
msgid ""
|
||||
"Force all Non-SSL requests to SSL - Attention: on some systems it could lead "
|
||||
"to endless loops."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:911
|
||||
#: mod/admin.php:928
|
||||
msgid "Old style 'Share'"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:911
|
||||
#: mod/admin.php:928
|
||||
msgid "Deactivates the bbcode element 'share' for repeating items."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:912
|
||||
#: mod/admin.php:929
|
||||
msgid "Hide help entry from navigation menu"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:912
|
||||
#: mod/admin.php:929
|
||||
msgid ""
|
||||
"Hides the menu entry for the Help pages from the navigation menu. You can "
|
||||
"still access it calling /help directly."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:913
|
||||
#: mod/admin.php:930
|
||||
msgid "Single user instance"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:913
|
||||
#: mod/admin.php:930
|
||||
msgid "Make this instance multi-user or single-user for the named user"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:914
|
||||
#: mod/admin.php:931
|
||||
msgid "Maximum image size"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:914
|
||||
#: mod/admin.php:931
|
||||
msgid ""
|
||||
"Maximum size in bytes of uploaded images. Default is 0, which means no "
|
||||
"limits."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:915
|
||||
#: mod/admin.php:932
|
||||
msgid "Maximum image length"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:915
|
||||
#: mod/admin.php:932
|
||||
msgid ""
|
||||
"Maximum length in pixels of the longest side of uploaded images. Default is "
|
||||
"-1, which means no limits."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:916
|
||||
#: mod/admin.php:933
|
||||
msgid "JPEG image quality"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:916
|
||||
#: mod/admin.php:933
|
||||
msgid ""
|
||||
"Uploaded JPEGS will be saved at this quality setting [0-100]. Default is "
|
||||
"100, which is full quality."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:918
|
||||
#: mod/admin.php:935
|
||||
msgid "Register policy"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:919
|
||||
#: mod/admin.php:936
|
||||
msgid "Maximum Daily Registrations"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:919
|
||||
#: mod/admin.php:936
|
||||
msgid ""
|
||||
"If registration is permitted above, this sets the maximum number of new user "
|
||||
"registrations to accept per day. If register is set to closed, this setting "
|
||||
"has no effect."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:920
|
||||
#: mod/admin.php:937
|
||||
msgid "Register text"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:920
|
||||
#: mod/admin.php:937
|
||||
msgid "Will be displayed prominently on the registration page."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:921
|
||||
#: mod/admin.php:938
|
||||
msgid "Accounts abandoned after x days"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:921
|
||||
#: mod/admin.php:938
|
||||
msgid ""
|
||||
"Will not waste system resources polling external sites for abandonded "
|
||||
"accounts. Enter 0 for no time limit."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:922
|
||||
#: mod/admin.php:939
|
||||
msgid "Allowed friend domains"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:922
|
||||
#: mod/admin.php:939
|
||||
msgid ""
|
||||
"Comma separated list of domains which are allowed to establish friendships "
|
||||
"with this site. Wildcards are accepted. Empty to allow any domains"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:923
|
||||
#: mod/admin.php:940
|
||||
msgid "Allowed email domains"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:923
|
||||
#: mod/admin.php:940
|
||||
msgid ""
|
||||
"Comma separated list of domains which are allowed in email addresses for "
|
||||
"registrations to this site. Wildcards are accepted. Empty to allow any "
|
||||
"domains"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:924
|
||||
#: mod/admin.php:941
|
||||
msgid "Block public"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:924
|
||||
#: mod/admin.php:941
|
||||
msgid ""
|
||||
"Check to block public access to all otherwise public personal pages on this "
|
||||
"site unless you are currently logged in."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:925
|
||||
#: mod/admin.php:942
|
||||
msgid "Force publish"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:925
|
||||
#: mod/admin.php:942
|
||||
msgid ""
|
||||
"Check to force all profiles on this site to be listed in the site directory."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:926
|
||||
#: mod/admin.php:943
|
||||
msgid "Global directory URL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:926
|
||||
#: mod/admin.php:943
|
||||
msgid ""
|
||||
"URL to the global directory. If this is not set, the global directory is "
|
||||
"completely unavailable to the application."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:927
|
||||
#: mod/admin.php:944
|
||||
msgid "Allow threaded items"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:927
|
||||
#: mod/admin.php:944
|
||||
msgid "Allow infinite level threading for items on this site."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:928
|
||||
#: mod/admin.php:945
|
||||
msgid "Private posts by default for new users"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:928
|
||||
#: mod/admin.php:945
|
||||
msgid ""
|
||||
"Set default post permissions for all new members to the default privacy "
|
||||
"group rather than public."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:929
|
||||
#: mod/admin.php:946
|
||||
msgid "Don't include post content in email notifications"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:929
|
||||
#: mod/admin.php:946
|
||||
msgid ""
|
||||
"Don't include the content of a post/comment/private message/etc. in the "
|
||||
"email notifications that are sent out from this site, as a privacy measure."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:930
|
||||
#: mod/admin.php:947
|
||||
msgid "Disallow public access to addons listed in the apps menu."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:930
|
||||
#: mod/admin.php:947
|
||||
msgid ""
|
||||
"Checking this box will restrict addons listed in the apps menu to members "
|
||||
"only."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:931
|
||||
#: mod/admin.php:948
|
||||
msgid "Don't embed private images in posts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:931
|
||||
#: mod/admin.php:948
|
||||
msgid ""
|
||||
"Don't replace locally-hosted private photos in posts with an embedded copy "
|
||||
"of the image. This means that contacts who receive posts containing private "
|
||||
"photos will have to authenticate and load each image, which may take a while."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:932
|
||||
#: mod/admin.php:949
|
||||
msgid "Allow Users to set remote_self"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:932
|
||||
#: mod/admin.php:949
|
||||
msgid ""
|
||||
"With checking this, every user is allowed to mark every contact as a "
|
||||
"remote_self in the repair contact dialog. Setting this flag on a contact "
|
||||
"causes mirroring every posting of that contact in the users stream."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:933
|
||||
#: mod/admin.php:950
|
||||
msgid "Block multiple registrations"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:933
|
||||
#: mod/admin.php:950
|
||||
msgid "Disallow users to register additional accounts for use as pages."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:934
|
||||
#: mod/admin.php:951
|
||||
msgid "OpenID support"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:934
|
||||
#: mod/admin.php:951
|
||||
msgid "OpenID support for registration and logins."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:935
|
||||
#: mod/admin.php:952
|
||||
msgid "Fullname check"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:935
|
||||
#: mod/admin.php:952
|
||||
msgid ""
|
||||
"Force users to register with a space between firstname and lastname in Full "
|
||||
"name, as an antispam measure"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:936
|
||||
#: mod/admin.php:953
|
||||
msgid "UTF-8 Regular expressions"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:936
|
||||
#: mod/admin.php:953
|
||||
msgid "Use PHP UTF8 regular expressions"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:937
|
||||
#: mod/admin.php:954
|
||||
msgid "Community Page Style"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:937
|
||||
#: mod/admin.php:954
|
||||
msgid ""
|
||||
"Type of community page to show. 'Global community' shows every public "
|
||||
"posting from an open distributed network that arrived on this server."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:938
|
||||
#: mod/admin.php:955
|
||||
msgid "Posts per user on community page"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:938
|
||||
#: mod/admin.php:955
|
||||
msgid ""
|
||||
"The maximum number of posts per user on the community page. (Not valid for "
|
||||
"'Global Community')"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:939
|
||||
#: mod/admin.php:956
|
||||
msgid "Enable OStatus support"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:939
|
||||
#: mod/admin.php:956
|
||||
msgid ""
|
||||
"Provide built-in OStatus (StatusNet, GNU Social etc.) compatibility. All "
|
||||
"communications in OStatus are public, so privacy warnings will be "
|
||||
"occasionally displayed."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:940
|
||||
#: mod/admin.php:957
|
||||
msgid "OStatus conversation completion interval"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:940
|
||||
#: mod/admin.php:957
|
||||
msgid ""
|
||||
"How often shall the poller check for new entries in OStatus conversations? "
|
||||
"This can be a very ressource task."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:941
|
||||
#: mod/admin.php:958
|
||||
msgid "Only import OStatus threads from our contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:958
|
||||
msgid ""
|
||||
"Normally we import every content from our OStatus contacts. With this option "
|
||||
"we only store threads that are started by a contact that is known on our "
|
||||
"system."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:959
|
||||
msgid "OStatus support can only be enabled if threading is enabled."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:943
|
||||
#: mod/admin.php:961
|
||||
msgid ""
|
||||
"Diaspora support can't be enabled because Friendica was installed into a sub "
|
||||
"directory."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:944
|
||||
#: mod/admin.php:962
|
||||
msgid "Enable Diaspora support"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:944
|
||||
#: mod/admin.php:962
|
||||
msgid "Provide built-in Diaspora network compatibility."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:945
|
||||
#: mod/admin.php:963
|
||||
msgid "Only allow Friendica contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:945
|
||||
#: mod/admin.php:963
|
||||
msgid ""
|
||||
"All contacts must use Friendica protocols. All other built-in communication "
|
||||
"protocols disabled."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:946
|
||||
#: mod/admin.php:964
|
||||
msgid "Verify SSL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:946
|
||||
#: mod/admin.php:964
|
||||
msgid ""
|
||||
"If you wish, you can turn on strict certificate checking. This will mean you "
|
||||
"cannot connect (at all) to self-signed SSL sites."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:947
|
||||
#: mod/admin.php:965
|
||||
msgid "Proxy user"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:948
|
||||
#: mod/admin.php:966
|
||||
msgid "Proxy URL"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:949
|
||||
#: mod/admin.php:967
|
||||
msgid "Network timeout"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:949
|
||||
#: mod/admin.php:967
|
||||
msgid "Value is in seconds. Set to 0 for unlimited (not recommended)."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:950
|
||||
#: mod/admin.php:968
|
||||
msgid "Delivery interval"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:950
|
||||
#: mod/admin.php:968
|
||||
msgid ""
|
||||
"Delay background delivery processes by this many seconds to reduce system "
|
||||
"load. Recommend: 4-5 for shared hosts, 2-3 for virtual private servers. 0-1 "
|
||||
"for large dedicated servers."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:951
|
||||
#: mod/admin.php:969
|
||||
msgid "Poll interval"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:951
|
||||
#: mod/admin.php:969
|
||||
msgid ""
|
||||
"Delay background polling processes by this many seconds to reduce system "
|
||||
"load. If 0, use delivery interval."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:952
|
||||
#: mod/admin.php:970
|
||||
msgid "Maximum Load Average"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:952
|
||||
#: mod/admin.php:970
|
||||
msgid ""
|
||||
"Maximum system load before delivery and poll processes are deferred - "
|
||||
"default 50."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:953
|
||||
#: mod/admin.php:971
|
||||
msgid "Maximum Load Average (Frontend)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:953
|
||||
#: mod/admin.php:971
|
||||
msgid "Maximum system load before the frontend quits service - default 50."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:954
|
||||
#: mod/admin.php:972
|
||||
msgid "Maximum table size for optimization"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:954
|
||||
#: mod/admin.php:972
|
||||
msgid ""
|
||||
"Maximum table size (in MB) for the automatic optimization - default 100 MB. "
|
||||
"Enter -1 to disable it."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:955
|
||||
#: mod/admin.php:973
|
||||
msgid "Minimum level of fragmentation"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:955
|
||||
#: mod/admin.php:973
|
||||
msgid ""
|
||||
"Minimum fragmenation level to start the automatic optimization - default "
|
||||
"value is 30%."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:957
|
||||
#: mod/admin.php:975
|
||||
msgid "Periodical check of global contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:957
|
||||
#: mod/admin.php:975
|
||||
msgid ""
|
||||
"If enabled, the global contacts are checked periodically for missing or "
|
||||
"outdated data and the vitality of the contacts and servers."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:958
|
||||
#: mod/admin.php:976
|
||||
msgid "Days between requery"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:958
|
||||
#: mod/admin.php:976
|
||||
msgid "Number of days after which a server is requeried for his contacts."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:959
|
||||
#: mod/admin.php:977
|
||||
msgid "Discover contacts from other servers"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:959
|
||||
#: mod/admin.php:977
|
||||
msgid ""
|
||||
"Periodically query other servers for contacts. You can choose between "
|
||||
"'users': the users on the remote system, 'Global Contacts': active contacts "
|
||||
|
|
@ -2708,32 +2729,32 @@ msgid ""
|
|||
"Global Contacts'."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:960
|
||||
#: mod/admin.php:978
|
||||
msgid "Timeframe for fetching global contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:960
|
||||
#: mod/admin.php:978
|
||||
msgid ""
|
||||
"When the discovery is activated, this value defines the timeframe for the "
|
||||
"activity of the global contacts that are fetched from other servers."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:961
|
||||
#: mod/admin.php:979
|
||||
msgid "Search the local directory"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:961
|
||||
#: mod/admin.php:979
|
||||
msgid ""
|
||||
"Search the local directory instead of the global directory. When searching "
|
||||
"locally, every search will be executed on the global directory in the "
|
||||
"background. This improves the search results when the search is repeated."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:963
|
||||
#: mod/admin.php:981
|
||||
msgid "Publish server information"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:963
|
||||
#: mod/admin.php:981
|
||||
msgid ""
|
||||
"If enabled, general server and usage data will be published. The data "
|
||||
"contains the name and version of the server, number of users with public "
|
||||
|
|
@ -2741,204 +2762,235 @@ msgid ""
|
|||
"href='http://the-federation.info/'>the-federation.info</a> for details."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:965
|
||||
#: mod/admin.php:983
|
||||
msgid "Use MySQL full text engine"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:965
|
||||
#: mod/admin.php:983
|
||||
msgid ""
|
||||
"Activates the full text engine. Speeds up search - but can only search for "
|
||||
"four and more characters."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:966
|
||||
#: mod/admin.php:984
|
||||
msgid "Suppress Language"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:966
|
||||
#: mod/admin.php:984
|
||||
msgid "Suppress language information in meta information about a posting."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:967
|
||||
#: mod/admin.php:985
|
||||
msgid "Suppress Tags"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:967
|
||||
#: mod/admin.php:985
|
||||
msgid "Suppress showing a list of hashtags at the end of the posting."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:968
|
||||
#: mod/admin.php:986
|
||||
msgid "Path to item cache"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:968
|
||||
#: mod/admin.php:986
|
||||
msgid "The item caches buffers generated bbcode and external images."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:969
|
||||
#: mod/admin.php:987
|
||||
msgid "Cache duration in seconds"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:969
|
||||
#: mod/admin.php:987
|
||||
msgid ""
|
||||
"How long should the cache files be hold? Default value is 86400 seconds (One "
|
||||
"day). To disable the item cache, set the value to -1."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:970
|
||||
#: mod/admin.php:988
|
||||
msgid "Maximum numbers of comments per post"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:970
|
||||
#: mod/admin.php:988
|
||||
msgid "How much comments should be shown for each post? Default value is 100."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:971
|
||||
#: mod/admin.php:989
|
||||
msgid "Path for lock file"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:971
|
||||
#: mod/admin.php:989
|
||||
msgid ""
|
||||
"The lock file is used to avoid multiple pollers at one time. Only define a "
|
||||
"folder here."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:972
|
||||
#: mod/admin.php:990
|
||||
msgid "Temp path"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:972
|
||||
#: mod/admin.php:990
|
||||
msgid ""
|
||||
"If you have a restricted system where the webserver can't access the system "
|
||||
"temp path, enter another path here."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:973
|
||||
#: mod/admin.php:991
|
||||
msgid "Base path to installation"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:973
|
||||
#: mod/admin.php:991
|
||||
msgid ""
|
||||
"If the system cannot detect the correct path to your installation, enter the "
|
||||
"correct path here. This setting should only be set if you are using a "
|
||||
"restricted system and symbolic links to your webroot."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:974
|
||||
#: mod/admin.php:992
|
||||
msgid "Disable picture proxy"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:974
|
||||
#: mod/admin.php:992
|
||||
msgid ""
|
||||
"The picture proxy increases performance and privacy. It shouldn't be used on "
|
||||
"systems with very low bandwith."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:975
|
||||
#: mod/admin.php:993
|
||||
msgid "Enable old style pager"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:975
|
||||
#: mod/admin.php:993
|
||||
msgid ""
|
||||
"The old style pager has page numbers but slows down massively the page speed."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:976
|
||||
#: mod/admin.php:994
|
||||
msgid "Only search in tags"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:976
|
||||
#: mod/admin.php:994
|
||||
msgid "On large systems the text search can slow down the system extremely."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:978
|
||||
#: mod/admin.php:996
|
||||
msgid "New base url"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:978
|
||||
#: mod/admin.php:996
|
||||
msgid ""
|
||||
"Change base url for this server. Sends relocate message to all DFRN contacts "
|
||||
"of all users."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:980
|
||||
#: mod/admin.php:998
|
||||
msgid "RINO Encryption"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:980
|
||||
#: mod/admin.php:998
|
||||
msgid "Encryption layer between nodes."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:981
|
||||
#: mod/admin.php:999
|
||||
msgid "Embedly API key"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:981
|
||||
#: mod/admin.php:999
|
||||
msgid ""
|
||||
"<a href='http://embed.ly'>Embedly</a> is used to fetch additional data for "
|
||||
"web pages. This is an optional parameter."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1010
|
||||
#: mod/admin.php:1001
|
||||
msgid "Enable 'worker' background processing"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1001
|
||||
msgid ""
|
||||
"The worker background processing limits the number of parallel background "
|
||||
"jobs to a maximum number and respects the system load."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1002
|
||||
msgid "Maximum number of parallel workers"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1002
|
||||
msgid ""
|
||||
"On shared hosters set this to 2. On larger systems, values of 10 are great. "
|
||||
"Default value is 4."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1003
|
||||
msgid "Don't use 'proc_open' with the worker"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1003
|
||||
msgid ""
|
||||
"Enable this if your system doesn't allow the use of 'proc_open'. This can "
|
||||
"happen on shared hosters. If this is enabled you should increase the "
|
||||
"frequency of poller calls in your crontab."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1032
|
||||
msgid "Update has been marked successful"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1018
|
||||
#, php-format
|
||||
msgid "Database structure update %s was successfully applied."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1021
|
||||
#, php-format
|
||||
msgid "Executing of database structure update %s failed with error: %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1033
|
||||
#, php-format
|
||||
msgid "Executing %s failed with error: %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1036
|
||||
#, php-format
|
||||
msgid "Update %s was successfully applied."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1040
|
||||
#, php-format
|
||||
msgid "Database structure update %s was successfully applied."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1043
|
||||
#, php-format
|
||||
msgid "Executing of database structure update %s failed with error: %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1055
|
||||
#, php-format
|
||||
msgid "Executing %s failed with error: %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1058
|
||||
#, php-format
|
||||
msgid "Update %s was successfully applied."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1062
|
||||
#, php-format
|
||||
msgid "Update %s did not return a status. Unknown if it succeeded."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1042
|
||||
#: mod/admin.php:1064
|
||||
#, php-format
|
||||
msgid "There was no additional update function %s that needed to be called."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1061
|
||||
#: mod/admin.php:1083
|
||||
msgid "No failed updates."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1062
|
||||
#: mod/admin.php:1084
|
||||
msgid "Check database structure"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1067
|
||||
#: mod/admin.php:1089
|
||||
msgid "Failed Updates"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1068
|
||||
#: mod/admin.php:1090
|
||||
msgid ""
|
||||
"This does not include updates prior to 1139, which did not return a status."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1069
|
||||
#: mod/admin.php:1091
|
||||
msgid "Mark success (if update was manually applied)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1070
|
||||
#: mod/admin.php:1092
|
||||
msgid "Attempt to execute this update step automatically"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1102
|
||||
#: mod/admin.php:1124
|
||||
#, php-format
|
||||
msgid ""
|
||||
"\n"
|
||||
|
|
@ -2946,7 +2998,7 @@ msgid ""
|
|||
"\t\t\t\tthe administrator of %2$s has set up an account for you."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1105
|
||||
#: mod/admin.php:1127
|
||||
#, php-format
|
||||
msgid ""
|
||||
"\n"
|
||||
|
|
@ -2982,168 +3034,168 @@ msgid ""
|
|||
"\t\t\tThank you and welcome to %4$s."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1137 include/user.php:423
|
||||
#: mod/admin.php:1159 include/user.php:423
|
||||
#, php-format
|
||||
msgid "Registration details for %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1149
|
||||
#: mod/admin.php:1171
|
||||
#, php-format
|
||||
msgid "%s user blocked/unblocked"
|
||||
msgid_plural "%s users blocked/unblocked"
|
||||
msgstr[0] ""
|
||||
msgstr[1] ""
|
||||
|
||||
#: mod/admin.php:1156
|
||||
#: mod/admin.php:1178
|
||||
#, php-format
|
||||
msgid "%s user deleted"
|
||||
msgid_plural "%s users deleted"
|
||||
msgstr[0] ""
|
||||
msgstr[1] ""
|
||||
|
||||
#: mod/admin.php:1203
|
||||
#: mod/admin.php:1225
|
||||
#, php-format
|
||||
msgid "User '%s' deleted"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1211
|
||||
#: mod/admin.php:1233
|
||||
#, php-format
|
||||
msgid "User '%s' unblocked"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1211
|
||||
#: mod/admin.php:1233
|
||||
#, php-format
|
||||
msgid "User '%s' blocked"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1302
|
||||
#: mod/admin.php:1324
|
||||
msgid "Add User"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1303
|
||||
#: mod/admin.php:1325
|
||||
msgid "select all"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1304
|
||||
#: mod/admin.php:1326
|
||||
msgid "User registrations waiting for confirm"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1305
|
||||
#: mod/admin.php:1327
|
||||
msgid "User waiting for permanent deletion"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1306
|
||||
#: mod/admin.php:1328
|
||||
msgid "Request date"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1306 mod/admin.php:1318 mod/admin.php:1319 mod/admin.php:1334
|
||||
#: mod/admin.php:1328 mod/admin.php:1340 mod/admin.php:1341 mod/admin.php:1356
|
||||
#: include/contact_selectors.php:79 include/contact_selectors.php:86
|
||||
msgid "Email"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1307
|
||||
#: mod/admin.php:1329
|
||||
msgid "No registrations."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1309
|
||||
#: mod/admin.php:1331
|
||||
msgid "Deny"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1313
|
||||
#: mod/admin.php:1335
|
||||
msgid "Site admin"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1314
|
||||
#: mod/admin.php:1336
|
||||
msgid "Account expired"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1317
|
||||
#: mod/admin.php:1339
|
||||
msgid "New User"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1318 mod/admin.php:1319
|
||||
#: mod/admin.php:1340 mod/admin.php:1341
|
||||
msgid "Register date"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1318 mod/admin.php:1319
|
||||
#: mod/admin.php:1340 mod/admin.php:1341
|
||||
msgid "Last login"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1318 mod/admin.php:1319
|
||||
#: mod/admin.php:1340 mod/admin.php:1341
|
||||
msgid "Last item"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1318
|
||||
#: mod/admin.php:1340
|
||||
msgid "Deleted since"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1319 mod/settings.php:41
|
||||
#: mod/admin.php:1341 mod/settings.php:41
|
||||
msgid "Account"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1321
|
||||
#: mod/admin.php:1343
|
||||
msgid ""
|
||||
"Selected users will be deleted!\\n\\nEverything these users had posted on "
|
||||
"this site will be permanently deleted!\\n\\nAre you sure?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1322
|
||||
#: mod/admin.php:1344
|
||||
msgid ""
|
||||
"The user {0} will be deleted!\\n\\nEverything this user has posted on this "
|
||||
"site will be permanently deleted!\\n\\nAre you sure?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1332
|
||||
#: mod/admin.php:1354
|
||||
msgid "Name of the new user."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1333
|
||||
#: mod/admin.php:1355
|
||||
msgid "Nickname"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1333
|
||||
#: mod/admin.php:1355
|
||||
msgid "Nickname of the new user."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1334
|
||||
#: mod/admin.php:1356
|
||||
msgid "Email address of the new user."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1377
|
||||
#: mod/admin.php:1399
|
||||
#, php-format
|
||||
msgid "Plugin %s disabled."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1381
|
||||
#: mod/admin.php:1403
|
||||
#, php-format
|
||||
msgid "Plugin %s enabled."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1392 mod/admin.php:1628
|
||||
#: mod/admin.php:1414 mod/admin.php:1650
|
||||
msgid "Disable"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1394 mod/admin.php:1630
|
||||
#: mod/admin.php:1416 mod/admin.php:1652
|
||||
msgid "Enable"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1417 mod/admin.php:1675
|
||||
#: mod/admin.php:1439 mod/admin.php:1697
|
||||
msgid "Toggle"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1425 mod/admin.php:1684
|
||||
#: mod/admin.php:1447 mod/admin.php:1706
|
||||
msgid "Author: "
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1426 mod/admin.php:1685
|
||||
#: mod/admin.php:1448 mod/admin.php:1707
|
||||
msgid "Maintainer: "
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1478
|
||||
#: mod/admin.php:1500
|
||||
msgid "Reload active plugins"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1483
|
||||
#: mod/admin.php:1505
|
||||
#, php-format
|
||||
msgid ""
|
||||
"There are currently no plugins available on your node. You can find the "
|
||||
|
|
@ -3151,62 +3203,62 @@ msgid ""
|
|||
"in the open plugin registry at %2$s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1588
|
||||
#: mod/admin.php:1610
|
||||
msgid "No themes found."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1666
|
||||
#: mod/admin.php:1688
|
||||
msgid "Screenshot"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1726
|
||||
#: mod/admin.php:1748
|
||||
msgid "Reload active themes"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1731
|
||||
#: mod/admin.php:1753
|
||||
#, php-format
|
||||
msgid "No themes found on the system. They should be paced in %1$s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1732
|
||||
#: mod/admin.php:1754
|
||||
msgid "[Experimental]"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1733
|
||||
#: mod/admin.php:1755
|
||||
msgid "[Unsupported]"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1757
|
||||
#: mod/admin.php:1779
|
||||
msgid "Log settings updated."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1794
|
||||
#: mod/admin.php:1816
|
||||
msgid "Clear"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1799
|
||||
#: mod/admin.php:1821
|
||||
msgid "Enable Debugging"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1800
|
||||
#: mod/admin.php:1822
|
||||
msgid "Log file"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1800
|
||||
#: mod/admin.php:1822
|
||||
msgid ""
|
||||
"Must be writable by web server. Relative to your Friendica top-level "
|
||||
"directory."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1801
|
||||
#: mod/admin.php:1823
|
||||
msgid "Log level"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1804
|
||||
#: mod/admin.php:1826
|
||||
msgid "PHP logging"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1805
|
||||
#: mod/admin.php:1827
|
||||
msgid ""
|
||||
"To enable logging of PHP errors and warnings you can add the following to "
|
||||
"the .htconfig.php file of your installation. The filename set in the "
|
||||
|
|
@ -3215,20 +3267,20 @@ msgid ""
|
|||
"'display_errors' is to enable these options, set to '0' to disable them."
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1931 mod/admin.php:1932 mod/settings.php:759
|
||||
#: mod/admin.php:1953 mod/admin.php:1954 mod/settings.php:760
|
||||
msgid "Off"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1931 mod/admin.php:1932 mod/settings.php:759
|
||||
#: mod/admin.php:1953 mod/admin.php:1954 mod/settings.php:760
|
||||
msgid "On"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1932
|
||||
#: mod/admin.php:1954
|
||||
#, php-format
|
||||
msgid "Lock feature %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/admin.php:1940
|
||||
#: mod/admin.php:1962
|
||||
msgid "Manage Additional Features"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -3245,7 +3297,7 @@ msgstr ""
|
|||
msgid "Saved Searches"
|
||||
msgstr ""
|
||||
|
||||
#: mod/network.php:201 include/group.php:293
|
||||
#: mod/network.php:201 include/group.php:296
|
||||
msgid "add"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -3362,31 +3414,31 @@ msgstr ""
|
|||
msgid "Sat"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:208 mod/settings.php:948 include/text.php:1274
|
||||
#: mod/events.php:208 mod/settings.php:952 include/text.php:1245
|
||||
msgid "Sunday"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:209 mod/settings.php:948 include/text.php:1274
|
||||
#: mod/events.php:209 mod/settings.php:952 include/text.php:1245
|
||||
msgid "Monday"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:210 include/text.php:1274
|
||||
#: mod/events.php:210 include/text.php:1245
|
||||
msgid "Tuesday"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:211 include/text.php:1274
|
||||
#: mod/events.php:211 include/text.php:1245
|
||||
msgid "Wednesday"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:212 include/text.php:1274
|
||||
#: mod/events.php:212 include/text.php:1245
|
||||
msgid "Thursday"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:213 include/text.php:1274
|
||||
#: mod/events.php:213 include/text.php:1245
|
||||
msgid "Friday"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:214 include/text.php:1274
|
||||
#: mod/events.php:214 include/text.php:1245
|
||||
msgid "Saturday"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -3406,7 +3458,7 @@ msgstr ""
|
|||
msgid "Apr"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:219 mod/events.php:231 include/text.php:1278
|
||||
#: mod/events.php:219 mod/events.php:231 include/text.php:1249
|
||||
msgid "May"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -3438,47 +3490,47 @@ msgstr ""
|
|||
msgid "Dec"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:227 include/text.php:1278
|
||||
#: mod/events.php:227 include/text.php:1249
|
||||
msgid "January"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:228 include/text.php:1278
|
||||
#: mod/events.php:228 include/text.php:1249
|
||||
msgid "February"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:229 include/text.php:1278
|
||||
#: mod/events.php:229 include/text.php:1249
|
||||
msgid "March"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:230 include/text.php:1278
|
||||
#: mod/events.php:230 include/text.php:1249
|
||||
msgid "April"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:232 include/text.php:1278
|
||||
#: mod/events.php:232 include/text.php:1249
|
||||
msgid "June"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:233 include/text.php:1278
|
||||
#: mod/events.php:233 include/text.php:1249
|
||||
msgid "July"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:234 include/text.php:1278
|
||||
#: mod/events.php:234 include/text.php:1249
|
||||
msgid "August"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:235 include/text.php:1278
|
||||
#: mod/events.php:235 include/text.php:1249
|
||||
msgid "September"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:236 include/text.php:1278
|
||||
#: mod/events.php:236 include/text.php:1249
|
||||
msgid "October"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:237 include/text.php:1278
|
||||
#: mod/events.php:237 include/text.php:1249
|
||||
msgid "November"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:238 include/text.php:1278
|
||||
#: mod/events.php:238 include/text.php:1249
|
||||
msgid "December"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -3486,15 +3538,15 @@ msgstr ""
|
|||
msgid "today"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:240 include/datetime.php:288
|
||||
#: mod/events.php:240 include/datetime.php:344
|
||||
msgid "month"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:241 include/datetime.php:289
|
||||
#: mod/events.php:241 include/datetime.php:345
|
||||
msgid "week"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:242 include/datetime.php:290
|
||||
#: mod/events.php:242 include/datetime.php:346
|
||||
msgid "day"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -3506,11 +3558,11 @@ msgstr ""
|
|||
msgid "Edit event"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:421 include/text.php:1728 include/text.php:1735
|
||||
#: mod/events.php:421 include/text.php:1651 include/text.php:1658
|
||||
msgid "link to source"
|
||||
msgstr ""
|
||||
|
||||
#: mod/events.php:456 include/identity.php:722 include/nav.php:79
|
||||
#: mod/events.php:456 include/identity.php:723 include/nav.php:79
|
||||
#: include/nav.php:140 view/theme/diabook/theme.php:127
|
||||
msgid "Events"
|
||||
msgstr ""
|
||||
|
|
@ -3568,7 +3620,7 @@ msgid "Share this event"
|
|||
msgstr ""
|
||||
|
||||
#: mod/events.php:572 mod/content.php:721 mod/editpost.php:145
|
||||
#: mod/photos.php:1631 mod/photos.php:1679 mod/photos.php:1767
|
||||
#: mod/photos.php:1617 mod/photos.php:1665 mod/photos.php:1753
|
||||
#: object/Item.php:719 include/conversation.php:1216
|
||||
msgid "Preview"
|
||||
msgstr ""
|
||||
|
|
@ -3584,7 +3636,7 @@ msgid ""
|
|||
"code or the translation of Friendica. Thank you all!"
|
||||
msgstr ""
|
||||
|
||||
#: mod/content.php:439 mod/content.php:742 mod/photos.php:1722
|
||||
#: mod/content.php:439 mod/content.php:742 mod/photos.php:1708
|
||||
#: object/Item.php:133 include/conversation.php:634
|
||||
msgid "Select"
|
||||
msgstr ""
|
||||
|
|
@ -3613,23 +3665,23 @@ msgstr[0] ""
|
|||
msgstr[1] ""
|
||||
|
||||
#: mod/content.php:607 object/Item.php:421 object/Item.php:434
|
||||
#: include/text.php:2004
|
||||
#: include/text.php:1927
|
||||
msgid "comment"
|
||||
msgid_plural "comments"
|
||||
msgstr[0] ""
|
||||
msgstr[1] ""
|
||||
|
||||
#: mod/content.php:608 boot.php:870 object/Item.php:422
|
||||
#: include/contact_widgets.php:242 include/forums.php:110
|
||||
#: include/items.php:5207 view/theme/vier/theme.php:264
|
||||
#: mod/content.php:608 boot.php:872 object/Item.php:422
|
||||
#: include/contact_widgets.php:242 include/ForumManager.php:117
|
||||
#: include/items.php:2113 view/theme/vier/theme.php:260
|
||||
msgid "show more"
|
||||
msgstr ""
|
||||
|
||||
#: mod/content.php:622 mod/photos.php:1418 object/Item.php:117
|
||||
#: mod/content.php:622 mod/photos.php:1404 object/Item.php:117
|
||||
msgid "Private Message"
|
||||
msgstr ""
|
||||
|
||||
#: mod/content.php:686 mod/photos.php:1607 object/Item.php:253
|
||||
#: mod/content.php:686 mod/photos.php:1593 object/Item.php:253
|
||||
msgid "I like this (toggle)"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -3637,7 +3689,7 @@ msgstr ""
|
|||
msgid "like"
|
||||
msgstr ""
|
||||
|
||||
#: mod/content.php:687 mod/photos.php:1608 object/Item.php:254
|
||||
#: mod/content.php:687 mod/photos.php:1594 object/Item.php:254
|
||||
msgid "I don't like this (toggle)"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -3653,13 +3705,13 @@ msgstr ""
|
|||
msgid "share"
|
||||
msgstr ""
|
||||
|
||||
#: mod/content.php:709 mod/photos.php:1627 mod/photos.php:1675
|
||||
#: mod/photos.php:1763 object/Item.php:707
|
||||
#: mod/content.php:709 mod/photos.php:1613 mod/photos.php:1661
|
||||
#: mod/photos.php:1749 object/Item.php:707
|
||||
msgid "This is you"
|
||||
msgstr ""
|
||||
|
||||
#: mod/content.php:711 mod/photos.php:1629 mod/photos.php:1677
|
||||
#: mod/photos.php:1765 boot.php:869 object/Item.php:393 object/Item.php:709
|
||||
#: mod/content.php:711 mod/photos.php:1615 mod/photos.php:1663
|
||||
#: mod/photos.php:1751 boot.php:871 object/Item.php:393 object/Item.php:709
|
||||
msgid "Comment"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -3695,7 +3747,7 @@ msgstr ""
|
|||
msgid "Video"
|
||||
msgstr ""
|
||||
|
||||
#: mod/content.php:730 mod/settings.php:721 object/Item.php:122
|
||||
#: mod/content.php:730 mod/settings.php:722 object/Item.php:122
|
||||
#: object/Item.php:124
|
||||
msgid "Edit"
|
||||
msgstr ""
|
||||
|
|
@ -4094,19 +4146,19 @@ msgstr ""
|
|||
msgid "Help:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/help.php:47 include/nav.php:113 view/theme/vier/theme.php:302
|
||||
#: mod/help.php:47 include/nav.php:113 view/theme/vier/theme.php:298
|
||||
msgid "Help"
|
||||
msgstr ""
|
||||
|
||||
#: mod/help.php:53 mod/p.php:16 mod/p.php:25 index.php:270
|
||||
#: mod/help.php:53 mod/p.php:16 mod/p.php:25 index.php:271
|
||||
msgid "Not Found"
|
||||
msgstr ""
|
||||
|
||||
#: mod/help.php:56 index.php:273
|
||||
#: mod/help.php:56 index.php:274
|
||||
msgid "Page not found."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_poll.php:103 mod/dfrn_poll.php:536
|
||||
#: mod/dfrn_poll.php:101 mod/dfrn_poll.php:534
|
||||
#, php-format
|
||||
msgid "%1$s welcomes %2$s"
|
||||
msgstr ""
|
||||
|
|
@ -4170,7 +4222,7 @@ msgstr ""
|
|||
msgid "Display"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:65 mod/settings.php:864
|
||||
#: mod/settings.php:65 mod/settings.php:868
|
||||
msgid "Social Networks"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -4182,7 +4234,7 @@ msgstr ""
|
|||
msgid "Connected apps"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:93 mod/uexport.php:85
|
||||
#: mod/settings.php:93 mod/uexport.php:37
|
||||
msgid "Export personal data"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -4194,685 +4246,689 @@ msgstr ""
|
|||
msgid "Missing some important data!"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:266
|
||||
#: mod/settings.php:267
|
||||
msgid "Failed to connect with email account using the settings provided."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:271
|
||||
#: mod/settings.php:272
|
||||
msgid "Email settings updated."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:286
|
||||
#: mod/settings.php:287
|
||||
msgid "Features updated"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:353
|
||||
#: mod/settings.php:354
|
||||
msgid "Relocate message has been send to your contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:367 include/user.php:39
|
||||
#: mod/settings.php:368 include/user.php:39
|
||||
msgid "Passwords do not match. Password unchanged."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:372
|
||||
#: mod/settings.php:373
|
||||
msgid "Empty passwords are not allowed. Password unchanged."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:380
|
||||
#: mod/settings.php:381
|
||||
msgid "Wrong password."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:391
|
||||
#: mod/settings.php:392
|
||||
msgid "Password changed."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:393
|
||||
#: mod/settings.php:394
|
||||
msgid "Password update failed. Please try again."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:462
|
||||
#: mod/settings.php:463
|
||||
msgid " Please use a shorter name."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:464
|
||||
#: mod/settings.php:465
|
||||
msgid " Name too short."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:473
|
||||
#: mod/settings.php:474
|
||||
msgid "Wrong Password"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:478
|
||||
#: mod/settings.php:479
|
||||
msgid " Not valid email."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:484
|
||||
#: mod/settings.php:485
|
||||
msgid " Cannot change to that email."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:540
|
||||
#: mod/settings.php:541
|
||||
msgid "Private forum has no privacy permissions. Using default privacy group."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:544
|
||||
#: mod/settings.php:545
|
||||
msgid "Private forum has no privacy permissions and no default privacy group."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:583
|
||||
#: mod/settings.php:584
|
||||
msgid "Settings updated."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:658 mod/settings.php:684 mod/settings.php:720
|
||||
#: mod/settings.php:659 mod/settings.php:685 mod/settings.php:721
|
||||
msgid "Add application"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:662 mod/settings.php:688
|
||||
#: mod/settings.php:663 mod/settings.php:689
|
||||
msgid "Consumer Key"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:663 mod/settings.php:689
|
||||
#: mod/settings.php:664 mod/settings.php:690
|
||||
msgid "Consumer Secret"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:664 mod/settings.php:690
|
||||
#: mod/settings.php:665 mod/settings.php:691
|
||||
msgid "Redirect"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:665 mod/settings.php:691
|
||||
#: mod/settings.php:666 mod/settings.php:692
|
||||
msgid "Icon url"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:676
|
||||
#: mod/settings.php:677
|
||||
msgid "You can't edit this application."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:719
|
||||
#: mod/settings.php:720
|
||||
msgid "Connected Apps"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:723
|
||||
#: mod/settings.php:724
|
||||
msgid "Client key starts with"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:724
|
||||
#: mod/settings.php:725
|
||||
msgid "No name"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:725
|
||||
#: mod/settings.php:726
|
||||
msgid "Remove authorization"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:737
|
||||
#: mod/settings.php:738
|
||||
msgid "No Plugin settings configured"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:745
|
||||
#: mod/settings.php:746
|
||||
msgid "Plugin Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:767
|
||||
#: mod/settings.php:768
|
||||
msgid "Additional Features"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:777 mod/settings.php:781
|
||||
#: mod/settings.php:778 mod/settings.php:782
|
||||
msgid "General Social Media Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:787
|
||||
#: mod/settings.php:788
|
||||
msgid "Disable intelligent shortening"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:789
|
||||
#: mod/settings.php:790
|
||||
msgid ""
|
||||
"Normally the system tries to find the best link to add to shortened posts. "
|
||||
"If this option is enabled then every shortened post will always point to the "
|
||||
"original friendica post."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:795
|
||||
#: mod/settings.php:796
|
||||
msgid "Automatically follow any GNU Social (OStatus) followers/mentioners"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:797
|
||||
#: mod/settings.php:798
|
||||
msgid ""
|
||||
"If you receive a message from an unknown OStatus user, this option decides "
|
||||
"what to do. If it is checked, a new contact will be created for every "
|
||||
"unknown user."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:806
|
||||
#: mod/settings.php:804
|
||||
msgid "Default group for OStatus contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:810
|
||||
msgid "Your legacy GNU Social account"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:808
|
||||
#: mod/settings.php:812
|
||||
msgid ""
|
||||
"If you enter your old GNU Social/Statusnet account name here (in the format "
|
||||
"user@domain.tld), your contacts will be added automatically. The field will "
|
||||
"be emptied when done."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:811
|
||||
#: mod/settings.php:815
|
||||
msgid "Repair OStatus subscriptions"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:820 mod/settings.php:821
|
||||
#: mod/settings.php:824 mod/settings.php:825
|
||||
#, php-format
|
||||
msgid "Built-in support for %s connectivity is %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:820 mod/dfrn_request.php:865
|
||||
#: mod/settings.php:824 mod/dfrn_request.php:863
|
||||
#: include/contact_selectors.php:80
|
||||
msgid "Diaspora"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:820 mod/settings.php:821
|
||||
#: mod/settings.php:824 mod/settings.php:825
|
||||
msgid "enabled"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:820 mod/settings.php:821
|
||||
#: mod/settings.php:824 mod/settings.php:825
|
||||
msgid "disabled"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:821
|
||||
#: mod/settings.php:825
|
||||
msgid "GNU Social (OStatus)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:857
|
||||
#: mod/settings.php:861
|
||||
msgid "Email access is disabled on this site."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:869
|
||||
#: mod/settings.php:873
|
||||
msgid "Email/Mailbox Setup"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:870
|
||||
#: mod/settings.php:874
|
||||
msgid ""
|
||||
"If you wish to communicate with email contacts using this service "
|
||||
"(optional), please specify how to connect to your mailbox."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:871
|
||||
#: mod/settings.php:875
|
||||
msgid "Last successful email check:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:873
|
||||
#: mod/settings.php:877
|
||||
msgid "IMAP server name:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:874
|
||||
#: mod/settings.php:878
|
||||
msgid "IMAP port:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:875
|
||||
#: mod/settings.php:879
|
||||
msgid "Security:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:875 mod/settings.php:880
|
||||
#: mod/settings.php:879 mod/settings.php:884
|
||||
msgid "None"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:876
|
||||
#: mod/settings.php:880
|
||||
msgid "Email login name:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:877
|
||||
#: mod/settings.php:881
|
||||
msgid "Email password:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:878
|
||||
#: mod/settings.php:882
|
||||
msgid "Reply-to address:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:879
|
||||
#: mod/settings.php:883
|
||||
msgid "Send public posts to all email contacts:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:880
|
||||
#: mod/settings.php:884
|
||||
msgid "Action after import:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:880
|
||||
#: mod/settings.php:884
|
||||
msgid "Mark as seen"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:880
|
||||
#: mod/settings.php:884
|
||||
msgid "Move to folder"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:881
|
||||
#: mod/settings.php:885
|
||||
msgid "Move to folder:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:967
|
||||
#: mod/settings.php:971
|
||||
msgid "Display Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:973 mod/settings.php:991
|
||||
#: mod/settings.php:977 mod/settings.php:995
|
||||
msgid "Display Theme:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:974
|
||||
#: mod/settings.php:978
|
||||
msgid "Mobile Theme:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:975
|
||||
#: mod/settings.php:979
|
||||
msgid "Update browser every xx seconds"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:975
|
||||
#: mod/settings.php:979
|
||||
msgid "Minimum of 10 seconds. Enter -1 to disable it."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:976
|
||||
#: mod/settings.php:980
|
||||
msgid "Number of items to display per page:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:976 mod/settings.php:977
|
||||
#: mod/settings.php:980 mod/settings.php:981
|
||||
msgid "Maximum of 100 items"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:977
|
||||
#: mod/settings.php:981
|
||||
msgid "Number of items to display per page when viewed from mobile device:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:978
|
||||
#: mod/settings.php:982
|
||||
msgid "Don't show emoticons"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:979
|
||||
#: mod/settings.php:983
|
||||
msgid "Calendar"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:980
|
||||
#: mod/settings.php:984
|
||||
msgid "Beginning of week:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:981
|
||||
#: mod/settings.php:985
|
||||
msgid "Don't show notices"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:982
|
||||
#: mod/settings.php:986
|
||||
msgid "Infinite scroll"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:983
|
||||
#: mod/settings.php:987
|
||||
msgid "Automatic updates only at the top of the network page"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:985 view/theme/cleanzero/config.php:82
|
||||
#: mod/settings.php:989 view/theme/cleanzero/config.php:82
|
||||
#: view/theme/dispy/config.php:72 view/theme/quattro/config.php:66
|
||||
#: view/theme/diabook/config.php:150 view/theme/vier/config.php:109
|
||||
#: view/theme/duepuntozero/config.php:61
|
||||
msgid "Theme settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1062
|
||||
#: mod/settings.php:1066
|
||||
msgid "User Types"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1063
|
||||
#: mod/settings.php:1067
|
||||
msgid "Community Types"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1064
|
||||
#: mod/settings.php:1068
|
||||
msgid "Normal Account Page"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1065
|
||||
#: mod/settings.php:1069
|
||||
msgid "This account is a normal personal profile"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1068
|
||||
#: mod/settings.php:1072
|
||||
msgid "Soapbox Page"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1069
|
||||
#: mod/settings.php:1073
|
||||
msgid "Automatically approve all connection/friend requests as read-only fans"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1072
|
||||
#: mod/settings.php:1076
|
||||
msgid "Community Forum/Celebrity Account"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1073
|
||||
#: mod/settings.php:1077
|
||||
msgid "Automatically approve all connection/friend requests as read-write fans"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1076
|
||||
#: mod/settings.php:1080
|
||||
msgid "Automatic Friend Page"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1077
|
||||
#: mod/settings.php:1081
|
||||
msgid "Automatically approve all connection/friend requests as friends"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1080
|
||||
#: mod/settings.php:1084
|
||||
msgid "Private Forum [Experimental]"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1081
|
||||
#: mod/settings.php:1085
|
||||
msgid "Private forum - approved members only"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1093
|
||||
#: mod/settings.php:1097
|
||||
msgid "OpenID:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1093
|
||||
#: mod/settings.php:1097
|
||||
msgid "(Optional) Allow this OpenID to login to this account."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1103
|
||||
#: mod/settings.php:1107
|
||||
msgid "Publish your default profile in your local site directory?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1109
|
||||
#: mod/settings.php:1113
|
||||
msgid "Publish your default profile in the global social directory?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1117
|
||||
#: mod/settings.php:1121
|
||||
msgid "Hide your contact/friend list from viewers of your default profile?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1121 include/acl_selectors.php:331
|
||||
#: mod/settings.php:1125 include/acl_selectors.php:331
|
||||
msgid "Hide your profile details from unknown viewers?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1121
|
||||
#: mod/settings.php:1125
|
||||
msgid ""
|
||||
"If enabled, posting public messages to Diaspora and other networks isn't "
|
||||
"possible."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1126
|
||||
#: mod/settings.php:1130
|
||||
msgid "Allow friends to post to your profile page?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1132
|
||||
#: mod/settings.php:1136
|
||||
msgid "Allow friends to tag your posts?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1138
|
||||
#: mod/settings.php:1142
|
||||
msgid "Allow us to suggest you as a potential friend to new members?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1144
|
||||
#: mod/settings.php:1148
|
||||
msgid "Permit unknown people to send you private mail?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1152
|
||||
#: mod/settings.php:1156
|
||||
msgid "Profile is <strong>not published</strong>."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1160
|
||||
#: mod/settings.php:1164
|
||||
#, php-format
|
||||
msgid "Your Identity Address is <strong>'%s'</strong> or '%s'."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1167
|
||||
#: mod/settings.php:1171
|
||||
msgid "Automatically expire posts after this many days:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1167
|
||||
#: mod/settings.php:1171
|
||||
msgid "If empty, posts will not expire. Expired posts will be deleted"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1168
|
||||
#: mod/settings.php:1172
|
||||
msgid "Advanced expiration settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1169
|
||||
#: mod/settings.php:1173
|
||||
msgid "Advanced Expiration"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1170
|
||||
#: mod/settings.php:1174
|
||||
msgid "Expire posts:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1171
|
||||
#: mod/settings.php:1175
|
||||
msgid "Expire personal notes:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1172
|
||||
#: mod/settings.php:1176
|
||||
msgid "Expire starred posts:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1173
|
||||
#: mod/settings.php:1177
|
||||
msgid "Expire photos:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1174
|
||||
#: mod/settings.php:1178
|
||||
msgid "Only expire posts by others:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1202
|
||||
#: mod/settings.php:1206
|
||||
msgid "Account Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1210
|
||||
#: mod/settings.php:1214
|
||||
msgid "Password Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1211 mod/register.php:274
|
||||
#: mod/settings.php:1215 mod/register.php:274
|
||||
msgid "New Password:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1212 mod/register.php:275
|
||||
#: mod/settings.php:1216 mod/register.php:275
|
||||
msgid "Confirm:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1212
|
||||
#: mod/settings.php:1216
|
||||
msgid "Leave password fields blank unless changing"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1213
|
||||
#: mod/settings.php:1217
|
||||
msgid "Current Password:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1213 mod/settings.php:1214
|
||||
#: mod/settings.php:1217 mod/settings.php:1218
|
||||
msgid "Your current password to confirm the changes"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1214
|
||||
#: mod/settings.php:1218
|
||||
msgid "Password:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1218
|
||||
#: mod/settings.php:1222
|
||||
msgid "Basic Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1219 include/identity.php:588
|
||||
#: mod/settings.php:1223 include/identity.php:589
|
||||
msgid "Full Name:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1220
|
||||
#: mod/settings.php:1224
|
||||
msgid "Email Address:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1221
|
||||
#: mod/settings.php:1225
|
||||
msgid "Your Timezone:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1222
|
||||
#: mod/settings.php:1226
|
||||
msgid "Your Language:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1222
|
||||
#: mod/settings.php:1226
|
||||
msgid ""
|
||||
"Set the language we use to show you friendica interface and to send you "
|
||||
"emails"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1223
|
||||
#: mod/settings.php:1227
|
||||
msgid "Default Post Location:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1224
|
||||
#: mod/settings.php:1228
|
||||
msgid "Use Browser Location:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1227
|
||||
#: mod/settings.php:1231
|
||||
msgid "Security and Privacy Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1229
|
||||
#: mod/settings.php:1233
|
||||
msgid "Maximum Friend Requests/Day:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1229 mod/settings.php:1259
|
||||
#: mod/settings.php:1233 mod/settings.php:1263
|
||||
msgid "(to prevent spam abuse)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1230
|
||||
#: mod/settings.php:1234
|
||||
msgid "Default Post Permissions"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1231
|
||||
#: mod/settings.php:1235
|
||||
msgid "(click to open/close)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1240 mod/photos.php:1199 mod/photos.php:1584
|
||||
#: mod/settings.php:1244 mod/photos.php:1185 mod/photos.php:1570
|
||||
msgid "Show to Groups"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1241 mod/photos.php:1200 mod/photos.php:1585
|
||||
#: mod/settings.php:1245 mod/photos.php:1186 mod/photos.php:1571
|
||||
msgid "Show to Contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1242
|
||||
#: mod/settings.php:1246
|
||||
msgid "Default Private Post"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1243
|
||||
#: mod/settings.php:1247
|
||||
msgid "Default Public Post"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1247
|
||||
#: mod/settings.php:1251
|
||||
msgid "Default Permissions for New Posts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1259
|
||||
#: mod/settings.php:1263
|
||||
msgid "Maximum private messages per day from unknown people:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1262
|
||||
#: mod/settings.php:1266
|
||||
msgid "Notification Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1263
|
||||
#: mod/settings.php:1267
|
||||
msgid "By default post a status message when:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1264
|
||||
#: mod/settings.php:1268
|
||||
msgid "accepting a friend request"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1265
|
||||
#: mod/settings.php:1269
|
||||
msgid "joining a forum/community"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1266
|
||||
#: mod/settings.php:1270
|
||||
msgid "making an <em>interesting</em> profile change"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1267
|
||||
#: mod/settings.php:1271
|
||||
msgid "Send a notification email when:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1268
|
||||
#: mod/settings.php:1272
|
||||
msgid "You receive an introduction"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1269
|
||||
#: mod/settings.php:1273
|
||||
msgid "Your introductions are confirmed"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1270
|
||||
#: mod/settings.php:1274
|
||||
msgid "Someone writes on your profile wall"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1271
|
||||
#: mod/settings.php:1275
|
||||
msgid "Someone writes a followup comment"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1272
|
||||
#: mod/settings.php:1276
|
||||
msgid "You receive a private message"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1273
|
||||
#: mod/settings.php:1277
|
||||
msgid "You receive a friend suggestion"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1274
|
||||
#: mod/settings.php:1278
|
||||
msgid "You are tagged in a post"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1275
|
||||
#: mod/settings.php:1279
|
||||
msgid "You are poked/prodded/etc. in a post"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1277
|
||||
#: mod/settings.php:1281
|
||||
msgid "Activate desktop notifications"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1277
|
||||
#: mod/settings.php:1281
|
||||
msgid "Show desktop popup on new notifications"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1279
|
||||
#: mod/settings.php:1283
|
||||
msgid "Text-only notification emails"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1281
|
||||
#: mod/settings.php:1285
|
||||
msgid "Send text only notification emails, without the html part"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1283
|
||||
#: mod/settings.php:1287
|
||||
msgid "Advanced Account/Page Type Settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1284
|
||||
#: mod/settings.php:1288
|
||||
msgid "Change the behaviour of this account for special situations"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1287
|
||||
#: mod/settings.php:1291
|
||||
msgid "Relocate"
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1288
|
||||
#: mod/settings.php:1292
|
||||
msgid ""
|
||||
"If you have moved this profile from another server, and some of your "
|
||||
"contacts don't receive your updates, try pushing this button."
|
||||
msgstr ""
|
||||
|
||||
#: mod/settings.php:1289
|
||||
#: mod/settings.php:1293
|
||||
msgid "Resend relocate message to contacts"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:96
|
||||
#: mod/dfrn_request.php:98
|
||||
msgid "This introduction has already been accepted."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:119 mod/dfrn_request.php:516
|
||||
#: mod/dfrn_request.php:121 mod/dfrn_request.php:514
|
||||
msgid "Profile location is not valid or does not contain profile information."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:124 mod/dfrn_request.php:521
|
||||
#: mod/dfrn_request.php:126 mod/dfrn_request.php:519
|
||||
msgid "Warning: profile location has no identifiable owner name."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:126 mod/dfrn_request.php:523
|
||||
#: mod/dfrn_request.php:128 mod/dfrn_request.php:521
|
||||
msgid "Warning: profile location has no profile photo."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:129 mod/dfrn_request.php:526
|
||||
#: mod/dfrn_request.php:131 mod/dfrn_request.php:524
|
||||
#, php-format
|
||||
msgid "%d required parameter was not found at the given location"
|
||||
msgid_plural "%d required parameters were not found at the given location"
|
||||
msgstr[0] ""
|
||||
msgstr[1] ""
|
||||
|
||||
#: mod/dfrn_request.php:172
|
||||
#: mod/dfrn_request.php:174
|
||||
msgid "Introduction complete."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -4909,93 +4965,93 @@ msgstr ""
|
|||
msgid "This account has not been configured for email. Request failed."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:474
|
||||
#: mod/dfrn_request.php:472
|
||||
msgid "You have already introduced yourself here."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:478
|
||||
#: mod/dfrn_request.php:476
|
||||
#, php-format
|
||||
msgid "Apparently you are already friends with %s."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:499
|
||||
#: mod/dfrn_request.php:497
|
||||
msgid "Invalid profile URL."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:505 include/follow.php:72
|
||||
#: mod/dfrn_request.php:503 include/follow.php:76
|
||||
msgid "Disallowed profile URL."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:596
|
||||
#: mod/dfrn_request.php:594
|
||||
msgid "Your introduction has been sent."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:636
|
||||
#: mod/dfrn_request.php:634
|
||||
msgid ""
|
||||
"Remote subscription can't be done for your network. Please subscribe "
|
||||
"directly on your system."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:659
|
||||
#: mod/dfrn_request.php:657
|
||||
msgid "Please login to confirm introduction."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:669
|
||||
#: mod/dfrn_request.php:667
|
||||
msgid ""
|
||||
"Incorrect identity currently logged in. Please login to <strong>this</"
|
||||
"strong> profile."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:683 mod/dfrn_request.php:700
|
||||
#: mod/dfrn_request.php:681 mod/dfrn_request.php:698
|
||||
msgid "Confirm"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:695
|
||||
#: mod/dfrn_request.php:693
|
||||
msgid "Hide this contact"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:698
|
||||
#: mod/dfrn_request.php:696
|
||||
#, php-format
|
||||
msgid "Welcome home %s."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:699
|
||||
#: mod/dfrn_request.php:697
|
||||
#, php-format
|
||||
msgid "Please confirm your introduction/connection request to %s."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:828
|
||||
#: mod/dfrn_request.php:826
|
||||
msgid ""
|
||||
"Please enter your 'Identity Address' from one of the following supported "
|
||||
"communications networks:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:849
|
||||
#: mod/dfrn_request.php:847
|
||||
#, php-format
|
||||
msgid ""
|
||||
"If you are not yet a member of the free social web, <a href=\"%s/siteinfo"
|
||||
"\">follow this link to find a public Friendica site and join us today</a>."
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:854
|
||||
#: mod/dfrn_request.php:852
|
||||
msgid "Friend/Connection Request"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:855
|
||||
#: mod/dfrn_request.php:853
|
||||
msgid ""
|
||||
"Examples: jojo@demo.friendica.com, http://demo.friendica.com/profile/jojo, "
|
||||
"testuser@identi.ca"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:863 include/contact_selectors.php:76
|
||||
#: mod/dfrn_request.php:861 include/contact_selectors.php:76
|
||||
msgid "Friendica"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:864
|
||||
#: mod/dfrn_request.php:862
|
||||
msgid "StatusNet/Federated Social Web"
|
||||
msgstr ""
|
||||
|
||||
#: mod/dfrn_request.php:866
|
||||
#: mod/dfrn_request.php:864
|
||||
#, php-format
|
||||
msgid ""
|
||||
" - please do not use this form. Instead, enter %s into your Diaspora search "
|
||||
|
|
@ -5083,7 +5139,7 @@ msgstr ""
|
|||
msgid "Choose a nickname: "
|
||||
msgstr ""
|
||||
|
||||
#: mod/register.php:280 boot.php:1405 include/nav.php:108
|
||||
#: mod/register.php:280 boot.php:1495 include/nav.php:108
|
||||
msgid "Register"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5111,7 +5167,7 @@ msgstr ""
|
|||
msgid "Only one search per minute is permitted for not logged in users."
|
||||
msgstr ""
|
||||
|
||||
#: mod/search.php:136 include/text.php:1003 include/nav.php:118
|
||||
#: mod/search.php:136 include/text.php:974 include/nav.php:118
|
||||
msgid "Search"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5125,16 +5181,16 @@ msgstr ""
|
|||
msgid "Search results for: %s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/directory.php:149 include/identity.php:313 include/identity.php:610
|
||||
#: mod/directory.php:149 include/identity.php:314 include/identity.php:611
|
||||
msgid "Status:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/directory.php:151 include/identity.php:315 include/identity.php:621
|
||||
#: mod/directory.php:151 include/identity.php:316 include/identity.php:622
|
||||
msgid "Homepage:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/directory.php:203 view/theme/diabook/theme.php:525
|
||||
#: view/theme/vier/theme.php:205
|
||||
#: view/theme/vier/theme.php:201
|
||||
msgid "Global Directory"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5193,21 +5249,21 @@ msgstr ""
|
|||
msgid "No contacts in common."
|
||||
msgstr ""
|
||||
|
||||
#: mod/uexport.php:77
|
||||
#: mod/uexport.php:29
|
||||
msgid "Export account"
|
||||
msgstr ""
|
||||
|
||||
#: mod/uexport.php:77
|
||||
#: mod/uexport.php:29
|
||||
msgid ""
|
||||
"Export your account info and contacts. Use this to make a backup of your "
|
||||
"account and/or to move it to another server."
|
||||
msgstr ""
|
||||
|
||||
#: mod/uexport.php:78
|
||||
#: mod/uexport.php:30
|
||||
msgid "Export all"
|
||||
msgstr ""
|
||||
|
||||
#: mod/uexport.php:78
|
||||
#: mod/uexport.php:30
|
||||
msgid ""
|
||||
"Export your accout info, contacts and all your items as json. Could be a "
|
||||
"very big file, and could take a lot of time. Use this to make a full backup "
|
||||
|
|
@ -5242,7 +5298,7 @@ msgid "Ignore/Hide"
|
|||
msgstr ""
|
||||
|
||||
#: mod/suggest.php:111 include/contact_widgets.php:35
|
||||
#: view/theme/diabook/theme.php:527 view/theme/vier/theme.php:207
|
||||
#: view/theme/diabook/theme.php:527 view/theme/vier/theme.php:203
|
||||
msgid "Friend Suggestions"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5274,11 +5330,11 @@ msgstr ""
|
|||
msgid "Romantic Partner"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:344 mod/photos.php:1647 include/conversation.php:508
|
||||
#: mod/profiles.php:344 mod/photos.php:1633 include/conversation.php:508
|
||||
msgid "Likes"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:348 mod/photos.php:1647 include/conversation.php:508
|
||||
#: mod/profiles.php:348 mod/photos.php:1633 include/conversation.php:508
|
||||
msgid "Dislikes"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5306,7 +5362,7 @@ msgstr ""
|
|||
msgid "Homepage"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:375 mod/profiles.php:708
|
||||
#: mod/profiles.php:375 mod/profiles.php:686
|
||||
msgid "Interests"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5314,7 +5370,7 @@ msgstr ""
|
|||
msgid "Address"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:386 mod/profiles.php:704
|
||||
#: mod/profiles.php:386 mod/profiles.php:682
|
||||
msgid "Location"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5322,260 +5378,260 @@ msgstr ""
|
|||
msgid "Profile updated."
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:565
|
||||
#: mod/profiles.php:551
|
||||
msgid " and "
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:573
|
||||
#: mod/profiles.php:559
|
||||
msgid "public profile"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:576
|
||||
#: mod/profiles.php:562
|
||||
#, php-format
|
||||
msgid "%1$s changed %2$s to “%3$s”"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:577
|
||||
#: mod/profiles.php:563
|
||||
#, php-format
|
||||
msgid " - Visit %1$s's %2$s"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:580
|
||||
#: mod/profiles.php:566
|
||||
#, php-format
|
||||
msgid "%1$s has an updated %2$s, changing %3$s."
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:655
|
||||
#: mod/profiles.php:633
|
||||
msgid "Hide contacts and friends:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:660
|
||||
#: mod/profiles.php:638
|
||||
msgid "Hide your contact/friend list from viewers of this profile?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:684
|
||||
#: mod/profiles.php:662
|
||||
msgid "Show more profile fields:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:695
|
||||
#: mod/profiles.php:673
|
||||
msgid "Edit Profile Details"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:697
|
||||
#: mod/profiles.php:675
|
||||
msgid "Change Profile Photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:698
|
||||
#: mod/profiles.php:676
|
||||
msgid "View this profile"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:699
|
||||
#: mod/profiles.php:677
|
||||
msgid "Create a new profile using these settings"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:700
|
||||
#: mod/profiles.php:678
|
||||
msgid "Clone this profile"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:701
|
||||
#: mod/profiles.php:679
|
||||
msgid "Delete this profile"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:702
|
||||
#: mod/profiles.php:680
|
||||
msgid "Basic information"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:703
|
||||
#: mod/profiles.php:681
|
||||
msgid "Profile picture"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:705
|
||||
#: mod/profiles.php:683
|
||||
msgid "Preferences"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:706
|
||||
#: mod/profiles.php:684
|
||||
msgid "Status information"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:707
|
||||
#: mod/profiles.php:685
|
||||
msgid "Additional information"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:710
|
||||
#: mod/profiles.php:688
|
||||
msgid "Profile Name:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:711
|
||||
#: mod/profiles.php:689
|
||||
msgid "Your Full Name:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:712
|
||||
#: mod/profiles.php:690
|
||||
msgid "Title/Description:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:713
|
||||
#: mod/profiles.php:691
|
||||
msgid "Your Gender:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:714
|
||||
#: mod/profiles.php:692
|
||||
msgid "Birthday :"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:715
|
||||
#: mod/profiles.php:693
|
||||
msgid "Street Address:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:716
|
||||
#: mod/profiles.php:694
|
||||
msgid "Locality/City:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:717
|
||||
#: mod/profiles.php:695
|
||||
msgid "Postal/Zip Code:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:718
|
||||
#: mod/profiles.php:696
|
||||
msgid "Country:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:719
|
||||
#: mod/profiles.php:697
|
||||
msgid "Region/State:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:720
|
||||
#: mod/profiles.php:698
|
||||
msgid "<span class=\"heart\">♥</span> Marital Status:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:721
|
||||
#: mod/profiles.php:699
|
||||
msgid "Who: (if applicable)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:722
|
||||
#: mod/profiles.php:700
|
||||
msgid "Examples: cathy123, Cathy Williams, cathy@example.com"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:723
|
||||
#: mod/profiles.php:701
|
||||
msgid "Since [date]:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:724 include/identity.php:619
|
||||
#: mod/profiles.php:702 include/identity.php:620
|
||||
msgid "Sexual Preference:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:725
|
||||
#: mod/profiles.php:703
|
||||
msgid "Homepage URL:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:726 include/identity.php:623
|
||||
#: mod/profiles.php:704 include/identity.php:624
|
||||
msgid "Hometown:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:727 include/identity.php:627
|
||||
#: mod/profiles.php:705 include/identity.php:628
|
||||
msgid "Political Views:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:728
|
||||
#: mod/profiles.php:706
|
||||
msgid "Religious Views:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:729
|
||||
#: mod/profiles.php:707
|
||||
msgid "Public Keywords:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:730
|
||||
#: mod/profiles.php:708
|
||||
msgid "Private Keywords:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:731 include/identity.php:635
|
||||
#: mod/profiles.php:709 include/identity.php:636
|
||||
msgid "Likes:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:732 include/identity.php:637
|
||||
#: mod/profiles.php:710 include/identity.php:638
|
||||
msgid "Dislikes:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:733
|
||||
#: mod/profiles.php:711
|
||||
msgid "Example: fishing photography software"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:734
|
||||
#: mod/profiles.php:712
|
||||
msgid "(Used for suggesting potential friends, can be seen by others)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:735
|
||||
#: mod/profiles.php:713
|
||||
msgid "(Used for searching profiles, never shown to others)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:736
|
||||
#: mod/profiles.php:714
|
||||
msgid "Tell us about yourself..."
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:737
|
||||
#: mod/profiles.php:715
|
||||
msgid "Hobbies/Interests"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:738
|
||||
#: mod/profiles.php:716
|
||||
msgid "Contact information and Social Networks"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:739
|
||||
#: mod/profiles.php:717
|
||||
msgid "Musical interests"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:740
|
||||
#: mod/profiles.php:718
|
||||
msgid "Books, literature"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:741
|
||||
#: mod/profiles.php:719
|
||||
msgid "Television"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:742
|
||||
#: mod/profiles.php:720
|
||||
msgid "Film/dance/culture/entertainment"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:743
|
||||
#: mod/profiles.php:721
|
||||
msgid "Love/romance"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:744
|
||||
#: mod/profiles.php:722
|
||||
msgid "Work/employment"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:745
|
||||
#: mod/profiles.php:723
|
||||
msgid "School/education"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:750
|
||||
#: mod/profiles.php:728
|
||||
msgid ""
|
||||
"This is your <strong>public</strong> profile.<br />It <strong>may</strong> "
|
||||
"be visible to anybody using the internet."
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:760
|
||||
#: mod/profiles.php:738
|
||||
msgid "Age: "
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:813
|
||||
#: mod/profiles.php:791
|
||||
msgid "Edit/Manage Profiles"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:814 include/identity.php:260 include/identity.php:286
|
||||
#: mod/profiles.php:792 include/identity.php:261 include/identity.php:287
|
||||
msgid "Change profile photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:815 include/identity.php:261
|
||||
#: mod/profiles.php:793 include/identity.php:262
|
||||
msgid "Create New Profile"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:826 include/identity.php:271
|
||||
#: mod/profiles.php:804 include/identity.php:272
|
||||
msgid "Profile Image"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:828 include/identity.php:274
|
||||
#: mod/profiles.php:806 include/identity.php:275
|
||||
msgid "visible to everybody"
|
||||
msgstr ""
|
||||
|
||||
#: mod/profiles.php:829 include/identity.php:275
|
||||
#: mod/profiles.php:807 include/identity.php:276
|
||||
msgid "Edit visibility"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5721,7 +5777,7 @@ msgstr ""
|
|||
msgid "Visible to:"
|
||||
msgstr ""
|
||||
|
||||
#: mod/notes.php:46 include/identity.php:730
|
||||
#: mod/notes.php:46 include/identity.php:731
|
||||
msgid "Personal Notes"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5878,15 +5934,15 @@ msgid ""
|
|||
"important, please visit http://friendica.com"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:99 include/identity.php:705
|
||||
#: mod/photos.php:99 include/identity.php:706
|
||||
msgid "Photo Albums"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:100 mod/photos.php:1899
|
||||
#: mod/photos.php:100 mod/photos.php:1885
|
||||
msgid "Recent Photos"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:103 mod/photos.php:1320 mod/photos.php:1901
|
||||
#: mod/photos.php:103 mod/photos.php:1306 mod/photos.php:1887
|
||||
msgid "Upload New Photos"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5898,7 +5954,7 @@ msgstr ""
|
|||
msgid "Album not found."
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:232 mod/photos.php:244 mod/photos.php:1262
|
||||
#: mod/photos.php:232 mod/photos.php:244 mod/photos.php:1248
|
||||
msgid "Delete Album"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5906,7 +5962,7 @@ msgstr ""
|
|||
msgid "Do you really want to delete this photo album and all its photos?"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:322 mod/photos.php:333 mod/photos.php:1580
|
||||
#: mod/photos.php:322 mod/photos.php:333 mod/photos.php:1566
|
||||
msgid "Delete Photo"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5923,151 +5979,151 @@ msgstr ""
|
|||
msgid "a photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:819
|
||||
#: mod/photos.php:813
|
||||
msgid "Image file is empty."
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:986
|
||||
#: mod/photos.php:972
|
||||
msgid "No photos selected"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1147
|
||||
#: mod/photos.php:1133
|
||||
#, php-format
|
||||
msgid "You have used %1$.2f Mbytes of %2$.2f Mbytes photo storage."
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1182
|
||||
#: mod/photos.php:1168
|
||||
msgid "Upload Photos"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1186 mod/photos.php:1257
|
||||
#: mod/photos.php:1172 mod/photos.php:1243
|
||||
msgid "New album name: "
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1187
|
||||
#: mod/photos.php:1173
|
||||
msgid "or existing album name: "
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1188
|
||||
#: mod/photos.php:1174
|
||||
msgid "Do not show a status post for this upload"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1190 mod/photos.php:1575 include/acl_selectors.php:347
|
||||
#: mod/photos.php:1176 mod/photos.php:1561 include/acl_selectors.php:347
|
||||
msgid "Permissions"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1201
|
||||
#: mod/photos.php:1187
|
||||
msgid "Private Photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1202
|
||||
#: mod/photos.php:1188
|
||||
msgid "Public Photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1270
|
||||
#: mod/photos.php:1256
|
||||
msgid "Edit Album"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1276
|
||||
#: mod/photos.php:1262
|
||||
msgid "Show Newest First"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1278
|
||||
#: mod/photos.php:1264
|
||||
msgid "Show Oldest First"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1306 mod/photos.php:1884
|
||||
#: mod/photos.php:1292 mod/photos.php:1870
|
||||
msgid "View Photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1353
|
||||
#: mod/photos.php:1339
|
||||
msgid "Permission denied. Access to this item may be restricted."
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1355
|
||||
#: mod/photos.php:1341
|
||||
msgid "Photo not available"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1411
|
||||
#: mod/photos.php:1397
|
||||
msgid "View photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1411
|
||||
#: mod/photos.php:1397
|
||||
msgid "Edit photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1412
|
||||
#: mod/photos.php:1398
|
||||
msgid "Use as profile photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1437
|
||||
#: mod/photos.php:1423
|
||||
msgid "View Full Size"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1523
|
||||
#: mod/photos.php:1509
|
||||
msgid "Tags: "
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1526
|
||||
#: mod/photos.php:1512
|
||||
msgid "[Remove any tag]"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1566
|
||||
#: mod/photos.php:1552
|
||||
msgid "New album name"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1567
|
||||
#: mod/photos.php:1553
|
||||
msgid "Caption"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1568
|
||||
#: mod/photos.php:1554
|
||||
msgid "Add a Tag"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1568
|
||||
#: mod/photos.php:1554
|
||||
msgid "Example: @bob, @Barbara_Jensen, @jim@example.com, #California, #camping"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1569
|
||||
#: mod/photos.php:1555
|
||||
msgid "Do not rotate"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1570
|
||||
#: mod/photos.php:1556
|
||||
msgid "Rotate CW (right)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1571
|
||||
#: mod/photos.php:1557
|
||||
msgid "Rotate CCW (left)"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1586
|
||||
#: mod/photos.php:1572
|
||||
msgid "Private photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1587
|
||||
#: mod/photos.php:1573
|
||||
msgid "Public photo"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1609 include/conversation.php:1182
|
||||
#: mod/photos.php:1595 include/conversation.php:1182
|
||||
msgid "Share"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1648 include/conversation.php:509
|
||||
#: mod/photos.php:1634 include/conversation.php:509
|
||||
#: include/conversation.php:1413
|
||||
msgid "Attending"
|
||||
msgid_plural "Attending"
|
||||
msgstr[0] ""
|
||||
msgstr[1] ""
|
||||
|
||||
#: mod/photos.php:1648 include/conversation.php:509
|
||||
#: mod/photos.php:1634 include/conversation.php:509
|
||||
msgid "Not attending"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1648 include/conversation.php:509
|
||||
#: mod/photos.php:1634 include/conversation.php:509
|
||||
msgid "Might attend"
|
||||
msgstr ""
|
||||
|
||||
#: mod/photos.php:1813
|
||||
#: mod/photos.php:1799
|
||||
msgid "Map"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -6127,60 +6183,60 @@ msgstr ""
|
|||
msgid "Item was not found."
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:868
|
||||
#: boot.php:870
|
||||
msgid "Delete this item?"
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:871
|
||||
#: boot.php:873
|
||||
msgid "show fewer"
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1292
|
||||
#: boot.php:1382
|
||||
#, php-format
|
||||
msgid "Update %s failed. See error logs."
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1404
|
||||
#: boot.php:1494
|
||||
msgid "Create a New Account"
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1429 include/nav.php:72
|
||||
#: boot.php:1519 include/nav.php:72
|
||||
msgid "Logout"
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1432
|
||||
#: boot.php:1522
|
||||
msgid "Nickname or Email address: "
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1433
|
||||
#: boot.php:1523
|
||||
msgid "Password: "
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1434
|
||||
#: boot.php:1524
|
||||
msgid "Remember me"
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1437
|
||||
#: boot.php:1527
|
||||
msgid "Or login using OpenID: "
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1443
|
||||
#: boot.php:1533
|
||||
msgid "Forgot your password?"
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1446
|
||||
#: boot.php:1536
|
||||
msgid "Website Terms of Service"
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1447
|
||||
#: boot.php:1537
|
||||
msgid "terms of service"
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1449
|
||||
#: boot.php:1539
|
||||
msgid "Website Privacy Policy"
|
||||
msgstr ""
|
||||
|
||||
#: boot.php:1450
|
||||
#: boot.php:1540
|
||||
msgid "privacy policy"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -6224,6 +6280,16 @@ msgstr ""
|
|||
msgid "via"
|
||||
msgstr ""
|
||||
|
||||
#: include/dfrn.php:1092
|
||||
#, php-format
|
||||
msgid "%s\\'s birthday"
|
||||
msgstr ""
|
||||
|
||||
#: include/dfrn.php:1093 include/datetime.php:565
|
||||
#, php-format
|
||||
msgid "Happy Birthday %s"
|
||||
msgstr ""
|
||||
|
||||
#: include/dbstructure.php:26
|
||||
#, php-format
|
||||
msgid ""
|
||||
|
|
@ -6296,7 +6362,7 @@ msgid "Examples: Robert Morgenstein, Fishing"
|
|||
msgstr ""
|
||||
|
||||
#: include/contact_widgets.php:36 view/theme/diabook/theme.php:526
|
||||
#: view/theme/vier/theme.php:206
|
||||
#: view/theme/vier/theme.php:202
|
||||
msgid "Similar Interests"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -6305,7 +6371,7 @@ msgid "Random Profile"
|
|||
msgstr ""
|
||||
|
||||
#: include/contact_widgets.php:38 view/theme/diabook/theme.php:528
|
||||
#: view/theme/vier/theme.php:208
|
||||
#: view/theme/vier/theme.php:204
|
||||
msgid "Invite Friends"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -6527,58 +6593,58 @@ msgstr ""
|
|||
msgid "Show visitors public community forums at the Advanced Profile Page"
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:77
|
||||
#: include/follow.php:81
|
||||
msgid "Connect URL missing."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:104
|
||||
#: include/follow.php:108
|
||||
msgid ""
|
||||
"This site is not configured to allow communications with other networks."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:105 include/follow.php:125
|
||||
#: include/follow.php:109 include/follow.php:129
|
||||
msgid "No compatible communication protocols or feeds were discovered."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:123
|
||||
#: include/follow.php:127
|
||||
msgid "The profile address specified does not provide adequate information."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:127
|
||||
#: include/follow.php:131
|
||||
msgid "An author or name was not found."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:129
|
||||
#: include/follow.php:133
|
||||
msgid "No browser URL could be matched to this address."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:131
|
||||
#: include/follow.php:135
|
||||
msgid ""
|
||||
"Unable to match @-style Identity Address with a known protocol or email "
|
||||
"contact."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:132
|
||||
#: include/follow.php:136
|
||||
msgid "Use mailto: in front of address to force email check."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:138
|
||||
#: include/follow.php:142
|
||||
msgid ""
|
||||
"The profile address specified belongs to a network which has been disabled "
|
||||
"on this site."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:148
|
||||
#: include/follow.php:152
|
||||
msgid ""
|
||||
"Limited profile. This person will be unable to receive direct/personal "
|
||||
"notifications from you."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:249
|
||||
#: include/follow.php:253
|
||||
msgid "Unable to retrieve contact information."
|
||||
msgstr ""
|
||||
|
||||
#: include/follow.php:302
|
||||
#: include/follow.php:288
|
||||
msgid "following"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -6593,245 +6659,240 @@ msgstr ""
|
|||
msgid "Default privacy group for new contacts"
|
||||
msgstr ""
|
||||
|
||||
#: include/group.php:239
|
||||
#: include/group.php:242
|
||||
msgid "Everybody"
|
||||
msgstr ""
|
||||
|
||||
#: include/group.php:262
|
||||
#: include/group.php:265
|
||||
msgid "edit"
|
||||
msgstr ""
|
||||
|
||||
#: include/group.php:285
|
||||
#: include/group.php:288
|
||||
msgid "Edit groups"
|
||||
msgstr ""
|
||||
|
||||
#: include/group.php:287
|
||||
#: include/group.php:290
|
||||
msgid "Edit group"
|
||||
msgstr ""
|
||||
|
||||
#: include/group.php:288
|
||||
#: include/group.php:291
|
||||
msgid "Create a new group"
|
||||
msgstr ""
|
||||
|
||||
#: include/group.php:291
|
||||
#: include/group.php:294
|
||||
msgid "Contacts not in any group"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:43 include/datetime.php:45
|
||||
#: include/datetime.php:57 include/datetime.php:59
|
||||
msgid "Miscellaneous"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:141
|
||||
#: include/datetime.php:178
|
||||
msgid "YYYY-MM-DD or MM-DD"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:271
|
||||
#: include/datetime.php:327
|
||||
msgid "never"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:277
|
||||
#: include/datetime.php:333
|
||||
msgid "less than a second ago"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:287
|
||||
#: include/datetime.php:343
|
||||
msgid "year"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:287
|
||||
#: include/datetime.php:343
|
||||
msgid "years"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:288
|
||||
#: include/datetime.php:344
|
||||
msgid "months"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:289
|
||||
#: include/datetime.php:345
|
||||
msgid "weeks"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:290
|
||||
#: include/datetime.php:346
|
||||
msgid "days"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:291
|
||||
#: include/datetime.php:347
|
||||
msgid "hour"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:291
|
||||
#: include/datetime.php:347
|
||||
msgid "hours"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:292
|
||||
#: include/datetime.php:348
|
||||
msgid "minute"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:292
|
||||
#: include/datetime.php:348
|
||||
msgid "minutes"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:293
|
||||
#: include/datetime.php:349
|
||||
msgid "second"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:293
|
||||
#: include/datetime.php:349
|
||||
msgid "seconds"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:302
|
||||
#: include/datetime.php:358
|
||||
#, php-format
|
||||
msgid "%1$d %2$s ago"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:474 include/items.php:2500
|
||||
#: include/datetime.php:564
|
||||
#, php-format
|
||||
msgid "%s's birthday"
|
||||
msgstr ""
|
||||
|
||||
#: include/datetime.php:475 include/items.php:2501
|
||||
#, php-format
|
||||
msgid "Happy Birthday %s"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:42
|
||||
msgid "Requested account is not available."
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:95 include/identity.php:284 include/identity.php:662
|
||||
#: include/identity.php:95 include/identity.php:285 include/identity.php:663
|
||||
msgid "Edit profile"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:244
|
||||
#: include/identity.php:245
|
||||
msgid "Atom feed"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:249
|
||||
#: include/identity.php:250
|
||||
msgid "Message"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:255 include/nav.php:185
|
||||
#: include/identity.php:256 include/nav.php:185
|
||||
msgid "Profiles"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:255
|
||||
#: include/identity.php:256
|
||||
msgid "Manage/edit profiles"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:425 include/identity.php:509
|
||||
#: include/identity.php:426 include/identity.php:510
|
||||
msgid "g A l F d"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:426 include/identity.php:510
|
||||
#: include/identity.php:427 include/identity.php:511
|
||||
msgid "F d"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:471 include/identity.php:556
|
||||
#: include/identity.php:472 include/identity.php:557
|
||||
msgid "[today]"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:483
|
||||
#: include/identity.php:484
|
||||
msgid "Birthday Reminders"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:484
|
||||
#: include/identity.php:485
|
||||
msgid "Birthdays this week:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:543
|
||||
#: include/identity.php:544
|
||||
msgid "[No description]"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:567
|
||||
#: include/identity.php:568
|
||||
msgid "Event Reminders"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:568
|
||||
#: include/identity.php:569
|
||||
msgid "Events this week:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:595
|
||||
#: include/identity.php:596
|
||||
msgid "j F, Y"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:596
|
||||
#: include/identity.php:597
|
||||
msgid "j F"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:603
|
||||
#: include/identity.php:604
|
||||
msgid "Birthday:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:607
|
||||
#: include/identity.php:608
|
||||
msgid "Age:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:616
|
||||
#: include/identity.php:617
|
||||
#, php-format
|
||||
msgid "for %1$d %2$s"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:629
|
||||
#: include/identity.php:630
|
||||
msgid "Religion:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:633
|
||||
#: include/identity.php:634
|
||||
msgid "Hobbies/Interests:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:640
|
||||
#: include/identity.php:641
|
||||
msgid "Contact information and Social Networks:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:642
|
||||
#: include/identity.php:643
|
||||
msgid "Musical interests:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:644
|
||||
#: include/identity.php:645
|
||||
msgid "Books, literature:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:646
|
||||
#: include/identity.php:647
|
||||
msgid "Television:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:648
|
||||
#: include/identity.php:649
|
||||
msgid "Film/dance/culture/entertainment:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:650
|
||||
#: include/identity.php:651
|
||||
msgid "Love/Romance:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:652
|
||||
#: include/identity.php:653
|
||||
msgid "Work/employment:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:654
|
||||
#: include/identity.php:655
|
||||
msgid "School/education:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:658
|
||||
#: include/identity.php:659
|
||||
msgid "Forums:"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:710 include/identity.php:713 include/nav.php:78
|
||||
#: include/identity.php:711 include/identity.php:714 include/nav.php:78
|
||||
msgid "Videos"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:725 include/nav.php:140
|
||||
#: include/identity.php:726 include/nav.php:140
|
||||
msgid "Events and Calendar"
|
||||
msgstr ""
|
||||
|
||||
#: include/identity.php:733
|
||||
#: include/identity.php:734
|
||||
msgid "Only You Can See This"
|
||||
msgstr ""
|
||||
|
||||
#: include/like.php:167 include/conversation.php:122
|
||||
#: include/conversation.php:258 include/text.php:1998
|
||||
#: include/conversation.php:258 include/text.php:1921
|
||||
#: view/theme/diabook/theme.php:463
|
||||
msgid "event"
|
||||
msgstr ""
|
||||
|
||||
#: include/like.php:184 include/conversation.php:141 include/diaspora.php:2185
|
||||
#: include/like.php:184 include/conversation.php:141 include/diaspora.php:2133
|
||||
#: view/theme/diabook/theme.php:480
|
||||
#, php-format
|
||||
msgid "%1$s likes %2$s's %3$s"
|
||||
|
|
@ -6892,31 +6953,31 @@ msgstr ""
|
|||
msgid "stopped following"
|
||||
msgstr ""
|
||||
|
||||
#: include/Contact.php:337 include/conversation.php:911
|
||||
#: include/Contact.php:339 include/conversation.php:911
|
||||
msgid "View Status"
|
||||
msgstr ""
|
||||
|
||||
#: include/Contact.php:339 include/conversation.php:913
|
||||
#: include/Contact.php:341 include/conversation.php:913
|
||||
msgid "View Photos"
|
||||
msgstr ""
|
||||
|
||||
#: include/Contact.php:340 include/conversation.php:914
|
||||
#: include/Contact.php:342 include/conversation.php:914
|
||||
msgid "Network Posts"
|
||||
msgstr ""
|
||||
|
||||
#: include/Contact.php:341 include/conversation.php:915
|
||||
#: include/Contact.php:343 include/conversation.php:915
|
||||
msgid "Edit Contact"
|
||||
msgstr ""
|
||||
|
||||
#: include/Contact.php:342
|
||||
#: include/Contact.php:344
|
||||
msgid "Drop Contact"
|
||||
msgstr ""
|
||||
|
||||
#: include/Contact.php:343 include/conversation.php:916
|
||||
#: include/Contact.php:345 include/conversation.php:916
|
||||
msgid "Send PM"
|
||||
msgstr ""
|
||||
|
||||
#: include/Contact.php:344 include/conversation.php:920
|
||||
#: include/Contact.php:346 include/conversation.php:920
|
||||
msgid "Poke"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -7131,16 +7192,7 @@ msgid_plural "Undecided"
|
|||
msgstr[0] ""
|
||||
msgstr[1] ""
|
||||
|
||||
#: include/forums.php:105 include/text.php:1015 include/nav.php:126
|
||||
#: view/theme/vier/theme.php:259
|
||||
msgid "Forums"
|
||||
msgstr ""
|
||||
|
||||
#: include/forums.php:107 view/theme/vier/theme.php:261
|
||||
msgid "External link to forum"
|
||||
msgstr ""
|
||||
|
||||
#: include/network.php:967
|
||||
#: include/network.php:975
|
||||
msgid "view full size"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -7176,186 +7228,191 @@ msgstr ""
|
|||
msgid "The end"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:894
|
||||
#: include/text.php:865
|
||||
msgid "No contacts"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:909
|
||||
#: include/text.php:880
|
||||
#, php-format
|
||||
msgid "%d Contact"
|
||||
msgid_plural "%d Contacts"
|
||||
msgstr[0] ""
|
||||
msgstr[1] ""
|
||||
|
||||
#: include/text.php:921
|
||||
#: include/text.php:892
|
||||
msgid "View Contacts"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1010 include/nav.php:121
|
||||
#: include/text.php:981 include/nav.php:121
|
||||
msgid "Full Text"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1011 include/nav.php:122
|
||||
#: include/text.php:982 include/nav.php:122
|
||||
msgid "Tags"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1066
|
||||
#: include/text.php:986 include/ForumManager.php:112 include/nav.php:126
|
||||
#: view/theme/vier/theme.php:255
|
||||
msgid "Forums"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1037
|
||||
msgid "poke"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1066
|
||||
#: include/text.php:1037
|
||||
msgid "poked"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1067
|
||||
#: include/text.php:1038
|
||||
msgid "ping"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1067
|
||||
#: include/text.php:1038
|
||||
msgid "pinged"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1068
|
||||
#: include/text.php:1039
|
||||
msgid "prod"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1068
|
||||
#: include/text.php:1039
|
||||
msgid "prodded"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1069
|
||||
#: include/text.php:1040
|
||||
msgid "slap"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1069
|
||||
#: include/text.php:1040
|
||||
msgid "slapped"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1070
|
||||
#: include/text.php:1041
|
||||
msgid "finger"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1070
|
||||
#: include/text.php:1041
|
||||
msgid "fingered"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1071
|
||||
#: include/text.php:1042
|
||||
msgid "rebuff"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1071
|
||||
#: include/text.php:1042
|
||||
msgid "rebuffed"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1085
|
||||
#: include/text.php:1056
|
||||
msgid "happy"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1086
|
||||
#: include/text.php:1057
|
||||
msgid "sad"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1087
|
||||
#: include/text.php:1058
|
||||
msgid "mellow"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1088
|
||||
#: include/text.php:1059
|
||||
msgid "tired"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1089
|
||||
#: include/text.php:1060
|
||||
msgid "perky"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1090
|
||||
#: include/text.php:1061
|
||||
msgid "angry"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1091
|
||||
#: include/text.php:1062
|
||||
msgid "stupified"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1092
|
||||
#: include/text.php:1063
|
||||
msgid "puzzled"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1093
|
||||
#: include/text.php:1064
|
||||
msgid "interested"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1094
|
||||
#: include/text.php:1065
|
||||
msgid "bitter"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1095
|
||||
#: include/text.php:1066
|
||||
msgid "cheerful"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1096
|
||||
#: include/text.php:1067
|
||||
msgid "alive"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1097
|
||||
#: include/text.php:1068
|
||||
msgid "annoyed"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1098
|
||||
#: include/text.php:1069
|
||||
msgid "anxious"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1099
|
||||
#: include/text.php:1070
|
||||
msgid "cranky"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1100
|
||||
#: include/text.php:1071
|
||||
msgid "disturbed"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1101
|
||||
#: include/text.php:1072
|
||||
msgid "frustrated"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1102
|
||||
#: include/text.php:1073
|
||||
msgid "motivated"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1103
|
||||
#: include/text.php:1074
|
||||
msgid "relaxed"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1104
|
||||
#: include/text.php:1075
|
||||
msgid "surprised"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1504
|
||||
#: include/text.php:1475
|
||||
msgid "bytes"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1536 include/text.php:1548
|
||||
#: include/text.php:1507 include/text.php:1519
|
||||
msgid "Click to open/close"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1722
|
||||
#: include/text.php:1645
|
||||
msgid "View on separate page"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:1723
|
||||
#: include/text.php:1646
|
||||
msgid "view on separate page"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:2002
|
||||
#: include/text.php:1925
|
||||
msgid "activity"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:2005
|
||||
#: include/text.php:1928
|
||||
msgid "post"
|
||||
msgstr ""
|
||||
|
||||
#: include/text.php:2173
|
||||
#: include/text.php:2096
|
||||
msgid "Item filed"
|
||||
msgstr ""
|
||||
|
||||
#: include/bbcode.php:482 include/bbcode.php:1157 include/bbcode.php:1158
|
||||
#: include/bbcode.php:482 include/bbcode.php:1159 include/bbcode.php:1160
|
||||
msgid "Image/photo"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -7371,11 +7428,11 @@ msgid ""
|
|||
"\"%s\" target=\"_blank\">post</a>"
|
||||
msgstr ""
|
||||
|
||||
#: include/bbcode.php:1117 include/bbcode.php:1137
|
||||
#: include/bbcode.php:1119 include/bbcode.php:1139
|
||||
msgid "$1 wrote:"
|
||||
msgstr ""
|
||||
|
||||
#: include/bbcode.php:1166 include/bbcode.php:1167
|
||||
#: include/bbcode.php:1168 include/bbcode.php:1169
|
||||
msgid "Encrypted content"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -7469,10 +7526,10 @@ msgid "App.net"
|
|||
msgstr ""
|
||||
|
||||
#: include/contact_selectors.php:103
|
||||
msgid "Redmatrix"
|
||||
msgid "Hubzilla/Redmatrix"
|
||||
msgstr ""
|
||||
|
||||
#: include/Scrape.php:624
|
||||
#: include/Scrape.php:623
|
||||
msgid " on Last.fm"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -7496,6 +7553,10 @@ msgstr ""
|
|||
msgid "This action is not available under your subscription plan."
|
||||
msgstr ""
|
||||
|
||||
#: include/ForumManager.php:114 view/theme/vier/theme.php:257
|
||||
msgid "External link to forum"
|
||||
msgstr ""
|
||||
|
||||
#: include/nav.php:72
|
||||
msgid "End this session"
|
||||
msgstr ""
|
||||
|
|
@ -7648,17 +7709,17 @@ msgstr ""
|
|||
msgid "Site map"
|
||||
msgstr ""
|
||||
|
||||
#: include/api.php:878
|
||||
#: include/api.php:906
|
||||
#, php-format
|
||||
msgid "Daily posting limit of %d posts reached. The post was rejected."
|
||||
msgstr ""
|
||||
|
||||
#: include/api.php:897
|
||||
#: include/api.php:926
|
||||
#, php-format
|
||||
msgid "Weekly posting limit of %d posts reached. The post was rejected."
|
||||
msgstr ""
|
||||
|
||||
#: include/api.php:916
|
||||
#: include/api.php:947
|
||||
#, php-format
|
||||
msgid "Monthly posting limit of %d posts reached. The post was rejected."
|
||||
msgstr ""
|
||||
|
|
@ -7781,27 +7842,27 @@ msgid ""
|
|||
"\t\tThank you and welcome to %2$s."
|
||||
msgstr ""
|
||||
|
||||
#: include/diaspora.php:720
|
||||
#: include/diaspora.php:719
|
||||
msgid "Sharing notification from Diaspora network"
|
||||
msgstr ""
|
||||
|
||||
#: include/diaspora.php:2625
|
||||
#: include/diaspora.php:2570
|
||||
msgid "Attachments:"
|
||||
msgstr ""
|
||||
|
||||
#: include/delivery.php:533
|
||||
#: include/delivery.php:438
|
||||
msgid "(no subject)"
|
||||
msgstr ""
|
||||
|
||||
#: include/delivery.php:544 include/enotify.php:37
|
||||
#: include/delivery.php:449 include/enotify.php:37
|
||||
msgid "noreply"
|
||||
msgstr ""
|
||||
|
||||
#: include/items.php:4926
|
||||
#: include/items.php:1832
|
||||
msgid "Do you really want to delete this item?"
|
||||
msgstr ""
|
||||
|
||||
#: include/items.php:5201
|
||||
#: include/items.php:2107
|
||||
msgid "Archives"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -8361,7 +8422,7 @@ msgstr[1] ""
|
|||
msgid "Done. You can now login with your username and password"
|
||||
msgstr ""
|
||||
|
||||
#: index.php:442
|
||||
#: index.php:434
|
||||
msgid "toggle mobile"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -8443,7 +8504,7 @@ msgstr ""
|
|||
|
||||
#: view/theme/diabook/config.php:160 view/theme/diabook/theme.php:391
|
||||
#: view/theme/diabook/theme.php:626 view/theme/vier/config.php:112
|
||||
#: view/theme/vier/theme.php:156
|
||||
#: view/theme/vier/theme.php:152
|
||||
msgid "Community Profiles"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -8454,19 +8515,19 @@ msgstr ""
|
|||
|
||||
#: view/theme/diabook/config.php:162 view/theme/diabook/theme.php:606
|
||||
#: view/theme/diabook/theme.php:628 view/theme/vier/config.php:114
|
||||
#: view/theme/vier/theme.php:377
|
||||
#: view/theme/vier/theme.php:373
|
||||
msgid "Connect Services"
|
||||
msgstr ""
|
||||
|
||||
#: view/theme/diabook/config.php:163 view/theme/diabook/theme.php:523
|
||||
#: view/theme/diabook/theme.php:629 view/theme/vier/config.php:115
|
||||
#: view/theme/vier/theme.php:203
|
||||
#: view/theme/vier/theme.php:199
|
||||
msgid "Find Friends"
|
||||
msgstr ""
|
||||
|
||||
#: view/theme/diabook/config.php:164 view/theme/diabook/theme.php:412
|
||||
#: view/theme/diabook/theme.php:630 view/theme/vier/config.php:116
|
||||
#: view/theme/vier/theme.php:185
|
||||
#: view/theme/vier/theme.php:181
|
||||
msgid "Last users"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -8488,7 +8549,7 @@ msgstr ""
|
|||
msgid "Your personal photos"
|
||||
msgstr ""
|
||||
|
||||
#: view/theme/diabook/theme.php:524 view/theme/vier/theme.php:204
|
||||
#: view/theme/diabook/theme.php:524 view/theme/vier/theme.php:200
|
||||
msgid "Local Directory"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -8508,7 +8569,7 @@ msgstr ""
|
|||
msgid "Set style"
|
||||
msgstr ""
|
||||
|
||||
#: view/theme/vier/theme.php:295
|
||||
#: view/theme/vier/theme.php:291
|
||||
msgid "Quick Start"
|
||||
msgstr ""
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,32 @@
|
|||
/* General style rules .*/
|
||||
.pull-right { float: right }
|
||||
|
||||
/* General designing elements */
|
||||
.btn {
|
||||
outline: none;
|
||||
-moz-box-shadow: inset 0px 1px 0px 0px #ffffff;
|
||||
-webkit-box-shadow: inset 0px 1px 0px 0px #ffffff;
|
||||
box-shadow: inset 0px 1px 0px 0px #ffffff;
|
||||
background-color: #ededed;
|
||||
text-indent: 0;
|
||||
border: 1px solid #dcdcdc;
|
||||
display: inline-block;
|
||||
color: #777777;
|
||||
padding: 5px 10px;
|
||||
text-align: center;
|
||||
}
|
||||
a.btn, a.btn:hover {
|
||||
text-decoration: none;
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
.menu-popup .divider {
|
||||
height: 1px;
|
||||
margin: 3px 0;
|
||||
overflow: hidden;
|
||||
background-color: #2d2d2d;
|
||||
}
|
||||
|
||||
/* List of social Networks */
|
||||
img.connector, img.connector-disabled {
|
||||
height: 40px;
|
||||
|
|
@ -277,20 +303,20 @@ a {
|
|||
margin: 10px 0 10px;
|
||||
}
|
||||
.version-match {
|
||||
font-weight: bold;
|
||||
color: #00a700;
|
||||
font-weight: bold;
|
||||
color: #00a700;
|
||||
}
|
||||
.federation-graph {
|
||||
width: 400px;
|
||||
height: 400px;
|
||||
float: right;
|
||||
margin: 20px;
|
||||
width: 400px;
|
||||
height: 400px;
|
||||
float: right;
|
||||
margin: 20px;
|
||||
}
|
||||
.federation-network-graph {
|
||||
width: 240px;
|
||||
height: 240px;
|
||||
float: left;
|
||||
margin: 20px;
|
||||
width: 240px;
|
||||
height: 240px;
|
||||
float: left;
|
||||
margin: 20px;
|
||||
}
|
||||
ul.federation-stats,
|
||||
ul.credits {
|
||||
|
|
@ -302,10 +328,10 @@ ul.credits li {
|
|||
width: 240px;
|
||||
}
|
||||
table#federation-stats {
|
||||
width: 100%;
|
||||
width: 100%;
|
||||
}
|
||||
td.federation-data {
|
||||
border-bottom: 1px solid #000;
|
||||
border-bottom: 1px solid #000;
|
||||
}
|
||||
|
||||
.contact-entry-photo img {
|
||||
|
|
@ -329,25 +355,48 @@ td.federation-data {
|
|||
}
|
||||
|
||||
.crepair-label {
|
||||
margin-top: 10px;
|
||||
float: left;
|
||||
width: 250px;
|
||||
margin-top: 10px;
|
||||
float: left;
|
||||
width: 250px;
|
||||
}
|
||||
|
||||
.crepair-input {
|
||||
margin-top: 10px;
|
||||
float: left;
|
||||
width: 200px;
|
||||
margin-top: 10px;
|
||||
float: left;
|
||||
width: 200px;
|
||||
}
|
||||
|
||||
.renderinfo {
|
||||
clear: both;
|
||||
clear: both;
|
||||
}
|
||||
|
||||
.p-addr {
|
||||
clear: both;
|
||||
clear: both;
|
||||
}
|
||||
|
||||
#live-community {
|
||||
clear: both;
|
||||
clear: both;
|
||||
}
|
||||
|
||||
/* contact-edit */
|
||||
#contact-edit-status-wrapper {
|
||||
border: 1px solid;
|
||||
padding: 10px;
|
||||
}
|
||||
#contact-edit-actions {
|
||||
float: right;
|
||||
display: inline-block;
|
||||
position: relative;
|
||||
}
|
||||
#contact-edit-actions > .menu-popup {
|
||||
right: 0;
|
||||
left: auto;
|
||||
}
|
||||
|
||||
#contact-edit-settings-label:after {
|
||||
content: ' »';
|
||||
}
|
||||
|
||||
#contact-edit-settings {
|
||||
display: none;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ msgstr ""
|
|||
"Project-Id-Version: friendica\n"
|
||||
"Report-Msgid-Bugs-To: \n"
|
||||
"POT-Creation-Date: 2016-01-24 06:49+0100\n"
|
||||
"PO-Revision-Date: 2016-01-30 08:43+0000\n"
|
||||
"PO-Revision-Date: 2016-02-16 10:29+0000\n"
|
||||
"Last-Translator: Sandro Santilli <strk@keybit.net>\n"
|
||||
"Language-Team: Italian (http://www.transifex.com/Friendica/friendica/language/it/)\n"
|
||||
"MIME-Version: 1.0\n"
|
||||
|
|
@ -41,8 +41,8 @@ msgstr "Forum"
|
|||
#, php-format
|
||||
msgid "%d contact edited."
|
||||
msgid_plural "%d contacts edited."
|
||||
msgstr[0] ""
|
||||
msgstr[1] ""
|
||||
msgstr[0] "%d contatto modificato."
|
||||
msgstr[1] "%d contatti modificati"
|
||||
|
||||
#: mod/contacts.php:159 mod/contacts.php:383
|
||||
msgid "Could not access contact record."
|
||||
|
|
@ -887,7 +887,7 @@ msgstr "Rimuovi"
|
|||
|
||||
#: mod/ostatus_subscribe.php:14
|
||||
msgid "Subscribing to OStatus contacts"
|
||||
msgstr ""
|
||||
msgstr "Iscrizione a contatti OStatus"
|
||||
|
||||
#: mod/ostatus_subscribe.php:25
|
||||
msgid "No contact provided."
|
||||
|
|
@ -1943,7 +1943,7 @@ msgstr "Ispeziona Coda di invio"
|
|||
|
||||
#: mod/admin.php:163 mod/admin.php:354
|
||||
msgid "Federation Statistics"
|
||||
msgstr ""
|
||||
msgstr "Statistiche sulla Federazione"
|
||||
|
||||
#: mod/admin.php:177 mod/admin.php:188 mod/admin.php:1792
|
||||
msgid "Logs"
|
||||
|
|
@ -1951,7 +1951,7 @@ msgstr "Log"
|
|||
|
||||
#: mod/admin.php:178 mod/admin.php:1859
|
||||
msgid "View Logs"
|
||||
msgstr ""
|
||||
msgstr "Vedi i log"
|
||||
|
||||
#: mod/admin.php:179
|
||||
msgid "probe address"
|
||||
|
|
@ -1982,7 +1982,7 @@ msgid ""
|
|||
"This page offers you some numbers to the known part of the federated social "
|
||||
"network your Friendica node is part of. These numbers are not complete but "
|
||||
"only reflect the part of the network your node is aware of."
|
||||
msgstr ""
|
||||
msgstr "Questa pagina offre alcuni numeri riguardo la porzione del social network federato di cui il tuo nodo Friendica fa parte. Questi numeri non sono completi ma riflettono esclusivamente la porzione di rete di cui il tuo nodo e' a conoscenza."
|
||||
|
||||
#: mod/admin.php:348
|
||||
msgid ""
|
||||
|
|
|
|||
|
|
@ -8,8 +8,8 @@ function string_plural_select_it($n){
|
|||
$a->strings["Network:"] = "Rete:";
|
||||
$a->strings["Forum"] = "Forum";
|
||||
$a->strings["%d contact edited."] = array(
|
||||
0 => "",
|
||||
1 => "",
|
||||
0 => "%d contatto modificato.",
|
||||
1 => "%d contatti modificati",
|
||||
);
|
||||
$a->strings["Could not access contact record."] = "Non è possibile accedere al contatto.";
|
||||
$a->strings["Could not locate selected profile."] = "Non riesco a trovare il profilo selezionato.";
|
||||
|
|
@ -186,7 +186,7 @@ $a->strings["Tag removed"] = "Tag rimosso";
|
|||
$a->strings["Remove Item Tag"] = "Rimuovi il tag";
|
||||
$a->strings["Select a tag to remove: "] = "Seleziona un tag da rimuovere: ";
|
||||
$a->strings["Remove"] = "Rimuovi";
|
||||
$a->strings["Subscribing to OStatus contacts"] = "";
|
||||
$a->strings["Subscribing to OStatus contacts"] = "Iscrizione a contatti OStatus";
|
||||
$a->strings["No contact provided."] = "Nessun contatto disponibile.";
|
||||
$a->strings["Couldn't fetch information for contact."] = "Non è stato possibile recuperare le informazioni del contatto.";
|
||||
$a->strings["Couldn't fetch friends for contact."] = "Non è stato possibile recuperare gli amici del contatto.";
|
||||
|
|
@ -419,16 +419,16 @@ $a->strings["Themes"] = "Temi";
|
|||
$a->strings["Additional features"] = "Funzionalità aggiuntive";
|
||||
$a->strings["DB updates"] = "Aggiornamenti Database";
|
||||
$a->strings["Inspect Queue"] = "Ispeziona Coda di invio";
|
||||
$a->strings["Federation Statistics"] = "";
|
||||
$a->strings["Federation Statistics"] = "Statistiche sulla Federazione";
|
||||
$a->strings["Logs"] = "Log";
|
||||
$a->strings["View Logs"] = "";
|
||||
$a->strings["View Logs"] = "Vedi i log";
|
||||
$a->strings["probe address"] = "controlla indirizzo";
|
||||
$a->strings["check webfinger"] = "verifica webfinger";
|
||||
$a->strings["Admin"] = "Amministrazione";
|
||||
$a->strings["Plugin Features"] = "Impostazioni Plugins";
|
||||
$a->strings["diagnostics"] = "diagnostiche";
|
||||
$a->strings["User registrations waiting for confirmation"] = "Utenti registrati in attesa di conferma";
|
||||
$a->strings["This page offers you some numbers to the known part of the federated social network your Friendica node is part of. These numbers are not complete but only reflect the part of the network your node is aware of."] = "";
|
||||
$a->strings["This page offers you some numbers to the known part of the federated social network your Friendica node is part of. These numbers are not complete but only reflect the part of the network your node is aware of."] = "Questa pagina offre alcuni numeri riguardo la porzione del social network federato di cui il tuo nodo Friendica fa parte. Questi numeri non sono completi ma riflettono esclusivamente la porzione di rete di cui il tuo nodo e' a conoscenza.";
|
||||
$a->strings["The <em>Auto Discovered Contact Directory</em> feature is not enabled, it will improve the data displayed here."] = "";
|
||||
$a->strings["Administration"] = "Amministrazione";
|
||||
$a->strings["Currently this node is aware of %d nodes from the following platforms:"] = "";
|
||||
|
|
|
|||
|
|
@ -19,7 +19,7 @@
|
|||
<script>
|
||||
var FedData = [
|
||||
{{foreach $counts as $c}}
|
||||
{ value: {{$c[0]['total']}}, label: "{{$c[0]['platform']}}", color: "#90EE90", highlight: "#EE90A1", },
|
||||
{ value: {{$c[0]['total']}}, label: "{{$c[0]['platform']}}", color: '{{$c[3]}}', highlight: "#EE90A1", },
|
||||
{{/foreach}}
|
||||
];
|
||||
var ctx = document.getElementById("FederationChart").getContext("2d");
|
||||
|
|
@ -40,7 +40,7 @@ var myDoughnutChart = new Chart(ctx).Doughnut(FedData, { animateRotate : false,
|
|||
<script>
|
||||
var {{$c[2]}}data = [
|
||||
{{foreach $c[1] as $v}}
|
||||
{ value: {{$v['total']}}, label: '{{$v['version']}}', color: "#90EE90", highlight: "#EE90A1",},
|
||||
{ value: {{$v['total']}}, label: '{{$v['version']}}', color: "{{$c[3]}}", highlight: "#EE90A1",},
|
||||
{{/foreach}}
|
||||
];
|
||||
var ctx = document.getElementById("{{$c[2]}}Chart").getContext("2d");
|
||||
|
|
|
|||
|
|
@ -87,6 +87,7 @@
|
|||
{{if $thread_allow.2}}
|
||||
{{include file="field_checkbox.tpl" field=$ostatus_disabled}}
|
||||
{{include file="field_select.tpl" field=$ostatus_poll_interval}}
|
||||
{{include file="field_checkbox.tpl" field=$ostatus_full_threads}}
|
||||
{{else}}
|
||||
<div class='field checkbox' id='div_id_{{$ostatus_disabled.0}}'>
|
||||
<label for='id_{{$ostatus_disabled.0}}'>{{$ostatus_disabled.1}}</label>
|
||||
|
|
@ -153,6 +154,12 @@
|
|||
{{include file="field_checkbox.tpl" field=$old_pager}}
|
||||
<div class="submit"><input type="submit" name="page_site" value="{{$submit|escape:'html'}}" /></div>
|
||||
|
||||
<h3>{{$worker_title}}</h3>
|
||||
{{include file="field_checkbox.tpl" field=$worker}}
|
||||
{{include file="field_input.tpl" field=$worker_queues}}
|
||||
{{include file="field_checkbox.tpl" field=$worker_dont_fork}}
|
||||
<div class="submit"><input type="submit" name="page_site" value="{{$submit|escape:'html'}}" /></div>
|
||||
|
||||
</form>
|
||||
|
||||
{{* separate form for relocate... *}}
|
||||
|
|
|
|||
|
|
@ -1,104 +1,98 @@
|
|||
|
||||
{{if $header}}<h2>{{$header}}</h2>{{/if}}
|
||||
|
||||
<div id="contact-edit-wrapper" >
|
||||
|
||||
{{* Insert Tab-Nav *}}
|
||||
{{$tab_str}}
|
||||
|
||||
<div id="contact-edit-drop-link" >
|
||||
<a href="contacts/{{$contact_id}}/drop" class="icon drophide" id="contact-edit-drop-link" onclick="return confirmDelete();" title="{{$delete}}" onmouseover="imgbright(this);" onmouseout="imgdull(this);"></a>
|
||||
</div>
|
||||
|
||||
<div id="contact-edit-drop-link-end"></div>
|
||||
|
||||
|
||||
<div id="contact-edit-nav-wrapper" >
|
||||
<div id="contact-edit-links">
|
||||
<ul>
|
||||
{{if $relation_text}}
|
||||
<li><div id="contact-edit-rel">{{$relation_text}}</div></li>
|
||||
{{/if}}
|
||||
{{if $lost_contact}}
|
||||
<li><div id="lost-contact-message">{{$lost_contact}}</div></li>
|
||||
{{/if}}
|
||||
{{if $insecure}}
|
||||
<li><div id="insecure-message">{{$insecure}}</div></li>
|
||||
{{/if}}
|
||||
{{if $blocked}}
|
||||
<li><div id="block-message">{{$blocked}}</div></li>
|
||||
{{/if}}
|
||||
{{if $ignored}}
|
||||
<li><div id="ignore-message">{{$ignored}}</div></li>
|
||||
{{/if}}
|
||||
{{if $archived}}
|
||||
<li><div id="archive-message">{{$archived}}</div></li>
|
||||
{{/if}}
|
||||
</ul>
|
||||
<div id="contact-edit-status-wrapper">
|
||||
<span id="contact-edit-contact-status">{{$contact_status}}</span>
|
||||
|
||||
<ul>
|
||||
{{* This is the Action menu where contact related actions like 'ignore', 'hide' can be performed *}}
|
||||
<div id="contact-edit-actions">
|
||||
<a class="btn" rel="#contact-actions-menu" href="#" id="contact-edit-actions-button">{{$contact_action_button}}</a>
|
||||
|
||||
{{if $common_text}}
|
||||
<li><div id="contact-edit-common"><a href="{{$common_link}}">{{$common_text}}</a></div></li>
|
||||
{{/if}}
|
||||
{{if $all_friends}}
|
||||
<li><div id="contact-edit-allfriends"><a href="allfriends/{{$contact_id}}">{{$all_friends}}</a></div></li>
|
||||
{{/if}}
|
||||
<ul role="menu" aria-haspopup="true" id="contact-actions-menu" class="menu-popup" >
|
||||
{{if $lblsuggest}}<li role="menuitem"><a href="#" title="{{$contact_actions.suggest.title}}" onclick="window.location.href='{{$contact_actions.suggest.url}}'; return false;">{{$contact_actions.suggest.label}}</a></li>{{/if}}
|
||||
{{if $poll_enabled}}<li role="menuitem"><a href="#" title="{{$contact_actions.update.title}}" onclick="window.location.href='{{$contact_actions.update.url}}'; return false;">{{$contact_actions.update.label}}</a></li>{{/if}}
|
||||
<li class="divider"></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.block.title}}" onclick="window.location.href='{{$contact_actions.block.url}}'; return false;">{{$contact_actions.block.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.ignore.title}}" onclick="window.location.href='{{$contact_actions.ignore.url}}'; return false;">{{$contact_actions.ignore.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.archive.title}}" onclick="window.location.href='{{$contact_actions.archive.url}}'; return false;">{{$contact_actions.archive.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.delete.title}}" onclick="return confirmDelete();">{{$contact_actions.delete.label}}</a></li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
{{* Block with status information about the contact *}}
|
||||
<ul>
|
||||
{{if $relation_text}}<li><div id="contact-edit-rel">{{$relation_text}}</div></li>{{/if}}
|
||||
|
||||
<!-- <li><a href="network/0?nets=all&cid={{$contact_id}}" id="contact-edit-view-recent">{{$lblrecent}}</a></li> -->
|
||||
{{if $lblsuggest}}
|
||||
<li><a href="fsuggest/{{$contact_id}}" id="contact-edit-suggest">{{$lblsuggest}}</a></li>
|
||||
{{/if}}
|
||||
{{if $follow}}
|
||||
<li><div id="contact-edit-follow"><a href="{{$follow}}">{{$follow_text}}</a></div></li>
|
||||
{{/if}}
|
||||
{{if $poll_enabled}}
|
||||
<li><div id="contact-edit-last-update-text">{{$lastupdtext}} <span id="contact-edit-last-updated">{{$last_update}}</span></div>
|
||||
{{if $poll_interval}}
|
||||
<span id="contact-edit-poll-text">{{$updpub}}</span> {{$poll_interval}}
|
||||
{{/if}}
|
||||
</li>
|
||||
{{/if}}
|
||||
|
||||
</ul>
|
||||
{{if $lost_contact}}<li><div id="lost-contact-message">{{$lost_contact}}</div></li>{{/if}}
|
||||
{{if $insecure}}<li><div id="insecure-message">{{$insecure}}</div></li> {{/if}}
|
||||
{{if $blocked}}<li><div id="block-message">{{$blocked}}</div></li>{{/if}}
|
||||
{{if $ignored}}<li><div id="ignore-message">{{$ignored}}</div></li>{{/if}}
|
||||
{{if $archived}}<li><div id="archive-message">{{$archived}}</div></li>{{/if}}
|
||||
</ul>
|
||||
|
||||
<ul>
|
||||
<!-- <li><a href="network/0?nets=all&cid={{$contact_id}}" id="contact-edit-view-recent">{{$lblrecent}}</a></li> -->
|
||||
{{if $follow}}<li><div id="contact-edit-follow"><a href="{{$follow}}">{{$follow_text}}</a></div></li>{{/if}}
|
||||
</ul>
|
||||
</div> {{* End of contact-edit-status-wrapper *}}
|
||||
|
||||
{{* Some information about the contact from the profile *}}
|
||||
<dl><dt>{{$profileurllabel}}</dt><dd><a target="blank" href="{{$url}}">{{$profileurl}}</a></dd></dl>
|
||||
{{if $location}}<dl><dt>{{$location_label}}</dt><dd>{{$location}}</dd></dl>{{/if}}
|
||||
{{if $keywords}}<dl><dt>{{$keywords_label}}</dt><dd>{{$keywords}}</dd></dl>{{/if}}
|
||||
{{if $about}}<dl><dt>{{$about_label}}</dt><dd>{{$about}}</dd></dl>{{/if}}
|
||||
</div>
|
||||
</div>
|
||||
<div id="contact-edit-nav-end"></div>
|
||||
</div>{{* End of contact-edit-links *}}
|
||||
|
||||
<hr />
|
||||
<div id="contact-edit-links-end"></div>
|
||||
|
||||
<form action="contacts/{{$contact_id}}" method="post" >
|
||||
<input type="hidden" name="contact_id" value="{{$contact_id}}">
|
||||
<hr />
|
||||
|
||||
<div id="contact-edit-poll-wrapper">
|
||||
{{if $poll_enabled}}
|
||||
<div id="contact-edit-last-update-text">{{$lastupdtext}} <span id="contact-edit-last-updated">{{$last_update}}</span></div>
|
||||
{{if $poll_interval}}
|
||||
<span id="contact-edit-poll-text">{{$updpub}}</span> {{$poll_interval}}
|
||||
<h4 id="contact-edit-settings-label" class="fakelink" onclick="openClose('contact-edit-settings')">{{$contact_settings_label}}</h4>
|
||||
<div id="contact-edit-settings">
|
||||
<form action="contacts/{{$contact_id}}" method="post" >
|
||||
<input type="hidden" name="contact_id" value="{{$contact_id}}">
|
||||
|
||||
<div id="contact-edit-end" ></div>
|
||||
{{include file="field_checkbox.tpl" field=$notify}}
|
||||
{{if $fetch_further_information}}
|
||||
{{include file="field_select.tpl" field=$fetch_further_information}}
|
||||
{{if $fetch_further_information.2 == 2 }} {{include file="field_textarea.tpl" field=$ffi_keyword_blacklist}} {{/if}}
|
||||
{{/if}}
|
||||
{{include file="field_checkbox.tpl" field=$hidden}}
|
||||
|
||||
<div id="contact-edit-info-wrapper">
|
||||
<h4>{{$lbl_info1}}</h4>
|
||||
<textarea id="contact-edit-info" rows="8" cols="60" name="info">{{$info}}</textarea>
|
||||
<input class="contact-edit-submit" type="submit" name="submit" value="{{$submit|escape:'html'}}" />
|
||||
</div>
|
||||
<div id="contact-edit-info-end"></div>
|
||||
|
||||
{{if $profile_select}}
|
||||
<div id="contact-edit-profile-select-text">
|
||||
<h4>{{$lbl_vis1}}</h4>
|
||||
<p>{{$lbl_vis2}}</p>
|
||||
</div>
|
||||
{{$profile_select}}
|
||||
<div id="contact-edit-profile-select-end"></div>
|
||||
<input class="contact-edit-submit" type="submit" name="submit" value="{{$submit|escape:'html'}}" />
|
||||
{{/if}}
|
||||
<span id="contact-edit-update-now" class="button"><a href="contacts/{{$contact_id}}/update" >{{$udnow}}</a></span>
|
||||
{{/if}}
|
||||
</div>
|
||||
<div id="contact-edit-end" ></div>
|
||||
{{include file="field_checkbox.tpl" field=$notify}}
|
||||
{{if $fetch_further_information}}
|
||||
{{include file="field_select.tpl" field=$fetch_further_information}}
|
||||
{{if $fetch_further_information.2 == 2 }} {{include file="field_textarea.tpl" field=$ffi_keyword_blacklist}} {{/if}}
|
||||
{{/if}}
|
||||
{{include file="field_checkbox.tpl" field=$hidden}}
|
||||
|
||||
<div id="contact-edit-info-wrapper">
|
||||
<h4>{{$lbl_info1}}</h4>
|
||||
<textarea id="contact-edit-info" rows="8" cols="60" name="info">{{$info}}</textarea>
|
||||
<input class="contact-edit-submit" type="submit" name="submit" value="{{$submit|escape:'html'}}" />
|
||||
</div>
|
||||
<div id="contact-edit-info-end"></div>
|
||||
|
||||
{{if $profile_select}}
|
||||
<div id="contact-edit-profile-select-text">
|
||||
<h4>{{$lbl_vis1}}</h4>
|
||||
<p>{{$lbl_vis2}}</p>
|
||||
</div>
|
||||
{{$profile_select}}
|
||||
<div id="contact-edit-profile-select-end"></div>
|
||||
<input class="contact-edit-submit" type="submit" name="submit" value="{{$submit|escape:'html'}}" />
|
||||
{{/if}}
|
||||
</form>
|
||||
</form>
|
||||
</div>
|
||||
</div>{{* End of contact-edit-nav-wrapper *}}
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -18,13 +18,13 @@
|
|||
{{/if}}
|
||||
|
||||
{{if $request}}
|
||||
<form action="{{$request}}" method="post" />
|
||||
<form action="{{$request}}" method="post">
|
||||
{{else}}
|
||||
<form action="dfrn_request/{{$nickname}}" method="post" />
|
||||
<form action="dfrn_request/{{$nickname}}" method="post">
|
||||
{{/if}}
|
||||
|
||||
{{if $photo}}
|
||||
<img src="{{$photo}}" alt="" id="dfrn-request-photo">
|
||||
<img src="{{$photo}}" alt="" id="dfrn-request-photo" />
|
||||
{{/if}}
|
||||
|
||||
{{if $url}}<dl><dt>{{$url_label}}</dt><dd><a target="blank" href="{{$zrl}}">{{$url}}</a></dd></dl>{{/if}}
|
||||
|
|
|
|||
|
|
@ -1,9 +0,0 @@
|
|||
|
||||
<decrypted_hdeader>
|
||||
<iv>{{$inner_iv}}</iv>
|
||||
<aes_key>{{$inner_key}}</aes_key>
|
||||
<author>
|
||||
<name>{{$author_name}}</name>
|
||||
<uri>{{$author_uri}}</uri>
|
||||
</author>
|
||||
</decrypted_header>
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<comment>
|
||||
<guid>{{$guid}}</guid>
|
||||
<parent_guid>{{$parent_guid}}</parent_guid>
|
||||
<author_signature>{{$authorsig}}</author_signature>
|
||||
<text>{{$body}}</text>
|
||||
<diaspora_handle>{{$handle}}</diaspora_handle>
|
||||
</comment>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,13 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<comment>
|
||||
<guid>{{$guid}}</guid>
|
||||
<parent_guid>{{$parent_guid}}</parent_guid>
|
||||
<parent_author_signature>{{$parentsig}}</parent_author_signature>
|
||||
<author_signature>{{$authorsig}}</author_signature>
|
||||
<text>{{$body}}</text>
|
||||
<diaspora_handle>{{$handle}}</diaspora_handle>
|
||||
</comment>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,30 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<conversation>
|
||||
<guid>{{$conv.guid}}</guid>
|
||||
<subject>{{$conv.subject}}</subject>
|
||||
<created_at>{{$conv.created_at}}</created_at>
|
||||
|
||||
{{foreach $conv.messages as $msg}}
|
||||
|
||||
<message>
|
||||
<guid>{{$msg.guid}}</guid>
|
||||
<parent_guid>{{$msg.parent_guid}}</parent_guid>
|
||||
{{if $msg.parent_author_signature}}
|
||||
<parent_author_signature>{{$msg.parent_author_signature}}</parent_author_signature>
|
||||
{{/if}}
|
||||
<author_signature>{{$msg.author_signature}}</author_signature>
|
||||
<text>{{$msg.text}}</text>
|
||||
<created_at>{{$msg.created_at}}</created_at>
|
||||
<diaspora_handle>{{$msg.diaspora_handle}}</diaspora_handle>
|
||||
<conversation_guid>{{$msg.conversation_guid}}</conversation_guid>
|
||||
</message>
|
||||
|
||||
{{/foreach}}
|
||||
|
||||
<diaspora_handle>{{$conv.diaspora_handle}}</diaspora_handle>
|
||||
<participant_handles>{{$conv.participant_handles}}</participant_handles>
|
||||
</conversation>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,13 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<like>
|
||||
<positive>{{$positive}}</positive>
|
||||
<guid>{{$guid}}</guid>
|
||||
<target_type>{{$target_type}}</target_type>
|
||||
<parent_guid>{{$parent_guid}}</parent_guid>
|
||||
<author_signature>{{$authorsig}}</author_signature>
|
||||
<diaspora_handle>{{$handle}}</diaspora_handle>
|
||||
</like>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,14 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<like>
|
||||
<positive>{{$positive}}</positive>
|
||||
<guid>{{$guid}}</guid>
|
||||
<target_type>{{$target_type}}</target_type>
|
||||
<parent_guid>{{$parent_guid}}</parent_guid>
|
||||
<parent_author_signature>{{$parentsig}}</parent_author_signature>
|
||||
<author_signature>{{$authorsig}}</author_signature>
|
||||
<diaspora_handle>{{$handle}}</diaspora_handle>
|
||||
</like>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<message>
|
||||
<guid>{{$msg.guid}}</guid>
|
||||
<parent_guid>{{$msg.parent_guid}}</parent_guid>
|
||||
{{if $msg.parent_author_signature}}
|
||||
<parent_author_signature>{{$msg.parent_author_signature}}</parent_author_signature>
|
||||
{{/if}}
|
||||
<author_signature>{{$msg.author_signature}}</author_signature>
|
||||
<text>{{$msg.text}}</text>
|
||||
<created_at>{{$msg.created_at}}</created_at>
|
||||
<diaspora_handle>{{$msg.diaspora_handle}}</diaspora_handle>
|
||||
<conversation_guid>{{$msg.conversation_guid}}</conversation_guid>
|
||||
</message>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,14 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<photo>
|
||||
<guid>{{$guid}}</guid>
|
||||
<diaspora_handle>{{$handle}}</diaspora_handle>
|
||||
<public>{{$public}}</public>
|
||||
<created_at>{{$created_at}}</created_at>
|
||||
<remote_photo_path>{{$path}}</remote_photo_path>
|
||||
<remote_photo_name>{{$filename}}</remote_photo_name>
|
||||
<status_message_guid>{{$msg_guid}}</status_message_guid>
|
||||
</photo>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,13 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<status_message>
|
||||
<raw_message>{{$body}}</raw_message>
|
||||
<guid>{{$guid}}</guid>
|
||||
<diaspora_handle>{{$handle}}</diaspora_handle>
|
||||
<public>{{$public}}</public>
|
||||
<created_at>{{$created}}</created_at>
|
||||
<provider_display_name>{{$provider}}</provider_display_name>
|
||||
</status_message>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post><profile>
|
||||
<diaspora_handle>{{$handle}}</diaspora_handle>
|
||||
<first_name>{{$first}}</first_name>
|
||||
<last_name>{{$last}}</last_name>
|
||||
<image_url>{{$large}}</image_url>
|
||||
<image_url_medium>{{$medium}}</image_url_medium>
|
||||
<image_url_small>{{$small}}</image_url_small>
|
||||
<birthday>{{$dob}}</birthday>
|
||||
<gender>{{$gender}}</gender>
|
||||
<bio>{{$about}}</bio>
|
||||
<location>{{$location}}</location>
|
||||
<searchable>{{$searchable}}</searchable>
|
||||
<tag_string>{{$tags}}</tag_string>
|
||||
</profile></post>
|
||||
</XML>
|
||||
|
|
@ -1,11 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<relayable_retraction>
|
||||
<target_type>{{$type}}</target_type>
|
||||
<target_guid>{{$guid}}</target_guid>
|
||||
<target_author_signature>{{$signature}}</target_author_signature>
|
||||
<sender_handle>{{$handle}}</sender_handle>
|
||||
</relayable_retraction>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,12 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<relayable_retraction>
|
||||
<parent_author_signature>{{$parentsig}}</parent_author_signature>
|
||||
<target_guid>{{$guid}}</target_guid>
|
||||
<target_type>{{$target_type}}</target_type>
|
||||
<sender_handle>{{$handle}}</sender_handle>
|
||||
<target_author_signature>{{$authorsig}}</target_author_signature>
|
||||
</relayable_retraction>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,14 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<reshare>
|
||||
<root_diaspora_id>{{$root_handle}}</root_diaspora_id>
|
||||
<root_guid>{{$root_guid}}</root_guid>
|
||||
<guid>{{$guid}}</guid>
|
||||
<diaspora_handle>{{$handle}}</diaspora_handle>
|
||||
<public>{{$public}}</public>
|
||||
<created_at>{{$created}}</created_at>
|
||||
<provider_display_name>{{$provider}}</provider_display_name>
|
||||
</reshare>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,10 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<retraction>
|
||||
<post_guid>{{$guid}}</post_guid>
|
||||
<diaspora_handle>{{$handle}}</diaspora_handle>
|
||||
<type>{{$type}}</type>
|
||||
</retraction>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,9 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<request>
|
||||
<sender_handle>{{$sender}}</sender_handle>
|
||||
<recipient_handle>{{$recipient}}</recipient_handle>
|
||||
</request>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,11 +0,0 @@
|
|||
|
||||
<XML>
|
||||
<post>
|
||||
<signed_retraction>
|
||||
<target_guid>{{$guid}}</target_guid>
|
||||
<target_type>{{$type}}</target_type>
|
||||
<sender_handle>{{$handle}}</sender_handle>
|
||||
<target_author_signature>{{$signature}}</target_author_signature>
|
||||
</signed_retraction>
|
||||
</post>
|
||||
</XML>
|
||||
|
|
@ -1,5 +1,5 @@
|
|||
<div class='field checkbox' id='div_id_{{$field.0}}'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<input type="checkbox" name='{{$field.0}}' id='id_{{$field.0}}' value="1" {{if $field.2}}checked="checked"{{/if}}>
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<input type="checkbox" name='{{$field.0}}' id='id_{{$field.0}}' aria-describedby='{{$field.0}}_tip' value="1" {{if $field.2}}checked="checked"{{/if}}>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -7,12 +7,12 @@
|
|||
{{foreach $field.4 as $opt=>$val}}<option value="{{$val|escape:'html'}}">{{/foreach}}
|
||||
</datalist> *}}
|
||||
|
||||
<input id="id_{{$field.0}}" type="text" value="{{$field.2}}">
|
||||
<input id="id_{{$field.0}}" type="text" value="{{$field.2}}" aria-describedby='{{$field.0}}_tip'>
|
||||
<select id="select_{{$field.0}}" onChange="$('#id_{{$field.0}}').val($(this).val())">
|
||||
<option value="">{{$field.5}}</option>
|
||||
{{foreach $field.4 as $opt=>$val}}<option value="{{$val|escape:'html'}}">{{$val}}</option>{{/foreach}}
|
||||
</select>
|
||||
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
|
||||
<div class='field input' id='wrapper_{{$field.0}}'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<input{{if $field.6 eq 'email'}} type='email'{{elseif $field.6 eq 'url'}} type='url'{{/if}} name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.2|escape:'html'}}"{{if $field.4 eq 'required'}} required{{/if}}{{if $field.5 eq 'autofocus'}} autofocus{{/if}}>
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<input{{if $field.6 eq 'email'}} type='email'{{elseif $field.6 eq 'url'}} type='url'{{/if}} name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.2|escape:'html'}}"{{if $field.4 eq 'required'}} required{{/if}}{{if $field.5 eq 'autofocus'}} autofocus{{/if}} aria-describedby='{{$field.0}}_tip'>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -2,6 +2,6 @@
|
|||
|
||||
<div class='field checkbox'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<input type="checkbox" name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.3|escape:'html'}}" {{if $field.2}}checked="true"{{/if}}>
|
||||
<span class='field_help'>{{$field.4}}</span>
|
||||
<input type="checkbox" name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.3|escape:'html'}}" {{if $field.2}}checked="true"{{/if}} aria-describedby='{{$field.0}}_tip'>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.4}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
|
||||
<div class='field input openid' id='wrapper_{{$field.0}}'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<input name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.2|escape:'html'}}">
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<input name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.2|escape:'html'}}" aria-describedby='{{$field.0}}_tip'>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
|
||||
<div class='field password' id='wrapper_{{$field.0}}'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<input type='password' name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.2|escape:'html'}}"{{if $field.4 eq 'required'}} required{{/if}}{{if $field.5 eq 'autofocus'}} autofocus{{/if}}>
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<input type='password' name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.2|escape:'html'}}"{{if $field.4 eq 'required'}} required{{/if}}{{if $field.5 eq 'autofocus'}} autofocus{{/if}} aria-describedby='{{$field.0}}_tip'>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -2,6 +2,6 @@
|
|||
|
||||
<div class='field radio'>
|
||||
<label for='id_{{$field.0}}_{{$field.2}}'>{{$field.1}}</label>
|
||||
<input type="radio" name='{{$field.0}}' id='id_{{$field.0}}_{{$field.2}}' value="{{$field.2|escape:'html'}}" {{if $field.4}}checked="true"{{/if}}>
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<input type="radio" name='{{$field.0}}' id='id_{{$field.0}}_{{$field.2}}' value="{{$field.2|escape:'html'}}" {{if $field.4}}checked="true"{{/if}} aria-describedby={{$field.0}}_tip'>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -2,6 +2,6 @@
|
|||
|
||||
<div class='field richtext'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<textarea name='{{$field.0}}' id='id_{{$field.0}}' class="fieldRichtext">{{$field.2}}</textarea>
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<textarea name='{{$field.0}}' id='id_{{$field.0}}' class="fieldRichtext" aria-describedby='{{$field.0}}_tip'>{{$field.2}}</textarea>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -2,8 +2,8 @@
|
|||
|
||||
<div class='field select'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<select name='{{$field.0}}' id='id_{{$field.0}}'>
|
||||
<select name='{{$field.0}}' id='id_{{$field.0}}' aria-describedby='{{$field.0}}_tip'>
|
||||
{{foreach $field.4 as $opt=>$val}}<option value="{{$opt|escape:'html'}}" {{if $opt==$field.2}}selected="selected"{{/if}}>{{$val}}</option>{{/foreach}}
|
||||
</select>
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -2,8 +2,8 @@
|
|||
|
||||
<div class='field select'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<select name='{{$field.0}}' id='id_{{$field.0}}'>
|
||||
<select name='{{$field.0}}' id='id_{{$field.0}}' aria-describedby='{{$field.0}}_tip'>
|
||||
{{$field.4}}
|
||||
</select>
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -2,6 +2,6 @@
|
|||
|
||||
<div class='field textarea'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<textarea name='{{$field.0}}' id='id_{{$field.0}}'>{{$field.2}}</textarea>
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<textarea name='{{$field.0}}' id='id_{{$field.0}}' aria-describedby='{{$field.0}}_tip'>{{$field.2}}</textarea>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -2,9 +2,9 @@
|
|||
{{if $field.5}}<script>$(function(){ previewTheme($("#id_{{$field.0}}")[0]); });</script>{{/if}}
|
||||
<div class='field select'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<select name='{{$field.0}}' id='id_{{$field.0}}' {{if $field.5}}onchange="previewTheme(this);"{{/if}} >
|
||||
<select name='{{$field.0}}' id='id_{{$field.0}}' {{if $field.5}}onchange="previewTheme(this);"{{/if}} aria-describedby='{{$field.0}}_tip'>
|
||||
{{foreach $field.4 as $opt=>$val}}<option value="{{$opt|escape:'html'}}" {{if $opt==$field.2}}selected="selected"{{/if}}>{{$val}}</option>{{/foreach}}
|
||||
</select>
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
{{if $field.5}}<div id="theme-preview"></div>{{/if}}
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
<div class='field yesno'>
|
||||
<label for='id_{{$field.0}}'>{{$field.1}}</label>
|
||||
<div class='onoff' id="id_{{$field.0}}_onoff">
|
||||
<input type="hidden" name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.2|escape:'html'}}">
|
||||
<input type="hidden" name='{{$field.0}}' id='id_{{$field.0}}' value="{{$field.2|escape:'html'}}" aria-describedby='{{$field.0}}_tip'>
|
||||
<a href="#" class='off'>
|
||||
{{if $field.4}}{{$field.4.0}}{{else}}OFF{{/if}}
|
||||
</a>
|
||||
|
|
@ -10,5 +10,5 @@
|
|||
{{if $field.4}}{{$field.4.1}}{{else}}ON{{/if}}
|
||||
</a>
|
||||
</div>
|
||||
<span class='field_help'>{{$field.3}}</span>
|
||||
<span class='field_help' role='tooltip' id='{{$field.0}}_tip'>{{$field.3}}</span>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -2,17 +2,17 @@
|
|||
<meta http-equiv="Content-Type" content="text/html;charset=utf-8" />
|
||||
<base href="{{$baseurl}}/" />
|
||||
<meta name="generator" content="{{$generator}}" />
|
||||
<link rel="stylesheet" href="{{$baseurl}}/view/global.css" type="text/css" media="all" />
|
||||
<link rel="stylesheet" href="{{$baseurl}}/library/colorbox/colorbox.css" type="text/css" media="screen" />
|
||||
<link rel="stylesheet" href="{{$baseurl}}/library/jgrowl/jquery.jgrowl.css" type="text/css" media="screen" />
|
||||
<link rel="stylesheet" href="{{$baseurl}}/library/datetimepicker/jquery.datetimepicker.css" type="text/css" media="screen" />
|
||||
<link rel="stylesheet" href="{{$baseurl}}/library/perfect-scrollbar/perfect-scrollbar.min.css" type="text/css" media="screen" />
|
||||
<link rel="stylesheet" href="view/global.css" type="text/css" media="all" />
|
||||
<link rel="stylesheet" href="library/colorbox/colorbox.css" type="text/css" media="screen" />
|
||||
<link rel="stylesheet" href="library/jgrowl/jquery.jgrowl.css" type="text/css" media="screen" />
|
||||
<link rel="stylesheet" href="library/datetimepicker/jquery.datetimepicker.css" type="text/css" media="screen" />
|
||||
<link rel="stylesheet" href="library/perfect-scrollbar/perfect-scrollbar.min.css" type="text/css" media="screen" />
|
||||
|
||||
<link rel="stylesheet" type="text/css" href="{{$stylesheet}}" media="all" />
|
||||
|
||||
<!--
|
||||
<link rel="shortcut icon" href="{{$baseurl}}/images/friendica-32.png" />
|
||||
<link rel="apple-touch-icon" href="{{$baseurl}}/images/friendica-128.png"/>
|
||||
<link rel="shortcut icon" href="images/friendica-32.png" />
|
||||
<link rel="apple-touch-icon" href="images/friendica-128.png"/>
|
||||
-->
|
||||
<link rel="shortcut icon" href="{{$shortcut_icon}}" />
|
||||
<link rel="apple-touch-icon" href="{{$touch_icon}}"/>
|
||||
|
|
@ -28,20 +28,20 @@
|
|||
<!--[if IE]>
|
||||
<script type="text/javascript" src="https://html5shiv.googlecode.com/svn/trunk/html5.js"></script>
|
||||
<![endif]-->
|
||||
<script type="text/javascript" src="{{$baseurl}}/js/modernizr.js" ></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/js/jquery.js" ></script>
|
||||
<!-- <script type="text/javascript" src="{{$baseurl}}/js/jquery-migrate.js" ></script>-->
|
||||
<script type="text/javascript" src="{{$baseurl}}/js/jquery-migrate.js" ></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/js/jquery.textinputs.js" ></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/js/fk.autocomplete.js" ></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/library/colorbox/jquery.colorbox-min.js"></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/library/jgrowl/jquery.jgrowl_minimized.js"></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/library/datetimepicker/jquery.datetimepicker.js"></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/library/tinymce/jscripts/tiny_mce/tiny_mce_src.js" ></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/library/perfect-scrollbar/perfect-scrollbar.jquery.js" ></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/js/acl.js" ></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/js/webtoolkit.base64.js" ></script>
|
||||
<script type="text/javascript" src="{{$baseurl}}/js/main.js" ></script>
|
||||
<script type="text/javascript" src="js/modernizr.js" ></script>
|
||||
<script type="text/javascript" src="js/jquery.js" ></script>
|
||||
<!-- <script type="text/javascript" src="js/jquery-migrate.js" ></script>-->
|
||||
<script type="text/javascript" src="js/jquery-migrate.js" ></script>
|
||||
<script type="text/javascript" src="js/jquery.textinputs.js" ></script>
|
||||
<script type="text/javascript" src="js/fk.autocomplete.js" ></script>
|
||||
<script type="text/javascript" src="library/colorbox/jquery.colorbox-min.js"></script>
|
||||
<script type="text/javascript" src="library/jgrowl/jquery.jgrowl_minimized.js"></script>
|
||||
<script type="text/javascript" src="library/datetimepicker/jquery.datetimepicker.js"></script>
|
||||
<script type="text/javascript" src="library/tinymce/jscripts/tiny_mce/tiny_mce_src.js" ></script>
|
||||
<script type="text/javascript" src="library/perfect-scrollbar/perfect-scrollbar.jquery.js" ></script>
|
||||
<script type="text/javascript" src="js/acl.js" ></script>
|
||||
<script type="text/javascript" src="js/webtoolkit.base64.js" ></script>
|
||||
<script type="text/javascript" src="js/main.js" ></script>
|
||||
<script>
|
||||
|
||||
var updateInterval = {{$update_interval}};
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
|
||||
|
||||
<form action="{{$dest_url}}" method="post" >
|
||||
<fieldset>
|
||||
<input type="hidden" name="auth-params" value="login" />
|
||||
|
||||
<div id="login_standard">
|
||||
|
|
@ -29,7 +30,7 @@
|
|||
<input type="hidden" name="{{$k}}" value="{{$v|escape:'html'}}" />
|
||||
{{/foreach}}
|
||||
|
||||
|
||||
</fieldset>
|
||||
</form>
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -1,10 +1,10 @@
|
|||
|
||||
<h3>{{$title}}</h3>
|
||||
|
||||
|
||||
{{foreach $options as $o}}
|
||||
<dl>
|
||||
<dt><a href="{{$baseurl}}/{{$o.0}}">{{$o.1}}</a></dt>
|
||||
<dd>{{$o.2}}</dd>
|
||||
</dl>
|
||||
{{/foreach}}
|
||||
<h3>{{$title}}</h3>
|
||||
|
||||
|
||||
{{foreach $options as $o}}
|
||||
<dl>
|
||||
<dt><a href="{{$o.0}}">{{$o.1}}</a></dt>
|
||||
<dd>{{$o.2}}</dd>
|
||||
</dl>
|
||||
{{/foreach}}
|
||||
|
|
|
|||
|
|
@ -10,7 +10,6 @@
|
|||
*/
|
||||
|
||||
function decaf_mobile_init(&$a) {
|
||||
$a->theme_info = array();
|
||||
$a->sourcename = 'Friendica mobile web';
|
||||
$a->videowidth = 250;
|
||||
$a->videoheight = 200;
|
||||
|
|
|
|||
|
|
@ -83,6 +83,26 @@ blockquote {
|
|||
margin-right: 5px;
|
||||
}
|
||||
|
||||
ul.menu-popup {
|
||||
position: absolute;
|
||||
display: none;
|
||||
width: auto;
|
||||
margin: 2px 0 0;
|
||||
padding: 0px;
|
||||
list-style: none;
|
||||
z-index: 100000;
|
||||
border: 2px solid #444444;
|
||||
background: #FFFFFF;
|
||||
}
|
||||
.menu-popup li a {
|
||||
padding: 2px;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
a.btn, a.btn:hover {
|
||||
text-decoration: none;
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
|
||||
/* nav */
|
||||
|
|
@ -140,12 +160,12 @@ nav #banner #logo-text a:hover { text-decoration: none; }
|
|||
|
||||
|
||||
.nav-commlink, .nav-login-link {
|
||||
display: block;
|
||||
height: 15px;
|
||||
display: block;
|
||||
height: 15px;
|
||||
margin-top: 67px;
|
||||
margin-right: 2px;
|
||||
//padding: 6px 10px;
|
||||
padding: 6px 3px;
|
||||
/*padding: 6px 10px;*/
|
||||
padding: 6px 3px;
|
||||
float: left;
|
||||
bottom: 140px;
|
||||
border: 1px solid #babdb6;
|
||||
|
|
@ -244,7 +264,7 @@ section {
|
|||
display:block;
|
||||
float:left;
|
||||
padding: 0.4em;
|
||||
//margin-right: 1em;
|
||||
/*margin-right: 1em;*/
|
||||
margin-right: 3px ;
|
||||
}
|
||||
.tab.active {
|
||||
|
|
@ -3371,17 +3391,6 @@ div.jGrowl div.info {
|
|||
.nav-notify.show {
|
||||
display: block;
|
||||
}
|
||||
ul.menu-popup {
|
||||
position: absolute;
|
||||
display: none;
|
||||
width: 10em;
|
||||
margin: 0px;
|
||||
padding: 0px;
|
||||
list-style: none;
|
||||
z-index: 100000;
|
||||
top: 90px;
|
||||
left: 200px;
|
||||
}
|
||||
#nav-notifications-menu {
|
||||
width: 320px;
|
||||
max-height: 400px;
|
||||
|
|
@ -3391,6 +3400,8 @@ ul.menu-popup {
|
|||
-webkit-border-radius: 5px;
|
||||
border-radius:5px;
|
||||
border: 1px solid #888;
|
||||
top: 90px;
|
||||
left: 200px;
|
||||
}
|
||||
#nav-notifications-menu .contactname { font-weight: bold; font-size: 0.9em; }
|
||||
#nav-notifications-menu img { float: left; margin-right: 5px; }
|
||||
|
|
|
|||
|
|
@ -2,7 +2,6 @@
|
|||
|
||||
function duepuntozero_init(&$a) {
|
||||
|
||||
$a->theme_info = array();
|
||||
set_template_engine($a, 'smarty3');
|
||||
|
||||
$colorset = get_pconfig( local_user(), 'duepuntozero','colorset');
|
||||
|
|
|
|||
|
|
@ -1,7 +1,6 @@
|
|||
<?php
|
||||
|
||||
function facepark_init(&$a) {
|
||||
$a->theme_info = array();
|
||||
set_template_engine($a, 'smarty3');
|
||||
|
||||
$a->page['htmlhead'] .= <<< EOT
|
||||
|
|
|
|||
|
|
@ -13,7 +13,6 @@
|
|||
if($(listID).is(":visible")) {
|
||||
$(listID).hide();
|
||||
$(listID+"-wrapper").show();
|
||||
alert($(listID+"-wrapper").attr("id"));
|
||||
}
|
||||
else {
|
||||
$(listID).show();
|
||||
|
|
|
|||
|
|
@ -139,6 +139,47 @@ blockquote {
|
|||
margin-right: 5px;
|
||||
}
|
||||
|
||||
.btn {
|
||||
outline: none;
|
||||
-moz-box-shadow: inset 0px 1px 0px 0px #ffffff;
|
||||
-webkit-box-shadow: inset 0px 1px 0px 0px #ffffff;
|
||||
box-shadow: inset 0px 1px 0px 0px #ffffff;
|
||||
background-color: #ededed;
|
||||
text-indent: 0;
|
||||
border: 1px solid #dcdcdc;
|
||||
display: inline-block;
|
||||
color: #777777;
|
||||
padding: 5px 10px;
|
||||
text-align: center;
|
||||
border-radius: 8px;
|
||||
}
|
||||
|
||||
.menu-popup {
|
||||
width: auto;
|
||||
border: 2px solid #444444;
|
||||
background: #FFFFFF;
|
||||
position: absolute;
|
||||
margin: 2px 0 0;
|
||||
display: none;
|
||||
z-index: 10000;
|
||||
}
|
||||
|
||||
.menu-popup li a {
|
||||
display: block;
|
||||
padding: 2px;
|
||||
}
|
||||
|
||||
.menu-popup li a:hover {
|
||||
color: #FFFFFF;
|
||||
background: #3465A4;
|
||||
text-decoration: none;
|
||||
}
|
||||
ul.menu-popup li.divider {
|
||||
height: 1px;
|
||||
margin: 3px 0;
|
||||
overflow: hidden;
|
||||
background-color: #2d2d2d;
|
||||
}
|
||||
|
||||
|
||||
/* nav */
|
||||
|
|
@ -2045,6 +2086,19 @@ input#profile-jot-email {
|
|||
margin-left: 15px;
|
||||
}
|
||||
|
||||
#contact-edit-status-wrapper {
|
||||
padding: 10px;
|
||||
border: 1px solid #aaa;
|
||||
border-radius: 8px;
|
||||
}
|
||||
|
||||
#contact-edit-contact-status {
|
||||
font-weight: bold;
|
||||
}
|
||||
#contact-edit-actions {
|
||||
float: right;
|
||||
display: inline-block;
|
||||
}
|
||||
#contact-edit-wrapper {
|
||||
margin-top: 10px;
|
||||
}
|
||||
|
|
@ -2059,14 +2113,10 @@ input#profile-jot-email {
|
|||
}
|
||||
|
||||
#contact-edit-last-update-text {
|
||||
float: left;
|
||||
clear: left;
|
||||
margin-top: 30px;
|
||||
}
|
||||
|
||||
#contact-edit-poll-text {
|
||||
float: left;
|
||||
clear: left;
|
||||
margin-top: 15px;
|
||||
margin-bottom: 0px;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -6,12 +6,6 @@
|
|||
|
||||
{{$tab_str}}
|
||||
|
||||
<div id="contact-edit-drop-link" >
|
||||
<a href="contacts/{{$contact_id}}/drop" class="icon drophide" id="contact-edit-drop-link" onclick="return confirmDelete();" title="{{$delete}}" {{*onmouseover="imgbright(this);" onmouseout="imgdull(this);"*}}></a>
|
||||
</div>
|
||||
|
||||
<div id="contact-edit-drop-link-end"></div>
|
||||
|
||||
<div class="vcard">
|
||||
<div class="fn">{{$name}}</div>
|
||||
<div id="profile-photo-wrapper"><img class="photo" style="width: 175px; height: 175px;" src="{{$photo}}" alt="{{$name}}" /></div>
|
||||
|
|
@ -20,41 +14,49 @@
|
|||
|
||||
<div id="contact-edit-nav-wrapper" >
|
||||
<div id="contact-edit-links">
|
||||
<ul>
|
||||
<li><div id="contact-edit-rel">{{$relation_text}}</div></li>
|
||||
<li><div id="contact-edit-nettype">{{$nettype}}</div></li>
|
||||
{{if $lost_contact}}
|
||||
<li><div id="lost-contact-message">{{$lost_contact}}</div></li>
|
||||
{{/if}}
|
||||
{{if $insecure}}
|
||||
<li><div id="insecure-message">{{$insecure}}</div></li>
|
||||
{{/if}}
|
||||
{{if $blocked}}
|
||||
<li><div id="block-message">{{$blocked}}</div></li>
|
||||
{{/if}}
|
||||
{{if $ignored}}
|
||||
<li><div id="ignore-message">{{$ignored}}</div></li>
|
||||
{{/if}}
|
||||
{{if $archived}}
|
||||
<li><div id="archive-message">{{$archived}}</div></li>
|
||||
{{/if}}
|
||||
<div id="contact-edit-status-wrapper">
|
||||
<span id="contact-edit-contact-status">{{$contact_status}}</span>
|
||||
|
||||
<li> </li>
|
||||
<div id="contact-edit-actions">
|
||||
<div class="btn" id="contact-edit-actions-button" onclick="openClose('contact-actions-menu')">{{$contact_action_button}}</div>
|
||||
|
||||
{{if $common_text}}
|
||||
<li><div id="contact-edit-common"><a href="{{$common_link}}">{{$common_text}}</a></div></li>
|
||||
{{/if}}
|
||||
{{if $all_friends}}
|
||||
<li><div id="contact-edit-allfriends"><a href="allfriends/{{$contact_id}}">{{$all_friends}}</a></div></li>
|
||||
{{/if}}
|
||||
<ul role="menu" aria-haspopup="true" id="contact-actions-menu" class="menu-popup" >
|
||||
{{if $lblsuggest}}<li role="menuitem"><a href="#" title="{{$contact_actions.suggest.title}}" onclick="window.location.href='{{$contact_actions.suggest.url}}'; return false;">{{$contact_actions.suggest.label}}</a></li>{{/if}}
|
||||
{{if $poll_enabled}}<li role="menuitem"><a href="#" title="{{$contact_actions.update.title}}" onclick="window.location.href='{{$contact_actions.update.url}}'; return false;">{{$contact_actions.update.label}}</a></li>{{/if}}
|
||||
<li class="divider"></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.block.title}}" onclick="window.location.href='{{$contact_actions.block.url}}'; return false;">{{$contact_actions.block.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.ignore.title}}" onclick="window.location.href='{{$contact_actions.ignore.url}}'; return false;">{{$contact_actions.ignore.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.archive.title}}" onclick="window.location.href='{{$contact_actions.archive.url}}'; return false;">{{$contact_actions.archive.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.delete.title}}" onclick="return confirmDelete();">{{$contact_actions.delete.label}}</a></li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<ul>
|
||||
<li><div id="contact-edit-rel">{{$relation_text}}</div></li>
|
||||
<li><div id="contact-edit-nettype">{{$nettype}}</div></li>
|
||||
{{if $poll_enabled}}
|
||||
<div id="contact-edit-poll-wrapper">
|
||||
<div id="contact-edit-last-update-text">{{$lastupdtext}} <span id="contact-edit-last-updated">{{$last_update}}</span></div>
|
||||
</div>
|
||||
{{/if}}
|
||||
{{if $lost_contact}}
|
||||
<li><div id="lost-contact-message">{{$lost_contact}}</div></li>
|
||||
{{/if}}
|
||||
{{if $insecure}}
|
||||
<li><div id="insecure-message">{{$insecure}}</div></li>
|
||||
{{/if}}
|
||||
{{if $blocked}}
|
||||
<li><div id="block-message">{{$blocked}}</div></li>
|
||||
{{/if}}
|
||||
{{if $ignored}}
|
||||
<li><div id="ignore-message">{{$ignored}}</div></li>
|
||||
{{/if}}
|
||||
{{if $archived}}
|
||||
<li><div id="archive-message">{{$archived}}</div></li>
|
||||
{{/if}}
|
||||
|
||||
<li><a href="network/0?nets=all&cid={{$contact_id}}" id="contact-edit-view-recent">{{$lblrecent}}</a></li>
|
||||
{{if $lblsuggest}}
|
||||
<li><a href="fsuggest/{{$contact_id}}" id="contact-edit-suggest">{{$lblsuggest}}</a></li>
|
||||
{{/if}}
|
||||
|
||||
</ul>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div id="contact-edit-nav-end"></div>
|
||||
|
|
@ -63,12 +65,6 @@
|
|||
<form action="contacts/{{$contact_id}}" method="post" >
|
||||
<input type="hidden" name="contact_id" value="{{$contact_id}}">
|
||||
|
||||
{{if $poll_enabled}}
|
||||
<div id="contact-edit-poll-wrapper">
|
||||
<div id="contact-edit-last-update-text">{{$lastupdtext}} <span id="contact-edit-last-updated">{{$last_update}}</span></div>
|
||||
<span id="contact-edit-poll-text">{{$updpub}} {{$poll_interval}}</span> <span id="contact-edit-update-now" class="button"><a id="update_now_link" href="contacts/{{$contact_id}}/update" >{{$udnow}}</a></span>
|
||||
</div>
|
||||
{{/if}}
|
||||
<div id="contact-edit-end" ></div>
|
||||
|
||||
{{include file="field_checkbox.tpl" field=$hidden}}
|
||||
|
|
|
|||
|
|
@ -10,7 +10,6 @@
|
|||
*/
|
||||
|
||||
function frost_mobile_init(&$a) {
|
||||
$a->theme_info = array();
|
||||
$a->sourcename = 'Friendica mobile web';
|
||||
$a->videowidth = 250;
|
||||
$a->videoheight = 200;
|
||||
|
|
|
|||
|
|
@ -113,6 +113,51 @@ blockquote {
|
|||
|
||||
.pull-right { float: right }
|
||||
|
||||
.btn {
|
||||
outline: none;
|
||||
-moz-box-shadow: inset 0px 1px 0px 0px #ffffff;
|
||||
-webkit-box-shadow: inset 0px 1px 0px 0px #ffffff;
|
||||
box-shadow: inset 0px 1px 0px 0px #ffffff;
|
||||
background-color: #ededed;
|
||||
text-indent: 0;
|
||||
border: 1px solid #dcdcdc;
|
||||
display: inline-block;
|
||||
color: #777777;
|
||||
padding: 5px 10px;
|
||||
text-align: center;
|
||||
border-radius: 8px;
|
||||
}
|
||||
a.btn {
|
||||
text-decoration: none;
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
.menu-popup {
|
||||
width: auto;
|
||||
border: 2px solid #444444;
|
||||
background: #FFFFFF;
|
||||
position: absolute;
|
||||
margin: 2px 0 0;
|
||||
display: none;
|
||||
z-index: 10000;
|
||||
}
|
||||
|
||||
.menu-popup li a {
|
||||
display: block;
|
||||
padding: 2px;
|
||||
}
|
||||
|
||||
.menu-popup li a:hover {
|
||||
color: #FFFFFF;
|
||||
background: #3465A4;
|
||||
text-decoration: none;
|
||||
}
|
||||
ul.menu-popup li.divider {
|
||||
height: 1px;
|
||||
margin: 3px 0;
|
||||
overflow: hidden;
|
||||
background-color: #2d2d2d;
|
||||
}
|
||||
|
||||
|
||||
/* nav */
|
||||
|
|
@ -1952,6 +1997,20 @@ input#dfrn-url {
|
|||
margin-left: 15px;
|
||||
}
|
||||
|
||||
#contact-edit-status-wrapper {
|
||||
padding: 10px;
|
||||
border: 1px solid #aaa;
|
||||
border-radius: 8px;
|
||||
}
|
||||
|
||||
#contact-edit-contact-status {
|
||||
font-weight: bold;
|
||||
}
|
||||
#contact-edit-actions {
|
||||
float: right;
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
#contact-edit-wrapper {
|
||||
margin-top: 10px;
|
||||
}
|
||||
|
|
@ -1989,11 +2048,6 @@ input#dfrn-url {
|
|||
margin-top: 5px;
|
||||
}
|
||||
|
||||
#contact-edit-drop-link {
|
||||
float: right;
|
||||
margin-right: 20px;
|
||||
}
|
||||
|
||||
#contact-edit-nav-end {
|
||||
clear: both;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -6,50 +6,51 @@
|
|||
|
||||
{{$tab_str}}
|
||||
|
||||
<div id="contact-edit-drop-link" >
|
||||
<a href="contacts/{{$contact_id}}/drop" class="icon drophide" id="contact-edit-drop-link" onclick="return confirmDelete();" title="{{$delete}}" {{*onmouseover="imgbright(this);" onmouseout="imgdull(this);"*}}></a>
|
||||
</div>
|
||||
|
||||
<div id="contact-edit-drop-link-end"></div>
|
||||
|
||||
|
||||
<div id="contact-edit-nav-wrapper" >
|
||||
<div id="contact-edit-links">
|
||||
<ul>
|
||||
<li><div id="contact-edit-rel">{{$relation_text}}</div></li>
|
||||
<li><div id="contact-edit-nettype">{{$nettype}}</div></li>
|
||||
{{if $lost_contact}}
|
||||
<li><div id="lost-contact-message">{{$lost_contact}}</div></li>
|
||||
{{/if}}
|
||||
{{if $insecure}}
|
||||
<li><div id="insecure-message">{{$insecure}}</div></li>
|
||||
{{/if}}
|
||||
{{if $blocked}}
|
||||
<li><div id="block-message">{{$blocked}}</div></li>
|
||||
{{/if}}
|
||||
{{if $ignored}}
|
||||
<li><div id="ignore-message">{{$ignored}}</div></li>
|
||||
{{/if}}
|
||||
{{if $archived}}
|
||||
<li><div id="archive-message">{{$archived}}</div></li>
|
||||
{{/if}}
|
||||
<div id="contact-edit-status-wrapper">
|
||||
<span id="contact-edit-contact-status">{{$contact_status}}</span>
|
||||
|
||||
<li> </li>
|
||||
<div id="contact-edit-actions">
|
||||
<a class="btn" rel="#contact-actions-menu" href="#" id="contact-edit-actions-button">{{$contact_action_button}}</a>
|
||||
|
||||
{{if $common_text}}
|
||||
<li><div id="contact-edit-common"><a href="{{$common_link}}">{{$common_text}}</a></div></li>
|
||||
{{/if}}
|
||||
{{if $all_friends}}
|
||||
<li><div id="contact-edit-allfriends"><a href="allfriends/{{$contact_id}}">{{$all_friends}}</a></div></li>
|
||||
{{/if}}
|
||||
<ul role="menu" aria-haspopup="true" id="contact-actions-menu" class="menu-popup" >
|
||||
{{if $lblsuggest}}<li role="menuitem"><a href="#" title="{{$contact_actions.suggest.title}}" onclick="window.location.href='{{$contact_actions.suggest.url}}'; return false;">{{$contact_actions.suggest.label}}</a></li>{{/if}}
|
||||
{{if $poll_enabled}}<li role="menuitem"><a href="#" title="{{$contact_actions.update.title}}" onclick="window.location.href='{{$contact_actions.update.url}}'; return false;">{{$contact_actions.update.label}}</a></li>{{/if}}
|
||||
<li class="divider"></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.block.title}}" onclick="window.location.href='{{$contact_actions.block.url}}'; return false;">{{$contact_actions.block.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.ignore.title}}" onclick="window.location.href='{{$contact_actions.ignore.url}}'; return false;">{{$contact_actions.ignore.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.archive.title}}" onclick="window.location.href='{{$contact_actions.archive.url}}'; return false;">{{$contact_actions.archive.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.delete.title}}" onclick="return confirmDelete();">{{$contact_actions.delete.label}}</a></li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<ul>
|
||||
<li><div id="contact-edit-rel">{{$relation_text}}</div></li>
|
||||
<li><div id="contact-edit-nettype">{{$nettype}}</div></li>
|
||||
{{if $poll_enabled}}
|
||||
<div id="contact-edit-poll-wrapper">
|
||||
<div id="contact-edit-last-update-text">{{$lastupdtext}} <span id="contact-edit-last-updated">{{$last_update}}</span></div>
|
||||
</div>
|
||||
{{/if}}
|
||||
{{if $lost_contact}}
|
||||
<li><div id="lost-contact-message">{{$lost_contact}}</div></li>
|
||||
{{/if}}
|
||||
{{if $insecure}}
|
||||
<li><div id="insecure-message">{{$insecure}}</div></li>
|
||||
{{/if}}
|
||||
{{if $blocked}}
|
||||
<li><div id="block-message">{{$blocked}}</div></li>
|
||||
{{/if}}
|
||||
{{if $ignored}}
|
||||
<li><div id="ignore-message">{{$ignored}}</div></li>
|
||||
{{/if}}
|
||||
{{if $archived}}
|
||||
<li><div id="archive-message">{{$archived}}</div></li>
|
||||
{{/if}}
|
||||
|
||||
<li><a href="network/?cid={{$contact_id}}" id="contact-edit-view-recent">{{$lblrecent}}</a></li>
|
||||
{{if $lblsuggest}}
|
||||
<li><a href="fsuggest/{{$contact_id}}" id="contact-edit-suggest">{{$lblsuggest}}</a></li>
|
||||
{{/if}}
|
||||
|
||||
</ul>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div id="contact-edit-nav-end"></div>
|
||||
|
|
@ -58,12 +59,6 @@
|
|||
<form action="contacts/{{$contact_id}}" method="post" >
|
||||
<input type="hidden" name="contact_id" value="{{$contact_id}}">
|
||||
|
||||
{{if $poll_enabled}}
|
||||
<div id="contact-edit-poll-wrapper">
|
||||
<div id="contact-edit-last-update-text">{{$lastupdtext}} <span id="contact-edit-last-updated">{{$last_update}}</span></div>
|
||||
<span id="contact-edit-poll-text">{{$updpub}}</span> {{$poll_interval}} <span id="contact-edit-update-now" class="button"><a href="contacts/{{$contact_id}}/update" >{{$udnow}}</a></span>
|
||||
</div>
|
||||
{{/if}}
|
||||
<div id="contact-edit-end" ></div>
|
||||
|
||||
{{include file="field_checkbox.tpl" field=$hidden}}
|
||||
|
|
|
|||
|
|
@ -10,7 +10,6 @@
|
|||
*/
|
||||
|
||||
function frost_init(&$a) {
|
||||
$a->theme_info = array();
|
||||
$a->videowidth = 400;
|
||||
$a->videoheight = 330;
|
||||
$a->theme_thread_allow = false;
|
||||
|
|
|
|||
|
|
@ -463,7 +463,7 @@ a:hover {
|
|||
text-decoration: underline;
|
||||
}
|
||||
blockquote {
|
||||
background: #FFFFFF;
|
||||
background: #ffffff;
|
||||
padding: 1em;
|
||||
margin-left: 1em;
|
||||
border-left: 1em solid #e6e6e6;
|
||||
|
|
@ -1655,6 +1655,9 @@ span[id^="showmore-wrap"] {
|
|||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
}
|
||||
#contact-edit-status-wrapper {
|
||||
border-color: #364e59;
|
||||
}
|
||||
/* editor */
|
||||
.jothidden {
|
||||
display: none;
|
||||
|
|
|
|||
|
|
@ -463,7 +463,7 @@ a:hover {
|
|||
text-decoration: underline;
|
||||
}
|
||||
blockquote {
|
||||
background: #FFFFFF;
|
||||
background: #ffffff;
|
||||
padding: 1em;
|
||||
margin-left: 1em;
|
||||
border-left: 1em solid #e6e6e6;
|
||||
|
|
@ -1655,6 +1655,9 @@ span[id^="showmore-wrap"] {
|
|||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
}
|
||||
#contact-edit-status-wrapper {
|
||||
border-color: #9ade00;
|
||||
}
|
||||
/* editor */
|
||||
.jothidden {
|
||||
display: none;
|
||||
|
|
|
|||
|
|
@ -420,7 +420,7 @@
|
|||
body {
|
||||
font-family: Liberation Sans, helvetica, arial, clean, sans-serif;
|
||||
font-size: 11px;
|
||||
background-color: #F6ECF9;
|
||||
background-color: #f6ecf9;
|
||||
color: #2d2d2d;
|
||||
margin: 50px 0 0 0;
|
||||
display: table;
|
||||
|
|
@ -463,7 +463,7 @@ a:hover {
|
|||
text-decoration: underline;
|
||||
}
|
||||
blockquote {
|
||||
background: #FFFFFF;
|
||||
background: #ffffff;
|
||||
padding: 1em;
|
||||
margin-left: 1em;
|
||||
border-left: 1em solid #e6e6e6;
|
||||
|
|
@ -1655,6 +1655,9 @@ span[id^="showmore-wrap"] {
|
|||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
}
|
||||
#contact-edit-status-wrapper {
|
||||
border-color: #86608e;
|
||||
}
|
||||
/* editor */
|
||||
.jothidden {
|
||||
display: none;
|
||||
|
|
@ -1753,7 +1756,7 @@ span[id^="showmore-wrap"] {
|
|||
height: 20px;
|
||||
width: 500px;
|
||||
font-weight: bold;
|
||||
border: 1px solid #F6ECF9;
|
||||
border: 1px solid #f6ecf9;
|
||||
}
|
||||
#jot #jot-title:-webkit-input-placeholder {
|
||||
font-weight: normal;
|
||||
|
|
@ -1780,7 +1783,7 @@ span[id^="showmore-wrap"] {
|
|||
margin: 0;
|
||||
height: 20px;
|
||||
width: 200px;
|
||||
border: 1px solid #F6ECF9;
|
||||
border: 1px solid #f6ecf9;
|
||||
}
|
||||
#jot #jot-category:hover {
|
||||
border: 1px solid #999999;
|
||||
|
|
|
|||
|
|
@ -408,19 +408,19 @@ aside {
|
|||
.group-delete-wrapper {
|
||||
float: right;
|
||||
margin-right: 50px;
|
||||
.drophide {
|
||||
background-image: url('../../../images/icons/22/delete.png');
|
||||
display: block; width: 22px; height: 22px;
|
||||
opacity: 0.3;
|
||||
position: relative;
|
||||
top: -50px;
|
||||
}
|
||||
.drop {
|
||||
background-image: url('../../../images/icons/22/delete.png');
|
||||
display: block; width: 22px; height: 22px;
|
||||
position: relative;
|
||||
top: -50px;
|
||||
}
|
||||
.drophide {
|
||||
background-image: url('../../../images/icons/22/delete.png');
|
||||
display: block; width: 22px; height: 22px;
|
||||
opacity: 0.3;
|
||||
position: relative;
|
||||
top: -50px;
|
||||
}
|
||||
.drop {
|
||||
background-image: url('../../../images/icons/22/delete.png');
|
||||
display: block; width: 22px; height: 22px;
|
||||
position: relative;
|
||||
top: -50px;
|
||||
}
|
||||
}
|
||||
/*
|
||||
#group-members {
|
||||
|
|
@ -502,7 +502,7 @@ section {
|
|||
}
|
||||
|
||||
.sparkle {
|
||||
cursor: url('icons/lock.cur'), pointer;
|
||||
cursor: url('icons/lock.cur'), pointer;
|
||||
}
|
||||
|
||||
/* wall item */
|
||||
|
|
@ -959,6 +959,7 @@ span[id^="showmore-wrap"] {
|
|||
text-overflow: ellipsis;
|
||||
}
|
||||
|
||||
#contact-edit-status-wrapper { border-color: @JotToolsOverBackgroundColor;}
|
||||
/* editor */
|
||||
.jothidden { display: none; }
|
||||
#jot {
|
||||
|
|
|
|||
|
|
@ -8,8 +8,6 @@
|
|||
*/
|
||||
|
||||
function quattro_init(&$a) {
|
||||
$a->theme_info = array();
|
||||
|
||||
$a->page['htmlhead'] .= '<script src="'.$a->get_baseurl().'/view/theme/quattro/tinycon.min.js"></script>';
|
||||
$a->page['htmlhead'] .= '<script src="'.$a->get_baseurl().'/view/theme/quattro/js/quattro.js"></script>';;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -236,6 +236,39 @@ section {
|
|||
color: #efefef;
|
||||
}
|
||||
|
||||
ul.menu-popup {
|
||||
position: absolute;
|
||||
display: none;
|
||||
width: auto;
|
||||
margin: 2px 0 0;
|
||||
padding: 0px;
|
||||
list-style: none;
|
||||
z-index: 100000;
|
||||
color: #2e3436;
|
||||
border-top: 1px;
|
||||
background: #eeeeee;
|
||||
border: 1px solid #7C7D7B;
|
||||
border-radius: 0px 0px 5px 5px;
|
||||
-webkit-border-radius: 0px 0px 5px 5px;
|
||||
-moz-border-radius: 0px 0px 5px 5px;
|
||||
box-shadow: 5px 5px 10px #242424;
|
||||
-moz-box-shadow: 5px 5px 10px #242424;
|
||||
-webkit-box-shadow: 5px 5px 10px #242424;
|
||||
}
|
||||
ul.menu-popup li a {
|
||||
white-space: nowrap;
|
||||
display: block;
|
||||
padding: 5px 2px;
|
||||
color: #2e3436;
|
||||
}
|
||||
ul.menu-popup li a:hover {
|
||||
color: #efefef;
|
||||
background: -webkit-gradient( linear, left top, left bottom, color-stop(0.05, #1873a2), color-stop(1, #6da6c4) );
|
||||
background: -moz-linear-gradient( center top, #1873a2 5%, #6da6c4 100% );
|
||||
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#1873a2', endColorstr='#6da6c4');
|
||||
background-color: #1873a2;
|
||||
}
|
||||
|
||||
/* ========= */
|
||||
/* = Login = */
|
||||
/* ========= */
|
||||
|
|
@ -4271,16 +4304,6 @@ a.active {
|
|||
.nav-notify.show {
|
||||
display: block;
|
||||
}
|
||||
ul.menu-popup {
|
||||
position: absolute;
|
||||
display: none;
|
||||
width: 10em;
|
||||
margin: 0px;
|
||||
padding: 0px;
|
||||
list-style: none;
|
||||
z-index: 100000;
|
||||
top: 40px;
|
||||
}
|
||||
#nav-notifications-menu {
|
||||
width: 320px;
|
||||
max-height: 400px;
|
||||
|
|
@ -4298,6 +4321,7 @@ ul.menu-popup {
|
|||
box-shadow: 5px 5px 10px #242424;
|
||||
-moz-box-shadow: 5px 5px 10px #242424;
|
||||
-webkit-box-shadow: 5px 5px 10px #242424;
|
||||
top: 40px;
|
||||
}
|
||||
|
||||
#nav-notifications-menu .contactname {
|
||||
|
|
@ -4406,6 +4430,10 @@ ul.menu-popup {
|
|||
background: #000000;
|
||||
}
|
||||
|
||||
.notify-seen a {
|
||||
color: #efefef !important;
|
||||
}
|
||||
|
||||
/* Pages profile widget ----------------------------------------------------------- */
|
||||
|
||||
#page-profile,
|
||||
|
|
|
|||
|
|
@ -11,7 +11,6 @@
|
|||
*/
|
||||
|
||||
function smoothly_init(&$a) {
|
||||
$a->theme_info = array();
|
||||
set_template_engine($a, 'smarty3');
|
||||
|
||||
$cssFile = null;
|
||||
|
|
|
|||
|
|
@ -228,6 +228,7 @@ li.icon.icon-large:before {
|
|||
.icon-key:before { content: "\f084"; }
|
||||
.icon.gears:before { content: "\f085"; }
|
||||
.icon-comments:before { content: "\f086"; }
|
||||
.icon-commenting:before { content: "\f27a"; }
|
||||
.icon.like:before { content: "\f087"; }
|
||||
.icon.dislike:before { content: "\f088"; }
|
||||
.icon-star-half:before { content: "\f089"; }
|
||||
|
|
|
|||
|
|
@ -8,6 +8,12 @@ hr { background-color: #343434 !important; }
|
|||
a, .wall-item-name, .fakelink {
|
||||
color: #989898 !important;
|
||||
}
|
||||
.btn, .btn:hover{
|
||||
color: #989898;
|
||||
border: 2px solid #0C1116;
|
||||
background-color: #0C1116;
|
||||
text-shadow: none;
|
||||
}
|
||||
|
||||
nav {
|
||||
color: #989898 !important;
|
||||
|
|
@ -36,7 +42,7 @@ body, section, blockquote, blockquote.shared_content, #profile-jot-form,
|
|||
}
|
||||
|
||||
#profile-jot-acl-wrapper, #event-notice, #event-wrapper,
|
||||
#cboxLoadedContent, .contact-photo-menu {
|
||||
#cboxLoadedContent, .contact-photo-menu, #contact-edit-status-wrapper {
|
||||
background-color: #252C33 !important;
|
||||
}
|
||||
|
||||
|
|
|
|||
Binary file not shown.
BIN
view/theme/vier/font/fontawesome-webfont.eot
Executable file → Normal file
BIN
view/theme/vier/font/fontawesome-webfont.eot
Executable file → Normal file
Binary file not shown.
169
view/theme/vier/font/fontawesome-webfont.svg
Executable file → Normal file
169
view/theme/vier/font/fontawesome-webfont.svg
Executable file → Normal file
|
|
@ -147,14 +147,14 @@
|
|||
<glyph unicode="" horiz-adv-x="1792" d="M1683 205l-166 -165q-19 -19 -45 -19t-45 19l-531 531l-531 -531q-19 -19 -45 -19t-45 19l-166 165q-19 19 -19 45.5t19 45.5l742 741q19 19 45 19t45 -19l742 -741q19 -19 19 -45.5t-19 -45.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1683 728l-742 -741q-19 -19 -45 -19t-45 19l-742 741q-19 19 -19 45.5t19 45.5l166 165q19 19 45 19t45 -19l531 -531l531 531q19 19 45 19t45 -19l166 -165q19 -19 19 -45.5t-19 -45.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1920" d="M1280 32q0 -13 -9.5 -22.5t-22.5 -9.5h-960q-8 0 -13.5 2t-9 7t-5.5 8t-3 11.5t-1 11.5v13v11v160v416h-192q-26 0 -45 19t-19 45q0 24 15 41l320 384q19 22 49 22t49 -22l320 -384q15 -17 15 -41q0 -26 -19 -45t-45 -19h-192v-384h576q16 0 25 -11l160 -192q7 -11 7 -21 zM1920 448q0 -24 -15 -41l-320 -384q-20 -23 -49 -23t-49 23l-320 384q-15 17 -15 41q0 26 19 45t45 19h192v384h-576q-16 0 -25 12l-160 192q-7 9 -7 20q0 13 9.5 22.5t22.5 9.5h960q8 0 13.5 -2t9 -7t5.5 -8t3 -11.5t1 -11.5v-13v-11v-160v-416h192q26 0 45 -19t19 -45z " />
|
||||
<glyph unicode="" horiz-adv-x="1664" d="M640 0q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1536 0q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1664 1088v-512q0 -24 -16 -42.5t-41 -21.5 l-1044 -122q1 -7 4.5 -21.5t6 -26.5t2.5 -22q0 -16 -24 -64h920q26 0 45 -19t19 -45t-19 -45t-45 -19h-1024q-26 0 -45 19t-19 45q0 14 11 39.5t29.5 59.5t20.5 38l-177 823h-204q-26 0 -45 19t-19 45t19 45t45 19h256q16 0 28.5 -6.5t20 -15.5t13 -24.5t7.5 -26.5 t5.5 -29.5t4.5 -25.5h1201q26 0 45 -19t19 -45z" />
|
||||
<glyph unicode="" horiz-adv-x="1664" d="M640 0q0 -52 -38 -90t-90 -38t-90 38t-38 90t38 90t90 38t90 -38t38 -90zM1536 0q0 -52 -38 -90t-90 -38t-90 38t-38 90t38 90t90 38t90 -38t38 -90zM1664 1088v-512q0 -24 -16.5 -42.5t-40.5 -21.5l-1044 -122q13 -60 13 -70q0 -16 -24 -64h920q26 0 45 -19t19 -45 t-19 -45t-45 -19h-1024q-26 0 -45 19t-19 45q0 11 8 31.5t16 36t21.5 40t15.5 29.5l-177 823h-204q-26 0 -45 19t-19 45t19 45t45 19h256q16 0 28.5 -6.5t19.5 -15.5t13 -24.5t8 -26t5.5 -29.5t4.5 -26h1201q26 0 45 -19t19 -45z" />
|
||||
<glyph unicode="" horiz-adv-x="1664" d="M1664 928v-704q0 -92 -66 -158t-158 -66h-1216q-92 0 -158 66t-66 158v960q0 92 66 158t158 66h320q92 0 158 -66t66 -158v-32h672q92 0 158 -66t66 -158z" />
|
||||
<glyph unicode="" horiz-adv-x="1920" d="M1879 584q0 -31 -31 -66l-336 -396q-43 -51 -120.5 -86.5t-143.5 -35.5h-1088q-34 0 -60.5 13t-26.5 43q0 31 31 66l336 396q43 51 120.5 86.5t143.5 35.5h1088q34 0 60.5 -13t26.5 -43zM1536 928v-160h-832q-94 0 -197 -47.5t-164 -119.5l-337 -396l-5 -6q0 4 -0.5 12.5 t-0.5 12.5v960q0 92 66 158t158 66h320q92 0 158 -66t66 -158v-32h544q92 0 158 -66t66 -158z" />
|
||||
<glyph unicode="" horiz-adv-x="768" d="M704 1216q0 -26 -19 -45t-45 -19h-128v-1024h128q26 0 45 -19t19 -45t-19 -45l-256 -256q-19 -19 -45 -19t-45 19l-256 256q-19 19 -19 45t19 45t45 19h128v1024h-128q-26 0 -45 19t-19 45t19 45l256 256q19 19 45 19t45 -19l256 -256q19 -19 19 -45z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1792 640q0 -26 -19 -45l-256 -256q-19 -19 -45 -19t-45 19t-19 45v128h-1024v-128q0 -26 -19 -45t-45 -19t-45 19l-256 256q-19 19 -19 45t19 45l256 256q19 19 45 19t45 -19t19 -45v-128h1024v128q0 26 19 45t45 19t45 -19l256 -256q19 -19 19 -45z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M640 640v-512h-256v512h256zM1024 1152v-1024h-256v1024h256zM2048 0v-128h-2048v1536h128v-1408h1920zM1408 896v-768h-256v768h256zM1792 1280v-1152h-256v1152h256z" />
|
||||
<glyph unicode="" d="M1280 926q-56 -25 -121 -34q68 40 93 117q-65 -38 -134 -51q-61 66 -153 66q-87 0 -148.5 -61.5t-61.5 -148.5q0 -29 5 -48q-129 7 -242 65t-192 155q-29 -50 -29 -106q0 -114 91 -175q-47 1 -100 26v-2q0 -75 50 -133.5t123 -72.5q-29 -8 -51 -8q-13 0 -39 4 q21 -63 74.5 -104t121.5 -42q-116 -90 -261 -90q-26 0 -50 3q148 -94 322 -94q112 0 210 35.5t168 95t120.5 137t75 162t24.5 168.5q0 18 -1 27q63 45 105 109zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5 t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" d="M1536 160q0 -119 -84.5 -203.5t-203.5 -84.5h-192v608h203l30 224h-233v143q0 54 28 83t96 29l132 1v207q-96 9 -180 9q-136 0 -218 -80.5t-82 -225.5v-166h-224v-224h224v-608h-544q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960 q119 0 203.5 -84.5t84.5 -203.5v-960z" />
|
||||
<glyph unicode="" d="M1248 1408q119 0 203.5 -84.5t84.5 -203.5v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-188v595h199l30 232h-229v148q0 56 23.5 84t91.5 28l122 1v207q-63 9 -178 9q-136 0 -217.5 -80t-81.5 -226v-171h-200v-232h200v-595h-532q-119 0 -203.5 84.5t-84.5 203.5v960 q0 119 84.5 203.5t203.5 84.5h960z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M928 704q0 14 -9 23t-23 9q-66 0 -113 -47t-47 -113q0 -14 9 -23t23 -9t23 9t9 23q0 40 28 68t68 28q14 0 23 9t9 23zM1152 574q0 -106 -75 -181t-181 -75t-181 75t-75 181t75 181t181 75t181 -75t75 -181zM128 0h1536v128h-1536v-128zM1280 574q0 159 -112.5 271.5 t-271.5 112.5t-271.5 -112.5t-112.5 -271.5t112.5 -271.5t271.5 -112.5t271.5 112.5t112.5 271.5zM256 1216h384v128h-384v-128zM128 1024h1536v118v138h-828l-64 -128h-644v-128zM1792 1280v-1280q0 -53 -37.5 -90.5t-90.5 -37.5h-1536q-53 0 -90.5 37.5t-37.5 90.5v1280 q0 53 37.5 90.5t90.5 37.5h1536q53 0 90.5 -37.5t37.5 -90.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M832 1024q0 80 -56 136t-136 56t-136 -56t-56 -136q0 -42 19 -83q-41 19 -83 19q-80 0 -136 -56t-56 -136t56 -136t136 -56t136 56t56 136q0 42 -19 83q41 -19 83 -19q80 0 136 56t56 136zM1683 320q0 -17 -49 -66t-66 -49q-9 0 -28.5 16t-36.5 33t-38.5 40t-24.5 26 l-96 -96l220 -220q28 -28 28 -68q0 -42 -39 -81t-81 -39q-40 0 -68 28l-671 671q-176 -131 -365 -131q-163 0 -265.5 102.5t-102.5 265.5q0 160 95 313t248 248t313 95q163 0 265.5 -102.5t102.5 -265.5q0 -189 -131 -365l355 -355l96 96q-3 3 -26 24.5t-40 38.5t-33 36.5 t-16 28.5q0 17 49 66t66 49q13 0 23 -10q6 -6 46 -44.5t82 -79.5t86.5 -86t73 -78t28.5 -41z" />
|
||||
<glyph unicode="" horiz-adv-x="1920" d="M896 640q0 106 -75 181t-181 75t-181 -75t-75 -181t75 -181t181 -75t181 75t75 181zM1664 128q0 52 -38 90t-90 38t-90 -38t-38 -90q0 -53 37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM1664 1152q0 52 -38 90t-90 38t-90 -38t-38 -90q0 -53 37.5 -90.5t90.5 -37.5 t90.5 37.5t37.5 90.5zM1280 731v-185q0 -10 -7 -19.5t-16 -10.5l-155 -24q-11 -35 -32 -76q34 -48 90 -115q7 -10 7 -20q0 -12 -7 -19q-23 -30 -82.5 -89.5t-78.5 -59.5q-11 0 -21 7l-115 90q-37 -19 -77 -31q-11 -108 -23 -155q-7 -24 -30 -24h-186q-11 0 -20 7.5t-10 17.5 l-23 153q-34 10 -75 31l-118 -89q-7 -7 -20 -7q-11 0 -21 8q-144 133 -144 160q0 9 7 19q10 14 41 53t47 61q-23 44 -35 82l-152 24q-10 1 -17 9.5t-7 19.5v185q0 10 7 19.5t16 10.5l155 24q11 35 32 76q-34 48 -90 115q-7 11 -7 20q0 12 7 20q22 30 82 89t79 59q11 0 21 -7 l115 -90q34 18 77 32q11 108 23 154q7 24 30 24h186q11 0 20 -7.5t10 -17.5l23 -153q34 -10 75 -31l118 89q8 7 20 7q11 0 21 -8q144 -133 144 -160q0 -9 -7 -19q-12 -16 -42 -54t-45 -60q23 -48 34 -82l152 -23q10 -2 17 -10.5t7 -19.5zM1920 198v-140q0 -16 -149 -31 q-12 -27 -30 -52q51 -113 51 -138q0 -4 -4 -7q-122 -71 -124 -71q-8 0 -46 47t-52 68q-20 -2 -30 -2t-30 2q-14 -21 -52 -68t-46 -47q-2 0 -124 71q-4 3 -4 7q0 25 51 138q-18 25 -30 52q-149 15 -149 31v140q0 16 149 31q13 29 30 52q-51 113 -51 138q0 4 4 7q4 2 35 20 t59 34t30 16q8 0 46 -46.5t52 -67.5q20 2 30 2t30 -2q51 71 92 112l6 2q4 0 124 -70q4 -3 4 -7q0 -25 -51 -138q17 -23 30 -52q149 -15 149 -31zM1920 1222v-140q0 -16 -149 -31q-12 -27 -30 -52q51 -113 51 -138q0 -4 -4 -7q-122 -71 -124 -71q-8 0 -46 47t-52 68 q-20 -2 -30 -2t-30 2q-14 -21 -52 -68t-46 -47q-2 0 -124 71q-4 3 -4 7q0 25 51 138q-18 25 -30 52q-149 15 -149 31v140q0 16 149 31q13 29 30 52q-51 113 -51 138q0 4 4 7q4 2 35 20t59 34t30 16q8 0 46 -46.5t52 -67.5q20 2 30 2t30 -2q51 71 92 112l6 2q4 0 124 -70 q4 -3 4 -7q0 -25 -51 -138q17 -23 30 -52q149 -15 149 -31z" />
|
||||
|
|
@ -219,8 +219,8 @@
|
|||
<glyph unicode="" horiz-adv-x="1792" d="M640 128q0 52 -38 90t-90 38t-90 -38t-38 -90t38 -90t90 -38t90 38t38 90zM256 640h384v256h-158q-13 0 -22 -9l-195 -195q-9 -9 -9 -22v-30zM1536 128q0 52 -38 90t-90 38t-90 -38t-38 -90t38 -90t90 -38t90 38t38 90zM1792 1216v-1024q0 -15 -4 -26.5t-13.5 -18.5 t-16.5 -11.5t-23.5 -6t-22.5 -2t-25.5 0t-22.5 0.5q0 -106 -75 -181t-181 -75t-181 75t-75 181h-384q0 -106 -75 -181t-181 -75t-181 75t-75 181h-64q-3 0 -22.5 -0.5t-25.5 0t-22.5 2t-23.5 6t-16.5 11.5t-13.5 18.5t-4 26.5q0 26 19 45t45 19v320q0 8 -0.5 35t0 38 t2.5 34.5t6.5 37t14 30.5t22.5 30l198 198q19 19 50.5 32t58.5 13h160v192q0 26 19 45t45 19h1024q26 0 45 -19t19 -45z" />
|
||||
<glyph unicode="" d="M1536 640q0 -209 -103 -385.5t-279.5 -279.5t-385.5 -103q-111 0 -218 32q59 93 78 164q9 34 54 211q20 -39 73 -67.5t114 -28.5q121 0 216 68.5t147 188.5t52 270q0 114 -59.5 214t-172.5 163t-255 63q-105 0 -196 -29t-154.5 -77t-109 -110.5t-67 -129.5t-21.5 -134 q0 -104 40 -183t117 -111q30 -12 38 20q2 7 8 31t8 30q6 23 -11 43q-51 61 -51 151q0 151 104.5 259.5t273.5 108.5q151 0 235.5 -82t84.5 -213q0 -170 -68.5 -289t-175.5 -119q-61 0 -98 43.5t-23 104.5q8 35 26.5 93.5t30 103t11.5 75.5q0 50 -27 83t-77 33 q-62 0 -105 -57t-43 -142q0 -73 25 -122l-99 -418q-17 -70 -13 -177q-206 91 -333 281t-127 423q0 209 103 385.5t279.5 279.5t385.5 103t385.5 -103t279.5 -279.5t103 -385.5z" />
|
||||
<glyph unicode="" d="M1248 1408q119 0 203.5 -84.5t84.5 -203.5v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-725q85 122 108 210q9 34 53 209q21 -39 73.5 -67t112.5 -28q181 0 295.5 147.5t114.5 373.5q0 84 -35 162.5t-96.5 139t-152.5 97t-197 36.5q-104 0 -194.5 -28.5t-153 -76.5 t-107.5 -109.5t-66.5 -128t-21.5 -132.5q0 -102 39.5 -180t116.5 -110q13 -5 23.5 0t14.5 19q10 44 15 61q6 23 -11 42q-50 62 -50 150q0 150 103.5 256.5t270.5 106.5q149 0 232.5 -81t83.5 -210q0 -168 -67.5 -286t-173.5 -118q-60 0 -97 43.5t-23 103.5q8 34 26.5 92.5 t29.5 102t11 74.5q0 49 -26.5 81.5t-75.5 32.5q-61 0 -103.5 -56.5t-42.5 -139.5q0 -72 24 -121l-98 -414q-24 -100 -7 -254h-183q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960z" />
|
||||
<glyph unicode="" d="M829 318q0 -76 -58.5 -112.5t-139.5 -36.5q-41 0 -80.5 9.5t-75.5 28.5t-58 53t-22 78q0 46 25 80t65.5 51.5t82 25t84.5 7.5q20 0 31 -2q2 -1 23 -16.5t26 -19t23 -18t24.5 -22t19 -22.5t17 -26t9 -26.5t4.5 -31.5zM755 863q0 -60 -33 -99.5t-92 -39.5q-53 0 -93 42.5 t-57.5 96.5t-17.5 106q0 61 32 104t92 43q53 0 93.5 -45t58 -101t17.5 -107zM861 1120l88 64h-265q-85 0 -161 -32t-127.5 -98t-51.5 -153q0 -93 64.5 -154.5t158.5 -61.5q22 0 43 3q-13 -29 -13 -54q0 -44 40 -94q-175 -12 -257 -63q-47 -29 -75.5 -73t-28.5 -95 q0 -43 18.5 -77.5t48.5 -56.5t69 -37t77.5 -21t76.5 -6q60 0 120.5 15.5t113.5 46t86 82.5t33 117q0 49 -20 89.5t-49 66.5t-58 47.5t-49 44t-20 44.5t15.5 42.5t37.5 39.5t44 42t37.5 59.5t15.5 82.5q0 60 -22.5 99.5t-72.5 90.5h83zM1152 672h128v64h-128v128h-64v-128 h-128v-64h128v-160h64v160zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1664" d="M735 740q0 -36 32 -70.5t77.5 -68t90.5 -73.5t77 -104t32 -142q0 -90 -48 -173q-72 -122 -211 -179.5t-298 -57.5q-132 0 -246.5 41.5t-171.5 137.5q-37 60 -37 131q0 81 44.5 150t118.5 115q131 82 404 100q-32 42 -47.5 74t-15.5 73q0 36 21 85q-46 -4 -68 -4 q-148 0 -249.5 96.5t-101.5 244.5q0 82 36 159t99 131q77 66 182.5 98t217.5 32h418l-138 -88h-131q74 -63 112 -133t38 -160q0 -72 -24.5 -129.5t-59 -93t-69.5 -65t-59.5 -61.5t-24.5 -66zM589 836q38 0 78 16.5t66 43.5q53 57 53 159q0 58 -17 125t-48.5 129.5 t-84.5 103.5t-117 41q-42 0 -82.5 -19.5t-65.5 -52.5q-47 -59 -47 -160q0 -46 10 -97.5t31.5 -103t52 -92.5t75 -67t96.5 -26zM591 -37q58 0 111.5 13t99 39t73 73t27.5 109q0 25 -7 49t-14.5 42t-27 41.5t-29.5 35t-38.5 34.5t-36.5 29t-41.5 30t-36.5 26q-16 2 -48 2 q-53 0 -105 -7t-107.5 -25t-97 -46t-68.5 -74.5t-27 -105.5q0 -70 35 -123.5t91.5 -83t119 -44t127.5 -14.5zM1401 839h213v-108h-213v-219h-105v219h-212v108h212v217h105v-217z" />
|
||||
<glyph unicode="" d="M917 631q0 26 -6 64h-362v-132h217q-3 -24 -16.5 -50t-37.5 -53t-66.5 -44.5t-96.5 -17.5q-99 0 -169 71t-70 171t70 171t169 71q92 0 153 -59l104 101q-108 100 -257 100q-160 0 -272 -112.5t-112 -271.5t112 -271.5t272 -112.5q165 0 266.5 105t101.5 270zM1262 585 h109v110h-109v110h-110v-110h-110v-110h110v-110h110v110zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M1437 623q0 -208 -87 -370.5t-248 -254t-369 -91.5q-149 0 -285 58t-234 156t-156 234t-58 285t58 285t156 234t234 156t285 58q286 0 491 -192l-199 -191q-117 113 -292 113q-123 0 -227.5 -62t-165.5 -168.5t-61 -232.5t61 -232.5t165.5 -168.5t227.5 -62 q83 0 152.5 23t114.5 57.5t78.5 78.5t49 83t21.5 74h-416v252h692q12 -63 12 -122zM2304 745v-210h-209v-209h-210v209h-209v210h209v209h210v-209h209z" />
|
||||
<glyph unicode="" horiz-adv-x="1920" d="M768 384h384v96h-128v448h-114l-148 -137l77 -80q42 37 55 57h2v-288h-128v-96zM1280 640q0 -70 -21 -142t-59.5 -134t-101.5 -101t-138 -39t-138 39t-101.5 101t-59.5 134t-21 142t21 142t59.5 134t101.5 101t138 39t138 -39t101.5 -101t59.5 -134t21 -142zM1792 384 v512q-106 0 -181 75t-75 181h-1152q0 -106 -75 -181t-181 -75v-512q106 0 181 -75t75 -181h1152q0 106 75 181t181 75zM1920 1216v-1152q0 -26 -19 -45t-45 -19h-1792q-26 0 -45 19t-19 45v1152q0 26 19 45t45 19h1792q26 0 45 -19t19 -45z" />
|
||||
<glyph unicode="" horiz-adv-x="1024" d="M1024 832q0 -26 -19 -45l-448 -448q-19 -19 -45 -19t-45 19l-448 448q-19 19 -19 45t19 45t45 19h896q26 0 45 -19t19 -45z" />
|
||||
<glyph unicode="" horiz-adv-x="1024" d="M1024 320q0 -26 -19 -45t-45 -19h-896q-26 0 -45 19t-19 45t19 45l448 448q19 19 45 19t45 -19l448 -448q19 -19 19 -45z" />
|
||||
|
|
@ -275,7 +275,7 @@
|
|||
<glyph unicode="" d="M768 1184q-148 0 -273 -73t-198 -198t-73 -273t73 -273t198 -198t273 -73t273 73t198 198t73 273t-73 273t-198 198t-273 73zM1536 640q0 -209 -103 -385.5t-279.5 -279.5t-385.5 -103t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103t385.5 -103 t279.5 -279.5t103 -385.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1664" d="M768 576v-384q0 -80 -56 -136t-136 -56h-384q-80 0 -136 56t-56 136v704q0 104 40.5 198.5t109.5 163.5t163.5 109.5t198.5 40.5h64q26 0 45 -19t19 -45v-128q0 -26 -19 -45t-45 -19h-64q-106 0 -181 -75t-75 -181v-32q0 -40 28 -68t68 -28h224q80 0 136 -56t56 -136z M1664 576v-384q0 -80 -56 -136t-136 -56h-384q-80 0 -136 56t-56 136v704q0 104 40.5 198.5t109.5 163.5t163.5 109.5t198.5 40.5h64q26 0 45 -19t19 -45v-128q0 -26 -19 -45t-45 -19h-64q-106 0 -181 -75t-75 -181v-32q0 -40 28 -68t68 -28h224q80 0 136 -56t56 -136z" />
|
||||
<glyph unicode="" horiz-adv-x="1664" d="M768 1216v-704q0 -104 -40.5 -198.5t-109.5 -163.5t-163.5 -109.5t-198.5 -40.5h-64q-26 0 -45 19t-19 45v128q0 26 19 45t45 19h64q106 0 181 75t75 181v32q0 40 -28 68t-68 28h-224q-80 0 -136 56t-56 136v384q0 80 56 136t136 56h384q80 0 136 -56t56 -136zM1664 1216 v-704q0 -104 -40.5 -198.5t-109.5 -163.5t-163.5 -109.5t-198.5 -40.5h-64q-26 0 -45 19t-19 45v128q0 26 19 45t45 19h64q106 0 181 75t75 181v32q0 40 -28 68t-68 28h-224q-80 0 -136 56t-56 136v384q0 80 56 136t136 56h384q80 0 136 -56t56 -136z" />
|
||||
<glyph unicode="" horiz-adv-x="1568" d="M496 192q0 -60 -42.5 -102t-101.5 -42q-60 0 -102 42t-42 102t42 102t102 42q59 0 101.5 -42t42.5 -102zM928 0q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM320 640q0 -66 -47 -113t-113 -47t-113 47t-47 113 t47 113t113 47t113 -47t47 -113zM1360 192q0 -46 -33 -79t-79 -33t-79 33t-33 79t33 79t79 33t79 -33t33 -79zM528 1088q0 -73 -51.5 -124.5t-124.5 -51.5t-124.5 51.5t-51.5 124.5t51.5 124.5t124.5 51.5t124.5 -51.5t51.5 -124.5zM992 1280q0 -80 -56 -136t-136 -56 t-136 56t-56 136t56 136t136 56t136 -56t56 -136zM1536 640q0 -40 -28 -68t-68 -28t-68 28t-28 68t28 68t68 28t68 -28t28 -68zM1328 1088q0 -33 -23.5 -56.5t-56.5 -23.5t-56.5 23.5t-23.5 56.5t23.5 56.5t56.5 23.5t56.5 -23.5t23.5 -56.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M526 142q0 -53 -37.5 -90.5t-90.5 -37.5q-52 0 -90 38t-38 90q0 53 37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1024 -64q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM320 640q0 -53 -37.5 -90.5t-90.5 -37.5 t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1522 142q0 -52 -38 -90t-90 -38q-53 0 -90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM558 1138q0 -66 -47 -113t-113 -47t-113 47t-47 113t47 113t113 47t113 -47t47 -113z M1728 640q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1088 1344q0 -80 -56 -136t-136 -56t-136 56t-56 136t56 136t136 56t136 -56t56 -136zM1618 1138q0 -93 -66 -158.5t-158 -65.5q-93 0 -158.5 65.5t-65.5 158.5 q0 92 65.5 158t158.5 66q92 0 158 -66t66 -158z" />
|
||||
<glyph unicode="" d="M1536 640q0 -209 -103 -385.5t-279.5 -279.5t-385.5 -103t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103t385.5 -103t279.5 -279.5t103 -385.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1792 416q0 -166 -127 -451q-3 -7 -10.5 -24t-13.5 -30t-13 -22q-12 -17 -28 -17q-15 0 -23.5 10t-8.5 25q0 9 2.5 26.5t2.5 23.5q5 68 5 123q0 101 -17.5 181t-48.5 138.5t-80 101t-105.5 69.5t-133 42.5t-154 21.5t-175.5 6h-224v-256q0 -26 -19 -45t-45 -19t-45 19 l-512 512q-19 19 -19 45t19 45l512 512q19 19 45 19t45 -19t19 -45v-256h224q713 0 875 -403q53 -134 53 -333z" />
|
||||
<glyph unicode="" horiz-adv-x="1664" d="M640 320q0 -40 -12.5 -82t-43 -76t-72.5 -34t-72.5 34t-43 76t-12.5 82t12.5 82t43 76t72.5 34t72.5 -34t43 -76t12.5 -82zM1280 320q0 -40 -12.5 -82t-43 -76t-72.5 -34t-72.5 34t-43 76t-12.5 82t12.5 82t43 76t72.5 34t72.5 -34t43 -76t12.5 -82zM1440 320 q0 120 -69 204t-187 84q-41 0 -195 -21q-71 -11 -157 -11t-157 11q-152 21 -195 21q-118 0 -187 -84t-69 -204q0 -88 32 -153.5t81 -103t122 -60t140 -29.5t149 -7h168q82 0 149 7t140 29.5t122 60t81 103t32 153.5zM1664 496q0 -207 -61 -331q-38 -77 -105.5 -133t-141 -86 t-170 -47.5t-171.5 -22t-167 -4.5q-78 0 -142 3t-147.5 12.5t-152.5 30t-137 51.5t-121 81t-86 115q-62 123 -62 331q0 237 136 396q-27 82 -27 170q0 116 51 218q108 0 190 -39.5t189 -123.5q147 35 309 35q148 0 280 -32q105 82 187 121t189 39q51 -102 51 -218 q0 -87 -27 -168q136 -160 136 -398z" />
|
||||
|
|
@ -362,7 +362,7 @@
|
|||
<glyph unicode="" d="M685 771q0 1 -126 222q-21 34 -52 34h-184q-18 0 -26 -11q-7 -12 1 -29l125 -216v-1l-196 -346q-9 -14 0 -28q8 -13 24 -13h185q31 0 50 36zM1309 1268q-7 12 -24 12h-187q-30 0 -49 -35l-411 -729q1 -2 262 -481q20 -35 52 -35h184q18 0 25 12q8 13 -1 28l-260 476v1 l409 723q8 16 0 28zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1280 640q0 37 -30 54l-512 320q-31 20 -65 2q-33 -18 -33 -56v-640q0 -38 33 -56q16 -8 31 -8q20 0 34 10l512 320q30 17 30 54zM1792 640q0 -96 -1 -150t-8.5 -136.5t-22.5 -147.5q-16 -73 -69 -123t-124 -58q-222 -25 -671 -25t-671 25q-71 8 -124.5 58t-69.5 123 q-14 65 -21.5 147.5t-8.5 136.5t-1 150t1 150t8.5 136.5t22.5 147.5q16 73 69 123t124 58q222 25 671 25t671 -25q71 -8 124.5 -58t69.5 -123q14 -65 21.5 -147.5t8.5 -136.5t1 -150z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M402 829l494 -305l-342 -285l-490 319zM1388 274v-108l-490 -293v-1l-1 1l-1 -1v1l-489 293v108l147 -96l342 284v2l1 -1l1 1v-2l343 -284zM554 1418l342 -285l-494 -304l-338 270zM1390 829l338 -271l-489 -319l-343 285zM1239 1418l489 -319l-338 -270l-494 304z" />
|
||||
<glyph unicode="" horiz-adv-x="1408" d="M928 135v-151l-707 -1v151zM1169 481v-701l-1 -35v-1h-1132l-35 1h-1v736h121v-618h928v618h120zM241 393l704 -65l-13 -150l-705 65zM309 709l683 -183l-39 -146l-683 183zM472 1058l609 -360l-77 -130l-609 360zM832 1389l398 -585l-124 -85l-399 584zM1285 1536 l121 -697l-149 -26l-121 697z" />
|
||||
<glyph unicode="" d="M1289 -96h-1118v480h-160v-640h1438v640h-160v-480zM347 428l33 157l783 -165l-33 -156zM450 802l67 146l725 -339l-67 -145zM651 1158l102 123l614 -513l-102 -123zM1048 1536l477 -641l-128 -96l-477 641zM330 65v159h800v-159h-800z" />
|
||||
<glyph unicode="" d="M1362 110v648h-135q20 -63 20 -131q0 -126 -64 -232.5t-174 -168.5t-240 -62q-197 0 -337 135.5t-140 327.5q0 68 20 131h-141v-648q0 -26 17.5 -43.5t43.5 -17.5h1069q25 0 43 17.5t18 43.5zM1078 643q0 124 -90.5 211.5t-218.5 87.5q-127 0 -217.5 -87.5t-90.5 -211.5 t90.5 -211.5t217.5 -87.5q128 0 218.5 87.5t90.5 211.5zM1362 1003v165q0 28 -20 48.5t-49 20.5h-174q-29 0 -49 -20.5t-20 -48.5v-165q0 -29 20 -49t49 -20h174q29 0 49 20t20 49zM1536 1211v-1142q0 -81 -58 -139t-139 -58h-1142q-81 0 -139 58t-58 139v1142q0 81 58 139 t139 58h1142q81 0 139 -58t58 -139z" />
|
||||
<glyph unicode="" d="M1248 1408q119 0 203.5 -84.5t84.5 -203.5v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960zM698 640q0 88 -62 150t-150 62t-150 -62t-62 -150t62 -150t150 -62t150 62t62 150zM1262 640q0 88 -62 150 t-150 62t-150 -62t-62 -150t62 -150t150 -62t150 62t62 150z" />
|
||||
<glyph unicode="" d="M768 914l201 -306h-402zM1133 384h94l-459 691l-459 -691h94l104 160h522zM1536 640q0 -209 -103 -385.5t-279.5 -279.5t-385.5 -103t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103t385.5 -103t279.5 -279.5t103 -385.5z" />
|
||||
|
|
@ -399,7 +399,7 @@
|
|||
<glyph unicode="" d="M1024 960v-640q0 -26 -19 -45t-45 -19q-20 0 -37 12l-448 320q-27 19 -27 52t27 52l448 320q17 12 37 12q26 0 45 -19t19 -45zM1280 160v960q0 13 -9.5 22.5t-22.5 9.5h-960q-13 0 -22.5 -9.5t-9.5 -22.5v-960q0 -13 9.5 -22.5t22.5 -9.5h960q13 0 22.5 9.5t9.5 22.5z M1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" d="M1024 640q0 -106 -75 -181t-181 -75t-181 75t-75 181t75 181t181 75t181 -75t75 -181zM768 1184q-148 0 -273 -73t-198 -198t-73 -273t73 -273t198 -198t273 -73t273 73t198 198t73 273t-73 273t-198 198t-273 73zM1536 640q0 -209 -103 -385.5t-279.5 -279.5 t-385.5 -103t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103t385.5 -103t279.5 -279.5t103 -385.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1664" d="M1023 349l102 -204q-58 -179 -210 -290t-339 -111q-156 0 -288.5 77.5t-210 210t-77.5 288.5q0 181 104.5 330t274.5 211l17 -131q-122 -54 -195 -165.5t-73 -244.5q0 -185 131.5 -316.5t316.5 -131.5q126 0 232.5 65t165 175.5t49.5 236.5zM1571 249l58 -114l-256 -128 q-13 -7 -29 -7q-40 0 -57 35l-239 477h-472q-24 0 -42.5 16.5t-21.5 40.5l-96 779q-2 16 6 42q14 51 57 82.5t97 31.5q66 0 113 -47t47 -113q0 -69 -52 -117.5t-120 -41.5l37 -289h423v-128h-407l16 -128h455q40 0 57 -35l228 -455z" />
|
||||
<glyph unicode="" d="M1254 899q16 85 -21 132q-52 65 -187 45q-17 -3 -41 -12.5t-57.5 -30.5t-64.5 -48.5t-59.5 -70t-44.5 -91.5q80 7 113.5 -16t26.5 -99q-5 -52 -52 -143q-43 -78 -71 -99q-44 -32 -87 14q-23 24 -37.5 64.5t-19 73t-10 84t-8.5 71.5q-23 129 -34 164q-12 37 -35.5 69 t-50.5 40q-57 16 -127 -25q-54 -32 -136.5 -106t-122.5 -102v-7q16 -8 25.5 -26t21.5 -20q21 -3 54.5 8.5t58 10.5t41.5 -30q11 -18 18.5 -38.5t15 -48t12.5 -40.5q17 -46 53 -187q36 -146 57 -197q42 -99 103 -125q43 -12 85 -1.5t76 31.5q131 77 250 237 q104 139 172.5 292.5t82.5 226.5zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" d="M1292 898q10 216 -161 222q-231 8 -312 -261q44 19 82 19q85 0 74 -96q-4 -57 -74 -167t-105 -110q-43 0 -82 169q-13 54 -45 255q-30 189 -160 177q-59 -7 -164 -100l-81 -72l-81 -72l52 -67q76 52 87 52q57 0 107 -179q15 -55 45 -164.5t45 -164.5q68 -179 164 -179 q157 0 383 294q220 283 226 444zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1152" d="M1152 704q0 -191 -94.5 -353t-256.5 -256.5t-353 -94.5h-160q-14 0 -23 9t-9 23v611l-215 -66q-3 -1 -9 -1q-10 0 -19 6q-13 10 -13 26v128q0 23 23 31l233 71v93l-215 -66q-3 -1 -9 -1q-10 0 -19 6q-13 10 -13 26v128q0 23 23 31l233 71v250q0 14 9 23t23 9h160 q14 0 23 -9t9 -23v-181l375 116q15 5 28 -5t13 -26v-128q0 -23 -23 -31l-393 -121v-93l375 116q15 5 28 -5t13 -26v-128q0 -23 -23 -31l-393 -121v-487q188 13 318 151t130 328q0 14 9 23t23 9h160q14 0 23 -9t9 -23z" />
|
||||
<glyph unicode="" horiz-adv-x="1408" d="M1152 736v-64q0 -14 -9 -23t-23 -9h-352v-352q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v352h-352q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h352v352q0 14 9 23t23 9h64q14 0 23 -9t9 -23v-352h352q14 0 23 -9t9 -23zM1280 288v832q0 66 -47 113t-113 47h-832 q-66 0 -113 -47t-47 -113v-832q0 -66 47 -113t113 -47h832q66 0 113 47t47 113zM1408 1120v-832q0 -119 -84.5 -203.5t-203.5 -84.5h-832q-119 0 -203.5 84.5t-84.5 203.5v832q0 119 84.5 203.5t203.5 84.5h832q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" horiz-adv-x="2176" d="M620 416q-110 -64 -268 -64h-128v64h-64q-13 0 -22.5 23.5t-9.5 56.5q0 24 7 49q-58 2 -96.5 10.5t-38.5 20.5t38.5 20.5t96.5 10.5q-7 25 -7 49q0 33 9.5 56.5t22.5 23.5h64v64h128q158 0 268 -64h1113q42 -7 106.5 -18t80.5 -14q89 -15 150 -40.5t83.5 -47.5t22.5 -40 t-22.5 -40t-83.5 -47.5t-150 -40.5q-16 -3 -80.5 -14t-106.5 -18h-1113zM1739 668q53 -36 53 -92t-53 -92l81 -30q68 48 68 122t-68 122zM625 400h1015q-217 -38 -456 -80q-57 0 -113 -24t-83 -48l-28 -24l-288 -288q-26 -26 -70.5 -45t-89.5 -19h-96l-93 464h29 q157 0 273 64zM352 816h-29l93 464h96q46 0 90 -19t70 -45l288 -288q4 -4 11 -10.5t30.5 -23t48.5 -29t61.5 -23t72.5 -10.5l456 -80h-1015q-116 64 -273 64z" />
|
||||
|
|
@ -410,9 +410,9 @@
|
|||
<glyph unicode="" horiz-adv-x="2048" d="M960 1536l960 -384v-128h-128q0 -26 -20.5 -45t-48.5 -19h-1526q-28 0 -48.5 19t-20.5 45h-128v128zM256 896h256v-768h128v768h256v-768h128v768h256v-768h128v768h256v-768h59q28 0 48.5 -19t20.5 -45v-64h-1664v64q0 26 20.5 45t48.5 19h59v768zM1851 -64 q28 0 48.5 -19t20.5 -45v-128h-1920v128q0 26 20.5 45t48.5 19h1782z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M1774 700l18 -316q4 -69 -82 -128t-235 -93.5t-323 -34.5t-323 34.5t-235 93.5t-82 128l18 316l574 -181q22 -7 48 -7t48 7zM2304 1024q0 -23 -22 -31l-1120 -352q-4 -1 -10 -1t-10 1l-652 206q-43 -34 -71 -111.5t-34 -178.5q63 -36 63 -109q0 -69 -58 -107l58 -433 q2 -14 -8 -25q-9 -11 -24 -11h-192q-15 0 -24 11q-10 11 -8 25l58 433q-58 38 -58 107q0 73 65 111q11 207 98 330l-333 104q-22 8 -22 31t22 31l1120 352q4 1 10 1t10 -1l1120 -352q22 -8 22 -31z" />
|
||||
<glyph unicode="" d="M859 579l13 -707q-62 11 -105 11q-41 0 -105 -11l13 707q-40 69 -168.5 295.5t-216.5 374.5t-181 287q58 -15 108 -15q43 0 111 15q63 -111 133.5 -229.5t167 -276.5t138.5 -227q37 61 109.5 177.5t117.5 190t105 176t107 189.5q54 -14 107 -14q56 0 114 14v0 q-28 -39 -60 -88.5t-49.5 -78.5t-56.5 -96t-49 -84q-146 -248 -353 -610z" />
|
||||
<glyph unicode="" horiz-adv-x="1280" d="M981 197q0 25 -7 49t-14.5 42t-27 41.5t-29.5 35t-38.5 34.5t-36.5 29t-41.5 30t-36.5 26q-16 2 -49 2q-53 0 -104.5 -7t-107 -25t-97 -46t-68.5 -74.5t-27 -105.5q0 -56 23.5 -102t61 -75.5t87 -50t100 -29t101.5 -8.5q58 0 111.5 13t99 39t73 73t27.5 109zM864 1055 q0 59 -17 125.5t-48 129t-84 103.5t-117 41q-42 0 -82.5 -19.5t-66.5 -52.5q-46 -59 -46 -160q0 -46 10 -97.5t31.5 -103t52 -92.5t75 -67t96.5 -26q37 0 77.5 16.5t65.5 43.5q53 56 53 159zM752 1536h417l-137 -88h-132q75 -63 113 -133t38 -160q0 -72 -24.5 -129.5 t-59.5 -93t-69.5 -65t-59 -61.5t-24.5 -66q0 -36 32 -70.5t77 -68t90.5 -73.5t77.5 -104t32 -142q0 -91 -49 -173q-71 -122 -209.5 -179.5t-298.5 -57.5q-132 0 -246.5 41.5t-172.5 137.5q-36 59 -36 131q0 81 44.5 150t118.5 115q131 82 404 100q-32 41 -47.5 73.5 t-15.5 73.5q0 40 21 85q-46 -4 -68 -4q-148 0 -249.5 96.5t-101.5 244.5q0 82 36 159t99 131q76 66 182 98t218 32z" />
|
||||
<glyph unicode="" horiz-adv-x="1984" d="M831 572q0 -56 -40.5 -96t-96.5 -40q-57 0 -98 40t-41 96q0 57 41.5 98t97.5 41t96.5 -41t40.5 -98zM1292 711q56 0 96.5 -41t40.5 -98q0 -56 -40.5 -96t-96.5 -40q-57 0 -98 40t-41 96q0 57 41.5 98t97.5 41zM1984 722q0 -62 -31 -114t-83 -82q5 -33 5 -61 q0 -121 -68.5 -230.5t-197.5 -193.5q-125 -82 -285.5 -125.5t-335.5 -43.5q-176 0 -336.5 43.5t-284.5 125.5q-129 84 -197.5 193t-68.5 231q0 29 5 66q-48 31 -77 81.5t-29 109.5q0 94 66 160t160 66q83 0 148 -55q248 158 592 164l134 423q4 14 17.5 21.5t28.5 4.5 l347 -82q22 50 68.5 81t102.5 31q77 0 131.5 -54.5t54.5 -131.5t-54.5 -132t-131.5 -55q-76 0 -130.5 54t-55.5 131l-315 74l-116 -366q327 -14 560 -166q64 58 151 58q94 0 160 -66t66 -160zM1664 1459q-45 0 -77 -32t-32 -77t32 -77t77 -32t77 32t32 77t-32 77t-77 32z M77 722q0 -67 51 -111q49 131 180 235q-36 25 -82 25q-62 0 -105.5 -43.5t-43.5 -105.5zM1567 105q112 73 171.5 166t59.5 194t-59.5 193.5t-171.5 165.5q-116 75 -265.5 115.5t-313.5 40.5t-313.5 -40.5t-265.5 -115.5q-112 -73 -171.5 -165.5t-59.5 -193.5t59.5 -194 t171.5 -166q116 -75 265.5 -115.5t313.5 -40.5t313.5 40.5t265.5 115.5zM1850 605q57 46 57 117q0 62 -43.5 105.5t-105.5 43.5q-49 0 -86 -28q131 -105 178 -238zM1258 237q11 11 27 11t27 -11t11 -27.5t-11 -27.5q-99 -99 -319 -99h-2q-220 0 -319 99q-11 11 -11 27.5 t11 27.5t27 11t27 -11q77 -77 265 -77h2q188 0 265 77z" />
|
||||
<glyph unicode="" d="M950 393q7 7 17.5 7t17.5 -7t7 -18t-7 -18q-65 -64 -208 -64h-1h-1q-143 0 -207 64q-8 7 -8 18t8 18q7 7 17.5 7t17.5 -7q49 -51 172 -51h1h1q122 0 173 51zM671 613q0 -37 -26 -64t-63 -27t-63 27t-26 64t26 63t63 26t63 -26t26 -63zM1214 1049q-29 0 -50 21t-21 50 q0 30 21 51t50 21q30 0 51 -21t21 -51q0 -29 -21 -50t-51 -21zM1216 1408q132 0 226 -94t94 -227v-894q0 -133 -94 -227t-226 -94h-896q-132 0 -226 94t-94 227v894q0 133 94 227t226 94h896zM1321 596q35 14 57 45.5t22 70.5q0 51 -36 87.5t-87 36.5q-60 0 -98 -48 q-151 107 -375 115l83 265l206 -49q1 -50 36.5 -85t84.5 -35q50 0 86 35.5t36 85.5t-36 86t-86 36q-36 0 -66 -20.5t-45 -53.5l-227 54q-9 2 -17.5 -2.5t-11.5 -14.5l-95 -302q-224 -4 -381 -113q-36 43 -93 43q-51 0 -87 -36.5t-36 -87.5q0 -37 19.5 -67.5t52.5 -45.5 q-7 -25 -7 -54q0 -98 74 -181.5t201.5 -132t278.5 -48.5q150 0 277.5 48.5t201.5 132t74 181.5q0 27 -6 54zM971 702q37 0 63 -26t26 -63t-26 -64t-63 -27t-63 27t-26 64t26 63t63 26z" />
|
||||
<glyph unicode="" d="M768 750h725q12 -67 12 -128q0 -217 -91 -387.5t-259.5 -266.5t-386.5 -96q-157 0 -299 60.5t-245 163.5t-163.5 245t-60.5 299t60.5 299t163.5 245t245 163.5t299 60.5q300 0 515 -201l-209 -201q-123 119 -306 119q-129 0 -238.5 -65t-173.5 -176.5t-64 -243.5 t64 -243.5t173.5 -176.5t238.5 -65q87 0 160 24t120 60t82 82t51.5 87t22.5 78h-436v264z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1095 369q16 -16 0 -31q-62 -62 -199 -62t-199 62q-16 15 0 31q6 6 15 6t15 -6q48 -49 169 -49q120 0 169 49q6 6 15 6t15 -6zM788 550q0 -37 -26 -63t-63 -26t-63.5 26t-26.5 63q0 38 26.5 64t63.5 26t63 -26.5t26 -63.5zM1183 550q0 -37 -26.5 -63t-63.5 -26t-63 26 t-26 63t26 63.5t63 26.5t63.5 -26t26.5 -64zM1434 670q0 49 -35 84t-85 35t-86 -36q-130 90 -311 96l63 283l200 -45q0 -37 26 -63t63 -26t63.5 26.5t26.5 63.5t-26.5 63.5t-63.5 26.5q-54 0 -80 -50l-221 49q-19 5 -25 -16l-69 -312q-180 -7 -309 -97q-35 37 -87 37 q-50 0 -85 -35t-35 -84q0 -35 18.5 -64t49.5 -44q-6 -27 -6 -56q0 -142 140 -243t337 -101q198 0 338 101t140 243q0 32 -7 57q30 15 48 43.5t18 63.5zM1792 640q0 -182 -71 -348t-191 -286t-286 -191t-348 -71t-348 71t-286 191t-191 286t-71 348t71 348t191 286t286 191 t348 71t348 -71t286 -191t191 -286t71 -348z" />
|
||||
<glyph unicode="" d="M939 407q13 -13 0 -26q-53 -53 -171 -53t-171 53q-13 13 0 26q5 6 13 6t13 -6q42 -42 145 -42t145 42q5 6 13 6t13 -6zM676 563q0 -31 -23 -54t-54 -23t-54 23t-23 54q0 32 22.5 54.5t54.5 22.5t54.5 -22.5t22.5 -54.5zM1014 563q0 -31 -23 -54t-54 -23t-54 23t-23 54 q0 32 22.5 54.5t54.5 22.5t54.5 -22.5t22.5 -54.5zM1229 666q0 42 -30 72t-73 30q-42 0 -73 -31q-113 78 -267 82l54 243l171 -39q1 -32 23.5 -54t53.5 -22q32 0 54.5 22.5t22.5 54.5t-22.5 54.5t-54.5 22.5q-48 0 -69 -43l-189 42q-17 5 -21 -13l-60 -268q-154 -6 -265 -83 q-30 32 -74 32q-43 0 -73 -30t-30 -72q0 -30 16 -55t42 -38q-5 -25 -5 -48q0 -122 120 -208.5t289 -86.5q170 0 290 86.5t120 208.5q0 25 -6 49q25 13 40.5 37.5t15.5 54.5zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960 q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" d="M866 697l90 27v62q0 79 -58 135t-138 56t-138 -55.5t-58 -134.5v-283q0 -20 -14 -33.5t-33 -13.5t-32.5 13.5t-13.5 33.5v120h-151v-122q0 -82 57.5 -139t139.5 -57q81 0 138.5 56.5t57.5 136.5v280q0 19 13.5 33t33.5 14q19 0 32.5 -14t13.5 -33v-54zM1199 502v122h-150 v-126q0 -20 -13.5 -33.5t-33.5 -13.5q-19 0 -32.5 14t-13.5 33v123l-90 -26l-60 28v-123q0 -80 58 -137t139 -57t138.5 57t57.5 139zM1536 640q0 -209 -103 -385.5t-279.5 -279.5t-385.5 -103t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103 t385.5 -103t279.5 -279.5t103 -385.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1920" d="M1062 824v118q0 42 -30 72t-72 30t-72 -30t-30 -72v-612q0 -175 -126 -299t-303 -124q-178 0 -303.5 125.5t-125.5 303.5v266h328v-262q0 -43 30 -72.5t72 -29.5t72 29.5t30 72.5v620q0 171 126.5 292t301.5 121q176 0 302 -122t126 -294v-136l-195 -58zM1592 602h328 v-266q0 -178 -125.5 -303.5t-303.5 -125.5q-177 0 -303 124.5t-126 300.5v268l131 -61l195 58v-270q0 -42 30 -71.5t72 -29.5t72 29.5t30 71.5v275z" />
|
||||
<glyph unicode="" d="M1472 160v480h-704v704h-480q-93 0 -158.5 -65.5t-65.5 -158.5v-480h704v-704h480q93 0 158.5 65.5t65.5 158.5zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5 t84.5 -203.5z" />
|
||||
|
|
@ -438,7 +438,7 @@
|
|||
<glyph unicode="" horiz-adv-x="2048" d="M1824 640q93 0 158.5 -65.5t65.5 -158.5v-384q0 -14 -9 -23t-23 -9h-96v-64q0 -80 -56 -136t-136 -56t-136 56t-56 136v64h-1024v-64q0 -80 -56 -136t-136 -56t-136 56t-56 136v64h-96q-14 0 -23 9t-9 23v384q0 93 65.5 158.5t158.5 65.5h28l105 419q23 94 104 157.5 t179 63.5h128v224q0 14 9 23t23 9h448q14 0 23 -9t9 -23v-224h128q98 0 179 -63.5t104 -157.5l105 -419h28zM320 160q66 0 113 47t47 113t-47 113t-113 47t-113 -47t-47 -113t47 -113t113 -47zM516 640h1016l-89 357q-2 8 -14 17.5t-21 9.5h-768q-9 0 -21 -9.5t-14 -17.5z M1728 160q66 0 113 47t47 113t-47 113t-113 47t-113 -47t-47 -113t47 -113t113 -47z" />
|
||||
<glyph unicode="" d="M1504 64q0 -26 -19 -45t-45 -19h-462q1 -17 6 -87.5t5 -108.5q0 -25 -18 -42.5t-43 -17.5h-320q-25 0 -43 17.5t-18 42.5q0 38 5 108.5t6 87.5h-462q-26 0 -45 19t-19 45t19 45l402 403h-229q-26 0 -45 19t-19 45t19 45l402 403h-197q-26 0 -45 19t-19 45t19 45l384 384 q19 19 45 19t45 -19l384 -384q19 -19 19 -45t-19 -45t-45 -19h-197l402 -403q19 -19 19 -45t-19 -45t-45 -19h-229l402 -403q19 -19 19 -45z" />
|
||||
<glyph unicode="" d="M1127 326q0 32 -30 51q-193 115 -447 115q-133 0 -287 -34q-42 -9 -42 -52q0 -20 13.5 -34.5t35.5 -14.5q5 0 37 8q132 27 243 27q226 0 397 -103q19 -11 33 -11q19 0 33 13.5t14 34.5zM1223 541q0 40 -35 61q-237 141 -548 141q-153 0 -303 -42q-48 -13 -48 -64 q0 -25 17.5 -42.5t42.5 -17.5q7 0 37 8q122 33 251 33q279 0 488 -124q24 -13 38 -13q25 0 42.5 17.5t17.5 42.5zM1331 789q0 47 -40 70q-126 73 -293 110.5t-343 37.5q-204 0 -364 -47q-23 -7 -38.5 -25.5t-15.5 -48.5q0 -31 20.5 -52t51.5 -21q11 0 40 8q133 37 307 37 q159 0 309.5 -34t253.5 -95q21 -12 40 -12q29 0 50.5 20.5t21.5 51.5zM1536 640q0 -209 -103 -385.5t-279.5 -279.5t-385.5 -103t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103t385.5 -103t279.5 -279.5t103 -385.5z" />
|
||||
<glyph unicode="" d="M1397 1408q58 0 98.5 -40.5t40.5 -98.5v-1258q0 -58 -40.5 -98.5t-98.5 -40.5h-1258q-58 0 -98.5 40.5t-40.5 98.5v1258q0 58 40.5 98.5t98.5 40.5h1258zM1465 11v1258q0 28 -20 48t-48 20h-1258q-28 0 -48 -20t-20 -48v-1258q0 -28 20 -48t48 -20h1258q28 0 48 20t20 48 zM694 749l188 -387l533 145v-496q0 -7 -5.5 -12.5t-12.5 -5.5h-1258q-7 0 -12.5 5.5t-5.5 12.5v141l711 195l-212 439q4 1 12 2.5t12 1.5q170 32 303.5 21.5t221 -46t143.5 -94.5q27 -28 -25 -42q-64 -16 -256 -62l-97 198q-111 7 -240 -16zM1397 1287q7 0 12.5 -5.5 t5.5 -12.5v-428q-85 30 -188 52q-294 64 -645 12l-18 -3l-65 134h-233l85 -190q-132 -51 -230 -137v560q0 7 5.5 12.5t12.5 5.5h1258zM286 387q-14 -3 -26 4.5t-14 21.5q-24 203 166 305l129 -270z" />
|
||||
<glyph unicode="" horiz-adv-x="1024" d="M1024 1233l-303 -582l24 -31h279v-415h-507l-44 -30l-142 -273l-30 -30h-301v303l303 583l-24 30h-279v415h507l44 30l142 273l30 30h301v-303z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M784 164l16 241l-16 523q-1 10 -7.5 17t-16.5 7q-9 0 -16 -7t-7 -17l-14 -523l14 -241q1 -10 7.5 -16.5t15.5 -6.5q22 0 24 23zM1080 193l11 211l-12 586q0 16 -13 24q-8 5 -16 5t-16 -5q-13 -8 -13 -24l-1 -6l-10 -579q0 -1 11 -236v-1q0 -10 6 -17q9 -11 23 -11 q11 0 20 9q9 7 9 20zM35 533l20 -128l-20 -126q-2 -9 -9 -9t-9 9l-17 126l17 128q2 9 9 9t9 -9zM121 612l26 -207l-26 -203q-2 -9 -10 -9q-9 0 -9 10l-23 202l23 207q0 9 9 9q8 0 10 -9zM401 159zM213 650l25 -245l-25 -237q0 -11 -11 -11q-10 0 -12 11l-21 237l21 245 q2 12 12 12q11 0 11 -12zM307 657l23 -252l-23 -244q-2 -13 -14 -13q-13 0 -13 13l-21 244l21 252q0 13 13 13q12 0 14 -13zM401 639l21 -234l-21 -246q-2 -16 -16 -16q-6 0 -10.5 4.5t-4.5 11.5l-20 246l20 234q0 6 4.5 10.5t10.5 4.5q14 0 16 -15zM784 164zM495 785 l21 -380l-21 -246q0 -7 -5 -12.5t-12 -5.5q-16 0 -18 18l-18 246l18 380q2 18 18 18q7 0 12 -5.5t5 -12.5zM589 871l19 -468l-19 -244q0 -8 -5.5 -13.5t-13.5 -5.5q-18 0 -20 19l-16 244l16 468q2 19 20 19q8 0 13.5 -5.5t5.5 -13.5zM687 911l18 -506l-18 -242 q-2 -21 -22 -21q-19 0 -21 21l-16 242l16 506q0 9 6.5 15.5t14.5 6.5q9 0 15 -6.5t7 -15.5zM1079 169v0v0zM881 915l15 -510l-15 -239q0 -10 -7.5 -17.5t-17.5 -7.5t-17 7t-8 18l-14 239l14 510q0 11 7.5 18t17.5 7t17.5 -7t7.5 -18zM980 896l14 -492l-14 -236q0 -11 -8 -19 t-19 -8t-19 8t-9 19l-12 236l12 492q1 12 9 20t19 8t18.5 -8t8.5 -20zM1192 404l-14 -231v0q0 -13 -9 -22t-22 -9t-22 9t-10 22l-6 114l-6 117l12 636v3q2 15 12 24q9 7 20 7q8 0 15 -5q14 -8 16 -26zM2304 423q0 -117 -83 -199.5t-200 -82.5h-786q-13 2 -22 11t-9 22v899 q0 23 28 33q85 34 181 34q195 0 338 -131.5t160 -323.5q53 22 110 22q117 0 200 -83t83 -201z" />
|
||||
<glyph unicode="" d="M768 768q237 0 443 43t325 127v-170q0 -69 -103 -128t-280 -93.5t-385 -34.5t-385 34.5t-280 93.5t-103 128v170q119 -84 325 -127t443 -43zM768 0q237 0 443 43t325 127v-170q0 -69 -103 -128t-280 -93.5t-385 -34.5t-385 34.5t-280 93.5t-103 128v170q119 -84 325 -127 t443 -43zM768 384q237 0 443 43t325 127v-170q0 -69 -103 -128t-280 -93.5t-385 -34.5t-385 34.5t-280 93.5t-103 128v170q119 -84 325 -127t443 -43zM768 1536q208 0 385 -34.5t280 -93.5t103 -128v-128q0 -69 -103 -128t-280 -93.5t-385 -34.5t-385 34.5t-280 93.5 t-103 128v128q0 69 103 128t280 93.5t385 34.5z" />
|
||||
<glyph unicode="" d="M1468 1156q28 -28 48 -76t20 -88v-1152q0 -40 -28 -68t-68 -28h-1344q-40 0 -68 28t-28 68v1600q0 40 28 68t68 28h896q40 0 88 -20t76 -48zM1024 1400v-376h376q-10 29 -22 41l-313 313q-12 12 -41 22zM1408 -128v1024h-416q-40 0 -68 28t-28 68v416h-768v-1536h1280z M894 465q33 -26 84 -56q59 7 117 7q147 0 177 -49q16 -22 2 -52q0 -1 -1 -2l-2 -2v-1q-6 -38 -71 -38q-48 0 -115 20t-130 53q-221 -24 -392 -83q-153 -262 -242 -262q-15 0 -28 7l-24 12q-1 1 -6 5q-10 10 -6 36q9 40 56 91.5t132 96.5q14 9 23 -6q2 -2 2 -4q52 85 107 197 q68 136 104 262q-24 82 -30.5 159.5t6.5 127.5q11 40 42 40h21h1q23 0 35 -15q18 -21 9 -68q-2 -6 -4 -8q1 -3 1 -8v-30q-2 -123 -14 -192q55 -164 146 -238zM318 54q52 24 137 158q-51 -40 -87.5 -84t-49.5 -74zM716 974q-15 -42 -2 -132q1 7 7 44q0 3 7 43q1 4 4 8 q-1 1 -1 2t-0.5 1.5t-0.5 1.5q-1 22 -13 36q0 -1 -1 -2v-2zM592 313q135 54 284 81q-2 1 -13 9.5t-16 13.5q-76 67 -127 176q-27 -86 -83 -197q-30 -56 -45 -83zM1238 329q-24 24 -140 24q76 -28 124 -28q14 0 18 1q0 1 -2 3z" />
|
||||
|
|
@ -454,12 +454,12 @@
|
|||
<glyph unicode="" horiz-adv-x="1792" d="M216 367l603 -402v359l-334 223zM154 511l193 129l-193 129v-258zM973 -35l603 402l-269 180l-334 -223v-359zM896 458l272 182l-272 182l-272 -182zM485 733l334 223v359l-603 -402zM1445 640l193 -129v258zM1307 733l269 180l-603 402v-359zM1792 913v-546 q0 -41 -34 -64l-819 -546q-21 -13 -43 -13t-43 13l-819 546q-34 23 -34 64v546q0 41 34 64l819 546q21 13 43 13t43 -13l819 -546q34 -23 34 -64z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1800 764q111 -46 179.5 -145.5t68.5 -221.5q0 -164 -118 -280.5t-285 -116.5q-4 0 -11.5 0.5t-10.5 0.5h-1209h-1h-2h-5q-170 10 -288 125.5t-118 280.5q0 110 55 203t147 147q-12 39 -12 82q0 115 82 196t199 81q95 0 172 -58q75 154 222.5 248t326.5 94 q166 0 306 -80.5t221.5 -218.5t81.5 -301q0 -6 -0.5 -18t-0.5 -18zM468 498q0 -122 84 -193t208 -71q137 0 240 99q-16 20 -47.5 56.5t-43.5 50.5q-67 -65 -144 -65q-55 0 -93.5 33.5t-38.5 87.5q0 53 38.5 87t91.5 34q44 0 84.5 -21t73 -55t65 -75t69 -82t77 -75t97 -55 t121.5 -21q121 0 204.5 71.5t83.5 190.5q0 121 -84 192t-207 71q-143 0 -241 -97q14 -16 29.5 -34t34.5 -40t29 -34q66 64 142 64q52 0 92 -33t40 -84q0 -57 -37 -91.5t-94 -34.5q-43 0 -82.5 21t-72 55t-65.5 75t-69.5 82t-77.5 75t-96.5 55t-118.5 21q-122 0 -207 -70.5 t-85 -189.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M896 1536q182 0 348 -71t286 -191t191 -286t71 -348t-71 -348t-191 -286t-286 -191t-348 -71t-348 71t-286 191t-191 286t-71 348t71 348t191 286t286 191t348 71zM896 1408q-190 0 -361 -90l194 -194q82 28 167 28t167 -28l194 194q-171 90 -361 90zM218 279l194 194 q-28 82 -28 167t28 167l-194 194q-90 -171 -90 -361t90 -361zM896 -128q190 0 361 90l-194 194q-82 -28 -167 -28t-167 28l-194 -194q171 -90 361 -90zM896 256q159 0 271.5 112.5t112.5 271.5t-112.5 271.5t-271.5 112.5t-271.5 -112.5t-112.5 -271.5t112.5 -271.5 t271.5 -112.5zM1380 473l194 -194q90 171 90 361t-90 361l-194 -194q28 -82 28 -167t-28 -167z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1792 640q0 -182 -71 -348t-191 -286t-286 -191t-348 -71t-348 71t-286 191t-191 286t-71 348q0 222 101 414.5t276.5 317t390.5 155.5v-260q-221 -45 -366.5 -221t-145.5 -406q0 -130 51 -248.5t136.5 -204t204 -136.5t248.5 -51t248.5 51t204 136.5t136.5 204t51 248.5 q0 230 -145.5 406t-366.5 221v260q215 -31 390.5 -155.5t276.5 -317t101 -414.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1760 640q0 -176 -68.5 -336t-184 -275.5t-275.5 -184t-336 -68.5t-336 68.5t-275.5 184t-184 275.5t-68.5 336q0 213 97 398.5t265 305.5t374 151v-228q-221 -45 -366.5 -221t-145.5 -406q0 -130 51 -248.5t136.5 -204t204 -136.5t248.5 -51t248.5 51t204 136.5 t136.5 204t51 248.5q0 230 -145.5 406t-366.5 221v228q206 -31 374 -151t265 -305.5t97 -398.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M19 662q8 217 116 406t305 318h5q0 -1 -1 -3q-8 -8 -28 -33.5t-52 -76.5t-60 -110.5t-44.5 -135.5t-14 -150.5t39 -157.5t108.5 -154q50 -50 102 -69.5t90.5 -11.5t69.5 23.5t47 32.5l16 16q39 51 53 116.5t6.5 122.5t-21 107t-26.5 80l-14 29q-10 25 -30.5 49.5t-43 41 t-43.5 29.5t-35 19l-13 6l104 115q39 -17 78 -52t59 -61l19 -27q1 48 -18.5 103.5t-40.5 87.5l-20 31l161 183l160 -181q-33 -46 -52.5 -102.5t-22.5 -90.5l-4 -33q22 37 61.5 72.5t67.5 52.5l28 17l103 -115q-44 -14 -85 -50t-60 -65l-19 -29q-31 -56 -48 -133.5t-7 -170 t57 -156.5q33 -45 77.5 -60.5t85 -5.5t76 26.5t57.5 33.5l21 16q60 53 96.5 115t48.5 121.5t10 121.5t-18 118t-37 107.5t-45.5 93t-45 72t-34.5 47.5l-13 17q-14 13 -7 13l10 -3q40 -29 62.5 -46t62 -50t64 -58t58.5 -65t55.5 -77t45.5 -88t38 -103t23.5 -117t10.5 -136 q3 -259 -108 -465t-312 -321t-456 -115q-185 0 -351 74t-283.5 198t-184 293t-60.5 353z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M874 -102v-66q-208 6 -385 109.5t-283 275.5l58 34q29 -49 73 -99l65 57q148 -168 368 -212l-17 -86q65 -12 121 -13zM276 428l-83 -28q22 -60 49 -112l-57 -33q-98 180 -98 385t98 385l57 -33q-30 -56 -49 -112l82 -28q-35 -100 -35 -212q0 -109 36 -212zM1528 251 l58 -34q-106 -172 -283 -275.5t-385 -109.5v66q56 1 121 13l-17 86q220 44 368 212l65 -57q44 50 73 99zM1377 805l-233 -80q14 -42 14 -85t-14 -85l232 -80q-31 -92 -98 -169l-185 162q-57 -67 -147 -85l48 -241q-52 -10 -98 -10t-98 10l48 241q-90 18 -147 85l-185 -162 q-67 77 -98 169l232 80q-14 42 -14 85t14 85l-233 80q33 93 99 169l185 -162q59 68 147 86l-48 240q44 10 98 10t98 -10l-48 -240q88 -18 147 -86l185 162q66 -76 99 -169zM874 1448v-66q-65 -2 -121 -13l17 -86q-220 -42 -368 -211l-65 56q-38 -42 -73 -98l-57 33 q106 172 282 275.5t385 109.5zM1705 640q0 -205 -98 -385l-57 33q27 52 49 112l-83 28q36 103 36 212q0 112 -35 212l82 28q-19 56 -49 112l57 33q98 -180 98 -385zM1585 1063l-57 -33q-35 56 -73 98l-65 -56q-148 169 -368 211l17 86q-56 11 -121 13v66q209 -6 385 -109.5 t282 -275.5zM1748 640q0 173 -67.5 331t-181.5 272t-272 181.5t-331 67.5t-331 -67.5t-272 -181.5t-181.5 -272t-67.5 -331t67.5 -331t181.5 -272t272 -181.5t331 -67.5t331 67.5t272 181.5t181.5 272t67.5 331zM1792 640q0 -182 -71 -348t-191 -286t-286 -191t-348 -71 t-348 71t-286 191t-191 286t-71 348t71 348t191 286t286 191t348 71t348 -71t286 -191t191 -286t71 -348z" />
|
||||
<glyph unicode="" d="M582 228q0 -66 -93 -66q-107 0 -107 63q0 64 98 64q102 0 102 -61zM546 694q0 -85 -74 -85q-77 0 -77 84q0 90 77 90q36 0 55 -25.5t19 -63.5zM712 769v125q-78 -29 -135 -29q-50 29 -110 29q-86 0 -145 -57t-59 -143q0 -50 29.5 -102t73.5 -67v-3q-38 -17 -38 -85 q0 -53 41 -77v-3q-113 -37 -113 -139q0 -45 20 -78.5t54 -51t72 -25.5t81 -8q224 0 224 188q0 67 -48 99t-126 46q-27 5 -51.5 20.5t-24.5 39.5q0 44 49 52q77 15 122 70t45 134q0 24 -10 52q37 9 49 13zM771 350h137q-2 27 -2 82v387q0 46 2 69h-137q3 -23 3 -71v-392 q0 -50 -3 -75zM1280 366v121q-30 -21 -68 -21q-53 0 -53 82v225h52q9 0 26.5 -1t26.5 -1v117h-105q0 82 3 102h-140q4 -24 4 -55v-47h-60v-117q36 3 37 3q3 0 11 -0.5t12 -0.5v-2h-2v-217q0 -37 2.5 -64t11.5 -56.5t24.5 -48.5t43.5 -31t66 -12q64 0 108 24zM924 1072 q0 36 -24 63.5t-60 27.5t-60.5 -27t-24.5 -64q0 -36 25 -62.5t60 -26.5t59.5 27t24.5 62zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M595 22q0 100 -165 100q-158 0 -158 -104q0 -101 172 -101q151 0 151 105zM536 777q0 61 -30 102t-89 41q-124 0 -124 -145q0 -135 124 -135q119 0 119 137zM805 1101v-202q-36 -12 -79 -22q16 -43 16 -84q0 -127 -73 -216.5t-197 -112.5q-40 -8 -59.5 -27t-19.5 -58 q0 -31 22.5 -51.5t58 -32t78.5 -22t86 -25.5t78.5 -37.5t58 -64t22.5 -98.5q0 -304 -363 -304q-69 0 -130 12.5t-116 41t-87.5 82t-32.5 127.5q0 165 182 225v4q-67 41 -67 126q0 109 63 137v4q-72 24 -119.5 108.5t-47.5 165.5q0 139 95 231.5t235 92.5q96 0 178 -47 q98 0 218 47zM1123 220h-222q4 45 4 134v609q0 94 -4 128h222q-4 -33 -4 -124v-613q0 -89 4 -134zM1724 442v-196q-71 -39 -174 -39q-62 0 -107 20t-70 50t-39.5 78t-18.5 92t-4 103v351h2v4q-7 0 -19 1t-18 1q-21 0 -59 -6v190h96v76q0 54 -6 89h227q-6 -41 -6 -165h171 v-190q-15 0 -43.5 2t-42.5 2h-85v-365q0 -131 87 -131q61 0 109 33zM1148 1389q0 -58 -39 -101.5t-96 -43.5q-58 0 -98 43.5t-40 101.5q0 59 39.5 103t98.5 44q58 0 96.5 -44.5t38.5 -102.5z" />
|
||||
<glyph unicode="" d="M825 547l343 588h-150q-21 -39 -63.5 -118.5t-68 -128.5t-59.5 -118.5t-60 -128.5h-3q-21 48 -44.5 97t-52 105.5t-46.5 92t-54 104.5t-49 95h-150l323 -589v-435h134v436zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960 q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" d="M809 532l266 499h-112l-157 -312q-24 -48 -44 -92l-42 92l-155 312h-120l263 -493v-324h101v318zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1280" d="M842 964q0 -80 -57 -136.5t-136 -56.5q-60 0 -111 35q-62 -67 -115 -146q-247 -371 -202 -859q1 -22 -12.5 -38.5t-34.5 -18.5h-5q-20 0 -35 13.5t-17 33.5q-14 126 -3.5 247.5t29.5 217t54 186t69 155.5t74 125q61 90 132 165q-16 35 -16 77q0 80 56.5 136.5t136.5 56.5 t136.5 -56.5t56.5 -136.5zM1223 953q0 -158 -78 -292t-212.5 -212t-292.5 -78q-64 0 -131 14q-21 5 -32.5 23.5t-6.5 39.5q5 20 23 31.5t39 7.5q51 -13 108 -13q97 0 186 38t153 102t102 153t38 186t-38 186t-102 153t-153 102t-186 38t-186 -38t-153 -102t-102 -153 t-38 -186q0 -114 52 -218q10 -20 3.5 -40t-25.5 -30t-39.5 -3t-30.5 26q-64 123 -64 265q0 119 46.5 227t124.5 186t186 124t226 46q158 0 292.5 -78t212.5 -212.5t78 -292.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M270 730q-8 19 -8 52q0 20 11 49t24 45q-1 22 7.5 53t22.5 43q0 139 92.5 288.5t217.5 209.5q139 66 324 66q133 0 266 -55q49 -21 90 -48t71 -56t55 -68t42 -74t32.5 -84.5t25.5 -89.5t22 -98l1 -5q55 -83 55 -150q0 -14 -9 -40t-9 -38q0 -1 1.5 -3.5t3.5 -5t2 -3.5 q77 -114 120.5 -214.5t43.5 -208.5q0 -43 -19.5 -100t-55.5 -57q-9 0 -19.5 7.5t-19 17.5t-19 26t-16 26.5t-13.5 26t-9 17.5q-1 1 -3 1l-5 -4q-59 -154 -132 -223q20 -20 61.5 -38.5t69 -41.5t35.5 -65q-2 -4 -4 -16t-7 -18q-64 -97 -302 -97q-53 0 -110.5 9t-98 20 t-104.5 30q-15 5 -23 7q-14 4 -46 4.5t-40 1.5q-41 -45 -127.5 -65t-168.5 -20q-35 0 -69 1.5t-93 9t-101 20.5t-74.5 40t-32.5 64q0 40 10 59.5t41 48.5q11 2 40.5 13t49.5 12q4 0 14 2q2 2 2 4l-2 3q-48 11 -108 105.5t-73 156.5l-5 3q-4 0 -12 -20q-18 -41 -54.5 -74.5 t-77.5 -37.5h-1q-4 0 -6 4.5t-5 5.5q-23 54 -23 100q0 275 252 466z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M580 1075q0 41 -25 66t-66 25q-43 0 -76 -25.5t-33 -65.5q0 -39 33 -64.5t76 -25.5q41 0 66 24.5t25 65.5zM1323 568q0 28 -25.5 50t-65.5 22q-27 0 -49.5 -22.5t-22.5 -49.5q0 -28 22.5 -50.5t49.5 -22.5q40 0 65.5 22t25.5 51zM1087 1075q0 41 -24.5 66t-65.5 25 q-43 0 -76 -25.5t-33 -65.5q0 -39 33 -64.5t76 -25.5q41 0 65.5 24.5t24.5 65.5zM1722 568q0 28 -26 50t-65 22q-27 0 -49.5 -22.5t-22.5 -49.5q0 -28 22.5 -50.5t49.5 -22.5q39 0 65 22t26 51zM1456 965q-31 4 -70 4q-169 0 -311 -77t-223.5 -208.5t-81.5 -287.5 q0 -78 23 -152q-35 -3 -68 -3q-26 0 -50 1.5t-55 6.5t-44.5 7t-54.5 10.5t-50 10.5l-253 -127l72 218q-290 203 -290 490q0 169 97.5 311t264 223.5t363.5 81.5q176 0 332.5 -66t262 -182.5t136.5 -260.5zM2048 404q0 -117 -68.5 -223.5t-185.5 -193.5l55 -181l-199 109 q-150 -37 -218 -37q-169 0 -311 70.5t-223.5 191.5t-81.5 264t81.5 264t223.5 191.5t311 70.5q161 0 303 -70.5t227.5 -192t85.5 -263.5z" />
|
||||
|
|
@ -483,13 +483,13 @@
|
|||
<glyph unicode="" horiz-adv-x="2048" d="M1024 1024h-384v-384h384v384zM1152 384v-128h-640v128h640zM1152 1152v-640h-640v640h640zM1792 384v-128h-512v128h512zM1792 640v-128h-512v128h512zM1792 896v-128h-512v128h512zM1792 1152v-128h-512v128h512zM256 192v960h-128v-960q0 -26 19 -45t45 -19t45 19 t19 45zM1920 192v1088h-1536v-1088q0 -33 -11 -64h1483q26 0 45 19t19 45zM2048 1408v-1216q0 -80 -56 -136t-136 -56h-1664q-80 0 -136 56t-56 136v1088h256v128h1792z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1024 13q-20 0 -93 73.5t-73 93.5q0 32 62.5 54t103.5 22t103.5 -22t62.5 -54q0 -20 -73 -93.5t-93 -73.5zM1294 284q-2 0 -40 25t-101.5 50t-128.5 25t-128.5 -25t-101 -50t-40.5 -25q-18 0 -93.5 75t-75.5 93q0 13 10 23q78 77 196 121t233 44t233 -44t196 -121 q10 -10 10 -23q0 -18 -75.5 -93t-93.5 -75zM1567 556q-11 0 -23 8q-136 105 -252 154.5t-268 49.5q-85 0 -170.5 -22t-149 -53t-113.5 -62t-79 -53t-31 -22q-17 0 -92 75t-75 93q0 12 10 22q132 132 320 205t380 73t380 -73t320 -205q10 -10 10 -22q0 -18 -75 -93t-92 -75z M1838 827q-11 0 -22 9q-179 157 -371.5 236.5t-420.5 79.5t-420.5 -79.5t-371.5 -236.5q-11 -9 -22 -9q-17 0 -92.5 75t-75.5 93q0 13 10 23q187 186 445 288t527 102t527 -102t445 -288q10 -10 10 -23q0 -18 -75.5 -93t-92.5 -75z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M384 0q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM768 0q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM384 384q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5 t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM1152 0q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM768 384q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5 t37.5 90.5zM384 768q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM1152 384q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM768 768q0 53 -37.5 90.5t-90.5 37.5 t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM1536 0v384q0 52 -38 90t-90 38t-90 -38t-38 -90v-384q0 -52 38 -90t90 -38t90 38t38 90zM1152 768q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5z M1536 1088v256q0 26 -19 45t-45 19h-1280q-26 0 -45 -19t-19 -45v-256q0 -26 19 -45t45 -19h1280q26 0 45 19t19 45zM1536 768q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM1664 1408v-1536q0 -52 -38 -90t-90 -38 h-1408q-52 0 -90 38t-38 90v1536q0 52 38 90t90 38h1408q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1112 1090q0 159 -237 159h-70q-32 0 -59.5 -21.5t-34.5 -52.5l-63 -276q-2 -5 -2 -16q0 -24 17 -39.5t41 -15.5h53q69 0 128.5 13t112.5 41t83.5 81.5t30.5 126.5zM1716 938q0 -265 -220 -428q-219 -161 -612 -161h-61q-32 0 -59 -21.5t-34 -52.5l-73 -316 q-8 -36 -40.5 -61.5t-69.5 -25.5h-213q-31 0 -53 20t-22 51q0 10 13 65h151q34 0 64 23.5t38 56.5l73 316q8 33 37.5 57t63.5 24h61q390 0 607 160t217 421q0 129 -51 207q183 -92 183 -335zM1533 1123q0 -264 -221 -428q-218 -161 -612 -161h-60q-32 0 -59.5 -22t-34.5 -53 l-73 -315q-8 -36 -40 -61.5t-69 -25.5h-214q-31 0 -52.5 19.5t-21.5 51.5q0 8 2 20l300 1301q8 36 40.5 61.5t69.5 25.5h444q68 0 125 -4t120.5 -15t113.5 -30t96.5 -50.5t77.5 -74t49.5 -103.5t18.5 -136z" />
|
||||
<glyph unicode="" d="M1519 890q18 -84 -4 -204q-87 -444 -565 -444h-44q-25 0 -44 -16.5t-24 -42.5l-4 -19l-55 -346l-2 -15q-5 -26 -24.5 -42.5t-44.5 -16.5h-251q-21 0 -33 15t-9 36q9 56 26.5 168t26.5 168t27 167.5t27 167.5q5 37 43 37h131q133 -2 236 21q175 39 287 144q102 95 155 246 q24 70 35 133q1 6 2.5 7.5t3.5 1t6 -3.5q79 -59 98 -162zM1347 1172q0 -107 -46 -236q-80 -233 -302 -315q-113 -40 -252 -42q0 -1 -90 -1l-90 1q-100 0 -118 -96q-2 -8 -85 -530q-1 -10 -12 -10h-295q-22 0 -36.5 16.5t-11.5 38.5l232 1471q5 29 27.5 48t51.5 19h598 q34 0 97.5 -13t111.5 -32q107 -41 163.5 -123t56.5 -196z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M602 949q19 -61 31 -123.5t17 -141.5t-14 -159t-62 -145q-21 81 -67 157t-95.5 127t-99 90.5t-78.5 57.5t-33 19q-62 34 -81.5 100t14.5 128t101 81.5t129 -14.5q138 -83 238 -177zM927 1236q11 -25 20.5 -46t36.5 -100.5t42.5 -150.5t25.5 -179.5t0 -205.5t-47.5 -209.5 t-105.5 -208.5q-51 -72 -138 -72q-54 0 -98 31q-57 40 -69 109t28 127q60 85 81 195t13 199.5t-32 180.5t-39 128t-22 52q-31 63 -8.5 129.5t85.5 97.5q34 17 75 17q47 0 88.5 -25t63.5 -69zM1248 567q-17 -160 -72 -311q-17 131 -63 246q25 174 -5 361q-27 178 -94 342 q114 -90 212 -211q9 -37 15 -80q26 -179 7 -347zM1520 1440q9 -17 23.5 -49.5t43.5 -117.5t50.5 -178t34 -227.5t5 -269t-47 -300t-112.5 -323.5q-22 -48 -66 -75.5t-95 -27.5q-39 0 -74 16q-67 31 -92.5 100t4.5 136q58 126 90 257.5t37.5 239.5t-3.5 213.5t-26.5 180.5 t-38.5 138.5t-32.5 90t-15.5 32.5q-34 65 -11.5 135.5t87.5 104.5q37 20 81 20q49 0 91.5 -25.5t66.5 -70.5z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M1975 546h-138q14 37 66 179l3 9q4 10 10 26t9 26l12 -55zM531 611l-58 295q-11 54 -75 54h-268l-2 -13q311 -79 403 -336zM710 960l-162 -438l-17 89q-26 70 -85 129.5t-131 88.5l135 -510h175l261 641h-176zM849 318h166l104 642h-166zM1617 944q-69 27 -149 27 q-123 0 -201 -59t-79 -153q-1 -102 145 -174q48 -23 67 -41t19 -39q0 -30 -30 -46t-69 -16q-86 0 -156 33l-22 11l-23 -144q74 -34 185 -34q130 -1 208.5 59t80.5 160q0 106 -140 174q-49 25 -71 42t-22 38q0 22 24.5 38.5t70.5 16.5q70 1 124 -24l15 -8zM2042 960h-128 q-65 0 -87 -54l-246 -588h174l35 96h212q5 -22 20 -96h154zM2304 1280v-1280q0 -52 -38 -90t-90 -38h-2048q-52 0 -90 38t-38 90v1280q0 52 38 90t90 38h2048q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M671 603h-13q-47 0 -47 -32q0 -22 20 -22q17 0 28 15t12 39zM1066 639h62v3q1 4 0.5 6.5t-1 7t-2 8t-4.5 6.5t-7.5 5t-11.5 2q-28 0 -36 -38zM1606 603h-12q-48 0 -48 -32q0 -22 20 -22q17 0 28 15t12 39zM1925 629q0 41 -30 41q-19 0 -31 -20t-12 -51q0 -42 28 -42 q20 0 32.5 20t12.5 52zM480 770h87l-44 -262h-56l32 201l-71 -201h-39l-4 200l-34 -200h-53l44 262h81l2 -163zM733 663q0 -6 -4 -42q-16 -101 -17 -113h-47l1 22q-20 -26 -58 -26q-23 0 -37.5 16t-14.5 42q0 39 26 60.5t73 21.5q14 0 23 -1q0 3 0.5 5.5t1 4.5t0.5 3 q0 20 -36 20q-29 0 -59 -10q0 4 7 48q38 11 67 11q74 0 74 -62zM889 721l-8 -49q-22 3 -41 3q-27 0 -27 -17q0 -8 4.5 -12t21.5 -11q40 -19 40 -60q0 -72 -87 -71q-34 0 -58 6q0 2 7 49q29 -8 51 -8q32 0 32 19q0 7 -4.5 11.5t-21.5 12.5q-43 20 -43 59q0 72 84 72 q30 0 50 -4zM977 721h28l-7 -52h-29q-2 -17 -6.5 -40.5t-7 -38.5t-2.5 -18q0 -16 19 -16q8 0 16 2l-8 -47q-21 -7 -40 -7q-43 0 -45 47q0 12 8 56q3 20 25 146h55zM1180 648q0 -23 -7 -52h-111q-3 -22 10 -33t38 -11q30 0 58 14l-9 -54q-30 -8 -57 -8q-95 0 -95 95 q0 55 27.5 90.5t69.5 35.5q35 0 55.5 -21t20.5 -56zM1319 722q-13 -23 -22 -62q-22 2 -31 -24t-25 -128h-56l3 14q22 130 29 199h51l-3 -33q14 21 25.5 29.5t28.5 4.5zM1506 763l-9 -57q-28 14 -50 14q-31 0 -51 -27.5t-20 -70.5q0 -30 13.5 -47t38.5 -17q21 0 48 13 l-10 -59q-28 -8 -50 -8q-45 0 -71.5 30.5t-26.5 82.5q0 70 35.5 114.5t91.5 44.5q26 0 61 -13zM1668 663q0 -18 -4 -42q-13 -79 -17 -113h-46l1 22q-20 -26 -59 -26q-23 0 -37 16t-14 42q0 39 25.5 60.5t72.5 21.5q15 0 23 -1q2 7 2 13q0 20 -36 20q-29 0 -59 -10q0 4 8 48 q38 11 67 11q73 0 73 -62zM1809 722q-14 -24 -21 -62q-23 2 -31.5 -23t-25.5 -129h-56l3 14q19 104 29 199h52q0 -11 -4 -33q15 21 26.5 29.5t27.5 4.5zM1950 770h56l-43 -262h-53l3 19q-23 -23 -52 -23q-31 0 -49.5 24t-18.5 64q0 53 27.5 92t64.5 39q31 0 53 -29z M2061 640q0 148 -72.5 273t-198 198t-273.5 73q-181 0 -328 -110q127 -116 171 -284h-50q-44 150 -158 253q-114 -103 -158 -253h-50q44 168 171 284q-147 110 -328 110q-148 0 -273.5 -73t-198 -198t-72.5 -273t72.5 -273t198 -198t273.5 -73q181 0 328 110 q-120 111 -165 264h50q46 -138 152 -233q106 95 152 233h50q-45 -153 -165 -264q147 -110 328 -110q148 0 273.5 73t198 198t72.5 273zM2304 1280v-1280q0 -52 -38 -90t-90 -38h-2048q-52 0 -90 38t-38 90v1280q0 52 38 90t90 38h2048q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M313 759q0 -51 -36 -84q-29 -26 -89 -26h-17v220h17q61 0 89 -27q36 -31 36 -83zM2089 824q0 -52 -64 -52h-19v101h20q63 0 63 -49zM380 759q0 74 -50 120.5t-129 46.5h-95v-333h95q74 0 119 38q60 51 60 128zM410 593h65v333h-65v-333zM730 694q0 40 -20.5 62t-75.5 42 q-29 10 -39.5 19t-10.5 23q0 16 13.5 26.5t34.5 10.5q29 0 53 -27l34 44q-41 37 -98 37q-44 0 -74 -27.5t-30 -67.5q0 -35 18 -55.5t64 -36.5q37 -13 45 -19q19 -12 19 -34q0 -20 -14 -33.5t-36 -13.5q-48 0 -71 44l-42 -40q44 -64 115 -64q51 0 83 30.5t32 79.5zM1008 604 v77q-37 -37 -78 -37q-49 0 -80.5 32.5t-31.5 82.5q0 48 31.5 81.5t77.5 33.5q43 0 81 -38v77q-40 20 -80 20q-74 0 -125.5 -50.5t-51.5 -123.5t51 -123.5t125 -50.5q42 0 81 19zM2240 0v527q-65 -40 -144.5 -84t-237.5 -117t-329.5 -137.5t-417.5 -134.5t-504 -118h1569 q26 0 45 19t19 45zM1389 757q0 75 -53 128t-128 53t-128 -53t-53 -128t53 -128t128 -53t128 53t53 128zM1541 584l144 342h-71l-90 -224l-89 224h-71l142 -342h35zM1714 593h184v56h-119v90h115v56h-115v74h119v57h-184v-333zM2105 593h80l-105 140q76 16 76 94q0 47 -31 73 t-87 26h-97v-333h65v133h9zM2304 1274v-1268q0 -56 -38.5 -95t-93.5 -39h-2040q-55 0 -93.5 39t-38.5 95v1268q0 56 38.5 95t93.5 39h2040q55 0 93.5 -39t38.5 -95z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M119 854h89l-45 108zM740 328l74 79l-70 79h-163v-49h142v-55h-142v-54h159zM898 406l99 -110v217zM1186 453q0 33 -40 33h-84v-69h83q41 0 41 36zM1475 457q0 29 -42 29h-82v-61h81q43 0 43 32zM1197 923q0 29 -42 29h-82v-60h81q43 0 43 31zM1656 854h89l-44 108z M699 1009v-271h-66v212l-94 -212h-57l-94 212v-212h-132l-25 60h-135l-25 -60h-70l116 271h96l110 -257v257h106l85 -184l77 184h108zM1255 453q0 -20 -5.5 -35t-14 -25t-22.5 -16.5t-26 -10t-31.5 -4.5t-31.5 -1t-32.5 0.5t-29.5 0.5v-91h-126l-80 90l-83 -90h-256v271h260 l80 -89l82 89h207q109 0 109 -89zM964 794v-56h-217v271h217v-57h-152v-49h148v-55h-148v-54h152zM2304 235v-229q0 -55 -38.5 -94.5t-93.5 -39.5h-2040q-55 0 -93.5 39.5t-38.5 94.5v678h111l25 61h55l25 -61h218v46l19 -46h113l20 47v-47h541v99l10 1q10 0 10 -14v-86h279 v23q23 -12 55 -18t52.5 -6.5t63 0.5t51.5 1l25 61h56l25 -61h227v58l34 -58h182v378h-180v-44l-25 44h-185v-44l-23 44h-249q-69 0 -109 -22v22h-172v-22q-24 22 -73 22h-628l-43 -97l-43 97h-198v-44l-22 44h-169l-78 -179v391q0 55 38.5 94.5t93.5 39.5h2040 q55 0 93.5 -39.5t38.5 -94.5v-678h-120q-51 0 -81 -22v22h-177q-55 0 -78 -22v22h-316v-22q-31 22 -87 22h-209v-22q-23 22 -91 22h-234l-54 -58l-50 58h-349v-378h343l55 59l52 -59h211v89h21q59 0 90 13v-102h174v99h8q8 0 10 -2t2 -10v-87h529q57 0 88 24v-24h168 q60 0 95 17zM1546 469q0 -23 -12 -43t-34 -29q25 -9 34 -26t9 -46v-54h-65v45q0 33 -12 43.5t-46 10.5h-69v-99h-65v271h154q48 0 77 -15t29 -58zM1269 936q0 -24 -12.5 -44t-33.5 -29q26 -9 34.5 -25.5t8.5 -46.5v-53h-65q0 9 0.5 26.5t0 25t-3 18.5t-8.5 16t-17.5 8.5 t-29.5 3.5h-70v-98h-64v271l153 -1q49 0 78 -14.5t29 -57.5zM1798 327v-56h-216v271h216v-56h-151v-49h148v-55h-148v-54zM1372 1009v-271h-66v271h66zM2065 357q0 -86 -102 -86h-126v58h126q34 0 34 25q0 16 -17 21t-41.5 5t-49.5 3.5t-42 22.5t-17 55q0 39 26 60t66 21 h130v-57h-119q-36 0 -36 -25q0 -16 17.5 -20.5t42 -4t49 -2.5t42 -21.5t17.5 -54.5zM2304 407v-101q-24 -35 -88 -35h-125v58h125q33 0 33 25q0 13 -12.5 19t-31 5.5t-40 2t-40 8t-31 24t-12.5 48.5q0 39 26.5 60t66.5 21h129v-57h-118q-36 0 -36 -25q0 -20 29 -22t68.5 -5 t56.5 -26zM2139 1008v-270h-92l-122 203v-203h-132l-26 60h-134l-25 -60h-75q-129 0 -129 133q0 138 133 138h63v-59q-7 0 -28 1t-28.5 0.5t-23 -2t-21.5 -6.5t-14.5 -13.5t-11.5 -23t-3 -33.5q0 -38 13.5 -58t49.5 -20h29l92 213h97l109 -256v256h99l114 -188v188h66z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M322 689h-15q-19 0 -19 18q0 28 19 85q5 15 15 19.5t28 4.5q77 0 77 -49q0 -41 -30.5 -59.5t-74.5 -18.5zM664 528q-47 0 -47 29q0 62 123 62l3 -3q-5 -88 -79 -88zM1438 687h-15q-19 0 -19 19q0 28 19 85q5 15 14.5 19t28.5 4q77 0 77 -49q0 -41 -30.5 -59.5 t-74.5 -18.5zM1780 527q-47 0 -47 30q0 62 123 62l3 -3q-5 -89 -79 -89zM373 894h-128q-8 0 -14.5 -4t-8.5 -7.5t-7 -12.5q-3 -7 -45 -190t-42 -192q0 -7 5.5 -12.5t13.5 -5.5h62q25 0 32.5 34.5l15 69t32.5 34.5q47 0 87.5 7.5t80.5 24.5t63.5 52.5t23.5 84.5 q0 36 -14.5 61t-41 36.5t-53.5 15.5t-62 4zM719 798q-38 0 -74 -6q-2 0 -8.5 -1t-9 -1.5l-7.5 -1.5t-7.5 -2t-6.5 -3t-6.5 -4t-5 -5t-4.5 -7t-4 -9q-9 -29 -9 -39t9 -10q5 0 21.5 5t19.5 6q30 8 58 8q74 0 74 -36q0 -11 -10 -14q-8 -2 -18 -3t-21.5 -1.5t-17.5 -1.5 q-38 -4 -64.5 -10t-56.5 -19.5t-45.5 -39t-15.5 -62.5q0 -38 26 -59.5t64 -21.5q24 0 45.5 6.5t33 13t38.5 23.5q-3 -7 -3 -15t5.5 -13.5t12.5 -5.5h56q1 1 7 3.5t7.5 3.5t5 3.5t5 5.5t2.5 8l45 194q4 13 4 30q0 81 -145 81zM1247 793h-74q-22 0 -39 -23q-5 -7 -29.5 -51 t-46.5 -81.5t-26 -38.5l-5 4q0 77 -27 166q-1 5 -3.5 8.5t-6 6.5t-6.5 5t-8.5 3t-8.5 1.5t-9.5 1t-9 0.5h-10h-8.5q-38 0 -38 -21l1 -5q5 -53 25 -151t25 -143q2 -16 2 -24q0 -19 -30.5 -61.5t-30.5 -58.5q0 -13 40 -13q61 0 76 25l245 415q10 20 10 26q0 9 -8 9zM1489 892 h-129q-18 0 -29 -23q-6 -13 -46.5 -191.5t-40.5 -190.5q0 -20 43 -20h7.5h9h9t9.5 1t8.5 2t8.5 3t6.5 4.5t5.5 6t3 8.5l21 91q2 10 10.5 17t19.5 7q47 0 87.5 7t80.5 24.5t63.5 52.5t23.5 84q0 36 -14.5 61t-41 36.5t-53.5 15.5t-62 4zM1835 798q-26 0 -74 -6 q-38 -6 -48 -16q-7 -8 -11 -19q-8 -24 -8 -39q0 -10 8 -10q1 0 41 12q30 8 58 8q74 0 74 -36q0 -12 -10 -14q-4 -1 -57 -7q-38 -4 -64.5 -10t-56.5 -19.5t-45.5 -39t-15.5 -62.5t26 -58.5t64 -21.5q24 0 45 6t34 13t38 24q-3 -15 -3 -16q0 -5 2 -8.5t6.5 -5.5t8 -3.5 t10.5 -2t9.5 -0.5h9.5h8q42 0 48 25l45 194q3 15 3 31q0 81 -145 81zM2157 889h-55q-25 0 -33 -40q-10 -44 -36.5 -167t-42.5 -190v-5q0 -16 16 -18h1h57q10 0 18.5 6.5t10.5 16.5l83 374h-1l1 5q0 7 -5.5 12.5t-13.5 5.5zM2304 1280v-1280q0 -52 -38 -90t-90 -38h-2048 q-52 0 -90 38t-38 90v1280q0 52 38 90t90 38h2048q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M745 630q0 -37 -25.5 -61.5t-62.5 -24.5q-29 0 -46.5 16t-17.5 44q0 37 25 62.5t62 25.5q28 0 46.5 -16.5t18.5 -45.5zM1530 779q0 -42 -22 -57t-66 -15l-32 -1l17 107q2 11 13 11h18q22 0 35 -2t25 -12.5t12 -30.5zM1881 630q0 -36 -25.5 -61t-61.5 -25q-29 0 -47 16 t-18 44q0 37 25 62.5t62 25.5q28 0 46.5 -16.5t18.5 -45.5zM513 801q0 59 -38.5 85.5t-100.5 26.5h-160q-19 0 -21 -19l-65 -408q-1 -6 3 -11t10 -5h76q20 0 22 19l18 110q1 8 7 13t15 6.5t17 1.5t19 -1t14 -1q86 0 135 48.5t49 134.5zM822 489l41 261q1 6 -3 11t-10 5h-76 q-14 0 -17 -33q-27 40 -95 40q-72 0 -122.5 -54t-50.5 -127q0 -59 34.5 -94t92.5 -35q28 0 58 12t48 32q-4 -12 -4 -21q0 -16 13 -16h69q19 0 22 19zM1269 752q0 5 -4 9.5t-9 4.5h-77q-11 0 -18 -10l-106 -156l-44 150q-5 16 -22 16h-75q-5 0 -9 -4.5t-4 -9.5q0 -2 19.5 -59 t42 -123t23.5 -70q-82 -112 -82 -120q0 -13 13 -13h77q11 0 18 10l255 368q2 2 2 7zM1649 801q0 59 -38.5 85.5t-100.5 26.5h-159q-20 0 -22 -19l-65 -408q-1 -6 3 -11t10 -5h82q12 0 16 13l18 116q1 8 7 13t15 6.5t17 1.5t19 -1t14 -1q86 0 135 48.5t49 134.5zM1958 489 l41 261q1 6 -3 11t-10 5h-76q-14 0 -17 -33q-26 40 -95 40q-72 0 -122.5 -54t-50.5 -127q0 -59 34.5 -94t92.5 -35q29 0 59 12t47 32q0 -1 -2 -9t-2 -12q0 -16 13 -16h69q19 0 22 19zM2176 898v1q0 14 -13 14h-74q-11 0 -13 -11l-65 -416l-1 -2q0 -5 4 -9.5t10 -4.5h66 q19 0 21 19zM392 764q-5 -35 -26 -46t-60 -11l-33 -1l17 107q2 11 13 11h19q40 0 58 -11.5t12 -48.5zM2304 1280v-1280q0 -52 -38 -90t-90 -38h-2048q-52 0 -90 38t-38 90v1280q0 52 38 90t90 38h2048q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M1597 633q0 -69 -21 -106q-19 -35 -52 -35q-23 0 -41 9v224q29 30 57 30q57 0 57 -122zM2035 669h-110q6 98 56 98q51 0 54 -98zM476 534q0 59 -33 91.5t-101 57.5q-36 13 -52 24t-16 25q0 26 38 26q58 0 124 -33l18 112q-67 32 -149 32q-77 0 -123 -38q-48 -39 -48 -109 q0 -58 32.5 -90.5t99.5 -56.5q39 -14 54.5 -25.5t15.5 -27.5q0 -31 -48 -31q-29 0 -70 12.5t-72 30.5l-18 -113q72 -41 168 -41q81 0 129 37q51 41 51 117zM771 749l19 111h-96v135l-129 -21l-18 -114l-46 -8l-17 -103h62v-219q0 -84 44 -120q38 -30 111 -30q32 0 79 11v118 q-32 -7 -44 -7q-42 0 -42 50v197h77zM1087 724v139q-15 3 -28 3q-32 0 -55.5 -16t-33.5 -46l-10 56h-131v-471h150v306q26 31 82 31q16 0 26 -2zM1124 389h150v471h-150v-471zM1746 638q0 122 -45 179q-40 52 -111 52q-64 0 -117 -56l-8 47h-132v-645l150 25v151 q36 -11 68 -11q83 0 134 56q61 65 61 202zM1278 986q0 33 -23 56t-56 23t-56 -23t-23 -56t23 -56.5t56 -23.5t56 23.5t23 56.5zM2176 629q0 113 -48 176q-50 64 -144 64q-96 0 -151.5 -66t-55.5 -180q0 -128 63 -188q55 -55 161 -55q101 0 160 40l-16 103q-57 -31 -128 -31 q-43 0 -63 19q-23 19 -28 66h248q2 14 2 52zM2304 1280v-1280q0 -52 -38 -90t-90 -38h-2048q-52 0 -90 38t-38 90v1280q0 52 38 90t90 38h2048q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1558 684q61 -356 298 -556q0 -52 -38 -90t-90 -38h-448q0 -106 -75 -181t-181 -75t-180.5 74.5t-75.5 180.5zM1024 -176q16 0 16 16t-16 16q-59 0 -101.5 42.5t-42.5 101.5q0 16 -16 16t-16 -16q0 -73 51.5 -124.5t124.5 -51.5zM2026 1424q8 -10 7.5 -23.5t-10.5 -22.5 l-1872 -1622q-10 -8 -23.5 -7t-21.5 11l-84 96q-8 10 -7.5 23.5t10.5 21.5l186 161q-19 32 -19 66q50 42 91 88t85 119.5t74.5 158.5t50 206t19.5 260q0 152 117 282.5t307 158.5q-8 19 -8 39q0 40 28 68t68 28t68 -28t28 -68q0 -20 -8 -39q124 -18 219 -82.5t148 -157.5 l418 363q10 8 23.5 7t21.5 -11z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1040 -160q0 16 -16 16q-59 0 -101.5 42.5t-42.5 101.5q0 16 -16 16t-16 -16q0 -73 51.5 -124.5t124.5 -51.5q16 0 16 16zM503 315l877 760q-42 88 -132.5 146.5t-223.5 58.5q-93 0 -169.5 -31.5t-121.5 -80.5t-69 -103t-24 -105q0 -384 -137 -645zM1856 128 q0 -52 -38 -90t-90 -38h-448q0 -106 -75 -181t-181 -75t-180.5 74.5t-75.5 180.5l149 129h757q-166 187 -227 459l111 97q61 -356 298 -556zM1942 1520l84 -96q8 -10 7.5 -23.5t-10.5 -22.5l-1872 -1622q-10 -8 -23.5 -7t-21.5 11l-84 96q-8 10 -7.5 23.5t10.5 21.5l186 161 q-19 32 -19 66q50 42 91 88t85 119.5t74.5 158.5t50 206t19.5 260q0 152 117 282.5t307 158.5q-8 19 -8 39q0 40 28 68t68 28t68 -28t28 -68q0 -20 -8 -39q124 -18 219 -82.5t148 -157.5l418 363q10 8 23.5 7t21.5 -11z" />
|
||||
|
|
@ -513,8 +513,143 @@
|
|||
<glyph unicode="" horiz-adv-x="2048" d="M785 528h207q-14 -158 -98.5 -248.5t-214.5 -90.5q-162 0 -254.5 116t-92.5 316q0 194 93 311.5t233 117.5q148 0 232 -87t97 -247h-203q-5 64 -35.5 99t-81.5 35q-57 0 -88.5 -60.5t-31.5 -177.5q0 -48 5 -84t18 -69.5t40 -51.5t66 -18q95 0 109 139zM1497 528h206 q-14 -158 -98 -248.5t-214 -90.5q-162 0 -254.5 116t-92.5 316q0 194 93 311.5t233 117.5q148 0 232 -87t97 -247h-204q-4 64 -35 99t-81 35q-57 0 -88.5 -60.5t-31.5 -177.5q0 -48 5 -84t18 -69.5t39.5 -51.5t65.5 -18q49 0 76.5 38t33.5 101zM1856 647q0 207 -15.5 307 t-60.5 161q-6 8 -13.5 14t-21.5 15t-16 11q-86 63 -697 63q-625 0 -710 -63q-5 -4 -17.5 -11.5t-21 -14t-14.5 -14.5q-45 -60 -60 -159.5t-15 -308.5q0 -208 15 -307.5t60 -160.5q6 -8 15 -15t20.5 -14t17.5 -12q44 -33 239.5 -49t470.5 -16q610 0 697 65q5 4 17 11t20.5 14 t13.5 16q46 60 61 159t15 309zM2048 1408v-1536h-2048v1536h2048z" />
|
||||
<glyph unicode="" d="M992 912v-496q0 -14 -9 -23t-23 -9h-160q-14 0 -23 9t-9 23v496q0 112 -80 192t-192 80h-272v-1152q0 -14 -9 -23t-23 -9h-160q-14 0 -23 9t-9 23v1344q0 14 9 23t23 9h464q135 0 249 -66.5t180.5 -180.5t66.5 -249zM1376 1376v-880q0 -135 -66.5 -249t-180.5 -180.5 t-249 -66.5h-464q-14 0 -23 9t-9 23v960q0 14 9 23t23 9h160q14 0 23 -9t9 -23v-768h272q112 0 192 80t80 192v880q0 14 9 23t23 9h160q14 0 23 -9t9 -23z" />
|
||||
<glyph unicode="" d="M1311 694v-114q0 -24 -13.5 -38t-37.5 -14h-202q-24 0 -38 14t-14 38v114q0 24 14 38t38 14h202q24 0 37.5 -14t13.5 -38zM821 464v250q0 53 -32.5 85.5t-85.5 32.5h-133q-68 0 -96 -52q-28 52 -96 52h-130q-53 0 -85.5 -32.5t-32.5 -85.5v-250q0 -22 21 -22h55 q22 0 22 22v230q0 24 13.5 38t38.5 14h94q24 0 38 -14t14 -38v-230q0 -22 21 -22h54q22 0 22 22v230q0 24 14 38t38 14h97q24 0 37.5 -14t13.5 -38v-230q0 -22 22 -22h55q21 0 21 22zM1410 560v154q0 53 -33 85.5t-86 32.5h-264q-53 0 -86 -32.5t-33 -85.5v-410 q0 -21 22 -21h55q21 0 21 21v180q31 -42 94 -42h191q53 0 86 32.5t33 85.5zM1536 1176v-1072q0 -96 -68 -164t-164 -68h-1072q-96 0 -164 68t-68 164v1072q0 96 68 164t164 68h1072q96 0 164 -68t68 -164z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" d="M915 450h-294l147 551zM1001 128h311l-324 1024h-440l-324 -1024h311l383 314zM1536 1120v-960q0 -118 -85 -203t-203 -85h-960q-118 0 -203 85t-85 203v960q0 118 85 203t203 85h960q118 0 203 -85t85 -203z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M2048 641q0 -21 -13 -36.5t-33 -19.5l-205 -356q3 -9 3 -18q0 -20 -12.5 -35.5t-32.5 -19.5l-193 -337q3 -8 3 -16q0 -23 -16.5 -40t-40.5 -17q-25 0 -41 18h-400q-17 -20 -43 -20t-43 20h-399q-17 -20 -43 -20q-23 0 -40 16.5t-17 40.5q0 8 4 20l-193 335 q-20 4 -32.5 19.5t-12.5 35.5q0 9 3 18l-206 356q-20 5 -32.5 20.5t-12.5 35.5q0 21 13.5 36.5t33.5 19.5l199 344q0 1 -0.5 3t-0.5 3q0 36 34 51l209 363q-4 10 -4 18q0 24 17 40.5t40 16.5q26 0 44 -21h396q16 21 43 21t43 -21h398q18 21 44 21q23 0 40 -16.5t17 -40.5 q0 -6 -4 -18l207 -358q23 -1 39 -17.5t16 -38.5q0 -13 -7 -27l187 -324q19 -4 31.5 -19.5t12.5 -35.5zM1063 -158h389l-342 354h-143l-342 -354h360q18 16 39 16t39 -16zM112 654q1 -4 1 -13q0 -10 -2 -15l208 -360q2 0 4.5 -1t5.5 -2.5l5 -2.5l188 199v347l-187 194 q-13 -8 -29 -10zM986 1438h-388l190 -200l554 200h-280q-16 -16 -38 -16t-38 16zM1689 226q1 6 5 11l-64 68l-17 -79h76zM1583 226l22 105l-252 266l-296 -307l63 -64h463zM1495 -142l16 28l65 310h-427l333 -343q8 4 13 5zM578 -158h5l342 354h-373v-335l4 -6q14 -5 22 -13 zM552 226h402l64 66l-309 321l-157 -166v-221zM359 226h163v189l-168 -177q4 -8 5 -12zM358 1051q0 -1 0.5 -2t0.5 -2q0 -16 -8 -29l171 -177v269zM552 1121v-311l153 -157l297 314l-223 236zM556 1425l-4 -8v-264l205 74l-191 201q-6 -2 -10 -3zM1447 1438h-16l-621 -224 l213 -225zM1023 946l-297 -315l311 -319l296 307zM688 634l-136 141v-284zM1038 270l-42 -44h85zM1374 618l238 -251l132 624l-3 5l-1 1zM1718 1018q-8 13 -8 29v2l-216 376q-5 1 -13 5l-437 -463l310 -327zM522 1142v223l-163 -282zM522 196h-163l163 -283v283zM1607 196 l-48 -227l130 227h-82zM1729 266l207 361q-2 10 -2 14q0 1 3 16l-171 296l-129 -612l77 -82q5 3 15 7z" />
|
||||
<glyph unicode="" d="M0 856q0 131 91.5 226.5t222.5 95.5h742l352 358v-1470q0 -132 -91.5 -227t-222.5 -95h-780q-131 0 -222.5 95t-91.5 227v790zM1232 102l-176 180v425q0 46 -32 79t-78 33h-484q-46 0 -78 -33t-32 -79v-492q0 -46 32.5 -79.5t77.5 -33.5h770z" />
|
||||
<glyph unicode="" d="M934 1386q-317 -121 -556 -362.5t-358 -560.5q-20 89 -20 176q0 208 102.5 384.5t278.5 279t384 102.5q82 0 169 -19zM1203 1267q93 -65 164 -155q-389 -113 -674.5 -400.5t-396.5 -676.5q-93 72 -155 162q112 386 395 671t667 399zM470 -67q115 356 379.5 622t619.5 384 q40 -92 54 -195q-292 -120 -516 -345t-343 -518q-103 14 -194 52zM1536 -125q-193 50 -367 115q-135 -84 -290 -107q109 205 274 370.5t369 275.5q-21 -152 -101 -284q65 -175 115 -370z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1893 1144l155 -1272q-131 0 -257 57q-200 91 -393 91q-226 0 -374 -148q-148 148 -374 148q-193 0 -393 -91q-128 -57 -252 -57h-5l155 1272q224 127 482 127q233 0 387 -106q154 106 387 106q258 0 482 -127zM1398 157q129 0 232 -28.5t260 -93.5l-124 1021 q-171 78 -368 78q-224 0 -374 -141q-150 141 -374 141q-197 0 -368 -78l-124 -1021q105 43 165.5 65t148.5 39.5t178 17.5q202 0 374 -108q172 108 374 108zM1438 191l-55 907q-211 -4 -359 -155q-152 155 -374 155q-176 0 -336 -66l-114 -941q124 51 228.5 76t221.5 25 q209 0 374 -102q172 107 374 102z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1500 165v733q0 21 -15 36t-35 15h-93q-20 0 -35 -15t-15 -36v-733q0 -20 15 -35t35 -15h93q20 0 35 15t15 35zM1216 165v531q0 20 -15 35t-35 15h-101q-20 0 -35 -15t-15 -35v-531q0 -20 15 -35t35 -15h101q20 0 35 15t15 35zM924 165v429q0 20 -15 35t-35 15h-101 q-20 0 -35 -15t-15 -35v-429q0 -20 15 -35t35 -15h101q20 0 35 15t15 35zM632 165v362q0 20 -15 35t-35 15h-101q-20 0 -35 -15t-15 -35v-362q0 -20 15 -35t35 -15h101q20 0 35 15t15 35zM2048 311q0 -166 -118 -284t-284 -118h-1244q-166 0 -284 118t-118 284 q0 116 63 214.5t168 148.5q-10 34 -10 73q0 113 80.5 193.5t193.5 80.5q102 0 180 -67q45 183 194 300t338 117q149 0 275 -73.5t199.5 -199.5t73.5 -275q0 -66 -14 -122q135 -33 221 -142.5t86 -247.5z" />
|
||||
<glyph unicode="" d="M0 1536h1536v-1392l-776 -338l-760 338v1392zM1436 209v926h-1336v-926l661 -294zM1436 1235v201h-1336v-201h1336zM181 937v-115h-37v115h37zM181 789v-115h-37v115h37zM181 641v-115h-37v115h37zM181 493v-115h-37v115h37zM181 345v-115h-37v115h37zM207 202l15 34 l105 -47l-15 -33zM343 142l15 34l105 -46l-15 -34zM478 82l15 34l105 -46l-15 -34zM614 23l15 33l104 -46l-15 -34zM797 10l105 46l15 -33l-105 -47zM932 70l105 46l15 -34l-105 -46zM1068 130l105 46l15 -34l-105 -46zM1203 189l105 47l15 -34l-105 -46zM259 1389v-36h-114 v36h114zM421 1389v-36h-115v36h115zM583 1389v-36h-115v36h115zM744 1389v-36h-114v36h114zM906 1389v-36h-114v36h114zM1068 1389v-36h-115v36h115zM1230 1389v-36h-115v36h115zM1391 1389v-36h-114v36h114zM181 1049v-79h-37v115h115v-36h-78zM421 1085v-36h-115v36h115z M583 1085v-36h-115v36h115zM744 1085v-36h-114v36h114zM906 1085v-36h-114v36h114zM1068 1085v-36h-115v36h115zM1230 1085v-36h-115v36h115zM1355 970v79h-78v36h115v-115h-37zM1355 822v115h37v-115h-37zM1355 674v115h37v-115h-37zM1355 526v115h37v-115h-37zM1355 378 v115h37v-115h-37zM1355 230v115h37v-115h-37zM760 265q-129 0 -221 91.5t-92 221.5q0 129 92 221t221 92q130 0 221.5 -92t91.5 -221q0 -130 -91.5 -221.5t-221.5 -91.5zM595 646q0 -36 19.5 -56.5t49.5 -25t64 -7t64 -2t49.5 -9t19.5 -30.5q0 -49 -112 -49q-97 0 -123 51 h-3l-31 -63q67 -42 162 -42q29 0 56.5 5t55.5 16t45.5 33t17.5 53q0 46 -27.5 69.5t-67.5 27t-79.5 3t-67 5t-27.5 25.5q0 21 20.5 33t40.5 15t41 3q34 0 70.5 -11t51.5 -34h3l30 58q-3 1 -21 8.5t-22.5 9t-19.5 7t-22 7t-20 4.5t-24 4t-23 1q-29 0 -56.5 -5t-54 -16.5 t-43 -34t-16.5 -53.5z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M863 504q0 112 -79.5 191.5t-191.5 79.5t-191 -79.5t-79 -191.5t79 -191t191 -79t191.5 79t79.5 191zM1726 505q0 112 -79 191t-191 79t-191.5 -79t-79.5 -191q0 -113 79.5 -192t191.5 -79t191 79.5t79 191.5zM2048 1314v-1348q0 -44 -31.5 -75.5t-76.5 -31.5h-1832 q-45 0 -76.5 31.5t-31.5 75.5v1348q0 44 31.5 75.5t76.5 31.5h431q44 0 76 -31.5t32 -75.5v-161h754v161q0 44 32 75.5t76 31.5h431q45 0 76.5 -31.5t31.5 -75.5z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1430 953zM1690 749q148 0 253 -98.5t105 -244.5q0 -157 -109 -261.5t-267 -104.5q-85 0 -162 27.5t-138 73.5t-118 106t-109 126.5t-103.5 132.5t-108.5 126t-117 106t-136 73.5t-159 27.5q-154 0 -251.5 -91.5t-97.5 -244.5q0 -157 104 -250t263 -93q100 0 208 37.5 t193 98.5q5 4 21 18.5t30 24t22 9.5q14 0 24.5 -10.5t10.5 -24.5q0 -24 -60 -77q-101 -88 -234.5 -142t-260.5 -54q-133 0 -245.5 58t-180 165t-67.5 241q0 205 141.5 341t347.5 136q120 0 226.5 -43.5t185.5 -113t151.5 -153t139 -167.5t133.5 -153.5t149.5 -113 t172.5 -43.5q102 0 168.5 61.5t66.5 162.5q0 95 -64.5 159t-159.5 64q-30 0 -81.5 -18.5t-68.5 -18.5q-20 0 -35.5 15t-15.5 35q0 18 8.5 57t8.5 59q0 159 -107.5 263t-266.5 104q-58 0 -111.5 -18.5t-84 -40.5t-55.5 -40.5t-33 -18.5q-15 0 -25.5 10.5t-10.5 25.5 q0 19 25 46q59 67 147 103.5t182 36.5q191 0 318 -125.5t127 -315.5q0 -37 -4 -66q57 15 115 15z" />
|
||||
<glyph unicode="" horiz-adv-x="1664" d="M1216 832q0 26 -19 45t-45 19h-128v128q0 26 -19 45t-45 19t-45 -19t-19 -45v-128h-128q-26 0 -45 -19t-19 -45t19 -45t45 -19h128v-128q0 -26 19 -45t45 -19t45 19t19 45v128h128q26 0 45 19t19 45zM640 0q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5 t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1536 0q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1664 1088v-512q0 -24 -16 -42.5t-41 -21.5l-1044 -122q1 -7 4.5 -21.5t6 -26.5t2.5 -22q0 -16 -24 -64h920 q26 0 45 -19t19 -45t-19 -45t-45 -19h-1024q-26 0 -45 19t-19 45q0 14 11 39.5t29.5 59.5t20.5 38l-177 823h-204q-26 0 -45 19t-19 45t19 45t45 19h256q16 0 28.5 -6.5t20 -15.5t13 -24.5t7.5 -26.5t5.5 -29.5t4.5 -25.5h1201q26 0 45 -19t19 -45z" />
|
||||
<glyph unicode="" horiz-adv-x="1664" d="M1280 832q0 26 -19 45t-45 19t-45 -19l-147 -146v293q0 26 -19 45t-45 19t-45 -19t-19 -45v-293l-147 146q-19 19 -45 19t-45 -19t-19 -45t19 -45l256 -256q19 -19 45 -19t45 19l256 256q19 19 19 45zM640 0q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5 t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1536 0q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1664 1088v-512q0 -24 -16 -42.5t-41 -21.5l-1044 -122q1 -7 4.5 -21.5t6 -26.5t2.5 -22q0 -16 -24 -64h920 q26 0 45 -19t19 -45t-19 -45t-45 -19h-1024q-26 0 -45 19t-19 45q0 14 11 39.5t29.5 59.5t20.5 38l-177 823h-204q-26 0 -45 19t-19 45t19 45t45 19h256q16 0 28.5 -6.5t20 -15.5t13 -24.5t7.5 -26.5t5.5 -29.5t4.5 -25.5h1201q26 0 45 -19t19 -45z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M212 768l623 -665l-300 665h-323zM1024 -4l349 772h-698zM538 896l204 384h-262l-288 -384h346zM1213 103l623 665h-323zM683 896h682l-204 384h-274zM1510 896h346l-288 384h-262zM1651 1382l384 -512q14 -18 13 -41.5t-17 -40.5l-960 -1024q-18 -20 -47 -20t-47 20 l-960 1024q-16 17 -17 40.5t13 41.5l384 512q18 26 51 26h1152q33 0 51 -26z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1811 -19q19 19 45 19t45 -19l128 -128l-90 -90l-83 83l-83 -83q-18 -19 -45 -19t-45 19l-83 83l-83 -83q-19 -19 -45 -19t-45 19l-83 83l-83 -83q-19 -19 -45 -19t-45 19l-83 83l-83 -83q-19 -19 -45 -19t-45 19l-83 83l-83 -83q-19 -19 -45 -19t-45 19l-83 83l-83 -83 q-19 -19 -45 -19t-45 19l-83 83l-83 -83q-19 -19 -45 -19t-45 19l-128 128l90 90l83 -83l83 83q19 19 45 19t45 -19l83 -83l83 83q19 19 45 19t45 -19l83 -83l83 83q19 19 45 19t45 -19l83 -83l83 83q19 19 45 19t45 -19l83 -83l83 83q19 19 45 19t45 -19l83 -83l83 83 q19 19 45 19t45 -19l83 -83zM237 19q-19 -19 -45 -19t-45 19l-128 128l90 90l83 -82l83 82q19 19 45 19t45 -19l83 -82l64 64v293l-210 314q-17 26 -7 56.5t40 40.5l177 58v299h128v128h256v128h256v-128h256v-128h128v-299l177 -58q30 -10 40 -40.5t-7 -56.5l-210 -314 v-293l19 18q19 19 45 19t45 -19l83 -82l83 82q19 19 45 19t45 -19l128 -128l-90 -90l-83 83l-83 -83q-18 -19 -45 -19t-45 19l-83 83l-83 -83q-19 -19 -45 -19t-45 19l-83 83l-83 -83q-19 -19 -45 -19t-45 19l-83 83l-83 -83q-19 -19 -45 -19t-45 19l-83 83l-83 -83 q-19 -19 -45 -19t-45 19l-83 83l-83 -83q-19 -19 -45 -19t-45 19l-83 83zM640 1152v-128l384 128l384 -128v128h-128v128h-512v-128h-128z" />
|
||||
<glyph unicode="" d="M576 0l96 448l-96 128l-128 64zM832 0l128 640l-128 -64l-96 -128zM992 1010q-2 4 -4 6q-10 8 -96 8q-70 0 -167 -19q-7 -2 -21 -2t-21 2q-97 19 -167 19q-86 0 -96 -8q-2 -2 -4 -6q2 -18 4 -27q2 -3 7.5 -6.5t7.5 -10.5q2 -4 7.5 -20.5t7 -20.5t7.5 -17t8.5 -17t9 -14 t12 -13.5t14 -9.5t17.5 -8t20.5 -4t24.5 -2q36 0 59 12.5t32.5 30t14.5 34.5t11.5 29.5t17.5 12.5h12q11 0 17.5 -12.5t11.5 -29.5t14.5 -34.5t32.5 -30t59 -12.5q13 0 24.5 2t20.5 4t17.5 8t14 9.5t12 13.5t9 14t8.5 17t7.5 17t7 20.5t7.5 20.5q2 7 7.5 10.5t7.5 6.5 q2 9 4 27zM1408 131q0 -121 -73 -190t-194 -69h-874q-121 0 -194 69t-73 190q0 61 4.5 118t19 125.5t37.5 123.5t63.5 103.5t93.5 74.5l-90 220h214q-22 64 -22 128q0 12 2 32q-194 40 -194 96q0 57 210 99q17 62 51.5 134t70.5 114q32 37 76 37q30 0 84 -31t84 -31t84 31 t84 31q44 0 76 -37q36 -42 70.5 -114t51.5 -134q210 -42 210 -99q0 -56 -194 -96q7 -81 -20 -160h214l-82 -225q63 -33 107.5 -96.5t65.5 -143.5t29 -151.5t8 -148.5z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M2301 500q12 -103 -22 -198.5t-99 -163.5t-158.5 -106t-196.5 -31q-161 11 -279.5 125t-134.5 274q-12 111 27.5 210.5t118.5 170.5l-71 107q-96 -80 -151 -194t-55 -244q0 -27 -18.5 -46.5t-45.5 -19.5h-256h-69q-23 -164 -149 -274t-294 -110q-185 0 -316.5 131.5 t-131.5 316.5t131.5 316.5t316.5 131.5q76 0 152 -27l24 45q-123 110 -304 110h-64q-26 0 -45 19t-19 45t19 45t45 19h128q78 0 145 -13.5t116.5 -38.5t71.5 -39.5t51 -36.5h512h115l-85 128h-222q-30 0 -49 22.5t-14 52.5q4 23 23 38t43 15h253q33 0 53 -28l70 -105 l114 114q19 19 46 19h101q26 0 45 -19t19 -45v-128q0 -26 -19 -45t-45 -19h-179l115 -172q131 63 275 36q143 -26 244 -134.5t118 -253.5zM448 128q115 0 203 72.5t111 183.5h-314q-35 0 -55 31q-18 32 -1 63l147 277q-47 13 -91 13q-132 0 -226 -94t-94 -226t94 -226 t226 -94zM1856 128q132 0 226 94t94 226t-94 226t-226 94q-60 0 -121 -24l174 -260q15 -23 10 -49t-27 -40q-15 -11 -36 -11q-35 0 -53 29l-174 260q-93 -95 -93 -225q0 -132 94 -226t226 -94z" />
|
||||
<glyph unicode="" d="M1408 0q0 -63 -61.5 -113.5t-164 -81t-225 -46t-253.5 -15.5t-253.5 15.5t-225 46t-164 81t-61.5 113.5q0 49 33 88.5t91 66.5t118 44.5t131 29.5q26 5 48 -10.5t26 -41.5q5 -26 -10.5 -48t-41.5 -26q-58 -10 -106 -23.5t-76.5 -25.5t-48.5 -23.5t-27.5 -19.5t-8.5 -12 q3 -11 27 -26.5t73 -33t114 -32.5t160.5 -25t201.5 -10t201.5 10t160.5 25t114 33t73 33.5t27 27.5q-1 4 -8.5 11t-27.5 19t-48.5 23.5t-76.5 25t-106 23.5q-26 4 -41.5 26t-10.5 48q4 26 26 41.5t48 10.5q71 -12 131 -29.5t118 -44.5t91 -66.5t33 -88.5zM1024 896v-384 q0 -26 -19 -45t-45 -19h-64v-384q0 -26 -19 -45t-45 -19h-256q-26 0 -45 19t-19 45v384h-64q-26 0 -45 19t-19 45v384q0 53 37.5 90.5t90.5 37.5h384q53 0 90.5 -37.5t37.5 -90.5zM928 1280q0 -93 -65.5 -158.5t-158.5 -65.5t-158.5 65.5t-65.5 158.5t65.5 158.5t158.5 65.5 t158.5 -65.5t65.5 -158.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1280 512h305q-5 -6 -10 -10.5t-9 -7.5l-3 -4l-623 -600q-18 -18 -44 -18t-44 18l-624 602q-5 2 -21 20h369q22 0 39.5 13.5t22.5 34.5l70 281l190 -667q6 -20 23 -33t39 -13q21 0 38 13t23 33l146 485l56 -112q18 -35 57 -35zM1792 940q0 -145 -103 -300h-369l-111 221 q-8 17 -25.5 27t-36.5 8q-45 -5 -56 -46l-129 -430l-196 686q-6 20 -23.5 33t-39.5 13t-39 -13.5t-22 -34.5l-116 -464h-423q-103 155 -103 300q0 220 127 344t351 124q62 0 126.5 -21.5t120 -58t95.5 -68.5t76 -68q36 36 76 68t95.5 68.5t120 58t126.5 21.5q224 0 351 -124 t127 -344z" />
|
||||
<glyph unicode="" horiz-adv-x="1280" d="M1152 960q0 -221 -147.5 -384.5t-364.5 -187.5v-260h224q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-224v-224q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v224h-224q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h224v260q-150 16 -271.5 103t-186 224t-52.5 292 q11 134 80.5 249t182 188t245.5 88q170 19 319 -54t236 -212t87 -306zM128 960q0 -185 131.5 -316.5t316.5 -131.5t316.5 131.5t131.5 316.5t-131.5 316.5t-316.5 131.5t-316.5 -131.5t-131.5 -316.5z" />
|
||||
<glyph unicode="" d="M1472 1408q26 0 45 -19t19 -45v-416q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v262l-382 -383q126 -156 126 -359q0 -117 -45.5 -223.5t-123 -184t-184 -123t-223.5 -45.5t-223.5 45.5t-184 123t-123 184t-45.5 223.5t45.5 223.5t123 184t184 123t223.5 45.5 q203 0 359 -126l382 382h-261q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h416zM576 0q185 0 316.5 131.5t131.5 316.5t-131.5 316.5t-316.5 131.5t-316.5 -131.5t-131.5 -316.5t131.5 -316.5t316.5 -131.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1280" d="M830 1220q145 -72 233.5 -210.5t88.5 -305.5q0 -221 -147.5 -384.5t-364.5 -187.5v-132h96q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-96v-96q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v96h-96q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h96v132q-217 24 -364.5 187.5 t-147.5 384.5q0 167 88.5 305.5t233.5 210.5q-165 96 -228 273q-6 16 3.5 29.5t26.5 13.5h69q21 0 29 -20q44 -106 140 -171t214 -65t214 65t140 171q8 20 37 20h61q17 0 26.5 -13.5t3.5 -29.5q-63 -177 -228 -273zM576 256q185 0 316.5 131.5t131.5 316.5t-131.5 316.5 t-316.5 131.5t-316.5 -131.5t-131.5 -316.5t131.5 -316.5t316.5 -131.5z" />
|
||||
<glyph unicode="" d="M1024 1504q0 14 9 23t23 9h288q26 0 45 -19t19 -45v-288q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v134l-254 -255q126 -158 126 -359q0 -221 -147.5 -384.5t-364.5 -187.5v-132h96q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-96v-96q0 -14 -9 -23t-23 -9h-64 q-14 0 -23 9t-9 23v96h-96q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h96v132q-149 16 -270.5 103t-186.5 223.5t-53 291.5q16 204 160 353.5t347 172.5q118 14 228 -19t198 -103l255 254h-134q-14 0 -23 9t-9 23v64zM576 256q185 0 316.5 131.5t131.5 316.5t-131.5 316.5 t-316.5 131.5t-316.5 -131.5t-131.5 -316.5t131.5 -316.5t316.5 -131.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1280 1504q0 14 9 23t23 9h288q26 0 45 -19t19 -45v-288q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v134l-254 -255q126 -158 126 -359q0 -221 -147.5 -384.5t-364.5 -187.5v-132h96q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-96v-96q0 -14 -9 -23t-23 -9h-64 q-14 0 -23 9t-9 23v96h-96q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h96v132q-217 24 -364.5 187.5t-147.5 384.5q0 201 126 359l-52 53l-101 -111q-9 -10 -22 -10.5t-23 7.5l-48 44q-10 8 -10.5 21.5t8.5 23.5l105 115l-111 112v-134q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9 t-9 23v288q0 26 19 45t45 19h288q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-133l106 -107l86 94q9 10 22 10.5t23 -7.5l48 -44q10 -8 10.5 -21.5t-8.5 -23.5l-90 -99l57 -56q158 126 359 126t359 -126l255 254h-134q-14 0 -23 9t-9 23v64zM832 256q185 0 316.5 131.5 t131.5 316.5t-131.5 316.5t-316.5 131.5t-316.5 -131.5t-131.5 -316.5t131.5 -316.5t316.5 -131.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1790 1007q12 -155 -52.5 -292t-186 -224t-271.5 -103v-260h224q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-224v-224q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v224h-512v-224q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v224h-224q-14 0 -23 9t-9 23v64q0 14 9 23 t23 9h224v260q-150 16 -271.5 103t-186 224t-52.5 292q17 206 164.5 356.5t352.5 169.5q206 21 377 -94q171 115 377 94q205 -19 352.5 -169.5t164.5 -356.5zM896 647q128 131 128 313t-128 313q-128 -131 -128 -313t128 -313zM576 512q115 0 218 57q-154 165 -154 391 q0 224 154 391q-103 57 -218 57q-185 0 -316.5 -131.5t-131.5 -316.5t131.5 -316.5t316.5 -131.5zM1152 128v260q-137 15 -256 94q-119 -79 -256 -94v-260h512zM1216 512q185 0 316.5 131.5t131.5 316.5t-131.5 316.5t-316.5 131.5q-115 0 -218 -57q154 -167 154 -391 q0 -226 -154 -391q103 -57 218 -57z" />
|
||||
<glyph unicode="" horiz-adv-x="1920" d="M1536 1120q0 14 9 23t23 9h288q26 0 45 -19t19 -45v-288q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v134l-254 -255q76 -95 107.5 -214t9.5 -247q-31 -182 -166 -312t-318 -156q-210 -29 -384.5 80t-241.5 300q-117 6 -221 57.5t-177.5 133t-113.5 192.5t-32 230 q9 135 78 252t182 191.5t248 89.5q118 14 227.5 -19t198.5 -103l255 254h-134q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h288q26 0 45 -19t19 -45v-288q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v134l-254 -255q59 -74 93 -169q182 -9 328 -124l255 254h-134q-14 0 -23 9 t-9 23v64zM1024 704q0 20 -4 58q-162 -25 -271 -150t-109 -292q0 -20 4 -58q162 25 271 150t109 292zM128 704q0 -168 111 -294t276 -149q-3 29 -3 59q0 210 135 369.5t338 196.5q-53 120 -163.5 193t-245.5 73q-185 0 -316.5 -131.5t-131.5 -316.5zM1088 -128 q185 0 316.5 131.5t131.5 316.5q0 168 -111 294t-276 149q3 -29 3 -59q0 -210 -135 -369.5t-338 -196.5q53 -120 163.5 -193t245.5 -73z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1664 1504q0 14 9 23t23 9h288q26 0 45 -19t19 -45v-288q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v134l-254 -255q76 -95 107.5 -214t9.5 -247q-32 -180 -164.5 -310t-313.5 -157q-223 -34 -409 90q-117 -78 -256 -93v-132h96q14 0 23 -9t9 -23v-64q0 -14 -9 -23 t-23 -9h-96v-96q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v96h-96q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h96v132q-155 17 -279.5 109.5t-187 237.5t-39.5 307q25 187 159.5 322.5t320.5 164.5q224 34 410 -90q146 97 320 97q201 0 359 -126l255 254h-134q-14 0 -23 9 t-9 23v64zM896 391q128 131 128 313t-128 313q-128 -131 -128 -313t128 -313zM128 704q0 -185 131.5 -316.5t316.5 -131.5q117 0 218 57q-154 167 -154 391t154 391q-101 57 -218 57q-185 0 -316.5 -131.5t-131.5 -316.5zM1216 256q185 0 316.5 131.5t131.5 316.5 t-131.5 316.5t-316.5 131.5q-117 0 -218 -57q154 -167 154 -391t-154 -391q101 -57 218 -57z" />
|
||||
<glyph unicode="" d="M1472 1408q26 0 45 -19t19 -45v-416q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v262l-213 -214l140 -140q9 -10 9 -23t-9 -22l-46 -46q-9 -9 -22 -9t-23 9l-140 141l-78 -79q126 -156 126 -359q0 -117 -45.5 -223.5t-123 -184t-184 -123t-223.5 -45.5t-223.5 45.5 t-184 123t-123 184t-45.5 223.5t45.5 223.5t123 184t184 123t223.5 45.5q203 0 359 -126l78 78l-172 172q-9 10 -9 23t9 22l46 46q9 9 22 9t23 -9l172 -172l213 213h-261q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h416zM576 0q185 0 316.5 131.5t131.5 316.5t-131.5 316.5 t-316.5 131.5t-316.5 -131.5t-131.5 -316.5t131.5 -316.5t316.5 -131.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1280" d="M640 892q217 -24 364.5 -187.5t147.5 -384.5q0 -167 -87 -306t-236 -212t-319 -54q-133 15 -245.5 88t-182 188t-80.5 249q-12 155 52.5 292t186 224t271.5 103v132h-160q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h160v165l-92 -92q-10 -9 -23 -9t-22 9l-46 46q-9 9 -9 22 t9 23l202 201q19 19 45 19t45 -19l202 -201q9 -10 9 -23t-9 -22l-46 -46q-9 -9 -22 -9t-23 9l-92 92v-165h160q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-160v-132zM576 -128q185 0 316.5 131.5t131.5 316.5t-131.5 316.5t-316.5 131.5t-316.5 -131.5t-131.5 -316.5 t131.5 -316.5t316.5 -131.5z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1901 621q19 -19 19 -45t-19 -45l-294 -294q-9 -10 -22.5 -10t-22.5 10l-45 45q-10 9 -10 22.5t10 22.5l185 185h-294v-224q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v224h-132q-24 -217 -187.5 -364.5t-384.5 -147.5q-167 0 -306 87t-212 236t-54 319q15 133 88 245.5 t188 182t249 80.5q155 12 292 -52.5t224 -186t103 -271.5h132v224q0 14 9 23t23 9h64q14 0 23 -9t9 -23v-224h294l-185 185q-10 9 -10 22.5t10 22.5l45 45q9 10 22.5 10t22.5 -10zM576 128q185 0 316.5 131.5t131.5 316.5t-131.5 316.5t-316.5 131.5t-316.5 -131.5 t-131.5 -316.5t131.5 -316.5t316.5 -131.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1280" d="M1152 960q0 -221 -147.5 -384.5t-364.5 -187.5v-612q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v612q-217 24 -364.5 187.5t-147.5 384.5q0 117 45.5 223.5t123 184t184 123t223.5 45.5t223.5 -45.5t184 -123t123 -184t45.5 -223.5zM576 512q185 0 316.5 131.5 t131.5 316.5t-131.5 316.5t-316.5 131.5t-316.5 -131.5t-131.5 -316.5t131.5 -316.5t316.5 -131.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1280" d="M1024 576q0 185 -131.5 316.5t-316.5 131.5t-316.5 -131.5t-131.5 -316.5t131.5 -316.5t316.5 -131.5t316.5 131.5t131.5 316.5zM1152 576q0 -117 -45.5 -223.5t-123 -184t-184 -123t-223.5 -45.5t-223.5 45.5t-184 123t-123 184t-45.5 223.5t45.5 223.5t123 184t184 123 t223.5 45.5t223.5 -45.5t184 -123t123 -184t45.5 -223.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" d="M1451 1408q35 0 60 -25t25 -60v-1366q0 -35 -25 -60t-60 -25h-391v595h199l30 232h-229v148q0 56 23.5 84t91.5 28l122 1v207q-63 9 -178 9q-136 0 -217.5 -80t-81.5 -226v-171h-200v-232h200v-595h-735q-35 0 -60 25t-25 60v1366q0 35 25 60t60 25h1366z" />
|
||||
<glyph unicode="" horiz-adv-x="1280" d="M0 939q0 108 37.5 203.5t103.5 166.5t152 123t185 78t202 26q158 0 294 -66.5t221 -193.5t85 -287q0 -96 -19 -188t-60 -177t-100 -149.5t-145 -103t-189 -38.5q-68 0 -135 32t-96 88q-10 -39 -28 -112.5t-23.5 -95t-20.5 -71t-26 -71t-32 -62.5t-46 -77.5t-62 -86.5 l-14 -5l-9 10q-15 157 -15 188q0 92 21.5 206.5t66.5 287.5t52 203q-32 65 -32 169q0 83 52 156t132 73q61 0 95 -40.5t34 -102.5q0 -66 -44 -191t-44 -187q0 -63 45 -104.5t109 -41.5q55 0 102 25t78.5 68t56 95t38 110.5t20 111t6.5 99.5q0 173 -109.5 269.5t-285.5 96.5 q-200 0 -334 -129.5t-134 -328.5q0 -44 12.5 -85t27 -65t27 -45.5t12.5 -30.5q0 -28 -15 -73t-37 -45q-2 0 -17 3q-51 15 -90.5 56t-61 94.5t-32.5 108t-11 106.5z" />
|
||||
<glyph unicode="" d="M985 562q13 0 97.5 -44t89.5 -53q2 -5 2 -15q0 -33 -17 -76q-16 -39 -71 -65.5t-102 -26.5q-57 0 -190 62q-98 45 -170 118t-148 185q-72 107 -71 194v8q3 91 74 158q24 22 52 22q6 0 18 -1.5t19 -1.5q19 0 26.5 -6.5t15.5 -27.5q8 -20 33 -88t25 -75q0 -21 -34.5 -57.5 t-34.5 -46.5q0 -7 5 -15q34 -73 102 -137q56 -53 151 -101q12 -7 22 -7q15 0 54 48.5t52 48.5zM782 32q127 0 243.5 50t200.5 134t134 200.5t50 243.5t-50 243.5t-134 200.5t-200.5 134t-243.5 50t-243.5 -50t-200.5 -134t-134 -200.5t-50 -243.5q0 -203 120 -368l-79 -233 l242 77q158 -104 345 -104zM782 1414q153 0 292.5 -60t240.5 -161t161 -240.5t60 -292.5t-60 -292.5t-161 -240.5t-240.5 -161t-292.5 -60q-195 0 -365 94l-417 -134l136 405q-108 178 -108 389q0 153 60 292.5t161 240.5t240.5 161t292.5 60z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M128 128h1024v128h-1024v-128zM128 640h1024v128h-1024v-128zM1696 192q0 40 -28 68t-68 28t-68 -28t-28 -68t28 -68t68 -28t68 28t28 68zM128 1152h1024v128h-1024v-128zM1696 704q0 40 -28 68t-68 28t-68 -28t-28 -68t28 -68t68 -28t68 28t28 68zM1696 1216 q0 40 -28 68t-68 28t-68 -28t-28 -68t28 -68t68 -28t68 28t28 68zM1792 384v-384h-1792v384h1792zM1792 896v-384h-1792v384h1792zM1792 1408v-384h-1792v384h1792z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M704 640q-159 0 -271.5 112.5t-112.5 271.5t112.5 271.5t271.5 112.5t271.5 -112.5t112.5 -271.5t-112.5 -271.5t-271.5 -112.5zM1664 512h352q13 0 22.5 -9.5t9.5 -22.5v-192q0 -13 -9.5 -22.5t-22.5 -9.5h-352v-352q0 -13 -9.5 -22.5t-22.5 -9.5h-192q-13 0 -22.5 9.5 t-9.5 22.5v352h-352q-13 0 -22.5 9.5t-9.5 22.5v192q0 13 9.5 22.5t22.5 9.5h352v352q0 13 9.5 22.5t22.5 9.5h192q13 0 22.5 -9.5t9.5 -22.5v-352zM928 288q0 -52 38 -90t90 -38h256v-238q-68 -50 -171 -50h-874q-121 0 -194 69t-73 190q0 53 3.5 103.5t14 109t26.5 108.5 t43 97.5t62 81t85.5 53.5t111.5 20q19 0 39 -17q79 -61 154.5 -91.5t164.5 -30.5t164.5 30.5t154.5 91.5q20 17 39 17q132 0 217 -96h-223q-52 0 -90 -38t-38 -90v-192z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M704 640q-159 0 -271.5 112.5t-112.5 271.5t112.5 271.5t271.5 112.5t271.5 -112.5t112.5 -271.5t-112.5 -271.5t-271.5 -112.5zM1781 320l249 -249q9 -9 9 -23q0 -13 -9 -22l-136 -136q-9 -9 -22 -9q-14 0 -23 9l-249 249l-249 -249q-9 -9 -23 -9q-13 0 -22 9l-136 136 q-9 9 -9 22q0 14 9 23l249 249l-249 249q-9 9 -9 23q0 13 9 22l136 136q9 9 22 9q14 0 23 -9l249 -249l249 249q9 9 23 9q13 0 22 -9l136 -136q9 -9 9 -22q0 -14 -9 -23zM1283 320l-181 -181q-37 -37 -37 -91q0 -53 37 -90l83 -83q-21 -3 -44 -3h-874q-121 0 -194 69 t-73 190q0 53 3.5 103.5t14 109t26.5 108.5t43 97.5t62 81t85.5 53.5t111.5 20q19 0 39 -17q154 -122 319 -122t319 122q20 17 39 17q28 0 57 -6q-28 -27 -41 -50t-13 -56q0 -54 37 -91z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M256 512h1728q26 0 45 -19t19 -45v-448h-256v256h-1536v-256h-256v1216q0 26 19 45t45 19h128q26 0 45 -19t19 -45v-704zM832 832q0 106 -75 181t-181 75t-181 -75t-75 -181t75 -181t181 -75t181 75t75 181zM2048 576v64q0 159 -112.5 271.5t-271.5 112.5h-704 q-26 0 -45 -19t-19 -45v-384h1152z" />
|
||||
<glyph unicode="" d="M1536 1536l-192 -448h192v-192h-274l-55 -128h329v-192h-411l-357 -832l-357 832h-411v192h329l-55 128h-274v192h192l-192 448h256l323 -768h378l323 768h256zM768 320l108 256h-216z" />
|
||||
<glyph unicode="" d="M1088 1536q185 0 316.5 -93.5t131.5 -226.5v-896q0 -130 -125.5 -222t-305.5 -97l213 -202q16 -15 8 -35t-30 -20h-1056q-22 0 -30 20t8 35l213 202q-180 5 -305.5 97t-125.5 222v896q0 133 131.5 226.5t316.5 93.5h640zM768 192q80 0 136 56t56 136t-56 136t-136 56 t-136 -56t-56 -136t56 -136t136 -56zM1344 768v512h-1152v-512h1152z" />
|
||||
<glyph unicode="" d="M1088 1536q185 0 316.5 -93.5t131.5 -226.5v-896q0 -130 -125.5 -222t-305.5 -97l213 -202q16 -15 8 -35t-30 -20h-1056q-22 0 -30 20t8 35l213 202q-180 5 -305.5 97t-125.5 222v896q0 133 131.5 226.5t316.5 93.5h640zM288 224q66 0 113 47t47 113t-47 113t-113 47 t-113 -47t-47 -113t47 -113t113 -47zM704 768v512h-544v-512h544zM1248 224q66 0 113 47t47 113t-47 113t-113 47t-113 -47t-47 -113t47 -113t113 -47zM1408 768v512h-576v-512h576z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M597 1115v-1173q0 -25 -12.5 -42.5t-36.5 -17.5q-17 0 -33 8l-465 233q-21 10 -35.5 33.5t-14.5 46.5v1140q0 20 10 34t29 14q14 0 44 -15l511 -256q3 -3 3 -5zM661 1014l534 -866l-534 266v600zM1792 996v-1054q0 -25 -14 -40.5t-38 -15.5t-47 13l-441 220zM1789 1116 q0 -3 -256.5 -419.5t-300.5 -487.5l-390 634l324 527q17 28 52 28q14 0 26 -6l541 -270q4 -2 4 -6z" />
|
||||
<glyph unicode="" d="M809 532l266 499h-112l-157 -312q-24 -48 -44 -92l-42 92l-155 312h-120l263 -493v-324h101v318zM1536 1408v-1536h-1536v1536h1536z" />
|
||||
<glyph unicode="" horiz-adv-x="2296" d="M478 -139q-8 -16 -27 -34.5t-37 -25.5q-25 -9 -51.5 3.5t-28.5 31.5q-1 22 40 55t68 38q23 4 34 -21.5t2 -46.5zM1819 -139q7 -16 26 -34.5t38 -25.5q25 -9 51.5 3.5t27.5 31.5q2 22 -39.5 55t-68.5 38q-22 4 -33 -21.5t-2 -46.5zM1867 -30q13 -27 56.5 -59.5t77.5 -41.5 q45 -13 82 4.5t37 50.5q0 46 -67.5 100.5t-115.5 59.5q-40 5 -63.5 -37.5t-6.5 -76.5zM428 -30q-13 -27 -56 -59.5t-77 -41.5q-45 -13 -82 4.5t-37 50.5q0 46 67.5 100.5t115.5 59.5q40 5 63 -37.5t6 -76.5zM1158 1094h1q-41 0 -76 -15q27 -8 44 -30.5t17 -49.5 q0 -35 -27 -60t-65 -25q-52 0 -80 43q-5 -23 -5 -42q0 -74 56 -126.5t135 -52.5q80 0 136 52.5t56 126.5t-56 126.5t-136 52.5zM1462 1312q-99 109 -220.5 131.5t-245.5 -44.5q27 60 82.5 96.5t118 39.5t121.5 -17t99.5 -74.5t44.5 -131.5zM2212 73q8 -11 -11 -42 q7 -23 7 -40q1 -56 -44.5 -112.5t-109.5 -91.5t-118 -37q-48 -2 -92 21.5t-66 65.5q-687 -25 -1259 0q-23 -41 -66.5 -65t-92.5 -22q-86 3 -179.5 80.5t-92.5 160.5q2 22 7 40q-19 31 -11 42q6 10 31 1q14 22 41 51q-7 29 2 38q11 10 39 -4q29 20 59 34q0 29 13 37 q23 12 51 -16q35 5 61 -2q18 -4 38 -19v73q-11 0 -18 2q-53 10 -97 44.5t-55 87.5q-9 38 0 81q15 62 93 95q2 17 19 35.5t36 23.5t33 -7.5t19 -30.5h13q46 -5 60 -23q3 -3 5 -7q10 1 30.5 3.5t30.5 3.5q-15 11 -30 17q-23 40 -91 43q0 6 1 10q-62 2 -118.5 18.5t-84.5 47.5 q-32 36 -42.5 92t-2.5 112q16 126 90 179q23 16 52 4.5t32 -40.5q0 -1 1.5 -14t2.5 -21t3 -20t5.5 -19t8.5 -10q27 -14 76 -12q48 46 98 74q-40 4 -162 -14l47 46q61 58 163 111q145 73 282 86q-20 8 -41 15.5t-47 14t-42.5 10.5t-47.5 11t-43 10q595 126 904 -139 q98 -84 158 -222q85 -10 121 9h1q5 3 8.5 10t5.5 19t3 19.5t3 21.5l1 14q3 28 32 40t52 -5q73 -52 91 -178q7 -57 -3.5 -113t-42.5 -91q-28 -32 -83.5 -48.5t-115.5 -18.5v-10q-71 -2 -95 -43q-14 -5 -31 -17q11 -1 32 -3.5t30 -3.5q1 4 5 8q16 18 60 23h13q5 18 19 30t33 8 t36 -23t19 -36q79 -32 93 -95q9 -40 1 -81q-12 -53 -56 -88t-97 -44q-10 -2 -17 -2q0 -49 -1 -73q20 15 38 19q26 7 61 2q28 28 51 16q14 -9 14 -37q33 -16 59 -34q27 13 38 4q10 -10 2 -38q28 -30 41 -51q23 8 31 -1zM1937 1025q0 -29 -9 -54q82 -32 112 -132 q4 37 -9.5 98.5t-41.5 90.5q-20 19 -36 17t-16 -20zM1859 925q35 -42 47.5 -108.5t-0.5 -124.5q67 13 97 45q13 14 18 28q-3 64 -31 114.5t-79 66.5q-15 -15 -52 -21zM1822 921q-30 0 -44 1q42 -115 53 -239q21 0 43 3q16 68 1 135t-53 100zM258 839q30 100 112 132 q-9 25 -9 54q0 18 -16.5 20t-35.5 -17q-28 -29 -41.5 -90.5t-9.5 -98.5zM294 737q29 -31 97 -45q-13 58 -0.5 124.5t47.5 108.5v0q-37 6 -52 21q-51 -16 -78.5 -66t-31.5 -115q9 -17 18 -28zM471 683q14 124 73 235q-19 -4 -55 -18l-45 -19v1q-46 -89 -20 -196q25 -3 47 -3z M1434 644q8 -38 16.5 -108.5t11.5 -89.5q3 -18 9.5 -21.5t23.5 4.5q40 20 62 85.5t23 125.5q-24 2 -146 4zM1152 1285q-116 0 -199 -82.5t-83 -198.5q0 -117 83 -199.5t199 -82.5t199 82.5t83 199.5q0 116 -83 198.5t-199 82.5zM1380 646q-106 2 -211 0v1q-1 -27 2.5 -86 t13.5 -66q29 -14 93.5 -14.5t95.5 10.5q9 3 11 39t-0.5 69.5t-4.5 46.5zM1112 447q8 4 9.5 48t-0.5 88t-4 63v1q-212 -3 -214 -3q-4 -20 -7 -62t0 -83t14 -46q34 -15 101 -16t101 10zM718 636q-16 -59 4.5 -118.5t77.5 -84.5q15 -8 24 -5t12 21q3 16 8 90t10 103 q-69 -2 -136 -6zM591 510q3 -23 -34 -36q132 -141 271.5 -240t305.5 -154q172 49 310.5 146t293.5 250q-33 13 -30 34l3 9v1v-1q-17 2 -50 5.5t-48 4.5q-26 -90 -82 -132q-51 -38 -82 1q-5 6 -9 14q-7 13 -17 62q-2 -5 -5 -9t-7.5 -7t-8 -5.5t-9.5 -4l-10 -2.5t-12 -2 l-12 -1.5t-13.5 -1t-13.5 -0.5q-106 -9 -163 11q-4 -17 -10 -26.5t-21 -15t-23 -7t-36 -3.5q-2 0 -3 -0.5t-3 -0.5h-3q-179 -17 -203 40q-2 -63 -56 -54q-47 8 -91 54q-12 13 -20 26q-17 29 -26 65q-58 -6 -87 -10q1 -2 4 -10zM507 -118q3 14 3 30q-17 71 -51 130t-73 70 q-41 12 -101.5 -14.5t-104.5 -80t-39 -107.5q35 -53 100 -93t119 -42q51 -2 94 28t53 79zM510 53q23 -63 27 -119q195 113 392 174q-98 52 -180.5 120t-179.5 165q-6 -4 -29 -13q0 -2 -1 -5t-1 -4q31 -18 22 -37q-12 -23 -56 -34q-10 -13 -29 -24h-1q-2 -83 1 -150 q19 -34 35 -73zM579 -113q532 -21 1145 0q-254 147 -428 196q-76 -35 -156 -57q-8 -3 -16 0q-65 21 -129 49q-208 -60 -416 -188h-1v-1q1 0 1 1zM1763 -67q4 54 28 120q14 38 33 71l-1 -1q3 77 3 153q-15 8 -30 25q-42 9 -56 33q-9 20 22 38q-2 4 -2 9q-16 4 -28 12 q-204 -190 -383 -284q198 -59 414 -176zM2155 -90q5 54 -39 107.5t-104 80t-102 14.5q-38 -11 -72.5 -70.5t-51.5 -129.5q0 -16 3 -30q10 -49 53 -79t94 -28q54 2 119 42t100 93z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M1524 -25q0 -68 -48 -116t-116 -48t-116.5 48t-48.5 116t48.5 116.5t116.5 48.5t116 -48.5t48 -116.5zM775 -25q0 -68 -48.5 -116t-116.5 -48t-116 48t-48 116t48 116.5t116 48.5t116.5 -48.5t48.5 -116.5zM0 1469q57 -60 110.5 -104.5t121 -82t136 -63t166 -45.5 t200 -31.5t250 -18.5t304 -9.5t372.5 -2.5q139 0 244.5 -5t181 -16.5t124 -27.5t71 -39.5t24 -51.5t-19.5 -64t-56.5 -76.5t-89.5 -91t-116 -104.5t-139 -119q-185 -157 -286 -247q29 51 76.5 109t94 105.5t94.5 98.5t83 91.5t54 80.5t13 70t-45.5 55.5t-116.5 41t-204 23.5 t-304 5q-168 -2 -314 6t-256 23t-204.5 41t-159.5 51.5t-122.5 62.5t-91.5 66.5t-68 71.5t-50.5 69.5t-40 68t-36.5 59.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M896 1472q-169 0 -323 -66t-265.5 -177.5t-177.5 -265.5t-66 -323t66 -323t177.5 -265.5t265.5 -177.5t323 -66t323 66t265.5 177.5t177.5 265.5t66 323t-66 323t-177.5 265.5t-265.5 177.5t-323 66zM896 1536q182 0 348 -71t286 -191t191 -286t71 -348t-71 -348 t-191 -286t-286 -191t-348 -71t-348 71t-286 191t-191 286t-71 348t71 348t191 286t286 191t348 71zM496 704q16 0 16 -16v-480q0 -16 -16 -16h-32q-16 0 -16 16v480q0 16 16 16h32zM896 640q53 0 90.5 -37.5t37.5 -90.5q0 -35 -17.5 -64t-46.5 -46v-114q0 -14 -9 -23 t-23 -9h-64q-14 0 -23 9t-9 23v114q-29 17 -46.5 46t-17.5 64q0 53 37.5 90.5t90.5 37.5zM896 1408q209 0 385.5 -103t279.5 -279.5t103 -385.5t-103 -385.5t-279.5 -279.5t-385.5 -103t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103zM544 928v-96 q0 -14 9 -23t23 -9h64q14 0 23 9t9 23v96q0 93 65.5 158.5t158.5 65.5t158.5 -65.5t65.5 -158.5v-96q0 -14 9 -23t23 -9h64q14 0 23 9t9 23v96q0 146 -103 249t-249 103t-249 -103t-103 -249zM1408 192v512q0 26 -19 45t-45 19h-896q-26 0 -45 -19t-19 -45v-512 q0 -26 19 -45t45 -19h896q26 0 45 19t19 45z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M1920 1024v-768h-1664v768h1664zM2048 448h128v384h-128v288q0 14 -9 23t-23 9h-1856q-14 0 -23 -9t-9 -23v-960q0 -14 9 -23t23 -9h1856q14 0 23 9t9 23v288zM2304 832v-384q0 -53 -37.5 -90.5t-90.5 -37.5v-160q0 -66 -47 -113t-113 -47h-1856q-66 0 -113 47t-47 113 v960q0 66 47 113t113 47h1856q66 0 113 -47t47 -113v-160q53 0 90.5 -37.5t37.5 -90.5z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M256 256v768h1280v-768h-1280zM2176 960q53 0 90.5 -37.5t37.5 -90.5v-384q0 -53 -37.5 -90.5t-90.5 -37.5v-160q0 -66 -47 -113t-113 -47h-1856q-66 0 -113 47t-47 113v960q0 66 47 113t113 47h1856q66 0 113 -47t47 -113v-160zM2176 448v384h-128v288q0 14 -9 23t-23 9 h-1856q-14 0 -23 -9t-9 -23v-960q0 -14 9 -23t23 -9h1856q14 0 23 9t9 23v288h128z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M256 256v768h896v-768h-896zM2176 960q53 0 90.5 -37.5t37.5 -90.5v-384q0 -53 -37.5 -90.5t-90.5 -37.5v-160q0 -66 -47 -113t-113 -47h-1856q-66 0 -113 47t-47 113v960q0 66 47 113t113 47h1856q66 0 113 -47t47 -113v-160zM2176 448v384h-128v288q0 14 -9 23t-23 9 h-1856q-14 0 -23 -9t-9 -23v-960q0 -14 9 -23t23 -9h1856q14 0 23 9t9 23v288h128z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M256 256v768h512v-768h-512zM2176 960q53 0 90.5 -37.5t37.5 -90.5v-384q0 -53 -37.5 -90.5t-90.5 -37.5v-160q0 -66 -47 -113t-113 -47h-1856q-66 0 -113 47t-47 113v960q0 66 47 113t113 47h1856q66 0 113 -47t47 -113v-160zM2176 448v384h-128v288q0 14 -9 23t-23 9 h-1856q-14 0 -23 -9t-9 -23v-960q0 -14 9 -23t23 -9h1856q14 0 23 9t9 23v288h128z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M2176 960q53 0 90.5 -37.5t37.5 -90.5v-384q0 -53 -37.5 -90.5t-90.5 -37.5v-160q0 -66 -47 -113t-113 -47h-1856q-66 0 -113 47t-47 113v960q0 66 47 113t113 47h1856q66 0 113 -47t47 -113v-160zM2176 448v384h-128v288q0 14 -9 23t-23 9h-1856q-14 0 -23 -9t-9 -23 v-960q0 -14 9 -23t23 -9h1856q14 0 23 9t9 23v288h128z" />
|
||||
<glyph unicode="" horiz-adv-x="1280" d="M1133 493q31 -30 14 -69q-17 -40 -59 -40h-382l201 -476q10 -25 0 -49t-34 -35l-177 -75q-25 -10 -49 0t-35 34l-191 452l-312 -312q-19 -19 -45 -19q-12 0 -24 5q-40 17 -40 59v1504q0 42 40 59q12 5 24 5q27 0 45 -19z" />
|
||||
<glyph unicode="" horiz-adv-x="1024" d="M832 1408q-320 0 -320 -224v-416h128v-128h-128v-544q0 -224 320 -224h64v-128h-64q-272 0 -384 146q-112 -146 -384 -146h-64v128h64q320 0 320 224v544h-128v128h128v416q0 224 -320 224h-64v128h64q272 0 384 -146q112 146 384 146h64v-128h-64z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M2048 1152h-128v-1024h128v-384h-384v128h-1280v-128h-384v384h128v1024h-128v384h384v-128h1280v128h384v-384zM1792 1408v-128h128v128h-128zM128 1408v-128h128v128h-128zM256 -128v128h-128v-128h128zM1664 0v128h128v1024h-128v128h-1280v-128h-128v-1024h128v-128 h1280zM1920 -128v128h-128v-128h128zM1280 896h384v-768h-896v256h-384v768h896v-256zM512 512h640v512h-640v-512zM1536 256v512h-256v-384h-384v-128h640z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M2304 768h-128v-640h128v-384h-384v128h-896v-128h-384v384h128v128h-384v-128h-384v384h128v640h-128v384h384v-128h896v128h384v-384h-128v-128h384v128h384v-384zM2048 1024v-128h128v128h-128zM1408 1408v-128h128v128h-128zM128 1408v-128h128v128h-128zM256 256 v128h-128v-128h128zM1536 384h-128v-128h128v128zM384 384h896v128h128v640h-128v128h-896v-128h-128v-640h128v-128zM896 -128v128h-128v-128h128zM2176 -128v128h-128v-128h128zM2048 128v640h-128v128h-384v-384h128v-384h-384v128h-384v-128h128v-128h896v128h128z" />
|
||||
<glyph unicode="" d="M1024 288v-416h-928q-40 0 -68 28t-28 68v1344q0 40 28 68t68 28h1344q40 0 68 -28t28 -68v-928h-416q-40 0 -68 -28t-28 -68zM1152 256h381q-15 -82 -65 -132l-184 -184q-50 -50 -132 -65v381z" />
|
||||
<glyph unicode="" d="M1400 256h-248v-248q29 10 41 22l185 185q12 12 22 41zM1120 384h288v896h-1280v-1280h896v288q0 40 28 68t68 28zM1536 1312v-1024q0 -40 -20 -88t-48 -76l-184 -184q-28 -28 -76 -48t-88 -20h-1024q-40 0 -68 28t-28 68v1344q0 40 28 68t68 28h1344q40 0 68 -28t28 -68 z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M1951 538q0 -26 -15.5 -44.5t-38.5 -23.5q-8 -2 -18 -2h-153v140h153q10 0 18 -2q23 -5 38.5 -23.5t15.5 -44.5zM1933 751q0 -25 -15 -42t-38 -21q-3 -1 -15 -1h-139v129h139q3 0 8.5 -0.5t6.5 -0.5q23 -4 38 -21.5t15 -42.5zM728 587v308h-228v-308q0 -58 -38 -94.5 t-105 -36.5q-108 0 -229 59v-112q53 -15 121 -23t109 -9l42 -1q328 0 328 217zM1442 403v113q-99 -52 -200 -59q-108 -8 -169 41t-61 142t61 142t169 41q101 -7 200 -58v112q-48 12 -100 19.5t-80 9.5l-28 2q-127 6 -218.5 -14t-140.5 -60t-71 -88t-22 -106t22 -106t71 -88 t140.5 -60t218.5 -14q101 4 208 31zM2176 518q0 54 -43 88.5t-109 39.5v3q57 8 89 41.5t32 79.5q0 55 -41 88t-107 36q-3 0 -12 0.5t-14 0.5h-455v-510h491q74 0 121.5 36.5t47.5 96.5zM2304 1280v-1280q0 -52 -38 -90t-90 -38h-2048q-52 0 -90 38t-38 90v1280q0 52 38 90 t90 38h2048q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M858 295v693q-106 -41 -172 -135.5t-66 -211.5t66 -211.5t172 -134.5zM1362 641q0 117 -66 211.5t-172 135.5v-694q106 41 172 135.5t66 211.5zM1577 641q0 -159 -78.5 -294t-213.5 -213.5t-294 -78.5q-119 0 -227.5 46.5t-187 125t-125 187t-46.5 227.5q0 159 78.5 294 t213.5 213.5t294 78.5t294 -78.5t213.5 -213.5t78.5 -294zM1960 634q0 139 -55.5 261.5t-147.5 205.5t-213.5 131t-252.5 48h-301q-176 0 -323.5 -81t-235 -230t-87.5 -335q0 -171 87 -317.5t236 -231.5t323 -85h301q129 0 251.5 50.5t214.5 135t147.5 202.5t55.5 246z M2304 1280v-1280q0 -52 -38 -90t-90 -38h-2048q-52 0 -90 38t-38 90v1280q0 52 38 90t90 38h2048q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1664 -96v1088q0 13 -9.5 22.5t-22.5 9.5h-1088q-13 0 -22.5 -9.5t-9.5 -22.5v-1088q0 -13 9.5 -22.5t22.5 -9.5h1088q13 0 22.5 9.5t9.5 22.5zM1792 992v-1088q0 -66 -47 -113t-113 -47h-1088q-66 0 -113 47t-47 113v1088q0 66 47 113t113 47h1088q66 0 113 -47t47 -113 zM1408 1376v-160h-128v160q0 13 -9.5 22.5t-22.5 9.5h-1088q-13 0 -22.5 -9.5t-9.5 -22.5v-1088q0 -13 9.5 -22.5t22.5 -9.5h160v-128h-160q-66 0 -113 47t-47 113v1088q0 66 47 113t113 47h1088q66 0 113 -47t47 -113z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M1728 1088l-384 -704h768zM448 1088l-384 -704h768zM1269 1280q-14 -40 -45.5 -71.5t-71.5 -45.5v-1291h608q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-1344q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h608v1291q-40 14 -71.5 45.5t-45.5 71.5h-491q-14 0 -23 9t-9 23v64 q0 14 9 23t23 9h491q21 57 70 92.5t111 35.5t111 -35.5t70 -92.5h491q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-491zM1088 1264q33 0 56.5 23.5t23.5 56.5t-23.5 56.5t-56.5 23.5t-56.5 -23.5t-23.5 -56.5t23.5 -56.5t56.5 -23.5zM2176 384q0 -73 -46.5 -131t-117.5 -91 t-144.5 -49.5t-139.5 -16.5t-139.5 16.5t-144.5 49.5t-117.5 91t-46.5 131q0 11 35 81t92 174.5t107 195.5t102 184t56 100q18 33 56 33t56 -33q4 -7 56 -100t102 -184t107 -195.5t92 -174.5t35 -81zM896 384q0 -73 -46.5 -131t-117.5 -91t-144.5 -49.5t-139.5 -16.5 t-139.5 16.5t-144.5 49.5t-117.5 91t-46.5 131q0 11 35 81t92 174.5t107 195.5t102 184t56 100q18 33 56 33t56 -33q4 -7 56 -100t102 -184t107 -195.5t92 -174.5t35 -81z" />
|
||||
<glyph unicode="" d="M1408 1408q0 -261 -106.5 -461.5t-266.5 -306.5q160 -106 266.5 -306.5t106.5 -461.5h96q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-1472q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h96q0 261 106.5 461.5t266.5 306.5q-160 106 -266.5 306.5t-106.5 461.5h-96q-14 0 -23 9 t-9 23v64q0 14 9 23t23 9h1472q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-96zM874 700q77 29 149 92.5t129.5 152.5t92.5 210t35 253h-1024q0 -132 35 -253t92.5 -210t129.5 -152.5t149 -92.5q19 -7 30.5 -23.5t11.5 -36.5t-11.5 -36.5t-30.5 -23.5q-77 -29 -149 -92.5 t-129.5 -152.5t-92.5 -210t-35 -253h1024q0 132 -35 253t-92.5 210t-129.5 152.5t-149 92.5q-19 7 -30.5 23.5t-11.5 36.5t11.5 36.5t30.5 23.5z" />
|
||||
<glyph unicode="" d="M1408 1408q0 -261 -106.5 -461.5t-266.5 -306.5q160 -106 266.5 -306.5t106.5 -461.5h96q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-1472q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h96q0 261 106.5 461.5t266.5 306.5q-160 106 -266.5 306.5t-106.5 461.5h-96q-14 0 -23 9 t-9 23v64q0 14 9 23t23 9h1472q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-96zM1280 1408h-1024q0 -66 9 -128h1006q9 61 9 128zM1280 -128q0 130 -34 249.5t-90.5 208t-126.5 152t-146 94.5h-230q-76 -31 -146 -94.5t-126.5 -152t-90.5 -208t-34 -249.5h1024z" />
|
||||
<glyph unicode="" d="M1408 1408q0 -261 -106.5 -461.5t-266.5 -306.5q160 -106 266.5 -306.5t106.5 -461.5h96q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-1472q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h96q0 261 106.5 461.5t266.5 306.5q-160 106 -266.5 306.5t-106.5 461.5h-96q-14 0 -23 9 t-9 23v64q0 14 9 23t23 9h1472q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-96zM1280 1408h-1024q0 -206 85 -384h854q85 178 85 384zM1223 192q-54 141 -145.5 241.5t-194.5 142.5h-230q-103 -42 -194.5 -142.5t-145.5 -241.5h910z" />
|
||||
<glyph unicode="" d="M1408 1408q0 -261 -106.5 -461.5t-266.5 -306.5q160 -106 266.5 -306.5t106.5 -461.5h96q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-1472q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h96q0 261 106.5 461.5t266.5 306.5q-160 106 -266.5 306.5t-106.5 461.5h-96q-14 0 -23 9 t-9 23v64q0 14 9 23t23 9h1472q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-96zM874 700q77 29 149 92.5t129.5 152.5t92.5 210t35 253h-1024q0 -132 35 -253t92.5 -210t129.5 -152.5t149 -92.5q19 -7 30.5 -23.5t11.5 -36.5t-11.5 -36.5t-30.5 -23.5q-137 -51 -244 -196 h700q-107 145 -244 196q-19 7 -30.5 23.5t-11.5 36.5t11.5 36.5t30.5 23.5z" />
|
||||
<glyph unicode="" d="M1504 -64q14 0 23 -9t9 -23v-128q0 -14 -9 -23t-23 -9h-1472q-14 0 -23 9t-9 23v128q0 14 9 23t23 9h1472zM130 0q3 55 16 107t30 95t46 87t53.5 76t64.5 69.5t66 60t70.5 55t66.5 47.5t65 43q-43 28 -65 43t-66.5 47.5t-70.5 55t-66 60t-64.5 69.5t-53.5 76t-46 87 t-30 95t-16 107h1276q-3 -55 -16 -107t-30 -95t-46 -87t-53.5 -76t-64.5 -69.5t-66 -60t-70.5 -55t-66.5 -47.5t-65 -43q43 -28 65 -43t66.5 -47.5t70.5 -55t66 -60t64.5 -69.5t53.5 -76t46 -87t30 -95t16 -107h-1276zM1504 1536q14 0 23 -9t9 -23v-128q0 -14 -9 -23t-23 -9 h-1472q-14 0 -23 9t-9 23v128q0 14 9 23t23 9h1472z" />
|
||||
<glyph unicode="" d="M768 1152q-53 0 -90.5 -37.5t-37.5 -90.5v-128h-32v93q0 48 -32 81.5t-80 33.5q-46 0 -79 -33t-33 -79v-429l-32 30v172q0 48 -32 81.5t-80 33.5q-46 0 -79 -33t-33 -79v-224q0 -47 35 -82l310 -296q39 -39 39 -102q0 -26 19 -45t45 -19h640q26 0 45 19t19 45v25 q0 41 10 77l108 436q10 36 10 77v246q0 48 -32 81.5t-80 33.5q-46 0 -79 -33t-33 -79v-32h-32v125q0 40 -25 72.5t-64 40.5q-14 2 -23 2q-46 0 -79 -33t-33 -79v-128h-32v122q0 51 -32.5 89.5t-82.5 43.5q-5 1 -13 1zM768 1280q84 0 149 -50q57 34 123 34q59 0 111 -27 t86 -76q27 7 59 7q100 0 170 -71.5t70 -171.5v-246q0 -51 -13 -108l-109 -436q-6 -24 -6 -71q0 -80 -56 -136t-136 -56h-640q-84 0 -138 58.5t-54 142.5l-308 296q-76 73 -76 175v224q0 99 70.5 169.5t169.5 70.5q11 0 16 -1q6 95 75.5 160t164.5 65q52 0 98 -21 q72 69 174 69z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M880 1408q-46 0 -79 -33t-33 -79v-656h-32v528q0 46 -33 79t-79 33t-79 -33t-33 -79v-528v-256l-154 205q-38 51 -102 51q-53 0 -90.5 -37.5t-37.5 -90.5q0 -43 26 -77l384 -512q38 -51 102 -51h688q34 0 61 22t34 56l76 405q5 32 5 59v498q0 46 -33 79t-79 33t-79 -33 t-33 -79v-272h-32v528q0 46 -33 79t-79 33t-79 -33t-33 -79v-528h-32v656q0 46 -33 79t-79 33zM880 1536q68 0 125.5 -35.5t88.5 -96.5q19 4 42 4q99 0 169.5 -70.5t70.5 -169.5v-17q105 6 180.5 -64t75.5 -175v-498q0 -40 -8 -83l-76 -404q-14 -79 -76.5 -131t-143.5 -52 h-688q-60 0 -114.5 27.5t-90.5 74.5l-384 512q-51 68 -51 154q0 106 75 181t181 75q78 0 128 -34v434q0 99 70.5 169.5t169.5 70.5q23 0 42 -4q31 61 88.5 96.5t125.5 35.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1073 -128h-177q-163 0 -226 141q-23 49 -23 102v5q-62 30 -98.5 88.5t-36.5 127.5q0 38 5 48h-261q-106 0 -181 75t-75 181t75 181t181 75h113l-44 17q-74 28 -119.5 93.5t-45.5 145.5q0 106 75 181t181 75q46 0 91 -17l628 -239h401q106 0 181 -75t75 -181v-668 q0 -88 -54 -157.5t-140 -90.5l-339 -85q-92 -23 -186 -23zM1024 583l-155 -71l-163 -74q-30 -14 -48 -41.5t-18 -60.5q0 -46 33 -79t79 -33q26 0 46 10l338 154q-49 10 -80.5 50t-31.5 90v55zM1344 272q0 46 -33 79t-79 33q-26 0 -46 -10l-290 -132q-28 -13 -37 -17 t-30.5 -17t-29.5 -23.5t-16 -29t-8 -40.5q0 -50 31.5 -82t81.5 -32q20 0 38 9l352 160q30 14 48 41.5t18 60.5zM1112 1024l-650 248q-24 8 -46 8q-53 0 -90.5 -37.5t-37.5 -90.5q0 -40 22.5 -73t59.5 -47l526 -200v-64h-640q-53 0 -90.5 -37.5t-37.5 -90.5t37.5 -90.5 t90.5 -37.5h535l233 106v198q0 63 46 106l111 102h-69zM1073 0q82 0 155 19l339 85q43 11 70 45.5t27 78.5v668q0 53 -37.5 90.5t-90.5 37.5h-308l-136 -126q-36 -33 -36 -82v-296q0 -46 33 -77t79 -31t79 35t33 81v208h32v-208q0 -70 -57 -114q52 -8 86.5 -48.5t34.5 -93.5 q0 -42 -23 -78t-61 -53l-310 -141h91z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1151 1536q61 0 116 -28t91 -77l572 -781q118 -159 118 -359v-355q0 -80 -56 -136t-136 -56h-384q-80 0 -136 56t-56 136v177l-286 143h-546q-80 0 -136 56t-56 136v32q0 119 84.5 203.5t203.5 84.5h420l42 128h-686q-100 0 -173.5 67.5t-81.5 166.5q-65 79 -65 182v32 q0 80 56 136t136 56h959zM1920 -64v355q0 157 -93 284l-573 781q-39 52 -103 52h-959q-26 0 -45 -19t-19 -45q0 -32 1.5 -49.5t9.5 -40.5t25 -43q10 31 35.5 50t56.5 19h832v-32h-832q-26 0 -45 -19t-19 -45q0 -44 3 -58q8 -44 44 -73t81 -29h640h91q40 0 68 -28t28 -68 q0 -15 -5 -30l-64 -192q-10 -29 -35 -47.5t-56 -18.5h-443q-66 0 -113 -47t-47 -113v-32q0 -26 19 -45t45 -19h561q16 0 29 -7l317 -158q24 -13 38.5 -36t14.5 -50v-197q0 -26 19 -45t45 -19h384q26 0 45 19t19 45z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M816 1408q-48 0 -79.5 -34t-31.5 -82q0 -14 3 -28l150 -624h-26l-116 482q-9 38 -39.5 62t-69.5 24q-47 0 -79 -34t-32 -81q0 -11 4 -29q3 -13 39 -161t68 -282t32 -138v-227l-307 230q-34 26 -77 26q-52 0 -89.5 -36.5t-37.5 -88.5q0 -67 56 -110l507 -379 q34 -26 76 -26h694q33 0 59 20.5t34 52.5l100 401q8 30 10 88t9 86l116 478q3 12 3 26q0 46 -33 79t-80 33q-38 0 -69 -25.5t-40 -62.5l-99 -408h-26l132 547q3 14 3 28q0 47 -32 80t-80 33q-38 0 -68.5 -24t-39.5 -62l-145 -602h-127l-164 682q-9 38 -39.5 62t-68.5 24z M1461 -256h-694q-85 0 -153 51l-507 380q-50 38 -78.5 94t-28.5 118q0 105 75 179t180 74q25 0 49.5 -5.5t41.5 -11t41 -20.5t35 -23t38.5 -29.5t37.5 -28.5l-123 512q-7 35 -7 59q0 93 60 162t152 79q14 87 80.5 144.5t155.5 57.5q83 0 148 -51.5t85 -132.5l103 -428 l83 348q20 81 85 132.5t148 51.5q87 0 152.5 -54t82.5 -139q93 -10 155 -78t62 -161q0 -30 -7 -57l-116 -477q-5 -22 -5 -67q0 -51 -13 -108l-101 -401q-19 -75 -79.5 -122.5t-137.5 -47.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M640 1408q-53 0 -90.5 -37.5t-37.5 -90.5v-512v-384l-151 202q-41 54 -107 54q-52 0 -89 -38t-37 -90q0 -43 26 -77l384 -512q38 -51 102 -51h718q22 0 39.5 13.5t22.5 34.5l92 368q24 96 24 194v217q0 41 -28 71t-68 30t-68 -28t-28 -68h-32v61q0 48 -32 81.5t-80 33.5 q-46 0 -79 -33t-33 -79v-64h-32v90q0 55 -37 94.5t-91 39.5q-53 0 -90.5 -37.5t-37.5 -90.5v-96h-32v570q0 55 -37 94.5t-91 39.5zM640 1536q107 0 181.5 -77.5t74.5 -184.5v-220q22 2 32 2q99 0 173 -69q47 21 99 21q113 0 184 -87q27 7 56 7q94 0 159 -67.5t65 -161.5 v-217q0 -116 -28 -225l-92 -368q-16 -64 -68 -104.5t-118 -40.5h-718q-60 0 -114.5 27.5t-90.5 74.5l-384 512q-51 68 -51 154q0 105 74.5 180.5t179.5 75.5q71 0 130 -35v547q0 106 75 181t181 75zM768 128v384h-32v-384h32zM1024 128v384h-32v-384h32zM1280 128v384h-32 v-384h32z" />
|
||||
<glyph unicode="" d="M1288 889q60 0 107 -23q141 -63 141 -226v-177q0 -94 -23 -186l-85 -339q-21 -86 -90.5 -140t-157.5 -54h-668q-106 0 -181 75t-75 181v401l-239 628q-17 45 -17 91q0 106 75 181t181 75q80 0 145.5 -45.5t93.5 -119.5l17 -44v113q0 106 75 181t181 75t181 -75t75 -181 v-261q27 5 48 5q69 0 127.5 -36.5t88.5 -98.5zM1072 896q-33 0 -60.5 -18t-41.5 -48l-74 -163l-71 -155h55q50 0 90 -31.5t50 -80.5l154 338q10 20 10 46q0 46 -33 79t-79 33zM1293 761q-22 0 -40.5 -8t-29 -16t-23.5 -29.5t-17 -30.5t-17 -37l-132 -290q-10 -20 -10 -46 q0 -46 33 -79t79 -33q33 0 60.5 18t41.5 48l160 352q9 18 9 38q0 50 -32 81.5t-82 31.5zM128 1120q0 -22 8 -46l248 -650v-69l102 111q43 46 106 46h198l106 233v535q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5v-640h-64l-200 526q-14 37 -47 59.5t-73 22.5 q-53 0 -90.5 -37.5t-37.5 -90.5zM1180 -128q44 0 78.5 27t45.5 70l85 339q19 73 19 155v91l-141 -310q-17 -38 -53 -61t-78 -23q-53 0 -93.5 34.5t-48.5 86.5q-44 -57 -114 -57h-208v32h208q46 0 81 33t35 79t-31 79t-77 33h-296q-49 0 -82 -36l-126 -136v-308 q0 -53 37.5 -90.5t90.5 -37.5h668z" />
|
||||
<glyph unicode="" horiz-adv-x="1973" d="M857 992v-117q0 -13 -9.5 -22t-22.5 -9h-298v-812q0 -13 -9 -22.5t-22 -9.5h-135q-13 0 -22.5 9t-9.5 23v812h-297q-13 0 -22.5 9t-9.5 22v117q0 14 9 23t23 9h793q13 0 22.5 -9.5t9.5 -22.5zM1895 995l77 -961q1 -13 -8 -24q-10 -10 -23 -10h-134q-12 0 -21 8.5 t-10 20.5l-46 588l-189 -425q-8 -19 -29 -19h-120q-20 0 -29 19l-188 427l-45 -590q-1 -12 -10 -20.5t-21 -8.5h-135q-13 0 -23 10q-9 10 -9 24l78 961q1 12 10 20.5t21 8.5h142q20 0 29 -19l220 -520q10 -24 20 -51q3 7 9.5 24.5t10.5 26.5l221 520q9 19 29 19h141 q13 0 22 -8.5t10 -20.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1042 833q0 88 -60 121q-33 18 -117 18h-123v-281h162q66 0 102 37t36 105zM1094 548l205 -373q8 -17 -1 -31q-8 -16 -27 -16h-152q-20 0 -28 17l-194 365h-155v-350q0 -14 -9 -23t-23 -9h-134q-14 0 -23 9t-9 23v960q0 14 9 23t23 9h294q128 0 190 -24q85 -31 134 -109 t49 -180q0 -92 -42.5 -165.5t-115.5 -109.5q6 -10 9 -16zM896 1376q-150 0 -286 -58.5t-234.5 -157t-157 -234.5t-58.5 -286t58.5 -286t157 -234.5t234.5 -157t286 -58.5t286 58.5t234.5 157t157 234.5t58.5 286t-58.5 286t-157 234.5t-234.5 157t-286 58.5zM1792 640 q0 -182 -71 -348t-191 -286t-286 -191t-348 -71t-348 71t-286 191t-191 286t-71 348t71 348t191 286t286 191t348 71t348 -71t286 -191t191 -286t71 -348z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M605 303q153 0 257 104q14 18 3 36l-45 82q-6 13 -24 17q-16 2 -27 -11l-4 -3q-4 -4 -11.5 -10t-17.5 -13t-23.5 -14.5t-28.5 -13.5t-33.5 -9.5t-37.5 -3.5q-76 0 -125 50t-49 127q0 76 48 125.5t122 49.5q37 0 71.5 -14t50.5 -28l16 -14q11 -11 26 -10q16 2 24 14l53 78 q13 20 -2 39q-3 4 -11 12t-30 23.5t-48.5 28t-67.5 22.5t-86 10q-148 0 -246 -96.5t-98 -240.5q0 -146 97 -241.5t247 -95.5zM1235 303q153 0 257 104q14 18 4 36l-45 82q-8 14 -25 17q-16 2 -27 -11l-4 -3q-4 -4 -11.5 -10t-17.5 -13t-23.5 -14.5t-28.5 -13.5t-33.5 -9.5 t-37.5 -3.5q-76 0 -125 50t-49 127q0 76 48 125.5t122 49.5q37 0 71.5 -14t50.5 -28l16 -14q11 -11 26 -10q16 2 24 14l53 78q13 20 -2 39q-3 4 -11 12t-30 23.5t-48.5 28t-67.5 22.5t-86 10q-147 0 -245.5 -96.5t-98.5 -240.5q0 -146 97 -241.5t247 -95.5zM896 1376 q-150 0 -286 -58.5t-234.5 -157t-157 -234.5t-58.5 -286t58.5 -286t157 -234.5t234.5 -157t286 -58.5t286 58.5t234.5 157t157 234.5t58.5 286t-58.5 286t-157 234.5t-234.5 157t-286 58.5zM896 1536q182 0 348 -71t286 -191t191 -286t71 -348t-71 -348t-191 -286t-286 -191 t-348 -71t-348 71t-286 191t-191 286t-71 348t71 348t191 286t286 191t348 71z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M736 736l384 -384l-384 -384l-672 672l672 672l168 -168l-96 -96l-72 72l-480 -480l480 -480l193 193l-289 287zM1312 1312l672 -672l-672 -672l-168 168l96 96l72 -72l480 480l-480 480l-193 -193l289 -287l-96 -96l-384 384z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M717 182l271 271l-279 279l-88 -88l192 -191l-96 -96l-279 279l279 279l40 -40l87 87l-127 128l-454 -454zM1075 190l454 454l-454 454l-271 -271l279 -279l88 88l-192 191l96 96l279 -279l-279 -279l-40 40l-87 -88zM1792 640q0 -182 -71 -348t-191 -286t-286 -191 t-348 -71t-348 71t-286 191t-191 286t-71 348t71 348t191 286t286 191t348 71t348 -71t286 -191t191 -286t71 -348z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M651 539q0 -39 -27.5 -66.5t-65.5 -27.5q-39 0 -66.5 27.5t-27.5 66.5q0 38 27.5 65.5t66.5 27.5q38 0 65.5 -27.5t27.5 -65.5zM1805 540q0 -39 -27.5 -66.5t-66.5 -27.5t-66.5 27.5t-27.5 66.5t27.5 66t66.5 27t66.5 -27t27.5 -66zM765 539q0 79 -56.5 136t-136.5 57 t-136.5 -56.5t-56.5 -136.5t56.5 -136.5t136.5 -56.5t136.5 56.5t56.5 136.5zM1918 540q0 80 -56.5 136.5t-136.5 56.5q-79 0 -136 -56.5t-57 -136.5t56.5 -136.5t136.5 -56.5t136.5 56.5t56.5 136.5zM850 539q0 -116 -81.5 -197.5t-196.5 -81.5q-116 0 -197.5 82t-81.5 197 t82 196.5t197 81.5t196.5 -81.5t81.5 -196.5zM2004 540q0 -115 -81.5 -196.5t-197.5 -81.5q-115 0 -196.5 81.5t-81.5 196.5t81.5 196.5t196.5 81.5q116 0 197.5 -81.5t81.5 -196.5zM1040 537q0 191 -135.5 326.5t-326.5 135.5q-125 0 -231 -62t-168 -168.5t-62 -231.5 t62 -231.5t168 -168.5t231 -62q191 0 326.5 135.5t135.5 326.5zM1708 1110q-254 111 -556 111q-319 0 -573 -110q117 0 223 -45.5t182.5 -122.5t122 -183t45.5 -223q0 115 43.5 219.5t118 180.5t177.5 123t217 50zM2187 537q0 191 -135 326.5t-326 135.5t-326.5 -135.5 t-135.5 -326.5t135.5 -326.5t326.5 -135.5t326 135.5t135 326.5zM1921 1103h383q-44 -51 -75 -114.5t-40 -114.5q110 -151 110 -337q0 -156 -77 -288t-209 -208.5t-287 -76.5q-133 0 -249 56t-196 155q-47 -56 -129 -179q-11 22 -53.5 82.5t-74.5 97.5 q-80 -99 -196.5 -155.5t-249.5 -56.5q-155 0 -287 76.5t-209 208.5t-77 288q0 186 110 337q-9 51 -40 114.5t-75 114.5h365q149 100 355 156.5t432 56.5q224 0 421 -56t348 -157z" />
|
||||
<glyph unicode="" horiz-adv-x="1280" d="M640 629q-188 0 -321 133t-133 320q0 188 133 321t321 133t321 -133t133 -321q0 -187 -133 -320t-321 -133zM640 1306q-92 0 -157.5 -65.5t-65.5 -158.5q0 -92 65.5 -157.5t157.5 -65.5t157.5 65.5t65.5 157.5q0 93 -65.5 158.5t-157.5 65.5zM1163 574q13 -27 15 -49.5 t-4.5 -40.5t-26.5 -38.5t-42.5 -37t-61.5 -41.5q-115 -73 -315 -94l73 -72l267 -267q30 -31 30 -74t-30 -73l-12 -13q-31 -30 -74 -30t-74 30q-67 68 -267 268l-267 -268q-31 -30 -74 -30t-73 30l-12 13q-31 30 -31 73t31 74l267 267l72 72q-203 21 -317 94 q-39 25 -61.5 41.5t-42.5 37t-26.5 38.5t-4.5 40.5t15 49.5q10 20 28 35t42 22t56 -2t65 -35q5 -4 15 -11t43 -24.5t69 -30.5t92 -24t113 -11q91 0 174 25.5t120 50.5l38 25q33 26 65 35t56 2t42 -22t28 -35z" />
|
||||
<glyph unicode="" d="M927 956q0 -66 -46.5 -112.5t-112.5 -46.5t-112.5 46.5t-46.5 112.5t46.5 112.5t112.5 46.5t112.5 -46.5t46.5 -112.5zM1141 593q-10 20 -28 32t-47.5 9.5t-60.5 -27.5q-10 -8 -29 -20t-81 -32t-127 -20t-124 18t-86 36l-27 18q-31 25 -60.5 27.5t-47.5 -9.5t-28 -32 q-22 -45 -2 -74.5t87 -73.5q83 -53 226 -67l-51 -52q-142 -142 -191 -190q-22 -22 -22 -52.5t22 -52.5l9 -9q22 -22 52.5 -22t52.5 22l191 191q114 -115 191 -191q22 -22 52.5 -22t52.5 22l9 9q22 22 22 52.5t-22 52.5l-191 190l-52 52q141 14 225 67q67 44 87 73.5t-2 74.5 zM1092 956q0 134 -95 229t-229 95t-229 -95t-95 -229t95 -229t229 -95t229 95t95 229zM1536 1120v-960q0 -119 -84.5 -203.5t-203.5 -84.5h-960q-119 0 -203.5 84.5t-84.5 203.5v960q0 119 84.5 203.5t203.5 84.5h960q119 0 203.5 -84.5t84.5 -203.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1720" d="M1565 1408q65 0 110 -45.5t45 -110.5v-519q0 -176 -68 -336t-182.5 -275t-274 -182.5t-334.5 -67.5q-176 0 -335.5 67.5t-274.5 182.5t-183 275t-68 336v519q0 64 46 110t110 46h1409zM861 344q47 0 82 33l404 388q37 35 37 85q0 49 -34.5 83.5t-83.5 34.5q-47 0 -82 -33 l-323 -310l-323 310q-35 33 -81 33q-49 0 -83.5 -34.5t-34.5 -83.5q0 -51 36 -85l405 -388q33 -33 81 -33z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M1494 -103l-295 695q-25 -49 -158.5 -305.5t-198.5 -389.5q-1 -1 -27.5 -0.5t-26.5 1.5q-82 193 -255.5 587t-259.5 596q-21 50 -66.5 107.5t-103.5 100.5t-102 43q0 5 -0.5 24t-0.5 27h583v-50q-39 -2 -79.5 -16t-66.5 -43t-10 -64q26 -59 216.5 -499t235.5 -540 q31 61 140 266.5t131 247.5q-19 39 -126 281t-136 295q-38 69 -201 71v50l513 -1v-47q-60 -2 -93.5 -25t-12.5 -69q33 -70 87 -189.5t86 -187.5q110 214 173 363q24 55 -10 79.5t-129 26.5q1 7 1 25v24q64 0 170.5 0.5t180 1t92.5 0.5v-49q-62 -2 -119 -33t-90 -81 l-213 -442q13 -33 127.5 -290t121.5 -274l441 1017q-14 38 -49.5 62.5t-65 31.5t-55.5 8v50l460 -4l1 -2l-1 -44q-139 -4 -201 -145q-526 -1216 -559 -1291h-49z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M949 643q0 -26 -16.5 -45t-41.5 -19q-26 0 -45 16.5t-19 41.5q0 26 17 45t42 19t44 -16.5t19 -41.5zM964 585l350 581q-9 -8 -67.5 -62.5t-125.5 -116.5t-136.5 -127t-117 -110.5t-50.5 -51.5l-349 -580q7 7 67 62t126 116.5t136 127t117 111t50 50.5zM1611 640 q0 -201 -104 -371q-3 2 -17 11t-26.5 16.5t-16.5 7.5q-13 0 -13 -13q0 -10 59 -44q-74 -112 -184.5 -190.5t-241.5 -110.5l-16 67q-1 10 -15 10q-5 0 -8 -5.5t-2 -9.5l16 -68q-72 -15 -146 -15q-199 0 -372 105q1 2 13 20.5t21.5 33.5t9.5 19q0 13 -13 13q-6 0 -17 -14.5 t-22.5 -34.5t-13.5 -23q-113 75 -192 187.5t-110 244.5l69 15q10 3 10 15q0 5 -5.5 8t-10.5 2l-68 -15q-14 72 -14 139q0 206 109 379q2 -1 18.5 -12t30 -19t17.5 -8q13 0 13 12q0 6 -12.5 15.5t-32.5 21.5l-20 12q77 112 189 189t244 107l15 -67q2 -10 15 -10q5 0 8 5.5 t2 10.5l-15 66q71 13 134 13q204 0 379 -109q-39 -56 -39 -65q0 -13 12 -13q11 0 48 64q111 -75 187.5 -186t107.5 -241l-56 -12q-10 -2 -10 -16q0 -5 5.5 -8t9.5 -2l57 13q14 -72 14 -140zM1696 640q0 163 -63.5 311t-170.5 255t-255 170.5t-311 63.5t-311 -63.5 t-255 -170.5t-170.5 -255t-63.5 -311t63.5 -311t170.5 -255t255 -170.5t311 -63.5t311 63.5t255 170.5t170.5 255t63.5 311zM1792 640q0 -182 -71 -348t-191 -286t-286 -191t-348 -71t-348 71t-286 191t-191 286t-71 348t71 348t191 286t286 191t348 71t348 -71t286 -191 t191 -286t71 -348z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M893 1536q240 2 451 -120q232 -134 352 -372l-742 39q-160 9 -294 -74.5t-185 -229.5l-276 424q128 159 311 245.5t383 87.5zM146 1131l337 -663q72 -143 211 -217t293 -45l-230 -451q-212 33 -385 157.5t-272.5 316t-99.5 411.5q0 267 146 491zM1732 962 q58 -150 59.5 -310.5t-48.5 -306t-153 -272t-246 -209.5q-230 -133 -498 -119l405 623q88 131 82.5 290.5t-106.5 277.5zM896 942q125 0 213.5 -88.5t88.5 -213.5t-88.5 -213.5t-213.5 -88.5t-213.5 88.5t-88.5 213.5t88.5 213.5t213.5 88.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M903 -256q-283 0 -504.5 150.5t-329.5 398.5q-58 131 -67 301t26 332.5t111 312t179 242.5l-11 -281q11 14 68 15.5t70 -15.5q42 81 160.5 138t234.5 59q-54 -45 -119.5 -148.5t-58.5 -163.5q25 -8 62.5 -13.5t63 -7.5t68 -4t50.5 -3q15 -5 9.5 -45.5t-30.5 -75.5 q-5 -7 -16.5 -18.5t-56.5 -35.5t-101 -34l15 -189l-139 67q-18 -43 -7.5 -81.5t36 -66.5t65.5 -41.5t81 -6.5q51 9 98 34.5t83.5 45t73.5 17.5q61 -4 89.5 -33t19.5 -65q-1 -2 -2.5 -5.5t-8.5 -12.5t-18 -15.5t-31.5 -10.5t-46.5 -1q-60 -95 -144.5 -135.5t-209.5 -29.5 q74 -61 162.5 -82.5t168.5 -6t154.5 52t128 87.5t80.5 104q43 91 39 192.5t-37.5 188.5t-78.5 125q87 -38 137 -79.5t77 -112.5q15 170 -57.5 343t-209.5 284q265 -77 412 -279.5t151 -517.5q2 -127 -40.5 -255t-123.5 -238t-189 -196t-247.5 -135.5t-288.5 -49.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1493 1308q-165 110 -359 110q-155 0 -293 -73t-240 -200q-75 -93 -119.5 -218t-48.5 -266v-42q4 -141 48.5 -266t119.5 -218q102 -127 240 -200t293 -73q194 0 359 110q-121 -108 -274.5 -168t-322.5 -60q-29 0 -43 1q-175 8 -333 82t-272 193t-181 281t-67 339 q0 182 71 348t191 286t286 191t348 71h3q168 -1 320.5 -60.5t273.5 -167.5zM1792 640q0 -192 -77 -362.5t-213 -296.5q-104 -63 -222 -63q-137 0 -255 84q154 56 253.5 233t99.5 405q0 227 -99 404t-253 234q119 83 254 83q119 0 226 -65q135 -125 210.5 -295t75.5 -361z " />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1792 599q0 -56 -7 -104h-1151q0 -146 109.5 -244.5t257.5 -98.5q99 0 185.5 46.5t136.5 130.5h423q-56 -159 -170.5 -281t-267.5 -188.5t-321 -66.5q-187 0 -356 83q-228 -116 -394 -116q-237 0 -237 263q0 115 45 275q17 60 109 229q199 360 475 606 q-184 -79 -427 -354q63 274 283.5 449.5t501.5 175.5q30 0 45 -1q255 117 433 117q64 0 116 -13t94.5 -40.5t66.5 -76.5t24 -115q0 -116 -75 -286q101 -182 101 -390zM1722 1239q0 83 -53 132t-137 49q-108 0 -254 -70q121 -47 222.5 -131.5t170.5 -195.5q51 135 51 216z M128 2q0 -86 48.5 -132.5t134.5 -46.5q115 0 266 83q-122 72 -213.5 183t-137.5 245q-98 -205 -98 -332zM632 715h728q-5 142 -113 237t-251 95q-144 0 -251.5 -95t-112.5 -237z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1792 288v960q0 13 -9.5 22.5t-22.5 9.5h-1600q-13 0 -22.5 -9.5t-9.5 -22.5v-960q0 -13 9.5 -22.5t22.5 -9.5h1600q13 0 22.5 9.5t9.5 22.5zM1920 1248v-960q0 -66 -47 -113t-113 -47h-736v-128h352q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-832q-14 0 -23 9t-9 23 v64q0 14 9 23t23 9h352v128h-736q-66 0 -113 47t-47 113v960q0 66 47 113t113 47h1600q66 0 113 -47t47 -113z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M138 1408h197q-70 -64 -126 -149q-36 -56 -59 -115t-30 -125.5t-8.5 -120t10.5 -132t21 -126t28 -136.5q4 -19 6 -28q51 -238 81 -329q57 -171 152 -275h-272q-48 0 -82 34t-34 82v1304q0 48 34 82t82 34zM1346 1408h308q48 0 82 -34t34 -82v-1304q0 -48 -34 -82t-82 -34 h-178q212 210 196 565l-469 -101q-2 -45 -12 -82t-31 -72t-59.5 -59.5t-93.5 -36.5q-123 -26 -199 40q-32 27 -53 61t-51.5 129t-64.5 258q-35 163 -45.5 263t-5.5 139t23 77q20 41 62.5 73t102.5 45q45 12 83.5 6.5t67 -17t54 -35t43 -48t34.5 -56.5l468 100 q-68 175 -180 287z" />
|
||||
<glyph unicode="" d="M1401 -11l-6 -6q-113 -114 -259 -175q-154 -64 -317 -64q-165 0 -317 64q-148 63 -259 175q-113 112 -175 258q-42 103 -54 189q-4 28 48 36q51 8 56 -20q1 -1 1 -4q18 -90 46 -159q50 -124 152 -226q98 -98 226 -152q132 -56 276 -56q143 0 276 56q128 55 225 152l6 6 q10 10 25 6q12 -3 33 -22q36 -37 17 -58zM929 604l-66 -66l63 -63q21 -21 -7 -49q-17 -17 -32 -17q-10 0 -19 10l-62 61l-66 -66q-5 -5 -15 -5q-15 0 -31 16l-2 2q-18 15 -18 29q0 7 8 17l66 65l-66 66q-16 16 14 45q18 18 31 18q6 0 13 -5l65 -66l65 65q18 17 48 -13 q27 -27 11 -44zM1400 547q0 -118 -46 -228q-45 -105 -126 -186q-80 -80 -187 -126t-228 -46t-228 46t-187 126q-82 82 -125 186q-15 32 -15 40h-1q-9 27 43 44q50 16 60 -12q37 -99 97 -167h1v339v2q3 136 102 232q105 103 253 103q147 0 251 -103t104 -249 q0 -147 -104.5 -251t-250.5 -104q-58 0 -112 16q-28 11 -13 61q16 51 44 43l14 -3q14 -3 32.5 -6t30.5 -3q104 0 176 71.5t72 174.5q0 101 -72 171q-71 71 -175 71q-107 0 -178 -80q-64 -72 -64 -160v-413q110 -67 242 -67q96 0 185 36.5t156 103.5t103.5 155t36.5 183 q0 198 -141 339q-140 140 -339 140q-200 0 -340 -140q-53 -53 -77 -87l-2 -2q-8 -11 -13 -15.5t-21.5 -9.5t-38.5 3q-21 5 -36.5 16.5t-15.5 26.5v680q0 15 10.5 26.5t27.5 11.5h877q30 0 30 -55t-30 -55h-811v-483h1q40 42 102 84t108 61q109 46 231 46q121 0 228 -46 t187 -126q81 -81 126 -186q46 -112 46 -229zM1369 1128q9 -8 9 -18t-5.5 -18t-16.5 -21q-26 -26 -39 -26q-9 0 -16 7q-106 91 -207 133q-128 56 -276 56q-133 0 -262 -49q-27 -10 -45 37q-9 25 -8 38q3 16 16 20q130 57 299 57q164 0 316 -64q137 -58 235 -152z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1551 60q15 6 26 3t11 -17.5t-15 -33.5q-13 -16 -44 -43.5t-95.5 -68t-141 -74t-188 -58t-229.5 -24.5q-119 0 -238 31t-209 76.5t-172.5 104t-132.5 105t-84 87.5q-8 9 -10 16.5t1 12t8 7t11.5 2t11.5 -4.5q192 -117 300 -166q389 -176 799 -90q190 40 391 135z M1758 175q11 -16 2.5 -69.5t-28.5 -102.5q-34 -83 -85 -124q-17 -14 -26 -9t0 24q21 45 44.5 121.5t6.5 98.5q-5 7 -15.5 11.5t-27 6t-29.5 2.5t-35 0t-31.5 -2t-31 -3t-22.5 -2q-6 -1 -13 -1.5t-11 -1t-8.5 -1t-7 -0.5h-5.5h-4.5t-3 0.5t-2 1.5l-1.5 3q-6 16 47 40t103 30 q46 7 108 1t76 -24zM1364 618q0 -31 13.5 -64t32 -58t37.5 -46t33 -32l13 -11l-227 -224q-40 37 -79 75.5t-58 58.5l-19 20q-11 11 -25 33q-38 -59 -97.5 -102.5t-127.5 -63.5t-140 -23t-137.5 21t-117.5 65.5t-83 113t-31 162.5q0 84 28 154t72 116.5t106.5 83t122.5 57 t130 34.5t119.5 18.5t99.5 6.5v127q0 65 -21 97q-34 53 -121 53q-6 0 -16.5 -1t-40.5 -12t-56 -29.5t-56 -59.5t-48 -96l-294 27q0 60 22 119t67 113t108 95t151.5 65.5t190.5 24.5q100 0 181 -25t129.5 -61.5t81 -83t45 -86t12.5 -73.5v-589zM692 597q0 -86 70 -133 q66 -44 139 -22q84 25 114 123q14 45 14 101v162q-59 -2 -111 -12t-106.5 -33.5t-87 -71t-32.5 -114.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1536 1280q52 0 90 -38t38 -90v-1280q0 -52 -38 -90t-90 -38h-1408q-52 0 -90 38t-38 90v1280q0 52 38 90t90 38h128v96q0 66 47 113t113 47h64q66 0 113 -47t47 -113v-96h384v96q0 66 47 113t113 47h64q66 0 113 -47t47 -113v-96h128zM1152 1376v-288q0 -14 9 -23t23 -9 h64q14 0 23 9t9 23v288q0 14 -9 23t-23 9h-64q-14 0 -23 -9t-9 -23zM384 1376v-288q0 -14 9 -23t23 -9h64q14 0 23 9t9 23v288q0 14 -9 23t-23 9h-64q-14 0 -23 -9t-9 -23zM1536 -128v1024h-1408v-1024h1408zM896 448h224q14 0 23 -9t9 -23v-64q0 -14 -9 -23t-23 -9h-224 v-224q0 -14 -9 -23t-23 -9h-64q-14 0 -23 9t-9 23v224h-224q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h224v224q0 14 9 23t23 9h64q14 0 23 -9t9 -23v-224z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1152 416v-64q0 -14 -9 -23t-23 -9h-576q-14 0 -23 9t-9 23v64q0 14 9 23t23 9h576q14 0 23 -9t9 -23zM128 -128h1408v1024h-1408v-1024zM512 1088v288q0 14 -9 23t-23 9h-64q-14 0 -23 -9t-9 -23v-288q0 -14 9 -23t23 -9h64q14 0 23 9t9 23zM1280 1088v288q0 14 -9 23 t-23 9h-64q-14 0 -23 -9t-9 -23v-288q0 -14 9 -23t23 -9h64q14 0 23 9t9 23zM1664 1152v-1280q0 -52 -38 -90t-90 -38h-1408q-52 0 -90 38t-38 90v1280q0 52 38 90t90 38h128v96q0 66 47 113t113 47h64q66 0 113 -47t47 -113v-96h384v96q0 66 47 113t113 47h64q66 0 113 -47 t47 -113v-96h128q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1111 151l-46 -46q-9 -9 -22 -9t-23 9l-188 189l-188 -189q-10 -9 -23 -9t-22 9l-46 46q-9 9 -9 22t9 23l189 188l-189 188q-9 10 -9 23t9 22l46 46q9 9 22 9t23 -9l188 -188l188 188q10 9 23 9t22 -9l46 -46q9 -9 9 -22t-9 -23l-188 -188l188 -188q9 -10 9 -23t-9 -22z M128 -128h1408v1024h-1408v-1024zM512 1088v288q0 14 -9 23t-23 9h-64q-14 0 -23 -9t-9 -23v-288q0 -14 9 -23t23 -9h64q14 0 23 9t9 23zM1280 1088v288q0 14 -9 23t-23 9h-64q-14 0 -23 -9t-9 -23v-288q0 -14 9 -23t23 -9h64q14 0 23 9t9 23zM1664 1152v-1280 q0 -52 -38 -90t-90 -38h-1408q-52 0 -90 38t-38 90v1280q0 52 38 90t90 38h128v96q0 66 47 113t113 47h64q66 0 113 -47t47 -113v-96h384v96q0 66 47 113t113 47h64q66 0 113 -47t47 -113v-96h128q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1303 572l-512 -512q-10 -9 -23 -9t-23 9l-288 288q-9 10 -9 23t9 22l46 46q9 9 22 9t23 -9l220 -220l444 444q10 9 23 9t22 -9l46 -46q9 -9 9 -22t-9 -23zM128 -128h1408v1024h-1408v-1024zM512 1088v288q0 14 -9 23t-23 9h-64q-14 0 -23 -9t-9 -23v-288q0 -14 9 -23 t23 -9h64q14 0 23 9t9 23zM1280 1088v288q0 14 -9 23t-23 9h-64q-14 0 -23 -9t-9 -23v-288q0 -14 9 -23t23 -9h64q14 0 23 9t9 23zM1664 1152v-1280q0 -52 -38 -90t-90 -38h-1408q-52 0 -90 38t-38 90v1280q0 52 38 90t90 38h128v96q0 66 47 113t113 47h64q66 0 113 -47 t47 -113v-96h384v96q0 66 47 113t113 47h64q66 0 113 -47t47 -113v-96h128q52 0 90 -38t38 -90z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M448 1536q26 0 45 -19t19 -45v-891l536 429q17 14 40 14q26 0 45 -19t19 -45v-379l536 429q17 14 40 14q26 0 45 -19t19 -45v-1152q0 -26 -19 -45t-45 -19h-1664q-26 0 -45 19t-19 45v1664q0 26 19 45t45 19h384z" />
|
||||
<glyph unicode="" horiz-adv-x="1024" d="M512 448q66 0 128 15v-655q0 -26 -19 -45t-45 -19h-128q-26 0 -45 19t-19 45v655q61 -15 128 -15zM512 1536q212 0 362 -150t150 -362t-150 -362t-362 -150t-362 150t-150 362t150 362t362 150zM512 1312q14 0 23 9t9 23t-9 23t-23 9q-146 0 -249 -103t-103 -249 q0 -14 9 -23t23 -9t23 9t9 23q0 119 84.5 203.5t203.5 84.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1745 1239q10 -10 10 -23t-10 -23l-141 -141q-28 -28 -68 -28h-1344q-26 0 -45 19t-19 45v256q0 26 19 45t45 19h576v64q0 26 19 45t45 19h128q26 0 45 -19t19 -45v-64h512q40 0 68 -28zM768 320h256v-512q0 -26 -19 -45t-45 -19h-128q-26 0 -45 19t-19 45v512zM1600 768 q26 0 45 -19t19 -45v-256q0 -26 -19 -45t-45 -19h-1344q-40 0 -68 28l-141 141q-10 10 -10 23t10 23l141 141q28 28 68 28h512v192h256v-192h576z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M2020 1525q28 -20 28 -53v-1408q0 -20 -11 -36t-29 -23l-640 -256q-24 -11 -48 0l-616 246l-616 -246q-10 -5 -24 -5q-19 0 -36 11q-28 20 -28 53v1408q0 20 11 36t29 23l640 256q24 11 48 0l616 -246l616 246q32 13 60 -6zM736 1390v-1270l576 -230v1270zM128 1173 v-1270l544 217v1270zM1920 107v1270l-544 -217v-1270z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M512 1536q13 0 22.5 -9.5t9.5 -22.5v-1472q0 -20 -17 -28l-480 -256q-7 -4 -15 -4q-13 0 -22.5 9.5t-9.5 22.5v1472q0 20 17 28l480 256q7 4 15 4zM1760 1536q13 0 22.5 -9.5t9.5 -22.5v-1472q0 -20 -17 -28l-480 -256q-7 -4 -15 -4q-13 0 -22.5 9.5t-9.5 22.5v1472 q0 20 17 28l480 256q7 4 15 4zM640 1536q8 0 14 -3l512 -256q18 -10 18 -29v-1472q0 -13 -9.5 -22.5t-22.5 -9.5q-8 0 -14 3l-512 256q-18 10 -18 29v1472q0 13 9.5 22.5t22.5 9.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M640 640q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM1024 640q0 53 -37.5 90.5t-90.5 37.5t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM1408 640q0 53 -37.5 90.5t-90.5 37.5 t-90.5 -37.5t-37.5 -90.5t37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5zM1792 640q0 -174 -120 -321.5t-326 -233t-450 -85.5q-110 0 -211 18q-173 -173 -435 -229q-52 -10 -86 -13q-12 -1 -22 6t-13 18q-4 15 20 37q5 5 23.5 21.5t25.5 23.5t23.5 25.5t24 31.5t20.5 37 t20 48t14.5 57.5t12.5 72.5q-146 90 -229.5 216.5t-83.5 269.5q0 174 120 321.5t326 233t450 85.5t450 -85.5t326 -233t120 -321.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M640 640q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1024 640q0 -53 -37.5 -90.5t-90.5 -37.5t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM1408 640q0 -53 -37.5 -90.5t-90.5 -37.5 t-90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5t90.5 -37.5t37.5 -90.5zM896 1152q-204 0 -381.5 -69.5t-282 -187.5t-104.5 -255q0 -112 71.5 -213.5t201.5 -175.5l87 -50l-27 -96q-24 -91 -70 -172q152 63 275 171l43 38l57 -6q69 -8 130 -8q204 0 381.5 69.5t282 187.5 t104.5 255t-104.5 255t-282 187.5t-381.5 69.5zM1792 640q0 -174 -120 -321.5t-326 -233t-450 -85.5q-70 0 -145 8q-198 -175 -460 -242q-49 -14 -114 -22h-5q-15 0 -27 10.5t-16 27.5v1q-3 4 -0.5 12t2 10t4.5 9.5l6 9t7 8.5t8 9q7 8 31 34.5t34.5 38t31 39.5t32.5 51 t27 59t26 76q-157 89 -247.5 220t-90.5 281q0 130 71 248.5t191 204.5t286 136.5t348 50.5t348 -50.5t286 -136.5t191 -204.5t71 -248.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1024" d="M512 345l512 295v-591l-512 -296v592zM0 640v-591l512 296zM512 1527v-591l-512 -296v591zM512 936l512 295v-591z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1709 1018q-10 -236 -332 -651q-333 -431 -562 -431q-142 0 -240 263q-44 160 -132 482q-72 262 -157 262q-18 0 -127 -76l-77 98q24 21 108 96.5t130 115.5q156 138 241 146q95 9 153 -55.5t81 -203.5q44 -287 66 -373q55 -249 120 -249q51 0 154 161q101 161 109 246 q13 139 -109 139q-57 0 -121 -26q120 393 459 382q251 -8 236 -326z" />
|
||||
<glyph unicode="" d="M0 1408h1536v-1536h-1536v1536zM1085 293l-221 631l221 297h-634l221 -297l-221 -631l317 -304z" />
|
||||
<glyph unicode="" d="M0 1408h1536v-1536h-1536v1536zM908 1088l-12 -33l75 -83l-31 -114l25 -25l107 57l107 -57l25 25l-31 114l75 83l-12 33h-95l-53 96h-32l-53 -96h-95zM641 925q32 0 44.5 -16t11.5 -63l174 21q0 55 -17.5 92.5t-50.5 56t-69 25.5t-85 7q-133 0 -199 -57.5t-66 -182.5v-72 h-96v-128h76q20 0 20 -8v-382q0 -14 -5 -20t-18 -7l-73 -7v-88h448v86l-149 14q-6 1 -8.5 1.5t-3.5 2.5t-0.5 4t1 7t0.5 10v387h191l38 128h-231q-6 0 -2 6t4 9v80q0 27 1.5 40.5t7.5 28t19.5 20t36.5 5.5zM1248 96v86l-54 9q-7 1 -9.5 2.5t-2.5 3t1 7.5t1 12v520h-275 l-23 -101l83 -22q23 -7 23 -27v-370q0 -14 -6 -18.5t-20 -6.5l-70 -9v-86h352z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1792 690q0 -58 -29.5 -105.5t-79.5 -72.5q12 -46 12 -96q0 -155 -106.5 -287t-290.5 -208.5t-400 -76.5t-399.5 76.5t-290 208.5t-106.5 287q0 47 11 94q-51 25 -82 73.5t-31 106.5q0 82 58 140.5t141 58.5q85 0 145 -63q218 152 515 162l116 521q3 13 15 21t26 5 l369 -81q18 37 54 59.5t79 22.5q62 0 106 -43.5t44 -105.5t-44 -106t-106 -44t-105.5 43.5t-43.5 105.5l-334 74l-104 -472q300 -9 519 -160q58 61 143 61q83 0 141 -58.5t58 -140.5zM418 491q0 -62 43.5 -106t105.5 -44t106 44t44 106t-44 105.5t-106 43.5q-61 0 -105 -44 t-44 -105zM1228 136q11 11 11 26t-11 26q-10 10 -25 10t-26 -10q-41 -42 -121 -62t-160 -20t-160 20t-121 62q-11 10 -26 10t-25 -10q-11 -10 -11 -25.5t11 -26.5q43 -43 118.5 -68t122.5 -29.5t91 -4.5t91 4.5t122.5 29.5t118.5 68zM1225 341q62 0 105.5 44t43.5 106 q0 61 -44 105t-105 44q-62 0 -106 -43.5t-44 -105.5t44 -106t106 -44z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M69 741h1q16 126 58.5 241.5t115 217t167.5 176t223.5 117.5t276.5 43q231 0 414 -105.5t294 -303.5q104 -187 104 -442v-188h-1125q1 -111 53.5 -192.5t136.5 -122.5t189.5 -57t213 -3t208 46.5t173.5 84.5v-377q-92 -55 -229.5 -92t-312.5 -38t-316 53 q-189 73 -311.5 249t-124.5 372q-3 242 111 412t325 268q-48 -60 -78 -125.5t-46 -159.5h635q8 77 -8 140t-47 101.5t-70.5 66.5t-80.5 41t-75 20.5t-56 8.5l-22 1q-135 -5 -259.5 -44.5t-223.5 -104.5t-176 -140.5t-138 -163.5z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M0 32v608h2304v-608q0 -66 -47 -113t-113 -47h-1984q-66 0 -113 47t-47 113zM640 256v-128h384v128h-384zM256 256v-128h256v128h-256zM2144 1408q66 0 113 -47t47 -113v-224h-2304v224q0 66 47 113t113 47h1984z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1549 857q55 0 85.5 -28.5t30.5 -83.5t-34 -82t-91 -27h-136v-177h-25v398h170zM1710 267l-4 -11l-5 -10q-113 -230 -330.5 -366t-474.5 -136q-182 0 -348 71t-286 191t-191 286t-71 348t71 348t191 286t286 191t348 71q244 0 454.5 -124t329.5 -338l2 -4l8 -16 q-30 -15 -136.5 -68.5t-163.5 -84.5q-6 -3 -479 -268q384 -183 799 -366zM896 -234q250 0 462.5 132.5t322.5 357.5l-287 129q-72 -140 -206 -222t-292 -82q-151 0 -280 75t-204 204t-75 280t75 280t204 204t280 75t280 -73.5t204 -204.5l280 143q-116 208 -321 329 t-443 121q-119 0 -232.5 -31.5t-209 -87.5t-176.5 -137t-137 -176.5t-87.5 -209t-31.5 -232.5t31.5 -232.5t87.5 -209t137 -176.5t176.5 -137t209 -87.5t232.5 -31.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1427 827l-614 386l92 151h855zM405 562l-184 116v858l1183 -743zM1424 697l147 -95v-858l-532 335zM1387 718l-500 -802h-855l356 571z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M640 528v224q0 16 -16 16h-96q-16 0 -16 -16v-224q0 -16 16 -16h96q16 0 16 16zM1152 528v224q0 16 -16 16h-96q-16 0 -16 -16v-224q0 -16 16 -16h96q16 0 16 16zM1664 496v-752h-640v320q0 80 -56 136t-136 56t-136 -56t-56 -136v-320h-640v752q0 16 16 16h96 q16 0 16 -16v-112h128v624q0 16 16 16h96q16 0 16 -16v-112h128v112q0 16 16 16h96q16 0 16 -16v-112h128v112q0 16 16 16h16v393q-32 19 -32 55q0 26 19 45t45 19t45 -19t19 -45q0 -36 -32 -55v-9h272q16 0 16 -16v-224q0 -16 -16 -16h-272v-128h16q16 0 16 -16v-112h128 v112q0 16 16 16h96q16 0 16 -16v-112h128v112q0 16 16 16h96q16 0 16 -16v-624h128v112q0 16 16 16h96q16 0 16 -16z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M2288 731q16 -8 16 -27t-16 -27l-320 -192q-8 -5 -16 -5q-9 0 -16 4q-16 10 -16 28v128h-858q37 -58 83 -165q16 -37 24.5 -55t24 -49t27 -47t27 -34t31.5 -26t33 -8h96v96q0 14 9 23t23 9h320q14 0 23 -9t9 -23v-320q0 -14 -9 -23t-23 -9h-320q-14 0 -23 9t-9 23v96h-96 q-32 0 -61 10t-51 23.5t-45 40.5t-37 46t-33.5 57t-28.5 57.5t-28 60.5q-23 53 -37 81.5t-36 65t-44.5 53.5t-46.5 17h-360q-22 -84 -91 -138t-157 -54q-106 0 -181 75t-75 181t75 181t181 75q88 0 157 -54t91 -138h104q24 0 46.5 17t44.5 53.5t36 65t37 81.5q19 41 28 60.5 t28.5 57.5t33.5 57t37 46t45 40.5t51 23.5t61 10h107q21 57 70 92.5t111 35.5q80 0 136 -56t56 -136t-56 -136t-136 -56q-62 0 -111 35.5t-70 92.5h-107q-17 0 -33 -8t-31.5 -26t-27 -34t-27 -47t-24 -49t-24.5 -55q-46 -107 -83 -165h1114v128q0 18 16 28t32 -1z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1150 774q0 -56 -39.5 -95t-95.5 -39h-253v269h253q56 0 95.5 -39.5t39.5 -95.5zM1329 774q0 130 -91.5 222t-222.5 92h-433v-896h180v269h253q130 0 222 91.5t92 221.5zM1792 640q0 -182 -71 -348t-191 -286t-286 -191t-348 -71t-348 71t-286 191t-191 286t-71 348 t71 348t191 286t286 191t348 71t348 -71t286 -191t191 -286t71 -348z" />
|
||||
<glyph unicode="" horiz-adv-x="2304" d="M1645 438q0 59 -34 106.5t-87 68.5q-7 -45 -23 -92q-7 -24 -27.5 -38t-44.5 -14q-12 0 -24 3q-31 10 -45 38.5t-4 58.5q23 71 23 143q0 123 -61 227.5t-166 165.5t-228 61q-134 0 -247 -73t-167 -194q108 -28 188 -106q22 -23 22 -55t-22 -54t-54 -22t-55 22 q-75 75 -180 75q-106 0 -181 -74.5t-75 -180.5t75 -180.5t181 -74.5h1046q79 0 134.5 55.5t55.5 133.5zM1798 438q0 -142 -100.5 -242t-242.5 -100h-1046q-169 0 -289 119.5t-120 288.5q0 153 100 267t249 136q62 184 221 298t354 114q235 0 408.5 -158.5t196.5 -389.5 q116 -25 192.5 -118.5t76.5 -214.5zM2048 438q0 -175 -97 -319q-23 -33 -64 -33q-24 0 -43 13q-26 17 -32 48.5t12 57.5q71 104 71 233t-71 233q-18 26 -12 57t32 49t57.5 11.5t49.5 -32.5q97 -142 97 -318zM2304 438q0 -244 -134 -443q-23 -34 -64 -34q-23 0 -42 13 q-26 18 -32.5 49t11.5 57q108 164 108 358q0 195 -108 357q-18 26 -11.5 57.5t32.5 48.5q26 18 57 12t49 -33q134 -198 134 -442z" />
|
||||
<glyph unicode="" d="M1500 -13q0 -89 -63 -152.5t-153 -63.5t-153.5 63.5t-63.5 152.5q0 90 63.5 153.5t153.5 63.5t153 -63.5t63 -153.5zM1267 268q-115 -15 -192.5 -102.5t-77.5 -205.5q0 -74 33 -138q-146 -78 -379 -78q-109 0 -201 21t-153.5 54.5t-110.5 76.5t-76 85t-44.5 83 t-23.5 66.5t-6 39.5q0 19 4.5 42.5t18.5 56t36.5 58t64 43.5t94.5 18t94 -17.5t63 -41t35.5 -53t17.5 -49t4 -33.5q0 -34 -23 -81q28 -27 82 -42t93 -17l40 -1q115 0 190 51t75 133q0 26 -9 48.5t-31.5 44.5t-49.5 41t-74 44t-93.5 47.5t-119.5 56.5q-28 13 -43 20 q-116 55 -187 100t-122.5 102t-72 125.5t-20.5 162.5q0 78 20.5 150t66 137.5t112.5 114t166.5 77t221.5 28.5q120 0 220 -26t164.5 -67t109.5 -94t64 -105.5t19 -103.5q0 -46 -15 -82.5t-36.5 -58t-48.5 -36t-49 -19.5t-39 -5h-8h-32t-39 5t-44 14t-41 28t-37 46t-24 70.5 t-10 97.5q-15 16 -59 25.5t-81 10.5l-37 1q-68 0 -117.5 -31t-70.5 -70t-21 -76q0 -24 5 -43t24 -46t53 -51t97 -53.5t150 -58.5q76 -25 138.5 -53.5t109 -55.5t83 -59t60.5 -59.5t41 -62.5t26.5 -62t14.5 -63.5t6 -62t1 -62.5z" />
|
||||
<glyph unicode="" d="M704 352v576q0 14 -9 23t-23 9h-256q-14 0 -23 -9t-9 -23v-576q0 -14 9 -23t23 -9h256q14 0 23 9t9 23zM1152 352v576q0 14 -9 23t-23 9h-256q-14 0 -23 -9t-9 -23v-576q0 -14 9 -23t23 -9h256q14 0 23 9t9 23zM1536 640q0 -209 -103 -385.5t-279.5 -279.5t-385.5 -103 t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103t385.5 -103t279.5 -279.5t103 -385.5z" />
|
||||
<glyph unicode="" d="M768 1408q209 0 385.5 -103t279.5 -279.5t103 -385.5t-103 -385.5t-279.5 -279.5t-385.5 -103t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103zM768 96q148 0 273 73t198 198t73 273t-73 273t-198 198t-273 73t-273 -73t-198 -198t-73 -273 t73 -273t198 -198t273 -73zM864 320q-14 0 -23 9t-9 23v576q0 14 9 23t23 9h192q14 0 23 -9t9 -23v-576q0 -14 -9 -23t-23 -9h-192zM480 320q-14 0 -23 9t-9 23v576q0 14 9 23t23 9h192q14 0 23 -9t9 -23v-576q0 -14 -9 -23t-23 -9h-192z" />
|
||||
<glyph unicode="" d="M1088 352v576q0 14 -9 23t-23 9h-576q-14 0 -23 -9t-9 -23v-576q0 -14 9 -23t23 -9h576q14 0 23 9t9 23zM1536 640q0 -209 -103 -385.5t-279.5 -279.5t-385.5 -103t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103t385.5 -103t279.5 -279.5 t103 -385.5z" />
|
||||
<glyph unicode="" d="M768 1408q209 0 385.5 -103t279.5 -279.5t103 -385.5t-103 -385.5t-279.5 -279.5t-385.5 -103t-385.5 103t-279.5 279.5t-103 385.5t103 385.5t279.5 279.5t385.5 103zM768 96q148 0 273 73t198 198t73 273t-73 273t-198 198t-273 73t-273 -73t-198 -198t-73 -273 t73 -273t198 -198t273 -73zM480 320q-14 0 -23 9t-9 23v576q0 14 9 23t23 9h576q14 0 23 -9t9 -23v-576q0 -14 -9 -23t-23 -9h-576z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M1757 128l35 -313q3 -28 -16 -50q-19 -21 -48 -21h-1664q-29 0 -48 21q-19 22 -16 50l35 313h1722zM1664 967l86 -775h-1708l86 775q3 24 21 40.5t43 16.5h256v-128q0 -53 37.5 -90.5t90.5 -37.5t90.5 37.5t37.5 90.5v128h384v-128q0 -53 37.5 -90.5t90.5 -37.5 t90.5 37.5t37.5 90.5v128h256q25 0 43 -16.5t21 -40.5zM1280 1152v-256q0 -26 -19 -45t-45 -19t-45 19t-19 45v256q0 106 -75 181t-181 75t-181 -75t-75 -181v-256q0 -26 -19 -45t-45 -19t-45 19t-19 45v256q0 159 112.5 271.5t271.5 112.5t271.5 -112.5t112.5 -271.5z" />
|
||||
<glyph unicode="" horiz-adv-x="2048" d="M1920 768q53 0 90.5 -37.5t37.5 -90.5t-37.5 -90.5t-90.5 -37.5h-15l-115 -662q-8 -46 -44 -76t-82 -30h-1280q-46 0 -82 30t-44 76l-115 662h-15q-53 0 -90.5 37.5t-37.5 90.5t37.5 90.5t90.5 37.5h1792zM485 -32q26 2 43.5 22.5t15.5 46.5l-32 416q-2 26 -22.5 43.5 t-46.5 15.5t-43.5 -22.5t-15.5 -46.5l32 -416q2 -25 20.5 -42t43.5 -17h5zM896 32v416q0 26 -19 45t-45 19t-45 -19t-19 -45v-416q0 -26 19 -45t45 -19t45 19t19 45zM1280 32v416q0 26 -19 45t-45 19t-45 -19t-19 -45v-416q0 -26 19 -45t45 -19t45 19t19 45zM1632 27l32 416 q2 26 -15.5 46.5t-43.5 22.5t-46.5 -15.5t-22.5 -43.5l-32 -416q-2 -26 15.5 -46.5t43.5 -22.5h5q25 0 43.5 17t20.5 42zM476 1244l-93 -412h-132l101 441q19 88 89 143.5t160 55.5h167q0 26 19 45t45 19h384q26 0 45 -19t19 -45h167q90 0 160 -55.5t89 -143.5l101 -441 h-132l-93 412q-11 44 -45.5 72t-79.5 28h-167q0 -26 -19 -45t-45 -19h-384q-26 0 -45 19t-19 45h-167q-45 0 -79.5 -28t-45.5 -72z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" d="M991 512l64 256h-254l-64 -256h254zM1759 1016l-56 -224q-7 -24 -31 -24h-327l-64 -256h311q15 0 25 -12q10 -14 6 -28l-56 -224q-5 -24 -31 -24h-327l-81 -328q-7 -24 -31 -24h-224q-16 0 -26 12q-9 12 -6 28l78 312h-254l-81 -328q-7 -24 -31 -24h-225q-15 0 -25 12 q-9 12 -6 28l78 312h-311q-15 0 -25 12q-9 12 -6 28l56 224q7 24 31 24h327l64 256h-311q-15 0 -25 12q-10 14 -6 28l56 224q5 24 31 24h327l81 328q7 24 32 24h224q15 0 25 -12q9 -12 6 -28l-78 -312h254l81 328q7 24 32 24h224q15 0 25 -12q9 -12 6 -28l-78 -312h311 q15 0 25 -12q9 -12 6 -28z" />
|
||||
<glyph unicode="" d="M841 483l148 -148l-149 -149zM840 1094l149 -149l-148 -148zM710 -130l464 464l-306 306l306 306l-464 464v-611l-255 255l-93 -93l320 -321l-320 -321l93 -93l255 255v-611zM1429 640q0 -209 -32 -365.5t-87.5 -257t-140.5 -162.5t-181.5 -86.5t-219.5 -24.5 t-219.5 24.5t-181.5 86.5t-140.5 162.5t-87.5 257t-32 365.5t32 365.5t87.5 257t140.5 162.5t181.5 86.5t219.5 24.5t219.5 -24.5t181.5 -86.5t140.5 -162.5t87.5 -257t32 -365.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1024" d="M596 113l173 172l-173 172v-344zM596 823l173 172l-173 172v-344zM628 640l356 -356l-539 -540v711l-297 -296l-108 108l372 373l-372 373l108 108l297 -296v711l539 -540z" />
|
||||
<glyph unicode="" d="M1280 256q0 52 -38 90t-90 38t-90 -38t-38 -90t38 -90t90 -38t90 38t38 90zM512 1024q0 52 -38 90t-90 38t-90 -38t-38 -90t38 -90t90 -38t90 38t38 90zM1536 256q0 -159 -112.5 -271.5t-271.5 -112.5t-271.5 112.5t-112.5 271.5t112.5 271.5t271.5 112.5t271.5 -112.5 t112.5 -271.5zM1440 1344q0 -20 -13 -38l-1056 -1408q-19 -26 -51 -26h-160q-26 0 -45 19t-19 45q0 20 13 38l1056 1408q19 26 51 26h160q26 0 45 -19t19 -45zM768 1024q0 -159 -112.5 -271.5t-271.5 -112.5t-271.5 112.5t-112.5 271.5t112.5 271.5t271.5 112.5 t271.5 -112.5t112.5 -271.5z" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
<glyph unicode="" horiz-adv-x="1792" />
|
||||
</font>
|
||||
</defs></svg>
|
||||
|
Before Width: | Height: | Size: 280 KiB After Width: | Height: | Size: 357 KiB |
BIN
view/theme/vier/font/fontawesome-webfont.ttf
Executable file → Normal file
BIN
view/theme/vier/font/fontawesome-webfont.ttf
Executable file → Normal file
Binary file not shown.
BIN
view/theme/vier/font/fontawesome-webfont.woff
Executable file → Normal file
BIN
view/theme/vier/font/fontawesome-webfont.woff
Executable file → Normal file
Binary file not shown.
BIN
view/theme/vier/font/fontawesome-webfont.woff2
Normal file
BIN
view/theme/vier/font/fontawesome-webfont.woff2
Normal file
Binary file not shown.
|
|
@ -24,72 +24,72 @@ img {
|
|||
}
|
||||
|
||||
#pending-update {
|
||||
float:right;
|
||||
color: #ffffff;
|
||||
font-weight: bold;
|
||||
background-color: #FF0000;
|
||||
padding: 0em 0.3em;
|
||||
float:right;
|
||||
color: #ffffff;
|
||||
font-weight: bold;
|
||||
background-color: #FF0000;
|
||||
padding: 0em 0.3em;
|
||||
}
|
||||
|
||||
.admin.linklist {
|
||||
border: 0px;
|
||||
padding: 0px;
|
||||
list-style: none;
|
||||
margin-top: 0px;
|
||||
border: 0px;
|
||||
padding: 0px;
|
||||
list-style: none;
|
||||
margin-top: 0px;
|
||||
}
|
||||
|
||||
.admin.link {
|
||||
list-style-position: inside;
|
||||
font-size: 1em;
|
||||
/* padding-left: 5px;
|
||||
margin: 5px; */
|
||||
list-style-position: inside;
|
||||
font-size: 1em;
|
||||
/* padding-left: 5px;
|
||||
margin: 5px; */
|
||||
}
|
||||
|
||||
#adminpage dl {
|
||||
clear: left;
|
||||
margin-bottom: 2px;
|
||||
padding-bottom: 2px;
|
||||
border-bottom: 1px solid black;
|
||||
clear: left;
|
||||
margin-bottom: 2px;
|
||||
padding-bottom: 2px;
|
||||
border-bottom: 1px solid black;
|
||||
}
|
||||
|
||||
#adminpage dt {
|
||||
width: 200px;
|
||||
float: left;
|
||||
font-weight: bold;
|
||||
width: 200px;
|
||||
float: left;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
#adminpage dd {
|
||||
margin-left: 200px;
|
||||
margin-left: 200px;
|
||||
}
|
||||
#adminpage h3 {
|
||||
border-bottom: 1px solid #898989;
|
||||
margin-bottom: 5px;
|
||||
margin-top: 10px;
|
||||
border-bottom: 1px solid #898989;
|
||||
margin-bottom: 5px;
|
||||
margin-top: 10px;
|
||||
}
|
||||
|
||||
#adminpage .submit {
|
||||
clear:left;
|
||||
clear:left;
|
||||
}
|
||||
|
||||
#adminpage #pluginslist {
|
||||
margin: 0px; padding: 0px;
|
||||
margin: 0px; padding: 0px;
|
||||
}
|
||||
|
||||
#adminpage .plugin {
|
||||
list-style: none;
|
||||
display: block;
|
||||
/* border: 1px solid #888888; */
|
||||
padding: 1em;
|
||||
margin-bottom: 5px;
|
||||
clear: left;
|
||||
list-style: none;
|
||||
display: block;
|
||||
/* border: 1px solid #888888; */
|
||||
padding: 1em;
|
||||
margin-bottom: 5px;
|
||||
clear: left;
|
||||
}
|
||||
|
||||
#adminpage .toggleplugin {
|
||||
float:left;
|
||||
margin-right: 1em;
|
||||
float:left;
|
||||
margin-right: 1em;
|
||||
}
|
||||
|
||||
#adminpage table {width:100%; border-bottom: 1p solid #000000; margin: 5px 0px;}
|
||||
#adminpage table {width:100%; border-bottom: 1px solid #000000; margin: 5px 0px;}
|
||||
#adminpage table th { text-align: left;}
|
||||
#adminpage td .icon { float: left;}
|
||||
#adminpage table#users img { width: 16px; height: 16px; }
|
||||
|
|
@ -247,15 +247,6 @@ div.pager {
|
|||
float: left;
|
||||
}
|
||||
|
||||
#contact-edit-drop-link-end {
|
||||
/* clear: both; */
|
||||
}
|
||||
|
||||
#contact-edit-links ul {
|
||||
list-style: none;
|
||||
list-style-type: none;
|
||||
}
|
||||
|
||||
.hide-comments-outer {
|
||||
margin-left: 80px;
|
||||
margin-bottom: 5px;
|
||||
|
|
@ -385,6 +376,14 @@ code {
|
|||
overflow: auto;
|
||||
padding: 0px;
|
||||
}
|
||||
.menu-popup .divider {
|
||||
width: 90%;
|
||||
height: 1px;
|
||||
margin: 3px auto;
|
||||
overflow: hidden;
|
||||
background-color: #737373;
|
||||
opacity: 0.4;
|
||||
}
|
||||
#saved-search-ul .tool:hover,
|
||||
#nets-sidebar .tool:hover,
|
||||
#sidebar-group-list .tool:hover {
|
||||
|
|
@ -793,7 +792,8 @@ nav #nav-user-linklabel:hover #nav-user-menu,
|
|||
nav #nav-user-linkmenu:hover #nav-user-menu,
|
||||
nav #nav-apps-link:hover #nav-apps-menu,
|
||||
nav #nav-site-linkmenu:hover #nav-site-menu,
|
||||
nav #nav-notifications-linkmenu:hover #nav-notifications-menu {
|
||||
nav #nav-notifications-linkmenu:hover #nav-notifications-menu,
|
||||
#contact-edit-actions:hover #contact-actions-menu {
|
||||
display:block;
|
||||
visibility:visible;
|
||||
opacity:1;
|
||||
|
|
@ -1432,8 +1432,8 @@ section.minimal {
|
|||
}
|
||||
.children .wall-item-container .wall-item-item .wall-item-content img {
|
||||
/* max-width: 650px; */
|
||||
/* max-width: 580px; */
|
||||
max-width: 100%;
|
||||
max-width: 520px;
|
||||
/* max-width: 100%; */
|
||||
}
|
||||
.wall-item-container .wall-item-links, .wall-item-container .wall-item-actions {
|
||||
display: table-cell;
|
||||
|
|
@ -2935,6 +2935,48 @@ a.mail-list-link {
|
|||
color: #999999;
|
||||
}
|
||||
|
||||
/* contact edit page */
|
||||
#contact-edit-nav-wrapper {
|
||||
margin-top: 24px;
|
||||
}
|
||||
#contact-edit-status-wrapper {
|
||||
border-color: #c9d8f6;
|
||||
background-color: #e0e8fa;
|
||||
border-radius: 3px;
|
||||
}
|
||||
|
||||
#contact-edit-contact-status {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
#contact-edit-drop-link-end {
|
||||
/* clear: both; */
|
||||
}
|
||||
|
||||
#contact-edit-links ul {
|
||||
list-style: none;
|
||||
list-style-type: none;
|
||||
}
|
||||
|
||||
#contact-edit-settings {
|
||||
margin-top: 10px;
|
||||
}
|
||||
|
||||
a.btn#contact-edit-actions-button {
|
||||
cursor: pointer;
|
||||
border-radius: 3px;
|
||||
font-size: inherit;
|
||||
font-weight: normal;
|
||||
height: auto;
|
||||
line-height: inherit;
|
||||
padding: 5px 10px;
|
||||
}
|
||||
|
||||
#lost-contact-message, #insecure-message,
|
||||
#block-message, #ignore-message, #archive-message {
|
||||
color: #CB4437;
|
||||
}
|
||||
|
||||
/* photo album page */
|
||||
.photo-top-image-wrapper {
|
||||
position: relative;
|
||||
|
|
|
|||
98
view/theme/vier/templates/contact_edit.tpl
Normal file
98
view/theme/vier/templates/contact_edit.tpl
Normal file
|
|
@ -0,0 +1,98 @@
|
|||
|
||||
{{if $header}}<h2>{{$header}}</h2>{{/if}}
|
||||
|
||||
<div id="contact-edit-wrapper" >
|
||||
|
||||
{{* Insert Tab-Nav *}}
|
||||
{{$tab_str}}
|
||||
|
||||
|
||||
<div id="contact-edit-nav-wrapper" >
|
||||
<div id="contact-edit-links">
|
||||
<div id="contact-edit-status-wrapper">
|
||||
<span id="contact-edit-contact-status">{{$contact_status}}</span>
|
||||
|
||||
{{* This is the Action menu where contact related actions like 'ignore', 'hide' can be performed *}}
|
||||
<div id="contact-edit-actions">
|
||||
<a class="btn" id="contact-edit-actions-button">{{$contact_action_button}}</a>
|
||||
|
||||
<ul role="menu" aria-haspopup="true" id="contact-actions-menu" class="menu-popup" >
|
||||
{{if $lblsuggest}}<li role="menuitem"><a href="#" title="{{$contact_actions.suggest.title}}" onclick="window.location.href='{{$contact_actions.suggest.url}}'; return false;">{{$contact_actions.suggest.label}}</a></li>{{/if}}
|
||||
{{if $poll_enabled}}<li role="menuitem"><a href="#" title="{{$contact_actions.update.title}}" onclick="window.location.href='{{$contact_actions.update.url}}'; return false;">{{$contact_actions.update.label}}</a></li>{{/if}}
|
||||
<li class="divider"></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.block.title}}" onclick="window.location.href='{{$contact_actions.block.url}}'; return false;">{{$contact_actions.block.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.ignore.title}}" onclick="window.location.href='{{$contact_actions.ignore.url}}'; return false;">{{$contact_actions.ignore.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.archive.title}}" onclick="window.location.href='{{$contact_actions.archive.url}}'; return false;">{{$contact_actions.archive.label}}</a></li>
|
||||
<li role="menuitem"><a href="#" title="{{$contact_actions.delete.title}}" onclick="return confirmDelete();">{{$contact_actions.delete.label}}</a></li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
{{* Block with status information about the contact *}}
|
||||
<ul>
|
||||
{{if $relation_text}}<li><div id="contact-edit-rel">{{$relation_text}}</div></li>{{/if}}
|
||||
|
||||
{{if $poll_enabled}}
|
||||
<li><div id="contact-edit-last-update-text">{{$lastupdtext}} <span id="contact-edit-last-updated">{{$last_update}}</span></div>
|
||||
{{if $poll_interval}}
|
||||
<span id="contact-edit-poll-text">{{$updpub}}</span> {{$poll_interval}}
|
||||
{{/if}}
|
||||
</li>
|
||||
{{/if}}
|
||||
|
||||
{{if $lost_contact}}<li><div id="lost-contact-message">{{$lost_contact}}</div></li>{{/if}}
|
||||
{{if $insecure}}<li><div id="insecure-message">{{$insecure}}</div></li> {{/if}}
|
||||
{{if $blocked}}<li><div id="block-message">{{$blocked}}</div></li>{{/if}}
|
||||
{{if $ignored}}<li><div id="ignore-message">{{$ignored}}</div></li>{{/if}}
|
||||
{{if $archived}}<li><div id="archive-message">{{$archived}}</div></li>{{/if}}
|
||||
</ul>
|
||||
|
||||
<ul>
|
||||
<!-- <li><a href="network/0?nets=all&cid={{$contact_id}}" id="contact-edit-view-recent">{{$lblrecent}}</a></li> -->
|
||||
{{if $follow}}<li><div id="contact-edit-follow"><a href="{{$follow}}">{{$follow_text}}</a></div></li>{{/if}}
|
||||
</ul>
|
||||
</div> {{* End of contact-edit-status-wrapper *}}
|
||||
|
||||
{{* Some information about the contact from the profile *}}
|
||||
<dl><dt>{{$profileurllabel}}</dt><dd><a target="blank" href="{{$url}}">{{$profileurl}}</a></dd></dl>
|
||||
{{if $location}}<dl><dt>{{$location_label}}</dt><dd>{{$location}}</dd></dl>{{/if}}
|
||||
{{if $keywords}}<dl><dt>{{$keywords_label}}</dt><dd>{{$keywords}}</dd></dl>{{/if}}
|
||||
{{if $about}}<dl><dt>{{$about_label}}</dt><dd>{{$about}}</dd></dl>{{/if}}
|
||||
</div>{{* End of contact-edit-links *}}
|
||||
|
||||
<div id="contact-edit-links-end"></div>
|
||||
|
||||
<hr />
|
||||
|
||||
<h4 id="contact-edit-settings-label" class="fakelink" onclick="openClose('contact-edit-settings')">{{$contact_settings_label}}</h4>
|
||||
<div id="contact-edit-settings">
|
||||
<form action="contacts/{{$contact_id}}" method="post" >
|
||||
<input type="hidden" name="contact_id" value="{{$contact_id}}">
|
||||
|
||||
<div id="contact-edit-end" ></div>
|
||||
{{include file="field_checkbox.tpl" field=$notify}}
|
||||
{{if $fetch_further_information}}
|
||||
{{include file="field_select.tpl" field=$fetch_further_information}}
|
||||
{{if $fetch_further_information.2 == 2 }} {{include file="field_textarea.tpl" field=$ffi_keyword_blacklist}} {{/if}}
|
||||
{{/if}}
|
||||
{{include file="field_checkbox.tpl" field=$hidden}}
|
||||
|
||||
<div id="contact-edit-info-wrapper">
|
||||
<h4>{{$lbl_info1}}</h4>
|
||||
<textarea id="contact-edit-info" rows="8" cols="60" name="info">{{$info}}</textarea>
|
||||
<input class="contact-edit-submit" type="submit" name="submit" value="{{$submit|escape:'html'}}" />
|
||||
</div>
|
||||
<div id="contact-edit-info-end"></div>
|
||||
|
||||
{{if $profile_select}}
|
||||
<div id="contact-edit-profile-select-text">
|
||||
<h4>{{$lbl_vis1}}</h4>
|
||||
<p>{{$lbl_vis2}}</p>
|
||||
</div>
|
||||
{{$profile_select}}
|
||||
<div id="contact-edit-profile-select-end"></div>
|
||||
<input class="contact-edit-submit" type="submit" name="submit" value="{{$submit|escape:'html'}}" />
|
||||
{{/if}}
|
||||
</form>
|
||||
</div>
|
||||
</div>{{* End of contact-edit-nav-wrapper *}}
|
||||
</div>
|
||||
|
|
@ -91,7 +91,7 @@
|
|||
{{if $item.threaded}}
|
||||
{{/if}}
|
||||
{{if $item.comment}}
|
||||
<a role="button" id="comment-{{$item.id}}" class="fakelink togglecomment" onclick="openClose('item-comments-{{$item.id}}'); commentExpand({{$item.id}});" title="{{$item.switchcomment}}"><i class="icon-reply"><span class="sr-only">{{$item.switchcomment}}</span></i></a>
|
||||
<a role="button" id="comment-{{$item.id}}" class="fakelink togglecomment" onclick="openClose('item-comments-{{$item.id}}'); commentExpand({{$item.id}});" title="{{$item.switchcomment}}"><i class="icon-commenting"><span class="sr-only">{{$item.switchcomment}}</span></i></a>
|
||||
{{/if}}
|
||||
|
||||
{{if $item.isevent}}
|
||||
|
|
|
|||
|
|
@ -19,10 +19,6 @@ function vier_init(&$a) {
|
|||
|
||||
set_template_engine($a, 'smarty3');
|
||||
|
||||
$baseurl = $a->get_baseurl();
|
||||
|
||||
$a->theme_info = array();
|
||||
|
||||
if ($a->argv[0].$a->argv[1] === "profile".$a->user['nickname'] or $a->argv[0] === "network" && local_user()) {
|
||||
vier_community_info();
|
||||
|
||||
|
|
@ -160,7 +156,7 @@ function vier_community_info() {
|
|||
$entry = replace_macros($tpl,array(
|
||||
'$id' => $rr['id'],
|
||||
//'$profile_link' => zrl($rr['url']),
|
||||
'$profile_link' => $a->get_baseurl().'/follow/?url='.urlencode($rr['url']),
|
||||
'$profile_link' => 'follow/?url='.urlencode($rr['url']),
|
||||
'$photo' => proxy_url($rr['photo'], false, PROXY_SIZE_MICRO),
|
||||
'$alt_text' => $rr['name'],
|
||||
));
|
||||
|
|
@ -186,11 +182,11 @@ function vier_community_info() {
|
|||
$aside['$lastusers_items'] = array();
|
||||
|
||||
foreach($r as $rr) {
|
||||
$profile_link = $a->get_baseurl() . '/profile/' . ((strlen($rr['nickname'])) ? $rr['nickname'] : $rr['profile_uid']);
|
||||
$profile_link = 'profile/' . ((strlen($rr['nickname'])) ? $rr['nickname'] : $rr['profile_uid']);
|
||||
$entry = replace_macros($tpl,array(
|
||||
'$id' => $rr['id'],
|
||||
'$profile_link' => $profile_link,
|
||||
'$photo' => $a->get_cached_avatar_image($rr['thumb']),
|
||||
'$photo' => $a->remove_baseurl($rr['thumb']),
|
||||
'$alt_text' => $rr['name']));
|
||||
$aside['$lastusers_items'][] = $entry;
|
||||
}
|
||||
|
|
@ -207,7 +203,7 @@ function vier_community_info() {
|
|||
$nv['suggest'] = Array('suggest', t('Friend Suggestions'), "", "");
|
||||
$nv['invite'] = Array('invite', t('Invite Friends'), "", "");
|
||||
|
||||
$nv['search'] = '<form name="simple_bar" method="get" action="'.$a->get_baseurl().'/dirfind">
|
||||
$nv['search'] = '<form name="simple_bar" method="get" action="dirfind">
|
||||
<span class="sbox_l"></span>
|
||||
<span class="sbox">
|
||||
<input type="text" name="search" size="13" maxlength="50">
|
||||
|
|
@ -241,12 +237,12 @@ function vier_community_info() {
|
|||
$selected = (($cid == $contact['id']) ? ' forum-selected' : '');
|
||||
|
||||
$entry = array(
|
||||
'url' => z_root() . '/network?f=&cid=' . $contact['id'],
|
||||
'external_url' => z_root() . '/redir/' . $contact['id'],
|
||||
'url' => 'network?f=&cid=' . $contact['id'],
|
||||
'external_url' => 'redir/' . $contact['id'],
|
||||
'name' => $contact['name'],
|
||||
'cid' => $contact['id'],
|
||||
'selected' => $selected,
|
||||
'micro' => proxy_url($contact['micro'], false, PROXY_SIZE_MICRO),
|
||||
'micro' => App::remove_baseurl(proxy_url($contact['micro'], false, PROXY_SIZE_MICRO)),
|
||||
'id' => ++$id,
|
||||
);
|
||||
$entries[] = $entry;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue