commit 03995d3bc642a4a15ef3a370e509671c895d58a3 Author: Jeena Date: Mon Oct 7 14:46:08 2013 +0200 exported from svn diff --git a/.htaccess b/.htaccess new file mode 100644 index 0000000..0f1f401 --- /dev/null +++ b/.htaccess @@ -0,0 +1,24 @@ + + RewriteEngine On + + # catches all cathegories + RewriteCond %{REQUEST_FILENAME} !-f + RewriteCond %{REQUEST_FILENAME} !-d + RewriteRule "^cat/([a-z0-9_\-\.,]+)/?([0-9]{0,4})/?$" archive.php?cat=$1&y=$2 [QSA] + + # catches all archive links, month and year + RewriteRule "^archive$" archive.php [QSA] + RewriteCond %{REQUEST_FILENAME} !-f + RewriteCond %{REQUEST_FILENAME} !-d + RewriteRule "^([0-9]{4})/?([0-9]{0,2})/?$" archive.php?y=$1&m=$2 [QSA] + + # cathes all permalinks + RewriteCond %{REQUEST_FILENAME} !-f + RewriteCond %{REQUEST_FILENAME} !-d + RewriteRule "^([0-9]{4})/?([0-9]{2})/?([a-z0-9_\-\./,]+)$" log.php?y=$1&m=$2&url=$3 [QSA] + + # catches all pages + RewriteCond %{REQUEST_FILENAME} !-f + RewriteCond %{REQUEST_FILENAME} !-d + RewriteRule "^([a-z0-9_\-\./,]+)$" page.php?url=$1 [QSA] + diff --git a/LICENSE.txt b/LICENSE.txt new file mode 100644 index 0000000..45645b4 --- /dev/null +++ b/LICENSE.txt @@ -0,0 +1,340 @@ + GNU GENERAL PUBLIC LICENSE + Version 2, June 1991 + + Copyright (C) 1989, 1991 Free Software Foundation, Inc. + 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +License is intended to guarantee your freedom to share and change free +software--to make sure the software is free for all its users. This +General Public License applies to most of the Free Software +Foundation's software and to any other program whose authors commit to +using it. (Some other Free Software Foundation software is covered by +the GNU Library General Public License instead.) You can apply it to +your programs, too. + + When we speak of free software, we are referring to freedom, not +price. Our General Public Licenses are designed to make sure that you +have the freedom to distribute copies of free software (and charge for +this service if you wish), that you receive source code or can get it +if you want it, that you can change the software or use pieces of it +in new free programs; and that you know you can do these things. + + To protect your rights, we need to make restrictions that forbid +anyone to deny you these rights or to ask you to surrender the rights. +These restrictions translate to certain responsibilities for you if you +distribute copies of the software, or if you modify it. + + For example, if you distribute copies of such a program, whether +gratis or for a fee, you must give the recipients all the rights that +you have. You must make sure that they, too, receive or can get the +source code. And you must show them these terms so they know their +rights. + + We protect your rights with two steps: (1) copyright the software, and +(2) offer you this license which gives you legal permission to copy, +distribute and/or modify the software. + + Also, for each author's protection and ours, we want to make certain +that everyone understands that there is no warranty for this free +software. If the software is modified by someone else and passed on, we +want its recipients to know that what they have is not the original, so +that any problems introduced by others will not reflect on the original +authors' reputations. + + Finally, any free program is threatened constantly by software +patents. We wish to avoid the danger that redistributors of a free +program will individually obtain patent licenses, in effect making the +program proprietary. To prevent this, we have made it clear that any +patent must be licensed for everyone's free use or not licensed at all. + + The precise terms and conditions for copying, distribution and +modification follow. + + GNU GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License applies to any program or other work which contains +a notice placed by the copyright holder saying it may be distributed +under the terms of this General Public License. The "Program", below, +refers to any such program or work, and a "work based on the Program" +means either the Program or any derivative work under copyright law: +that is to say, a work containing the Program or a portion of it, +either verbatim or with modifications and/or translated into another +language. (Hereinafter, translation is included without limitation in +the term "modification".) Each licensee is addressed as "you". + +Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running the Program is not restricted, and the output from the Program +is covered only if its contents constitute a work based on the +Program (independent of having been made by running the Program). +Whether that is true depends on what the Program does. + + 1. You may copy and distribute verbatim copies of the Program's +source code as you receive it, in any medium, provided that you +conspicuously and appropriately publish on each copy an appropriate +copyright notice and disclaimer of warranty; keep intact all the +notices that refer to this License and to the absence of any warranty; +and give any other recipients of the Program a copy of this License +along with the Program. + +You may charge a fee for the physical act of transferring a copy, and +you may at your option offer warranty protection in exchange for a fee. + + 2. You may modify your copy or copies of the Program or any portion +of it, thus forming a work based on the Program, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) You must cause the modified files to carry prominent notices + stating that you changed the files and the date of any change. + + b) You must cause any work that you distribute or publish, that in + whole or in part contains or is derived from the Program or any + part thereof, to be licensed as a whole at no charge to all third + parties under the terms of this License. + + c) If the modified program normally reads commands interactively + when run, you must cause it, when started running for such + interactive use in the most ordinary way, to print or display an + announcement including an appropriate copyright notice and a + notice that there is no warranty (or else, saying that you provide + a warranty) and that users may redistribute the program under + these conditions, and telling the user how to view a copy of this + License. (Exception: if the Program itself is interactive but + does not normally print such an announcement, your work based on + the Program is not required to print an announcement.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Program, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Program, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the +entire whole, and thus to each and every part regardless of who wrote it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Program. + +In addition, mere aggregation of another work not based on the Program +with the Program (or with a work based on the Program) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + + 3. You may copy and distribute the Program (or a work based on it, +under Section 2) in object code or executable form under the terms of +Sections 1 and 2 above provided that you also do one of the following: + + a) Accompany it with the complete corresponding machine-readable + source code, which must be distributed under the terms of Sections + 1 and 2 above on a medium customarily used for software interchange; or, + + b) Accompany it with a written offer, valid for at least three + years, to give any third party, for a charge no more than your + cost of physically performing source distribution, a complete + machine-readable copy of the corresponding source code, to be + distributed under the terms of Sections 1 and 2 above on a medium + customarily used for software interchange; or, + + c) Accompany it with the information you received as to the offer + to distribute corresponding source code. (This alternative is + allowed only for noncommercial distribution and only if you + received the program in object code or executable form with such + an offer, in accord with Subsection b above.) + +The source code for a work means the preferred form of the work for +making modifications to it. For an executable work, complete source +code means all the source code for all modules it contains, plus any +associated interface definition files, plus the scripts used to +control compilation and installation of the executable. However, as a +special exception, the source code distributed need not include +anything that is normally distributed (in either source or binary +form) with the major components (compiler, kernel, and so on) of the +operating system on which the executable runs, unless that component +itself accompanies the executable. + +If distribution of executable or object code is made by offering +access to copy from a designated place, then offering equivalent +access to copy the source code from the same place counts as +distribution of the source code, even though third parties are not +compelled to copy the source along with the object code. + + 4. You may not copy, modify, sublicense, or distribute the Program +except as expressly provided under this License. Any attempt +otherwise to copy, modify, sublicense or distribute the Program is +void, and will automatically terminate your rights under this License. +However, parties who have received copies, or rights, from you under +this License will not have their licenses terminated so long as such +parties remain in full compliance. + + 5. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Program or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Program (or any work based on the +Program), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Program or works based on it. + + 6. Each time you redistribute the Program (or any work based on the +Program), the recipient automatically receives a license from the +original licensor to copy, distribute or modify the Program subject to +these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties to +this License. + + 7. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Program at all. For example, if a patent +license would not permit royalty-free redistribution of the Program by +all those who receive copies directly or indirectly through you, then +the only way you could satisfy both it and this License would be to +refrain entirely from distribution of the Program. + +If any portion of this section is held invalid or unenforceable under +any particular circumstance, the balance of the section is intended to +apply and the section as a whole is intended to apply in other +circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system, which is +implemented by public license practices. Many people have made +generous contributions to the wide range of software distributed +through that system in reliance on consistent application of that +system; it is up to the author/donor to decide if he or she is willing +to distribute software through any other system and a licensee cannot +impose that choice. + +This section is intended to make thoroughly clear what is believed to +be a consequence of the rest of this License. + + 8. If the distribution and/or use of the Program is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Program under this License +may add an explicit geographical distribution limitation excluding +those countries, so that distribution is permitted only in or among +countries not thus excluded. In such case, this License incorporates +the limitation as if written in the body of this License. + + 9. The Free Software Foundation may publish revised and/or new versions +of the General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns. + +Each version is given a distinguishing version number. If the Program +specifies a version number of this License which applies to it and "any +later version", you have the option of following the terms and conditions +either of that version or of any later version published by the Free +Software Foundation. If the Program does not specify a version number of +this License, you may choose any version ever published by the Free Software +Foundation. + + 10. If you wish to incorporate parts of the Program into other free +programs whose distribution conditions are different, write to the author +to ask for permission. For software which is copyrighted by the Free +Software Foundation, write to the Free Software Foundation; we sometimes +make exceptions for this. Our decision will be guided by the two goals +of preserving the free status of all derivatives of our free software and +of promoting the sharing and reuse of software generally. + + NO WARRANTY + + 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY +FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN +OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES +PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED +OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS +TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE +PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, +REPAIR OR CORRECTION. + + 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR +REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, +INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING +OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED +TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY +YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER +PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE +POSSIBILITY OF SUCH DAMAGES. + + END OF TERMS AND CONDITIONS + + How to Apply These Terms to Your New Programs + + If you develop a new program, and you want it to be of the greatest +possible use to the public, the best way to achieve this is to make it +free software which everyone can redistribute and change under these terms. + + To do so, attach the following notices to the program. It is safest +to attach them to the start of each source file to most effectively +convey the exclusion of warranty; and each file should have at least +the "copyright" line and a pointer to where the full notice is found. + + + Copyright (C) + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + + +Also add information on how to contact you by electronic and paper mail. + +If the program is interactive, make it output a short notice like this +when it starts in an interactive mode: + + Gnomovision version 69, Copyright (C) year name of author + Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. + This is free software, and you are welcome to redistribute it + under certain conditions; type `show c' for details. + +The hypothetical commands `show w' and `show c' should show the appropriate +parts of the General Public License. Of course, the commands you use may +be called something other than `show w' and `show c'; they could even be +mouse-clicks or menu items--whatever suits your program. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the program, if +necessary. Here is a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the program + `Gnomovision' (which makes passes at compilers) written by James Hacker. + + , 1 April 1989 + Ty Coon, President of Vice + +This General Public License does not permit incorporating your program into +proprietary programs. If your program is a subroutine library, you may +consider it more useful to permit linking proprietary applications with the +library. If this is what you want to do, use the GNU Library General +Public License instead of this License. diff --git a/README.txt b/README.txt new file mode 100644 index 0000000..d89e983 --- /dev/null +++ b/README.txt @@ -0,0 +1,41 @@ +### Weblogsystem Jlog +### Programmiert von Jeena Paradies, Dennis Riehle, Robert Bienert +### Mailingliste: +### Projektseite: +### Hilfe zur Installation: +### + +Dieses Programm steht unter der GPL. Eine Kopie der Lizenz habe ich als +Textdatei (Englisch LICENSE.txt) dem Paket beigefügt. + +Wir sehen es sehr gerne wenn sich Leute im Rahmen ihrer Möglichkeiten am +Projekt beteiligen. Insbesondere durch: + +1) Rückmeldungen über Fehler in der Software +2) Mitarbeit an der Software selbst, Plugins oder Programmiertips +3) Mitarbeit an der Dokumentation (siehe Wiki) + + +### Dankeschön an andere Programmierer + +Dieses Programm nutzt zum Auszeichnen der vom Benutzer eingegebenen +Daten die BBCode-Parserklasse für PHP + von Christian Seiler, +welche auch unter der GPL steht. + +Die Komunikation über XML-RPC übernimmt die IXR-Library + Sie steht zwar unter der Artistic +Licence, aber ich bekam vom Autor persönlich die Erlaubnis sie zu nutzen, +danke an dieser Stelle noch einmal an Simon Willison: »You have my +permission to use IXR in your software, re-licensing it if necessary. Thanks +for asking, and sorry the original license didn't work for you. I'll +consider changing the license to something more compatible (BSD probably) +in the future. Cheers, Simon« + +Um über HTTP Dateien zu holen wird HTTP_Request von PEAR mit allen +Abhängigkeiten verwendet zu finden unter: + + +Außerdem nutzt es in veränderter Form das Sessionbasierte Loginsystem +von Benjamin Wilfing, erhältlich unter: + diff --git a/admin/auth.php b/admin/auth.php new file mode 100644 index 0000000..a80d8a9 --- /dev/null +++ b/admin/auth.php @@ -0,0 +1,13 @@ + 23 OR + $minute < 0 OR $minute > 59 OR + $second < 0 OR $second > 59 + ) $errors[] = $l['admin']['false_date']; +*/ + if($form_input['section'] == 'page') { + $sql = "SELECT id FROM ".JLOG_DB_CONTENT." WHERE url = '".$f['url']."';"; + } + else { + $sql = "SELECT id FROM ".JLOG_DB_CONTENT." WHERE + YEAR(date) = ".date("Y", $f['date'])." AND + MONTH(date) = ".date("m", $f['date'])." AND + url = '".$f['url']."';"; + } + + $check_url = new Query($sql); + + if($check_url->error()) { + echo "
\n";
+         echo $check_url->getError();
+         echo "
\n"; + die(); + } + + if($check_url->numRows() > 0) { + $c = $check_url->fetch(); + if($c['id'] != $form_input['id'] AND $form_input['section'] != 'page') $errors[] = $l['admin']['url_duplicate']; + elseif($c['id'] != $form_input['id'] AND $form_input['section'] == 'page') $errors[] = $l['admin']['url_duplicate_page']; + } + } + + if(strlen(trim($form_input['teaserpic']) > 0) AND !is_file(JLOG_BASEPATH.'img'.DIRECTORY_SEPARATOR."t_".$form_input['teaserpic'])) { + $errors[] = $l['admin']['false_teaserpic']; + } + + if($form_input['teaserpiconblog'] == "1" AND strlen(trim($form_input['teaserpic'])) == 0) $errors[] = $l['admin']['no_teaserpic_uploaded']; + + if(strlen(trim($form_input['teaser'])) < 1) $errors[] = $l['admin']['no_teaser']; + if(strlen(trim($form_input['content'])) < 1) $errors[] = $l['admin']['no_content']; + + return $errors; +} + +// Eingabeformular +function form_output($form_input) { + $form_input = array_htmlspecialchars($form_input); +global $l, $categories, $plugins; + + if($form_input['teaserpiconblog'] == 1) $form_input['teaserpiconblog_check'] = "checked='checked'"; + if($form_input['section'] == 'page') $page = " checked='checked'"; + else $weblog = " checked='checked'"; + if($form_input['allowcomments'] === '0') $form_input['comments_check'] = "checked='checked'"; + if($form_input['allowpingback'] === '0') $form_input['pingback_check'] = "checked='checked'"; + + $o = " +
+
".$l['admin']['metadata']." +


+   +

+


+

+


+

+


+

+


+

+".$categories->output_select($form_input['categories'])." + +


+

+ +
+ +
".$l['admin']['contentdata']." + +



+

+ +

+ + + + ".add_session_id_input_tag()." +

+
+
+ + "; + + ### Plugin Hook + $o = $plugins->callHook('adminForm', $o, $form_input); + + return $o; +} + +function preview_output($form_input) { +global $l, $bbcode, $categories; + + // get data from _post + if(empty($form_input['date'])) $form_input['date'] = time(); + $output = "

".$l['admin']['preview']."

\n
".do_entry($form_input, NULL, $section)."
"; + + return $output; +} + +function insert_blog($form_input) { +global $l, $plugins; + + if($form_input['allowcomments'] != "0") $form_input['allowcomments'] = "1"; + if($form_input['allowpingback'] != "0") $form_input['allowpingback'] = "1"; + + $form_input = escape_for_mysql($form_input); + $sql = "INSERT INTO ".JLOG_DB_CONTENT." ( + topic, + url, + section, + date, + teaser, + teaserpic, + teaserpiconblog, + keywords, + content, + comments, + allowpingback ) + VALUES ( + '".$form_input['topic']."', + '".$form_input['url']."', + '".$form_input['section']."', + NOW(), + '".$form_input['teaser']."', + '".$form_input['teaserpic']."', + '".$form_input['teaserpiconblog']."', + '".$form_input['keywords']."', + '".$form_input['content']."', + '".$form_input['allowcomments']."', + '".$form_input['allowpingback']."' );"; + + $writeblog = new Query($sql); + $id = mysql_insert_id(); + if($writeblog->error()) { + echo "
\n";
+        echo $writeblog->getError();
+        echo "
\n"; + die(); + } + + if(is_array($form_input['categories']) AND $form_input['categories']['0'] != 'no_categories') { + $sql = "INSERT INTO ".JLOG_DB_CATASSIGN." ( cat_id, content_id ) + VALUES \n"; + foreach($form_input['categories'] AS $category) { + if(++$i > 1) $sql .= ",\n"; + $sql .= "( '".$category."', '".$id."')"; + } + $sql .= ";"; + + $catassign = new Query($sql); + if($catassign->error()) { + echo "
\n";
+        echo $catassign->getError();
+        echo "
\n"; + die(); + } + } + + ### Plugin Hook + $plugins->callHook('insertEntry', $id, $form_input); + return $id; +} + +function get_blog($id) { +global $l, $categories; + + $sql = 'SELECT id, url, topic, UNIX_TIMESTAMP(date) AS date, ' . + 'teaser, teaserpic, teaserpiconblog, keywords, ' . + 'content, comments, allowpingback, section FROM ' . + JLOG_DB_CONTENT . ' WHERE id = \'' . $id . + '\' LIMIT 1;'; + + $blog = new Query($sql); + if($blog->error()) { + echo "
\n";
+        echo $blog->getError();
+        echo "
\n"; + die(); + } + $form_input = $blog->fetch(); + + $form_input['categories'] = $categories->get_assigned_categories($form_input['id']); + + return $form_input; +} + +function update_blog($form_input) { +global $l, $plugins; + + if($form_input['allowcomments'] != "0") $form_input['allowcomments'] = "1"; + if($form_input['allowpingback'] != "0") $form_input['allowpingback'] = "1"; + + $form_input = escape_for_mysql($form_input); + $sql = "UPDATE ".JLOG_DB_CONTENT." SET + topic = '".$form_input['topic']."', + url = '".$form_input['url']."', + section = '".$form_input['section']."', + teaser = '".$form_input['teaser']."', + teaserpic = '".$form_input['teaserpic']."', + teaserpiconblog = '".$form_input['teaserpiconblog']."', + keywords = '".$form_input['keywords']."', + content = '".$form_input['content']."', + comments = '".$form_input['allowcomments']."', + allowpingback = '".$form_input['allowpingback']."' + WHERE id = '".$form_input['id']."' LIMIT 1;"; + + + $updateblog = new Query($sql); + if($updateblog->error()) { + echo "
\n";
+        echo $updateblog->getError();
+        echo "
\n"; + die(); + } + + if(is_array($form_input['categories'])) { + $sql = "DELETE FROM ".JLOG_DB_CATASSIGN." WHERE content_id = '".$form_input['id']."';"; + $trashcatassign = new Query($sql); + if($trashcatassign->error()) { + echo "
\n";
+        echo $trashcatassign->getError();
+        echo "
\n"; + die(); + } + + if(is_array($form_input['categories']) AND $form_input['categories']['0'] != 'no_categories') { + $sql = "INSERT INTO ".JLOG_DB_CATASSIGN." ( cat_id, content_id ) + VALUES \n"; + foreach($form_input['categories'] AS $category) { + if(++$i > 1) $sql .= ",\n"; + $sql .= "( '".$category."', '".$form_input['id']."')"; + } + $sql .= ";"; + + $catassign = new Query($sql); + if($catassign->error()) { + echo "
\n";
+            echo $catassign->getError();
+            echo "
\n"; + die(); + } + } + } + + ### Plugin Hook + $plugins->callHook('updateEntry', $form_input['id'], $form_input); + + return $l['admin']['data_updated']; +} + +function trash_blog($id) { +global $l; + + $sql = "DELETE FROM ".JLOG_DB_CONTENT." WHERE id = '".escape_for_mysql($id)."' LIMIT 1"; + + $trashblog = new Query($sql); + if($trashblog->error()) { + echo "
\n";
+        echo $trashblog->getError();
+        echo "
\n"; + die(); + } + return $l['admin']['postleted']; +} + +/** + * add PHPSESSID GET parameter if cookies are not allowed + **/ +function add_session_id_to_url($url="") { + if(empty($_COOKIE[session_name()])) { + if(strpos($url, "?") === false) $url .= "?"; + else $url .= "&"; + $url .= session_name() . "=" . htmlspecialchars(session_id()); + } + return $url; +} + +/** + * add PHPSESSID -Tag if cookies are not allowed + */ +function add_session_id_input_tag() { + if(empty($_COOKIE[session_name()])) { + return ""; + } +} + +// output the administration menu +function output_admin_menu() { +global $l, $plugins; + $o = '

+ '.$l['admin']['menu_home'].' | + '.$l['admin']['menu_categories'].' | + '.$l['admin']['menu_comments'].' | + '.$l['admin']['menu_settings'].' | + '.$l['admin']['menu_plugins'].' | + '.$l['admin']['menu_logout'].' +

'; + + ### Plugin Hook + $o = $plugins->callHook('adminMenu', $o); + + return $o; +} + + +// eof diff --git a/admin/categories.php b/admin/categories.php new file mode 100644 index 0000000..504579b --- /dev/null +++ b/admin/categories.php @@ -0,0 +1,79 @@ +".$l['admin']['cat_title']."\n"; + + switch ($get['action']) { + + case 'new': + if(isset($form_input['form_submit'])) { + if(!is_array($errors = $categories->validate($form_input))) { + $categories->new_cat($form_input); + $categories->get_categories(); + $c['main'] .= "

»» ".$l['admin']['cat_new']."

+ ".$categories->output_whole_list_admin(); + } + else { + $c['main'] .= error_output($errors); + $c['main'] .= $categories->output_form($form_input, 'new', $l['admin']['cat_new']); + } + } + else $c['main'] .= $categories->output_form('', 'new', $l['admin']['cat_new']); + break; + + case 'change': + if(isset($form_input['form_submit'])) { + if(!is_array($errors = $categories->validate($form_input))) { + $categories->change_cat($form_input); + $categories->get_categories(); + $c['main'] .= "

".$l['admin']['cat_new_ok']."

".$categories->output_whole_list_admin(); + } + else { + $c['main'] .= error_output($errors); + $c['main'] .= $categories->output_form($form_input, 'new', $l['admin']['cat_new']); + } + } + else { + $form_input['name'] = $categories->get($get['id'], 'name'); + $form_input['id'] = $get['id']; + $form_input['url'] = $categories->get($get['id'], 'url'); + $form_input['description'] = $categories->get($get['id'], 'description'); + + $c['main'] .= $categories->output_form($form_input, 'change', $l['admin']['cat_change']); + } + break; + + case 'trash': + if($form_input['form_submit'] == $l['admin']['yes']) { + $categories->trash_cat($form_input['id']); + $categories->get_categories(); + $c['main'] .= "

".$l['admin']['cat_trash_ok']." + ".$l['admin']['cat_admincenter']."

"; + } + else { + $c['main'] .= "
+

".$l['admin']['cat_really_trash']."

+

".$categories->link($get['id'])."

+

+ + ".add_session_id_input_tag()." + ".$l['admin']['no']."

+
"; + } + break; + + default: + $c['main'] .= "

»» ".$l['admin']['cat_new']."

+ ".$categories->output_whole_list_admin(); + } + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> diff --git a/admin/change.php b/admin/change.php new file mode 100644 index 0000000..f936d62 --- /dev/null +++ b/admin/change.php @@ -0,0 +1,60 @@ +".$l['admin']['change_headline'].""; + +if($get['action'] == "trash" AND $post['trash'] == $l['admin']['yes']) { + $c['main'] .= "

".trash_blog($get['id'])."

"; + include_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'update.php'); +} +elseif ($get['action'] == "trash" AND empty($post['trash'])) { + $c['main'] .= " +
+

".$l['admin']['rearly_delete']." + ".add_session_id_input_tag()." + ".$l['admin']['no']."

+
"; + $form_input = get_blog($get['id']); + $c['main'] .= preview_output($form_input); + $c['title'] = $l['admin']['delete_blogentry']; +} + +else { + if(isset($get['id'])) $form_input = get_blog($get['id']); + elseif (isset($_POST)) $form_input = $post; + else $c['main'] .= $l['admin']['error_occurred']; + + if($post['form_submitted'] == $l['admin']['preview']) { + $c['main'] .= error_output(check_input($form_input)); + $c['main'] .= preview_output($form_input); + $c['main'] .= form_output($form_input); + } + elseif($post['form_submitted'] == $l['admin']['publish']) { + // Put data to database + if(!check_input($form_input)) { + $c['main'] .= "

".update_blog($form_input)."

"; + include_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'update.php'); + } + else { + // show preview and form + $c['main'] .= error_output(check_input($form_input)); + $c['main'] .= form_output($form_input); + } + } + else { + // show form + $c['main'] .= form_output($form_input); + } +} + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> diff --git a/admin/comments.php b/admin/comments.php new file mode 100644 index 0000000..1784bed --- /dev/null +++ b/admin/comments.php @@ -0,0 +1,217 @@ +callHook('deleteComment', $get['id']); + + if( trash($get['id'], JLOG_DB_COMMENTS ) == true) { + $c['main'] .= $l['admin']['kill_c_killed']; + include_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'update.php'); + } +} +elseif ($get['action'] == 'trash' AND empty($data['trash'])) { +$c['main'] .= " +
+

".$l['admin']['kill_c_sure']." + + ".add_session_id_input_tag()." + ".$l['admin']['no']."

+
"; + + $sql = 'SELECT id, sid, name, city, email, homepage, content, ' . + 'date, reference, mail_by_comment, type FROM ' . + JLOG_DB_COMMENTS." + WHERE id = ".$mysql_id." + ORDER BY id DESC LIMIT 1;"; + + $comment = new Query($sql); + if($comment->error()) { + echo "
\n"; 
+        echo $comment->getError(); 
+        echo "
\n"; + die(); + } + + $daten = $comment->fetch(); + $c['main'] .= "
    ".do_comment($daten, "x")."
"; + +} +elseif($get['action'] == 'change' AND !empty($get['id'])) { + + $l["comments_comment_topic"] = $l['admin']["comments_comment_topic"]; + $l["comments_by"] = $l['admin']["comments_by"]; + $l["comments_name"] = $l['admin']["comments_name"]; + $l["comments_city"] = $l['admin']["comments_city"]; + $l["comments_email"] = $l['admin']["comments_email"]; + $l["comments_homepage"] = $l['admin']["comments_homepage"]; + $l["comments_bbcode"] = $l['admin']["comments_bbcode"]; + $l["comments_send"] = $l['admin']["comments_send"]; + $l["comments_preview"] = $l['admin']["comments_preview"]; + $l["comments_no_sid"] = $l['admin']["comments_no_sid"]; + $l["comments_false_mail"] = $l['admin']["comments_false_mail"]; + $l["comments_notext"] = $l['admin']["comments_notext"]; + $l["comments_false_hp"] = $l['admin']["comments_false_hp"]; + $l["comments_anonym"] = $l['admin']["comments_anonym"]; + $l["comments_permalink"] = $l['admin']["comments_permalink"]; + $l["comments_from"] = $l['admin']["comments_from"]; + $l["comments_posted"] = $l['admin']["comments_posted"]; + $l["comments_entryform"] = $l['admin']["comments_entryform"]; + $l["comments_mail_by_comment"] = $l['admin']["comments_mail_by_comment"]; + $l["comments_thx"] = $l['admin']["comments_thx"]; + $l["comments_preview"] = $l['admin']["comments_preview"]; + $l["comments_send"] = $l['admin']["comments_send"]; + $l["comments_bold"] = $l['admin']["comments_bold"]; + $l["comments_italic"] = $l['admin']["comments_italic"]; + $l["comments_quote"] = $l['admin']["comments_quote"]; + $l["comments_url"] = $l['admin']["comments_url"]; + $l["comments_plz_format_txt"] = $l['admin']["comments_plz_format_txt"]; + $l["comments_url_href"] = $l['admin']["comments_url_href"]; + $l["comments_url_node"] = $l['admin']["comments_url_node"]; + + if($data['form_submitted'] == $l['comments_preview']) { + $c['main'] .= "\n

".$l['admin']['comments_change_h']."

+
    + ".do_comment($data, 1)." +
".com_form_output($data).com_javascript_variables(); + } + elseif($data['form_submitted'] == $l['comments_send']) { + if(count($errors = com_check_errors($data)) > 0) $c['main'] .= "\n

".$l['admin']['comments_change_h']."

\n".error_output($error).com_form_output($data).com_javascript_variables(); + else { + + $data = com_clean_data($data); + +### Plugin Hook + $data = $plugins->callHook('updateComment', $data); + + $data = escape_for_mysql($data); + + $sql = "UPDATE ".JLOG_DB_COMMENTS." + SET + name = '".$data['name']."', + city = '".$data['city']."', + email = '".$data['email']."', + homepage = '".$data['homepage']."', + content = '".$data['content']."', + mail_by_comment = '".$data['mail_by_comment']."' + WHERE id = '".$data['id']."' LIMIT 1;"; + + $updatecomment = new Query($sql); + if($updatecomment->error()) { + echo "
\n"; 
+               echo $updatecomment->getError(); 
+               echo "
\n"; + die(); + } + $c['main'] .= "\n

".$l['admin']['comments_change_h']."

\n".$l['admin']['comments_updated']." ".$l['admin']['comments_admin'].""; + include_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'update.php'); + } + } + else { + $sql = 'SELECT id, sid, name, city, email, homepage, content, ' . + 'UNIX_TIMESTAMP(date) AS date, reference, ' . + 'mail_by_comment, type FROM '.JLOG_DB_COMMENTS." + WHERE id = ".$mysql_id." + ORDER BY id DESC LIMIT 1;"; + + $comment = new Query($sql); + if($comment->error()) { + echo "
\n"; 
+            echo $comment->getError(); 
+            echo "
\n"; + die(); + } + + $data = $comment->fetch(); + if(empty($data['name'])) $data['name'] = $l['comments_name']; + if(empty($data['city'])) $data['city'] = $l['comments_city']; + if(empty($data['email'])) $data['email'] = $l['comments_email']; + if(empty($data['homepage'])) $data['homepage'] = $l['comments_homepage']; + + $c['main'] .= "\n

".$l['admin']['comments_change_h']."

+
    + ".do_comment($data, 1)." +
".com_form_output($data).com_javascript_variables(); + } +} +else { +$yl = new Year_Links($get['y'], JLOG_START_YEAR, add_session_id_to_url(JLOG_PATH."/admin/comments.php"), $l['admin']); + + $c['main'] .= " +

".$l['admin']['kill_c_topic']."

+

".$l['admin']['kill_c_description']."

+

".$yl->get_admin_linklist()."

+ + + + "; + + $sql = "SELECT + ".JLOG_DB_COMMENTS.".id AS id, + ".JLOG_DB_CONTENT.".url AS url, + UNIX_TIMESTAMP(".JLOG_DB_CONTENT.".date) AS reference_date, + UNIX_TIMESTAMP(".JLOG_DB_COMMENTS.".date) AS date, + ".JLOG_DB_COMMENTS.".name AS name, + ".JLOG_DB_CONTENT.".topic AS topic, + ".JLOG_DB_COMMENTS.".email AS email, + ".JLOG_DB_COMMENTS.".type AS type + FROM ".JLOG_DB_COMMENTS.", ".JLOG_DB_CONTENT." + WHERE ".JLOG_DB_COMMENTS.".reference = ".JLOG_DB_CONTENT.".id + AND YEAR(".JLOG_DB_COMMENTS.".date) = '".$yl->get_selected_year()."' + ORDER BY id DESC;"; + + $comments = new Query($sql); + if($comments->error()) { + echo "
\n"; 
+        echo $comments->getError(); 
+        echo "
\n"; + die(); + } + + while ($daten = $comments->fetch()) { + + if(empty($daten['name'])) $daten['name'] = $l['comments_anonym']; + elseif($daten['type'] != 'pingback') $daten['name'] = htmlspecialchars($daten['name'], ENT_QUOTES); + + if(!empty($daten['email'])) { + $email_a = ""; + $email_b = ""; + } + else { + $email_a = ""; + $email_b = ""; + } + $comment = " + + + + + + + + "; + + ### Plugin Hook + $c['main'] .= $plugins->callHook('commentAdminList', $comment, $daten); + + } + + $c['main'] .= " +
".$l['admin']['change']."".$l['admin']['delete']."ID".$l['comments_name']."".$l['comments_posted']."".$l['admin']['kill_c_entry']."
".$l[".$l[".$daten['id']."".$email_a.$daten['name'].$email_b."".strftime(JLOG_DATE_COMMENT, $daten['date'])."".$daten['topic']."
"; +} + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> diff --git a/admin/export-rss2.php b/admin/export-rss2.php new file mode 100644 index 0000000..d865d6c --- /dev/null +++ b/admin/export-rss2.php @@ -0,0 +1,13 @@ + diff --git a/admin/index.php b/admin/index.php new file mode 100644 index 0000000..39e1a05 --- /dev/null +++ b/admin/index.php @@ -0,0 +1,75 @@ +".$l['admin']['section_weblog']." | ".$l['admin']['section_page'].""; + $where = "section = 'page'"; + } + else { + $show_section = "".$l['admin']['section_weblog']." | ".$l['admin']['section_page'].""; + $where = "YEAR(date) = '".escape_for_mysql($yl->get_selected_year()) + ."' AND section = 'weblog'"; + $year_menu = "

".$yl->get_admin_linklist()."

\n"; + + } + + + + $c['meta']['title'] = $l['admin']['index_headline']; + + $c['main'] .= output_admin_menu()." +

".$l['admin']['admin_headline']."

+

»» ".$l['admin']['new_post']."

+

".$l['admin']['section_show'].": ".$show_section."

".$year_menu." + + + + + + + "; + + $sql = "SELECT + id, + date as mysql_date, + UNIX_TIMESTAMP(date) AS date, + topic + FROM ".JLOG_DB_CONTENT." + WHERE ".$where." + ORDER BY mysql_date DESC;"; + + $blog = new Query($sql); + if($blog->error()) { + echo "
\n";
+        echo $blog->getError();
+        echo "
\n"; + die(); + } + + while ($daten = $blog->fetch()) { + $list = " + + + + + + "; + + ### Plugin Hook + $c['main'] .= $plugins->callHook('adminList', $list, $daten); + } + + $c['main'] .= " +
".$l['admin']['change']."".$l['admin']['delete']."".$l['admin']['date']."".$l['admin']['headline']."
".$l[".$l[".strftime(JLOG_DATE_SUBCURRENT, $daten['date'])."".htmlspecialchars($daten['topic'], ENT_QUOTES)."
+"; + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; + +// eof \ No newline at end of file diff --git a/admin/login.php b/admin/login.php new file mode 100644 index 0000000..10912ec --- /dev/null +++ b/admin/login.php @@ -0,0 +1,76 @@ + +### autor: Benjamin Wilfing +### email: benjamin.wilfing@selfhtml.org +### homepage: +### +### adapted for Jlog by Jeena Paradies + +ini_set("session.use_trans_sid", false); + +define("JLOG_ADMIN", true); +define("JLOG_LOGIN", true); +require_once('..'.DIRECTORY_SEPARATOR.'scripts'.DIRECTORY_SEPARATOR.'prepend.inc.php'); +require(JLOG_BASEPATH.'admin'.DIRECTORY_SEPARATOR.'blog.func.php'); + +$false_password = ""; +$get = strip($_GET); +$post = strip($_POST); + +### Plugin Hook +$dispatch_login = $plugins->callHook('dispatchLogin', true); + +if ($_SERVER['REQUEST_METHOD'] == 'POST' AND $dispatch_login) { + session_start(); + $passwort = $post['password']; + $url = !empty($post['url']) ? $post['url'] : ''; + $hostname = $_SERVER['HTTP_HOST']; + $path = dirname($_SERVER['SCRIPT_NAME']) . '/'; + + if (strpos($url, "\n") !== false or strpos($url, "\r") !== false) { + die('Somebody tried to hack Jlog with Response-Splitting.'); + } + + if (md5($passwort) == JLOG_ADMIN_PASSWORD) { + $_SESSION['logged_in'] = true; + session_regenerate_id(); // neue SID + + if ($_SERVER['SERVER_PROTOCOL'] == 'HTTP/1.1') { + if (php_sapi_name() == 'cgi') header('Status: 303 See Other'); + else header('HTTP/1.1 303 See Other'); + } + + if ($path == $url) $url = $path . 'new.php'; + if (!empty($url)) $path = $url; + + header('Location: ' . add_session_id_to_url("http://".$hostname.$path)); + exit; + } + else { + $false_password = "

".$l['admin']['login_false_pw']."

\n"; + } +} +else { + setcookie("cookieallowed", "true", time() + 180); +} + +$c['meta']['title'] = $l['admin']['login_headline']; +$c['main'] = ' +

'.$l['admin']['login_headline'].'

+ ' . $false_password . ' +
+

+ +

+

+

+
+'; + +### Plugin Hook +$c["main"] = $plugins->callHook('loginForm', $c["main"]); + + +require_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; + diff --git a/admin/logout.php b/admin/logout.php new file mode 100644 index 0000000..491255d --- /dev/null +++ b/admin/logout.php @@ -0,0 +1,9 @@ + diff --git a/admin/media/select-picture.php b/admin/media/select-picture.php new file mode 100644 index 0000000..a0ef43f --- /dev/null +++ b/admin/media/select-picture.php @@ -0,0 +1,54 @@ + + + + +<?php echo $l['admin']['pic_choose_old'] ?> + + + + + +

+ +

+
+


+

+


+

+

+
+\n"; + } + } +} +?> + + diff --git a/admin/media/select-teaser.php b/admin/media/select-teaser.php new file mode 100644 index 0000000..74e6b95 --- /dev/null +++ b/admin/media/select-teaser.php @@ -0,0 +1,43 @@ + + + + +<?php echo $l['admin']['pic_choose_old_teaser'] ?> + + + + +

+ "; + } +} + +?> + + diff --git a/admin/media/upload-picture.php b/admin/media/upload-picture.php new file mode 100644 index 0000000..0705ecf --- /dev/null +++ b/admin/media/upload-picture.php @@ -0,0 +1,88 @@ + + + + +<?php echo $l['admin']['pic_upload_header'] ?> + + + + + +

+ $max_file_size) $errors[] = $l['admin']['pic_to_big']." (".number_format($_FILES['probe']['size']/1000,0,",","")." KB)"; + + + if(empty($errors)) { + $nr = 0; + switch(true) + { + case preg_match('~.jpg|jpeg~i', $e): + for(;;) { $nr++; if (!file_exists($up_dir.$nr.".jpg")) break; } + $filename = $nr.".jpg"; + break; + case preg_match('~.gif~i', $e): + for(;;) { $nr++; if (!file_exists($up_dir.$nr.".gif")) break; } + $filename = $nr.".gif"; + break; + case preg_match('~.png~i', $e): + for(;;) { $nr++; if (!file_exists($up_dir.$nr.".png")) break; } + $filename = $nr.".png"; + break; + } + + if(empty($errors)) { + if(!move_uploaded_file($_FILES['probe']['tmp_name'], $up_dir.$filename)) $errors[] = $l['admin']['pic_error']; + else chmod($up_dir.$filename, 0664); + } + } + if (empty($errors)) { + ?> +

+

+
+


+

+


+

+

+
+ +

+
+ + +

+ +
+ + + diff --git a/admin/media/upload-teaser.php b/admin/media/upload-teaser.php new file mode 100644 index 0000000..c18c68c --- /dev/null +++ b/admin/media/upload-teaser.php @@ -0,0 +1,92 @@ + + + + +<?php echo $l['admin']['pic_upload_teaser'] ?> + + + + +

+ $max_file_size) $errors[] = $l['admin']['pic_to_big']." (".number_format($_FILES['probe']['size']/1000,0,",","")." KB)"; + + if(empty($errors)) { + $nr = 0; + switch(true) + { + case preg_match('~.jpg|jpeg~i', $e): + for(;;) { $nr++; if (!file_exists($up_dir."t_".$nr.".jpg")) break; } + $filename = "t_".$nr.".jpg"; + break; + case preg_match('~.gif~i', $e): + for(;;) { $nr++; if (!file_exists($up_dir."t_".$nr.".gif")) break; } + $filename = "t_".$nr.".gif"; + break; + case preg_match('~.png~i', $e): + for(;;) { $nr++; if (!file_exists($up_dir."t_".$nr.".png")) break; } + $filename = "t_".$nr.".png"; + break; + } + + + $imginfo = getimagesize($_FILES['probe']['tmp_name']); + + if($imginfo[1] > 150 AND $imginfo[0] > 150 ) { + $errors[] = $l['admin']['pic_height_widht']; + } + elseif($imginfo[0] > 150 ) { + $errors[] = $l['admin']['pic_width']; + } + elseif($imginfo[1] > 150 ) { + $errors[] = $l['admin']['pic_height']; + } + if(empty($errors)) { + if(!move_uploaded_file($_FILES['probe']['tmp_name'], $up_dir.$filename)) $errors[] = $l['admin']['pic_error']; + else chmod($up_dir.$filename, 0664); + } + } + if (empty($errors)) { + ?> +

+ +

+ +

+
+ + +

+ +
+ + + diff --git a/admin/new.php b/admin/new.php new file mode 100644 index 0000000..5e81395 --- /dev/null +++ b/admin/new.php @@ -0,0 +1,103 @@ +".$l['admin']['new_post'].""; + $form_input = strip($_POST); + $form_input['date'] = strftime("%Y-%m-%d %H:%M:%s"); + +if($_POST['form_submitted'] == $l['admin']['preview']) { + $c['main'] .= error_output(check_input($form_input)); + $c['main'] .= preview_output($form_input); + $c['main'] .= form_output($form_input); +} +elseif($_POST['form_submitted'] == $l['admin']['publish']) { + // Put data to database + if(!check_input($form_input)) { + if($id = insert_blog($form_input)) { + $c['main'] .= "

".$l['admin']['entry_saved']."

"; + include_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'update.php'); + + // ping blog services and pingback + if($form_input['section'] == 'weblog') { + $blogservices = explode("\n", str_replace("\r", "\n", str_replace("\r\n", "\n", JLOG_BLOGSERVICES))); + foreach($blogservices as $blogservice) { + if(strlen($blogservice) > 0) $pingresult[] = doPing(trim($blogservice)); + } + // if(is_array($pingresult)) $c['main'] .= "\n
    ".join($pingresult)."\n
"; + + if($form_input['allowpingback'] != '0') { + $blogentryForURL = get_blog($id); + require_once(JLOG_BASEPATH.'xmlrpc.php'); + $pingback = new Jlog_SendPingback($bbcode->parse($form_input['content']), blog($blogentryForURL['date'], $blogentryForURL['url']), " -- Jlog v".JLOG_SOFTWARE_VERSION); + + $responces = array(); + $responces = $pingback->doPingbacks(); + +/* Die Ergebnisse der Pings verwirren den User nur habe ich mittlerweile festgestellt. + + if(count($responces) > 0) { + $c['main'] .= "
    "; + foreach($responces as $responce) { + $c['main'] .= "\n
  • ".$responce."
  • "; + } + $c['main'] .= "\n
"; + } +*/ + + } + } + } + } + else { + // show preview and form + $c['main'] .= error_output(check_input($form_input)); + $c['main'] .= form_output($form_input); + } +} +else { + // show form + $c['main'] .= form_output($form_input); +} + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; + +// verschiedene Dienste anpingen bei neuem Eintrag + +function doPing($url) { + $blog_title = JLOG_WEBSITE; + $blog_url = JLOG_PATH; + $timeout = 30; //Sekunden + $url = parse_url($url); + + $fp = @fsockopen($url['host'], 80, $errno, $errstr, $timeout); + if(!$fp) { + $response = 'Fehler: '.$errstr.' ('.$errno.')
Es konnte keine Verbindung hergestellt werden'; + } else { + $data_string = ' + + weblogUpdates.ping + + '.$blog_title.' + '.$blog_url.' + + '; + $data_header = "POST ".$url['path']." HTTP/1.0\r\n". + "Host: $host\r\n". + "Content-Type: text/xml\r\n". + "User-Agent: qxm XML-RPC Client\r\n". + "Content-Length: ".strlen($data_string)."\r\n\r\n"; + fputs($fp, $data_header); + fputs($fp, $data_string); + unset($response); + fclose($fp); + } + if(isset($response)) return '
  • '.$url['host'].' '.$response.'
  • '; +} + +// eof diff --git a/admin/plugin.php b/admin/plugin.php new file mode 100644 index 0000000..7478a4f --- /dev/null +++ b/admin/plugin.php @@ -0,0 +1,53 @@ +".$pluginName."\n"; + } + } + closedir($handle); + + if(!empty($availablePlugins)) { + $availablePlugins = "
      \n".$availablePlugins."
    \n"; + $title = $l['admin']['plugins_headline']; + } + + else { + $availablePlugins = "

    ".$l['admin']['plugins_not_avaliable']."

    "; + $title = $l['admin']['plugins_h_not_avaliable']; + } + + } + } + else { + $title = $get['jplug']; + $availablePlugins = "

    ".$l['admin']['plugin_no_content']."

    "; + } + + + + $c['meta']['title'] = $title; + $c['main'] .= "

    ".$title."

    \n"; + + $c['main'] .= $plugins->callHook('adminContent', $availablePlugins); + + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> diff --git a/admin/settings.php b/admin/settings.php new file mode 100644 index 0000000..d7d672a --- /dev/null +++ b/admin/settings.php @@ -0,0 +1,33 @@ +".$l['admin']['m_title'].""; + + $settings = new Settings($l); + if($_POST) { + $settings->importDataByArray(strip($_POST)); + if(count($errors = $settings->validate()) == 0) { + if(count($errors = $settings->do_settings()) == 0) { + $c['main'] .= $l['admin']['m_settings_ok']; + } + + } + if(count($errors) > 0) { + $c['main'] .= error_output($errors); + $c['main'] .= $settings->form_output(); + } + } + else { + $settings->importDataByConstants(); + $c['main'] .= $settings->form_output(); + } +require_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'update.php'); +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> diff --git a/admin/update.php b/admin/update.php new file mode 100644 index 0000000..e95f556 --- /dev/null +++ b/admin/update.php @@ -0,0 +1,35 @@ + Jlog 1.1.0 + + define("JLOG_ADMIN", true); + define("JLOG_UPDATE", true); + + // load prepend.inc.php + require_once('..'.DIRECTORY_SEPARATOR.'scripts'.DIRECTORY_SEPARATOR.'prepend.inc.php'); + + include(JLOG_BASEPATH.'lang'.DIRECTORY_SEPARATOR.'lang.'.JLOG_LANGUAGE.'.inc.php'); + include(JLOG_BASEPATH.'lang'.DIRECTORY_SEPARATOR.'lang-admin.'.JLOG_LANGUAGE.'.inc.php'); + + // Rendering + $c['meta']['title'] = "Update"; + //$c['main'] = sprintf("

    Update von %s auf %s

    ", JLOG_INSTALLED_VERSION, JLOG_SOFTWARE_VERSION); + + require_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'JlogUpdater.php'); + $updater = new JlogUpdater(); + + if ($updater->isUp2Date()) { + $c['main'] = '

    Das Update auf ' . JLOG_INSTALLED_VERSION . ' wurde bereits erfolgreich durchgeführt.

    '; + } + else if (!isset($_POST['update'])) { + $c['main'] = $updater->prepareForm($l); + } + else { + $c['main'] = $updater->performUpdate($l); + + // Ready :-) + require(JLOG_BASEPATH."scripts".DIRECTORY_SEPARATOR."update.php"); + } + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> \ No newline at end of file diff --git a/archive.php b/archive.php new file mode 100644 index 0000000..c41a209 --- /dev/null +++ b/archive.php @@ -0,0 +1,138 @@ +get($categories->get_id($get['cat']), 'name'); + $c['main'] .= "

    ".$l['content_categories_header']." ".$categories->get($categories->get_id($get['cat']), 'name')." ".$yl->get_selected_year()."

    "; + $c['main'] .= "

    ".$categories->get($categories->get_id($get['cat']), 'description')."

    "; + + $sql_archive = " + SELECT + ".JLOG_DB_CONTENT.".*, + ".JLOG_DB_CONTENT.".date as mysql_date, + DATE_FORMAT(".JLOG_DB_CONTENT.".date, '%c') AS month, + DATE_FORMAT(".JLOG_DB_CONTENT.".date, '%Y') AS year, + UNIX_TIMESTAMP(".JLOG_DB_CONTENT.".date) AS date + FROM ".JLOG_DB_CONTENT." + LEFT JOIN ".JLOG_DB_CATASSIGN." + ON ".JLOG_DB_CONTENT.".id = ".JLOG_DB_CATASSIGN.".content_id + WHERE ".JLOG_DB_CATASSIGN.".cat_id = '".escape_for_mysql($categories->get_id($get['cat']))."' + AND YEAR(".JLOG_DB_CONTENT.".date) = '".escape_for_mysql($yl->get_selected_year())."' + ORDER BY mysql_date DESC;"; + + $c['main'] .= "

    ".$yl->get_linklist()."

    "; + + } + elseif(empty($get['y'])) { + $c['meta']['title'] = $l['content_archive_header']; + $c['main'] = "

    ".$c['meta']['title']."

    "; + + $sql_archive = "SELECT id, url, topic, + date as mysql_date, + DATE_FORMAT(date, '%c') AS month, + DATE_FORMAT(".JLOG_DB_CONTENT.".date, '%Y') AS year, + UNIX_TIMESTAMP(date) AS date, + teaser, teaserpic, teaserpiconblog, keywords, content, + comments, allowpingback, section + FROM ".JLOG_DB_CONTENT." + WHERE section = 'weblog' + ORDER BY mysql_date DESC + LIMIT ".$p.", ".$amount.";"; + + $sql_count = "SELECT count(*) AS count FROM ".JLOG_DB_CONTENT." WHERE section = 'weblog'"; + + $count_query = new Query($sql_count); + if($count_query->error()) { + echo "
    \n";
    +                echo $count_query->getError();
    +                echo "
    \n"; + die(); + } + $_count = $count_query->fetch(); + $count_query->free(); + $count = $_count['count']; + } + else { + if(!empty($get['m'])) $where_month = " AND MONTH(date) = '".escape_for_mysql($get['m'])."'"; + $c['meta']['title'] = $l['content_archive_header']; + $c['main'] = "

    ".$c['meta']['title']." ".$yl->get_selected_year()."

    "; + + $sql_archive = "SELECT id, url, topic, + date as mysql_date, + DATE_FORMAT(date, '%c') AS month, + DATE_FORMAT(".JLOG_DB_CONTENT.".date, '%Y') AS year, + UNIX_TIMESTAMP(date) AS date, + teaser, teaserpic, teaserpiconblog, keywords, content, + comments, allowpingback, section + FROM ".JLOG_DB_CONTENT.$where_from." + WHERE + YEAR(date) = '".escape_for_mysql($yl->get_selected_year())."' + ".$where_month." + AND section = 'weblog' + ORDER BY mysql_date;"; + + $c['main'] .= "

    ".$yl->get_linklist()."

    "; + } + + $cc = count_comments(); + + $archive = new Query($sql_archive); + if($archive->error()) { + echo "
    \n";
    +        echo $archive->getError();
    +        echo "
    \n"; + die(); + } + +$months = array_flip($l['months']); + +if($archive->numRows() > 0) { + // initialise variables to keep track of last posts month and year + $last_month = false; + $last_year = false; + + while ($daten = $archive->fetch()) { + if(empty($daten)) break 1; + + // did we already reach a new month or year? + if (($last_month != $daten['month']) OR ($last_year != $daten['year'])) { + if ($last_month) { $c['main'] .= " \n"; } + $c['main'] .= "

    ".array_search($daten['month'], $months)." ".$daten['year']."

    \n"; + $c['main'] .= "
    \n"; + // set last month and year to values of current post + $last_month = $daten['month']; + $last_year = $daten['year']; + } + $c['main'] .= do_teaser($daten, $cc, "

    ", "

    "); + } + if(empty($get['y'])) { + $c['main'] .= "

    "; + if(($p - $amount) >= 0) { + $c['main'] .= "<— ".$l['content_archive_preview'].""; + $c['meta']['aditionalheader'] .= ' '."\n"; + } + if((($p - $amount) >= 0) && (($p + $amount) < $count)) $c['main'] .= " | "; + if(($p + $amount) < $count) { + $c['main'] .= "".$l['content_archive_next']." —>"; + $c['meta']['aditionalheader'] .= ' '."\n"; + } + $c['main'] .= "

    "; + } + $c['main'] .= "
    \n"; +} + + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> diff --git a/error404.php b/error404.php new file mode 100644 index 0000000..bd031d8 --- /dev/null +++ b/error404.php @@ -0,0 +1,15 @@ +".$l['err404_topic']."\n

    ".$l['err404_message']."

    "; + $c['main'] .= '
    +

    +

    +
    '; + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> diff --git a/img/JLOG_edit.png b/img/JLOG_edit.png new file mode 100644 index 0000000..e2b8f68 Binary files /dev/null and b/img/JLOG_edit.png differ diff --git a/img/JLOG_rss-full.png b/img/JLOG_rss-full.png new file mode 100644 index 0000000..d72c71d Binary files /dev/null and b/img/JLOG_rss-full.png differ diff --git a/img/JLOG_rss-summary.png b/img/JLOG_rss-summary.png new file mode 100644 index 0000000..61b1715 Binary files /dev/null and b/img/JLOG_rss-summary.png differ diff --git a/img/JLOG_trash.png b/img/JLOG_trash.png new file mode 100644 index 0000000..29fbe6b Binary files /dev/null and b/img/JLOG_trash.png differ diff --git a/index.php b/index.php new file mode 100644 index 0000000..d2453e8 --- /dev/null +++ b/index.php @@ -0,0 +1,107 @@ +error()) { + echo "
    \n";
    +        echo $blog->getError();
    +        echo "
    \n"; + die(); + } + +$number_of = $blog->numRows(); + +// -- ganze Posts ausgeben +$i_orginal = 0; +while (++$i_orginal <= JLOG_MAX_BLOG_ORGINAL) { + $cd = array(); + $cd = $blog->fetch(); + $c['meta']['date'] = $cd['metadate']; + if(empty($cd)) break 1; + $c['main'] .= do_entry($cd, $cc); +} + +// -- Teaser ausgeben +$i = 0; +while (++$i <= JLOG_MAX_BLOG_BIG) { + $cd = $blog->fetch(); + if(empty($c['meta']['date'])) $c['meta']['date'] = $cd['metadate']; + if(empty($cd)) break 1; + $c['main'] .= do_teaser($cd, $cc); +} + +if((JLOG_MAX_BLOG_BIG > 0) AND ($number_of > (JLOG_MAX_BLOG_BIG + JLOG_MAX_BLOG_ORGINAL))) $c['main'] .= "\n
    "; + +if($number_of > JLOG_MAX_BLOG_BIG + JLOG_MAX_BLOG_ORGINAL) $c['main'] .= "\n
      "; + +// -- Liste mit alten Beiträgen ausgeben +$linklist = false; +while ($cd = $blog->fetch()) { + if(empty($c['meta']['date'])) $c['meta']['date'] = $cd['metadate']; + ++$i; + $linklist = true; + + $tmp_comments = ""; + if(isset($cc[$cd['id']]) AND $cc[$cd['id']] != 0) $tmp_comments = " (".$cc[$cd['id']].")"; + + $c['main'] .= " +
    • ".strftime(JLOG_DATE_SUBCURRENT, $cd['date'])." ".htmlspecialchars($cd['topic'], ENT_QUOTES)."".$tmp_comments."
    • "; + } + +if($linklist) $c['main'] .= "\n
    \n
    "; + +// -- Link zum Archiv + $c['main'] .= " + "; + +// -- Daten in Template einfügen und ausgeben -- +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; + +// eof diff --git a/lang/lang-admin.de.inc.php b/lang/lang-admin.de.inc.php new file mode 100644 index 0000000..711a1a2 --- /dev/null +++ b/lang/lang-admin.de.inc.php @@ -0,0 +1,246 @@ + "Inhalte", +"menu_categories" => "Kategorien", +"menu_comments" => "Kommentare", +"menu_settings" => "Einstellungen", +"menu_plugins" => "Plugins", +"menu_logout" => "Ausloggen", +"new_post" => "Neuen Eintrag erstellen", +"index_headline" => "Admincenter", +"change_headline" => "Alten Weblogeintrag ändern", +"go" => "los", +"admin_headline" => "Administrationscenter", +"change" => "Ändern", +"delete" => "Löschen", +"date" => "Datum", +"headline" => "Überschrift", +"metadata" => "Metadaten", +"contentdata" => "Inhalt des Eintrages", +"url" => "URL für permanenten Link (nur 0-9 a-z -.,_/)", +"keywords" => "Schlüsselwörter, Keywords", +"categories" => "Kategorie (Mehrfachauswahl mit [Strg], bzw. Apfel Taste)", +"no_categories" => "keine", +"preview" => "Vorschau", +"publish" => "Veröffentlichen", +"submit" => "Absenden", +"cancel" => "Abbrechen", +"no_headline" => "Überschrift fehlt", +"no_url" => "URL fehlt", +"false_url_letters" => "Der URL darf nur Kleinbuchstaben (a-z), Zahlen (0-9) und diese Zeichen enthalten: -.,_/", +"url_duplicate" => "Während eines Monats darf ein URL nur ein einziges mal vorkommen sonst kann das Blog sie nicht auseinanderhalten", +"url_duplicate_page" => "Pages müssen unikate URLs haben, das heißt, dass jede page einen anderen URL haben muss", +"false_teaserpic" => "Die Angabe des Bildes für die Zusammenfassung stimmt nicht, ein solches Bild wurde nicht hochgeladen", +"no_teaserpic_uploaded" => "Das Bild für die Zusammenfassung kann nicht im Blog angezeigt werden wenn es nicht hochgeladen wurde", +"no_teaser" => "Zusammenfassung fehlt", +"no_content" => "Inhalt fehlt", +"pic_for_teaser" => "Ein Bild für die Zusammenfassung (max 150px):", +"pic_upload" => "Bild hochladen", +"pic_choose" => "Bild auswählen", +"show_tpic_on_archive" => "Dieses Bild auch auf der richtigen Blogseite anzeigen.", +"teaser" => "Zusammenfassung", +"contentpic_choose" => "Ein Bild für den Inhalt:", +"content" => "Inhalt des Beitrags", +"howto_bbcode" => "Wie nutze ich BBCode?", +"content_choose_year" => "Das Jahr wählen:", + +"content_bold" => "fett", +"content_italic" => "kursiv", +"content_quote" => "Zitat", +"content_url" => "Link", +"content_plz_format_txt" => "Bitte gebe den zu formatierenden Text ein:", +"content_input_on_pos" => "Einfügen an Position", +"content_url_href" => "Linkziel eingeben:", +"content_url_node" => "Linktext eingeben:", +"content_list" => "Liste", +"content_headline" => "Überschrift", + +"section" => "Art des Beitrages", +"section_show" => "Art der Beiträge zeigen", +"section_weblog" => "weblog", +"section_page" => "page", + +"entry_saved" => "Eintrag gespeichert.", +"data_updated" => "Daten aktualisiert.", +"post_deleted" => "Der Blogeintrag wurde gelöscht.", +"index_topic" => "Letzte Weblogbeiträge", + +"yes" => "Ja", +"no" => "Nein", +"rearly_delete" => "Diesen Eintrag wirklich löschen?", +"delete_blogentry" => "Eintrag löschen", +"postdeleted" => "Eintrag gelöscht", +"error_occurred" => "Ein Fehler ist aufgetreten", + +"can_not_open" => "Kann Datei nicht öffnen", +"can_not_write" => "Kann in Datei nicht schreiben", +"no_wrtitenable" => "Die Datei ist nicht beschreibbar", +"rss_ok" => "RSS und Aktuelles erfolgreich aktualisiert.", +"master_ok" => "Setupdatei erfolgreich aktualisiert.", + +"pic_choose_old" => "Älteres Bild auswählen", +"pic_choose_old_teaser" => "Älteres Teaserbild auswählen", +"pic_upload_header" => "Bild hochladen", +"pic_upload_teaser" => "Teaserbild hochladen", +"pic_error" => "Fehler beim Hochladen bitte Administrator benachrichtigen", +"pic_uploaded" => "Bild wurde hochgeladen", +"pic_insert" => "Bild einfügen", +"pic_instructions" => "Nur PNG, GIF oder JPEG Bilder hochladen. Die Dateigröße darf 300 kB nicht überschreiten.", +"pic_upload" => "Hochladen", +"pic_class" => "CSS Klasse falls benötigt", +"pic_alt" => "Alternativtext", + +"pic_height_widht" => "Bild ist zu hoch und zu breit", +"pic_width" => "Bild ist zu breit", +"pic_height" => "Bild ist zu hoch", +"pic_instr_teaser" => "Nur PNG, GIF oder JPEG Bilder hochladen, die nicht breiter oder höher als 150px sind und 60 kB nicht überschreiten.", +"pic_bad_type" => "Falsches Format", +"pic_to_big" => "Das Bild ist zu groß", + +"kill_c_topic" => "Kommentare administrieren", +"kill_c_killed" => "Kommentar erfolgreich gelöscht.", +"kill_c_sure" => "Diesen Kommentar wirklich löschen?", +"kill_c_h2" => "Unwiederbringlich löschen", +"kill_c_description" => "Achtung, wenn ein Kommentar hier gelöscht wird ist er unwiederbringlich verloren!", +"kill_c_entry" => "Weblogeintrag", +"kill_c_email" => "Diesen Kommentar löschen", +"comments_change_h" => "Kommentar ändern", +"comments_anonym" => "Anonym", +"comments_mail_txt" => "Neuer Kommentar auf ".JLOG_WEBSITE."\nDer Titel war: ", +"comments_posted" => "schrieb am", +"comments_mailsubject" => "Kommentar auf ".JLOG_WEBSITE, +"comments_comment_topic" => "Kommentare", +"comments_by" => "Kommentar von", +"comments_name" => "Name", +"comments_city" => "Stadt / Land", +"comments_email" => "E-Mail", +"comments_homepage" => "http://", +"comments_bbcode" => "Wie benutze ich", +"comments_send" => "Absenden", +"comments_preview" => "Vorschau", +"comments_no_sid" => "Es scheint eine Manipulation vorzuliegen", +"comments_false_mail" => "Die E-Mail Adresse sieht nicht richtig aus", +"comments_notext" => "Es wurde kein Text eingegeben", +"comments_false_hp" => "Die URL zur Homepage scheint falsch zu sein", +"comments_permalink" => "Permanenter link zu diesem Kommentar", +"comments_from" => "aus", +"comments_posted" => "schrieb am", +"comments_entryform" => "Kommentar ändern", +"comments_mail_by_comment" => "Bei Kommentar benachrichtigen", +"comments_thx" => "Der Kommentar wurde geändert", +"comments_preview" => "Vorschau", +"comments_send" => "Senden", +"comments_bold" => "fett", +"comments_italic" => "kursiv", +"comments_quote" => "Zitat", +"comments_url" => "Link", +"comments_plz_format_txt" => "Bitte gebe den zu formatierenden Text ein:", +"comments_url_href" => "Linkziel eingeben:", +"comments_url_node" => "Linktext eingeben:", +"comments_updated" => "Der Kommentar wurde geändert. Zurück zum", +"comments_admin" => "Kommentar Administrationscenter", +"comments_closed" => "Kommentare für diesen Beitrag schließen", + +"m_writenable" => "beschreibbar", +"m_title" => "Haupteinstellungen des Weblogs", +"m_clean_url" => "Saubere URLs (mod_rewrite) verwenden? Beispiel: http://example.com/2005/01/firefox", +"m_metadata" => "Metadaten", +"m_language" => "Sprache des Weblogs", +"m_website" => "Der Name des Weblogs", +"m_publisher" => "Name des Verfassers der Einträge", +"m_admin_password" => "Administrationscenter Passwort", +"m_admin_password_again" => "Passwort bestätigen", +"m_admin_password_admin" => "(leer lassen falls unverändert)", +"m_email" => "E-Mail des Betreibers des Weblogs", +"m_description" => "Eine Kurze Beschreibung des Weblogs", +"m_bs" => "Weblogdienste bei neuem Eintrag benachrichtigen, die den eigenen Eintrag in ihre Suchmaschinen aufnehmen (für jeden eine Zeile)", +"m_bs_weblogs_com" => "weblogs.com", +"m_bs_technorati_com" => "technorati.com", +"m_bs_blogg_de" => "blogg.de", +"m_behavior" => "Verhalten des Weblogs", +"m_max_blog_orginal" => "Anzahl der Einträge, die vollständig auf der Startseite erscheinen", +"m_max_blog_big" => "Anzahl der Einträge, deren Beschreibung auf der Startseite erscheinen", +"m_max_blog_small" => "Anzahl der Einträge, deren Datum und Name auf der Startseite erscheinen", +"m_sub_current" => "Anzahl der Einträge, deren Datum und Name in der Subnavigation, die auf jeder Seite erscheint, erscheinen", +"m_info_by_comment" => "Benachrichtigung des Betreibers des Weblogs bei neuem Kommentar", +"m_database" => "Datenbank", +"m_db" => "Datenbankname", +"m_db_url" => "Datenbank Hostname, in der Regel localhost", +"m_db_user" => "Datenbank Username", +"m_db_pwd" => "Datenbank Passwort", +"m_db_prefix" => "Kürzel, das Tabellennamen vorangestellt wird", +"m_date" => "Format des Datums wie bei der PHP-Funktion strftime()", +"m_date_posting" => "Format für den Eintrag", +"m_date_comment" => "Format für die Kommentare", +"m_date_subcurrent" => "Format für die Subnavigation", +"m_settings_ok" => "Die Einstellungen wurden gespeichert.", + +"e_path" => "Die angegebene URL scheint nicht zu stimmen", +"e_basepath" => "Das angegebene Verzeichnis existiert nicht", +"e_website" => "Bitte Namen des Weblogs eingeben", +"e_publisher" => "Bitte Namen des Betreibers eingeben", +"e_admin_password" => "Bitte Administrationscenter Passwort eingeben", +"e_admin_password_again" => "Bitte Administrationscenter Passwort bestätigen", +"e_email" => "E-Mail Adresse des Betreibers scheint falsch zu sein", +"e_description" => "Bitte eine Beschreibung des Weblogs eingeben", +"e_max_blog_orginal" => "Anzahl der Einträge, die vollständig auf der Startseite erscheinen muss eine Zahl größer oder gleich Null sein", +"e_max_blog_big" => "Anzahl der Einträge, deren Beschreibung auf der Startseite erscheinen muss eine Zahl größer oder gleich Null sein", +"e_max_blog_small" => "Anzahl der Einträge, deren Datum und Name auf der Startseite erscheinen muss eine Zahl größer oder gleich Null sein", +"e_sub_current" => "Anzahl der Einträge, deren Datum und Name in der Subnavigation erscheinen muss eine Zahl größer oder gleich Null sein", +"e_start_year" => "Das versteckte Jahresfeld ist leer", +"e_db" => "Bitte Namen der Datenbank eingeben", +"e_db_url" => "Bitte Datenbank Hostname eingeben", +"e_db_user" => "Bitte Datenbank Benutzernamen eingeben", +"e_db_prefix" => "Das Kürzel, welches als Prefix für die Tabellennamen verwendet werden soll, darf nur aus alphanumerischen Zeichen bestehen. Sie können die Angabe auch leer lassen.", +"e_db_occurred" => "Datenbankfehler", +"e_db_is" => "Es ist ein Fehler auf ".JLOG_PATH." aufgetreten. Der Fehler lautet:", + +"s_phpv_tolow" => "Die PHP Version ist zu alt, bitte auf eine neuere upgraden, bzw. deinen Provider danach fragen", +"s_mysqlv_tolow" => "Die MySQL Version ist zu alt, bitte auf eine neuere upgraden, bzw. deinen Provider danach fragen", +"s_personal_not_wrtbl" => "Das Verzeichnis 'personal' ist nicht beschreibbar. (Chmod 777)", +"s_img_not_wrtbl" => "Das Verzeichnis 'img' ist nicht beschreibbar. (Chmod 777)", +"s_tables_ok" => "Tabellen in der Datenbank angelegt.", +"s_ready_head" => "Setup erfolgreich beendet", +"s_ready" => "Glückwunsch! Nun kannst du im Administrations Center den ersten Eintrag machen.", +"s_ready_menu_admin" => "Zum Administrations Center", +"s_ready_menu_home" => "Auf die Startseite", +"s_problem_fwrite" => "Probleme beim Erstellen notwendiger Dateien", +"s_problem_chmod" => "Probleme beim Setzen der Schreibrechte", +"s_problem_fwrite" => "Probleme beim notwendigem Schreiben in Dateien", +"s_personal_ok" => "Dateien im Verzeichnis 'personal' angelegt", +"s_install" => "Installieren", + +"login_headline" => "Geschützter Bereich", +"login_password" => "Passwort eingeben:", +"login_send" => "Einloggen", +"login_cookies" => "Hinweis! Cookies müssen aktiv sein.", +"login_false_pw" => "Es wurde ein falsches Passwort eingegeben.", + +"cat_name" => "Name der Kategorie", +"cat_url" => "URL im Kategoriearchiv (nur a-z 0-9 _-,. )", +"cat_description" => "Beschreibung der Kategorie, die im Archiv auftaucht", +"cat_new" => "Neue Kategorie anlegen", +"cat_title" => "Kategorien Verwaltung", +"cat_noname" => "Die Kategorie muss einen Namen haben", +"cat_change" => "Die Kategoriedaten ändern", +"cat_new_ok" => "Neue Kategorie angelegt", +"cat_really_trash" => "Folgende Kategorie wirklich löschen? (Alle Informationen gehen verloren)", +"cat_trash_ok" => "Kategorie erfolgreich gelöscht. Zurück zum", +"cat_admincenter" => "Kategorie Administrationscenter", +"cat_duplicate" => "Eine andere Kategorie hat diesen URL schon besetzt.", + +"update_start" => 'Update starten!', +"update_successfull_part" => 'Das Update wurde erfolgreich ausgeführt.', +"update_successfull" => "Alle Updates wurden erfolgreich durchgeführt. Viel Spaß!", +"update_failure" => "Ein Update ist fehlgeschlagen.", +"pingback_closed" => "Pingbacks für diesen Eintrag schließen.", + +"plugin_no_content" => "Das Plugin muss nicht administriert werden.", +"plugins_h_not_avaliable" => "Keine Plugins", +"plugins_not_avaliable" => "Es wurden keine Plugins gefunden.", +"plugins_headline" => "Plugin Administration", + +// Do not change the folowing line +); +// eof \ No newline at end of file diff --git a/lang/lang-admin.en.inc.php b/lang/lang-admin.en.inc.php new file mode 100644 index 0000000..85ca46e --- /dev/null +++ b/lang/lang-admin.en.inc.php @@ -0,0 +1,246 @@ + "Contents", +"menu_categories" => "Categories", +"menu_comments" => "Comments", +"menu_settings" => "Settings", +"menu_plugins" => "Plugins", +"menu_logout" => "Log out", +"new_post" => "Write a new entry", +"index_headline" => "Administration Center", +"change_headline" => "Edit an old entry", +"go" => "Go", +"admin_headline" => "Administration Center", +"change" => "Edit", +"delete" => "Delete", +"date" => "Date", +"headline" => "Headline", +"metadata" => "Metadata", +"contentdata" => "Entry contents", +"url" => "URL for permanent Link (only 0-9 a-z _-,./ )", +"keywords" => "Keywords", +"categories" => "Category (Select more than one category with the help of the [Ctrl] key or the Apple key)", +"no_categories" => "none", +"preview" => "Preview", +"publish" => "Publish", +"submit" => "Submit", +"cancel" => "Cancel", +"no_headline" => "Entry headline is missing.", +"no_url" => "Entry URL is missing.", +"false_url_letters" => "The entry URL may consist of lower case letters, numbers and this characters _-.,/", +"url_duplicate" => "During one month one certain URL may occur only once as Jlog would be confused by two entries bearing one and the same name.", +"url_duplicate_page" => "Pages must have unique URLs, that is to say that every page must have a different URL.", +"false_teaserpic" => "The declaration of the teaser picture is wrong as the specified picture has not been uploaded to the server.", +"no_teaserpic_uploaded" => "The teaser picture cannot be shown in the blog if it has not been uploaded to the server.", +"no_teaser" => "Entry teaser is missing.", +"no_content" => "Entry content is missing.", +"pic_for_teaser" => "A picture to be shown next to the teaser (max. 150px):", +"pic_upload" => "Upload the picture", +"pic_choose" => "Select a picture", +"show_tpic_on_archive" => "Show this picture on the actual entry page, too.", +"teaser" => "Teaser", +"contentpic_choose" => "A picture to be shown next to the entry content:", +"content" => "Entry content", +"howto_bbcode" => "How to use BBCode?", +"content_choose_year" => "Choose Year:", + +"content_bold" => "bold", +"content_italic" => "italic", +"content_quote" => "Quote", +"content_url" => "Link", +"content_plz_format_txt" => "Please enter the text to be formatted:", +"content_input_on_pos" => "Paste at position", +"content_url_href" => "Enter link location:", +"content_url_node" => "Enter link text:", +"content_list" => "List", +"content_headline" => "Headline", + +"section" => "Type of entry:", +"section_show" => "Show types of entries", +"section_weblog" => "Weblog", +"section_page" => "Page", + +"entry_saved" => "Your entry has been saved.", +"data_updated" => "The data have been updated.", +"post_deleted" => "The blog entry has been deleted.", +"index_topic" => "Latest weblog entries", + +"yes" => "Yes", +"no" => "No", +"rearly_delete" => "Do you really want do delete this entry?", +"delete_blogentry" => "Delete entry", +"postdeleted" => "The entry has been deleted.", +"error_occurred" => "An error occured.", + +"can_not_open" => "Cannot open specified file.", +"can_not_write" => "Cannot write in specified file.", +"no_wrtitenable" => "The specified file is not writable.", +"rss_ok" => "RSS feed and News page have been successfully updated.", +"master_ok" => "The setup file has been successfully updated.", + +"pic_choose_old" => "Select an older picture", +"pic_choose_old_teaser" => "Select an older teaser picture", +"pic_upload_header" => "Upload picture", +"pic_upload_teaser" => "Upload teaser picture", +"pic_error" => "Upload error, please notify your server administrator.", +"pic_uploaded" => "Picture has been uploaded.", +"pic_insert" => "Paste a picture", +"pic_instructions" => "Upload only PNG, GIF or JPEG pictures. File size may not exceed 300 kB.", +"pic_upload" => "Upload", +"pic_class" => "CSS Class, if needed", +"pic_alt" => "Alternative text", + +"pic_height_widht" => "Picture is too high and too wide.", +"pic_width" => "Picture is too wide.", +"pic_height" => "Picture is too high.", +"pic_instr_teaser" => "Upload only PNG, GIF or JPEG pictures not being wider or higher than 150px and not exceeding file sizes of 60 kB.", +"pic_bad_type" => "Wrong format", +"pic_to_big" => "The picture is too big.", + +"kill_c_topic" => "Adminster comments", +"kill_c_killed" => "The comment has successfully been deleted.", +"kill_c_sure" => "Do you really want to delete this comment?", +"kill_c_h2" => "Delete irretrievably", +"kill_c_description" => "Attention: Once a comment is deleted from this list, it will be irretrievably lost!", +"kill_c_entry" => "Weblog entry", +"kill_c_email" => "Delete this comment", +"comments_change_h" => "Edit this comment", +"comments_anonym" => "Anonymous", +"comments_mail_txt" => "New comment on ".JLOG_WEBSITE."\nIts headline is:", +"comments_posted" => "wrote on", +"comments_mailsubject" => "Comment on ".JLOG_WEBSITE, +"comments_comment_topic" => "Comments", +"comments_by" => "Comment of", +"comments_name" => "Name", +"comments_city" => "City / Country", +"comments_email" => "E-mail", +"comments_homepage" => "http://", +"comments_bbcode" => "How to use", +"comments_send" => "Submit", +"comments_preview" => "Preview", +"comments_no_sid" => "Some spoofing seems to be on the go.", +"comments_false_mail" => "Your e-mail address does not look correct.", +"comments_notext" => "No text was entered.", +"comments_false_hp" => "The homepage URL seems to be wrong.", +"comments_permalink" => "Permanent link to this comment", +"comments_from" => "from", +"comments_posted" => "wrote on", +"comments_entryform" => "Edit this comment", +"comments_mail_by_comment" => "Notify me about comments", +"comments_thx" => "The comment has been edited.", +"comments_preview" => "Preview", +"comments_send" => "Submit", +"comments_bold" => "bold", +"comments_italic" => "italic", +"comments_quote" => "Quote", +"comments_url" => "Link", +"comments_plz_format_txt" => "Please enter the text to be formatted:", +"comments_url_href" => "Enter link location:", +"comments_url_node" => "Enter link text:", +"comments_updated" => "The comment has been edited. Back to", +"comments_admin" => "Comment Administration Center", +"comments_closed" => "Disable the comment function for this entry", + +"m_writenable" => "writeable", +"m_title" => "Weblog main settings", +"m_clean_url" => "Shall clean URLs (mod_rewrite) be used? Example: http://example.com/2005/01/firefox", +"m_metadata" => "Metadata", +"m_language" => "Language of your weblog", +"m_website" => "Weblog name", +"m_publisher" => "Name of the author of the entries", +"m_admin_password" => "Administration Center password", +"m_admin_password_again" => "Confirm password", +"m_admin_password_admin" => "(keep empty to not change it)", +"m_email" => "E-mail address of the owner of the weblog", +"m_description" => "A short description of the weblog", +"m_bs" => "Notify weblog services about new entries to make them add your entries to their search engine (one per line)", +"m_bs_weblogs_com" => "weblogs.com", +"m_bs_technorati_com" => "technorati.com", +"m_bs_blogg_de" => "blogg.de", +"m_behavior" => "Weblog behavior", +"m_max_blog_orginal" => "Number of entries that are shown completely on the weblog main page", +"m_max_blog_big" => "Number of entries that are announced by their description on the weblog main page", +"m_max_blog_small" => "Number of entries that are announced by their headline and date on the weblog main page", +"m_sub_current" => "Number of entries that are announced by their headline and date in the sub-navigation on every page of the weblog", +"m_info_by_comment" => "Notify the owner of the weblog about new comments", +"m_database" => "Database", +"m_db" => "Name of database", +"m_db_url" => "Hostname of database, usually localhost", +"m_db_user" => "Username of database", +"m_db_pwd" => "Password of database", +"m_db_prefix" => "Short identification code to be prefixed to table names", +"m_date" => "Date format (a format string like the one of the PHP function strftime())", +"m_date_posting" => "for postings", +"m_date_comment" => "for comments", +"m_date_subcurrent" => "for the subnavigation", +"m_settings_ok" => "Your settings have been saved.", + +"e_path" => "The specified URL seems to be wrong.", +"e_basepath" => "The specified directory does not exist.", +"e_website" => "Please enter the name of the weblog.", +"e_publisher" => "Please enter the name of the owner of the weblog.", +"e_admin_password" => "Please enter the password that is required to access the Administration Center.", +"e_admin_password_again" => "Please confirm the password of the Administration Center.", +"e_email" => "The e-mail address of the owner of the weblog seems to be wrong.", +"e_description" => "Please enter a description of the weblog.", +"e_max_blog_orginal" => "Number of entries that are shown completely on the weblog main page must be a number greater than or equal to zero.", +"e_max_blog_big" => "Number of entries that are announced by their description on the weblog main page must be a number greater than or equal to zero.", +"e_max_blog_small" => "Number of entries that are announced by their headline and date on the weblog main page must be a number greater than or equal to zero.", +"e_sub_current" => "Number of entries that are announced by their headline and date in the sub-navigation on every page of the weblog must be a number greater than or equal to zero.", +"e_start_year" => "The hidden year field is empty.", +"e_db" => "Please enter the name of the database.", +"e_db_url" => "Please enter the hostname of the database.", +"e_db_user" => "Please enter the username of the database.", +"e_db_prefix" => "The prefix for table names must not contain anything but alpha-numeric characters. However, you can leave option empty.", +"e_db_occurred" => "Database error", +"e_db_is" => "A error occured in ".JLOG_PATH.". It is:", + +"s_phpv_tolow" => "Your PHP version is too old, please upgrade to a newer one or ask your server administrator to do this.", +"s_mysqlv_tolow" => "Your MySQL version is too old, please upgrade to a newer one or ask your server administrator to do this.", +"s_personal_not_wrtbl" => "The directory 'personal' is not writeable. (Chmod 777)", +"s_img_not_wrtbl" => "The directory 'img' is not writeable. (Chmod 777)", +"s_tables_ok" => "Tables have been created in the database.", +"s_ready_head" => "Setup has been successfully finished.", +"s_ready" => "Congratulations! You can start writing your first blog entry in the Administration Center.", +"s_ready_menu_admin" => "To the Administration Center", +"s_ready_menu_home" => "To the weblog main page", +"s_problem_fwrite" => "Problems occured during the Creation of required files.", +"s_problem_chmod" => "Problems occured while setting write permissions.", +"s_problem_fwrite" => "Problems occured during required writing access to files.", +"s_personal_ok" => "Files in the directory 'personal' have been created.", +"s_install" => "Install", + +"login_headline" => "Protected area", +"login_password" => "Enter password:", +"login_send" => "Log in", +"login_cookies" => "Please note: Cookies must be activated in your browser!", +"login_false_pw" => "Wrong password entered.", + +"cat_name" => "Category name", +"cat_url" => "URL in category archive (only a-z 0-9 _-,. )", +"cat_description" => "Category descriptiom that occurs in the archive", +"cat_new" => "Create new category", +"cat_title" => "Categories management", +"cat_noname" => "The category must have a name.", +"cat_change" => "Edit category data", +"cat_new_ok" => "The new category has been created.", +"cat_really_trash" => "Do you really want to delete the following category? (All information will be lost.)", +"cat_trash_ok" => "The category has successfully been deleted. Back to", +"cat_admincenter" => "Categories Administration Center", +"cat_duplicate" => "Another category is already using this URL.", + +"update_start" => 'Perform update!', +"update_successfull_part" => 'This update has been performed successfully.', +"update_successfull" => "All updates have been performed. Have fun!", +"update_failure" => "Ein Update ist fehlgeschlagen.", +"pingback_closed" => "Close pingbacks for this entry.", + +"plugin_no_content" => "There is no need to administrate this plugin.", +"plugins_h_not_avaliable" => "No plugins available", +"plugins_not_avaliable" => "I couldn't find any plugins.", +"plugins_headline" => "Plugin Administration", + +// Do not change the folowing line! +); +// eof \ No newline at end of file diff --git a/lang/lang-admin.it.inc.php b/lang/lang-admin.it.inc.php new file mode 100644 index 0000000..c0bff8a --- /dev/null +++ b/lang/lang-admin.it.inc.php @@ -0,0 +1,241 @@ + "Contenuti", +"menu_categories" => "Categorie", +"menu_comments" => "Commenti", +"menu_settings" => "Settaggi", +"menu_plugins" => "Plugins", +"menu_logout" => "Log out", +"new_post" => "Scrivi una nuova nota", +"index_headline" => "Administration Center", +"change_headline" => "Modifica una vecchia nota", +"go" => "Vai", +"admin_headline" => "Centro d'amministrazione", +"change" => "Modifica", +"delete" => "Cancella", +"date" => "Data", +"headline" => "Titolo", +"metadata" => "Metadata", +"contentdata" => "Contenuti della nota", +"url" => "URL per Link permanenti (only 0-9 a-z _-,. )", +"keywords" => "Parola chiave", +"categories" => "Categoria (seleziona piu di una categoria con help file di [Ctrl] tasto or the Apple tasto)", +"no_categories" => "nessuna", +"preview" => "Anteprima", +"publish" => "Pubblica", +"submit" => "Inoltrare", +"cancel" => "Cancella", +"no_headline" => "Inseerisci il titolo se mancante.", +"no_url" => "Inserisci URL se mancante.", +"false_url_letters" => "Il nuovo URL deve contenere lettere minuscole, numeri e questi caratteri _-.,/", +"url_duplicate" => "Derante un mese gli URL in Jlog devono avere tutti nomi diversi per evitare che il sistema si confonda.", +"url_duplicate_page" => "La pagina deve avere un solo URLs,in questo modo ogni pagina ha un diverso URL.", +"false_teaserpic" => "L’immagine introduttiva non esiste,l’immagine non é stata salvata nel server.", +"no_teaserpic_uploaded" => "L’immagine introduttiva non puo essere mostrata nel blog se non e stata salvata nel server.", +"no_teaser" => "L'introduzzione manca.", +"no_content" => "Inserisci cintenuto perche mancante.", +"pic_for_teaser" => "Un immagine sara visualizzata nella prossima introduzione (max. 150px):", +"pic_upload" => "Upload immagine", +"pic_choose" => "Seleziona una immagine", +"show_tpic_on_archive" => "Mostra questa immagine anche nell'attuale nota.", +"teaser" => "Introduzione", +"contentpic_choose" => "L'immagine sara visualizzata nella nuova categoria:", +"content" => "Contenuti nota", +"howto_bbcode" => "Come usare BBCode?", +"content_choose_year" => "Sciegli l'anno:", + +"content_bold" => "Grassetto", +"content_italic" => "Corsivo", +"content_quote" => "Citazione", +"content_url" => "Link", +"content_plz_format_txt" => "Perfavore sciegliere il testo per cambiare lo stile:", +"content_input_on_pos" => "Incolla", +"content_url_href" => "Inserisci dove si trova il link:", +"content_url_node" => "Inserisci link testo:", +"content_list" => "Lista", +"content_headline" => "Titolo", + +"section" => "Tipo di nota:", +"section_show" => "Mostra tipi di note", +"section_weblog" => "Weblog", +"section_page" => "Pagina", + +"entry_saved" => "La tua nota e stata salvata .", +"data_updated" => "I dati sono stati updated.", +"post_deleted" => "La nota deve essere cancellata.", +"index_topic" => "Ultima nota nel weblog", + +"yes" => "Si", +"no" => "No", +"rearly_delete" => "Vuoi veramente cancellare questa nota?", +"delete_blogentry" => "Cancella nota", +"postdeleted" => "La nota e stata cancellata.", +"error_occurred" => "Errore in corso.", + +"can_not_open" => "Impossibile aprire il file specificato.", +"can_not_write" => "Impossibile scrivere il file specificato.", +"no_wrtitenable" => "Non si puo scrivere questo file.", +"rss_ok" => "RSS feed e News page sono state aggiornate con successo.", +"master_ok" => "Il file di setup e stato aggiornato con successo.", + +"pic_choose_old" => "Selezionare foto precedenti", +"pic_choose_old_teaser" => "Select an older teaser picture", +"pic_upload_header" => "Aggiorna immagini", +"pic_upload_teaser" => "Upload teaser picture", +"pic_error" => "Errore di aggiornamento, per favore notificarlo all'aministratore del server.", +"pic_uploaded" => "Le immagini sono state aggiornate.", +"pic_insert" => "Incolla una immagine", +"pic_instructions" => "Aggiornare solo immagini PNG, GIF or JPEG. La dimensione del file non deve essere superiore a 300 kB.", +"pic_upload" => "Aggiorna", +"pic_class" => "CSS Class, se necessario", +"pic_alt" => "Testi alternativi", + +"pic_height_widht" => "L'immagine e troppo larga e alta.", +"pic_width" => "L'immagine e troppo larga.", +"pic_height" => "L'immagine e troppo alta.", +"pic_instr_teaser" => "Aggiorna solo immagini in PNG, GIF or JPEG non devono essere alte o larghe piu di 150px e non devono eccedere oltre 60 kB.", +"pic_bad_type" => "Formato non valido", +"pic_to_big" => "L'immagine e troppo grande.", + +"kill_c_topic" => "Commenti dell'amministratore", +"kill_c_killed" => "Il commento e stato cancellato.", +"kill_c_sure" => "Vuoi veramente cancellare questo commento?", +"kill_c_h2" => "Cancellazione irreversibile", +"kill_c_description" => "Attenzione: Un commento e stato cancellato dalla lista, sara perso per sempre!", +"kill_c_entry" => "Nota Weblog", +"kill_c_email" => "Cancella questo commento", +"comments_change_h" => "Modifica questo commento", +"comments_anonym" => "Anonimo", +"comments_mail_txt" => "Nuovo commento in ".JLOG_WEBSITE."\nIts il titolo e:", +"comments_posted" => "scrivi", +"comments_mailsubject" => "Commento on ".JLOG_WEBSITE, +"comments_comment_topic" => "Commenti", +"comments_by" => "Commento off", +"comments_name" => "Nome", +"comments_city" => "Citta / Paese", +"comments_email" => "E-mail", +"comments_homepage" => "http://", +"comments_bbcode" => "Come si usa", +"comments_send" => "Inoltra", +"comments_preview" => "Anteprima", +"comments_no_sid" => "Stai scherzando?.", +"comments_false_mail" => "L'indirizzo e-mail non e corretto.", +"comments_notext" => "Non e presente nessun testo.", +"comments_false_hp" => "Homepage URL sembra errato.", +"comments_permalink" => "Link permanente per questo commento", +"comments_from" => "da", +"comments_posted" => "scrivi", +"comments_entryform" => "Modifica questo commento", +"comments_mail_by_comment" => "Tienimi informato su questo commento", +"comments_thx" => "Il commento é stato creato con successo.", +"comments_preview" => "Anteprima", +"comments_send" => "Inoltra", +"comments_bold" => "Grassetto", +"comments_italic" => "Corsivo", +"comments_quote" => "Quote", +"comments_url" => "Link", +"comments_plz_format_txt" => "Perfavore sciegliere il testo per cambiare lo stile:", +"comments_url_href" => "Inserire la locazione del link:", +"comments_url_node" => "Inserire link text:", +"comments_updated" => "Il commento e stato creato. Indietro", +"comments_admin" => "Commento Administration Center", +"comments_closed" => "Disabilita i commenti per questa nota", + +"m_writenable" => "writeable", +"m_title" => "Weblog settaggi", +"m_clean_url" => "Pulire URLs (mod_rewrite) usati? Esempio: http://example.com/2005/01/firefox", +"m_metadata" => "Metadata", +"m_language" => "Lingua del vostro weblog", +"m_website" => "Nome Weblog", +"m_publisher" => "Nome dell'autore della nota", +"m_admin_password" => "Administration Center password", +"m_admin_password_again" => "Conferma password", +"m_admin_password_admin" => "(lascia vuoto per non cambiarla)", +"m_email" => "E-mail del proprietario del weblog", +"m_description" => "Piccola descrizione del weblog", +"m_bs" => "Notifica quando si aggiungono nuove note (uno per riga)", +"m_bs_weblogs_com" => "weblogs.com", +"m_bs_technorati_com" => "technorati.com", +"m_bs_blogg_de" => "blogg.de", +"m_behavior" => "Carattere weblog", +"m_max_blog_orginal" => "Il numero delle note si strova nella pagina principale", +"m_max_blog_big" => "Numero di note con descrizione presenti nella pagina principale del weblog", +"m_max_blog_small" => "Numero di note con titolo e data presenti nella pagina principale del weblog", +"m_sub_current" => "Numero di note che sono introdotte da titolo e data ipresenti nelle altre pagine del weblog", +"m_info_by_comment" => "Avvisa il proprietario della nota quando ci sono nuovi commenti ", +"m_database" => "Database", +"m_db" => "Nome database", +"m_db_url" => "Hostname del database, solitamente localhost", +"m_db_user" => "Username del database", +"m_db_pwd" => "Password del database", +"m_db_prefix" => "Codice identificazione per prefissi in table names", +"m_date" => "Forma data (a format string like the one of the PHP function strftime())", +"m_date_posting" => "per affissioni", +"m_date_comment" => "per commenti", +"m_date_subcurrent" => "per la subnavigation", +"m_settings_ok" => "I tuoi settaggi sono stati salvati.", + +"e_path" => "Specificare URL perche non corretto.", +"e_basepath" => "Specificare directory non esiste.", +"e_website" => "Perfavore inserire il nome weblog.", +"e_publisher" => "Perfavore inserire il nome del propietario del weblog.", +"e_admin_password" => "Inserire la password necessaria per avere accesso all'Administration Center.", +"e_admin_password_again" => "Confermare password per Administration Center.", +"e_email" => "L'e-mail del propietario del weblog non e corretto.", +"e_description" => "Inserire descrizione del weblog.", +"e_max_blog_orginal" => "Il numero di note e visualizzato nella pagina principale e deve essere maggiore o uguale a zero.", +"e_max_blog_big" => "Numero di note con descrizione presenti nella pagina principale del weblog deve essere maggiore o uguale a zero.", +"e_max_blog_small" => "Numero di note con titolo e data presenti nella pagina principale del weblog deve essere maggiore o uguale a zero.", +"e_sub_current" => "Numero di note che sono introdotte da titolo e data ipresenti nelle altre pagine del weblog deve essere maggiore o uguale a zero.", +"e_start_year" => "La casella nascosta dell'anno e vuota.", +"e_db" => "Inserire nome database.", +"e_db_url" => "Inserire hostname del database.", +"e_db_user" => "Inserire username del database.", +"e_db_occurred" => "Errore database", +"e_db_is" => "Errore in ".JLOG_PATH.". E:", + +"s_phpv_tolow" => "La tua versione del PHP e troppo vecchia, perfavore aggiornare o chiedere all'aministrator del server.", +"s_mysqlv_tolow" => "La tuaversione del MySQL e troppo vecchia, perfavore aggiornare o chiedere all'aministrator del server.", +"s_personal_not_wrtbl" => "La directory 'personal' non puo essere scritta. (Chmod 777)", +"s_img_not_wrtbl" => "La directory 'img' non puo essere scritta. (Chmod 777)", +"s_tables_ok" => "Le tabelle sono state create nel database.", +"s_ready_head" => "Installazione completata con successo.", +"s_ready" => "Tanti auguri! Puoi iniziare a scrivere a scrivere la tua prima nota in Administration Center.", +"s_ready_menu_admin" => "Per Administration Center", +"s_ready_menu_home" => "Per la pagina principale del weblog", +"s_problem_fwrite" => "Problema durante la creazione del file richiesto.", +"s_problem_chmod" => "Problema durante setting write permissions.", +"s_problem_fwrite" => "Problema durante la scrittura del file.", +"s_personal_ok" => "I file in 'personal' sono stati creati.", +"s_install" => "Installa", + +"login_headline" => "Area protetta", +"login_password" => "Inserisci password:", +"login_send" => "Log in", +"login_cookies" => "Attenzione: I Cookies devono essere attivati nel tuo browser!", + +"cat_name" => "Nome categoria", +"cat_url" => "URL in archivio categorie (only a-z 0-9 _-,. )", +"cat_description" => "Descrizione della categoria richiesta", +"cat_new" => "Crea una nuova categoria", +"cat_title" => "Gestione categorie", +"cat_noname" => "La categoria deve avere un nome.", +"cat_change" => "Modifica data categoria", +"cat_new_ok" => "Una nuova categoria e stata creata.", +"cat_really_trash" => "Vuoi veramente cancellare la seguente categoria? (Tutte le informazioni saranno perse.)", +"cat_trash_ok" => "La categoria e stata cancellata. Indietro", +"cat_admincenter" => "Categorie Administration Center", +"cat_duplicate" => "Un altra categoria sta usando questo URL.", + +"update_successfull" => "Aggiornato con successo. Have fun!", +"pingback_closed" => "Chiudi pingbacks per questa nota.", + +"plugin_no_content" => "Non occorre questo plugin.", +"plugins_h_not_avaliable" => "Plugin non disponibili", +"plugins_not_avaliable" => "Non trovo nessun plugins.", +"plugins_headline" => "Plugin Administration", + +// Do not change the folowing line! +); +// eof \ No newline at end of file diff --git a/lang/lang-admin.pl.inc.php b/lang/lang-admin.pl.inc.php new file mode 100644 index 0000000..cec356c --- /dev/null +++ b/lang/lang-admin.pl.inc.php @@ -0,0 +1,241 @@ + "Zawartosść", +"menu_categories" => "Kategorie", +"menu_comments" => "Komentarze", +"menu_settings" => "Konfiguracja", +"menu_plugins" => "Wtyczki", +"menu_logout" => "Wyloguj Å›iÄ™", +"new_post" => "Napisz nowy watek", +"index_headline" => "Centrum Administracyjne", +"change_headline" => "Edytuj stary watek", +"go" => "Start", +"admin_headline" => "Centrum Administracyjne", +"change" => "Edytuj", +"delete" => "Kasuj", +"date" => "Data", +"headline" => "Nagłówek", +"metadata" => "Metadane", +"contentdata" => "Zawartość watku", +"url" => "URL na permanentny link (tylko 0-9 a-z _-,./ )", +"keywords" => "SÅ‚owa kluczowe", +"categories" => "Kategoria (Wybierz wiÄ™cej niż jednÄ… kategoriÄ™ za pomocÄ… klawisza [Ctrl] albo klawisza Apple)", +"no_categories" => "żadna", +"preview" => "PodglÄ…d", +"publish" => "Publikuj", +"submit" => "Zaloguj", +"cancel" => "Anuluj", +"no_headline" => "Brak nagłówka watku.", +"no_url" => "Brak URL watku.", +"false_url_letters" => "W URL możecz tylko używac a do z i _-.,/", +"url_duplicate" => "W ciÄ…gu jednego miesiÄ…ca okreÅ›lony URL może siÄ™ pojawic tylko raz,", +"url_duplicate_page" => "Strony muszÄ… mieć unikalne URLe, co oznacza że każda strona musi mieć inny URL.", +"false_teaserpic" => "Okreslony obrazek nie zostal zapisany na serwerze.", +"no_teaserpic_uploaded" => "Obrazek skróconego opisu nie moze byc pokazany w blogu jesli nie zoatal zapisany na serwerze.", +"no_teaser" => "Brak skróconego opisu.", +"no_content" => "Brak zawartośći artykuÅ‚u.", +"pic_for_teaser" => "Obrazek który zostanie pokazany przy skróconym opisie (max. 150px):", +"pic_upload" => "SciÄ…gnij obrazek", +"pic_choose" => "Wybierz obrazek", +"show_tpic_on_archive" => "Pokaz ten obrazek rowniez na bieżącej stronie.", +"teaser" => "Skrócony opis", +"contentpic_choose" => "Obrazek który zostanie pokazany przy zawartośći arkykuÅ‚u:", +"content" => "Zawartość artykuÅ‚u", +"howto_bbcode" => "Jak używać BBCode?", +"content_choose_year" => "Wybierz rok:", + +"content_bold" => "wytluszczony", +"content_italic" => "pochyÅ‚y", +"content_quote" => "cytat", +"content_url" => "link", +"content_plz_format_txt" => "Prosze wprowadzic tekst do sformatowania:", +"content_input_on_pos" => "Wklej do", +"content_url_href" => "Wprowadź lokalizacje linku:", +"content_url_node" => "Wprowadź tekst linku:", +"content_list" => "Lista", +"content_headline" => "Naglówek", + +"section" => "Rodzaj watku:", +"section_show" => "Pokaż rodzaje watkuw", +"section_weblog" => "Weblog", +"section_page" => "Strona", + +"entry_saved" => "Twój watek zostaÅ‚ zapisany.", +"data_updated" => "Dane zostaly uaktualnione.", +"post_deleted" => "Watek zostal usuniety.", +"index_topic" => "Ostatnie wejscia na weblog", + +"yes" => "Tak", +"no" => "Nie", +"rearly_delete" => "Czy jestes pewny/a ze chcesz zlikwidowac ten watek?", +"delete_blogentry" => "Zlikwiduj watek", +"postdeleted" => "Watek zostal zlikwidowany.", +"error_occurred" => "Pojawil sie blad.", + +"can_not_open" => "Nie da sie otworzyc tego dokumentu.", +"can_not_write" => "Cannot write in specified file.", +"no_wrtitenable" => "The specified file is not writable.", +"rss_ok" => "RSS feed and News page zostaly pomyslnie uaktualnione.", +"master_ok" => "setup zostal pomyslnie uaktualniony.", + +"pic_choose_old" => "Wybierz starszy obrazek", +"pic_choose_old_teaser" => "Wybierz starszy obrazek skróconego opisu", +"pic_upload_header" => "WyÅ›lij obrazek", +"pic_upload_teaser" => "WyÅ›lij obrazek skróconego opisu", +"pic_error" => "WyÅ›lij raport o bÅ‚edzie, prosze zawiadomic administratora swojego serwera.", +"pic_uploaded" => "Obrazek zostal wysÅ‚any.", +"pic_insert" => "Wklej obrazek", +"pic_instructions" => "WyÅ›lij tylko obrazki o rozszerzeniu PNG, GIF lub JPEG. Rozmiar dokumentu nie może przekroczyc 300 kB.", +"pic_upload" => "WyÅ›lij", +"pic_class" => "w potżebie klassa CSS", +"pic_alt" => "tekst alternatywny", + +"pic_height_widht" => "Obrazek jest zbyt wysoki i zbyt szeroki.", +"pic_width" => "Obrazek jest zbyt szeroki.", +"pic_height" => "Obrazek jest zbyt wysoki.", +"pic_instr_teaser" => "Wyslij tylko obrazki z rozszerzeniem PNG, GIF lub JPEG, ktore nie sa szersze ani wyzsze niz 150px i rozmiar dokumentu nie przekracza 60 kB.", +"pic_bad_type" => "ZÅ‚y format", +"pic_to_big" => "Obrazek jest zbyt duży.", + +"kill_c_topic" => "Komentarze administratora", +"kill_c_killed" => "Komentarz zostaÅ‚ pomyÅ›lnie usuniety.", +"kill_c_sure" => "Czy jesteÅ› pewny ze chcesz usunąć ten komentarz?", +"kill_c_h2" => "UsuÅ„ calkowicie", +"kill_c_description" => "Uwaga: Gdy komentarz zostanie usuniÄ™ty z listy, nie bÄ™dzie możliwe jego odtworzenie!", +"kill_c_entry" => "Weblog artykół", +"kill_c_email" => "UsuÅ„ ten komentarz", +"comments_change_h" => "Edytuj ten komentarz", +"comments_anonym" => "Anonim", +"comments_mail_txt" => "Nowy komentarz na ".JLOG_WEBSITE."\nJego nagłówek jest:", +"comments_posted" => "pisany", +"comments_mailsubject" => "Komentarz na ".JLOG_WEBSITE, +"comments_comment_topic" => "Komentarze", +"comments_by" => "komentarz od", +"comments_name" => "ImiÄ™", +"comments_city" => "Miejscowość / Kraj", +"comments_email" => "emaila", +"comments_homepage" => "http://", +"comments_bbcode" => "Jak używać", +"comments_send" => "WyÅ›lij", +"comments_preview" => "PodglÄ…d", +"comments_no_sid" => "To wyglÄ…da na manipulacjÄ™.", +"comments_false_mail" => "Twoj adres emaila jest niepoprawny.", +"comments_notext" => "Nie zostaÅ‚ wprowadzony tekst.", +"comments_false_hp" => "URL strony glównej jest bÅ‚edny.", +"comments_permalink" => "Permanentny link do tego komentarza", +"comments_from" => "od", +"comments_posted" => "pisany", +"comments_entryform" => "Edytuj ten komentarz", +"comments_mail_by_comment" => "Powiadom mnie o komentarzach", +"comments_thx" => "Komentarz zostaÅ‚ edytowany.", +"comments_preview" => "PodglÄ…d", +"comments_send" => "WyÅ›lij", +"comments_bold" => "wytluszczony", +"comments_italic" => "pochyÅ‚y", +"comments_quote" => "cytat", +"comments_url" => "link", +"comments_plz_format_txt" => "Prosze wprowadzić tekst do sformatowania:", +"comments_url_href" => "Wprowadź link location:", +"comments_url_node" => "Wprowadź tekst linka:", +"comments_updated" => "Komentarz zostaÅ‚ edytowany. Z powrotem do", +"comments_admin" => "Centrum administrowania komentarzy", +"comments_closed" => "Wyłącz komentaże teko artykuÅ‚u", + +"m_writenable" => "prawo do zapisu", +"m_title" => "Główne ustawienia webloga", +"m_clean_url" => "Używac Å‚adne URL (mod_rewrite)? PrzykÅ‚ad: http://example.com/2005/01/firefox", +"m_metadata" => "Metadane", +"m_language" => "Jezyk twojego webloga", +"m_website" => "Nazwa webloga", +"m_publisher" => "Imie autora watkow", +"m_admin_password" => "Haslo centrum administracyjnego", +"m_admin_password_again" => "Potwierdź hasÅ‚o", +"m_admin_password_admin" => "(zostaw puste abe nie zmieniać)", +"m_email" => "Address emaila wÅ‚aÅ›ciciela tego webloga", +"m_description" => "Krótki opis webloga", +"m_bs" => "Zawiadom serwisy blogowe o nowym artykule aby dodali jego do swoich przeszukiwarek (jeden na linjÄ™)", +"m_bs_weblogs_com" => "weblogs.com", +"m_bs_technorati_com" => "technorati.com", +"m_bs_blogg_de" => "blogg.de", +"m_behavior" => "zachowanie na weblogu", +"m_max_blog_orginal" => "Ile artykuÅ‚uw pokazać na stronie głównej?", +"m_max_blog_big" => "Ile krótkich opisów artykuÅ‚uw pokazać na stronie głównej?", +"m_max_blog_small" => "Ile nagłówkuw z datÄ… artykuÅ‚uw pokazać na stronie głównej?", +"m_sub_current" => "Ile nagłówkuw z datÄ… artykuÅ‚uw pokazać na boku każdej strony webloga?", +"m_info_by_comment" => "Zawiadom wÅ‚asciciela webloga o nowych komentarzach", +"m_database" => "Baza danych", +"m_db" => "Nazwa bazy danych", +"m_db_url" => "Hostname bazy danych, normalnie localhost", +"m_db_user" => "Użytkownik bazy danych", +"m_db_pwd" => "Haslo bazy danych", +"m_db_prefix" => "Krótki prefix nazw tabelów", +"m_date" => "Format daty (jak w funkcji PHP strftime())", +"m_date_posting" => "dla artykuÅ‚uw", +"m_date_comment" => "dla komentarzy", +"m_date_subcurrent" => "dla bocznej nawigacji", +"m_settings_ok" => "Twoje ustawienia zostaly zapisane.", + +"e_path" => "Dany URL jest bÅ‚edny.", +"e_basepath" => "Nie ma danego katalogu.", +"e_website" => "Prosze wprowadzic nazwÄ™ webloga.", +"e_publisher" => "Prosze wprowadzic imiÄ™ wÅ‚aųciciela webloga.", +"e_admin_password" => "Prosze wprowadzic hasÅ‚o dostÄ™pu do centrum administracyjnego.", +"e_admin_password_again" => "Prosze potwierdzic hasÅ‚o centrum administracyjnego.", +"e_email" => "Adres emaila wÅ‚aÅ›ciciela webloga jest bÅ‚edny.", +"e_description" => "Prosze wprowadzic opis webloga.", +"e_max_blog_orginal" => "Ilość artykuÅ‚uw na głównej stronie muÅ›i byci 0 albo wiÄ™cej.", +"e_max_blog_big" => "Ilość skróconegych opisuw na głównej stronie muÅ›i byci 0 albo wiÄ™cej.", +"e_max_blog_small" => "Ilość nagłówkuw z datÄ… na głównej stronie muÅ›i byci 0 albo wiÄ™cej.", +"e_sub_current" => "Ilość nagłówkuw z datÄ… na boku każdej strony muÅ›i byci 0 albo wiÄ™cej.", +"e_start_year" => "Ukryty rok byÅ‚ pusty.", +"e_db" => "Prosze wprowadzic nazwÄ™ bazy danych.", +"e_db_url" => "Prosze wprowadzic the nazwa hosta bazy danych.", +"e_db_user" => "Prosze wprowadzic imie użytkownika bazy danych.", +"e_db_occurred" => "BÅ‚ad bazy danych", +"e_db_is" => "PojawiÅ‚ siÄ™ bÅ‚ad w ".JLOG_PATH.". To jest:", + +"s_phpv_tolow" => "Twoja wersja PHP jest zbyt stara, proszÄ™ zaopatrzyć siÄ™ w nowszÄ… lub poprosić o to administratora serwera.", +"s_mysqlv_tolow" => "Twoja wersja MySQL jest zbyt stara, proszÄ™ zaopatrzyć siÄ™ w nowszÄ… lub poprosić o to administratora serwera.", +"s_personal_not_wrtbl" => "Nie mam prawa pisac do kataloga 'personal'. (Chmod 777)", +"s_img_not_wrtbl" => "Nie mam prawa pisac do kataloga 'img'. (Chmod 777)", +"s_tables_ok" => "Tabely bazy danych zostaÅ‚y ztwożone.", +"s_ready_head" => "Twój nowy weblog zostaÅ‚ utworzony.", +"s_ready" => "Gratulacje! Mozesz zacząć pisac swój pierwszy wpis w centrum administracynym.", +"s_ready_menu_admin" => "Do centrum administracyjnego", +"s_ready_menu_home" => "Do strony glównej weblogu", +"s_problem_chmod" => "Błąd w ciÄ…gu ustawienia prawa pisania.", +"s_problem_fwrite" => "Błąd w ciÄ…gu pisania danych do pliku.", +"s_personal_ok" => "Pliki w katalogu 'personal' zostaÅ‚y utworzona.", +"s_install" => "Instaluj", + +"login_headline" => "Obszar chroniony", +"login_password" => "Wprowadź hasÅ‚o:", +"login_send" => "Zaloguj siÄ™", +"login_cookies" => "Uwaga: Cookie muszÄ… być aktywne w twojej przeglÄ…darce!", +"login_false_pw" => "Wprowadzono zÅ‚e hasÅ‚o.", + +"cat_name" => "Nazwa kategorii", +"cat_url" => "URL archiwie kategorii (tylko a-z 0-9 _-,. )", +"cat_description" => "Opis kategorii które pojawiÅ‚y siÄ™ w archiwum", +"cat_new" => "Stwóz nowÄ… kategorie", +"cat_title" => "Zarzadzanie kategoriami", +"cat_noname" => "Kategoria musi mieć nazwÄ™.", +"cat_change" => "Edytuj dane kategorii", +"cat_new_ok" => "ZostaÅ‚a utworzona nowa kategoria.", +"cat_really_trash" => "Czy jesteÅ› pewny że chcesz usunąć nastÄ™pujacÄ… kategorie? (Wszystkie informacje zostanÄ… stracone.)", +"cat_trash_ok" => "Kategoria zostaÅ‚a pomyÅ„lnie usuniÄ™ta. Z powrotem do", +"cat_admincenter" => "Centrum administracji kategoriami", +"cat_duplicate" => "Inna kategoria już używa tego URL.", + +"update_successfull" => "Uaktualnienie zostaÅ‚o pomyÅ›lnie dokonane. Have fun!", +"pingback_closed" => "Nie dopuÅ›cić pingbacków dla tego artykuÅ‚u.", + +"plugin_no_content" => "Nie potrzeba administrować tego pluginu.", +"plugins_h_not_avaliable" => "Nie ma pluginuw", +"plugins_not_avaliable" => "Nie mozna znalezc zadnych pluginuw.", +"plugins_headline" => "Administracja pluginuw", + +// Do not change the folowing line! +); +// eof \ No newline at end of file diff --git a/lang/lang-admin.sv.inc.php b/lang/lang-admin.sv.inc.php new file mode 100644 index 0000000..1ebde89 --- /dev/null +++ b/lang/lang-admin.sv.inc.php @@ -0,0 +1,241 @@ + "InnehÃ¥ll", +"menu_categories" => "Kategorier", +"menu_comments" => "Kommentarer", +"menu_settings" => "Inställningar", +"menu_plugins" => "Plugins", +"menu_logout" => "Logga ut", +"new_post" => "Skriv ett nytt inlägg", +"index_headline" => "Administrationscenter", +"change_headline" => "Editera ett gammalt inlägg", +"go" => "Go", +"admin_headline" => "Administrationscenter", +"change" => "Editera", +"delete" => "Radera", +"date" => "Datum", +"headline" => "Rubrik", +"metadata" => "Metadata", +"contentdata" => "InnehÃ¥ll", +"url" => "URL för permanent länk (bara 0-9 a-z _-,./ )", +"keywords" => "Nyckelord", +"categories" => "Kategori (Välj flera kategorier med hjälp av [Ctrl] eller Command tangenten)", +"no_categories" => "ingen", +"preview" => "Förhandsgranskning", +"publish" => "Publicera", +"submit" => "Skicka", +"cancel" => "Avbryt", +"no_headline" => "Rubriken fattas.", +"no_url" => "URL fattas.", +"false_url_letters" => "URLen fÃ¥r bara innehÃ¥lla smÃ¥ bokstäver, siffror eller _-.,/", +"url_duplicate" => "Exakt samma webblogginlägg-url fÃ¥r ej förekomma tvÃ¥ gÃ¥nger under samma mÃ¥nad", +"url_duplicate_page" => "Alla sidor-url:er mÃ¥sta vara unika.", +"false_teaserpic" => "Teaserbilden har inte blivit upladdad än.", +"no_teaserpic_uploaded" => "Teaserbilden kan inte visas om den inte är uppladdad.", +"no_teaser" => "Teaser fattas.", +"no_content" => "InnehÃ¥ll fattas.", +"pic_for_teaser" => "Bilden som ska visas i teasern (max 150px):", +"pic_upload" => "Ladda upp bild", +"pic_choose" => "Välj bild", +"show_tpic_on_archive" => "Visa bilden även i bloggen.", +"teaser" => "Teaser", +"contentpic_choose" => "Bilden som visas i innehÃ¥ll:", +"content" => "InnehÃ¥ll", +"howto_bbcode" => "Hur använder man BBCode?", +"content_choose_year" => "Välj Ã¥r:", + +"content_bold" => "fet", +"content_italic" => "kursiv", +"content_quote" => "citera", +"content_url" => "länk", +"content_plz_format_txt" => "Skriv in texten som ska formateras:", +"content_input_on_pos" => "Klistra in vid position:", +"content_url_href" => "Skriv in URLen:", +"content_url_node" => "Skriv in texten:", +"content_list" => "lista", +"content_headline" => "rubrik", + +"section" => "Typ av inlägg:", +"section_show" => "Visa typer av inlägg", +"section_weblog" => "Webblogg", +"section_page" => "Sida", + +"entry_saved" => "Inlägg har sparats.", +"data_updated" => "Datan har uppdaterats.", +"post_deleted" => "Blogginlägg har raderats.", +"index_topic" => "Senaste blogginlägg", + +"yes" => "Ja", +"no" => "Nej", +"rearly_delete" => "Är du säker att du vill radera inlägget?", +"delete_blogentry" => "Radera inlägget", +"error_occurred" => "Ett fel har upstÃ¥tt.", + +"can_not_open" => "Kan inte öppna filen.", +"can_not_write" => "Kan inte spara filen.", +"no_wrtitenable" => "Det gÃ¥r inte att skriva till filen.", +"rss_ok" => "RSS och 'aktuellt' har uppdaterats.", +"master_ok" => "Setupfilen har uppdaterats.", + +"pic_choose_old" => "Välj en gammal bild", +"pic_choose_old_teaser" => "Välj en gammal teaserbild", +"pic_upload_header" => "Ladda upp en bild", +"pic_upload_teaser" => "Ladda upp en teaserbild", +"pic_error" => "Det har uppstÃ¥tt ett fel, kontakta serveradministratören.", +"pic_uploaded" => "Bilden har laddats upp.", +"pic_insert" => "Infoga bilden", +"pic_instructions" => "Endast uppladdning av PNG-, GIF- eller JPEG-bilder. Bilden fÃ¥r inte vara större än 300 kB.", +"pic_upload" => "Ladda upp", +"pic_class" => "CSS klass (vid behov)", +"pic_alt" => "Alternativtext", + +"pic_height_widht" => "Bilden är för bred och för hög.", +"pic_width" => "Bilden är för bred.", +"pic_height" => "Bilden är för hög.", +"pic_instr_teaser" => "Endast uppladdning av PNG-, GIF- eller JPEG-bilder som inte är bredare än 150px och inte större än 60 kB.", +"pic_bad_type" => "Fel bildformat", +"pic_to_big" => "Bilden är för stor.", + +"kill_c_topic" => "Administrera kommentarer", +"kill_c_killed" => "Kommentaren raderades.", +"kill_c_sure" => "Är du säker att du vill radera kommentaren?", +"kill_c_h2" => "Radera", +"kill_c_description" => "Varning! När en kommentar en gÃ¥ng har tagits bort frÃ¥n denna lista, är den oÃ¥terkalleligen raderad.", +"kill_c_entry" => "Webblogg inlägg", +"kill_c_email" => "Radera kommentaren", +"comments_change_h" => "Editera kommentaren", +"comments_anonym" => "Anonym", +"comments_mail_txt" => "Ny kommentar pÃ¥ ".JLOG_WEBSITE."\nRubriken var:", +"comments_posted" => "skriven", +"comments_mailsubject" => "Kommentar pÃ¥ ".JLOG_WEBSITE, + +"comments_comment_topic" => "Kommentarer", +"comments_by" => "Kommentar frÃ¥n", +"comments_name" => "Namn", +"comments_city" => "Stad / Land", +"comments_email" => "e-post", +"comments_homepage" => "http://", +"comments_bbcode" => "Hur använder jag", +"comments_send" => "Skicka", +"comments_preview" => "Förhandsgranskning", +"comments_no_sid" => "Det verkar ha skett en manipulation", +"comments_false_mail" => "E-postadressen ser inte korrekt ut", +"comments_notext" => "Ingen text har skrivits", +"comments_false_hp" => "Kontrollera att rätt URL har angivits", +"comments_anonym" => "Anonym", +"comments_permalink" => "Permanent länk till denna kommentar", +"comments_from" => "frÃ¥n", +"comments_posted" => "skrev den", +"comments_entryform" => "Din kommentar", +"comments_mail_by_comment" => "Underrätta vid kommentar", +"comments_thx" => "Kommentaren blev uppdaterat.", +"comments_preview" => "Förhandsgranskning", +"comments_bold" => "fet", +"comments_italic" => "kursiv", +"comments_quote" => "citera", +"comments_url" => "länk", +"comments_updated" => "Kommentaren har uppdaterats. GÃ¥ tillbaks till", +"comments_admin" => "Kommentar-administationscenter", +"comments_plz_format_txt" => "Vänligen ange texten som ska formateras", +"comments_url_href" => "Ange länkmÃ¥l:", +"comments_url_node" => "Ange länktext:", +"comments_closed" => "Kommentarerna är stängda för detta inlägg.", + +"m_title" => "Huvudinställningar", +"m_clean_url" => "Ska rena URLer (mod_rewrite) användas? Exempel: http://example.com/2005/01/firefox", +"m_metadata" => "Metadata", +"m_language" => "Din webbloggs sprÃ¥k", +"m_website" => "Webbloggs namn", +"m_publisher" => "Författarens namn", +"m_admin_password" => "Administrationcenter lösenord", +"m_admin_password_again" => "Bekräfta lösenordet", +"m_admin_password_admin" => "(lämna blank för att inte ändra)", +"m_email" => "Författarens e-postadress", +"m_description" => "En kort introduktion om bloggen", +"m_bs" => "Notifera webblogg-services om nya inlägg sÃ¥ de kan lägga till den i sin sökmotor (en service per linje)", +"m_bs_weblogs_com" => "weblogs.com", +"m_bs_technorati_com" => "technorati.com", +"m_bs_blogg_de" => "blogg.de", +"m_behavior" => "Webbloggbeteende", +"m_max_blog_orginal" => "Hur mÃ¥nga inlägg ska visas komplett pÃ¥ startsidan?", +"m_max_blog_big" => "Hur mÃ¥nga inlägg ska visas som ingress pÃ¥ startsidan?", +"m_max_blog_small" => "Hur mÃ¥nga inlägg ska visas som en lista med rubrik och datum pÃ¥ startsidan?", +"m_sub_current" => "Hur mÃ¥nga inlägg ska visas i subnavigationen?", +"m_info_by_comment" => "E-post till författaren att en ny kommentar har inkommit", +"m_database" => "Databas", +"m_db" => "Databasens namn", +"m_db_url" => "Databasens hostnamn, oftast localhost", +"m_db_user" => "Databasens användarnamn", +"m_db_pwd" => "Databasens lösenord", +"m_db_prefix" => "Kort identifikation som prefix pÃ¥ tabellnamn i databasen", +"m_date" => "Datumformat (en formatsträng som i PHP-funktionen strftime())", +"m_date_posting" => "för inlägg", +"m_date_comment" => "för kommentarer", +"m_date_subcurrent" => "för subnavigationen", +"m_settings_ok" => "Dina inställningar har sparats.", + +"e_path" => "URLen verkar fel.", +"e_basepath" => "Katalogen existerar inte.", +"e_website" => "Skriv in bloggens namn.", +"e_publisher" => "Skriv in författarens namn.", +"e_admin_password" => "Skriv in lösenordet till administrationscentret.", +"e_admin_password_again" => "Skriv in lösenordet en gÃ¥ng till för att verifiera den.", +"e_email" => "E-postadressen verkar fel.", +"e_description" => "Skriv in en kort beskrivning om bloggen.", +"e_max_blog_orginal" => "Antal av inlägg som ska visas komplett pÃ¥ startsidan mÃ¥sta vara noll eller mer.", +"e_max_blog_big" => "Antal av inlägg som ska visas som ingress pÃ¥ startsidan mÃ¥sta vara noll eller mer.", +"e_max_blog_small" => "Antal av inlägg som ska visas som en lista med rubrik och datum pÃ¥ startsidan mÃ¥sta vara noll eller mer.", +"e_sub_current" => "Antal av inlägg som ska visas som en lista med rubrik och datum i subnavigationen mÃ¥sta vara noll eller mer.", +"e_start_year" => "Gömda fälten för Ã¥ret är tom.", +"e_db" => "Skriv in databasens namn.", +"e_db_url" => "Skriv in databasens hostnamn.", +"e_db_user" => "Skriv in databasens användernamn.", +"e_db_occurred" => "Databas fel", +"e_db_is" => "Ett fel har uppstÃ¥tt pÃ¥ ".JLOG_PATH.". Det är:", + +"s_phpv_tolow" => "Din PHP-version är för gammal, vänligen uppgradera till en nyare eller be din serveradministratör att göra det.", +"s_mysqlv_tolow" => "Din MYSQL-version är för gammal, vänligen uppgradera till en nyare eller be din serveradministratör att göra det.", +"s_personal_not_wrtbl" => "Det gÃ¥r inte att skriva i katalogen 'personal'. (Chmod 777)", +"s_img_not_wrtbl" => "Det gÃ¥r inte att skriva i katalogen 'img'. (Chmod 777)", +"s_tables_ok" => "Tabellerna i databasen har skapats.", +"s_ready_head" => "Bloggen har installerats.", +"s_ready" => "Grattis! Nu kan du börja skriva i administrationscenter", +"s_ready_menu_admin" => "Till administrationscenter", +"s_ready_menu_home" => "Till startsidan", +"s_problem_fwrite" => "Ett problem uppstod medan nödvändiga filer skapades.", +"s_problem_chmod" => "Ett problem uppstod medan rättigheterna till de nödvändiga filerna ändrades.", +"s_personal_ok" => "Filer i katalogen 'personal' skapades.", +"s_install" => "Installera nu!", + +"login_headline" => "Administrationscenter", +"login_password" => "Skriv in ditt lösenord:", +"login_send" => "Logga in", +"login_cookies" => "Notera: Du mÃ¥ste ha cookies pÃ¥ i din webbläsare!", +"login_false_pw" => "Fel lösenord.", + +"cat_name" => "Kategoriens namn", +"cat_url" => "URL i kategoriarkivet (bara a-z 0-9 _-,. )", +"cat_description" => "Kategoribeskrivning som visas i arkivet", +"cat_new" => "Skapa ny kategori", +"cat_title" => "Kategorimanagement", +"cat_noname" => "Kategorien mÃ¥ste ha ett namn.", +"cat_change" => "Ändra kategoriens data", +"cat_new_ok" => "Ny kategori har skapats.", +"cat_really_trash" => "Är du säker att du vill radera kategorien?", +"cat_trash_ok" => "Kategorien blev raderat. Tillbacks till", +"cat_admincenter" => "Kategori administrationscenter", +"cat_duplicate" => "En annan kategori använder redan samma URL.", + +"update_successfull" => "Uppdateringen lyckades. Ha sÃ¥ kul!", +"pingback_closed" => "Avaktivera pingbacks för detta inlägg.", + +"plugin_no_content" => "Man behöver inte administrera pluginet.", +"plugins_h_not_avaliable" => "Inga plugins hittades", +"plugins_not_avaliable" => "Jag kunde inte hitta nÃ¥got plugin.", +"plugins_headline" => "Plugin administration", + +// Do not change the folowing line! +); + +// eof \ No newline at end of file diff --git a/lang/lang.de.inc.php b/lang/lang.de.inc.php new file mode 100644 index 0000000..b614caa --- /dev/null +++ b/lang/lang.de.inc.php @@ -0,0 +1,121 @@ + "Herzlich Willkommen", +"subnav_current" => "Aktuelle Einträge", +"subnav_info" => "Informationen", +"subnav_rss" => "Aktuelles von dieser Seite per RSS Feed. Mehr darüber erfahren Sie auf der Seite von Alp Uçkan.", +"subnav_copyright" => "Alle Rechte vorbehalten.", +"subnav_powered" => "Powered by", + +"content_posted" => "geschrieben am", +"content_more" => "weiterlesen", +"content_more_title" => "Ganzen Eintrag lesen", +"content_permalink" => "permanenter Link zu diesem Eintrag", +"content_posted" => "Eingestellt am", +"content_archive" => "Ältere Weblogeinträge gibt es im", +"content_archivelink" => "Archiv", +"content_archive_header" => "Archivierte Einträge", +"content_categories_header"=> "Kategorie", +"content_skip" => "Zum Hauptinhalt springen.", +"content_choose_year" => "Das Jahr wählen:", +"content_search_header" => "Suche auf der Webseite", +"content_search" => "suchen", +"content_nothing_found" => "Es wurden 0 Ergebnisse gefunden. Vorschläge:
    • Überprüfen Sie die Schreibweise.
    • Suchen Sie mit anderen bzw. weniger Schlüsselwörtern.
    • Entfernen Sie Frage- oder Pluszeichen.
    ", +"content_search_topic" => "Weblog durchsuchen", +"content_from" => "von", +"content_comments" => "Kommentare", +"content_comment_plz" => "kommentieren", +"content_comments_title" => "zu Kommentaren springen", +"content_cat_linklist" => "zugeordnete Kategorien", +"content_cat_link" => "Alle Einträge dieser Kategorie anzeigen", +"content_categorieslist_h" => "Kategorien", +"content_archive_preview" => "Vorherige Seite", +"content_archive_next" => "Nächste Seite", + +"meta_start" => "Zurück zur Startseite", +"meta_search" => "Suche", +"meta_copyright" => "Urheberrecht", + +"comments_comment_topic" => "Kommentare", +"comments_by" => "Kommentar von", +"comments_name" => "Name", +"comments_city" => "Stadt / Land", +"comments_email" => "E-Mail", +"comments_homepage" => "http://", +"comments_bbcode" => "Wie benutze ich", +"comments_send" => "Absenden", +"comments_preview" => "Vorschau", +"comments_no_sid" => "Es scheint eine Manipulation vorzuliegen", +"comments_false_mail" => "Die E-Mail Adresse sieht nicht richtig aus", +"comments_notext" => "Es wurde kein Text eingegeben", +"comments_false_hp" => "Die URL zur Homepage scheint falsch zu sein", +"comments_anonym" => "Anonym", +"comments_permalink" => "Permanenter link zu diesem Kommentar", +"comments_from" => "aus", +"comments_posted" => "schrieb am", +"comments_entryform" => "Dein Kommentar", +"comments_save_data" => "Userdaten in einem Cookie sichern", +"comments_mail_by_comment" => "Bei Kommentar benachrichtigen", +"comments_duplicate" => "Aus versehen wurde das Formular zwei mal abgesandt", +"comments_thx" => "Danke - Der Kommentar wurde gespeichert", +"comments_mailsubject" => "Kommentar auf ".JLOG_WEBSITE, +"comments_mail_txt" => "Neuer Kommentar auf ".JLOG_WEBSITE."\nDer Titel war: ", +"comments_stop_receiving" => "Um die Benachrichtigung bei neuen Kommentaren abzustellen klicken Sie hier:", +"comments_stop_successful" => "Die Benachrichtigung wurde abgestellt.", +"comments_preview" => "Vorschau", +"comments_send" => "Senden", +"comments_show" => "Kommentare anzeigen", +"comments_hide" => "Kommentare verstecken", +"comments_bold" => "fett", +"comments_italic" => "kursiv", +"comments_quote" => "Zitat", +"comments_url" => "Link", +"comments_plz_format_txt" => "Bitte gebe den zu formatierenden Text ein:", +"comments_url_href" => "Linkziel eingeben:", +"comments_url_node" => "Linktext eingeben:", +"comments_closed" => "Die Kommentare sind für diesen Eintrag geschlossen.", +"comments_teaser_closed" => "(Kommentare geschlossen)", +"pingback_topic" => "Pingbacks", + +"db_error" => "Datenbankfehler", +"plz_try_again" => "Bitte versuchen Sie es später noch einmal.", + +"error" => "Fehler", +"err404_topic" => "Fehler 404 - Seite nicht gefunden", +"err404_message" => "Diese Seite existiert leider nicht. Versuchen Sie sie über die Suchfunktion zu finden.", + +"language" => "de-de", +"locale" => array('de_DE.UTF-8', 'de_DE.UTF-8@euro', 'de_DE'), +"date_format" => "%d. %B %Y um %H:%M Uhr", +"date_format_comment" => "%d.%m.%Y", +"date_format_subcurrent" => "%d.%m.%Y", + +"index_topic" => "Startseite", +"bbtitle" => "BBcode nutzen", +"bbxmp" => "
    • Zeilenumbrüche werden automatisch erzeugt und man kann die Codeschnipsel auch kombinieren.
    • +
    • [url]http://example.com[/url]
    • +
    • [url=http://example.com]Beispiellink[/url]
    • +
    • [b]fett[/b]
    • +
    • [i]kursiv[/i]
    • +
    • [quote]Ein zitierter Text welcher aus einer anderen Quelle stammt. Es empfiehlt sich die Quelle auch mit anzugeben.[/quote]

    ", + +// do not change the following line +"months" => array ( +// here you can change the months for the archive +1 => "Januar", +2 => "Februar", +3 => "März", +4 => "April", +5 => "Mai", +6 => "Juni", +7 => "Juli", +8 => "August", +9 => "September", +10 => "Oktober", +11 => "November", +12 => "Dezember" + +// do not change the folowing lines + ) +); ?> diff --git a/lang/lang.en.inc.php b/lang/lang.en.inc.php new file mode 100644 index 0000000..49ce8d6 --- /dev/null +++ b/lang/lang.en.inc.php @@ -0,0 +1,122 @@ + "Welcome", +"subnav_current" => "Recent weblog entries", +"subnav_info" => "Information", +"subnav_rss" => "Recent weblogentries as a RSS feed. Read more about RSS on mezzoblue.com.", +"subnav_copyright" => "All rights reserved.", +"subnav_powered" => "Powered by", + +"content_posted" => "posted on", +"content_more" => "read more", +"content_more_title" => "read the whole entry", +"content_permalink" => "permanent link for this article", +"content_posted" => "Posted on", +"content_archive" => "You can find older weblog entries in the", +"content_archivelink" => "archive", +"content_archive_header" => "Archive", +"content_categories_header"=> "Category", +"content_skip" => "skip to maincontent", +"content_choose_year" => "Choose the year:", +"content_search_header" => "Search the weblog", +"content_search" => "search", +"content_nothing_found" => "We found 0 results. Suggestions:
    • Check your spelling.
    • Try different or fewer keywords.
    • Remove quotation marks or plus signs.
    ", +"content_search_topic" => "Search this weblog", +"content_from" => "from", +"content_comments" => "Comments", +"content_comment_plz" => "comment", +"content_comments_title" => "skip to comments", +"content_cat_linklist" => "assigned categories", +"content_cat_link" => "Show all entries to this category", +"content_categorieslist_h" => "Categories", +"content_archive_preview" => "previous page", +"content_archive_next" => "next page", + +"meta_start" => "back to homepage", +"meta_search" => "Search", +"meta_copyright" => "Copyright", + +"comments_comment_topic" => "Comments", +"comments_by" => "Comment by", +"comments_name" => "name", +"comments_city" => "city / country", +"comments_email" => "email", +"comments_homepage" => "http://", +"comments_bbcode" => "How to use", +"comments_send" => "send", +"comments_preview" => "preview", +"comments_no_sid" => "There must be some manipulation", +"comments_false_mail" => "email address looks wrong", +"comments_notext" => "you have to write some text", +"comments_false_hp" => "Homepage URL looks wrong", +"comments_anonym" => "Anonymous", +"comments_permalink" => "permalink to this comment", +"comments_from" => "from", +"comments_posted" => "wrote on", +"comments_entryform" => "Your comment", +"comments_save_data" => "save userdata in a cookie", +"comments_mail_by_comment" => "mail me in case of a new comment", +"comments_duplicate" => "form was send twice by mistake", +"comments_thx" => "Thanks - Your comment was saved", +"comments_mailsubject" => "New comment on ".JLOG_WEBSITE, +"comments_mail_txt" => "Someone just responded to the entry you subscribed to at: ".JLOG_WEBSITE."\nThe title of the entry was: ", +"comments_stop_receiving" => "To stop receiving notifications for this comment, click here:", +"comments_stop_successful" => "Stopping receiving notifications was successful.", +"comments_preview" => "preview", +"comments_send" => "send", +"comments_show" => "show comments", +"comments_hide" => "hide comments", +"comments_bold" => "bold", +"comments_italic" => "italic", +"comments_quote" => "quote", +"comments_url" => "link", +"comments_plz_format_txt" => "Please enter your Text:", +"comments_url_href" => "enter linktarget:", +"comments_url_node" => "enter linktext:", +"comments_closed" => "Comments are closed for this entry.", +"comments_teaser_closed" => "(Comments closed)", +"pingback_topic" => "Pingbacks", + +"db_error" => "Database error", +"plz_try_again" => "Please try again later.", + +"error" => "Error", +"err404_topic" => "error 404", +"err404_message" => "There is no such page. Please try the search engine on this page.", + +"language" => "en-gb", +"locale" => array( "en_US", "us", "verUS" ), +"date_format" => "%d. %B %Y um %H:%M Uhr", +"date_format_comment" => "%d.%m.%Y", +"date_format_subcurrent" => "%d.%m.%Y", + +"index_topic" => "Homepage and News", +"bbtitle" => "Using BBcode", +"bbxmp" => "

    Linebreakes are automaticly transformed. Notice that you can combine this code snippets.

    +

    [url]http://example.com[/url]

    +

    [url=http://example.com]example link[/url]

    +

    [b]bold[/b]

    +

    [i]italic[/i]

    +

    [quote]A quoted text from an other source. Pleace add the + source as a link.[/quote]

    ", + +// do not change the following line +"months" => array ( +// here you can change the months for the archive +1 => "January", +2 => "February", +3 => "March", +4 => "April", +5 => "May", +6 => "June", +7 => "July", +8 => "August", +9 => "September", +10 => "October", +11 => "November", +12 => "December" + +// do not change the folowing lines + ) +); ?> diff --git a/lang/lang.it.inc.php b/lang/lang.it.inc.php new file mode 100644 index 0000000..692aea7 --- /dev/null +++ b/lang/lang.it.inc.php @@ -0,0 +1,121 @@ + "Benvenuti", +"subnav_current" => "Recenti note nel weblog ", +"subnav_info" => "Informazioni", +"subnav_rss" => "Recenti note nel weblog as a RSS feed. Leggi di più riguardo RSS in mezzoblue.com.", +"subnav_copyright" => "Tutti i diritti sono riservati.", +"subnav_powered" => "Powered by", + +"content_posted" => "Pubblicato il", +"content_more" => "Leggi di più", +"content_more_title" => "Leggi l'intera nota", +"content_permalink" => "Link permanente per questo aricolo", +"content_posted" => "Pubblicato il", +"content_archive" => "Puoi trovare vecchie note weblog in ", +"content_archivelink" => "Archivio", +"content_archive_header" => "Archivio", +"content_categories_header"=> "Categoria", +"content_skip" => "vai ai contenuti principali", +"content_choose_year" => "Sciegli l'anno:", +"content_search_header" => "Cerca il weblog", +"content_search" => "Cerca", +"content_nothing_found" => "Sono stati trovato 0 risultati.Suggerimento:
    • Controlla l'ortografia.
    • Prova con una differente parola chiave.
    • Cancellare virgolette o segno più.
    ", +"content_search_topic" => "Cerca questo weblog", +"content_from" => "da", +"content_comments" => "Commenti", +"content_comment_plz" => "Commenti", +"content_comments_title" => "vai ai commenti", +"content_cat_linklist" => "Categorie assegnate", +"content_cat_link" => "Mostra tutte le note di questa categoria", +"content_categorieslist_h" => "Categorie", +"content_archive_preview" => "Pagina precedente", +"content_archive_next" => "Prossima pagina", + +"meta_start" => "Vai alla homepage", +"meta_search" => "Cerca", +"meta_copyright" => "Copyright", + +"comments_comment_topic" => "Commenti", +"comments_by" => "Commento di", +"comments_name" => "Nome", +"comments_city" => "Città/ Paese", +"comments_email" => "e-mail", +"comments_homepage" => "http://", +"comments_bbcode" => "Come si usa", +"comments_send" => "Invia", +"comments_preview" => "Anteprima", +"comments_no_sid" => "Stai manipolando qualcosa!", +"comments_false_mail" => "L'indirizzo e-mail non è corretto", +"comments_notext" => "Devi scrivere qualcosa", +"comments_false_hp" => "Homepage URL non corretta", +"comments_anonym" => "Anonimo", +"comments_permalink" => "permalink per questo commento", +"comments_from" => "da", +"comments_posted" => "Scritto il", +"comments_entryform" => "Tuo commento", +"comments_save_data" => "Salva userdata in cookie", +"comments_mail_by_comment" => "Inviami una e-mail in caso di nuovi commenti", +"comments_duplicate" => "Nota spedita due volte", +"comments_thx" => "Grazie - Il tuo commento è stato salvato", +"comments_mailsubject" => "Nuovo commento in ".JLOG_WEBSITE, +"comments_mail_txt" => "Qualcuno ha risposto alla tua nota: ".JLOG_WEBSITE."\nIl titolo della nota era: ", +"comments_stop_receiving" => "Per non ricevere piu notifiche riguardo questo commento, clicca qui:", +"comments_stop_successful" => "Notifice annullate con successo.", +"comments_preview" => "Anteprima", +"comments_send" => "Invia", +"comments_show" => "Visualizza commenti", +"comments_hide" => "Nascondi commenti", +"comments_bold" => "Grassetto", +"comments_italic" => "Corsivo", +"comments_quote" => "Cita espressione", +"comments_url" => "link", +"comments_plz_format_txt" => "Perfavore inserire il testo:", +"comments_url_href" => "Inserire linktarget:", +"comments_url_node" => "Inserire linktext:", +"comments_closed" => "I commenti sono chiusi per questa nota.", +"comments_teaser_closed" => "(Commenti stop)", +"pingback_topic" => "Pingbacks", + +"db_error" => "Errore database", +"plz_try_again" => "Riprovare più tardi, grazie.", + +"error" => "Errore", +"err404_topic" => "Errore 404", +"err404_message" => "Non ci sono file riguardanti la ricerca in questa pagina. Perfavore prova a usare il motore di ricerca di questa pagina.", + +"language" => "it-it", +"locale" => array( "it_IT", "it" ), +"date_format" => "%d. %B %Y alle %H:%M", +"date_format_comment" => "%d.%m.%Y", +"date_format_subcurrent" => "%d.%m.%Y", + +"index_topic" => "Homepage e News", +"bbtitle" => "Usare BBcode", +"bbxmp" => "

    Linebreakes sono trasformate automaticamente. Nota che puoi combinare i pezzi del codice.

    +

    [url]http://example.com[/url]

    +

    [url=http://example.com]example link[/url]

    +

    [b]Grassetto[/b]

    +

    [i]Corsivo[/i]

    +

    [quote]La citazione providene da un altra sorgente. Perfavore aggiungi la sorgente .[/quote]

    ", + +// do not change the following line +"months" => array ( +// here you can change the months for the archive +1 => "Gennaio", +2 => "Febbraio", +3 => "Marzo", +4 => "Aprile", +5 => "Maggio", +6 => "Giugno", +7 => "Luglio", +8 => "Agosto", +9 => "Settembre", +10 => "Ottobre", +11 => "Novembre", +12 => "Dicembre" + +// do not change the folowing lines + ) +); ?> diff --git a/lang/lang.pl.inc.php b/lang/lang.pl.inc.php new file mode 100644 index 0000000..94f5ef6 --- /dev/null +++ b/lang/lang.pl.inc.php @@ -0,0 +1,122 @@ + "Witamy", +"subnav_current" => "Ostatnie wartki", +"subnav_info" => "Informacja", +"subnav_rss" => "Ostatnie wartki jako RSS. Przeczytaj wiecej o RSS na mezzoblue.com.", +"subnav_copyright" => "Wszystkie prawa zastrzezone.", +"subnav_powered" => "Powered by", + +"content_more" => "przeczytaj więcej", +"content_more_title" => "przeczytaj cały wartek", +"content_permalink" => "permanentny link dla tego wartku", +"content_posted" => "Pisany", +"content_archive" => "Starsze wartki znajdżesz w", +"content_archivelink" => "archiwum", +"content_archive_header" => "Archiwum", +"content_categories_header"=> "Kategoria", +"content_skip" => "przejdz do tekstu", +"content_choose_year" => "Wybierz rok:", +"content_search_header" => "Przeszukaj weblog", +"content_search" => "szukaj", +"content_nothing_found" => "Znaleziono 0 wyników. Sugestie:
    • Sprawdz czy poprawnie wpisaÅ‚es wyszukiwanÄ… frazÄ™.
    • Wprowadz inne lub mniej słów.
    • UsuÅ„ cudzysłów lub znak plus.
    ", +"content_search_topic" => "Przeszukaj ten weblog", +"content_from" => "od", +"content_comments" => "Komentarze", +"content_comment_plz" => "komentarz", +"content_comments_title" => "przejdź do komentarzy", +"content_cat_linklist" => "przyznaczone kategorie", +"content_cat_link" => "Pokaż wszystkie wartki tej kategori", +"content_categorieslist_h" => "Kategorie", +"content_archive_preview" => "poprzednia strona", +"content_archive_next" => "następna strona", + +"meta_start" => "powrót do strony glównej", +"meta_search" => "Szukaj", +"meta_copyright" => "Prawa autorskie", + +"comments_comment_topic" => "Komentarze", +"comments_by" => "Komentowane przez", +"comments_name" => "imię", +"comments_city" => "miejscowość / kraj", +"comments_email" => "emaila", +"comments_homepage" => "http://", +"comments_bbcode" => "Jak używać", +"comments_send" => "wyślij", +"comments_preview" => "podgląd", +"comments_no_sid" => "Coś jest nie tak, wygląda na manipulacje", +"comments_false_mail" => "adres emaila jest niepoprawny", +"comments_notext" => "trzeba napisac jakiś tekst", +"comments_false_hp" => "URL strony glównej jest niepoprawny", +"comments_anonym" => "Anonim", +"comments_permalink" => "link permanentny do tego komentarza", +"comments_from" => "od", +"comments_posted" => "pisany", +"comments_entryform" => "Twój komentarz", +"comments_save_data" => "zapisz dane uzytkownika w cookie", +"comments_mail_by_comment" => "zawiadom mnie gdy pojawi się nowy komentarz", +"comments_duplicate" => "formularz został wysłany przez pomyłkę", +"comments_thx" => "Dziekujemy - Twój komentarz został zachowany", +"comments_mailsubject" => "Nowy komentarz na ".JLOG_WEBSITE, +"comments_mail_txt" => "Ktoś napisał komentarz na: ".JLOG_WEBSITE."\n Tytół wartku był: ", +"comments_stop_receiving" => "Aby przestać otrzymywać notyfikacje kliknij tutaj:", +"comments_stop_successful" => "Notyfikacje zostaly zatżymane.", +"comments_preview" => "podglad", +"comments_send" => "wyślij", +"comments_show" => "pokaż komentarze", +"comments_hide" => "ukryj komentarze", +"comments_bold" => "bold", # TODO +"comments_italic" => "italic", # TODO +"comments_quote" => "quote", # TODO +"comments_url" => "link", +"comments_plz_format_txt" => "Prosze wprowadzić swój tekst:", +"comments_url_href" => "wprowadź url:", +"comments_url_node" => "wprowadź text:", +"comments_closed" => "Na tym wartku komentarze zostały zamknięte.", +"comments_teaser_closed" => "(Zamknięte komentarze)", +"pingback_topic" => "Pingbaki", + +"db_error" => "Błąd bazy danych", +"plz_try_again" => "Prosze ponownie spróbować później.", + +"error" => "Błąd", +"err404_topic" => "błąd 404", +"err404_message" => "Nie ma takiej strony. Prosze użyć przeglądarki na tej stronie.", + +"language" => "en-gb", +"locale" => array( "en_US", "us", "verUS" ), +"date_format" => "%d. %B %Y um %H:%M Uhr", +"date_format_comment" => "%d.%m.%Y", +"date_format_subcurrent" => "%d.%m.%Y", + +"index_topic" => "Strona glówna", +"bbtitle" => "Urzywanie BBcode", +"bbxmp" => "

    Linebreakes are automaticly transformed. Notice that you can combine this code snippets.

    +

    [url]http://example.com[/url]

    +

    [url=http://example.com]example link[/url]

    +

    [b]bold[/b]

    +

    [i]italic[/i]

    +

    [quote]A quoted text from an other source. Pleace add the + source as a link.[/quote]

    ", + +// do not change the following line +"months" => array ( +// tutaj mozna zmienic miesiace for the archive +1 => "Styczen", +2 => "Luty", +3 => "Marzec", +4 => "Kwiecien", +5 => "Maj", +6 => "Czerwiec", +7 => "Lipiec", +8 => "Śierpień", +9 => "Wrzesień", +10 => "Październik", +11 => "Listopad", +12 => "Grudzień" + +// do not change the folowing lines + ) +); +// eof \ No newline at end of file diff --git a/lang/lang.sv.inc.php b/lang/lang.sv.inc.php new file mode 100644 index 0000000..2213030 --- /dev/null +++ b/lang/lang.sv.inc.php @@ -0,0 +1,121 @@ + "Välkommen", +"subnav_current" => "Aktuella inlägg", +"subnav_info" => "Information", +"subnav_rss" => "Aktuellt från denna sida via RSS Feed. Mer info om detta hittar du på http://susning.nu/RSS.", +"subnav_copyright" => "Alla rättigheter förbehållna", +"subnav_powered" => "Powered by", + +"content_posted" => "skrivet den", +"content_more" => "läs mer", +"content_more_title" => "Läs hela webbloginlägget", +"content_permalink" => "permanent länk till detta webbloginlägg", +"content_posted" => "Inlagt den", +"content_archive" => "Äldre webbloginlägg finns i", +"content_archivelink" => "Arkiv", +"content_archive_header" => "Arkiverade inlägg", +"content_categories_header"=> "Kategori", +"content_skip" => "Hoppa till huvudinnehåll.", +"content_choose_year" => "Välj år:", +"content_search_header" => "Sök på webbsidan", +"content_search" => "sök", +"content_nothing_found" => "Antal träffar: 0. Förslag: :
    • Kontrollera stavningen.
    • Sök med andra eller färre nyckelord.
    • Radera frÃ¥ge- eller plustecken.
    ", +"content_search_topic" => "Sök igenom webblog", +"content_from" => "från", +"content_comments" => "Kommentarer", +"content_comment_plz" => "kommentera", +"content_comments_title" => "hoppa till kommentarer", +"content_cat_linklist" => "tilldelade kategorier", +"content_cat_link" => "Visa alla inlägg ur denna kategori", +"content_categorieslist_h" => "Kategorier", +"content_archive_preview" => "Föregående sida", +"content_archive_next" => "Nästa sida", + +"meta_start" => "Tillbaka till startsidan", +"meta_search" => "Genomsöker", +"meta_copyright" => "Upphovsrätt", + +"comments_comment_topic" => "Kommentarer", +"comments_by" => "Kommentar från", +"comments_name" => "Namn", +"comments_city" => "Stad / Land", +"comments_email" => "E-mail", +"comments_homepage" => "http://", +"comments_bbcode" => "Hur använder jag", +"comments_send" => "Skicka", +"comments_preview" => "Förhandsgranskning", +"comments_no_sid" => "Det verkar ha skett en manipulation", +"comments_false_mail" => "E-mailadressen ser inte korrekt ut", +"comments_notext" => "Ingen text har skrivits", +"comments_false_hp" => "Kontrollera att rätt URL har angivits", +"comments_anonym" => "Anonym", +"comments_permalink" => "Permanent länk till denna kommentar", +"comments_from" => "från", +"comments_posted" => "skrev den", +"comments_entryform" => "Din kommentar", +"comments_save_data" => "Spara användarinställningar", +"comments_mail_by_comment" => "Underrätta vid kommentar", +"comments_duplicate" => "Formuläret skickades av misstag två gånger", +"comments_thx" => "Tack - Kommentaren har sparats", +"comments_mailsubject" => "Kommentar på ".JLOG_WEBSITE, +"comments_mail_txt" => "Ny kommentar på ".JLOG_WEBSITE."\nTiteln var: ", +"comments_stop_receiving" => "För att avaktivera underrättelsen vid nya kommentarer, klicka här:", +"comments_stop_successful" => "Underrättelsen har avaktiverats", +"comments_preview" => "Förhandsgranskning", +"comments_send" => "Skicka", +"comments_show" => "visa kommentarer", +"comments_hide" => "dölj kommentarer", +"comments_bold" => "fet", +"comments_italic" => "kursiv", +"comments_quote" => "citera", +"comments_url" => "länk", +"comments_plz_format_txt" => "Vänligen ange texten som ska formateras", +"comments_url_href" => "Ange länkmål:", +"comments_url_node" => "Ange länktext:", +"comments_closed" => "Kommentarerna är stängda för detta inlägg.", +"comments_teaser_closed" => "(Kommentarer stängda)", +"pingback_topic" => "Pingbacks", + +"db_error" => "Databasfel", +"plz_try_again" => "Var god försök igen senare.", + +"error" => "Error", +"err404_topic" => "Error 404 - Sidan hittades inte", +"err404_message" => "Denna sida existerar tyvärr inte. Försök hitta den genom sökfunktionen.", + +"language" => "sv-se", +"locale" => array('sv_SE', 'sve_sve'), +"date_format" => "%Y-%B-%d kl %H:%M", +"date_format_comment" => "%Y-%m-%d", +"date_format_subcurrent" => "%Y-%m-%d", + +"index_topic" => "Startsida", +"bbtitle" => "Använd BBcode", +"bbxmp" => "
    • Radbrytning sker automatiskt och man kan även kombinera kodstyckena.
    • +
    • [url]http://example.com[/url]
    • +
    • [url=http://example.com]Exempellänk[/url]
    • +
    • [b]fet[/b]
    • +
    • [i]kursiv[/i]
    • +
    • [quote]Ett citat ur en annan källtext. Det rekommenderas att även ange denna.[/quote]

    ", + +// do not change the following line +"months" => array ( +// here you can change the months for the archive +1 => "januari", +2 => "februari", +3 => "mars", +4 => "april", +5 => "maj", +6 => "juni", +7 => "juli", +8 => "august", +9 => "september", +10 => "oktober", +11 => "november", +12 => "december" + +// do not change the folowing lines + ) +); ?> diff --git a/learn_bb.php b/learn_bb.php new file mode 100644 index 0000000..c9abcde --- /dev/null +++ b/learn_bb.php @@ -0,0 +1,27 @@ + + + ".$l['bbtitle']." + + + +

    ".$l['bbtitle']."

    + ".$l['bbxmp']." + + "; +} + +else { + $c['title'] = $l['bbtitle']; + $c['main'] = $l['bbxmp']; + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; + +} +?> diff --git a/log.php b/log.php new file mode 100644 index 0000000..b0b48f5 --- /dev/null +++ b/log.php @@ -0,0 +1,308 @@ +error()) { + echo "
    \n";
    +        echo $blog->getError();
    +        echo "
    \n"; + die(); + } + + if($blog->numRows() == 0) { + header($_SERVER["SERVER_PROTOCOL"]." 404 Not Found"); + include_once(JLOG_BASEPATH."error404.php"); + exit; + } +} +else { + header($_SERVER["SERVER_PROTOCOL"]." 404 Not Found"); + include_once(JLOG_BASEPATH."error404.php"); + exit; +} + + +$blogentry = $blog->fetch(); + +// get comments from Database + +$sql_comments = "SELECT + id, sid, name, city, email, homepage, + content, UNIX_TIMESTAMP(date) AS date, + reference, mail_by_comment, type + FROM ".JLOG_DB_COMMENTS." + WHERE reference = '".$blogentry['id']."' + ORDER BY date;"; + +$c['meta']['date'] = $blogentry['metadate']; +$c['meta']['description'] = strip_tags($bbcode->parse($blogentry['teaser'])); +$c['meta']['keywords'] = $blogentry['keywords']; +$c['meta']['title'] = $blogentry['topic']; +$c['meta']['pingback'] = true; + +$c['main'] = do_entry($blogentry); + +// Form entry + +$com_form = strip($_POST); +if(!isset($com_form['type'])) $com_form['type'] = ""; +$error = com_check_errors($com_form); + +// Preview +if(isset($com_form['form_submitted']) AND $com_form['form_submitted'] === $l['comments_preview']) { + + $comments = new Query($sql_comments); + if($comments->error()) { + echo "
    \n";
    +        echo $comments->getError();
    +        echo "
    \n"; + die(); + } + + $commentsArray = array(); + $countComments = 0; + while($commentsArray[] = $comments->fetch()); + + foreach($commentsArray as $tmp_comment) if($tmp_comment['type'] != 'pingback') ++$countComments; + + $preview = ""; + if(isset($error)) $preview .= error_output($error); + $clear_form = com_clean_data($com_form); + $clear_form['id'] = ""; + + ### Plugin Hook + $clear_form = $plugins->callHook('previewComment', $clear_form, $blogentry); + + $preview .= "
      + ".do_comment($clear_form, $countComments)." +
    "; + + $c['form_content'] .= $preview; + $c['form_content'] .= com_form_output($com_form).com_javascript_variables(); +} + +// Send data to DB +elseif(isset($com_form['form_submitted']) AND $com_form['form_submitted'] == $l['comments_send'] AND $blogentry['comments'] == 1) { + + if(isset($error)) { + + $c['form_content'] .= error_output($error); + $c['form_content'] .= com_form_output($com_form).com_javascript_variables(); + } + else { + // Send comment + + $com_form = com_clean_data($com_form); + + ### Plugin Hook + $com_form = $plugins->callHook('newComment', $com_form, $blogentry); + + $com = escape_for_mysql($com_form); + if(!isset($com['mail_by_comment'])) $com['mail_by_comment'] = ""; + + $sql = "INSERT INTO ".JLOG_DB_COMMENTS." ( + sid, + name, + city, + email, + homepage, + content, + reference, + mail_by_comment, + date, + type + ) + VALUES ( + '".$com['sid']."', + '".$com['name']."', + '".$com['city']."', + '".$com['email']."', + '".$com['homepage']."', + '".$com['content']."', + '".$blogentry['id']."', + '".$com['mail_by_comment']."', + NOW(), + '".$com['type']."' + )"; + + $newcomment = new Query($sql); + $cid = mysql_insert_id(); + if($newcomment->error()) { + if($newcomment->getErrno() == 1062) { + $errors[] = $l['comments_duplicate']; + $c['form_content'] .= error_output($errors, 'entryform').com_javascript_variables(); + } + else { + echo "
    \n";
    +                 echo $newcomment->getError();
    +                 echo "
    \n"; + die(); + } + } + else { + if(isset($com_form['cookie']) AND $com_form['cookie'] == 1) set_cookie($com_form); + else trash_cookie(); + + include_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'update.php'); + + $sql = "SELECT DISTINCT email + FROM ".JLOG_DB_COMMENTS." WHERE reference = '".$blogentry['id']."' AND mail_by_comment = 1"; + $comment_mail = new Query($sql); + + // we are going to send some mail + require_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'mail.class.php'); + + if($comment_mail->error()) { + echo "
    \n";
    +                echo $comment_mail->getError();
    +                echo "
    \n"; + die(); + } + elseif( JLOG_INFO_BY_COMMENT ) { + // we need this for some mail texts + require(JLOG_BASEPATH.'lang'.DIRECTORY_SEPARATOR.'lang-admin.'.JLOG_LANGUAGE.'.inc.php'); + + $mail = new Jlog_Mail(); + $mail->setFrom($com_form['email'], $com_form['name']); + $mail->setSubject($l['admin']['comments_mailsubject']." - ".$blogentry['topic']); + + $text = $l['admin']['comments_mail_txt']." »".$blogentry['topic']."«\n- -\n"; + if(!empty($com_form['name'])) $text .= $com_form['name']; + else $text .= $l['admin']['comments_anonym']; + if(!empty($com_form['city'])) $text .= " ".$l['comments_from']." ".$com_form['city']; + $text .= " ".$l['admin']['comments_posted']." ".$date.":\n\n"; + $text .= html_entity_decode(strip_tags($bbcomments->parse($com_form['content']))); + $text .= "\n\n".str_replace ( '&', '&', blog($blogentry['date'], $blogentry['url']))."#c".$cid; + $text .= "\n\n".$l['admin']['kill_c_email']."\n".JLOG_PATH."/admin/comments.php?action=trash&id=".$cid; + $mail->setText($text); + + ### Plugin Hook + $mail = $plugins->callHook('adminMail', $mail, $blogentry, $cid); + $mail->send(JLOG_EMAIL); + } + + $mail = new Jlog_Mail(); + $mail->setSubject($l['comments_mailsubject']." - ".$blogentry['topic']); + $mail->setFrom(JLOG_EMAIL, JLOG_WEBSITE); + + $text = $l['comments_mail_txt']." »".$blogentry['topic']."«\n- -\n"; + if(!empty($com_form['name'])) $text .= $com_form['name']; + else $text .= $l['comments_anonym']; + if(!empty($com_form['city'])) $text .= " ".$l['comments_from']." ".$com_form['city']; + $text .= " ".$l['comments_posted']." ".$date.":\n\n"; + $text .= html_entity_decode(strip_tags($bbcomments->parse($com_form['content']))); + $text .= "\n\n".str_replace ( '&', '&', blog($blogentry['date'], $blogentry['url']))."#c".$cid.""; + $text .= "\n-- \n".$l['comments_stop_receiving']."\n"; + $text .= JLOG_PATH."/stop.php?id=".$blogentry['id']."&email="; + + while ($data = $comment_mail->fetch()) { + if($data['email'] != $com_form['email']) { + // set text for current user + $mail->setText($text . $data['email']); + $mail = $plugins->callHook('commentorMail', $mail, $blogentry); + // send mail + $mail->send(); + } + } + $c['form_content'] .= "

    ".$l['comments_thx']."

    ".com_javascript_variables(); + } + } +} + +// If nothing happens +elseif($blogentry['comments'] == 1) { + $com_form['name'] = $l['comments_name']; + $com_form['city'] = $l['comments_city']; + $com_form['email'] = $l['comments_email']; + $com_form['homepage'] = $l['comments_homepage']; + $com_form['sid'] = new_sid(); + if(isset($_COOKIE["jlog_userdata"])) { + $cookie = unserialize(urldecode($_COOKIE["jlog_userdata"])); + if($cookie != "") $com_form['cookie'] = 1; + if($cookie[0] != "") $com_form['name'] = $cookie[0]; + if($cookie[1] != "") $com_form['city'] = $cookie[1]; + if($cookie[2] != "") $com_form['email'] = $cookie[2]; + if($cookie[3] != "") $com_form['homepage'] = $cookie[3]; + } + $c['form_content'] .= com_form_output($com_form).com_javascript_variables(); +} +else $c['form_content'] .= "

    ".$l['comments_closed']."

    \n".com_javascript_variables(); + + + +// get comments and pingbacks + +$comments = new Query($sql_comments); +if($comments->error()) { + echo "
    \n";
    +    echo $comments->getError();
    +    echo "
    \n"; + die(); +} +$countPingbacks = 0; +$countComments = 0; +$commentsArray = array(); +$no_comments = ""; + +while($tmp_commentsArray = $comments->fetch()) $commentsArray[] = $tmp_commentsArray; +foreach($commentsArray as $tmp_comment) { + if($tmp_comment['type'] == 'pingback') ++$countPingbacks; + else ++$countComments; +} + +if($countPingbacks > 0) { + if($countComments < 1) $no_comments = " class='entryform'"; + $c['main'] .= "\n

    ".$l['pingback_topic']."

    \n
      "; + foreach($commentsArray as $pingback) { + if($pingback['type'] == 'pingback') $c['main'] .= "\n
    1. ".$pingback['name']."
    2. "; + } + $c['main'] .= "\n
    \n"; +} + +if($countComments < 1) $no_comments = " class='entryform'"; +$c['main'] .= "\n

    ".$l['comments_comment_topic']."

    \n"; + +if($countComments > 0) { + $c['main'] .= "
      "; + + $i = 0; + foreach($commentsArray as $data) { + if($data['type'] !== 'pingback') { + ++$i; + $data = com_clean_data($data); + $c['main'] .= do_comment($data, $i); + } + } + + $c['main'] .= "\n
    \n"; +} + +$c['main'] .= $c['form_content']; + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; + +?> diff --git a/page.php b/page.php new file mode 100644 index 0000000..f2198f3 --- /dev/null +++ b/page.php @@ -0,0 +1,45 @@ +error()) { + echo "
    \n";
    +        echo $blog->getError();
    +        echo "
    \n"; + die(); + } + + if($blog->numRows() == 0) { + header($_SERVER["SERVER_PROTOCOL"]." 404 Not Found"); + include_once(JLOG_BASEPATH."error404.php"); + exit; + } + $daten = $blog->fetch(); + + $c['meta']['date'] = $daten['metadate']; + $c['meta']['description'] = strip_tags($bbcode->parse($daten['teaser'])); + $c['meta']['keywords'] = $daten['keywords']; + $c['meta']['title'] = $daten['topic']; + + $c['main'] = do_entry($daten, NULL, 'page'); + + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> diff --git a/personal/css/admin.css b/personal/css/admin.css new file mode 100644 index 0000000..51ff90b --- /dev/null +++ b/personal/css/admin.css @@ -0,0 +1,28 @@ +/* -- CSS for the Jlog admincenter v0.2 -- */ +/* -- last edit 15 Dec 2004 -- */ + +#admin { margin: 0; padding: 0; border: 0; } +#admin p { font-weight: normal; } +#admin input, #admin textarea { font-weight: normal; font-family: inherit; font-size: inherit; padding-left: 0.2em; } +#admin input.long { width: 90%; } +#admin input.short { width: 3em; } +#admin input.button { width: auto; margin: 1em; } +#admin textarea { width: 90%; } +#admin form dt { font-weight: normal; margin: 0.5em 0 0 0; } +#admin form dd { margin: 0 0 0 1em; } +#admin form textarea.small { height: 2.7em; } +#admin form textarea.big { height: 15em; } + +#admin table { empty-cells: show; border-spacing: 0; font-size: 1em; } +#admin table tr td, +#admin table tr th { padding: 3px 8px; border-left: 1px dotted #bdaa94; vertical-align: top; } +#admin table tr th { border-bottom: 1px dotted #bdaa94; } +#admin table a, #admin table a img { border: none; background: none; } + +#admin a img.admin { border: none; background: none; } + +#admin h2.preview { color: red; text-align: center; background-color: white; } +#admin .preview { background: #FFF5F7; margin: 0 -10px; padding: 10px; } + +#admin .hide { display: none; } +#admin-menu { position: relative; z-index: 2; } diff --git a/personal/css/ielte6.css b/personal/css/ielte6.css new file mode 100644 index 0000000..2d93510 --- /dev/null +++ b/personal/css/ielte6.css @@ -0,0 +1,34 @@ +/* additional hacks for IE + * btw. IE sucks! ;-) + */ + + #pokal { /* do not display the alpha image */ + display: none; + } + + #container { /* IE max-width and PNG no-alpha hack */ + height: 1%; + width: 750px; + width:expression(document.body.clientWidth>805?"800px":"auto"); + background-image: url(img/banner-ielte6.jpg); + } + + #main { width: 63%; margin: 0 0 0 15px; } + + ul.comments li { + overflow-x: scroll; + } + + #admin table { /* adapting the font size for IE 5.x */ + font-size: 1em; + } + + * html #subnav { /* Box-Model Bug */ + content:"\"; width: 30%; padding: 2em 1.5em; + } + + * html #main { width: 62.5%; margin: 0 0 0 15px; } + + html + body #admin { /* close the hole in IE 5.0 */ + margin: 0; + } diff --git a/personal/css/img/Browse.plb b/personal/css/img/Browse.plb new file mode 100644 index 0000000..b5d3fd6 Binary files /dev/null and b/personal/css/img/Browse.plb differ diff --git a/personal/css/img/banner-ielte6.jpg b/personal/css/img/banner-ielte6.jpg new file mode 100644 index 0000000..f357afb Binary files /dev/null and b/personal/css/img/banner-ielte6.jpg differ diff --git a/personal/css/img/banner.jpg b/personal/css/img/banner.jpg new file mode 100644 index 0000000..b73ce5b Binary files /dev/null and b/personal/css/img/banner.jpg differ diff --git a/personal/css/img/body.png b/personal/css/img/body.png new file mode 100644 index 0000000..51b09b9 Binary files /dev/null and b/personal/css/img/body.png differ diff --git a/personal/css/img/border.png b/personal/css/img/border.png new file mode 100644 index 0000000..f4fdb83 Binary files /dev/null and b/personal/css/img/border.png differ diff --git a/personal/css/img/cheese.png b/personal/css/img/cheese.png new file mode 100644 index 0000000..6893ffd Binary files /dev/null and b/personal/css/img/cheese.png differ diff --git a/personal/css/img/footer.png b/personal/css/img/footer.png new file mode 100644 index 0000000..d132ed7 Binary files /dev/null and b/personal/css/img/footer.png differ diff --git a/personal/css/img/pokal.png b/personal/css/img/pokal.png new file mode 100644 index 0000000..c9814e5 Binary files /dev/null and b/personal/css/img/pokal.png differ diff --git a/personal/css/popup.css b/personal/css/popup.css new file mode 100644 index 0000000..d3196ab --- /dev/null +++ b/personal/css/popup.css @@ -0,0 +1,34 @@ +body { + font-family: Verdana, Arial, Helvetica, sans-serif; + color: black; + font-size: 0.8em; + background-color: #eee; + margin: 0px; + padding: 10px 5%; +} +h1 { + margin: 0px 0px 20px 0px; + font-size: 140%; +} +.caution { + color: red; + font-weight: bold; +} +ul { list-style-type: none; margin: 0; } +ul.error { list-style-type: disc; } +li { margin: 0.5em; } +.error { color: red; } +a { color: brown; } +img { border: none; } +a img { + border: none; + margin: 0 0 0.5em 0; +} +p { margin: 0; padding: 0.5em 0 0.5em 0 } +blockquote { + border: 1px solid #999; + border-left: 3px solid #aaa; + padding: 0 1em 0.3em 1em; + margin: 0; + background: #eee url(/img/anfuehrungszeichen.png) 2% 1px no-repeat; +} diff --git a/personal/css/print.css b/personal/css/print.css new file mode 100644 index 0000000..ec681cd --- /dev/null +++ b/personal/css/print.css @@ -0,0 +1,19 @@ +/* print.css for the default template of Jlog + * see screen.css for more details + */ + +/* -- hide -- */ + #subnav, .skip, .entryform, .hidecomments, #entryform, hr { display: none; } + +/* -- main settings -- */ + body { font-family: Georgia, "Times New Roman", Times, serif; } + h1 { text-align: right; margin-top: 0; } + blockquote { font-style: italic; } + +/* -- links -- */ + a { text-decoration: none; } + #main a:after { font-size: 70%; content:" <"attr(href)">"; } + #main .meta a:after, #main h2 a:after { content:""; } + +/* -- comments -- */ + ul#commentslist { list-style-type: none; } diff --git a/personal/css/screen.css b/personal/css/screen.css new file mode 100644 index 0000000..4b9600e --- /dev/null +++ b/personal/css/screen.css @@ -0,0 +1,213 @@ +/* screen.css for the standard Jlog template. + * + * Author: Jeena Paradies + * License: GPL (see LICENSE.txt in this package) + * + */ + +/* -- main positionering -- */ + body { + font-size: 100.01%; + font-family: verdana, arial, sans-serif; + background: #ffdc6c url(img/body.png); + color: black; + min-width: 500px; + margin: 0 20px; + padding: 0; + text-align: center; + } + #container { + font-size: 0.8em; + text-align: left; + margin: 0 auto; + max-width: 800px; + background: url(img/banner.jpg) no-repeat 0 2.4em white; + border: 1px solid #2B2B2B; + border-top: 0; + position: relative; + } + #main { + margin: 0 0 0 25px; + padding: 190px 0 2em 0; + width: 64.5%; + float: left; + } + + /* Clearfix-Hack */ + #main:after { + content: "."; + display: block; + height: 0; + clear: both; + visibility: hidden; + } + + #main {display: inline-table;} + + /* Hides from IE-mac \*/ + * html #main {height: 1%;} + #main {display: block;} + /* End hide from IE-mac */ + + /* -- logo -- */ + h1 { + font-size: 2em; + font-weight: normal; + padding: 0 5%; + margin: 0; + background: url(img/cheese.png) right bottom repeat-y white; + } + h1 a:link, h1 a:visited { color: black; text-decoration: none; } + + /* -- pokal -- */ + #pokal { + position: absolute; + left: -21px; + top: 4.5em; + width: 128px; + height: 198px; + background: url(img/pokal.png) no-repeat; + margin: 0; + padding: 0; + } + + /* -- subnavigation -- */ + #subnav { + width: 26%; + margin: 1em 1px 1em 0; + float: right; + margin-top: 165px; + padding: 1% 1% 1% 2%; + font-size: 0.8em; + background: url(img/border.png) repeat-y white; + } + #subnav dt { + font-weight: bold; + margin-top: 1.5em; + } + #subnav dd { + padding: 0.5em; + margin: 0; + line-height: 120%; + } + #subnav ul { + margin: 0; padding: 0; + list-style-type: none; + } + #subnav ul li { margin-bottom: 0.5em; } + .rss img { vertical-align: middle; border: 0; width: 94px; height: 15px; } + + /* -- footer -- */ + #footer { + clear: both; + height: 60px; + background: url(img/footer.png) no-repeat top center; + } + +/* -- basic styles -- */ + .skip { + position: absolute; + left: -999px; + width: 990px; + } + hr { + background-color: #aaa; + color: #aaa; + border: 0 none; + height: 1px; + margin: 1em 0; + clear: both; + } + .error { color: red; } + blockquote { + background: url(img/border.png) repeat-y; + padding: 0 0.5em; + font-style: italic; + } + #searchform { text-align: center; } + .meta.date { margin-top: 0; } + .meta { font-style: italic; font-size: 0.85em; } + .searchword { background: yellow; } + + /* -- pictures -- */ + .fl { float: left; margin: 0 1em 1em 0; } + .fr { float: right; margin: 0 0 1em 1em; } + #main img, dl.img { + border: 1px solid #aaa; + padding: 2px; + max-width: 95%; + } + dl.img dt { padding: 0; margin: 0;} + #main dl.img dt img { margin: 0; padding: 0; max-width: 100%; border: none; } + dl.img dd { margin: 0; padding: 0 0.3em; font-size: 90%; } + .teaser { clear: both; } + + /* -- main link styles -- */ + a:link { color: #18518b; } + a:visited { color: #555; } + a:hover { color: black; } + + /* -- headlines -- */ + h2, h3, h4, h5, h6 { + font-weight: normal; + font-family: verdana, sans-serif; + position: relative; + z-index: 2; + } + h2 { font-size: 1.7em; margin: 0; } + h3 { font-size: 1.2em; } + h4 { font-size: 1.1em; } + h5 { font-size: 1em; } + h6 { font-size: 0.9em; } + h2 a:link, h2 a:visited, + .teaser h3 a:link, .teaser h3 a:visited, + .teaser h4 a:link, .teaser h4 a:visited { text-decoration: none; color: black; } + h2 a:hover, .teaser h3 a:hover, .teaser h4 a:hover { text-decoration: underline; } + .teaser h3, .teaser h4 { margin: 0; } + + /* -- textareas and inputs -- */ + fieldset { border: 1px solid #aaa; padding: 1em; } + legend { padding: 1em; font-weight: bold; } + input.long, input.short, input.userdata, textarea, select { + background: #f7f7f7; + border: 1px solid #bbb; + border-right: 1px solid #d8d8d8; + border-bottom: 1px solid #D8D8D8; + } + +/* -- aditional styles for the home- and searchpage -- */ + .teaser h2 { font-size: 1.3em; } + .teaser h3, .teaser h4 { font-weight: bold; } + .teaserpic { float: right; margin: 0 0 1em 1em; } + .entries , .search li { list-style-type: none; } + .search li { border-top: 1px solid #d8d8d8; padding-top: 1em; } + ul.search { margin: auto 5%; padding-left: 0; } + h2.search { text-align: center; } + .archive { margin-left: 5%; } + .archivenavigation { text-align: center; border-top: 1px dotted #aaa; padding-top: 0.7em; margin-top: 2em; } + +/* -- comments -- */ + p.hidecomments { font-size: 0.75em; text-align: right; line-height: 1px; padding: 0; margin-bottom: 0; } + #preview li { border: solid 1px red; } + ul.comments .meta { font-size: 1.3em; } + ul.comments { list-style-type: none; font-size: 0.9em;} + ul.comments li { + padding: 0 1em 0.5em 1em; + margin: 1em 0; + background: #f7f7f7; + border: 1px solid #ccc; + border-left: 1px solid #d8d8d8; + border-top: 1px solid #D8D8D8; + overflow-x: scroll; + } + ul.comments li p { margin: 0.5em; } + ul.comments a.permalink { + font: normal bold 1.5em monospace; + border-right: 1px solid #d8d8d8; + text-decoration: none; + padding-right: 0.2em; + margin-right: 0.2em; + } + ul.comments a.permalink:hover { text-decoration: underline; } + #pingbackslist { margin-bottom: 3em; } + textarea { width: 90%; min-width: 10em; } diff --git a/personal/template.tpl b/personal/template.tpl new file mode 100644 index 0000000..d07b1c4 --- /dev/null +++ b/personal/template.tpl @@ -0,0 +1,40 @@ + + + + <jlog:title /> - <jlog:website /> + + + + + + +

    +
    +

    + +
    + +
    + +
    + + diff --git a/plugins/.htaccess b/plugins/.htaccess new file mode 100644 index 0000000..4dbcc9b --- /dev/null +++ b/plugins/.htaccess @@ -0,0 +1,2 @@ +Order allow,deny +Deny from All \ No newline at end of file diff --git a/plugins/CommentCloser.jplug.php b/plugins/CommentCloser.jplug.php new file mode 100644 index 0000000..a443d7b --- /dev/null +++ b/plugins/CommentCloser.jplug.php @@ -0,0 +1,126 @@ + + * @author: Robert Bienert + * @version: 1.3 + * @date: 2009-01-04 + * + * Dieses Plugin schliesst nach einer bestimmten, festzulegenden + * Laufzeit die Kommentare eines Artikels. + * + * Konstanten-Praefix: COMMENT_CLOSER + */ + +define('COMMENT_CLOSER_CFG_FILE', JLOG_BASEPATH . 'personal' . + DIRECTORY_SEPARATOR . 'settings.CommentCloser.inc.php'); + +if (@file_exists(COMMENT_CLOSER_CFG_FILE)) + include_once COMMENT_CLOSER_CFG_FILE; + +class CommentCloser extends JlogPlugin { + var $_units = array('SECOND', 'MINUTE', 'HOUR', 'DAY', 'WEEK', + 'MONTH', 'YEAR', + ); + // Dieses Array kann lokalisiert werden: + var $_unit_desc = array('Sekunden', 'Minuten', 'Stunden', + 'Tagen', 'Wochen', 'Monaten', 'Jahren' + ); + + // Konfigurationsoberflaeche + function hook_adminContent($output) { + $lifeTime = defined('COMMENT_CLOSER_LIFETIME') ? + COMMENT_CLOSER_LIFETIME : ''; + $timeUnit = defined('COMMENT_CLOSER_TIMEUNIT') ? + COMMENT_CLOSER_TIMEUNIT : ''; + $self = htmlspecialchars($_SERVER['REQUEST_URI']); + + if (array_key_exists('commclose_do', $_POST)) { + $lifeTime = $_POST['commclose_lifetime']; + $timeUnit = $_POST['commclose_unit']; + // Einheiten pruefen + if (! in_array($timeUnit, $this->_units)) + $timeUnit = ''; + + // keine (negative) Zeit XXX implicit cast + if ($lifeTime + 0 <= 0) + $lifeTime = 0; + + # XXX MySQL bug: WEEK wird bei mir nicht + # erkannt, deshalb manuelles Umrechnen: + if ($timeUnit == 'WEEK') { + $lifeTime *= 7; + $timeUnit = 'DAY'; + } + + $mask = umask(0); + + if (($f = @fopen(COMMENT_CLOSER_CFG_FILE, 'wb'))) + { + @fwrite($f, "'); + @fclose($f); + } + + umask($mask); + } + + $output = << +

    +

    +

    Nach der angegeben Zeit können Beiträge nicht mehr kommentiert werden.

    + +EOT; + + return $output; + } + + // Pruefen auf zu schliessende Beitraege + function hook_onUpdate($data) { + // Kein Schliessen gewuenscht, Plugin nicht konfiguriert + // oder ungueltige Werte gesetzt: + if (!defined('COMMENT_CLOSER_LIFETIME') || + COMMENT_CLOSER_LIFETIME+0 <= 0 || + !defined('COMMENT_CLOSER_TIMEUNIT') || + !in_array(COMMENT_CLOSER_TIMEUNIT, + $this->_units)) + { + return $data; + } + + $q = new Query('UPDATE ' . JLOG_DB_PREFIX . + 'content SET comments=0 ' . + 'WHERE date < DATE_SUB(NOW(), INTERVAL ' . + COMMENT_CLOSER_LIFETIME . ' ' . + COMMENT_CLOSER_TIMEUNIT . + ') AND comments=1'); + # TODO error handling + + return $data; + } +} +?> diff --git a/plugins/MiniAntispam.jplug.php b/plugins/MiniAntispam.jplug.php new file mode 100644 index 0000000..67c5365 --- /dev/null +++ b/plugins/MiniAntispam.jplug.php @@ -0,0 +1,38 @@ + + * @author: Jeena Paradies + * @version: 1.0 + * @date: 2006-05-10 + */ + +class MiniAntispam extends JlogPlugin { + + function hook_commentForm($form) { + $uid = $this->generate_uid(); + $uid_inputs = "\n ".''; + $uid_inputs .= "\n ".''; + + return str_replace("

    ", "

    ".$uid_inputs, $form); + } + + function hook_newComment($form) { + if(empty($form['publickey']) OR $form['publickey'] != $form['privatkey']) { + die("

    Hi spammer

    Please don't spam me."); + } + return $form; + } + + function generate_uid($len = 40) { + $acceptedChars = 'azertyuiopqsdfghjklmwxcvbnAZERTYUIOPQSDFGHJKLMWXCVBN0123456789.,-;_'; + $maxchar = strlen($acceptedChars)-1; + $uid = ''; + mt_srand((double)microtime()*1000000); + + for($i=0; $i < $len; $i++) $uid .= $acceptedChars{ mt_rand(0, $maxchar) }; + + return $uid; + } + +} +?> diff --git a/scripts/JlogUpdater.php b/scripts/JlogUpdater.php new file mode 100644 index 0000000..cf70868 --- /dev/null +++ b/scripts/JlogUpdater.php @@ -0,0 +1,149 @@ + next version in history + * + * @var array + */ + var $versions = array( + '1.0.2' => '1.1.0', + '1.1.0' => '1.1.1', + '1.1.1' => '1.1.2', + '1.1.2' => '1.1.3' + ); + + function JlogUpdater() + { + require_once(JLOG_BASEPATH."scripts".DIRECTORY_SEPARATOR."settings.class.php"); + } + + function getOldVersion() + { + return JLOG_INSTALLED_VERSION; + } + + function getNewVersion() + { + return JLOG_SOFTWARE_VERSION; + } + + function isUp2Date() + { + if (version_compare($this->getOldVersion(), $this->getNewVersion(), '<')) { + return false; + } + return true; + } + + function prepareForm($l) + { + $html = '
    ' + . '

    ' . $l['admin']['e_admin_password'] . ': ' + . '' + . '

    '; + $version = $this->getOldVersion(); + while (isset($this->versions[$version])) { + $class = $this->_loadUpdateClass($version, $this->versions[$version]); + $html .= sprintf("

    Update %s%s

    \n", $version, $this->versions[$version]); + $html .= $class->getForm($l); + $version = $this->versions[$version]; + } + $html .= '

    '; + $html .= '
    '; + return $html; + } + + function performUpdate($l) + { + if (JLOG_AMDIN_PASSWORD !== md5($_POST['jlog_password']) and JLOG_ADMIN_PASSWORD !== md5(utf8_decode($_POST['jlog_password']))) { + return '

    ' . $l['admin']['login_false_pw'] . '

    '; + } + + require_once(JLOG_BASEPATH."scripts".DIRECTORY_SEPARATOR."settings.class.php"); + // read current settings from environment + $settings = new Settings($l); + $settings->importDataByConstants(); + + $error = false; + $html = ''; + $version = $this->getOldVersion(); + while (isset($this->versions[$version])) { + $class = $this->_loadUpdateClass($version, $this->versions[$version]); + $html .= sprintf("

    Update %s%s

    \n", $version, $this->versions[$version]); + $result = $class->performUpdate($l, $settings); + if ($result === true) { + // we know that update class ran successfully + $result = $this->_updateVersionNumber($settings, $this->versions[$version]); + // check if errors occured + if (!empty($result)) { + $this->_renderErrors($result); + break; + } + else { + $html .= '

    ' . $l['admin']['update_successfull_part'] . '

    '; + } + } + else { + $html .= $this->_renderErrors($result); + break; + } + $version = $this->versions[$version]; + } + if ($error) { + $html .= '

    ' . $l['admin']['update_failure'] . '

    '; + } + else { + $html .= '

    ' . $l['admin']['update_successfull'] . '

    '; + } + return $html; + } + + function _getUpdateFile($oldver, $newver) + { + $oldver = str_replace('.', '', $oldver); + $newver = str_replace('.', '', $newver); + return "{$oldver}To{$newver}.php"; + } + + function _getUpdateClass($oldver, $newver) + { + $oldver = str_replace('.', '', $oldver); + $newver = str_replace('.', '', $newver); + return "JlogUpdate_{$oldver}To{$newver}"; + } + + function _loadUpdateClass($oldver, $newver) + { + $file = $this->_getUpdateFile($oldver, $newver); + $class = $this->_getUpdateClass($oldver, $newver); + require_once(dirname(__FILE__) . DIRECTORY_SEPARATOR . 'update' . DIRECTORY_SEPARATOR . $file); + return new $class(); + } + + function _renderErrors($errors) + { + $html = '
      '; + foreach ($errors as $error) { + $html .= '
    • ' . $error . '
    • '; + } + $html .= '
    '; + return $html; + } + + function _updateVersionNumber($settings, $newver) + { + $settings->setValue('jlog_installed_version', $newver); + $settings->setValue('jlog_installed_url', JLOG_SOFTWARE_URL); + $settings->setValue('jlog_installed_phpv', JLOG_SOFTWARE_PHPV); + $settings->setValue('jlog_installed_mysqlv', JLOG_SOFTWARE_MYSQLV); + + // rewrite settings.inc.php + return $settings->do_settings(); + } +} + +// eof \ No newline at end of file diff --git a/scripts/bbcode.php b/scripts/bbcode.php new file mode 100644 index 0000000..d153756 --- /dev/null +++ b/scripts/bbcode.php @@ -0,0 +1,172 @@ +' . $content . ''; + } +} + +// Funktion zum Einbinden von Bildern +function do_bbcode_img ($action, $attributes, $content, $params, $node_object) { + if ($action == 'validate') { + if (isset($attributes['caption'])) { + $node_object->setFlag('paragraph_type', BBCODE_PARAGRAPH_BLOCK_ELEMENT); + if ($node_object->_parent->type() == STRINGPARSER_NODE_ROOT OR + in_array($node_object->_parent->_codeInfo['content_type'], array('block', 'list', 'listitem'))) { + return true; + } + else return false; + } + else return true; + } + $title = empty($attributes["title"]) ? "" : " title='".htmlspecialchars($attributes["title"])."'"; + + if (isset($attributes['class']) AND isset($attributes['caption'])) $class_caption = " class='img ".htmlspecialchars($attributes['class'])."'"; + elseif (isset($attributes['class'])) $class = " class='".htmlspecialchars($attributes['class'])."'"; + elseif (isset($attributes['caption'])) $class_caption = " class='img'"; // bugfix by Sebastian Kochendörfer #215 + + if (strpos($content, "http://") === 0) return "".htmlspecialchars($attributes["; + else { + list($img_width, $img_height, $img_type, $img_attr) = @getimagesize(JLOG_BASEPATH.'/img'.DIRECTORY_SEPARATOR.htmlspecialchars($content)); + $img = "".htmlspecialchars($attributes["; + } + + if(isset($attributes['caption'])) { + return "\n\n
    ".$img."
    \n
    ".htmlspecialchars($attributes['caption'])."
    \n\n"; + } + else return $img; +} + +// Funktion zum Einbinden von HTML Code, welcher vom Browser interpretiert wird +function do_bbcode_html($action, $attributes, $content, $params, $node_object) { + if ($action == 'validate') return true; + return $content; +} + +$bbcode = new StringParser_BBCode (); +$bbcode->addFilter (STRINGPARSER_FILTER_PRE, 'convertlinebreaks'); +$bbcode->addFilter (STRINGPARSER_FILTER_POST, 'special_character'); + +$bbcode->addParser (array ('block', 'inline', 'link', 'listitem'), 'htmlspecialchars'); +$bbcode->addParser (array ('block', 'inline', 'link', 'listitem'), 'nl2br'); +$bbcode->addParser ('list', 'bbcode_stripcontents'); +$bbcode->setRootParagraphHandling (true); + +$bbcode->addCode ('b', 'simple_replace', null, array ('start_tag' => '', 'end_tag' => ''), + 'inline', array ('listitem', 'block', 'inline', 'link'), array ()); + +$bbcode->addCode ('i', 'simple_replace', null, array ('start_tag' => '', 'end_tag' => ''), + 'inline', array ('listitem', 'block', 'inline', 'link'), array ()); + +$bbcode->addCode ('headline', 'simple_replace', null, array('start_tag' => '

    ', 'end_tag' => '

    '), + 'block', array('block'), array('inline', 'link')); + +$bbcode->addCode ('quote', 'simple_replace', null, array('start_tag' => '
    ', 'end_tag' => '
    '), + 'block', array('block', 'listitem'), array('inline', 'link')); + +$bbcode->addCode ('url', 'usecontent?', 'do_bbcode_url', array ('usecontent_param' => 'default'), + 'link', array ('listitem', 'block', 'inline'), array ('link')); + +$bbcode->addCode ('img', 'usecontent', 'do_bbcode_img', array (), + 'image', array ('listitem', 'block', 'inline', 'link'), array ()); + +$bbcode->addCode ('html', 'usecontent', 'do_bbcode_html', array (), + 'html', array ('listitem', 'block', 'inline', 'link'), array ('image')); + +$bbcode->addCode ('list', 'simple_replace', null, array ('start_tag' => '
      ', 'end_tag' => '
    '), + 'list', array ('block', 'listitem'), array ()); + +$bbcode->addCode ('olist', 'simple_replace', null, array ('start_tag' => '
      ', 'end_tag' => '
    '), + 'list', array ('block', 'listitem'), array ()); + +$bbcode->addCode ('*', 'simple_replace', null, array ('start_tag' => '
  • ', 'end_tag' => '
  • '), + 'listitem', array ('list', 'olist' ), array ()); + +$bbcode->setCodeFlag ('*', 'closetag', BBCODE_CLOSETAG_OPTIONAL); +$bbcode->setCodeFlag ('*', 'paragraphs', false); +$bbcode->setCodeFlag ('list', 'paragraph_type', BBCODE_PARAGRAPH_BLOCK_ELEMENT); +$bbcode->setCodeFlag ('list', 'opentag.before.newline', BBCODE_NEWLINE_DROP); +$bbcode->setCodeFlag ('list', 'closetag.after.newline', BBCODE_NEWLINE_DROP); +$bbcode->setCodeFlag ('olist', 'paragraph_type', BBCODE_PARAGRAPH_BLOCK_ELEMENT); +$bbcode->setCodeFlag ('olist', 'opentag.before.newline', BBCODE_NEWLINE_DROP); +$bbcode->setCodeFlag ('olist', 'closetag.before.newline', BBCODE_NEWLINE_DROP); +$bbcode->setCodeFlag ('headline', 'paragraph_type', BBCODE_PARAGRAPH_BLOCK_ELEMENT); +$bbcode->setCodeFlag ('headline', 'opentag.before.newline', BBCODE_NEWLINE_DROP); +$bbcode->setCodeFlag ('headline', 'closetag.after.newline', BBCODE_NEWLINE_DROP); +$bbcode->setCodeFlag ('html', 'opentag.before.newline', BBCODE_NEWLINE_DROP); +$bbcode->setCodeFlag ('html', 'closetag.after.newline', BBCODE_NEWLINE_DROP); +$bbcode->setCodeFlag ('quote', 'paragraph_type', BBCODE_PARAGRAPH_BLOCK_ELEMENT); +$bbcode->setCodeFlag ('quote', 'paragraphs', true); +$bbcode->setCodeFlag ('quote', 'opentag.before.newline', BBCODE_NEWLINE_DROP); +$bbcode->setCodeFlag ('quote', 'closetag.after.newline', BBCODE_NEWLINE_DROP); + +// BBCode for comments +$bbcomments = new StringParser_BBCode (); +$bbcomments->addFilter (STRINGPARSER_FILTER_PRE, 'convertlinebreaks'); +$bbcomments->addFilter (STRINGPARSER_FILTER_POST, 'special_character'); + +$bbcomments->addParser (array ('block', 'inline', 'link'), 'htmlspecialchars'); +$bbcomments->addParser (array ('block', 'inline', 'link'), 'nl2br'); +$bbcomments->setRootParagraphHandling (true); + +$bbcomments->addCode ('b', 'simple_replace', null, array ('start_tag' => '', 'end_tag' => ''), + 'inline', array ('block', 'inline', 'link'), array ()); +$bbcomments->addCode ('i', 'simple_replace', null, array ('start_tag' => '', 'end_tag' => ''), + 'inline', array ('block', 'inline', 'link'), array ()); +$bbcomments->addCode ('url', 'usecontent?', 'do_bbcode_url', array ('usecontent_param' => 'default'), + 'link', array ('block', 'inline'), array ('link')); +$bbcomments->addCode ('quote', 'simple_replace', null, array('start_tag' => '
    ', 'end_tag' => '
    '), + 'block', array('block'), array('inline', 'link')); + +$bbcomments->setCodeFlag ('quote', 'paragraph_type', BBCODE_PARAGRAPH_BLOCK_ELEMENT); +$bbcomments->setCodeFlag ('quote', 'paragraphs', true); +$bbcomments->setCodeFlag ('quote', 'opentag.before.newline', BBCODE_NEWLINE_DROP); +$bbcomments->setCodeFlag ('quote', 'closetag.after.newline', BBCODE_NEWLINE_DROP); + +// eof diff --git a/scripts/categories.class.php b/scripts/categories.class.php new file mode 100644 index 0000000..0adf1e6 --- /dev/null +++ b/scripts/categories.class.php @@ -0,0 +1,250 @@ +l = $l; + + $this->get_categories(); + } + + function get($id, $data) { + return $this->categories[$id][$data]; + } + + function get_id($url) { + foreach($this->categories AS $cat) { + if($cat['url'] == $url) return $cat['id']; + } + + } + + function get_categories() { + if(!defined("JLOG_UPDATE") AND !defined("JLOG_LOGIN")) { + $sql = "SELECT id, name, url, description FROM ".JLOG_DB_CATEGORIES; + $cat = new Query($sql); + if($cat->error()) { + echo "
    \n";
    +                echo $cat->getError();
    +                echo "
    \n"; + die(); + } + while($c = $cat->fetch()) { + $this->categories[$c['id']] = + array('id' => $c['id'], 'name' => $c['name'], 'url' => $c['url'], 'description' => $c['description'] ); + } + } + } + + function get_assigned_categories($id) { + $sql = "SELECT cat_id FROM ".JLOG_DB_CATASSIGN." WHERE content_id = '".$id."'"; + $assigned = new Query($sql); + if($assigned->error()) { + echo "
    \n";
    +            echo $assigned->getError();
    +            echo "
    \n"; + die(); + } + $ids = array(); + while($a = $assigned->fetch()) { + $ids[] = $a['cat_id']; + } + return $ids; + } + + function output_select($catassign) { + // $catassign is an array which contains all assigned ids + + if(count($this->categories) > 0) { + $output = "


    \n" + ." \n

    "; + + return $output; + } + } + + function output_rss($id) { + $ids = $this->get_assigned_categories($id); + if(is_array($ids)) { + foreach($ids AS $i) { + $output .= " ".$this->get($i, 'name')."\n"; + } + } + return $output; + } + + function output_assigned_links($ids) { + if(!is_array($ids)) $ids = $this->get_assigned_categories($ids); + if(is_array($ids)) { + foreach($ids as $id) { + $output .= $this->link($id)." "; + } + } + if(isset($output)) return " » ".$output.""; + } + + function output_whole_list($_before = "
      \n", $_after = "
    \n", $before = "
  • ", $after = "
  • \n") { + if(is_array($this->categories) AND count($this->categories)) { + $output = $_before; + foreach($this->categories AS $id => $tmp) { + $output .= $before.$this->link($id).$after; + } + $output .= $_after; + return $output; + } + else return false; + } + + function link($id) { + if(JLOG_CLEAN_URL) return "".$this->categories[$id]['name'].""; + else return "".$this->categories[$id]['name'].""; + } + + function output_whole_list_admin() { + $output = " + + + + + + "; + + foreach($this->categories AS $id => $tmp) { + $output .= " + + + + + \n"; + } + + $output .= "
    ".$this->l['admin']['change']."".$this->l['admin']['delete']."".$this->l['admin']['cat_name']."
    ".$this->l[".$this->l[".$this->link($id)."
    \n"; + + return $output; + } + + function output_form($form_input = "", $action = 'new', $legend) { + $output = " +
    +
    ".$legend." +


    +

    +


    + +

    +


    +

    +

    + ".$this->l['admin']['cancel']." + ".add_session_id_input_tag()."

    +
    +
    "; + + return $output; + } + + function new_cat($form_input) { + + $form_input = escape_for_mysql($form_input); + + $sql = "INSERT INTO ".JLOG_DB_CATEGORIES." (name, url, description) VALUES + ('".$form_input['name']."', + '".$form_input['url']."', + '".$form_input['description']."');"; + + $new = new Query($sql); + + if($new->error()) { + echo "
    \n";
    +         echo $new->getError();
    +         echo "
    \n"; + die(); + } + } + + function change_cat($form_input) { + + $form_input = escape_for_mysql($form_input); + + $sql = "UPDATE ".JLOG_DB_CATEGORIES." + SET + name = '".$form_input['name']."', + url = '".$form_input['url']."', + description = '".$form_input['description']."' + WHERE + id = '".$form_input['id']."' LIMIT 1;"; + + $change = new Query($sql); + + if($change->error()) { + echo "
    \n";
    +         echo $change->getError();
    +         echo "
    \n"; + die(); + } + } + + function trash_cat($id) { + + $sql = "DELETE FROM ".JLOG_DB_CATEGORIES." WHERE id = '".escape_for_mysql($id)."' LIMIT 1"; + $trash = new Query($sql); + if($trash->error()) { + echo "
    \n";
    +        echo $trash->getError();
    +        echo "
    \n"; + die(); + } + + $sql = "DELETE FROM ".JLOG_DB_CATASSIGN." WHERE cat_id = '".escape_for_mysql($id)."' LIMIT 1"; + $trash = new Query($sql); + if($trash->error()) { + echo "
    \n";
    +        echo $trash->getError();
    +        echo "
    \n"; + die(); + } + + + } + + function validate($form_input) { + if(empty($form_input['name'])) $errors[] = $this->l['admin']['cat_noname']; + + if(empty($form_input['url'])) $errors[] = $this->l['admin']['no_url']; + elseif(!preg_match("/^[a-z0-9\-_\.,]+$/", $form_input['url'])) $errors[] = $this->l['admin']['false_url_letters']; + else { + $sql = "SELECT id FROM ".JLOG_DB_CATEGORIES." WHERE url = '".escape_for_mysql($form_input['url'])."';"; + + $check_url = new Query($sql); + + if($check_url->error()) { + echo "
    \n";
    +             echo $check_url->getError();
    +             echo "
    \n"; + die(); + } + + if($check_url->numRows() > 0) { + $c = $check_url->fetch(); + if($c['id'] != $form_input['id']) $errors[] = $this->l['admin']['cat_duplicate']; + } + } + + return $errors; + } +} +?> diff --git a/scripts/comments.php b/scripts/comments.php new file mode 100644 index 0000000..0b6d0b3 --- /dev/null +++ b/scripts/comments.php @@ -0,0 +1,141 @@ + +
    ".$l['comments_entryform']." +

    + ".$l['comments_bbcode']." + BBcode? + +
    + +

    +

    + +
    + + +

    +

    +  "; + if(defined('JLOG_ADMIN')) $output .= "\n \n"; + else { + $output .= " \n"; + } + $output .= " +

    +

    + + "; + + if(defined("JLOG_ADMIN")) $output .= add_session_id_input_tag(); + + $output .= " +

    +
    + \n + "; + + ### Plugin Hook + $output = $plugins->callHook('commentForm', $output, $com_form); + + return $output; + } + + function com_javascript_variables() { + global $l; + return " + + "; + } + + function com_check_errors($com_form) { + global $l; + if(empty($com_form['sid'])) $errors[] = $l['comments_no_sid']; + if(isset($com_form['email']) AND $com_form['email'] != "" AND !preg_match("/^[^@]+@.+\.\D{2,6}$/", $com_form['email']) AND $com_form['email'] != $l['comments_email']) $errors[] = $l['comments_false_mail']; + if(empty($com_form['content'])) $errors[] = $l['comments_notext']; + if(isset($errors)) return $errors; + } + + function com_clean_data($data) { + global $l; + if(empty($data['name']) OR $data['name'] == $l['comments_name']) $data['name'] = ""; + if(empty($data['city']) OR $data['city'] == $l['comments_city']) $data['city'] = ""; + if(empty($data['email']) OR $data['email'] == $l['comments_email']) $data['email'] = ""; + if(empty($data['homepage']) OR $data['homepage'] == $l['comments_homepage']) $data['homepage'] = ""; + + if(empty($data['date'])) $data['date'] = time(); + + return $data; + } + + function set_cookie($data) { + $userdaten = array( $data['name'], + $data['city'], + $data['email'], + $data['homepage'] ); + $cookielife = time() + 42 * 24 * 60 * 60; + $path = parse_url(JLOG_PATH); + if(!isset($path['path'])) $path['path'] = ""; + setcookie("jlog_userdata", urlencode(serialize($userdaten)), $cookielife, $path['path']."/"); + } + + function trash_cookie() { + $cookielife = time() - 3600; + setcookie("jlog_userdata", '', $cookielife, "/"); + } + + function new_sid() { + list($usec, $sec) = explode(' ', microtime()); + mt_srand((float) $sec + ((float) $usec * 100000)); + return $_SERVER["REMOTE_ADDR"]."-".time()."-".mt_rand(1000,9999); + } + + // Funcitons + + function do_comment($data, $nr) { + global $l, $bbcomments, $plugins; + + $meta = array_htmlspecialchars($data); + $comment = " +
  • +

    "; + if(!empty($meta['homepage'])) $comment .= ""; + if(!empty($meta['name'])) $comment .= $meta['name']; + else $comment .= $l['comments_anonym']; + if(!empty($meta['homepage'])) $comment .= ""; + $comment .= ""; + if(!empty($meta['city'])) $comment .= " ".$l['comments_from']." ".$meta['city']; + $comment .= " ".$l['comments_posted']." ".strftime(JLOG_DATE_COMMENT, $data['date']).":

    \n".$bbcomments->parse($data['content'])."
  • "; + + ### Plugin Hook + $comment = $plugins->callHook('showComment', $comment, $data, $nr); + + return $comment; + } +?> diff --git a/scripts/database.class.php b/scripts/database.class.php new file mode 100644 index 0000000..bf804da --- /dev/null +++ b/scripts/database.class.php @@ -0,0 +1,71 @@ +_sql = trim($sql); + $this->_result = mysql_query($this->_sql); + if(!$this->_result) { + $this->_errno = mysql_errno(); + $this->_error = mysql_error(); + } + } + + //Methoden + function error() + { + // Result-ID in einer tmp-Variablen speichern + $tmp = $this->_result; + // Variable in boolean umwandeln + $tmp = (bool)$tmp; + // Variable invertieren + $tmp = !$tmp; + // und zurückgeben + return $tmp; + } + + function getError() { + if($this->error()) { + $str = "request:\n".$this->_sql."\n"; + $str .= "response:\n".$this->_error."\n"; + $str .= "Errorcode: ".$this->_errno; + } + else $str = "No error."; + return $str; + } + function getErrno() { + return $this->_errno; + } + + function fetch() { + if($this->error()) { + echo "An Error has occurred, please check your MySQL-Query."; + $return = null; + } + else $return = mysql_fetch_assoc($this->_result); + return $return; + } + + function numRows() { + if($this->error()) { + $return = -1; + } + else $return = mysql_num_rows($this->_result); + return $return; + } + + function free() { + // Speicher freimachen + mysql_free_result($this->_result); + } + + } +?> diff --git a/scripts/do_template.php b/scripts/do_template.php new file mode 100644 index 0000000..66b85b6 --- /dev/null +++ b/scripts/do_template.php @@ -0,0 +1,121 @@ +'."\n"; +if(isset($c['meta']['robots'])) $c['meta']['aditionalheader'] .= ' '."\n"; +if(isset($c['meta']['keywords'])) $c['meta']['aditionalheader'] .= ' '."\n"; +if(isset($c['meta']['description'])) $c['meta']['aditionalheader'] .= ' '."\n"; +if(isset($c['meta']['date'])) $c['meta']['aditionalheader'] .= ' '; +if(isset($c['meta']['pingback'])) { + $c['meta']['aditionalheader'] .= "\n".' '; + header("X-Pingback: ".JLOG_PATH."/xmlrpc.php"); +} + +$c['meta']['aditionalheader'] .= +' + + + + + + '; + +// do this on admincenter +if(defined('JLOG_ADMIN')) { + // turn off cashing + header("Expires: Mon, 26 Jul 1997 05:00:00 GMT"); + header("Last-Modified: " . gmdate("D, d M Y H:i:s") ." GMT"); + header("Cache-Control: no-cache"); + header("Pragma: no-cache"); + header("Cache-Control: post-check=0, pre-check=0", FALSE); + // include admin.css + $c['meta']['aditionalheader'] .= "\n ".''; + $c['main'] = "
    ".$c['main']."
    "; +} + +$_search = array ( + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "" +); + +$_replace = array ( + $l['language'], + htmlspecialchars(JLOG_WEBSITE, ENT_QUOTES), + htmlspecialchars($c['meta']['title']), + $c['meta']['aditionalheader'], + JLOG_PATH, + $l['content_skip'], + $l['meta_start'], + $l['subnav_aboutpage'], + JLOG_DESCRIPTION, + $l['content_search_topic'], + '', // bugfix + $l['content_search'], + $l['content_categorieslist_h'], + $l['subnav_current'], + $c['subnav_current'], + $l['content_archive'], + archive(), + $l['content_archivelink'], + $l['subnav_info'], + $l['subnav_rss'], + "XML - Fullpost XML - Summary", + "© ".date('Y')." ".JLOG_PUBLISHER.", ".$l['subnav_copyright'], + $c['main'], + $l['subnav_powered']." Jlog" +); + +$body = str_replace($_search, $_replace, $_body); + +$jlogTemplateTags = new JLOG_Tags($body); + + if(($categorieslist_tag = $jlogTemplateTags->getTag('categorieslist')) !== false) { + if(strlen($categorieslist_class = $jlogTemplateTags->getAttributeValue('categorieslist', 'class'))>0) $categorieslist_class = ' class="'.$categorieslist_class.'"'; + if( $categorieslist = $categories->output_whole_list("\n ".''."\n")) { + $body = str_replace($categorieslist_tag, $categorieslist, $body ); + } + else $body = str_replace($categorieslist_tag, '', $body ); + } + +$body = $plugins->callHook('body', $body, $jlogTemplateTags); diff --git a/scripts/general.func.php b/scripts/general.func.php new file mode 100644 index 0000000..1a449d2 --- /dev/null +++ b/scripts/general.func.php @@ -0,0 +1,313 @@ +callHook('permalink', $permalink, $date, $url, $section); + + return $permalink; +} + +function archive() { + if(JLOG_CLEAN_URL === true) return JLOG_PATH."/archive"; + else return JLOG_PATH."/archive.php"; +} + +// get year links +class Year_Links { + + function Year_Links($get, $start, $page, $l, $cat="") { + $date = getdate(); + $this->_now = $date['year']; + $this->_start = $start; + $this->_page = $page; + $this->_l = $l; + if(JLOG_CLEAN_URL === true) { + if($cat != "") { + list($tmp, $cat) = explode("=", $cat); + $this->cat = "/cat/".$cat; + } + } + elseif($cat !== "") $this->cat = $cat."&"; + + if($get >= $this->_start OR $get <= $this->_now AND preg_match("[0-9]", $get)) $this->year = $get; + else $this->year = $this->_now; + } + + function get_linklist() { + + for($y = $this->_start; $y <= $this->_now; $y++) { + if($y != $this->_start) $years_links .= " | "; + if($y == $this->year) $years_links .= " ".$y.""; + else { + if(JLOG_CLEAN_URL === true) $years_links .= " ".$y."\n"; + else $years_links .= " cat."y=".$y."'>".$y."\n"; + } + } + + return $this->_l['content_choose_year'].$years_links; + } + + function get_admin_linklist() { + + for($y = $this->_start; $y <= $this->_now; $y++) { + if($y != $this->_start) $years_links .= " | "; + if($y == $this->year) $years_links .= " ".$y.""; + else $years_links .= " ".$y."\n"; + } + + return $this->_l['content_choose_year'].$years_links; + + } + +// get selected year + function get_selected_year() { + return $this->year; + } +} + +// kill Magic Quotes +function strip($_data) { + if (!get_magic_quotes_gpc()) return $_data; + else { + if (is_array($_data)) foreach($_data as $key => $val) $_data[$key] = strip($val); + else $_data = stripslashes($_data); + return $_data; + } +} +// escape input for mysql +function escape_for_mysql($_data) { + if (is_array($_data)) foreach($_data as $key => $val) $_data[$key] = escape_for_mysql($val); + else $_data = mysql_escape_string($_data); + return $_data; +} +// htmlspecialchars a whole array +function array_htmlspecialchars($_data) { + if (is_array($_data)) foreach($_data as $key => $val) $_data[$key] = array_htmlspecialchars($val); + else $_data = htmlspecialchars($_data, ENT_QUOTES); + return $_data; +} +// Fehler ausgeben +function error_output($errors, $id = "", $headline = false) { +global $l; + $error = ""; + if($headline === false) $headline = $l["error"]; + if(isset($errors)) { + if(strlen($headline) > 0) $error = "\n

    ".$headline."

    "; + $error .= "\n
      \n"; + foreach($errors AS $f) $error .= "
    • ".$f."
    • \n"; + $error .= "
    \n"; + } + return $error; +} + +// Aus der Datenbank löschen (wird beim Kommentarlöschen gebraucht) + +function trash($id, $table) { + $sql = "DELETE FROM ".$table." WHERE id = '".$id."' LIMIT 1"; + + $trash = new Query($sql); + if($trash->error()) { + echo "
    \n";
    +        echo $trash->getError();
    +        echo "
    \n"; + die(); + } + return true; +} + +// output a teaser +function do_teaser($data, $cc, $pre = '

    ', $post = '

    ') { +global $l, $bbcode, $categories, $plugins; + + if(empty($data['date_url'])) $data['date_url'] = $data['date']; # fix for search.php + + $output = "\n
    \n"; + if($data['teaserpic'] != "") { + list($img_width, $img_height, $img_type, $img_attr) = @getimagesize(JLOG_BASEPATH.'img'.DIRECTORY_SEPARATOR.'t_'.$data['teaserpic']); + $output .= " \n"; + } + $output .= " ".$pre."".htmlspecialchars($data['topic'], ENT_QUOTES)."".$post." +

    ".$l['content_posted']." ".strftime(JLOG_DATE, $data['date']).$categories->output_assigned_links($data['id'])."

    "; + $output .= $bbcode->parse($data['teaser']); + + $output .="

    ".$l['content_more'].""; + + if($data['section'] == 'weblog') { + if(isset($cc[$data['id']]) AND $cc[$data['id']] != 0) $tmp_comments = " ".$l['content_comments']." (".$cc[$data['id']].")"; + elseif($data['comments'] === '0') $tmp_comments = $l['comments_teaser_closed']; + else $tmp_comments = " ".$l['content_comment_plz'].""; + $output .= " | ".$tmp_comments; + } + $output .= "

    \n
    \n"; + + ### Plugin Hook + $output = $plugins->callHook('doTeaser', $output, $data, $cc, $pre, $post); + + return $output; +} + +function do_entry($data, $cc = NULL, $section = 'weblog', $pre = '

    ', $post = '

    ') { +global $l, $bbcode, $categories, $plugins; + + $output = " +
    + ".$pre."".htmlspecialchars($data['topic'], ENT_QUOTES)."".$post."\n"; + + if($data['teaserpic'] != "" AND $data['teaserpiconblog'] == 1) { + list($img_width, $img_height, $img_type, $img_attr) = @getimagesize(JLOG_BASEPATH.'img'.DIRECTORY_SEPARATOR.'t_'.$data['teaserpic']); + $output .= ""; + } + + if($section == 'weblog' OR ($cat = $categories->output_assigned_links($data['id'])) != "") { + $output .= "

    "; + if($section == 'weblog') $output .= $l['content_posted']." ".strftime(JLOG_DATE, $data['date']); + $output .= $categories->output_assigned_links($data['id'])."

    "; + } + + $output .= $bbcode->parse($data['content']); + $path_parts = pathinfo($_SERVER['SCRIPT_NAME']); + + if($data['section'] == 'weblog' AND $path_parts['basename'] != 'log.php') { + if(isset($cc[$data['id']]) AND $cc[$data['id']] != 0) $tmp_comments = " ".$l['content_comments']." (".$cc[$data['id']].")"; + elseif($data['comments'] === '0') $tmp_comments = $l['comments_teaser_closed']; + else $tmp_comments = "".$l['content_comment_plz'].""; + $output .="

    ".$tmp_comments."

    "; + } + + if($section == 'weblog') $output .= '
    '; + $output .= "
    \n"; + + ### Plugin Hook + $output = $plugins->callHook('doEntry', $output, $data, $cc, $section); + + return $output; +} + +function count_comments() { + // -- Kommentare zählen + $sql = "SELECT reference, COUNT(*) as count FROM ".JLOG_DB_COMMENTS." WHERE type <> 'pingback' GROUP BY reference"; + $comments = new Query($sql); + if($comments->error()) { + echo "
    \n";
    +                echo $comments->getError();
    +             echo "
    \n"; + die(); + } + // -- Anzahl der jeweiligen Kommentare + $com = array(); + while($c = $comments->fetch()) $com[$c['reference']] = $c['count']; + + ### Plugin Hook + global $plugins; + $com = $plugins->callHook('countComments', $com); + + return $com; +} + +if (!function_exists('is_a')) { + function is_a($object, $class) + { + if (!is_object($object)) { + return false; + } + + if (get_class($object) == strtolower($class)) { + return true; + } else { + return is_subclass_of($object, $class); + } + } +} + +if (!function_exists("stripos")) { + function stripos($str,$needle,$offset=0) { + return strpos( strtolower($str), strtolower($needle), $offset ); + } +} + +if(!function_exists('str_ireplace')){ + function str_ireplace($search, $replace, $subject){ + if(is_array($search)){ + array_walk($search, create_function('&$pat, $key', '"/".preg_quote($pat, "/")."/i"')); + } + else{ + $search = '/'.preg_quote($search, '/').'/i'; + } + return preg_replace($search, $replace, $subject); + } +} + +if ( !function_exists('file_put_contents') && !defined('FILE_APPEND') ) { + define('FILE_APPEND', 1); + function file_put_contents($n, $d, $flag = false) { + $mode = ($flag == FILE_APPEND || strtoupper($flag) == 'FILE_APPEND') ? 'a' : 'w'; + $f = @fopen($n, $mode); + if ($f === false) { + return 0; + } else { + if (is_array($d)) $d = implode($d); + $bytes_written = fwrite($f, $d); + fclose($f); + return $bytes_written; + } + } +} + + +function my_serialize_cfg($arg) { + if(is_string($arg)) return "'".preg_replace("/'/","\\'",$arg)."'"; + elseif(is_integer($arg)) return (string)$arg; + elseif(is_float($arg)) return (string)$arg; + elseif(is_null($arg)) return 'NULL'; + elseif(is_bool($arg)) { + if($arg) return 'true'; + else return 'false'; + } + elseif(is_array($arg)) { + $retval = 'Array('; + foreach($arg as $key => $value) { + $retval .= my_serialize_cfg($key).' => '.my_serialize_cfg($value).','; + } + $retval .= ')'; + return $retval; + } + else die("unsupported type! ".gettype($arg)); +} + +class JLOG_Tags { + var $tree = array(); + + function JLOG_Tags($body) { + preg_match_all('/]*)\/?>(<\/(\1):(\2)>)?/ims', $body, $this->tree); + } + + function getTag($tagname) { + if(($tagnr = array_search($tagname, $this->tree[1])) !== false) return $this->tree[0][$tagnr]; + else return false; + } + + function getAttributeValue($tagname, $attribute) { + $pattern = '/(?:^|\s)([a-z]\w+)(?:=)(?:(?:\'([^\']+)\')|(?:"([^"]*)")|([^\s,]+))/i'; + if(($tagnr = array_search($tagname, $this->tree[1])) !== false) { + preg_match_all($pattern, $this->tree[2][ $tagnr ], $matches, PREG_SET_ORDER); + $a = count($matches); + for($i=0;$i<$a;$i++) { + if($matches[$i][1] == $attribute) return $matches[$i][3]; + } + } + else return; + } +} +?> \ No newline at end of file diff --git a/scripts/ixr-library.inc.php b/scripts/ixr-library.inc.php new file mode 100644 index 0000000..26f4b3c --- /dev/null +++ b/scripts/ixr-library.inc.php @@ -0,0 +1,817 @@ + htmlspecialchars) + Site: http://scripts.incutio.com/xmlrpc/ + Manual: http://scripts.incutio.com/xmlrpc/manual.php + Made available under the Artistic License: http://www.opensource.org/licenses/artistic-license.php +*/ + + +class IXR_Value { + var $data; + var $type; + function IXR_Value ($data, $type = false) { + $this->data = $data; + if (!$type) { + $type = $this->calculateType(); + } + $this->type = $type; + if ($type == 'struct') { + /* Turn all the values in the array in to new IXR_Value objects */ + foreach ($this->data as $key => $value) { + $this->data[$key] = new IXR_Value($value); + } + } + if ($type == 'array') { + for ($i = 0, $j = count($this->data); $i < $j; $i++) { + $this->data[$i] = new IXR_Value($this->data[$i]); + } + } + } + function calculateType() { + if ($this->data === true || $this->data === false) { + return 'boolean'; + } + if (is_integer($this->data)) { + return 'int'; + } + if (is_double($this->data)) { + return 'double'; + } + // Deal with IXR object types base64 and date + if (is_object($this->data) && is_a($this->data, 'IXR_Date')) { + return 'date'; + } + if (is_object($this->data) && is_a($this->data, 'IXR_Base64')) { + return 'base64'; + } + // If it is a normal PHP object convert it in to a struct + if (is_object($this->data)) { + $this->data = get_object_vars($this->data); + return 'struct'; + } + if (!is_array($this->data)) { + return 'string'; + } + /* We have an array - is it an array or a struct ? */ + if ($this->isStruct($this->data)) { + return 'struct'; + } else { + return 'array'; + } + } + function getXml() { + /* Return XML for this value */ + switch ($this->type) { + case 'boolean': + return ''.(($this->data) ? '1' : '0').''; + break; + case 'int': + return ''.$this->data.''; + break; + case 'double': + return ''.$this->data.''; + break; + case 'string': + return ''.htmlspecialchars($this->data).''; + break; + case 'array': + $return = ''."\n"; + foreach ($this->data as $item) { + $return .= ' '.$item->getXml()."\n"; + } + $return .= ''; + return $return; + break; + case 'struct': + $return = ''."\n"; + foreach ($this->data as $name => $value) { + $return .= " $name"; + $return .= $value->getXml()."\n"; + } + $return .= ''; + return $return; + break; + case 'date': + case 'base64': + return $this->data->getXml(); + break; + } + return false; + } + function isStruct($array) { + /* Nasty function to check if an array is a struct or not */ + $expected = 0; + foreach ($array as $key => $value) { + if ((string)$key != (string)$expected) { + return true; + } + $expected++; + } + return false; + } +} + + +class IXR_Message { + var $message; + var $messageType; // methodCall / methodResponse / fault + var $faultCode; + var $faultString; + var $methodName; + var $params; + // Current variable stacks + var $_arraystructs = array(); // The stack used to keep track of the current array/struct + var $_arraystructstypes = array(); // Stack keeping track of if things are structs or array + var $_currentStructName = array(); // A stack as well + var $_param; + var $_value; + var $_currentTag; + var $_currentTagContents; + // The XML parser + var $_parser; + function IXR_Message ($message) { + $this->message = $message; + } + function parse() { + // first remove the XML declaration + $this->message = preg_replace('/<\?xml(.*)?\?'.'>/', '', $this->message); + if (trim($this->message) == '') { + return false; + } + $this->_parser = xml_parser_create(); + // Set XML parser to take the case of tags in to account + xml_parser_set_option($this->_parser, XML_OPTION_CASE_FOLDING, false); + // Set XML parser callback functions + xml_set_object($this->_parser, $this); + xml_set_element_handler($this->_parser, 'tag_open', 'tag_close'); + xml_set_character_data_handler($this->_parser, 'cdata'); + if (!xml_parse($this->_parser, $this->message)) { + /* die(sprintf('XML error: %s at line %d', + xml_error_string(xml_get_error_code($this->_parser)), + xml_get_current_line_number($this->_parser))); */ + return false; + } + xml_parser_free($this->_parser); + // Grab the error messages, if any + if ($this->messageType == 'fault') { + $this->faultCode = $this->params[0]['faultCode']; + $this->faultString = $this->params[0]['faultString']; + } + return true; + } + function tag_open($parser, $tag, $attr) { + $this->currentTag = $tag; + switch($tag) { + case 'methodCall': + case 'methodResponse': + case 'fault': + $this->messageType = $tag; + break; + /* Deal with stacks of arrays and structs */ + case 'data': // data is to all intents and puposes more interesting than array + $this->_arraystructstypes[] = 'array'; + $this->_arraystructs[] = array(); + break; + case 'struct': + $this->_arraystructstypes[] = 'struct'; + $this->_arraystructs[] = array(); + break; + } + } + function cdata($parser, $cdata) { + $this->_currentTagContents .= $cdata; + } + function tag_close($parser, $tag) { + $valueFlag = false; + switch($tag) { + case 'int': + case 'i4': + $value = (int)trim($this->_currentTagContents); + $this->_currentTagContents = ''; + $valueFlag = true; + break; + case 'double': + $value = (double)trim($this->_currentTagContents); + $this->_currentTagContents = ''; + $valueFlag = true; + break; + case 'string': + $value = (string)trim($this->_currentTagContents); + $this->_currentTagContents = ''; + $valueFlag = true; + break; + case 'dateTime.iso8601': + $value = new IXR_Date(trim($this->_currentTagContents)); + // $value = $iso->getTimestamp(); + $this->_currentTagContents = ''; + $valueFlag = true; + break; + case 'value': + // "If no type is indicated, the type is string." + if (trim($this->_currentTagContents) != '') { + $value = (string)$this->_currentTagContents; + $this->_currentTagContents = ''; + $valueFlag = true; + } + break; + case 'boolean': + $value = (boolean)trim($this->_currentTagContents); + $this->_currentTagContents = ''; + $valueFlag = true; + break; + case 'base64': + $value = base64_decode($this->_currentTagContents); + $this->_currentTagContents = ''; + $valueFlag = true; + break; + /* Deal with stacks of arrays and structs */ + case 'data': + case 'struct': + $value = array_pop($this->_arraystructs); + array_pop($this->_arraystructstypes); + $valueFlag = true; + break; + case 'member': + array_pop($this->_currentStructName); + break; + case 'name': + $this->_currentStructName[] = trim($this->_currentTagContents); + $this->_currentTagContents = ''; + break; + case 'methodName': + $this->methodName = trim($this->_currentTagContents); + $this->_currentTagContents = ''; + break; + } + if ($valueFlag) { + /* + if (!is_array($value) && !is_object($value)) { + $value = trim($value); + } + */ + if (count($this->_arraystructs) > 0) { + // Add value to struct or array + if ($this->_arraystructstypes[count($this->_arraystructstypes)-1] == 'struct') { + // Add to struct + $this->_arraystructs[count($this->_arraystructs)-1][$this->_currentStructName[count($this->_currentStructName)-1]] = $value; + } else { + // Add to array + $this->_arraystructs[count($this->_arraystructs)-1][] = $value; + } + } else { + // Just add as a paramater + $this->params[] = $value; + } + } + } +} + + +class IXR_Server { + var $data; + var $callbacks = array(); + var $message; + var $capabilities; + function IXR_Server($callbacks = false, $data = false) { + $this->setCapabilities(); + if ($callbacks) { + $this->callbacks = $callbacks; + } + $this->setCallbacks(); + $this->serve($data); + } + function serve($data = false) { + if (!$data) { + global $HTTP_RAW_POST_DATA; + if (!$HTTP_RAW_POST_DATA) { + die('XML-RPC server accepts POST requests only.'); + } + $data = $HTTP_RAW_POST_DATA; + } + $this->message = new IXR_Message($data); + if (!$this->message->parse()) { + $this->error(-32700, 'parse error. not well formed'); + } + if ($this->message->messageType != 'methodCall') { + $this->error(-32600, 'server error. invalid xml-rpc. not conforming to spec. Request must be a methodCall'); + } + $result = $this->call($this->message->methodName, $this->message->params); + // Is the result an error? + if (is_a($result, 'IXR_Error')) { + $this->error($result); + } + // Encode the result + $r = new IXR_Value($result); + $resultxml = $r->getXml(); + // Create the XML + $xml = << + + + + $resultxml + + + + + +EOD; + // Send it + $this->output($xml); + } + function call($methodname, $args) { + if (!$this->hasMethod($methodname)) { + return new IXR_Error(-32601, 'server error. requested method '.$methodname.' does not exist.'); + } + $method = $this->callbacks[$methodname]; + // Perform the callback and send the response + if (count($args) == 1) { + // If only one paramater just send that instead of the whole array + $args = $args[0]; + } + // Are we dealing with a function or a method? + if (substr($method, 0, 5) == 'this:') { + // It's a class method - check it exists + $method = substr($method, 5); + if (!method_exists($this, $method)) { + return new IXR_Error(-32601, 'server error. requested class method "'.$method.'" does not exist.'); + } + // Call the method + $result = $this->$method($args); + } else { + // It's a function - does it exist? + if (!function_exists($method)) { + return new IXR_Error(-32601, 'server error. requested function "'.$method.'" does not exist.'); + } + // Call the function + $result = $method($args); + } + return $result; + } + + function error($error, $message = false) { + // Accepts either an error object or an error code and message + if ($message && !is_object($error)) { + $error = new IXR_Error($error, $message); + } + $this->output($error->getXml()); + } + function output($xml) { + $xml = ''."\n".$xml; + $length = strlen($xml); + header('Connection: close'); + header('Content-Length: '.$length); + header('Content-Type: text/xml'); + header('Date: '.date('r')); + echo $xml; + exit; + } + function hasMethod($method) { + return in_array($method, array_keys($this->callbacks)); + } + function setCapabilities() { + // Initialises capabilities array + $this->capabilities = array( + 'xmlrpc' => array( + 'specUrl' => 'http://www.xmlrpc.com/spec', + 'specVersion' => 1 + ), + 'faults_interop' => array( + 'specUrl' => 'http://xmlrpc-epi.sourceforge.net/specs/rfc.fault_codes.php', + 'specVersion' => 20010516 + ), + 'system.multicall' => array( + 'specUrl' => 'http://www.xmlrpc.com/discuss/msgReader$1208', + 'specVersion' => 1 + ), + ); + } + function getCapabilities($args) { + return $this->capabilities; + } + function setCallbacks() { + $this->callbacks['system.getCapabilities'] = 'this:getCapabilities'; + $this->callbacks['system.listMethods'] = 'this:listMethods'; + $this->callbacks['system.multicall'] = 'this:multiCall'; + } + function listMethods($args) { + // Returns a list of methods - uses array_reverse to ensure user defined + // methods are listed before server defined methods + return array_reverse(array_keys($this->callbacks)); + } + function multiCall($methodcalls) { + // See http://www.xmlrpc.com/discuss/msgReader$1208 + $return = array(); + foreach ($methodcalls as $call) { + $method = $call['methodName']; + $params = $call['params']; + if ($method == 'system.multicall') { + $result = new IXR_Error(-32600, 'Recursive calls to system.multicall are forbidden'); + } else { + $result = $this->call($method, $params); + } + if (is_a($result, 'IXR_Error')) { + $return[] = array( + 'faultCode' => $result->code, + 'faultString' => $result->message + ); + } else { + $return[] = array($result); + } + } + return $return; + } +} + +class IXR_Request { + var $method; + var $args; + var $xml; + function IXR_Request($method, $args) { + $this->method = $method; + $this->args = $args; + $this->xml = << + +{$this->method} + + +EOD; + foreach ($this->args as $arg) { + $this->xml .= ''; + $v = new IXR_Value($arg); + $this->xml .= $v->getXml(); + $this->xml .= "\n"; + } + $this->xml .= ''; + } + function getLength() { + return strlen($this->xml); + } + function getXml() { + return $this->xml; + } +} + + +class IXR_Client { + var $server; + var $port; + var $path; + var $useragent; + var $response; + var $message = false; + var $debug = false; + // Storage place for an error message + var $error = false; + function IXR_Client($server, $path = false, $port = 80) { + if (!$path) { + // Assume we have been given a URL instead + $bits = parse_url($server); + $this->server = $bits['host']; + $this->port = isset($bits['port']) ? $bits['port'] : 80; + $this->path = isset($bits['path']) ? $bits['path'] : '/'; + // Make absolutely sure we have a path + if (!$this->path) { + $this->path = '/'; + } + } else { + $this->server = $server; + $this->path = $path; + $this->port = $port; + } + $this->useragent = 'The Incutio XML-RPC PHP Library'; + } + function query() { + $args = func_get_args(); + $method = array_shift($args); + $request = new IXR_Request($method, $args); + $length = $request->getLength(); + $xml = $request->getXml(); + $r = "\r\n"; + $request = "POST {$this->path} HTTP/1.0$r"; + $request .= "Host: {$this->server}$r"; + $request .= "Content-Type: text/xml$r"; + $request .= "User-Agent: {$this->useragent}$r"; + $request .= "Content-length: {$length}$r$r"; + $request .= $xml; + // Now send the request + if ($this->debug) { + echo '
    '.htmlspecialchars($request)."\n
    \n\n"; + } + $fp = @fsockopen($this->server, $this->port); + if (!$fp) { + $this->error = new IXR_Error(-32300, 'transport error - could not open socket'); + return false; + } + fputs($fp, $request); + $contents = ''; + $gotFirstLine = false; + $gettingHeaders = true; + while (!feof($fp)) { + $line = fgets($fp, 4096); + if (!$gotFirstLine) { + // Check line for '200' + if (strstr($line, '200') === false) { + $this->error = new IXR_Error(-32300, 'transport error - HTTP status code was not 200'); + return false; + } + $gotFirstLine = true; + } + if (trim($line) == '') { + $gettingHeaders = false; + } + if (!$gettingHeaders) { + $contents .= trim($line)."\n"; + } + } + if ($this->debug) { + echo '
    '.htmlspecialchars($contents)."\n
    \n\n"; + } + // Now parse what we've got back + $this->message = new IXR_Message($contents); + if (!$this->message->parse()) { + // XML error + $this->error = new IXR_Error(-32700, 'parse error. not well formed'); + return false; + } + // Is the message a fault? + if ($this->message->messageType == 'fault') { + $this->error = new IXR_Error($this->message->faultCode, $this->message->faultString); + return false; + } + // Message must be OK + return true; + } + function getResponse() { + // methodResponses can only have one param - return that + return $this->message->params[0]; + } + function isError() { + return (is_object($this->error)); + } + function getErrorCode() { + return $this->error->code; + } + function getErrorMessage() { + return $this->error->message; + } +} + + +class IXR_Error { + var $code; + var $message; + function IXR_Error($code, $message) { + $this->code = $code; + $this->message = $message; + } + function getXml() { + $xml = << + + + + + faultCode + {$this->code} + + + faultString + {$this->message} + + + + + + +EOD; + return $xml; + } +} + + +class IXR_Date { + var $year; + var $month; + var $day; + var $hour; + var $minute; + var $second; + function IXR_Date($time) { + // $time can be a PHP timestamp or an ISO one + if (is_numeric($time)) { + $this->parseTimestamp($time); + } else { + $this->parseIso($time); + } + } + function parseTimestamp($timestamp) { + $this->year = date('Y', $timestamp); + $this->month = date('Y', $timestamp); + $this->day = date('Y', $timestamp); + $this->hour = date('H', $timestamp); + $this->minute = date('i', $timestamp); + $this->second = date('s', $timestamp); + } + function parseIso($iso) { + $this->year = substr($iso, 0, 4); + $this->month = substr($iso, 4, 2); + $this->day = substr($iso, 6, 2); + $this->hour = substr($iso, 9, 2); + $this->minute = substr($iso, 12, 2); + $this->second = substr($iso, 15, 2); + } + function getIso() { + return $this->year.$this->month.$this->day.'T'.$this->hour.':'.$this->minute.':'.$this->second; + } + function getXml() { + return ''.$this->getIso().''; + } + function getTimestamp() { + return mktime($this->hour, $this->minute, $this->second, $this->month, $this->day, $this->year); + } +} + + +class IXR_Base64 { + var $data; + function IXR_Base64($data) { + $this->data = $data; + } + function getXml() { + return ''.base64_encode($this->data).''; + } +} + + +class IXR_IntrospectionServer extends IXR_Server { + var $signatures; + var $help; + function IXR_IntrospectionServer() { + $this->setCallbacks(); + $this->setCapabilities(); + $this->capabilities['introspection'] = array( + 'specUrl' => 'http://xmlrpc.usefulinc.com/doc/reserved.html', + 'specVersion' => 1 + ); + $this->addCallback( + 'system.methodSignature', + 'this:methodSignature', + array('array', 'string'), + 'Returns an array describing the return type and required parameters of a method' + ); + $this->addCallback( + 'system.getCapabilities', + 'this:getCapabilities', + array('struct'), + 'Returns a struct describing the XML-RPC specifications supported by this server' + ); + $this->addCallback( + 'system.listMethods', + 'this:listMethods', + array('array'), + 'Returns an array of available methods on this server' + ); + $this->addCallback( + 'system.methodHelp', + 'this:methodHelp', + array('string', 'string'), + 'Returns a documentation string for the specified method' + ); + } + function addCallback($method, $callback, $args, $help) { + $this->callbacks[$method] = $callback; + $this->signatures[$method] = $args; + $this->help[$method] = $help; + } + function call($methodname, $args) { + // Make sure it's in an array + if ($args && !is_array($args)) { + $args = array($args); + } + // Over-rides default call method, adds signature check + if (!$this->hasMethod($methodname)) { + return new IXR_Error(-32601, 'server error. requested method "'.$this->message->methodName.'" not specified.'); + } + $method = $this->callbacks[$methodname]; + $signature = $this->signatures[$methodname]; + $returnType = array_shift($signature); + // Check the number of arguments + if (count($args) != count($signature)) { + // print 'Num of args: '.count($args).' Num in signature: '.count($signature); + return new IXR_Error(-32602, 'server error. wrong number of method parameters'); + } + // Check the argument types + $ok = true; + $argsbackup = $args; + for ($i = 0, $j = count($args); $i < $j; $i++) { + $arg = array_shift($args); + $type = array_shift($signature); + switch ($type) { + case 'int': + case 'i4': + if (is_array($arg) || !is_int($arg)) { + $ok = false; + } + break; + case 'base64': + case 'string': + if (!is_string($arg)) { + $ok = false; + } + break; + case 'boolean': + if ($arg !== false && $arg !== true) { + $ok = false; + } + break; + case 'float': + case 'double': + if (!is_float($arg)) { + $ok = false; + } + break; + case 'date': + case 'dateTime.iso8601': + if (!is_a($arg, 'IXR_Date')) { + $ok = false; + } + break; + } + if (!$ok) { + return new IXR_Error(-32602, 'server error. invalid method parameters'); + } + } + // It passed the test - run the "real" method call + return parent::call($methodname, $argsbackup); + } + function methodSignature($method) { + if (!$this->hasMethod($method)) { + return new IXR_Error(-32601, 'server error. requested method "'.$method.'" not specified.'); + } + // We should be returning an array of types + $types = $this->signatures[$method]; + $return = array(); + foreach ($types as $type) { + switch ($type) { + case 'string': + $return[] = 'string'; + break; + case 'int': + case 'i4': + $return[] = 42; + break; + case 'double': + $return[] = 3.1415; + break; + case 'dateTime.iso8601': + $return[] = new IXR_Date(time()); + break; + case 'boolean': + $return[] = true; + break; + case 'base64': + $return[] = new IXR_Base64('base64'); + break; + case 'array': + $return[] = array('array'); + break; + case 'struct': + $return[] = array('struct' => 'struct'); + break; + } + } + return $return; + } + function methodHelp($method) { + return $this->help[$method]; + } +} + + +class IXR_ClientMulticall extends IXR_Client { + var $calls = array(); + function IXR_ClientMulticall($server, $path = false, $port = 80) { + parent::IXR_Client($server, $path, $port); + $this->useragent = 'The Incutio XML-RPC PHP Library (multicall client)'; + } + function addCall() { + $args = func_get_args(); + $methodName = array_shift($args); + $struct = array( + 'methodName' => $methodName, + 'params' => $args + ); + $this->calls[] = $struct; + } + function query() { + // Prepare multicall, then call the parent::query() method + return parent::query('system.multicall', $this->calls); + } +} + +?> diff --git a/scripts/javascripts.js b/scripts/javascripts.js new file mode 100644 index 0000000..5c79bbc --- /dev/null +++ b/scripts/javascripts.js @@ -0,0 +1,332 @@ +// TODO: I'd like to have an extra "js" directory for all JavaScripts +// a theme needs. + +/* + * Jlogs not minified version of JavaScript + */ + +function jlog_bbcode(insText, aTag, eTag) { + if (!insText) { return ''; } + return aTag + insText + eTag; +} + +function jlog_bbcode_link(insText, aTag, eTag) { + var url = new RegExp('^(http://|https://|www.|ftp://|news:|mailto:).'); + var www = new RegExp('^(www.).'); + var mail = new RegExp('^[^@]+@[^@]+\.[a-zA-Z]+$'); + var http = new RegExp('^(http://)$'); + var node, href; + if((url.test(insText)) || (mail.test(insText))) { + href = insText; + if (mail.test(href)) { href = 'mailto:' + insText; } + if (www.test(href)) { href = 'http://' + href; } + node = prompt(jlog_l_comments_url_node); + if((node !== null) && (node !== '')) { insText = '[url=' + href + ']' + node + eTag; } + else if(node === '') { insText = aTag + href + eTag; } + } + else { + node = insText; + if(node === '') { node = prompt(jlog_l_comments_url_node, insText); } + href = prompt(jlog_l_comments_url_href, 'http://'); + if (http.test(href)) { return insText; } + if (www.test(href)) { href = 'http://' + href; } + if(((node !== null) && (node !== '')) && ((href !== null) && (href !== ''))) { + insText = '[url=' + href + ']' + node + eTag; + } + else if((href !== null) && (href !== '')) { insText = aTag + href + eTag; } + } + return insText; +} + + +function jlog_bbcode_list(o_insText, aTag, eTag) { + var insText = o_insText.replace(/(\n|\r|\r\n)(?=(.+))/g, '$1[*]'); + return '[list]\n[*]' + insText + eTag + '\n'; +} + +function jlog_bbcode_insert(aTag, eTag, completeText) { + var input = document.forms.entryform.elements.content; + input.focus(); + var insText; + /* für Internet Explorer und Opera >= 8 */ + if(typeof document.selection != 'undefined') { + /* Einfügen des Formatierungscodes */ + var range = document.selection.createRange(); + insText = range.text; + if (aTag === '[url]') { range.text = jlog_bbcode_link(insText, aTag, eTag); } + else if(eTag === '[/list]') { range.text = jlog_bbcode_list(insText, aTag, eTag); } + else { range.text = jlog_bbcode(insText, aTag, eTag); } + + /* Anpassen der Cursorposition */ + range = document.selection.createRange(); + if (insText.length === 0) { + range.move('character', -eTag.length); + } else { + range.moveStart('character', insText.length); + } + range.select(); + } + /* für neuere auf Gecko basierende Browser */ + else if(typeof input.selectionStart != 'undefined') + { + /* Einfügen des Formatierungscodes */ + var start = input.selectionStart; + var end = input.selectionEnd; + insText = input.value.substring(start, end); + if(aTag === '[url]') { insText = jlog_bbcode_link(insText, aTag, eTag); } + else if(eTag === '[/list]') { insText = jlog_bbcode_list(insText, aTag, eTag); } + else { insText = jlog_bbcode(insText, aTag, eTag); } + + input.value = input.value.substr(0, start) + insText + input.value.substr(end); + + /* Anpassen der Cursorposition */ + var pos; + if (insText.length === 0) { + pos = start + aTag.length + eTag.length; + } else { + pos = start + insText.length; + } + input.selectionStart = pos; + input.selectionEnd = pos; + } + /* für die übrigen Browser */ + else + { + /* Einfügen des Formatierungscodes */ + if(aTag === '[url]') { insText = jlog_bbcode_link('', aTag, eTag); } + else if(eTag === '[/list]') { insText = jlog_bbcode_list('', aTag, eTag); } + else { insText = jlog_bbcode(prompt(jlog_l_comments_plz_format_txt), aTag, eTag); } + input.value += insText; + } +} + +function jlog_bbcode_img(jfilename) { + var jclass = ''; + var jalt = ''; + if ( document.getElementById("class").value !== '') { + jclass = ' class=\"' + document.getElementById("class").value + '\"'; + } + if ( document.getElementById("alt").value !== '') { + jalt = ' alt=\"' + document.getElementById("alt").value + '\"'; + } + var jimg = '[img' + jclass + jalt + ']' + jfilename + '[/img]'; + opener.parent.jlog_insertAtCursor(jimg); + window.close(); +} + +// from http://www.alexking.org/blog/2003/06/02/inserting-at-the-cursor-using-javascript/ +function jlog_insertAtCursor(insText) { + //IE and Opera support + var field = document.forms.entryform.elements.content; + if (document.selection) { + field.focus(); + var sel = document.selection.createRange(); + sel.text = insText; + } + //MOZILLA/NETSCAPE support + else if (field.selectionStart || field.selectionStart == '0') { + var startPos = field.selectionStart; + var endPos = field.selectionEnd; + field.value = field.value.substring(0, startPos) + insText + field.value.substring(endPos, field.value.length); + } else { + field.value += insText; + } +} + +var show = true; + +function jlog_killcomments() { + + var commentslist = document.getElementById("commentslist"); + var pingbacks_header = document.getElementById("pingbacks"); + var pingbacks_list = document.getElementById("pingbackslist"); + + if (show) { + document.getElementById("hidecomments").firstChild.nodeValue = jlog_l_comments_show; + show=false; + if(pingbacks_header) { pingbacks_header.style.display = "none"; } + if(pingbacks_list) { pingbacks_list.style.display = "none"; } + document.getElementById("comments").style.display = "none"; + document.getElementById("entryform").style.display = "none"; + if(commentslist) { commentslist.style.display = "none"; } + } + else { + document.getElementById("hidecomments").firstChild.nodeValue = jlog_l_comments_hide; + show=true; + if(pingbacks_header) { pingbacks_header.style.display = "block"; } + if(pingbacks_list) { pingbacks_list.style.display = "block"; } + document.getElementById("comments").style.display = "block"; + document.getElementById("entryform").style.display = "block"; + if(commentslist) { commentslist.style.display = "block"; } + } +} + +var jlog_bbcode_br; + +function jlog_bbcode_do_button(titel, aTag, eTag) { + var button = document.createElement("input"); + button.onclick = function() { + jlog_bbcode_insert(aTag, eTag); + return false; + }; + button.className = "jlog_bbcode"; + button.type = "button"; + button.value = titel; + jlog_bbcode_br.parentNode.insertBefore(button, jlog_bbcode_br); +} + +/* from http://www.kryogenix.org/code/browser/searchhi/ */ +function jlog_highlightWord(node,word) { + + if (node.hasChildNodes) { + for (var hi_cn=0;hi_cn + * @author Stig Bakken + * @author Tomas V.V.Cox + * @author Greg Beaver + * @copyright 1997-2005 The PHP Group + * @license http://www.php.net/license/3_0.txt PHP License 3.0 + * @version CVS: $Id: PEAR.php,v 1.96 2005/09/21 00:12:35 cellog Exp $ + * @link http://pear.php.net/package/PEAR + * @since File available since Release 0.1 + */ + +define('PEAR_ERROR_RETURN', 1); +define('PEAR_ERROR_PRINT', 2); +define('PEAR_ERROR_TRIGGER', 4); +define('PEAR_ERROR_DIE', 8); +define('PEAR_ERROR_CALLBACK', 16); + +define('PEAR_ERROR_EXCEPTION', 32); + +define('PEAR_ZE2', (function_exists('version_compare') && + version_compare(zend_version(), "2-dev", "ge"))); + +if (substr(PHP_OS, 0, 3) == 'WIN') { + define('OS_WINDOWS', true); + define('OS_UNIX', false); + define('PEAR_OS', 'Windows'); +} else { + define('OS_WINDOWS', false); + define('OS_UNIX', true); + define('PEAR_OS', 'Unix'); // blatant assumption +} + +if (!defined('PATH_SEPARATOR')) { + if (OS_WINDOWS) { + define('PATH_SEPARATOR', ';'); + } else { + define('PATH_SEPARATOR', ':'); + } +} + +$GLOBALS['_PEAR_default_error_mode'] = PEAR_ERROR_RETURN; +$GLOBALS['_PEAR_default_error_options'] = E_USER_NOTICE; +$GLOBALS['_PEAR_destructor_object_list'] = array(); +$GLOBALS['_PEAR_shutdown_funcs'] = array(); +$GLOBALS['_PEAR_error_handler_stack'] = array(); + +@ini_set('track_errors', true); + +class PEAR +{ + + var $_debug = false; + var $_default_error_mode = null; + var $_default_error_options = null; + var $_default_error_handler = ''; + var $_error_class = 'PEAR_Error'; + var $_expected_errors = array(); + + function PEAR($error_class = null) + { + $classname = strtolower(get_class($this)); + if ($this->_debug) { + print "PEAR constructor called, class=$classname\n"; + } + if ($error_class !== null) { + $this->_error_class = $error_class; + } + while ($classname && strcasecmp($classname, "pear")) { + $destructor = "_$classname"; + if (method_exists($this, $destructor)) { + global $_PEAR_destructor_object_list; + $_PEAR_destructor_object_list[] = &$this; + if (!isset($GLOBALS['_PEAR_SHUTDOWN_REGISTERED'])) { + register_shutdown_function("_PEAR_call_destructors"); + $GLOBALS['_PEAR_SHUTDOWN_REGISTERED'] = true; + } + break; + } else { + $classname = get_parent_class($classname); + } + } + } + + function _PEAR() { + if ($this->_debug) { + printf("PEAR destructor called, class=%s\n", strtolower(get_class($this))); + } + } + + function &getStaticProperty($class, $var) + { + static $properties; + return $properties[$class][$var]; + } + + function registerShutdownFunc($func, $args = array()) + { + $GLOBALS['_PEAR_shutdown_funcs'][] = array($func, $args); + } + + function isError($data, $code = null) + { + if (is_a($data, 'PEAR_Error')) { + if (is_null($code)) { + return true; + } elseif (is_string($code)) { + return $data->getMessage() == $code; + } else { + return $data->getCode() == $code; + } + } + return false; + } + + function setErrorHandling($mode = null, $options = null) + { + if (isset($this) && is_a($this, 'PEAR')) { + $setmode = &$this->_default_error_mode; + $setoptions = &$this->_default_error_options; + } else { + $setmode = &$GLOBALS['_PEAR_default_error_mode']; + $setoptions = &$GLOBALS['_PEAR_default_error_options']; + } + + switch ($mode) { + case PEAR_ERROR_EXCEPTION: + case PEAR_ERROR_RETURN: + case PEAR_ERROR_PRINT: + case PEAR_ERROR_TRIGGER: + case PEAR_ERROR_DIE: + case null: + $setmode = $mode; + $setoptions = $options; + break; + + case PEAR_ERROR_CALLBACK: + $setmode = $mode; + // class/object method callback + if (is_callable($options)) { + $setoptions = $options; + } else { + trigger_error("invalid error callback", E_USER_WARNING); + } + break; + + default: + trigger_error("invalid error mode", E_USER_WARNING); + break; + } + } + + function expectError($code = '*') + { + if (is_array($code)) { + array_push($this->_expected_errors, $code); + } else { + array_push($this->_expected_errors, array($code)); + } + return sizeof($this->_expected_errors); + } + + function popExpect() + { + return array_pop($this->_expected_errors); + } + + function _checkDelExpect($error_code) + { + $deleted = false; + + foreach ($this->_expected_errors AS $key => $error_array) { + if (in_array($error_code, $error_array)) { + unset($this->_expected_errors[$key][array_search($error_code, $error_array)]); + $deleted = true; + } + + if (0 == count($this->_expected_errors[$key])) { + unset($this->_expected_errors[$key]); + } + } + return $deleted; + } + + function delExpect($error_code) + { + $deleted = false; + + if ((is_array($error_code) && (0 != count($error_code)))) { + foreach($error_code as $key => $error) { + if ($this->_checkDelExpect($error)) { + $deleted = true; + } else { + $deleted = false; + } + } + return $deleted ? true : PEAR::raiseError("The expected error you submitted does not exist"); // IMPROVE ME + } elseif (!empty($error_code)) { + if ($this->_checkDelExpect($error_code)) { + return true; + } else { + return PEAR::raiseError("The expected error you submitted does not exist"); // IMPROVE ME + } + } else { + return PEAR::raiseError("The expected error you submitted is empty"); // IMPROVE ME + } + } + + function &raiseError($message = null, + $code = null, + $mode = null, + $options = null, + $userinfo = null, + $error_class = null, + $skipmsg = false) + { + // The error is yet a PEAR error object + if (is_object($message)) { + $code = $message->getCode(); + $userinfo = $message->getUserInfo(); + $error_class = $message->getType(); + $message->error_message_prefix = ''; + $message = $message->getMessage(); + } + + if (isset($this) && isset($this->_expected_errors) && sizeof($this->_expected_errors) > 0 && sizeof($exp = end($this->_expected_errors))) { + if ($exp[0] == "*" || + (is_int(reset($exp)) && in_array($code, $exp)) || + (is_string(reset($exp)) && in_array($message, $exp))) { + $mode = PEAR_ERROR_RETURN; + } + } + if ($mode === null) { + if (isset($this) && isset($this->_default_error_mode)) { + $mode = $this->_default_error_mode; + $options = $this->_default_error_options; + } elseif (isset($GLOBALS['_PEAR_default_error_mode'])) { + $mode = $GLOBALS['_PEAR_default_error_mode']; + $options = $GLOBALS['_PEAR_default_error_options']; + } + } + + if ($error_class !== null) { + $ec = $error_class; + } elseif (isset($this) && isset($this->_error_class)) { + $ec = $this->_error_class; + } else { + $ec = 'PEAR_Error'; + } + if ($skipmsg) { + $a = &new $ec($code, $mode, $options, $userinfo); + return $a; + } else { + $a = &new $ec($message, $code, $mode, $options, $userinfo); + return $a; + } + } + + function &throwError($message = null, + $code = null, + $userinfo = null) + { + if (isset($this) && is_a($this, 'PEAR')) { + $a = &$this->raiseError($message, $code, null, null, $userinfo); + return $a; + } else { + $a = &PEAR::raiseError($message, $code, null, null, $userinfo); + return $a; + } + } + + function staticPushErrorHandling($mode, $options = null) + { + $stack = &$GLOBALS['_PEAR_error_handler_stack']; + $def_mode = &$GLOBALS['_PEAR_default_error_mode']; + $def_options = &$GLOBALS['_PEAR_default_error_options']; + $stack[] = array($def_mode, $def_options); + switch ($mode) { + case PEAR_ERROR_EXCEPTION: + case PEAR_ERROR_RETURN: + case PEAR_ERROR_PRINT: + case PEAR_ERROR_TRIGGER: + case PEAR_ERROR_DIE: + case null: + $def_mode = $mode; + $def_options = $options; + break; + + case PEAR_ERROR_CALLBACK: + $def_mode = $mode; + if (is_callable($options)) { + $def_options = $options; + } else { + trigger_error("invalid error callback", E_USER_WARNING); + } + break; + + default: + trigger_error("invalid error mode", E_USER_WARNING); + break; + } + $stack[] = array($mode, $options); + return true; + } + + function staticPopErrorHandling() + { + $stack = &$GLOBALS['_PEAR_error_handler_stack']; + $setmode = &$GLOBALS['_PEAR_default_error_mode']; + $setoptions = &$GLOBALS['_PEAR_default_error_options']; + array_pop($stack); + list($mode, $options) = $stack[sizeof($stack) - 1]; + array_pop($stack); + switch ($mode) { + case PEAR_ERROR_EXCEPTION: + case PEAR_ERROR_RETURN: + case PEAR_ERROR_PRINT: + case PEAR_ERROR_TRIGGER: + case PEAR_ERROR_DIE: + case null: + $setmode = $mode; + $setoptions = $options; + break; + + case PEAR_ERROR_CALLBACK: + $setmode = $mode; + // class/object method callback + if (is_callable($options)) { + $setoptions = $options; + } else { + trigger_error("invalid error callback", E_USER_WARNING); + } + break; + + default: + trigger_error("invalid error mode", E_USER_WARNING); + break; + } + return true; + } + + function pushErrorHandling($mode, $options = null) + { + $stack = &$GLOBALS['_PEAR_error_handler_stack']; + if (isset($this) && is_a($this, 'PEAR')) { + $def_mode = &$this->_default_error_mode; + $def_options = &$this->_default_error_options; + } else { + $def_mode = &$GLOBALS['_PEAR_default_error_mode']; + $def_options = &$GLOBALS['_PEAR_default_error_options']; + } + $stack[] = array($def_mode, $def_options); + + if (isset($this) && is_a($this, 'PEAR')) { + $this->setErrorHandling($mode, $options); + } else { + PEAR::setErrorHandling($mode, $options); + } + $stack[] = array($mode, $options); + return true; + } + + function popErrorHandling() + { + $stack = &$GLOBALS['_PEAR_error_handler_stack']; + array_pop($stack); + list($mode, $options) = $stack[sizeof($stack) - 1]; + array_pop($stack); + if (isset($this) && is_a($this, 'PEAR')) { + $this->setErrorHandling($mode, $options); + } else { + PEAR::setErrorHandling($mode, $options); + } + return true; + } + + function loadExtension($ext) + { + if (!extension_loaded($ext)) { + if ((ini_get('enable_dl') != 1) || (ini_get('safe_mode') == 1)) { + return false; + } + if (OS_WINDOWS) { + $suffix = '.dll'; + } elseif (PHP_OS == 'HP-UX') { + $suffix = '.sl'; + } elseif (PHP_OS == 'AIX') { + $suffix = '.a'; + } elseif (PHP_OS == 'OSX') { + $suffix = '.bundle'; + } else { + $suffix = '.so'; + } + return @dl('php_'.$ext.$suffix) || @dl($ext.$suffix); + } + return true; + } + +} + +function _PEAR_call_destructors() +{ + global $_PEAR_destructor_object_list; + if (is_array($_PEAR_destructor_object_list) && + sizeof($_PEAR_destructor_object_list)) + { + reset($_PEAR_destructor_object_list); + if (@PEAR::getStaticProperty('PEAR', 'destructlifo')) { + $_PEAR_destructor_object_list = array_reverse($_PEAR_destructor_object_list); + } + while (list($k, $objref) = each($_PEAR_destructor_object_list)) { + $classname = get_class($objref); + while ($classname) { + $destructor = "_$classname"; + if (method_exists($objref, $destructor)) { + $objref->$destructor(); + break; + } else { + $classname = get_parent_class($classname); + } + } + } + $_PEAR_destructor_object_list = array(); + } + + if (is_array($GLOBALS['_PEAR_shutdown_funcs']) AND !empty($GLOBALS['_PEAR_shutdown_funcs'])) { + foreach ($GLOBALS['_PEAR_shutdown_funcs'] as $value) { + call_user_func_array($value[0], $value[1]); + } + } +} + +class PEAR_Error +{ + + function PEAR_Error($message = 'unknown error', $code = null, + $mode = null, $options = null, $userinfo = null) + { + if ($mode === null) { + $mode = PEAR_ERROR_RETURN; + } + $this->message = $message; + $this->code = $code; + $this->mode = $mode; + $this->userinfo = $userinfo; + if (function_exists("debug_backtrace")) { + if (@!PEAR::getStaticProperty('PEAR_Error', 'skiptrace')) { + $this->backtrace = debug_backtrace(); + } + } + if ($mode & PEAR_ERROR_CALLBACK) { + $this->level = E_USER_NOTICE; + $this->callback = $options; + } else { + if ($options === null) { + $options = E_USER_NOTICE; + } + $this->level = $options; + $this->callback = null; + } + if ($this->mode & PEAR_ERROR_PRINT) { + if (is_null($options) || is_int($options)) { + $format = "%s"; + } else { + $format = $options; + } + printf($format, $this->getMessage()); + } + if ($this->mode & PEAR_ERROR_TRIGGER) { + trigger_error($this->getMessage(), $this->level); + } + if ($this->mode & PEAR_ERROR_DIE) { + $msg = $this->getMessage(); + if (is_null($options) || is_int($options)) { + $format = "%s"; + if (substr($msg, -1) != "\n") { + $msg .= "\n"; + } + } else { + $format = $options; + } + die(sprintf($format, $msg)); + } + if ($this->mode & PEAR_ERROR_CALLBACK) { + if (is_callable($this->callback)) { + call_user_func($this->callback, $this); + } + } + if ($this->mode & PEAR_ERROR_EXCEPTION) { + trigger_error("PEAR_ERROR_EXCEPTION is obsolete, use class PEAR_Exception for exceptions", E_USER_WARNING); + eval('$e = new Exception($this->message, $this->code);throw($e);'); + } + } + + function getMode() { + return $this->mode; + } + + function getCallback() { + return $this->callback; + } + + function getMessage() + { + return ($this->error_message_prefix . $this->message); + } + + function getCode() + { + return $this->code; + } + + function getType() + { + return get_class($this); + } + + function getUserInfo() + { + return $this->userinfo; + } + + function getDebugInfo() + { + return $this->getUserInfo(); + } + + function getBacktrace($frame = null) + { + if (defined('PEAR_IGNORE_BACKTRACE')) { + return null; + } + if ($frame === null) { + return $this->backtrace; + } + return $this->backtrace[$frame]; + } + + function addUserInfo($info) + { + if (empty($this->userinfo)) { + $this->userinfo = $info; + } else { + $this->userinfo .= " ** $info"; + } + } + + function toString() { + $modes = array(); + $levels = array(E_USER_NOTICE => 'notice', + E_USER_WARNING => 'warning', + E_USER_ERROR => 'error'); + if ($this->mode & PEAR_ERROR_CALLBACK) { + if (is_array($this->callback)) { + $callback = (is_object($this->callback[0]) ? + strtolower(get_class($this->callback[0])) : + $this->callback[0]) . '::' . + $this->callback[1]; + } else { + $callback = $this->callback; + } + return sprintf('[%s: message="%s" code=%d mode=callback '. + 'callback=%s prefix="%s" info="%s"]', + strtolower(get_class($this)), $this->message, $this->code, + $callback, $this->error_message_prefix, + $this->userinfo); + } + if ($this->mode & PEAR_ERROR_PRINT) { + $modes[] = 'print'; + } + if ($this->mode & PEAR_ERROR_TRIGGER) { + $modes[] = 'trigger'; + } + if ($this->mode & PEAR_ERROR_DIE) { + $modes[] = 'die'; + } + if ($this->mode & PEAR_ERROR_RETURN) { + $modes[] = 'return'; + } + return sprintf('[%s: message="%s" code=%d mode=%s level=%s '. + 'prefix="%s" info="%s"]', + strtolower(get_class($this)), $this->message, $this->code, + implode("|", $modes), $levels[$this->level], + $this->error_message_prefix, + $this->userinfo); + } + +} + +/** + * HTTP_Request.php code: + */ + +// +-----------------------------------------------------------------------+ +// | Copyright (c) 2002-2003, Richard Heyes | +// | All rights reserved. | +// +-----------------------------------------------------------------------+ + +define('HTTP_REQUEST_METHOD_GET', 'GET', true); +define('HTTP_REQUEST_METHOD_HEAD', 'HEAD', true); +define('HTTP_REQUEST_METHOD_POST', 'POST', true); +define('HTTP_REQUEST_METHOD_PUT', 'PUT', true); +define('HTTP_REQUEST_METHOD_DELETE', 'DELETE', true); +define('HTTP_REQUEST_METHOD_OPTIONS', 'OPTIONS', true); +define('HTTP_REQUEST_METHOD_TRACE', 'TRACE', true); + +define('HTTP_REQUEST_HTTP_VER_1_0', '1.0', true); +define('HTTP_REQUEST_HTTP_VER_1_1', '1.1', true); + +class HTTP_Request { + + var $_url; + var $_method; + var $_http; + var $_requestHeaders; + var $_user; + var $_pass; + var $_sock; + var $_proxy_host; + var $_proxy_port; + var $_proxy_user; + var $_proxy_pass; + var $_postData; + var $_body; + var $_bodyDisallowed = array('TRACE'); + var $_postFiles = array(); + var $_timeout; + var $_response; + var $_allowRedirects; + var $_maxRedirects; + var $_redirects; + var $_useBrackets = true; + var $_listeners = array(); + var $_saveBody = true; + var $_readTimeout = null; + var $_socketOptions = null; + + function HTTP_Request($url = '', $params = array()) + { + $this->_sock = &new Net_Socket(); + $this->_method = HTTP_REQUEST_METHOD_GET; + $this->_http = HTTP_REQUEST_HTTP_VER_1_1; + $this->_requestHeaders = array(); + $this->_postData = array(); + $this->_body = null; + + $this->_user = null; + $this->_pass = null; + + $this->_proxy_host = null; + $this->_proxy_port = null; + $this->_proxy_user = null; + $this->_proxy_pass = null; + + $this->_allowRedirects = false; + $this->_maxRedirects = 3; + $this->_redirects = 0; + + $this->_timeout = null; + $this->_response = null; + + foreach ($params as $key => $value) { + $this->{'_' . $key} = $value; + } + + if (!empty($url)) { + $this->setURL($url); + } + + $this->addHeader('User-Agent', 'PEAR HTTP_Request class ( http://pear.php.net/ )'); + + $this->addHeader('Connection', 'close'); + + if (!empty($this->_user)) { + $this->addHeader('Authorization', 'Basic ' . base64_encode($this->_user . ':' . $this->_pass)); + } + + if (HTTP_REQUEST_HTTP_VER_1_1 == $this->_http && extension_loaded('zlib') && + 0 == (2 & ini_get('mbstring.func_overload'))) { + + $this->addHeader('Accept-Encoding', 'gzip'); + } + } + + function _generateHostHeader() + { + if ($this->_url->port != 80 AND strcasecmp($this->_url->protocol, 'http') == 0) { + $host = $this->_url->host . ':' . $this->_url->port; + + } elseif ($this->_url->port != 443 AND strcasecmp($this->_url->protocol, 'https') == 0) { + $host = $this->_url->host . ':' . $this->_url->port; + + } elseif ($this->_url->port == 443 AND strcasecmp($this->_url->protocol, 'https') == 0 AND strpos($this->_url->url, ':443') !== false) { + $host = $this->_url->host . ':' . $this->_url->port; + + } else { + $host = $this->_url->host; + } + + return $host; + } + + function reset($url, $params = array()) + { + $this->HTTP_Request($url, $params); + } + + function setURL($url) + { + $this->_url = &new Net_URL($url, $this->_useBrackets); + + if (!empty($this->_url->user) || !empty($this->_url->pass)) { + $this->setBasicAuth($this->_url->user, $this->_url->pass); + } + + if (HTTP_REQUEST_HTTP_VER_1_1 == $this->_http) { + $this->addHeader('Host', $this->_generateHostHeader()); + } + } + + function setProxy($host, $port = 8080, $user = null, $pass = null) + { + $this->_proxy_host = $host; + $this->_proxy_port = $port; + $this->_proxy_user = $user; + $this->_proxy_pass = $pass; + + if (!empty($user)) { + $this->addHeader('Proxy-Authorization', 'Basic ' . base64_encode($user . ':' . $pass)); + } + } + + function setBasicAuth($user, $pass) + { + $this->_user = $user; + $this->_pass = $pass; + + $this->addHeader('Authorization', 'Basic ' . base64_encode($user . ':' . $pass)); + } + + function setMethod($method) + { + $this->_method = $method; + } + + function setHttpVer($http) + { + $this->_http = $http; + } + + function addHeader($name, $value) + { + $this->_requestHeaders[strtolower($name)] = $value; + } + + function removeHeader($name) + { + if (isset($this->_requestHeaders[strtolower($name)])) { + unset($this->_requestHeaders[strtolower($name)]); + } + } + + function addQueryString($name, $value, $preencoded = false) + { + $this->_url->addQueryString($name, $value, $preencoded); + } + + function addRawQueryString($querystring, $preencoded = true) + { + $this->_url->addRawQueryString($querystring, $preencoded); + } + + function addPostData($name, $value, $preencoded = false) + { + if ($preencoded) { + $this->_postData[$name] = $value; + } else { + $this->_postData[$name] = $this->_arrayMapRecursive('urlencode', $value); + } + } + + function _arrayMapRecursive($callback, $value) + { + if (!is_array($value)) { + return call_user_func($callback, $value); + } else { + $map = array(); + foreach ($value as $k => $v) { + $map[$k] = $this->_arrayMapRecursive($callback, $v); + } + return $map; + } + } + + function addFile($inputName, $fileName, $contentType = 'application/octet-stream') + { + if (!is_array($fileName) && !is_readable($fileName)) { + return PEAR::raiseError("File '{$fileName}' is not readable"); + } elseif (is_array($fileName)) { + foreach ($fileName as $name) { + if (!is_readable($name)) { + return PEAR::raiseError("File '{$name}' is not readable"); + } + } + } + $this->addHeader('Content-Type', 'multipart/form-data'); + $this->_postFiles[$inputName] = array( + 'name' => $fileName, + 'type' => $contentType + ); + return true; + } + + function addRawPostData($postdata, $preencoded = true) + { + $this->_body = $preencoded ? $postdata : urlencode($postdata); + } + + function setBody($body) + { + $this->_body = $body; + } + + function clearPostData() + { + $this->_postData = null; + } + + function addCookie($name, $value) + { + $cookies = isset($this->_requestHeaders['cookie']) ? $this->_requestHeaders['cookie']. '; ' : ''; + $this->addHeader('Cookie', $cookies . $name . '=' . $value); + } + + function clearCookies() + { + $this->removeHeader('Cookie'); + } + + function sendRequest($saveBody = true) + { + if (!is_a($this->_url, 'Net_URL')) { + return PEAR::raiseError('No URL given.'); + } + + $host = isset($this->_proxy_host) ? $this->_proxy_host : $this->_url->host; + $port = isset($this->_proxy_port) ? $this->_proxy_port : $this->_url->port; + + if (strcasecmp($this->_url->protocol, 'https') == 0 AND function_exists('file_get_contents') AND extension_loaded('openssl')) { + if (isset($this->_proxy_host)) { + return PEAR::raiseError('HTTPS proxies are not supported.'); + } + $host = 'ssl://' . $host; + } + + $magicQuotes = ini_get('magic_quotes_runtime'); + ini_set('magic_quotes_runtime', false); + + $err = $this->_sock->connect($host, $port, null, $this->_timeout, $this->_socketOptions); + PEAR::isError($err) or $err = $this->_sock->write($this->_buildRequest()); + + if (!PEAR::isError($err)) { + if (!empty($this->_readTimeout)) { + $this->_sock->setTimeout($this->_readTimeout[0], $this->_readTimeout[1]); + } + + $this->_notify('sentRequest'); + + $this->_response = &new HTTP_Response($this->_sock, $this->_listeners); + $err = $this->_response->process($this->_saveBody && $saveBody); + } + + ini_set('magic_quotes_runtime', $magicQuotes); + + if (PEAR::isError($err)) { + return $err; + } + + if ( $this->_allowRedirects + AND $this->_redirects <= $this->_maxRedirects + AND $this->getResponseCode() > 300 + AND $this->getResponseCode() < 399 + AND !empty($this->_response->_headers['location'])) { + + $redirect = $this->_response->_headers['location']; + + // Absolute URL + if (preg_match('/^https?:\/\//i', $redirect)) { + $this->_url = &new Net_URL($redirect); + $this->addHeader('Host', $this->_generateHostHeader()); + // Absolute path + } elseif ($redirect{0} == '/') { + $this->_url->path = $redirect; + + // Relative path + } elseif (substr($redirect, 0, 3) == '../' OR substr($redirect, 0, 2) == './') { + if (substr($this->_url->path, -1) == '/') { + $redirect = $this->_url->path . $redirect; + } else { + $redirect = dirname($this->_url->path) . '/' . $redirect; + } + $redirect = Net_URL::resolvePath($redirect); + $this->_url->path = $redirect; + + } else { + if (substr($this->_url->path, -1) == '/') { + $redirect = $this->_url->path . $redirect; + } else { + $redirect = dirname($this->_url->path) . '/' . $redirect; + } + $this->_url->path = $redirect; + } + + $this->_redirects++; + return $this->sendRequest($saveBody); + + } elseif ($this->_allowRedirects AND $this->_redirects > $this->_maxRedirects) { + return PEAR::raiseError('Too many redirects'); + } + + $this->_sock->disconnect(); + + return true; + } + + function getResponseCode() + { + return isset($this->_response->_code) ? $this->_response->_code : false; + } + + function getResponseHeader($headername = null) + { + if (!isset($headername)) { + return isset($this->_response->_headers)? $this->_response->_headers: array(); + } else { + $headername = strtolower($headername); + return isset($this->_response->_headers[$headername]) ? $this->_response->_headers[$headername] : false; + } + } + + function getResponseBody() + { + return isset($this->_response->_body) ? $this->_response->_body : false; + } + + function getResponseCookies() + { + return isset($this->_response->_cookies) ? $this->_response->_cookies : false; + } + + function _buildRequest() + { + $separator = ini_get('arg_separator.output'); + ini_set('arg_separator.output', '&'); + $querystring = ($querystring = $this->_url->getQueryString()) ? '?' . $querystring : ''; + ini_set('arg_separator.output', $separator); + + $host = isset($this->_proxy_host) ? $this->_url->protocol . '://' . $this->_url->host : ''; + $port = (isset($this->_proxy_host) AND $this->_url->port != 80) ? ':' . $this->_url->port : ''; + $path = (empty($this->_url->path)? '/': $this->_url->path) . $querystring; + $url = $host . $port . $path; + + $request = $this->_method . ' ' . $url . ' HTTP/' . $this->_http . "\r\n"; + + if (in_array($this->_method, $this->_bodyDisallowed) || + (HTTP_REQUEST_METHOD_POST != $this->_method && empty($this->_body)) || + (HTTP_REQUEST_METHOD_POST != $this->_method && empty($this->_postData) && empty($this->_postFiles))) { + + $this->removeHeader('Content-Type'); + } else { + if (empty($this->_requestHeaders['content-type'])) { + $this->addHeader('Content-Type', 'application/x-www-form-urlencoded'); + } elseif ('multipart/form-data' == $this->_requestHeaders['content-type']) { + $boundary = 'HTTP_Request_' . md5(uniqid('request') . microtime()); + $this->addHeader('Content-Type', 'multipart/form-data; boundary=' . $boundary); + } + } + + if (!empty($this->_requestHeaders)) { + foreach ($this->_requestHeaders as $name => $value) { + $canonicalName = implode('-', array_map('ucfirst', explode('-', $name))); + $request .= $canonicalName . ': ' . $value . "\r\n"; + } + } + + if (in_array($this->_method, $this->_bodyDisallowed) || + (HTTP_REQUEST_METHOD_POST != $this->_method && empty($this->_body))) { + + $request .= "\r\n"; + + } elseif (HTTP_REQUEST_METHOD_POST == $this->_method && + (!empty($this->_postData) || !empty($this->_postFiles))) { + + if (!isset($boundary)) { + $postdata = implode('&', array_map( + create_function('$a', 'return $a[0] . \'=\' . $a[1];'), + $this->_flattenArray('', $this->_postData) + )); + + } else { + $postdata = ''; + if (!empty($this->_postData)) { + $flatData = $this->_flattenArray('', $this->_postData); + foreach ($flatData as $item) { + $postdata .= '--' . $boundary . "\r\n"; + $postdata .= 'Content-Disposition: form-data; name="' . $item[0] . '"'; + $postdata .= "\r\n\r\n" . urldecode($item[1]) . "\r\n"; + } + } + foreach ($this->_postFiles as $name => $value) { + if (is_array($value['name'])) { + $varname = $name . ($this->_useBrackets? '[]': ''); + } else { + $varname = $name; + $value['name'] = array($value['name']); + } + foreach ($value['name'] as $key => $filename) { + $fp = fopen($filename, 'r'); + $data = fread($fp, filesize($filename)); + fclose($fp); + $basename = basename($filename); + $type = is_array($value['type'])? @$value['type'][$key]: $value['type']; + + $postdata .= '--' . $boundary . "\r\n"; + $postdata .= 'Content-Disposition: form-data; name="' . $varname . '"; filename="' . $basename . '"'; + $postdata .= "\r\nContent-Type: " . $type; + $postdata .= "\r\n\r\n" . $data . "\r\n"; + } + } + $postdata .= '--' . $boundary . "--\r\n"; + } + $request .= 'Content-Length: ' . strlen($postdata) . "\r\n\r\n"; + $request .= $postdata; + + // Explicitly set request body + } elseif (!empty($this->_body)) { + + $request .= 'Content-Length: ' . strlen($this->_body) . "\r\n\r\n"; + $request .= $this->_body; + } + + return $request; + } + + function _flattenArray($name, $values) + { + if (!is_array($values)) { + return array(array($name, $values)); + } else { + $ret = array(); + foreach ($values as $k => $v) { + if (empty($name)) { + $newName = $k; + } elseif ($this->_useBrackets) { + $newName = $name . '[' . $k . ']'; + } else { + $newName = $name; + } + $ret = array_merge($ret, $this->_flattenArray($newName, $v)); + } + return $ret; + } + } + + function attach(&$listener) + { + if (!is_a($listener, 'HTTP_Request_Listener')) { + return false; + } + $this->_listeners[$listener->getId()] =& $listener; + return true; + } + + function detach(&$listener) + { + if (!is_a($listener, 'HTTP_Request_Listener') || + !isset($this->_listeners[$listener->getId()])) { + return false; + } + unset($this->_listeners[$listener->getId()]); + return true; + } + + function _notify($event, $data = null) + { + foreach (array_keys($this->_listeners) as $id) { + $this->_listeners[$id]->update($this, $event, $data); + } + } +} + +class HTTP_Response +{ + + var $_sock; + var $_protocol; + var $_code; + var $_headers; + var $_cookies; + var $_body = ''; + var $_chunkLength = 0; + var $_listeners = array(); + function HTTP_Response(&$sock, &$listeners) + { + $this->_sock =& $sock; + $this->_listeners =& $listeners; + } + + function process($saveBody = true) + { + do { + $line = $this->_sock->readLine(); + if (sscanf($line, 'HTTP/%s %s', $http_version, $returncode) != 2) { + return PEAR::raiseError('Malformed response.'); + } else { + $this->_protocol = 'HTTP/' . $http_version; + $this->_code = intval($returncode); + } + while ('' !== ($header = $this->_sock->readLine())) { + $this->_processHeader($header); + } + } while (100 == $this->_code); + + $this->_notify('gotHeaders', $this->_headers); + + $chunked = isset($this->_headers['transfer-encoding']) && ('chunked' == $this->_headers['transfer-encoding']); + $gzipped = isset($this->_headers['content-encoding']) && ('gzip' == $this->_headers['content-encoding']); + $hasBody = false; + if (!isset($this->_headers['content-length']) || 0 != $this->_headers['content-length']) { + while (!$this->_sock->eof()) { + if ($chunked) { + $data = $this->_readChunked(); + } else { + $data = $this->_sock->read(4096); + } + if ('' == $data) { + break; + } else { + $hasBody = true; + if ($saveBody || $gzipped) { + $this->_body .= $data; + } + $this->_notify($gzipped? 'gzTick': 'tick', $data); + } + } + } + if ($hasBody) { + if ($gzipped) { + $this->_body = gzinflate(substr($this->_body, 10)); + $this->_notify('gotBody', $this->_body); + } else { + $this->_notify('gotBody'); + } + } + return true; + } + + function _processHeader($header) + { + list($headername, $headervalue) = explode(':', $header, 2); + $headername = strtolower($headername); + $headervalue = ltrim($headervalue); + + if ('set-cookie' != $headername) { + if (isset($this->_headers[$headername])) { + $this->_headers[$headername] .= ',' . $headervalue; + } else { + $this->_headers[$headername] = $headervalue; + } + } else { + $this->_parseCookie($headervalue); + } + } + + function _parseCookie($headervalue) + { + $cookie = array( + 'expires' => null, + 'domain' => null, + 'path' => null, + 'secure' => false + ); + + if (!strpos($headervalue, ';')) { + $pos = strpos($headervalue, '='); + $cookie['name'] = trim(substr($headervalue, 0, $pos)); + $cookie['value'] = trim(substr($headervalue, $pos + 1)); + + } else { + $elements = explode(';', $headervalue); + $pos = strpos($elements[0], '='); + $cookie['name'] = trim(substr($elements[0], 0, $pos)); + $cookie['value'] = trim(substr($elements[0], $pos + 1)); + + for ($i = 1; $i < count($elements); $i++) { + if (false === strpos($elements[$i], '=')) { + $elName = trim($elements[$i]); + $elValue = null; + } else { + list ($elName, $elValue) = array_map('trim', explode('=', $elements[$i])); + } + $elName = strtolower($elName); + if ('secure' == $elName) { + $cookie['secure'] = true; + } elseif ('expires' == $elName) { + $cookie['expires'] = str_replace('"', '', $elValue); + } elseif ('path' == $elName || 'domain' == $elName) { + $cookie[$elName] = urldecode($elValue); + } else { + $cookie[$elName] = $elValue; + } + } + } + $this->_cookies[] = $cookie; + } + + function _readChunked() + { + if (0 == $this->_chunkLength) { + $line = $this->_sock->readLine(); + if (preg_match('/^([0-9a-f]+)/i', $line, $matches)) { + $this->_chunkLength = hexdec($matches[1]); + if (0 == $this->_chunkLength) { + $this->_sock->readLine(); + return ''; + } + } else { + return ''; + } + } + $data = $this->_sock->read($this->_chunkLength); + $this->_chunkLength -= strlen($data); + if (0 == $this->_chunkLength) { + $this->_sock->readLine(); + } + return $data; + } + + function _notify($event, $data = null) + { + foreach (array_keys($this->_listeners) as $id) { + $this->_listeners[$id]->update($this, $event, $data); + } + } +} + +/** + * Socket.php + */ + +// +----------------------------------------------------------------------+ +// | PHP Version 4 | +// +----------------------------------------------------------------------+ +// | Copyright (c) 1997-2003 The PHP Group | +// +----------------------------------------------------------------------+ +// | This source file is subject to version 2.0 of the PHP license, | +// | that is bundled with this package in the file LICENSE, and is | +// | available at through the world-wide-web at | +// | http://www.php.net/license/2_02.txt. | +// | If you did not receive a copy of the PHP license and are unable to | +// | obtain it through the world-wide-web, please send a note to | +// | license@php.net so we can mail you a copy immediately. | +// +----------------------------------------------------------------------+ +// | Authors: Stig Bakken | +// | Chuck Hagenbuch | +// +----------------------------------------------------------------------+ +// +// $Id: Socket.php,v 1.24 2005/02/03 20:40:16 chagenbu Exp $ + + +define('NET_SOCKET_READ', 1); +define('NET_SOCKET_WRITE', 2); +define('NET_SOCKET_ERROR', 3); + +class Net_Socket extends PEAR { + + var $fp = null; + var $blocking = true; + var $persistent = false; + var $addr = ''; + var $port = 0; + var $timeout = false; + var $lineLength = 2048; + + function connect($addr, $port = 0, $persistent = null, $timeout = null, $options = null) + { + if (is_resource($this->fp)) { + @fclose($this->fp); + $this->fp = null; + } + + if (!$addr) { + return $this->raiseError('$addr cannot be empty'); + } elseif (strspn($addr, '.0123456789') == strlen($addr) || + strstr($addr, '/') !== false) { + $this->addr = $addr; + } else { + $this->addr = @gethostbyname($addr); + } + + $this->port = $port % 65536; + + if ($persistent !== null) { + $this->persistent = $persistent; + } + + if ($timeout !== null) { + $this->timeout = $timeout; + } + + $openfunc = $this->persistent ? 'pfsockopen' : 'fsockopen'; + $errno = 0; + $errstr = ''; + if ($options && function_exists('stream_context_create')) { + if ($this->timeout) { + $timeout = $this->timeout; + } else { + $timeout = 0; + } + $context = stream_context_create($options); + $fp = @$openfunc($this->addr, $this->port, $errno, $errstr, $timeout, $context); + } else { + if ($this->timeout) { + $fp = @$openfunc($this->addr, $this->port, $errno, $errstr, $this->timeout); + } else { + $fp = @$openfunc($this->addr, $this->port, $errno, $errstr); + } + } + + if (!$fp) { + return $this->raiseError($errstr, $errno); + } + + $this->fp = $fp; + + return $this->setBlocking($this->blocking); + } + + function disconnect() + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + @fclose($this->fp); + $this->fp = null; + return true; + } + + function isBlocking() + { + return $this->blocking; + } + + function setBlocking($mode) + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + $this->blocking = $mode; + socket_set_blocking($this->fp, $this->blocking); + return true; + } + + function setTimeout($seconds, $microseconds) + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + return socket_set_timeout($this->fp, $seconds, $microseconds); + } + + function getStatus() + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + return socket_get_status($this->fp); + } + + function gets($size) + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + return @fgets($this->fp, $size); + } + + function read($size) + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + return @fread($this->fp, $size); + } + + function write($data, $blocksize = null) + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + if (is_null($blocksize) && !OS_WINDOWS) { + return fwrite($this->fp, $data); + } else { + if (is_null($blocksize)) { + $blocksize = 1024; + } + + $pos = 0; + $size = strlen($data); + while ($pos < $size) { + $written = @fwrite($this->fp, substr($data, $pos, $blocksize)); + if ($written === false) { + return false; + } + $pos += $written; + } + + return $pos; + } + } + + function writeLine($data) + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + return fwrite($this->fp, $data . "\r\n"); + } + + function eof() + { + return (is_resource($this->fp) && feof($this->fp)); + } + + function readByte() + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + return ord(@fread($this->fp, 1)); + } + + function readWord() + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + $buf = @fread($this->fp, 2); + return (ord($buf[0]) + (ord($buf[1]) << 8)); + } + + function readInt() + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + $buf = @fread($this->fp, 4); + return (ord($buf[0]) + (ord($buf[1]) << 8) + + (ord($buf[2]) << 16) + (ord($buf[3]) << 24)); + } + + function readString() + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + $string = ''; + while (($char = @fread($this->fp, 1)) != "\x00") { + $string .= $char; + } + return $string; + } + + function readIPAddress() + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + $buf = @fread($this->fp, 4); + return sprintf("%s.%s.%s.%s", ord($buf[0]), ord($buf[1]), + ord($buf[2]), ord($buf[3])); + } + + function readLine() + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + $line = ''; + $timeout = time() + $this->timeout; + while (!feof($this->fp) && (!$this->timeout || time() < $timeout)) { + $line .= @fgets($this->fp, $this->lineLength); + if (substr($line, -1) == "\n") { + return rtrim($line, "\r\n"); + } + } + return $line; + } + + function readAll() + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + $data = ''; + while (!feof($this->fp)) { + $data .= @fread($this->fp, $this->lineLength); + } + return $data; + } + + function select($state, $tv_sec, $tv_usec = 0) + { + if (!is_resource($this->fp)) { + return $this->raiseError('not connected'); + } + + $read = null; + $write = null; + $except = null; + if ($state & NET_SOCKET_READ) { + $read[] = $this->fp; + } + if ($state & NET_SOCKET_WRITE) { + $write[] = $this->fp; + } + if ($state & NET_SOCKET_ERROR) { + $except[] = $this->fp; + } + if (false === ($sr = stream_select($read, $write, $except, $tv_sec, $tv_usec))) { + return false; + } + + $result = 0; + if (count($read)) { + $result |= NET_SOCKET_READ; + } + if (count($write)) { + $result |= NET_SOCKET_WRITE; + } + if (count($except)) { + $result |= NET_SOCKET_ERROR; + } + return $result; + } + +} + +/** + * URL.php + */ +// +-----------------------------------------------------------------------+ +// | Copyright (c) 2002-2004, Richard Heyes | +// | All rights reserved. | +// +-----------------------------------------------------------------------+ +// $Id: URL.php,v 1.36 2004/06/19 18:58:50 richard Exp $ + +class Net_URL +{ + + var $url; + var $protocol; + var $username; + var $password; + var $host; + var $port; + var $path; + var $querystring; + var $anchor; + var $useBrackets; + function Net_URL($url = null, $useBrackets = true) + { + $this->__construct($url, $useBrackets); + } + + function __construct($url = null, $useBrackets = true) + { + $HTTP_SERVER_VARS = !empty($_SERVER) ? $_SERVER : $GLOBALS['HTTP_SERVER_VARS']; + + $this->useBrackets = $useBrackets; + $this->url = $url; + $this->user = ''; + $this->pass = ''; + $this->host = ''; + $this->port = 80; + $this->path = ''; + $this->querystring = array(); + $this->anchor = ''; + + if (!preg_match('/^[a-z0-9]+:\/\//i', $url)) { + + $this->protocol = (@$HTTP_SERVER_VARS['HTTPS'] == 'on' ? 'https' : 'http'); + + if (!empty($HTTP_SERVER_VARS['HTTP_HOST']) AND preg_match('/^(.*)(:([0-9]+))?$/U', $HTTP_SERVER_VARS['HTTP_HOST'], $matches)) { + $host = $matches[1]; + if (!empty($matches[3])) { + $port = $matches[3]; + } else { + $port = $this->getStandardPort($this->protocol); + } + } + + $this->user = ''; + $this->pass = ''; + $this->host = !empty($host) ? $host : (isset($HTTP_SERVER_VARS['SERVER_NAME']) ? $HTTP_SERVER_VARS['SERVER_NAME'] : 'localhost'); + $this->port = !empty($port) ? $port : (isset($HTTP_SERVER_VARS['SERVER_PORT']) ? $HTTP_SERVER_VARS['SERVER_PORT'] : $this->getStandardPort($this->protocol)); + $this->path = !empty($HTTP_SERVER_VARS['SCRIPT_NAME']) ? $HTTP_SERVER_VARS['SCRIPT_NAME'] : '/'; + $this->querystring = isset($HTTP_SERVER_VARS['QUERY_STRING']) ? $this->_parseRawQuerystring($HTTP_SERVER_VARS['QUERY_STRING']) : null; + $this->anchor = ''; + } + + if (!empty($url)) { + $urlinfo = parse_url($url); + + $this->querystring = array(); + + foreach ($urlinfo as $key => $value) { + switch ($key) { + case 'scheme': + $this->protocol = $value; + $this->port = $this->getStandardPort($value); + break; + + case 'user': + case 'pass': + case 'host': + case 'port': + $this->$key = $value; + break; + + case 'path': + if ($value{0} == '/') { + $this->path = $value; + } else { + $path = dirname($this->path) == DIRECTORY_SEPARATOR ? '' : dirname($this->path); + $this->path = sprintf('%s/%s', $path, $value); + } + break; + + case 'query': + $this->querystring = $this->_parseRawQueryString($value); + break; + + case 'fragment': + $this->anchor = $value; + break; + } + } + } + } + + function getURL() + { + $querystring = $this->getQueryString(); + + $this->url = $this->protocol . '://' + . $this->user . (!empty($this->pass) ? ':' : '') + . $this->pass . (!empty($this->user) ? '@' : '') + . $this->host . ($this->port == $this->getStandardPort($this->protocol) ? '' : ':' . $this->port) + . $this->path + . (!empty($querystring) ? '?' . $querystring : '') + . (!empty($this->anchor) ? '#' . $this->anchor : ''); + + return $this->url; + } + + function addQueryString($name, $value, $preencoded = false) + { + if ($preencoded) { + $this->querystring[$name] = $value; + } else { + $this->querystring[$name] = is_array($value) ? array_map('rawurlencode', $value): rawurlencode($value); + } + } + + function removeQueryString($name) + { + if (isset($this->querystring[$name])) { + unset($this->querystring[$name]); + } + } + + function addRawQueryString($querystring) + { + $this->querystring = $this->_parseRawQueryString($querystring); + } + + function getQueryString() + { + if (!empty($this->querystring)) { + foreach ($this->querystring as $name => $value) { + if (is_array($value)) { + foreach ($value as $k => $v) { + $querystring[] = $this->useBrackets ? sprintf('%s[%s]=%s', $name, $k, $v) : ($name . '=' . $v); + } + } elseif (!is_null($value)) { + $querystring[] = $name . '=' . $value; + } else { + $querystring[] = $name; + } + } + $querystring = implode(ini_get('arg_separator.output'), $querystring); + } else { + $querystring = ''; + } + + return $querystring; + } + + function _parseRawQuerystring($querystring) + { + $parts = preg_split('/[' . preg_quote(ini_get('arg_separator.input'), '/') . ']/', $querystring, -1, PREG_SPLIT_NO_EMPTY); + $return = array(); + + foreach ($parts as $part) { + if (strpos($part, '=') !== false) { + $value = substr($part, strpos($part, '=') + 1); + $key = substr($part, 0, strpos($part, '=')); + } else { + $value = null; + $key = $part; + } + if (substr($key, -2) == '[]') { + $key = substr($key, 0, -2); + if (@!is_array($return[$key])) { + $return[$key] = array(); + $return[$key][] = $value; + } else { + $return[$key][] = $value; + } + } elseif (!$this->useBrackets AND !empty($return[$key])) { + $return[$key] = (array)$return[$key]; + $return[$key][] = $value; + } else { + $return[$key] = $value; + } + } + + return $return; + } + + function resolvePath($path) + { + $path = explode('/', str_replace('//', '/', $path)); + + for ($i=0; $i 1 OR ($i == 1 AND $path[0] != '') ) ) { + unset($path[$i]); + unset($path[$i-1]); + $path = array_values($path); + $i -= 2; + + } elseif ($path[$i] == '..' AND $i == 1 AND $path[0] == '') { + unset($path[$i]); + $path = array_values($path); + $i--; + + } else { + continue; + } + } + + return implode('/', $path); + } + + function getStandardPort($scheme) + { + switch (strtolower($scheme)) { + case 'http': return 80; + case 'https': return 443; + case 'ftp': return 21; + case 'imap': return 143; + case 'imaps': return 993; + case 'pop3': return 110; + case 'pop3s': return 995; + default: return null; + } + } + + function setProtocol($protocol, $port = null) + { + $this->protocol = $protocol; + $this->port = is_null($port) ? $this->getStandardPort() : $port; + } + +} + + +?> diff --git a/scripts/jlogPlugins.class.php b/scripts/jlogPlugins.class.php new file mode 100644 index 0000000..578f87c --- /dev/null +++ b/scripts/jlogPlugins.class.php @@ -0,0 +1,83 @@ +get = strip($_GET); + + if(is_dir($plugindirectory)) { + $handle = opendir($plugindirectory); + while( false !== ( $file = readdir ($handle) ) ) { + if(substr($file, -10) === '.jplug.php') { + include_once $plugindirectory.$file; + $this->register( substr($file, 0, -10) ); + } + } + closedir($handle); + + } + } + + function register($plugin) { + $this->plugins[] = new $plugin; + } + + // Aufruf $JLogPluginManagerInstanz->callHook('eins', $param1[, $param2, ...]); + // $param1 = Pflicht-Parameter, alle anderen optional + function callHook($hook) { + $hook = 'hook_' . $hook; + + $parameters = func_get_args(); + array_shift($parameters); // $hook entfernen + if (!isset($parameters[0])) + die('fatal error - no parameters'); + + $hookresult = $parameters[0]; + + foreach ($this->plugins as $plugin) { + $parameters[0] = $hookresult; + if($hook == 'hook_adminTitle' OR $hook == 'hook_adminContent') { + if(strtolower($this->get['jplug']) === strtolower(get_class($plugin))) + $hookresult = call_user_func_array(array($plugin, $hook), $parameters); + } + else $hookresult = call_user_func_array(array($plugin, $hook), $parameters); + } + return $hookresult; + } +} +?> diff --git a/scripts/mail.class.php b/scripts/mail.class.php new file mode 100644 index 0000000..f673538 --- /dev/null +++ b/scripts/mail.class.php @@ -0,0 +1,279 @@ +_from = 'no-reply@' . $_SERVER['SERVER_NAME']; + $this->_subject = 'Kein Betreff - No Subject'; + $this->addHeader('MIME-Version', '1.0'); + $this->addHeader('Content-Type', 'text/plain; charset=UTF-8'); + $this->addHeader('Content-Transfer-Encoding', '8bit'); + $this->addHeader('X-Mailer', 'Jlog with PHP ' . phpversion()); + } + + /** + * setFrom() - sets from value + * + * @access public + * @param string $email + * @param string $name + * @return void + */ + function setFrom($email, $name) + { + if (!empty($email) and !empty($name)) { + $this->_from = "$name <$email>"; + } + } + + /** + * getFrom() - gets from value + * + * @access public + * @return string + */ + function getFrom() + { + return $this->_from; + } + + /** + * setSubject() - sets subject + * + * @access public + * @param string $text + * @return void + */ + function setSubject($text) + { + if (strlen($text) > 0) { + $this->_subject = $text; + } + } + + /** + * getSubject() - gets subject + * + * @access public + * @return string + */ + function getSubject() + { + return $this->_subject; + } + + /** + * setText() - sets content of email + * + * @access public + * @param string $text + * @return void + */ + function setText($text) + { + $this->_text = $text; + } + + /** + * appendText() - appends content to the email + * + * @access public + * @param string $text + * @return void + */ + function appendText($text) + { + $this->_text .= $text; + } + + /** + * getText() - gets content of email + * + * @access public + * @return string + */ + function getText() + { + return $this->_text; + } + + /** + * addHeader() - adds an additional header + * + * Adds a header, by replacing any earlier headers of the same name. + * If no value is passed, the key is interpreted as a header line and + * split into key and value. + * + * @access public + * @param string $key + * @param string $value + * @return void + */ + function addHeader($key, $value = null) + { + if ($value === null) { + $data = explode(':', $key, 1); + if (count($data) !== 2) return false; + $key = $data[0]; + $value = $data[1]; + } + if (strlen($key) < 1 or strlen($value) < 1) return false; + $this->_header[$key] = $value; + } + + /** + * unsetHeader() - deletes a header + * + * @access public + * @param string $key + * @return void + */ + function unsetHeader($key) + { + if (isset($this->_header[$key])) unset($this->_header[$key]); + } + + /** + * getHeader() - gets a header + * + * @access public + * @return string|null + */ + function getHeader($key) + { + if (isset($this->_header[$key])) return $this->_header[$key]; + return null; + } + + /** + * getHeaders() - gets all headers + * + * @access public + * @return array + */ + function getHeaders() + { + return $this->_header; + } + + /** + * getCleanHeaderString() - gets sanitized header string + * + * @access public + * @return string + */ + function getCleanHeaderString() + { + $headers = ''; + foreach ($this->_header as $key => $value) { + // remove all non alpha-numeric chars, except for dash + $key = preg_replace('/[^a-zA-Z0-9-]/', '', $key); + // remove line breaks to prevent header injection + $value = str_replace(array("\r", "\n"), '', $value); + // add header + $headers .= "$key: $value\r\n"; + } + return $headers; + } + + /** + * dropMail() - sets drop mail flag + * + * Sets a flag that causes the send() method to skip sending this + * email, so that this mail is actualy dropped. + * + * @access public + * @return void + */ + function dropMail() + { + $this->_dropped = true; + } + + /** + * send() - sends mail + * + * @access public + * @param string $to + * @return boolean + */ + function send($to) + { + if ($this->_dropped) return false; + + $this->addHeader('From', $this->_from); + + $safe_mode = strtolower(ini_get('safe_mode')); + if ($safe_mode == 1 or $safe_mode == 'on' or $safe_mode == 'yes') { + @mail($to, $this->_subject, $this->_text, $this->getCleanHeaderString()); + } + else { + @mail($to, $this->_subject, $this->_text, $this->getCleanHeaderString(), "-f".JLOG_EMAIL); + } + return true; + } +} + +// eof diff --git a/scripts/prepend.inc.php b/scripts/prepend.inc.php new file mode 100644 index 0000000..dcf0280 --- /dev/null +++ b/scripts/prepend.inc.php @@ -0,0 +1,91 @@ +".$l['db_error']."
    ".$l['plz_try_again']."."); +} +// select our database +$select = @mysql_select_db(JLOG_DB); +if ($connect == FALSE) { + mail(JLOG_EMAIL, $l['admin']['e_db'], $l['admin']['e_db_is']."\n".mysql_error()); + die("".$l['db_error']."
    ".$l['plz_try_again']."."); +} +// do some settings +@mysql_query("SET NAMES utf8"); +@mysql_query("SET sql_mode=''"); + +// some more code that needs to run for every page - however, this +// code requires an established connection to the database +setlocale(LC_TIME, $l['locale']); +require_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'categories.class.php'); +require_once(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'jlogPlugins.class.php'); +$plugins = new JlogPluginManager(JLOG_BASEPATH.'plugins'.DIRECTORY_SEPARATOR); + +// call hooks for bbcode plugins +$bbcode = $plugins->callHook('bbcode', $bbcode); +$bbcomments = $plugins->callHook('bbcomments', $bbcomments); + +// eof \ No newline at end of file diff --git a/scripts/settings.class.php b/scripts/settings.class.php new file mode 100644 index 0000000..5eed38f --- /dev/null +++ b/scripts/settings.class.php @@ -0,0 +1,533 @@ +l = $l; + } + + /** + * getValue() - reads configuration data + * + * This procedure returns the value for then configuration option + * specified by $key or an array of all options if $key is not + * specified or false + * + * @access public + * @param string|boolean $key + * @return mixed + */ + function getValue($key = false) { + if($key === false) return $this->d; + else return $this->d[strtolower($key)]; + } + + /** + * setValue() - sets configuration data + * + * @access public + * @param string|boolean $key + * @param mixed $value + * @return mixed + */ + function setValue($key, $value) { + $this->d[strtolower($key)] = $value; + } + + /** + * importDataByConstants() + * + * imports data from global constats starting with JLOG_ prefix + * + * @access public + * @return void + */ + function importDataByConstants() { + # no return + // this is a blacklist of constats which are not to be written in settings.inc.php + $search = array( + 'JLOG_ADMIN', + 'JLOG_DB_CONTENT', + 'JLOG_DB_COMMENTS', + 'JLOG_DB_CATASSIGN', + 'JLOG_DB_CATEGORIES', + 'JLOG_DB_ATTRIBUTES', + 'JLOG_UPDATE', + 'JLOG_LOGIN', + 'JLOG_SOFTWARE_VERSION', + 'JLOG_SOFTWARE_URL', + 'JLOG_SOFTWARE_PHPV', + 'JLOG_SOFTWARE_MYSQLV', + 'JLOG_ADMIN_PASSWORD_AGAIN' + ); + + // get all needed constants and put it into the class + $constants = get_defined_constants(); + foreach($constants as $key => $value) { + if(!in_array($key, $search) AND strpos($key, "JLOG_") !== false) { + $this->setValue($key, $value); + } + } + } + + /** + * importDataByArray() - sets configuration data + * + * Sets configuration data according to $d. If working in + * non-exclusive mode (the default), $d is merged into the current + * configuration, otherwise the current configuration is discared + * and $d is set as the new configuration. + * + * @access public + * @param array $d + * @param boolean $exclusiv + * @return void + */ + function importDataByArray($d = false, $exclusiv = false) { + + // get the data from users $d array and put it into the class + if($d !== false) { + if($exclusiv) $this->d = $d; + else $this->d = array_merge($this->d, $d); + } + + if(JLOG_ADMIN === true) { + $this->d['jlog_db'] = JLOG_DB; + $this->d['jlog_db_url'] = JLOG_DB_URL; + $this->d['jlog_db_user'] = JLOG_DB_USER; + $this->d['jlog_db_pwd'] = JLOG_DB_PWD; + $this->d['jlog_db_prefix'] = JLOG_DB_PREFIX; + $this->d['jlog_start_year'] = JLOG_START_YEAR; + $this->d['jlog_path'] = JLOG_PATH; + $this->d['jlog_basepath'] = JLOG_BASEPATH; + if($this->d['jlog_admin_password'] == '') { + $this->jlog_admin_password = JLOG_ADMIN_PASSWORD; + } + else { + $this->d['jlog_admin_password'] = md5($this->d['jlog_admin_password']); + $this->d['jlog_admin_password_again'] = md5($this->d['jlog_admin_password_again']); + } + $this->d['jlog_installed_version'] = JLOG_INSTALLED_VERSION; + $this->d['jlog_installed_url'] = JLOG_INSTALLED_URL; + $this->d['jlog_installed_phpv'] = JLOG_INSTALLED_PHPV; + $this->d['jlog_installed_mysqlv'] = JLOG_INSTALLED_MYSQLV; + } + else { + $this->d['jlog_admin_password'] = md5($this->d['jlog_admin_password']); + $this->d['jlog_admin_password_again'] = md5($this->d['jlog_admin_password_again']); + } + + if((defined('JLOG_SETUP') AND JLOG_SETUP === true)) + { + $this->d['jlog_installed_version'] = JLOG_SOFTWARE_VERSION; + $this->d['jlog_installed_url'] = JLOG_SOFTWARE_URL; + $this->d['jlog_installed_phpv'] = JLOG_SOFTWARE_PHPV; + $this->d['jlog_installed_mysqlv'] = JLOG_SOFTWARE_MYSQLV; + } + } + + /** + * importSuggestedData() - preallocates configuration data + * + * Initialises the configuration with useful settings during + * the installation process. + * + * @access public + * @return void + */ + function importSuggestedData() { + // suggest some data for setup + $this->setValue('jlog_path', $this->getSuggestPath()); + $this->setValue('jlog_basepath', dirname(dirname( __FILE__ )).DIRECTORY_SEPARATOR); + $date = getdate(); + $this->setValue('jlog_start_year', $date['year']); + $this->setValue('jlog_max_blog_orginal', 1); + $this->setValue('jlog_max_blog_big', 4); + $this->setValue('jlog_max_blog_small', 15); + $this->setValue('jlog_sub_current', 6); + $this->setValue('jlog_date', $this->l['date_format']); + $this->setValue('jlog_date_comment', $this->l['date_format_comment']); + $this->setValue('jlog_date_subcurrent', $this->l['date_format_subcurrent']); + $this->setValue('jlog_info_by_comment', true); + $this->setValue('jlog_db_url', 'localhost'); + $this->setValue('jlog_db_prefix', 'jlog_'); + $this->setValue('jlog_blogservices', 'http://rpc.pingomatic.com/'); + $this->setValue('jlog_language', (defined('JLOG_LANGUAGE') ? JLOG_LANGUAGE : 'de')); + } + + + /** + * getSuggestPath() - generate a suggestion for JLOG_PATH + * + * @access private + * @return string + */ + function getSuggestPath() { + $host = empty($_SERVER['HTTP_HOST']) + ? (empty($_SERVER['SERVER_NAME']) + ? $_SERVER['SERVER_ADDR'] + : $_SERVER['SERVER_NAME']) + : $_SERVER['HTTP_HOST']; + $proto = (empty($_SERVER['HTTPS']) OR $_SERVER['HTTPS'] == 'off') + ? 'http' + : 'https'; + $port = $_SERVER['SERVER_PORT']; + + $uri = $proto . '://' . $host; + if ((('http' == $proto) and (80 != $port)) + or (('https' == $proto) and (443 != $port))) + { + $uri .= ':' . $port; + } + $uri .= dirname($_SERVER['SCRIPT_NAME']); + + return $uri; + } + + /** + * defaultValue() - gets a value of an array + * + * Look for index $key in the array $array and return + * the corresponding value if it exists or the default + * value $default if it doesn't. + * + * @access public + * @param array $array + * @param mixed $key + * @param mixed $default + * @return mixed + */ + function defaultValue($array, $key, $default = '') { + if(isset($array[$key])) { + return $array[$key]; + } + else { + return $default; + } + } + + /** + * form_output() - generates HTML output for formular + * + * @access public + * @return string + */ + function form_output() { + # returns the filled form + + $data = array_htmlspecialchars($this->d); + + if(isset($data['jlog_clean_url']) AND ($data['jlog_clean_url'] === 'true' OR $data['jlog_clean_url'] === '1')) + $d['clean_url_yes'] = " checked='checked'"; + else $d['clean_url_no'] = " checked='checked'"; + + if(isset($data['jlog_info_by_comment'])) $d['info_by_comment'] = " checked='checked'"; + else $d['info_by_comment'] = ""; + + if(isset($data['jlog_bs_weblogs_com']) AND ($data['jlog_bs_weblogs_com'] === 'true' OR $data['jlog_bs_weblogs_com'] === '1')) + $d['bs_weblogs_com'] = " checked='checked' "; + + if(defined("JLOG_ADMIN") AND JLOG_ADMIN === true) $admincenter_password = " ".$this->l['admin']['m_admin_password_admin']; + else $admincenter_password = ''; + + // get available languages + $dir = opendir(dirname(__FILE__).DIRECTORY_SEPARATOR.'..'.DIRECTORY_SEPARATOR.'lang'); + $languages = array(); + while(($file = readdir($dir)) !== false) { + if($file == '.' OR $file == '..') continue; + if(!preg_match('/lang\.([a-zA-z0-9]+)\.inc\.php/', $file, $matches)) continue; + $languages[] = $matches[1]; + } + + // do the form + $form = " +
    +
    ".$this->l['admin']['m_metadata']." +


    "; + + if(defined("JLOG_ADMIN") AND JLOG_ADMIN === true) $form .= add_session_id_input_tag(); + + $form .= "

    +


    +

    +


    +

    +


    +

    +


    +

    +


    +

    +
    + +
    ".$this->l['admin']['m_behavior']." +


    + +

    +


    +

    +


    +

    +


    +

    +


    +

    +

    +

    +

    +

    +

    +

    +

    +
    + "; + + if(defined('JLOG_SETUP') AND JLOG_SETUP === true) { + $form .= + " +
    ".$this->l['admin']['m_database']." +


    +

    +


    +

    +


    +

    +


    +

    +


    + +

    + + +
    + "; + } + + $form .= " +

    +
    + "; + + return $form; + } + + /** + * validate() - validates the current configuration + * + * If the current configuration is valid, an empty array is returned. + * Otherwise the returned array containes all errors, described in the + * current language. + * + * @access public + * @return array + */ + function validate() { + # if everything validate then return true + # otherwise return the $errors array + + $errors = array(); + + // paths + if(empty($this->d['jlog_path']) OR (check_url($this->d['jlog_path'], array ('http')) === false)) $errors[] = $this->l['admin']['e_path']; + if(empty($this->d['jlog_basepath']) OR !is_dir($this->d['jlog_basepath'])) $errors[] = $this->l['admin']['e_basepath']; + if($this->d['jlog_clean_url'] != 'true') $this->d['jlog_clean_url'] = 'false'; + // metadata + if(empty($this->d['jlog_website'])) $errors[] = $this->l['admin']['e_website']; + if(empty($this->d['jlog_publisher'])) $errors[] = $this->l['admin']['e_publisher']; + if(defined('JLOG_SETUP') AND JLOG_SETUP) { + if($this->d['jlog_admin_password'] == md5("")) + $errors[] = $this->l['admin']['e_admin_password']; + elseif($this->d['jlog_admin_password'] !== $this->d['jlog_admin_password_again']) + $errors[] = $this->l['admin']['e_admin_password_again']; + } + elseif(!empty($this->d['jlog_admin_password']) AND $this->d['jlog_admin_password'] !== $this->d['jlog_admin_password_again']) { + $errors[] = $this->l['admin']['e_admin_password_again']; + } + // Fix of bug #148 + if(isset($this->d['jlog_admin_password_again'])) + unset($this->d['jlog_admin_password_again']); + + if(empty($this->d['jlog_email']) OR !strpos($this->d['jlog_email'], '@')) $errors[] = $this->l['admin']['e_email']; + if(empty($this->d['jlog_description'])) $errors[] = $this->l['admin']['e_description']; + // behavour + if(!is_numeric($this->d['jlog_max_blog_orginal']) OR intval($this->d['jlog_max_blog_orginal']) < 0) $errors[] = $this->l['admin']['e_max_blog_orginal']; + if(!is_numeric($this->d['jlog_max_blog_big']) OR intval($this->d['jlog_max_blog_big']) < 0) $errors[] = $this->l['admin']['e_max_blog_big']; + if(!is_numeric($this->d['jlog_max_blog_small']) OR intval($this->d['jlog_max_blog_small']) < 0) $errors[] = $this->l['admin']['e_max_blog_small']; + if(!is_numeric($this->d['jlog_sub_current']) OR intval($this->d['jlog_sub_current']) < 0) $errors[] = $this->l['admin']['e_sub_current']; + if(!is_numeric($this->d['jlog_start_year'])) $errors[] = $this->l['admin']['e_start_year']; + if($this->d['jlog_info_by_comment'] != 'true') $this->d['jlog_info_by_comment'] = 'false'; + // database + if(empty($this->d['jlog_db'])) $errors[] = $this->l['admin']['e_db']; + if(empty($this->d['jlog_db_url'])) $errors[] = $this->l['admin']['e_db_url']; + // Fix of bug #196, prefix should only contain alphanumeric values, can be empty! + if(!preg_match('/^[a-zA-Z0-9_]*$/', $this->d['jlog_db_prefix'])) $errors[] = $this->l['admin']['e_db_prefix']; + + return $errors; + } + + /** + * do_settings() - save configuration + * + * Saves the current configuration to the settings.inc.php file + * in the personal folder. Return an empty array if configuration + * was saved successfully, or an array containing descriptions of + * the errors that occured otherwise. + * + * @access public + * @return array + */ + function do_settings() { + # if it's all done return true + # otherwise return the $errors array + + $errors = array(); + + // if there is no new password set the old + if(JLOG_ADMIN AND empty($this->d['jlog_admin_password'])) $this->d['jlog_admin_password'] = JLOG_ADMIN_PASSWORD; + + // remove slashes at the end of JLOG_PATH if present + $this->d['jlog_path'] = rtrim($this->d['jlog_path'], '/'); + // make shure JLOG_BASEPATH ends with a slash!! + $this->d['jlog_basepath'] = rtrim($this->d['jlog_basepath'], '/\\') . DIRECTORY_SEPARATOR; + + // no quotes for bolean and numbers + $no_quotes = array ( + 'jlog_clean_url' => 'bool', + 'jlog_max_blog_orginal' => 'int', + 'jlog_max_blog_big' => 'int', + 'jlog_max_blog_small' => 'int', + 'jlog_sub_current' => 'int', + 'jlog_start_year' => 'int', + 'jlog_info_by_comment' => 'bool' + ); + + // serialize data to file format + $file_content = 'd as $key => $value) { + $output = ''; + if(isset($no_quotes[$key])) { + // boolean values + if($no_quotes[$key] == 'bool') { + if($value == 'true' OR $value === true) $output = 'true'; + else $output = 'false'; + } + // numeric values + else { + $output = (int) $value; + } + } + // string values + else { + $output = '\'' . $this->escapeForPhp($value) . '\''; + } + $key = '\'' . $this->escapeForPhp(strtoupper($key)) . '\''; + $file_content .= 'define(' . $key . ', ' . $output . ');' . PHP_EOL; + } + + $file_content .= '// eof'; + + // write to settings.inc.php + if(!$handle = fopen(JLOG_BASEPATH."personal".DIRECTORY_SEPARATOR."settings.inc.php", "w")) $errors[] = $this->l['admin']['can_not_open']." /personal/settings.inc.php"; + if(!fwrite($handle, $file_content)) $errors[] = $this->l['admin']['can_not_write']." /personal/settings.inc.php"; + fclose($handle); + + return $errors; + } + + /** + * escapeForPhp() + * + * escapes $value so that it can be used between single quotes in a + * PHP script, single quotes are better than double qoutes, as therein no + * further substituions are performed + * + * @access public + * @param string $value + * @return string + */ + function escapeForPhp($value) { + $value = str_replace('\\', '\\\\', $value); + $value = str_replace("'", "\'", $value); + $value = str_replace("\0", '', $value); + $value = str_replace("\r\n", "'.chr(13).chr(10).'", $value); + $value = str_replace("\r", "'.chr(13).'", $value); + $value = str_replace("\n", "'.chr(10).'", $value); + return $value; + } +} + +// eof \ No newline at end of file diff --git a/scripts/stringparser.class.php b/scripts/stringparser.class.php new file mode 100644 index 0000000..3f48ffa --- /dev/null +++ b/scripts/stringparser.class.php @@ -0,0 +1,1544 @@ + + * @copyright Christian Seiler 2004-2008 + * @package stringparser + * + * The MIT License + * + * Copyright (c) 2004-2009 Christian Seiler + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +/** + * String parser mode: Search for the next character + * @see StringParser::_parserMode + */ +define ('STRINGPARSER_MODE_SEARCH', 1); +/** + * String parser mode: Look at each character of the string + * @see StringParser::_parserMode + */ +define ('STRINGPARSER_MODE_LOOP', 2); +/** + * Filter type: Prefilter + * @see StringParser::addFilter, StringParser::_prefilters + */ +define ('STRINGPARSER_FILTER_PRE', 1); +/** + * Filter type: Postfilter + * @see StringParser::addFilter, StringParser::_postfilters + */ +define ('STRINGPARSER_FILTER_POST', 2); + +/** + * Generic string parser class + * + * This is an abstract class for any type of string parser. + * + * @package stringparser + */ +class StringParser { + /** + * String parser mode + * + * There are two possible modes: searchmode and loop mode. In loop mode + * every single character is looked at in a loop and it is then decided + * what action to take. This is the most straight-forward approach to + * string parsing but due to the nature of PHP as a scripting language, + * it can also cost performance. In search mode the class posseses a + * list of relevant characters for parsing and uses the + * {@link PHP_MANUAL#strpos strpos} function to search for the next + * relevant character. The search mode will be faster than the loop mode + * in most circumstances but it is also more difficult to implement. + * The subclass that does the string parsing itself will define which + * mode it will implement. + * + * @access protected + * @var int + * @see STRINGPARSER_MODE_SEARCH, STRINGPARSER_MODE_LOOP + */ + var $_parserMode = STRINGPARSER_MODE_SEARCH; + + /** + * Raw text + * @access protected + * @var string + */ + var $_text = ''; + + /** + * Parse stack + * @access protected + * @var array + */ + var $_stack = array (); + + /** + * Current position in raw text + * @access protected + * @var integer + */ + var $_cpos = -1; + + /** + * Root node + * @access protected + * @var mixed + */ + var $_root = null; + + /** + * Length of the text + * @access protected + * @var integer + */ + var $_length = -1; + + /** + * Flag if this object is already parsing a text + * + * This flag is to prevent recursive calls to the parse() function that + * would cause very nasty things. + * + * @access protected + * @var boolean + */ + var $_parsing = false; + + /** + * Strict mode + * + * Whether to stop parsing if a parse error occurs. + * + * @access public + * @var boolean + */ + var $strict = false; + + /** + * Characters or strings to look for + * @access protected + * @var array + */ + var $_charactersSearch = array (); + + /** + * Characters currently allowed + * + * Note that this will only be evaluated in loop mode; in search mode + * this would ruin every performance increase. Note that only single + * characters are permitted here, no strings. Please also note that in + * loop mode, {@link StringParser::_charactersSearch _charactersSearch} + * is evaluated before this variable. + * + * If in strict mode, parsing is stopped if a character that is not + * allowed is encountered. If not in strict mode, the character is + * simply ignored. + * + * @access protected + * @var array + */ + var $_charactersAllowed = array (); + + /** + * Current parser status + * @access protected + * @var int + */ + var $_status = 0; + + /** + * Prefilters + * @access protected + * @var array + */ + var $_prefilters = array (); + + /** + * Postfilters + * @access protected + * @var array + */ + var $_postfilters = array (); + + /** + * Recently reparsed? + * @access protected + * @var bool + */ + var $_recentlyReparsed = false; + + /** + * Constructor + * + * @access public + */ + function StringParser () { + } + + /** + * Add a filter + * + * @access public + * @param int $type The type of the filter + * @param mixed $callback The callback to call + * @return bool + * @see STRINGPARSER_FILTER_PRE, STRINGPARSER_FILTER_POST + */ + function addFilter ($type, $callback) { + // make sure the function is callable + if (!is_callable ($callback)) { + return false; + } + + switch ($type) { + case STRINGPARSER_FILTER_PRE: + $this->_prefilters[] = $callback; + break; + case STRINGPARSER_FILTER_POST: + $this->_postfilters[] = $callback; + break; + default: + return false; + } + + return true; + } + + /** + * Remove all filters + * + * @access public + * @param int $type The type of the filter or 0 for all + * @return bool + * @see STRINGPARSER_FILTER_PRE, STRINGPARSER_FILTER_POST + */ + function clearFilters ($type = 0) { + switch ($type) { + case 0: + $this->_prefilters = array (); + $this->_postfilters = array (); + break; + case STRINGPARSER_FILTER_PRE: + $this->_prefilters = array (); + break; + case STRINGPARSER_FILTER_POST: + $this->_postfilters = array (); + break; + default: + return false; + } + return true; + } + + /** + * This function parses the text + * + * @access public + * @param string $text The text to parse + * @return mixed Either the root object of the tree if no output method + * is defined, the tree reoutput to e.g. a string or false + * if an internal error occured, such as a parse error if + * in strict mode or the object is already parsing a text. + */ + function parse ($text) { + if ($this->_parsing) { + return false; + } + $this->_parsing = true; + $this->_text = $this->_applyPrefilters ($text); + $this->_output = null; + $this->_length = strlen ($this->_text); + $this->_cpos = 0; + unset ($this->_stack); + $this->_stack = array (); + if (is_object ($this->_root)) { + StringParser_Node::destroyNode ($this->_root); + } + unset ($this->_root); + $this->_root =& new StringParser_Node_Root (); + $this->_stack[0] =& $this->_root; + + $this->_parserInit (); + + $finished = false; + + while (!$finished) { + switch ($this->_parserMode) { + case STRINGPARSER_MODE_SEARCH: + $res = $this->_searchLoop (); + if (!$res) { + $this->_parsing = false; + return false; + } + break; + case STRINGPARSER_MODE_LOOP: + $res = $this->_loop (); + if (!$res) { + $this->_parsing = false; + return false; + } + break; + default: + $this->_parsing = false; + return false; + } + + $res = $this->_closeRemainingBlocks (); + if (!$res) { + if ($this->strict) { + $this->_parsing = false; + return false; + } else { + $res = $this->_reparseAfterCurrentBlock (); + if (!$res) { + $this->_parsing = false; + return false; + } + continue; + } + } + $finished = true; + } + + $res = $this->_modifyTree (); + + if (!$res) { + $this->_parsing = false; + return false; + } + + $res = $this->_outputTree (); + + if (!$res) { + $this->_parsing = false; + return false; + } + + if (is_null ($this->_output)) { + $root =& $this->_root; + unset ($this->_root); + $this->_root = null; + while (count ($this->_stack)) { + unset ($this->_stack[count($this->_stack)-1]); + } + $this->_stack = array (); + $this->_parsing = false; + return $root; + } + + $res = StringParser_Node::destroyNode ($this->_root); + if (!$res) { + $this->_parsing = false; + return false; + } + unset ($this->_root); + $this->_root = null; + while (count ($this->_stack)) { + unset ($this->_stack[count($this->_stack)-1]); + } + $this->_stack = array (); + + $this->_parsing = false; + return $this->_output; + } + + /** + * Apply prefilters + * + * It is possible to specify prefilters for the parser to do some + * manipulating of the string beforehand. + */ + function _applyPrefilters ($text) { + foreach ($this->_prefilters as $filter) { + if (is_callable ($filter)) { + $ntext = call_user_func ($filter, $text); + if (is_string ($ntext)) { + $text = $ntext; + } + } + } + return $text; + } + + /** + * Apply postfilters + * + * It is possible to specify postfilters for the parser to do some + * manipulating of the string afterwards. + */ + function _applyPostfilters ($text) { + foreach ($this->_postfilters as $filter) { + if (is_callable ($filter)) { + $ntext = call_user_func ($filter, $text); + if (is_string ($ntext)) { + $text = $ntext; + } + } + } + return $text; + } + + /** + * Abstract method: Manipulate the tree + * @access protected + * @return bool + */ + function _modifyTree () { + return true; + } + + /** + * Abstract method: Output tree + * @access protected + * @return bool + */ + function _outputTree () { + // this could e.g. call _applyPostfilters + return true; + } + + /** + * Restart parsing after current block + * + * To achieve this the current top stack object is removed from the + * tree. Then the current item + * + * @access protected + * @return bool + */ + function _reparseAfterCurrentBlock () { + // this should definitely not happen! + if (($stack_count = count ($this->_stack)) < 2) { + return false; + } + $topelem =& $this->_stack[$stack_count-1]; + + $node_parent =& $topelem->_parent; + // remove the child from the tree + $res = $node_parent->removeChild ($topelem, false); + if (!$res) { + return false; + } + $res = $this->_popNode (); + if (!$res) { + return false; + } + + // now try to get the position of the object + if ($topelem->occurredAt < 0) { + return false; + } + // HACK: could it be necessary to set a different status + // if yes, how should this be achieved? Another member of + // StringParser_Node? + $this->_setStatus (0); + $res = $this->_appendText ($this->_text{$topelem->occurredAt}); + if (!$res) { + return false; + } + + $this->_cpos = $topelem->occurredAt + 1; + $this->_recentlyReparsed = true; + + return true; + } + + /** + * Abstract method: Close remaining blocks + * @access protected + */ + function _closeRemainingBlocks () { + // everything closed + if (count ($this->_stack) == 1) { + return true; + } + // not everything closed + if ($this->strict) { + return false; + } + while (count ($this->_stack) > 1) { + $res = $this->_popNode (); + if (!$res) { + return false; + } + } + return true; + } + + /** + * Abstract method: Initialize the parser + * @access protected + */ + function _parserInit () { + $this->_setStatus (0); + } + + /** + * Abstract method: Set a specific status + * @access protected + */ + function _setStatus ($status) { + if ($status != 0) { + return false; + } + $this->_charactersSearch = array (); + $this->_charactersAllowed = array (); + $this->_status = $status; + return true; + } + + /** + * Abstract method: Handle status + * @access protected + * @param int $status The current status + * @param string $needle The needle that was found + * @return bool + */ + function _handleStatus ($status, $needle) { + $this->_appendText ($needle); + $this->_cpos += strlen ($needle); + return true; + } + + /** + * Search mode loop + * @access protected + * @return bool + */ + function _searchLoop () { + $i = 0; + while (1) { + // make sure this is false! + $this->_recentlyReparsed = false; + + list ($needle, $offset) = $this->_strpos ($this->_charactersSearch, $this->_cpos); + // parser ends here + if ($needle === false) { + // original status 0 => no problem + if (!$this->_status) { + break; + } + // not in original status? strict mode? + if ($this->strict) { + return false; + } + // break up parsing operation of current node + $res = $this->_reparseAfterCurrentBlock (); + if (!$res) { + return false; + } + continue; + } + // get subtext + $subtext = substr ($this->_text, $this->_cpos, $offset - $this->_cpos); + $res = $this->_appendText ($subtext); + if (!$res) { + return false; + } + $this->_cpos = $offset; + $res = $this->_handleStatus ($this->_status, $needle); + if (!$res && $this->strict) { + return false; + } + if (!$res) { + $res = $this->_appendText ($this->_text{$this->_cpos}); + if (!$res) { + return false; + } + $this->_cpos++; + continue; + } + if ($this->_recentlyReparsed) { + $this->_recentlyReparsed = false; + continue; + } + $this->_cpos += strlen ($needle); + } + + // get subtext + if ($this->_cpos < strlen ($this->_text)) { + $subtext = substr ($this->_text, $this->_cpos); + $res = $this->_appendText ($subtext); + if (!$res) { + return false; + } + } + + return true; + } + + /** + * Loop mode loop + * + * @access protected + * @return bool + */ + function _loop () { + // HACK: This method ist not yet implemented correctly, the code below + // DOES NOT WORK! Do not use! + + return false; + /* + while ($this->_cpos < $this->_length) { + $needle = $this->_strDetect ($this->_charactersSearch, $this->_cpos); + + if ($needle === false) { + // not found => see if character is allowed + if (!in_array ($this->_text{$this->_cpos}, $this->_charactersAllowed)) { + if ($strict) { + return false; + } + // ignore + continue; + } + // lot's of FIXMES + $res = $this->_appendText ($this->_text{$this->_cpos}); + if (!$res) { + return false; + } + } + + // get subtext + $subtext = substr ($this->_text, $offset, $offset - $this->_cpos); + $res = $this->_appendText ($subtext); + if (!$res) { + return false; + } + $this->_cpos = $subtext; + $res = $this->_handleStatus ($this->_status, $needle); + if (!$res && $strict) { + return false; + } + } + // original status 0 => no problem + if (!$this->_status) { + return true; + } + // not in original status? strict mode? + if ($this->strict) { + return false; + } + // break up parsing operation of current node + $res = $this->_reparseAfterCurrentBlock (); + if (!$res) { + return false; + } + // this will not cause an infinite loop because + // _reparseAfterCurrentBlock will increase _cpos by one! + return $this->_loop (); + */ + } + + /** + * Abstract method Append text depending on current status + * @access protected + * @param string $text The text to append + * @return bool On success, the function returns true, else false + */ + function _appendText ($text) { + if (!strlen ($text)) { + return true; + } + // default: call _appendToLastTextChild + return $this->_appendToLastTextChild ($text); + } + + /** + * Append text to last text child of current top parser stack node + * @access protected + * @param string $text The text to append + * @return bool On success, the function returns true, else false + */ + function _appendToLastTextChild ($text) { + $scount = count ($this->_stack); + if ($scount == 0) { + return false; + } + return $this->_stack[$scount-1]->appendToLastTextChild ($text); + } + + /** + * Searches {@link StringParser::_text _text} for every needle that is + * specified by using the {@link PHP_MANUAL#strpos strpos} function. It + * returns an associative array with the key 'needle' + * pointing at the string that was found first and the key + * 'offset' pointing at the offset at which the string was + * found first. If no needle was found, the 'needle' + * element is false and the 'offset' element + * is -1. + * + * @access protected + * @param array $needles + * @param int $offset + * @return array + * @see StringParser::_text + */ + function _strpos ($needles, $offset) { + $cur_needle = false; + $cur_offset = -1; + + if ($offset < strlen ($this->_text)) { + foreach ($needles as $needle) { + $n_offset = strpos ($this->_text, $needle, $offset); + if ($n_offset !== false && ($n_offset < $cur_offset || $cur_offset < 0)) { + $cur_needle = $needle; + $cur_offset = $n_offset; + } + } + } + + return array ($cur_needle, $cur_offset, 'needle' => $cur_needle, 'offset' => $cur_offset); + } + + /** + * Detects a string at the current position + * + * @access protected + * @param array $needles The strings that are to be detected + * @param int $offset The current offset + * @return mixed The string that was detected or the needle + */ + function _strDetect ($needles, $offset) { + foreach ($needles as $needle) { + $l = strlen ($needle); + if (substr ($this->_text, $offset, $l) == $needle) { + return $needle; + } + } + return false; + } + + + /** + * Adds a node to the current parse stack + * + * @access protected + * @param object $node The node that is to be added + * @return bool True on success, else false. + * @see StringParser_Node, StringParser::_stack + */ + function _pushNode (&$node) { + $stack_count = count ($this->_stack); + $max_node =& $this->_stack[$stack_count-1]; + if (!$max_node->appendChild ($node)) { + return false; + } + $this->_stack[$stack_count] =& $node; + return true; + } + + /** + * Removes a node from the current parse stack + * + * @access protected + * @return bool True on success, else false. + * @see StringParser_Node, StringParser::_stack + */ + function _popNode () { + $stack_count = count ($this->_stack); + unset ($this->_stack[$stack_count-1]); + return true; + } + + /** + * Execute a method on the top element + * + * @access protected + * @return mixed + */ + function _topNode () { + $args = func_get_args (); + if (!count ($args)) { + return; // oops? + } + $method = array_shift ($args); + $stack_count = count ($this->_stack); + $method = array (&$this->_stack[$stack_count-1], $method); + if (!is_callable ($method)) { + return; // oops? + } + return call_user_func_array ($method, $args); + } + + /** + * Get a variable of the top element + * + * @access protected + * @return mixed + */ + function _topNodeVar ($var) { + $stack_count = count ($this->_stack); + return $this->_stack[$stack_count-1]->$var; + } +} + +/** + * Node type: Unknown node + * @see StringParser_Node::_type + */ +define ('STRINGPARSER_NODE_UNKNOWN', 0); + +/** + * Node type: Root node + * @see StringParser_Node::_type + */ +define ('STRINGPARSER_NODE_ROOT', 1); + +/** + * Node type: Text node + * @see StringParser_Node::_type + */ +define ('STRINGPARSER_NODE_TEXT', 2); + +/** + * Global value that is a counter of string parser node ids. Compare it to a + * sequence in databases. + * @var int + */ +$GLOBALS['__STRINGPARSER_NODE_ID'] = 0; + +/** + * Generic string parser node class + * + * This is an abstract class for any type of node that is used within the + * string parser. General warning: This class contains code regarding references + * that is very tricky. Please do not touch this code unless you exactly know + * what you are doing. Incorrect handling of references may cause PHP to crash + * with a segmentation fault! You have been warned. + * + * @package stringparser + */ +class StringParser_Node { + /** + * The type of this node. + * + * There are three standard node types: root node, text node and unknown + * node. All node types are integer constants. Any node type of a + * subclass must be at least 32 to allow future developements. + * + * @access protected + * @var int + * @see STRINGPARSER_NODE_ROOT, STRINGPARSER_NODE_TEXT + * @see STRINGPARSER_NODE_UNKNOWN + */ + var $_type = STRINGPARSER_NODE_UNKNOWN; + + /** + * The node ID + * + * This ID uniquely identifies this node. This is needed when searching + * for a specific node in the children array. Please note that this is + * only an internal variable and should never be used - not even in + * subclasses and especially not in external data structures. This ID + * has nothing to do with any type of ID in HTML oder XML. + * + * @access protected + * @var int + * @see StringParser_Node::_children + */ + var $_id = -1; + + /** + * The parent of this node. + * + * It is either null (root node) or a reference to the parent object. + * + * @access protected + * @var mixed + * @see StringParser_Node::_children + */ + var $_parent = null; + + /** + * The children of this node. + * + * It contains an array of references to all the children nodes of this + * node. + * + * @access protected + * @var array + * @see StringParser_Node::_parent + */ + var $_children = array (); + + /** + * Occured at + * + * This defines the position in the parsed text where this node occurred + * at. If -1, this value was not possible to be determined. + * + * @access public + * @var int + */ + var $occurredAt = -1; + + /** + * Constructor + * + * Currently, the constructor only allocates a new ID for the node and + * assigns it. + * + * @access public + * @param int $occurredAt The position in the text where this node + * occurred at. If not determinable, it is -1. + * @global __STRINGPARSER_NODE_ID + */ + function StringParser_Node ($occurredAt = -1) { + $this->_id = $GLOBALS['__STRINGPARSER_NODE_ID']++; + $this->occurredAt = $occurredAt; + } + + /** + * Type of the node + * + * This function returns the type of the node + * + * @access public + * @return int + */ + function type () { + return $this->_type; + } + + /** + * Prepend a node + * + * @access public + * @param object $node The node to be prepended. + * @return bool On success, the function returns true, else false. + */ + function prependChild (&$node) { + if (!is_object ($node)) { + return false; + } + + // root nodes may not be children of other nodes! + if ($node->_type == STRINGPARSER_NODE_ROOT) { + return false; + } + + // if node already has a parent + if ($node->_parent !== false) { + // remove node from there + $parent =& $node->_parent; + if (!$parent->removeChild ($node, false)) { + return false; + } + unset ($parent); + } + + $index = count ($this->_children) - 1; + // move all nodes to a new index + while ($index >= 0) { + // save object + $object =& $this->_children[$index]; + // we have to unset it because else it will be + // overridden in in the loop + unset ($this->_children[$index]); + // put object to new position + $this->_children[$index+1] =& $object; + $index--; + } + $this->_children[0] =& $node; + return true; + } + + /** + * Append text to last text child + * @access public + * @param string $text The text to append + * @return bool On success, the function returns true, else false + */ + function appendToLastTextChild ($text) { + $ccount = count ($this->_children); + if ($ccount == 0 || $this->_children[$ccount-1]->_type != STRINGPARSER_NODE_TEXT) { + $ntextnode =& new StringParser_Node_Text ($text); + return $this->appendChild ($ntextnode); + } else { + $this->_children[$ccount-1]->appendText ($text); + return true; + } + } + + /** + * Append a node to the children + * + * This function appends a node to the children array(). It + * automatically sets the {@link StrinParser_Node::_parent _parent} + * property of the node that is to be appended. + * + * @access public + * @param object $node The node that is to be appended. + * @return bool On success, the function returns true, else false. + */ + function appendChild (&$node) { + if (!is_object ($node)) { + return false; + } + + // root nodes may not be children of other nodes! + if ($node->_type == STRINGPARSER_NODE_ROOT) { + return false; + } + + // if node already has a parent + if ($node->_parent !== null) { + // remove node from there + $parent =& $node->_parent; + if (!$parent->removeChild ($node, false)) { + return false; + } + unset ($parent); + } + + // append it to current node + $new_index = count ($this->_children); + $this->_children[$new_index] =& $node; + $node->_parent =& $this; + return true; + } + + /** + * Insert a node before another node + * + * @access public + * @param object $node The node to be inserted. + * @param object $reference The reference node where the new node is + * to be inserted before. + * @return bool On success, the function returns true, else false. + */ + function insertChildBefore (&$node, &$reference) { + if (!is_object ($node)) { + return false; + } + + // root nodes may not be children of other nodes! + if ($node->_type == STRINGPARSER_NODE_ROOT) { + return false; + } + + // is the reference node a child? + $child = $this->_findChild ($reference); + + if ($child === false) { + return false; + } + + // if node already has a parent + if ($node->_parent !== null) { + // remove node from there + $parent =& $node->_parent; + if (!$parent->removeChild ($node, false)) { + return false; + } + unset ($parent); + } + + $index = count ($this->_children) - 1; + // move all nodes to a new index + while ($index >= $child) { + // save object + $object =& $this->_children[$index]; + // we have to unset it because else it will be + // overridden in in the loop + unset ($this->_children[$index]); + // put object to new position + $this->_children[$index+1] =& $object; + $index--; + } + $this->_children[$child] =& $node; + return true; + } + + /** + * Insert a node after another node + * + * @access public + * @param object $node The node to be inserted. + * @param object $reference The reference node where the new node is + * to be inserted after. + * @return bool On success, the function returns true, else false. + */ + function insertChildAfter (&$node, &$reference) { + if (!is_object ($node)) { + return false; + } + + // root nodes may not be children of other nodes! + if ($node->_type == STRINGPARSER_NODE_ROOT) { + return false; + } + + // is the reference node a child? + $child = $this->_findChild ($reference); + + if ($child === false) { + return false; + } + + // if node already has a parent + if ($node->_parent !== false) { + // remove node from there + $parent =& $node->_parent; + if (!$parent->removeChild ($node, false)) { + return false; + } + unset ($parent); + } + + $index = count ($this->_children) - 1; + // move all nodes to a new index + while ($index >= $child + 1) { + // save object + $object =& $this->_children[$index]; + // we have to unset it because else it will be + // overridden in in the loop + unset ($this->_children[$index]); + // put object to new position + $this->_children[$index+1] =& $object; + $index--; + } + $this->_children[$child + 1] =& $node; + return true; + } + + /** + * Remove a child node + * + * This function removes a child from the children array. A parameter + * tells the function whether to destroy the child afterwards or not. + * If the specified node is not a child of this node, the function will + * return false. + * + * @access public + * @param mixed $child The child to destroy; either an integer + * specifying the index of the child or a reference + * to the child itself. + * @param bool $destroy Destroy the child afterwards. + * @return bool On success, the function returns true, else false. + */ + function removeChild (&$child, $destroy = false) { + if (is_object ($child)) { + // if object: get index + $object =& $child; + unset ($child); + $child = $this->_findChild ($object); + if ($child === false) { + return false; + } + } else { + // remove reference on $child + $save = $child; + unset($child); + $child = $save; + + // else: get object + if (!isset($this->_children[$child])) { + return false; + } + $object =& $this->_children[$child]; + } + + // store count for later use + $ccount = count ($this->_children); + + // index out of bounds + if (!is_int ($child) || $child < 0 || $child >= $ccount) { + return false; + } + + // inkonsistency + if ($this->_children[$child]->_parent === null || + $this->_children[$child]->_parent->_id != $this->_id) { + return false; + } + + // $object->_parent = null would equal to $this = null + // as $object->_parent is a reference to $this! + // because of this, we have to unset the variable to remove + // the reference and then redeclare the variable + unset ($object->_parent); $object->_parent = null; + + // we have to unset it because else it will be overridden in + // in the loop + unset ($this->_children[$child]); + + // move all remaining objects one index higher + while ($child < $ccount - 1) { + // save object + $obj =& $this->_children[$child+1]; + // we have to unset it because else it will be + // overridden in in the loop + unset ($this->_children[$child+1]); + // put object to new position + $this->_children[$child] =& $obj; + // UNSET THE OBJECT! + unset ($obj); + $child++; + } + + if ($destroy) { + return StringParser_Node::destroyNode ($object); + unset ($object); + } + return true; + } + + /** + * Get the first child of this node + * + * @access public + * @return mixed + */ + function &firstChild () { + $ret = null; + if (!count ($this->_children)) { + return $ret; + } + return $this->_children[0]; + } + + /** + * Get the last child of this node + * + * @access public + * @return mixed + */ + function &lastChild () { + $ret = null; + $c = count ($this->_children); + if (!$c) { + return $ret; + } + return $this->_children[$c-1]; + } + + /** + * Destroy a node + * + * @access public + * @static + * @param object $node The node to destroy + * @return bool True on success, else false. + */ + function destroyNode (&$node) { + if ($node === null) { + return false; + } + // if parent exists: remove node from tree! + if ($node->_parent !== null) { + $parent =& $node->_parent; + // directly return that result because the removeChild + // method will call destroyNode again + return $parent->removeChild ($node, true); + } + + // node has children + while (count ($node->_children)) { + $child = 0; + // remove first child until no more children remain + if (!$node->removeChild ($child, true)) { + return false; + } + unset($child); + } + + // now call the nodes destructor + if (!$node->_destroy ()) { + return false; + } + + // now just unset it and prey that there are no more references + // to this node + unset ($node); + + return true; + } + + /** + * Destroy this node + * + * + * @access protected + * @return bool True on success, else false. + */ + function _destroy () { + return true; + } + + /** + * Find a child node + * + * This function searches for a node in the own children and returns + * the index of the node or false if the node is not a child of this + * node. + * + * @access protected + * @param mixed $child The node to look for. + * @return mixed The index of the child node on success, else false. + */ + function _findChild (&$child) { + if (!is_object ($child)) { + return false; + } + + $ccount = count ($this->_children); + for ($i = 0; $i < $ccount; $i++) { + if ($this->_children[$i]->_id == $child->_id) { + return $i; + } + } + + return false; + } + + /** + * Checks equality of this node and another node + * + * @access public + * @param mixed $node The node to be compared with + * @return bool True if the other node equals to this node, else false. + */ + function equals (&$node) { + return ($this->_id == $node->_id); + } + + /** + * Determines whether a criterium matches this node + * + * @access public + * @param string $criterium The criterium that is to be checked + * @param mixed $value The value that is to be compared + * @return bool True if this node matches that criterium + */ + function matchesCriterium ($criterium, $value) { + return false; + } + + /** + * Search for nodes with a certain criterium + * + * This may be used to implement getElementsByTagName etc. + * + * @access public + * @param string $criterium The criterium that is to be checked + * @param mixed $value The value that is to be compared + * @return array All subnodes that match this criterium + */ + function &getNodesByCriterium ($criterium, $value) { + $nodes = array (); + $node_ctr = 0; + for ($i = 0; $i < count ($this->_children); $i++) { + if ($this->_children[$i]->matchesCriterium ($criterium, $value)) { + $nodes[$node_ctr++] =& $this->_children[$i]; + } + $subnodes = $this->_children[$i]->getNodesByCriterium ($criterium, $value); + if (count ($subnodes)) { + $subnodes_count = count ($subnodes); + for ($j = 0; $j < $subnodes_count; $j++) { + $nodes[$node_ctr++] =& $subnodes[$j]; + unset ($subnodes[$j]); + } + } + unset ($subnodes); + } + return $nodes; + } + + /** + * Search for nodes with a certain criterium and return the count + * + * Similar to getNodesByCriterium + * + * @access public + * @param string $criterium The criterium that is to be checked + * @param mixed $value The value that is to be compared + * @return int The number of subnodes that match this criterium + */ + function getNodeCountByCriterium ($criterium, $value) { + $node_ctr = 0; + for ($i = 0; $i < count ($this->_children); $i++) { + if ($this->_children[$i]->matchesCriterium ($criterium, $value)) { + $node_ctr++; + } + $subnodes = $this->_children[$i]->getNodeCountByCriterium ($criterium, $value); + $node_ctr += $subnodes; + } + return $node_ctr; + } + + /** + * Dump nodes + * + * This dumps a tree of nodes + * + * @access public + * @param string $prefix The prefix that is to be used for indentation + * @param string $linesep The line separator + * @param int $level The initial level of indentation + * @return string + */ + function dump ($prefix = " ", $linesep = "\n", $level = 0) { + $str = str_repeat ($prefix, $level) . $this->_id . ": " . $this->_dumpToString () . $linesep; + for ($i = 0; $i < count ($this->_children); $i++) { + $str .= $this->_children[$i]->dump ($prefix, $linesep, $level + 1); + } + return $str; + } + + /** + * Dump this node to a string + * + * @access protected + * @return string + */ + function _dumpToString () { + if ($this->_type == STRINGPARSER_NODE_ROOT) { + return "root"; + } + return (string)$this->_type; + } +} + +/** + * String parser root node class + * + * @package stringparser + */ +class StringParser_Node_Root extends StringParser_Node { + /** + * The type of this node. + * + * This node is a root node. + * + * @access protected + * @var int + * @see STRINGPARSER_NODE_ROOT + */ + var $_type = STRINGPARSER_NODE_ROOT; +} + +/** + * String parser text node class + * + * @package stringparser + */ +class StringParser_Node_Text extends StringParser_Node { + /** + * The type of this node. + * + * This node is a text node. + * + * @access protected + * @var int + * @see STRINGPARSER_NODE_TEXT + */ + var $_type = STRINGPARSER_NODE_TEXT; + + /** + * Node flags + * + * @access protected + * @var array + */ + var $_flags = array (); + + /** + * The content of this node + * @access public + * @var string + */ + var $content = ''; + + /** + * Constructor + * + * @access public + * @param string $content The initial content of this element + * @param int $occurredAt The position in the text where this node + * occurred at. If not determinable, it is -1. + * @see StringParser_Node_Text::content + */ + function StringParser_Node_Text ($content, $occurredAt = -1) { + parent::StringParser_Node ($occurredAt); + $this->content = $content; + } + + /** + * Append text to content + * + * @access public + * @param string $text The text to append + * @see StringParser_Node_Text::content + */ + function appendText ($text) { + $this->content .= $text; + } + + /** + * Set a flag + * + * @access public + * @param string $name The name of the flag + * @param mixed $value The value of the flag + */ + function setFlag ($name, $value) { + $this->_flags[$name] = $value; + return true; + } + + /** + * Get Flag + * + * @access public + * @param string $flag The requested flag + * @param string $type The requested type of the return value + * @param mixed $default The default return value + */ + function getFlag ($flag, $type = 'mixed', $default = null) { + if (!isset ($this->_flags[$flag])) { + return $default; + } + $return = $this->_flags[$flag]; + if ($type != 'mixed') { + settype ($return, $type); + } + return $return; + } + + /** + * Dump this node to a string + */ + function _dumpToString () { + return "text \"".substr (preg_replace ('/\s+/', ' ', $this->content), 0, 40)."\" [f:".preg_replace ('/\s+/', ' ', join(':', array_keys ($this->_flags)))."]"; + } +} + +?> \ No newline at end of file diff --git a/scripts/stringparser_bbcode.class.php b/scripts/stringparser_bbcode.class.php new file mode 100644 index 0000000..9142609 --- /dev/null +++ b/scripts/stringparser_bbcode.class.php @@ -0,0 +1,1979 @@ + + * @copyright Christian Seiler 2004-2008 + * @package stringparser + * + * The MIT License + * + * Copyright (c) 2004-2008 Christian Seiler + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN + * THE SOFTWARE. + */ + +require_once dirname(__FILE__).'/stringparser.class.php'; + +define ('BBCODE_CLOSETAG_FORBIDDEN', -1); +define ('BBCODE_CLOSETAG_OPTIONAL', 0); +define ('BBCODE_CLOSETAG_IMPLICIT', 1); +define ('BBCODE_CLOSETAG_IMPLICIT_ON_CLOSE_ONLY', 2); +define ('BBCODE_CLOSETAG_MUSTEXIST', 3); + +define ('BBCODE_NEWLINE_PARSE', 0); +define ('BBCODE_NEWLINE_IGNORE', 1); +define ('BBCODE_NEWLINE_DROP', 2); + +define ('BBCODE_PARAGRAPH_ALLOW_BREAKUP', 0); +define ('BBCODE_PARAGRAPH_ALLOW_INSIDE', 1); +define ('BBCODE_PARAGRAPH_BLOCK_ELEMENT', 2); + +/** + * BB code string parser class + * + * @package stringparser + */ +class StringParser_BBCode extends StringParser { + /** + * String parser mode + * + * The BBCode string parser works in search mode + * + * @access protected + * @var int + * @see STRINGPARSER_MODE_SEARCH, STRINGPARSER_MODE_LOOP + */ + var $_parserMode = STRINGPARSER_MODE_SEARCH; + + /** + * Defined BB Codes + * + * The registered BB codes + * + * @access protected + * @var array + */ + var $_codes = array (); + + /** + * Registered parsers + * + * @access protected + * @var array + */ + var $_parsers = array (); + + /** + * Defined maximum occurrences + * + * @access protected + * @var array + */ + var $_maxOccurrences = array (); + + /** + * Root content type + * + * @access protected + * @var string + */ + var $_rootContentType = 'block'; + + /** + * Do not output but return the tree + * + * @access protected + * @var bool + */ + var $_noOutput = false; + + /** + * Global setting: case sensitive + * + * @access protected + * @var bool + */ + var $_caseSensitive = true; + + /** + * Root paragraph handling enabled + * + * @access protected + * @var bool + */ + var $_rootParagraphHandling = false; + + /** + * Paragraph handling parameters + * @access protected + * @var array + */ + var $_paragraphHandling = array ( + 'detect_string' => "\n\n", + 'start_tag' => '

    ', + 'end_tag' => "

    \n" + ); + + /** + * Allow mixed attribute types (e.g. [code=bla attr=blub]) + * @access private + * @var bool + */ + var $_mixedAttributeTypes = false; + + /** + * Whether to call validation function again (with $action == 'validate_auto') when closetag comes + * @access protected + * @var bool + */ + var $_validateAgain = false; + + /** + * Add a code + * + * @access public + * @param string $name The name of the code + * @param string $callback_type See documentation + * @param string $callback_func The callback function to call + * @param array $callback_params The callback parameters + * @param string $content_type See documentation + * @param array $allowed_within See documentation + * @param array $not_allowed_within See documentation + * @return bool + */ + function addCode ($name, $callback_type, $callback_func, $callback_params, $content_type, $allowed_within, $not_allowed_within) { + if (isset ($this->_codes[$name])) { + return false; // already exists + } + if (!preg_match ('/^[a-zA-Z0-9*_!+-]+$/', $name)) { + return false; // invalid + } + $this->_codes[$name] = array ( + 'name' => $name, + 'callback_type' => $callback_type, + 'callback_func' => $callback_func, + 'callback_params' => $callback_params, + 'content_type' => $content_type, + 'allowed_within' => $allowed_within, + 'not_allowed_within' => $not_allowed_within, + 'flags' => array () + ); + return true; + } + + /** + * Remove a code + * + * @access public + * @param $name The code to remove + * @return bool + */ + function removeCode ($name) { + if (isset ($this->_codes[$name])) { + unset ($this->_codes[$name]); + return true; + } + return false; + } + + /** + * Remove all codes + * + * @access public + */ + function removeAllCodes () { + $this->_codes = array (); + } + + /** + * Set a code flag + * + * @access public + * @param string $name The name of the code + * @param string $flag The name of the flag to set + * @param mixed $value The value of the flag to set + * @return bool + */ + function setCodeFlag ($name, $flag, $value) { + if (!isset ($this->_codes[$name])) { + return false; + } + $this->_codes[$name]['flags'][$flag] = $value; + return true; + } + + /** + * Set occurrence type + * + * Example: + * $bbcode->setOccurrenceType ('url', 'link'); + * $bbcode->setMaxOccurrences ('link', 4); + * Would create the situation where a link may only occur four + * times in the hole text. + * + * @access public + * @param string $code The name of the code + * @param string $type The name of the occurrence type to set + * @return bool + */ + function setOccurrenceType ($code, $type) { + return $this->setCodeFlag ($code, 'occurrence_type', $type); + } + + /** + * Set maximum number of occurrences + * + * @access public + * @param string $type The name of the occurrence type + * @param int $count The maximum number of occurrences + * @return bool + */ + function setMaxOccurrences ($type, $count) { + settype ($count, 'integer'); + if ($count < 0) { // sorry, does not make any sense + return false; + } + $this->_maxOccurrences[$type] = $count; + return true; + } + + /** + * Add a parser + * + * @access public + * @param string $type The content type for which the parser is to add + * @param mixed $parser The function to call + * @return bool + */ + function addParser ($type, $parser) { + if (is_array ($type)) { + foreach ($type as $t) { + $this->addParser ($t, $parser); + } + return true; + } + if (!isset ($this->_parsers[$type])) { + $this->_parsers[$type] = array (); + } + $this->_parsers[$type][] = $parser; + return true; + } + + /** + * Set root content type + * + * @access public + * @param string $content_type The new root content type + */ + function setRootContentType ($content_type) { + $this->_rootContentType = $content_type; + } + + /** + * Set paragraph handling on root element + * + * @access public + * @param bool $enabled The new status of paragraph handling on root element + */ + function setRootParagraphHandling ($enabled) { + $this->_rootParagraphHandling = (bool)$enabled; + } + + /** + * Set paragraph handling parameters + * + * @access public + * @param string $detect_string The string to detect + * @param string $start_tag The replacement for the start tag (e.g.

    ) + * @param string $end_tag The replacement for the start tag (e.g.

    ) + */ + function setParagraphHandlingParameters ($detect_string, $start_tag, $end_tag) { + $this->_paragraphHandling = array ( + 'detect_string' => $detect_string, + 'start_tag' => $start_tag, + 'end_tag' => $end_tag + ); + } + + /** + * Set global case sensitive flag + * + * If this is set to true, the class normally is case sensitive, but + * the case_sensitive code flag may override this for a single code. + * + * If this is set to false, all codes are case insensitive. + * + * @access public + * @param bool $caseSensitive + */ + function setGlobalCaseSensitive ($caseSensitive) { + $this->_caseSensitive = (bool)$caseSensitive; + } + + /** + * Get global case sensitive flag + * + * @access public + * @return bool + */ + function globalCaseSensitive () { + return $this->_caseSensitive; + } + + /** + * Set mixed attribute types flag + * + * If set, [code=val1 attr=val2] will cause 2 attributes to be parsed: + * 'default' will have value 'val1', 'attr' will have value 'val2'. + * If not set, only one attribute 'default' will have the value + * 'val1 attr=val2' (the default and original behaviour) + * + * @access public + * @param bool $mixedAttributeTypes + */ + function setMixedAttributeTypes ($mixedAttributeTypes) { + $this->_mixedAttributeTypes = (bool)$mixedAttributeTypes; + } + + /** + * Get mixed attribute types flag + * + * @access public + * @return bool + */ + function mixedAttributeTypes () { + return $this->_mixedAttributeTypes; + } + + /** + * Set validate again flag + * + * If this is set to true, the class calls the validation function + * again with $action == 'validate_again' when closetag comes. + * + * @access public + * @param bool $validateAgain + */ + function setValidateAgain ($validateAgain) { + $this->_validateAgain = (bool)$validateAgain; + } + + /** + * Get validate again flag + * + * @access public + * @return bool + */ + function validateAgain () { + return $this->_validateAgain; + } + + /** + * Get a code flag + * + * @access public + * @param string $name The name of the code + * @param string $flag The name of the flag to get + * @param string $type The type of the return value + * @param mixed $default The default return value + * @return bool + */ + function getCodeFlag ($name, $flag, $type = 'mixed', $default = null) { + if (!isset ($this->_codes[$name])) { + return $default; + } + if (!array_key_exists ($flag, $this->_codes[$name]['flags'])) { + return $default; + } + $return = $this->_codes[$name]['flags'][$flag]; + if ($type != 'mixed') { + settype ($return, $type); + } + return $return; + } + + /** + * Set a specific status + * @access protected + */ + function _setStatus ($status) { + switch ($status) { + case 0: + $this->_charactersSearch = array ('[/', '['); + $this->_status = $status; + break; + case 1: + $this->_charactersSearch = array (']', ' = "', '="', ' = \'', '=\'', ' = ', '=', ': ', ':', ' '); + $this->_status = $status; + break; + case 2: + $this->_charactersSearch = array (']'); + $this->_status = $status; + $this->_savedName = ''; + break; + case 3: + if ($this->_quoting !== null) { + if ($this->_mixedAttributeTypes) { + $this->_charactersSearch = array ('\\\\', '\\'.$this->_quoting, $this->_quoting.' ', $this->_quoting.']', $this->_quoting); + } else { + $this->_charactersSearch = array ('\\\\', '\\'.$this->_quoting, $this->_quoting.']', $this->_quoting); + } + $this->_status = $status; + break; + } + if ($this->_mixedAttributeTypes) { + $this->_charactersSearch = array (' ', ']'); + } else { + $this->_charactersSearch = array (']'); + } + $this->_status = $status; + break; + case 4: + $this->_charactersSearch = array (' ', ']', '="', '=\'', '='); + $this->_status = $status; + $this->_savedName = ''; + $this->_savedValue = ''; + break; + case 5: + if ($this->_quoting !== null) { + $this->_charactersSearch = array ('\\\\', '\\'.$this->_quoting, $this->_quoting.' ', $this->_quoting.']', $this->_quoting); + } else { + $this->_charactersSearch = array (' ', ']'); + } + $this->_status = $status; + $this->_savedValue = ''; + break; + case 7: + $this->_charactersSearch = array ('[/'.$this->_topNode ('name').']'); + if (!$this->_topNode ('getFlag', 'case_sensitive', 'boolean', true) || !$this->_caseSensitive) { + $this->_charactersSearch[] = '[/'; + } + $this->_status = $status; + break; + default: + return false; + } + return true; + } + + /** + * Abstract method Append text depending on current status + * @access protected + * @param string $text The text to append + * @return bool On success, the function returns true, else false + */ + function _appendText ($text) { + if (!strlen ($text)) { + return true; + } + switch ($this->_status) { + case 0: + case 7: + return $this->_appendToLastTextChild ($text); + case 1: + return $this->_topNode ('appendToName', $text); + case 2: + case 4: + $this->_savedName .= $text; + return true; + case 3: + return $this->_topNode ('appendToAttribute', 'default', $text); + case 5: + $this->_savedValue .= $text; + return true; + default: + return false; + } + } + + /** + * Restart parsing after current block + * + * To achieve this the current top stack object is removed from the + * tree. Then the current item + * + * @access protected + * @return bool + */ + function _reparseAfterCurrentBlock () { + if ($this->_status == 2) { + // this status will *never* call _reparseAfterCurrentBlock itself + // so this is called if the loop ends + // therefore, just add the [/ to the text + + // _savedName should be empty but just in case + $this->_cpos -= strlen ($this->_savedName); + $this->_savedName = ''; + $this->_status = 0; + $this->_appendText ('[/'); + return true; + } else { + return parent::_reparseAfterCurrentBlock (); + } + } + + /** + * Apply parsers + */ + function _applyParsers ($type, $text) { + if (!isset ($this->_parsers[$type])) { + return $text; + } + foreach ($this->_parsers[$type] as $parser) { + if (is_callable ($parser)) { + $ntext = call_user_func ($parser, $text); + if (is_string ($ntext)) { + $text = $ntext; + } + } + } + return $text; + } + + /** + * Handle status + * @access protected + * @param int $status The current status + * @param string $needle The needle that was found + * @return bool + */ + function _handleStatus ($status, $needle) { + switch ($status) { + case 0: // NORMAL TEXT + if ($needle != '[' && $needle != '[/') { + $this->_appendText ($needle); + return true; + } + if ($needle == '[') { + $node =& new StringParser_BBCode_Node_Element ($this->_cpos); + $res = $this->_pushNode ($node); + if (!$res) { + return false; + } + $this->_setStatus (1); + } else if ($needle == '[/') { + if (count ($this->_stack) <= 1) { + $this->_appendText ($needle); + return true; + } + $this->_setStatus (2); + } + break; + case 1: // OPEN TAG + if ($needle == ']') { + return $this->_openElement (0); + } else if (trim ($needle) == ':' || trim ($needle) == '=') { + $this->_quoting = null; + $this->_setStatus (3); // default value parser + break; + } else if (trim ($needle) == '="' || trim ($needle) == '= "' || trim ($needle) == '=\'' || trim ($needle) == '= \'') { + $this->_quoting = substr (trim ($needle), -1); + $this->_setStatus (3); // default value parser with quotation + break; + } else if ($needle == ' ') { + $this->_setStatus (4); // attribute parser + break; + } else { + $this->_appendText ($needle); + return true; + } + // break not necessary because every if clause contains return + case 2: // CLOSE TAG + if ($needle != ']') { + $this->_appendText ($needle); + return true; + } + $closecount = 0; + if (!$this->_isCloseable ($this->_savedName, $closecount)) { + $this->_setStatus (0); + $this->_appendText ('[/'.$this->_savedName.$needle); + return true; + } + // this validates the code(s) to be closed after the content tree of + // that code(s) are built - if the second validation fails, we will have + // to reparse. note that as _reparseAfterCurrentBlock will not work correctly + // if we're in $status == 2, we will have to set our status to 0 manually + if (!$this->_validateCloseTags ($closecount)) { + $this->_setStatus (0); + return $this->_reparseAfterCurrentBlock (); + } + $this->_setStatus (0); + for ($i = 0; $i < $closecount; $i++) { + if ($i == $closecount - 1) { + $this->_topNode ('setHadCloseTag'); + } + if (!$this->_popNode ()) { + return false; + } + } + break; + case 3: // DEFAULT ATTRIBUTE + if ($this->_quoting !== null) { + if ($needle == '\\\\') { + $this->_appendText ('\\'); + return true; + } else if ($needle == '\\'.$this->_quoting) { + $this->_appendText ($this->_quoting); + return true; + } else if ($needle == $this->_quoting.' ') { + $this->_setStatus (4); + return true; + } else if ($needle == $this->_quoting.']') { + return $this->_openElement (2); + } else if ($needle == $this->_quoting) { + // can't be, only ']' and ' ' allowed after quoting char + return $this->_reparseAfterCurrentBlock (); + } else { + $this->_appendText ($needle); + return true; + } + } else { + if ($needle == ' ') { + $this->_setStatus (4); + return true; + } else if ($needle == ']') { + return $this->_openElement (2); + } else { + $this->_appendText ($needle); + return true; + } + } + // break not needed because every if clause contains return! + case 4: // ATTRIBUTE NAME + if ($needle == ' ') { + if (strlen ($this->_savedName)) { + $this->_topNode ('setAttribute', $this->_savedName, true); + } + // just ignore and continue in same mode + $this->_setStatus (4); // reset parameters + return true; + } else if ($needle == ']') { + if (strlen ($this->_savedName)) { + $this->_topNode ('setAttribute', $this->_savedName, true); + } + return $this->_openElement (2); + } else if ($needle == '=') { + $this->_quoting = null; + $this->_setStatus (5); + return true; + } else if ($needle == '="') { + $this->_quoting = '"'; + $this->_setStatus (5); + return true; + } else if ($needle == '=\'') { + $this->_quoting = '\''; + $this->_setStatus (5); + return true; + } else { + $this->_appendText ($needle); + return true; + } + // break not needed because every if clause contains return! + case 5: // ATTRIBUTE VALUE + if ($this->_quoting !== null) { + if ($needle == '\\\\') { + $this->_appendText ('\\'); + return true; + } else if ($needle == '\\'.$this->_quoting) { + $this->_appendText ($this->_quoting); + return true; + } else if ($needle == $this->_quoting.' ') { + $this->_topNode ('setAttribute', $this->_savedName, $this->_savedValue); + $this->_setStatus (4); + return true; + } else if ($needle == $this->_quoting.']') { + $this->_topNode ('setAttribute', $this->_savedName, $this->_savedValue); + return $this->_openElement (2); + } else if ($needle == $this->_quoting) { + // can't be, only ']' and ' ' allowed after quoting char + return $this->_reparseAfterCurrentBlock (); + } else { + $this->_appendText ($needle); + return true; + } + } else { + if ($needle == ' ') { + $this->_topNode ('setAttribute', $this->_savedName, $this->_savedValue); + $this->_setStatus (4); + return true; + } else if ($needle == ']') { + $this->_topNode ('setAttribute', $this->_savedName, $this->_savedValue); + return $this->_openElement (2); + } else { + $this->_appendText ($needle); + return true; + } + } + // break not needed because every if clause contains return! + case 7: + if ($needle == '[/') { + // this was case insensitive match + if (strtolower (substr ($this->_text, $this->_cpos + strlen ($needle), strlen ($this->_topNode ('name')) + 1)) == strtolower ($this->_topNode ('name').']')) { + // this matched + $this->_cpos += strlen ($this->_topNode ('name')) + 1; + } else { + // it didn't match + $this->_appendText ($needle); + return true; + } + } + $closecount = $this->_savedCloseCount; + if (!$this->_topNode ('validate')) { + return $this->_reparseAfterCurrentBlock (); + } + // do we have to close subnodes? + if ($closecount) { + // get top node + $mynode =& $this->_stack[count ($this->_stack)-1]; + // close necessary nodes + for ($i = 0; $i <= $closecount; $i++) { + if (!$this->_popNode ()) { + return false; + } + } + if (!$this->_pushNode ($mynode)) { + return false; + } + } + $this->_setStatus (0); + $this->_popNode (); + return true; + default: + return false; + } + return true; + } + + /** + * Open the next element + * + * @access protected + * @return bool + */ + function _openElement ($type = 0) { + $name = $this->_getCanonicalName ($this->_topNode ('name')); + if ($name === false) { + return $this->_reparseAfterCurrentBlock (); + } + $occ_type = $this->getCodeFlag ($name, 'occurrence_type', 'string'); + if ($occ_type !== null && isset ($this->_maxOccurrences[$occ_type])) { + $max_occs = $this->_maxOccurrences[$occ_type]; + $occs = $this->_root->getNodeCountByCriterium ('flag:occurrence_type', $occ_type); + if ($occs >= $max_occs) { + return $this->_reparseAfterCurrentBlock (); + } + } + $closecount = 0; + $this->_topNode ('setCodeInfo', $this->_codes[$name]); + if (!$this->_isOpenable ($name, $closecount)) { + return $this->_reparseAfterCurrentBlock (); + } + $this->_setStatus (0); + switch ($type) { + case 0: + $cond = $this->_isUseContent ($this->_stack[count($this->_stack)-1], false); + break; + case 1: + $cond = $this->_isUseContent ($this->_stack[count($this->_stack)-1], true); + break; + case 2: + $cond = $this->_isUseContent ($this->_stack[count($this->_stack)-1], true); + break; + default: + $cond = false; + break; + } + if ($cond) { + $this->_savedCloseCount = $closecount; + $this->_setStatus (7); + return true; + } + if (!$this->_topNode ('validate')) { + return $this->_reparseAfterCurrentBlock (); + } + // do we have to close subnodes? + if ($closecount) { + // get top node + $mynode =& $this->_stack[count ($this->_stack)-1]; + // close necessary nodes + for ($i = 0; $i <= $closecount; $i++) { + if (!$this->_popNode ()) { + return false; + } + } + if (!$this->_pushNode ($mynode)) { + return false; + } + } + + if ($this->_codes[$name]['callback_type'] == 'simple_replace_single' || $this->_codes[$name]['callback_type'] == 'callback_replace_single') { + if (!$this->_popNode ()) { + return false; + } + } + + return true; + } + + /** + * Is a node closeable? + * + * @access protected + * @return bool + */ + function _isCloseable ($name, &$closecount) { + $node =& $this->_findNamedNode ($name, false); + if ($node === false) { + return false; + } + $scount = count ($this->_stack); + for ($i = $scount - 1; $i > 0; $i--) { + $closecount++; + if ($this->_stack[$i]->equals ($node)) { + return true; + } + if ($this->_stack[$i]->getFlag ('closetag', 'integer', BBCODE_CLOSETAG_IMPLICIT) == BBCODE_CLOSETAG_MUSTEXIST) { + return false; + } + } + return false; + } + + /** + * Revalidate codes when close tags appear + * + * @access protected + * @return bool + */ + function _validateCloseTags ($closecount) { + $scount = count ($this->_stack); + for ($i = $scount - 1; $i >= $scount - $closecount; $i--) { + if ($this->_validateAgain) { + if (!$this->_stack[$i]->validate ('validate_again')) { + return false; + } + } + } + return true; + } + + /** + * Is a node openable? + * + * @access protected + * @return bool + */ + function _isOpenable ($name, &$closecount) { + if (!isset ($this->_codes[$name])) { + return false; + } + + $closecount = 0; + + $allowed_within = $this->_codes[$name]['allowed_within']; + $not_allowed_within = $this->_codes[$name]['not_allowed_within']; + + $scount = count ($this->_stack); + if ($scount == 2) { // top level element + if (!in_array ($this->_rootContentType, $allowed_within)) { + return false; + } + } else { + if (!in_array ($this->_stack[$scount-2]->_codeInfo['content_type'], $allowed_within)) { + return $this->_isOpenableWithClose ($name, $closecount); + } + } + + for ($i = 1; $i < $scount - 1; $i++) { + if (in_array ($this->_stack[$i]->_codeInfo['content_type'], $not_allowed_within)) { + return $this->_isOpenableWithClose ($name, $closecount); + } + } + + return true; + } + + /** + * Is a node openable by closing other nodes? + * + * @access protected + * @return bool + */ + function _isOpenableWithClose ($name, &$closecount) { + $tnname = $this->_getCanonicalName ($this->_topNode ('name')); + if (!in_array ($this->getCodeFlag ($tnname, 'closetag', 'integer', BBCODE_CLOSETAG_IMPLICIT), array (BBCODE_CLOSETAG_FORBIDDEN, BBCODE_CLOSETAG_OPTIONAL))) { + return false; + } + $node =& $this->_findNamedNode ($name, true); + if ($node === false) { + return false; + } + $scount = count ($this->_stack); + if ($scount < 3) { + return false; + } + for ($i = $scount - 2; $i > 0; $i--) { + $closecount++; + if ($this->_stack[$i]->equals ($node)) { + return true; + } + if (in_array ($this->_stack[$i]->getFlag ('closetag', 'integer', BBCODE_CLOSETAG_IMPLICIT), array (BBCODE_CLOSETAG_IMPLICIT_ON_CLOSE_ONLY, BBCODE_CLOSETAG_MUSTEXIST))) { + return false; + } + if ($this->_validateAgain) { + if (!$this->_stack[$i]->validate ('validate_again')) { + return false; + } + } + } + + return false; + } + + /** + * Abstract method: Close remaining blocks + * @access protected + */ + function _closeRemainingBlocks () { + // everything closed + if (count ($this->_stack) == 1) { + return true; + } + // not everything close + if ($this->strict) { + return false; + } + while (count ($this->_stack) > 1) { + if ($this->_topNode ('getFlag', 'closetag', 'integer', BBCODE_CLOSETAG_IMPLICIT) == BBCODE_CLOSETAG_MUSTEXIST) { + return false; // sorry + } + $res = $this->_popNode (); + if (!$res) { + return false; + } + } + return true; + } + + /** + * Find a node with a specific name in stack + * + * @access protected + * @return mixed + */ + function &_findNamedNode ($name, $searchdeeper = false) { + $lname = $this->_getCanonicalName ($name); + $case_sensitive = $this->_caseSensitive && $this->getCodeFlag ($lname, 'case_sensitive', 'boolean', true); + if ($case_sensitive) { + $name = strtolower ($name); + } + $scount = count ($this->_stack); + if ($searchdeeper) { + $scount--; + } + for ($i = $scount - 1; $i > 0; $i--) { + if (!$case_sensitive) { + $cmp_name = strtolower ($this->_stack[$i]->name ()); + } else { + $cmp_name = $this->_stack[$i]->name (); + } + if ($cmp_name == $lname) { + return $this->_stack[$i]; + } + } + $result = false; + return $result; + } + + /** + * Abstract method: Output tree + * @access protected + * @return bool + */ + function _outputTree () { + if ($this->_noOutput) { + return true; + } + $output = $this->_outputNode ($this->_root); + if (is_string ($output)) { + $this->_output = $this->_applyPostfilters ($output); + unset ($output); + return true; + } + + return false; + } + + /** + * Output a node + * @access protected + * @return bool + */ + function _outputNode (&$node) { + $output = ''; + if ($node->_type == STRINGPARSER_BBCODE_NODE_PARAGRAPH || $node->_type == STRINGPARSER_BBCODE_NODE_ELEMENT || $node->_type == STRINGPARSER_NODE_ROOT) { + $ccount = count ($node->_children); + for ($i = 0; $i < $ccount; $i++) { + $suboutput = $this->_outputNode ($node->_children[$i]); + if (!is_string ($suboutput)) { + return false; + } + $output .= $suboutput; + } + if ($node->_type == STRINGPARSER_BBCODE_NODE_PARAGRAPH) { + return $this->_paragraphHandling['start_tag'].$output.$this->_paragraphHandling['end_tag']; + } + if ($node->_type == STRINGPARSER_BBCODE_NODE_ELEMENT) { + return $node->getReplacement ($output); + } + return $output; + } else if ($node->_type == STRINGPARSER_NODE_TEXT) { + $output = $node->content; + $before = ''; + $after = ''; + $ol = strlen ($output); + switch ($node->getFlag ('newlinemode.begin', 'integer', BBCODE_NEWLINE_PARSE)) { + case BBCODE_NEWLINE_IGNORE: + if ($ol && $output{0} == "\n") { + $before = "\n"; + } + // don't break! + case BBCODE_NEWLINE_DROP: + if ($ol && $output{0} == "\n") { + $output = substr ($output, 1); + $ol--; + } + break; + } + switch ($node->getFlag ('newlinemode.end', 'integer', BBCODE_NEWLINE_PARSE)) { + case BBCODE_NEWLINE_IGNORE: + if ($ol && $output{$ol-1} == "\n") { + $after = "\n"; + } + // don't break! + case BBCODE_NEWLINE_DROP: + if ($ol && $output{$ol-1} == "\n") { + $output = substr ($output, 0, -1); + $ol--; + } + break; + } + // can't do anything + if ($node->_parent === null) { + return $before.$output.$after; + } + if ($node->_parent->_type == STRINGPARSER_BBCODE_NODE_PARAGRAPH) { + $parent =& $node->_parent; + unset ($node); + $node =& $parent; + unset ($parent); + // if no parent for this paragraph + if ($node->_parent === null) { + return $before.$output.$after; + } + } + if ($node->_parent->_type == STRINGPARSER_NODE_ROOT) { + return $before.$this->_applyParsers ($this->_rootContentType, $output).$after; + } + if ($node->_parent->_type == STRINGPARSER_BBCODE_NODE_ELEMENT) { + return $before.$this->_applyParsers ($node->_parent->_codeInfo['content_type'], $output).$after; + } + return $before.$output.$after; + } + } + + /** + * Abstract method: Manipulate the tree + * @access protected + * @return bool + */ + function _modifyTree () { + // first pass: try to do newline handling + $nodes =& $this->_root->getNodesByCriterium ('needsTextNodeModification', true); + $nodes_count = count ($nodes); + for ($i = 0; $i < $nodes_count; $i++) { + $v = $nodes[$i]->getFlag ('opentag.before.newline', 'integer', BBCODE_NEWLINE_PARSE); + if ($v != BBCODE_NEWLINE_PARSE) { + $n =& $nodes[$i]->findPrevAdjentTextNode (); + if (!is_null ($n)) { + $n->setFlag ('newlinemode.end', $v); + } + unset ($n); + } + $v = $nodes[$i]->getFlag ('opentag.after.newline', 'integer', BBCODE_NEWLINE_PARSE); + if ($v != BBCODE_NEWLINE_PARSE) { + $n =& $nodes[$i]->firstChildIfText (); + if (!is_null ($n)) { + $n->setFlag ('newlinemode.begin', $v); + } + unset ($n); + } + $v = $nodes[$i]->getFlag ('closetag.before.newline', 'integer', BBCODE_NEWLINE_PARSE); + if ($v != BBCODE_NEWLINE_PARSE) { + $n =& $nodes[$i]->lastChildIfText (); + if (!is_null ($n)) { + $n->setFlag ('newlinemode.end', $v); + } + unset ($n); + } + $v = $nodes[$i]->getFlag ('closetag.after.newline', 'integer', BBCODE_NEWLINE_PARSE); + if ($v != BBCODE_NEWLINE_PARSE) { + $n =& $nodes[$i]->findNextAdjentTextNode (); + if (!is_null ($n)) { + $n->setFlag ('newlinemode.begin', $v); + } + unset ($n); + } + } + + // second pass a: do paragraph handling on root element + if ($this->_rootParagraphHandling) { + $res = $this->_handleParagraphs ($this->_root); + if (!$res) { + return false; + } + } + + // second pass b: do paragraph handling on other elements + unset ($nodes); + $nodes =& $this->_root->getNodesByCriterium ('flag:paragraphs', true); + $nodes_count = count ($nodes); + for ($i = 0; $i < $nodes_count; $i++) { + $res = $this->_handleParagraphs ($nodes[$i]); + if (!$res) { + return false; + } + } + + // second pass c: search for empty paragraph nodes and remove them + unset ($nodes); + $nodes =& $this->_root->getNodesByCriterium ('empty', true); + $nodes_count = count ($nodes); + if (isset ($parent)) { + unset ($parent); $parent = null; + } + for ($i = 0; $i < $nodes_count; $i++) { + if ($nodes[$i]->_type != STRINGPARSER_BBCODE_NODE_PARAGRAPH) { + continue; + } + unset ($parent); + $parent =& $nodes[$i]->_parent; + $parent->removeChild ($nodes[$i], true); + } + + return true; + } + + /** + * Handle paragraphs + * @access protected + * @param object $node The node to handle + * @return bool + */ + function _handleParagraphs (&$node) { + // if this node is already a subnode of a paragraph node, do NOT + // do paragraph handling on this node! + if ($this->_hasParagraphAncestor ($node)) { + return true; + } + $dest_nodes = array (); + $last_node_was_paragraph = false; + $prevtype = STRINGPARSER_NODE_TEXT; + $paragraph = null; + while (count ($node->_children)) { + $mynode =& $node->_children[0]; + $node->removeChild ($mynode); + $subprevtype = $prevtype; + $sub_nodes =& $this->_breakupNodeByParagraphs ($mynode); + for ($i = 0; $i < count ($sub_nodes); $i++) { + if (!$last_node_was_paragraph || ($prevtype == $sub_nodes[$i]->_type && ($i != 0 || $prevtype != STRINGPARSER_BBCODE_NODE_ELEMENT))) { + unset ($paragraph); + $paragraph =& new StringParser_BBCode_Node_Paragraph (); + } + $prevtype = $sub_nodes[$i]->_type; + if ($sub_nodes[$i]->_type != STRINGPARSER_BBCODE_NODE_ELEMENT || $sub_nodes[$i]->getFlag ('paragraph_type', 'integer', BBCODE_PARAGRAPH_ALLOW_BREAKUP) != BBCODE_PARAGRAPH_BLOCK_ELEMENT) { + $paragraph->appendChild ($sub_nodes[$i]); + $dest_nodes[] =& $paragraph; + $last_node_was_paragraph = true; + } else { + $dest_nodes[] =& $sub_nodes[$i]; + $last_onde_was_paragraph = false; + unset ($paragraph); + $paragraph =& new StringParser_BBCode_Node_Paragraph (); + } + } + } + $count = count ($dest_nodes); + for ($i = 0; $i < $count; $i++) { + $node->appendChild ($dest_nodes[$i]); + } + unset ($dest_nodes); + unset ($paragraph); + return true; + } + + /** + * Search for a paragraph node in tree in upward direction + * @access protected + * @param object $node The node to analyze + * @return bool + */ + function _hasParagraphAncestor (&$node) { + if ($node->_parent === null) { + return false; + } + $parent =& $node->_parent; + if ($parent->_type == STRINGPARSER_BBCODE_NODE_PARAGRAPH) { + return true; + } + return $this->_hasParagraphAncestor ($parent); + } + + /** + * Break up nodes + * @access protected + * @param object $node The node to break up + * @return array + */ + function &_breakupNodeByParagraphs (&$node) { + $detect_string = $this->_paragraphHandling['detect_string']; + $dest_nodes = array (); + // text node => no problem + if ($node->_type == STRINGPARSER_NODE_TEXT) { + $cpos = 0; + while (($npos = strpos ($node->content, $detect_string, $cpos)) !== false) { + $subnode =& new StringParser_Node_Text (substr ($node->content, $cpos, $npos - $cpos), $node->occurredAt + $cpos); + // copy flags + foreach ($node->_flags as $flag => $value) { + if ($flag == 'newlinemode.begin') { + if ($cpos == 0) { + $subnode->setFlag ($flag, $value); + } + } else if ($flag == 'newlinemode.end') { + // do nothing + } else { + $subnode->setFlag ($flag, $value); + } + } + $dest_nodes[] =& $subnode; + unset ($subnode); + $cpos = $npos + strlen ($detect_string); + } + $subnode =& new StringParser_Node_Text (substr ($node->content, $cpos), $node->occurredAt + $cpos); + if ($cpos == 0) { + $value = $node->getFlag ('newlinemode.begin', 'integer', null); + if ($value !== null) { + $subnode->setFlag ('newlinemode.begin', $value); + } + } + $value = $node->getFlag ('newlinemode.end', 'integer', null); + if ($value !== null) { + $subnode->setFlag ('newlinemode.end', $value); + } + $dest_nodes[] =& $subnode; + unset ($subnode); + return $dest_nodes; + } + // not a text node or an element node => no way + if ($node->_type != STRINGPARSER_BBCODE_NODE_ELEMENT) { + $dest_nodes[] =& $node; + return $dest_nodes; + } + if ($node->getFlag ('paragraph_type', 'integer', BBCODE_PARAGRAPH_ALLOW_BREAKUP) != BBCODE_PARAGRAPH_ALLOW_BREAKUP || !count ($node->_children)) { + $dest_nodes[] =& $node; + return $dest_nodes; + } + $dest_node =& $node->duplicate (); + $nodecount = count ($node->_children); + // now this node allows breakup - do it + for ($i = 0; $i < $nodecount; $i++) { + $firstnode =& $node->_children[0]; + $node->removeChild ($firstnode); + $sub_nodes =& $this->_breakupNodeByParagraphs ($firstnode); + for ($j = 0; $j < count ($sub_nodes); $j++) { + if ($j != 0) { + $dest_nodes[] =& $dest_node; + unset ($dest_node); + $dest_node =& $node->duplicate (); + } + $dest_node->appendChild ($sub_nodes[$j]); + } + unset ($sub_nodes); + } + $dest_nodes[] =& $dest_node; + return $dest_nodes; + } + + /** + * Is this node a usecontent node + * @access protected + * @param object $node The node to check + * @param bool $check_attrs Also check whether 'usecontent?'-attributes exist + * @return bool + */ + function _isUseContent (&$node, $check_attrs = false) { + $name = $this->_getCanonicalName ($node->name ()); + // this should NOT happen + if ($name === false) { + return false; + } + if ($this->_codes[$name]['callback_type'] == 'usecontent') { + return true; + } + $result = false; + if ($this->_codes[$name]['callback_type'] == 'callback_replace?') { + $result = true; + } else if ($this->_codes[$name]['callback_type'] != 'usecontent?') { + return false; + } + if ($check_attrs === false) { + return !$result; + } + $attributes = array_keys ($this->_topNodeVar ('_attributes')); + $p = @$this->_codes[$name]['callback_params']['usecontent_param']; + if (is_array ($p)) { + foreach ($p as $param) { + if (in_array ($param, $attributes)) { + return $result; + } + } + } else { + if (in_array ($p, $attributes)) { + return $result; + } + } + return !$result; + } + + /** + * Get canonical name of a code + * + * @access protected + * @param string $name + * @return string + */ + function _getCanonicalName ($name) { + if (isset ($this->_codes[$name])) { + return $name; + } + $found = false; + // try to find the code in the code list + foreach (array_keys ($this->_codes) as $rname) { + // match + if (strtolower ($rname) == strtolower ($name)) { + $found = $rname; + break; + } + } + if ($found === false || ($this->_caseSensitive && $this->getCodeFlag ($found, 'case_sensitive', 'boolean', true))) { + return false; + } + return $rname; + } +} + +/** + * Node type: BBCode Element node + * @see StringParser_BBCode_Node_Element::_type + */ +define ('STRINGPARSER_BBCODE_NODE_ELEMENT', 32); + +/** + * Node type: BBCode Paragraph node + * @see StringParser_BBCode_Node_Paragraph::_type + */ +define ('STRINGPARSER_BBCODE_NODE_PARAGRAPH', 33); + + +/** + * BBCode String parser paragraph node class + * + * @package stringparser + */ +class StringParser_BBCode_Node_Paragraph extends StringParser_Node { + /** + * The type of this node. + * + * This node is a bbcode paragraph node. + * + * @access protected + * @var int + * @see STRINGPARSER_BBCODE_NODE_PARAGRAPH + */ + var $_type = STRINGPARSER_BBCODE_NODE_PARAGRAPH; + + /** + * Determines whether a criterium matches this node + * + * @access public + * @param string $criterium The criterium that is to be checked + * @param mixed $value The value that is to be compared + * @return bool True if this node matches that criterium + */ + function matchesCriterium ($criterium, $value) { + if ($criterium == 'empty') { + if (!count ($this->_children)) { + return true; + } + if (count ($this->_children) > 1) { + return false; + } + if ($this->_children[0]->_type != STRINGPARSER_NODE_TEXT) { + return false; + } + if (!strlen ($this->_children[0]->content)) { + return true; + } + if (strlen ($this->_children[0]->content) > 2) { + return false; + } + $f_begin = $this->_children[0]->getFlag ('newlinemode.begin', 'integer', BBCODE_NEWLINE_PARSE); + $f_end = $this->_children[0]->getFlag ('newlinemode.end', 'integer', BBCODE_NEWLINE_PARSE); + $content = $this->_children[0]->content; + if ($f_begin != BBCODE_NEWLINE_PARSE && $content{0} == "\n") { + $content = substr ($content, 1); + } + if ($f_end != BBCODE_NEWLINE_PARSE && $content{strlen($content)-1} == "\n") { + $content = substr ($content, 0, -1); + } + if (!strlen ($content)) { + return true; + } + return false; + } + } +} + +/** + * BBCode String parser element node class + * + * @package stringparser + */ +class StringParser_BBCode_Node_Element extends StringParser_Node { + /** + * The type of this node. + * + * This node is a bbcode element node. + * + * @access protected + * @var int + * @see STRINGPARSER_BBCODE_NODE_ELEMENT + */ + var $_type = STRINGPARSER_BBCODE_NODE_ELEMENT; + + /** + * Element name + * + * @access protected + * @var string + * @see StringParser_BBCode_Node_Element::name + * @see StringParser_BBCode_Node_Element::setName + * @see StringParser_BBCode_Node_Element::appendToName + */ + var $_name = ''; + + /** + * Element flags + * + * @access protected + * @var array + */ + var $_flags = array (); + + /** + * Element attributes + * + * @access protected + * @var array + */ + var $_attributes = array (); + + /** + * Had a close tag + * + * @access protected + * @var bool + */ + var $_hadCloseTag = false; + + /** + * Was processed by paragraph handling + * + * @access protected + * @var bool + */ + var $_paragraphHandled = false; + + ////////////////////////////////////////////////// + + /** + * Duplicate this node (but without children / parents) + * + * @access public + * @return object + */ + function &duplicate () { + $newnode =& new StringParser_BBCode_Node_Element ($this->occurredAt); + $newnode->_name = $this->_name; + $newnode->_flags = $this->_flags; + $newnode->_attributes = $this->_attributes; + $newnode->_hadCloseTag = $this->_hadCloseTag; + $newnode->_paragraphHandled = $this->_paragraphHandled; + $newnode->_codeInfo = $this->_codeInfo; + return $newnode; + } + + /** + * Retreive name of this element + * + * @access public + * @return string + */ + function name () { + return $this->_name; + } + + /** + * Set name of this element + * + * @access public + * @param string $name The new name of the element + */ + function setName ($name) { + $this->_name = $name; + return true; + } + + /** + * Append to name of this element + * + * @access public + * @param string $chars The chars to append to the name of the element + */ + function appendToName ($chars) { + $this->_name .= $chars; + return true; + } + + /** + * Append to attribute of this element + * + * @access public + * @param string $name The name of the attribute + * @param string $chars The chars to append to the attribute of the element + */ + function appendToAttribute ($name, $chars) { + if (!isset ($this->_attributes[$name])) { + $this->_attributes[$name] = $chars; + return true; + } + $this->_attributes[$name] .= $chars; + return true; + } + + /** + * Set attribute + * + * @access public + * @param string $name The name of the attribute + * @param string $value The new value of the attribute + */ + function setAttribute ($name, $value) { + $this->_attributes[$name] = $value; + return true; + } + + /** + * Set code info + * + * @access public + * @param array $info The code info array + */ + function setCodeInfo ($info) { + $this->_codeInfo = $info; + $this->_flags = $info['flags']; + return true; + } + + /** + * Get attribute value + * + * @access public + * @param string $name The name of the attribute + */ + function attribute ($name) { + if (!isset ($this->_attributes[$name])) { + return null; + } + return $this->_attributes[$name]; + } + + /** + * Set flag that this element had a close tag + * + * @access public + */ + function setHadCloseTag () { + $this->_hadCloseTag = true; + } + + /** + * Set flag that this element was already processed by paragraph handling + * + * @access public + */ + function setParagraphHandled () { + $this->_paragraphHandled = true; + } + + /** + * Get flag if this element was already processed by paragraph handling + * + * @access public + * @return bool + */ + function paragraphHandled () { + return $this->_paragraphHandled; + } + + /** + * Get flag if this element had a close tag + * + * @access public + * @return bool + */ + function hadCloseTag () { + return $this->_hadCloseTag; + } + + /** + * Determines whether a criterium matches this node + * + * @access public + * @param string $criterium The criterium that is to be checked + * @param mixed $value The value that is to be compared + * @return bool True if this node matches that criterium + */ + function matchesCriterium ($criterium, $value) { + if ($criterium == 'tagName') { + return ($value == $this->_name); + } + if ($criterium == 'needsTextNodeModification') { + return (($this->getFlag ('opentag.before.newline', 'integer', BBCODE_NEWLINE_PARSE) != BBCODE_NEWLINE_PARSE || $this->getFlag ('opentag.after.newline', 'integer', BBCODE_NEWLINE_PARSE) != BBCODE_NEWLINE_PARSE || ($this->_hadCloseTag && ($this->getFlag ('closetag.before.newline', 'integer', BBCODE_NEWLINE_PARSE) != BBCODE_NEWLINE_PARSE || $this->getFlag ('closetag.after.newline', 'integer', BBCODE_NEWLINE_PARSE) != BBCODE_NEWLINE_PARSE))) == (bool)$value); + } + if (substr ($criterium, 0, 5) == 'flag:') { + $criterium = substr ($criterium, 5); + return ($this->getFlag ($criterium) == $value); + } + if (substr ($criterium, 0, 6) == '!flag:') { + $criterium = substr ($criterium, 6); + return ($this->getFlag ($criterium) != $value); + } + if (substr ($criterium, 0, 6) == 'flag=:') { + $criterium = substr ($criterium, 6); + return ($this->getFlag ($criterium) === $value); + } + if (substr ($criterium, 0, 7) == '!flag=:') { + $criterium = substr ($criterium, 7); + return ($this->getFlag ($criterium) !== $value); + } + return parent::matchesCriterium ($criterium, $value); + } + + /** + * Get first child if it is a text node + * + * @access public + * @return mixed + */ + function &firstChildIfText () { + $ret =& $this->firstChild (); + if (is_null ($ret)) { + return $ret; + } + if ($ret->_type != STRINGPARSER_NODE_TEXT) { + // DON'T DO $ret = null WITHOUT unset BEFORE! + // ELSE WE WILL ERASE THE NODE ITSELF! EVIL! + unset ($ret); + $ret = null; + } + return $ret; + } + + /** + * Get last child if it is a text node AND if this element had a close tag + * + * @access public + * @return mixed + */ + function &lastChildIfText () { + $ret =& $this->lastChild (); + if (is_null ($ret)) { + return $ret; + } + if ($ret->_type != STRINGPARSER_NODE_TEXT || !$this->_hadCloseTag) { + // DON'T DO $ret = null WITHOUT unset BEFORE! + // ELSE WE WILL ERASE THE NODE ITSELF! EVIL! + if ($ret->_type != STRINGPARSER_NODE_TEXT && !$ret->hadCloseTag ()) { + $ret2 =& $ret->_findPrevAdjentTextNodeHelper (); + unset ($ret); + $ret =& $ret2; + unset ($ret2); + } else { + unset ($ret); + $ret = null; + } + } + return $ret; + } + + /** + * Find next adjent text node after close tag + * + * returns the node or null if none exists + * + * @access public + * @return mixed + */ + function &findNextAdjentTextNode () { + $ret = null; + if (is_null ($this->_parent)) { + return $ret; + } + if (!$this->_hadCloseTag) { + return $ret; + } + $ccount = count ($this->_parent->_children); + $found = false; + for ($i = 0; $i < $ccount; $i++) { + if ($this->_parent->_children[$i]->equals ($this)) { + $found = $i; + break; + } + } + if ($found === false) { + return $ret; + } + if ($found < $ccount - 1) { + if ($this->_parent->_children[$found+1]->_type == STRINGPARSER_NODE_TEXT) { + return $this->_parent->_children[$found+1]; + } + return $ret; + } + if ($this->_parent->_type == STRINGPARSER_BBCODE_NODE_ELEMENT && !$this->_parent->hadCloseTag ()) { + $ret =& $this->_parent->findNextAdjentTextNode (); + return $ret; + } + return $ret; + } + + /** + * Find previous adjent text node before open tag + * + * returns the node or null if none exists + * + * @access public + * @return mixed + */ + function &findPrevAdjentTextNode () { + $ret = null; + if (is_null ($this->_parent)) { + return $ret; + } + $ccount = count ($this->_parent->_children); + $found = false; + for ($i = 0; $i < $ccount; $i++) { + if ($this->_parent->_children[$i]->equals ($this)) { + $found = $i; + break; + } + } + if ($found === false) { + return $ret; + } + if ($found > 0) { + if ($this->_parent->_children[$found-1]->_type == STRINGPARSER_NODE_TEXT) { + return $this->_parent->_children[$found-1]; + } + if (!$this->_parent->_children[$found-1]->hadCloseTag ()) { + $ret =& $this->_parent->_children[$found-1]->_findPrevAdjentTextNodeHelper (); + } + return $ret; + } + return $ret; + } + + /** + * Helper function for findPrevAdjentTextNode + * + * Looks at the last child node; if it's a text node, it returns it, + * if the element node did not have an open tag, it calls itself + * recursively. + */ + function &_findPrevAdjentTextNodeHelper () { + $lastnode =& $this->lastChild (); + if ($lastnode === null || $lastnode->_type == STRINGPARSER_NODE_TEXT) { + return $lastnode; + } + if (!$lastnode->hadCloseTag ()) { + $ret =& $lastnode->_findPrevAdjentTextNodeHelper (); + } else { + $ret = null; + } + return $ret; + } + + /** + * Get Flag + * + * @access public + * @param string $flag The requested flag + * @param string $type The requested type of the return value + * @param mixed $default The default return value + * @return mixed + */ + function getFlag ($flag, $type = 'mixed', $default = null) { + if (!isset ($this->_flags[$flag])) { + return $default; + } + $return = $this->_flags[$flag]; + if ($type != 'mixed') { + settype ($return, $type); + } + return $return; + } + + /** + * Set a flag + * + * @access public + * @param string $name The name of the flag + * @param mixed $value The value of the flag + */ + function setFlag ($name, $value) { + $this->_flags[$name] = $value; + return true; + } + + /** + * Validate code + * + * @access public + * @param string $action The action which is to be called ('validate' + * for first validation, 'validate_again' for + * second validation (optional)) + * @return bool + */ + function validate ($action = 'validate') { + if ($action != 'validate' && $action != 'validate_again') { + return false; + } + if ($this->_codeInfo['callback_type'] != 'simple_replace' && $this->_codeInfo['callback_type'] != 'simple_replace_single') { + if (!is_callable ($this->_codeInfo['callback_func'])) { + return false; + } + + if (($this->_codeInfo['callback_type'] == 'usecontent' || $this->_codeInfo['callback_type'] == 'usecontent?' || $this->_codeInfo['callback_type'] == 'callback_replace?') && count ($this->_children) == 1 && $this->_children[0]->_type == STRINGPARSER_NODE_TEXT) { + // we have to make sure the object gets passed on as a reference + // if we do call_user_func(..., &$this) this will clash with PHP5 + $callArray = array ($action, $this->_attributes, $this->_children[0]->content, $this->_codeInfo['callback_params']); + $callArray[] =& $this; + $res = call_user_func_array ($this->_codeInfo['callback_func'], $callArray); + if ($res) { + // ok, now, if we've got a usecontent type, set a flag that + // this may not be broken up by paragraph handling! + // but PLEASE do NOT change if already set to any other setting + // than BBCODE_PARAGRAPH_ALLOW_BREAKUP because we could + // override e.g. BBCODE_PARAGRAPH_BLOCK_ELEMENT! + $val = $this->getFlag ('paragraph_type', 'integer', BBCODE_PARAGRAPH_ALLOW_BREAKUP); + if ($val == BBCODE_PARAGRAPH_ALLOW_BREAKUP) { + $this->_flags['paragraph_type'] = BBCODE_PARAGRAPH_ALLOW_INSIDE; + } + } + return $res; + } + + // we have to make sure the object gets passed on as a reference + // if we do call_user_func(..., &$this) this will clash with PHP5 + $callArray = array ($action, $this->_attributes, null, $this->_codeInfo['callback_params']); + $callArray[] =& $this; + return call_user_func_array ($this->_codeInfo['callback_func'], $callArray); + } + return (bool)(!count ($this->_attributes)); + } + + /** + * Get replacement for this code + * + * @access public + * @param string $subcontent The content of all sub-nodes + * @return string + */ + function getReplacement ($subcontent) { + if ($this->_codeInfo['callback_type'] == 'simple_replace' || $this->_codeInfo['callback_type'] == 'simple_replace_single') { + if ($this->_codeInfo['callback_type'] == 'simple_replace_single') { + if (strlen ($subcontent)) { // can't be! + return false; + } + return $this->_codeInfo['callback_params']['start_tag']; + } + return $this->_codeInfo['callback_params']['start_tag'].$subcontent.$this->_codeInfo['callback_params']['end_tag']; + } + // else usecontent, usecontent? or callback_replace or callback_replace_single + // => call function (the function is callable, determined in validate()!) + + // we have to make sure the object gets passed on as a reference + // if we do call_user_func(..., &$this) this will clash with PHP5 + $callArray = array ('output', $this->_attributes, $subcontent, $this->_codeInfo['callback_params']); + $callArray[] =& $this; + return call_user_func_array ($this->_codeInfo['callback_func'], $callArray); + } + + /** + * Dump this node to a string + * + * @access protected + * @return string + */ + function _dumpToString () { + $str = "bbcode \"".substr (preg_replace ('/\s+/', ' ', $this->_name), 0, 40)."\""; + if (count ($this->_attributes)) { + $attribs = array_keys ($this->_attributes); + sort ($attribs); + $str .= ' ('; + $i = 0; + foreach ($attribs as $attrib) { + if ($i != 0) { + $str .= ', '; + } + $str .= $attrib.'="'; + $str .= substr (preg_replace ('/\s+/', ' ', $this->_attributes[$attrib]), 0, 10); + $str .= '"'; + $i++; + } + $str .= ')'; + } + return $str; + } +} + +?> \ No newline at end of file diff --git a/scripts/update.php b/scripts/update.php new file mode 100644 index 0000000..3b86e05 --- /dev/null +++ b/scripts/update.php @@ -0,0 +1,135 @@ +error()) { + echo "
    \n";
    +        echo $rss_sub->getError();
    +        echo "
    \n"; + die(); + } +if(defined('JLOG_ADMIN') AND !defined('JLOG_COMMENTS')) { + $data['rss'] = " + + + ".htmlspecialchars(JLOG_WEBSITE)." + ".htmlspecialchars(JLOG_PATH)." + ".htmlspecialchars(JLOG_DESCRIPTION)." + ".$l['language']." + ".date('r')." + http://blogs.law.harvard.edu/tech/rss + <a href="".JLOG_SOFTWARE_URL."">Jlog v".JLOG_SOFTWARE_VERSION."</a> + ".htmlspecialchars(JLOG_PUBLISHER)." ".htmlspecialchars(JLOG_EMAIL)." + &copy;".$now_date['year']." by ".htmlspecialchars(JLOG_PUBLISHER)."\n\n"; + + $data['rss_full'] = $data['rss']; +} +$data['sub'] = "
      \n"; + + if(!isset($cc)) $cc = count_comments(); + +$sub = 0; +while ($row = $rss_sub->fetch()) { +++$sub; + + if($sub <= JLOG_SUB_CURRENT) { + $tmp_comments = ""; + if(isset($cc[$row['id']]) AND $cc[$row['id']] != 0) $tmp_comments = " (".$cc[$row['id']].")"; + $data['sub'] .= "
    • ".strftime(JLOG_DATE_SUBCURRENT, $row['date'])." ".htmlspecialchars($row['topic'], ENT_QUOTES)."".$tmp_comments."
    • \n"; + } + + if($sub <= 15 AND defined('JLOG_ADMIN')) { + +# Kopfdaten + $data['rss'] .= " \n ".htmlspecialchars($row['topic'], ENT_QUOTES)."\n"; + $data['rss_full'] .= " \n ".htmlspecialchars($row['topic'], ENT_QUOTES)."\n"; + + $data['rss'] .= " ".blog($row['date'], $row['url'])."\n"; + $data['rss_full'] .= " ".blog($row['date'], $row['url'])."\n"; + + $data['rss'] .= " ".date('r', $row['date'])."\n"; + $data['rss_full'] .= " ".date('r', $row['date'])."\n"; + + $data['rss'] .= " ".blog($row['date'], $row['url'])."\n"; + $data['rss_full'] .= " ".blog($row['date'], $row['url'])."\n"; + + $data['rss'] .= " ".blog($row['date'], $row['url'])."#comments\n"; + $data['rss_full'] .= " ".blog($row['date'], $row['url'])."#comments\n"; + + $data['rss'] .= $categories->output_rss($row['id']); + $data['rss_full'] .= $categories->output_rss($row['id']); + + +# Inhaltsdaten + $data['rss'] .= " \n".htmlspecialchars($bbcode->parse($row['teaser']))."\n \n"; + $data['rss_full'] .= " \n"; + + if($row['teaserpiconblog'] == 1) $data['rss_full'] .= htmlspecialchars(""); + $data['rss_full'] .= htmlspecialchars($bbcode->parse($row['content']))."\n \n"; + + $data['rss'] .= " \n\n"; + $data['rss_full'] .= " \n\n"; + } +} +if(defined('JLOG_ADMIN') AND !defined('JLOG_COMMENTS')) { + $data['rss'] .= "\n"; + $data['rss_full'] .= "\n"; +} +$data['sub'] .= "
    "; + +if(defined('JLOG_ADMIN') AND !defined('JLOG_COMMENTS')) { + $file['rss'] = JLOG_BASEPATH.'personal'.DIRECTORY_SEPARATOR.'rss.xml'; + $file['rss_full'] = JLOG_BASEPATH.'personal'.DIRECTORY_SEPARATOR.'rss-full.xml'; +} + +$file['sub'] = JLOG_BASEPATH.'personal'.DIRECTORY_SEPARATOR.'subcurrent.inc'; + + ### Plugin Hook + if (isset($plugins) and is_object($plugins)) { + $data = $plugins->callHook('onUpdate', $data); + } + +$i = 0; + + foreach($file AS $d => $filename) { + if (is_writable($filename)) { + if (!$handle = fopen($filename, 'w')) { + $errors[] .= $l['admin']['can_not_open']." ($filename)"; + exit; + } + if (!fwrite($handle, $data[$d])) { + $errors[] .= $l['admin']['can_not_write']." ($filename)"; + exit; + } + ++$i; + fclose($handle); + } else { + $errors[] .= $l['admin']['no_wrtitenable']." ($filename)"; + } + } + + +if(count($errors) > 0) { + $c['main'] .= error_output($errors); +} + +if($i == 4 AND defined('JLOG_ADMIN') AND !defined('JLOG_COMMENTS')) $c['main'] .= "

    ".$l['admin']['rss_ok']."

    "; +unset($i); +unset($sub); + +?> diff --git a/scripts/update/102To110.php b/scripts/update/102To110.php new file mode 100644 index 0000000..0166c4e --- /dev/null +++ b/scripts/update/102To110.php @@ -0,0 +1,66 @@ +languages[] = $matches[1]; + } + } + + function getForm($l) + { + $html = "


    + +

    +

    Die Zeichenkodierung ihrer Template-Datei personal/template.tpl muss nach UTF-8 umgewandelt werden. Wenn diese Datei + beschreibbar ist (z.B.: chmod 777), wird dies vom Updatescript automatisch für sie erledigt. + Andernfalls müssen Sie die Konvertierung nachträglich manuell vornehmen.

    + "; + return $html; + } + + function performUpdate($l, $settings) + { + // convert all settings to utf8 + foreach($settings->d as $key => $value) { + $settings->d[$key] = utf8_encode($value); + } + + // reset hash of the administrator password + $settings->d['jlog_admin_password'] = md5($_POST['password']); + + // store chosen language + $lang = in_array($_POST['j110_language'], $this->languages) ? $_POST['j110_language'] : 'de'; + $settings->d['jlog_language'] = $lang; + + $update_errors = array(); + + /** + * On a correct Jlog 1.0.2 installation, the template is saved with an ISO + * encoding, so we're going to try to convert this to UTF-8 + */ + $template = JLOG_BASEPATH."personal".DIRECTORY_SEPARATOR."template.tpl"; + if(@file_put_contents($template, utf8_encode(@file_get_contents($template))) == false) { + $update_errors[] = 'Die Datei personal/template.tpl konnte nicht in UTF-8 Kodierung konvertiert werden.'; + } + + + if(empty($update_errors)) { + return true; + } + else { + return $update_errors; + } + } +} \ No newline at end of file diff --git a/scripts/update/110To111.php b/scripts/update/110To111.php new file mode 100644 index 0000000..62af685 --- /dev/null +++ b/scripts/update/110To111.php @@ -0,0 +1,14 @@ +Keine Einstellungen notwendig.

    '; + } + + function performUpdate($l, $settings) + { + return true; + } +} \ No newline at end of file diff --git a/scripts/update/111To112.php b/scripts/update/111To112.php new file mode 100644 index 0000000..b95394c --- /dev/null +++ b/scripts/update/111To112.php @@ -0,0 +1,28 @@ +Dieses Script behebt ein paar fehlerhafte Einstellungen.' + .' Es ist keine Konfiguration notwendig.

    '; + } + + function performUpdate($l, $settings) + { + // in jlog versions prior to jlog 1.1.2 we had escaping problems that caused + // a lot of backslashes in front of a double quote + // so we have to replace \" or \\" or \\\" and so on by ". + $data = array( + 'jlog_description' => $settings->getValue('jlog_description'), + 'jlog_website' => $settings->getValue('jlog_website'), + 'jlog_publisher' => $settings->getValue('jlog_publisher') + ); + foreach ($data as $key => $value) { + $value = preg_replace('=\\\\+"=', '"', $value); + $settings->setValue($key, $value); + } + + return true; + } +} \ No newline at end of file diff --git a/scripts/update/112To113.php b/scripts/update/112To113.php new file mode 100644 index 0000000..35f6045 --- /dev/null +++ b/scripts/update/112To113.php @@ -0,0 +1,15 @@ +Bitte beachten Sie, dass nach Durchführung dieses Updates eventuell einzelne Plugins nicht mehr funktionieren.
    ' + . 'Kontaktieren Sie in einem solchen Fall den Plugin-Autor bzzgl. eines Updates für das Plugin.

    '; + } + + function performUpdate($l, $settings) + { + return true; + } +} \ No newline at end of file diff --git a/scripts/update/Example.php b/scripts/update/Example.php new file mode 100644 index 0000000..d8faec7 --- /dev/null +++ b/scripts/update/Example.php @@ -0,0 +1,42 @@ +Do not need anything to configure for this update.

    '; + } + + /** + * This function has to perform the update + * + * Must return true, if everything went well, of an array of error + * messages, if something went wrong. + * The first parameter again in the language array. + */ + function performUpdate($l) + { + return true; + } +} \ No newline at end of file diff --git a/scripts/url_syntax.php b/scripts/url_syntax.php new file mode 100644 index 0000000..7657c12 --- /dev/null +++ b/scripts/url_syntax.php @@ -0,0 +1,248 @@ +#%"]'; +$reserved = '[;/?:@&=]'; +$uchar = "(?:${alphanum}|${safe}|${extra}|${escape})"; +$xchar = "(?:${alphanum}|${safe}|${extra}|${reserved}|${escape})"; +$uchar = str_replace (']|[', '', $uchar); // Make string smaller, and speed up regex. +$uchar = str_replace (']|[', '', $xchar); // Make string smaller, and speed up regex. + +# URL schemeparts for ip based protocols: +$user = "(?:(?:${uchar}|[;?&=])*)"; +$password = "(?:(?:${uchar}|[;?&=])*)"; +$hostnumber = "(?:${digits}(?:${dot}${digits}){3})"; +$toplabel = "(?:${alpha}(?:(?:${alphanum}|-)*${alphanum})?)"; +$domainlabel = "(?:${alphanum}(?:(?:${alphanum}|-)*${alphanum})?)"; +$hostname = "(?:(?:${domainlabel}${dot})*${toplabel})"; +$host = "(?:${hostname}|${hostnumber})"; +$hostport = "(?:${host}(?::${digits})?)"; +$login = "(?:(?:${user}(?::${password})?\@)?${hostport})"; + +# The predefined schemes: + +# FTP (see also RFC959) +$fsegment = "(?:(?:${uchar}|[?:\@&=])*)"; +$fpath = "(?:${fsegment}(?:/${fsegment})*)"; +$ftpurl = "(?:ftp://${login}(?:/${fpath}(?:;type=[AIDaid])?)?)"; + +# FILE +$fileurl = "(?:file://(?:${host}|localhost)?/${fpath})"; + +# HTTP +$hsegment = "(?:(?:${uchar}|[~;:\@&=])*)"; +$search = "(?:(?:${uchar}|[;:\@&=])*)"; +$hpath = "(?:${hsegment}(?:/${hsegment})*)"; +$httpurl = "(?:https?://${hostport}(?:/${hpath}(?:${qm}${search})?)?)"; + +# GOPHER (see also RFC1436) +$gopher_plus = "(?:${xchar}*)"; +$selector = "(?:${xchar}*)"; +$gtype = $xchar; // Omitted parens! +$gopherurl = "(?:gopher://${hostport}(?:/${gtype}(?:${selector}" . + "(?:%09${search}(?:%09${gopher_plus})?)?)?)?)"; + +# MAILTO (see also RFC822) +$encoded822addr = "(?:$xchar+)"; +$mailtourl = "(?:mailto:$encoded822addr)"; +$mailtonpurl = $encoded822addr; + +# NEWS (see also RFC1036) +$article = "(?:(?:${uchar}|[;/?:&=])+\@${host})"; +$group = "(?:${alpha}(?:${alphanum}|[_.+-])*)"; +$grouppart = "(?:${article}|${group}|${ast})"; +$newsurl = "(?:news:${grouppart})"; + +# NNTP (see also RFC977) +$nntpurl = "(?:nntp://${hostport}/${group}(?:/${digits})?)"; + +# TELNET +$telneturl = "(?:telnet://${login}/?)"; + +# WAIS (see also RFC1625) +$wpath = "(?:${uchar}*)"; +$wtype = "(?:${uchar}*)"; +$database = "(?:${uchar}*)"; +$waisdoc = "(?:wais://${hostport}/${database}/${wtype}/${wpath})"; +$waisindex = "(?:wais://${hostport}/${database}${qm}${search})"; +$waisdatabase = "(?:wais://${hostport}/${database})"; +# $waisurl = "(?:${waisdatabase}|${waisindex}|${waisdoc})"; +# Speed up: the 3 types share a common prefix. +$waisurl = "(?:wais://${hostport}/${database}" . + "(?:(?:/${wtype}/${wpath})|${qm}${search})?)"; + +# PROSPERO +$fieldvalue = "(?:(?:${uchar}|[?:\@&])*)"; +$fieldname = "(?:(?:${uchar}|[?:\@&])*)"; +$fieldspec = "(?:;${fieldname}=${fieldvalue})"; +$psegment = "(?:(?:${uchar}|[?:\@&=])*)"; +$ppath = "(?:${psegment}(?:/${psegment})*)"; +$prosperourl = "(?:prospero://${hostport}/${ppath}(?:${fieldspec})*)"; + +# LDAP (see also RFC1959) +# First. import stuff from RFC 1779 (Distinguished Names). +# We've modified things a bit. +$dn_separator = "(?:[;,])"; +$dn_optional_space = "(?:${nl}?${space}*)"; +$dn_spaced_separator = "(?:${dn_optional_space}${dn_separator}" . + "${dn_optional_space})"; +$dn_oid = "(?:${digits}(?:${dot}${digits})*)"; +$dn_keychar = "(?:${xalphanum}|${space})"; +$dn_key = "(?:${dn_keychar}+|(?:OID|oid)${dot}${dn_oid})"; +$dn_string = "(?:${uchar}*)"; +$dn_attribute = "(?:(?:${dn_key}${dn_optional_space}=" . + "${dn_optional_space})?${dn_string})"; +$dn_name_component = "(?:${dn_attribute}(?:${dn_optional_space}" . + "${plus}${dn_optional_space}${dn_attribute})*)"; +$dn_name = "(?:${dn_name_component}" . + "(?:${dn_spaced_separator}${dn_name_component})*" . + "${dn_spaced_separator}?)"; + +# RFC 1558 defines the filter syntax, but that requires a PDA to recognize. +# Since that's too powerful for Perl's REs, we allow any char between the +# parenthesis (which have to be there.) +$ldap_filter = "(?:\(${xchar}+\))"; + +# This is from RFC 1777. It defines an attributetype as an 'OCTET STRING', +# whatever that is. +$ldap_attr_type = "(?:${uchar}+)"; # I'm just guessing here. + # The RFCs aren't clear. + +# Now we are at the grammar of RFC 1959. +$ldap_attr_list = "(?:${ldap_attr_type}(?:,${ldap_attr_type})*)"; +$ldap_attrs = "(?:${ldap_attr_list}?)"; + +$ldap_scope = "(?:base|one|sub)"; +$ldapurl = "(?:ldap://(?:${hostport})?/${dn_name}" . + "(?:${qm}${ldap_attrs}" . + "(?:${qm}${ldap_scope}(?:${qm}${ldap_filter})?)?)?)"; + + +# RFC 2056 defines the format of URLs for the Z39.50 protocol. +$z_database = "(?:${uchar}+)"; +$z_docid = "(?:${uchar}+)"; +$z_elementset = "(?:${uchar}+)"; +$z_recordsyntax = "(?:${uchar}+)"; +$z_scheme = "(?:z39${dot}50[rs])"; +$z39_50url = "(?:${z_scheme}://${hostport}" . + "(?:/(?:${z_database}(?:${plus}${z_database})*" . + "(?:${qm}${z_docid})?)?" . + "(?:;esn=${z_elementset})?" . + "(?:;rs=${z_recordsyntax}" . + "(?:${plus}${z_recordsyntax})*)?))"; + + +# RFC 2111 defines the format for cid/mid URLs. +$url_addr_spec = "(?:(?:${uchar}|[;?:@&=])*)"; +$message_id = $url_addr_spec; +$content_id = $url_addr_spec; +$cidurl = "(?:cid:${content_id})"; +$midurl = "(?:mid:${message_id}(?:/${content_id})?)"; + + +# RFC 2122 defines the Vemmi URLs. +$vemmi_attr = "(?:(?:${uchar}|[/?:@&])*)"; +$vemmi_value = "(?:(?:${uchar}|[/?:@&])*)"; +$vemmi_service = "(?:(?:${uchar}|[/?:@&=])*)"; +$vemmi_param = "(?:;${vemmi_attr}=${vemmi_value})"; +$vemmiurl = "(?:vemmi://${hostport}" . + "(?:/${vemmi_service}(?:${vemmi_param}*))?)"; + +# RFC 2192 for IMAP URLs. +# Import from RFC 2060. +# $imap4_astring = ""; +# $imap4_search_key = ""; +# $imap4_section_text = ""; +$imap4_nz_number = $nz_digits; +$achar = "(?:${uchar}|[&=~])"; +$bchar = "(?:${uchar}|[&=~:\@/])"; +$enc_auth_type = "(?:${achar}+)"; +$enc_list_mbox = "(?:${bchar}+)"; +$enc_mailbox = "(?:${bchar}+)"; +$enc_search = "(?:${bchar}+)"; +$enc_section = "(?:${bchar}+)"; +$enc_user = "(?:${achar}+)"; +$i_auth = "(?:;[Aa][Uu][Tt][Hh]=(?:${ast}|${enc_auth_type}))"; +$i_list_type = "(?:[Ll](?:[Ii][Ss][Tt]|[Ss][Uu][Bb]))"; +$i_mailboxlist = "(?:${enc_list_mbox}?;[Tt][Yy][Pp][Ee]=${i_list_type})"; +$i_uidvalidity = "(?:;[Uu][Ii][Dd][Vv][Aa][Ll][Ii][Dd][Ii][Tt][Yy]=" . + "${imap4_nz_number})"; +$i_messagelist = "(?:${enc_mailbox}(?:${qm}${enc_search})?" . + "(?:${i_uidvalidity})?)"; +$i_section = "(?:/;[Ss][Ee][Cc][Tt][Ii][Oo][Nn]=${enc_section})"; +$i_uid = "(?:/;[Uu][Ii][Dd]=${imap4_nz_number})"; +$i_messagepart = "(?:${enc_mailbox}(?:${i_uidvalidity})?${i_uid}" . + "(?:${i_section})?)"; +$i_command = "(?:${i_mailboxlist}|${i_messagelist}|${i_messagepart})"; +$i_userauth = "(?:(?:${enc_user}(?:${i_auth})?)|" . + "(?:${i_auth}(?:${enc_user})?))"; +$i_server = "(?:(?:${i_userauth}\@)?${hostport})"; +$imapurl = "(?:imap://${i_server}/(?:$i_command)?)"; + +# RFC 2224 for NFS. +$nfs_mark = '[\$\-_.\!~*\'(),]'; +$nfs_unreserved = "(?:${alphanum}|${nfs_mark})"; +$nfs_unreserved = str_replace (']|[', '', $nfs_unreserved); // Make string smaller, and speed up regex. +$nfs_pchar = "(?:${nfs_unreserved}|${escape}|[:\@&=+])"; +$nfs_segment = "(?:${nfs_pchar}*)"; +$nfs_path_segs = "(?:${nfs_segment}(?:/${nfs_segment})*)"; +$nfs_url_path = "(?:/?${nfs_path_segs})"; +$nfs_rel_path = "(?:${nfs_path_segs}?)"; +$nfs_abs_path = "(?:/${nfs_rel_path})"; +$nfs_net_path = "(?://${hostport}(?:${nfs_abs_path})?)"; +$nfs_rel_url = "(?:${nfs_net_path}|${nfs_abs_path}|${nfs_rel_path})"; +$nfsurl = "(?:nfs:${nfs_rel_url})"; + +$valid_types = array ( + 'http', 'ftp', 'news', 'nntp', 'telnet', 'gopher', 'wais', 'mailto', + 'mailtonp', 'file', 'prospero', 'ldap', 'z39_50', 'cid', 'mid', 'vemmi', + 'imap', 'nfs' +); + +# Combining all the different URL formats into a single regex. + +$valid = false; + +if (!is_array ($types)) { + $types = array ($types); +} + +foreach ($types as $type) { + if (!in_array ($type, $valid_types)) { + continue; + } + $re = $type.'url'; + if (preg_match ('!^'.$$re.'$!i', $url2check)) { + $valid = $type; + break; + } +} + +return $valid; + +} + +?> diff --git a/scripts/version.inc.php b/scripts/version.inc.php new file mode 100644 index 0000000..23677aa --- /dev/null +++ b/scripts/version.inc.php @@ -0,0 +1,31 @@ +".$l['content_search_header'].""; + + $searchstring = strip($_GET['q']); + + $c['main'] .= '
    +

    +

    +
    + +'; + +if(!empty($searchstring)) { + + $sql_searchstring = escape_for_mysql($searchstring); + + $sql = " + SELECT + id, + url, + UNIX_TIMESTAMP(date) AS date_url, + 0 AS comment_id, + topic, + UNIX_TIMESTAMP(date) AS date, + keywords, + teaser, + section, + comments, + MATCH ( topic, keywords, teaser, content ) AGAINST ('".$sql_searchstring."') AS scoring + FROM ".JLOG_DB_CONTENT." + WHERE + MATCH ( topic, keywords, teaser, content ) AGAINST ( '".$sql_searchstring."' ) + + UNION + SELECT + ".JLOG_DB_COMMENTS.".reference AS id, + ".JLOG_DB_CONTENT.".url AS url, + UNIX_TIMESTAMP(".JLOG_DB_CONTENT.".date) AS date_url, + ".JLOG_DB_COMMENTS.".id AS comment_id, + name AS topic, + UNIX_TIMESTAMP(".JLOG_DB_COMMENTS.".date) AS date, + 'comment_keywords' AS keywords, + ".JLOG_DB_COMMENTS.".content AS teaser, + 'comment', + 2, + MATCH(name, city, email, homepage, ".JLOG_DB_COMMENTS.".content) AGAINST ('".$sql_searchstring."') AS scoring + FROM ".JLOG_DB_COMMENTS.", ".JLOG_DB_CONTENT." + WHERE + MATCH ( name, city, email, homepage, ".JLOG_DB_COMMENTS.".content ) AGAINST ( '".$sql_searchstring."' ) + AND ".JLOG_DB_COMMENTS.".reference = ".JLOG_DB_CONTENT.".id + AND ".JLOG_DB_COMMENTS.".type = '' + + ORDER BY scoring desc + LIMIT 40;"; + + + $search = new Query($sql); + if($search->error()) { + echo "
    \n";
    +        echo $search->getError();
    +        echo "
    \n"; + die(); + } + + if($search->numRows() < 1) { + $c['main'] .= "

    ".$l['content_nothing_found']."

    "; + } + else { + $cc = count_comments(); + $c['main'] .= "\n"; + } +} +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> diff --git a/setup.php b/setup.php new file mode 100644 index 0000000..4aedf19 --- /dev/null +++ b/setup.php @@ -0,0 +1,315 @@ +importDataByArray(strip($_POST)); + + // validate user entry + if(count($errors = $setup->validate()) == 0) { + define("JLOG_BASEPATH", $setup->getValue('jlog_basepath')); + if(is_writable(JLOG_BASEPATH.'personal'.DIRECTORY_SEPARATOR)) { + $c .= "
      \n"; + + // build some MySQL tables + if(count($errors = create_mysql_tables($setup->getValue(false))) == 0) { + $c .= "
    • ".$l['admin']['s_tables_ok']."
    • \n"; + + // create and chmod on some directories and files + if(count($errors = do_personal()) == 0) { + $c .= "
    • ".$l['admin']['s_personal_ok']."
    • \n"; + + // build settings.inc.php + if(count($errors = $setup->do_settings()) == 0) $c .= "
    • ".$l['admin']['master_ok']."
    • \n"; + } + $c .= "
    "; + } + } + else { + $errors[] = $l['admin']['s_personal_not_wrtbl']; + } + } + if(count($errors) > 0) { + $c .= error_output($errors); + $c .= $setup->form_output(); + } + else $c .= "

    ".$l['admin']['s_ready_head']."

    "."

    ".$l['admin']['s_ready']."

    "; + } + else { + // validate PHP and MySQL versions + if(!version_compare(phpversion(), JLOG_PHPV, ">=") == 1) $errors[] = $l['admin']['s_phpv_tolow']; + if(!is_writable($basepath.'personal'.DIRECTORY_SEPARATOR)) $errors[] = $l['admin']['s_personal_not_wrtbl']; + if(!is_writable($basepath.'img'.DIRECTORY_SEPARATOR)) $errors[] = $l['admin']['s_img_not_wrtbl']; + + if(empty($errors)) { + // output form + $setup->importSuggestedData(); + $c .= $setup->form_output(); + } + else $c .= error_output($errors); + } + + echo do_htmlpage($c); + + + + + +#### some needed functions for the setup #### + + function create_mysql_tables($data) { + # returns false if all tables were created, if not returns the $errors array + + $sql['content'] = ' + CREATE TABLE `'.$data['jlog_db_prefix'].'content` ( + id int(11) auto_increment, + url varchar(200), + topic varchar(255), + date datetime, + teaser mediumtext, + teaserpic varchar(10), + teaserpiconblog tinyint(1), + keywords varchar(255), + content longtext, + comments tinyint(1) default \'1\', + allowpingback tinyint(1) default \'1\', + section varchar(10) default \'weblog\', + UNIQUE KEY id (id), + FULLTEXT KEY content_index (content, topic, teaser, keywords) + ) TYPE=MyISAM CHARACTER SET utf8;'; + + $sql['comments'] = ' + CREATE TABLE `'.$data["jlog_db_prefix"].'comments` ( + id int(11) auto_increment, + sid varchar(35), + name varchar(255), + city varchar(255), + email varchar(255), + homepage varchar(255), + content mediumtext, + date datetime, + reference int(11), + mail_by_comment tinyint(1), + type varchar(30) default \'\', + PRIMARY KEY (id), + UNIQUE KEY sid (sid), + FULLTEXT KEY comments_index ( name, city, email, homepage, content ) + ) TYPE=MyISAM CHARACTER SET utf8;'; + + $sql['categories'] = ' + CREATE TABLE `'.$data["jlog_db_prefix"].'categories` ( + id tinyint(4) auto_increment, + name tinytext, + url varchar(100), + description text, + UNIQUE KEY id (id), + UNIQUE KEY url (url) + ) TYPE=MyISAM CHARACTER SET utf8;'; + + $sql['catassign'] = ' + CREATE TABLE `'.$data["jlog_db_prefix"].'catassign` ( + content_id int(11), + cat_id tinyint(4) + ) TYPE=MyISAM CHARACTER SET utf8;'; + + $sql['attributes'] = ' + CREATE TABLE `'.$data["jlog_db_prefix"].'attributes` ( + id int(10) unsigned NOT NULL auto_increment, + entry_id int(10) unsigned NOT NULL default \'0\', + name varchar(120) NOT NULL default \'\', + value varchar(250) NOT NULL default \'\', + PRIMARY KEY (id), + KEY entry_id (entry_id) + ) TYPE=MyISAM CHARACTER SET utf8;'; + + global $l; + + if(!@mysql_connect($data['jlog_db_url'], $data['jlog_db_user'], $data['jlog_db_pwd'])) $errors[] = "Falsche Zugangsdaten | ".mysql_error(); + elseif(!@mysql_select_db($data['jlog_db'])) $errors[] = "Datenbank ".$data['jlog_db']." extistiert nicht".mysql_error(); + elseif(!version_compare(mysql_get_server_info(), JLOG_MYSQLV, ">=") == 1) $errors[] = $l['admin']['s_mysqlv_tolow']; + else { + new Query("SET NAMES utf8"); + $create['content'] = new Query($sql['content']); + if($create['content']->error()) $errors[] = "MySQL
    ".$create['content']->getError()."
    "; + $create['comments'] = new Query($sql['comments']); + if($create['comments']->error()) $errors[] = "MySQL
    ".$create['comments']->getError()."
    "; + $create['categories'] = new Query($sql['categories']); + if($create['categories']->error()) $errors[] = "MySQL
    ".$create['categories']->getError()."
    "; + $create['catassign'] = new Query($sql['catassign']); + if($create['catassign']->error()) $errors[] = "MySQL
    ".$create['catassign']->getError()."
    "; + $create['attributes'] = new Query($sql['attributes']); + if($create['attributes']->error()) $errors[] = "MySQL
    ".$create['attributes']->getError()."
    "; + } + + return $errors; + } + + function do_personal() { + # returns true if all files and dirs could be generated + # if not returns the $errors array + + global $l; + + // make some dirs + $oldmask = umask(0); + + // make some files + if(!fopen(JLOG_BASEPATH."personal".DIRECTORY_SEPARATOR."settings.inc.php", "w")) $errors[] = $l['admin']['s_problem_fwrite']." /personal/settings.inc.php"; + if(!fopen(JLOG_BASEPATH."personal".DIRECTORY_SEPARATOR."rss.xml", "w")) $errors[] = $l['admin']['s_problem_fwrite']." /personal/rss.xml"; + if(!fopen(JLOG_BASEPATH."personal".DIRECTORY_SEPARATOR."rss-full.xml", "w")) $errors[] = $l['admin']['s_problem_fwrite']." /personal/rss-full.xml"; + if(!fopen(JLOG_BASEPATH."personal".DIRECTORY_SEPARATOR."subcurrent.inc", "w")) $errors[] = $l['admin']['s_problem_fwrite']." /personal/subcurrent.inc"; + + // chmod 666 so that the user have the ability to delete/write to this files + if(!chmod(JLOG_BASEPATH."personal".DIRECTORY_SEPARATOR."settings.inc.php", 0666)) $errors[] = $l['admin']['s_problem_chmod']." /personal/settings.inc.php"; + if(!chmod(JLOG_BASEPATH."personal".DIRECTORY_SEPARATOR."rss.xml", 0666)) $errors[] = $l['admin']['s_problem_chmod']." /personal/rss.xml"; + if(!chmod(JLOG_BASEPATH."personal".DIRECTORY_SEPARATOR."rss-full.xml", 0666)) $errors[] = $l['admin']['s_problem_chmod']." /personal/rss-full.xml"; + if(!chmod(JLOG_BASEPATH."personal".DIRECTORY_SEPARATOR."subcurrent.inc", 0666)) $errors[] = $l['admin']['s_problem_chmod']." /personal/subcurrent.inc"; + + umask($oldmask); + + return $errors; + } + + function do_htmlpage($content) { + + return ' + + SETUP Jlog ' . JLOG_NEW_VERSION . ' + + + + + +
    +

    SETUP

    + '.$content.' +
    + +'; + } + + function getlang ($allowed, $default) { + $string = $_SERVER['HTTP_ACCEPT_LANGUAGE']; + if (empty($string)) { + return $default; + } + + $accepted_languages = preg_split('/,\s*/', $string); + + $cur_l = $default; + $cur_q = 0; + + foreach ($accepted_languages as $accepted_language) { + $res = preg_match ('/^([a-z]{1,8}(?:-[a-z]{1,8})*)'. + '(?:;\s*q=(0(?:\.[0-9]{1,3})?|1(?:\.0{1,3})?))?$/i', $accepted_language, $matches); + + if (!$res) { + continue; + } + + $lang_code = explode ('-', $matches[1]); + + if (isset($matches[2])) { + $lang_quality = (float)$matches[2]; + } else { + $lang_quality = 1.0; + } + + while (count ($lang_code)) { + if (in_array (strtolower (join ('-', $lang_code)), $allowed)) { + if ($lang_quality > $cur_q) { + $cur_l = strtolower (join ('-', $lang_code)); + $cur_q = $lang_quality; + break; + } + } + array_pop ($lang_code); + } + } + + return $cur_l; + } diff --git a/stop.php b/stop.php new file mode 100644 index 0000000..f0bba47 --- /dev/null +++ b/stop.php @@ -0,0 +1,27 @@ +error()) { + echo "
    \n";
    +        echo $stop->getError();
    +        echo "
    \n"; + die(); + } + + $c['main'] = "

    ".$l['comments_stop_successful']."

    "; + +require(JLOG_BASEPATH.'scripts'.DIRECTORY_SEPARATOR.'do_template.php'); +echo $body; +?> diff --git a/xmlrpc.php b/xmlrpc.php new file mode 100644 index 0000000..d960502 --- /dev/null +++ b/xmlrpc.php @@ -0,0 +1,244 @@ +get_ping($args); + if($pingback->validate()) { + $pingback->write_to_db(); + return "Thanks for your ping."; + } + } + $server = new IXR_Server(array('pingback.ping' => 'ping')); + } + +class Jlog_GetPingback { + + var $errors = array(); // array + var $method = ""; // string + var $sourceURI = ""; // string + var $targetURI = array(); // array incl: orginal, parsed [array from parse_url()], y, m, url + var $title = ""; // string + var $sid = ""; // string + + function Jlog_GetPingback($db_content, $db_comments, $path, $sid = NULL) { + $this->db_content = $db_content; + $this->db_comments = $db_comments; + $this->path = $path; + if($sid != NULL) $this->sid = $sid; + } + + function get_ping($uris) { + + $ymurls = array(); + $tmp_host_got = ""; + $tmp_host_path_parsed = array(); + $tmp_host_path = ""; + + $this->sourceURI = trim($uris[0]); + $this->targetURI['orginal'] = trim(str_replace(array('"','<', '>', '&'), array('"', '<', '>', '&'), $uris[1])); + $this->targetURI['parsed'] = parse_url($this->targetURI['orginal']); + $tmp_host_got = str_replace('www.', '', $this->targetURI['parsed']['host']).$this->targetURI['parsed']['path']; + $tmp_host_path_parsed = parse_url($this->path); + $tmp_host_path = str_replace('www.', '', $tmp_host_path_parsed['host']).'/log.php'; + + if(!empty($this->targetURI['parsed']['query']) AND ($tmp_host_got == $tmp_host_path)) { + + $ymurls = explode('&', $this->targetURI['parsed']['query']); + $this->_counter = count($ymurls); + + foreach($ymurls AS $ymurl) { + if(substr($ymurl, 0, 2) == 'y=') $this->targetURI['y'] = substr($ymurl, 2); + elseif(substr($ymurl, 0, 2) == 'm=') $this->targetURI['m'] = substr($ymurl, 2); + elseif(substr($ymurl, 0, 4) == 'url=') $this->targetURI['url'] = substr($ymurl, 4); + } + } + else { + ### Plugin Hook + global $plugins; + $tmp_URI = $plugins->callHook('xmlrpcPermalink', $this->targetURI['orginal']); + + $regex = "#^".$this->path."/([0-9]{4})/?([0-9]{2})/?([a-z0-9_\-]+)$#"; + preg_match($regex, $tmp_URI, $matches); + $this->targetURI['y'] = $matches[1]; + $this->targetURI['m'] = $matches[2]; + $this->targetURI['url'] = $matches[3]; + } + + } + + function validate() { + + + if(!strpos($this->targetURI['orginal'], str_replace(array('http://', 'https://'), '', str_replace('www.', '', $this->path)))) + $this->send_error(0, 'Target URI ('.$this->targetURI['orginal'].') is not this page: '.$this->path); + + + // is there such a post? + $sql = "SELECT id, allowpingback FROM ".$this->db_content." WHERE + YEAR(date) = '".escape_for_mysql($this->targetURI['y'])."' AND + MONTH(date) = '".escape_for_mysql($this->targetURI['m'])."' AND + url = '".escape_for_mysql($this->targetURI['url'])."' AND + section = 'weblog' + LIMIT 1"; + $blog = new Query($sql); + if($blog->error()) $this->send_error(0, 'Could not read my database.'); + $blogrow = $blog->fetch(); + + if($blog->numRows() != 1) $this->send_error(32, 'The specified target URI does not exist.'.$this->targetURI['orginal']); + if($blogrow['allowpingback'] === 0) $this->send_error(33, 'The specified target URI cannot be used as a target. It it is not a pingback-enabled resource.'); + else $this->reference = $blogrow['id']; + + $s =& new HTTP_Request($this->sourceURI); + if(PEAR::isError($s->sendRequest())) $this->send_error(16, 'The source URI does not exist.'); + else { + $source = $s->getResponseBody(); + $source = strip_tags(str_replace(''); + + if (!$this->isLinkInHTML($this->targetURI['orginal'], $source)) + $this->send_error(17, 'The source URI does not contain a link to the target URI, and so cannot be used as a source.'); + + preg_match('|([^<]*?)|is', $source, $title); + + if(! $utf8 = preg_match ('/charset\s*=\s*utf-8/i', $s->getResponseHeader("Content-Type"))) + $utf8 = 'application/xhtml+xml' == strtolower(trim($s->getResponseHeader("Content-Type"))); + + // since text in database is utf8 encoded, we need to *en*code the title to utf8 if it isn't already, not *de*code it + $this->title = empty($title[1]) ? $this->sourceURI : html_entity_decode($utf8 ? $title[1] : utf8_encode($title[1])); + } + + $sql = "SELECT COUNT(*) AS ping FROM ".$this->db_comments." WHERE + reference = '".escape_for_mysql($blogrow['id'])."' AND + homepage = '".escape_for_mysql($this->sourceURI)."' AND + name = '".escape_for_mysql($this->title)."' AND + type = 'pingback' + LIMIT 1"; + $p = new Query($sql); + if($p->error()) $this->send_error(0, 'Could not read my database.'); + $f = $p->fetch(); + + if($f['ping'] > 0) $this->send_error(48, 'The pingback has already been registered.'); + + if(count($this->errors) > 0) return false; + else return true; + } + + function write_to_db() { + $sql = "INSERT INTO ".$this->db_comments." ( + sid, + name, + homepage, + reference, + date, + type + ) + VALUES ( + '".escape_for_mysql($this->sid)."', + '".escape_for_mysql($this->title)."', + '".escape_for_mysql($this->sourceURI)."', + '".escape_for_mysql($this->reference)."', + NOW(), + 'pingback' + )"; + $ping = new Query($sql); + + if($ping->error()) $this->send_error(0, 'Could not write to database.'); + + } + + function send_error($nr, $string) { + $this->errors[] = $nr." ".$string; + $error = new IXR_Error($nr, $string); + $this->send_xml($error->getXml()); + } + + function get_errors() { + return $this->errors; + } + + function send_xml($xml) { + header('Connection: close'); + header('Content-Length: '.strlen($xml)); + header('Content-Type: text/xml'); + header('Date: '.date('r')); + echo $xml; + exit; + } + + function isLinkInHTML($search, $html) { + preg_match_all('#]+href\s*=\s*("([^"]+)"|\'([^\']+)\')[^>]*>(.+)#Ui', $html, $matches); + $links = array_unique(array_merge($matches[2], $matches[3])); + + foreach($links as $link) { + if($search === str_replace('&', '&', $link)) return true; + } + return false; + } + +} + +class Jlog_SendPingback { + + var $pageslinkedto = array(); + var $useragent = ""; + + function Jlog_SendPingback($html, $pagelinkedfrom, $useragent) { + // neet to prevent & in url + $this->pagelinkedfrom = htmlspecialchars_decode($pagelinkedfrom); + $this->useragent = $useragent; + + preg_match_all('#]+href\s*=\s*("([^"]+)"|\'([^\']+)\')[^>]*>(.+)#Ui', $html, $matches); + $pageslinkedto = array(); + $pageslinkedto = array_unique(array_merge($matches[2], $matches[3])); + $count = count($pageslinkedto); + for($i = 0; $count > $i; $i++) { + if(substr($pageslinkedto[$i], 0, 4) !== "http") unset($pageslinkedto[$i]); + // htmlspecialchars_decode is easier than str_replace + else $pageslinkedto[$i] = htmlspecialchars_decode($pageslinkedto[$i]); + } + $this->pageslinkedto = $pageslinkedto; + } + + function doPingbacks() { + foreach($this->pageslinkedto as $pagelinkedto) { + $feedback[] = $this->send($pagelinkedto); + } + return $feedback; + } + + function send($pagelinkedto) { + + $s =& new HTTP_Request($pagelinkedto); + if(PEAR::isError($s->sendRequest())) return $pagelinkedto." — Error: The source URI does not exist."; + else { + $xmlrpcserver = $s->getResponseHeader("X-Pingback"); + if(!empty($xmlrpcserver)); + else { + if(preg_match('', $s->getResponseBody(), $matches)) { + $xmlrpcserver = $matches[1]; + } + else return $pagelinkedto." — This is not a pingback-enabled resource."; + } + + $client = new IXR_Client($xmlrpcserver); + $client->timeout = 3; + $client->useragent = $this->useragent; + + // when set to true, this outputs debug messages by itself + $client->debug = false; + + if (! $client->query('pingback.ping', $this->pagelinkedfrom, $pagelinkedto ) ) + return $pagelinkedto." — Error: ".$client->getErrorMessage(); + + else return $pagelinkedto." — ".$client->getResponse(); + } + } + +} +?>