]> source.dussan.org Git - nextcloud-server.git/commitdiff
New app: contacts
authorJakob Sack <kde@jakobsack.de>
Sat, 6 Aug 2011 20:32:06 +0000 (22:32 +0200)
committerJakob Sack <kde@jakobsack.de>
Sat, 6 Aug 2011 20:32:06 +0000 (22:32 +0200)
14 files changed:
apps/contacts/appinfo/app.php [new file with mode: 0644]
apps/contacts/appinfo/info.xml [new file with mode: 0644]
apps/contacts/carddav.php [new file with mode: 0644]
apps/contacts/css/styles.css [new file with mode: 0644]
apps/contacts/details.php [new file with mode: 0644]
apps/contacts/img/icon.png [new file with mode: 0644]
apps/contacts/index.php [new file with mode: 0644]
apps/contacts/js/interface.js [new file with mode: 0644]
apps/contacts/lib/addressbook.php [new file with mode: 0644]
apps/contacts/lib/connector_sabre.php [new file with mode: 0644]
apps/contacts/photo.php [new file with mode: 0644]
apps/contacts/templates/_contacts.php [new file with mode: 0644]
apps/contacts/templates/_details.php [new file with mode: 0644]
apps/contacts/templates/index.php [new file with mode: 0644]

diff --git a/apps/contacts/appinfo/app.php b/apps/contacts/appinfo/app.php
new file mode 100644 (file)
index 0000000..f38a45f
--- /dev/null
@@ -0,0 +1,18 @@
+<?php
+
+OC::$CLASSPATH['OC_Contacts_Addressbook'] = 'apps/contacts/lib/addressbook.php';
+OC::$CLASSPATH['OC_Connector_Sabre_CardDAV'] = 'apps/contacts/lib/connector_sabre.php';
+
+OC_App::register( array( 
+  'order' => 10,
+  'id' => 'contacts',
+  'name' => 'Contacts' ));
+
+OC_App::addNavigationEntry( array( 
+  'id' => 'contacts_index',
+  'order' => 10,
+  'href' => OC_Helper::linkTo( 'contacts', 'index.php' ),
+  'icon' => OC_Helper::imagePath( 'contacts', 'icon.png' ),
+  'name' => 'Addressbook' ));
+
+?>
diff --git a/apps/contacts/appinfo/info.xml b/apps/contacts/appinfo/info.xml
new file mode 100644 (file)
index 0000000..93463b9
--- /dev/null
@@ -0,0 +1,9 @@
+<?xml version="1.0"?> 
+<info>
+       <id>contacts</id>
+       <name>Contacts</name>
+       <version>0.1</version>
+       <licence>AGPL</licence>
+       <author>Jakob Sack</author>
+       <require>2</require>
+</info>
diff --git a/apps/contacts/carddav.php b/apps/contacts/carddav.php
new file mode 100644 (file)
index 0000000..ae2c5b9
--- /dev/null
@@ -0,0 +1,28 @@
+<?php
+
+// Do not load FS ...
+$RUNTIME_NOSETUPFS = true;
+
+require_once('../../lib/base.php');
+
+// Backends
+$authBackend = new OC_Connector_Sabre_Auth();
+$principalBackend = new OC_Connector_Sabre_Principal();
+$carddavBackend   = new OC_Connector_Sabre_CardDAV();
+
+// Root nodes
+$nodes = array(
+    new Sabre_DAVACL_PrincipalCollection($principalBackend),
+    new Sabre_CardDAV_AddressBookRoot($principalBackend, $carddavBackend),
+);
+
+// Fire up server
+$server = new Sabre_DAV_Server($nodes);
+$server->setBaseUri($WEBROOT.'/apps/contacts/carddav.php');
+// Add plugins
+$server->addPlugin(new Sabre_DAV_Auth_Plugin($authBackend,'ownCloud'));
+$server->addPlugin(new Sabre_CardDAV_Plugin());
+$server->addPlugin(new Sabre_DAVACL_Plugin());
+
+// And off we go!
+$server->exec();
diff --git a/apps/contacts/css/styles.css b/apps/contacts/css/styles.css
new file mode 100644 (file)
index 0000000..8d1c8b6
--- /dev/null
@@ -0,0 +1 @@
diff --git a/apps/contacts/details.php b/apps/contacts/details.php
new file mode 100644 (file)
index 0000000..7ab1b64
--- /dev/null
@@ -0,0 +1,57 @@
+<?php
+/**
+ * ownCloud - Addressbook
+ *
+ * @author Jakob Sack
+ * @copyright 2011 Jakob Sack mail@jakobsack.de
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU AFFERO GENERAL PUBLIC LICENSE
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or any later version.
+ *
+ * This library 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 AFFERO GENERAL PUBLIC LICENSE for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public
+ * License along with this library.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+// Init owncloud
+require_once('../../lib/base.php');
+
+$id = $_GET['id'];
+
+$l10n = new OC_L10N('contacts');
+
+// Check if we are a user
+if( !OC_User::isLoggedIn()){
+       echo $l10n->t('You need to log in!');
+       exit();
+}
+
+
+$card = OC_Contacts_Addressbook::findCard( $id );
+if( $card === false ){
+       echo json_encode( array( 'status' => 'error', 'data' => array( 'message' => $l10n->t('Can not find Contact!'))));
+       exit();
+}
+
+$addressbook = OC_Contacts_Addressbook::findAddressbook( $card['addressbookid'] );
+if( $addressbook === false || $addressbook['userid'] != OC_USER::getUser()){
+       echo json_encode( array( 'status' => 'error', 'data' => array( 'message' => $l10n->t('This is not your contact!'))));
+       exit();
+}
+
+$vcard = Sabre_VObject_Reader::read($card['carddata']);
+$details = OC_Contacts_Addressbook::structureContact($vcard);
+
+$tmpl = new OC_Template('contacts','_details');
+$tmpl->assign('details',$details);
+$tmpl->assign('id',$id);
+$page = $tmpl->fetchPage();
+
+echo json_encode( array( 'status' => 'success', 'data' => array( 'page' => $page )));
diff --git a/apps/contacts/img/icon.png b/apps/contacts/img/icon.png
new file mode 100644 (file)
index 0000000..ea2ed9e
Binary files /dev/null and b/apps/contacts/img/icon.png differ
diff --git a/apps/contacts/index.php b/apps/contacts/index.php
new file mode 100644 (file)
index 0000000..2d5bcef
--- /dev/null
@@ -0,0 +1,68 @@
+<?php
+/**
+ * ownCloud - Addressbook
+ *
+ * @author Jakob Sack
+ * @copyright 2011 Jakob Sack mail@jakobsack.de
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU AFFERO GENERAL PUBLIC LICENSE
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or any later version.
+ *
+ * This library 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 AFFERO GENERAL PUBLIC LICENSE for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public
+ * License along with this library.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+function contactsort($a,$b){
+       return strcmp($a['name'],$b['name']);
+}
+
+// Init owncloud
+require_once('../../lib/base.php');
+
+// Check if we are a user
+if( !OC_User::isLoggedIn()){
+       header( 'Location: '.OC_Helper::linkTo( '', 'index.php' ));
+       exit();
+}
+
+// Load the files we need
+OC_App::setActiveNavigationEntry( 'contacts_index' );
+
+// Load a specific user?
+$id = isset( $_GET['id'] ) ? $_GET['id'] : null;
+
+// Addressbooks to load
+$openaddressbooks = explode(';',OC_Preferences::getValue(OC_User::getUser(),'contacts','openaddressbooks',null));
+
+$contacts = array();
+foreach( $openaddressbooks as $addressbook ){
+       $addressbookcontacts = OC_Contacts_Addressbook::allCards($addressbook);
+       foreach( $addressbookcontacts as $contact ){
+               $contacts[] = array( 'name' => $contact['fullname'], 'id' => $contact['id'] );
+       }
+}
+
+
+usort($contacts,'contactsort');
+$details = array();
+
+if( !is_null($id) || count($contacts)){
+       $contact = OC_Contacts_Addressbook::findCard(is_null($id)?$contacts[0]['id']:$id);
+       $vcard = Sabre_VObject_Reader::read($contact['carddata']);
+       $details = OC_Contacts_Addressbook::structureContact($vcard);
+}
+
+// Process the template
+$tmpl = new OC_Template( 'contacts', 'index', 'user' );
+$tmpl->assign('contacts', $contacts);
+$tmpl->assign('details', $details );
+$tmpl->assign('id',$id);
+$tmpl->printPage();
diff --git a/apps/contacts/js/interface.js b/apps/contacts/js/interface.js
new file mode 100644 (file)
index 0000000..045562b
--- /dev/null
@@ -0,0 +1,14 @@
+$(document).ready(function(){
+       $('.contacts_contacts').find('li').live('click',function(){
+               var id = $(this).attr('x-id');
+               $.getJSON('details.php',{'id':id},function(jsondata){
+                       if(jsondata.status == 'success'){
+                               $('.contacts_details').html(jsondata.data.page);
+                       }
+                       else{
+                               alert(jsondata.data.message);
+                       }
+               });
+               return false;
+       });
+});
diff --git a/apps/contacts/lib/addressbook.php b/apps/contacts/lib/addressbook.php
new file mode 100644 (file)
index 0000000..c0f26c7
--- /dev/null
@@ -0,0 +1,287 @@
+<?php
+/**
+ * ownCloud - Addressbook
+ *
+ * @author Jakob Sack
+ * @copyright 2011 Jakob Sack mail@jakobsack.de
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU AFFERO GENERAL PUBLIC LICENSE
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or any later version.
+ *
+ * This library 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 AFFERO GENERAL PUBLIC LICENSE for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public
+ * License along with this library.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+/*
+ *
+ * The following SQL statement is just a help for developers and will not be
+ * executed!
+ *
+ * CREATE TABLE contacts_addressbooks (
+ * id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ * userid VARCHAR(255) NOT NULL,
+ * displayname VARCHAR(255),
+ * uri VARCHAR(100),
+ * description TEXT,
+ * ctag INT(11) UNSIGNED NOT NULL DEFAULT '1'
+ * );
+ * 
+ * CREATE TABLE contacts_cards (
+ * id INT(11) UNSIGNED NOT NULL PRIMARY KEY AUTO_INCREMENT,
+ * addressbookid INT(11) UNSIGNED NOT NULL,
+ * fullname VARCHAR(255),
+ * carddata TEXT,
+ * uri VARCHAR(100),
+ * lastmodified INT(11) UNSIGNED
+ * );
+ */
+
+/**
+ * This class manages our addressbooks.
+ */
+class OC_Contacts_Addressbook{
+       public static function allAddressbooks($uid){
+               $stmt = OC_DB::prepare( 'SELECT * FROM *PREFIX*contacts_addressbooks WHERE userid = ?' );
+               $result = $stmt->execute(array($uid));
+               
+               $addressbooks = array();
+               while( $row = $result->fetchRow()){
+                       $addressbooks[] = $row;
+               }
+
+               return $addressbooks;
+       }
+       
+       public static function allAddressbooksWherePrincipalURIIs($principaluri){
+               $uid = self::extractUserID($principaluri);
+               return self::allAddressbooks($uid);
+       }
+
+       public static function findAddressbook($id){
+               $stmt = OC_DB::prepare( 'SELECT * FROM *PREFIX*contacts_addressbooks WHERE id = ?' );
+               $result = $stmt->execute(array($id));
+
+               return $result->fetchRow();
+       }
+
+       public static function addAddressbook($userid,$name,$description){
+               $all = self::allAddressbooks($userid);
+               $uris = array();
+               foreach($all as $i){
+                       $uris[] = $i['uri'];
+               }
+
+               $uri = self::createURI('name', $uris );
+
+               $stmt = OC_DB::prepare( 'INSERT INTO *PREFIX*contacts_addressbooks (userid,displayname,uri,description,ctag) VALUES(?,?,?,?,?)' );
+               $result = $stmt->execute(array($userid,$name,$uri,$description,1));
+
+               return OC_DB::insertid();
+       }
+
+       public static function addAddressbookFromDAVData($principaluri,$uri,$name,$description){
+               $userid = self::extractUserID($principaluri);
+               
+               $stmt = OC_DB::prepare( 'INSERT INTO *PREFIX*contacts_addressbooks (userid,displayname,uri,description,ctag) VALUES(?,?,?,?,?)' );
+               $result = $stmt->execute(array($userid,$name,$uri,$description,1));
+
+               return OC_DB::insertid();
+       }
+
+       public static function editAddressbook($id,$name,$description){
+               // Need these ones for checking uri
+               $addressbook = self::find($id);
+
+               if(is_null($name)){
+                       $name = $addressbook['name'];
+               }
+               if(is_null($description)){
+                       $description = $addressbook['description'];
+               }
+               
+               $stmt = OC_DB::prepare( 'UPDATE *PREFIX*contacts_addressbooks SET displayname=?,description=?, ctag=ctag+1 WHERE id=?' );
+               $result = $stmt->execute(array($name,$description,$id));
+
+               return true;
+       }
+
+       public static function touchAddressbook($id){
+               $stmt = OC_DB::prepare( 'UPDATE *PREFIX*contacts_addressbooks SET ctag = ctag + 1 WHERE id = ?' );
+               $stmt->execute(array($id));
+
+               return true;
+       }
+
+       public static function deleteAddressbook($id){
+               $stmt = OC_DB::prepare( 'DELETE FROM *PREFIX*contacts_cards WHERE id = ?' );
+               $stmt->execute(array($id));
+               
+               $stmt = OC_DB::prepare( 'DELETE FROM *PREFIX*contacts_addressbooks WHERE addressbookid = ?' );
+               $stmt->execute(array($id));
+
+               return true;
+       }
+
+       public static function allCards($id){
+               $stmt = OC_DB::prepare( 'SELECT * FROM *PREFIX*contacts_cards WHERE addressbookid = ?' );
+               $result = $stmt->execute(array($id));
+
+               $addressbooks = array();
+               while( $row = $result->fetchRow()){
+                       $addressbooks[] = $row;
+               }
+
+               return $addressbooks;
+       }
+       
+       public static function findCard($id){
+               $stmt = OC_DB::prepare( 'SELECT * FROM *PREFIX*contacts_cards WHERE id = ?' );
+               $result = $stmt->execute(array($id));
+
+               return $result->fetchRow();
+       }
+
+       public static function findCardWhereDAVDataIs($aid,$uri){
+               $stmt = OC_DB::prepare( 'SELECT * FROM *PREFIX*contacts_cards WHERE addressbookid = ? AND uri = ?' );
+               $result = $stmt->execute(array($aid,$uri));
+
+               return $result->fetchRow();
+       }
+
+       public static function addCard($id,$data){
+               $fn = null;
+               $uri = null;
+               $card = Sabre_VObject_Reader::read($data);
+               foreach($card->children as $property){
+                       if($property->name == 'FN'){
+                               $fn = $property->value;
+                       }
+                       elseif(is_null($uri) && $property->name == 'UID' ){
+                               $uri = $property->value.'.vcf';
+                       }
+               }
+               $uri = self::createUID().'.vcf';
+
+               $stmt = OC_DB::prepare( 'INSERT INTO *PREFIX*contacts_cards (addressbookid,fullname,carddata,uri,lastmodified) VALUES(?,?,?,?,?)' );
+               $result = $stmt->execute(array($id,$fn,$data,$uri,time()));
+
+               self::touch($id);
+
+               return OC_DB::insertid;
+       }
+
+       public static function addCardFromDAVData($id,$uri,$data){
+               $fn = null;
+               $card = Sabre_VObject_Reader::read($data);
+               foreach($card->children as $property){
+                       if($property->name == 'FN'){
+                               $fn = $property->value;
+                       }
+               }
+
+               $stmt = OC_DB::prepare( 'INSERT INTO *PREFIX*contacts_cards (addressbookid,fullname,carddata,uri,lastmodified) VALUES(?,?,?,?,?)' );
+               $result = $stmt->execute(array($id,$fn,$data,$uri,time()));
+
+               self::touch($id);
+
+               return OC_DB::insertid;
+       }
+
+       public static function editCard($id, $data){
+               $oldcard = self::findCard($id,$aid,$uri);
+               $fn = null;
+               $card = Sabre_VObject_Reader::read($data);
+               foreach($card->children as $property){
+                       if($property->name == 'FN'){
+                               $fn = $property->value;
+                       }
+               }
+
+               $stmt = OC_DB::prepare( 'UPDATE *PREFIX*contacts_cards SET fullname = ?,carddata = ?, lastmodified = ? WHERE id = ?' );
+               $result = $stmt->execute(array($fn,$data,time(),$id));
+
+               self::touch($oldcard['addressbookid']);
+
+               return true;
+       }
+
+       public static function editCardFromDAVData($aid,$uri,$data){
+               $oldcard = self::findCardWhereDAVDataIs($aid,$uri);
+
+               $fn = null;
+               $card = Sabre_VObject_Reader::read($data);
+               foreach($card->children as $property){
+                       if($property->name == 'FN'){
+                               $fn = $property->value;
+                       }
+               }
+
+               $stmt = OC_DB::prepare( 'UPDATE *PREFIX*contacts_cards SET fullname = ?,carddata = ?, lastmodified = ? WHERE id = ?' );
+               $result = $stmt->execute(array($fn,$data,time(),$oldcard['id']));
+
+               self::touch($oldcard['addressbookid']);
+
+               return true;
+       }
+       
+       public static function deleteCard($id){
+               $stmt = OC_DB::prepare( 'DELETE FROM *PREFIX*contacts_addressbooks WHERE id = ?' );
+               $stmt->execute(array($id));
+
+               return true;
+       }
+
+       public static function deleteCardFromDAVData($aid,$uri){
+               $stmt = OC_DB::prepare( 'DELETE FROM *PREFIX*contacts_addressbooks WHERE addressbookid = ? AND uri=?' );
+               $stmt->execute(array($aid,$uri));
+
+               return true;
+       }
+       
+       public static function createURI($name,$existing){
+               $name = strtolower($name);
+               $newname = $name;
+               $i = 1;
+               while(in_array($newname,$existing)){
+                       $newname = $name.$i;
+                       $i = $i + 1;
+               }
+               return $newname;
+       }
+
+       public static function createUID(){
+               return substr(md5(rand().time()),0,10);
+       }
+       
+       public static function extractUserID($principaluri){
+               list($prefix,$userid) = Sabre_DAV_URLUtil::splitPath($principaluri);
+               return $userid;
+       }
+
+       public static function structureContact($object){
+               $details = array();
+               foreach($object->children as $property){
+                       $temp = array(
+                               'name' => $property->name,
+                               'value' => ($property->name == 'PHOTO' || $property->name == 'LOGO' ? null : $property->value ),
+                               'parameters' => array());
+                       foreach($property->parameters as $parameter){
+                               $temp['parameters'][] = array( 'name' => $parameter->name, 'value' => $parameter->value);
+                       }
+                       if(array_key_exists($property->name,$details)){
+                               $details[$property->name][] = $temp;
+                       }
+                       else{
+                               $details[$property->name] = array($temp);
+                       }
+               }
+               return $details;
+       }
+}
diff --git a/apps/contacts/lib/connector_sabre.php b/apps/contacts/lib/connector_sabre.php
new file mode 100644 (file)
index 0000000..98e2598
--- /dev/null
@@ -0,0 +1,186 @@
+<?php
+
+/**
+ * PDO CardDAV backend
+ * 
+ * @package Sabre
+ * @subpackage CardDAV
+ * @copyright Copyright (C) 2007-2011 Rooftop Solutions. All rights reserved.
+ * @author Evert Pot (http://www.rooftopsolutions.nl/) 
+ * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License
+ */
+
+/**
+ * This CardDAV backend uses PDO to store addressbooks
+ */
+class OC_Connector_Sabre_CardDAV extends Sabre_CardDAV_Backend_Abstract {
+       /**
+        * Returns the list of addressbooks for a specific user.
+        *
+        * @param string $principaluri
+        * @return array
+        */
+       public function getAddressBooksForUser($principaluri) {
+               $data = OC_Contacts_Addressbook::allAddressbooksWherePrincipalURIIs($principaluri);
+               $addressbooks = array();
+               
+               foreach($data as $i) {
+                       $addressbooks[] = array(
+                               'id'  => $i['id'],
+                               'uri' => $i['uri'],
+                               'principaluri' => 'principals/'.$i['userid'],
+                               '{DAV:}displayname' => $i['displayname'],
+                               '{' . Sabre_CardDAV_Plugin::NS_CARDDAV . '}addressbook-description' => $i['description'],
+                               '{http://calendarserver.org/ns/}getctag' => $i['ctag'],
+                       );
+               }
+
+               return $addressbooks;
+       }
+
+
+       /**
+        * Updates an addressbook's properties
+        *
+        * See Sabre_DAV_IProperties for a description of the mutations array, as
+        * well as the return value.
+        *
+        * @param mixed $addressbookid
+        * @param array $mutations
+        * @see Sabre_DAV_IProperties::updateProperties
+        * @return bool|array
+        */
+       public function updateAddressBook($addressbookid, array $mutations) {
+               $name = null;
+               $description = null;
+
+               foreach($mutations as $property=>$newvalue) {
+                       switch($property) {
+                               case '{DAV:}displayname' :
+                                       $name = $newvalue;
+                                       break;
+                               case '{' . Sabre_CardDAV_Plugin::NS_CARDDAV . '}addressbook-description' :
+                                       $description = $newvalue;
+                                       break;
+                               default :
+                                       // If any unsupported values were being updated, we must
+                                       // let the entire request fail.
+                                       return false;
+                       }
+               }
+
+               OC_Contacts_Addressbook::editAddressbook($addressbookid,$name,$description);
+
+               return true;
+
+       }
+
+       /**
+        * Creates a new address book
+        *
+        * @param string $principaluri
+        * @param string $url Just the 'basename' of the url.
+        * @param array $properties
+        * @return void
+        */
+       public function createAddressBook($principaluri, $url, array $properties) {
+
+               $displayname = null;
+               $description = null;
+
+               foreach($properties as $property=>$newvalue) {
+
+                       switch($property) {
+                               case '{DAV:}displayname' :
+                                       $displayname = $newvalue;
+                                       break;
+                               case '{' . Sabre_CardDAV_Plugin::NS_CARDDAV . '}addressbook-description' :
+                                       $description = $newvalue;
+                                       break;
+                               default :
+                                       throw new Sabre_DAV_Exception_BadRequest('Unknown property: ' . $property);
+                       }
+
+               }
+
+               OC_Contacts_Addressbook::addAddressbookFromDAVData($principaluri,$url,$name,$description);
+       }
+
+       /**
+        * Deletes an entire addressbook and all its contents
+        *
+        * @param int $addressbookid
+        * @return void
+        */
+       public function deleteAddressBook($addressbookid) {
+               OC_Contacts_Addressbook::deleteAddressbook($addressbookid);
+       }
+
+       /**
+        * Returns all cards for a specific addressbook id.
+        *
+        * @param mixed $addressbookid
+        * @return array
+        */
+       public function getCards($addressbookid) {
+               $data = OC_Contacts_Addressbook::allCards($addressbookid);
+               $cards = array();
+               foreach($data as $i){
+                       $cards[] = array(
+                               'id' => $i['id'],
+                               'carddata' => $i['carddata'],
+                               'uri' => $i['uri'],
+                               'lastmodified' => $i['lastmodified'] );
+               }
+
+               return $cards;
+       }
+       
+       /**
+        * Returns a specfic card
+        *
+        * @param mixed $addressbookid
+        * @param string $carduri
+        * @return array
+        */
+       public function getCard($addressbookid, $carduri) {
+               return OC_Contacts_Addressbook::findCardWhereDAVDataIs($addressbookid,$carduri);
+
+       }
+
+       /**
+        * Creates a new card
+        *
+        * @param mixed $addressbookid
+        * @param string $carduri
+        * @param string $carddata
+        * @return bool
+        */
+       public function createCard($addressbookid, $carduri, $carddata) {
+               OC_Contacts_Addressbook::addCardFromDAVData($addressbookid, $carduri, $carddata);
+               return true;
+       }
+
+       /**
+        * Updates a card
+        *
+        * @param mixed $addressbookid
+        * @param string $carduri
+        * @param string $carddata
+        * @return bool
+        */
+       public function updateCard($addressbookid, $carduri, $carddata) {
+               return OC_Contacts_Addressbook::editCardFromDAVData($addressbookid, $carduri, $carddata);
+       }
+
+       /**
+        * Deletes a card
+        *
+        * @param mixed $addressbookid
+        * @param string $carduri
+        * @return bool
+        */
+       public function deleteCard($addressbookid, $carduri) {
+               return OC_Contacts_Addressbook::deleteCardFromDAVData($addressbookid, $carduri);
+       }
+}
diff --git a/apps/contacts/photo.php b/apps/contacts/photo.php
new file mode 100644 (file)
index 0000000..6238642
--- /dev/null
@@ -0,0 +1,85 @@
+<?php
+/**
+ * ownCloud - Addressbook
+ *
+ * @author Jakob Sack
+ * @copyright 2011 Jakob Sack mail@jakobsack.de
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU AFFERO GENERAL PUBLIC LICENSE
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or any later version.
+ *
+ * This library 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 AFFERO GENERAL PUBLIC LICENSE for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public
+ * License along with this library.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ */
+
+// Init owncloud
+require_once('../../lib/base.php');
+
+$id = $_GET['id'];
+
+$l10n = new OC_L10N('contacts');
+
+// Check if we are a user
+if( !OC_User::isLoggedIn()){
+       echo $l10n->t('You need to log in!');
+       exit();
+}
+
+
+$card = OC_Contacts_Addressbook::findCard( $id );
+if( $card === false ){
+       echo $l10n->t('Can not find Contact!');
+       exit();
+}
+
+$addressbook = OC_Contacts_Addressbook::findAddressbook( $card['addressbookid'] );
+if( $addressbook === false || $addressbook['userid'] != OC_USER::getUser()){
+       echo $l10n->t('This is not your contact!');
+       exit();
+}
+
+$content = Sabre_VObject_Reader::read($card['carddata']);
+
+// Photo :-)
+foreach($content->children as $child){
+       if($child->name == 'PHOTO'){
+               $mime = 'image/jpeg';
+               foreach($child->parameters as $parameter){
+                       if( $parameter->name == 'TYPE' ){
+                               $mime = $parameter->value;
+                       }
+               }
+               $photo = base64_decode($child->value);
+               header('Content-Type: '.$mime);
+               header('Content-Length: ' . strlen($photo));
+               echo $photo;
+               exit();
+       }
+}
+// Logo :-/
+foreach($content->children as $child){
+       if($child->name == 'PHOTO'){
+               $mime = 'image/jpeg';
+               foreach($child->parameters as $parameter){
+                       if($parameter->name == 'TYPE'){
+                               $mime = $parameter->value;
+                       }
+               }
+               $photo = base64_decode($child->value());
+               header('Content-Type: '.$mime);
+               header('Content-Length: ' . strlen($photo));
+               echo $photo;
+               exit();
+       }
+}
+
+// Not found :-(
+echo $l10n->t('This card does not contain photo data!');
diff --git a/apps/contacts/templates/_contacts.php b/apps/contacts/templates/_contacts.php
new file mode 100644 (file)
index 0000000..bf633b7
--- /dev/null
@@ -0,0 +1,3 @@
+<?php foreach( $_['contacts'] as $contact ): ?>
+       <li x-id="<?php echo $contact['id']; ?>"><a href="index.php?id=<?php echo $contact['id']; ?>"><?php echo $contact['name']; ?></a></li>
+<?php endforeach; ?>
diff --git a/apps/contacts/templates/_details.php b/apps/contacts/templates/_details.php
new file mode 100644 (file)
index 0000000..e27b17e
--- /dev/null
@@ -0,0 +1,4 @@
+Name <?php echo $_['details']['FN'][0]['value']; ?>
+<?php if(array_key_exists('PHOTO',$_['details'])): ?>
+       <img src="photo.php?id=<?php echo $_['id']; ?>">
+<?php endif; ?>
\ No newline at end of file
diff --git a/apps/contacts/templates/index.php b/apps/contacts/templates/index.php
new file mode 100644 (file)
index 0000000..0cd214b
--- /dev/null
@@ -0,0 +1,13 @@
+<?php // Include Style and Script
+OC_Util::addScript('contacts','interface');
+OC_Util::addStyle('contacts','styles');
+?>
+
+<div class="contacts_contacts leftcontent">
+       <ul>
+               <?php echo $this->inc("_contacts"); ?>
+       </ul>
+</div>
+<div class="contacts_details rightcontent">
+       <?php echo $this->inc("_details"); ?>
+</div>