diff options
102 files changed, 11238 insertions, 11238 deletions
diff --git a/.travis.yml b/.travis.yml index e63dd3f6a..26e3212ea 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,73 +1,73 @@ language: php php: - - 5.4 - - 5.5 - - 5.6 + - 5.4 + - 5.5 + - 5.6 env: - - DB=sqlite - # enable if there are tests for it - # - DB=postgresql - # - DB=mysql + - DB=sqlite + # enable if there are tests for it + # - DB=postgresql + # - DB=mysql before_install: - # get a newer node.js version - - "export DISPLAY=:99.0" - - "sh -e /etc/init.d/xvfb start" - - sudo add-apt-repository -y ppa:chris-lea/node.js # ubuntu 12.04 only - - sudo apt-get update - - sudo apt-get -o DPkg::Options::="--force-confold" -y upgrade - - npm install -g npm@latest + # get a newer node.js version + - "export DISPLAY=:99.0" + - "sh -e /etc/init.d/xvfb start" + - sudo add-apt-repository -y ppa:chris-lea/node.js # ubuntu 12.04 only + - sudo apt-get update + - sudo apt-get -o DPkg::Options::="--force-confold" -y upgrade + - npm install -g npm@latest install: - - cd .. - - sudo apt-get -y install nodejs python3-jinja2 python3-setuptools apache2 libapache2-mod-fastcgi firefox chromium-browser - - export CHROME_BIN=/usr/bin/chromium-browser - - sudo easy_install3 pip # ubuntu 12.04 only - - sudo pip3 install ocdev - # clone core - - ocdev setup core --dir owncloud - - mv news owncloud/apps/ + - cd .. + - sudo apt-get -y install nodejs python3-jinja2 python3-setuptools apache2 libapache2-mod-fastcgi firefox chromium-browser + - export CHROME_BIN=/usr/bin/chromium-browser + - sudo easy_install3 pip # ubuntu 12.04 only + - sudo pip3 install ocdev + # clone core + - ocdev setup core --dir owncloud + - mv news owncloud/apps/ before_script: - # set up databases and users for postgres and mysql - - createuser -U travis -s oc_autotest - - mysql -e 'create database oc_autotest;' - - mysql -u root -e "CREATE USER 'oc_autotest'@'localhost';" - - mysql -u root -e "grant all on oc_autotest.* to 'oc_autotest'@'localhost';" - # set up php under apache - - sudo cp ~/.phpenv/versions/$(phpenv version-name)/etc/php-fpm.conf.default ~/.phpenv/versions/$(phpenv version-name)/etc/php-fpm.conf - - sudo a2enmod rewrite actions fastcgi alias - - echo "cgi.fix_pathinfo = 1" >> ~/.phpenv/versions/$(phpenv version-name)/etc/php.ini - - ~/.phpenv/versions/$(phpenv version-name)/sbin/php-fpm - - sudo cp -f owncloud/apps/news/tests/travis/travis-ci-apache /etc/apache2/sites-available/default - - sudo sed -e "s?%TRAVIS_BUILD_DIR%?$(pwd)?g" --in-place /etc/apache2/sites-available/default - - sudo service apache2 restart - # fill owncloud with default configs and enable news - - cd owncloud - - ocdev ci $DB - - php -f console.php app:enable news - - cd apps/news + # set up databases and users for postgres and mysql + - createuser -U travis -s oc_autotest + - mysql -e 'create database oc_autotest;' + - mysql -u root -e "CREATE USER 'oc_autotest'@'localhost';" + - mysql -u root -e "grant all on oc_autotest.* to 'oc_autotest'@'localhost';" + # set up php under apache + - sudo cp ~/.phpenv/versions/$(phpenv version-name)/etc/php-fpm.conf.default ~/.phpenv/versions/$(phpenv version-name)/etc/php-fpm.conf + - sudo a2enmod rewrite actions fastcgi alias + - echo "cgi.fix_pathinfo = 1" >> ~/.phpenv/versions/$(phpenv version-name)/etc/php.ini + - ~/.phpenv/versions/$(phpenv version-name)/sbin/php-fpm + - sudo cp -f owncloud/apps/news/tests/travis/travis-ci-apache /etc/apache2/sites-available/default + - sudo sed -e "s?%TRAVIS_BUILD_DIR%?$(pwd)?g" --in-place /etc/apache2/sites-available/default + - sudo service apache2 restart + # fill owncloud with default configs and enable news + - cd owncloud + - ocdev ci $DB + - php -f console.php app:enable news + - cd apps/news script: - # php unit tests - - phpunit --coverage-clover=coverage.clover tests/unit - - wget https://scrutinizer-ci.com/ocular.phar - - php ocular.phar code-coverage:upload --format=php-clover coverage.clover - - cd js/ - # install javascript deps (putting it into install section fails often) - - npm install --deps # npm install needs to run before sudo npm install because otherwise it fails because a tmp file exists in the home dir - - sudo npm -g install grunt-cli protractor - # js unit tests - - grunt ci-unit - # acceptance tests - #- webdriver-manager update - #- grunt ci-e2e --verbose - # debug section to check what went wrong - - sudo apt-get install curl - - curl http://admin:admin@localhost/owncloud/index.php - - curl http://admin:admin@localhost/owncloud/index.php/apps/news/ - - sudo cat ../../../data/owncloud.log + # php unit tests + - phpunit --coverage-clover=coverage.clover tests/unit + - wget https://scrutinizer-ci.com/ocular.phar + - php ocular.phar code-coverage:upload --format=php-clover coverage.clover + - cd js/ + # install javascript deps (putting it into install section fails often) + - npm install --deps # npm install needs to run before sudo npm install because otherwise it fails because a tmp file exists in the home dir + - sudo npm -g install grunt-cli protractor + # js unit tests + - grunt ci-unit + # acceptance tests + #- webdriver-manager update + #- grunt ci-e2e --verbose + # debug section to check what went wrong + - sudo apt-get install curl + - curl http://admin:admin@localhost/owncloud/index.php + - curl http://admin:admin@localhost/owncloud/index.php/apps/news/ + - sudo cat ../../../data/owncloud.log addons: - postgresql: "9.3" + postgresql: "9.3" diff --git a/appinfo/app.php b/appinfo/app.php index 8188d3eeb..2809795fb 100644 --- a/appinfo/app.php +++ b/appinfo/app.php @@ -18,9 +18,9 @@ use \OCA\News\Config\DependencyException; // Turn all errors into exceptions to combat shitty library behavior set_error_handler(function ($code, $message) { - if ($code === E_ERROR || $code === E_USER_ERROR) { - throw new \Exception($message, $code); - } + if ($code === E_ERROR || $code === E_USER_ERROR) { + throw new \Exception($message, $code); + } }); $container = new Application(); diff --git a/appinfo/application.php b/appinfo/application.php index e410ce701..8a1f02a4c 100644 --- a/appinfo/application.php +++ b/appinfo/application.php @@ -56,432 +56,432 @@ use \OCA\News\ArticleEnhancer\RegexArticleEnhancer; $thirdPartyLibs = [ - '\HTMLPurifier' => 'htmlpurifier/library/HTMLPurifier.auto.php', - '\SimplePie' => 'simplepie/autoloader.php', - '\ZendXML\Security' => 'ZendXml/vendor/autoload.php', - '\Net_URL2' => 'Net_URL2/Net/URL2.php' + '\HTMLPurifier' => 'htmlpurifier/library/HTMLPurifier.auto.php', + '\SimplePie' => 'simplepie/autoloader.php', + '\ZendXML\Security' => 'ZendXml/vendor/autoload.php', + '\Net_URL2' => 'Net_URL2/Net/URL2.php' ]; // to prevent clashes with installed app framework versions foreach ($thirdPartyLibs as $class => $path) { - if (!class_exists($class)) { - require_once __DIR__ . '/../3rdparty/' . $path; - } + if (!class_exists($class)) { + require_once __DIR__ . '/../3rdparty/' . $path; + } } class Application extends App { - public function __construct(array $urlParams=array()){ - parent::__construct('news', $urlParams); - - $container = $this->getContainer(); - - - /** - * Controllers - */ - $container->registerService('PageController', function($c) { - return new PageController( - $c->query('AppName'), - $c->query('Request'), - $c->query('CoreConfig'), - $c->query('URLGenerator'), - $c->query('AppConfig'), - $c->query('L10N'), - $c->query('UserId') - ); - }); - - $container->registerService('AdminController', function($c) { - return new AdminController( - $c->query('AppName'), - $c->query('Request'), - $c->query('Config'), - $c->query('ConfigPath') - ); - }); - - $container->registerService('FolderController', function($c) { - return new FolderController( - $c->query('AppName'), - $c->query('Request'), - $c->query('FolderService'), - $c->query('FeedService'), - $c->query('ItemService'), - $c->query('UserId') - ); - }); - - $container->registerService('FeedController', function($c) { - return new FeedController( - $c->query('AppName'), - $c->query('Request'), - $c->query('FolderService'), - $c->query('FeedService'), - $c->query('ItemService'), - $c->query('CoreConfig'), - $c->query('UserId') - ); - }); - - $container->registerService('ItemController', function($c) { - return new ItemController( - $c->query('AppName'), - $c->query('Request'), - $c->query('FeedService'), - $c->query('ItemService'), - $c->query('CoreConfig'), - $c->query('UserId') - ); - }); - - $container->registerService('ExportController', function($c) { - return new ExportController( - $c->query('AppName'), - $c->query('Request'), - $c->query('FolderService'), - $c->query('FeedService'), - $c->query('ItemService'), - $c->query('OPMLExporter'), - $c->query('UserId') - ); - }); - - $container->registerService('UtilityApiController', function($c) { - return new UtilityApiController( - $c->query('AppName'), - $c->query('Request'), - $c->query('Updater'), - $c->query('CoreConfig') - ); - }); - - $container->registerService('FolderApiController', function($c) { - return new FolderApiController( - $c->query('AppName'), - $c->query('Request'), - $c->query('FolderService'), - $c->query('ItemService'), - $c->query('UserId') - ); - }); - - $container->registerService('FeedApiController', function($c) { - return new FeedApiController( - $c->query('AppName'), - $c->query('Request'), - $c->query('FeedService'), - $c->query('ItemService'), - $c->query('Logger'), - $c->query('UserId'), - $c->query('LoggerParameters') - ); - }); - - $container->registerService('ItemApiController', function($c) { - return new ItemApiController( - $c->query('AppName'), - $c->query('Request'), - $c->query('ItemService'), - $c->query('UserId') - ); - }); - - /** - * Business Layer - */ - $container->registerService('FolderService', function($c) { - return new FolderService( - $c->query('FolderMapper'), - $c->query('L10N'), - $c->query('TimeFactory'), - $c->query('Config') - ); - }); - - $container->registerService('FeedService', function($c) { - return new FeedService( - $c->query('FeedMapper'), - $c->query('Fetcher'), - $c->query('ItemMapper'), - $c->query('Logger'), - $c->query('L10N'), - $c->query('TimeFactory'), - $c->query('Config'), - $c->query('Enhancer'), - $c->query('HTMLPurifier'), - $c->query('LoggerParameters') - ); - }); - - $container->registerService('ItemService', function($c) { - return new ItemService( - $c->query('ItemMapper'), - $c->query('StatusFlag'), - $c->query('TimeFactory'), - $c->query('Config') - ); - }); - - // compability for plugins pre 3.0 - $container->registerService('FolderBusinessLayer', function($c) { - return $c->query('FolderService'); - }); - $container->registerService('FeedBusinessLayer', function($c) { - return $c->query('FeedService'); - }); - $container->registerService('ItemBusinessLayer', function($c) { - return $c->query('ItemService'); - }); - - /** - * Mappers - */ - $container->registerService('MapperFactory', function($c) { - return new MapperFactory( - $c->query('DatabaseType'), - $c->query('Db') - ); - }); - - $container->registerService('FolderMapper', function($c) { - return new FolderMapper( - $c->query('Db') - ); - }); - - $container->registerService('FeedMapper', function($c) { - return new FeedMapper( - $c->query('Db') - ); - }); - - $container->registerService('ItemMapper', function($c) { - return $c->query('MapperFactory')->getItemMapper( - $c->query('Db') - ); - }); - - - /** - * App config parser - */ - $container->registerService('AppConfig', function($c) { - // order extensions in name => version - $loadedExtensions = get_loaded_extensions(); - $extensions = []; - foreach ($loadedExtensions as $extension) { - $extensions[$extension] = phpversion($extension); - } - - $extensions['libxml'] = LIBXML_DOTTED_VERSION; - - $config = new AppConfig( - $c->query('ServerContainer')->getNavigationManager(), - $c->query('URLGenerator'), - phpversion(), - implode('.', Util::getVersion()), - $extensions, - $c->query('DatabaseType') - ); - - $config->loadConfig(__DIR__ . '/app.json'); - - return $config; - }); - - /** - * Core - */ - $container->registerService('L10N', function($c) { - return $c->query('ServerContainer')->getL10N($c->query('AppName')); - }); - - $container->registerService('URLGenerator', function($c) { - return $c->query('ServerContainer')->getURLGenerator(); - }); - - $container->registerService('UserId', function() { - return User::getUser(); - }); - - $container->registerService('Logger', function($c) { - return $c->query('ServerContainer')->getLogger(); - }); - - $container->registerService('LoggerParameters', function($c) { - return ['app' => $c->query('AppName')]; - }); - - $container->registerService('Db', function($c) { - return $c->query('ServerContainer')->getDb(); - }); - - $container->registerService('CoreConfig', function($c) { - return $c->query('ServerContainer')->getConfig(); - }); - - $container->registerService('DatabaseType', function($c) { - return $c->query('ServerContainer')->getConfig()->getSystemValue('dbtype'); - }); - - - /** - * Utility - */ - $container->registerService('ConfigView', function() { - $view = new View('/news/config'); - if (!$view->file_exists('')) { - $view->mkdir(''); - } - - return $view; - }); - - $container->registerService('ConfigPath', function() { - return 'config.ini'; - }); - - $container->registerService('Config', function($c) { - $config = new Config( - $c->query('ConfigView'), - $c->query('Logger'), - $c->query('LoggerParameters') - ); - $config->read($c->query('ConfigPath'), true); - return $config; - }); - - $container->registerService('simplePieCacheDirectory', function($c) { - $directory = $c->query('CoreConfig')->getSystemValue('datadirectory') . - '/news/cache/simplepie'; - - if(!is_dir($directory)) { - mkdir($directory, 0770, true); - } - return $directory; - }); - - $container->registerService('HTMLPurifier', function($c) { - $directory = $c->query('CoreConfig')->getSystemValue('datadirectory') . - '/news/cache/purifier'; - - if(!is_dir($directory)) { - mkdir($directory, 0770, true); - } - - $config = \HTMLPurifier_Config::createDefault(); - $config->set('HTML.ForbiddenAttributes', 'class'); - $config->set('Cache.SerializerPath', $directory); - $config->set('HTML.SafeIframe', true); - $config->set('URI.SafeIframeRegexp', - '%^(?:https?:)?//(' . - 'www.youtube(?:-nocookie)?.com/embed/|' . - 'player.vimeo.com/video/)%'); //allow YouTube and Vimeo - return new \HTMLPurifier($config); - }); - - $container->registerService('GlobalArticleEnhancer', function() { - return new GlobalArticleEnhancer(); - }); - - $container->registerService('Enhancer', function($c) { - $enhancer = new Enhancer(); - - // register simple enhancers from config json file - $xpathEnhancerConfig = file_get_contents( - __DIR__ . '/../articleenhancer/xpathenhancers.json' - ); - - foreach(json_decode($xpathEnhancerConfig, true) as $feed => $config) { - $articleEnhancer = new XPathArticleEnhancer( - $c->query('SimplePieAPIFactory'), - $config, - $c->query('Config') - ); - $enhancer->registerEnhancer($feed, $articleEnhancer); - } - - $regexEnhancerConfig = file_get_contents( - __DIR__ . '/../articleenhancer/regexenhancers.json' - ); - foreach(json_decode($regexEnhancerConfig, true) as $feed => $config) { - foreach ($config as $matchArticleUrl => $regex) { - $articleEnhancer = new RegexArticleEnhancer($matchArticleUrl, $regex); - $enhancer->registerEnhancer($feed, $articleEnhancer); - } - } - - $enhancer->registerGlobalEnhancer($c->query('GlobalArticleEnhancer')); - - return $enhancer; - }); - - /** - * Fetchers - */ - $container->registerService('Fetcher', function($c) { - $fetcher = new Fetcher(); - - // register fetchers in order - // the most generic fetcher should be the last one - $fetcher->registerFetcher($c->query('FeedFetcher')); - - return $fetcher; - }); - - $container->registerService('FeedFetcher', function($c) { - return new FeedFetcher($c->query('SimplePieAPIFactory'), - $c->query('FaviconFetcher'), - $c->query('TimeFactory'), - $c->query('simplePieCacheDirectory'), - $c->query('Config'), - $c->query('AppConfig') - ); - }); - - $container->registerService('StatusFlag', function() { - return new StatusFlag(); - }); - - $container->registerService('OPMLExporter', function() { - return new OPMLExporter(); - }); - - $container->registerService('Updater', function($c) { - return new Updater( - $c->query('FolderService'), - $c->query('FeedService'), - $c->query('ItemService') - ); - }); - - $container->registerService('SimplePieAPIFactory', function() { - return new SimplePieAPIFactory(); - }); - - $container->registerService('FaviconFetcher', function($c) { - return new FaviconFetcher( - $c->query('SimplePieAPIFactory') - ); - }); - - } - - public function getAppConfig() { - return $this->getContainer()->query('AppConfig'); - } - - - public function getLogger() { - return $this->getContainer()->query('Logger'); - } - - - public function getLoggerParameters() { - return $this->getContainer()->query('LoggerParameters'); - } + public function __construct(array $urlParams=array()){ + parent::__construct('news', $urlParams); + + $container = $this->getContainer(); + + + /** + * Controllers + */ + $container->registerService('PageController', function($c) { + return new PageController( + $c->query('AppName'), + $c->query('Request'), + $c->query('CoreConfig'), + $c->query('URLGenerator'), + $c->query('AppConfig'), + $c->query('L10N'), + $c->query('UserId') + ); + }); + + $container->registerService('AdminController', function($c) { + return new AdminController( + $c->query('AppName'), + $c->query('Request'), + $c->query('Config'), + $c->query('ConfigPath') + ); + }); + + $container->registerService('FolderController', function($c) { + return new FolderController( + $c->query('AppName'), + $c->query('Request'), + $c->query('FolderService'), + $c->query('FeedService'), + $c->query('ItemService'), + $c->query('UserId') + ); + }); + + $container->registerService('FeedController', function($c) { + return new FeedController( + $c->query('AppName'), + $c->query('Request'), + $c->query('FolderService'), + $c->query('FeedService'), + $c->query('ItemService'), + $c->query('CoreConfig'), + $c->query('UserId') + ); + }); + + $container->registerService('ItemController', function($c) { + return new ItemController( + $c->query('AppName'), + $c->query('Request'), + $c->query('FeedService'), + $c->query('ItemService'), + $c->query('CoreConfig'), + $c->query('UserId') + ); + }); + + $container->registerService('ExportController', function($c) { + return new ExportController( + $c->query('AppName'), + $c->query('Request'), + $c->query('FolderService'), + $c->query('FeedService'), + $c->query('ItemService'), + $c->query('OPMLExporter'), + $c->query('UserId') + ); + }); + + $container->registerService('UtilityApiController', function($c) { + return new UtilityApiController( + $c->query('AppName'), + $c->query('Request'), + $c->query('Updater'), + $c->query('CoreConfig') + ); + }); + + $container->registerService('FolderApiController', function($c) { + return new FolderApiController( + $c->query('AppName'), + $c->query('Request'), + $c->query('FolderService'), + $c->query('ItemService'), + $c->query('UserId') + ); + }); + + $container->registerService('FeedApiController', function($c) { + return new FeedApiController( + $c->query('AppName'), + $c->query('Request'), + $c->query('FeedService'), + $c->query('ItemService'), + $c->query('Logger'), + $c->query('UserId'), + $c->query('LoggerParameters') + ); + }); + + $container->registerService('ItemApiController', function($c) { + return new ItemApiController( + $c->query('AppName'), + $c->query('Request'), + $c->query('ItemService'), + $c->query('UserId') + ); + }); + + /** + * Business Layer + */ + $container->registerService('FolderService', function($c) { + return new FolderService( + $c->query('FolderMapper'), + $c->query('L10N'), + $c->query('TimeFactory'), + $c->query('Config') + ); + }); + + $container->registerService('FeedService', function($c) { + return new FeedService( + $c->query('FeedMapper'), + $c->query('Fetcher'), + $c->query('ItemMapper'), + $c->query('Logger'), + $c->query('L10N'), + $c->query('TimeFactory'), + $c->query('Config'), + $c->query('Enhancer'), + $c->query('HTMLPurifier'), + $c->query('LoggerParameters') + ); + }); + + $container->registerService('ItemService', function($c) { + return new ItemService( + $c->query('ItemMapper'), + $c->query('StatusFlag'), + $c->query('TimeFactory'), + $c->query('Config') + ); + }); + + // compability for plugins pre 3.0 + $container->registerService('FolderBusinessLayer', function($c) { + return $c->query('FolderService'); + }); + $container->registerService('FeedBusinessLayer', function($c) { + return $c->query('FeedService'); + }); + $container->registerService('ItemBusinessLayer', function($c) { + return $c->query('ItemService'); + }); + + /** + * Mappers + */ + $container->registerService('MapperFactory', function($c) { + return new MapperFactory( + $c->query('DatabaseType'), + $c->query('Db') + ); + }); + + $container->registerService('FolderMapper', function($c) { + return new FolderMapper( + $c->query('Db') + ); + }); + + $container->registerService('FeedMapper', function($c) { + return new FeedMapper( + $c->query('Db') + ); + }); + + $container->registerService('ItemMapper', function($c) { + return $c->query('MapperFactory')->getItemMapper( + $c->query('Db') + ); + }); + + + /** + * App config parser + */ + $container->registerService('AppConfig', function($c) { + // order extensions in name => version + $loadedExtensions = get_loaded_extensions(); + $extensions = []; + foreach ($loadedExtensions as $extension) { + $extensions[$extension] = phpversion($extension); + } + + $extensions['libxml'] = LIBXML_DOTTED_VERSION; + + $config = new AppConfig( + $c->query('ServerContainer')->getNavigationManager(), + $c->query('URLGenerator'), + phpversion(), + implode('.', Util::getVersion()), + $extensions, + $c->query('DatabaseType') + ); + + $config->loadConfig(__DIR__ . '/app.json'); + + return $config; + }); + + /** + * Core + */ + $container->registerService('L10N', function($c) { + return $c->query('ServerContainer')->getL10N($c->query('AppName')); + }); + + $container->registerService('URLGenerator', function($c) { + return $c->query('ServerContainer')->getURLGenerator(); + }); + + $container->registerService('UserId', function() { + return User::getUser(); + }); + + $container->registerService('Logger', function($c) { + return $c->query('ServerContainer')->getLogger(); + }); + + $container->registerService('LoggerParameters', function($c) { + return ['app' => $c->query('AppName')]; + }); + + $container->registerService('Db', function($c) { + return $c->query('ServerContainer')->getDb(); + }); + + $container->registerService('CoreConfig', function($c) { + return $c->query('ServerContainer')->getConfig(); + }); + + $container->registerService('DatabaseType', function($c) { + return $c->query('ServerContainer')->getConfig()->getSystemValue('dbtype'); + }); + + + /** + * Utility + */ + $container->registerService('ConfigView', function() { + $view = new View('/news/config'); + if (!$view->file_exists('')) { + $view->mkdir(''); + } + + return $view; + }); + + $container->registerService('ConfigPath', function() { + return 'config.ini'; + }); + + $container->registerService('Config', function($c) { + $config = new Config( + $c->query('ConfigView'), + $c->query('Logger'), + $c->query('LoggerParameters') + ); + $config->read($c->query('ConfigPath'), true); + return $config; + }); + + $container->registerService('simplePieCacheDirectory', function($c) { + $directory = $c->query('CoreConfig')->getSystemValue('datadirectory') . + '/news/cache/simplepie'; + + if(!is_dir($directory)) { + mkdir($directory, 0770, true); + } + return $directory; + }); + + $container->registerService('HTMLPurifier', function($c) { + $directory = $c->query('CoreConfig')->getSystemValue('datadirectory') . + '/news/cache/purifier'; + + if(!is_dir($directory)) { + mkdir($directory, 0770, true); + } + + $config = \HTMLPurifier_Config::createDefault(); + $config->set('HTML.ForbiddenAttributes', 'class'); + $config->set('Cache.SerializerPath', $directory); + $config->set('HTML.SafeIframe', true); + $config->set('URI.SafeIframeRegexp', + '%^(?:https?:)?//(' . + 'www.youtube(?:-nocookie)?.com/embed/|' . + 'player.vimeo.com/video/)%'); //allow YouTube and Vimeo + return new \HTMLPurifier($config); + }); + + $container->registerService('GlobalArticleEnhancer', function() { + return new GlobalArticleEnhancer(); + }); + + $container->registerService('Enhancer', function($c) { + $enhancer = new Enhancer(); + + // register simple enhancers from config json file + $xpathEnhancerConfig = file_get_contents( + __DIR__ . '/../articleenhancer/xpathenhancers.json' + ); + + foreach(json_decode($xpathEnhancerConfig, true) as $feed => $config) { + $articleEnhancer = new XPathArticleEnhancer( + $c->query('SimplePieAPIFactory'), + $config, + $c->query('Config') + ); + $enhancer->registerEnhancer($feed, $articleEnhancer); + } + + $regexEnhancerConfig = file_get_contents( + __DIR__ . '/../articleenhancer/regexenhancers.json' + ); + foreach(json_decode($regexEnhancerConfig, true) as $feed => $config) { + foreach ($config as $matchArticleUrl => $regex) { + $articleEnhancer = new RegexArticleEnhancer($matchArticleUrl, $regex); + $enhancer->registerEnhancer($feed, $articleEnhancer); + } + } + + $enhancer->registerGlobalEnhancer($c->query('GlobalArticleEnhancer')); + + return $enhancer; + }); + + /** + * Fetchers + */ + $container->registerService('Fetcher', function($c) { + $fetcher = new Fetcher(); + + // register fetchers in order + // the most generic fetcher should be the last one + $fetcher->registerFetcher($c->query('FeedFetcher')); + + return $fetcher; + }); + + $container->registerService('FeedFetcher', function($c) { + return new FeedFetcher($c->query('SimplePieAPIFactory'), + $c->query('FaviconFetcher'), + $c->query('TimeFactory'), + $c->query('simplePieCacheDirectory'), + $c->query('Config'), + $c->query('AppConfig') + ); + }); + + $container->registerService('StatusFlag', function() { + return new StatusFlag(); + }); + + $container->registerService('OPMLExporter', function() { + return new OPMLExporter(); + }); + + $container->registerService('Updater', function($c) { + return new Updater( + $c->query('FolderService'), + $c->query('FeedService'), + $c->query('ItemService') + ); + }); + + $container->registerService('SimplePieAPIFactory', function() { + return new SimplePieAPIFactory(); + }); + + $container->registerService('FaviconFetcher', function($c) { + return new FaviconFetcher( + $c->query('SimplePieAPIFactory') + ); + }); + + } + + public function getAppConfig() { + return $this->getContainer()->query('AppConfig'); + } + + + public function getLogger() { + return $this->getContainer()->query('Logger'); + } + + + public function getLoggerParameters() { + return $this->getContainer()->query('LoggerParameters'); + } } diff --git a/appinfo/database.xml b/appinfo/database.xml index eebd7603b..12b1ba4f9 100644 --- a/appinfo/database.xml +++ b/appinfo/database.xml @@ -1,269 +1,269 @@ <database> - <name>*dbname*</name> - <create>true</create> - <overwrite>false</overwrite> - <charset>utf8</charset> - <table> - <name>*dbprefix*news_folders</name> - <declaration> - <field> - <name>id</name> - <type>integer</type> - <notnull>true</notnull> - <autoincrement>true</autoincrement> - <unsigned>true</unsigned> - <primary>true</primary> - <length>8</length> - </field> - <field> - <name>parent_id</name> - <type>integer</type> - <length>8</length> - <notnull>false</notnull> - </field> - <field> - <name>name</name> - <type>text</type> - <length>100</length> - <notnull>true</notnull> - </field> - <field> - <name>user_id</name> - <type>text</type> - <default></default> - <notnull>true</notnull> - <length>64</length> - </field> - <field> - <name>opened</name> - <type>boolean</type> - <default>true</default> - <notnull>true</notnull> - </field> - <field> - <name>deleted_at</name> - <type>integer</type> - <length>8</length> - <default>0</default> - <notnull>false</notnull> - <unsigned>true</unsigned> - </field> + <name>*dbname*</name> + <create>true</create> + <overwrite>false</overwrite> + <charset>utf8</charset> + <table> + <name>*dbprefix*news_folders</name> + <declaration> + <field> + <name>id</name> + <type>integer</type> + <notnull>true</notnull> + <autoincrement>true</autoincrement> + <unsigned>true</unsigned> + <primary>true</primary> + <length>8</length> + </field> + <field> + <name>parent_id</name> + <type>integer</type> + <length>8</length> + <notnull>false</notnull> + </field> + <field> + <name>name</name> + <type>text</type> + <length>100</length> + <notnull>true</notnull> + </field> + <field> + <name>user_id</name> + <type>text</type> + <default></default> + <notnull>true</notnull> + <length>64</length> + </field> + <field> + <name>opened</name> + <type>boolean</type> + <default>true</default> + <notnull>true</notnull> + </field> + <field> + <name>deleted_at</name> + <type>integer</type> + <length>8</length> + <default>0</default> + <notnull>false</notnull> + <unsigned>true</unsigned> + </field> - <index> - <name>news_folders_parent_id_index</name> - <field> - <name>parent_id</name> - </field> - </index> + <index> + <name>news_folders_parent_id_index</name> + <field> + <name>parent_id</name> + </field> + </index> - <index> - <name>news_folders_user_id_index</name> - <field> - <name>user_id</name> - </field> - </index> - </declaration> - </table> + <index> + <name>news_folders_user_id_index</name> + <field> + <name>user_id</name> + </field> + </index> + </declaration> + </table> - <table> - <name>*dbprefix*news_feeds</name> - <declaration> - <field> - <name>id</name> - <type>integer</type> - <notnull>true</notnull> - <autoincrement>true</autoincrement> - <primary>true</primary> - <length>8</length> - <unsigned>true</unsigned> - </field> - <field> - <name>user_id</name> - <type>text</type> - <default></default> - <notnull>true</notnull> - <length>64</length> - </field> - <field> - <name>url_hash</name> - <type>text</type> - <length>32</length> - <notnull>true</notnull> - </field> - <field> - <name>url</name> - <type>clob</type> - <notnull>true</notnull> - </field> - <field> - <name>title</name> - <type>clob</type> - <notnull>true</notnull> - </field> - <field> - <name>link</name> - <type>clob</type> - <notnull>false</notnull> - </field> - <field> - <name>favicon_link</name> - <type>clob</type> - <notnull>false</notnull> - </field> - <field> - <name>added</name> - <type>integer</type> - <default></default> - <length>8</length> - <notnull>false</notnull> - <unsigned>true</unsigned> - </field> - <field> - <name>articles_per_update</name> - <type>integer</type> - <default>0</default> - <length>8</length> - <notnull>true</notnull> - </field> - <field> - <name>deleted_at</name> - <type>integer</type> - <default>0</default> - <notnull>false</notnull> - <length>8</length> - <unsigned>true</unsigned> - </field> - <field> - <name>folder_id</name> - <type>integer</type> - <length>8</length> - <notnull>true</notnull> - </field> - <field> - <name>prevent_update</name> - <type>boolean</type> - <default>false</default> - <notnull>true</notnull> - </field> + <table> + <name>*dbprefix*news_feeds</name> + <declaration> + <field> + <name>id</name> + <type>integer</type> + <notnull>true</notnull> + <autoincrement>true</autoincrement> + <primary>true</primary> + <length>8</length> + <unsigned>true</unsigned> + </field> + <field> + <name>user_id</name> + <type>text</type> + <default></default> + <notnull>true</notnull> + <length>64</length> + </field> + <field> + <name>url_hash</name> + <type>text</type> + <length>32</length> + <notnull>true</notnull> + </field> + <field> + <name>url</name> + <type>clob</type> + <notnull>true</notnull> + </field> + <field> + <name>title</name> + <type>clob</type> + <notnull>true</notnull> + </field> + <field> + <name>link</name> + <type>clob</type> + <notnull>false</notnull> + </field> + <field> + <name>favicon_link</name> + <type>clob</type> + <notnull>false</notnull> + </field> + <field> + <name>added</name> + <type>integer</type> + <default></default> + <length>8</length> + <notnull>false</notnull> + <unsigned>true</unsigned> + </field> + <field> + <name>articles_per_update</name> + <type>integer</type> + <default>0</default> + <length>8</length> + <notnull>true</notnull> + </field> + <field> + <name>deleted_at</name> + <type>integer</type> + <default>0</default> + <notnull>false</notnull> + <length>8</length> + <unsigned>true</unsigned> + </field> + <field> + <name>folder_id</name> + <type>integer</type> + <length>8</length> + <notnull>true</notnull> + </field> + <field> + <name>prevent_update</name> + <type>boolean</type> + <default>false</default> + <notnull>true</notnull> + </field> - <index> - <name>news_feeds_user_id_index</name> - <field> - <name>user_id</name> - </field> - </index> + <index> + <name>news_feeds_user_id_index</name> + <field> + <name>user_id</name> + </field> + </index> - <index> - <name>news_feeds_folder_id_index</name> - <field> - <name>folder_id</name> - </field> - </index> + <index> + <name>news_feeds_folder_id_index</name> + <field> + <name>folder_id</name> + </field> + </index> - <index> - <name>news_feeds_url_hash_index</name> - <field> - <name>url_hash</name> - </field> - </index> - </declaration> - </table> + <index> + <name>news_feeds_url_hash_index</name> + <field> + <name>url_hash</name> + </field> + </index> + </declaration> + </table> - <table> - <name>*dbprefix*news_items</name> - <declaration> - <field> - <name>id</name> - <type>integer</type> - <length>8</length> - <notnull>true</notnull> - <autoincrement>true</autoincrement> - <primary>true</primary> - <unsigned>true</unsigned> - </field> - <field> - <name>guid_hash</name> - <type>text</type> - <notnull>true</notnull> - <length>32</length> - </field> - <field> - <name>guid</name> - <type>clob</type> - <notnull>true</notnull> - </field> - <field> - <name>url</name> - <type>clob</type> - </field> - <field> - <name>title</name> - <type>clob</type> - </field> - <field> - <name>author</name> - <type>clob</type> - <notnull>false</notnull> - </field> - <field> - <name>pub_date</name> - <type>integer</type> - <length>8</length> - <unsigned>true</unsigned> - <notnull>false</notnull> - </field> - <field> - <name>body</name> - <type>clob</type> - <notnull>false</notnull> - </field> - <field> - <name>enclosure_mime</name> - <type>clob</type> - <notnull>false</notnull> - </field> - <field> - <name>enclosure_link</name> - <type>clob</type> - <notnull>false</notnull> - </field> - <field> - <name>feed_id</name> - <type>integer</type> - <length>8</length> - <notnull>true</notnull> - </field> - <field> - <name>status</name> - <type>integer</type> - <length>8</length> - <notnull>true</notnull> - </field> - <field> - <name>last_modified</name> - <type>integer</type> - <default></default> - <length>8</length> - <notnull>false</notnull> - <unsigned>true</unsigned> - </field> + <table> + <name>*dbprefix*news_items</name> + <declaration> + <field> + <name>id</name> + <type>integer</type> + <length>8</length> + <notnull>true</notnull> + <autoincrement>true</autoincrement> + <primary>true</primary> + <unsigned>true</unsigned> + </field> + <field> + <name>guid_hash</name> + <type>text</type> + <notnull>true</notnull> + <length>32</length> + </field> + <field> + <name>guid</name> + <type>clob</type> + <notnull>true</notnull> + </field> + <field> + <name>url</name> + <type>clob</type> + </field> + <field> + <name>title</name> + <type>clob</type> + </field> + <field> + <name>author</name> + <type>clob</type> + <notnull>false</notnull> + </field> + <field> + <name>pub_date</name> + <type>integer</type> + <length>8</length> + <unsigned>true</unsigned> + <notnull>false</notnull> + </field> + <field> + <name>body</name> + <type>clob</type> + <notnull>false</notnull> + </field> + <field> + <name>enclosure_mime</name> + <type>clob</type> + <notnull>false</notnull> + </field> + <field> + <name>enclosure_link</name> + <type>clob</type> + <notnull>false</notnull> + </field> + <field> + <name>feed_id</name> + <type>integer</type> + <length>8</length> + <notnull>true</notnull> + </field> + <field> + <name>status</name> + <type>integer</type> + <length>8</length> + <notnull>true</notnull> + </field> + <field> + <name>last_modified</name> + <type>integer</type> + <default></default> + <length>8</length> + <notnull>false</notnull> + <unsigned>true</unsigned> + </field> - <index> - <name>news_items_feed_id_index</name> - <field> - <name>feed_id</name> - </field> - </index> + <index> + <name>news_items_feed_id_index</name> + <field> + <name>feed_id</name> + </field> + </index> - <index> - <name>news_items_item_guid</name> - <field> - <name>guid_hash</name> - </field> - <field> - <name>feed_id</name> - </field> - </index> - </declaration> - </table> + <index> + <name>news_items_item_guid</name> + <field> + <name>guid_hash</name> + </field> + <field> + <name>feed_id</name> + </field> + </index> + </declaration> + </table> </database> diff --git a/appinfo/info.xml b/appinfo/info.xml index 3e6242c8e..91e51ad96 100644 --- a/appinfo/info.xml +++ b/appinfo/info.xml @@ -1,10 +1,10 @@ <?xml version="1.0"?> <info> - <id>news</id> - <name>News</name> - <description>An RSS/Atom feed reader. Requires ownCloud backgroundjobs or an updater script to be enabled to update your feeds. See the README.md in the apps top directory</description> + <id>news</id> + <name>News</name> + <description>An RSS/Atom feed reader. Requires ownCloud backgroundjobs or an updater script to be enabled to update your feeds. See the README.md in the apps top directory</description> <licence>AGPL</licence> - <version>3.406</version> - <require>7.0.3</require> + <version>3.406</version> + <require>7.0.3</require> <author>Bernhard Posselt, Alessandro Cosentino, Jan-Christoph Borchardt</author> </info> diff --git a/appinfo/routes.php b/appinfo/routes.php index 930fdb136..4287bd4a9 100644 --- a/appinfo/routes.php +++ b/appinfo/routes.php @@ -17,82 +17,82 @@ use \OCA\News\AppInfo\Application; $application = new Application(); $application->registerRoutes($this, ['routes' => [ - // page - ['name' => 'page#index', 'url' => '/', 'verb' => 'GET'], - ['name' => 'page#settings', 'url' => '/settings', 'verb' => 'GET'], - ['name' => 'page#update_settings', 'url' => '/settings', 'verb' => 'PUT'], - ['name' => 'page#manifest', 'url' => '/manifest.webapp', 'verb' => 'GET'], + // page + ['name' => 'page#index', 'url' => '/', 'verb' => 'GET'], + ['name' => 'page#settings', 'url' => '/settings', 'verb' => 'GET'], + ['name' => 'page#update_settings', 'url' => '/settings', 'verb' => 'PUT'], + ['name' => 'page#manifest', 'url' => '/manifest.webapp', 'verb' => 'GET'], - // admin - ['name' => 'admin#update', 'url' => '/admin', 'verb' => 'PUT'], + // admin + ['name' => 'admin#update', 'url' => '/admin', 'verb' => 'PUT'], - // folders - ['name' => 'folder#index', 'url' => '/folders', 'verb' => 'GET'], - ['name' => 'folder#create', 'url' => '/folders', 'verb' => 'POST'], - ['name' => 'folder#delete', 'url' => '/folders/{folderId}', 'verb' => 'DELETE'], - ['name' => 'folder#restore', 'url' => '/folders/{folderId}/restore', 'verb' => 'POST'], - ['name' => 'folder#rename', 'url' => '/folders/{folderId}/rename', 'verb' => 'POST'], - ['name' => 'folder#read', 'url' => '/folders/{folderId}/read', 'verb' => 'POST'], - ['name' => 'folder#open', 'url' => '/folders/{folderId}/open', 'verb' => 'POST'], + // folders + ['name' => 'folder#index', 'url' => '/folders', 'verb' => 'GET'], + ['name' => 'folder#create', 'url' => '/folders', 'verb' => 'POST'], + ['name' => 'folder#delete', 'url' => '/folders/{folderId}', 'verb' => 'DELETE'], + ['name' => 'folder#restore', 'url' => '/folders/{folderId}/restore', 'verb' => 'POST'], + ['name' => 'folder#rename', 'url' => '/folders/{folderId}/rename', 'verb' => 'POST'], + ['name' => 'folder#read', 'url' => '/folders/{folderId}/read', 'verb' => 'POST'], + ['name' => 'folder#open', 'url' => '/folders/{folderId}/open', 'verb' => 'POST'], - // feeds - ['name' => 'feed#index', 'url' => '/feeds', 'verb' => 'GET'], - ['name' => 'feed#create', 'url' => '/feeds', 'verb' => 'POST'], - ['name' => 'feed#delete', 'url' => '/feeds/{feedId}', 'verb' => 'DELETE'], - ['name' => 'feed#restore', 'url' => '/feeds/{feedId}/restore', 'verb' => 'POST'], - ['name' => 'feed#move', 'url' => '/feeds/{feedId}/move', 'verb' => 'POST'], - ['name' => 'feed#rename', 'url' => '/feeds/{feedId}/rename', 'verb' => 'POST'], - ['name' => 'feed#read', 'url' => '/feeds/{feedId}/read', 'verb' => 'POST'], - ['name' => 'feed#update', 'url' => '/feeds/{feedId}/update', 'verb' => 'POST'], - ['name' => 'feed#active', 'url' => '/feeds/active', 'verb' => 'GET'], - ['name' => 'feed#import', 'url' => '/feeds/import/articles', 'verb' => 'POST'], + // feeds + ['name' => 'feed#index', 'url' => '/feeds', 'verb' => 'GET'], + ['name' => 'feed#create', 'url' => '/feeds', 'verb' => 'POST'], + ['name' => 'feed#delete', 'url' => '/feeds/{feedId}', 'verb' => 'DELETE'], + ['name' => 'feed#restore', 'url' => '/feeds/{feedId}/restore', 'verb' => 'POST'], + ['name' => 'feed#move', 'url' => '/feeds/{feedId}/move', 'verb' => 'POST'], + ['name' => 'feed#rename', 'url' => '/feeds/{feedId}/rename', 'verb' => 'POST'], + ['name' => 'feed#read', 'url' => '/feeds/{feedId}/read', 'verb' => 'POST'], + ['name' => 'feed#update', 'url' => '/feeds/{feedId}/update', 'verb' => 'POST'], + ['name' => 'feed#active', 'url' => '/feeds/active', 'verb' => 'GET'], + ['name' => 'feed#import', 'url' => '/feeds/import/articles', 'verb' => 'POST'], - // items - ['name' => 'item#index', 'url' => '/items', 'verb' => 'GET'], - ['name' => 'item#new_items', 'url' => '/items/new', 'verb' => 'GET'], - ['name' => 'item#readAll', 'url' => '/items/read', 'verb' => 'POST'], - ['name' => 'item#read', 'url' => '/items/{itemId}/read', 'verb' => 'POST'], - ['name' => 'item#read_multiple', 'url' => '/items/read/multiple', 'verb' => 'POST'], - ['name' => 'item#star', 'url' => '/items/{feedId}/{guidHash}/star', 'verb' => 'POST'], + // items + ['name' => 'item#index', 'url' => '/items', 'verb' => 'GET'], + ['name' => 'item#new_items', 'url' => '/items/new', 'verb' => 'GET'], + ['name' => 'item#readAll', 'url' => '/items/read', 'verb' => 'POST'], + ['name' => 'item#read', 'url' => '/items/{itemId}/read', 'verb' => 'POST'], + ['name' => 'item#read_multiple', 'url' => '/items/read/multiple', 'verb' => 'POST'], + ['name' => 'item#star', 'url' => '/items/{feedId}/{guidHash}/star', 'verb' => 'POST'], - // export - ['name' => 'export#opml', 'url' => '/export/opml', 'verb' => 'GET'], - ['name' => 'export#articles', 'url' => '/export/articles', 'verb' => 'GET'], + // export + ['name' => 'export#opml', 'url' => '/export/opml', 'verb' => 'GET'], + ['name' => 'export#articles', 'url' => '/export/articles', 'verb' => 'GET'], - // API 1.2 - ['name' => 'utility_api#version', 'url' => '/api/v1-2/version', 'verb' => 'GET'], - ['name' => 'utility_api#before_update', 'url' => '/api/v1-2/cleanup/before-update', 'verb' => 'GET'], - ['name' => 'utility_api#after_update', 'url' => '/api/v1-2/cleanup/after-update', 'verb' => 'GET'], - ['name' => 'utility_api#preflighted_cors', 'url' => '/api/v1-2/{path}', 'verb' => 'OPTIONS', 'requirements' => ['path' => '.+']], + // API 1.2 + ['name' => 'utility_api#version', 'url' => '/api/v1-2/version', 'verb' => 'GET'], + ['name' => 'utility_api#before_update', 'url' => '/api/v1-2/cleanup/before-update', 'verb' => 'GET'], + ['name' => 'utility_api#after_update', 'url' => '/api/v1-2/cleanup/after-update', 'verb' => 'GET'], + ['name' => 'utility_api#preflighted_cors', 'url' => '/api/v1-2/{path}', 'verb' => 'OPTIONS', 'requirements' => ['path' => '.+']], - // folders - ['name' => 'folder_api#index', 'url' => '/api/v1-2/folders', 'verb' => 'GET'], - ['name' => 'folder_api#create', 'url' => '/api/v1-2/folders', 'verb' => 'POST'], - ['name' => 'folder_api#update', 'url' => '/api/v1-2/folders/{folderId}', 'verb' => 'PUT'], - ['name' => 'folder_api#delete', 'url' => '/api/v1-2/folders/{folderId}', 'verb' => 'DELETE'], - ['name' => 'folder_api#read', 'url' => '/api/v1-2/folders/{folderId}/read', 'verb' => 'PUT'], // FIXME: POST would be more correct + // folders + ['name' => 'folder_api#index', 'url' => '/api/v1-2/folders', 'verb' => 'GET'], + ['name' => 'folder_api#create', 'url' => '/api/v1-2/folders', 'verb' => 'POST'], + ['name' => 'folder_api#update', 'url' => '/api/v1-2/folders/{folderId}', 'verb' => 'PUT'], + ['name' => 'folder_api#delete', 'url' => '/api/v1-2/folders/{folderId}', 'verb' => 'DELETE'], + ['name' => 'folder_api#read', 'url' => '/api/v1-2/folders/{folderId}/read', 'verb' => 'PUT'], // FIXME: POST would be more correct - // feeds - ['name' => 'feed_api#index', 'url' => '/api/v1-2/feeds', 'verb' => 'GET'], - ['name' => 'feed_api#create', 'url' => '/api/v1-2/feeds', 'verb' => 'POST'], - ['name' => 'feed_api#update', 'url' => '/api/v1-2/feeds/{feedId}', 'verb' => 'PUT'], - ['name' => 'feed_api#delete', 'url' => '/api/v1-2/feeds/{feedId}', 'verb' => 'DELETE'], - ['name' => 'feed_api#from_all_users', 'url' => '/api/v1-2/feeds/all', 'verb' => 'GET'], - ['name' => 'feed_api#move', 'url' => '/api/v1-2/feeds/{feedId}/move', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'feed_api#rename', 'url' => '/api/v1-2/feeds/{feedId}/rename', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'feed_api#read', 'url' => '/api/v1-2/feeds/{feedId}/read', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'feed_api#update', 'url' => '/api/v1-2/feeds/update', 'verb' => 'GET'], + // feeds + ['name' => 'feed_api#index', 'url' => '/api/v1-2/feeds', 'verb' => 'GET'], + ['name' => 'feed_api#create', 'url' => '/api/v1-2/feeds', 'verb' => 'POST'], + ['name' => 'feed_api#update', 'url' => '/api/v1-2/feeds/{feedId}', 'verb' => 'PUT'], + ['name' => 'feed_api#delete', 'url' => '/api/v1-2/feeds/{feedId}', 'verb' => 'DELETE'], + ['name' => 'feed_api#from_all_users', 'url' => '/api/v1-2/feeds/all', 'verb' => 'GET'], + ['name' => 'feed_api#move', 'url' => '/api/v1-2/feeds/{feedId}/move', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'feed_api#rename', 'url' => '/api/v1-2/feeds/{feedId}/rename', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'feed_api#read', 'url' => '/api/v1-2/feeds/{feedId}/read', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'feed_api#update', 'url' => '/api/v1-2/feeds/update', 'verb' => 'GET'], - // items - ['name' => 'item_api#index', 'url' => '/api/v1-2/items', 'verb' => 'GET'], - ['name' => 'item_api#updated', 'url' => '/api/v1-2/items/updated', 'verb' => 'GET'], - ['name' => 'item_api#read', 'url' => '/api/v1-2/items/{itemId}/read', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'item_api#unread', 'url' => '/api/v1-2/items/{itemId}/unread', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'item_api#read_all', 'url' => '/api/v1-2/items/read', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'item_api#read_multiple', 'url' => '/api/v1-2/items/read/multiple', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'item_api#unread_multiple', 'url' => '/api/v1-2/items/unread/multiple', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'item_api#star', 'url' => '/api/v1-2/items/{feedId}/{guidHash}/star', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'item_api#unstar', 'url' => '/api/v1-2/items/{feedId}/{guidHash}/unstar', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'item_api#star_multiple', 'url' => '/api/v1-2/items/star/multiple', 'verb' => 'PUT'], // FIXME: POST would be more correct - ['name' => 'item_api#unstar_multiple', 'url' => '/api/v1-2/items/unstar/multiple', 'verb' => 'PUT'], // FIXME: POST would be more correct + // items + ['name' => 'item_api#index', 'url' => '/api/v1-2/items', 'verb' => 'GET'], + ['name' => 'item_api#updated', 'url' => '/api/v1-2/items/updated', 'verb' => 'GET'], + ['name' => 'item_api#read', 'url' => '/api/v1-2/items/{itemId}/read', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'item_api#unread', 'url' => '/api/v1-2/items/{itemId}/unread', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'item_api#read_all', 'url' => '/api/v1-2/items/read', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'item_api#read_multiple', 'url' => '/api/v1-2/items/read/multiple', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'item_api#unread_multiple', 'url' => '/api/v1-2/items/unread/multiple', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'item_api#star', 'url' => '/api/v1-2/items/{feedId}/{guidHash}/star', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'item_api#unstar', 'url' => '/api/v1-2/items/{feedId}/{guidHash}/unstar', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'item_api#star_multiple', 'url' => '/api/v1-2/items/star/multiple', 'verb' => 'PUT'], // FIXME: POST would be more correct + ['name' => 'item_api#unstar_multiple', 'url' => '/api/v1-2/items/unstar/multiple', 'verb' => 'PUT'], // FIXME: POST would be more correct ]]); diff --git a/articleenhancer/articleenhancer.php b/articleenhancer/articleenhancer.php index 0587f4bad..a151de656 100644 --- a/articleenhancer/articleenhancer.php +++ b/articleenhancer/articleenhancer.php @@ -21,5 +21,5 @@ interface ArticleEnhancer { * @param \OCA\News\Db\Item $item * @return \OCA\News\Db\Item enhanced item */ - public function enhance(Item $item); + public function enhance(Item $item); }
\ No newline at end of file diff --git a/articleenhancer/enhancer.php b/articleenhancer/enhancer.php index e0ad2ab2d..abe8360d2 100644 --- a/articleenhancer/enhancer.php +++ b/articleenhancer/enhancer.php @@ -16,68 +16,68 @@ namespace OCA\News\ArticleEnhancer; class Enhancer { - private $enhancers = []; - private $globalEnhancers = []; - - /** - * @param string $feedUrl - * @param ArticleEnhancer $enhancer - */ - public function registerEnhancer($feedUrl, ArticleEnhancer $enhancer){ - $feedUrl = $this->removeTrailingSlash($feedUrl); - - // create hashkeys for all supported protocols for quick access - $this->enhancers[$feedUrl] = $enhancer; - $this->enhancers['https://' . $feedUrl] = $enhancer; - $this->enhancers['http://' . $feedUrl] = $enhancer; - $this->enhancers['https://www.' . $feedUrl] = $enhancer; - $this->enhancers['http://www.' . $feedUrl] = $enhancer; - } - - - /** - * Registers enhancers that are run for every item and after all previous - * enhancers have been run - * @param ArticleEnhancer $enhancer - */ - public function registerGlobalEnhancer (ArticleEnhancer $enhancer) { - $this->globalEnhancers[] = $enhancer; - } - - - /** - * @param \OCA\News\Db\Item $item - * @param string $feedUrl - * @return \OCA\News\Db\Item enhanced item - */ - public function enhance($item, $feedUrl){ - $feedUrl = $this->removeTrailingSlash($feedUrl); - - if(array_key_exists($feedUrl, $this->enhancers)) { - $result = $this->enhancers[$feedUrl]->enhance($item); - } else { - $result = $item; - } - - foreach ($this->globalEnhancers as $enhancer) { - $result = $enhancer->enhance($result); - } - - return $result; - } + private $enhancers = []; + private $globalEnhancers = []; + + /** + * @param string $feedUrl + * @param ArticleEnhancer $enhancer + */ + public function registerEnhancer($feedUrl, ArticleEnhancer $enhancer){ + $feedUrl = $this->removeTrailingSlash($feedUrl); + + // create hashkeys for all supported protocols for quick access + $this->enhancers[$feedUrl] = $enhancer; + $this->enhancers['https://' . $feedUrl] = $enhancer; + $this->enhancers['http://' . $feedUrl] = $enhancer; + $this->enhancers['https://www.' . $feedUrl] = $enhancer; + $this->enhancers['http://www.' . $feedUrl] = $enhancer; + } + + + /** + * Registers enhancers that are run for every item and after all previous + * enhancers have been run + * @param ArticleEnhancer $enhancer + */ + public function registerGlobalEnhancer (ArticleEnhancer $enhancer) { + $this->globalEnhancers[] = $enhancer; + } + + + /** + * @param \OCA\News\Db\Item $item + * @param string $feedUrl + * @return \OCA\News\Db\Item enhanced item + */ + public function enhance($item, $feedUrl){ + $feedUrl = $this->removeTrailingSlash($feedUrl); + + if(array_key_exists($feedUrl, $this->enhancers)) { + $result = $this->enhancers[$feedUrl]->enhance($item); + } else { + $result = $item; + } + + foreach ($this->globalEnhancers as $enhancer) { + $result = $enhancer->enhance($result); + } + + return $result; + } /** * @param string $url * @return string */ - private function removeTrailingSlash($url) { - if($url[strlen($url)-1] === '/') { - return substr($url, 0, -1); - } else { - return $url; - } - } + private function removeTrailingSlash($url) { + if($url[strlen($url)-1] === '/') { + return substr($url, 0, -1); + } else { + return $url; + } + } }
\ No newline at end of file diff --git a/articleenhancer/globalarticleenhancer.php b/articleenhancer/globalarticleenhancer.php index 117c0981c..b556a285a 100644 --- a/articleenhancer/globalarticleenhancer.php +++ b/articleenhancer/globalarticleenhancer.php @@ -21,47 +21,47 @@ use \OCA\News\Db\Item; class GlobalArticleEnhancer implements ArticleEnhancer { - /** - * This method is run after all enhancers and for every item - */ - public function enhance(Item $item) { + /** + * This method is run after all enhancers and for every item + */ + public function enhance(Item $item) { - $dom = new \DOMDocument(); + $dom = new \DOMDocument(); - // wrap it inside a div if there is none to prevent invalid wrapping - // inside <p> tags - $body = '<div>' . $item->getBody() . '</div>'; + // wrap it inside a div if there is none to prevent invalid wrapping + // inside <p> tags + $body = '<div>' . $item->getBody() . '</div>'; - Security::scan($body, $dom, function ($xml, $dom) { - return @$dom->loadHTML($xml, LIBXML_HTML_NOIMPLIED - | LIBXML_HTML_NODEFDTD | LIBXML_NONET); - }); + Security::scan($body, $dom, function ($xml, $dom) { + return @$dom->loadHTML($xml, LIBXML_HTML_NOIMPLIED + | LIBXML_HTML_NODEFDTD | LIBXML_NONET); + }); - $xpath = new \DOMXpath($dom); + $xpath = new \DOMXpath($dom); - // remove youtube autoplay - // NOTE: PHP supports only XPath 1.0 so no matches() function :( - $youtubeIframes = "//iframe[contains(@src, 'youtube.com')]"; + // remove youtube autoplay + // NOTE: PHP supports only XPath 1.0 so no matches() function :( + $youtubeIframes = "//iframe[contains(@src, 'youtube.com')]"; - $elements = $xpath->query($youtubeIframes); - foreach ($elements as $element) { + $elements = $xpath->query($youtubeIframes); + foreach ($elements as $element) { - // src needs to be matched against regex to prevent false positives - // and because theres no XPath matches function available - $src = $element->getAttribute('src'); - $regex = '%^(http://|https://|//)(www\.)?youtube.com/.*\?.*autoplay=1.*%i'; + // src needs to be matched against regex to prevent false positives + // and because theres no XPath matches function available + $src = $element->getAttribute('src'); + $regex = '%^(http://|https://|//)(www\.)?youtube.com/.*\?.*autoplay=1.*%i'; - if (preg_match($regex, $src)) { - $replaced = str_replace('autoplay=1', 'autoplay=0', $src); - $element->setAttribute('src', $replaced); - } - } + if (preg_match($regex, $src)) { + $replaced = str_replace('autoplay=1', 'autoplay=0', $src); + $element->setAttribute('src', $replaced); + } + } - // save all changes back to the item - $item->setBody(trim($dom->saveHTML())); + // save all changes back to the item + $item->setBody(trim($dom->saveHTML())); - return $item; - } + return $item; + } }
\ No newline at end of file diff --git a/articleenhancer/regexarticleenhancer.php b/articleenhancer/regexarticleenhancer.php index 543eca09b..0f600468e 100644 --- a/articleenhancer/regexarticleenhancer.php +++ b/articleenhancer/regexarticleenhancer.php @@ -18,29 +18,29 @@ use \OCA\News\Db\Item; class RegexArticleEnhancer implements ArticleEnhancer { - private $matchArticleUrl; - private $regexPair; - - public function __construct($matchArticleUrl, array $regexPair) { - $this->matchArticleUrl = $matchArticleUrl; - $this->regexPair = $regexPair; - } - - - /** - * @param \OCA\News\Db\Item $item - * @return \OCA\News\Db\Item enhanced item - */ - public function enhance(Item $item) { - if (preg_match($this->matchArticleUrl, $item->getUrl())) { - $body = $item->getBody(); - foreach($this->regexPair as $search => $replaceWith) { - $body = preg_replace($search, $replaceWith, $body); - } - $item->setBody($body); - } - return $item; - } + private $matchArticleUrl; + private $regexPair; + + public function __construct($matchArticleUrl, array $regexPair) { + $this->matchArticleUrl = $matchArticleUrl; + $this->regexPair = $regexPair; + } + + + /** + * @param \OCA\News\Db\Item $item + * @return \OCA\News\Db\Item enhanced item + */ + public function enhance(Item $item) { + if (preg_match($this->matchArticleUrl, $item->getUrl())) { + $body = $item->getBody(); + foreach($this->regexPair as $search => $replaceWith) { + $body = preg_replace($search, $replaceWith, $body); + } + $item->setBody($body); + } + return $item; + } } diff --git a/articleenhancer/regexenhancers.json b/articleenhancer/regexenhancers.json index 1a67900aa..fd83d0b3f 100644 --- a/articleenhancer/regexenhancers.json +++ b/articleenhancer/regexenhancers.json @@ -1,36 +1,36 @@ { - "twogag.com": { - "%(?:www.twogag.com/archives)|(feedproxy.google.com/~r/TwoGuysAndGuy)%": { - "%http://www.twogag.com/comics-rss/([^.]+)\\.jpg%": "http://www.twogag.com/comics/$1.jpg" - } - }, - "buttersafe.com": { - "%(?:buttersafe.com)|(feedproxy.google.com/~r/Buttersafe)%": { - "%buttersafe.com/comics/rss/([^.]+)RSS([^.]+)?.jpg%": "buttersafe.com/comics/$1$2.jpg" - } - }, - "nichtlustig.de": { - "%nichtlustig.de%": { - "%.*static.nichtlustig.de/comics/full/(\\d+).*%s": "<img src=\"http://static.nichtlustig.de/comics/full/$1.jpg\" />" - } - }, - "nerfnow.com": { - "%feedproxy.google.com/~r/nerfnow%": { - "%(width|width)=\"\\d+\"%": "", - "%nerfnow.com/comic/thumb/(\\d+)/large%": "nerfnow.com/comic/image/$1", - "%<div><a target=\"_blank\" href=\"http://www.nerfnow.com/comic/\\d+\">Click for full size</a></div>%": "", - "%<img src=\"http://feeds.feedburner.com[^>]+>%": "" - } - }, - "fowllanguagecomics.com": { - "%fowllanguagecomics.com/comic%": { - "%\\?resize=[^\"]+%": "" - } - }, - "cheerupemokid.com": { - "%feedproxy.google.com/~r/cheerupemokid%": { - "%-\\d+x\\d+%": "", - "%(width|height)=\"\\d+\"%" : "" - } - } + "twogag.com": { + "%(?:www.twogag.com/archives)|(feedproxy.google.com/~r/TwoGuysAndGuy)%": { + "%http://www.twogag.com/comics-rss/([^.]+)\\.jpg%": "http://www.twogag.com/comics/$1.jpg" + } + }, + "buttersafe.com": { + "%(?:buttersafe.com)|(feedproxy.google.com/~r/Buttersafe)%": { + "%buttersafe.com/comics/rss/([^.]+)RSS([^.]+)?.jpg%": "buttersafe.com/comics/$1$2.jpg" + } + }, + "nichtlustig.de": { + "%nichtlustig.de%": { + "%.*static.nichtlustig.de/comics/full/(\\d+).*%s": "<img src=\"http://static.nichtlustig.de/comics/full/$1.jpg\" />" + } + }, + "nerfnow.com": { + "%feedproxy.google.com/~r/nerfnow%": { + "%(width|width)=\"\\d+\"%": "", + "%nerfnow.com/comic/thumb/(\\d+)/large%": "nerfnow.com/comic/image/$1", + "%<div><a target=\"_blank\" href=\"http://www.nerfnow.com/comic/\\d+\">Click for full size</a></div>%": "", + "%<img src=\"http://feeds.feedburner.com[^>]+>%": "" + } + }, + "fowllanguagecomics.com": { + "%fowllanguagecomics.com/comic%": { + "%\\?resize=[^\"]+%": "" + } + }, + "cheerupemokid.com": { + "%feedproxy.google.com/~r/cheerupemokid%": { + "%-\\d+x\\d+%": "", + "%(width|height)=\"\\d+\"%" : "" + } + } } diff --git a/articleenhancer/xpatharticleenhancer.php b/articleenhancer/xpatharticleenhancer.php index 623b42bfc..7d80868f5 100644 --- a/articleenhancer/xpatharticleenhancer.php +++ b/articleenhancer/xpatharticleenhancer.php @@ -27,10 +27,10 @@ use \OCA\News\Config\Config; class XPathArticleEnhancer implements ArticleEnhancer { - private $fileFactory; - private $maximumTimeout; - private $config; - private $regexXPathPair; + private $fileFactory; + private $maximumTimeout; + private $config; + private $regexXPathPair; /** @@ -40,152 +40,152 @@ class XPathArticleEnhancer implements ArticleEnhancer { * page * @param \OCA\News\Config\Config $config */ - public function __construct(SimplePieAPIFactory $fileFactory, - array $regexXPathPair, - Config $config){ - $this->fileFactory = $fileFactory; - $this->regexXPathPair = $regexXPathPair; - $this->config = $config; - $this->maximumTimeout = $config->getFeedFetcherTimeout(); - } - - /** - * @param \OCA\News\Db\Item $item - * @return \OCA\News\Db\Item enhanced item - */ - public function enhance(Item $item){ - - foreach($this->regexXPathPair as $regex => $search) { - - if(preg_match($regex, $item->getUrl())) { - $file = $this->getFile($item->getUrl()); - - // convert encoding by detecting charset from header + public function __construct(SimplePieAPIFactory $fileFactory, + array $regexXPathPair, + Config $config){ + $this->fileFactory = $fileFactory; + $this->regexXPathPair = $regexXPathPair; + $this->config = $config; + $this->maximumTimeout = $config->getFeedFetcherTimeout(); + } + + /** + * @param \OCA\News\Db\Item $item + * @return \OCA\News\Db\Item enhanced item + */ + public function enhance(Item $item){ + + foreach($this->regexXPathPair as $regex => $search) { + + if(preg_match($regex, $item->getUrl())) { + $file = $this->getFile($item->getUrl()); + + // convert encoding by detecting charset from header $contentType = $file->headers['content-type']; $body = $file->body; - if( preg_match( '/(?<=charset=)[^;]*/', $contentType, $matches ) ) { + if( preg_match( '/(?<=charset=)[^;]*/', $contentType, $matches ) ) { $body = mb_convert_encoding($body, 'HTML-ENTITIES', $matches[0]); - } - - $dom = new DOMDocument(); - - Security::scan($body, $dom, function ($xml, $dom) { - return @$dom->loadHTML($xml, LIBXML_NONET); - }); - - $xpath = new DOMXpath($dom); - $xpathResult = $xpath->evaluate($search); - - // in case it wasnt a text query assume its a dom element and - // convert it to text - if(!is_string($xpathResult)) { - $xpathResult = $this->domToString($xpathResult); - } - - $xpathResult = trim($xpathResult); - - // convert all relative to absolute URLs - $xpathResult = $this->substituteRelativeLinks($xpathResult, $item->getUrl()); - - if($xpathResult) { - $item->setBody($xpathResult); - } - } - } - - return $item; - } - - - private function getFile($url) { - return $this->fileFactory->getFile( - $url, $this->maximumTimeout, 5, null, 'Mozilla/5.0 AppleWebKit' - ); - } - - - /** - * Method which converts all relative "href" and "src" URLs of - * a HTML snippet with their absolute equivalent - * @param string $xmlString a HTML snippet as string with the relative URLs to be replaced - * @param string $absoluteUrl the approptiate absolute url of the HTML snippet - * @return string the result HTML snippet as a string - */ - protected function substituteRelativeLinks($xmlString, $absoluteUrl) { - $dom = new DOMDocument(); - $dom->preserveWhiteSpace = false; - - $isOk = Security::scan($xmlString, $dom, function ($xml, $dom) { - // wrap in div to prevent loadHTML from inserting weird elements - $xml = '<div>' . $xml . '</div>'; - return @$dom->loadHTML($xml, LIBXML_NONET | LIBXML_HTML_NODEFDTD - | LIBXML_HTML_NOIMPLIED); - }); - - if($xmlString === '' || !$isOk) { - return false; - } - - foreach (['href', 'src'] as $attribute) { - $xpath = new DOMXpath($dom); - $xpathResult = $xpath->query( - "//*[@" . $attribute . " " . - "and not(contains(@" . $attribute . ", '://')) " . - "and not(starts-with(@" . $attribute . ", 'mailto:')) " . - "and not(starts-with(@" . $attribute . ", '//'))]"); - foreach ($xpathResult as $linkNode) { - $urlElement = $linkNode->attributes->getNamedItem($attribute); - $abs = $this->relativeToAbsoluteUrl($urlElement->nodeValue, $absoluteUrl); - $urlElement->nodeValue = htmlspecialchars($abs); - } - } - - $xmlString = $dom->saveHTML(); - - // domdocument spoils the string with line breaks between the elements. strip them. - $xmlString = str_replace("\n", '', $xmlString); - - return $xmlString; - } - - - /** - * Method which builds a URL by taking a relative URL and its corresponding - * absolute URL - * For example relative URL "../example/path/file.php?a=1#anchor" and - * absolute URL "https://username:password@www.website.com/subfolder/index.html" - * will result in "https://username:password@www.website.com/example/path/file.php?a=1#anchor" - * @param string $relativeUrl the relative URL - * @param string $absoluteUrl the absolute URL with at least scheme and host - * @return string the resulting absolute URL - */ - protected function relativeToAbsoluteUrl($relativeUrl, $absoluteUrl) { - $base = new \Net_URL2($absoluteUrl); - return $base->resolve($relativeUrl); - } - - - /** - * Method which turns an xpath result to a string - * you can customize it by overwriting this method - * @param mixed $xpathResult the result from the xpath query - * @return string the result as a string - */ - protected function domToString($xpathResult) { - $result = ''; - foreach($xpathResult as $node) { - $result .= $this->toInnerHTML($node); - } - return $result; - } - - - protected function toInnerHTML($node) { - $dom = new DOMDocument(); - $dom->appendChild($dom->importNode($node, true)); - return trim($dom->saveHTML($dom->documentElement)); - } + } + + $dom = new DOMDocument(); + + Security::scan($body, $dom, function ($xml, $dom) { + return @$dom->loadHTML($xml, LIBXML_NONET); + }); + + $xpath = new DOMXpath($dom); + $xpathResult = $xpath->evaluate($search); + + // in case it wasnt a text query assume its a dom element and + // convert it to text + if(!is_string($xpathResult)) { + $xpathResult = $this->domToString($xpathResult); + } + + $xpathResult = trim($xpathResult); + + // convert all relative to absolute URLs + $xpathResult = $this->substituteRelativeLinks($xpathResult, $item->getUrl()); + + if($xpathResult) { + $item->setBody($xpathResult); + } + } + } + + return $item; + } + + + private function getFile($url) { + return $this->fileFactory->getFile( + $url, $this->maximumTimeout, 5, null, 'Mozilla/5.0 AppleWebKit' + ); + } + + + /** + * Method which converts all relative "href" and "src" URLs of + * a HTML snippet with their absolute equivalent + * @param string $xmlString a HTML snippet as string with the relative URLs to be replaced + * @param string $absoluteUrl the approptiate absolute url of the HTML snippet + * @return string the result HTML snippet as a string + */ + protected function substituteRelativeLinks($xmlString, $absoluteUrl) { + $dom = new DOMDocument(); + $dom->preserveWhiteSpace = false; + + $isOk = Security::scan($xmlString, $dom, function ($xml, $dom) { + // wrap in div to prevent loadHTML from inserting weird elements + $xml = '<div>' . $xml . '</div>'; + return @$dom->loadHTML($xml, LIBXML_NONET | LIBXML_HTML_NODEFDTD + | LIBXML_HTML_NOIMPLIED); + }); + + if($xmlString === '' || !$isOk) { + return false; + } + + foreach (['href', 'src'] as $attribute) { + $xpath = new DOMXpath($dom); + $xpathResult = $xpath->query( + "//*[@" . $attribute . " " . + "and not(contains(@" . $attribute . ", '://')) " . + "and not(starts-with(@" . $attribute . ", 'mailto:')) " . + "and not(starts-with(@" . $attribute . ", '//'))]"); + foreach ($xpathResult as $linkNode) { + $urlElement = $linkNode->attributes->getNamedItem($attribute); + $abs = $this->relativeToAbsoluteUrl($urlElement->nodeValue, $absoluteUrl); + $urlElement->nodeValue = htmlspecialchars($abs); + } + } + + $xmlString = $dom->saveHTML(); + + // domdocument spoils the string with line breaks between the elements. strip them. + $xmlString = str_replace("\n", '', $xmlString); + + return $xmlString; + } + + + /** + * Method which builds a URL by taking a relative URL and its corresponding + * absolute URL + * For example relative URL "../example/path/file.php?a=1#anchor" and + * absolute URL "https://username:password@www.website.com/subfolder/index.html" + * will result in "https://username:password@www.website.com/example/path/file.php?a=1#anchor" + * @param string $relativeUrl the relative URL + * @param string $absoluteUrl the absolute URL with at least scheme and host + * @return string the resulting absolute URL + */ + protected function relativeToAbsoluteUrl($relativeUrl, $absoluteUrl) { + $base = new \Net_URL2($absoluteUrl); + return $base->resolve($relativeUrl); + } + + + /** + * Method which turns an xpath result to a string + * you can customize it by overwriting this method + * @param mixed $xpathResult the result from the xpath query + * @return string the result as a string + */ + protected function domToString($xpathResult) { + $result = ''; + foreach($xpathResult as $node) { + $result .= $this->toInnerHTML($node); + } + return $result; + } + + + protected function toInnerHTML($node) { + $dom = new DOMDocument(); + $dom->appendChild($dom->importNode($node, true)); + return trim($dom->saveHTML($dom->documentElement)); + } } diff --git a/articleenhancer/xpathenhancers.json b/articleenhancer/xpathenhancers.json index 1441ce920..4a66e86d1 100644 --- a/articleenhancer/xpathenhancers.json +++ b/articleenhancer/xpathenhancers.json @@ -1,126 +1,126 @@ { - "cad-comic.com": { - "%cad-comic.com/cad/\\d+/$%": "//*[@id='content']/img" - }, - "slashdot.org": { - "%rss.slashdot.org%": "//article/div[@class='body'] | //article[@class='layout-article']/div" - }, - "explosm.net": { - "%explosm.net/comics%": "//*[@id='maincontent']/div[2]/div/img", - "%explosm.net/show%": "//*[@id='videoPlayer']/iframe" - }, - "themerepublic.net": { - "%feedproxy.google.com/~r/blogspot/DngUJ%": "//*[@class='post hentry']" - }, - "penny-arcade.com": { - "%penny-arcade.com/comic%": "//*[@id='comicFrame']/a/img", - "%penny-arcade.com/news%": "//*[@class='postBody']/*" - }, - "leasticoulddo.com": { - "%feedproxy.google.com/~r/LICD%": "//*[@id='comic-img']/a/img | //*[@id='comic-img']/img | //*[@id='post']" - }, - "escapistmagazine.com/articles/view/comicsandcosplay/comics/critical-miss": { - "%escapistmagazine.com/articles/view/comicsandcosplay/comics/critical-miss%": "//*[@class='body']/span/img | //div[@class='folder_nav_links']/following::p" - }, - "escapistmagazine.com/articles/view/comicsandcosplay/comics/namegame": { - "%escapistmagazine.com/articles/view/comicsandcosplay/comics/namegame%": "//*[@class='body']/span/p/img[@height != \"120\"]" - }, - "escapistmagazine.com/articles/view/comicsandcosplay/comics/stolen-pixels": { - "%escapistmagazine.com/articles/view/comicsandcosplay/comics/stolen-pixels%": "//*[@class='body']/span/p[2]/img" - }, - "escapistmagazine.com/articles/view/comicsandcosplay/comics/bumhugparade": { - "%escapistmagazine.com/articles/view/comicsandcosplay/comics/bumhugparade%": "//*[@class='body']/span/p[2]/img" - }, - "escapistmagazine.com/articles/view/comicsandcosplay/comics/escapistradiotheater": { - "%escapistmagazine.com/articles/view/comicsandcosplay/comics/escapistradiotheater%": "//*[@class='body']/span/p[2]/img" - }, - "escapistmagazine.com/articles/view/comicsandcosplay/comics/paused": { - "%escapistmagazine.com/articles/view/comicsandcosplay/comics/paused%": "//*[@class='body']/span/p[2]/img | //*[@class='body']/span/div/img" - }, - "escapistmagazine.com/articles/view/comicsandcosplay/comics/fraughtwithperil": { - "%escapistmagazine.com/articles/view/comicsandcosplay/comics/fraughtwithperil%": "//*[@class='body']" - }, - "trenchescomic.com": { - "%trenchescomic.com/comic%": "//*[@class=\"top\"]/img", - "%trenchescomic.com/tales%": "//*[@class=\"copy\"]" - }, - "lfgcomic.com": { - "%(lfgcomic.com/page)|(feedproxy.google.com/~r/LookingForGroup)%": "//*[@id=\"comic\"]/img | //*[@class=\"content\"]" - }, - "sandraandwoo.com": { - "%feedproxy.google.com/~r/sandraandwoo%": "//*[@id=\"comic\"]/img | //*[@class=\"post\"]/div[@class=\"entry\"] | //*[@class=\"transcript\"]" - }, - "sandraandwoo.com/gaia": { - "%feedproxy.google.com/~r/gaiacomic%": "//*[@id=\"comic\"]/img | //*[@class=\"post\"]/div[@class=\"entry\"] | //*[@class=\"transcript\"]" - }, - "theoatmeal.com": { - "%theoatmeal.com/blog%": "//*[@class=\"post_body\"]", - "%theoatmeal.com/comics%": "//*[@id=\"comic\"] | //*[@class=\"super_vacum\"] | //*[@class=\"pad\"]" - }, - "loldwell.com": { - "%loldwell.com/\\?p=%": "//*[@id=\"comic\"]" - }, - "mokepon.smackjeeves.com": { - "%mokepon.smackjeeves.com/comics%": "//*[@id=\"comic_area\"]/img | //*[@id=\"comic_area\"]/a/img" - }, - "twokinds.keenspot.com": { - "%twokinds.keenspot.com/%": "//*[@class=\"comic\"]/div/a/img | //*[@class=\"comic\"]/div/img | //*[@id=\"cg_img\"]/img | //*[@id=\"cg_img\"]/a/img" - }, - "niceteethcomic.com": { - "%niceteethcomic.com/archives%": "//*[@class=\"comicpane\"]/a/img" - }, - "awkwardzombie.com" :{ - "%awkwardzombie.com/index.php\\?comic=%": "//*[@id=\"comic\"]/img" - }, - "vgcats.com": { - "%vgcats.com/comics%": "//*[@align=\"center\"]/img" - }, - "vgcats.com/super": { - "%vgcats.com/super%": "//div[@align=\"center\"]/p/img" - }, - "chaoslife.findchaos.com": { - "%chaoslife.findchaos.com%": "//div[@id=\"comic\"]" - }, - "forlackofabettercomic.com/archive.php": { - "%forlackofabettercomic.com/\\?id=%": "//div[@id=\"comicset\"]/a/img" - }, - "heise.de/newsticker": { - "%heise.de%": "//*[@class='meldung_wrapper']/*[not(contains(@class, 'dossier'))]" - }, - "heise.de/developer": { - "%heise.de%": "//*[@class='meldung_wrapper']/*[not(contains(@class, 'dossier'))]" - }, - "heise.de/open/news": { - "%heise.de%": "//*[@class='meldung_wrapper']/*[not(contains(@class, 'dossier'))]" - }, - "spiegel.de": { - "%spiegel.de/(?!.*video).*%": "//p[@class='article-intro'] | //*[@itemprop='description' and not(ancestor::*[contains( normalize-space( @class ), 'article-section' )]) ] | //*[(@class='spPanoImageTeaserPic' or @class='spPanoGalleryTeaserPic' or @class='spPanoPlayerTeaserPic') and not(ancestor::*[contains( normalize-space( @class ), 'article-section' )])] | //*[@class='image-buttons-panel' and not(ancestor::*[contains( normalize-space( @class ), 'article-section' )])]/*[1]/img | //*[@class='article-image-description' and not(ancestor::*[contains( normalize-space( @class ), 'article-section' )]) ]/p | //*[@id='content-main']/*[@id='js-article-column']/div[contains( normalize-space( @class ), 'article-section' )]" - }, - "eqcomics.com": { - "%feedproxy.google.com/~r/eqcomics%": "//div[@id=\"comic\"]/div/a/img" - }, - "loadingartist.com": { - "%feedproxy.google.com/~r/LoadingArtist%": "//div[@id=\"comic\"]" - }, - "thegamercat.com": { - "%thegamercat.com%": "//div[@id=\"comic\"] | //div[@class=\"post-content\"]/div[@class=\"entry\"]/p" - }, - "niebezpiecznik.pl": { - "%feedproxy.google.com/~r/niebezpiecznik%": "//div[@class=\"entry\"]" - }, - "maximumble.thebookofbiff.com": { - "%maximumble.thebookofbiff.com%": "//div[@id=\"comic\"]/div/a/img" - }, - "omgubuntu.co.uk": { - "%www.omgubuntu.co.uk%": "//div[@class=\"entry-content\"]" - }, - "tu-chemnitz.de/tu/presse/": { - "%tu-chemnitz.de%": "//div[@id='content_inhalt']/*[preceding-sibling::h1 and following-sibling::div[@id]]" - }, - "cliquerefresh.com": { - "%cliquerefresh.com/comic%": "//div[@class=\"comicImg\"]/img | //div[@class=\"comicImg\"]/a/img" - }, - "satwcomic.com": { - "%feedproxy.google.com/~r/satwcomic%": "//div[@class=\"comicmid\"]/center/a/img" - } + "cad-comic.com": { + "%cad-comic.com/cad/\\d+/$%": "//*[@id='content']/img" + }, + "slashdot.org": { + "%rss.slashdot.org%": "//article/div[@class='body'] | //article[@class='layout-article']/div" + }, + "explosm.net": { + "%explosm.net/comics%": "//*[@id='maincontent']/div[2]/div/img", + "%explosm.net/show%": "//*[@id='videoPlayer']/iframe" + }, + "themerepublic.net": { + "%feedproxy.google.com/~r/blogspot/DngUJ%": "//*[@class='post hentry']" + }, + "penny-arcade.com": { + "%penny-arcade.com/comic%": "//*[@id='comicFrame']/a/img", + "%penny-arcade.com/news%": "//*[@class='postBody']/*" + }, + "leasticoulddo.com": { + "%feedproxy.google.com/~r/LICD%": "//*[@id='comic-img']/a/img | //*[@id='comic-img']/img | //*[@id='post']" + }, + "escapistmagazine.com/articles/view/comicsandcosplay/comics/critical-miss": { + "%escapistmagazine.com/articles/view/comicsandcosplay/comics/critical-miss%": "//*[@class='body']/span/img | //div[@class='folder_nav_links']/following::p" + }, + "escapistmagazine.com/articles/view/comicsandcosplay/comics/namegame": { + "%escapistmagazine.com/articles/view/comicsandcosplay/comics/namegame%": "//*[@class='body']/span/p/img[@height != \"120\"]" + }, + "escapistmagazine.com/articles/view/comicsandcosplay/comics/stolen-pixels": { + "%escapistmagazine.com/articles/view/comicsandcosplay/comics/stolen-pixels%": "//*[@class='body']/span/p[2]/img" + }, + "escapistmagazine.com/articles/view/comicsandcosplay/comics/bumhugparade": { + "%escapistmagazine.com/articles/view/comicsandcosplay/comics/bumhugparade%": "//*[@class='body']/span/p[2]/img" + }, + "escapistmagazine.com/articles/view/comicsandcosplay/comics/escapistradiotheater": { + "%escapistmagazine.com/articles/view/comicsandcosplay/comics/escapistradiotheater%": "//*[@class='body']/span/p[2]/img" + }, + "escapistmagazine.com/articles/view/comicsandcosplay/comics/paused": { + "%escapistmagazine.com/articles/view/comicsandcosplay/comics/paused%": "//*[@class='body']/span/p[2]/img | //*[@class='body']/span/div/img" + }, + "escapistmagazine.com/articles/view/comicsandcosplay/comics/fraughtwithperil": { + "%escapistmagazine.com/articles/view/comicsandcosplay/comics/fraughtwithperil%": "//*[@class='body']" + }, + "trenchescomic.com": { + "%trenchescomic.com/comic%": "//*[@class=\"top\"]/img", + "%trenchescomic.com/tales%": "//*[@class=\"copy\"]" + }, + "lfgcomic.com": { + "%(lfgcomic.com/page)|(feedproxy.google.com/~r/LookingForGroup)%": "//*[@id=\"comic\"]/img | //*[@class=\"content\"]" + }, + "sandraandwoo.com": { + "%feedproxy.google.com/~r/sandraandwoo%": "//*[@id=\"comic\"]/img | //*[@class=\"post\"]/div[@class=\"entry\"] | //*[@class=\"transcript\"]" + }, + "sandraandwoo.com/gaia": { + "%feedproxy.google.com/~r/gaiacomic%": "//*[@id=\"comic\"]/img | //*[@class=\"post\"]/div[@class=\"entry\"] | //*[@class=\"transcript\"]" + }, + "theoatmeal.com": { + "%theoatmeal.com/blog%": "//*[@class=\"post_body\"]", + "%theoatmeal.com/comics%": "//*[@id=\"comic\"] | //*[@class=\"super_vacum\"] | //*[@class=\"pad\"]" + }, + "loldwell.com": { + "%loldwell.com/\\?p=%": "//*[@id=\"comic\"]" + }, + "mokepon.smackjeeves.com": { + "%mokepon.smackjeeves.com/comics%": "//*[@id=\"comic_area\"]/img | //*[@id=\"comic_area\"]/a/img" + }, + "twokinds.keenspot.com": { + "%twokinds.keenspot.com/%": "//*[@class=\"comic\"]/div/a/img | //*[@class=\"comic\"]/div/img | //*[@id=\"cg_img\"]/img | //*[@id=\"cg_img\"]/a/img" + }, + "niceteethcomic.com": { + "%niceteethcomic.com/archives%": "//*[@class=\"comicpane\"]/a/img" + }, + "awkwardzombie.com" :{ + "%awkwardzombie.com/index.php\\?comic=%": "//*[@id=\"comic\"]/img" + }, + "vgcats.com": { + "%vgcats.com/comics%": "//*[@align=\"center\"]/img" + }, + "vgcats.com/super": { + "%vgcats.com/super%": "//div[@align=\"center\"]/p/img" + }, + "chaoslife.findchaos.com": { + "%chaoslife.findchaos.com%": "//div[@id=\"comic\"]" + }, + "forlackofabettercomic.com/archive.php": { + "%forlackofabettercomic.com/\\?id=%": "//div[@id=\"comicset\"]/a/img" + }, + "heise.de/newsticker": { + "%heise.de%": "//*[@class='meldung_wrapper']/*[not(contains(@class, 'dossier'))]" + }, + "heise.de/developer": { + "%heise.de%": "//*[@class='meldung_wrapper']/*[not(contains(@class, 'dossier'))]" + }, + "heise.de/open/news": { + "%heise.de%": "//*[@class='meldung_wrapper']/*[not(contains(@class, 'dossier'))]" + }, + "spiegel.de": { + "%spiegel.de/(?!.*video).*%": "//p[@class='article-intro'] | //*[@itemprop='description' and not(ancestor::*[contains( normalize-space( @class ), 'article-section' )]) ] | //*[(@class='spPanoImageTeaserPic' or @class='spPanoGalleryTeaserPic' or @class='spPanoPlayerTeaserPic') and not(ancestor::*[contains( normalize-space( @class ), 'article-section' )])] | //*[@class='image-buttons-panel' and not(ancestor::*[contains( normalize-space( @class ), 'article-section' )])]/*[1]/img | //*[@class='article-image-description' and not(ancestor::*[contains( normalize-space( @class ), 'article-section' )]) ]/p | //*[@id='content-main']/*[@id='js-article-column']/div[contains( normalize-space( @class ), 'article-section' )]" + }, + "eqcomics.com": { + "%feedproxy.google.com/~r/eqcomics%": "//div[@id=\"comic\"]/div/a/img" + }, + "loadingartist.com": { + "%feedproxy.google.com/~r/LoadingArtist%": "//div[@id=\"comic\"]" + }, + "thegamercat.com": { + "%thegamercat.com%": "//div[@id=\"comic\"] | //div[@class=\"post-content\"]/div[@class=\"entry\"]/p" + }, + "niebezpiecznik.pl": { + "%feedproxy.google.com/~r/niebezpiecznik%": "//div[@class=\"entry\"]" + }, + "maximumble.thebookofbiff.com": { + "%maximumble.thebookofbiff.com%": "//div[@id=\"comic\"]/div/a/img" + }, + "omgubuntu.co.uk": { + "%www.omgubuntu.co.uk%": "//div[@class=\"entry-content\"]" + }, + "tu-chemnitz.de/tu/presse/": { + "%tu-chemnitz.de%": "//div[@id='content_inhalt']/*[preceding-sibling::h1 and following-sibling::div[@id]]" + }, + "cliquerefresh.com": { + "%cliquerefresh.com/comic%": "//div[@class=\"comicImg\"]/img | //div[@class=\"comicImg\"]/a/img" + }, + "satwcomic.com": { + "%feedproxy.google.com/~r/satwcomic%": "//div[@class=\"comicmid\"]/center/a/img" + } } diff --git a/config/appconfig.php b/config/appconfig.php index e738b22cd..a9045eb9a 100644 --- a/config/appconfig.php +++ b/config/appconfig.php @@ -22,271 +22,271 @@ use \OCP\App; // Used to parse app.json file, should be in core at some point class AppConfig { - private $config; - private $navigationManager; - private $urlGenerator; - private $phpVersion; - private $ownCloudVersion; - private $installedExtensions; - private $databaseType; - - /** - * TODO: External deps that are needed: - * - add jobs - * - connect to hooks - */ - public function __construct(INavigationManager $navigationManager, - IURLGenerator $urlGenerator, - $phpVersion, - $ownCloudVersion, - $installedExtensions, - $databaseType) { - $this->navigationManager = $navigationManager; - $this->urlGenerator = $urlGenerator; - $this->ownCloudVersion = $ownCloudVersion; - $this->phpVersion = $phpVersion; - $this->installedExtensions = $installedExtensions; - $this->databaseType = $databaseType; - $this->config = []; - } - - - /** - * @param string|array $data path to the config file or an array with the config - */ - public function loadConfig($data) { - if(is_array($data)) { - $this->config = $data; - } else { - $json = file_get_contents($data); - $this->config = json_decode($json, true); - } - - // fill config with default values if no navigation is added - if(array_key_exists('navigation', $this->config)) { - $nav =& $this->config['navigation']; - - // add defaults - $defaults = [ - 'id' => $this->config['id'], - 'route' => $this->config['id'] . '.page.index', - 'order' => 10, - 'icon' => 'app.svg', - 'name' => $this->config['name'] - ]; - - foreach($defaults as $key => $value) { - if(!array_key_exists($key, $nav)) { - $nav[$key] = $value; - } - } - } - } - - /** - * @param string $key if given returns the value of the config at index $key - * @return array|mixed the config - */ - public function getConfig($key=null) { - // FIXME: is this function interface a good idea? - if($key !== null) { - return $this->config[$key]; - } else { - return $this->config; - } - } - - - /** - * Registers all config options - */ - public function registerAll() { - $this->registerNavigation(); - $this->registerBackgroundJobs(); - $this->registerHooks(); - $this->registerAdmin(); - } - - - /** - * Parses the navigation and creates a navigation entry if needed - */ - public function registerNavigation() { - // if key is missing, don't create a navigation - if(array_key_exists('navigation', $this->config)) { - $nav =& $this->config['navigation']; - - $navConfig = [ - 'id' => $nav['id'], - 'order' => $nav['order'], - 'name' => $nav['name'] - ]; - - $navConfig['href'] = $this->urlGenerator->linkToRoute($nav['route']); - $navConfig['icon'] = $this->urlGenerator->imagePath($nav['id'], - $nav['icon']); - - $this->navigationManager->add($navConfig); - } - - } - - /** - * Registers admin pages - */ - public function registerAdmin() { - if ($this->config['admin']) { - App::registerAdmin($this->config['id'], 'admin/admin'); - } - } - - - /** - * Registers all jobs in the config - */ - public function registerBackgroundJobs() { - // FIXME: this is temporarily static because core jobs are not public - // yet, therefore legacy code - foreach ($this->config['jobs'] as $job) { - Backgroundjob::addRegularTask($job, 'run'); - } - } - - - /** - * Registers all hooks in the config - */ - public function registerHooks() { - // FIXME: this is temporarily static because core emitters are not future - // proof, therefore legacy code in here - foreach ($this->config['hooks'] as $listen => $react) { - $listener = explode('::', $listen); - $reaction = explode('::', $react); - - // config is written like HookNamespace::method => Class::method - Util::connectHook($listener[0], $listener[1], $reaction[0], - $reaction[1]); - } - } - - - private function testDatabaseDependencies($deps) { - if(array_key_exists('databases', $deps)) { - $databases = $deps['databases']; - $databaseType = $this->databaseType; - - if(!in_array($databaseType, $databases)) { - return 'Database ' . $databaseType . ' not supported.' . - 'App is only compatible with ' . - implode(', ', $databases); - } - } - - return ''; - } - - - private function testPHPDependencies($deps) { - if (array_key_exists('php', $deps)) { - return $this->requireVersion($this->phpVersion, $deps['php'], - 'PHP'); - } - - return ''; - } - - - private function testLibraryDependencies($deps) { - if (array_key_exists('libs', $deps)) { - foreach ($deps['libs'] as $lib => $versions) { - if(array_key_exists($lib, $this->installedExtensions)) { - return $this->requireVersion($this->installedExtensions[$lib], - $versions, 'PHP extension ' . $lib); - } else { - return 'PHP extension ' . $lib . ' required but not installed'; - } - } - } - - return ''; - } - - - /** - * Validates all dependencies that the app has - * @throws DependencyException if one version is not satisfied - */ - public function testDependencies() { - if(array_key_exists('dependencies', $this->config)) { - $deps = $this->config['dependencies']; - - $msg = $this->testDatabaseDependencies($deps); - $msg .= $this->testPHPDependencies($deps); - $msg .= $this->testLibraryDependencies($deps); - - if($msg !== '') { - throw new DependencyException($msg); - } - } - } - - - /** - * Compares a version with a version requirement string - * @param string $actual the actual version that is there - * @param string $required a version requirement in the form of - * <=5.3,>4.5 versions are separated with a comma - * @param string $versionType a description of the string that is prepended - * to the error message - * @return string an error message if the version is not met, + private $config; + private $navigationManager; + private $urlGenerator; + private $phpVersion; + private $ownCloudVersion; + private $installedExtensions; + private $databaseType; + + /** + * TODO: External deps that are needed: + * - add jobs + * - connect to hooks + */ + public function __construct(INavigationManager $navigationManager, + IURLGenerator $urlGenerator, + $phpVersion, + $ownCloudVersion, + $installedExtensions, + $databaseType) { + $this->navigationManager = $navigationManager; + $this->urlGenerator = $urlGenerator; + $this->ownCloudVersion = $ownCloudVersion; + $this->phpVersion = $phpVersion; + $this->installedExtensions = $installedExtensions; + $this->databaseType = $databaseType; + $this->config = []; + } + + + /** + * @param string|array $data path to the config file or an array with the config + */ + public function loadConfig($data) { + if(is_array($data)) { + $this->config = $data; + } else { + $json = file_get_contents($data); + $this->config = json_decode($json, true); + } + + // fill config with default values if no navigation is added + if(array_key_exists('navigation', $this->config)) { + $nav =& $this->config['navigation']; + + // add defaults + $defaults = [ + 'id' => $this->config['id'], + 'route' => $this->config['id'] . '.page.index', + 'order' => 10, + 'icon' => 'app.svg', + 'name' => $this->config['name'] + ]; + + foreach($defaults as $key => $value) { + if(!array_key_exists($key, $nav)) { + $nav[$key] = $value; + } + } + } + } + + /** + * @param string $key if given returns the value of the config at index $key + * @return array|mixed the config + */ + public function getConfig($key=null) { + // FIXME: is this function interface a good idea? + if($key !== null) { + return $this->config[$key]; + } else { + return $this->config; + } + } + + + /** + * Registers all config options + */ + public function registerAll() { + $this->registerNavigation(); + $this->registerBackgroundJobs(); + $this->registerHooks(); + $this->registerAdmin(); + } + + + /** + * Parses the navigation and creates a navigation entry if needed + */ + public function registerNavigation() { + // if key is missing, don't create a navigation + if(array_key_exists('navigation', $this->config)) { + $nav =& $this->config['navigation']; + + $navConfig = [ + 'id' => $nav['id'], + 'order' => $nav['order'], + 'name' => $nav['name'] + ]; + + $navConfig['href'] = $this->urlGenerator->linkToRoute($nav['route']); + $navConfig['icon'] = $this->urlGenerator->imagePath($nav['id'], + $nav['icon']); + + $this->navigationManager->add($navConfig); + } + + } + + /** + * Registers admin pages + */ + public function registerAdmin() { + if ($this->config['admin']) { + App::registerAdmin($this->config['id'], 'admin/admin'); + } + } + + + /** + * Registers all jobs in the config + */ + public function registerBackgroundJobs() { + // FIXME: this is temporarily static because core jobs are not public + // yet, therefore legacy code + foreach ($this->config['jobs'] as $job) { + Backgroundjob::addRegularTask($job, 'run'); + } + } + + + /** + * Registers all hooks in the config + */ + public function registerHooks() { + // FIXME: this is temporarily static because core emitters are not future + // proof, therefore legacy code in here + foreach ($this->config['hooks'] as $listen => $react) { + $listener = explode('::', $listen); + $reaction = explode('::', $react); + + // config is written like HookNamespace::method => Class::method + Util::connectHook($listener[0], $listener[1], $reaction[0], + $reaction[1]); + } + } + + + private function testDatabaseDependencies($deps) { + if(array_key_exists('databases', $deps)) { + $databases = $deps['databases']; + $databaseType = $this->databaseType; + + if(!in_array($databaseType, $databases)) { + return 'Database ' . $databaseType . ' not supported.' . + 'App is only compatible with ' . + implode(', ', $databases); + } + } + + return ''; + } + + + private function testPHPDependencies($deps) { + if (array_key_exists('php', $deps)) { + return $this->requireVersion($this->phpVersion, $deps['php'], + 'PHP'); + } + + return ''; + } + + + private function testLibraryDependencies($deps) { + if (array_key_exists('libs', $deps)) { + foreach ($deps['libs'] as $lib => $versions) { + if(array_key_exists($lib, $this->installedExtensions)) { + return $this->requireVersion($this->installedExtensions[$lib], + $versions, 'PHP extension ' . $lib); + } else { + return 'PHP extension ' . $lib . ' required but not installed'; + } + } + } + + return ''; + } + + + /** + * Validates all dependencies that the app has + * @throws DependencyException if one version is not satisfied + */ + public function testDependencies() { + if(array_key_exists('dependencies', $this->config)) { + $deps = $this->config['dependencies']; + + $msg = $this->testDatabaseDependencies($deps); + $msg .= $this->testPHPDependencies($deps); + $msg .= $this->testLibraryDependencies($deps); + + if($msg !== '') { + throw new DependencyException($msg); + } + } + } + + + /** + * Compares a version with a version requirement string + * @param string $actual the actual version that is there + * @param string $required a version requirement in the form of + * <=5.3,>4.5 versions are separated with a comma + * @param string $versionType a description of the string that is prepended + * to the error message + * @return string an error message if the version is not met, * empty string if ok - */ - private function requireVersion($actual, $required, $versionType) { - $requiredVersions = $this->splitVersions($required); - - foreach($requiredVersions as $version) { - // accept * as wildcard for any version - if($version['version'] === '*') { - continue; - } - if(!version_compare($actual, $version['version'], $version['operator'])) { - return $versionType . ' Version not satisfied: ' . $version['operator'] . - $version['version'] . ' required but found ' . $actual . '\n'; - } - } - - return ''; - } - - - /** - * Versions can be separated by a comma so split them - * @param string $versions a version requirement in the form of - * <=5.3,>4.5 versions are separated with a comma - * @return array of arrays with key=version value=operator - */ - private function splitVersions($versions) { - $result = []; - $versions = explode(',', $versions); - - foreach($versions as $version) { - preg_match('/^(?<operator><|<=|>=|>|<>)?(?<version>.*)$/', $version, $matches); - if($matches['operator'] !== '') { - $required = [ - 'version' => $matches['version'], - 'operator' => $matches['operator'], - ]; - } else { - $required = [ - 'version' => $matches['version'], - 'operator' => '==', - ]; - } - $result[] = $required; - } - - return $result; - } + */ + private function requireVersion($actual, $required, $versionType) { + $requiredVersions = $this->splitVersions($required); + + foreach($requiredVersions as $version) { + // accept * as wildcard for any version + if($version['version'] === '*') { + continue; + } + if(!version_compare($actual, $version['version'], $version['operator'])) { + return $versionType . ' Version not satisfied: ' . $version['operator'] . + $version['version'] . ' required but found ' . $actual . '\n'; + } + } + + return ''; + } + + + /** + * Versions can be separated by a comma so split them + * @param string $versions a version requirement in the form of + * <=5.3,>4.5 versions are separated with a comma + * @return array of arrays with key=version value=operator + */ + private function splitVersions($versions) { + $result = []; + $versions = explode(',', $versions); + + foreach($versions as $version) { + preg_match('/^(?<operator><|<=|>=|>|<>)?(?<version>.*)$/', $version, $matches); + if($matches['operator'] !== '') { + $required = [ + 'version' => $matches['version'], + 'operator' => $matches['operator'], + ]; + } else { + $required = [ + 'version' => $matches['version'], + 'operator' => '==', + ]; + } + $result[] = $required; + } + + return $result; + } }
\ No newline at end of file diff --git a/config/config.php b/config/config.php index d84e4076c..25e8a2294 100644 --- a/config/config.php +++ b/config/config.php @@ -18,179 +18,179 @@ use \OCP\ILogger; class Config { - private $fileSystem; - private $autoPurgeMinimumInterval; // seconds, used to define how - // long deleted folders and feeds - // should still be kept for an - // undo actions - private $autoPurgeCount; // number of allowed unread articles per feed - private $simplePieCacheDuration; // seconds - private $feedFetcherTimeout; // seconds - private $useCronUpdates; // turn off updates run by owncloud cronjob - private $proxyHost; - private $proxyPort; - private $proxyUser; - private $proxyPassword; - private $logger; - private $loggerParams; + private $fileSystem; + private $autoPurgeMinimumInterval; // seconds, used to define how + // long deleted folders and feeds + // should still be kept for an + // undo actions + private $autoPurgeCount; // number of allowed unread articles per feed + private $simplePieCacheDuration; // seconds + private $feedFetcherTimeout; // seconds + private $useCronUpdates; // turn off updates run by owncloud cronjob + private $proxyHost; + private $proxyPort; + private $proxyUser; + private $proxyPassword; + private $logger; + private $loggerParams; - public function __construct($fileSystem, ILogger $logger, $loggerParams) { - $this->fileSystem = $fileSystem; - $this->autoPurgeMinimumInterval = 60; - $this->autoPurgeCount = 200; - $this->simplePieCacheDuration = 30*60; - $this->feedFetcherTimeout = 60; - $this->useCronUpdates = true; - $this->logger = $logger; - $this->proxyHost = ''; - $this->proxyPort = 8080; - $this->proxyUser = ''; - $this->proxyPassword = ''; - $this->loggerParams = $loggerParams; - } + public function __construct($fileSystem, ILogger $logger, $loggerParams) { + $this->fileSystem = $fileSystem; + $this->autoPurgeMinimumInterval = 60; + $this->autoPurgeCount = 200; + $this->simplePieCacheDuration = 30*60; + $this->feedFetcherTimeout = 60; + $this->useCronUpdates = true; + $this->logger = $logger; + $this->proxyHost = ''; + $this->proxyPort = 8080; + $this->proxyUser = ''; + $this->proxyPassword = ''; + $this->loggerParams = $loggerParams; + } - public function getProxyPort() { - return $this->proxyPort; - } + public function getProxyPort() { + return $this->proxyPort; + } - public function getProxyHost() { - return $this->proxyHost; - } + public function getProxyHost() { + return $this->proxyHost; + } - public function getProxyAuth() { - if($this->proxyUser === '') { - return null; - } else { - return $this->proxyUser . ':' . $this->proxyPassword; - } - } + public function getProxyAuth() { + if($this->proxyUser === '') { + return null; + } else { + return $this->proxyUser . ':' . $this->proxyPassword; + } + } - public function getProxyUser() { - return $this->proxyUser; - } + public function getProxyUser() { + return $this->proxyUser; + } - public function getProxyPassword() { - return $this->proxyPassword; - } + public function getProxyPassword() { + return $this->proxyPassword; + } - public function getAutoPurgeMinimumInterval() { - if ($this->autoPurgeMinimumInterval > 60) { - return $this->autoPurgeMinimumInterval; - } else { - return 60; - } - } + public function getAutoPurgeMinimumInterval() { + if ($this->autoPurgeMinimumInterval > 60) { + return $this->autoPurgeMinimumInterval; + } else { + return 60; + } + } - public function getAutoPurgeCount() { - return $this->autoPurgeCount; - } - - - public function getSimplePieCacheDuration() { - return $this->simplePieCacheDuration; - } - - - public function getFeedFetcherTimeout() { - return $this->feedFetcherTimeout; - } - - - public function getUseCronUpdates() { - return $this->useCronUpdates; - } - - - public function setAutoPurgeMinimumInterval($value) { - $this->autoPurgeMinimumInterval = $value; - } - - - public function setAutoPurgeCount($value) { - $this->autoPurgeCount = $value; - } - - - public function setSimplePieCacheDuration($value) { - $this->simplePieCacheDuration = $value; - } - - - public function setFeedFetcherTimeout($value) { - $this->feedFetcherTimeout = $value; - } + public function getAutoPurgeCount() { + return $this->autoPurgeCount; + } + + + public function getSimplePieCacheDuration() { + return $this->simplePieCacheDuration; + } + + + public function getFeedFetcherTimeout() { + return $this->feedFetcherTimeout; + } + + + public function getUseCronUpdates() { + return $this->useCronUpdates; + } + + + public function setAutoPurgeMinimumInterval($value) { + $this->autoPurgeMinimumInterval = $value; + } + + + public function setAutoPurgeCount($value) { + $this->autoPurgeCount = $value; + } + + + public function setSimplePieCacheDuration($value) { + $this->simplePieCacheDuration = $value; + } + + + public function setFeedFetcherTimeout($value) { + $this->feedFetcherTimeout = $value; + } - public function setUseCronUpdates($value) { - $this->useCronUpdates = $value; - } + public function setUseCronUpdates($value) { + $this->useCronUpdates = $value; + } - public function setProxyPort($value) { - $this->proxyPort = $value; - } + public function setProxyPort($value) { + $this->proxyPort = $value; + } - public function setProxyHost($value) { - $this->proxyHost = $value; - } + public function setProxyHost($value) { + $this->proxyHost = $value; + } - public function setProxyUser($value) { - $this->proxyUser = $value; - } + public function setProxyUser($value) { + $this->proxyUser = $value; + } - public function setProxyPassword($value) { - $this->proxyPassword = $value; - } + public function setProxyPassword($value) { + $this->proxyPassword = $value; + } - public function read($configPath, $createIfNotExists=false) { - if($createIfNotExists && !$this->fileSystem->file_exists($configPath)) { + public function read($configPath, $createIfNotExists=false) { + if($createIfNotExists && !$this->fileSystem->file_exists($configPath)) { - $this->write($configPath); + $this->write($configPath); - } else { + } else { - $content = $this->fileSystem->file_get_contents($configPath); - $configValues = parse_ini_string($content); + $content = $this->fileSystem->file_get_contents($configPath); + $configValues = parse_ini_string($content); - if($configValues === false || count($configValues) === 0) { - $this->logger->warning('Configuration invalid. Ignoring values.', - $this->loggerParams); - } else { + if($configValues === false || count($configValues) === 0) { + $this->logger->warning('Configuration invalid. Ignoring values.', + $this->loggerParams); + } else { - foreach($configValues as $key => $value) { - if(property_exists($this, $key)) { - $type = gettype($this->$key); - settype($value, $type); - $this->$key = $value; - } else { - $this->logger->warning('Configuration value "' . $key . - '" does not exist. Ignored value.' , $this->loggerParams); - } - } + foreach($configValues as $key => $value) { + if(property_exists($this, $key)) { + $type = gettype($this->$key); + settype($value, $type); + $this->$key = $value; + } else { + $this->logger->warning('Configuration value "' . $key . + '" does not exist. Ignored value.' , $this->loggerParams); + } + } - } - } - } + } + } + } - public function write($configPath) { - $ini = - "autoPurgeMinimumInterval = " . $this->autoPurgeMinimumInterval . "\n" . - "autoPurgeCount = " . $this->autoPurgeCount . "\n" . - "simplePieCacheDuration = " . $this->simplePieCacheDuration . "\n" . - "feedFetcherTimeout = " . $this->feedFetcherTimeout . "\n" . - "useCronUpdates = " . var_export($this->useCronUpdates, true) . "\n" . - "proxyHost = " . $this->proxyHost . "\n" . - "proxyPort = " . $this->proxyPort . "\n" . - "proxyUser = " . $this->proxyUser . "\n" . - "proxyPassword = " . $this->proxyPassword; - ; + public function write($configPath) { + $ini = + "autoPurgeMinimumInterval = " . $this->autoPurgeMinimumInterval . "\n" . + "autoPurgeCount = " . $this->autoPurgeCount . "\n" . + "simplePieCacheDuration = " . $this->simplePieCacheDuration . "\n" . + "feedFetcherTimeout = " . $this->feedFetcherTimeout . "\n" . + "useCronUpdates = " . var_export($this->useCronUpdates, true) . "\n" . + "proxyHost = " . $this->proxyHost . "\n" . + "proxyPort = " . $this->proxyPort . "\n" . + "proxyUser = " . $this->proxyUser . "\n" . + "proxyPassword = " . $this->proxyPassword; + ; - $this->fileSystem->file_put_contents($configPath, $ini); - } + $this->fileSystem->file_put_contents($configPath, $ini); + } }
\ No newline at end of file diff --git a/config/schema.json b/config/schema.json index c65a1c8dd..13dca5132 100644 --- a/config/schema.json +++ b/config/schema.json @@ -1,182 +1,182 @@ { - "title": "ownCloud App Schema", - "type": "object", - "properties": { - "name": { - "type": "string" - }, - "id": { - "type": "string", - "pattern": "^[a-z_]+$" - }, - "description": { - "type": "string" - }, - "licence": { - "type": "string", - "enum": ["AGPL", "MIT", "GPL", "LGPL", "BSD","Apache"] - }, - "admin": { - "type": "boolean" - }, - "version": { - "type": "string", - "pattern": "^[0-9]+(\\.[0-9]+)*$" - }, - "authors": { - "type": "array", - "items": { - "type": "object", - "properties": { - "name": { + "title": "ownCloud App Schema", + "type": "object", + "properties": { + "name": { "type": "string" - }, - "email": { - "type": "string", - "pattern": "^.+@.+\\..+$" - }, - "homepage": { + }, + "id": { "type": "string", - "pattern": "^https?://.*$" - } + "pattern": "^[a-z_]+$" }, - "required": ["name", "email"], - "additionalProperties": false - } - }, - "repository": { - "type": "object", - "properties": { - "type": { - "type": "string" + "description": { + "type": "string" }, - "url": { - "type": "string" - } - }, - "required": ["type", "url"], - "additionalProperties": false - }, - "homepage": { - "type": "string", - "pattern": "^https?://.*$" - }, - "bugs": { - "type": "string", - "pattern": "^https?://.*$" - }, - "documentation": { - "type": "object", - "properties": { - "user": { - "type": "string", - "pattern": "^https?://.*$" + "licence": { + "type": "string", + "enum": ["AGPL", "MIT", "GPL", "LGPL", "BSD","Apache"] }, "admin": { - "type": "string", - "pattern": "^https?://.*$" + "type": "boolean" }, - "developer": { - "type": "string", - "pattern": "^https?://.*$" - } - }, - "additionalProperties": false - }, - "jobs": { - "type": "array", - "items": { - "type": "string", - "pattern": "^[a-zA-Z-_:\\\\]+$" - } - }, - "hooks": { - "type": "object", - "patternProperties": { - "^[a-zA-Z-_:\\\\]+$": { - "type": "string", - "pattern": "^[a-zA-Z-_:\\\\]+$" - } - } - }, - "navigation": { - "type": "object", - "properties": { - "route": { - "type": "string", - "pattern": "^([a-z]+(\\.[a-z]+)*)*|(/.+/.*)$" + "version": { + "type": "string", + "pattern": "^[0-9]+(\\.[0-9]+)*$" }, - "icon": { - "type": "string" + "authors": { + "type": "array", + "items": { + "type": "object", + "properties": { + "name": { + "type": "string" + }, + "email": { + "type": "string", + "pattern": "^.+@.+\\..+$" + }, + "homepage": { + "type": "string", + "pattern": "^https?://.*$" + } + }, + "required": ["name", "email"], + "additionalProperties": false + } }, - "name": { - "type": "string" + "repository": { + "type": "object", + "properties": { + "type": { + "type": "string" + }, + "url": { + "type": "string" + } + }, + "required": ["type", "url"], + "additionalProperties": false }, - "order": { - "type": "integer" - } - }, - "additionalProperties": false - }, - "categories": { - "type": "array", - "items": { - "type": "string", - "enum": ["Filesystem", "Authentication", "PIM", "Multimedia", - "Productivity", "Games", "Tools", "Other"] - }, - "minItems": 1, - "uniqueItems": true - }, - "dependencies": { - "type": "object", - "properties": { - "databases": { - "type": "array", - "items": { + "homepage": { "type": "string", - "enum": ["pgsql", "mysql", "sqlite3", "mssql", "oracle"] - }, - "uniqueItems": true + "pattern": "^https?://.*$" }, - "php": { - "type": "string", - "pattern": "^((=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*(,(=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*)*|\\*)$" + "bugs": { + "type": "string", + "pattern": "^https?://.*$" }, - "apps": { - "type": "object", - "patternProperties": { - "^[a-z_]+$": { - "type": "string", - "pattern": "^((=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*(,(=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*)*|\\*)$" - } - } + "documentation": { + "type": "object", + "properties": { + "user": { + "type": "string", + "pattern": "^https?://.*$" + }, + "admin": { + "type": "string", + "pattern": "^https?://.*$" + }, + "developer": { + "type": "string", + "pattern": "^https?://.*$" + } + }, + "additionalProperties": false }, - "libs": { - "type": "object", - "patternProperties": { - "^[a-z_]+$": { - "type": "string", - "pattern": "^((=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*(,(=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*)*|\\*)$" + "jobs": { + "type": "array", + "items": { + "type": "string", + "pattern": "^[a-zA-Z-_:\\\\]+$" + } + }, + "hooks": { + "type": "object", + "patternProperties": { + "^[a-zA-Z-_:\\\\]+$": { + "type": "string", + "pattern": "^[a-zA-Z-_:\\\\]+$" + } } - } }, - "owncloud": { - "type": "string", - "pattern": "^((=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*(,(=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*)*|\\*)$" + "navigation": { + "type": "object", + "properties": { + "route": { + "type": "string", + "pattern": "^([a-z]+(\\.[a-z]+)*)*|(/.+/.*)$" + }, + "icon": { + "type": "string" + }, + "name": { + "type": "string" + }, + "order": { + "type": "integer" + } + }, + "additionalProperties": false + }, + "categories": { + "type": "array", + "items": { + "type": "string", + "enum": ["Filesystem", "Authentication", "PIM", "Multimedia", + "Productivity", "Games", "Tools", "Other"] + }, + "minItems": 1, + "uniqueItems": true + }, + "dependencies": { + "type": "object", + "properties": { + "databases": { + "type": "array", + "items": { + "type": "string", + "enum": ["pgsql", "mysql", "sqlite3", "mssql", "oracle"] + }, + "uniqueItems": true + }, + "php": { + "type": "string", + "pattern": "^((=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*(,(=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*)*|\\*)$" + }, + "apps": { + "type": "object", + "patternProperties": { + "^[a-z_]+$": { + "type": "string", + "pattern": "^((=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*(,(=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*)*|\\*)$" + } + } + }, + "libs": { + "type": "object", + "patternProperties": { + "^[a-z_]+$": { + "type": "string", + "pattern": "^((=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*(,(=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*)*|\\*)$" + } + } + }, + "owncloud": { + "type": "string", + "pattern": "^((=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*(,(=|<|>|<=|>=)?[0-9]+(\\.[0-9]+)*)*|\\*)$" + } + }, + "additionalProperties": false } - }, - "additionalProperties": false - } - }, - "required": [ - "name", - "id", - "description", - "licence", - "version", - "authors", - "repository" - ], - "additionalProperties": false + }, + "required": [ + "name", + "id", + "description", + "licence", + "version", + "authors", + "repository" + ], + "additionalProperties": false }
\ No newline at end of file diff --git a/controller/admincontroller.php b/controller/admincontroller.php index 2b876c394..cd3ae9df4 100644 --- a/controller/admincontroller.php +++ b/controller/admincontroller.php @@ -21,56 +21,56 @@ use \OCA\News\Config\Config; class AdminController extends Controller { - private $config; - private $configPath; + private $config; + private $configPath; - public function __construct($appName, IRequest $request, Config $config, - $configPath){ - parent::__construct($appName, $request); - $this->config = $config; - $this->configPath = $configPath; - } + public function __construct($appName, IRequest $request, Config $config, + $configPath){ + parent::__construct($appName, $request); + $this->config = $config; + $this->configPath = $configPath; + } - // There are no checks for the index method since the output is rendered - // in admin/admin.php - public function index() { - $data = [ - 'autoPurgeMinimumInterval' => $this->config->getAutoPurgeMinimumInterval(), - 'autoPurgeCount' => $this->config->getAutoPurgeCount(), - 'cacheDuration' => $this->config->getSimplePieCacheDuration(), - 'feedFetcherTimeout' => $this->config->getFeedFetcherTimeout(), - 'useCronUpdates' => $this->config->getUseCronUpdates(), - ]; - return new TemplateResponse($this->appName, 'admin', $data, 'blank'); - } + // There are no checks for the index method since the output is rendered + // in admin/admin.php + public function index() { + $data = [ + 'autoPurgeMinimumInterval' => $this->config->getAutoPurgeMinimumInterval(), + 'autoPurgeCount' => $this->config->getAutoPurgeCount(), + 'cacheDuration' => $this->config->getSimplePieCacheDuration(), + 'feedFetcherTimeout' => $this->config->getFeedFetcherTimeout(), + 'useCronUpdates' => $this->config->getUseCronUpdates(), + ]; + return new TemplateResponse($this->appName, 'admin', $data, 'blank'); + } - /** - * @param int $autoPurgeMinimumInterval - * @param int $autoPurgeCount - * @param int $cacheDuration - * @param int $feedFetcherTimeout - * @param bool $useCronUpdates - * @return array with the updated values - */ - public function update($autoPurgeMinimumInterval, $autoPurgeCount, - $cacheDuration, $feedFetcherTimeout, - $useCronUpdates) { - $this->config->setAutoPurgeMinimumInterval($autoPurgeMinimumInterval); - $this->config->setAutoPurgeCount($autoPurgeCount); - $this->config->setSimplePieCacheDuration($cacheDuration); - $this->config->setFeedFetcherTimeout($feedFetcherTimeout); - $this->config->setUseCronUpdates($useCronUpdates); - $this->config->write($this->configPath); + /** + * @param int $autoPurgeMinimumInterval + * @param int $autoPurgeCount + * @param int $cacheDuration + * @param int $feedFetcherTimeout + * @param bool $useCronUpdates + * @return array with the updated values + */ + public function update($autoPurgeMinimumInterval, $autoPurgeCount, + $cacheDuration, $feedFetcherTimeout, + $useCronUpdates) { + $this->config->setAutoPurgeMinimumInterval($autoPurgeMinimumInterval); + $this->config->setAutoPurgeCount($autoPurgeCount); + $this->config->setSimplePieCacheDuration($cacheDuration); + $this->config->setFeedFetcherTimeout($feedFetcherTimeout); + $this->config->setUseCronUpdates($useCronUpdates); + $this->config->write($this->configPath); - return [ - 'autoPurgeMinimumInterval' => $this->config->getAutoPurgeMinimumInterval(), - 'autoPurgeCount' => $this->config->getAutoPurgeCount(), - 'cacheDuration' => $this->config->getSimplePieCacheDuration(), - 'feedFetcherTimeout' => $this->config->getFeedFetcherTimeout(), - 'useCronUpdates' => $this->config->getUseCronUpdates(), - ]; - } + return [ + 'autoPurgeMinimumInterval' => $this->config->getAutoPurgeMinimumInterval(), + 'autoPurgeCount' => $this->config->getAutoPurgeCount(), + 'cacheDuration' => $this->config->getSimplePieCacheDuration(), + 'feedFetcherTimeout' => $this->config->getFeedFetcherTimeout(), + 'useCronUpdates' => $this->config->getUseCronUpdates(), + ]; + } }
\ No newline at end of file diff --git a/controller/exportcontroller.php b/controller/exportcontroller.php index b455f2fcc..1d0f7086c 100644 --- a/controller/exportcontroller.php +++ b/controller/exportcontroller.php @@ -26,64 +26,64 @@ use \OCA\News\Utility\OPMLExporter; class ExportController extends Controller { - private $opmlExporter; - private $folderService; - private $feedService; - private $itemService; - private $userId; + private $opmlExporter; + private $folderService; + private $feedService; + private $itemService; + private $userId; - public function __construct($appName, - IRequest $request, - FolderService $folderService, - FeedService $feedService, - ItemService $itemService, - OPMLExporter $opmlExporter, - $userId){ - parent::__construct($appName, $request); - $this->feedService = $feedService; - $this->folderService = $folderService; - $this->opmlExporter = $opmlExporter; - $this->itemService = $itemService; - $this->userId = $userId; - } + public function __construct($appName, + IRequest $request, + FolderService $folderService, + FeedService $feedService, + ItemService $itemService, + OPMLExporter $opmlExporter, + $userId){ + parent::__construct($appName, $request); + $this->feedService = $feedService; + $this->folderService = $folderService; + $this->opmlExporter = $opmlExporter; + $this->itemService = $itemService; + $this->userId = $userId; + } - /** - * @NoAdminRequired - * @NoCSRFRequired - */ - public function opml(){ - $feeds = $this->feedService->findAll($this->userId); - $folders = $this->folderService->findAll($this->userId); - $opml = $this->opmlExporter->build($folders, $feeds)->saveXML(); - return new TextDownloadResponse($opml, 'subscriptions.opml', 'text/xml'); - } + /** + * @NoAdminRequired + * @NoCSRFRequired + */ + public function opml(){ + $feeds = $this->feedService->findAll($this->userId); + $folders = $this->folderService->findAll($this->userId); + $opml = $this->opmlExporter->build($folders, $feeds)->saveXML(); + return new TextDownloadResponse($opml, 'subscriptions.opml', 'text/xml'); + } - /** - * @NoAdminRequired - * @NoCSRFRequired - */ - public function articles(){ - $feeds = $this->feedService->findAll($this->userId); - $items = $this->itemService->getUnreadOrStarred($this->userId); + /** + * @NoAdminRequired + * @NoCSRFRequired + */ + public function articles(){ + $feeds = $this->feedService->findAll($this->userId); + $items = $this->itemService->getUnreadOrStarred($this->userId); - // build assoc array for fast access - $feedsDict = []; - foreach($feeds as $feed) { - $feedsDict['feed' . $feed->getId()] = $feed; - } + // build assoc array for fast access + $feedsDict = []; + foreach($feeds as $feed) { + $feedsDict['feed' . $feed->getId()] = $feed; + } - $articles = []; - foreach($items as $item) { - $articles[] = $item->toExport($feedsDict); - } - - $response = new JSONResponse($articles); - $response->addHeader('Content-Disposition', - 'attachment; filename="articles.json"'); - return $response; - } + $articles = []; + foreach($items as $item) { + $articles[] = $item->toExport($feedsDict); + } + + $response = new JSONResponse($articles); + $response->addHeader('Content-Disposition', + 'attachment; filename="articles.json"'); + return $response; + } }
\ No newline at end of file diff --git a/controller/feedapicontroller.php b/controller/feedapicontroller.php index 33a9cbb7f..c75cd5879 100644 --- a/controller/feedapicontroller.php +++ b/controller/feedapicontroller.php @@ -26,53 +26,53 @@ use \OCA\News\Service\ServiceConflictException; class FeedApiController extends ApiController { - use JSONHttpError; - - private $itemService; - private $feedService; - private $userId; - private $logger; - private $loggerParams; - private $serializer; - - public function __construct($appName, - IRequest $request, - FeedService $feedService, - ItemService $itemService, - ILogger $logger, - $userId, - $loggerParams){ - parent::__construct($appName, $request); - $this->feedService = $feedService; - $this->itemService = $itemService; - $this->userId = $userId; - $this->logger = $logger; - $this->loggerParams = $loggerParams; - $this->serializer = new EntityApiSerializer('feeds'); - } - - - /** - * @NoAdminRequired - * @NoCSRFRequired - * @CORS - */ - public function index() { - - $result = [ - 'starredCount' => $this->itemService->starredCount($this->userId), - 'feeds' => $this->feedService->findAll($this->userId) - ]; - - - try { - $result['newestItemId'] = $this->itemService->getNewestItemId($this->userId); - - // in case there are no items, ignore - } catch(ServiceNotFoundException $ex) {} - - return $this->serializer->serialize($result); - } + use JSONHttpError; + + private $itemService; + private $feedService; + private $userId; + private $logger; + private $loggerParams; + private $serializer; + + public function __construct($appName, + IRequest $request, + FeedService $feedService, + ItemService $itemService, + ILogger $logger, + $userId, + $loggerParams){ + parent::__construct($appName, $request); + $this->feedService = $feedService; + $this->itemService = $itemService; + $this->userId = $userId; + $this->logger = $logger; + $this->loggerParams = $loggerParams; + $this->serializer = new EntityApiSerializer('feeds'); + } + + + /** + * @NoAdminRequired + * @NoCSRFRequired + * @CORS + */ + public function index() { + + $result = [ + 'starredCount' => $this->itemService->starredCount($this->userId), + 'feeds' => $this->feedService->findAll($this->userId) + ]; + + + try { + $result['newestItemId'] = $this->itemService->getNewestItemId($this->userId); + + // in case there are no items, ignore + } catch(ServiceNotFoundException $ex) {} + + return $this->serializer->serialize($result); + } /** @@ -84,27 +84,27 @@ class FeedApiController extends ApiController { * @param int $folderId * @return array|mixed|\OCP\AppFramework\Http\JSONResponse */ - public function create($url, $folderId=0) { - try { - $this->feedService->purgeDeleted($this->userId, false); + public function create($url, $folderId=0) { + try { + $this->feedService->purgeDeleted($this->userId, false); - $feed = $this->feedService->create($url, $folderId, $this->userId); - $result = ['feeds' => [$feed]]; + $feed = $this->feedService->create($url, $folderId, $this->userId); + $result = ['feeds' => [$feed]]; - try { - $result['newestItemId'] = $this->itemService->getNewestItemId($this->userId); + try { + $result['newestItemId'] = $this->itemService->getNewestItemId($this->userId); - // in case there are no items, ignore - } catch(ServiceNotFoundException $ex) {} + // in case there are no items, ignore + } catch(ServiceNotFoundException $ex) {} - return $this->serializer->serialize($result); + return $this->serializer->serialize($result); - } catch(ServiceConflictException $ex) { - return $this->error($ex, Http::STATUS_CONFLICT); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } - } + } catch(ServiceConflictException $ex) { + return $this->error($ex, Http::STATUS_CONFLICT); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } + } /** @@ -115,28 +115,28 @@ class FeedApiController extends ApiController { * @param int $feedId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function delete($feedId) { - try { - $this->feedService->delete($feedId, $this->userId); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function delete($feedId) { + try { + $this->feedService->delete($feedId, $this->userId); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } - /** - * @NoAdminRequired - * @NoCSRFRequired - * @CORS - * - * @param int $feedId - * @param int $newestItemId - */ - public function read($feedId, $newestItemId) { - $this->itemService->readFeed($feedId, $newestItemId, $this->userId); - } + /** + * @NoAdminRequired + * @NoCSRFRequired + * @CORS + * + * @param int $feedId + * @param int $newestItemId + */ + public function read($feedId, $newestItemId) { + $this->itemService->readFeed($feedId, $newestItemId, $this->userId); + } /** @@ -148,15 +148,15 @@ class FeedApiController extends ApiController { * @param int $folderId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function move($feedId, $folderId) { - try { - $this->feedService->move($feedId, $folderId, $this->userId); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function move($feedId, $folderId) { + try { + $this->feedService->move($feedId, $folderId, $this->userId); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } /** @@ -168,51 +168,51 @@ class FeedApiController extends ApiController { * @param string $feedTitle * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function rename($feedId, $feedTitle) { - try { - $this->feedService->rename($feedId, $feedTitle, $this->userId); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function rename($feedId, $feedTitle) { + try { + $this->feedService->rename($feedId, $feedTitle, $this->userId); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } - - - /** - * @NoCSRFRequired - * @CORS - */ - public function fromAllUsers() { - $feeds = $this->feedService->findAllFromAllUsers(); - $result = ['feeds' => []]; - - foreach ($feeds as $feed) { - $result['feeds'][] = [ - 'id' => $feed->getId(), - 'userId' => $feed->getUserId() - ]; - } - - return $result; - } - - - /** - * @NoCSRFRequired - * - * @param string $userId - * @param int $feedId - */ - public function update($userId, $feedId) { - try { - $this->feedService->update($feedId, $userId); - // ignore update failure (feed could not be reachable etc, we don't care) - } catch(\Exception $ex) { - $this->logger->debug('Could not update feed ' . $ex->getMessage(), - $this->loggerParams); - } - } + } + + + /** + * @NoCSRFRequired + * @CORS + */ + public function fromAllUsers() { + $feeds = $this->feedService->findAllFromAllUsers(); + $result = ['feeds' => []]; + + foreach ($feeds as $feed) { + $result['feeds'][] = [ + 'id' => $feed->getId(), + 'userId' => $feed->getUserId() + ]; + } + + return $result; + } + + + /** + * @NoCSRFRequired + * + * @param string $userId + * @param int $feedId + */ + public function update($userId, $feedId) { + try { + $this->feedService->update($feedId, $userId); + // ignore update failure (feed could not be reachable etc, we don't care) + } catch(\Exception $ex) { + $this->logger->debug('Could not update feed ' . $ex->getMessage(), + $this->loggerParams); + } + } } diff --git a/controller/feedcontroller.php b/controller/feedcontroller.php index 686eec9e3..e1544bff0 100644 --- a/controller/feedcontroller.php +++ b/controller/feedcontroller.php @@ -28,94 +28,94 @@ use \OCA\News\Db\FeedType; class FeedController extends Controller { - use JSONHttpError; - - private $feedService; - private $folderService; - private $itemService; - private $userId; - private $settings; - - public function __construct($appName, - IRequest $request, - FolderService $folderService, - FeedService $feedService, - ItemService $itemService, - IConfig $settings, - $userId){ - parent::__construct($appName, $request); - $this->feedService = $feedService; - $this->folderService = $folderService; - $this->itemService = $itemService; - $this->userId = $userId; - $this->settings = $settings; - } - - - /** - * @NoAdminRequired - */ - public function index(){ - - // this method is also used to update the interface - // because of this we also pass the starred count and the newest - // item id which will be used for marking feeds read - $params = [ - 'feeds' => $this->feedService->findAll($this->userId), - 'starred' => $this->itemService->starredCount($this->userId) - ]; - - try { - $params['newestItemId'] = - $this->itemService->getNewestItemId($this->userId); - - // An exception occurs if there is a newest item. If there is none, - // simply ignore it and do not add the newestItemId - } catch (ServiceNotFoundException $ex) {} - - return $params; - } - - - /** - * @NoAdminRequired - */ - public function active(){ - $feedId = (int) $this->settings->getUserValue($this->userId, - $this->appName,'lastViewedFeedId'); - $feedType = $this->settings->getUserValue($this->userId, $this->appName, - 'lastViewedFeedType'); - - // cast from null to int is 0 - if($feedType !== null){ - $feedType = (int) $feedType; - } - - // check if feed or folder exists - try { - if($feedType === FeedType::FOLDER){ - $this->folderService->find($feedId, $this->userId); - - } elseif ($feedType === FeedType::FEED){ - $this->feedService->find($feedId, $this->userId); - - // if its the first launch, those values will be null - } elseif($feedType === null){ - throw new ServiceNotFoundException(''); - } - - } catch (ServiceNotFoundException $ex){ - $feedId = 0; - $feedType = FeedType::SUBSCRIPTIONS; - } - - return [ - 'activeFeed' => [ - 'id' => $feedId, - 'type' => $feedType - ] - ]; - } + use JSONHttpError; + + private $feedService; + private $folderService; + private $itemService; + private $userId; + private $settings; + + public function __construct($appName, + IRequest $request, + FolderService $folderService, + FeedService $feedService, + ItemService $itemService, + IConfig $settings, + $userId){ + parent::__construct($appName, $request); + $this->feedService = $feedService; + $this->folderService = $folderService; + $this->itemService = $itemService; + $this->userId = $userId; + $this->settings = $settings; + } + + + /** + * @NoAdminRequired + */ + public function index(){ + + // this method is also used to update the interface + // because of this we also pass the starred count and the newest + // item id which will be used for marking feeds read + $params = [ + 'feeds' => $this->feedService->findAll($this->userId), + 'starred' => $this->itemService->starredCount($this->userId) + ]; + + try { + $params['newestItemId'] = + $this->itemService->getNewestItemId($this->userId); + + // An exception occurs if there is a newest item. If there is none, + // simply ignore it and do not add the newestItemId + } catch (ServiceNotFoundException $ex) {} + + return $params; + } + + + /** + * @NoAdminRequired + */ + public function active(){ + $feedId = (int) $this->settings->getUserValue($this->userId, + $this->appName,'lastViewedFeedId'); + $feedType = $this->settings->getUserValue($this->userId, $this->appName, + 'lastViewedFeedType'); + + // cast from null to int is 0 + if($feedType !== null){ + $feedType = (int) $feedType; + } + + // check if feed or folder exists + try { + if($feedType === FeedType::FOLDER){ + $this->folderService->find($feedId, $this->userId); + + } elseif ($feedType === FeedType::FEED){ + $this->feedService->find($feedId, $this->userId); + + // if its the first launch, those values will be null + } elseif($feedType === null){ + throw new ServiceNotFoundException(''); + } + + } catch (ServiceNotFoundException $ex){ + $feedId = 0; + $feedType = FeedType::SUBSCRIPTIONS; + } + + return [ + 'activeFeed' => [ + 'id' => $feedId, + 'type' => $feedType + ] + ]; + } /** @@ -126,33 +126,33 @@ class FeedController extends Controller { * @param string $title * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function create($url, $parentFolderId, $title){ - try { - // we need to purge deleted feeds if a feed is created to - // prevent already exists exceptions - $this->feedService->purgeDeleted($this->userId, false); + public function create($url, $parentFolderId, $title){ + try { + // we need to purge deleted feeds if a feed is created to + // prevent already exists exceptions + $this->feedService->purgeDeleted($this->userId, false); - $feed = $this->feedService->create($url, $parentFolderId, - $this->userId, $title); - $params = ['feeds' => [$feed]]; + $feed = $this->feedService->create($url, $parentFolderId, + $this->userId, $title); + $params = ['feeds' => [$feed]]; - try { - $params['newestItemId'] = - $this->itemService->getNewestItemId($this->userId); + try { + $params['newestItemId'] = + $this->itemService->getNewestItemId($this->userId); - // An exception occurs if there is a newest item. If there is none, - // simply ignore it and do not add the newestItemId - } catch (ServiceNotFoundException $ex) {} + // An exception occurs if there is a newest item. If there is none, + // simply ignore it and do not add the newestItemId + } catch (ServiceNotFoundException $ex) {} - return $params; + return $params; - } catch(ServiceConflictException $ex) { - return $this->error($ex, Http::STATUS_CONFLICT); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_UNPROCESSABLE_ENTITY); - } + } catch(ServiceConflictException $ex) { + return $this->error($ex, Http::STATUS_CONFLICT); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_UNPROCESSABLE_ENTITY); + } - } + } /** @@ -161,15 +161,15 @@ class FeedController extends Controller { * @param int $feedId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function delete($feedId){ - try { - $this->feedService->markDeleted($feedId, $this->userId); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function delete($feedId){ + try { + $this->feedService->markDeleted($feedId, $this->userId); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } /** @@ -178,26 +178,26 @@ class FeedController extends Controller { * @param int $feedId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function update($feedId){ - try { - $feed = $this->feedService->update($feedId, $this->userId); + public function update($feedId){ + try { + $feed = $this->feedService->update($feedId, $this->userId); - return [ - 'feeds' => [ - // only pass unread count to not accidentally readd - // the feed again - [ - 'id' => $feed->getId(), - 'unreadCount' => $feed->getUnreadCount() - ] - ] - ]; + return [ + 'feeds' => [ + // only pass unread count to not accidentally readd + // the feed again + [ + 'id' => $feed->getId(), + 'unreadCount' => $feed->getUnreadCount() + ] + ] + ]; - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } - } + } /** @@ -207,15 +207,15 @@ class FeedController extends Controller { * @param int $parentFolderId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function move($feedId, $parentFolderId){ - try { - $this->feedService->move($feedId, $parentFolderId, $this->userId); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function move($feedId, $parentFolderId){ + try { + $this->feedService->move($feedId, $parentFolderId, $this->userId); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } /** * @NoAdminRequired @@ -224,15 +224,15 @@ class FeedController extends Controller { * @param string $feedTitle * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function rename($feedId, $feedTitle) { - try { - $this->feedService->rename($feedId, $feedTitle, $this->userId); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function rename($feedId, $feedTitle) { + try { + $this->feedService->rename($feedId, $feedTitle, $this->userId); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } /** @@ -241,19 +241,19 @@ class FeedController extends Controller { * @param array $json * @return array */ - public function import($json) { - $feed = $this->feedService->importArticles($json, $this->userId); + public function import($json) { + $feed = $this->feedService->importArticles($json, $this->userId); - $params = [ - 'starred' => $this->itemService->starredCount($this->userId) - ]; + $params = [ + 'starred' => $this->itemService->starredCount($this->userId) + ]; - if($feed) { - $params['feeds'] = [$feed]; - } + if($feed) { + $params['feeds'] = [$feed]; + } - return $params; - } + return $params; + } /** @@ -263,18 +263,18 @@ class FeedController extends Controller { * @param int $highestItemId * @return array */ - public function read($feedId, $highestItemId){ - $this->itemService->readFeed($feedId, $highestItemId, $this->userId); + public function read($feedId, $highestItemId){ + $this->itemService->readFeed($feedId, $highestItemId, $this->userId); - return [ - 'feeds' => [ - [ - 'id' => $feedId, - 'unreadCount' => 0 - ] - ] - ]; - } + return [ + 'feeds' => [ + [ + 'id' => $feedId, + 'unreadCount' => 0 + ] + ] + ]; + } /** @@ -283,15 +283,15 @@ class FeedController extends Controller { * @param int $feedId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function restore($feedId){ - try { - $this->feedService->unmarkDeleted($feedId, $this->userId); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function restore($feedId){ + try { + $this->feedService->unmarkDeleted($feedId, $this->userId); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } }
\ No newline at end of file diff --git a/controller/folderapicontroller.php b/controller/folderapicontroller.php index 84f1dbdf5..ab2b5601f 100644 --- a/controller/folderapicontroller.php +++ b/controller/folderapicontroller.php @@ -26,36 +26,36 @@ use \OCA\News\Service\ServiceValidationException; class FolderApiController extends ApiController { - use JSONHttpError; - - private $folderService; - private $itemService; - private $userId; - private $serializer; - - public function __construct($appName, - IRequest $request, - FolderService $folderService, - ItemService $itemService, - $userId){ - parent::__construct($appName, $request); - $this->folderService = $folderService; - $this->itemService = $itemService; - $this->userId = $userId; - $this->serializer = new EntityApiSerializer('folders'); - } - - - /** - * @NoAdminRequired - * @NoCSRFRequired - * @CORS - */ - public function index() { - return $this->serializer->serialize( - $this->folderService->findAll($this->userId) - ); - } + use JSONHttpError; + + private $folderService; + private $itemService; + private $userId; + private $serializer; + + public function __construct($appName, + IRequest $request, + FolderService $folderService, + ItemService $itemService, + $userId){ + parent::__construct($appName, $request); + $this->folderService = $folderService; + $this->itemService = $itemService; + $this->userId = $userId; + $this->serializer = new EntityApiSerializer('folders'); + } + + + /** + * @NoAdminRequired + * @NoCSRFRequired + * @CORS + */ + public function index() { + return $this->serializer->serialize( + $this->folderService->findAll($this->userId) + ); + } /** @@ -66,18 +66,18 @@ class FolderApiController extends ApiController { * @param string $name * @return array|mixed|\OCP\AppFramework\Http\JSONResponse */ - public function create($name) { - try { - $this->folderService->purgeDeleted($this->userId, false); - return $this->serializer->serialize( - $this->folderService->create($name, $this->userId) - ); - } catch(ServiceValidationException $ex) { - return $this->error($ex, Http::STATUS_UNPROCESSABLE_ENTITY); - } catch(ServiceConflictException $ex) { - return $this->error($ex, Http::STATUS_CONFLICT); - } - } + public function create($name) { + try { + $this->folderService->purgeDeleted($this->userId, false); + return $this->serializer->serialize( + $this->folderService->create($name, $this->userId) + ); + } catch(ServiceValidationException $ex) { + return $this->error($ex, Http::STATUS_UNPROCESSABLE_ENTITY); + } catch(ServiceConflictException $ex) { + return $this->error($ex, Http::STATUS_CONFLICT); + } + } /** @@ -88,15 +88,15 @@ class FolderApiController extends ApiController { * @param int $folderId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function delete($folderId) { - try { - $this->folderService->delete($folderId, $this->userId); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function delete($folderId) { + try { + $this->folderService->delete($folderId, $this->userId); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } /** @@ -107,33 +107,33 @@ class FolderApiController extends ApiController { * @param string $name * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function update($folderId, $name) { - try { - $this->folderService->rename($folderId, $name, $this->userId); - - } catch(ServiceValidationException $ex) { - return $this->error($ex, Http::STATUS_UNPROCESSABLE_ENTITY); - } catch(ServiceConflictException $ex) { - return $this->error($ex, Http::STATUS_CONFLICT); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function update($folderId, $name) { + try { + $this->folderService->rename($folderId, $name, $this->userId); + + } catch(ServiceValidationException $ex) { + return $this->error($ex, Http::STATUS_UNPROCESSABLE_ENTITY); + } catch(ServiceConflictException $ex) { + return $this->error($ex, Http::STATUS_CONFLICT); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } - - - /** - * @NoAdminRequired - * @NoCSRFRequired - * @CORS - * - * @param int $folderId - * @param int $newestItemId - */ - public function read($folderId, $newestItemId) { - $this->itemService->readFolder($folderId, $newestItemId, $this->userId); - } + } + + + /** + * @NoAdminRequired + * @NoCSRFRequired + * @CORS + * + * @param int $folderId + * @param int $newestItemId + */ + public function read($folderId, $newestItemId) { + $this->itemService->readFolder($folderId, $newestItemId, $this->userId); + } } diff --git a/controller/foldercontroller.php b/controller/foldercontroller.php index 9488a7d6c..d5ccc7c62 100644 --- a/controller/foldercontroller.php +++ b/controller/foldercontroller.php @@ -27,34 +27,34 @@ use \OCA\News\Service\ServiceValidationException; class FolderController extends Controller { - use JSONHttpError; - - private $folderService; - private $feedService; - private $itemService; - private $userId; - - public function __construct($appName, - IRequest $request, - FolderService $folderService, - FeedService $feedService, - ItemService $itemService, - $userId) { - parent::__construct($appName, $request); - $this->folderService = $folderService; - $this->feedService = $feedService; - $this->itemService = $itemService; - $this->userId = $userId; - } - - - /** - * @NoAdminRequired - */ - public function index() { - $folders = $this->folderService->findAll($this->userId); - return ['folders' => $folders]; - } + use JSONHttpError; + + private $folderService; + private $feedService; + private $itemService; + private $userId; + + public function __construct($appName, + IRequest $request, + FolderService $folderService, + FeedService $feedService, + ItemService $itemService, + $userId) { + parent::__construct($appName, $request); + $this->folderService = $folderService; + $this->feedService = $feedService; + $this->itemService = $itemService; + $this->userId = $userId; + } + + + /** + * @NoAdminRequired + */ + public function index() { + $folders = $this->folderService->findAll($this->userId); + return ['folders' => $folders]; + } /** @@ -64,15 +64,15 @@ class FolderController extends Controller { * @param bool $open * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function open($folderId, $open) { - try { - $this->folderService->open($folderId, $open, $this->userId); - } catch(ServiceNotFoundException $ex) { - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function open($folderId, $open) { + try { + $this->folderService->open($folderId, $open, $this->userId); + } catch(ServiceNotFoundException $ex) { + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } /** @@ -81,22 +81,22 @@ class FolderController extends Controller { * @param string $folderName * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function create($folderName) { - try { - // we need to purge deleted folders if a folder is created to - // prevent already exists exceptions - $this->folderService->purgeDeleted($this->userId, false); - $folder = $this->folderService->create($folderName, $this->userId); + public function create($folderName) { + try { + // we need to purge deleted folders if a folder is created to + // prevent already exists exceptions + $this->folderService->purgeDeleted($this->userId, false); + $folder = $this->folderService->create($folderName, $this->userId); - return ['folders' => [$folder]]; + return ['folders' => [$folder]]; - } catch(ServiceConflictException $ex) { - return $this->error($ex, Http::STATUS_CONFLICT); - } catch(ServiceValidationException $ex) { - return $this->error($ex, Http::STATUS_UNPROCESSABLE_ENTITY); - } + } catch(ServiceConflictException $ex) { + return $this->error($ex, Http::STATUS_CONFLICT); + } catch(ServiceValidationException $ex) { + return $this->error($ex, Http::STATUS_UNPROCESSABLE_ENTITY); + } - } + } /** @@ -105,15 +105,15 @@ class FolderController extends Controller { * @param int $folderId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function delete($folderId) { - try { - $this->folderService->markDeleted($folderId, $this->userId); - } catch (ServiceNotFoundException $ex){ - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function delete($folderId) { + try { + $this->folderService->markDeleted($folderId, $this->userId); + } catch (ServiceNotFoundException $ex){ + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } /** @@ -123,22 +123,22 @@ class FolderController extends Controller { * @param int $folderId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function rename($folderName, $folderId) { - try { - $folder = $this->folderService->rename($folderId, $folderName, - $this->userId); + public function rename($folderName, $folderId) { + try { + $folder = $this->folderService->rename($folderId, $folderName, + $this->userId); - return ['folders' => [$folder]]; + return ['folders' => [$folder]]; - } catch(ServiceConflictException $ex) { - return $this->error($ex, Http::STATUS_CONFLICT); - } catch(ServiceValidationException $ex) { - return $this->error($ex, Http::STATUS_UNPROCESSABLE_ENTITY); - } catch (ServiceNotFoundException $ex){ - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + } catch(ServiceConflictException $ex) { + return $this->error($ex, Http::STATUS_CONFLICT); + } catch(ServiceValidationException $ex) { + return $this->error($ex, Http::STATUS_UNPROCESSABLE_ENTITY); + } catch (ServiceNotFoundException $ex){ + return $this->error($ex, Http::STATUS_NOT_FOUND); + } - } + } /** * @NoAdminRequired @@ -147,11 +147,11 @@ class FolderController extends Controller { * @param int $highestItemId * @return array */ - public function read($folderId, $highestItemId) { - $this->itemService->readFolder($folderId, $highestItemId, $this->userId); + public function read($folderId, $highestItemId) { + $this->itemService->readFolder($folderId, $highestItemId, $this->userId); - return ['feeds' => $this->feedService->findAll($this->userId)]; - } + return ['feeds' => $this->feedService->findAll($this->userId)]; + } /** @@ -160,15 +160,15 @@ class FolderController extends Controller { * @param int $folderId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function restore($folderId) { - try { - $this->folderService->unmarkDeleted($folderId, $this->userId); - } catch (ServiceNotFoundException $ex){ - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + public function restore($folderId) { + try { + $this->folderService->unmarkDeleted($folderId, $this->userId); + } catch (ServiceNotFoundException $ex){ + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } }
\ No newline at end of file diff --git a/controller/itemapicontroller.php b/controller/itemapicontroller.php index ebfbc218b..3674d644c 100644 --- a/controller/itemapicontroller.php +++ b/controller/itemapicontroller.php @@ -22,21 +22,21 @@ use \OCA\News\Service\ServiceNotFoundException; class ItemApiController extends ApiController { - use JSONHttpError; + use JSONHttpError; - private $itemService; - private $userId; - private $serializer; + private $itemService; + private $userId; + private $serializer; - public function __construct($appName, - IRequest $request, - ItemService $itemService, - $userId){ - parent::__construct($appName, $request); - $this->itemService = $itemService; - $this->userId = $userId; - $this->serializer = new EntityApiSerializer('items'); - } + public function __construct($appName, + IRequest $request, + ItemService $itemService, + $userId){ + parent::__construct($appName, $request); + $this->itemService = $itemService; + $this->userId = $userId; + $this->serializer = new EntityApiSerializer('items'); + } /** @@ -52,15 +52,15 @@ class ItemApiController extends ApiController { * @param bool $oldestFirst * @return array|mixed */ - public function index($type, $id, $getRead, $batchSize=20, $offset=0, - $oldestFirst=false) { - return $this->serializer->serialize( - $this->itemService->findAll( - $id, $type, $batchSize, $offset, $getRead, $oldestFirst, - $this->userId - ) - ); - } + public function index($type, $id, $getRead, $batchSize=20, $offset=0, + $oldestFirst=false) { + return $this->serializer->serialize( + $this->itemService->findAll( + $id, $type, $batchSize, $offset, $getRead, $oldestFirst, + $this->userId + ) + ); + } /** @@ -73,23 +73,23 @@ class ItemApiController extends ApiController { * @param int $lastModified * @return array|mixed */ - public function updated($type, $id, $lastModified=0) { - return $this->serializer->serialize( - $this->itemService->findAllNew($id, $type, $lastModified, - true, $this->userId) - ); - } + public function updated($type, $id, $lastModified=0) { + return $this->serializer->serialize( + $this->itemService->findAllNew($id, $type, $lastModified, + true, $this->userId) + ); + } - private function setRead($isRead, $itemId) { - try { - $this->itemService->read($itemId, $isRead, $this->userId); - } catch(ServiceNotFoundException $ex){ - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + private function setRead($isRead, $itemId) { + try { + $this->itemService->read($itemId, $isRead, $this->userId); + } catch(ServiceNotFoundException $ex){ + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } /** @@ -100,9 +100,9 @@ class ItemApiController extends ApiController { * @param int $itemId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function read($itemId) { - return $this->setRead(true, $itemId); - } + public function read($itemId) { + return $this->setRead(true, $itemId); + } /** @@ -113,20 +113,20 @@ class ItemApiController extends ApiController { * @param int $itemId * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function unread($itemId) { - return $this->setRead(false, $itemId); - } + public function unread($itemId) { + return $this->setRead(false, $itemId); + } - private function setStarred($isStarred, $feedId, $guidHash) { - try { - $this->itemService->star($feedId, $guidHash, $isStarred, $this->userId); - } catch(ServiceNotFoundException $ex){ - return $this->error($ex, Http::STATUS_NOT_FOUND); - } + private function setStarred($isStarred, $feedId, $guidHash) { + try { + $this->itemService->star($feedId, $guidHash, $isStarred, $this->userId); + } catch(ServiceNotFoundException $ex){ + return $this->error($ex, Http::STATUS_NOT_FOUND); + } return []; - } + } /** @@ -138,9 +138,9 @@ class ItemApiController extends ApiController { * @param string $guidHash * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function star($feedId, $guidHash) { - return $this->setStarred(true, $feedId, $guidHash); - } + public function star($feedId, $guidHash) { + return $this->setStarred(true, $feedId, $guidHash); + } /** @@ -152,92 +152,92 @@ class ItemApiController extends ApiController { * @param string $guidHash * @return array|\OCP\AppFramework\Http\JSONResponse */ - public function unstar($feedId, $guidHash) { - return $this->setStarred(false, $feedId, $guidHash); - } - - - /** - * @NoAdminRequired - * @NoCSRFRequired - * @CORS - * - * @param int $newestItemId - */ - public function readAll($newestItemId) { - $this->itemService->readAll($newestItemId, $this->userId); - } - - - private function setMultipleRead($isRead, $items) { - foreach($items as $id) { - try { - $this->itemService->read($id, $isRead, $this->userId); - } catch(ServiceNotFoundException $ex) { - continue; - } - } - } - - - /** - * @NoAdminRequired - * @NoCSRFRequired - * @CORS - * - * @param int[] item ids - */ - public function readMultiple($items) { - $this->setMultipleRead(true, $items); - } - - - /** - * @NoAdminRequired - * @NoCSRFRequired - * @CORS - * - * @param int[] item ids - */ - public function unreadMultiple($items) { - $this->setMultipleRead(false, $items); - } - - - private function setMultipleStarred($isStarred, $items) { - foreach($items as $item) { - try { - $this->itemService->star($item['feedId'], $item['guidHash'], - $isStarred, $this->userId); - } catch(ServiceNotFoundException $ex) { - continue; - } - } - } - - - /** - * @NoAdminRequired - * @NoCSRFRequired - * @CORS - * - * @param int[] item ids - */ - public function starMultiple($items) { - $this->setMultipleStarred(true, $items); - } - - - /** - * @NoAdminRequired - * @NoCSRFRequired - * @CORS - * - * @param int[] item ids - */ - public function unstarMultiple($items) { - $this->setMultipleStarred(false, $items); - } + public function unstar($feedId, $guidHash) { + return $this->setStarred(false, $feedId, $guidHash); + } + + + /** + * @NoAdminRequired + * @NoCSRFRequired + * @CORS + * + * @param int $newestItemId + */ + public function readAll($newestItemId) { + $this->itemService->readAll($newestItemId, $this->userId); + } + + + private function setMultipleRead($isRead, $items) { + foreach($items as $id) { + try { + $this->itemService->read($id, $isRead, $this->userId); + } catch(ServiceNotFoundException $ex) { + continue; + } + } + } + + + /** + * @NoAdminRequired + * @NoCSRFRequired + * @CORS + * + * @param int[] item ids + */ + public function readMultiple($items) { + $this->setMultipleRead(true, $items); + } + + + /** + * @NoAdminRequired + * @NoCSRFRequired + * @CORS + * + * @param int[] item ids + */ + public function unreadMultiple($items) { + $this->setMultipleRead(false, $items); + } + + + private function setMultipleStarred($isStarred, $items) { + foreach($items as $item) { + try { + $this->itemService->star($item['feedId'], $item['guidHash'], + $isStarred, $this->userId); + } catch(ServiceNotFoundException $ex) { + continue; + } + } + } + + + /** + * @NoAdminRequired + * @NoCSRFRequired + * @CORS + * + * @param int[] item ids + */ + public function starMultiple($items) { + $this->setMultipleStarred(true, $items); + } + + + /** + * @NoAdminRequired + * @NoCSRFRequired + * @CORS + * + * @param int[] item ids + */ + public function unstarMultiple($items) { + $this->setMultipleStarred(false, $items); + } } diff --git a/controller/jsonhttperror.php b/controller/jsonhttperror.php index a271878a8..722019ae1 100644 --- a/controller/jsonhttperror.php +++ b/controller/jsonhttperror.php @@ -17,15 +17,15 @@ use \OCP\AppFramework\Http\JSONResponse; trait JSONHttpError { - /** - * @param \Exception $exception the message that is returned taken from the - * exception - * @param int $code the http error code - * @return \OCP\AppFramework\Http\JSONResponse - */ - public function error(\Exception $exception, $code) { - return new JSONResponse(['message' => $exception->getMessage()], $code); - } + /** + * @param \Exception $exception the message that is returned taken from the + * exception + * @param int $code the http error code + * @return \OCP\AppFramework\Http\JSONResponse + */ + public function error(\Exception $exception, $code) { + return new JSONResponse(['message' => $exception->getMessage()], $code); + } }
\ No newline at end of file diff --git a/controller/pagecontroller.php b/controller/pagecontroller.php index e8b651608..90f702d49 100644 --- a/controller/pagecontroller.php +++ b/controller/pagecontroller.php @@ -24,70 +24,70 @@ use \OCA\News\Config\AppConfig; class PageController extends Controller { - private $settings; - private $l10n; - private $userId; - private $appConfig; - private $urlGenerator; - - public function __construct($appName, - IRequest $request, - IConfig $settings, - IURLGenerator $urlGenerator, + private $settings; + private $l10n; + private $userId; + private $appConfig; + private $urlGenerator; + + public function __construct($appName, + IRequest $request, + IConfig $settings, + IURLGenerator $urlGenerator, AppConfig $appConfig, - IL10N $l10n, - $userId){ - parent::__construct($appName, $request); - $this->settings = $settings; - $this->urlGenerator = $urlGenerator; - $this->appConfig = $appConfig; - $this->l10n = $l10n; - $this->userId = $userId; - } - - - /** - * @NoAdminRequired - * @NoCSRFRequired - */ - public function index() { - return new TemplateResponse($this->appName, 'index'); - } - - - /** - * @NoAdminRequired - */ - public function settings() { - $settings = ['showAll', 'compact', 'preventReadOnScroll', 'oldestFirst']; - - $result = ['language' => $this->l10n->getLanguageCode()]; - - foreach ($settings as $setting) { - $result[$setting] = $this->settings->getUserValue( - $this->userId, $this->appName, $setting - ) === '1'; - } - return ['settings' => $result]; - } - - - /** - * @NoAdminRequired - * - * @param bool $showAll - * @param bool $compact - * @param bool $preventReadOnScroll - * @param bool $oldestFirst - */ - public function updateSettings($showAll, $compact, $preventReadOnScroll, $oldestFirst) { - $settings = ['showAll', 'compact', 'preventReadOnScroll', 'oldestFirst']; - - foreach ($settings as $setting) { - $this->settings->setUserValue($this->userId, $this->appName, - $setting, ${$setting}); - } - } + IL10N $l10n, + $userId){ + parent::__construct($appName, $request); + $this->settings = $settings; + $this->urlGenerator = $urlGenerator; + $this->appConfig = $appConfig; + $this->l10n = $l10n; + $this->userId = $userId; + } + + + /** + * @NoAdminRequired + * @NoCSRFRequired + */ + public function index() { + return new TemplateResponse($this->appName, 'index'); + } + + + /** + * @NoAdminRequired + */ + public function settings() { + $settings = ['showAll', 'compact', 'preventReadOnScroll', 'oldestFirst']; + + $result = ['language' => $this->l10n->getLanguageCode()]; + + foreach ($settings as $setting) { + $result[$setting] = $this->settings->getUserValue( + $this->userId, $this->appName, $setting + ) === '1'; + } + return ['settings' => $result]; + } + + + /** + * @NoAdminRequired + * + * @param bool $showAll + * @param bool $compact + * @param bool $preventReadOnScroll + * @param bool $oldestFirst + */ + public function updateSettings($showAll, $compact, $preventReadOnScroll, $oldestFirst) { + $settings = ['showAll', 'compact', 'preventReadOnScroll', 'oldestFirst']; + + foreach ($settings as $setting) { + $this->settings->setUserValue($this->userId, $this->appName, + $setting, ${$setting}); + } + } /** diff --git a/controller/utilityapicontroller.php b/controller/utilityapicontroller.php index 6dae8d027..44745a074 100644 --- a/controller/utilityapicontroller.php +++ b/controller/utilityapicontroller.php @@ -23,45 +23,45 @@ use \OCA\News\Utility\Updater; class UtilityApiController extends ApiController { - private $updater; - private $settings; + private $updater; + private $settings; - public function __construct($appName, - IRequest $request, - Updater $updater, - IConfig $settings){ - parent::__construct($appName, $request); - $this->updater = $updater; - $this->settings = $settings; - } + public function __construct($appName, + IRequest $request, + Updater $updater, + IConfig $settings){ + parent::__construct($appName, $request); + $this->updater = $updater; + $this->settings = $settings; + } - /** - * @NoAdminRequired - * @NoCSRFRequired - * @API - */ - public function version() { - $version = $this->settings->getAppValue($this->appName, - 'installed_version'); - return ['version' => $version]; - } + /** + * @NoAdminRequired + * @NoCSRFRequired + * @API + */ + public function version() { + $version = $this->settings->getAppValue($this->appName, + 'installed_version'); + return ['version' => $version]; + } - /** - * @NoCSRFRequired - */ - public function beforeUpdate() { - $this->updater->beforeUpdate(); - } + /** + * @NoCSRFRequired + */ + public function beforeUpdate() { + $this->updater->beforeUpdate(); + } - /** - * @NoCSRFRequired - */ - public function afterUpdate() { - $this->updater->afterUpdate(); - } + /** + * @NoCSRFRequired + */ + public function afterUpdate() { + $this->updater->afterUpdate(); + } } diff --git a/cron/updater.php b/cron/updater.php index 40e134b02..b04472334 100644 --- a/cron/updater.php +++ b/cron/updater.php @@ -20,19 +20,19 @@ use \OCA\News\AppInfo\Application; class Updater { - static public function run() { - $app = new Application(); - - $container = $app->getContainer(); - - // make it possible to turn off cron updates if you use an external - // script to execute updates in parallel - if ($container->query('Config')->getUseCronUpdates()) { - $container->query('Updater')->beforeUpdate(); - $container->query('Updater')->update(); - $container->query('Updater')->afterUpdate(); - } - } + static public function run() { + $app = new Application(); + + $container = $app->getContainer(); + + // make it possible to turn off cron updates if you use an external + // script to execute updates in parallel + if ($container->query('Config')->getUseCronUpdates()) { + $container->query('Updater')->beforeUpdate(); + $container->query('Updater')->update(); + $container->query('Updater')->afterUpdate(); + } + } } @@ -12,257 +12,257 @@ #app-navigation > .with-icon ul li > a, #app-navigation > .with-icon ul li.app-navigation-entry-loading > a { - padding-left: 68px; - background-position: 44px center; + padding-left: 68px; + background-position: 44px center; } #app-navigation li:hover > a, #app-navigation .selected, #app-navigation .selected a { - background-color: #ddd; + background-color: #ddd; } #app-navigation .with-icon a, #app-navigation .app-navigation-entry-loading a { - padding-left: 44px; - background-size: 16px 16px; - background-position: 14px center; - background-repeat: no-repeat; + padding-left: 44px; + background-size: 16px 16px; + background-position: 14px center; + background-repeat: no-repeat; } #app-navigation .collapsible.open { - background-image: linear-gradient(top, rgb(238,238,238) 0%, rgb(245,245,245) 100%); - background-image: -o-linear-gradient(top, rgb(238,238,238) 0%, rgb(245,245,245) 100%); - background-image: -moz-linear-gradient(top, rgb(238,238,238) 0%, rgb(245,245,245) 100%); - background-image: -webkit-linear-gradient(top, rgb(238,238,238) 0%, rgb(245,245,245) 100%); - background-image: -ms-linear-gradient(top, rgb(238,238,238) 0%, rgb(245,245,245) 100%); + background-image: linear-gradient(top, rgb(238,238,238) 0%, rgb(245,245,245) 100%); + background-image: -o-linear-gradient(top, rgb(238,238,238) 0%, rgb(245,245,245) 100%); + background-image: -moz-linear-gradient(top, rgb(238,238,238) 0%, rgb(245,245,245) 100%); + background-image: -webkit-linear-gradient(top, rgb(238,238,238) 0%, rgb(245,245,245) 100%); + background-image: -ms-linear-gradient(top, rgb(238,238,238) 0%, rgb(245,245,245) 100%); } #app-navigation > ul .collapsible.open:hover { - box-shadow: inset 0 0 3px #ddd; + box-shadow: inset 0 0 3px #ddd; } #app-navigation > ul .collapsible.open ul { - display: block; + display: block; } /* Deleted entries with undo button */ #app-navigation .app-navigation-entry-deleted { - display: inline-block; - height: 44px; - width: 100%; + display: inline-block; + height: 44px; + width: 100%; } - #app-navigation .app-navigation-entry-deleted-description { - padding-left: 12px; - position: relative; - white-space: nowrap; - text-overflow: ellipsis; - overflow: hidden; - display: inline-block; - width: 201px; /* fallback for IE8 */ - width: calc(100% - 49px); - line-height: 44px; - float: left; - } - - #app-navigation .app-navigation-entry-deleted-button { - margin: 0; - height: 44px; - width: 44px; - line-height: 44px; - border: 0; - display: inline-block; - background-color: transparent; - opacity: .5; - } - - #app-navigation .app-navigation-entry-deleted-button:hover { - opacity: 1; - } + #app-navigation .app-navigation-entry-deleted-description { + padding-left: 12px; + position: relative; + white-space: nowrap; + text-overflow: ellipsis; + overflow: hidden; + display: inline-block; + width: 201px; /* fallback for IE8 */ + width: calc(100% - 49px); + line-height: 44px; + float: left; + } + + #app-navigation .app-navigation-entry-deleted-button { + margin: 0; + height: 44px; + width: 44px; + line-height: 44px; + border: 0; + display: inline-block; + background-color: transparent; + opacity: .5; + } + + #app-navigation .app-navigation-entry-deleted-button:hover { + opacity: 1; + } /** * App navigation utils, buttons and counters for drop down menu */ #app-navigation .app-navigation-entry-utils { - position: absolute; - top: 0; - right: 0; - z-index: 10; + position: absolute; + top: 0; + right: 0; + z-index: 10; } - #app-navigation .app-navigation-entry-utils ul { - display: block !important; - } - - - #app-navigation .app-navigation-entry-utils li { - float: left; - width: 44px !important; - height: 44px; - line-height: 44px; - } - - #app-navigation .active > .app-navigation-entry-utils li { - display: inline-block; - } - - #app-navigation .app-navigation-entry-utils button { - height: 38px; - width: 38px; - line-height: 38px; - float: left; - } - - #app-navigation .app-navigation-entry-utils-menu-button { - display: none; - } - #app-navigation .app-navigation-entry-utils-menu-button button { - border: 0; - opacity: .5; - background-color: transparent; - background-repeat: no-repeat; - background-position: center; - background-image: url('../img/7/more.svg'); - } - - #app-navigation .app-navigation-entry-utils-menu-button:hover button, - #app-navigation .app-navigation-entry-utils-menu-button:focus button { - background-color: transparent; - opacity: 1; - } - - #app-navigation .app-navigation-entry-utils-counter { - overflow: hidden; - text-overflow: hidden; - text-align: right; - font-size: 9pt; - width: 38px; - line-height: 44px; - padding: 0 10px; - } - - #app-navigation .app-navigation-entry-utils ul, - #app-navigation .app-navigation-entry-menu ul { - list-style-type: none; - } + #app-navigation .app-navigation-entry-utils ul { + display: block !important; + } + + + #app-navigation .app-navigation-entry-utils li { + float: left; + width: 44px !important; + height: 44px; + line-height: 44px; + } + + #app-navigation .active > .app-navigation-entry-utils li { + display: inline-block; + } + + #app-navigation .app-navigation-entry-utils button { + height: 38px; + width: 38px; + line-height: 38px; + float: left; + } + + #app-navigation .app-navigation-entry-utils-menu-button { + display: none; + } + #app-navigation .app-navigation-entry-utils-menu-button button { + border: 0; + opacity: .5; + background-color: transparent; + background-repeat: no-repeat; + background-position: center; + background-image: url('../img/7/more.svg'); + } + + #app-navigation .app-navigation-entry-utils-menu-button:hover button, + #app-navigation .app-navigation-entry-utils-menu-button:focus button { + background-color: transparent; + opacity: 1; + } + + #app-navigation .app-navigation-entry-utils-counter { + overflow: hidden; + text-overflow: hidden; + text-align: right; + font-size: 9pt; + width: 38px; + line-height: 44px; + padding: 0 10px; + } + + #app-navigation .app-navigation-entry-utils ul, + #app-navigation .app-navigation-entry-menu ul { + list-style-type: none; + } #app-navigation .app-navigation-entry-menu { - display: none; - position: absolute; - background-color: #eee; - color: #333; - border-radius: 3px; - border-top-right-radius: 0px; - z-index: 110; - margin: -5px 14px 5px 10px; - right: 0; - border: 1px solid #bbb; - -webkit-filter: drop-shadow(0 0 5px rgba(150, 150, 150, 0.75)); - -moz-filter: drop-shadow(0 0 5px rgba(150, 150, 150, 0.75)); - -ms-filter: drop-shadow(0 0 5px rgba(150, 150, 150, 0.75)); - -o-filter: drop-shadow(0 0 5px rgba(150, 150, 150, 0.75)); - filter: drop-shadow(0 0 5px rgba(150, 150, 150, 0.75)); + display: none; + position: absolute; + background-color: #eee; + color: #333; + border-radius: 3px; + border-top-right-radius: 0px; + z-index: 110; + margin: -5px 14px 5px 10px; + right: 0; + border: 1px solid #bbb; + -webkit-filter: drop-shadow(0 0 5px rgba(150, 150, 150, 0.75)); + -moz-filter: drop-shadow(0 0 5px rgba(150, 150, 150, 0.75)); + -ms-filter: drop-shadow(0 0 5px rgba(150, 150, 150, 0.75)); + -o-filter: drop-shadow(0 0 5px rgba(150, 150, 150, 0.75)); + filter: drop-shadow(0 0 5px rgba(150, 150, 150, 0.75)); } #app-navigation .app-navigation-entry-menu.open { - display: block; + display: block; } /* miraculous border arrow stuff */ #app-navigation .app-navigation-entry-menu:after, #app-navigation .app-navigation-entry-menu:before { - bottom: 100%; - right: 0; /* change this to adjust the arrow position */ - border: solid transparent; - content: " "; - height: 0; - width: 0; - position: absolute; - pointer-events: none; + bottom: 100%; + right: 0; /* change this to adjust the arrow position */ + border: solid transparent; + content: " "; + height: 0; + width: 0; + position: absolute; + pointer-events: none; } #app-navigation .app-navigation-entry-menu:after { - border-color: rgba(238, 238, 238, 0); - border-bottom-color: #eee; - border-width: 10px; - margin-left: -10px; + border-color: rgba(238, 238, 238, 0); + border-bottom-color: #eee; + border-width: 10px; + margin-left: -10px; } #app-navigation .app-navigation-entry-menu:before { - border-color: rgba(187, 187, 187, 0); - border-bottom-color: #bbb; - border-width: 11px; - margin-left: -11px; + border-color: rgba(187, 187, 187, 0); + border-bottom-color: #bbb; + border-width: 11px; + margin-left: -11px; } - /* list of options for an entry */ - #app-navigation .app-navigation-entry-menu ul { - display: block !important; - } - - #app-navigation .app-navigation-entry-menu li { - float: left; - width: 38px !important; - } - - #app-navigation .app-navigation-entry-menu li button { - float: right; - width: 36px !important; - height: 36px; - line-height: 36px; - border: 0; - opacity: .5; - background-color: transparent; - } - - #app-navigation .app-navigation-entry-menu li button:hover, - #app-navigation .app-navigation-entry-menu li button:focus { - opacity: 1; - background-color: transparent; - } + /* list of options for an entry */ + #app-navigation .app-navigation-entry-menu ul { + display: block !important; + } + + #app-navigation .app-navigation-entry-menu li { + float: left; + width: 38px !important; + } + + #app-navigation .app-navigation-entry-menu li button { + float: right; + width: 36px !important; + height: 36px; + line-height: 36px; + border: 0; + opacity: .5; + background-color: transparent; + } + + #app-navigation .app-navigation-entry-menu li button:hover, + #app-navigation .app-navigation-entry-menu li button:focus { + opacity: 1; + background-color: transparent; + } /* editing an entry */ #app-navigation .app-navigation-entry-edit { - padding-left: 5px; - padding-right: 5px; - display: inline-block; - height: 39px; - width: 100%; + padding-left: 5px; + padding-right: 5px; + display: inline-block; + height: 39px; + width: 100%; } - #app-navigation .app-navigation-entry-edit input { - border-bottom-right-radius: 0; - border-top-right-radius: 0; - width: 204px; /* fallback for IE8 */ - width: calc(100% - 36px); - padding: 5px; - margin-right: 0; - height: 38px; - float: left; - border: 1px solid rgba(190,190,190,.9); - } - - #app-navigation .app-navigation-entry-edit button, - #app-navigation .app-navigation-entry-edit input[type="submit"] { - width: 36px; - height: 38px; - float: left; - } - - #app-navigation .app-navigation-entry-edit .icon-checkmark { - border-bottom-left-radius: 0; - border-top-left-radius: 0; - border-left: 0; - margin-right: 0; - } + #app-navigation .app-navigation-entry-edit input { + border-bottom-right-radius: 0; + border-top-right-radius: 0; + width: 204px; /* fallback for IE8 */ + width: calc(100% - 36px); + padding: 5px; + margin-right: 0; + height: 38px; + float: left; + border: 1px solid rgba(190,190,190,.9); + } + + #app-navigation .app-navigation-entry-edit button, + #app-navigation .app-navigation-entry-edit input[type="submit"] { + width: 36px; + height: 38px; + float: left; + } + + #app-navigation .app-navigation-entry-edit .icon-checkmark { + border-bottom-left-radius: 0; + border-top-left-radius: 0; + border-left: 0; + margin-right: 0; + } #app-content { - z-index: 25; + z-index: 25; } #app-settings, #expanddiv { - z-index: 15; + z-index: 15; } diff --git a/css/mobile.css b/css/mobile.css index 68ab1e646..0434be329 100644 --- a/css/mobile.css +++ b/css/mobile.css @@ -15,15 +15,15 @@ } #app-content .heading h1 { - margin-right: 0; + margin-right: 0; } #app-content .utils { - padding-right: 15px; + padding-right: 15px; } #app-content .article { - padding-right: 15px; - padding-left: 44px; + padding-right: 15px; + padding-left: 44px; } } diff --git a/db/entityjsonserializer.php b/db/entityjsonserializer.php index 7e3357304..c0d946452 100644 --- a/db/entityjsonserializer.php +++ b/db/entityjsonserializer.php @@ -16,13 +16,13 @@ namespace OCA\News\Db; trait EntityJSONSerializer { - public function serializeFields($properties) { - $result = []; - foreach($properties as $property) { - $result[$property] = $this->$property; - } - return $result; - } + public function serializeFields($properties) { + $result = []; + foreach($properties as $property) { + $result[$property] = $this->$property; + } + return $result; + } }
\ No newline at end of file diff --git a/db/feed.php b/db/feed.php index c5b76656e..0f5a9ba47 100644 --- a/db/feed.php +++ b/db/feed.php @@ -43,94 +43,94 @@ use \OCP\AppFramework\Db\Entity; */ class Feed extends Entity implements IAPI, \JsonSerializable { - use EntityJSONSerializer; - - protected $userId; - protected $urlHash; - protected $url; - protected $title; - protected $faviconLink; - protected $added; - protected $folderId; - protected $unreadCount; - protected $link; - protected $preventUpdate; - protected $deletedAt; - protected $articlesPerUpdate; - - public function __construct(){ - $this->addType('parentId', 'integer'); - $this->addType('added', 'integer'); - $this->addType('folderId', 'integer'); - $this->addType('unreadCount', 'integer'); - $this->addType('preventUpdate', 'boolean'); - $this->addType('deletedAt', 'integer'); - $this->addType('articlesPerUpdate', 'integer'); - } - - - /** - * Turns entitie attributes into an array - */ - public function jsonSerialize() { - $serialized = $this->serializeFields([ - 'id', - 'userId', - 'urlHash', - 'url', - 'title', - 'faviconLink', - 'added', - 'folderId', - 'unreadCount', - 'link', - 'preventUpdate', - 'deletedAt', - 'articlesPerUpdate', - ]); - - $url = parse_url($this->link)['host']; - - // strip leading www. to avoid css class confusion - if (strpos($url, 'www.') === 0) { - $url = substr($url, 4); - } - - $serialized['cssClass'] = 'custom-' . str_replace('.', '-', $url); - - return $serialized; - } - - - public function toAPI() { - return $this->serializeFields([ - 'id', - 'url', - 'title', - 'faviconLink', - 'added', - 'folderId', - 'unreadCount', - 'link' - ]); - } - - - public function setUrl($url) { - $url = trim($url); - if(strpos($url, 'http') === 0) { - parent::setUrl($url); - $this->setUrlHash(md5($url)); - } - } - - - public function setLink($url) { - $url = trim($url); - if(strpos($url, 'http') === 0) { - parent::setLink($url); - } - } + use EntityJSONSerializer; + + protected $userId; + protected $urlHash; + protected $url; + protected $title; + protected $faviconLink; + protected $added; + protected $folderId; + protected $unreadCount; + protected $link; + protected $preventUpdate; + protected $deletedAt; + protected $articlesPerUpdate; + + public function __construct(){ + $this->addType('parentId', 'integer'); + $this->addType('added', 'integer'); + $this->addType('folderId', 'integer'); + $this->addType('unreadCount', 'integer'); + $this->addType('preventUpdate', 'boolean'); + $this->addType('deletedAt', 'integer'); + $this->addType('articlesPerUpdate', 'integer'); + } + + + /** + * Turns entitie attributes into an array + */ + public function jsonSerialize() { + $serialized = $this->serializeFields([ + 'id', + 'userId', + 'urlHash', + 'url', + 'title', + 'faviconLink', + 'added', + 'folderId', + 'unreadCount', + 'link', + 'preventUpdate', + 'deletedAt', + 'articlesPerUpdate', + ]); + + $url = parse_url($this->link)['host']; + + // strip leading www. to avoid css class confusion + if (strpos($url, 'www.') === 0) { + $url = substr($url, 4); + } + + $serialized['cssClass'] = 'custom-' . str_replace('.', '-', $url); + + return $serialized; + } + + + public function toAPI() { + return $this->serializeFields([ + 'id', + 'url', + 'title', + 'faviconLink', + 'added', + 'folderId', + 'unreadCount', + 'link' + ]); + } + + + public function setUrl($url) { + $url = trim($url); + if(strpos($url, 'http') === 0) { + parent::setUrl($url); + $this->setUrlHash(md5($url)); + } + } + + + public function setLink($url) { + $url = trim($url); + if(strpos($url, 'http') === 0) { + parent::setLink($url); + } + } }
\ No newline at end of file diff --git a/db/feedmapper.php b/db/feedmapper.php index b913288a6..ab55c6f1b 100644 --- a/db/feedmapper.php +++ b/db/feedmapper.php @@ -20,158 +20,158 @@ use \OCP\AppFramework\Db\Entity; class FeedMapper extends NewsMapper { - public function __construct(IDb $db) { - parent::__construct($db, 'news_feeds', '\OCA\News\Db\Feed'); - } - - - public function find($id, $userId){ - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - // WARNING: this is a desperate attempt at making this query work - // because prepared statements dont work. This is a possible - // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. - // think twice when changing this - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE `feeds`.`id` = ? ' . - 'AND `feeds`.`user_id` = ? ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - $params = [$id, $userId]; - - return $this->findEntity($sql, $params); - } - - - public function findAllFromUser($userId){ - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` '. - 'ON `feeds`.`folder_id` = `folders`.`id` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - // WARNING: this is a desperate attempt at making this query work - // because prepared statements dont work. This is a possible - // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. - // think twice when changing this - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE `feeds`.`user_id` = ? ' . - 'AND (`feeds`.`folder_id` = 0 ' . - 'OR `folders`.`deleted_at` = 0' . - ')' . - 'AND `feeds`.`deleted_at` = 0 ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - $params = [$userId]; - - return $this->findEntities($sql, $params); - } - - - public function findAll(){ - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` '. - 'ON `feeds`.`folder_id` = `folders`.`id` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - // WARNING: this is a desperate attempt at making this query work - // because prepared statements don't work. This is a possible - // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. - // think twice when changing this - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE (`feeds`.`folder_id` = 0 ' . - 'OR `folders`.`deleted_at` = 0' . - ')' . - 'AND `feeds`.`deleted_at` = 0 ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - - return $this->findEntities($sql); - } - - - public function findByUrlHash($hash, $userId){ - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - // WARNING: this is a desperate attempt at making this query work - // because prepared statements dont work. This is a possible - // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. - // think twice when changing this - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE `feeds`.`url_hash` = ? ' . - 'AND `feeds`.`user_id` = ? ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - $params = [$hash, $userId]; - - return $this->findEntity($sql, $params); - } - - - public function delete(Entity $entity){ - parent::delete($entity); - - // someone please slap me for doing this manually :P - // we needz CASCADE + FKs please - $sql = 'DELETE FROM `*PREFIX*news_items` WHERE `feed_id` = ?'; - $params = [$entity->getId()]; - $this->execute($sql, $params); - } - - - /** - * @param int $deleteOlderThan if given gets all entries with a delete date - * older than that timestamp - * @param string $userId if given returns only entries from the given user - * @return array with the database rows - */ - public function getToDelete($deleteOlderThan=null, $userId=null) { - $sql = 'SELECT * FROM `*PREFIX*news_feeds` ' . - 'WHERE `deleted_at` > 0 '; - $params = []; - - // sometimes we want to delete all entries - if ($deleteOlderThan !== null) { - $sql .= 'AND `deleted_at` < ? '; - $params[] = $deleteOlderThan; - } - - // we need to sometimes only delete feeds of a user - if($userId !== null) { - $sql .= 'AND `user_id` = ?'; - $params[] = $userId; - } - - return $this->findEntities($sql, $params); - } - - - /** - * Deletes all feeds of a user, delete items first since the user_id - * is not defined in there - * @param string $userId the name of the user - */ - public function deleteUser($userId) { - $sql = 'DELETE FROM `*PREFIX*news_feeds` WHERE `user_id` = ?'; - $this->execute($sql, [$userId]); - } + public function __construct(IDb $db) { + parent::__construct($db, 'news_feeds', '\OCA\News\Db\Feed'); + } + + + public function find($id, $userId){ + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + // WARNING: this is a desperate attempt at making this query work + // because prepared statements dont work. This is a possible + // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. + // think twice when changing this + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE `feeds`.`id` = ? ' . + 'AND `feeds`.`user_id` = ? ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + $params = [$id, $userId]; + + return $this->findEntity($sql, $params); + } + + + public function findAllFromUser($userId){ + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` '. + 'ON `feeds`.`folder_id` = `folders`.`id` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + // WARNING: this is a desperate attempt at making this query work + // because prepared statements dont work. This is a possible + // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. + // think twice when changing this + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE `feeds`.`user_id` = ? ' . + 'AND (`feeds`.`folder_id` = 0 ' . + 'OR `folders`.`deleted_at` = 0' . + ')' . + 'AND `feeds`.`deleted_at` = 0 ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + $params = [$userId]; + + return $this->findEntities($sql, $params); + } + + + public function findAll(){ + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` '. + 'ON `feeds`.`folder_id` = `folders`.`id` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + // WARNING: this is a desperate attempt at making this query work + // because prepared statements don't work. This is a possible + // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. + // think twice when changing this + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE (`feeds`.`folder_id` = 0 ' . + 'OR `folders`.`deleted_at` = 0' . + ')' . + 'AND `feeds`.`deleted_at` = 0 ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + + return $this->findEntities($sql); + } + + + public function findByUrlHash($hash, $userId){ + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + // WARNING: this is a desperate attempt at making this query work + // because prepared statements dont work. This is a possible + // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. + // think twice when changing this + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE `feeds`.`url_hash` = ? ' . + 'AND `feeds`.`user_id` = ? ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + $params = [$hash, $userId]; + + return $this->findEntity($sql, $params); + } + + + public function delete(Entity $entity){ + parent::delete($entity); + + // someone please slap me for doing this manually :P + // we needz CASCADE + FKs please + $sql = 'DELETE FROM `*PREFIX*news_items` WHERE `feed_id` = ?'; + $params = [$entity->getId()]; + $this->execute($sql, $params); + } + + + /** + * @param int $deleteOlderThan if given gets all entries with a delete date + * older than that timestamp + * @param string $userId if given returns only entries from the given user + * @return array with the database rows + */ + public function getToDelete($deleteOlderThan=null, $userId=null) { + $sql = 'SELECT * FROM `*PREFIX*news_feeds` ' . + 'WHERE `deleted_at` > 0 '; + $params = []; + + // sometimes we want to delete all entries + if ($deleteOlderThan !== null) { + $sql .= 'AND `deleted_at` < ? '; + $params[] = $deleteOlderThan; + } + + // we need to sometimes only delete feeds of a user + if($userId !== null) { + $sql .= 'AND `user_id` = ?'; + $params[] = $userId; + } + + return $this->findEntities($sql, $params); + } + + + /** + * Deletes all feeds of a user, delete items first since the user_id + * is not defined in there + * @param string $userId the name of the user + */ + public function deleteUser($userId) { + $sql = 'DELETE FROM `*PREFIX*news_feeds` WHERE `user_id` = ?'; + $this->execute($sql, [$userId]); + } } diff --git a/db/feedtype.php b/db/feedtype.php index 2539214ed..d43948a3c 100644 --- a/db/feedtype.php +++ b/db/feedtype.php @@ -15,9 +15,9 @@ namespace OCA\News\Db; class FeedType { - const FEED = 0; - const FOLDER = 1; - const STARRED = 2; - const SUBSCRIPTIONS = 3; - const SHARED = 4; + const FEED = 0; + const FOLDER = 1; + const STARRED = 2; + const SUBSCRIPTIONS = 3; + const SHARED = 4; };
\ No newline at end of file diff --git a/db/folder.php b/db/folder.php index d5f50685f..6d4af1aa3 100644 --- a/db/folder.php +++ b/db/folder.php @@ -31,38 +31,38 @@ use \OCP\AppFramework\Db\Entity; */ class Folder extends Entity implements IAPI, \JsonSerializable { - use EntityJSONSerializer; + use EntityJSONSerializer; - protected $parentId; - protected $name; - protected $userId; - protected $opened; - protected $deletedAt; + protected $parentId; + protected $name; + protected $userId; + protected $opened; + protected $deletedAt; - public function __construct(){ - $this->addType('parentId', 'integer'); - $this->addType('opened', 'boolean'); - $this->addType('deletedAt', 'integer'); - } + public function __construct(){ + $this->addType('parentId', 'integer'); + $this->addType('opened', 'boolean'); + $this->addType('deletedAt', 'integer'); + } - /** - * Turns entitie attributes into an array - */ - public function jsonSerialize() { - return $this->serializeFields([ - 'id', - 'parentId', - 'name', - 'userId', - 'opened', - 'deletedAt', - ]); - } + /** + * Turns entitie attributes into an array + */ + public function jsonSerialize() { + return $this->serializeFields([ + 'id', + 'parentId', + 'name', + 'userId', + 'opened', + 'deletedAt', + ]); + } - public function toAPI() { - return $this->serializeFields([ - 'id', - 'name' - ]); - } + public function toAPI() { + return $this->serializeFields([ + 'id', + 'name' + ]); + } }
\ No newline at end of file diff --git a/db/foldermapper.php b/db/foldermapper.php index 2c4d2aca5..bce599b45 100644 --- a/db/foldermapper.php +++ b/db/foldermapper.php @@ -18,90 +18,90 @@ use \OCP\AppFramework\Db\Entity; class FolderMapper extends NewsMapper { - public function __construct(IDb $db) { - parent::__construct($db, 'news_folders', '\OCA\News\Db\Folder'); - } - - public function find($id, $userId){ - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `id` = ? ' . - 'AND `user_id` = ?'; - - return $this->findEntity($sql, [$id, $userId]); - } - - - public function findAllFromUser($userId){ - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `user_id` = ? ' . - 'AND `deleted_at` = 0'; - $params = [$userId]; - - return $this->findEntities($sql, $params); - } - - - public function findByName($folderName, $userId){ - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `name` = ? ' . - 'AND `user_id` = ?'; - $params = [$folderName, $userId]; - - return $this->findEntities($sql, $params); - } - - - public function delete(Entity $entity){ - parent::delete($entity); - - // someone please slap me for doing this manually :P - // we needz CASCADE + FKs please - $sql = 'DELETE FROM `*PREFIX*news_feeds` WHERE `folder_id` = ?'; - $params = [$entity->getId()]; - $this->execute($sql, $params); - - $sql = 'DELETE FROM `*PREFIX*news_items` WHERE `feed_id` NOT IN '. - '(SELECT `feeds`.`id` FROM `*PREFIX*news_feeds` `feeds`)'; - - $this->execute($sql); - } - - - /** - * @param int $deleteOlderThan if given gets all entries with a delete date - * older than that timestamp - * @param string $userId if given returns only entries from the given user - * @return array with the database rows - */ - public function getToDelete($deleteOlderThan=null, $userId=null) { - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `deleted_at` > 0 '; - $params = []; - - // sometimes we want to delete all entries - if ($deleteOlderThan !== null) { - $sql .= 'AND `deleted_at` < ? '; - $params[] = $deleteOlderThan; - } - - // we need to sometimes only delete feeds of a user - if($userId !== null) { - $sql .= 'AND `user_id` = ?'; - $params[] = $userId; - } - - return $this->findEntities($sql, $params); - } - - - /** - * Deletes all folders of a user - * @param string $userId the name of the user - */ - public function deleteUser($userId) { - $sql = 'DELETE FROM `*PREFIX*news_folders` WHERE `user_id` = ?'; - $this->execute($sql, [$userId]); - } + public function __construct(IDb $db) { + parent::__construct($db, 'news_folders', '\OCA\News\Db\Folder'); + } + + public function find($id, $userId){ + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `id` = ? ' . + 'AND `user_id` = ?'; + + return $this->findEntity($sql, [$id, $userId]); + } + + + public function findAllFromUser($userId){ + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `user_id` = ? ' . + 'AND `deleted_at` = 0'; + $params = [$userId]; + + return $this->findEntities($sql, $params); + } + + + public function findByName($folderName, $userId){ + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `name` = ? ' . + 'AND `user_id` = ?'; + $params = [$folderName, $userId]; + + return $this->findEntities($sql, $params); + } + + + public function delete(Entity $entity){ + parent::delete($entity); + + // someone please slap me for doing this manually :P + // we needz CASCADE + FKs please + $sql = 'DELETE FROM `*PREFIX*news_feeds` WHERE `folder_id` = ?'; + $params = [$entity->getId()]; + $this->execute($sql, $params); + + $sql = 'DELETE FROM `*PREFIX*news_items` WHERE `feed_id` NOT IN '. + '(SELECT `feeds`.`id` FROM `*PREFIX*news_feeds` `feeds`)'; + + $this->execute($sql); + } + + + /** + * @param int $deleteOlderThan if given gets all entries with a delete date + * older than that timestamp + * @param string $userId if given returns only entries from the given user + * @return array with the database rows + */ + public function getToDelete($deleteOlderThan=null, $userId=null) { + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `deleted_at` > 0 '; + $params = []; + + // sometimes we want to delete all entries + if ($deleteOlderThan !== null) { + $sql .= 'AND `deleted_at` < ? '; + $params[] = $deleteOlderThan; + } + + // we need to sometimes only delete feeds of a user + if($userId !== null) { + $sql .= 'AND `user_id` = ?'; + $params[] = $userId; + } + + return $this->findEntities($sql, $params); + } + + + /** + * Deletes all folders of a user + * @param string $userId the name of the user + */ + public function deleteUser($userId) { + $sql = 'DELETE FROM `*PREFIX*news_folders` WHERE `user_id` = ?'; + $this->execute($sql, [$userId]); + } }
\ No newline at end of file diff --git a/db/iapi.php b/db/iapi.php index e5de5bd38..ff9791753 100644 --- a/db/iapi.php +++ b/db/iapi.php @@ -14,5 +14,5 @@ namespace OCA\News\Db; interface IAPI { - public function toAPI(); + public function toAPI(); } diff --git a/db/item.php b/db/item.php index a53c825ff..5c353b058 100644 --- a/db/item.php +++ b/db/item.php @@ -41,177 +41,177 @@ use \OCP\AppFramework\Db\Entity; */ class Item extends Entity implements IAPI, \JsonSerializable { - use EntityJSONSerializer; - - protected $guidHash; - protected $guid; - protected $url; - protected $title; - protected $author; - protected $pubDate; - protected $body; - protected $enclosureMime; - protected $enclosureLink; - protected $feedId; - protected $status = 0; - protected $lastModified; - - public function __construct(){ - $this->addType('pubDate', 'integer'); - $this->addType('feedId', 'integer'); - $this->addType('status', 'integer'); - $this->addType('lastModified', 'integer'); - } - - - public function setRead() { - $this->markFieldUpdated('status'); - $this->status &= ~StatusFlag::UNREAD; - } - - public function isRead() { - return !(($this->status & StatusFlag::UNREAD) === StatusFlag::UNREAD); - } - - public function setUnread() { - $this->markFieldUpdated('status'); - $this->status |= StatusFlag::UNREAD; - } - - public function isUnread() { - return !$this->isRead(); - } - - public function setStarred() { - $this->markFieldUpdated('status'); - $this->status |= StatusFlag::STARRED; - } - - public function isStarred() { - return ($this->status & StatusFlag::STARRED) === StatusFlag::STARRED; - } - - public function setUnstarred() { - $this->markFieldUpdated('status'); - $this->status &= ~StatusFlag::STARRED; - } - - public function isUnstarred() { - return !$this->isStarred(); - } - - /** - * Turns entitie attributes into an array - */ - public function jsonSerialize() { - return [ - 'id' => $this->getId(), - 'guid' => $this->getGuid(), - 'guidHash' => $this->getGuidHash(), - 'url' => $this->getUrl(), - 'title' => $this->getTitle(), - 'author' => $this->getAuthor(), - 'pubDate' => $this->getPubDate(), - 'body' => $this->getBody(), - 'enclosureMime' => $this->getEnclosureMime(), - 'enclosureLink' => $this->getEnclosureLink(), - 'feedId' => $this->getFeedId(), - 'unread' => $this->isUnread(), - 'starred' => $this->isStarred(), - 'lastModified' => $this->getLastModified() - ]; - } - - public function toAPI() { - return [ - 'id' => $this->getId(), - 'guid' => $this->getGuid(), - 'guidHash' => $this->getGuidHash(), - 'url' => $this->getUrl(), - 'title' => $this->getTitle(), - 'author' => $this->getAuthor(), - 'pubDate' => $this->getPubDate(), - 'body' => $this->getBody(), - 'enclosureMime' => $this->getEnclosureMime(), - 'enclosureLink' => $this->getEnclosureLink(), - 'feedId' => $this->getFeedId(), - 'unread' => $this->isUnread(), - 'starred' => $this->isStarred(), - 'lastModified' => $this->getLastModified() - ]; - } - - - public function toExport($feeds) { - return [ - 'guid' => $this->getGuid(), - 'url' => $this->getUrl(), - 'title' => $this->getTitle(), - 'author' => $this->getAuthor(), - 'pubDate' => $this->getPubDate(), - 'body' => $this->getBody(), - 'enclosureMime' => $this->getEnclosureMime(), - 'enclosureLink' => $this->getEnclosureLink(), - 'unread' => $this->isUnread(), - 'starred' => $this->isStarred(), - 'feedLink' => $feeds['feed'. $this->getFeedId()]->getLink() - ]; - } - - - public static function fromImport($import) { - $item = new static(); - $item->setGuid($import['guid']); - $item->setUrl($import['url']); - $item->setTitle($import['title']); - $item->setAuthor($import['author']); - $item->setPubDate($import['pubDate']); - $item->setBody($import['body']); - $item->setEnclosureMime($import['enclosureMime']); - $item->setEnclosureLink($import['enclosureLink']); - if($import['unread']) { - $item->setUnread(); - } else { - $item->setRead(); - } - if($import['starred']) { - $item->setStarred(); - } else { - $item->setUnstarred(); - } - - return $item; - } - - - public function setAuthor($name) { - parent::setAuthor(strip_tags($name)); - } - - - public function setTitle($title) { - parent::setTitle(strip_tags($title)); - } - - - public function setUrl($url) { - $url = trim($url); - if(strpos($url, 'http') === 0 || strpos($url, 'magnet') === 0) { - parent::setUrl($url); - } - } - - - public function setGuid($guid) { - parent::setGuid($guid); - $this->setGuidHash(md5($guid)); - } - - - public function setBody($body) { - // FIXME: this should not happen if the target="_blank" is already on the link - parent::setBody(str_replace('<a', '<a target="_blank"', $body)); - } + use EntityJSONSerializer; + + protected $guidHash; + protected $guid; + protected $url; + protected $title; + protected $author; + protected $pubDate; + protected $body; + protected $enclosureMime; + protected $enclosureLink; + protected $feedId; + protected $status = 0; + protected $lastModified; + + public function __construct(){ + $this->addType('pubDate', 'integer'); + $this->addType('feedId', 'integer'); + $this->addType('status', 'integer'); + $this->addType('lastModified', 'integer'); + } + + + public function setRead() { + $this->markFieldUpdated('status'); + $this->status &= ~StatusFlag::UNREAD; + } + + public function isRead() { + return !(($this->status & StatusFlag::UNREAD) === StatusFlag::UNREAD); + } + + public function setUnread() { + $this->markFieldUpdated('status'); + $this->status |= StatusFlag::UNREAD; + } + + public function isUnread() { + return !$this->isRead(); + } + + public function setStarred() { + $this->markFieldUpdated('status'); + $this->status |= StatusFlag::STARRED; + } + + public function isStarred() { + return ($this->status & StatusFlag::STARRED) === StatusFlag::STARRED; + } + + public function setUnstarred() { + $this->markFieldUpdated('status'); + $this->status &= ~StatusFlag::STARRED; + } + + public function isUnstarred() { + return !$this->isStarred(); + } + + /** + * Turns entitie attributes into an array + */ + public function jsonSerialize() { + return [ + 'id' => $this->getId(), + 'guid' => $this->getGuid(), + 'guidHash' => $this->getGuidHash(), + 'url' => $this->getUrl(), + 'title' => $this->getTitle(), + 'author' => $this->getAuthor(), + 'pubDate' => $this->getPubDate(), + 'body' => $this->getBody(), + 'enclosureMime' => $this->getEnclosureMime(), + 'enclosureLink' => $this->getEnclosureLink(), + 'feedId' => $this->getFeedId(), + 'unread' => $this->isUnread(), + 'starred' => $this->isStarred(), + 'lastModified' => $this->getLastModified() + ]; + } + + public function toAPI() { + return [ + 'id' => $this->getId(), + 'guid' => $this->getGuid(), + 'guidHash' => $this->getGuidHash(), + 'url' => $this->getUrl(), + 'title' => $this->getTitle(), + 'author' => $this->getAuthor(), + 'pubDate' => $this->getPubDate(), + 'body' => $this->getBody(), + 'enclosureMime' => $this->getEnclosureMime(), + 'enclosureLink' => $this->getEnclosureLink(), + 'feedId' => $this->getFeedId(), + 'unread' => $this->isUnread(), + 'starred' => $this->isStarred(), + 'lastModified' => $this->getLastModified() + ]; + } + + + public function toExport($feeds) { + return [ + 'guid' => $this->getGuid(), + 'url' => $this->getUrl(), + 'title' => $this->getTitle(), + 'author' => $this->getAuthor(), + 'pubDate' => $this->getPubDate(), + 'body' => $this->getBody(), + 'enclosureMime' => $this->getEnclosureMime(), + 'enclosureLink' => $this->getEnclosureLink(), + 'unread' => $this->isUnread(), + 'starred' => $this->isStarred(), + 'feedLink' => $feeds['feed'. $this->getFeedId()]->getLink() + ]; + } + + + public static function fromImport($import) { + $item = new static(); + $item->setGuid($import['guid']); + $item->setUrl($import['url']); + $item->setTitle($import['title']); + $item->setAuthor($import['author']); + $item->setPubDate($import['pubDate']); + $item->setBody($import['body']); + $item->setEnclosureMime($import['enclosureMime']); + $item->setEnclosureLink($import['enclosureLink']); + if($import['unread']) { + $item->setUnread(); + } else { + $item->setRead(); + } + if($import['starred']) { + $item->setStarred(); + } else { + $item->setUnstarred(); + } + + return $item; + } + + + public function setAuthor($name) { + parent::setAuthor(strip_tags($name)); + } + + + public function setTitle($title) { + parent::setTitle(strip_tags($title)); + } + + + public function setUrl($url) { + $url = trim($url); + if(strpos($url, 'http') === 0 || strpos($url, 'magnet') === 0) { + parent::setUrl($url); + } + } + + + public function setGuid($guid) { + parent::setGuid($guid); + $this->setGuidHash(md5($guid)); + } + + + public function setBody($body) { + // FIXME: this should not happen if the target="_blank" is already on the link + parent::setBody(str_replace('<a', '<a target="_blank"', $body)); + } } diff --git a/db/itemmapper.php b/db/itemmapper.php index 636df0667..5923372b9 100644 --- a/db/itemmapper.php +++ b/db/itemmapper.php @@ -18,275 +18,275 @@ use \OCP\IDb; class ItemMapper extends NewsMapper { - public function __construct(IDb $db){ - parent::__construct($db, 'news_items', '\OCA\News\Db\Item'); - } - - - private function makeSelectQuery($prependTo, $oldestFirst=false){ - if($oldestFirst) { - $ordering = 'ASC'; - } else { - $ordering = 'DESC'; - } - - return 'SELECT `items`.* FROM `*PREFIX*news_items` `items` '. - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` '. - 'AND `feeds`.`deleted_at` = 0 ' . - 'AND `feeds`.`user_id` = ? ' . - $prependTo . - 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` ' . - 'ON `folders`.`id` = `feeds`.`folder_id` ' . - 'WHERE `feeds`.`folder_id` = 0 ' . - 'OR `folders`.`deleted_at` = 0 ' . - 'ORDER BY `items`.`id` ' . $ordering; - } - - private function makeSelectQueryStatus($prependTo, $status, $oldestFirst=false) { - // Hi this is Ray and you're watching Jack Ass - // Now look closely: this is how we adults handle weird bugs in our - // code: we take them variables and we cast the shit out of them - $status = (int) $status; - - // now im gonna slowly stick them in the query, be careful! - return $this->makeSelectQuery( - - // WARNING: this is a desperate attempt at making this query work - // because prepared statements dont work. This is a possible - // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. - // think twice when changing this - 'AND ((`items`.`status` & ' . $status . ') = ' . $status . ') ' . - $prependTo, $oldestFirst - ); - } - - - public function find($id, $userId){ - $sql = $this->makeSelectQuery('AND `items`.`id` = ? '); - return $this->findEntity($sql, [$userId, $id]); - } - - - public function starredCount($userId){ - $sql = 'SELECT COUNT(*) AS size FROM `*PREFIX*news_items` `items` '. - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` '. - 'AND `feeds`.`deleted_at` = 0 ' . - 'AND `feeds`.`user_id` = ? ' . - 'AND ((`items`.`status` & ' . StatusFlag::STARRED . ') = ' . - StatusFlag::STARRED . ')' . - 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` ' . - 'ON `folders`.`id` = `feeds`.`folder_id` ' . - 'WHERE `feeds`.`folder_id` = 0 ' . - 'OR `folders`.`deleted_at` = 0'; - - $params = [$userId]; - - $result = $this->execute($sql, $params)->fetch(); - - return (int) $result['size']; - } - - - public function readAll($highestItemId, $time, $userId) { - $sql = 'UPDATE `*PREFIX*news_items` ' . - 'SET `status` = `status` & ? ' . - ', `last_modified` = ? ' . - 'WHERE `feed_id` IN (' . - 'SELECT `id` FROM `*PREFIX*news_feeds` ' . - 'WHERE `user_id` = ? ' . - ') '. - 'AND `id` <= ?'; - $params = [~StatusFlag::UNREAD, $time, $userId, $highestItemId]; - $this->execute($sql, $params); - } - - - public function readFolder($folderId, $highestItemId, $time, $userId) { - $sql = 'UPDATE `*PREFIX*news_items` ' . - 'SET `status` = `status` & ? ' . - ', `last_modified` = ? ' . - 'WHERE `feed_id` IN (' . - 'SELECT `id` FROM `*PREFIX*news_feeds` ' . - 'WHERE `folder_id` = ? ' . - 'AND `user_id` = ? ' . - ') '. - 'AND `id` <= ?'; - $params = [~StatusFlag::UNREAD, $time, $folderId, $userId, - $highestItemId]; - $this->execute($sql, $params); - } - - - public function readFeed($feedId, $highestItemId, $time, $userId){ - $sql = 'UPDATE `*PREFIX*news_items` ' . - 'SET `status` = `status` & ? ' . - ', `last_modified` = ? ' . - 'WHERE `feed_id` = ? ' . - 'AND `id` <= ? ' . - 'AND EXISTS (' . - 'SELECT * FROM `*PREFIX*news_feeds` ' . - 'WHERE `user_id` = ? ' . - 'AND `id` = ? ) '; - $params = [~StatusFlag::UNREAD, $time, $feedId, $highestItemId, - $userId, $feedId]; - - $this->execute($sql, $params); - } - - - private function getOperator($oldestFirst) { - if($oldestFirst) { - return '>'; - } else { - return '<'; - } - } - - - public function findAllNew($updatedSince, $status, $userId){ - $sql = $this->makeSelectQueryStatus( - 'AND `items`.`last_modified` >= ? ', $status); - $params = [$userId, $updatedSince]; - return $this->findEntities($sql, $params); - } - - - public function findAllNewFolder($id, $updatedSince, $status, $userId){ - $sql = 'AND `feeds`.`folder_id` = ? ' . - 'AND `items`.`last_modified` >= ? '; - $sql = $this->makeSelectQueryStatus($sql, $status); - $params = [$userId, $id, $updatedSince]; - return $this->findEntities($sql, $params); - } - - - public function findAllNewFeed($id, $updatedSince, $status, $userId){ - $sql = 'AND `items`.`feed_id` = ? ' . - 'AND `items`.`last_modified` >= ? '; - $sql = $this->makeSelectQueryStatus($sql, $status); - $params = [$userId, $id, $updatedSince]; - return $this->findEntities($sql, $params); - } - - - public function findAllFeed($id, $limit, $offset, $status, $oldestFirst, $userId){ - $params = [$userId, $id]; - $sql = 'AND `items`.`feed_id` = ? '; - if($offset !== 0){ - $sql .= 'AND `items`.`id` ' . $this->getOperator($oldestFirst) . ' ? '; - $params[] = $offset; - } - $sql = $this->makeSelectQueryStatus($sql, $status, $oldestFirst); - return $this->findEntities($sql, $params, $limit); - } - - - public function findAllFolder($id, $limit, $offset, $status, $oldestFirst, $userId){ - $params = [$userId, $id]; - $sql = 'AND `feeds`.`folder_id` = ? '; - if($offset !== 0){ - $sql .= 'AND `items`.`id` ' . $this->getOperator($oldestFirst) . ' ? '; - $params[] = $offset; - } - $sql = $this->makeSelectQueryStatus($sql, $status, $oldestFirst); - return $this->findEntities($sql, $params, $limit); - } - - - public function findAll($limit, $offset, $status, $oldestFirst, $userId){ - $params = [$userId]; - $sql = ''; - if($offset !== 0){ - $sql .= 'AND `items`.`id` ' . $this->getOperator($oldestFirst) . ' ? '; - $params[] = $offset; - } - $sql = $this->makeSelectQueryStatus($sql, $status, $oldestFirst); - return $this->findEntities($sql, $params, $limit); - } - - - public function findAllUnreadOrStarred($userId) { - $params = [$userId]; - $status = StatusFlag::UNREAD | StatusFlag::STARRED; - $sql = 'AND ((`items`.`status` & ' . $status . ') > 0) '; - $sql = $this->makeSelectQuery($sql); - return $this->findEntities($sql, $params); - } - - - public function findByGuidHash($guidHash, $feedId, $userId){ - $sql = $this->makeSelectQuery( - 'AND `items`.`guid_hash` = ? ' . - 'AND `feeds`.`id` = ? '); - - return $this->findEntity($sql, [$userId, $guidHash, $feedId]); - } - - - /** - * Delete all items for feeds that have over $threshold unread and not - * starred items - */ - public function deleteReadOlderThanThreshold($threshold){ - $status = StatusFlag::STARRED | StatusFlag::UNREAD; - $sql = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . - '`items`.`feed_id` AS `feed_id` ' . - 'FROM `*PREFIX*news_items` `items` ' . - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'WHERE NOT ((`items`.`status` & ?) > 0) ' . - 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . - 'HAVING COUNT(*) > ?'; - $params = [$status, $threshold]; - $result = $this->execute($sql, $params); - - while($row = $result->fetch()) { - - $size = (int) $row['size']; - $limit = $size - $threshold; - - if($limit > 0) { - $params = [$status, $row['feed_id']]; - - $sql = 'DELETE FROM `*PREFIX*news_items` ' . - 'WHERE NOT ((`status` & ?) > 0) ' . - 'AND `feed_id` = ? ' . - 'ORDER BY `id` ASC'; - - $this->execute($sql, $params, $limit); - } - } - } - - - public function getNewestItemId($userId) { - $sql = 'SELECT MAX(`items`.`id`) AS `max_id` FROM `*PREFIX*news_items` `items` '. - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` '. - 'AND `feeds`.`user_id` = ?'; - $params = [$userId]; - - $result = $this->findOneQuery($sql, $params); - - return (int) $result['max_id']; - } - - - /** - * Deletes all items of a user - * @param string $userId the name of the user - */ - public function deleteUser($userId) { - $sql = 'DELETE FROM `*PREFIX*news_items` ' . - 'WHERE `feed_id` IN (' . - 'SELECT `feeds`.`id` FROM `*PREFIX*news_feeds` `feeds` ' . - 'WHERE `feeds`.`user_id` = ?' . - ')'; - - $this->execute($sql, [$userId]); - } + public function __construct(IDb $db){ + parent::__construct($db, 'news_items', '\OCA\News\Db\Item'); + } + + + private function makeSelectQuery($prependTo, $oldestFirst=false){ + if($oldestFirst) { + $ordering = 'ASC'; + } else { + $ordering = 'DESC'; + } + + return 'SELECT `items`.* FROM `*PREFIX*news_items` `items` '. + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` '. + 'AND `feeds`.`deleted_at` = 0 ' . + 'AND `feeds`.`user_id` = ? ' . + $prependTo . + 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` ' . + 'ON `folders`.`id` = `feeds`.`folder_id` ' . + 'WHERE `feeds`.`folder_id` = 0 ' . + 'OR `folders`.`deleted_at` = 0 ' . + 'ORDER BY `items`.`id` ' . $ordering; + } + + private function makeSelectQueryStatus($prependTo, $status, $oldestFirst=false) { + // Hi this is Ray and you're watching Jack Ass + // Now look closely: this is how we adults handle weird bugs in our + // code: we take them variables and we cast the shit out of them + $status = (int) $status; + + // now im gonna slowly stick them in the query, be careful! + return $this->makeSelectQuery( + + // WARNING: this is a desperate attempt at making this query work + // because prepared statements dont work. This is a possible + // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. + // think twice when changing this + 'AND ((`items`.`status` & ' . $status . ') = ' . $status . ') ' . + $prependTo, $oldestFirst + ); + } + + + public function find($id, $userId){ + $sql = $this->makeSelectQuery('AND `items`.`id` = ? '); + return $this->findEntity($sql, [$userId, $id]); + } + + + public function starredCount($userId){ + $sql = 'SELECT COUNT(*) AS size FROM `*PREFIX*news_items` `items` '. + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` '. + 'AND `feeds`.`deleted_at` = 0 ' . + 'AND `feeds`.`user_id` = ? ' . + 'AND ((`items`.`status` & ' . StatusFlag::STARRED . ') = ' . + StatusFlag::STARRED . ')' . + 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` ' . + 'ON `folders`.`id` = `feeds`.`folder_id` ' . + 'WHERE `feeds`.`folder_id` = 0 ' . + 'OR `folders`.`deleted_at` = 0'; + + $params = [$userId]; + + $result = $this->execute($sql, $params)->fetch(); + + return (int) $result['size']; + } + + + public function readAll($highestItemId, $time, $userId) { + $sql = 'UPDATE `*PREFIX*news_items` ' . + 'SET `status` = `status` & ? ' . + ', `last_modified` = ? ' . + 'WHERE `feed_id` IN (' . + 'SELECT `id` FROM `*PREFIX*news_feeds` ' . + 'WHERE `user_id` = ? ' . + ') '. + 'AND `id` <= ?'; + $params = [~StatusFlag::UNREAD, $time, $userId, $highestItemId]; + $this->execute($sql, $params); + } + + + public function readFolder($folderId, $highestItemId, $time, $userId) { + $sql = 'UPDATE `*PREFIX*news_items` ' . + 'SET `status` = `status` & ? ' . + ', `last_modified` = ? ' . + 'WHERE `feed_id` IN (' . + 'SELECT `id` FROM `*PREFIX*news_feeds` ' . + 'WHERE `folder_id` = ? ' . + 'AND `user_id` = ? ' . + ') '. + 'AND `id` <= ?'; + $params = [~StatusFlag::UNREAD, $time, $folderId, $userId, + $highestItemId]; + $this->execute($sql, $params); + } + + + public function readFeed($feedId, $highestItemId, $time, $userId){ + $sql = 'UPDATE `*PREFIX*news_items` ' . + 'SET `status` = `status` & ? ' . + ', `last_modified` = ? ' . + 'WHERE `feed_id` = ? ' . + 'AND `id` <= ? ' . + 'AND EXISTS (' . + 'SELECT * FROM `*PREFIX*news_feeds` ' . + 'WHERE `user_id` = ? ' . + 'AND `id` = ? ) '; + $params = [~StatusFlag::UNREAD, $time, $feedId, $highestItemId, + $userId, $feedId]; + + $this->execute($sql, $params); + } + + + private function getOperator($oldestFirst) { + if($oldestFirst) { + return '>'; + } else { + return '<'; + } + } + + + public function findAllNew($updatedSince, $status, $userId){ + $sql = $this->makeSelectQueryStatus( + 'AND `items`.`last_modified` >= ? ', $status); + $params = [$userId, $updatedSince]; + return $this->findEntities($sql, $params); + } + + + public function findAllNewFolder($id, $updatedSince, $status, $userId){ + $sql = 'AND `feeds`.`folder_id` = ? ' . + 'AND `items`.`last_modified` >= ? '; + $sql = $this->makeSelectQueryStatus($sql, $status); + $params = [$userId, $id, $updatedSince]; + return $this->findEntities($sql, $params); + } + + + public function findAllNewFeed($id, $updatedSince, $status, $userId){ + $sql = 'AND `items`.`feed_id` = ? ' . + 'AND `items`.`last_modified` >= ? '; + $sql = $this->makeSelectQueryStatus($sql, $status); + $params = [$userId, $id, $updatedSince]; + return $this->findEntities($sql, $params); + } + + + public function findAllFeed($id, $limit, $offset, $status, $oldestFirst, $userId){ + $params = [$userId, $id]; + $sql = 'AND `items`.`feed_id` = ? '; + if($offset !== 0){ + $sql .= 'AND `items`.`id` ' . $this->getOperator($oldestFirst) . ' ? '; + $params[] = $offset; + } + $sql = $this->makeSelectQueryStatus($sql, $status, $oldestFirst); + return $this->findEntities($sql, $params, $limit); + } + + + public function findAllFolder($id, $limit, $offset, $status, $oldestFirst, $userId){ + $params = [$userId, $id]; + $sql = 'AND `feeds`.`folder_id` = ? '; + if($offset !== 0){ + $sql .= 'AND `items`.`id` ' . $this->getOperator($oldestFirst) . ' ? '; + $params[] = $offset; + } + $sql = $this->makeSelectQueryStatus($sql, $status, $oldestFirst); + return $this->findEntities($sql, $params, $limit); + } + + + public function findAll($limit, $offset, $status, $oldestFirst, $userId){ + $params = [$userId]; + $sql = ''; + if($offset !== 0){ + $sql .= 'AND `items`.`id` ' . $this->getOperator($oldestFirst) . ' ? '; + $params[] = $offset; + } + $sql = $this->makeSelectQueryStatus($sql, $status, $oldestFirst); + return $this->findEntities($sql, $params, $limit); + } + + + public function findAllUnreadOrStarred($userId) { + $params = [$userId]; + $status = StatusFlag::UNREAD | StatusFlag::STARRED; + $sql = 'AND ((`items`.`status` & ' . $status . ') > 0) '; + $sql = $this->makeSelectQuery($sql); + return $this->findEntities($sql, $params); + } + + + public function findByGuidHash($guidHash, $feedId, $userId){ + $sql = $this->makeSelectQuery( + 'AND `items`.`guid_hash` = ? ' . + 'AND `feeds`.`id` = ? '); + + return $this->findEntity($sql, [$userId, $guidHash, $feedId]); + } + + + /** + * Delete all items for feeds that have over $threshold unread and not + * starred items + */ + public function deleteReadOlderThanThreshold($threshold){ + $status = StatusFlag::STARRED | StatusFlag::UNREAD; + $sql = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . + '`items`.`feed_id` AS `feed_id` ' . + 'FROM `*PREFIX*news_items` `items` ' . + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'WHERE NOT ((`items`.`status` & ?) > 0) ' . + 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . + 'HAVING COUNT(*) > ?'; + $params = [$status, $threshold]; + $result = $this->execute($sql, $params); + + while($row = $result->fetch()) { + + $size = (int) $row['size']; + $limit = $size - $threshold; + + if($limit > 0) { + $params = [$status, $row['feed_id']]; + + $sql = 'DELETE FROM `*PREFIX*news_items` ' . + 'WHERE NOT ((`status` & ?) > 0) ' . + 'AND `feed_id` = ? ' . + 'ORDER BY `id` ASC'; + + $this->execute($sql, $params, $limit); + } + } + } + + + public function getNewestItemId($userId) { + $sql = 'SELECT MAX(`items`.`id`) AS `max_id` FROM `*PREFIX*news_items` `items` '. + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` '. + 'AND `feeds`.`user_id` = ?'; + $params = [$userId]; + + $result = $this->findOneQuery($sql, $params); + + return (int) $result['max_id']; + } + + + /** + * Deletes all items of a user + * @param string $userId the name of the user + */ + public function deleteUser($userId) { + $sql = 'DELETE FROM `*PREFIX*news_items` ' . + 'WHERE `feed_id` IN (' . + 'SELECT `feeds`.`id` FROM `*PREFIX*news_feeds` `feeds` ' . + 'WHERE `feeds`.`user_id` = ?' . + ')'; + + $this->execute($sql, [$userId]); + } } diff --git a/db/mapperfactory.php b/db/mapperfactory.php index 4af75cefa..6bc9346ca 100644 --- a/db/mapperfactory.php +++ b/db/mapperfactory.php @@ -18,23 +18,23 @@ use \OCA\News\Db\Postgres\ItemMapper as PostgresItemMapper; class MapperFactory { - private $dbType; - private $db; - - public function __construct($dbType, IDb $db) { - $this->dbType = $dbType; - $this->db = $db; - } - - - public function getItemMapper() { - switch($this->dbType) { - case 'pgsql': - return new PostgresItemMapper($this->db); - default: - return new ItemMapper($this->db); - } - } + private $dbType; + private $db; + + public function __construct($dbType, IDb $db) { + $this->dbType = $dbType; + $this->db = $db; + } + + + public function getItemMapper() { + switch($this->dbType) { + case 'pgsql': + return new PostgresItemMapper($this->db); + default: + return new ItemMapper($this->db); + } + } }
\ No newline at end of file diff --git a/db/newsmapper.php b/db/newsmapper.php index 955e3ba00..c483bd329 100644 --- a/db/newsmapper.php +++ b/db/newsmapper.php @@ -28,7 +28,7 @@ abstract class NewsMapper extends Mapper { * @param string $userId the id of the user * @return \OCP\AppFramework\Db\Entity */ - public abstract function find($id, $userId); + public abstract function find($id, $userId); }
\ No newline at end of file diff --git a/db/postgres/itemmapper.php b/db/postgres/itemmapper.php index 593a0719a..643055f1a 100644 --- a/db/postgres/itemmapper.php +++ b/db/postgres/itemmapper.php @@ -20,50 +20,50 @@ use \OCA\News\Db\StatusFlag; class ItemMapper extends \OCA\News\Db\ItemMapper { - public function __construct(IDb $db){ - parent::__construct($db); - } - - - /** - * Delete all items for feeds that have over $threshold unread and not - * starred items - */ - public function deleteReadOlderThanThreshold($threshold){ - $status = StatusFlag::STARRED | StatusFlag::UNREAD; - $sql = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . - '`items`.`feed_id` AS `feed_id` ' . - 'FROM `*PREFIX*news_items` `items` ' . - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'WHERE NOT ((`items`.`status` & ?) > 0) ' . - 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . - 'HAVING COUNT(*) > ?'; - $params = [$status, $threshold]; - $result = $this->execute($sql, $params); - - while($row = $result->fetch()) { - - $size = (int) $row['size']; - $limit = $size - $threshold; - - if($limit > 0) { - $params = [$status, $row['feed_id'], $limit]; - - $sql = 'DELETE FROM `*PREFIX*news_items` ' . - 'WHERE `id` IN (' . - 'SELECT `id` FROM `*PREFIX*news_items` ' . - 'WHERE NOT ((`status` & ?) > 0) ' . - 'AND `feed_id` = ? ' . - 'ORDER BY `id` ASC ' . - 'LIMIT ?' . - ')'; - - $this->execute($sql, $params); - } - } - - } + public function __construct(IDb $db){ + parent::__construct($db); + } + + + /** + * Delete all items for feeds that have over $threshold unread and not + * starred items + */ + public function deleteReadOlderThanThreshold($threshold){ + $status = StatusFlag::STARRED | StatusFlag::UNREAD; + $sql = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . + '`items`.`feed_id` AS `feed_id` ' . + 'FROM `*PREFIX*news_items` `items` ' . + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'WHERE NOT ((`items`.`status` & ?) > 0) ' . + 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . + 'HAVING COUNT(*) > ?'; + $params = [$status, $threshold]; + $result = $this->execute($sql, $params); + + while($row = $result->fetch()) { + + $size = (int) $row['size']; + $limit = $size - $threshold; + + if($limit > 0) { + $params = [$status, $row['feed_id'], $limit]; + + $sql = 'DELETE FROM `*PREFIX*news_items` ' . + 'WHERE `id` IN (' . + 'SELECT `id` FROM `*PREFIX*news_items` ' . + 'WHERE NOT ((`status` & ?) > 0) ' . + 'AND `feed_id` = ? ' . + 'ORDER BY `id` ASC ' . + 'LIMIT ?' . + ')'; + + $this->execute($sql, $params); + } + } + + } }
\ No newline at end of file diff --git a/db/statusflag.php b/db/statusflag.php index d24f81275..a3bfd4b18 100644 --- a/db/statusflag.php +++ b/db/statusflag.php @@ -14,30 +14,30 @@ namespace OCA\News\Db; class StatusFlag { - const UNREAD = 0x02; - const STARRED = 0x04; - const DELETED = 0x08; - const UPDATED = 0x16; - - - /** - * Get status for query - */ - public function typeToStatus($type, $showAll){ - if($type === FeedType::STARRED){ - return self::STARRED; - } else { - $status = 0; - } - - if($showAll){ - $status &= ~self::UNREAD; - } else { - $status |= self::UNREAD; - } - - return $status; - } + const UNREAD = 0x02; + const STARRED = 0x04; + const DELETED = 0x08; + const UPDATED = 0x16; + + + /** + * Get status for query + */ + public function typeToStatus($type, $showAll){ + if($type === FeedType::STARRED){ + return self::STARRED; + } else { + $status = 0; + } + + if($showAll){ + $status &= ~self::UNREAD; + } else { + $status |= self::UNREAD; + } + + return $status; + } }
\ No newline at end of file diff --git a/fetcher/feedfetcher.php b/fetcher/feedfetcher.php index c08bf4606..648cb90d8 100644 --- a/fetcher/feedfetcher.php +++ b/fetcher/feedfetcher.php @@ -23,198 +23,198 @@ use \OCA\News\Config\AppConfig; class FeedFetcher implements IFeedFetcher { - private $cacheDirectory; - private $cacheDuration; - private $faviconFetcher; - private $simplePieFactory; - private $fetchTimeout; - private $time; - private $proxyHost; - private $proxyPort; - private $proxyAuth; - private $appConfig; - - public function __construct(SimplePieAPIFactory $simplePieFactory, - FaviconFetcher $faviconFetcher, - $time, - $cacheDirectory, - Config $config, - AppConfig $appConfig){ - $this->cacheDirectory = $cacheDirectory; - $this->cacheDuration = $config->getSimplePieCacheDuration(); - $this->fetchTimeout = $config->getFeedFetcherTimeout(); - $this->faviconFetcher = $faviconFetcher; - $this->simplePieFactory = $simplePieFactory; - $this->time = $time; - $this->proxyHost = $config->getProxyHost(); - $this->proxyPort = $config->getProxyPort(); - $this->proxyAuth = $config->getProxyAuth(); - $this->appConfig = $appConfig; - } - - - /** - * This fetcher handles all the remaining urls therefore always returns true - */ - public function canHandle($url){ - return true; - } - - - /** - * Fetch a feed from remote - * @param string $url remote url of the feed - * @param boolean $getFavicon if the favicon should also be fetched, defaults - * to true - * @throws FetcherException if simple pie fails - * @return array an array containing the new feed and its items, first - * element being the Feed and second element being an array of Items - */ - public function fetch($url, $getFavicon=true) { - $simplePie = $this->simplePieFactory->getCore(); - $simplePie->set_feed_url($url); - $simplePie->enable_cache(true); - $simplePie->set_useragent('ownCloud News/' . - $this->appConfig->getConfig('version') . - ' (+https://owncloud.org/; 1 subscriber; feed-url=' . $url . ')'); - $simplePie->set_stupidly_fast(true); // disable simple pie sanitation - // we use htmlpurifier - $simplePie->set_timeout($this->fetchTimeout); - $simplePie->set_cache_location($this->cacheDirectory); - $simplePie->set_cache_duration($this->cacheDuration); - - if(trim($this->proxyHost) !== '') { - $simplePie->set_proxyhost($this->proxyHost); - $simplePie->set_proxyport($this->proxyPort); - $simplePie->set_proxyuserpwd($this->proxyAuth); - } - - try { - if (!$simplePie->init()) { - throw new \Exception('Could not initialize simple pie on feed with url ' . $url); - } - - // somehow $simplePie turns into a feed after init - $items = []; - $permaLink = $simplePie->get_permalink(); - if ($feedItems = $simplePie->get_items()) { - foreach($feedItems as $feedItem) { - array_push($items, $this->buildItem($feedItem, $permaLink)); - } - } - - $feed = $this->buildFeed($simplePie, $url, $getFavicon); - - return [$feed, $items]; - - } catch(\Exception $ex){ - throw new FetcherException($ex->getMessage()); - } - - } - - - private function decodeTwice($string) { - // behold! ' is not converted by PHP that's why we need to do it - // manually (TM) - return str_replace(''', '\'', - html_entity_decode( - html_entity_decode( - $string, ENT_QUOTES, 'UTF-8' - ), - ENT_QUOTES, 'UTF-8' - ) - ); - } - - - protected function buildItem($simplePieItem, $feedLink) { - $item = new Item(); - $item->setStatus(0); - $item->setUnread(); - $url = $this->decodeTwice($simplePieItem->get_permalink()); - if (!$url) { - $url = $feedLink; - } - $item->setUrl($url); - - // unescape content because angularjs helps against XSS - $item->setTitle($this->decodeTwice($simplePieItem->get_title())); - $guid = $simplePieItem->get_id(); - $item->setGuid($guid); - - // purification is done in the service layer - $item->setBody($simplePieItem->get_content()); - - // pubdate is not required. if not given use the current date - $date = $simplePieItem->get_date('U'); - if(!$date) { - $date = $this->time->getTime(); - } - - $item->setPubDate($date); - - $item->setLastModified($this->time->getTime()); - - $author = $simplePieItem->get_author(); - if ($author !== null) { - $name = $this->decodeTwice($author->get_name()); - if ($name) { - $item->setAuthor($name); - } else { - $item->setAuthor($this->decodeTwice($author->get_email())); - } - } - - // TODO: make it work for video files also - $enclosure = $simplePieItem->get_enclosure(); - if($enclosure !== null) { - $enclosureType = $enclosure->get_type(); - if(stripos($enclosureType, 'audio/') !== false || - stripos($enclosureType, 'video/') !== false) { - $item->setEnclosureMime($enclosureType); - $item->setEnclosureLink($enclosure->get_link()); - } - } - - return $item; - } - - - protected function buildFeed($simplePieFeed, $url, $getFavicon) { - $feed = new Feed(); - - // unescape content because angularjs helps against XSS - $title = strip_tags($this->decodeTwice($simplePieFeed->get_title())); - - // if there is no title use the url - if(!$title) { - $title = $url; - } - - $feed->setTitle($title); - $feed->setUrl($url); - - $link = $simplePieFeed->get_permalink(); - if (!$link) { - $link = $url; - } - $feed->setLink($link); - - $feed->setAdded($this->time->getTime()); - - if ($getFavicon) { - // use the favicon from the page first since most feeds use a weird image - $favicon = $this->faviconFetcher->fetch($feed->getLink()); - - if (!$favicon) { - $favicon = $simplePieFeed->get_image_url(); - } - - $feed->setFaviconLink($favicon); - } - - return $feed; - } + private $cacheDirectory; + private $cacheDuration; + private $faviconFetcher; + private $simplePieFactory; + private $fetchTimeout; + private $time; + private $proxyHost; + private $proxyPort; + private $proxyAuth; + private $appConfig; + + public function __construct(SimplePieAPIFactory $simplePieFactory, + FaviconFetcher $faviconFetcher, + $time, + $cacheDirectory, + Config $config, + AppConfig $appConfig){ + $this->cacheDirectory = $cacheDirectory; + $this->cacheDuration = $config->getSimplePieCacheDuration(); + $this->fetchTimeout = $config->getFeedFetcherTimeout(); + $this->faviconFetcher = $faviconFetcher; + $this->simplePieFactory = $simplePieFactory; + $this->time = $time; + $this->proxyHost = $config->getProxyHost(); + $this->proxyPort = $config->getProxyPort(); + $this->proxyAuth = $config->getProxyAuth(); + $this->appConfig = $appConfig; + } + + + /** + * This fetcher handles all the remaining urls therefore always returns true + */ + public function canHandle($url){ + return true; + } + + + /** + * Fetch a feed from remote + * @param string $url remote url of the feed + * @param boolean $getFavicon if the favicon should also be fetched, defaults + * to true + * @throws FetcherException if simple pie fails + * @return array an array containing the new feed and its items, first + * element being the Feed and second element being an array of Items + */ + public function fetch($url, $getFavicon=true) { + $simplePie = $this->simplePieFactory->getCore(); + $simplePie->set_feed_url($url); + $simplePie->enable_cache(true); + $simplePie->set_useragent('ownCloud News/' . + $this->appConfig->getConfig('version') . + ' (+https://owncloud.org/; 1 subscriber; feed-url=' . $url . ')'); + $simplePie->set_stupidly_fast(true); // disable simple pie sanitation + // we use htmlpurifier + $simplePie->set_timeout($this->fetchTimeout); + $simplePie->set_cache_location($this->cacheDirectory); + $simplePie->set_cache_duration($this->cacheDuration); + + if(trim($this->proxyHost) !== '') { + $simplePie->set_proxyhost($this->proxyHost); + $simplePie->set_proxyport($this->proxyPort); + $simplePie->set_proxyuserpwd($this->proxyAuth); + } + + try { + if (!$simplePie->init()) { + throw new \Exception('Could not initialize simple pie on feed with url ' . $url); + } + + // somehow $simplePie turns into a feed after init + $items = []; + $permaLink = $simplePie->get_permalink(); + if ($feedItems = $simplePie->get_items()) { + foreach($feedItems as $feedItem) { + array_push($items, $this->buildItem($feedItem, $permaLink)); + } + } + + $feed = $this->buildFeed($simplePie, $url, $getFavicon); + + return [$feed, $items]; + + } catch(\Exception $ex){ + throw new FetcherException($ex->getMessage()); + } + + } + + + private function decodeTwice($string) { + // behold! ' is not converted by PHP that's why we need to do it + // manually (TM) + return str_replace(''', '\'', + html_entity_decode( + html_entity_decode( + $string, ENT_QUOTES, 'UTF-8' + ), + ENT_QUOTES, 'UTF-8' + ) + ); + } + + + protected function buildItem($simplePieItem, $feedLink) { + $item = new Item(); + $item->setStatus(0); + $item->setUnread(); + $url = $this->decodeTwice($simplePieItem->get_permalink()); + if (!$url) { + $url = $feedLink; + } + $item->setUrl($url); + + // unescape content because angularjs helps against XSS + $item->setTitle($this->decodeTwice($simplePieItem->get_title())); + $guid = $simplePieItem->get_id(); + $item->setGuid($guid); + + // purification is done in the service layer + $item->setBody($simplePieItem->get_content()); + + // pubdate is not required. if not given use the current date + $date = $simplePieItem->get_date('U'); + if(!$date) { + $date = $this->time->getTime(); + } + + $item->setPubDate($date); + + $item->setLastModified($this->time->getTime()); + + $author = $simplePieItem->get_author(); + if ($author !== null) { + $name = $this->decodeTwice($author->get_name()); + if ($name) { + $item->setAuthor($name); + } else { + $item->setAuthor($this->decodeTwice($author->get_email())); + } + } + + // TODO: make it work for video files also + $enclosure = $simplePieItem->get_enclosure(); + if($enclosure !== null) { + $enclosureType = $enclosure->get_type(); + if(stripos($enclosureType, 'audio/') !== false || + stripos($enclosureType, 'video/') !== false) { + $item->setEnclosureMime($enclosureType); + $item->setEnclosureLink($enclosure->get_link()); + } + } + + return $item; + } + + + protected function buildFeed($simplePieFeed, $url, $getFavicon) { + $feed = new Feed(); + + // unescape content because angularjs helps against XSS + $title = strip_tags($this->decodeTwice($simplePieFeed->get_title())); + + // if there is no title use the url + if(!$title) { + $title = $url; + } + + $feed->setTitle($title); + $feed->setUrl($url); + + $link = $simplePieFeed->get_permalink(); + if (!$link) { + $link = $url; + } + $feed->setLink($link); + + $feed->setAdded($this->time->getTime()); + + if ($getFavicon) { + // use the favicon from the page first since most feeds use a weird image + $favicon = $this->faviconFetcher->fetch($feed->getLink()); + + if (!$favicon) { + $favicon = $simplePieFeed->get_image_url(); + } + + $feed->setFaviconLink($favicon); + } + + return $feed; + } } diff --git a/fetcher/fetcher.php b/fetcher/fetcher.php index fbdaaa6b8..4b4c09e1c 100644 --- a/fetcher/fetcher.php +++ b/fetcher/fetcher.php @@ -16,39 +16,39 @@ namespace OCA\News\Fetcher; class Fetcher { - private $fetchers; - - public function __construct(){ - $this->fetchers = []; - } - - - /** - * Add an additional fetcher - * @param IFeedFetcher $fetcher the fetcher - */ - public function registerFetcher(IFeedFetcher $fetcher){ - $this->fetchers[] = $fetcher; - } - - /** - * Fetch a feed from remote - * @param string $url remote url of the feed - * @param boolean $getFavicon if the favicon should also be fetched, defaults - * to true - * @throws FetcherException if simple pie fails - * @return array an array containing the new feed and its items, first - * element being the Feed and second element being an array of Items - */ - public function fetch($url, $getFavicon=true){ - foreach($this->fetchers as $fetcher){ - if($fetcher->canHandle($url)){ - return $fetcher->fetch($url, $getFavicon); - } - } - - return [null, []]; - } + private $fetchers; + + public function __construct(){ + $this->fetchers = []; + } + + + /** + * Add an additional fetcher + * @param IFeedFetcher $fetcher the fetcher + */ + public function registerFetcher(IFeedFetcher $fetcher){ + $this->fetchers[] = $fetcher; + } + + /** + * Fetch a feed from remote + * @param string $url remote url of the feed + * @param boolean $getFavicon if the favicon should also be fetched, defaults + * to true + * @throws FetcherException if simple pie fails + * @return array an array containing the new feed and its items, first + * element being the Feed and second element being an array of Items + */ + public function fetch($url, $getFavicon=true){ + foreach($this->fetchers as $fetcher){ + if($fetcher->canHandle($url)){ + return $fetcher->fetch($url, $getFavicon); + } + } + + return [null, []]; + } }
\ No newline at end of file diff --git a/fetcher/fetcherexception.php b/fetcher/fetcherexception.php index 24600bbef..27dd42f39 100644 --- a/fetcher/fetcherexception.php +++ b/fetcher/fetcherexception.php @@ -15,12 +15,12 @@ namespace OCA\News\Fetcher; class FetcherException extends \Exception { - /** - * Constructor - * @param string $msg the error message - */ - public function __construct($msg){ - parent::__construct($msg); - } + /** + * Constructor + * @param string $msg the error message + */ + public function __construct($msg){ + parent::__construct($msg); + } }
\ No newline at end of file diff --git a/fetcher/ifeedfetcher.php b/fetcher/ifeedfetcher.php index 10d0a9af6..8869d9292 100644 --- a/fetcher/ifeedfetcher.php +++ b/fetcher/ifeedfetcher.php @@ -15,21 +15,21 @@ namespace OCA\News\Fetcher; interface IFeedFetcher { - /** - * @param string $url remote url of the feed - * @param boolean $getFavicon if the favicon should also be fetched, defaults - * to true - * @throws FetcherException if the fetcher encounters a problem - * @return array an array containing the new feed and its items, first - * element being the Feed and second element being an array of Items - */ - function fetch($url, $getFavicon=true); + /** + * @param string $url remote url of the feed + * @param boolean $getFavicon if the favicon should also be fetched, defaults + * to true + * @throws FetcherException if the fetcher encounters a problem + * @return array an array containing the new feed and its items, first + * element being the Feed and second element being an array of Items + */ + function fetch($url, $getFavicon=true); - /** - * @param string $url the url that should be fetched - * @return boolean if the fetcher can handle the url. This fetcher will be - * used exclusively to fetch the feed and the items of the page - */ - function canHandle($url); + /** + * @param string $url the url that should be fetched + * @return boolean if the fetcher can handle the url. This fetcher will be + * used exclusively to fetch the feed and the items of the page + */ + function canHandle($url); }
\ No newline at end of file diff --git a/hooks/user.php b/hooks/user.php index 0502960ec..8ad12e880 100644 --- a/hooks/user.php +++ b/hooks/user.php @@ -21,7 +21,7 @@ class User { public static function deleteUser($params) { $userId = $params['uid']; - + $app = new Application(); $container = $app->getContainer(); diff --git a/http/textdownloadresponse.php b/http/textdownloadresponse.php index 7a9d59c7d..9a90e6454 100644 --- a/http/textdownloadresponse.php +++ b/http/textdownloadresponse.php @@ -21,28 +21,28 @@ use \OCP\AppFramework\Http\DownloadResponse; */ class TextDownloadResponse extends DownloadResponse { - private $content; - - /** - * Creates a response that prompts the user to download a file which - * contains the passed string - * @param string $content the content that should be written into the file - * @param string $filename the name that the downloaded file should have - * @param string $contentType the mimetype that the downloaded file should have - */ - public function __construct($content, $filename, $contentType){ - parent::__construct($filename, $contentType); - $this->content = $content; - } - - - /** - * Simply sets the headers and returns the file contents - * @return string the file contents - */ - public function render(){ - return $this->content; - } + private $content; + + /** + * Creates a response that prompts the user to download a file which + * contains the passed string + * @param string $content the content that should be written into the file + * @param string $filename the name that the downloaded file should have + * @param string $contentType the mimetype that the downloaded file should have + */ + public function __construct($content, $filename, $contentType){ + parent::__construct($filename, $contentType); + $this->content = $content; + } + + + /** + * Simply sets the headers and returns the file contents + * @return string the file contents + */ + public function render(){ + return $this->content; + } } diff --git a/http/textresponse.php b/http/textresponse.php index 8ea015329..7f1866ec4 100644 --- a/http/textresponse.php +++ b/http/textresponse.php @@ -20,27 +20,27 @@ use \OCP\AppFramework\Http\Response; */ class TextResponse extends Response { - private $content; - - /** - * Creates a response that just outputs text - * @param string $content the content that should be written into the file - * @param string $contentType the mimetype. text/ is added automatically so - * only plain or html can be added to get text/plain or text/html - */ - public function __construct($content, $contentType='plain'){ - $this->content = $content; - $this->addHeader('Content-type', 'text/' . $contentType); - } - - - /** - * Simply sets the headers and returns the file contents - * @return string the file contents - */ - public function render(){ - return $this->content; - } + private $content; + + /** + * Creates a response that just outputs text + * @param string $content the content that should be written into the file + * @param string $contentType the mimetype. text/ is added automatically so + * only plain or html can be added to get text/plain or text/html + */ + public function __construct($content, $contentType='plain'){ + $this->content = $content; + $this->addHeader('Content-type', 'text/' . $contentType); + } + + + /** + * Simply sets the headers and returns the file contents + * @return string the file contents + */ + public function render(){ + return $this->content; + } } diff --git a/js/bower.json b/js/bower.json index 131364cee..fab85ce2e 100644 --- a/js/bower.json +++ b/js/bower.json @@ -1,35 +1,35 @@ { - "name": "ownCloud-news", - "version": "3.4.6", - "homepage": "https://github.com/owncloud/news", - "authors": [ - "Bernhard Posselt <dev@bernhard-posselt.com>" - ], - "description": "An RSS/Atom feed reader", - "keywords": [ - "rss", - "atom", - "owncloud", - "feed", - "reader", - "app" - ], - "license": "AGPL", - "private": true, - "ignore": [ - "**/.*", - "node_modules", - "bower_components", - "test", - "tests" - ], - "dependencies": { - "angular": "~1.3.*", - "angular-route": "~1.3.*", - "angular-mocks": "~1.3.*", - "angular-sanitize": "~1.3.*", - "jquery": "~2.*", - "momentjs": "~2.8.*", - "es6-shim": "~0.18.*" - } + "name": "ownCloud-news", + "version": "3.4.6", + "homepage": "https://github.com/owncloud/news", + "authors": [ + "Bernhard Posselt <dev@bernhard-posselt.com>" + ], + "description": "An RSS/Atom feed reader", + "keywords": [ + "rss", + "atom", + "owncloud", + "feed", + "reader", + "app" + ], + "license": "AGPL", + "private": true, + "ignore": [ + "**/.*", + "node_modules", + "bower_components", + "test", + "tests" + ], + "dependencies": { + "angular": "~1.3.*", + "angular-route": "~1.3.*", + "angular-mocks": "~1.3.*", + "angular-sanitize": "~1.3.*", + "jquery": "~2.*", + "momentjs": "~2.8.*", + "es6-shim": "~0.18.*" + } } diff --git a/js/package.json b/js/package.json index 271e069c1..24e7c146a 100644 --- a/js/package.json +++ b/js/package.json @@ -1,49 +1,49 @@ { - "name": "ownCloud-news", - "version": "3.4.6", - "description": "An RSS/Atom feed reader", - "main": "build/app.js", - "scripts": { - "test": "grunt ci-unit" - }, - "repository": { - "type": "git", - "url": "https://github.com/owncloud/news" - }, - "keywords": [ - "rss", - "atom", - "feed", - "reader", - "owncloud", - "app" - ], - "author": "Bernhard Posselt", - "license": "AGPL", - "bugs": { - "url": "https://github.com/owncloud/news/issues" - }, - "homepage": "https://github.com/owncloud/news", - "devDependencies": { - "grunt": "^0.4.5", - "grunt-contrib-concat": "^0.5.0", - "grunt-contrib-connect": "^0.8.0", - "grunt-contrib-cssmin": "^0.10.0", - "grunt-contrib-jshint": "^0.10.0", - "grunt-contrib-uglify": "^0.6.0", - "grunt-contrib-watch": "^0.6.1", - "grunt-karma": "^0.9.0", - "grunt-ng-annotate": "^0.4.0", - "grunt-phpunit": "^0.3.5", - "grunt-protractor-runner": "^1.1.4", - "grunt-protractor-webdriver": "^0.1.9", - "grunt-wrap": "^0.3.0", - "karma": "^0.12.24", - "karma-chrome-launcher": "^0.1.5", - "karma-coverage": "^0.2.6", - "karma-firefox-launcher": "^0.1.3", - "karma-jasmine": "^0.1.5", - "karma-phantomjs-launcher": "^0.1.4" - }, - "dependencies": {} + "name": "ownCloud-news", + "version": "3.4.6", + "description": "An RSS/Atom feed reader", + "main": "build/app.js", + "scripts": { + "test": "grunt ci-unit" + }, + "repository": { + "type": "git", + "url": "https://github.com/owncloud/news" + }, + "keywords": [ + "rss", + "atom", + "feed", + "reader", + "owncloud", + "app" + ], + "author": "Bernhard Posselt", + "license": "AGPL", + "bugs": { + "url": "https://github.com/owncloud/news/issues" + }, + "homepage": "https://github.com/owncloud/news", + "devDependencies": { + "grunt": "^0.4.5", + "grunt-contrib-concat": "^0.5.0", + "grunt-contrib-connect": "^0.8.0", + "grunt-contrib-cssmin": "^0.10.0", + "grunt-contrib-jshint": "^0.10.0", + "grunt-contrib-uglify": "^0.6.0", + "grunt-contrib-watch": "^0.6.1", + "grunt-karma": "^0.9.0", + "grunt-ng-annotate": "^0.4.0", + "grunt-phpunit": "^0.3.5", + "grunt-protractor-runner": "^1.1.4", + "grunt-protractor-webdriver": "^0.1.9", + "grunt-wrap": "^0.3.0", + "karma": "^0.12.24", + "karma-chrome-launcher": "^0.1.5", + "karma-coverage": "^0.2.6", + "karma-firefox-launcher": "^0.1.3", + "karma-jasmine": "^0.1.5", + "karma-phantomjs-launcher": "^0.1.4" + }, + "dependencies": {} } diff --git a/service/feedservice.php b/service/feedservice.php index ce1c48af9..ca3335396 100644 --- a/service/feedservice.php +++ b/service/feedservice.php @@ -29,357 +29,357 @@ use \OCA\News\Config\Config; class FeedService extends Service { - private $feedFetcher; - private $itemMapper; - private $feedMapper; - private $logger; - private $l10n; - private $timeFactory; - private $autoPurgeMinimumInterval; - private $enhancer; - private $purifier; - private $loggerParams; - - public function __construct(FeedMapper $feedMapper, - Fetcher $feedFetcher, - ItemMapper $itemMapper, - ILogger $logger, - IL10N $l10n, - $timeFactory, - Config $config, - Enhancer $enhancer, - $purifier, - $loggerParams){ - parent::__construct($feedMapper); - $this->feedFetcher = $feedFetcher; - $this->itemMapper = $itemMapper; - $this->logger = $logger; - $this->l10n = $l10n; - $this->timeFactory = $timeFactory; - $this->autoPurgeMinimumInterval = $config->getAutoPurgeMinimumInterval(); - $this->enhancer = $enhancer; - $this->purifier = $purifier; - $this->feedMapper = $feedMapper; - $this->loggerParams = $loggerParams; - } - - /** - * Finds all feeds of a user - * @param string $userId the name of the user - * @return Feed[] - */ - public function findAll($userId){ - return $this->feedMapper->findAllFromUser($userId); - } - - - /** - * Finds all feeds from all users - * @return array of feeds - */ - public function findAllFromAllUsers() { - return $this->feedMapper->findAll(); - } - - - /** - * Creates a new feed - * @param string $feedUrl the url to the feed - * @param int $folderId the folder where it should be put into, 0 for root folder - * @param string $userId for which user the feed should be created - * @param string $title if given, this is used for the opml feed title - * @throws ServiceConflictException if the feed exists already - * @throws ServiceNotFoundException if the url points to an invalid feed - * @return Feed the newly created feed - */ - public function create($feedUrl, $folderId, $userId, $title=null){ - // first try if the feed exists already - try { - list($feed, $items) = $this->feedFetcher->fetch($feedUrl); - - // try again if feed exists depending on the reported link - try { - $this->feedMapper->findByUrlHash($feed->getUrlHash(), $userId); - throw new ServiceConflictException( - $this->l10n->t('Can not add feed: Exists already')); - - // If no matching feed was found everything was ok - } catch(DoesNotExistException $ex){} - - // insert feed - $feed->setFolderId($folderId); - $feed->setUserId($userId); - $feed->setArticlesPerUpdate(count($items)); - - if ($title) { - $feed->setTitle($title); - } - - $feed = $this->feedMapper->insert($feed); - - // insert items in reverse order because the first one is usually the - // newest item - $unreadCount = 0; - for($i=count($items)-1; $i>=0; $i--){ - $item = $items[$i]; - $item->setFeedId($feed->getId()); - - // check if item exists (guidhash is the same) - // and ignore it if it does - try { - $this->itemMapper->findByGuidHash( - $item->getGuidHash(), $item->getFeedId(), $userId); - continue; - } catch(DoesNotExistException $ex){ - $unreadCount += 1; - $item = $this->enhancer->enhance($item, $feed->getLink()); - $item->setBody($this->purifier->purify($item->getBody())); - $this->itemMapper->insert($item); - } - } - - // set unread count - $feed->setUnreadCount($unreadCount); - - return $feed; - } catch(FetcherException $ex){ - $this->logger->debug($ex->getMessage(), $this->loggerParams); - throw new ServiceNotFoundException( - $this->l10n->t( - 'Can not add feed: URL does not exist, SSL Certificate can not be validated ' . - 'or feed has invalid xml')); - } - } - - - /** - * Runs all the feed updates - */ - public function updateAll(){ - // TODO: this method is not covered by any tests - $feeds = $this->feedMapper->findAll(); - foreach($feeds as $feed){ - try { - $this->update($feed->getId(), $feed->getUserId()); - } catch(\Exception $ex){ - $this->logger->debug('Could not update feed ' . $ex->getMessage(), - $this->loggerParams); - } - } - } - - - /** - * Updates a single feed - * @param int $feedId the id of the feed that should be updated - * @param string $userId the id of the user - * @throws ServiceNotFoundException if the feed does not exist - * @return Feed the updated feed entity - */ - public function update($feedId, $userId){ - try { - $existingFeed = $this->feedMapper->find($feedId, $userId); - - if($existingFeed->getPreventUpdate() === true) { - return $existingFeed; - } - - try { - list(, $items) = $this->feedFetcher->fetch( - $existingFeed->getUrl(), false); - - // update number of articles on every feed update - if($existingFeed->getArticlesPerUpdate() !== count($items)) { - $existingFeed->setArticlesPerUpdate(count($items)); - $this->feedMapper->update($existingFeed); - } - - // insert items in reverse order because the first one is usually - // the newest item - for($i=count($items)-1; $i>=0; $i--){ - $item = $items[$i]; - $item->setFeedId($existingFeed->getId()); - - try { - $this->itemMapper->findByGuidHash($item->getGuidHash(), $feedId, $userId); - } catch(DoesNotExistException $ex){ - $item = $this->enhancer->enhance($item, - $existingFeed->getLink()); - $item->setBody($this->purifier->purify($item->getBody())); - $this->itemMapper->insert($item); - } - } - - } catch(FetcherException $ex){ - // failed updating is not really a problem, so only log it - - $this->logger->debug('Can not update feed with url ' . $existingFeed->getUrl() . - ': Not found or bad source', $this->loggerParams); - $this->logger->debug($ex->getMessage(), $this->loggerParams); - } - - return $this->feedMapper->find($feedId, $userId); - - } catch (DoesNotExistException $ex){ - throw new ServiceNotFoundException('Feed does not exist'); - } - - } - - - /** - * Moves a feed into a different folder - * @param int $feedId the id of the feed that should be moved - * @param int $folderId the id of the folder where the feed should be moved to - * @param string $userId the name of the user whose feed should be moved - * @throws ServiceNotFoundException if the feed does not exist - */ - public function move($feedId, $folderId, $userId){ - $feed = $this->find($feedId, $userId); - $feed->setFolderId($folderId); - $this->feedMapper->update($feed); - } - - - /** - * Rename a feed - * @param int $feedId the id of the feed that should be moved - * @param string $feedTitle the new title of the feed - * @param string $userId the name of the user whose feed should be renamed - * @throws ServiceNotFoundException if the feed does not exist - */ - public function rename($feedId, $feedTitle, $userId) { - $feed = $this->find($feedId, $userId); - $feed->setTitle($feedTitle); - $this->feedMapper->update($feed); - } - - - /** - * Import articles - * @param array $json the array with json - * @param string $userId the username - * @return Feed if one had to be created for nonexistent feeds - */ - public function importArticles($json, $userId) { - $url = 'http://owncloud/nofeed'; - $urlHash = md5($url); - - // build assoc array for fast access - $feeds = $this->findAll($userId); - $feedsDict = []; - foreach($feeds as $feed) { - $feedsDict[$feed->getLink()] = $feed; - } - - $createdFeed = false; - - // loop over all items and get the corresponding feed - // if the feed does not exist, create a separate feed for them - foreach ($json as $entry) { - $item = Item::fromImport($entry); - $item->setLastModified($this->timeFactory->getTime()); - $feedLink = $entry['feedLink']; // this is not set on the item yet - - if(array_key_exists($feedLink, $feedsDict)) { - $feed = $feedsDict[$feedLink]; - $item->setFeedId($feed->getId()); - } elseif(array_key_exists($url, $feedsDict)) { - $feed = $feedsDict[$url]; - $item->setFeedId($feed->getId()); - } else { - $createdFeed = true; - $feed = new Feed(); - $feed->setUserId($userId); - $feed->setLink($url); - $feed->setUrl($url); - $feed->setTitle($this->l10n->t('Articles without feed')); - $feed->setAdded($this->timeFactory->getTime()); - $feed->setFolderId(0); - $feed->setPreventUpdate(true); - $feed = $this->feedMapper->insert($feed); - - $item->setFeedId($feed->getId()); - $feedsDict[$feed->getLink()] = $feed; - } - - try { - // if item exists, copy the status - $existingItem = $this->itemMapper->findByGuidHash( - $item->getGuidHash(), $feed->getId(), $userId); - $existingItem->setStatus($item->getStatus()); - $this->itemMapper->update($existingItem); - } catch(DoesNotExistException $ex){ - $item->setBody($this->purifier->purify($item->getBody())); - $this->itemMapper->insert($item); - } - } - - if($createdFeed) { - return $this->feedMapper->findByUrlHash($urlHash, $userId); - } + private $feedFetcher; + private $itemMapper; + private $feedMapper; + private $logger; + private $l10n; + private $timeFactory; + private $autoPurgeMinimumInterval; + private $enhancer; + private $purifier; + private $loggerParams; + + public function __construct(FeedMapper $feedMapper, + Fetcher $feedFetcher, + ItemMapper $itemMapper, + ILogger $logger, + IL10N $l10n, + $timeFactory, + Config $config, + Enhancer $enhancer, + $purifier, + $loggerParams){ + parent::__construct($feedMapper); + $this->feedFetcher = $feedFetcher; + $this->itemMapper = $itemMapper; + $this->logger = $logger; + $this->l10n = $l10n; + $this->timeFactory = $timeFactory; + $this->autoPurgeMinimumInterval = $config->getAutoPurgeMinimumInterval(); + $this->enhancer = $enhancer; + $this->purifier = $purifier; + $this->feedMapper = $feedMapper; + $this->loggerParams = $loggerParams; + } + + /** + * Finds all feeds of a user + * @param string $userId the name of the user + * @return Feed[] + */ + public function findAll($userId){ + return $this->feedMapper->findAllFromUser($userId); + } + + + /** + * Finds all feeds from all users + * @return array of feeds + */ + public function findAllFromAllUsers() { + return $this->feedMapper->findAll(); + } + + + /** + * Creates a new feed + * @param string $feedUrl the url to the feed + * @param int $folderId the folder where it should be put into, 0 for root folder + * @param string $userId for which user the feed should be created + * @param string $title if given, this is used for the opml feed title + * @throws ServiceConflictException if the feed exists already + * @throws ServiceNotFoundException if the url points to an invalid feed + * @return Feed the newly created feed + */ + public function create($feedUrl, $folderId, $userId, $title=null){ + // first try if the feed exists already + try { + list($feed, $items) = $this->feedFetcher->fetch($feedUrl); + + // try again if feed exists depending on the reported link + try { + $this->feedMapper->findByUrlHash($feed->getUrlHash(), $userId); + throw new ServiceConflictException( + $this->l10n->t('Can not add feed: Exists already')); + + // If no matching feed was found everything was ok + } catch(DoesNotExistException $ex){} + + // insert feed + $feed->setFolderId($folderId); + $feed->setUserId($userId); + $feed->setArticlesPerUpdate(count($items)); + + if ($title) { + $feed->setTitle($title); + } + + $feed = $this->feedMapper->insert($feed); + + // insert items in reverse order because the first one is usually the + // newest item + $unreadCount = 0; + for($i=count($items)-1; $i>=0; $i--){ + $item = $items[$i]; + $item->setFeedId($feed->getId()); + + // check if item exists (guidhash is the same) + // and ignore it if it does + try { + $this->itemMapper->findByGuidHash( + $item->getGuidHash(), $item->getFeedId(), $userId); + continue; + } catch(DoesNotExistException $ex){ + $unreadCount += 1; + $item = $this->enhancer->enhance($item, $feed->getLink()); + $item->setBody($this->purifier->purify($item->getBody())); + $this->itemMapper->insert($item); + } + } + + // set unread count + $feed->setUnreadCount($unreadCount); + + return $feed; + } catch(FetcherException $ex){ + $this->logger->debug($ex->getMessage(), $this->loggerParams); + throw new ServiceNotFoundException( + $this->l10n->t( + 'Can not add feed: URL does not exist, SSL Certificate can not be validated ' . + 'or feed has invalid xml')); + } + } + + + /** + * Runs all the feed updates + */ + public function updateAll(){ + // TODO: this method is not covered by any tests + $feeds = $this->feedMapper->findAll(); + foreach($feeds as $feed){ + try { + $this->update($feed->getId(), $feed->getUserId()); + } catch(\Exception $ex){ + $this->logger->debug('Could not update feed ' . $ex->getMessage(), + $this->loggerParams); + } + } + } + + + /** + * Updates a single feed + * @param int $feedId the id of the feed that should be updated + * @param string $userId the id of the user + * @throws ServiceNotFoundException if the feed does not exist + * @return Feed the updated feed entity + */ + public function update($feedId, $userId){ + try { + $existingFeed = $this->feedMapper->find($feedId, $userId); + + if($existingFeed->getPreventUpdate() === true) { + return $existingFeed; + } + + try { + list(, $items) = $this->feedFetcher->fetch( + $existingFeed->getUrl(), false); + + // update number of articles on every feed update + if($existingFeed->getArticlesPerUpdate() !== count($items)) { + $existingFeed->setArticlesPerUpdate(count($items)); + $this->feedMapper->update($existingFeed); + } + + // insert items in reverse order because the first one is usually + // the newest item + for($i=count($items)-1; $i>=0; $i--){ + $item = $items[$i]; + $item->setFeedId($existingFeed->getId()); + + try { + $this->itemMapper->findByGuidHash($item->getGuidHash(), $feedId, $userId); + } catch(DoesNotExistException $ex){ + $item = $this->enhancer->enhance($item, + $existingFeed->getLink()); + $item->setBody($this->purifier->purify($item->getBody())); + $this->itemMapper->insert($item); + } + } + + } catch(FetcherException $ex){ + // failed updating is not really a problem, so only log it + + $this->logger->debug('Can not update feed with url ' . $existingFeed->getUrl() . + ': Not found or bad source', $this->loggerParams); + $this->logger->debug($ex->getMessage(), $this->loggerParams); + } + + return $this->feedMapper->find($feedId, $userId); + + } catch (DoesNotExistException $ex){ + throw new ServiceNotFoundException('Feed does not exist'); + } + + } + + + /** + * Moves a feed into a different folder + * @param int $feedId the id of the feed that should be moved + * @param int $folderId the id of the folder where the feed should be moved to + * @param string $userId the name of the user whose feed should be moved + * @throws ServiceNotFoundException if the feed does not exist + */ + public function move($feedId, $folderId, $userId){ + $feed = $this->find($feedId, $userId); + $feed->setFolderId($folderId); + $this->feedMapper->update($feed); + } + + + /** + * Rename a feed + * @param int $feedId the id of the feed that should be moved + * @param string $feedTitle the new title of the feed + * @param string $userId the name of the user whose feed should be renamed + * @throws ServiceNotFoundException if the feed does not exist + */ + public function rename($feedId, $feedTitle, $userId) { + $feed = $this->find($feedId, $userId); + $feed->setTitle($feedTitle); + $this->feedMapper->update($feed); + } + + + /** + * Import articles + * @param array $json the array with json + * @param string $userId the username + * @return Feed if one had to be created for nonexistent feeds + */ + public function importArticles($json, $userId) { + $url = 'http://owncloud/nofeed'; + $urlHash = md5($url); + + // build assoc array for fast access + $feeds = $this->findAll($userId); + $feedsDict = []; + foreach($feeds as $feed) { + $feedsDict[$feed->getLink()] = $feed; + } + + $createdFeed = false; + + // loop over all items and get the corresponding feed + // if the feed does not exist, create a separate feed for them + foreach ($json as $entry) { + $item = Item::fromImport($entry); + $item->setLastModified($this->timeFactory->getTime()); + $feedLink = $entry['feedLink']; // this is not set on the item yet + + if(array_key_exists($feedLink, $feedsDict)) { + $feed = $feedsDict[$feedLink]; + $item->setFeedId($feed->getId()); + } elseif(array_key_exists($url, $feedsDict)) { + $feed = $feedsDict[$url]; + $item->setFeedId($feed->getId()); + } else { + $createdFeed = true; + $feed = new Feed(); + $feed->setUserId($userId); + $feed->setLink($url); + $feed->setUrl($url); + $feed->setTitle($this->l10n->t('Articles without feed')); + $feed->setAdded($this->timeFactory->getTime()); + $feed->setFolderId(0); + $feed->setPreventUpdate(true); + $feed = $this->feedMapper->insert($feed); + + $item->setFeedId($feed->getId()); + $feedsDict[$feed->getLink()] = $feed; + } + + try { + // if item exists, copy the status + $existingItem = $this->itemMapper->findByGuidHash( + $item->getGuidHash(), $feed->getId(), $userId); + $existingItem->setStatus($item->getStatus()); + $this->itemMapper->update($existingItem); + } catch(DoesNotExistException $ex){ + $item->setBody($this->purifier->purify($item->getBody())); + $this->itemMapper->insert($item); + } + } + + if($createdFeed) { + return $this->feedMapper->findByUrlHash($urlHash, $userId); + } return null; - } - - - /** - * Use this to mark a feed as deleted. That way it can be un-deleted - * @param int $feedId the id of the feed that should be deleted - * @param string $userId the name of the user for security reasons - * @throws ServiceNotFoundException when feed does not exist - */ - public function markDeleted($feedId, $userId) { - $feed = $this->find($feedId, $userId); - $feed->setDeletedAt($this->timeFactory->getTime()); - $this->feedMapper->update($feed); - } - - - /** - * Use this to undo a feed deletion - * @param int $feedId the id of the feed that should be restored - * @param string $userId the name of the user for security reasons - * @throws ServiceNotFoundException when feed does not exist - */ - public function unmarkDeleted($feedId, $userId) { - $feed = $this->find($feedId, $userId); - $feed->setDeletedAt(0); - $this->feedMapper->update($feed); - } - - - /** - * Deletes all deleted feeds - * @param string $userId if given it purges only feeds of that user - * @param boolean $useInterval defaults to true, if true it only purges - * entries in a given interval to give the user a chance to undo the - * deletion - */ - public function purgeDeleted($userId=null, $useInterval=true) { - $deleteOlderThan = null; - - if ($useInterval) { - $now = $this->timeFactory->getTime(); - $deleteOlderThan = $now - $this->autoPurgeMinimumInterval; - } - - $toDelete = $this->feedMapper->getToDelete($deleteOlderThan, $userId); - - foreach ($toDelete as $feed) { - $this->feedMapper->delete($feed); - } - } - - - /** - * Deletes all feeds of a user, delete items first since the user_id - * is not defined in there - * @param string $userId the name of the user - */ - public function deleteUser($userId) { - $this->feedMapper->deleteUser($userId); - } + } + + + /** + * Use this to mark a feed as deleted. That way it can be un-deleted + * @param int $feedId the id of the feed that should be deleted + * @param string $userId the name of the user for security reasons + * @throws ServiceNotFoundException when feed does not exist + */ + public function markDeleted($feedId, $userId) { + $feed = $this->find($feedId, $userId); + $feed->setDeletedAt($this->timeFactory->getTime()); + $this->feedMapper->update($feed); + } + + + /** + * Use this to undo a feed deletion + * @param int $feedId the id of the feed that should be restored + * @param string $userId the name of the user for security reasons + * @throws ServiceNotFoundException when feed does not exist + */ + public function unmarkDeleted($feedId, $userId) { + $feed = $this->find($feedId, $userId); + $feed->setDeletedAt(0); + $this->feedMapper->update($feed); + } + + + /** + * Deletes all deleted feeds + * @param string $userId if given it purges only feeds of that user + * @param boolean $useInterval defaults to true, if true it only purges + * entries in a given interval to give the user a chance to undo the + * deletion + */ + public function purgeDeleted($userId=null, $useInterval=true) { + $deleteOlderThan = null; + + if ($useInterval) { + $now = $this->timeFactory->getTime(); + $deleteOlderThan = $now - $this->autoPurgeMinimumInterval; + } + + $toDelete = $this->feedMapper->getToDelete($deleteOlderThan, $userId); + + foreach ($toDelete as $feed) { + $this->feedMapper->delete($feed); + } + } + + + /** + * Deletes all feeds of a user, delete items first since the user_id + * is not defined in there + * @param string $userId the name of the user + */ + public function deleteUser($userId) { + $this->feedMapper->deleteUser($userId); + } } diff --git a/service/folderservice.php b/service/folderservice.php index 88cc8355e..eb1e584f5 100644 --- a/service/folderservice.php +++ b/service/folderservice.php @@ -22,152 +22,152 @@ use \OCA\News\Config\Config; class FolderService extends Service { - private $l10n; - private $timeFactory; - private $autoPurgeMinimumInterval; - private $folderMapper; - - public function __construct(FolderMapper $folderMapper, - IL10N $l10n, - $timeFactory, - Config $config){ - parent::__construct($folderMapper); - $this->l10n = $l10n; - $this->timeFactory = $timeFactory; - $this->autoPurgeMinimumInterval = $config->getAutoPurgeMinimumInterval(); - $this->folderMapper = $folderMapper; - } - - /** - * Returns all folders of a user - * @param string $userId the name of the user - * @return array of folders - */ - public function findAll($userId) { - return $this->folderMapper->findAllFromUser($userId); - } - - - private function validateFolder($folderName, $userId){ - $existingFolders = $this->folderMapper->findByName($folderName, $userId); - if(count($existingFolders) > 0){ - - throw new ServiceConflictException( - $this->l10n->t('Can not add folder: Exists already')); - } - - if(mb_strlen($folderName) === 0) { - throw new ServiceValidationException('Folder name can not be empty'); - } - } - - - /** - * Creates a new folder - * @param string $folderName the name of the folder - * @param string $userId the name of the user for whom it should be created - * @param int $parentId the parent folder id, deprecated we don't nest folders - * @throws ServiceConflictException if name exists already - * @throws ServiceValidationException if the folder has invalid parameters - * @return Folder the newly created folder - */ - public function create($folderName, $userId, $parentId=0) { - $this->validateFolder($folderName, $userId); - - $folder = new Folder(); - $folder->setName($folderName); - $folder->setUserId($userId); - $folder->setParentId($parentId); - $folder->setOpened(true); - return $this->folderMapper->insert($folder); - } - - - /** - * @throws ServiceException if the folder does not exist - */ - public function open($folderId, $opened, $userId){ - $folder = $this->find($folderId, $userId); - $folder->setOpened($opened); - $this->folderMapper->update($folder); - } - - - /** - * Renames a folder - * @param int $folderId the id of the folder that should be deleted - * @param string $folderName the new name of the folder - * @param string $userId the name of the user for security reasons - * @throws ServiceConflictException if name exists already - * @throws ServiceValidationException if the folder has invalid parameters - * @throws ServiceNotFoundException if the folder does not exist - * @return Folder the updated folder - */ - public function rename($folderId, $folderName, $userId){ - $this->validateFolder($folderName, $userId); - - $folder = $this->find($folderId, $userId); - $folder->setName($folderName); - return $this->folderMapper->update($folder); - } - - - /** - * Use this to mark a folder as deleted. That way it can be un-deleted - * @param int $folderId the id of the folder that should be deleted - * @param string $userId the name of the user for security reasons - * @throws ServiceNotFoundException when folder does not exist - */ - public function markDeleted($folderId, $userId) { - $folder = $this->find($folderId, $userId); - $folder->setDeletedAt($this->timeFactory->getTime()); - $this->folderMapper->update($folder); - } - - - /** - * Use this to restore a folder - * @param int $folderId the id of the folder that should be restored - * @param string $userId the name of the user for security reasons - * @throws ServiceNotFoundException when folder does not exist - */ - public function unmarkDeleted($folderId, $userId) { - $folder = $this->find($folderId, $userId); - $folder->setDeletedAt(0); - $this->folderMapper->update($folder); - } - - - /** - * Deletes all deleted folders - * @param string $userId if given it purges only folders of that user - * @param boolean $useInterval defaults to true, if true it only purges - * entries in a given interval to give the user a chance to undo the - * deletion - */ - public function purgeDeleted($userId=null, $useInterval=true) { - $deleteOlderThan = null; - - if ($useInterval) { - $now = $this->timeFactory->getTime(); - $deleteOlderThan = $now - $this->autoPurgeMinimumInterval; - } - - $toDelete = $this->folderMapper->getToDelete($deleteOlderThan, $userId); - - foreach ($toDelete as $folder) { - $this->folderMapper->delete($folder); - } - } - - - /** - * Deletes all folders of a user - * @param string $userId the name of the user - */ - public function deleteUser($userId) { - $this->folderMapper->deleteUser($userId); - } + private $l10n; + private $timeFactory; + private $autoPurgeMinimumInterval; + private $folderMapper; + + public function __construct(FolderMapper $folderMapper, + IL10N $l10n, + $timeFactory, + Config $config){ + parent::__construct($folderMapper); + $this->l10n = $l10n; + $this->timeFactory = $timeFactory; + $this->autoPurgeMinimumInterval = $config->getAutoPurgeMinimumInterval(); + $this->folderMapper = $folderMapper; + } + + /** + * Returns all folders of a user + * @param string $userId the name of the user + * @return array of folders + */ + public function findAll($userId) { + return $this->folderMapper->findAllFromUser($userId); + } + + + private function validateFolder($folderName, $userId){ + $existingFolders = $this->folderMapper->findByName($folderName, $userId); + if(count($existingFolders) > 0){ + + throw new ServiceConflictException( + $this->l10n->t('Can not add folder: Exists already')); + } + + if(mb_strlen($folderName) === 0) { + throw new ServiceValidationException('Folder name can not be empty'); + } + } + + + /** + * Creates a new folder + * @param string $folderName the name of the folder + * @param string $userId the name of the user for whom it should be created + * @param int $parentId the parent folder id, deprecated we don't nest folders + * @throws ServiceConflictException if name exists already + * @throws ServiceValidationException if the folder has invalid parameters + * @return Folder the newly created folder + */ + public function create($folderName, $userId, $parentId=0) { + $this->validateFolder($folderName, $userId); + + $folder = new Folder(); + $folder->setName($folderName); + $folder->setUserId($userId); + $folder->setParentId($parentId); + $folder->setOpened(true); + return $this->folderMapper->insert($folder); + } + + + /** + * @throws ServiceException if the folder does not exist + */ + public function open($folderId, $opened, $userId){ + $folder = $this->find($folderId, $userId); + $folder->setOpened($opened); + $this->folderMapper->update($folder); + } + + + /** + * Renames a folder + * @param int $folderId the id of the folder that should be deleted + * @param string $folderName the new name of the folder + * @param string $userId the name of the user for security reasons + * @throws ServiceConflictException if name exists already + * @throws ServiceValidationException if the folder has invalid parameters + * @throws ServiceNotFoundException if the folder does not exist + * @return Folder the updated folder + */ + public function rename($folderId, $folderName, $userId){ + $this->validateFolder($folderName, $userId); + + $folder = $this->find($folderId, $userId); + $folder->setName($folderName); + return $this->folderMapper->update($folder); + } + + + /** + * Use this to mark a folder as deleted. That way it can be un-deleted + * @param int $folderId the id of the folder that should be deleted + * @param string $userId the name of the user for security reasons + * @throws ServiceNotFoundException when folder does not exist + */ + public function markDeleted($folderId, $userId) { + $folder = $this->find($folderId, $userId); + $folder->setDeletedAt($this->timeFactory->getTime()); + $this->folderMapper->update($folder); + } + + + /** + * Use this to restore a folder + * @param int $folderId the id of the folder that should be restored + * @param string $userId the name of the user for security reasons + * @throws ServiceNotFoundException when folder does not exist + */ + public function unmarkDeleted($folderId, $userId) { + $folder = $this->find($folderId, $userId); + $folder->setDeletedAt(0); + $this->folderMapper->update($folder); + } + + + /** + * Deletes all deleted folders + * @param string $userId if given it purges only folders of that user + * @param boolean $useInterval defaults to true, if true it only purges + * entries in a given interval to give the user a chance to undo the + * deletion + */ + public function purgeDeleted($userId=null, $useInterval=true) { + $deleteOlderThan = null; + + if ($useInterval) { + $now = $this->timeFactory->getTime(); + $deleteOlderThan = $now - $this->autoPurgeMinimumInterval; + } + + $toDelete = $this->folderMapper->getToDelete($deleteOlderThan, $userId); + + foreach ($toDelete as $folder) { + $this->folderMapper->delete($folder); + } + } + + + /** + * Deletes all folders of a user + * @param string $userId the name of the user + */ + public function deleteUser($userId) { + $this->folderMapper->deleteUser($userId); + } } diff --git a/service/itemservice.php b/service/itemservice.php index 792fcc987..1b94c089f 100644 --- a/service/itemservice.php +++ b/service/itemservice.php @@ -23,219 +23,219 @@ use \OCA\News\Config\Config; class ItemService extends Service { - private $statusFlag; - private $autoPurgeCount; - private $timeFactory; - private $itemMapper; - - public function __construct(ItemMapper $itemMapper, - StatusFlag $statusFlag, - $timeFactory, - Config $config){ - parent::__construct($itemMapper); - $this->statusFlag = $statusFlag; - $this->autoPurgeCount = $config->getAutoPurgeCount(); - $this->timeFactory = $timeFactory; - $this->itemMapper = $itemMapper; - } - - - /** - * Returns all new items - * @param int $id the id of the feed, 0 for starred or all items - * @param int $type the type of the feed - * @param int $updatedSince a timestamp with the last modification date - * returns only items with a >= modified timestamp - * @param boolean $showAll if unread items should also be returned - * @param string $userId the name of the user - * @return array of items - */ - public function findAllNew($id, $type, $updatedSince, $showAll, $userId){ - $status = $this->statusFlag->typeToStatus($type, $showAll); - - switch($type){ - case FeedType::FEED: - return $this->itemMapper->findAllNewFeed( - $id, $updatedSince, $status, $userId - ); - case FeedType::FOLDER: - return $this->itemMapper->findAllNewFolder( - $id, $updatedSince, $status, $userId - ); - default: - return $this->itemMapper->findAllNew( - $updatedSince, $status, $userId - ); - } - } - - - /** - * Returns all items - * @param int $id the id of the feed, 0 for starred or all items - * @param int $type the type of the feed - * @param int $limit how many items should be returned - * @param int $offset the offset - * @param boolean $showAll if unread items should also be returned - * @param boolean $oldestFirst if it should be ordered by oldest first - * @param string $userId the name of the user - * @return array of items - */ - public function findAll($id, $type, $limit, $offset, $showAll, $oldestFirst, - $userId){ - $status = $this->statusFlag->typeToStatus($type, $showAll); - - switch($type){ - case FeedType::FEED: - return $this->itemMapper->findAllFeed( - $id, $limit, $offset, $status, $oldestFirst, $userId - ); - case FeedType::FOLDER: - return $this->itemMapper->findAllFolder( - $id, $limit, $offset, $status, $oldestFirst, $userId - ); - default: - return $this->itemMapper->findAll( - $limit, $offset, $status, $oldestFirst, $userId - ); - } - } - - - /** - * Star or unstar an item - * @param int $feedId the id of the item's feed that should be starred - * @param string $guidHash the guidHash of the item that should be starred - * @param boolean $isStarred if true the item will be marked as starred, if false unstar - * @param string $userId the name of the user for security reasons - * @throws ServiceNotFoundException if the item does not exist - */ - public function star($feedId, $guidHash, $isStarred, $userId){ - try { - $item = $this->itemMapper->findByGuidHash($guidHash, $feedId, $userId); - - $item->setLastModified($this->timeFactory->getTime()); - if($isStarred){ - $item->setStarred(); - } else { - $item->setUnstarred(); - } - $this->itemMapper->update($item); - } catch(DoesNotExistException $ex) { - throw new ServiceNotFoundException($ex->getMessage()); - } - } - - - /** - * Read or unread an item - * @param int $itemId the id of the item that should be read - * @param boolean $isRead if true the item will be marked as read, if false unread - * @param string $userId the name of the user for security reasons - * @throws ServiceNotFoundException if the item does not exist - */ - public function read($itemId, $isRead, $userId){ - $item = $this->find($itemId, $userId); - $item->setLastModified($this->timeFactory->getTime()); - if($isRead){ - $item->setRead(); - } else { - $item->setUnread(); - } - $this->itemMapper->update($item); - } - - - /** - * Set all items read - * @param int $highestItemId all items below that are marked read. This is used - * to prevent marking items as read that the users hasn't seen yet - * @param string $userId the name of the user - */ - public function readAll($highestItemId, $userId){ - $time = $this->timeFactory->getTime(); - $this->itemMapper->readAll($highestItemId, $time, $userId); - } - - - /** - * Set a folder read - * @param int $folderId the id of the folder that should be marked read - * @param int $highestItemId all items below that are marked read. This is used - * to prevent marking items as read that the users hasn't seen yet - * @param string $userId the name of the user - */ - public function readFolder($folderId, $highestItemId, $userId){ - $time = $this->timeFactory->getTime(); - $this->itemMapper->readFolder($folderId, $highestItemId, $time, $userId); - } - - - /** - * Set a feed read - * @param int $feedId the id of the feed that should be marked read - * @param int $highestItemId all items below that are marked read. This is used - * to prevent marking items as read that the users hasn't seen yet - * @param string $userId the name of the user - */ - public function readFeed($feedId, $highestItemId, $userId){ - $time = $this->timeFactory->getTime(); - $this->itemMapper->readFeed($feedId, $highestItemId, $time, $userId); - } - - - /** - * This method deletes all unread feeds that are not starred and over the - * count of $this->autoPurgeCount starting by the oldest. This is to clean - * up the database so that old entries don't spam your db. As criteria for - * old, the id is taken - */ - public function autoPurgeOld(){ - $this->itemMapper->deleteReadOlderThanThreshold($this->autoPurgeCount); - } - - - /** - * Returns the newest item id, use this for marking feeds read - * @param string $userId the name of the user - * @throws ServiceNotFoundException if there is no newest item - * @return int - */ - public function getNewestItemId($userId) { - try { - return $this->itemMapper->getNewestItemId($userId); - } catch(DoesNotExistException $ex) { - throw new ServiceNotFoundException($ex->getMessage()); - } - } - - - /** - * Returns the starred count - * @param string $userId the name of the user - * @return int the count - */ - public function starredCount($userId){ - return $this->itemMapper->starredCount($userId); - } - - - /** - * @param string $userId from which user the items should be taken - * @return array of items which are starred or unread - */ - public function getUnreadOrStarred($userId) { - return $this->itemMapper->findAllUnreadOrStarred($userId); - } - - - /** - * Deletes all items of a user - * @param string $userId the name of the user - */ - public function deleteUser($userId) { - $this->itemMapper->deleteUser($userId); - } + private $statusFlag; + private $autoPurgeCount; + private $timeFactory; + private $itemMapper; + + public function __construct(ItemMapper $itemMapper, + StatusFlag $statusFlag, + $timeFactory, + Config $config){ + parent::__construct($itemMapper); + $this->statusFlag = $statusFlag; + $this->autoPurgeCount = $config->getAutoPurgeCount(); + $this->timeFactory = $timeFactory; + $this->itemMapper = $itemMapper; + } + + + /** + * Returns all new items + * @param int $id the id of the feed, 0 for starred or all items + * @param int $type the type of the feed + * @param int $updatedSince a timestamp with the last modification date + * returns only items with a >= modified timestamp + * @param boolean $showAll if unread items should also be returned + * @param string $userId the name of the user + * @return array of items + */ + public function findAllNew($id, $type, $updatedSince, $showAll, $userId){ + $status = $this->statusFlag->typeToStatus($type, $showAll); + + switch($type){ + case FeedType::FEED: + return $this->itemMapper->findAllNewFeed( + $id, $updatedSince, $status, $userId + ); + case FeedType::FOLDER: + return $this->itemMapper->findAllNewFolder( + $id, $updatedSince, $status, $userId + ); + default: + return $this->itemMapper->findAllNew( + $updatedSince, $status, $userId + ); + } + } + + + /** + * Returns all items + * @param int $id the id of the feed, 0 for starred or all items + * @param int $type the type of the feed + * @param int $limit how many items should be returned + * @param int $offset the offset + * @param boolean $showAll if unread items should also be returned + * @param boolean $oldestFirst if it should be ordered by oldest first + * @param string $userId the name of the user + * @return array of items + */ + public function findAll($id, $type, $limit, $offset, $showAll, $oldestFirst, + $userId){ + $status = $this->statusFlag->typeToStatus($type, $showAll); + + switch($type){ + case FeedType::FEED: + return $this->itemMapper->findAllFeed( + $id, $limit, $offset, $status, $oldestFirst, $userId + ); + case FeedType::FOLDER: + return $this->itemMapper->findAllFolder( + $id, $limit, $offset, $status, $oldestFirst, $userId + ); + default: + return $this->itemMapper->findAll( + $limit, $offset, $status, $oldestFirst, $userId + ); + } + } + + + /** + * Star or unstar an item + * @param int $feedId the id of the item's feed that should be starred + * @param string $guidHash the guidHash of the item that should be starred + * @param boolean $isStarred if true the item will be marked as starred, if false unstar + * @param string $userId the name of the user for security reasons + * @throws ServiceNotFoundException if the item does not exist + */ + public function star($feedId, $guidHash, $isStarred, $userId){ + try { + $item = $this->itemMapper->findByGuidHash($guidHash, $feedId, $userId); + + $item->setLastModified($this->timeFactory->getTime()); + if($isStarred){ + $item->setStarred(); + } else { + $item->setUnstarred(); + } + $this->itemMapper->update($item); + } catch(DoesNotExistException $ex) { + throw new ServiceNotFoundException($ex->getMessage()); + } + } + + + /** + * Read or unread an item + * @param int $itemId the id of the item that should be read + * @param boolean $isRead if true the item will be marked as read, if false unread + * @param string $userId the name of the user for security reasons + * @throws ServiceNotFoundException if the item does not exist + */ + public function read($itemId, $isRead, $userId){ + $item = $this->find($itemId, $userId); + $item->setLastModified($this->timeFactory->getTime()); + if($isRead){ + $item->setRead(); + } else { + $item->setUnread(); + } + $this->itemMapper->update($item); + } + + + /** + * Set all items read + * @param int $highestItemId all items below that are marked read. This is used + * to prevent marking items as read that the users hasn't seen yet + * @param string $userId the name of the user + */ + public function readAll($highestItemId, $userId){ + $time = $this->timeFactory->getTime(); + $this->itemMapper->readAll($highestItemId, $time, $userId); + } + + + /** + * Set a folder read + * @param int $folderId the id of the folder that should be marked read + * @param int $highestItemId all items below that are marked read. This is used + * to prevent marking items as read that the users hasn't seen yet + * @param string $userId the name of the user + */ + public function readFolder($folderId, $highestItemId, $userId){ + $time = $this->timeFactory->getTime(); + $this->itemMapper->readFolder($folderId, $highestItemId, $time, $userId); + } + + + /** + * Set a feed read + * @param int $feedId the id of the feed that should be marked read + * @param int $highestItemId all items below that are marked read. This is used + * to prevent marking items as read that the users hasn't seen yet + * @param string $userId the name of the user + */ + public function readFeed($feedId, $highestItemId, $userId){ + $time = $this->timeFactory->getTime(); + $this->itemMapper->readFeed($feedId, $highestItemId, $time, $userId); + } + + + /** + * This method deletes all unread feeds that are not starred and over the + * count of $this->autoPurgeCount starting by the oldest. This is to clean + * up the database so that old entries don't spam your db. As criteria for + * old, the id is taken + */ + public function autoPurgeOld(){ + $this->itemMapper->deleteReadOlderThanThreshold($this->autoPurgeCount); + } + + + /** + * Returns the newest item id, use this for marking feeds read + * @param string $userId the name of the user + * @throws ServiceNotFoundException if there is no newest item + * @return int + */ + public function getNewestItemId($userId) { + try { + return $this->itemMapper->getNewestItemId($userId); + } catch(DoesNotExistException $ex) { + throw new ServiceNotFoundException($ex->getMessage()); + } + } + + + /** + * Returns the starred count + * @param string $userId the name of the user + * @return int the count + */ + public function starredCount($userId){ + return $this->itemMapper->starredCount($userId); + } + + + /** + * @param string $userId from which user the items should be taken + * @return array of items which are starred or unread + */ + public function getUnreadOrStarred($userId) { + return $this->itemMapper->findAllUnreadOrStarred($userId); + } + + + /** + * Deletes all items of a user + * @param string $userId the name of the user + */ + public function deleteUser($userId) { + $this->itemMapper->deleteUser($userId); + } } diff --git a/service/service.php b/service/service.php index f3700de98..e53468828 100644 --- a/service/service.php +++ b/service/service.php @@ -21,42 +21,42 @@ use \OCA\News\Db\NewsMapper; abstract class Service { - protected $mapper; - - public function __construct(NewsMapper $mapper){ - $this->mapper = $mapper; - } - - - /** - * Delete an entity - * @param int $id the id of the entity - * @param string $userId the name of the user for security reasons - * @throws ServiceNotFoundException if the entity does not exist, or there - * are more than one of it - */ - public function delete($id, $userId){ - $entity = $this->find($id, $userId); - $this->mapper->delete($entity); - } - - - /** - * Finds an entity by id - * @param int $id the id of the entity - * @param string $userId the name of the user for security reasons - * @throws ServiceNotFoundException if the entity does not exist, or there - * are more than one of it - * @return \OCP\AppFramework\Db\Entity the entity - */ - public function find($id, $userId){ - try { - return $this->mapper->find($id, $userId); - } catch(DoesNotExistException $ex){ - throw new ServiceNotFoundException($ex->getMessage()); - } catch(MultipleObjectsReturnedException $ex){ - throw new ServiceNotFoundException($ex->getMessage()); - } - } + protected $mapper; + + public function __construct(NewsMapper $mapper){ + $this->mapper = $mapper; + } + + + /** + * Delete an entity + * @param int $id the id of the entity + * @param string $userId the name of the user for security reasons + * @throws ServiceNotFoundException if the entity does not exist, or there + * are more than one of it + */ + public function delete($id, $userId){ + $entity = $this->find($id, $userId); + $this->mapper->delete($entity); + } + + + /** + * Finds an entity by id + * @param int $id the id of the entity + * @param string $userId the name of the user for security reasons + * @throws ServiceNotFoundException if the entity does not exist, or there + * are more than one of it + * @return \OCP\AppFramework\Db\Entity the entity + */ + public function find($id, $userId){ + try { + return $this->mapper->find($id, $userId); + } catch(DoesNotExistException $ex){ + throw new ServiceNotFoundException($ex->getMessage()); + } catch(MultipleObjectsReturnedException $ex){ + throw new ServiceNotFoundException($ex->getMessage()); + } + } } diff --git a/service/serviceconflictexception.php b/service/serviceconflictexception.php index edcd0fd89..d27fb98c1 100644 --- a/service/serviceconflictexception.php +++ b/service/serviceconflictexception.php @@ -16,12 +16,12 @@ namespace OCA\News\Service; class ServiceConflictException extends ServiceException { - /** - * Constructor - * @param string $msg the error message - */ - public function __construct($msg){ - parent::__construct($msg); - } + /** + * Constructor + * @param string $msg the error message + */ + public function __construct($msg){ + parent::__construct($msg); + } }
\ No newline at end of file diff --git a/service/serviceexception.php b/service/serviceexception.php index 401b3db09..1a789e0b0 100644 --- a/service/serviceexception.php +++ b/service/serviceexception.php @@ -16,12 +16,12 @@ namespace OCA\News\Service; class ServiceException extends \Exception { - /** - * Constructor - * @param string $msg the error message - */ - public function __construct($msg){ - parent::__construct($msg); - } + /** + * Constructor + * @param string $msg the error message + */ + public function __construct($msg){ + parent::__construct($msg); + } }
\ No newline at end of file diff --git a/service/servicenotfoundexception.php b/service/servicenotfoundexception.php index fb7e37dca..e4ee61fbe 100644 --- a/service/servicenotfoundexception.php +++ b/service/servicenotfoundexception.php @@ -16,12 +16,12 @@ namespace OCA\News\Service; class ServiceNotFoundException extends ServiceException { - /** - * Constructor - * @param string $msg the error message - */ - public function __construct($msg){ - parent::__construct($msg); - } + /** + * Constructor + * @param string $msg the error message + */ + public function __construct($msg){ + parent::__construct($msg); + } }
\ No newline at end of file diff --git a/service/servicevalidationexception.php b/service/servicevalidationexception.php index 62d74f8e9..510df0a22 100644 --- a/service/servicevalidationexception.php +++ b/service/servicevalidationexception.php @@ -16,12 +16,12 @@ namespace OCA\News\Service; class ServiceValidationException extends ServiceException { - /** - * Constructor - * @param string $msg the error message - */ - public function __construct($msg){ - parent::__construct($msg); - } + /** + * Constructor + * @param string $msg the error message + */ + public function __construct($msg){ + parent::__construct($msg); + } }
\ No newline at end of file diff --git a/templates/part.navigation.starredfeed.php b/templates/part.navigation.starredfeed.php index adf3434db..b970c20b9 100644 --- a/templates/part.navigation.starredfeed.php +++ b/templates/part.navigation.starredfeed.php @@ -1,14 +1,14 @@ <li ng-class="{ - active: Navigation.isStarredActive(), - unread: Navigation.getStarredCount() > 0 - }" - class="with-counter starred-feed"> + active: Navigation.isStarredActive(), + unread: Navigation.getStarredCount() > 0 + }" + class="with-counter starred-feed"> - <a class="icon-starred" ng-href="#/items/starred/"> - <?php p($l->t('Starred')) ?> - </a> + <a class="icon-starred" ng-href="#/items/starred/"> + <?php p($l->t('Starred')) ?> + </a> - <div class="app-navigation-entry-utils"> + <div class="app-navigation-entry-utils"> <ul> <li class="app-navigation-entry-utils-counter" ng-show="Navigation.getStarredCount() > 0" diff --git a/templates/part.navigation.unreadfeed.php b/templates/part.navigation.unreadfeed.php index 968e1eec4..fc62427cd 100644 --- a/templates/part.navigation.unreadfeed.php +++ b/templates/part.navigation.unreadfeed.php @@ -1,18 +1,18 @@ <li ng-class="{ - active: Navigation.isSubscriptionsActive(), - unread: Navigation.getUnreadCount() > 0 - }" + active: Navigation.isSubscriptionsActive(), + unread: Navigation.getUnreadCount() > 0 + }" class="subscriptions-feed with-counter with-menu"> - <a class="icon-rss" ng-href="#/items/" ng-if="!Navigation.isShowAll()"> - <?php p($l->t('Unread articles'))?> - </a> + <a class="icon-rss" ng-href="#/items/" ng-if="!Navigation.isShowAll()"> + <?php p($l->t('Unread articles'))?> + </a> - <a class="icon-rss" ng-href="#/items/" ng-if="Navigation.isShowAll()"> - <?php p($l->t('All articles'))?> - </a> + <a class="icon-rss" ng-href="#/items/" ng-if="Navigation.isShowAll()"> + <?php p($l->t('All articles'))?> + </a> - <div class="app-navigation-entry-utils"> + <div class="app-navigation-entry-utils"> <ul> <li class="app-navigation-entry-utils-counter" ng-show="Navigation.getUnreadCount() > 0" @@ -25,7 +25,7 @@ <div class="app-navigation-entry-menu"> <ul> - <li><button class="icon-checkmark" + <li><button class="icon-checkmark" title="<?php p($l->t('Read all')); ?>" ng-click="Navigation.markRead()"></button> </li> diff --git a/tests/classloader.php b/tests/classloader.php index c7a8b9f4d..c660057df 100644 --- a/tests/classloader.php +++ b/tests/classloader.php @@ -18,20 +18,20 @@ require_once __DIR__ . '/../../../tests/lib/appframework/db/mappertestutility.ph // to execute without owncloud, we need to create our own classloader spl_autoload_register(function ($className){ - if (strpos($className, 'OCA\\') === 0) { + if (strpos($className, 'OCA\\') === 0) { - $path = strtolower(str_replace('\\', '/', substr($className, 3)) . '.php'); - $relPath = __DIR__ . '/../..' . $path; + $path = strtolower(str_replace('\\', '/', substr($className, 3)) . '.php'); + $relPath = __DIR__ . '/../..' . $path; - if(file_exists($relPath)){ - require_once $relPath; - } - } else if(strpos($className, 'OCP\\') === 0) { - $path = strtolower(str_replace('\\', '/', substr($className, 3)) . '.php'); - $relPath = __DIR__ . '/../../../lib/public' . $path; + if(file_exists($relPath)){ + require_once $relPath; + } + } else if(strpos($className, 'OCP\\') === 0) { + $path = strtolower(str_replace('\\', '/', substr($className, 3)) . '.php'); + $relPath = __DIR__ . '/../../../lib/public' . $path; - if(file_exists($relPath)){ - require_once $relPath; - } - } + if(file_exists($relPath)){ + require_once $relPath; + } + } });
\ No newline at end of file diff --git a/tests/unit/articleenhancer/EnhancerTest.php b/tests/unit/articleenhancer/EnhancerTest.php index 49222a34d..d25b20dc7 100644 --- a/tests/unit/articleenhancer/EnhancerTest.php +++ b/tests/unit/articleenhancer/EnhancerTest.php @@ -17,85 +17,85 @@ use \OCA\News\Db\Item; class AddEnhancer implements ArticleEnhancer { - public function enhance(Item $item) { - $body = $item->getBody(); - $item->setBody($body += 1); - return $item; - } + public function enhance(Item $item) { + $body = $item->getBody(); + $item->setBody($body += 1); + return $item; + } } class EnhancerTest extends \PHPUnit_Framework_TestCase { - private $enhancer; - private $articleEnhancer; - private $articleEnhancer2; - - protected function setUp(){ - $this->enhancer = new Enhancer(); - $this->articleEnhancer = $this->getMockBuilder( - '\OCA\News\ArticleEnhancer\ArticleEnhancer') - ->disableOriginalConstructor() - ->getMock(); - $this->enhancer->registerEnhancer('test.com', $this->articleEnhancer); - } - - - public function testEnhanceSetsCorrectHash(){ - $item = new Item(); - $item->setUrl('hi'); - $urls = [ - 'https://test.com', - 'https://www.test.com', - 'https://test.com/', - 'http://test.com', - 'http://test.com/', - 'http://www.test.com' - ]; - for ($i=0; $i < count($urls); $i++) { - $this->articleEnhancer->expects($this->at($i)) - ->method('enhance') - ->with($this->equalTo($item)) - ->will($this->returnValue($item)); - } - - for ($i=0; $i < count($urls); $i++) { - $url = $urls[$i]; - $result = $this->enhancer->enhance($item, $url); - $this->assertEquals($item, $result); - } - - } - - - public function testNotMatchShouldJustReturnItem() { - $item = new Item(); - $item->setUrl('hi'); - - $url = 'https://tests.com'; - $this->articleEnhancer->expects($this->never()) - ->method('enhance'); - - $result = $this->enhancer->enhance($item, $url); - $this->assertEquals($item, $result); - } - - - public function testGlobalEnhancer() { - $this->enhancer->registerGlobalEnhancer( - new AddEnhancer() - ); - - $this->enhancer->registerGlobalEnhancer( - new AddEnhancer() - ); - - $item = new Item(); - $item->setBody(1); - - $result = $this->enhancer->enhance($item, 'test'); - - $this->assertEquals(3, $result->getBody()); - } + private $enhancer; + private $articleEnhancer; + private $articleEnhancer2; + + protected function setUp(){ + $this->enhancer = new Enhancer(); + $this->articleEnhancer = $this->getMockBuilder( + '\OCA\News\ArticleEnhancer\ArticleEnhancer') + ->disableOriginalConstructor() + ->getMock(); + $this->enhancer->registerEnhancer('test.com', $this->articleEnhancer); + } + + + public function testEnhanceSetsCorrectHash(){ + $item = new Item(); + $item->setUrl('hi'); + $urls = [ + 'https://test.com', + 'https://www.test.com', + 'https://test.com/', + 'http://test.com', + 'http://test.com/', + 'http://www.test.com' + ]; + for ($i=0; $i < count($urls); $i++) { + $this->articleEnhancer->expects($this->at($i)) + ->method('enhance') + ->with($this->equalTo($item)) + ->will($this->returnValue($item)); + } + + for ($i=0; $i < count($urls); $i++) { + $url = $urls[$i]; + $result = $this->enhancer->enhance($item, $url); + $this->assertEquals($item, $result); + } + + } + + + public function testNotMatchShouldJustReturnItem() { + $item = new Item(); + $item->setUrl('hi'); + + $url = 'https://tests.com'; + $this->articleEnhancer->expects($this->never()) + ->method('enhance'); + + $result = $this->enhancer->enhance($item, $url); + $this->assertEquals($item, $result); + } + + + public function testGlobalEnhancer() { + $this->enhancer->registerGlobalEnhancer( + new AddEnhancer() + ); + + $this->enhancer->registerGlobalEnhancer( + new AddEnhancer() + ); + + $item = new Item(); + $item->setBody(1); + + $result = $this->enhancer->enhance($item, 'test'); + + $this->assertEquals(3, $result->getBody()); + } }
\ No newline at end of file diff --git a/tests/unit/articleenhancer/GlobalArticleEnhancerTest.php b/tests/unit/articleenhancer/GlobalArticleEnhancerTest.php index 84c55ad9d..3add03eb5 100644 --- a/tests/unit/articleenhancer/GlobalArticleEnhancerTest.php +++ b/tests/unit/articleenhancer/GlobalArticleEnhancerTest.php @@ -18,54 +18,54 @@ use \OCA\News\Db\Item; class GlobalArticleEnhancerTest extends \PHPUnit_Framework_TestCase { - private $enhancer; + private $enhancer; - protected function setUp() { - $this->enhancer = new GlobalArticleEnhancer(); - } + protected function setUp() { + $this->enhancer = new GlobalArticleEnhancer(); + } - public function testNoReplaceYoutubeAutoplay() { - $body = '<iframe width="728" height="410" src="//www.youtube.com/embed/autoplay=1/AWE6UpXQoGU" frameborder="0" allowfullscreen=""></iframe>'; - $expected = '<div><iframe width="728" height="410" src="//www.youtube.com/embed/autoplay=1/AWE6UpXQoGU" frameborder="0" allowfullscreen=""></iframe></div>'; - $item = new Item(); - $item->setBody($body); + public function testNoReplaceYoutubeAutoplay() { + $body = '<iframe width="728" height="410" src="//www.youtube.com/embed/autoplay=1/AWE6UpXQoGU" frameborder="0" allowfullscreen=""></iframe>'; + $expected = '<div><iframe width="728" height="410" src="//www.youtube.com/embed/autoplay=1/AWE6UpXQoGU" frameborder="0" allowfullscreen=""></iframe></div>'; + $item = new Item(); + $item->setBody($body); - $result = $this->enhancer->enhance($item); - $this->assertEquals($expected, $result->getBody()); - } + $result = $this->enhancer->enhance($item); + $this->assertEquals($expected, $result->getBody()); + } - public function testReplaceYoutubeAutoplay() { - $body = 'test <iframe width="728" height="410" src="//www.youtube.com/embed/AWE6UpXQoGU?tst=1&autoplay=1&abc=1" frameborder="0" allowfullscreen=""></iframe>'; - $expected = '<div>test <iframe width="728" height="410" src="//www.youtube.com/embed/AWE6UpXQoGU?tst=1&autoplay=0&abc=1" frameborder="0" allowfullscreen=""></iframe></div>'; - $item = new Item(); - $item->setBody($body); + public function testReplaceYoutubeAutoplay() { + $body = 'test <iframe width="728" height="410" src="//www.youtube.com/embed/AWE6UpXQoGU?tst=1&autoplay=1&abc=1" frameborder="0" allowfullscreen=""></iframe>'; + $expected = '<div>test <iframe width="728" height="410" src="//www.youtube.com/embed/AWE6UpXQoGU?tst=1&autoplay=0&abc=1" frameborder="0" allowfullscreen=""></iframe></div>'; + $item = new Item(); + $item->setBody($body); - $result = $this->enhancer->enhance($item); - $this->assertEquals($expected, $result->getBody()); - } + $result = $this->enhancer->enhance($item); + $this->assertEquals($expected, $result->getBody()); + } - public function testMultipleParagraphs() { - $body = '<p>paragraph 1</p><p>paragraph 2</p>'; - $expected = '<div>' . $body . '</div>'; - $item = new Item(); - $item->setBody($body); + public function testMultipleParagraphs() { + $body = '<p>paragraph 1</p><p>paragraph 2</p>'; + $expected = '<div>' . $body . '</div>'; + $item = new Item(); + $item->setBody($body); - $result = $this->enhancer->enhance($item); - $this->assertEquals($expected, $result->getBody()); - } + $result = $this->enhancer->enhance($item); + $this->assertEquals($expected, $result->getBody()); + } - public function testMultipleParagraphsInDiv() { - $body = '<p>paragraph 1</p><p>paragraph 2</p>'; - $expected = '<div>' . $body . '</div>'; - $item = new Item(); - $item->setBody($body); + public function testMultipleParagraphsInDiv() { + $body = '<p>paragraph 1</p><p>paragraph 2</p>'; + $expected = '<div>' . $body . '</div>'; + $item = new Item(); + $item->setBody($body); - $result = $this->enhancer->enhance($item); - $this->assertEquals($expected, $result->getBody()); - } + $result = $this->enhancer->enhance($item); + $this->assertEquals($expected, $result->getBody()); + } } diff --git a/tests/unit/articleenhancer/RegexArticleEnhancerTest.php b/tests/unit/articleenhancer/RegexArticleEnhancerTest.php index a08371f47..018a596fa 100644 --- a/tests/unit/articleenhancer/RegexArticleEnhancerTest.php +++ b/tests/unit/articleenhancer/RegexArticleEnhancerTest.php @@ -19,17 +19,17 @@ use \OCA\News\Db\Item; class RegexArticleEnhancerTest extends \PHPUnit_Framework_TestCase { - public function testRegexEnhancer() { - $item = new Item(); - $item->setBody('atests is a nice thing'); - $item->setUrl('http://john.com'); - $regex = ["%tes(ts)%" => "heho$1tests"]; - - $regexEnhancer = new RegexArticleEnhancer('%john.com%', $regex); - $item = $regexEnhancer->enhance($item); - - $this->assertEquals('ahehotstests is a nice thing', $item->getBody()); - } + public function testRegexEnhancer() { + $item = new Item(); + $item->setBody('atests is a nice thing'); + $item->setUrl('http://john.com'); + $regex = ["%tes(ts)%" => "heho$1tests"]; + + $regexEnhancer = new RegexArticleEnhancer('%john.com%', $regex); + $item = $regexEnhancer->enhance($item); + + $this->assertEquals('ahehotstests is a nice thing', $item->getBody()); + } }
\ No newline at end of file diff --git a/tests/unit/articleenhancer/XPathArticleEnhancerTest.php b/tests/unit/articleenhancer/XPathArticleEnhancerTest.php index 082a2030c..0d4130e9e 100644 --- a/tests/unit/articleenhancer/XPathArticleEnhancerTest.php +++ b/tests/unit/articleenhancer/XPathArticleEnhancerTest.php @@ -18,310 +18,310 @@ use \OCA\News\Db\Item; class XPathArticleEnhancerTest extends \PHPUnit_Framework_TestCase { - private $testEnhancer; - private $fileFactory; - private $timeout; - private $redirects; - private $headers; - private $userAgent; - private $proxyHost; - private $proxyPort; - private $proxyAuth; - - protected function setUp() { - $this->timeout = 30; - $this->fileFactory = $this->getMockBuilder('\OCA\News\Utility\SimplePieAPIFactory') - ->disableOriginalConstructor() - ->getMock(); - $this->proxyHost = 'test'; - $this->proxyPort = 3; - $this->proxyAuth = 'hi'; - $this->config = $this->getMockBuilder( - '\OCA\News\Config\Config') - ->disableOriginalConstructor() - ->getMock(); - $this->config->expects($this->any()) - ->method('getProxyHost') - ->will($this->returnValue('')); - $this->config->expects($this->any()) - ->method('getProxyAuth') - ->will($this->returnValue($this->proxyAuth)); - $this->config->expects($this->any()) - ->method('getProxyPort') - ->will($this->returnValue($this->proxyPort)); - $this->config->expects($this->any()) - ->method('getFeedFetcherTimeout') - ->will($this->returnValue($this->timeout)); - - $this->testEnhancer = new XPathArticleEnhancer( - $this->fileFactory, - [ - '/explosm.net\/comics/' => '//*[@id=\'maincontent\']/div[2]/div/span', - '/explosm.net\/shorts/' => '//*[@id=\'maincontent\']/div/div', - '/explosm.net\/all/' => '//body/*', - '/themerepublic.net/' => '//*[@class=\'post hentry\']' - ], - $this->config - ); - $this->redirects = 5; - $this->headers = null; - $this->userAgent = 'Mozilla/5.0 AppleWebKit'; - } - - - public function testXPathUsesNoProxy() { - $file = new \stdClass; - $file->headers = ["content-type"=>"text/html; charset=utf-8"]; - $file->body = ''; - $item = new Item(); - $item->setUrl('https://www.explosm.net/comics/312'); - $item->setBody('Hello thar'); - - $this->fileFactory->expects($this->once()) - ->method('getFile') - ->with($this->equalTo($item->getUrl()), - $this->equalTo($this->timeout), - $this->equalTo($this->redirects), - $this->equalTo($this->headers), - $this->equalTo($this->userAgent), - $this->equalTo(false)) - ->will($this->returnValue($file)); - - $result = $this->testEnhancer->enhance($item); - $this->assertEquals('Hello thar', $result->getBody()); - } - - - public function testDoesNotModifiyNotMatchingResults() { - $item = new Item(); - $item->setUrl('http://explosm.net'); - $this->assertEquals($item, $this->testEnhancer->enhance($item)); - } - - - public function testDoesModifiyArticlesThatMatch() { - $file = new \stdClass; - $file->headers = ["content-type"=>"text/html; charset=utf-8"]; - $file->body = '<html> - <body> - <div id="maincontent"> - <div>nooo</div> - <div><div><span>hiho</span></div></div> - </div> - </body> - </html>'; - $item = new Item(); - $item->setUrl('https://www.explosm.net/comics/312'); - $item->setBody('Hello thar'); - - $this->fileFactory->expects($this->once()) - ->method('getFile') - ->with($this->equalTo($item->getUrl()), - $this->equalTo($this->timeout), - $this->equalTo($this->redirects), - $this->equalTo($this->headers), - $this->equalTo($this->userAgent)) - ->will($this->returnValue($file)); - - $result = $this->testEnhancer->enhance($item); - $this->assertEquals('<div><span>hiho</span></div>', $result->getBody()); - } - - - public function testDoesModifiyAllArticlesThatMatch() { - $file = new \stdClass; - $file->headers = ["content-type"=>"text/html; charset=utf-8"]; - $file->body = '<html> - <body> - <div id="maincontent"> - <div>nooo<div>hiho</div></div> - <div><div>rawr</div></div> - </div> - </body> - </html>'; - $item = new Item(); - $item->setUrl('https://www.explosm.net/shorts/312'); - $item->setBody('Hello thar'); - - $this->fileFactory->expects($this->once()) - ->method('getFile') - ->with($this->equalTo($item->getUrl()), - $this->equalTo($this->timeout), - $this->equalTo($this->redirects), - $this->equalTo($this->headers), - $this->equalTo($this->userAgent)) - ->will($this->returnValue($file)); - - $result = $this->testEnhancer->enhance($item); - $this->assertEquals('<div><div>hiho</div><div>rawr</div></div>', - $result->getBody()); - } - - - public function testModificationHandlesEmptyResults() { - $file = new \stdClass; - $file->headers = ["content-type"=>"text/html; charset=utf-8"]; - $file->body = '<html> - <body> - <div id="maincontent"> - </div> - </body> - </html>'; - $item = new Item(); - $item->setUrl('https://www.explosm.net/comics/312'); - $item->setBody('Hello thar'); - - $this->fileFactory->expects($this->once()) - ->method('getFile') - ->with($this->equalTo($item->getUrl()), - $this->equalTo($this->timeout), - $this->equalTo($this->redirects), - $this->equalTo($this->headers), - $this->equalTo($this->userAgent)) - ->will($this->returnValue($file)); - - $result = $this->testEnhancer->enhance($item); - $this->assertEquals('Hello thar', $result->getBody()); - } - - - public function testModificationDoesNotBreakOnEmptyDom() { - $file = new \stdClass; - $file->headers = ["content-type"=>"text/html; charset=utf-8"]; - $file->body = ''; - $item = new Item(); - $item->setUrl('https://www.explosm.net/comics/312'); - $item->setBody('Hello thar'); - - $this->fileFactory->expects($this->once()) - ->method('getFile') - ->with($this->equalTo($item->getUrl()), - $this->equalTo($this->timeout), - $this->equalTo($this->redirects), - $this->equalTo($this->headers), - $this->equalTo($this->userAgent)) - ->will($this->returnValue($file)); - - $result = $this->testEnhancer->enhance($item); - $this->assertEquals('Hello thar', $result->getBody()); - } - - - public function testModificationDoesNotBreakOnBrokenDom() { - $file = new \stdClass; - $file->headers = ["content-type"=>"text/html; charset=utf-8"]; - $file->body = '<html/><p> - <body> - <div id="maincontent"> - </div> - </body> - </html>'; - $item = new Item(); - $item->setUrl('https://www.explosm.net/comics/312'); - $item->setBody('Hello thar'); - - $this->fileFactory->expects($this->once()) - ->method('getFile') - ->with($this->equalTo($item->getUrl()), - $this->equalTo($this->timeout), - $this->equalTo($this->redirects), - $this->equalTo($this->headers), - $this->equalTo($this->userAgent)) - ->will($this->returnValue($file)); - - $result = $this->testEnhancer->enhance($item); - $this->assertEquals('Hello thar', $result->getBody()); - } - - - public function testTransformRelativeUrls() { - $file = new \stdClass; - $file->headers = ["content-type"=>"text/html; charset=utf-8"]; - $file->body = '<html> - <body> - <a href="../a/relative/url.html?a=1#b">link</a> - <a href="b/relative/url.html">link2</a> - <img src="/another/relative/link.jpg"></img> - </body> - </html>'; - $item = new Item(); - $item->setUrl('https://www.explosm.net/all/312'); - $item->setBody('Hello thar'); - - $this->fileFactory->expects($this->once()) - ->method('getFile') - ->with($this->equalTo($item->getUrl()), - $this->equalTo($this->timeout), - $this->equalTo($this->redirects), - $this->equalTo($this->headers), - $this->equalTo($this->userAgent)) - ->will($this->returnValue($file)); - - $result = $this->testEnhancer->enhance($item); - $this->assertEquals('<div>' . - '<a target="_blank" href="https://www.explosm.net/a/relative/url.html?a=1#b">link</a>' . - '<a target="_blank" href="https://www.explosm.net/all/b/relative/url.html">link2</a>' . - '<img src="https://www.explosm.net/another/relative/link.jpg">' . - '</div>', $result->getBody()); - } - - public function testTransformRelativeUrlSpecials() { - $file = new \stdClass; - $file->headers = ["content-type"=>"text/html; charset=utf-8"]; - $file->body = '<html> - <body> - <img src="relative/url.png?a=1&b=2"> - </body> - </html>'; - $item = new Item(); - $item->setUrl('https://username:secret@www.explosm.net/all/312'); - $item->setBody('Hello thar'); - - $this->fileFactory->expects($this->once()) - ->method('getFile') - ->with($this->equalTo($item->getUrl()), - $this->equalTo($this->timeout), - $this->equalTo($this->redirects), - $this->equalTo($this->headers), - $this->equalTo($this->userAgent)) - ->will($this->returnValue($file)); - - $result = $this->testEnhancer->enhance($item); - $this->assertEquals( - '<div><img src="https://username:secret@www.explosm.net/all/relative/url.png?a=1&b=2"></div>', - $result->getBody()); - } - - public function testDontTransformAbsoluteUrlsAndMails() { - $file = new \stdClass; - $file->headers = ["content-type"=>"text/html; charset=utf-8"]; - $file->body = '<html> - <body> - <img src="http://www.url.com/absolute/url.png"> - <a href="mailto:test@testsite.com">mail</a> - </body> - </html>'; - $item = new Item(); - $item->setUrl('https://www.explosm.net/all/312'); - $item->setBody('Hello thar'); - - $this->fileFactory->expects($this->once()) - ->method('getFile') - ->with($this->equalTo($item->getUrl()), - $this->equalTo($this->timeout), - $this->equalTo($this->redirects), - $this->equalTo($this->headers), - $this->equalTo($this->userAgent)) - ->will($this->returnValue($file)); - - $result = $this->testEnhancer->enhance($item); - $this->assertEquals( - '<div>' . - '<img src="http://www.url.com/absolute/url.png">' . - '<a target="_blank" href="mailto:test@testsite.com">mail</a>' . - '</div>', - $result->getBody() - ); - } + private $testEnhancer; + private $fileFactory; + private $timeout; + private $redirects; + private $headers; + private $userAgent; + private $proxyHost; + private $proxyPort; + private $proxyAuth; + + protected function setUp() { + $this->timeout = 30; + $this->fileFactory = $this->getMockBuilder('\OCA\News\Utility\SimplePieAPIFactory') + ->disableOriginalConstructor() + ->getMock(); + $this->proxyHost = 'test'; + $this->proxyPort = 3; + $this->proxyAuth = 'hi'; + $this->config = $this->getMockBuilder( + '\OCA\News\Config\Config') + ->disableOriginalConstructor() + ->getMock(); + $this->config->expects($this->any()) + ->method('getProxyHost') + ->will($this->returnValue('')); + $this->config->expects($this->any()) + ->method('getProxyAuth') + ->will($this->returnValue($this->proxyAuth)); + $this->config->expects($this->any()) + ->method('getProxyPort') + ->will($this->returnValue($this->proxyPort)); + $this->config->expects($this->any()) + ->method('getFeedFetcherTimeout') + ->will($this->returnValue($this->timeout)); + + $this->testEnhancer = new XPathArticleEnhancer( + $this->fileFactory, + [ + '/explosm.net\/comics/' => '//*[@id=\'maincontent\']/div[2]/div/span', + '/explosm.net\/shorts/' => '//*[@id=\'maincontent\']/div/div', + '/explosm.net\/all/' => '//body/*', + '/themerepublic.net/' => '//*[@class=\'post hentry\']' + ], + $this->config + ); + $this->redirects = 5; + $this->headers = null; + $this->userAgent = 'Mozilla/5.0 AppleWebKit'; + } + + + public function testXPathUsesNoProxy() { + $file = new \stdClass; + $file->headers = ["content-type"=>"text/html; charset=utf-8"]; + $file->body = ''; + $item = new Item(); + $item->setUrl('https://www.explosm.net/comics/312'); + $item->setBody('Hello thar'); + + $this->fileFactory->expects($this->once()) + ->method('getFile') + ->with($this->equalTo($item->getUrl()), + $this->equalTo($this->timeout), + $this->equalTo($this->redirects), + $this->equalTo($this->headers), + $this->equalTo($this->userAgent), + $this->equalTo(false)) + ->will($this->returnValue($file)); + + $result = $this->testEnhancer->enhance($item); + $this->assertEquals('Hello thar', $result->getBody()); + } + + + public function testDoesNotModifiyNotMatchingResults() { + $item = new Item(); + $item->setUrl('http://explosm.net'); + $this->assertEquals($item, $this->testEnhancer->enhance($item)); + } + + + public function testDoesModifiyArticlesThatMatch() { + $file = new \stdClass; + $file->headers = ["content-type"=>"text/html; charset=utf-8"]; + $file->body = '<html> + <body> + <div id="maincontent"> + <div>nooo</div> + <div><div><span>hiho</span></div></div> + </div> + </body> + </html>'; + $item = new Item(); + $item->setUrl('https://www.explosm.net/comics/312'); + $item->setBody('Hello thar'); + + $this->fileFactory->expects($this->once()) + ->method('getFile') + ->with($this->equalTo($item->getUrl()), + $this->equalTo($this->timeout), + $this->equalTo($this->redirects), + $this->equalTo($this->headers), + $this->equalTo($this->userAgent)) + ->will($this->returnValue($file)); + + $result = $this->testEnhancer->enhance($item); + $this->assertEquals('<div><span>hiho</span></div>', $result->getBody()); + } + + + public function testDoesModifiyAllArticlesThatMatch() { + $file = new \stdClass; + $file->headers = ["content-type"=>"text/html; charset=utf-8"]; + $file->body = '<html> + <body> + <div id="maincontent"> + <div>nooo<div>hiho</div></div> + <div><div>rawr</div></div> + </div> + </body> + </html>'; + $item = new Item(); + $item->setUrl('https://www.explosm.net/shorts/312'); + $item->setBody('Hello thar'); + + $this->fileFactory->expects($this->once()) + ->method('getFile') + ->with($this->equalTo($item->getUrl()), + $this->equalTo($this->timeout), + $this->equalTo($this->redirects), + $this->equalTo($this->headers), + $this->equalTo($this->userAgent)) + ->will($this->returnValue($file)); + + $result = $this->testEnhancer->enhance($item); + $this->assertEquals('<div><div>hiho</div><div>rawr</div></div>', + $result->getBody()); + } + + + public function testModificationHandlesEmptyResults() { + $file = new \stdClass; + $file->headers = ["content-type"=>"text/html; charset=utf-8"]; + $file->body = '<html> + <body> + <div id="maincontent"> + </div> + </body> + </html>'; + $item = new Item(); + $item->setUrl('https://www.explosm.net/comics/312'); + $item->setBody('Hello thar'); + + $this->fileFactory->expects($this->once()) + ->method('getFile') + ->with($this->equalTo($item->getUrl()), + $this->equalTo($this->timeout), + $this->equalTo($this->redirects), + $this->equalTo($this->headers), + $this->equalTo($this->userAgent)) + ->will($this->returnValue($file)); + + $result = $this->testEnhancer->enhance($item); + $this->assertEquals('Hello thar', $result->getBody()); + } + + + public function testModificationDoesNotBreakOnEmptyDom() { + $file = new \stdClass; + $file->headers = ["content-type"=>"text/html; charset=utf-8"]; + $file->body = ''; + $item = new Item(); + $item->setUrl('https://www.explosm.net/comics/312'); + $item->setBody('Hello thar'); + + $this->fileFactory->expects($this->once()) + ->method('getFile') + ->with($this->equalTo($item->getUrl()), + $this->equalTo($this->timeout), + $this->equalTo($this->redirects), + $this->equalTo($this->headers), + $this->equalTo($this->userAgent)) + ->will($this->returnValue($file)); + + $result = $this->testEnhancer->enhance($item); + $this->assertEquals('Hello thar', $result->getBody()); + } + + + public function testModificationDoesNotBreakOnBrokenDom() { + $file = new \stdClass; + $file->headers = ["content-type"=>"text/html; charset=utf-8"]; + $file->body = '<html/><p> + <body> + <div id="maincontent"> + </div> + </body> + </html>'; + $item = new Item(); + $item->setUrl('https://www.explosm.net/comics/312'); + $item->setBody('Hello thar'); + + $this->fileFactory->expects($this->once()) + ->method('getFile') + ->with($this->equalTo($item->getUrl()), + $this->equalTo($this->timeout), + $this->equalTo($this->redirects), + $this->equalTo($this->headers), + $this->equalTo($this->userAgent)) + ->will($this->returnValue($file)); + + $result = $this->testEnhancer->enhance($item); + $this->assertEquals('Hello thar', $result->getBody()); + } + + + public function testTransformRelativeUrls() { + $file = new \stdClass; + $file->headers = ["content-type"=>"text/html; charset=utf-8"]; + $file->body = '<html> + <body> + <a href="../a/relative/url.html?a=1#b">link</a> + <a href="b/relative/url.html">link2</a> + <img src="/another/relative/link.jpg"></img> + </body> + </html>'; + $item = new Item(); + $item->setUrl('https://www.explosm.net/all/312'); + $item->setBody('Hello thar'); + + $this->fileFactory->expects($this->once()) + ->method('getFile') + ->with($this->equalTo($item->getUrl()), + $this->equalTo($this->timeout), + $this->equalTo($this->redirects), + $this->equalTo($this->headers), + $this->equalTo($this->userAgent)) + ->will($this->returnValue($file)); + + $result = $this->testEnhancer->enhance($item); + $this->assertEquals('<div>' . + '<a target="_blank" href="https://www.explosm.net/a/relative/url.html?a=1#b">link</a>' . + '<a target="_blank" href="https://www.explosm.net/all/b/relative/url.html">link2</a>' . + '<img src="https://www.explosm.net/another/relative/link.jpg">' . + '</div>', $result->getBody()); + } + + public function testTransformRelativeUrlSpecials() { + $file = new \stdClass; + $file->headers = ["content-type"=>"text/html; charset=utf-8"]; + $file->body = '<html> + <body> + <img src="relative/url.png?a=1&b=2"> + </body> + </html>'; + $item = new Item(); + $item->setUrl('https://username:secret@www.explosm.net/all/312'); + $item->setBody('Hello thar'); + + $this->fileFactory->expects($this->once()) + ->method('getFile') + ->with($this->equalTo($item->getUrl()), + $this->equalTo($this->timeout), + $this->equalTo($this->redirects), + $this->equalTo($this->headers), + $this->equalTo($this->userAgent)) + ->will($this->returnValue($file)); + + $result = $this->testEnhancer->enhance($item); + $this->assertEquals( + '<div><img src="https://username:secret@www.explosm.net/all/relative/url.png?a=1&b=2"></div>', + $result->getBody()); + } + + public function testDontTransformAbsoluteUrlsAndMails() { + $file = new \stdClass; + $file->headers = ["content-type"=>"text/html; charset=utf-8"]; + $file->body = '<html> + <body> + <img src="http://www.url.com/absolute/url.png"> + <a href="mailto:test@testsite.com">mail</a> + </body> + </html>'; + $item = new Item(); + $item->setUrl('https://www.explosm.net/all/312'); + $item->setBody('Hello thar'); + + $this->fileFactory->expects($this->once()) + ->method('getFile') + ->with($this->equalTo($item->getUrl()), + $this->equalTo($this->timeout), + $this->equalTo($this->redirects), + $this->equalTo($this->headers), + $this->equalTo($this->userAgent)) + ->will($this->returnValue($file)); + + $result = $this->testEnhancer->enhance($item); + $this->assertEquals( + '<div>' . + '<img src="http://www.url.com/absolute/url.png">' . + '<a target="_blank" href="mailto:test@testsite.com">mail</a>' . + '</div>', + $result->getBody() + ); + } } diff --git a/tests/unit/config/AppConfigTest.php b/tests/unit/config/AppConfigTest.php index 34ab2738a..01bacbf5c 100644 --- a/tests/unit/config/AppConfigTest.php +++ b/tests/unit/config/AppConfigTest.php @@ -16,174 +16,174 @@ namespace OCA\News\Config; class AppConfigTest extends \PHPUnit_Framework_TestCase { - private $nav; - private $config; - private $url; - - public function setUp() { - $this->nav = $this->getMockBuilder('\OCP\INavigationManager') - ->disableOriginalConstructor() - ->getMock(); - $this->url = $this->getMockBuilder('\OCP\IURLGenerator') - ->disableOriginalConstructor() - ->getMock(); - $phpVersion = '5.3'; - $ownCloudVersion = '6.0.3'; - $installedExtensions = ['curl' => '4.3']; - $databaseType = 'oracle'; - - $this->config = new AppConfig($this->nav, $this->url, $phpVersion, - $ownCloudVersion, $installedExtensions, $databaseType); - } - - public function testGetId() { - $this->config->loadConfig(__DIR__ . '/../../../appinfo/app.json'); - $this->assertEquals('news', $this->config->getConfig('id')); - } - - - public function testGetConfig() { - $config = file_get_contents(__DIR__ . '/../../../appinfo/app.json'); - $config = json_decode($config, true); - $this->config->loadConfig($config); - $config['navigation'] = [ - 'id' => 'news', - 'order' => 10, - 'route' => 'news.page.index', - 'icon' => 'app.svg', - 'name' => 'News', - ]; - $this->assertEquals($config, $this->config->getConfig()); - } - - - public function testNoNavigation() { - $this->config->loadConfig([]); - - $this->nav->expects($this->never()) - ->method('add'); - } - - - public function testDefaultNavigation() { - $expected = [ - 'id' => 'news', - 'href' => 'news.page.index', - 'order' => 10, - 'icon' => 'app.svg', - 'name' => 'News' - ]; - - $this->url->expects($this->once()) - ->method('linkToRoute') - ->with($this->equalTo('news.page.index')) - ->will($this->returnValue('news.page.index')); - - $this->url->expects($this->once()) - ->method('imagePath') - ->with($this->equalTo('news'), - $this->equalTo('app.svg')) - ->will($this->returnValue('app.svg')); - - $this->nav->expects($this->once()) - ->method('add') - ->with($this->equalTo($expected)); - - $this->config->loadConfig([ - 'id' => 'news', - 'name' => 'News', - 'navigation' => [] - ]); - $this->config->registerNavigation(); - } - - - public function testCustomNavigation() { - $expected = [ - 'id' => 'abc', - 'href' => 'abc.page.index', - 'order' => 1, - 'icon' => 'test.svg', - 'name' => 'haha' - ]; - - $this->url->expects($this->once()) - ->method('linkToRoute') - ->with($this->equalTo('abc.page.index')) - ->will($this->returnValue('abc.page.index')); - - $this->url->expects($this->once()) - ->method('imagePath') - ->with($this->equalTo('abc'), - $this->equalTo('test.svg')) - ->will($this->returnValue('test.svg')); - - $this->nav->expects($this->once()) - ->method('add') - ->with($this->equalTo($expected)); - - $this->config->loadConfig([ - 'id' => 'abc', - 'name' => 'News', - 'navigation' => $expected - ]); - $this->config->registerNavigation(); - } - - - /** - * @expectedException \OCA\News\Config\DependencyException - */ - public function testPHPVersion() { - $this->config->loadConfig([ - 'dependencies' => [ - 'php' => '5.7' - ] - ]); - $this->config->testDependencies(); - } - - - /** - * @expectedException \OCA\News\Config\DependencyException - */ - public function testLibsVersion() { - $this->config->loadConfig([ - 'dependencies' => [ - 'libs' => [ - 'curl' => '>=4.3,<=4.3' - ] - ] - ]); - $this->config->testDependencies(); - } - - - /** - * @expectedException \OCA\News\Config\DependencyException - */ - public function testLibsExistence() { - $this->config->loadConfig([ - 'dependencies' => [ - 'libs' => [ - 'dope' => '>=4.3,<=4.3' - ] - ] - ]); - $this->config->testDependencies(); - } - - - - /** - * @expectedException \OCA\News\Config\DependencyException - */ - public function testSupportedDb() { - $this->config->loadConfig([ - 'dependencies' => [ - "databases" => ['pgsql', 'sqlite'] - ] - ]); - $this->config->testDependencies(); - } + private $nav; + private $config; + private $url; + + public function setUp() { + $this->nav = $this->getMockBuilder('\OCP\INavigationManager') + ->disableOriginalConstructor() + ->getMock(); + $this->url = $this->getMockBuilder('\OCP\IURLGenerator') + ->disableOriginalConstructor() + ->getMock(); + $phpVersion = '5.3'; + $ownCloudVersion = '6.0.3'; + $installedExtensions = ['curl' => '4.3']; + $databaseType = 'oracle'; + + $this->config = new AppConfig($this->nav, $this->url, $phpVersion, + $ownCloudVersion, $installedExtensions, $databaseType); + } + + public function testGetId() { + $this->config->loadConfig(__DIR__ . '/../../../appinfo/app.json'); + $this->assertEquals('news', $this->config->getConfig('id')); + } + + + public function testGetConfig() { + $config = file_get_contents(__DIR__ . '/../../../appinfo/app.json'); + $config = json_decode($config, true); + $this->config->loadConfig($config); + $config['navigation'] = [ + 'id' => 'news', + 'order' => 10, + 'route' => 'news.page.index', + 'icon' => 'app.svg', + 'name' => 'News', + ]; + $this->assertEquals($config, $this->config->getConfig()); + } + + + public function testNoNavigation() { + $this->config->loadConfig([]); + + $this->nav->expects($this->never()) + ->method('add'); + } + + + public function testDefaultNavigation() { + $expected = [ + 'id' => 'news', + 'href' => 'news.page.index', + 'order' => 10, + 'icon' => 'app.svg', + 'name' => 'News' + ]; + + $this->url->expects($this->once()) + ->method('linkToRoute') + ->with($this->equalTo('news.page.index')) + ->will($this->returnValue('news.page.index')); + + $this->url->expects($this->once()) + ->method('imagePath') + ->with($this->equalTo('news'), + $this->equalTo('app.svg')) + ->will($this->returnValue('app.svg')); + + $this->nav->expects($this->once()) + ->method('add') + ->with($this->equalTo($expected)); + + $this->config->loadConfig([ + 'id' => 'news', + 'name' => 'News', + 'navigation' => [] + ]); + $this->config->registerNavigation(); + } + + + public function testCustomNavigation() { + $expected = [ + 'id' => 'abc', + 'href' => 'abc.page.index', + 'order' => 1, + 'icon' => 'test.svg', + 'name' => 'haha' + ]; + + $this->url->expects($this->once()) + ->method('linkToRoute') + ->with($this->equalTo('abc.page.index')) + ->will($this->returnValue('abc.page.index')); + + $this->url->expects($this->once()) + ->method('imagePath') + ->with($this->equalTo('abc'), + $this->equalTo('test.svg')) + ->will($this->returnValue('test.svg')); + + $this->nav->expects($this->once()) + ->method('add') + ->with($this->equalTo($expected)); + + $this->config->loadConfig([ + 'id' => 'abc', + 'name' => 'News', + 'navigation' => $expected + ]); + $this->config->registerNavigation(); + } + + + /** + * @expectedException \OCA\News\Config\DependencyException + */ + public function testPHPVersion() { + $this->config->loadConfig([ + 'dependencies' => [ + 'php' => '5.7' + ] + ]); + $this->config->testDependencies(); + } + + + /** + * @expectedException \OCA\News\Config\DependencyException + */ + public function testLibsVersion() { + $this->config->loadConfig([ + 'dependencies' => [ + 'libs' => [ + 'curl' => '>=4.3,<=4.3' + ] + ] + ]); + $this->config->testDependencies(); + } + + + /** + * @expectedException \OCA\News\Config\DependencyException + */ + public function testLibsExistence() { + $this->config->loadConfig([ + 'dependencies' => [ + 'libs' => [ + 'dope' => '>=4.3,<=4.3' + ] + ] + ]); + $this->config->testDependencies(); + } + + + + /** + * @expectedException \OCA\News\Config\DependencyException + */ + public function testSupportedDb() { + $this->config->loadConfig([ + 'dependencies' => [ + "databases" => ['pgsql', 'sqlite'] + ] + ]); + $this->config->testDependencies(); + } }
\ No newline at end of file diff --git a/tests/unit/config/ConfigTest.php b/tests/unit/config/ConfigTest.php index b03eeb325..6a2b07c71 100644 --- a/tests/unit/config/ConfigTest.php +++ b/tests/unit/config/ConfigTest.php @@ -16,200 +16,200 @@ namespace OCA\News\Config; class ConfigTest extends \PHPUnit_Framework_TestCase { - private $fileSystem; - private $config; - private $configPath; - private $loggerParams; - - public function setUp() { - $this->logger = $this->getMockBuilder( - '\OCP\ILogger') - ->disableOriginalConstructor() - ->getMock(); - $this->fileSystem = $this->getMock('FileSystem', [ - 'file_get_contents', - 'file_put_contents', - 'file_exists' - ]); - $this->loggerParams = ['hi']; - $this->config = new Config($this->fileSystem, $this->logger, $this->loggerParams); - $this->configPath = 'config.json'; - } - - - public function testDefaults() { - $this->assertEquals(60, $this->config->getAutoPurgeMinimumInterval()); - $this->assertEquals(200, $this->config->getAutoPurgeCount()); - $this->assertEquals(30*60, $this->config->getSimplePieCacheDuration()); - $this->assertEquals(60, $this->config->getFeedFetcherTimeout()); - $this->assertEquals(true, $this->config->getUseCronUpdates()); - $this->assertEquals(8080, $this->config->getProxyPort()); - $this->assertEquals('', $this->config->getProxyHost()); - $this->assertEquals(null, $this->config->getProxyAuth()); - $this->assertEquals('', $this->config->getProxyUser()); - $this->assertEquals('', $this->config->getProxyPassword()); - } - - - public function testRead () { - $this->fileSystem->expects($this->once()) - ->method('file_get_contents') - ->with($this->equalTo($this->configPath)) - ->will($this->returnValue("autoPurgeCount = 3\nuseCronUpdates = true")); - - $this->config->read($this->configPath); - - $this->assertSame(3, $this->config->getAutoPurgeCount()); - $this->assertSame(true, $this->config->getUseCronUpdates()); - } - - - public function testReadIgnoresVeryLowPurgeInterval () { - $this->fileSystem->expects($this->once()) - ->method('file_get_contents') - ->with($this->equalTo($this->configPath)) - ->will($this->returnValue("autoPurgeMinimumInterval = 59")); - - $this->config->read($this->configPath); - - $this->assertSame(60, $this->config->getAutoPurgeMinimumInterval()); - } - - - - public function testReadBool () { - $this->fileSystem->expects($this->once()) - ->method('file_get_contents') - ->with($this->equalTo($this->configPath)) - ->will($this->returnValue("autoPurgeCount = 3\nuseCronUpdates = false")); - - $this->config->read($this->configPath); - - $this->assertSame(3, $this->config->getAutoPurgeCount()); - $this->assertSame(false, $this->config->getUseCronUpdates()); - } - - - public function testReadLogsInvalidValue() { - $this->fileSystem->expects($this->once()) - ->method('file_get_contents') - ->with($this->equalTo($this->configPath)) - ->will($this->returnValue('autoPurgeCounts = 3')); - $this->logger->expects($this->once()) - ->method('warning') - ->with($this->equalTo('Configuration value "autoPurgeCounts" ' . - 'does not exist. Ignored value.'), - $this->equalTo($this->loggerParams)); - - $this->config->read($this->configPath); - } - - - public function testReadLogsInvalidINI() { - $this->fileSystem->expects($this->once()) - ->method('file_get_contents') - ->with($this->equalTo($this->configPath)) - ->will($this->returnValue('')); - $this->logger->expects($this->once()) - ->method('warning') - ->with($this->equalTo('Configuration invalid. Ignoring values.'), - $this->equalTo($this->loggerParams)); - - $this->config->read($this->configPath); - } - - - public function testWrite () { - $json = "autoPurgeMinimumInterval = 60\n" . - "autoPurgeCount = 3\n" . - "simplePieCacheDuration = 1800\n" . - "feedFetcherTimeout = 60\n" . - "useCronUpdates = true\n" . - "proxyHost = yo man\n" . - "proxyPort = 12\n" . - "proxyUser = this is a test\n". - "proxyPassword = se"; - $this->config->setAutoPurgeCount(3); - $this->config->setProxyHost("yo man"); - $this->config->setProxyPort(12); - $this->config->setProxyUser("this is a test"); - $this->config->setProxyPassword("se"); + private $fileSystem; + private $config; + private $configPath; + private $loggerParams; + + public function setUp() { + $this->logger = $this->getMockBuilder( + '\OCP\ILogger') + ->disableOriginalConstructor() + ->getMock(); + $this->fileSystem = $this->getMock('FileSystem', [ + 'file_get_contents', + 'file_put_contents', + 'file_exists' + ]); + $this->loggerParams = ['hi']; + $this->config = new Config($this->fileSystem, $this->logger, $this->loggerParams); + $this->configPath = 'config.json'; + } + + + public function testDefaults() { + $this->assertEquals(60, $this->config->getAutoPurgeMinimumInterval()); + $this->assertEquals(200, $this->config->getAutoPurgeCount()); + $this->assertEquals(30*60, $this->config->getSimplePieCacheDuration()); + $this->assertEquals(60, $this->config->getFeedFetcherTimeout()); + $this->assertEquals(true, $this->config->getUseCronUpdates()); + $this->assertEquals(8080, $this->config->getProxyPort()); + $this->assertEquals('', $this->config->getProxyHost()); + $this->assertEquals(null, $this->config->getProxyAuth()); + $this->assertEquals('', $this->config->getProxyUser()); + $this->assertEquals('', $this->config->getProxyPassword()); + } + + + public function testRead () { + $this->fileSystem->expects($this->once()) + ->method('file_get_contents') + ->with($this->equalTo($this->configPath)) + ->will($this->returnValue("autoPurgeCount = 3\nuseCronUpdates = true")); + + $this->config->read($this->configPath); + + $this->assertSame(3, $this->config->getAutoPurgeCount()); + $this->assertSame(true, $this->config->getUseCronUpdates()); + } + + + public function testReadIgnoresVeryLowPurgeInterval () { + $this->fileSystem->expects($this->once()) + ->method('file_get_contents') + ->with($this->equalTo($this->configPath)) + ->will($this->returnValue("autoPurgeMinimumInterval = 59")); + + $this->config->read($this->configPath); + + $this->assertSame(60, $this->config->getAutoPurgeMinimumInterval()); + } + + + + public function testReadBool () { + $this->fileSystem->expects($this->once()) + ->method('file_get_contents') + ->with($this->equalTo($this->configPath)) + ->will($this->returnValue("autoPurgeCount = 3\nuseCronUpdates = false")); + + $this->config->read($this->configPath); + + $this->assertSame(3, $this->config->getAutoPurgeCount()); + $this->assertSame(false, $this->config->getUseCronUpdates()); + } + + + public function testReadLogsInvalidValue() { + $this->fileSystem->expects($this->once()) + ->method('file_get_contents') + ->with($this->equalTo($this->configPath)) + ->will($this->returnValue('autoPurgeCounts = 3')); + $this->logger->expects($this->once()) + ->method('warning') + ->with($this->equalTo('Configuration value "autoPurgeCounts" ' . + 'does not exist. Ignored value.'), + $this->equalTo($this->loggerParams)); + + $this->config->read($this->configPath); + } + + + public function testReadLogsInvalidINI() { + $this->fileSystem->expects($this->once()) + ->method('file_get_contents') + ->with($this->equalTo($this->configPath)) + ->will($this->returnValue('')); + $this->logger->expects($this->once()) + ->method('warning') + ->with($this->equalTo('Configuration invalid. Ignoring values.'), + $this->equalTo($this->loggerParams)); + + $this->config->read($this->configPath); + } + + + public function testWrite () { + $json = "autoPurgeMinimumInterval = 60\n" . + "autoPurgeCount = 3\n" . + "simplePieCacheDuration = 1800\n" . + "feedFetcherTimeout = 60\n" . + "useCronUpdates = true\n" . + "proxyHost = yo man\n" . + "proxyPort = 12\n" . + "proxyUser = this is a test\n". + "proxyPassword = se"; + $this->config->setAutoPurgeCount(3); + $this->config->setProxyHost("yo man"); + $this->config->setProxyPort(12); + $this->config->setProxyUser("this is a test"); + $this->config->setProxyPassword("se"); - $this->fileSystem->expects($this->once()) - ->method('file_put_contents') - ->with($this->equalTo($this->configPath), - $this->equalTo($json)); + $this->fileSystem->expects($this->once()) + ->method('file_put_contents') + ->with($this->equalTo($this->configPath), + $this->equalTo($json)); - $this->config->write($this->configPath); - } + $this->config->write($this->configPath); + } - public function testNoProxyAuthReturnsNull() { - $this->assertNull($this->config->getProxyAuth()); - } + public function testNoProxyAuthReturnsNull() { + $this->assertNull($this->config->getProxyAuth()); + } - public function testReadingNonExistentConfigWillWriteDefaults() { - $this->fileSystem->expects($this->once()) - ->method('file_exists') - ->with($this->equalTo($this->configPath)) - ->will($this->returnValue(false)); + public function testReadingNonExistentConfigWillWriteDefaults() { + $this->fileSystem->expects($this->once()) + ->method('file_exists') + ->with($this->equalTo($this->configPath)) + ->will($this->returnValue(false)); - $this->config->setUseCronUpdates(false); + $this->config->setUseCronUpdates(false); - $json = "autoPurgeMinimumInterval = 60\n" . - "autoPurgeCount = 200\n" . - "simplePieCacheDuration = 1800\n" . - "feedFetcherTimeout = 60\n" . - "useCronUpdates = false\n" . - "proxyHost = \n" . - "proxyPort = 8080\n" . - "proxyUser = \n" . - "proxyPassword = "; + $json = "autoPurgeMinimumInterval = 60\n" . + "autoPurgeCount = 200\n" . + "simplePieCacheDuration = 1800\n" . + "feedFetcherTimeout = 60\n" . + "useCronUpdates = false\n" . + "proxyHost = \n" . + "proxyPort = 8080\n" . + "proxyUser = \n" . + "proxyPassword = "; - $this->fileSystem->expects($this->once()) - ->method('file_put_contents') - ->with($this->equalTo($this->configPath), - $this->equalTo($json)); + $this->fileSystem->expects($this->once()) + ->method('file_put_contents') + ->with($this->equalTo($this->configPath), + $this->equalTo($json)); - $this->config->read($this->configPath, true); - } + $this->config->read($this->configPath, true); + } - public function testEncodesUserAndPasswordInHTTPBasicAuth() { - $this->config->setProxyUser("this is a test"); - $this->config->setProxyPassword("se"); + public function testEncodesUserAndPasswordInHTTPBasicAuth() { + $this->config->setProxyUser("this is a test"); + $this->config->setProxyPassword("se"); - $this->assertEquals('this is a test:se', $this->config->getProxyAuth()); - } + $this->assertEquals('this is a test:se', $this->config->getProxyAuth()); + } - public function testNoLowMinimumAutoPurgeInterval() { - $this->config->setAutoPurgeMinimumInterval(59); - $interval = $this->config->getAutoPurgeMinimumInterval(); + public function testNoLowMinimumAutoPurgeInterval() { + $this->config->setAutoPurgeMinimumInterval(59); + $interval = $this->config->getAutoPurgeMinimumInterval(); - $this->assertSame(60, $interval); - } - - - public function testMinimumAutoPurgeInterval() { - $this->config->setAutoPurgeMinimumInterval(61); - $interval = $this->config->getAutoPurgeMinimumInterval(); + $this->assertSame(60, $interval); + } + + + public function testMinimumAutoPurgeInterval() { + $this->config->setAutoPurgeMinimumInterval(61); + $interval = $this->config->getAutoPurgeMinimumInterval(); - $this->assertSame(61, $interval); - } + $this->assertSame(61, $interval); + } - public function testCacheDuration() { - $this->config->setSimplePieCacheDuration(21); - $duration = $this->config->getSimplePieCacheDuration(); + public function testCacheDuration() { + $this->config->setSimplePieCacheDuration(21); + $duration = $this->config->getSimplePieCacheDuration(); - $this->assertSame(21, $duration); - } + $this->assertSame(21, $duration); + } - public function testFeedFetcherTimeout() { - $this->config->setFeedFetcherTimeout(2); - $timout = $this->config->getFeedFetcherTimeout(); + public function testFeedFetcherTimeout() { + $this->config->setFeedFetcherTimeout(2); + $timout = $this->config->getFeedFetcherTimeout(); - $this->assertSame(2, $timout); - } + $this->assertSame(2, $timout); + } }
\ No newline at end of file diff --git a/tests/unit/controller/ExportControllerTest.php b/tests/unit/controller/ExportControllerTest.php index 28d69c6f3..29760e6f4 100644 --- a/tests/unit/controller/ExportControllerTest.php +++ b/tests/unit/controller/ExportControllerTest.php @@ -23,105 +23,105 @@ use \OCA\News\Db\Feed; class ExportControllerTest extends \PHPUnit_Framework_TestCase { - private $appName; - private $request; - private $controller; - private $user; - private $feedService; - private $folderService; - private $itemService; - private $opmlExporter; - - /** - * Gets run before each test - */ - public function setUp(){ - $this->appName = 'news'; - $this->user = 'john'; - $this->itemService = $this->getMockBuilder( - '\OCA\News\Service\ItemService') - ->disableOriginalConstructor() - ->getMock(); - $this->feedService = $this->getMockBuilder( - '\OCA\News\Service\FeedService') - ->disableOriginalConstructor() - ->getMock(); - $this->folderService = $this->getMockBuilder( - '\OCA\News\Service\FolderService') - ->disableOriginalConstructor() - ->getMock(); - $this->request = $this->getMockBuilder('\OCP\IRequest') - ->disableOriginalConstructor() - ->getMock(); - $this->opmlExporter = new OPMLExporter(); - $this->controller = new ExportController($this->appName, $this->request, - $this->folderService, $this->feedService, - $this->itemService, $this->opmlExporter, $this->user); - } - - - public function testOpmlExportNoFeeds(){ - $opml = - "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" . - "<opml version=\"2.0\">\n" . - " <head>\n" . - " <title>Subscriptions</title>\n" . - " </head>\n" . - " <body/>\n" . - "</opml>\n"; - - $this->feedService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue([])); - $this->folderService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue([])); - - $return = $this->controller->opml(); - $this->assertTrue($return instanceof TextDownloadResponse); - $this->assertEquals($opml, $return->render()); - } - - - public function testGetAllArticles(){ - $item1 = new Item(); - $item1->setFeedId(3); - $item2 = new Item(); - $item2->setFeedId(5); - - $feed1 = new Feed(); - $feed1->setId(3); - $feed1->setLink('http://goo'); - $feed2 = new Feed(); - $feed2->setId(5); - $feed2->setLink('http://gee'); - $feeds = [$feed1, $feed2]; - - $articles = [$item1, $item2]; - - $this->feedService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - $this->itemService->expects($this->once()) - ->method('getUnreadOrStarred') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($articles)); - - - $return = $this->controller->articles(); - $headers = $return->getHeaders(); - $this->assertEquals('attachment; filename="articles.json"', $headers ['Content-Disposition']); - - $this->assertEquals('[{"guid":null,"url":null,"title":null,' . - '"author":null,"pubDate":null,"body":null,"enclosureMime":null,' . - '"enclosureLink":null,"unread":false,"starred":false,' . - '"feedLink":"http:\/\/goo"},{"guid":null,"url":null,"title":null,' . - '"author":null,"pubDate":null,"body":null,"enclosureMime":null,' . - '"enclosureLink":null,"unread":false,"starred":false,' . - '"feedLink":"http:\/\/gee"}]', $return->render()); - } + private $appName; + private $request; + private $controller; + private $user; + private $feedService; + private $folderService; + private $itemService; + private $opmlExporter; + + /** + * Gets run before each test + */ + public function setUp(){ + $this->appName = 'news'; + $this->user = 'john'; + $this->itemService = $this->getMockBuilder( + '\OCA\News\Service\ItemService') + ->disableOriginalConstructor() + ->getMock(); + $this->feedService = $this->getMockBuilder( + '\OCA\News\Service\FeedService') + ->disableOriginalConstructor() + ->getMock(); + $this->folderService = $this->getMockBuilder( + '\OCA\News\Service\FolderService') + ->disableOriginalConstructor() + ->getMock(); + $this->request = $this->getMockBuilder('\OCP\IRequest') + ->disableOriginalConstructor() + ->getMock(); + $this->opmlExporter = new OPMLExporter(); + $this->controller = new ExportController($this->appName, $this->request, + $this->folderService, $this->feedService, + $this->itemService, $this->opmlExporter, $this->user); + } + + + public function testOpmlExportNoFeeds(){ + $opml = + "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" . + "<opml version=\"2.0\">\n" . + " <head>\n" . + " <title>Subscriptions</title>\n" . + " </head>\n" . + " <body/>\n" . + "</opml>\n"; + + $this->feedService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue([])); + $this->folderService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue([])); + + $return = $this->controller->opml(); + $this->assertTrue($return instanceof TextDownloadResponse); + $this->assertEquals($opml, $return->render()); + } + + + public function testGetAllArticles(){ + $item1 = new Item(); + $item1->setFeedId(3); + $item2 = new Item(); + $item2->setFeedId(5); + + $feed1 = new Feed(); + $feed1->setId(3); + $feed1->setLink('http://goo'); + $feed2 = new Feed(); + $feed2->setId(5); + $feed2->setLink('http://gee'); + $feeds = [$feed1, $feed2]; + + $articles = [$item1, $item2]; + + $this->feedService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + $this->itemService->expects($this->once()) + ->method('getUnreadOrStarred') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($articles)); + + + $return = $this->controller->articles(); + $headers = $return->getHeaders(); + $this->assertEquals('attachment; filename="articles.json"', $headers ['Content-Disposition']); + + $this->assertEquals('[{"guid":null,"url":null,"title":null,' . + '"author":null,"pubDate":null,"body":null,"enclosureMime":null,' . + '"enclosureLink":null,"unread":false,"starred":false,' . + '"feedLink":"http:\/\/goo"},{"guid":null,"url":null,"title":null,' . + '"author":null,"pubDate":null,"body":null,"enclosureMime":null,' . + '"enclosureLink":null,"unread":false,"starred":false,' . + '"feedLink":"http:\/\/gee"}]', $return->render()); + } }
\ No newline at end of file diff --git a/tests/unit/controller/FeedApiControllerTest.php b/tests/unit/controller/FeedApiControllerTest.php index 8dff56f2e..d14782856 100644 --- a/tests/unit/controller/FeedApiControllerTest.php +++ b/tests/unit/controller/FeedApiControllerTest.php @@ -24,322 +24,322 @@ use \OCA\News\Db\Item; class FeedApiControllerTest extends \PHPUnit_Framework_TestCase { - private $feedService; - private $itemService; - private $feedAPI; - private $appName; - private $user; - private $request; - private $msg; - private $logger; - private $loggerParams; - - protected function setUp() { - $this->user = 'tom'; - $this->loggerParams = ['hi']; - $this->logger = $this->getMockBuilder( - '\OCP\ILogger') - ->disableOriginalConstructor() - ->getMock(); - $this->appName = 'news'; - $this->request = $this->getMockBuilder( - '\OCP\IRequest') - ->disableOriginalConstructor() - ->getMock(); - $this->feedService = $this->getMockBuilder( - '\OCA\News\Service\FeedService') - ->disableOriginalConstructor() - ->getMock(); - $this->itemService = $this->getMockBuilder( - '\OCA\News\Service\ItemService') - ->disableOriginalConstructor() - ->getMock(); - $this->feedAPI = new FeedApiController( - $this->appName, - $this->request, - $this->feedService, - $this->itemService, - $this->logger, - $this->user, - $this->loggerParams - ); - $this->msg = 'hohoho'; - } - - - public function testIndex() { - $feeds = [new Feed()]; - $starredCount = 3; - $newestItemId = 2; - - $this->itemService->expects($this->once()) - ->method('starredCount') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($starredCount)); - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($newestItemId)); - $this->feedService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - - $response = $this->feedAPI->index(); - - $this->assertEquals([ - 'feeds' => [$feeds[0]->toAPI()], - 'starredCount' => $starredCount, - 'newestItemId' => $newestItemId - ], $response); - } - - - public function testIndexNoNewestItemId() { - $feeds = [new Feed()]; - $starredCount = 3; - - $this->itemService->expects($this->once()) - ->method('starredCount') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($starredCount)); - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->with($this->equalTo($this->user)) - ->will($this->throwException(new ServiceNotFoundException(''))); - $this->feedService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - - $response = $this->feedAPI->index(); - - $this->assertEquals([ - 'feeds' => [$feeds[0]->toAPI()], - 'starredCount' => $starredCount, - ], $response); - } - - - public function testDelete() { - $this->feedService->expects($this->once()) - ->method('delete') - ->with( - $this->equalTo(2), - $this->equalTo($this->user)); - - $this->feedAPI->delete(2); - } - - - public function testDeleteDoesNotExist() { - $this->feedService->expects($this->once()) - ->method('delete') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); - - $response = $this->feedAPI->delete(2); - - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); - } - - - public function testCreate() { - $feeds = [new Feed()]; - - $this->feedService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->feedService->expects($this->once()) - ->method('create') - ->with( - $this->equalTo('url'), - $this->equalTo(3), - $this->equalTo($this->user)) - ->will($this->returnValue($feeds[0])); - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->will($this->returnValue(3)); - - $response = $this->feedAPI->create('url', 3); - - $this->assertEquals([ - 'feeds' => [$feeds[0]->toAPI()], - 'newestItemId' => 3 - ], $response); - } - - - public function testCreateNoItems() { - $feeds = [new Feed()]; - - $this->feedService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->feedService->expects($this->once()) - ->method('create') - ->with( - $this->equalTo('ho'), - $this->equalTo(3), - $this->equalTo($this->user)) - ->will($this->returnValue($feeds[0])); - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->will($this->throwException(new ServiceNotFoundException(''))); - - $response = $this->feedAPI->create('ho', 3); - - $this->assertEquals([ - 'feeds' => [$feeds[0]->toAPI()] - ], $response); - } - - - - public function testCreateExists() { - $this->feedService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->feedService->expects($this->once()) - ->method('create') - ->will($this->throwException(new ServiceConflictException($this->msg))); - - $response = $this->feedAPI->create('ho', 3); - - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_CONFLICT, $response->getStatus()); - } + private $feedService; + private $itemService; + private $feedAPI; + private $appName; + private $user; + private $request; + private $msg; + private $logger; + private $loggerParams; + + protected function setUp() { + $this->user = 'tom'; + $this->loggerParams = ['hi']; + $this->logger = $this->getMockBuilder( + '\OCP\ILogger') + ->disableOriginalConstructor() + ->getMock(); + $this->appName = 'news'; + $this->request = $this->getMockBuilder( + '\OCP\IRequest') + ->disableOriginalConstructor() + ->getMock(); + $this->feedService = $this->getMockBuilder( + '\OCA\News\Service\FeedService') + ->disableOriginalConstructor() + ->getMock(); + $this->itemService = $this->getMockBuilder( + '\OCA\News\Service\ItemService') + ->disableOriginalConstructor() + ->getMock(); + $this->feedAPI = new FeedApiController( + $this->appName, + $this->request, + $this->feedService, + $this->itemService, + $this->logger, + $this->user, + $this->loggerParams + ); + $this->msg = 'hohoho'; + } + + + public function testIndex() { + $feeds = [new Feed()]; + $starredCount = 3; + $newestItemId = 2; + + $this->itemService->expects($this->once()) + ->method('starredCount') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($starredCount)); + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($newestItemId)); + $this->feedService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + + $response = $this->feedAPI->index(); + + $this->assertEquals([ + 'feeds' => [$feeds[0]->toAPI()], + 'starredCount' => $starredCount, + 'newestItemId' => $newestItemId + ], $response); + } + + + public function testIndexNoNewestItemId() { + $feeds = [new Feed()]; + $starredCount = 3; + + $this->itemService->expects($this->once()) + ->method('starredCount') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($starredCount)); + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->with($this->equalTo($this->user)) + ->will($this->throwException(new ServiceNotFoundException(''))); + $this->feedService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + + $response = $this->feedAPI->index(); + + $this->assertEquals([ + 'feeds' => [$feeds[0]->toAPI()], + 'starredCount' => $starredCount, + ], $response); + } + + + public function testDelete() { + $this->feedService->expects($this->once()) + ->method('delete') + ->with( + $this->equalTo(2), + $this->equalTo($this->user)); + + $this->feedAPI->delete(2); + } + + + public function testDeleteDoesNotExist() { + $this->feedService->expects($this->once()) + ->method('delete') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); + + $response = $this->feedAPI->delete(2); + + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); + } + + + public function testCreate() { + $feeds = [new Feed()]; + + $this->feedService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->feedService->expects($this->once()) + ->method('create') + ->with( + $this->equalTo('url'), + $this->equalTo(3), + $this->equalTo($this->user)) + ->will($this->returnValue($feeds[0])); + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->will($this->returnValue(3)); + + $response = $this->feedAPI->create('url', 3); + + $this->assertEquals([ + 'feeds' => [$feeds[0]->toAPI()], + 'newestItemId' => 3 + ], $response); + } + + + public function testCreateNoItems() { + $feeds = [new Feed()]; + + $this->feedService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->feedService->expects($this->once()) + ->method('create') + ->with( + $this->equalTo('ho'), + $this->equalTo(3), + $this->equalTo($this->user)) + ->will($this->returnValue($feeds[0])); + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->will($this->throwException(new ServiceNotFoundException(''))); + + $response = $this->feedAPI->create('ho', 3); + + $this->assertEquals([ + 'feeds' => [$feeds[0]->toAPI()] + ], $response); + } + + + + public function testCreateExists() { + $this->feedService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->feedService->expects($this->once()) + ->method('create') + ->will($this->throwException(new ServiceConflictException($this->msg))); + + $response = $this->feedAPI->create('ho', 3); + + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_CONFLICT, $response->getStatus()); + } - public function testCreateError() { - $this->feedService->expects($this->once()) - ->method('create') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); + public function testCreateError() { + $this->feedService->expects($this->once()) + ->method('create') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); - $response = $this->feedAPI->create('ho', 3); + $response = $this->feedAPI->create('ho', 3); - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); - } + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); + } - public function testRead() { - $this->itemService->expects($this->once()) - ->method('readFeed') - ->with( - $this->equalTo(3), - $this->equalTo(30), - $this->equalTo($this->user)); - - $this->feedAPI->read(3, 30); - } - - - public function testMove() { - $this->feedService->expects($this->once()) - ->method('move') - ->with( - $this->equalTo(3), - $this->equalTo(30), - $this->equalTo($this->user)); - - $this->feedAPI->move(3, 30); - } - - - public function testMoveDoesNotExist() { - $this->feedService->expects($this->once()) - ->method('move') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); + public function testRead() { + $this->itemService->expects($this->once()) + ->method('readFeed') + ->with( + $this->equalTo(3), + $this->equalTo(30), + $this->equalTo($this->user)); + + $this->feedAPI->read(3, 30); + } + + + public function testMove() { + $this->feedService->expects($this->once()) + ->method('move') + ->with( + $this->equalTo(3), + $this->equalTo(30), + $this->equalTo($this->user)); + + $this->feedAPI->move(3, 30); + } + + + public function testMoveDoesNotExist() { + $this->feedService->expects($this->once()) + ->method('move') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); - $response = $this->feedAPI->move(3, 4); + $response = $this->feedAPI->move(3, 4); - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); - } + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); + } - public function testRename() { - $feedId = 3; - $feedTitle = 'test'; + public function testRename() { + $feedId = 3; + $feedTitle = 'test'; - $this->feedService->expects($this->once()) - ->method('rename') - ->with( - $this->equalTo($feedId), - $this->equalTo($feedTitle), - $this->equalTo($this->user)); + $this->feedService->expects($this->once()) + ->method('rename') + ->with( + $this->equalTo($feedId), + $this->equalTo($feedTitle), + $this->equalTo($this->user)); - $this->feedAPI->rename($feedId, $feedTitle); - } + $this->feedAPI->rename($feedId, $feedTitle); + } - public function testRenameError() { - $feedId = 3; - $feedTitle = 'test'; + public function testRenameError() { + $feedId = 3; + $feedTitle = 'test'; - $this->feedService->expects($this->once()) - ->method('rename') - ->with( - $this->equalTo($feedId), - $this->equalTo($feedTitle), - $this->equalTo($this->user)) - ->will($this->throwException(new ServiceNotFoundException('hi'))); + $this->feedService->expects($this->once()) + ->method('rename') + ->with( + $this->equalTo($feedId), + $this->equalTo($feedTitle), + $this->equalTo($this->user)) + ->will($this->throwException(new ServiceNotFoundException('hi'))); - $result = $this->feedAPI->rename($feedId, $feedTitle); - $data = $result->getData(); - $code = $result->getStatus(); + $result = $this->feedAPI->rename($feedId, $feedTitle); + $data = $result->getData(); + $code = $result->getStatus(); - $this->assertSame(Http::STATUS_NOT_FOUND, $code); - $this->assertSame('hi', $data['message']); - } + $this->assertSame(Http::STATUS_NOT_FOUND, $code); + $this->assertSame('hi', $data['message']); + } - public function testfromAllUsers(){ - $feed = new Feed(); - $feed->setUrl(3); - $feed->setId(1); - $feed->setUserId('john'); - $feeds = [$feed]; - $this->feedService->expects($this->once()) - ->method('findAllFromAllUsers') - ->will($this->returnValue($feeds)); - $response = json_encode($this->feedAPI->fromAllUsers()); - $this->assertEquals('{"feeds":[{"id":1,"userId":"john"}]}', $response); - } + public function testfromAllUsers(){ + $feed = new Feed(); + $feed->setUrl(3); + $feed->setId(1); + $feed->setUserId('john'); + $feeds = [$feed]; + $this->feedService->expects($this->once()) + ->method('findAllFromAllUsers') + ->will($this->returnValue($feeds)); + $response = json_encode($this->feedAPI->fromAllUsers()); + $this->assertEquals('{"feeds":[{"id":1,"userId":"john"}]}', $response); + } - public function testUpdate() { - $feedId = 3; - $userId = 'hi'; + public function testUpdate() { + $feedId = 3; + $userId = 'hi'; - $this->feedService->expects($this->once()) - ->method('update') - ->with($this->equalTo($feedId), $this->equalTo($userId)); + $this->feedService->expects($this->once()) + ->method('update') + ->with($this->equalTo($feedId), $this->equalTo($userId)); - $this->feedAPI->update($userId, $feedId); - } + $this->feedAPI->update($userId, $feedId); + } - public function testUpdateError() { - $feedId = 3; - $userId = 'hi'; - $this->feedService->expects($this->once()) - ->method('update') - ->will($this->throwException(new \Exception($this->msg))); - $this->logger->expects($this->once()) - ->method('debug') - ->with($this->equalTo('Could not update feed ' . $this->msg), - $this->equalTo($this->loggerParams)); + public function testUpdateError() { + $feedId = 3; + $userId = 'hi'; + $this->feedService->expects($this->once()) + ->method('update') + ->will($this->throwException(new \Exception($this->msg))); + $this->logger->expects($this->once()) + ->method('debug') + ->with($this->equalTo('Could not update feed ' . $this->msg), + $this->equalTo($this->loggerParams)); - $this->feedAPI->update($userId, $feedId); + $this->feedAPI->update($userId, $feedId); - } + } } diff --git a/tests/unit/controller/FeedControllerTest.php b/tests/unit/controller/FeedControllerTest.php index ed20308ec..34b0a847b 100644 --- a/tests/unit/controller/FeedControllerTest.php +++ b/tests/unit/controller/FeedControllerTest.php @@ -23,483 +23,483 @@ use \OCA\News\Service\ServiceConflictException; class FeedControllerTest extends \PHPUnit_Framework_TestCase { - private $appName; - private $feedService; - private $request; - private $controller; - private $folderService; - private $itemService; - private $settings; - private $exampleResult; - - - /** - * Gets run before each test - */ - public function setUp(){ - $this->appName = 'news'; - $this->user = 'jack'; - $this->settings = $this->getMockBuilder( - '\OCP\IConfig') - ->disableOriginalConstructor() - ->getMock(); - $this->itemService = $this->getMockBuilder('\OCA\News\Service\ItemService') - ->disableOriginalConstructor() - ->getMock(); - $this->feedService = $this->getMockBuilder('\OCA\News\Service\FeedService') - ->disableOriginalConstructor() - ->getMock(); - $this->folderService = $this->getMockBuilder('\OCA\News\Service\FolderService') - ->disableOriginalConstructor() - ->getMock(); - $this->request = $this->getMockBuilder( - '\OCP\IRequest') - ->disableOriginalConstructor() - ->getMock(); - $this->controller = new FeedController($this->appName, $this->request, - $this->folderService, - $this->feedService, - $this->itemService, - $this->settings, - $this->user); - $this->exampleResult = [ - 'activeFeed' => [ - 'id' => 0, - 'type' => FeedType::SUBSCRIPTIONS - ] - ]; - } - - - public function testIndex(){ - $result = [ - 'feeds' => [ - ['a feed'], - ], - 'starred' => 13 - ]; - $this->feedService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($result['feeds'])); - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->with($this->equalTo($this->user)) - ->will($this->throwException(new ServiceNotFoundException(''))); - $this->itemService->expects($this->once()) - ->method('starredCount') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($result['starred'])); - - $response = $this->controller->index(); - - $this->assertEquals($result, $response); - } - - - public function testIndexHighestItemIdExists(){ - $result = [ - 'feeds' => [ - ['a feed'], - ], - 'starred' => 13, - 'newestItemId' => 5 - ]; - $this->feedService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($result['feeds'])); - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($result['newestItemId'])); - $this->itemService->expects($this->once()) - ->method('starredCount') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($result['starred'])); - - $response = $this->controller->index(); - - $this->assertEquals($result, $response); - } - - - - private function activeInitMocks($id, $type){ - $this->settings->expects($this->at(0)) - ->method('getUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('lastViewedFeedId')) - ->will($this->returnValue($id)); - $this->settings->expects($this->at(1)) - ->method('getUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('lastViewedFeedType')) - ->will($this->returnValue($type)); - } - - - public function testActive(){ - $id = 3; - $type = FeedType::STARRED; - $result = [ - 'activeFeed' => [ - 'id' => $id, - 'type' => $type - ] - ]; - - $this->activeInitMocks($id, $type); - - $response = $this->controller->active(); - - $this->assertEquals($result, $response); - } - - - public function testActiveFeedDoesNotExist(){ - $id = 3; - $type = FeedType::FEED; - $ex = new ServiceNotFoundException('hiu'); - $result = $this->exampleResult; - - $this->feedService->expects($this->once()) - ->method('find') - ->with($this->equalTo($id), $this->equalTo($this->user)) - ->will($this->throwException($ex)); - - $this->activeInitMocks($id, $type); - - $response = $this->controller->active(); - - $this->assertEquals($result, $response); - } - - - public function testActiveFolderDoesNotExist(){ - $id = 3; - $type = FeedType::FOLDER; - $ex = new ServiceNotFoundException('hiu'); - $result = $this->exampleResult; + private $appName; + private $feedService; + private $request; + private $controller; + private $folderService; + private $itemService; + private $settings; + private $exampleResult; + + + /** + * Gets run before each test + */ + public function setUp(){ + $this->appName = 'news'; + $this->user = 'jack'; + $this->settings = $this->getMockBuilder( + '\OCP\IConfig') + ->disableOriginalConstructor() + ->getMock(); + $this->itemService = $this->getMockBuilder('\OCA\News\Service\ItemService') + ->disableOriginalConstructor() + ->getMock(); + $this->feedService = $this->getMockBuilder('\OCA\News\Service\FeedService') + ->disableOriginalConstructor() + ->getMock(); + $this->folderService = $this->getMockBuilder('\OCA\News\Service\FolderService') + ->disableOriginalConstructor() + ->getMock(); + $this->request = $this->getMockBuilder( + '\OCP\IRequest') + ->disableOriginalConstructor() + ->getMock(); + $this->controller = new FeedController($this->appName, $this->request, + $this->folderService, + $this->feedService, + $this->itemService, + $this->settings, + $this->user); + $this->exampleResult = [ + 'activeFeed' => [ + 'id' => 0, + 'type' => FeedType::SUBSCRIPTIONS + ] + ]; + } + + + public function testIndex(){ + $result = [ + 'feeds' => [ + ['a feed'], + ], + 'starred' => 13 + ]; + $this->feedService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($result['feeds'])); + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->with($this->equalTo($this->user)) + ->will($this->throwException(new ServiceNotFoundException(''))); + $this->itemService->expects($this->once()) + ->method('starredCount') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($result['starred'])); + + $response = $this->controller->index(); + + $this->assertEquals($result, $response); + } + + + public function testIndexHighestItemIdExists(){ + $result = [ + 'feeds' => [ + ['a feed'], + ], + 'starred' => 13, + 'newestItemId' => 5 + ]; + $this->feedService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($result['feeds'])); + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($result['newestItemId'])); + $this->itemService->expects($this->once()) + ->method('starredCount') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($result['starred'])); + + $response = $this->controller->index(); + + $this->assertEquals($result, $response); + } + + + + private function activeInitMocks($id, $type){ + $this->settings->expects($this->at(0)) + ->method('getUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('lastViewedFeedId')) + ->will($this->returnValue($id)); + $this->settings->expects($this->at(1)) + ->method('getUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('lastViewedFeedType')) + ->will($this->returnValue($type)); + } + + + public function testActive(){ + $id = 3; + $type = FeedType::STARRED; + $result = [ + 'activeFeed' => [ + 'id' => $id, + 'type' => $type + ] + ]; + + $this->activeInitMocks($id, $type); + + $response = $this->controller->active(); + + $this->assertEquals($result, $response); + } + + + public function testActiveFeedDoesNotExist(){ + $id = 3; + $type = FeedType::FEED; + $ex = new ServiceNotFoundException('hiu'); + $result = $this->exampleResult; + + $this->feedService->expects($this->once()) + ->method('find') + ->with($this->equalTo($id), $this->equalTo($this->user)) + ->will($this->throwException($ex)); + + $this->activeInitMocks($id, $type); + + $response = $this->controller->active(); + + $this->assertEquals($result, $response); + } + + + public function testActiveFolderDoesNotExist(){ + $id = 3; + $type = FeedType::FOLDER; + $ex = new ServiceNotFoundException('hiu'); + $result = $this->exampleResult; - $this->folderService->expects($this->once()) - ->method('find') - ->with($this->equalTo($id), $this->equalTo($this->user)) - ->will($this->throwException($ex)); + $this->folderService->expects($this->once()) + ->method('find') + ->with($this->equalTo($id), $this->equalTo($this->user)) + ->will($this->throwException($ex)); - $this->activeInitMocks($id, $type); + $this->activeInitMocks($id, $type); - $response = $this->controller->active(); + $response = $this->controller->active(); - $this->assertEquals($result, $response); - } + $this->assertEquals($result, $response); + } - public function testActiveActiveIsNull(){ - $id = 3; - $type = null; - $result = $this->exampleResult; + public function testActiveActiveIsNull(){ + $id = 3; + $type = null; + $result = $this->exampleResult; - $this->activeInitMocks($id, $type); + $this->activeInitMocks($id, $type); - $response = $this->controller->active(); + $response = $this->controller->active(); - $this->assertEquals($result, $response); - } + $this->assertEquals($result, $response); + } - public function testCreate(){ - $result = [ - 'feeds' => [new Feed()], - 'newestItemId' => 3 - ]; + public function testCreate(){ + $result = [ + 'feeds' => [new Feed()], + 'newestItemId' => 3 + ]; - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->will($this->returnValue($result['newestItemId'])); - $this->feedService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->feedService->expects($this->once()) - ->method('create') - ->with($this->equalTo('hi'), - $this->equalTo(4), - $this->equalTo($this->user), - $this->equalTo('yo')) - ->will($this->returnValue($result['feeds'][0])); + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->will($this->returnValue($result['newestItemId'])); + $this->feedService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->feedService->expects($this->once()) + ->method('create') + ->with($this->equalTo('hi'), + $this->equalTo(4), + $this->equalTo($this->user), + $this->equalTo('yo')) + ->will($this->returnValue($result['feeds'][0])); - $response = $this->controller->create('hi', 4, 'yo'); + $response = $this->controller->create('hi', 4, 'yo'); - $this->assertEquals($result, $response); - } + $this->assertEquals($result, $response); + } - public function testCreateNoItems(){ - $result = ['feeds' => [new Feed()]]; + public function testCreateNoItems(){ + $result = ['feeds' => [new Feed()]]; - $this->feedService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->feedService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->will($this->throwException(new ServiceNotFoundException(''))); + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->will($this->throwException(new ServiceNotFoundException(''))); - $this->feedService->expects($this->once()) - ->method('create') - ->with($this->equalTo('hi'), - $this->equalTo(4), - $this->equalTo($this->user), - $this->equalTo('yo')) - ->will($this->returnValue($result['feeds'][0])); + $this->feedService->expects($this->once()) + ->method('create') + ->with($this->equalTo('hi'), + $this->equalTo(4), + $this->equalTo($this->user), + $this->equalTo('yo')) + ->will($this->returnValue($result['feeds'][0])); - $response = $this->controller->create('hi', 4, 'yo'); + $response = $this->controller->create('hi', 4, 'yo'); - $this->assertEquals($result, $response); - } + $this->assertEquals($result, $response); + } - public function testCreateReturnsErrorForInvalidCreate(){ - $msg = 'except'; - $ex = new ServiceNotFoundException($msg); - $this->feedService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->feedService->expects($this->once()) - ->method('create') - ->will($this->throwException($ex)); + public function testCreateReturnsErrorForInvalidCreate(){ + $msg = 'except'; + $ex = new ServiceNotFoundException($msg); + $this->feedService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->feedService->expects($this->once()) + ->method('create') + ->will($this->throwException($ex)); - $response = $this->controller->create('hi', 4, 'test'); - $params = json_decode($response->render(), true); + $response = $this->controller->create('hi', 4, 'test'); + $params = json_decode($response->render(), true); - $this->assertEquals($msg, $params['message']); - $this->assertEquals($response->getStatus(), Http::STATUS_UNPROCESSABLE_ENTITY); - } + $this->assertEquals($msg, $params['message']); + $this->assertEquals($response->getStatus(), Http::STATUS_UNPROCESSABLE_ENTITY); + } - public function testCreateReturnsErrorForDuplicateCreate(){ - $msg = 'except'; - $ex = new ServiceConflictException($msg); - $this->feedService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->feedService->expects($this->once()) - ->method('create') - ->will($this->throwException($ex)); + public function testCreateReturnsErrorForDuplicateCreate(){ + $msg = 'except'; + $ex = new ServiceConflictException($msg); + $this->feedService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->feedService->expects($this->once()) + ->method('create') + ->will($this->throwException($ex)); - $response = $this->controller->create('hi', 4, 'test'); - $params = json_decode($response->render(), true); + $response = $this->controller->create('hi', 4, 'test'); + $params = json_decode($response->render(), true); - $this->assertEquals($msg, $params['message']); - $this->assertEquals($response->getStatus(), Http::STATUS_CONFLICT); - } + $this->assertEquals($msg, $params['message']); + $this->assertEquals($response->getStatus(), Http::STATUS_CONFLICT); + } - public function testDelete(){ - $this->feedService->expects($this->once()) - ->method('markDeleted') - ->with($this->equalTo(4)); + public function testDelete(){ + $this->feedService->expects($this->once()) + ->method('markDeleted') + ->with($this->equalTo(4)); - $this->controller->delete(4); - } + $this->controller->delete(4); + } - public function testDeleteDoesNotExist(){ - $msg = 'hehe'; + public function testDeleteDoesNotExist(){ + $msg = 'hehe'; - $this->feedService->expects($this->once()) - ->method('markDeleted') - ->will($this->throwException(new ServiceNotFoundException($msg))); + $this->feedService->expects($this->once()) + ->method('markDeleted') + ->will($this->throwException(new ServiceNotFoundException($msg))); - $response = $this->controller->delete(4); - $params = json_decode($response->render(), true); + $response = $this->controller->delete(4); + $params = json_decode($response->render(), true); - $this->assertEquals($msg, $params['message']); - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - } + $this->assertEquals($msg, $params['message']); + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + } - public function testUpdate(){ - $feed = new Feed(); - $feed->setId(3); - $feed->setUnreadCount(44); - $result = [ - 'feeds' => [ - [ - 'id' => $feed->getId(), - 'unreadCount' => $feed->getUnreadCount() - ] - ] - ]; + public function testUpdate(){ + $feed = new Feed(); + $feed->setId(3); + $feed->setUnreadCount(44); + $result = [ + 'feeds' => [ + [ + 'id' => $feed->getId(), + 'unreadCount' => $feed->getUnreadCount() + ] + ] + ]; - $this->feedService->expects($this->once()) - ->method('update') - ->with($this->equalTo(4), $this->equalTo($this->user)) - ->will($this->returnValue($feed)); + $this->feedService->expects($this->once()) + ->method('update') + ->with($this->equalTo(4), $this->equalTo($this->user)) + ->will($this->returnValue($feed)); - $response = $this->controller->update(4); + $response = $this->controller->update(4); - $this->assertEquals($result, $response); - } + $this->assertEquals($result, $response); + } - public function testUpdateReturnsJSONError(){ - $this->feedService->expects($this->once()) - ->method('update') - ->with($this->equalTo(4), $this->equalTo($this->user)) - ->will($this->throwException(new ServiceNotFoundException('NO!'))); + public function testUpdateReturnsJSONError(){ + $this->feedService->expects($this->once()) + ->method('update') + ->with($this->equalTo(4), $this->equalTo($this->user)) + ->will($this->throwException(new ServiceNotFoundException('NO!'))); - $response = $this->controller->update(4); - $render = $response->render(); + $response = $this->controller->update(4); + $render = $response->render(); - $this->assertEquals('{"message":"NO!"}', $render); - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - } + $this->assertEquals('{"message":"NO!"}', $render); + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + } - public function testMove(){ - $this->feedService->expects($this->once()) - ->method('move') - ->with($this->equalTo(4), - $this->equalTo(3), - $this->equalTo($this->user)); + public function testMove(){ + $this->feedService->expects($this->once()) + ->method('move') + ->with($this->equalTo(4), + $this->equalTo(3), + $this->equalTo($this->user)); - $this->controller->move(4, 3); + $this->controller->move(4, 3); - } + } - public function testMoveDoesNotExist(){ - $msg = 'john'; + public function testMoveDoesNotExist(){ + $msg = 'john'; - $this->feedService->expects($this->once()) - ->method('move') - ->will($this->throwException(new ServiceNotFoundException($msg))); + $this->feedService->expects($this->once()) + ->method('move') + ->will($this->throwException(new ServiceNotFoundException($msg))); - $response = $this->controller->move(4, 3); - $params = json_decode($response->render(), true); + $response = $this->controller->move(4, 3); + $params = json_decode($response->render(), true); - $this->assertEquals($msg, $params['message']); - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - } + $this->assertEquals($msg, $params['message']); + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + } - public function testRename(){ - $this->feedService->expects($this->once()) - ->method('rename') - ->with($this->equalTo(4), - $this->equalTo('title'), - $this->equalTo($this->user)); + public function testRename(){ + $this->feedService->expects($this->once()) + ->method('rename') + ->with($this->equalTo(4), + $this->equalTo('title'), + $this->equalTo($this->user)); - $this->controller->rename(4, 'title'); - } + $this->controller->rename(4, 'title'); + } - public function testRenameDoesNotExist(){ - $msg = 'hi'; + public function testRenameDoesNotExist(){ + $msg = 'hi'; - $this->feedService->expects($this->once()) - ->method('rename') - ->with($this->equalTo(4), - $this->equalTo('title'), - $this->equalTo($this->user)) - ->will($this->throwException(new ServiceNotFoundException($msg))); + $this->feedService->expects($this->once()) + ->method('rename') + ->with($this->equalTo(4), + $this->equalTo('title'), + $this->equalTo($this->user)) + ->will($this->throwException(new ServiceNotFoundException($msg))); - $response = $this->controller->rename(4, 'title'); + $response = $this->controller->rename(4, 'title'); - $params = $response->getData(); + $params = $response->getData(); - $this->assertEquals($msg, $params['message']); - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - } + $this->assertEquals($msg, $params['message']); + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + } - public function testImport() { - $feed = new Feed(); + public function testImport() { + $feed = new Feed(); - $expected = [ - 'starred' => 3, - 'feeds' => [$feed] - ]; + $expected = [ + 'starred' => 3, + 'feeds' => [$feed] + ]; - $this->feedService->expects($this->once()) - ->method('importArticles') - ->with($this->equalTo(array('json')), - $this->equalTo($this->user)) - ->will($this->returnValue($feed)); + $this->feedService->expects($this->once()) + ->method('importArticles') + ->with($this->equalTo(array('json')), + $this->equalTo($this->user)) + ->will($this->returnValue($feed)); - $this->itemService->expects($this->once()) - ->method('starredCount') - ->with($this->equalTo($this->user)) - ->will($this->returnValue(3)); + $this->itemService->expects($this->once()) + ->method('starredCount') + ->with($this->equalTo($this->user)) + ->will($this->returnValue(3)); - $response = $this->controller->import(array('json')); + $response = $this->controller->import(array('json')); - $this->assertEquals($expected, $response); - } + $this->assertEquals($expected, $response); + } - public function testImportCreatesNoAdditionalFeed() { - $this->feedService->expects($this->once()) - ->method('importArticles') - ->with($this->equalTo(array('json')), - $this->equalTo($this->user)) - ->will($this->returnValue(null)); + public function testImportCreatesNoAdditionalFeed() { + $this->feedService->expects($this->once()) + ->method('importArticles') + ->with($this->equalTo(array('json')), + $this->equalTo($this->user)) + ->will($this->returnValue(null)); - $this->itemService->expects($this->once()) - ->method('starredCount') - ->with($this->equalTo($this->user)) - ->will($this->returnValue(3)); + $this->itemService->expects($this->once()) + ->method('starredCount') + ->with($this->equalTo($this->user)) + ->will($this->returnValue(3)); - $response = $this->controller->import(array('json')); + $response = $this->controller->import(array('json')); - $this->assertEquals(['starred' => 3], $response); - } + $this->assertEquals(['starred' => 3], $response); + } - public function testReadFeed(){ - $expected = [ - 'feeds' => [ - [ - 'id' => 4, - 'unreadCount' => 0 - ] - ] - ]; + public function testReadFeed(){ + $expected = [ + 'feeds' => [ + [ + 'id' => 4, + 'unreadCount' => 0 + ] + ] + ]; - $this->itemService->expects($this->once()) - ->method('readFeed') - ->with($this->equalTo(4), $this->equalTo(5), $this->user); + $this->itemService->expects($this->once()) + ->method('readFeed') + ->with($this->equalTo(4), $this->equalTo(5), $this->user); - $response = $this->controller->read(4, 5); - $this->assertEquals($expected, $response); - } + $response = $this->controller->read(4, 5); + $this->assertEquals($expected, $response); + } - public function testRestore() { - $this->feedService->expects($this->once()) - ->method('unmarkDeleted') - ->with($this->equalTo(4)); + public function testRestore() { + $this->feedService->expects($this->once()) + ->method('unmarkDeleted') + ->with($this->equalTo(4)); - $this->controller->restore(4); - } + $this->controller->restore(4); + } - public function testRestoreDoesNotExist(){ - $msg = 'hehe'; + public function testRestoreDoesNotExist(){ + $msg = 'hehe'; - $this->feedService->expects($this->once()) - ->method('unmarkDeleted') - ->will($this->throwException(new ServiceNotFoundException($msg))); + $this->feedService->expects($this->once()) + ->method('unmarkDeleted') + ->will($this->throwException(new ServiceNotFoundException($msg))); - $response = $this->controller->restore(4); - $params = json_decode($response->render(), true); + $response = $this->controller->restore(4); + $params = json_decode($response->render(), true); - $this->assertEquals($msg, $params['message']); - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - } + $this->assertEquals($msg, $params['message']); + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + } } diff --git a/tests/unit/controller/FolderApiControllerTest.php b/tests/unit/controller/FolderApiControllerTest.php index 22e038e16..c0371661a 100644 --- a/tests/unit/controller/FolderApiControllerTest.php +++ b/tests/unit/controller/FolderApiControllerTest.php @@ -27,209 +27,209 @@ use \OCA\News\Db\Item; class FolderApiControllerTest extends \PHPUnit_Framework_TestCase { - private $folderService; - private $itemService; - private $folderAPI; - private $appName; - private $user; - private $request; - private $msg; - - protected function setUp() { - $this->appName = 'news'; - $this->user = 'tom'; - $this->request = $this->getMockBuilder( - '\OCP\IRequest') - ->disableOriginalConstructor() - ->getMock(); - $this->folderService = $this->getMockBuilder( - '\OCA\News\Service\FolderService') - ->disableOriginalConstructor() - ->getMock(); - $this->itemService = $this->getMockBuilder( - '\OCA\News\Service\ItemService') - ->disableOriginalConstructor() - ->getMock(); - $this->folderAPI = new FolderApiController( - $this->appName, - $this->request, - $this->folderService, - $this->itemService, - $this->user - ); - $this->msg = 'test'; - } - - - public function testIndex() { - $folders = [new Folder()]; - - $this->folderService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($folders)); - - $response = $this->folderAPI->index(); - - $this->assertEquals([ - 'folders' => [$folders[0]->toAPI()] - ], $response); - } - - - public function testCreate() { - $folderName = 'test'; - $folder = new Folder(); - $folder->setName($folderName); - - $this->folderService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->folderService->expects($this->once()) - ->method('create') - ->with($this->equalTo($folderName), $this->equalTo($this->user)) - ->will($this->returnValue($folder)); - - $response = $this->folderAPI->create($folderName); - - $this->assertEquals([ - 'folders' => [$folder->toAPI()] - ], $response); - } - + private $folderService; + private $itemService; + private $folderAPI; + private $appName; + private $user; + private $request; + private $msg; + + protected function setUp() { + $this->appName = 'news'; + $this->user = 'tom'; + $this->request = $this->getMockBuilder( + '\OCP\IRequest') + ->disableOriginalConstructor() + ->getMock(); + $this->folderService = $this->getMockBuilder( + '\OCA\News\Service\FolderService') + ->disableOriginalConstructor() + ->getMock(); + $this->itemService = $this->getMockBuilder( + '\OCA\News\Service\ItemService') + ->disableOriginalConstructor() + ->getMock(); + $this->folderAPI = new FolderApiController( + $this->appName, + $this->request, + $this->folderService, + $this->itemService, + $this->user + ); + $this->msg = 'test'; + } + + + public function testIndex() { + $folders = [new Folder()]; + + $this->folderService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($folders)); + + $response = $this->folderAPI->index(); + + $this->assertEquals([ + 'folders' => [$folders[0]->toAPI()] + ], $response); + } + + + public function testCreate() { + $folderName = 'test'; + $folder = new Folder(); + $folder->setName($folderName); + + $this->folderService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->folderService->expects($this->once()) + ->method('create') + ->with($this->equalTo($folderName), $this->equalTo($this->user)) + ->will($this->returnValue($folder)); + + $response = $this->folderAPI->create($folderName); + + $this->assertEquals([ + 'folders' => [$folder->toAPI()] + ], $response); + } + - public function testCreateAlreadyExists() { - $msg = 'exists'; - - $this->folderService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->folderService->expects($this->once()) - ->method('create') - ->will($this->throwException(new ServiceConflictException($msg))); + public function testCreateAlreadyExists() { + $msg = 'exists'; + + $this->folderService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->folderService->expects($this->once()) + ->method('create') + ->will($this->throwException(new ServiceConflictException($msg))); - $response = $this->folderAPI->create('hi'); + $response = $this->folderAPI->create('hi'); - $data = $response->getData(); - $this->assertEquals($msg, $data['message']); - $this->assertEquals(Http::STATUS_CONFLICT, $response->getStatus()); - } + $data = $response->getData(); + $this->assertEquals($msg, $data['message']); + $this->assertEquals(Http::STATUS_CONFLICT, $response->getStatus()); + } - public function testCreateInvalidFolderName() { - $msg = 'exists'; + public function testCreateInvalidFolderName() { + $msg = 'exists'; - $this->folderService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->folderService->expects($this->once()) - ->method('create') - ->will($this->throwException(new ServiceValidationException($msg))); + $this->folderService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->folderService->expects($this->once()) + ->method('create') + ->will($this->throwException(new ServiceValidationException($msg))); - $response = $this->folderAPI->create('hi'); + $response = $this->folderAPI->create('hi'); - $data = $response->getData(); - $this->assertEquals($msg, $data['message']); - $this->assertEquals(Http::STATUS_UNPROCESSABLE_ENTITY, $response->getStatus()); - } + $data = $response->getData(); + $this->assertEquals($msg, $data['message']); + $this->assertEquals(Http::STATUS_UNPROCESSABLE_ENTITY, $response->getStatus()); + } - public function testDelete() { - $folderId = 23; - $this->folderService->expects($this->once()) - ->method('delete') - ->with($this->equalTo($folderId), $this->equalTo($this->user)); + public function testDelete() { + $folderId = 23; + $this->folderService->expects($this->once()) + ->method('delete') + ->with($this->equalTo($folderId), $this->equalTo($this->user)); - $this->folderAPI->delete(23); - } + $this->folderAPI->delete(23); + } - public function testDeleteDoesNotExist() { - $folderId = 23; + public function testDeleteDoesNotExist() { + $folderId = 23; - $this->folderService->expects($this->once()) - ->method('delete') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); + $this->folderService->expects($this->once()) + ->method('delete') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); - $response = $this->folderAPI->delete($folderId); + $response = $this->folderAPI->delete($folderId); - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); - } + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); + } - public function testUpdate() { - $folderId = 23; - $folderName = 'test'; + public function testUpdate() { + $folderId = 23; + $folderName = 'test'; - $this->folderService->expects($this->once()) - ->method('rename') - ->with($this->equalTo($folderId), - $this->equalTo($folderName), - $this->equalTo($this->user)); + $this->folderService->expects($this->once()) + ->method('rename') + ->with($this->equalTo($folderId), + $this->equalTo($folderName), + $this->equalTo($this->user)); - $this->folderAPI->update($folderId, $folderName); - } + $this->folderAPI->update($folderId, $folderName); + } - public function testUpdateDoesNotExist() { - $folderId = 23; - $folderName = 'test'; + public function testUpdateDoesNotExist() { + $folderId = 23; + $folderName = 'test'; - $this->folderService->expects($this->once()) - ->method('rename') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); + $this->folderService->expects($this->once()) + ->method('rename') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); - $response = $this->folderAPI->update($folderId, $folderName); + $response = $this->folderAPI->update($folderId, $folderName); - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); - } + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); + } - public function testUpdateExists() { - $folderId = 23; - $folderName = 'test'; + public function testUpdateExists() { + $folderId = 23; + $folderName = 'test'; - $this->folderService->expects($this->once()) - ->method('rename') - ->will($this->throwException(new ServiceConflictException($this->msg))); + $this->folderService->expects($this->once()) + ->method('rename') + ->will($this->throwException(new ServiceConflictException($this->msg))); - $response = $this->folderAPI->update($folderId, $folderName); + $response = $this->folderAPI->update($folderId, $folderName); - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_CONFLICT, $response->getStatus()); - } + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_CONFLICT, $response->getStatus()); + } - public function testUpdateInvalidFolderName() { - $folderId = 23; - $folderName = ''; + public function testUpdateInvalidFolderName() { + $folderId = 23; + $folderName = ''; - $this->folderService->expects($this->once()) - ->method('rename') - ->will($this->throwException(new ServiceValidationException($this->msg))); + $this->folderService->expects($this->once()) + ->method('rename') + ->will($this->throwException(new ServiceValidationException($this->msg))); - $response = $this->folderAPI->update($folderId, $folderName); + $response = $this->folderAPI->update($folderId, $folderName); - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_UNPROCESSABLE_ENTITY, $response->getStatus()); - } + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_UNPROCESSABLE_ENTITY, $response->getStatus()); + } - public function testRead() { - $this->itemService->expects($this->once()) - ->method('readFolder') - ->with( - $this->equalTo(3), - $this->equalTo(30), - $this->equalTo($this->user)); + public function testRead() { + $this->itemService->expects($this->once()) + ->method('readFolder') + ->with( + $this->equalTo(3), + $this->equalTo(30), + $this->equalTo($this->user)); - $this->folderAPI->read(3, 30); - } + $this->folderAPI->read(3, 30); + } } diff --git a/tests/unit/controller/FolderControllerTest.php b/tests/unit/controller/FolderControllerTest.php index 9ff293b2a..b06c97c79 100644 --- a/tests/unit/controller/FolderControllerTest.php +++ b/tests/unit/controller/FolderControllerTest.php @@ -24,275 +24,275 @@ use \OCA\News\Service\ServiceValidationException; class FolderControllerTest extends \PHPUnit_Framework_TestCase { - private $appName; - private $folderService; - private $itemService; - private $feedService; - private $request; - private $controller; - private $msg; - - - /** - * Gets run before each test - */ - public function setUp(){ - $this->appName = 'news'; - $this->user = 'jack'; - $this->folderService = $this->getMockBuilder( - '\OCA\News\Service\FolderService') - ->disableOriginalConstructor() - ->getMock(); - $this->feedService = $this->getMockBuilder( - '\OCA\News\Service\FeedService') - ->disableOriginalConstructor() - ->getMock(); - $this->itemService = $this->getMockBuilder( - '\OCA\News\Service\ItemService') - ->disableOriginalConstructor() - ->getMock(); - $this->request = $this->getMockBuilder( - '\OCP\IRequest') - ->disableOriginalConstructor() - ->getMock(); - $this->controller = new FolderController($this->appName, $this->request, - $this->folderService, - $this->feedService, - $this->itemService, - $this->user); - $this->msg = 'ron'; - } - - - - public function testIndex(){ - $return = [new Folder(), new Folder()]; - $this->folderService->expects($this->once()) - ->method('findAll') - ->will($this->returnValue($return)); - - $response = $this->controller->index(); - $expected = ['folders' => $return]; - $this->assertEquals($expected, $response); - } - - - public function testOpen(){ - $this->folderService->expects($this->once()) - ->method('open') - ->with($this->equalTo(3), - $this->equalTo(true), $this->equalTo($this->user)); - - $this->controller->open(3, true); - - } + private $appName; + private $folderService; + private $itemService; + private $feedService; + private $request; + private $controller; + private $msg; + + + /** + * Gets run before each test + */ + public function setUp(){ + $this->appName = 'news'; + $this->user = 'jack'; + $this->folderService = $this->getMockBuilder( + '\OCA\News\Service\FolderService') + ->disableOriginalConstructor() + ->getMock(); + $this->feedService = $this->getMockBuilder( + '\OCA\News\Service\FeedService') + ->disableOriginalConstructor() + ->getMock(); + $this->itemService = $this->getMockBuilder( + '\OCA\News\Service\ItemService') + ->disableOriginalConstructor() + ->getMock(); + $this->request = $this->getMockBuilder( + '\OCP\IRequest') + ->disableOriginalConstructor() + ->getMock(); + $this->controller = new FolderController($this->appName, $this->request, + $this->folderService, + $this->feedService, + $this->itemService, + $this->user); + $this->msg = 'ron'; + } + + + + public function testIndex(){ + $return = [new Folder(), new Folder()]; + $this->folderService->expects($this->once()) + ->method('findAll') + ->will($this->returnValue($return)); + + $response = $this->controller->index(); + $expected = ['folders' => $return]; + $this->assertEquals($expected, $response); + } + + + public function testOpen(){ + $this->folderService->expects($this->once()) + ->method('open') + ->with($this->equalTo(3), + $this->equalTo(true), $this->equalTo($this->user)); + + $this->controller->open(3, true); + + } - public function testOpenDoesNotExist(){ - $this->folderService->expects($this->once()) - ->method('open') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); - - $response = $this->controller->open(5, true); + public function testOpenDoesNotExist(){ + $this->folderService->expects($this->once()) + ->method('open') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); + + $response = $this->controller->open(5, true); - $params = json_decode($response->render(), true); + $params = json_decode($response->render(), true); - $this->assertEquals($this->msg, $params['message']); - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - } + $this->assertEquals($this->msg, $params['message']); + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + } - public function testCollapse(){ - $this->folderService->expects($this->once()) - ->method('open') - ->with($this->equalTo(5), - $this->equalTo(false), $this->equalTo($this->user)); + public function testCollapse(){ + $this->folderService->expects($this->once()) + ->method('open') + ->with($this->equalTo(5), + $this->equalTo(false), $this->equalTo($this->user)); - $this->controller->open(5, false); + $this->controller->open(5, false); - } + } - public function testCreate(){ - $result = ['folders' => [new Folder()]]; + public function testCreate(){ + $result = ['folders' => [new Folder()]]; - $this->folderService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->folderService->expects($this->once()) - ->method('create') - ->with($this->equalTo('tech'), - $this->equalTo($this->user)) - ->will($this->returnValue($result['folders'][0])); + $this->folderService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->folderService->expects($this->once()) + ->method('create') + ->with($this->equalTo('tech'), + $this->equalTo($this->user)) + ->will($this->returnValue($result['folders'][0])); - $response = $this->controller->create('tech'); + $response = $this->controller->create('tech'); - $this->assertEquals($result, $response); - } + $this->assertEquals($result, $response); + } - public function testCreateReturnsErrorForInvalidCreate(){ - $msg = 'except'; - $ex = new ServiceValidationException($msg); - $this->folderService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->folderService->expects($this->once()) - ->method('create') - ->will($this->throwException($ex)); + public function testCreateReturnsErrorForInvalidCreate(){ + $msg = 'except'; + $ex = new ServiceValidationException($msg); + $this->folderService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->folderService->expects($this->once()) + ->method('create') + ->will($this->throwException($ex)); - $response = $this->controller->create('tech'); - $params = json_decode($response->render(), true); + $response = $this->controller->create('tech'); + $params = json_decode($response->render(), true); - $this->assertEquals($response->getStatus(), Http::STATUS_UNPROCESSABLE_ENTITY); - $this->assertEquals($msg, $params['message']); - } + $this->assertEquals($response->getStatus(), Http::STATUS_UNPROCESSABLE_ENTITY); + $this->assertEquals($msg, $params['message']); + } - public function testCreateReturnsErrorForDuplicateCreate(){ - $msg = 'except'; - $ex = new ServiceConflictException($msg); - $this->folderService->expects($this->once()) - ->method('purgeDeleted') - ->with($this->equalTo($this->user), $this->equalTo(false)); - $this->folderService->expects($this->once()) - ->method('create') - ->will($this->throwException($ex)); + public function testCreateReturnsErrorForDuplicateCreate(){ + $msg = 'except'; + $ex = new ServiceConflictException($msg); + $this->folderService->expects($this->once()) + ->method('purgeDeleted') + ->with($this->equalTo($this->user), $this->equalTo(false)); + $this->folderService->expects($this->once()) + ->method('create') + ->will($this->throwException($ex)); - $response = $this->controller->create('tech'); - $params = json_decode($response->render(), true); + $response = $this->controller->create('tech'); + $params = json_decode($response->render(), true); - $this->assertEquals($response->getStatus(), Http::STATUS_CONFLICT); - $this->assertEquals($msg, $params['message']); - } + $this->assertEquals($response->getStatus(), Http::STATUS_CONFLICT); + $this->assertEquals($msg, $params['message']); + } - public function testDelete(){ - $this->folderService->expects($this->once()) - ->method('markDeleted') - ->with($this->equalTo(5), - $this->equalTo($this->user)); + public function testDelete(){ + $this->folderService->expects($this->once()) + ->method('markDeleted') + ->with($this->equalTo(5), + $this->equalTo($this->user)); - $this->controller->delete(5); - } + $this->controller->delete(5); + } - public function testDeleteDoesNotExist(){ - $this->folderService->expects($this->once()) - ->method('markDeleted') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); + public function testDeleteDoesNotExist(){ + $this->folderService->expects($this->once()) + ->method('markDeleted') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); - $response = $this->controller->delete(5); + $response = $this->controller->delete(5); - $params = json_decode($response->render(), true); + $params = json_decode($response->render(), true); - $this->assertEquals($this->msg, $params['message']); - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - } + $this->assertEquals($this->msg, $params['message']); + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + } - public function testRename(){ - $result = ['folders' => [new Folder()]]; + public function testRename(){ + $result = ['folders' => [new Folder()]]; - $this->folderService->expects($this->once()) - ->method('rename') - ->with($this->equalTo(4), - $this->equalTo('tech'), - $this->equalTo($this->user)) - ->will($this->returnValue($result['folders'][0])); + $this->folderService->expects($this->once()) + ->method('rename') + ->with($this->equalTo(4), + $this->equalTo('tech'), + $this->equalTo($this->user)) + ->will($this->returnValue($result['folders'][0])); - $response = $this->controller->rename('tech', 4); + $response = $this->controller->rename('tech', 4); - $this->assertEquals($result, $response); - } + $this->assertEquals($result, $response); + } - public function testRenameReturnsErrorForInvalidCreate(){ - $msg = 'except'; - $ex = new ServiceValidationException($msg); - $this->folderService->expects($this->once()) - ->method('rename') - ->will($this->throwException($ex)); + public function testRenameReturnsErrorForInvalidCreate(){ + $msg = 'except'; + $ex = new ServiceValidationException($msg); + $this->folderService->expects($this->once()) + ->method('rename') + ->will($this->throwException($ex)); - $response = $this->controller->rename('tech', 4); - $params = json_decode($response->render(), true); + $response = $this->controller->rename('tech', 4); + $params = json_decode($response->render(), true); - $this->assertEquals($response->getStatus(), Http::STATUS_UNPROCESSABLE_ENTITY); - $this->assertEquals($msg, $params['message']); - } + $this->assertEquals($response->getStatus(), Http::STATUS_UNPROCESSABLE_ENTITY); + $this->assertEquals($msg, $params['message']); + } - public function testRenameDoesNotExist(){ - $msg = 'except'; - $ex = new ServiceNotFoundException($msg); - $this->folderService->expects($this->once()) - ->method('rename') - ->will($this->throwException($ex)); + public function testRenameDoesNotExist(){ + $msg = 'except'; + $ex = new ServiceNotFoundException($msg); + $this->folderService->expects($this->once()) + ->method('rename') + ->will($this->throwException($ex)); - $response = $this->controller->rename('tech', 5); - $params = json_decode($response->render(), true); + $response = $this->controller->rename('tech', 5); + $params = json_decode($response->render(), true); - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - $this->assertEquals($msg, $params['message']); - } + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + $this->assertEquals($msg, $params['message']); + } - public function testRenameReturnsErrorForDuplicateCreate(){ - $msg = 'except'; - $ex = new ServiceConflictException($msg); - $this->folderService->expects($this->once()) - ->method('rename') - ->will($this->throwException($ex)); + public function testRenameReturnsErrorForDuplicateCreate(){ + $msg = 'except'; + $ex = new ServiceConflictException($msg); + $this->folderService->expects($this->once()) + ->method('rename') + ->will($this->throwException($ex)); - $response = $this->controller->rename('tech', 1); - $params = json_decode($response->render(), true); + $response = $this->controller->rename('tech', 1); + $params = json_decode($response->render(), true); - $this->assertEquals($response->getStatus(), Http::STATUS_CONFLICT); - $this->assertEquals($msg, $params['message']); - } + $this->assertEquals($response->getStatus(), Http::STATUS_CONFLICT); + $this->assertEquals($msg, $params['message']); + } - public function testRead(){ - $feed = new Feed(); - $expected = ['feeds' => [$feed]]; + public function testRead(){ + $feed = new Feed(); + $expected = ['feeds' => [$feed]]; - $this->itemService->expects($this->once()) - ->method('readFolder') - ->with($this->equalTo(4), - $this->equalTo(5), - $this->equalTo($this->user)); - $this->feedService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue([$feed])); + $this->itemService->expects($this->once()) + ->method('readFolder') + ->with($this->equalTo(4), + $this->equalTo(5), + $this->equalTo($this->user)); + $this->feedService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue([$feed])); - $response = $this->controller->read(4, 5); - $this->assertEquals($expected, $response); - } + $response = $this->controller->read(4, 5); + $this->assertEquals($expected, $response); + } - public function testRestore(){ - $this->folderService->expects($this->once()) - ->method('unmarkDeleted') - ->with($this->equalTo(5), - $this->equalTo($this->user)); + public function testRestore(){ + $this->folderService->expects($this->once()) + ->method('unmarkDeleted') + ->with($this->equalTo(5), + $this->equalTo($this->user)); - $this->controller->restore(5); - } + $this->controller->restore(5); + } - public function testRestoreDoesNotExist(){ - $this->folderService->expects($this->once()) - ->method('unmarkDeleted') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); + public function testRestoreDoesNotExist(){ + $this->folderService->expects($this->once()) + ->method('unmarkDeleted') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); - $response = $this->controller->restore(5); + $response = $this->controller->restore(5); - $params = json_decode($response->render(), true); + $params = json_decode($response->render(), true); - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - $this->assertEquals($this->msg, $params['message']); - } + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + $this->assertEquals($this->msg, $params['message']); + } }
\ No newline at end of file diff --git a/tests/unit/controller/ItemApiControllerTest.php b/tests/unit/controller/ItemApiControllerTest.php index f2bbd92b6..12b9d3225 100644 --- a/tests/unit/controller/ItemApiControllerTest.php +++ b/tests/unit/controller/ItemApiControllerTest.php @@ -21,344 +21,344 @@ use \OCA\News\Db\Item; class ItemApiControllerTest extends \PHPUnit_Framework_TestCase { - private $itemService; - private $itemAPI; - private $api; - private $user; - private $request; - private $msg; - - protected function setUp() { - $this->user = 'tom'; - $this->appName = 'news'; - $this->request = $this->getMockBuilder( - '\OCP\IRequest') - ->disableOriginalConstructor() - ->getMock(); - $this->itemService = $this->getMockBuilder( - '\OCA\News\Service\ItemService') - ->disableOriginalConstructor() - ->getMock(); - $this->itemAPI = new ItemApiController( - $this->appName, - $this->request, - $this->itemService, - $this->user - ); - $this->msg = 'hi'; - } - - - public function testIndex() { - $items = [new Item()]; - - $this->itemService->expects($this->once()) - ->method('findAll') - ->with( - $this->equalTo(2), - $this->equalTo(1), - $this->equalTo(30), - $this->equalTo(20), - $this->equalTo(true), - $this->equalTo(true), - $this->equalTo($this->user) - ) - ->will($this->returnValue($items)); - - $response = $this->itemAPI->index(1, 2, true, 30, 20, true); - - $this->assertEquals([ - 'items' => [$items[0]->toApi()] - ], $response); - } - - - public function testIndexDefaultBatchSize() { - $items = [new Item()]; - - $this->itemService->expects($this->once()) - ->method('findAll') - ->with( - $this->equalTo(2), - $this->equalTo(1), - $this->equalTo(20), - $this->equalTo(0), - $this->equalTo(false), - $this->equalTo(false), - $this->equalTo($this->user) - ) - ->will($this->returnValue($items)); - - $response = $this->itemAPI->index(1, 2, false); - - $this->assertEquals([ - 'items' => [$items[0]->toApi()] - ], $response); - } - - - public function testUpdated() { - $items = [new Item()]; - - $this->itemService->expects($this->once()) - ->method('findAllNew') - ->with( - $this->equalTo(2), - $this->equalTo(1), - $this->equalTo(30), - $this->equalTo(true), - $this->equalTo($this->user) - ) - ->will($this->returnValue($items)); - - $response = $this->itemAPI->updated(1, 2, 30); - - $this->assertEquals([ - 'items' => [$items[0]->toApi()] - ], $response); - } - - - public function testRead() { - $this->itemService->expects($this->once()) - ->method('read') - ->with( - $this->equalTo(2), - $this->equalTo(true), - $this->equalTo($this->user) - ); - - $this->itemAPI->read(2); - } - - - public function testReadDoesNotExist() { - $this->itemService->expects($this->once()) - ->method('read') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); - - $response = $this->itemAPI->read(2); - - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); - } - - - public function testUnread() { - $this->itemService->expects($this->once()) - ->method('read') - ->with( - $this->equalTo(2), - $this->equalTo(false), - $this->equalTo($this->user) - ); - - $this->itemAPI->unread(2); - } - - - public function testUnreadDoesNotExist() { - $this->itemService->expects($this->once()) - ->method('read') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); - - $response = $this->itemAPI->unread(2); + private $itemService; + private $itemAPI; + private $api; + private $user; + private $request; + private $msg; + + protected function setUp() { + $this->user = 'tom'; + $this->appName = 'news'; + $this->request = $this->getMockBuilder( + '\OCP\IRequest') + ->disableOriginalConstructor() + ->getMock(); + $this->itemService = $this->getMockBuilder( + '\OCA\News\Service\ItemService') + ->disableOriginalConstructor() + ->getMock(); + $this->itemAPI = new ItemApiController( + $this->appName, + $this->request, + $this->itemService, + $this->user + ); + $this->msg = 'hi'; + } + + + public function testIndex() { + $items = [new Item()]; + + $this->itemService->expects($this->once()) + ->method('findAll') + ->with( + $this->equalTo(2), + $this->equalTo(1), + $this->equalTo(30), + $this->equalTo(20), + $this->equalTo(true), + $this->equalTo(true), + $this->equalTo($this->user) + ) + ->will($this->returnValue($items)); + + $response = $this->itemAPI->index(1, 2, true, 30, 20, true); + + $this->assertEquals([ + 'items' => [$items[0]->toApi()] + ], $response); + } + + + public function testIndexDefaultBatchSize() { + $items = [new Item()]; + + $this->itemService->expects($this->once()) + ->method('findAll') + ->with( + $this->equalTo(2), + $this->equalTo(1), + $this->equalTo(20), + $this->equalTo(0), + $this->equalTo(false), + $this->equalTo(false), + $this->equalTo($this->user) + ) + ->will($this->returnValue($items)); + + $response = $this->itemAPI->index(1, 2, false); + + $this->assertEquals([ + 'items' => [$items[0]->toApi()] + ], $response); + } + + + public function testUpdated() { + $items = [new Item()]; + + $this->itemService->expects($this->once()) + ->method('findAllNew') + ->with( + $this->equalTo(2), + $this->equalTo(1), + $this->equalTo(30), + $this->equalTo(true), + $this->equalTo($this->user) + ) + ->will($this->returnValue($items)); + + $response = $this->itemAPI->updated(1, 2, 30); + + $this->assertEquals([ + 'items' => [$items[0]->toApi()] + ], $response); + } + + + public function testRead() { + $this->itemService->expects($this->once()) + ->method('read') + ->with( + $this->equalTo(2), + $this->equalTo(true), + $this->equalTo($this->user) + ); + + $this->itemAPI->read(2); + } + + + public function testReadDoesNotExist() { + $this->itemService->expects($this->once()) + ->method('read') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); + + $response = $this->itemAPI->read(2); + + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); + } + + + public function testUnread() { + $this->itemService->expects($this->once()) + ->method('read') + ->with( + $this->equalTo(2), + $this->equalTo(false), + $this->equalTo($this->user) + ); + + $this->itemAPI->unread(2); + } + + + public function testUnreadDoesNotExist() { + $this->itemService->expects($this->once()) + ->method('read') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); + + $response = $this->itemAPI->unread(2); - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); - } - - - public function testStar() { - $this->itemService->expects($this->once()) - ->method('star') - ->with( - $this->equalTo(2), - $this->equalTo('hash'), - $this->equalTo(true), - $this->equalTo($this->user) - ); - - $this->itemAPI->star(2, 'hash'); - } - - - public function testStarDoesNotExist() { - $this->itemService->expects($this->once()) - ->method('star') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); - - $response = $this->itemAPI->star(2, 'test'); - - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); - } - - - public function testUnstar() { - $this->itemService->expects($this->once()) - ->method('star') - ->with( - $this->equalTo(2), - $this->equalTo('hash'), - $this->equalTo(false), - $this->equalTo($this->user) - ); - - $this->itemAPI->unstar(2, 'hash'); - } - - - public function testUnstarDoesNotExist() { - $this->itemService->expects($this->once()) - ->method('star') - ->will($this->throwException(new ServiceNotFoundException($this->msg))); - - $response = $this->itemAPI->unstar(2, 'test'); - - $data = $response->getData(); - $this->assertEquals($this->msg, $data['message']); - $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); - } - - - public function testReadAll() { - $this->itemService->expects($this->once()) - ->method('readAll') - ->with( - $this->equalTo(30), - $this->equalTo($this->user)); - - $this->itemAPI->readAll(30); - } - - - - public function testReadMultiple() { - $this->itemService->expects($this->at(0)) - ->method('read') - ->with($this->equalTo(2), - $this->equalTo(true), - $this->equalTo($this->user)); - $this->itemService->expects($this->at(1)) - ->method('read') - ->with($this->equalTo(4), - $this->equalTo(true), - $this->equalTo($this->user)); - $this->itemAPI->readMultiple([2, 4]); - } - - - public function testReadMultipleDoesntCareAboutException() { - $this->itemService->expects($this->at(0)) - ->method('read') - ->will($this->throwException(new ServiceNotFoundException(''))); - $this->itemService->expects($this->at(1)) - ->method('read') - ->with($this->equalTo(4), - $this->equalTo(true), - $this->equalTo($this->user)); - $this->itemAPI->readMultiple([2, 4]); - } - - - public function testUnreadMultiple() { - $this->itemService->expects($this->at(0)) - ->method('read') - ->with($this->equalTo(2), - $this->equalTo(false), - $this->equalTo($this->user)); - $this->itemService->expects($this->at(1)) - ->method('read') - ->with($this->equalTo(4), - $this->equalTo(false), - $this->equalTo($this->user)); - $this->itemAPI->unreadMultiple([2, 4]); - } - - - public function testStarMultiple() { - $ids = [ - [ - 'feedId' => 2, - 'guidHash' => 'a' - ], - [ - 'feedId' => 4, - 'guidHash' => 'b' - ] - ]; - - $this->itemService->expects($this->at(0)) - ->method('star') - ->with($this->equalTo(2), - $this->equalTo('a'), - $this->equalTo(true), - $this->equalTo($this->user)); - $this->itemService->expects($this->at(1)) - ->method('star') - ->with($this->equalTo(4), - $this->equalTo('b'), - $this->equalTo(true), - $this->equalTo($this->user)); - $this->itemAPI->starMultiple($ids); - } - - - public function testStarMultipleDoesntCareAboutException() { - $ids = [ - [ - 'feedId' => 2, - 'guidHash' => 'a' - ], - [ - 'feedId' => 4, - 'guidHash' => 'b' - ] - ]; - - $this->itemService->expects($this->at(0)) - ->method('star') - ->will($this->throwException(new ServiceNotFoundException(''))); - $this->itemService->expects($this->at(1)) - ->method('star') - ->with($this->equalTo(4), - $this->equalTo('b'), - $this->equalTo(true), - $this->equalTo($this->user)); - $this->itemAPI->starMultiple($ids); - } - - - public function testUnstarMultiple() { - $ids = [ - [ - 'feedId' => 2, - 'guidHash' => 'a' - ], - [ - 'feedId' => 4, - 'guidHash' => 'b' - ] - ]; - - $this->itemService->expects($this->at(0)) - ->method('star') - ->with($this->equalTo(2), - $this->equalTo('a'), - $this->equalTo(false), - $this->equalTo($this->user)); - $this->itemService->expects($this->at(1)) - ->method('star') - ->with($this->equalTo(4), - $this->equalTo('b'), - $this->equalTo(false), - $this->equalTo($this->user)); - $this->itemAPI->unstarMultiple($ids); - } + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); + } + + + public function testStar() { + $this->itemService->expects($this->once()) + ->method('star') + ->with( + $this->equalTo(2), + $this->equalTo('hash'), + $this->equalTo(true), + $this->equalTo($this->user) + ); + + $this->itemAPI->star(2, 'hash'); + } + + + public function testStarDoesNotExist() { + $this->itemService->expects($this->once()) + ->method('star') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); + + $response = $this->itemAPI->star(2, 'test'); + + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); + } + + + public function testUnstar() { + $this->itemService->expects($this->once()) + ->method('star') + ->with( + $this->equalTo(2), + $this->equalTo('hash'), + $this->equalTo(false), + $this->equalTo($this->user) + ); + + $this->itemAPI->unstar(2, 'hash'); + } + + + public function testUnstarDoesNotExist() { + $this->itemService->expects($this->once()) + ->method('star') + ->will($this->throwException(new ServiceNotFoundException($this->msg))); + + $response = $this->itemAPI->unstar(2, 'test'); + + $data = $response->getData(); + $this->assertEquals($this->msg, $data['message']); + $this->assertEquals(Http::STATUS_NOT_FOUND, $response->getStatus()); + } + + + public function testReadAll() { + $this->itemService->expects($this->once()) + ->method('readAll') + ->with( + $this->equalTo(30), + $this->equalTo($this->user)); + + $this->itemAPI->readAll(30); + } + + + + public function testReadMultiple() { + $this->itemService->expects($this->at(0)) + ->method('read') + ->with($this->equalTo(2), + $this->equalTo(true), + $this->equalTo($this->user)); + $this->itemService->expects($this->at(1)) + ->method('read') + ->with($this->equalTo(4), + $this->equalTo(true), + $this->equalTo($this->user)); + $this->itemAPI->readMultiple([2, 4]); + } + + + public function testReadMultipleDoesntCareAboutException() { + $this->itemService->expects($this->at(0)) + ->method('read') + ->will($this->throwException(new ServiceNotFoundException(''))); + $this->itemService->expects($this->at(1)) + ->method('read') + ->with($this->equalTo(4), + $this->equalTo(true), + $this->equalTo($this->user)); + $this->itemAPI->readMultiple([2, 4]); + } + + + public function testUnreadMultiple() { + $this->itemService->expects($this->at(0)) + ->method('read') + ->with($this->equalTo(2), + $this->equalTo(false), + $this->equalTo($this->user)); + $this->itemService->expects($this->at(1)) + ->method('read') + ->with($this->equalTo(4), + $this->equalTo(false), + $this->equalTo($this->user)); + $this->itemAPI->unreadMultiple([2, 4]); + } + + + public function testStarMultiple() { + $ids = [ + [ + 'feedId' => 2, + 'guidHash' => 'a' + ], + [ + 'feedId' => 4, + 'guidHash' => 'b' + ] + ]; + + $this->itemService->expects($this->at(0)) + ->method('star') + ->with($this->equalTo(2), + $this->equalTo('a'), + $this->equalTo(true), + $this->equalTo($this->user)); + $this->itemService->expects($this->at(1)) + ->method('star') + ->with($this->equalTo(4), + $this->equalTo('b'), + $this->equalTo(true), + $this->equalTo($this->user)); + $this->itemAPI->starMultiple($ids); + } + + + public function testStarMultipleDoesntCareAboutException() { + $ids = [ + [ + 'feedId' => 2, + 'guidHash' => 'a' + ], + [ + 'feedId' => 4, + 'guidHash' => 'b' + ] + ]; + + $this->itemService->expects($this->at(0)) + ->method('star') + ->will($this->throwException(new ServiceNotFoundException(''))); + $this->itemService->expects($this->at(1)) + ->method('star') + ->with($this->equalTo(4), + $this->equalTo('b'), + $this->equalTo(true), + $this->equalTo($this->user)); + $this->itemAPI->starMultiple($ids); + } + + + public function testUnstarMultiple() { + $ids = [ + [ + 'feedId' => 2, + 'guidHash' => 'a' + ], + [ + 'feedId' => 4, + 'guidHash' => 'b' + ] + ]; + + $this->itemService->expects($this->at(0)) + ->method('star') + ->with($this->equalTo(2), + $this->equalTo('a'), + $this->equalTo(false), + $this->equalTo($this->user)); + $this->itemService->expects($this->at(1)) + ->method('star') + ->with($this->equalTo(4), + $this->equalTo('b'), + $this->equalTo(false), + $this->equalTo($this->user)); + $this->itemAPI->unstarMultiple($ids); + } } diff --git a/tests/unit/controller/ItemControllerTest.php b/tests/unit/controller/ItemControllerTest.php index b366fdfa0..fd0904ef7 100644 --- a/tests/unit/controller/ItemControllerTest.php +++ b/tests/unit/controller/ItemControllerTest.php @@ -23,316 +23,316 @@ use \OCA\News\Service\ServiceNotFoundException; class ItemControllerTest extends \PHPUnit_Framework_TestCase { - private $appName; - private $settings; - private $itemService; - private $feedService; - private $request; - private $controller; - private $newestItemId; - - - /** - * Gets run before each test - */ - public function setUp(){ - $this->appName = 'news'; - $this->user = 'jackob'; - $this->settings = $this->getMockBuilder( - '\OCP\IConfig') - ->disableOriginalConstructor() - ->getMock(); - $this->itemService = - $this->getMockBuilder('\OCA\News\Service\ItemService') - ->disableOriginalConstructor() - ->getMock(); - $this->feedService = - $this->getMockBuilder('\OCA\News\Service\FeedService') - ->disableOriginalConstructor() - ->getMock(); - $this->request = $this->getMockBuilder( - '\OCP\IRequest') - ->disableOriginalConstructor() - ->getMock(); - $this->controller = new ItemController($this->appName, $this->request, - $this->feedService, $this->itemService, $this->settings, - $this->user); - $this->newestItemId = 12312; - } - - - public function testRead(){ - $this->itemService->expects($this->once()) - ->method('read') - ->with(4, true, $this->user); - - $this->controller->read(4, true); - } - - - public function testReadDoesNotExist(){ - $msg = 'hi'; - - $this->itemService->expects($this->once()) - ->method('read') - ->will($this->throwException(new ServiceNotFoundException($msg))); - - $response = $this->controller->read(4); - $params = json_decode($response->render(), true); - - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - $this->assertEquals($msg, $params['message']); - } - - - public function testReadMultiple() { - $this->itemService->expects($this->at(0)) - ->method('read') - ->with($this->equalTo(2), - $this->equalTo(true), - $this->equalTo($this->user)); - $this->itemService->expects($this->at(1)) - ->method('read') - ->with($this->equalTo(4), - $this->equalTo(true), - $this->equalTo($this->user)); - $this->controller->readMultiple([2, 4]); - } - - - public function testReadMultipleDontStopOnException() { - $this->itemService->expects($this->at(0)) - ->method('read') - ->with($this->equalTo(2), - $this->equalTo(true), - $this->equalTo($this->user)) - ->will($this->throwException(new ServiceNotFoundException('yo'))); - $this->itemService->expects($this->at(1)) - ->method('read') - ->with($this->equalTo(4), - $this->equalTo(true), - $this->equalTo($this->user)); - $this->controller->readMultiple([2, 4]); - } - - - public function testStar(){ - $this->itemService->expects($this->once()) - ->method('star') - ->with( - $this->equalTo(4), - $this->equalTo('test'), - $this->equalTo(true), - $this->equalTo($this->user)); - - $this->controller->star(4, 'test', true); - } - - - public function testStarDoesNotExist(){ - $msg = 'ho'; - - $this->itemService->expects($this->once()) - ->method('star') - ->will($this->throwException(new ServiceNotFoundException($msg)));; - - $response = $this->controller->star(4, 'test', false); - $params = json_decode($response->render(), true); - - $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); - $this->assertEquals($msg, $params['message']); - } - - - public function testReadAll(){ - $feed = new Feed(); - - $expected = ['feeds' => [$feed]]; - - $this->itemService->expects($this->once()) - ->method('readAll') - ->with($this->equalTo(5), - $this->equalTo($this->user)); - $this->feedService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue([$feed])); - - $response = $this->controller->readAll(5); - $this->assertEquals($expected, $response); - } - - - private function itemsApiExpects($id, $type, $oldestFirst='1'){ - $this->settings->expects($this->at(0)) - ->method('getUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('showAll')) - ->will($this->returnValue('1')); - $this->settings->expects($this->at(1)) - ->method('getUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('oldestFirst')) - ->will($this->returnValue($oldestFirst)); - $this->settings->expects($this->at(2)) - ->method('setUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('lastViewedFeedId'), - $this->equalTo($id)); - $this->settings->expects($this->at(3)) - ->method('setUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('lastViewedFeedType'), - $this->equalTo($type)); - } - - - public function testIndex(){ - $feeds = [new Feed()]; - $result = [ - 'items' => [new Item()], - 'feeds' => $feeds, - 'newestItemId' => $this->newestItemId, - 'starred' => 3111 - ]; - - $this->itemsApiExpects(2, FeedType::FEED, '0'); - - $this->feedService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($this->newestItemId)); - - $this->itemService->expects($this->once()) - ->method('starredCount') - ->with($this->equalTo($this->user)) - ->will($this->returnValue(3111)); - - $this->itemService->expects($this->once()) - ->method('findAll') - ->with( - $this->equalTo(2), - $this->equalTo(FeedType::FEED), - $this->equalTo(3), - $this->equalTo(0), - $this->equalTo(true), - $this->equalTo(false), - $this->equalTo($this->user)) - ->will($this->returnValue($result['items'])); - - $response = $this->controller->index(FeedType::FEED, 2, 3); - $this->assertEquals($result, $response); - } - - - public function testItemsOffsetNotZero(){ - $result = ['items' => [new Item()]]; - - $this->itemsApiExpects(2, FeedType::FEED); - - $this->itemService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo(2), - $this->equalTo(FeedType::FEED), - $this->equalTo(3), - $this->equalTo(10), - $this->equalTo(true), - $this->equalTo(true), - $this->equalTo($this->user)) - ->will($this->returnValue($result['items'])); - - $this->feedService->expects($this->never()) - ->method('findAll'); - - $response = $this->controller->index(FeedType::FEED, 2, 3, 10); - $this->assertEquals($result, $response); - } - - - public function testGetItemsNoNewestItemsId(){ - $this->itemsApiExpects(2, FeedType::FEED); - - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->with($this->equalTo($this->user)) - ->will($this->throwException(new ServiceNotFoundException(''))); - - $response = $this->controller->index(FeedType::FEED, 2, 3); - $this->assertEquals([], $response); - } - - - public function testNewItems(){ - $feeds = [new Feed()]; - $result = [ - 'items' => [new Item()], - 'feeds' => $feeds, - 'newestItemId' => $this->newestItemId, - 'starred' => 3111 - ]; - - $this->settings->expects($this->once()) - ->method('getUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('showAll')) - ->will($this->returnValue('1')); - - $this->feedService->expects($this->once()) - ->method('findAll') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($this->newestItemId)); - - $this->itemService->expects($this->once()) - ->method('starredCount') - ->with($this->equalTo($this->user)) - ->will($this->returnValue(3111)); - - $this->itemService->expects($this->once()) - ->method('findAllNew') - ->with( - $this->equalTo(2), - $this->equalTo(FeedType::FEED), - $this->equalTo(3), - $this->equalTo(true), - $this->equalTo($this->user)) - ->will($this->returnValue($result['items'])); - - $response = $this->controller->newItems(FeedType::FEED, 2, 3); - $this->assertEquals($result, $response); - } - - - public function testGetNewItemsNoNewestItemsId(){ - $this->settings->expects($this->once()) - ->method('getUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('showAll')) - ->will($this->returnValue('1')); - - $this->itemService->expects($this->once()) - ->method('getNewestItemId') - ->with($this->equalTo($this->user)) - ->will($this->throwException(new ServiceNotFoundException(''))); - - $response = $this->controller->newItems(FeedType::FEED, 2, 3); - $this->assertEquals([], $response); - } + private $appName; + private $settings; + private $itemService; + private $feedService; + private $request; + private $controller; + private $newestItemId; + + + /** + * Gets run before each test + */ + public function setUp(){ + $this->appName = 'news'; + $this->user = 'jackob'; + $this->settings = $this->getMockBuilder( + '\OCP\IConfig') + ->disableOriginalConstructor() + ->getMock(); + $this->itemService = + $this->getMockBuilder('\OCA\News\Service\ItemService') + ->disableOriginalConstructor() + ->getMock(); + $this->feedService = + $this->getMockBuilder('\OCA\News\Service\FeedService') + ->disableOriginalConstructor() + ->getMock(); + $this->request = $this->getMockBuilder( + '\OCP\IRequest') + ->disableOriginalConstructor() + ->getMock(); + $this->controller = new ItemController($this->appName, $this->request, + $this->feedService, $this->itemService, $this->settings, + $this->user); + $this->newestItemId = 12312; + } + + + public function testRead(){ + $this->itemService->expects($this->once()) + ->method('read') + ->with(4, true, $this->user); + + $this->controller->read(4, true); + } + + + public function testReadDoesNotExist(){ + $msg = 'hi'; + + $this->itemService->expects($this->once()) + ->method('read') + ->will($this->throwException(new ServiceNotFoundException($msg))); + + $response = $this->controller->read(4); + $params = json_decode($response->render(), true); + + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + $this->assertEquals($msg, $params['message']); + } + + + public function testReadMultiple() { + $this->itemService->expects($this->at(0)) + ->method('read') + ->with($this->equalTo(2), + $this->equalTo(true), + $this->equalTo($this->user)); + $this->itemService->expects($this->at(1)) + ->method('read') + ->with($this->equalTo(4), + $this->equalTo(true), + $this->equalTo($this->user)); + $this->controller->readMultiple([2, 4]); + } + + + public function testReadMultipleDontStopOnException() { + $this->itemService->expects($this->at(0)) + ->method('read') + ->with($this->equalTo(2), + $this->equalTo(true), + $this->equalTo($this->user)) + ->will($this->throwException(new ServiceNotFoundException('yo'))); + $this->itemService->expects($this->at(1)) + ->method('read') + ->with($this->equalTo(4), + $this->equalTo(true), + $this->equalTo($this->user)); + $this->controller->readMultiple([2, 4]); + } + + + public function testStar(){ + $this->itemService->expects($this->once()) + ->method('star') + ->with( + $this->equalTo(4), + $this->equalTo('test'), + $this->equalTo(true), + $this->equalTo($this->user)); + + $this->controller->star(4, 'test', true); + } + + + public function testStarDoesNotExist(){ + $msg = 'ho'; + + $this->itemService->expects($this->once()) + ->method('star') + ->will($this->throwException(new ServiceNotFoundException($msg)));; + + $response = $this->controller->star(4, 'test', false); + $params = json_decode($response->render(), true); + + $this->assertEquals($response->getStatus(), Http::STATUS_NOT_FOUND); + $this->assertEquals($msg, $params['message']); + } + + + public function testReadAll(){ + $feed = new Feed(); + + $expected = ['feeds' => [$feed]]; + + $this->itemService->expects($this->once()) + ->method('readAll') + ->with($this->equalTo(5), + $this->equalTo($this->user)); + $this->feedService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue([$feed])); + + $response = $this->controller->readAll(5); + $this->assertEquals($expected, $response); + } + + + private function itemsApiExpects($id, $type, $oldestFirst='1'){ + $this->settings->expects($this->at(0)) + ->method('getUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('showAll')) + ->will($this->returnValue('1')); + $this->settings->expects($this->at(1)) + ->method('getUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('oldestFirst')) + ->will($this->returnValue($oldestFirst)); + $this->settings->expects($this->at(2)) + ->method('setUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('lastViewedFeedId'), + $this->equalTo($id)); + $this->settings->expects($this->at(3)) + ->method('setUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('lastViewedFeedType'), + $this->equalTo($type)); + } + + + public function testIndex(){ + $feeds = [new Feed()]; + $result = [ + 'items' => [new Item()], + 'feeds' => $feeds, + 'newestItemId' => $this->newestItemId, + 'starred' => 3111 + ]; + + $this->itemsApiExpects(2, FeedType::FEED, '0'); + + $this->feedService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($this->newestItemId)); + + $this->itemService->expects($this->once()) + ->method('starredCount') + ->with($this->equalTo($this->user)) + ->will($this->returnValue(3111)); + + $this->itemService->expects($this->once()) + ->method('findAll') + ->with( + $this->equalTo(2), + $this->equalTo(FeedType::FEED), + $this->equalTo(3), + $this->equalTo(0), + $this->equalTo(true), + $this->equalTo(false), + $this->equalTo($this->user)) + ->will($this->returnValue($result['items'])); + + $response = $this->controller->index(FeedType::FEED, 2, 3); + $this->assertEquals($result, $response); + } + + + public function testItemsOffsetNotZero(){ + $result = ['items' => [new Item()]]; + + $this->itemsApiExpects(2, FeedType::FEED); + + $this->itemService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo(2), + $this->equalTo(FeedType::FEED), + $this->equalTo(3), + $this->equalTo(10), + $this->equalTo(true), + $this->equalTo(true), + $this->equalTo($this->user)) + ->will($this->returnValue($result['items'])); + + $this->feedService->expects($this->never()) + ->method('findAll'); + + $response = $this->controller->index(FeedType::FEED, 2, 3, 10); + $this->assertEquals($result, $response); + } + + + public function testGetItemsNoNewestItemsId(){ + $this->itemsApiExpects(2, FeedType::FEED); + + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->with($this->equalTo($this->user)) + ->will($this->throwException(new ServiceNotFoundException(''))); + + $response = $this->controller->index(FeedType::FEED, 2, 3); + $this->assertEquals([], $response); + } + + + public function testNewItems(){ + $feeds = [new Feed()]; + $result = [ + 'items' => [new Item()], + 'feeds' => $feeds, + 'newestItemId' => $this->newestItemId, + 'starred' => 3111 + ]; + + $this->settings->expects($this->once()) + ->method('getUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('showAll')) + ->will($this->returnValue('1')); + + $this->feedService->expects($this->once()) + ->method('findAll') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($this->newestItemId)); + + $this->itemService->expects($this->once()) + ->method('starredCount') + ->with($this->equalTo($this->user)) + ->will($this->returnValue(3111)); + + $this->itemService->expects($this->once()) + ->method('findAllNew') + ->with( + $this->equalTo(2), + $this->equalTo(FeedType::FEED), + $this->equalTo(3), + $this->equalTo(true), + $this->equalTo($this->user)) + ->will($this->returnValue($result['items'])); + + $response = $this->controller->newItems(FeedType::FEED, 2, 3); + $this->assertEquals($result, $response); + } + + + public function testGetNewItemsNoNewestItemsId(){ + $this->settings->expects($this->once()) + ->method('getUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('showAll')) + ->will($this->returnValue('1')); + + $this->itemService->expects($this->once()) + ->method('getNewestItemId') + ->with($this->equalTo($this->user)) + ->will($this->throwException(new ServiceNotFoundException(''))); + + $response = $this->controller->newItems(FeedType::FEED, 2, 3); + $this->assertEquals([], $response); + } }
\ No newline at end of file diff --git a/tests/unit/controller/PageControllerTest.php b/tests/unit/controller/PageControllerTest.php index ec2fcae14..60ae8c66b 100644 --- a/tests/unit/controller/PageControllerTest.php +++ b/tests/unit/controller/PageControllerTest.php @@ -16,23 +16,23 @@ namespace OCA\News\Controller; class PageControllerTest extends \PHPUnit_Framework_TestCase { - private $settings; - private $appName; - private $request; - private $controller; - private $user; - private $l10n; - private $urlGenerator; - private $appConfig; - private $configData; - - /** - * Gets run before each test - */ - public function setUp(){ - $this->appName = 'news'; - $this->user = 'becka'; - $this->configData = [ + private $settings; + private $appName; + private $request; + private $controller; + private $user; + private $l10n; + private $urlGenerator; + private $appConfig; + private $configData; + + /** + * Gets run before each test + */ + public function setUp(){ + $this->appName = 'news'; + $this->user = 'becka'; + $this->configData = [ 'name' => 'AppTest', 'id' => 'apptest', 'authors' => [ @@ -42,19 +42,19 @@ class PageControllerTest extends \PHPUnit_Framework_TestCase { 'description' => 'This is a test app', 'homepage' => 'https://github.com/owncloud/test' ]; - $this->l10n = $this->request = $this->getMockBuilder( - '\OCP\IL10n') - ->disableOriginalConstructor() - ->getMock(); - $this->settings = $this->getMockBuilder( - '\OCP\IConfig') - ->disableOriginalConstructor() - ->getMock(); - $this->request = $this->getMockBuilder( - '\OCP\IRequest') - ->disableOriginalConstructor() - ->getMock(); - $this->urlGenerator = $this->getMockBuilder( + $this->l10n = $this->request = $this->getMockBuilder( + '\OCP\IL10n') + ->disableOriginalConstructor() + ->getMock(); + $this->settings = $this->getMockBuilder( + '\OCP\IConfig') + ->disableOriginalConstructor() + ->getMock(); + $this->request = $this->getMockBuilder( + '\OCP\IRequest') + ->disableOriginalConstructor() + ->getMock(); + $this->urlGenerator = $this->getMockBuilder( '\OCP\IURLGenerator') ->disableOriginalConstructor() ->getMock(); @@ -62,93 +62,93 @@ class PageControllerTest extends \PHPUnit_Framework_TestCase { '\OCA\News\Config\AppConfig') ->disableOriginalConstructor() ->getMock(); - $this->controller = new PageController($this->appName, $this->request, - $this->settings, $this->urlGenerator, $this->appConfig, $this->l10n, - $this->user); - } - - - public function testIndex(){ - $response = $this->controller->index(); - $this->assertEquals('index', $response->getTemplateName()); - } - - - public function testSettings() { - $result = [ - 'settings' => [ - 'showAll' => true, - 'compact' => true, - 'preventReadOnScroll' => true, - 'oldestFirst' => true, - 'language' => 'de', - ] - ]; - - $this->l10n->expects($this->once()) - ->method('getLanguageCode') - ->will($this->returnValue('de')); - $this->settings->expects($this->at(0)) - ->method('getUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('showAll')) - ->will($this->returnValue('1')); - $this->settings->expects($this->at(1)) - ->method('getUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('compact')) - ->will($this->returnValue('1')); - $this->settings->expects($this->at(2)) - ->method('getUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('preventReadOnScroll')) - ->will($this->returnValue('1')); - $this->settings->expects($this->at(3)) - ->method('getUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('oldestFirst')) - ->will($this->returnValue('1')); - - $response = $this->controller->settings(); - $this->assertEquals($result, $response); - } - - - public function testUpdateSettings() { - $this->settings->expects($this->at(0)) - ->method('setUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('showAll'), - $this->equalTo(true)); - $this->settings->expects($this->at(1)) - ->method('setUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('compact'), - $this->equalTo(true)); - $this->settings->expects($this->at(2)) - ->method('setUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('preventReadOnScroll'), - $this->equalTo(false)); - $this->settings->expects($this->at(3)) - ->method('setUserValue') - ->with($this->equalTo($this->user), - $this->equalTo($this->appName), - $this->equalTo('oldestFirst'), - $this->equalTo(true)); - $this->controller->updateSettings(true, true, false, true); - - } - - - public function testManifest(){ + $this->controller = new PageController($this->appName, $this->request, + $this->settings, $this->urlGenerator, $this->appConfig, $this->l10n, + $this->user); + } + + + public function testIndex(){ + $response = $this->controller->index(); + $this->assertEquals('index', $response->getTemplateName()); + } + + + public function testSettings() { + $result = [ + 'settings' => [ + 'showAll' => true, + 'compact' => true, + 'preventReadOnScroll' => true, + 'oldestFirst' => true, + 'language' => 'de', + ] + ]; + + $this->l10n->expects($this->once()) + ->method('getLanguageCode') + ->will($this->returnValue('de')); + $this->settings->expects($this->at(0)) + ->method('getUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('showAll')) + ->will($this->returnValue('1')); + $this->settings->expects($this->at(1)) + ->method('getUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('compact')) + ->will($this->returnValue('1')); + $this->settings->expects($this->at(2)) + ->method('getUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('preventReadOnScroll')) + ->will($this->returnValue('1')); + $this->settings->expects($this->at(3)) + ->method('getUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('oldestFirst')) + ->will($this->returnValue('1')); + + $response = $this->controller->settings(); + $this->assertEquals($result, $response); + } + + + public function testUpdateSettings() { + $this->settings->expects($this->at(0)) + ->method('setUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('showAll'), + $this->equalTo(true)); + $this->settings->expects($this->at(1)) + ->method('setUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('compact'), + $this->equalTo(true)); + $this->settings->expects($this->at(2)) + ->method('setUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('preventReadOnScroll'), + $this->equalTo(false)); + $this->settings->expects($this->at(3)) + ->method('setUserValue') + ->with($this->equalTo($this->user), + $this->equalTo($this->appName), + $this->equalTo('oldestFirst'), + $this->equalTo(true)); + $this->controller->updateSettings(true, true, false, true); + + } + + + public function testManifest(){ $this->appConfig->expects($this->once()) ->method('getConfig') ->will($this->returnValue($this->configData)); diff --git a/tests/unit/controller/UtilityApiControllerTest.php b/tests/unit/controller/UtilityApiControllerTest.php index d9c298858..efff559d8 100644 --- a/tests/unit/controller/UtilityApiControllerTest.php +++ b/tests/unit/controller/UtilityApiControllerTest.php @@ -16,57 +16,57 @@ namespace OCA\News\Controller; class UtilityApiControllerTest extends \PHPUnit_Framework_TestCase { - private $settings; - private $request; - private $newsAPI; - private $updater; - private $appName; + private $settings; + private $request; + private $newsAPI; + private $updater; + private $appName; - protected function setUp() { - $this->appName = 'news'; - $this->settings = $this->getMockBuilder( - '\OCP\IConfig') - ->disableOriginalConstructor() - ->getMock(); - $this->request = $this->getMockBuilder( - '\OCP\IRequest') - ->disableOriginalConstructor() - ->getMock(); - $this->updater = $this->getMockBuilder( - '\OCA\News\Utility\Updater') - ->disableOriginalConstructor() - ->getMock(); - $this->newsAPI = new UtilityApiController($this->appName, $this->request, - $this->updater, $this->settings); - } + protected function setUp() { + $this->appName = 'news'; + $this->settings = $this->getMockBuilder( + '\OCP\IConfig') + ->disableOriginalConstructor() + ->getMock(); + $this->request = $this->getMockBuilder( + '\OCP\IRequest') + ->disableOriginalConstructor() + ->getMock(); + $this->updater = $this->getMockBuilder( + '\OCA\News\Utility\Updater') + ->disableOriginalConstructor() + ->getMock(); + $this->newsAPI = new UtilityApiController($this->appName, $this->request, + $this->updater, $this->settings); + } - public function testGetVersion(){ - $this->settings->expects($this->once()) - ->method('getAppValue') - ->with($this->equalTo($this->appName), - $this->equalTo('installed_version')) - ->will($this->returnValue('1.0')); + public function testGetVersion(){ + $this->settings->expects($this->once()) + ->method('getAppValue') + ->with($this->equalTo($this->appName), + $this->equalTo('installed_version')) + ->will($this->returnValue('1.0')); - $response = $this->newsAPI->version(); - $version = $response['version']; + $response = $this->newsAPI->version(); + $version = $response['version']; - $this->assertEquals('1.0', $version); - } + $this->assertEquals('1.0', $version); + } - public function testBeforeUpdate(){ - $this->updater->expects($this->once()) - ->method('beforeUpdate'); - $this->newsAPI->beforeUpdate(); - } + public function testBeforeUpdate(){ + $this->updater->expects($this->once()) + ->method('beforeUpdate'); + $this->newsAPI->beforeUpdate(); + } - public function testAfterUpdate(){ - $this->updater->expects($this->once()) - ->method('afterUpdate'); - $this->newsAPI->afterUpdate(); - } + public function testAfterUpdate(){ + $this->updater->expects($this->once()) + ->method('afterUpdate'); + $this->newsAPI->afterUpdate(); + } } diff --git a/tests/unit/db/FeedMapperTest.php b/tests/unit/db/FeedMapperTest.php index 93137d8d4..a1a570b87 100644 --- a/tests/unit/db/FeedMapperTest.php +++ b/tests/unit/db/FeedMapperTest.php @@ -16,313 +16,313 @@ namespace OCA\News\Db; class FeedMapperTest extends \Test\AppFramework\Db\MapperTestUtility { - private $mapper; - private $feeds; - - protected function setUp(){ - parent::setUp(); - - $this->mapper = new FeedMapper($this->db); - - // create mock feeds - $feed1 = new Feed(); - $feed2 = new Feed(); - - $this->feeds = [$feed1, $feed2]; - $this->user = 'herman'; - } - - - public function testFind(){ - $userId = 'john'; - $id = 3; - $rows = [ - ['id' => $this->feeds[0]->getId()], - ]; - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE `feeds`.`id` = ? ' . - 'AND `feeds`.`user_id` = ? ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - $params = [$id, $userId]; - $this->setMapperResult($sql, $params, $rows); - - $result = $this->mapper->find($id, $userId); - $this->assertEquals($this->feeds[0], $result); - - } - - - public function testFindNotFound(){ - $userId = 'john'; - $id = 3; - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE `feeds`.`id` = ? ' . - 'AND `feeds`.`user_id` = ? ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - $params = [$id, $userId]; - $this->setMapperResult($sql, $params); - - $this->setExpectedException('\OCP\AppFramework\Db\DoesNotExistException'); - $this->mapper->find($id, $userId); - } - - - public function testFindMoreThanOneResultFound(){ - $userId = 'john'; - $id = 3; - $rows = [ - ['id' => $this->feeds[0]->getId()], - ['id' => $this->feeds[1]->getId()] - ]; - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE `feeds`.`id` = ? ' . - 'AND `feeds`.`user_id` = ? ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - $params = [$id, $userId]; - $this->setMapperResult($sql, $params, $rows); - - $this->setExpectedException('\OCP\AppFramework\Db\MultipleObjectsReturnedException'); - $this->mapper->find($id, $userId); - } - - - public function testFindAll(){ - $rows = [ - ['id' => $this->feeds[0]->getId()], - ['id' => $this->feeds[1]->getId()] - ]; - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` '. - 'ON `feeds`.`folder_id` = `folders`.`id` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - // WARNING: this is a desperate attempt at making this query work - // because prepared statements dont work. This is a possible - // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. - // think twice when changing this - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE (`feeds`.`folder_id` = 0 ' . - 'OR `folders`.`deleted_at` = 0' . - ')' . - 'AND `feeds`.`deleted_at` = 0 ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - - $this->setMapperResult($sql, [], $rows); - - $result = $this->mapper->findAll(); - $this->assertEquals($this->feeds, $result); - } - - - public function testFindAllFromUser(){ - $userId = 'john'; - $rows = [ - ['id' => $this->feeds[0]->getId()], - ['id' => $this->feeds[1]->getId()] - ]; - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` '. - 'ON `feeds`.`folder_id` = `folders`.`id` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - // WARNING: this is a desperate attempt at making this query work - // because prepared statements dont work. This is a possible - // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. - // think twice when changing this - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE `feeds`.`user_id` = ? ' . - 'AND (`feeds`.`folder_id` = 0 ' . - 'OR `folders`.`deleted_at` = 0' . - ')' . - 'AND `feeds`.`deleted_at` = 0 ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - $this->setMapperResult($sql, [$userId], $rows); - - $result = $this->mapper->findAllFromUser($userId); - $this->assertEquals($this->feeds, $result); - } - - - public function testFindByUrlHash(){ - $urlHash = md5('hihi'); - $row = [['id' => $this->feeds[0]->getId()]]; - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE `feeds`.`url_hash` = ? ' . - 'AND `feeds`.`user_id` = ? ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - $this->setMapperResult($sql, [$urlHash, $this->user], $row); - - $result = $this->mapper->findByUrlHash($urlHash, $this->user); - $this->assertEquals($this->feeds[0], $result); - } - - - public function testFindByUrlHashNotFound(){ - $urlHash = md5('hihi'); - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE `feeds`.`url_hash` = ? ' . - 'AND `feeds`.`user_id` = ? ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - $this->setMapperResult($sql, [$urlHash, $this->user]); - - $this->setExpectedException('\OCP\AppFramework\Db\DoesNotExistException'); - $this->mapper->findByUrlHash($urlHash, $this->user); - } - - - public function testFindByUrlHashMoreThanOneResultFound(){ - $urlHash = md5('hihi'); - $rows = [ - ['id' => $this->feeds[0]->getId()], - ['id' => $this->feeds[1]->getId()] - ]; - $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . - 'FROM `*PREFIX*news_feeds` `feeds` ' . - 'LEFT JOIN `*PREFIX*news_items` `items` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . - StatusFlag::UNREAD . ' ' . - 'WHERE `feeds`.`url_hash` = ? ' . - 'AND `feeds`.`user_id` = ? ' . - 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. - '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. - '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. - '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; - $this->setMapperResult($sql, [$urlHash, $this->user], $rows); - - $this->setExpectedException('\OCP\AppFramework\Db\MultipleObjectsReturnedException'); - $this->mapper->findByUrlHash($urlHash, $this->user); - } - - - public function testDelete(){ - $feed = new Feed(); - $feed->setId(3); - - $sql = 'DELETE FROM `*PREFIX*news_feeds` WHERE `id` = ?'; - $arguments = [$feed->getId()]; - - $sql2 = 'DELETE FROM `*PREFIX*news_items` WHERE `feed_id` = ?'; - $arguments2 = [$feed->getId()]; - - $pdoResult = $this->getMock('Result', ['fetch']); - $pdoResult->expects($this->any())->method('fetch'); - - $this->setMapperResult($sql, $arguments); - $this->setMapperResult($sql2, $arguments2); - - $this->mapper->delete($feed); - - } - - - public function testGetPurgeDeleted(){ - $rows = [ - ['id' => $this->feeds[0]->getId()], - ['id' => $this->feeds[1]->getId()] - ]; - $deleteOlderThan = 110; - $sql = 'SELECT * FROM `*PREFIX*news_feeds` ' . - 'WHERE `deleted_at` > 0 ' . - 'AND `deleted_at` < ? '; - $this->setMapperResult($sql, [$deleteOlderThan], $rows); - $result = $this->mapper->getToDelete($deleteOlderThan); - - $this->assertEquals($this->feeds, $result); - } - - - public function testGetPurgeDeletedFromUser(){ - $rows = [ - ['id' => $this->feeds[0]->getId()], - ['id' => $this->feeds[1]->getId()] - ]; - $deleteOlderThan = 110; - $sql = 'SELECT * FROM `*PREFIX*news_feeds` ' . - 'WHERE `deleted_at` > 0 ' . - 'AND `deleted_at` < ? ' . - 'AND `user_id` = ?'; - $this->setMapperResult($sql, [$deleteOlderThan, $this->user], $rows); - $result = $this->mapper->getToDelete($deleteOlderThan, $this->user); - - $this->assertEquals($this->feeds, $result); - } - - - public function testGetAllPurgeDeletedFromUser(){ - $rows = [ - ['id' => $this->feeds[0]->getId()], - ['id' => $this->feeds[1]->getId()] - ]; - - $sql = 'SELECT * FROM `*PREFIX*news_feeds` ' . - 'WHERE `deleted_at` > 0 ' . - 'AND `user_id` = ?'; - $this->setMapperResult($sql, [$this->user], $rows); - $result = $this->mapper->getToDelete(null, $this->user); - - $this->assertEquals($this->feeds, $result); - } - - - public function testDeleteFromUser(){ - $userId = 'john'; - $sql = 'DELETE FROM `*PREFIX*news_feeds` WHERE `user_id` = ?'; - - $this->setMapperResult($sql, [$userId]); - - $this->mapper->deleteUser($userId); - } + private $mapper; + private $feeds; + + protected function setUp(){ + parent::setUp(); + + $this->mapper = new FeedMapper($this->db); + + // create mock feeds + $feed1 = new Feed(); + $feed2 = new Feed(); + + $this->feeds = [$feed1, $feed2]; + $this->user = 'herman'; + } + + + public function testFind(){ + $userId = 'john'; + $id = 3; + $rows = [ + ['id' => $this->feeds[0]->getId()], + ]; + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE `feeds`.`id` = ? ' . + 'AND `feeds`.`user_id` = ? ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + $params = [$id, $userId]; + $this->setMapperResult($sql, $params, $rows); + + $result = $this->mapper->find($id, $userId); + $this->assertEquals($this->feeds[0], $result); + + } + + + public function testFindNotFound(){ + $userId = 'john'; + $id = 3; + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE `feeds`.`id` = ? ' . + 'AND `feeds`.`user_id` = ? ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + $params = [$id, $userId]; + $this->setMapperResult($sql, $params); + + $this->setExpectedException('\OCP\AppFramework\Db\DoesNotExistException'); + $this->mapper->find($id, $userId); + } + + + public function testFindMoreThanOneResultFound(){ + $userId = 'john'; + $id = 3; + $rows = [ + ['id' => $this->feeds[0]->getId()], + ['id' => $this->feeds[1]->getId()] + ]; + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE `feeds`.`id` = ? ' . + 'AND `feeds`.`user_id` = ? ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + $params = [$id, $userId]; + $this->setMapperResult($sql, $params, $rows); + + $this->setExpectedException('\OCP\AppFramework\Db\MultipleObjectsReturnedException'); + $this->mapper->find($id, $userId); + } + + + public function testFindAll(){ + $rows = [ + ['id' => $this->feeds[0]->getId()], + ['id' => $this->feeds[1]->getId()] + ]; + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` '. + 'ON `feeds`.`folder_id` = `folders`.`id` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + // WARNING: this is a desperate attempt at making this query work + // because prepared statements dont work. This is a possible + // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. + // think twice when changing this + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE (`feeds`.`folder_id` = 0 ' . + 'OR `folders`.`deleted_at` = 0' . + ')' . + 'AND `feeds`.`deleted_at` = 0 ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + + $this->setMapperResult($sql, [], $rows); + + $result = $this->mapper->findAll(); + $this->assertEquals($this->feeds, $result); + } + + + public function testFindAllFromUser(){ + $userId = 'john'; + $rows = [ + ['id' => $this->feeds[0]->getId()], + ['id' => $this->feeds[1]->getId()] + ]; + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` '. + 'ON `feeds`.`folder_id` = `folders`.`id` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + // WARNING: this is a desperate attempt at making this query work + // because prepared statements dont work. This is a possible + // SQL INJECTION RISK WHEN MODIFIED WITHOUT THOUGHT. + // think twice when changing this + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE `feeds`.`user_id` = ? ' . + 'AND (`feeds`.`folder_id` = 0 ' . + 'OR `folders`.`deleted_at` = 0' . + ')' . + 'AND `feeds`.`deleted_at` = 0 ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + $this->setMapperResult($sql, [$userId], $rows); + + $result = $this->mapper->findAllFromUser($userId); + $this->assertEquals($this->feeds, $result); + } + + + public function testFindByUrlHash(){ + $urlHash = md5('hihi'); + $row = [['id' => $this->feeds[0]->getId()]]; + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE `feeds`.`url_hash` = ? ' . + 'AND `feeds`.`user_id` = ? ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + $this->setMapperResult($sql, [$urlHash, $this->user], $row); + + $result = $this->mapper->findByUrlHash($urlHash, $this->user); + $this->assertEquals($this->feeds[0], $result); + } + + + public function testFindByUrlHashNotFound(){ + $urlHash = md5('hihi'); + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE `feeds`.`url_hash` = ? ' . + 'AND `feeds`.`user_id` = ? ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + $this->setMapperResult($sql, [$urlHash, $this->user]); + + $this->setExpectedException('\OCP\AppFramework\Db\DoesNotExistException'); + $this->mapper->findByUrlHash($urlHash, $this->user); + } + + + public function testFindByUrlHashMoreThanOneResultFound(){ + $urlHash = md5('hihi'); + $rows = [ + ['id' => $this->feeds[0]->getId()], + ['id' => $this->feeds[1]->getId()] + ]; + $sql = 'SELECT `feeds`.*, COUNT(`items`.`id`) AS `unread_count` ' . + 'FROM `*PREFIX*news_feeds` `feeds` ' . + 'LEFT JOIN `*PREFIX*news_items` `items` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'AND (`items`.`status` & ' . StatusFlag::UNREAD . ') = ' . + StatusFlag::UNREAD . ' ' . + 'WHERE `feeds`.`url_hash` = ? ' . + 'AND `feeds`.`user_id` = ? ' . + 'GROUP BY `feeds`.`id`, `feeds`.`user_id`, `feeds`.`url_hash`,'. + '`feeds`.`url`, `feeds`.`title`, `feeds`.`link`,'. + '`feeds`.`favicon_link`, `feeds`.`added`, `feeds`.`articles_per_update`,'. + '`feeds`.`folder_id`, `feeds`.`prevent_update`, `feeds`.`deleted_at`'; + $this->setMapperResult($sql, [$urlHash, $this->user], $rows); + + $this->setExpectedException('\OCP\AppFramework\Db\MultipleObjectsReturnedException'); + $this->mapper->findByUrlHash($urlHash, $this->user); + } + + + public function testDelete(){ + $feed = new Feed(); + $feed->setId(3); + + $sql = 'DELETE FROM `*PREFIX*news_feeds` WHERE `id` = ?'; + $arguments = [$feed->getId()]; + + $sql2 = 'DELETE FROM `*PREFIX*news_items` WHERE `feed_id` = ?'; + $arguments2 = [$feed->getId()]; + + $pdoResult = $this->getMock('Result', ['fetch']); + $pdoResult->expects($this->any())->method('fetch'); + + $this->setMapperResult($sql, $arguments); + $this->setMapperResult($sql2, $arguments2); + + $this->mapper->delete($feed); + + } + + + public function testGetPurgeDeleted(){ + $rows = [ + ['id' => $this->feeds[0]->getId()], + ['id' => $this->feeds[1]->getId()] + ]; + $deleteOlderThan = 110; + $sql = 'SELECT * FROM `*PREFIX*news_feeds` ' . + 'WHERE `deleted_at` > 0 ' . + 'AND `deleted_at` < ? '; + $this->setMapperResult($sql, [$deleteOlderThan], $rows); + $result = $this->mapper->getToDelete($deleteOlderThan); + + $this->assertEquals($this->feeds, $result); + } + + + public function testGetPurgeDeletedFromUser(){ + $rows = [ + ['id' => $this->feeds[0]->getId()], + ['id' => $this->feeds[1]->getId()] + ]; + $deleteOlderThan = 110; + $sql = 'SELECT * FROM `*PREFIX*news_feeds` ' . + 'WHERE `deleted_at` > 0 ' . + 'AND `deleted_at` < ? ' . + 'AND `user_id` = ?'; + $this->setMapperResult($sql, [$deleteOlderThan, $this->user], $rows); + $result = $this->mapper->getToDelete($deleteOlderThan, $this->user); + + $this->assertEquals($this->feeds, $result); + } + + + public function testGetAllPurgeDeletedFromUser(){ + $rows = [ + ['id' => $this->feeds[0]->getId()], + ['id' => $this->feeds[1]->getId()] + ]; + + $sql = 'SELECT * FROM `*PREFIX*news_feeds` ' . + 'WHERE `deleted_at` > 0 ' . + 'AND `user_id` = ?'; + $this->setMapperResult($sql, [$this->user], $rows); + $result = $this->mapper->getToDelete(null, $this->user); + + $this->assertEquals($this->feeds, $result); + } + + + public function testDeleteFromUser(){ + $userId = 'john'; + $sql = 'DELETE FROM `*PREFIX*news_feeds` WHERE `user_id` = ?'; + + $this->setMapperResult($sql, [$userId]); + + $this->mapper->deleteUser($userId); + } } diff --git a/tests/unit/db/FeedTest.php b/tests/unit/db/FeedTest.php index f7fe9b885..936948813 100644 --- a/tests/unit/db/FeedTest.php +++ b/tests/unit/db/FeedTest.php @@ -17,77 +17,77 @@ namespace OCA\News\Db; class FeedTest extends \PHPUnit_Framework_TestCase { - private function createFeed() { - $feed = new Feed(); - $feed->setId(3); - $feed->setUrl('http://google.com/some/weird/path'); - $feed->setTitle('title'); - $feed->setFaviconLink('favicon'); - $feed->setAdded(123); - $feed->setFolderId(1); - $feed->setUnreadCount(321); - $feed->setLink('https://www.google.com/some/weird/path'); - - return $feed; - } - - public function testToAPI() { - $feed = $this->createFeed(); - - $this->assertEquals([ - 'id' => 3, - 'url' => 'http://google.com/some/weird/path', - 'title' => 'title', - 'faviconLink' => 'favicon', - 'added' => 123, - 'folderId' => 1, - 'unreadCount' => 321, - 'link' => 'https://www.google.com/some/weird/path' - ], $feed->toAPI()); - } - - - public function testSerialize() { - $feed = $this->createFeed(); - - $this->assertEquals([ - 'id' => 3, - 'url' => 'http://google.com/some/weird/path', - 'title' => 'title', - 'faviconLink' => 'favicon', - 'added' => 123, - 'folderId' => 1, - 'unreadCount' => 321, - 'link' => 'https://www.google.com/some/weird/path', - 'userId' => null, - 'urlHash' => '44168618f55392b145629d6b3922e84b', - 'preventUpdate' => null, - 'deletedAt' => null, - 'articlesPerUpdate' => null, - 'cssClass' => 'custom-google-com', - ], $feed->jsonSerialize()); - } - - - public function testSetXSSUrl() { - $feed = new Feed(); - $feed->setUrl('javascript:alert()'); - $this->assertEquals('', $feed->getUrl()); - } - - - public function testSetUrlUpdatesHash() { - $feed = new Feed(); - $feed->setUrl('http://test'); - $this->assertEquals(md5('http://test'), $feed->getUrlHash()); - } - - - public function testSetXSSLink() { - $feed = new Feed(); - $feed->setLink('javascript:alert()'); - $this->assertEquals('', $feed->getLink()); - } + private function createFeed() { + $feed = new Feed(); + $feed->setId(3); + $feed->setUrl('http://google.com/some/weird/path'); + $feed->setTitle('title'); + $feed->setFaviconLink('favicon'); + $feed->setAdded(123); + $feed->setFolderId(1); + $feed->setUnreadCount(321); + $feed->setLink('https://www.google.com/some/weird/path'); + + return $feed; + } + + public function testToAPI() { + $feed = $this->createFeed(); + + $this->assertEquals([ + 'id' => 3, + 'url' => 'http://google.com/some/weird/path', + 'title' => 'title', + 'faviconLink' => 'favicon', + 'added' => 123, + 'folderId' => 1, + 'unreadCount' => 321, + 'link' => 'https://www.google.com/some/weird/path' + ], $feed->toAPI()); + } + + + public function testSerialize() { + $feed = $this->createFeed(); + + $this->assertEquals([ + 'id' => 3, + 'url' => 'http://google.com/some/weird/path', + 'title' => 'title', + 'faviconLink' => 'favicon', + 'added' => 123, + 'folderId' => 1, + 'unreadCount' => 321, + 'link' => 'https://www.google.com/some/weird/path', + 'userId' => null, + 'urlHash' => '44168618f55392b145629d6b3922e84b', + 'preventUpdate' => null, + 'deletedAt' => null, + 'articlesPerUpdate' => null, + 'cssClass' => 'custom-google-com', + ], $feed->jsonSerialize()); + } + + + public function testSetXSSUrl() { + $feed = new Feed(); + $feed->setUrl('javascript:alert()'); + $this->assertEquals('', $feed->getUrl()); + } + + + public function testSetUrlUpdatesHash() { + $feed = new Feed(); + $feed->setUrl('http://test'); + $this->assertEquals(md5('http://test'), $feed->getUrlHash()); + } + + + public function testSetXSSLink() { + $feed = new Feed(); + $feed->setLink('javascript:alert()'); + $this->assertEquals('', $feed->getLink()); + } }
\ No newline at end of file diff --git a/tests/unit/db/FolderMapperTest.php b/tests/unit/db/FolderMapperTest.php index 6a2e94588..1078d205f 100644 --- a/tests/unit/db/FolderMapperTest.php +++ b/tests/unit/db/FolderMapperTest.php @@ -16,173 +16,173 @@ namespace OCA\News\Db; class FolderMapperTest extends \Test\AppFramework\Db\MapperTestUtility { - private $folderMapper; - private $folders; - private $user; + private $folderMapper; + private $folders; + private $user; - protected function setUp(){ - parent::setUp(); + protected function setUp(){ + parent::setUp(); - $this->folderMapper = new FolderMapper($this->db); + $this->folderMapper = new FolderMapper($this->db); - // create mock folders - $folder1 = new Folder(); - $folder2 = new Folder(); + // create mock folders + $folder1 = new Folder(); + $folder2 = new Folder(); - $this->folders = [$folder1, $folder2]; - $this->user = 'hh'; - $this->twoRows = [ - ['id' => $this->folders[0]->getId()], - ['id' => $this->folders[1]->getId()] - ]; - } + $this->folders = [$folder1, $folder2]; + $this->user = 'hh'; + $this->twoRows = [ + ['id' => $this->folders[0]->getId()], + ['id' => $this->folders[1]->getId()] + ]; + } - public function testFind(){ - $userId = 'john'; - $id = 3; - $rows = [['id' => $this->folders[0]->getId()]]; - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `id` = ? ' . - 'AND `user_id` = ?'; + public function testFind(){ + $userId = 'john'; + $id = 3; + $rows = [['id' => $this->folders[0]->getId()]]; + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `id` = ? ' . + 'AND `user_id` = ?'; - $this->setMapperResult($sql, [$id, $userId], $rows); + $this->setMapperResult($sql, [$id, $userId], $rows); - $result = $this->folderMapper->find($id, $userId); - $this->assertEquals($this->folders[0], $result); + $result = $this->folderMapper->find($id, $userId); + $this->assertEquals($this->folders[0], $result); - } + } - public function testFindNotFound(){ - $userId = 'john'; - $id = 3; - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `id` = ? ' . - 'AND `user_id` = ?'; + public function testFindNotFound(){ + $userId = 'john'; + $id = 3; + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `id` = ? ' . + 'AND `user_id` = ?'; - $this->setMapperResult($sql, [$id, $userId]); + $this->setMapperResult($sql, [$id, $userId]); - $this->setExpectedException('\OCP\AppFramework\Db\DoesNotExistException'); - $this->folderMapper->find($id, $userId); - } + $this->setExpectedException('\OCP\AppFramework\Db\DoesNotExistException'); + $this->folderMapper->find($id, $userId); + } - public function testFindMoreThanOneResultFound(){ - $userId = 'john'; - $id = 3; - $rows = $this->twoRows; - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `id` = ? ' . - 'AND `user_id` = ?'; + public function testFindMoreThanOneResultFound(){ + $userId = 'john'; + $id = 3; + $rows = $this->twoRows; + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `id` = ? ' . + 'AND `user_id` = ?'; - $this->setMapperResult($sql, [$id, $userId], $rows); + $this->setMapperResult($sql, [$id, $userId], $rows); - $this->setExpectedException('\OCP\AppFramework\Db\MultipleObjectsReturnedException'); - $this->folderMapper->find($id, $userId); - } + $this->setExpectedException('\OCP\AppFramework\Db\MultipleObjectsReturnedException'); + $this->folderMapper->find($id, $userId); + } - public function testFindAllFromUser(){ - $userId = 'john'; - $rows = $this->twoRows; - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `user_id` = ? ' . - 'AND `deleted_at` = 0'; + public function testFindAllFromUser(){ + $userId = 'john'; + $rows = $this->twoRows; + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `user_id` = ? ' . + 'AND `deleted_at` = 0'; - $this->setMapperResult($sql, [$userId], $rows); + $this->setMapperResult($sql, [$userId], $rows); - $result = $this->folderMapper->findAllFromUser($userId); - $this->assertEquals($this->folders, $result); - } + $result = $this->folderMapper->findAllFromUser($userId); + $this->assertEquals($this->folders, $result); + } - public function testFindByName(){ - $folderName = 'heheh'; - $userId = 'john'; - $rows = $this->twoRows; - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `name` = ? ' . - 'AND `user_id` = ?'; + public function testFindByName(){ + $folderName = 'heheh'; + $userId = 'john'; + $rows = $this->twoRows; + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `name` = ? ' . + 'AND `user_id` = ?'; - $this->setMapperResult($sql, [$folderName, $userId], $rows); + $this->setMapperResult($sql, [$folderName, $userId], $rows); - $result = $this->folderMapper->findByName($folderName, $userId); - $this->assertEquals($this->folders, $result); - } + $result = $this->folderMapper->findByName($folderName, $userId); + $this->assertEquals($this->folders, $result); + } - public function testDelete(){ - $folder = new Folder(); - $folder->setId(3); + public function testDelete(){ + $folder = new Folder(); + $folder->setId(3); - $sql = 'DELETE FROM `*PREFIX*news_folders` WHERE `id` = ?'; - $arguments = [$folder->getId()]; + $sql = 'DELETE FROM `*PREFIX*news_folders` WHERE `id` = ?'; + $arguments = [$folder->getId()]; - $sql2 = 'DELETE FROM `*PREFIX*news_feeds` WHERE `folder_id` = ?'; + $sql2 = 'DELETE FROM `*PREFIX*news_feeds` WHERE `folder_id` = ?'; - $sql3 = 'DELETE FROM `*PREFIX*news_items` WHERE `feed_id` NOT IN '. - '(SELECT `feeds`.`id` FROM `*PREFIX*news_feeds` `feeds`)'; - $arguments2 = [$folder->getId()]; + $sql3 = 'DELETE FROM `*PREFIX*news_items` WHERE `feed_id` NOT IN '. + '(SELECT `feeds`.`id` FROM `*PREFIX*news_feeds` `feeds`)'; + $arguments2 = [$folder->getId()]; - $this->setMapperResult($sql, $arguments); - $this->setMapperResult($sql2, $arguments2); - $this->setMapperResult($sql3); + $this->setMapperResult($sql, $arguments); + $this->setMapperResult($sql2, $arguments2); + $this->setMapperResult($sql3); - $this->folderMapper->delete($folder); - } + $this->folderMapper->delete($folder); + } - public function testGetPurgeDeleted(){ - $rows = $this->twoRows; - $deleteOlderThan = 110; - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `deleted_at` > 0 ' . - 'AND `deleted_at` < ? '; - $this->setMapperResult($sql, [$deleteOlderThan], $rows); - $result = $this->folderMapper->getToDelete($deleteOlderThan); + public function testGetPurgeDeleted(){ + $rows = $this->twoRows; + $deleteOlderThan = 110; + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `deleted_at` > 0 ' . + 'AND `deleted_at` < ? '; + $this->setMapperResult($sql, [$deleteOlderThan], $rows); + $result = $this->folderMapper->getToDelete($deleteOlderThan); - $this->assertEquals($this->folders, $result); - } + $this->assertEquals($this->folders, $result); + } - public function testGetPurgeDeletedUser(){ - $rows = $this->twoRows; - $deleteOlderThan = 110; - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `deleted_at` > 0 ' . - 'AND `deleted_at` < ? ' . - 'AND `user_id` = ?'; - $this->setMapperResult($sql, [$deleteOlderThan, $this->user], $rows); - $result = $this->folderMapper->getToDelete($deleteOlderThan, $this->user); + public function testGetPurgeDeletedUser(){ + $rows = $this->twoRows; + $deleteOlderThan = 110; + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `deleted_at` > 0 ' . + 'AND `deleted_at` < ? ' . + 'AND `user_id` = ?'; + $this->setMapperResult($sql, [$deleteOlderThan, $this->user], $rows); + $result = $this->folderMapper->getToDelete($deleteOlderThan, $this->user); - $this->assertEquals($this->folders, $result); - } + $this->assertEquals($this->folders, $result); + } - public function testGetAllPurgeDeletedUser(){ - $rows = $this->twoRows; + public function testGetAllPurgeDeletedUser(){ + $rows = $this->twoRows; - $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . - 'WHERE `deleted_at` > 0 ' . - 'AND `user_id` = ?'; - $this->setMapperResult($sql, [$this->user], $rows); - $result = $this->folderMapper->getToDelete(null, $this->user); + $sql = 'SELECT * FROM `*PREFIX*news_folders` ' . + 'WHERE `deleted_at` > 0 ' . + 'AND `user_id` = ?'; + $this->setMapperResult($sql, [$this->user], $rows); + $result = $this->folderMapper->getToDelete(null, $this->user); - $this->assertEquals($this->folders, $result); - } + $this->assertEquals($this->folders, $result); + } - public function testDeleteFromUser(){ - $userId = 'john'; - $sql = 'DELETE FROM `*PREFIX*news_folders` WHERE `user_id` = ?'; + public function testDeleteFromUser(){ + $userId = 'john'; + $sql = 'DELETE FROM `*PREFIX*news_folders` WHERE `user_id` = ?'; - $this->setMapperResult($sql, [$userId]); + $this->setMapperResult($sql, [$userId]); - $this->folderMapper->deleteUser($userId); - } + $this->folderMapper->deleteUser($userId); + } }
\ No newline at end of file diff --git a/tests/unit/db/FolderTest.php b/tests/unit/db/FolderTest.php index c4921b0f5..9d55035f1 100644 --- a/tests/unit/db/FolderTest.php +++ b/tests/unit/db/FolderTest.php @@ -17,34 +17,34 @@ namespace OCA\News\Db; class FolderTest extends \PHPUnit_Framework_TestCase { - public function testToAPI() { - $folder = new Folder(); - $folder->setId(3); - $folder->setName('name'); - - $this->assertEquals([ - 'id' => 3, - 'name' => 'name' - ], $folder->toAPI()); - } - - - public function testSerialize() { - $folder = new Folder(); - $folder->setId(3); - $folder->setName('john'); - $folder->setParentId(4); - $folder->setUserId('abc'); - $folder->setOpened(true); - $folder->setDeletedAt(9); - - $this->assertEquals([ - 'id' => 3, - 'parentId' => 4, - 'name' => 'john', - 'userId' => 'abc', - 'opened' => true, - 'deletedAt' => 9, - ], $folder->jsonSerialize()); - } + public function testToAPI() { + $folder = new Folder(); + $folder->setId(3); + $folder->setName('name'); + + $this->assertEquals([ + 'id' => 3, + 'name' => 'name' + ], $folder->toAPI()); + } + + + public function testSerialize() { + $folder = new Folder(); + $folder->setId(3); + $folder->setName('john'); + $folder->setParentId(4); + $folder->setUserId('abc'); + $folder->setOpened(true); + $folder->setDeletedAt(9); + + $this->assertEquals([ + 'id' => 3, + 'parentId' => 4, + 'name' => 'john', + 'userId' => 'abc', + 'opened' => true, + 'deletedAt' => 9, + ], $folder->jsonSerialize()); + } }
\ No newline at end of file diff --git a/tests/unit/db/ItemMapperTest.php b/tests/unit/db/ItemMapperTest.php index daff20822..46ab2165a 100644 --- a/tests/unit/db/ItemMapperTest.php +++ b/tests/unit/db/ItemMapperTest.php @@ -16,443 +16,443 @@ namespace OCA\News\Db; class ItemMapperTest extends \Test\AppFramework\Db\MapperTestUtility { - private $mapper; - private $items; - private $newestItemId; - private $limit; - private $user; - private $offset; - private $updatedSince; - private $status; - - - public function setUp() { - parent::setup(); - - $this->mapper = new ItemMapper($this->db); - - // create mock items - $item1 = new Item(); - $item2 = new Item(); - - $this->items = array( - $item1, - $item2 - ); - - $this->userId = 'john'; - $this->id = 3; - $this->folderId = 2; - - $this->row = array( - array('id' => $this->items[0]->getId()), - ); - - $this->rows = array( - array('id' => $this->items[0]->getId()), - array('id' => $this->items[1]->getId()) - ); - - $this->user = 'john'; - $this->limit = 10; - $this->offset = 3; - $this->id = 11; - $this->status = 333; - $this->updatedSince = 323; - $this->newestItemId = 2; - - } - - - private function makeSelectQuery($prependTo, $oldestFirst=false){ - if ($oldestFirst) { - $ordering = 'ASC'; - } else { - $ordering = 'DESC'; - } - - return 'SELECT `items`.* FROM `*PREFIX*news_items` `items` '. - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` '. - 'AND `feeds`.`deleted_at` = 0 ' . - 'AND `feeds`.`user_id` = ? ' . - $prependTo . - 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` ' . - 'ON `folders`.`id` = `feeds`.`folder_id` ' . - 'WHERE `feeds`.`folder_id` = 0 ' . - 'OR `folders`.`deleted_at` = 0 ' . - 'ORDER BY `items`.`id` ' . $ordering; - } - - private function makeSelectQueryStatus($prependTo, $status, - $oldestFirst=false) { - $status = (int) $status; - - return $this->makeSelectQuery( - 'AND ((`items`.`status` & ' . $status . ') = ' . $status . ') ' . - $prependTo, $oldestFirst - ); - } - - - public function testFind(){ - $sql = $this->makeSelectQuery('AND `items`.`id` = ? '); - - $this->setMapperResult($sql, array($this->userId, $this->id), $this->row); - - $result = $this->mapper->find($this->id, $this->userId); - $this->assertEquals($this->items[0], $result); - } - - - public function testGetStarredCount(){ - $userId = 'john'; - $row = array( - array('size' => 9) - ); - $sql = 'SELECT COUNT(*) AS size FROM `*PREFIX*news_items` `items` '. - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` '. - 'AND `feeds`.`deleted_at` = 0 ' . - 'AND `feeds`.`user_id` = ? ' . - 'AND ((`items`.`status` & ' . StatusFlag::STARRED . ') = ' . - StatusFlag::STARRED . ')' . - 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` ' . - 'ON `folders`.`id` = `feeds`.`folder_id` ' . - 'WHERE `feeds`.`folder_id` = 0 ' . - 'OR `folders`.`deleted_at` = 0'; - - $this->setMapperResult($sql, array($userId), $row); - - $result = $this->mapper->starredCount($userId); - $this->assertEquals($row[0]['size'], $result); - } - - - public function testReadAll(){ - $sql = 'UPDATE `*PREFIX*news_items` ' . - 'SET `status` = `status` & ? ' . - ', `last_modified` = ? ' . - 'WHERE `feed_id` IN (' . - 'SELECT `id` FROM `*PREFIX*news_feeds` ' . - 'WHERE `user_id` = ? ' . - ') '. - 'AND `id` <= ?'; - $params = array(~StatusFlag::UNREAD, $this->updatedSince, $this->user, 3); - $this->setMapperResult($sql, $params); - $this->mapper->readAll(3, $this->updatedSince, $this->user); - } - - - public function testReadFolder(){ - $sql = 'UPDATE `*PREFIX*news_items` ' . - 'SET `status` = `status` & ? ' . - ', `last_modified` = ? ' . - 'WHERE `feed_id` IN (' . - 'SELECT `id` FROM `*PREFIX*news_feeds` ' . - 'WHERE `folder_id` = ? ' . - 'AND `user_id` = ? ' . - ') '. - 'AND `id` <= ?'; - $params = array(~StatusFlag::UNREAD, $this->updatedSince, 3, $this->user, 6); - $this->setMapperResult($sql, $params); - $this->mapper->readFolder(3, 6, $this->updatedSince, $this->user); - } - - - public function testReadFeed(){ - $sql = 'UPDATE `*PREFIX*news_items` ' . - 'SET `status` = `status` & ? ' . - ', `last_modified` = ? ' . - 'WHERE `feed_id` = ? ' . - 'AND `id` <= ? ' . - 'AND EXISTS (' . - 'SELECT * FROM `*PREFIX*news_feeds` ' . - 'WHERE `user_id` = ? ' . - 'AND `id` = ? ) '; - $params = array(~StatusFlag::UNREAD, $this->updatedSince, 3, 6, - $this->user, 3); - $this->setMapperResult($sql, $params); - $this->mapper->readFeed(3, 6, $this->updatedSince, $this->user); - } - - - public function testFindAllNew(){ - $sql = 'AND `items`.`last_modified` >= ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status); - $params = array($this->user, $this->updatedSince); - - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAllNew($this->updatedSince, - $this->status, $this->user); - - $this->assertEquals($this->items, $result); - } - - - public function testFindAllNewFolder(){ - $sql = 'AND `feeds`.`folder_id` = ? ' . - 'AND `items`.`last_modified` >= ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status); - - $params = array($this->user, $this->id, $this->updatedSince); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAllNewFolder($this->id, $this->updatedSince, - $this->status, $this->user); - - $this->assertEquals($this->items, $result); - } - - - public function testFindAllNewFeed(){ - $sql = 'AND `items`.`feed_id` = ? ' . - 'AND `items`.`last_modified` >= ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status); - $params = array($this->user, $this->id, $this->updatedSince); - - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAllNewFeed($this->id, $this->updatedSince, - $this->status, $this->user); - - $this->assertEquals($this->items, $result); - } - - - public function testFindAllUnreadOrStarred(){ - $status = StatusFlag::UNREAD | StatusFlag::STARRED; - $sql = 'AND ((`items`.`status` & ' . $status . ') > 0) '; - $sql = $this->makeSelectQuery($sql); - $params = array($this->user); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAllUnreadOrStarred($this->user); - - $this->assertEquals($this->items, $result); - } - - - public function testFindAllFeed(){ - $sql = 'AND `items`.`feed_id` = ? ' . - 'AND `items`.`id` < ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status); - $params = array($this->user, $this->id, $this->offset); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAllFeed($this->id, $this->limit, - $this->offset, $this->status, false, $this->user); - - $this->assertEquals($this->items, $result); - } - - - public function testFindAllFeedOldestFirst(){ - $sql = 'AND `items`.`feed_id` = ? ' . - 'AND `items`.`id` > ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status, true); - $params = array($this->user, $this->id, $this->offset); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAllFeed($this->id, $this->limit, - $this->offset, $this->status, true, $this->user); - - $this->assertEquals($this->items, $result); - } + private $mapper; + private $items; + private $newestItemId; + private $limit; + private $user; + private $offset; + private $updatedSince; + private $status; + + + public function setUp() { + parent::setup(); + + $this->mapper = new ItemMapper($this->db); + + // create mock items + $item1 = new Item(); + $item2 = new Item(); + + $this->items = array( + $item1, + $item2 + ); + + $this->userId = 'john'; + $this->id = 3; + $this->folderId = 2; + + $this->row = array( + array('id' => $this->items[0]->getId()), + ); + + $this->rows = array( + array('id' => $this->items[0]->getId()), + array('id' => $this->items[1]->getId()) + ); + + $this->user = 'john'; + $this->limit = 10; + $this->offset = 3; + $this->id = 11; + $this->status = 333; + $this->updatedSince = 323; + $this->newestItemId = 2; + + } + + + private function makeSelectQuery($prependTo, $oldestFirst=false){ + if ($oldestFirst) { + $ordering = 'ASC'; + } else { + $ordering = 'DESC'; + } + + return 'SELECT `items`.* FROM `*PREFIX*news_items` `items` '. + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` '. + 'AND `feeds`.`deleted_at` = 0 ' . + 'AND `feeds`.`user_id` = ? ' . + $prependTo . + 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` ' . + 'ON `folders`.`id` = `feeds`.`folder_id` ' . + 'WHERE `feeds`.`folder_id` = 0 ' . + 'OR `folders`.`deleted_at` = 0 ' . + 'ORDER BY `items`.`id` ' . $ordering; + } + + private function makeSelectQueryStatus($prependTo, $status, + $oldestFirst=false) { + $status = (int) $status; + + return $this->makeSelectQuery( + 'AND ((`items`.`status` & ' . $status . ') = ' . $status . ') ' . + $prependTo, $oldestFirst + ); + } + + + public function testFind(){ + $sql = $this->makeSelectQuery('AND `items`.`id` = ? '); + + $this->setMapperResult($sql, array($this->userId, $this->id), $this->row); + + $result = $this->mapper->find($this->id, $this->userId); + $this->assertEquals($this->items[0], $result); + } + + + public function testGetStarredCount(){ + $userId = 'john'; + $row = array( + array('size' => 9) + ); + $sql = 'SELECT COUNT(*) AS size FROM `*PREFIX*news_items` `items` '. + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` '. + 'AND `feeds`.`deleted_at` = 0 ' . + 'AND `feeds`.`user_id` = ? ' . + 'AND ((`items`.`status` & ' . StatusFlag::STARRED . ') = ' . + StatusFlag::STARRED . ')' . + 'LEFT OUTER JOIN `*PREFIX*news_folders` `folders` ' . + 'ON `folders`.`id` = `feeds`.`folder_id` ' . + 'WHERE `feeds`.`folder_id` = 0 ' . + 'OR `folders`.`deleted_at` = 0'; + + $this->setMapperResult($sql, array($userId), $row); + + $result = $this->mapper->starredCount($userId); + $this->assertEquals($row[0]['size'], $result); + } + + + public function testReadAll(){ + $sql = 'UPDATE `*PREFIX*news_items` ' . + 'SET `status` = `status` & ? ' . + ', `last_modified` = ? ' . + 'WHERE `feed_id` IN (' . + 'SELECT `id` FROM `*PREFIX*news_feeds` ' . + 'WHERE `user_id` = ? ' . + ') '. + 'AND `id` <= ?'; + $params = array(~StatusFlag::UNREAD, $this->updatedSince, $this->user, 3); + $this->setMapperResult($sql, $params); + $this->mapper->readAll(3, $this->updatedSince, $this->user); + } + + + public function testReadFolder(){ + $sql = 'UPDATE `*PREFIX*news_items` ' . + 'SET `status` = `status` & ? ' . + ', `last_modified` = ? ' . + 'WHERE `feed_id` IN (' . + 'SELECT `id` FROM `*PREFIX*news_feeds` ' . + 'WHERE `folder_id` = ? ' . + 'AND `user_id` = ? ' . + ') '. + 'AND `id` <= ?'; + $params = array(~StatusFlag::UNREAD, $this->updatedSince, 3, $this->user, 6); + $this->setMapperResult($sql, $params); + $this->mapper->readFolder(3, 6, $this->updatedSince, $this->user); + } + + + public function testReadFeed(){ + $sql = 'UPDATE `*PREFIX*news_items` ' . + 'SET `status` = `status` & ? ' . + ', `last_modified` = ? ' . + 'WHERE `feed_id` = ? ' . + 'AND `id` <= ? ' . + 'AND EXISTS (' . + 'SELECT * FROM `*PREFIX*news_feeds` ' . + 'WHERE `user_id` = ? ' . + 'AND `id` = ? ) '; + $params = array(~StatusFlag::UNREAD, $this->updatedSince, 3, 6, + $this->user, 3); + $this->setMapperResult($sql, $params); + $this->mapper->readFeed(3, 6, $this->updatedSince, $this->user); + } + + + public function testFindAllNew(){ + $sql = 'AND `items`.`last_modified` >= ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status); + $params = array($this->user, $this->updatedSince); + + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAllNew($this->updatedSince, + $this->status, $this->user); + + $this->assertEquals($this->items, $result); + } + + + public function testFindAllNewFolder(){ + $sql = 'AND `feeds`.`folder_id` = ? ' . + 'AND `items`.`last_modified` >= ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status); + + $params = array($this->user, $this->id, $this->updatedSince); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAllNewFolder($this->id, $this->updatedSince, + $this->status, $this->user); + + $this->assertEquals($this->items, $result); + } + + + public function testFindAllNewFeed(){ + $sql = 'AND `items`.`feed_id` = ? ' . + 'AND `items`.`last_modified` >= ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status); + $params = array($this->user, $this->id, $this->updatedSince); + + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAllNewFeed($this->id, $this->updatedSince, + $this->status, $this->user); + + $this->assertEquals($this->items, $result); + } + + + public function testFindAllUnreadOrStarred(){ + $status = StatusFlag::UNREAD | StatusFlag::STARRED; + $sql = 'AND ((`items`.`status` & ' . $status . ') > 0) '; + $sql = $this->makeSelectQuery($sql); + $params = array($this->user); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAllUnreadOrStarred($this->user); + + $this->assertEquals($this->items, $result); + } + + + public function testFindAllFeed(){ + $sql = 'AND `items`.`feed_id` = ? ' . + 'AND `items`.`id` < ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status); + $params = array($this->user, $this->id, $this->offset); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAllFeed($this->id, $this->limit, + $this->offset, $this->status, false, $this->user); + + $this->assertEquals($this->items, $result); + } + + + public function testFindAllFeedOldestFirst(){ + $sql = 'AND `items`.`feed_id` = ? ' . + 'AND `items`.`id` > ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status, true); + $params = array($this->user, $this->id, $this->offset); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAllFeed($this->id, $this->limit, + $this->offset, $this->status, true, $this->user); + + $this->assertEquals($this->items, $result); + } - public function testFindAllFeedOffsetZero(){ - $sql = 'AND `items`.`feed_id` = ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status); - $params = array($this->user, $this->id); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAllFeed($this->id, $this->limit, - 0, $this->status, false, $this->user); + public function testFindAllFeedOffsetZero(){ + $sql = 'AND `items`.`feed_id` = ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status); + $params = array($this->user, $this->id); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAllFeed($this->id, $this->limit, + 0, $this->status, false, $this->user); - $this->assertEquals($this->items, $result); - } + $this->assertEquals($this->items, $result); + } - public function testFindAllFolder(){ - $sql = 'AND `feeds`.`folder_id` = ? ' . - 'AND `items`.`id` < ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status); - $params = array($this->user, $this->id, - $this->offset); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAllFolder($this->id, $this->limit, - $this->offset, $this->status, false, $this->user); + public function testFindAllFolder(){ + $sql = 'AND `feeds`.`folder_id` = ? ' . + 'AND `items`.`id` < ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status); + $params = array($this->user, $this->id, + $this->offset); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAllFolder($this->id, $this->limit, + $this->offset, $this->status, false, $this->user); - $this->assertEquals($this->items, $result); - } + $this->assertEquals($this->items, $result); + } - public function testFindAllFolderOldestFirst(){ - $sql = 'AND `feeds`.`folder_id` = ? ' . - 'AND `items`.`id` > ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status, true); - $params = array($this->user, $this->id, - $this->offset); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAllFolder($this->id, $this->limit, - $this->offset, $this->status, true, $this->user); + public function testFindAllFolderOldestFirst(){ + $sql = 'AND `feeds`.`folder_id` = ? ' . + 'AND `items`.`id` > ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status, true); + $params = array($this->user, $this->id, + $this->offset); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAllFolder($this->id, $this->limit, + $this->offset, $this->status, true, $this->user); - $this->assertEquals($this->items, $result); - } + $this->assertEquals($this->items, $result); + } - public function testFindAllFolderOffsetZero(){ - $sql = 'AND `feeds`.`folder_id` = ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status); - $params = array($this->user, $this->id); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAllFolder($this->id, $this->limit, - 0, $this->status, false, $this->user); + public function testFindAllFolderOffsetZero(){ + $sql = 'AND `feeds`.`folder_id` = ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status); + $params = array($this->user, $this->id); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAllFolder($this->id, $this->limit, + 0, $this->status, false, $this->user); - $this->assertEquals($this->items, $result); - } + $this->assertEquals($this->items, $result); + } - public function testFindAll(){ - $sql = 'AND `items`.`id` < ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status); - $params = array($this->user, $this->offset); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAll($this->limit, - $this->offset, $this->status, false, $this->user); + public function testFindAll(){ + $sql = 'AND `items`.`id` < ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status); + $params = array($this->user, $this->offset); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAll($this->limit, + $this->offset, $this->status, false, $this->user); - $this->assertEquals($this->items, $result); - } + $this->assertEquals($this->items, $result); + } - public function testFindAllOldestFirst(){ - $sql = 'AND `items`.`id` > ? '; - $sql = $this->makeSelectQueryStatus($sql, $this->status, true); - $params = array($this->user, $this->offset); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAll($this->limit, - $this->offset, $this->status, true, $this->user); + public function testFindAllOldestFirst(){ + $sql = 'AND `items`.`id` > ? '; + $sql = $this->makeSelectQueryStatus($sql, $this->status, true); + $params = array($this->user, $this->offset); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAll($this->limit, + $this->offset, $this->status, true, $this->user); - $this->assertEquals($this->items, $result); - } + $this->assertEquals($this->items, $result); + } - public function testFindAllOffsetZero(){ - $sql = $this->makeSelectQueryStatus('', $this->status); - $params = array($this->user); - $this->setMapperResult($sql, $params, $this->rows); - $result = $this->mapper->findAll($this->limit, - 0, $this->status, false, $this->user); + public function testFindAllOffsetZero(){ + $sql = $this->makeSelectQueryStatus('', $this->status); + $params = array($this->user); + $this->setMapperResult($sql, $params, $this->rows); + $result = $this->mapper->findAll($this->limit, + 0, $this->status, false, $this->user); - $this->assertEquals($this->items, $result); - } + $this->assertEquals($this->items, $result); + } - public function testFindByGuidHash(){ - $hash = md5('test'); - $feedId = 3; - $sql = $this->makeSelectQuery( - 'AND `items`.`guid_hash` = ? ' . - 'AND `feeds`.`id` = ? '); + public function testFindByGuidHash(){ + $hash = md5('test'); + $feedId = 3; + $sql = $this->makeSelectQuery( + 'AND `items`.`guid_hash` = ? ' . + 'AND `feeds`.`id` = ? '); - $this->setMapperResult($sql, array($this->userId, $hash, $feedId), $this->row); + $this->setMapperResult($sql, array($this->userId, $hash, $feedId), $this->row); - $result = $this->mapper->findByGuidHash($hash, $feedId, $this->userId); - $this->assertEquals($this->items[0], $result); - } + $result = $this->mapper->findByGuidHash($hash, $feedId, $this->userId); + $this->assertEquals($this->items[0], $result); + } - public function testDeleteReadOlderThanThresholdDoesNotDeleteBelowThreshold(){ - $status = StatusFlag::STARRED | StatusFlag::UNREAD; - $sql = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . - '`items`.`feed_id` AS `feed_id` ' . - 'FROM `*PREFIX*news_items` `items` ' . - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'WHERE NOT ((`items`.`status` & ?) > 0) ' . - 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . - 'HAVING COUNT(*) > ?'; + public function testDeleteReadOlderThanThresholdDoesNotDeleteBelowThreshold(){ + $status = StatusFlag::STARRED | StatusFlag::UNREAD; + $sql = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . + '`items`.`feed_id` AS `feed_id` ' . + 'FROM `*PREFIX*news_items` `items` ' . + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'WHERE NOT ((`items`.`status` & ?) > 0) ' . + 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . + 'HAVING COUNT(*) > ?'; - $threshold = 10; - $rows = array(array('feed_id' => 30, 'size' => 9)); - $params = array($status, $threshold); + $threshold = 10; + $rows = array(array('feed_id' => 30, 'size' => 9)); + $params = array($status, $threshold); - $this->setMapperResult($sql, $params, $rows); - $this->mapper->deleteReadOlderThanThreshold($threshold); + $this->setMapperResult($sql, $params, $rows); + $this->mapper->deleteReadOlderThanThreshold($threshold); - } + } - public function testDeleteReadOlderThanThreshold(){ - $threshold = 10; - $status = StatusFlag::STARRED | StatusFlag::UNREAD; + public function testDeleteReadOlderThanThreshold(){ + $threshold = 10; + $status = StatusFlag::STARRED | StatusFlag::UNREAD; - $sql1 = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . - '`items`.`feed_id` AS `feed_id` ' . - 'FROM `*PREFIX*news_items` `items` ' . - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'WHERE NOT ((`items`.`status` & ?) > 0) ' . - 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . - 'HAVING COUNT(*) > ?'; - $params1 = array($status, $threshold); + $sql1 = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . + '`items`.`feed_id` AS `feed_id` ' . + 'FROM `*PREFIX*news_items` `items` ' . + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'WHERE NOT ((`items`.`status` & ?) > 0) ' . + 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . + 'HAVING COUNT(*) > ?'; + $params1 = array($status, $threshold); - $row = array('feed_id' => 30, 'size' => 11); + $row = array('feed_id' => 30, 'size' => 11); - $sql2 = 'DELETE FROM `*PREFIX*news_items` ' . - 'WHERE NOT ((`status` & ?) > 0) ' . - 'AND `feed_id` = ? ' . - 'ORDER BY `id` ASC'; - $params2 = array($status, 30); + $sql2 = 'DELETE FROM `*PREFIX*news_items` ' . + 'WHERE NOT ((`status` & ?) > 0) ' . + 'AND `feed_id` = ? ' . + 'ORDER BY `id` ASC'; + $params2 = array($status, 30); - $this->setMapperResult($sql1, $params1, array($row)); - $this->setMapperResult($sql2, $params2); + $this->setMapperResult($sql1, $params1, array($row)); + $this->setMapperResult($sql2, $params2); - $this->mapper->deleteReadOlderThanThreshold($threshold); - } + $this->mapper->deleteReadOlderThanThreshold($threshold); + } - public function testGetNewestItem() { - $sql = 'SELECT MAX(`items`.`id`) AS `max_id` FROM `*PREFIX*news_items` `items` '. - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` '. - 'AND `feeds`.`user_id` = ?'; - $params = array($this->user); - $rows = array(array('max_id' => 3)); + public function testGetNewestItem() { + $sql = 'SELECT MAX(`items`.`id`) AS `max_id` FROM `*PREFIX*news_items` `items` '. + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` '. + 'AND `feeds`.`user_id` = ?'; + $params = array($this->user); + $rows = array(array('max_id' => 3)); - $this->setMapperResult($sql, $params, $rows); + $this->setMapperResult($sql, $params, $rows); - $result = $this->mapper->getNewestItemId($this->user); - $this->assertEquals(3, $result); - } + $result = $this->mapper->getNewestItemId($this->user); + $this->assertEquals(3, $result); + } - public function testGetNewestItemIdNotFound() { - $sql = 'SELECT MAX(`items`.`id`) AS `max_id` FROM `*PREFIX*news_items` `items` '. - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` '. - 'AND `feeds`.`user_id` = ?'; - $params = array($this->user); - $rows = array(); + public function testGetNewestItemIdNotFound() { + $sql = 'SELECT MAX(`items`.`id`) AS `max_id` FROM `*PREFIX*news_items` `items` '. + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` '. + 'AND `feeds`.`user_id` = ?'; + $params = array($this->user); + $rows = array(); - $this->setMapperResult($sql, $params, $rows); - $this->setExpectedException('\OCP\AppFramework\Db\DoesNotExistException'); + $this->setMapperResult($sql, $params, $rows); + $this->setExpectedException('\OCP\AppFramework\Db\DoesNotExistException'); - $this->mapper->getNewestItemId($this->user); - } + $this->mapper->getNewestItemId($this->user); + } - public function testDeleteFromUser(){ - $userId = 'john'; - $sql = 'DELETE FROM `*PREFIX*news_items` ' . - 'WHERE `feed_id` IN (' . - 'SELECT `feeds`.`id` FROM `*PREFIX*news_feeds` `feeds` ' . - 'WHERE `feeds`.`user_id` = ?' . - ')'; + public function testDeleteFromUser(){ + $userId = 'john'; + $sql = 'DELETE FROM `*PREFIX*news_items` ' . + 'WHERE `feed_id` IN (' . + 'SELECT `feeds`.`id` FROM `*PREFIX*news_feeds` `feeds` ' . + 'WHERE `feeds`.`user_id` = ?' . + ')'; - $this->setMapperResult($sql, array($userId)); + $this->setMapperResult($sql, array($userId)); - $this->mapper->deleteUser($userId); - } + $this->mapper->deleteUser($userId); + } }
\ No newline at end of file diff --git a/tests/unit/db/ItemTest.php b/tests/unit/db/ItemTest.php index 6c1a16c20..2739baabd 100644 --- a/tests/unit/db/ItemTest.php +++ b/tests/unit/db/ItemTest.php @@ -16,263 +16,263 @@ namespace OCA\News\Db; class ItemTest extends \PHPUnit_Framework_TestCase { - private $item; - - protected function setUp(){ - $this->item = new Item(); - $this->item->setStatus(0); - } - - - public function testSetRead(){ - $this->item->setRead(); - - $this->assertTrue($this->item->isRead()); - } - - - public function testSetUnread(){ - $this->item->setUnread(); - - $this->assertTrue($this->item->isUnread()); - } - - - public function testSetStarred(){ - $this->item->setStarred(); - - $this->assertTrue($this->item->isStarred()); - } - - - public function testSetUnstarred(){ - $this->item->setUnstarred(); - - $this->assertTrue($this->item->isUnstarred()); - } - - - public function testToAPI() { - $item = new Item(); - $item->setId(3); - $item->setGuid('guid'); - $item->setGuidHash('hash'); - $item->setUrl('https://google'); - $item->setTitle('title'); - $item->setAuthor('author'); - $item->setPubDate(123); - $item->setBody('body'); - $item->setEnclosureMime('audio/ogg'); - $item->setEnclosureLink('enclink'); - $item->setFeedId(1); - $item->setStatus(0); - $item->setUnread(); - $item->setStarred(); - $item->setLastModified(321); - - $this->assertEquals([ - 'id' => 3, - 'guid' => 'guid', - 'guidHash' => 'hash', - 'url' => 'https://google', - 'title' => 'title', - 'author' => 'author', - 'pubDate' => 123, - 'body' => 'body', - 'enclosureMime' => 'audio/ogg', - 'enclosureLink' => 'enclink', - 'feedId' => 1, - 'unread' => true, - 'starred' => true, - 'lastModified' => 321 - ], $item->toAPI()); - } - - - public function testJSONSerialize() { - $item = new Item(); - $item->setId(3); - $item->setGuid('guid'); - $item->setGuidHash('hash'); - $item->setUrl('https://google'); - $item->setTitle('title'); - $item->setAuthor('author'); - $item->setPubDate(123); - $item->setBody('body'); - $item->setEnclosureMime('audio/ogg'); - $item->setEnclosureLink('enclink'); - $item->setFeedId(1); - $item->setStatus(0); - $item->setUnread(); - $item->setStarred(); - $item->setLastModified(321); - - $this->assertEquals([ - 'id' => 3, - 'guid' => 'guid', - 'guidHash' => 'hash', - 'url' => 'https://google', - 'title' => 'title', - 'author' => 'author', - 'pubDate' => 123, - 'body' => 'body', - 'enclosureMime' => 'audio/ogg', - 'enclosureLink' => 'enclink', - 'feedId' => 1, - 'unread' => true, - 'starred' => true, - 'lastModified' => 321 - ], $item->jsonSerialize()); - } - - public function testToExport() { - $item = new Item(); - $item->setId(3); - $item->setGuid('guid'); - $item->setGuidHash('hash'); - $item->setUrl('https://google'); - $item->setTitle('title'); - $item->setAuthor('author'); - $item->setPubDate(123); - $item->setBody('body'); - $item->setEnclosureMime('audio/ogg'); - $item->setEnclosureLink('enclink'); - $item->setFeedId(1); - $item->setStatus(0); - $item->setRead(); - $item->setStarred(); - $item->setLastModified(321); - - $feed = new Feed(); - $feed->setLink('http://test'); - $feeds = ["feed1" => $feed]; - - $this->assertEquals([ - 'guid' => 'guid', - 'url' => 'https://google', - 'title' => 'title', - 'author' => 'author', - 'pubDate' => 123, - 'body' => 'body', - 'enclosureMime' => 'audio/ogg', - 'enclosureLink' => 'enclink', - 'unread' => false, - 'starred' => true, - 'feedLink' => 'http://test' - ], $item->toExport($feeds)); - } - - - private function createImportItem($isRead) { - $item = new Item(); - $item->setGuid('guid'); - $item->setUrl('https://google'); - $item->setTitle('title'); - $item->setAuthor('author'); - $item->setPubDate(123); - $item->setBody('body'); - $item->setEnclosureMime('audio/ogg'); - $item->setEnclosureLink('enclink'); - $item->setStarred(); - - if ($isRead) { - $item->setUnread(); - } else { - $item->setRead(); - } - - return $item; - } - - - public function testFromImport() { - $item = $this->createImportItem(false); - - $import = [ - 'guid' => $item->getGuid(), - 'url' => $item->getUrl(), - 'title' => $item->getTitle(), - 'author' => $item->getAuthor(), - 'pubDate' => $item->getPubDate(), - 'body' => $item->getBody(), - 'enclosureMime' => $item->getEnclosureMime(), - 'enclosureLink' => $item->getEnclosureLink(), - 'unread' => $item->isUnread(), - 'starred' => $item->isStarred(), - ]; - - $compareWith = Item::fromImport($import); - - $this->assertEquals($item, $compareWith); - } - - - public function testFromImportRead() { - $item = $this->createImportItem(true); - - $import = [ - 'guid' => $item->getGuid(), - 'url' => $item->getUrl(), - 'title' => $item->getTitle(), - 'author' => $item->getAuthor(), - 'pubDate' => $item->getPubDate(), - 'body' => $item->getBody(), - 'enclosureMime' => $item->getEnclosureMime(), - 'enclosureLink' => $item->getEnclosureLink(), - 'unread' => $item->isUnread(), - 'starred' => $item->isStarred(), - ]; - - $compareWith = Item::fromImport($import); - - $this->assertEquals($item, $compareWith); - } - - - - public function testSetAuthor(){ - $item = new Item(); - $item->setAuthor('<a>my link</li>'); - $this->assertEquals('my link', $item->getAuthor()); - $this->assertContains('author', $item->getUpdatedFields()); - } - - - public function testSetTitle(){ - $item = new Item(); - $item->setTitle('<a>my link</li>'); - $this->assertEquals('my link', $item->getTitle()); - $this->assertContains('title', $item->getUpdatedFields()); - } - - - public function testSetXSSUrl() { - $item = new Item(); - $item->setUrl('javascript:alert()'); - $this->assertEquals('', $item->getUrl()); - } - - - public function testSetMagnetUrl() { - $item = new Item(); - $item->setUrl('magnet://link.com'); - $this->assertEquals('magnet://link.com', $item->getUrl()); - } - - - public function testSetGuidUpdatesHash() { - $item = new Item(); - $item->setGuid('http://test'); - $this->assertEquals(md5('http://test'), $item->getGuidHash()); - } - - - public function testMakeLinksInBodyOpenNewTab() { - $item = new Item(); - $item->setBody("<a href=\"test\">ha</a>"); - $this->assertEquals("<a target=\"_blank\" href=\"test\">ha</a>", - $item->getBody()); - } + private $item; + + protected function setUp(){ + $this->item = new Item(); + $this->item->setStatus(0); + } + + + public function testSetRead(){ + $this->item->setRead(); + + $this->assertTrue($this->item->isRead()); + } + + + public function testSetUnread(){ + $this->item->setUnread(); + + $this->assertTrue($this->item->isUnread()); + } + + + public function testSetStarred(){ + $this->item->setStarred(); + + $this->assertTrue($this->item->isStarred()); + } + + + public function testSetUnstarred(){ + $this->item->setUnstarred(); + + $this->assertTrue($this->item->isUnstarred()); + } + + + public function testToAPI() { + $item = new Item(); + $item->setId(3); + $item->setGuid('guid'); + $item->setGuidHash('hash'); + $item->setUrl('https://google'); + $item->setTitle('title'); + $item->setAuthor('author'); + $item->setPubDate(123); + $item->setBody('body'); + $item->setEnclosureMime('audio/ogg'); + $item->setEnclosureLink('enclink'); + $item->setFeedId(1); + $item->setStatus(0); + $item->setUnread(); + $item->setStarred(); + $item->setLastModified(321); + + $this->assertEquals([ + 'id' => 3, + 'guid' => 'guid', + 'guidHash' => 'hash', + 'url' => 'https://google', + 'title' => 'title', + 'author' => 'author', + 'pubDate' => 123, + 'body' => 'body', + 'enclosureMime' => 'audio/ogg', + 'enclosureLink' => 'enclink', + 'feedId' => 1, + 'unread' => true, + 'starred' => true, + 'lastModified' => 321 + ], $item->toAPI()); + } + + + public function testJSONSerialize() { + $item = new Item(); + $item->setId(3); + $item->setGuid('guid'); + $item->setGuidHash('hash'); + $item->setUrl('https://google'); + $item->setTitle('title'); + $item->setAuthor('author'); + $item->setPubDate(123); + $item->setBody('body'); + $item->setEnclosureMime('audio/ogg'); + $item->setEnclosureLink('enclink'); + $item->setFeedId(1); + $item->setStatus(0); + $item->setUnread(); + $item->setStarred(); + $item->setLastModified(321); + + $this->assertEquals([ + 'id' => 3, + 'guid' => 'guid', + 'guidHash' => 'hash', + 'url' => 'https://google', + 'title' => 'title', + 'author' => 'author', + 'pubDate' => 123, + 'body' => 'body', + 'enclosureMime' => 'audio/ogg', + 'enclosureLink' => 'enclink', + 'feedId' => 1, + 'unread' => true, + 'starred' => true, + 'lastModified' => 321 + ], $item->jsonSerialize()); + } + + public function testToExport() { + $item = new Item(); + $item->setId(3); + $item->setGuid('guid'); + $item->setGuidHash('hash'); + $item->setUrl('https://google'); + $item->setTitle('title'); + $item->setAuthor('author'); + $item->setPubDate(123); + $item->setBody('body'); + $item->setEnclosureMime('audio/ogg'); + $item->setEnclosureLink('enclink'); + $item->setFeedId(1); + $item->setStatus(0); + $item->setRead(); + $item->setStarred(); + $item->setLastModified(321); + + $feed = new Feed(); + $feed->setLink('http://test'); + $feeds = ["feed1" => $feed]; + + $this->assertEquals([ + 'guid' => 'guid', + 'url' => 'https://google', + 'title' => 'title', + 'author' => 'author', + 'pubDate' => 123, + 'body' => 'body', + 'enclosureMime' => 'audio/ogg', + 'enclosureLink' => 'enclink', + 'unread' => false, + 'starred' => true, + 'feedLink' => 'http://test' + ], $item->toExport($feeds)); + } + + + private function createImportItem($isRead) { + $item = new Item(); + $item->setGuid('guid'); + $item->setUrl('https://google'); + $item->setTitle('title'); + $item->setAuthor('author'); + $item->setPubDate(123); + $item->setBody('body'); + $item->setEnclosureMime('audio/ogg'); + $item->setEnclosureLink('enclink'); + $item->setStarred(); + + if ($isRead) { + $item->setUnread(); + } else { + $item->setRead(); + } + + return $item; + } + + + public function testFromImport() { + $item = $this->createImportItem(false); + + $import = [ + 'guid' => $item->getGuid(), + 'url' => $item->getUrl(), + 'title' => $item->getTitle(), + 'author' => $item->getAuthor(), + 'pubDate' => $item->getPubDate(), + 'body' => $item->getBody(), + 'enclosureMime' => $item->getEnclosureMime(), + 'enclosureLink' => $item->getEnclosureLink(), + 'unread' => $item->isUnread(), + 'starred' => $item->isStarred(), + ]; + + $compareWith = Item::fromImport($import); + + $this->assertEquals($item, $compareWith); + } + + + public function testFromImportRead() { + $item = $this->createImportItem(true); + + $import = [ + 'guid' => $item->getGuid(), + 'url' => $item->getUrl(), + 'title' => $item->getTitle(), + 'author' => $item->getAuthor(), + 'pubDate' => $item->getPubDate(), + 'body' => $item->getBody(), + 'enclosureMime' => $item->getEnclosureMime(), + 'enclosureLink' => $item->getEnclosureLink(), + 'unread' => $item->isUnread(), + 'starred' => $item->isStarred(), + ]; + + $compareWith = Item::fromImport($import); + + $this->assertEquals($item, $compareWith); + } + + + + public function testSetAuthor(){ + $item = new Item(); + $item->setAuthor('<a>my link</li>'); + $this->assertEquals('my link', $item->getAuthor()); + $this->assertContains('author', $item->getUpdatedFields()); + } + + + public function testSetTitle(){ + $item = new Item(); + $item->setTitle('<a>my link</li>'); + $this->assertEquals('my link', $item->getTitle()); + $this->assertContains('title', $item->getUpdatedFields()); + } + + + public function testSetXSSUrl() { + $item = new Item(); + $item->setUrl('javascript:alert()'); + $this->assertEquals('', $item->getUrl()); + } + + + public function testSetMagnetUrl() { + $item = new Item(); + $item->setUrl('magnet://link.com'); + $this->assertEquals('magnet://link.com', $item->getUrl()); + } + + + public function testSetGuidUpdatesHash() { + $item = new Item(); + $item->setGuid('http://test'); + $this->assertEquals(md5('http://test'), $item->getGuidHash()); + } + + + public function testMakeLinksInBodyOpenNewTab() { + $item = new Item(); + $item->setBody("<a href=\"test\">ha</a>"); + $this->assertEquals("<a target=\"_blank\" href=\"test\">ha</a>", + $item->getBody()); + } }
\ No newline at end of file diff --git a/tests/unit/db/MapperFactoryTest.php b/tests/unit/db/MapperFactoryTest.php index d96c9d857..3ebc0ce17 100644 --- a/tests/unit/db/MapperFactoryTest.php +++ b/tests/unit/db/MapperFactoryTest.php @@ -16,35 +16,35 @@ namespace OCA\News\Db; class MapperFactoryTest extends \PHPUnit_Framework_TestCase { - private $db; - private $settings; + private $db; + private $settings; - public function setUp() { - $this->db = $this->getMockBuilder('\OCP\IDb') - ->disableOriginalConstructor() - ->getMock(); - } + public function setUp() { + $this->db = $this->getMockBuilder('\OCP\IDb') + ->disableOriginalConstructor() + ->getMock(); + } - public function testGetItemMapperSqlite() { - $factory = new MapperFactory('sqlite', $this->db); + public function testGetItemMapperSqlite() { + $factory = new MapperFactory('sqlite', $this->db); - $this->assertTrue($factory->getItemMapper() instanceof ItemMapper); - } + $this->assertTrue($factory->getItemMapper() instanceof ItemMapper); + } - public function testGetItemMapperMysql() { - $factory = new MapperFactory('mysql', $this->db); + public function testGetItemMapperMysql() { + $factory = new MapperFactory('mysql', $this->db); - $this->assertTrue($factory->getItemMapper() instanceof ItemMapper); - } + $this->assertTrue($factory->getItemMapper() instanceof ItemMapper); + } - public function testGetItemMapperPostgres() { - $factory = new MapperFactory('pgsql', $this->db); + public function testGetItemMapperPostgres() { + $factory = new MapperFactory('pgsql', $this->db); - $this->assertTrue($factory->getItemMapper() instanceof \OCA\News\Db\Postgres\ItemMapper); - } + $this->assertTrue($factory->getItemMapper() instanceof \OCA\News\Db\Postgres\ItemMapper); + } }
\ No newline at end of file diff --git a/tests/unit/db/postgres/ItemMapperTest.php b/tests/unit/db/postgres/ItemMapperTest.php index 528f6003a..04550695d 100644 --- a/tests/unit/db/postgres/ItemMapperTest.php +++ b/tests/unit/db/postgres/ItemMapperTest.php @@ -19,104 +19,104 @@ use \OCA\News\Db\StatusFlag; class ItemMapperTest extends \Test\AppFramework\Db\MapperTestUtility { - private $mapper; - private $items; - private $newestItemId; - private $limit; - private $user; - private $offset; - private $updatedSince; - private $status; + private $mapper; + private $items; + private $newestItemId; + private $limit; + private $user; + private $offset; + private $updatedSince; + private $status; - public function setUp() { - parent::setUp(); + public function setUp() { + parent::setUp(); - $this->mapper = new ItemMapper($this->db); + $this->mapper = new ItemMapper($this->db); - // create mock items - $item1 = new Item(); - $item2 = new Item(); + // create mock items + $item1 = new Item(); + $item2 = new Item(); - $this->items = [$item1, $item2]; + $this->items = [$item1, $item2]; - $this->userId = 'john'; - $this->id = 3; - $this->folderId = 2; + $this->userId = 'john'; + $this->id = 3; + $this->folderId = 2; - $this->row = [['id' => $this->items[0]->getId()]]; + $this->row = [['id' => $this->items[0]->getId()]]; - $this->rows = [ - ['id' => $this->items[0]->getId()], - ['id' => $this->items[1]->getId()] - ]; + $this->rows = [ + ['id' => $this->items[0]->getId()], + ['id' => $this->items[1]->getId()] + ]; - $this->user = 'john'; - $this->limit = 10; - $this->offset = 3; - $this->id = 11; - $this->status = 333; - $this->updatedSince = 323; - $this->newestItemId = 2; + $this->user = 'john'; + $this->limit = 10; + $this->offset = 3; + $this->id = 11; + $this->status = 333; + $this->updatedSince = 323; + $this->newestItemId = 2; - } + } - public function testDeleteReadOlderThanThresholdDoesNotDeleteBelowThreshold(){ - $status = StatusFlag::STARRED | StatusFlag::UNREAD; - $sql = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . - '`items`.`feed_id` AS `feed_id` ' . - 'FROM `*PREFIX*news_items` `items` ' . - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'WHERE NOT ((`items`.`status` & ?) > 0) ' . - 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . - 'HAVING COUNT(*) > ?'; + public function testDeleteReadOlderThanThresholdDoesNotDeleteBelowThreshold(){ + $status = StatusFlag::STARRED | StatusFlag::UNREAD; + $sql = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . + '`items`.`feed_id` AS `feed_id` ' . + 'FROM `*PREFIX*news_items` `items` ' . + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'WHERE NOT ((`items`.`status` & ?) > 0) ' . + 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . + 'HAVING COUNT(*) > ?'; - $threshold = 10; - $rows = [['feed_id' => 30, 'size' => 9]]; - $params = [$status, $threshold]; + $threshold = 10; + $rows = [['feed_id' => 30, 'size' => 9]]; + $params = [$status, $threshold]; - $this->setMapperResult($sql, $params, $rows); - $this->mapper->deleteReadOlderThanThreshold($threshold); + $this->setMapperResult($sql, $params, $rows); + $this->mapper->deleteReadOlderThanThreshold($threshold); - } + } - public function testDeleteReadOlderThanThreshold(){ - $threshold = 10; - $status = StatusFlag::STARRED | StatusFlag::UNREAD; + public function testDeleteReadOlderThanThreshold(){ + $threshold = 10; + $status = StatusFlag::STARRED | StatusFlag::UNREAD; - $sql1 = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . - '`items`.`feed_id` AS `feed_id` ' . - 'FROM `*PREFIX*news_items` `items` ' . - 'JOIN `*PREFIX*news_feeds` `feeds` ' . - 'ON `feeds`.`id` = `items`.`feed_id` ' . - 'WHERE NOT ((`items`.`status` & ?) > 0) ' . - 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . - 'HAVING COUNT(*) > ?'; - $params1 = [$status, $threshold]; + $sql1 = 'SELECT COUNT(*) - `feeds`.`articles_per_update` AS `size`, ' . + '`items`.`feed_id` AS `feed_id` ' . + 'FROM `*PREFIX*news_items` `items` ' . + 'JOIN `*PREFIX*news_feeds` `feeds` ' . + 'ON `feeds`.`id` = `items`.`feed_id` ' . + 'WHERE NOT ((`items`.`status` & ?) > 0) ' . + 'GROUP BY `items`.`feed_id`, `feeds`.`articles_per_update` ' . + 'HAVING COUNT(*) > ?'; + $params1 = [$status, $threshold]; - $row = ['feed_id' => 30, 'size' => 11]; + $row = ['feed_id' => 30, 'size' => 11]; - $sql2 = 'DELETE FROM `*PREFIX*news_items` ' . - 'WHERE `id` IN (' . - 'SELECT `id` FROM `*PREFIX*news_items` ' . - 'WHERE NOT ((`status` & ?) > 0) ' . - 'AND `feed_id` = ? ' . - 'ORDER BY `id` ASC ' . - 'LIMIT ?' . - ')'; - $params2 = [$status, 30, 1]; + $sql2 = 'DELETE FROM `*PREFIX*news_items` ' . + 'WHERE `id` IN (' . + 'SELECT `id` FROM `*PREFIX*news_items` ' . + 'WHERE NOT ((`status` & ?) > 0) ' . + 'AND `feed_id` = ? ' . + 'ORDER BY `id` ASC ' . + 'LIMIT ?' . + ')'; + $params2 = [$status, 30, 1]; - $this->setMapperResult($sql1, $params1, [$row]); - $this->setMapperResult($sql2, $params2); + $this->setMapperResult($sql1, $params1, [$row]); + $this->setMapperResult($sql2, $params2); - $this->mapper->deleteReadOlderThanThreshold($threshold); - } + $this->mapper->deleteReadOlderThanThreshold($threshold); + } } diff --git a/tests/unit/fetcher/FeedFetcherTest.php b/tests/unit/fetcher/FeedFetcherTest.php index 948e25e9b..6a0cec4dc 100644 --- a/tests/unit/fetcher/FeedFetcherTest.php +++ b/tests/unit/fetcher/FeedFetcherTest.php @@ -19,443 +19,443 @@ use \OCA\News\Db\Feed; class FeedFetcherTest extends \PHPUnit_Framework_TestCase { - private $fetcher; - private $core; - private $coreFactory; - private $faviconFetcher; - private $url; - private $cacheDirectory; - private $cacheDuration; - private $time; - private $item; - private $purifier; - private $fetchTimeout; - private $proxyHost; - private $getProxyPort; - private $proxyAuth; - private $config; - private $appconfig; - - // items - private $permalink; - private $title; - private $guid; - private $pub; - private $body; - private $author; - private $authorMail; - private $enclosureLink; - - // feed - private $feedTitle; - private $feedLink; - private $feedImage; - private $webFavicon; - - protected function setUp(){ - $this->core = $this->getMock( - '\SimplePie_Core', [ - 'set_timeout', - 'set_feed_url', - 'enable_cache', - 'set_stupidly_fast', - 'set_cache_location', - 'set_cache_duration', - 'set_proxyhost', - 'set_proxyport', - 'set_proxyuserpwd', - 'set_useragent', - 'init', - 'get_permalink', - 'get_items', - 'get_title', - 'get_image_url' - ]); - $this->coreFactory = $this->getMockBuilder( - '\OCA\News\Utility\SimplePieAPIFactory') - ->disableOriginalConstructor() - ->getMock(); - $this->coreFactory->expects($this->any()) - ->method('getCore') - ->will($this->returnValue($this->core)); - $this->item = $this->getMockBuilder( - '\SimplePie_Item') - ->disableOriginalConstructor() - ->getMock(); - $this->faviconFetcher = $this->getMockBuilder( - '\OCA\News\Utility\FaviconFetcher') - ->disableOriginalConstructor() - ->getMock(); - $this->appconfig = $this->getMockBuilder( - '\OCA\News\Config\AppConfig') - ->disableOriginalConstructor() - ->getMock(); - $this->time = 2323; - $timeFactory = $this->getMock('TimeFactory', ['getTime']); - $timeFactory->expects($this->any()) - ->method('getTime') - ->will($this->returnValue($this->time)); - $this->cacheDuration = 100; - $this->cacheDirectory = 'dir/'; - $this->proxyHost = 'test'; - $this->proxyPort = 30; - $this->proxyAuth = 'hi'; - $this->fetchTimeout = 40; - $this->config = $this->getMockBuilder( - '\OCA\News\Config\Config') - ->disableOriginalConstructor() - ->getMock(); - $this->config->expects($this->any()) - ->method('getSimplePieCacheDuration') - ->will($this->returnValue($this->cacheDuration)); - $this->config->expects($this->any()) - ->method('getProxyHost') - ->will($this->returnValue($this->proxyHost)); - $this->config->expects($this->any()) - ->method('getProxyAuth') - ->will($this->returnValue($this->proxyAuth)); - $this->config->expects($this->any()) - ->method('getProxyPort') - ->will($this->returnValue($this->proxyPort)); - $this->config->expects($this->any()) - ->method('getFeedFetcherTimeout') - ->will($this->returnValue($this->fetchTimeout)); - $this->appconfig->expects($this->any()) - ->method('getConfig') - ->with($this->equalTo('version')) - ->will($this->returnValue(3)); - $this->fetcher = new FeedFetcher($this->coreFactory, - $this->faviconFetcher, - $timeFactory, - $this->cacheDirectory, - $this->config, - $this->appconfig); - $this->url = 'http://tests'; - - $this->permalink = 'http://permalink'; - $this->title = 'my&lt;' title'; - $this->guid = 'hey guid here'; - $this->body = 'let the bodies hit the floor <a href="test">test</a>'; - $this->body2 = 'let the bodies hit the floor <a target="_blank" href="test">test</a>'; - $this->pub = 23111; - $this->author = '<boogieman'; - $this->enclosureLink = 'http://enclosure.you'; - - $this->feedTitle = '<a>&its a</a> title'; - $this->feedLink = 'http://goatse'; - $this->feedImage = '/an/image'; - $this->webFavicon = 'http://anon.google.com'; - $this->authorMail = 'doe@joes.com'; - } - - - public function testCanHandle(){ - $url = 'google.de'; - - $this->assertTrue($this->fetcher->canHandle($url)); - } - - - public function testDoesNotUseProxyIfNotEnabled() { - $this->config->expects($this->any()) - ->method('getProxyHost') - ->will($this->returnValue('')); - $this->core->expects($this->never()) - ->method('set_proxyhost'); - $this->core->expects($this->never()) - ->method('set_proxyport'); - $this->core->expects($this->never()) - ->method('set_proxyuserpwd'); - } - - - public function testFetchThrowsExceptionWhenInitFailed() { - $this->core->expects($this->once()) - ->method('set_feed_url') - ->with($this->equalTo($this->url)); - $this->core->expects($this->once()) - ->method('enable_cache') - ->with($this->equalTo(true)); - $this->core->expects($this->once()) - ->method('set_timeout') - ->with($this->equalTo($this->fetchTimeout)); - $this->core->expects($this->once()) - ->method('set_cache_location') - ->with($this->equalTo($this->cacheDirectory)); - $this->core->expects($this->once()) - ->method('set_proxyhost') - ->with($this->equalTo($this->proxyHost)); - $this->core->expects($this->once()) - ->method('set_proxyport') - ->with($this->equalTo($this->proxyPort)); - $this->core->expects($this->once()) - ->method('set_proxyuserpwd') - ->with($this->equalTo($this->proxyAuth)); - $this->core->expects($this->once()) - ->method('set_stupidly_fast') - ->with($this->equalTo(true)); - $this->core->expects($this->once()) - ->method('set_cache_duration') - ->with($this->equalTo($this->cacheDuration)); - $this->core->expects($this->once()) - ->method('set_useragent') - ->with($this->equalTo( - 'ownCloud News/3 (+https://owncloud.org/; 1 subscriber; ' . - 'feed-url=http://tests)')); - $this->setExpectedException('\OCA\News\Fetcher\FetcherException'); - $this->fetcher->fetch($this->url); - } - - - public function testShouldCatchExceptionsAndThrowOwnException() { - $this->core->expects($this->once()) - ->method('init') - ->will($this->returnValue(true)); - $this->core->expects($this->once()) - ->method('get_items') - ->will($this->throwException(new \Exception('oh noes!'))); - $this->setExpectedException('\OCA\News\Fetcher\FetcherException'); - $this->fetcher->fetch($this->url); - } - - - private function expectCore($method, $return, $count = 1) { - $this->core->expects($this->exactly($count)) - ->method($method) - ->will($this->returnValue($return)); - } - - private function expectItem($method, $return, $count = 1) { - $this->item->expects($this->exactly($count)) - ->method($method) - ->will($this->returnValue($return)); - } - - - private function createItem($author=false, $enclosureType=null, $noPubDate=false) { - $this->expectItem('get_permalink', $this->permalink); - $this->expectItem('get_title', $this->title); - $this->expectItem('get_id', $this->guid); - $this->expectItem('get_content', $this->body); - - $item = new Item(); - - if($noPubDate) { - $this->expectItem('get_date', 0); - $item->setPubDate($this->time); - } else { - $this->expectItem('get_date', $this->pub); - $item->setPubDate($this->pub); - } - - $item->setStatus(0); - $item->setUnread(); - $item->setUrl($this->permalink); - $item->setTitle('my<\' title'); - $item->setGuid($this->guid); - $item->setGuidHash(md5($this->guid)); - $item->setBody($this->body); - $item->setLastModified($this->time); - if($author) { - $mock = $this->getMock('author', ['get_name']); - $mock->expects($this->once()) - ->method('get_name') - ->will($this->returnValue($this->author)); - $this->expectItem('get_author', $mock); - $item->setAuthor(html_entity_decode($this->author)); - } else { - $mock = $this->getMock('author', ['get_name', 'get_email']); - $mock->expects($this->any()) - ->method('get_name') - ->will($this->returnValue('')); - $mock->expects($this->any()) - ->method('get_email') - ->will($this->returnValue($this->authorMail)); - - $this->expectItem('get_author', $mock); - $item->setAuthor(html_entity_decode($this->authorMail)); - } - - if($enclosureType === 'audio/ogg') { - $mock = $this->getMock('enclosure', ['get_type', 'get_link']); - $mock->expects($this->any()) - ->method('get_type') - ->will($this->returnValue($enclosureType)); - $mock->expects($this->any()) - ->method('get_link') - ->will($this->returnValue($this->enclosureLink)); - $this->expectItem('get_enclosure', $mock); - $item->setEnclosureMime($enclosureType); - $item->setEnclosureLink($this->enclosureLink); - } elseif ($enclosureType === 'video/ogg') { - $mock = $this->getMock('enclosure', ['get_type', 'get_link']); - $mock->expects($this->any()) - ->method('get_type') - ->will($this->returnValue($enclosureType)); - $mock->expects($this->any()) - ->method('get_link') - ->will($this->returnValue($this->enclosureLink)); - $this->expectItem('get_enclosure', $mock); - $item->setEnclosureMime($enclosureType); - $item->setEnclosureLink($this->enclosureLink); - } - return $item; - } - - - private function createFeed($hasFeedFavicon=false, $hasWebFavicon=false) { - $this->expectCore('get_title', $this->feedTitle); - $this->expectCore('get_permalink', $this->feedLink, 2); - - $feed = new Feed(); - $feed->setTitle('&its a title'); - $feed->setUrl($this->url); - $feed->setLink($this->feedLink); - $feed->setAdded($this->time); - - if($hasWebFavicon) { - $this->faviconFetcher->expects($this->once()) - ->method('fetch') - ->with($this->equalTo($this->feedLink)) - ->will($this->returnValue($this->webFavicon)); - $feed->setFaviconLink($this->webFavicon); - } - - if($hasFeedFavicon) { - $this->expectCore('get_image_url', $this->feedImage); - $feed->setFaviconLink($this->feedImage); - } elseif(!$hasWebFavicon) { - $feed->setFaviconLink(null); - $this->expectCore('get_image_url', null); - } - - - return $feed; - } - - - public function testFetchMapItems(){ - $this->core->expects($this->once()) - ->method('init') - ->will($this->returnValue(true)); - $item = $this->createItem(false, 'audio/ogg'); - $feed = $this->createFeed(); - $this->expectCore('get_items', [$this->item]); - $result = $this->fetcher->fetch($this->url); - - $this->assertEquals([$feed, [$item]], $result); - } - - - public function testFetchMapItemsNoFeedTitleUsesUrl(){ - $this->expectCore('get_title', ''); - $this->expectCore('get_permalink', $this->feedLink, 2); - - $feed = new Feed(); - $feed->setTitle($this->url); - $feed->setUrl($this->url); - $feed->setLink($this->feedLink); - $feed->setAdded($this->time); - $feed->setFaviconLink(null); - - $this->core->expects($this->once()) - ->method('init') - ->will($this->returnValue(true)); - $item = $this->createItem(); - $this->expectCore('get_items', [$this->item]); - $result = $this->fetcher->fetch($this->url); - - $this->assertEquals([$feed, [$item]], $result); - } - - public function testFetchMapItemsAuthorExists(){ - $this->core->expects($this->once()) - ->method('init') - ->will($this->returnValue(true)); - $item = $this->createItem(true); - $feed = $this->createFeed(true); - $this->expectCore('get_items', [$this->item]); - $result = $this->fetcher->fetch($this->url); - - $this->assertEquals([$feed, [$item]], $result); - } - - - public function testFetchMapItemsEnclosureExists(){ - $this->core->expects($this->once()) - ->method('init') - ->will($this->returnValue(true)); - $item = $this->createItem(false, true); - $feed = $this->createFeed(false, true); - $this->expectCore('get_items', [$this->item]); - $result = $this->fetcher->fetch($this->url); - - $this->assertEquals([$feed, [$item]], $result); - } - - - public function testFetchMapItemsNoPubdate(){ - $this->core->expects($this->once()) - ->method('init') - ->will($this->returnValue(true)); - $item = $this->createItem(false, true, true); - $feed = $this->createFeed(false, true); - $this->expectCore('get_items', [$this->item]); - $result = $this->fetcher->fetch($this->url); - - $this->assertEquals([$feed, [$item]], $result); - } - - - public function testFetchMapItemsGetFavicon() { - $this->expectCore('get_title', $this->feedTitle); - $this->expectCore('get_permalink', $this->feedLink, 2); - - $feed = new Feed(); - $feed->setTitle('&its a title'); - $feed->setUrl($this->url); - $feed->setLink($this->feedLink); - $feed->setAdded($this->time); - $feed->setFaviconLink($this->webFavicon); - - $this->core->expects($this->once()) - ->method('init') - ->will($this->returnValue(true)); - - $this->faviconFetcher->expects($this->once()) - ->method('fetch') - ->will($this->returnValue($this->webFavicon)); - - $item = $this->createItem(false, 'video/ogg'); - $this->expectCore('get_items', [$this->item]); - $result = $this->fetcher->fetch($this->url); - - $this->assertEquals([$feed, [$item]], $result); - } - - public function testFetchMapItemsNoGetFavicon() { - $this->expectCore('get_title', $this->feedTitle); - $this->expectCore('get_permalink', $this->feedLink, 2); - - $feed = new Feed(); - $feed->setTitle('&its a title'); - $feed->setUrl($this->url); - $feed->setLink($this->feedLink); - $feed->setAdded($this->time); - - $this->core->expects($this->once()) - ->method('init') - ->will($this->returnValue(true)); - - $this->faviconFetcher->expects($this->never()) - ->method('fetch'); - - $item = $this->createItem(false, true); - $this->expectCore('get_items', [$this->item]); - $result = $this->fetcher->fetch($this->url, false); - - $this->assertEquals([$feed, [$item]], $result); - } + private $fetcher; + private $core; + private $coreFactory; + private $faviconFetcher; + private $url; + private $cacheDirectory; + private $cacheDuration; + private $time; + private $item; + private $purifier; + private $fetchTimeout; + private $proxyHost; + private $getProxyPort; + private $proxyAuth; + private $config; + private $appconfig; + + // items + private $permalink; + private $title; + private $guid; + private $pub; + private $body; + private $author; + private $authorMail; + private $enclosureLink; + + // feed + private $feedTitle; + private $feedLink; + private $feedImage; + private $webFavicon; + + protected function setUp(){ + $this->core = $this->getMock( + '\SimplePie_Core', [ + 'set_timeout', + 'set_feed_url', + 'enable_cache', + 'set_stupidly_fast', + 'set_cache_location', + 'set_cache_duration', + 'set_proxyhost', + 'set_proxyport', + 'set_proxyuserpwd', + 'set_useragent', + 'init', + 'get_permalink', + 'get_items', + 'get_title', + 'get_image_url' + ]); + $this->coreFactory = $this->getMockBuilder( + '\OCA\News\Utility\SimplePieAPIFactory') + ->disableOriginalConstructor() + ->getMock(); + $this->coreFactory->expects($this->any()) + ->method('getCore') + ->will($this->returnValue($this->core)); + $this->item = $this->getMockBuilder( + '\SimplePie_Item') + ->disableOriginalConstructor() + ->getMock(); + $this->faviconFetcher = $this->getMockBuilder( + '\OCA\News\Utility\FaviconFetcher') + ->disableOriginalConstructor() + ->getMock(); + $this->appconfig = $this->getMockBuilder( + '\OCA\News\Config\AppConfig') + ->disableOriginalConstructor() + ->getMock(); + $this->time = 2323; + $timeFactory = $this->getMock('TimeFactory', ['getTime']); + $timeFactory->expects($this->any()) + ->method('getTime') + ->will($this->returnValue($this->time)); + $this->cacheDuration = 100; + $this->cacheDirectory = 'dir/'; + $this->proxyHost = 'test'; + $this->proxyPort = 30; + $this->proxyAuth = 'hi'; + $this->fetchTimeout = 40; + $this->config = $this->getMockBuilder( + '\OCA\News\Config\Config') + ->disableOriginalConstructor() + ->getMock(); + $this->config->expects($this->any()) + ->method('getSimplePieCacheDuration') + ->will($this->returnValue($this->cacheDuration)); + $this->config->expects($this->any()) + ->method('getProxyHost') + ->will($this->returnValue($this->proxyHost)); + $this->config->expects($this->any()) + ->method('getProxyAuth') + ->will($this->returnValue($this->proxyAuth)); + $this->config->expects($this->any()) + ->method('getProxyPort') + ->will($this->returnValue($this->proxyPort)); + $this->config->expects($this->any()) + ->method('getFeedFetcherTimeout') + ->will($this->returnValue($this->fetchTimeout)); + $this->appconfig->expects($this->any()) + ->method('getConfig') + ->with($this->equalTo('version')) + ->will($this->returnValue(3)); + $this->fetcher = new FeedFetcher($this->coreFactory, + $this->faviconFetcher, + $timeFactory, + $this->cacheDirectory, + $this->config, + $this->appconfig); + $this->url = 'http://tests'; + + $this->permalink = 'http://permalink'; + $this->title = 'my&lt;' title'; + $this->guid = 'hey guid here'; + $this->body = 'let the bodies hit the floor <a href="test">test</a>'; + $this->body2 = 'let the bodies hit the floor <a target="_blank" href="test">test</a>'; + $this->pub = 23111; + $this->author = '<boogieman'; + $this->enclosureLink = 'http://enclosure.you'; + + $this->feedTitle = '<a>&its a</a> title'; + $this->feedLink = 'http://goatse'; + $this->feedImage = '/an/image'; + $this->webFavicon = 'http://anon.google.com'; + $this->authorMail = 'doe@joes.com'; + } + + + public function testCanHandle(){ + $url = 'google.de'; + + $this->assertTrue($this->fetcher->canHandle($url)); + } + + + public function testDoesNotUseProxyIfNotEnabled() { + $this->config->expects($this->any()) + ->method('getProxyHost') + ->will($this->returnValue('')); + $this->core->expects($this->never()) + ->method('set_proxyhost'); + $this->core->expects($this->never()) + ->method('set_proxyport'); + $this->core->expects($this->never()) + ->method('set_proxyuserpwd'); + } + + + public function testFetchThrowsExceptionWhenInitFailed() { + $this->core->expects($this->once()) + ->method('set_feed_url') + ->with($this->equalTo($this->url)); + $this->core->expects($this->once()) + ->method('enable_cache') + ->with($this->equalTo(true)); + $this->core->expects($this->once()) + ->method('set_timeout') + ->with($this->equalTo($this->fetchTimeout)); + $this->core->expects($this->once()) + ->method('set_cache_location') + ->with($this->equalTo($this->cacheDirectory)); + $this->core->expects($this->once()) + ->method('set_proxyhost') + ->with($this->equalTo($this->proxyHost)); + $this->core->expects($this->once()) + ->method('set_proxyport') + ->with($this->equalTo($this->proxyPort)); + $this->core->expects($this->once()) + ->method('set_proxyuserpwd') + ->with($this->equalTo($this->proxyAuth)); + $this->core->expects($this->once()) + ->method('set_stupidly_fast') + ->with($this->equalTo(true)); + $this->core->expects($this->once()) + ->method('set_cache_duration') + ->with($this->equalTo($this->cacheDuration)); + $this->core->expects($this->once()) + ->method('set_useragent') + ->with($this->equalTo( + 'ownCloud News/3 (+https://owncloud.org/; 1 subscriber; ' . + 'feed-url=http://tests)')); + $this->setExpectedException('\OCA\News\Fetcher\FetcherException'); + $this->fetcher->fetch($this->url); + } + + + public function testShouldCatchExceptionsAndThrowOwnException() { + $this->core->expects($this->once()) + ->method('init') + ->will($this->returnValue(true)); + $this->core->expects($this->once()) + ->method('get_items') + ->will($this->throwException(new \Exception('oh noes!'))); + $this->setExpectedException('\OCA\News\Fetcher\FetcherException'); + $this->fetcher->fetch($this->url); + } + + + private function expectCore($method, $return, $count = 1) { + $this->core->expects($this->exactly($count)) + ->method($method) + ->will($this->returnValue($return)); + } + + private function expectItem($method, $return, $count = 1) { + $this->item->expects($this->exactly($count)) + ->method($method) + ->will($this->returnValue($return)); + } + + + private function createItem($author=false, $enclosureType=null, $noPubDate=false) { + $this->expectItem('get_permalink', $this->permalink); + $this->expectItem('get_title', $this->title); + $this->expectItem('get_id', $this->guid); + $this->expectItem('get_content', $this->body); + + $item = new Item(); + + if($noPubDate) { + $this->expectItem('get_date', 0); + $item->setPubDate($this->time); + } else { + $this->expectItem('get_date', $this->pub); + $item->setPubDate($this->pub); + } + + $item->setStatus(0); + $item->setUnread(); + $item->setUrl($this->permalink); + $item->setTitle('my<\' title'); + $item->setGuid($this->guid); + $item->setGuidHash(md5($this->guid)); + $item->setBody($this->body); + $item->setLastModified($this->time); + if($author) { + $mock = $this->getMock('author', ['get_name']); + $mock->expects($this->once()) + ->method('get_name') + ->will($this->returnValue($this->author)); + $this->expectItem('get_author', $mock); + $item->setAuthor(html_entity_decode($this->author)); + } else { + $mock = $this->getMock('author', ['get_name', 'get_email']); + $mock->expects($this->any()) + ->method('get_name') + ->will($this->returnValue('')); + $mock->expects($this->any()) + ->method('get_email') + ->will($this->returnValue($this->authorMail)); + + $this->expectItem('get_author', $mock); + $item->setAuthor(html_entity_decode($this->authorMail)); + } + + if($enclosureType === 'audio/ogg') { + $mock = $this->getMock('enclosure', ['get_type', 'get_link']); + $mock->expects($this->any()) + ->method('get_type') + ->will($this->returnValue($enclosureType)); + $mock->expects($this->any()) + ->method('get_link') + ->will($this->returnValue($this->enclosureLink)); + $this->expectItem('get_enclosure', $mock); + $item->setEnclosureMime($enclosureType); + $item->setEnclosureLink($this->enclosureLink); + } elseif ($enclosureType === 'video/ogg') { + $mock = $this->getMock('enclosure', ['get_type', 'get_link']); + $mock->expects($this->any()) + ->method('get_type') + ->will($this->returnValue($enclosureType)); + $mock->expects($this->any()) + ->method('get_link') + ->will($this->returnValue($this->enclosureLink)); + $this->expectItem('get_enclosure', $mock); + $item->setEnclosureMime($enclosureType); + $item->setEnclosureLink($this->enclosureLink); + } + return $item; + } + + + private function createFeed($hasFeedFavicon=false, $hasWebFavicon=false) { + $this->expectCore('get_title', $this->feedTitle); + $this->expectCore('get_permalink', $this->feedLink, 2); + + $feed = new Feed(); + $feed->setTitle('&its a title'); + $feed->setUrl($this->url); + $feed->setLink($this->feedLink); + $feed->setAdded($this->time); + + if($hasWebFavicon) { + $this->faviconFetcher->expects($this->once()) + ->method('fetch') + ->with($this->equalTo($this->feedLink)) + ->will($this->returnValue($this->webFavicon)); + $feed->setFaviconLink($this->webFavicon); + } + + if($hasFeedFavicon) { + $this->expectCore('get_image_url', $this->feedImage); + $feed->setFaviconLink($this->feedImage); + } elseif(!$hasWebFavicon) { + $feed->setFaviconLink(null); + $this->expectCore('get_image_url', null); + } + + + return $feed; + } + + + public function testFetchMapItems(){ + $this->core->expects($this->once()) + ->method('init') + ->will($this->returnValue(true)); + $item = $this->createItem(false, 'audio/ogg'); + $feed = $this->createFeed(); + $this->expectCore('get_items', [$this->item]); + $result = $this->fetcher->fetch($this->url); + + $this->assertEquals([$feed, [$item]], $result); + } + + + public function testFetchMapItemsNoFeedTitleUsesUrl(){ + $this->expectCore('get_title', ''); + $this->expectCore('get_permalink', $this->feedLink, 2); + + $feed = new Feed(); + $feed->setTitle($this->url); + $feed->setUrl($this->url); + $feed->setLink($this->feedLink); + $feed->setAdded($this->time); + $feed->setFaviconLink(null); + + $this->core->expects($this->once()) + ->method('init') + ->will($this->returnValue(true)); + $item = $this->createItem(); + $this->expectCore('get_items', [$this->item]); + $result = $this->fetcher->fetch($this->url); + + $this->assertEquals([$feed, [$item]], $result); + } + + public function testFetchMapItemsAuthorExists(){ + $this->core->expects($this->once()) + ->method('init') + ->will($this->returnValue(true)); + $item = $this->createItem(true); + $feed = $this->createFeed(true); + $this->expectCore('get_items', [$this->item]); + $result = $this->fetcher->fetch($this->url); + + $this->assertEquals([$feed, [$item]], $result); + } + + + public function testFetchMapItemsEnclosureExists(){ + $this->core->expects($this->once()) + ->method('init') + ->will($this->returnValue(true)); + $item = $this->createItem(false, true); + $feed = $this->createFeed(false, true); + $this->expectCore('get_items', [$this->item]); + $result = $this->fetcher->fetch($this->url); + + $this->assertEquals([$feed, [$item]], $result); + } + + + public function testFetchMapItemsNoPubdate(){ + $this->core->expects($this->once()) + ->method('init') + ->will($this->returnValue(true)); + $item = $this->createItem(false, true, true); + $feed = $this->createFeed(false, true); + $this->expectCore('get_items', [$this->item]); + $result = $this->fetcher->fetch($this->url); + + $this->assertEquals([$feed, [$item]], $result); + } + + + public function testFetchMapItemsGetFavicon() { + $this->expectCore('get_title', $this->feedTitle); + $this->expectCore('get_permalink', $this->feedLink, 2); + + $feed = new Feed(); + $feed->setTitle('&its a title'); + $feed->setUrl($this->url); + $feed->setLink($this->feedLink); + $feed->setAdded($this->time); + $feed->setFaviconLink($this->webFavicon); + + $this->core->expects($this->once()) + ->method('init') + ->will($this->returnValue(true)); + + $this->faviconFetcher->expects($this->once()) + ->method('fetch') + ->will($this->returnValue($this->webFavicon)); + + $item = $this->createItem(false, 'video/ogg'); + $this->expectCore('get_items', [$this->item]); + $result = $this->fetcher->fetch($this->url); + + $this->assertEquals([$feed, [$item]], $result); + } + + public function testFetchMapItemsNoGetFavicon() { + $this->expectCore('get_title', $this->feedTitle); + $this->expectCore('get_permalink', $this->feedLink, 2); + + $feed = new Feed(); + $feed->setTitle('&its a title'); + $feed->setUrl($this->url); + $feed->setLink($this->feedLink); + $feed->setAdded($this->time); + + $this->core->expects($this->once()) + ->method('init') + ->will($this->returnValue(true)); + + $this->faviconFetcher->expects($this->never()) + ->method('fetch'); + + $item = $this->createItem(false, true); + $this->expectCore('get_items', [$this->item]); + $result = $this->fetcher->fetch($this->url, false); + + $this->assertEquals([$feed, [$item]], $result); + } } diff --git a/tests/unit/fetcher/FetcherTest.php b/tests/unit/fetcher/FetcherTest.php index 7421bc9e5..1ab81fc1e 100644 --- a/tests/unit/fetcher/FetcherTest.php +++ b/tests/unit/fetcher/FetcherTest.php @@ -28,103 +28,103 @@ namespace OCA\News\Fetcher; class FetcherTest extends \PHPUnit_Framework_TestCase { - private $fetcher; - - protected function setUp(){ - $this->fetcher = new Fetcher(); - } - - - public function testFetch(){ - $url = 'hi'; - $mockFetcher = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') - ->disableOriginalConstructor() - ->getMock(); - $mockFetcher->expects($this->once()) - ->method('canHandle') - ->with($this->equalTo($url)) - ->will($this->returnValue(true)); - $this->fetcher->registerFetcher($mockFetcher); - - $this->fetcher->fetch($url); - } - - - public function testNoFetchers(){ - $url = 'hi'; - $mockFetcher = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') - ->disableOriginalConstructor() - ->getMock(); - $mockFetcher->expects($this->once()) - ->method('canHandle') - ->with($this->equalTo($url)) - ->will($this->returnValue(false)); - $mockFetcher2 = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') - ->disableOriginalConstructor() - ->getMock(); - $mockFetcher2->expects($this->once()) - ->method('canHandle') - ->with($this->equalTo($url)) - ->will($this->returnValue(false)); - - $this->fetcher->registerFetcher($mockFetcher); - $this->fetcher->registerFetcher($mockFetcher2); - - $result = $this->fetcher->fetch($url); - $this->assertEquals([null, []], $result); - } - - public function testMultipleFetchers(){ - $url = 'hi'; - $mockFetcher = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') - ->disableOriginalConstructor() - ->getMock(); - $mockFetcher->expects($this->once()) - ->method('canHandle') - ->with($this->equalTo($url)) - ->will($this->returnValue(false)); - $mockFetcher2 = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') - ->disableOriginalConstructor() - ->getMock(); - $mockFetcher2->expects($this->once()) - ->method('canHandle') - ->with($this->equalTo($url)) - ->will($this->returnValue(true)); - - $this->fetcher->registerFetcher($mockFetcher); - $this->fetcher->registerFetcher($mockFetcher2); - - $this->fetcher->fetch($url); - } - - - public function testMultipleFetchersOnlyOneShouldHandle(){ - $url = 'hi'; - $return = 'zeas'; - $mockFetcher = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') - ->disableOriginalConstructor() - ->getMock(); - $mockFetcher->expects($this->once()) - ->method('canHandle') - ->with($this->equalTo($url)) - ->will($this->returnValue(true)); - $mockFetcher->expects($this->once()) - ->method('fetch') - ->with($this->equalTo($url)) - ->will($this->returnValue($return)); - $mockFetcher2 = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') - ->disableOriginalConstructor() - ->getMock(); - $mockFetcher2->expects($this->never()) - ->method('canHandle'); - - $this->fetcher->registerFetcher($mockFetcher); - $this->fetcher->registerFetcher($mockFetcher2); - - $result = $this->fetcher->fetch($url); - - $this->assertEquals($return, $result); - } + private $fetcher; + + protected function setUp(){ + $this->fetcher = new Fetcher(); + } + + + public function testFetch(){ + $url = 'hi'; + $mockFetcher = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') + ->disableOriginalConstructor() + ->getMock(); + $mockFetcher->expects($this->once()) + ->method('canHandle') + ->with($this->equalTo($url)) + ->will($this->returnValue(true)); + $this->fetcher->registerFetcher($mockFetcher); + + $this->fetcher->fetch($url); + } + + + public function testNoFetchers(){ + $url = 'hi'; + $mockFetcher = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') + ->disableOriginalConstructor() + ->getMock(); + $mockFetcher->expects($this->once()) + ->method('canHandle') + ->with($this->equalTo($url)) + ->will($this->returnValue(false)); + $mockFetcher2 = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') + ->disableOriginalConstructor() + ->getMock(); + $mockFetcher2->expects($this->once()) + ->method('canHandle') + ->with($this->equalTo($url)) + ->will($this->returnValue(false)); + + $this->fetcher->registerFetcher($mockFetcher); + $this->fetcher->registerFetcher($mockFetcher2); + + $result = $this->fetcher->fetch($url); + $this->assertEquals([null, []], $result); + } + + public function testMultipleFetchers(){ + $url = 'hi'; + $mockFetcher = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') + ->disableOriginalConstructor() + ->getMock(); + $mockFetcher->expects($this->once()) + ->method('canHandle') + ->with($this->equalTo($url)) + ->will($this->returnValue(false)); + $mockFetcher2 = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') + ->disableOriginalConstructor() + ->getMock(); + $mockFetcher2->expects($this->once()) + ->method('canHandle') + ->with($this->equalTo($url)) + ->will($this->returnValue(true)); + + $this->fetcher->registerFetcher($mockFetcher); + $this->fetcher->registerFetcher($mockFetcher2); + + $this->fetcher->fetch($url); + } + + + public function testMultipleFetchersOnlyOneShouldHandle(){ + $url = 'hi'; + $return = 'zeas'; + $mockFetcher = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') + ->disableOriginalConstructor() + ->getMock(); + $mockFetcher->expects($this->once()) + ->method('canHandle') + ->with($this->equalTo($url)) + ->will($this->returnValue(true)); + $mockFetcher->expects($this->once()) + ->method('fetch') + ->with($this->equalTo($url)) + ->will($this->returnValue($return)); + $mockFetcher2 = $this->getMockBuilder('\OCA\News\Fetcher\IFeedFetcher') + ->disableOriginalConstructor() + ->getMock(); + $mockFetcher2->expects($this->never()) + ->method('canHandle'); + + $this->fetcher->registerFetcher($mockFetcher); + $this->fetcher->registerFetcher($mockFetcher2); + + $result = $this->fetcher->fetch($url); + + $this->assertEquals($return, $result); + } }
\ No newline at end of file diff --git a/tests/unit/http/TextDownloadResponseTest.php b/tests/unit/http/TextDownloadResponseTest.php index 47ee657cd..d78464e68 100644 --- a/tests/unit/http/TextDownloadResponseTest.php +++ b/tests/unit/http/TextDownloadResponseTest.php @@ -18,13 +18,13 @@ namespace OCA\News\Http; class TextDownloadResponseTest extends \PHPUnit_Framework_TestCase { - protected function setUp() { - $this->response = new TextDownloadResponse('sometext', 'file', 'content'); - } + protected function setUp() { + $this->response = new TextDownloadResponse('sometext', 'file', 'content'); + } - public function testRender() { - $this->assertEquals('sometext', $this->response->render()); - } + public function testRender() { + $this->assertEquals('sometext', $this->response->render()); + } }
\ No newline at end of file diff --git a/tests/unit/http/TextResponseTest.php b/tests/unit/http/TextResponseTest.php index c0b5ca3a0..790cbe340 100644 --- a/tests/unit/http/TextResponseTest.php +++ b/tests/unit/http/TextResponseTest.php @@ -18,27 +18,27 @@ namespace OCA\News\Http; class TextResponseTest extends \PHPUnit_Framework_TestCase { - protected function setUp() { - $this->response = new TextResponse('sometext'); - } + protected function setUp() { + $this->response = new TextResponse('sometext'); + } - public function testRender() { - $this->assertEquals('sometext', $this->response->render()); - } + public function testRender() { + $this->assertEquals('sometext', $this->response->render()); + } - public function testContentTypeDefaultsToText(){ - $headers = $this->response->getHeaders(); + public function testContentTypeDefaultsToText(){ + $headers = $this->response->getHeaders(); - $this->assertEquals('text/plain', $headers['Content-type']); - } + $this->assertEquals('text/plain', $headers['Content-type']); + } - public function testContentTypeIsSetableViaConstructor(){ - $response = new TextResponse('sometext', 'html'); - $headers = $response->getHeaders(); + public function testContentTypeIsSetableViaConstructor(){ + $response = new TextResponse('sometext', 'html'); + $headers = $response->getHeaders(); - $this->assertEquals('text/html', $headers['Content-type']); - } + $this->assertEquals('text/html', $headers['Content-type']); + } }
\ No newline at end of file diff --git a/tests/unit/service/FeedServiceTest.php b/tests/unit/service/FeedServiceTest.php index cc8d3018e..f7c804ec5 100644 --- a/tests/unit/service/FeedServiceTest.php +++ b/tests/unit/service/FeedServiceTest.php @@ -24,699 +24,699 @@ use \OCA\News\Fetcher\FetcherException; class FeedServiceTest extends \PHPUnit_Framework_TestCase { - private $feedMapper; - private $feedService; - private $user; - private $response; - private $fetcher; - private $itemMapper; - private $threshold; - private $time; - private $importParser; - private $autoPurgeMinimumInterval; - private $enhancer; - private $purifier; - private $l10n; - private $logger; - private $loggerParams; - - protected function setUp(){ - $this->logger = $this->getMockBuilder( - '\OCP\ILogger') - ->disableOriginalConstructor() - ->getMock(); - $this->loggerParams = ['hi']; - $this->time = 222; - $this->autoPurgeMinimumInterval = 10; - $timeFactory = $this->getMock('TimeFactory', ['getTime']); - $timeFactory->expects($this->any()) - ->method('getTime') - ->will($this->returnValue($this->time)); - $this->l10n = $this->getMockBuilder('\OCP\IL10N') - ->disableOriginalConstructor() - ->getMock(); - $this->feedMapper = $this->getMockBuilder('\OCA\News\Db\FeedMapper') - ->disableOriginalConstructor() - ->getMock(); - $this->fetcher = $this->getMockBuilder('\OCA\News\Fetcher\Fetcher') - ->disableOriginalConstructor() - ->getMock(); - $this->itemMapper = $this->getMockBuilder('\OCA\News\Db\ItemMapper') - ->disableOriginalConstructor() - ->getMock(); - $this->enhancer = $this->getMockBuilder('\OCA\News\ArticleEnhancer\Enhancer') - ->disableOriginalConstructor() - ->getMock(); - $this->purifier = $this->getMock('purifier', ['purify']); - $config = $this->getMockBuilder( - '\OCA\News\Config\Config') - ->disableOriginalConstructor() - ->getMock(); - $config->expects($this->any()) - ->method('getAutoPurgeMinimumInterval') - ->will($this->returnValue($this->autoPurgeMinimumInterval)); - - $this->feedService = new FeedService($this->feedMapper, - $this->fetcher, $this->itemMapper, $this->logger, $this->l10n, - $timeFactory, $config, $this->enhancer, $this->purifier, $this->loggerParams); - $this->user = 'jack'; - } - - - public function testFindAll(){ - $this->feedMapper->expects($this->once()) - ->method('findAllFromUser') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($this->response)); - - $result = $this->feedService->findAll($this->user); - $this->assertEquals($this->response, $result); - } - - - public function testCreateDoesNotFindFeed(){ - $ex = new FetcherException('hi'); - $url = 'test'; - $this->l10n->expects($this->once()) - ->method('t'); - $this->fetcher->expects($this->once()) - ->method('fetch') - ->with($this->equalTo($url)) - ->will($this->throwException($ex)); - $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); - $this->feedService->create($url, 1, $this->user); - } - - public function testCreate(){ - $url = 'http://test'; - $folderId = 10; - $createdFeed = new Feed(); - $ex = new DoesNotExistException('yo'); - $createdFeed->setUrl($url); - $createdFeed->setUrlHash('hsssi'); - $createdFeed->setLink($url); - $createdFeed->setTitle('hehoy'); - $item1 = new Item(); - $item1->setGuidHash('hi'); - $item2 = new Item(); - $item2->setGuidHash('yo'); - $return = [ - $createdFeed, - [$item1, $item2] - ]; - - $this->feedMapper->expects($this->once()) - ->method('findByUrlHash') - ->with($this->equalTo($createdFeed->getUrlHash()), $this->equalTo($this->user)) - ->will($this->throwException($ex)); - $this->fetcher->expects($this->once()) - ->method('fetch') - ->with($this->equalTo($url)) - ->will($this->returnValue($return)); - $this->feedMapper->expects($this->once()) - ->method('insert') - ->with($this->equalTo($createdFeed)) - ->will($this->returnValue($createdFeed)); - $this->itemMapper->expects($this->at(0)) - ->method('findByGuidHash') - ->with( - $this->equalTo($item2->getGuidHash()), - $this->equalTo($item2->getFeedId()), - $this->equalTo($this->user)) - ->will($this->throwException($ex)); - $this->enhancer->expects($this->at(0)) - ->method('enhance') - ->with($this->equalTo($return[1][1]), - $this->equalTo($url)) - ->will($this->returnValue($return[1][1])); - $this->purifier->expects($this->at(0)) - ->method('purify') - ->with($this->equalTo($return[1][1]->getBody())) - ->will($this->returnValue($return[1][1]->getBody())); - $this->itemMapper->expects($this->at(1)) - ->method('insert') - ->with($this->equalTo($return[1][1])); - $this->itemMapper->expects($this->at(2)) - ->method('findByGuidHash') - ->with( - $this->equalTo($item1->getGuidHash()), - $this->equalTo($item1->getFeedId()), - $this->equalTo($this->user)) - ->will($this->throwException($ex)); - $this->enhancer->expects($this->at(1)) - ->method('enhance') - ->with($this->equalTo($return[1][0]), - $this->equalTo($url)) - ->will($this->returnValue($return[1][0])); - $this->purifier->expects($this->at(1)) - ->method('purify') - ->with($this->equalTo($return[1][0]->getBody())) - ->will($this->returnValue($return[1][0]->getBody())); - $this->itemMapper->expects($this->at(3)) - ->method('insert') - ->with($this->equalTo($return[1][0])); - - $feed = $this->feedService->create($url, $folderId, $this->user); - - $this->assertEquals($feed->getFolderId(), $folderId); - $this->assertEquals($feed->getUrl(), $url); - $this->assertEquals($feed->getArticlesPerUpdate(), 2); - } - - - public function testCreateItemGuidExistsAlready(){ - $url = 'http://test'; - $folderId = 10; - $ex = new DoesNotExistException('yo'); - $createdFeed = new Feed(); - $createdFeed->setUrl($url); - $createdFeed->setUrlHash($url); - $createdFeed->setLink($url); - $item1 = new Item(); - $item1->setGuidHash('hi'); - $item2 = new Item(); - $item2->setGuidHash('yo'); - $return = [ - $createdFeed, - [$item1, $item2] - ]; - - $this->feedMapper->expects($this->once()) - ->method('findByUrlHash') - ->with($this->equalTo($createdFeed->getUrlHash()), - $this->equalTo($this->user)) - ->will($this->throwException($ex)); - $this->fetcher->expects($this->once()) - ->method('fetch') - ->with($this->equalTo($url)) - ->will($this->returnValue($return)); - $this->feedMapper->expects($this->once()) - ->method('insert') - ->with($this->equalTo($createdFeed)) - ->will($this->returnValue($createdFeed)); - $this->itemMapper->expects($this->at(0)) - ->method('findByGuidHash') - ->with( - $this->equalTo($item2->getGuidHash()), - $this->equalTo($item2->getFeedId()), - $this->equalTo($this->user)) - ->will($this->throwException($ex)); - $this->enhancer->expects($this->at(0)) - ->method('enhance') - ->with($this->equalTo($return[1][1]), - $this->equalTo($url)) - ->will($this->returnValue($return[1][1])); - $this->purifier->expects($this->at(0)) - ->method('purify') - ->with($this->equalTo($return[1][1]->getBody())) - ->will($this->returnValue($return[1][1]->getBody())); - $this->itemMapper->expects($this->at(1)) - ->method('insert') - ->with($this->equalTo($return[1][1])); - $this->itemMapper->expects($this->at(2)) - ->method('findByGuidHash') - ->with( - $this->equalTo($item1->getGuidHash()), - $this->equalTo($item1->getFeedId()), - $this->equalTo($this->user)); - - $feed = $this->feedService->create($url, $folderId, $this->user); - - $this->assertEquals($feed->getFolderId(), $folderId); - $this->assertEquals($feed->getUrl(), $url); - $this->assertEquals(1, $feed->getUnreadCount()); - } - - - public function testUpdateCreatesNewEntry(){ - $feed = new Feed(); - $feed->setId(3); - $feed->setArticlesPerUpdate(1); - $feed->setUrlHash('yo'); - - $item = new Item(); - $item->setGuidHash(md5('hi')); - $item->setFeedId(3); - $items = [$item]; - - $ex = new DoesNotExistException('hi'); - - $fetchReturn = [$feed, $items]; - - $this->feedMapper->expects($this->at(0)) - ->method('find') - ->with($this->equalTo($feed->getId()), - $this->equalTo($this->user)) - ->will($this->returnValue($feed)); - $this->fetcher->expects($this->once()) - ->method('fetch') - ->will($this->returnValue($fetchReturn)); - $this->itemMapper->expects($this->once()) - ->method('findByGuidHash') - ->with($this->equalTo($items[0]->getGuidHash()), - $this->equalTo($items[0]->getFeedId()), - $this->equalTo($this->user)) - ->will($this->throwException($ex)); - $this->enhancer->expects($this->at(0)) - ->method('enhance') - ->with($this->equalTo($items[0]), - $this->equalTo($feed->getUrl())) - ->will($this->returnValue($items[0])); - $this->purifier->expects($this->at(0)) - ->method('purify') - ->with($this->equalTo($items[0]->getBody())) - ->will($this->returnValue($items[0]->getBody())); - $this->itemMapper->expects($this->once()) - ->method('insert') - ->with($this->equalTo($items[0])); - - $this->feedMapper->expects($this->at(1)) - ->method('find') - ->with($feed->getId(), $this->user) - ->will($this->returnValue($feed)); - - $return = $this->feedService->update($feed->getId(), $this->user); - - $this->assertEquals($return, $feed); - } - - - public function testUpdateUpdatesArticlesPerFeedCount() { - $feed = new Feed(); - $feed->setId(3); - $feed->setUrlHash('yo'); - - $existingFeed = new Feed(); - $feed->setArticlesPerUpdate(2); - - $item = new Item(); - $item->setGuidHash(md5('hi')); - $item->setFeedId(3); - $items = [$item]; - - $this->feedMapper->expects($this->any()) - ->method('find') - ->will($this->returnValue($existingFeed)); - - $this->fetcher->expects($this->once()) - ->method('fetch') - ->will($this->returnValue([$feed, $items])); - - $this->feedMapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($existingFeed)); - - - $this->feedService->update($feed->getId(), $this->user); - } - - public function testUpdateFails(){ - $feed = new Feed(); - $feed->setId(3); - $ex = new FetcherException(''); - - $this->feedMapper->expects($this->at(0)) - ->method('find') - ->with($this->equalTo($feed->getId()), - $this->equalTo($this->user)) - ->will($this->returnValue($feed)); - $this->fetcher->expects($this->once()) - ->method('fetch') - ->will($this->throwException($ex)); - $this->logger->expects($this->any()) - ->method('debug'); - - $this->feedMapper->expects($this->at(1)) - ->method('find') - ->with($feed->getId(), $this->user) - ->will($this->returnValue($feed)); - - $return = $this->feedService->update($feed->getId(), $this->user); - - $this->assertEquals($return, $feed); - } - - - public function testUpdateDoesNotFindEntry() { - $feed = new Feed(); - $feed->setId(3); - - $ex = new DoesNotExistException(''); - - $this->feedMapper->expects($this->at(0)) - ->method('find') - ->with($this->equalTo($feed->getId()), - $this->equalTo($this->user)) - ->will($this->throwException($ex)); - - $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); - $this->feedService->update($feed->getId(), $this->user); - } - - - public function testUpdateDoesNotFindUpdatedEntry() { - $feed = new Feed(); - $feed->setId(3); - $feed->setArticlesPerUpdate(1); - - $item = new Item(); - $item->setGuidHash(md5('hi')); - $item->setPubDate(3333); - $item->setId(4); - $items = [$item]; - - $item2 = new Item(); - $item2->setPubDate(111); - - $fetchReturn = [$feed, $items]; - $ex = new DoesNotExistException(''); - - $this->feedMapper->expects($this->at(0)) - ->method('find') - ->with($this->equalTo($feed->getId()), - $this->equalTo($this->user)) - ->will($this->returnValue($feed)); - $this->fetcher->expects($this->once()) - ->method('fetch') - ->will($this->returnValue($fetchReturn)); - $this->itemMapper->expects($this->once()) - ->method('findByGuidHash') - ->with($this->equalTo($item->getGuidHash()), - $this->equalTo($feed->getId()), - $this->equalTo($this->user)) - ->will($this->returnValue($item2));; - - $this->feedMapper->expects($this->at(1)) - ->method('find') - ->with($this->equalTo($feed->getId()), - $this->equalTo($this->user)) - ->will($this->throwException($ex)); - - $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); - $this->feedService->update($feed->getId(), $this->user); - } - - - public function testUpdateDoesntUpdateIfFeedIsPrevented() { - $feedId = 3; - $feed = new Feed(); - $feed->setFolderId(16); - $feed->setId($feedId); - $feed->setPreventUpdate(true); - - $this->feedMapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($feedId), - $this->equalTo($this->user)) - ->will($this->returnValue($feed)); - $this->fetcher->expects($this->never()) - ->method('fetch'); - - $this->feedService->update($feedId, $this->user); - } - - - public function testMove(){ - $feedId = 3; - $folderId = 4; - $feed = new Feed(); - $feed->setFolderId(16); - $feed->setId($feedId); - - $this->feedMapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($feedId), $this->equalTo($this->user)) - ->will($this->returnValue($feed)); - - $this->feedMapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($feed)); - - $this->feedService->move($feedId, $folderId, $this->user); - - $this->assertEquals($folderId, $feed->getFolderId()); - } - - - public function testRenameFeed(){ - $feedId = 3; - $feedTitle = "New Feed Title"; - $feed = new Feed(); - $feed->setTitle("Feed Title"); - $feed->setId($feedId); - - $this->feedMapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($feedId), $this->equalTo($this->user)) - ->will($this->returnValue($feed)); - - $this->feedMapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($feed)); - - $this->feedService->rename($feedId, $feedTitle, $this->user); - - $this->assertEquals($feedTitle, $feed->getTitle()); - } - - - public function testImportArticles(){ - $url = 'http://owncloud/nofeed'; - - $feed = new Feed(); - $feed->setId(3); - $feed->setUserId($this->user); - $feed->setUrl($url); - $feed->setLink($url); - $feed->setTitle('Articles without feed'); - $feed->setAdded($this->time); - $feed->setFolderId(0); - $feed->setPreventUpdate(true); - - $feeds = [$feed]; - - $item = new Item(); - $item->setFeedId(3); - $item->setAuthor('john'); - $item->setGuid('s'); - $item->setTitle('hey'); - $item->setPubDate(333); - $item->setBody('come over'); - $item->setEnclosureMime('mime'); - $item->setEnclosureLink('lin'); - $item->setUnread(); - $item->setUnstarred(); - $item->setLastModified($this->time); - - $json = $item->toExport(['feed3' => $feed]); - - $items = [$json]; - - $this->feedMapper->expects($this->once()) - ->method('findAllFromUser') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - - $this->itemMapper->expects($this->once()) - ->method('findByGuidHash') - ->will($this->throwException(new DoesNotExistException('yo'))); - $this->itemMapper->expects($this->once()) - ->method('insert') - ->with($this->equalTo($item)); - - $this->purifier->expects($this->once()) - ->method('purify') - ->with($this->equalTo($item->getBody())) - ->will($this->returnValue($item->getBody())); - - $result = $this->feedService->importArticles($items, $this->user); - - $this->assertEquals(null, $result); - } - - - public function testImportArticlesCreatesOwnFeedWhenNotFound(){ - $url = 'http://owncloud/args'; - - $feed = new Feed(); - $feed->setId(3); - $feed->setUserId($this->user); - $feed->setUrl($url); - $feed->setLink($url); - $feed->setTitle('Articles without feed'); - $feed->setAdded($this->time); - $feed->setFolderId(0); - $feed->setPreventUpdate(true); - - $feeds = [$feed]; - - $item = new Item(); - $item->setFeedId(3); - $item->setAuthor('john'); - $item->setGuid('s'); - $item->setTitle('hey'); - $item->setPubDate(333); - $item->setBody('come over'); - $item->setEnclosureMime('mime'); - $item->setEnclosureLink('lin'); - $item->setUnread(); - $item->setUnstarred(); - $item->setLastModified($this->time); - - $json = $item->toExport(['feed3' => $feed]); - $json2 = $json; - $json2['feedLink'] = 'http://test.com'; // believe it or not this copies stuff :D - - $items = [$json, $json2]; - - $insertFeed = new Feed(); - $insertFeed->setLink('http://owncloud/nofeed'); - $insertFeed->setUrl('http://owncloud/nofeed'); - $insertFeed->setUserId($this->user); - $insertFeed->setTitle('Articles without feed'); - $insertFeed->setAdded($this->time); - $insertFeed->setPreventUpdate(true); - $insertFeed->setFolderId(0); - - $this->l10n->expects($this->once()) - ->method('t') - ->will($this->returnValue('Articles without feed')); - $this->feedMapper->expects($this->once()) - ->method('findAllFromUser') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - $this->feedMapper->expects($this->once()) - ->method('insert') - ->with($this->equalTo($insertFeed)) - ->will($this->returnValue($insertFeed)); - - - $this->itemMapper->expects($this->at(0)) - ->method('findByGuidHash') - ->will($this->throwException(new DoesNotExistException('yo'))); - $this->purifier->expects($this->once()) - ->method('purify') - ->with($this->equalTo($item->getBody())) - ->will($this->returnValue($item->getBody())); - $this->itemMapper->expects($this->at(1)) - ->method('insert') - ->with($this->equalTo($item)); - - $this->itemMapper->expects($this->at(2)) - ->method('findByGuidHash') - ->will($this->returnValue($item)); - $this->itemMapper->expects($this->at(3)) - ->method('update') - ->with($this->equalTo($item)); - - $this->feedMapper->expects($this->once()) - ->method('findByUrlHash') - ->will($this->returnValue($feed)); - - $result = $this->feedService->importArticles($items, $this->user); - - $this->assertEquals($feed, $result); - } - - - public function testMarkDeleted() { - $id = 3; - $feed = new Feed(); - $feed2 = new Feed(); - $feed2->setDeletedAt($this->time); - - $this->feedMapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($id), $this->equalTo($this->user)) - ->will($this->returnValue($feed)); - $this->feedMapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($feed2)); - - $this->feedService->markDeleted($id, $this->user); - } - - - public function testUnmarkDeleted() { - $id = 3; - $feed = new Feed(); - $feed2 = new Feed(); - $feed2->setDeletedAt(0); - - $this->feedMapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($id), $this->equalTo($this->user)) - ->will($this->returnValue($feed)); - $this->feedMapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($feed2)); - - $this->feedService->unmarkDeleted($id, $this->user); - } - - - public function testPurgeDeleted(){ - $feed1 = new Feed(); - $feed1->setId(3); - $feed2 = new Feed(); - $feed2->setId(5); - $feeds = [$feed1, $feed2]; - - $time = $this->time - $this->autoPurgeMinimumInterval; - $this->feedMapper->expects($this->once()) - ->method('getToDelete') - ->with($this->equalTo($time), $this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - $this->feedMapper->expects($this->at(1)) - ->method('delete') - ->with($this->equalTo($feed1)); - $this->feedMapper->expects($this->at(2)) - ->method('delete') - ->with($this->equalTo($feed2)); - - $this->feedService->purgeDeleted($this->user); - } - - - public function testPurgeDeletedWithoutInterval(){ - $feed1 = new Feed(); - $feed1->setId(3); - $feed2 = new Feed(); - $feed2->setId(5); - $feeds = [$feed1, $feed2]; - - $this->feedMapper->expects($this->once()) - ->method('getToDelete') - ->with($this->equalTo(null), $this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - $this->feedMapper->expects($this->at(1)) - ->method('delete') - ->with($this->equalTo($feed1)); - $this->feedMapper->expects($this->at(2)) - ->method('delete') - ->with($this->equalTo($feed2)); - - $this->feedService->purgeDeleted($this->user, false); - } - - - public function testfindAllFromAllUsers() { - $expected = 'hi'; - $this->feedMapper->expects($this->once()) - ->method('findAll') - ->will($this->returnValue($expected)); - $result = $this->feedService->findAllFromAllUsers(); - $this->assertEquals($expected, $result); - } - - - public function testDeleteUser() { - $this->feedMapper->expects($this->once()) - ->method('deleteUser') - ->will($this->returnValue($this->user)); - - $this->feedService->deleteUser($this->user); - } + private $feedMapper; + private $feedService; + private $user; + private $response; + private $fetcher; + private $itemMapper; + private $threshold; + private $time; + private $importParser; + private $autoPurgeMinimumInterval; + private $enhancer; + private $purifier; + private $l10n; + private $logger; + private $loggerParams; + + protected function setUp(){ + $this->logger = $this->getMockBuilder( + '\OCP\ILogger') + ->disableOriginalConstructor() + ->getMock(); + $this->loggerParams = ['hi']; + $this->time = 222; + $this->autoPurgeMinimumInterval = 10; + $timeFactory = $this->getMock('TimeFactory', ['getTime']); + $timeFactory->expects($this->any()) + ->method('getTime') + ->will($this->returnValue($this->time)); + $this->l10n = $this->getMockBuilder('\OCP\IL10N') + ->disableOriginalConstructor() + ->getMock(); + $this->feedMapper = $this->getMockBuilder('\OCA\News\Db\FeedMapper') + ->disableOriginalConstructor() + ->getMock(); + $this->fetcher = $this->getMockBuilder('\OCA\News\Fetcher\Fetcher') + ->disableOriginalConstructor() + ->getMock(); + $this->itemMapper = $this->getMockBuilder('\OCA\News\Db\ItemMapper') + ->disableOriginalConstructor() + ->getMock(); + $this->enhancer = $this->getMockBuilder('\OCA\News\ArticleEnhancer\Enhancer') + ->disableOriginalConstructor() + ->getMock(); + $this->purifier = $this->getMock('purifier', ['purify']); + $config = $this->getMockBuilder( + '\OCA\News\Config\Config') + ->disableOriginalConstructor() + ->getMock(); + $config->expects($this->any()) + ->method('getAutoPurgeMinimumInterval') + ->will($this->returnValue($this->autoPurgeMinimumInterval)); + + $this->feedService = new FeedService($this->feedMapper, + $this->fetcher, $this->itemMapper, $this->logger, $this->l10n, + $timeFactory, $config, $this->enhancer, $this->purifier, $this->loggerParams); + $this->user = 'jack'; + } + + + public function testFindAll(){ + $this->feedMapper->expects($this->once()) + ->method('findAllFromUser') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($this->response)); + + $result = $this->feedService->findAll($this->user); + $this->assertEquals($this->response, $result); + } + + + public function testCreateDoesNotFindFeed(){ + $ex = new FetcherException('hi'); + $url = 'test'; + $this->l10n->expects($this->once()) + ->method('t'); + $this->fetcher->expects($this->once()) + ->method('fetch') + ->with($this->equalTo($url)) + ->will($this->throwException($ex)); + $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); + $this->feedService->create($url, 1, $this->user); + } + + public function testCreate(){ + $url = 'http://test'; + $folderId = 10; + $createdFeed = new Feed(); + $ex = new DoesNotExistException('yo'); + $createdFeed->setUrl($url); + $createdFeed->setUrlHash('hsssi'); + $createdFeed->setLink($url); + $createdFeed->setTitle('hehoy'); + $item1 = new Item(); + $item1->setGuidHash('hi'); + $item2 = new Item(); + $item2->setGuidHash('yo'); + $return = [ + $createdFeed, + [$item1, $item2] + ]; + + $this->feedMapper->expects($this->once()) + ->method('findByUrlHash') + ->with($this->equalTo($createdFeed->getUrlHash()), $this->equalTo($this->user)) + ->will($this->throwException($ex)); + $this->fetcher->expects($this->once()) + ->method('fetch') + ->with($this->equalTo($url)) + ->will($this->returnValue($return)); + $this->feedMapper->expects($this->once()) + ->method('insert') + ->with($this->equalTo($createdFeed)) + ->will($this->returnValue($createdFeed)); + $this->itemMapper->expects($this->at(0)) + ->method('findByGuidHash') + ->with( + $this->equalTo($item2->getGuidHash()), + $this->equalTo($item2->getFeedId()), + $this->equalTo($this->user)) + ->will($this->throwException($ex)); + $this->enhancer->expects($this->at(0)) + ->method('enhance') + ->with($this->equalTo($return[1][1]), + $this->equalTo($url)) + ->will($this->returnValue($return[1][1])); + $this->purifier->expects($this->at(0)) + ->method('purify') + ->with($this->equalTo($return[1][1]->getBody())) + ->will($this->returnValue($return[1][1]->getBody())); + $this->itemMapper->expects($this->at(1)) + ->method('insert') + ->with($this->equalTo($return[1][1])); + $this->itemMapper->expects($this->at(2)) + ->method('findByGuidHash') + ->with( + $this->equalTo($item1->getGuidHash()), + $this->equalTo($item1->getFeedId()), + $this->equalTo($this->user)) + ->will($this->throwException($ex)); + $this->enhancer->expects($this->at(1)) + ->method('enhance') + ->with($this->equalTo($return[1][0]), + $this->equalTo($url)) + ->will($this->returnValue($return[1][0])); + $this->purifier->expects($this->at(1)) + ->method('purify') + ->with($this->equalTo($return[1][0]->getBody())) + ->will($this->returnValue($return[1][0]->getBody())); + $this->itemMapper->expects($this->at(3)) + ->method('insert') + ->with($this->equalTo($return[1][0])); + + $feed = $this->feedService->create($url, $folderId, $this->user); + + $this->assertEquals($feed->getFolderId(), $folderId); + $this->assertEquals($feed->getUrl(), $url); + $this->assertEquals($feed->getArticlesPerUpdate(), 2); + } + + + public function testCreateItemGuidExistsAlready(){ + $url = 'http://test'; + $folderId = 10; + $ex = new DoesNotExistException('yo'); + $createdFeed = new Feed(); + $createdFeed->setUrl($url); + $createdFeed->setUrlHash($url); + $createdFeed->setLink($url); + $item1 = new Item(); + $item1->setGuidHash('hi'); + $item2 = new Item(); + $item2->setGuidHash('yo'); + $return = [ + $createdFeed, + [$item1, $item2] + ]; + + $this->feedMapper->expects($this->once()) + ->method('findByUrlHash') + ->with($this->equalTo($createdFeed->getUrlHash()), + $this->equalTo($this->user)) + ->will($this->throwException($ex)); + $this->fetcher->expects($this->once()) + ->method('fetch') + ->with($this->equalTo($url)) + ->will($this->returnValue($return)); + $this->feedMapper->expects($this->once()) + ->method('insert') + ->with($this->equalTo($createdFeed)) + ->will($this->returnValue($createdFeed)); + $this->itemMapper->expects($this->at(0)) + ->method('findByGuidHash') + ->with( + $this->equalTo($item2->getGuidHash()), + $this->equalTo($item2->getFeedId()), + $this->equalTo($this->user)) + ->will($this->throwException($ex)); + $this->enhancer->expects($this->at(0)) + ->method('enhance') + ->with($this->equalTo($return[1][1]), + $this->equalTo($url)) + ->will($this->returnValue($return[1][1])); + $this->purifier->expects($this->at(0)) + ->method('purify') + ->with($this->equalTo($return[1][1]->getBody())) + ->will($this->returnValue($return[1][1]->getBody())); + $this->itemMapper->expects($this->at(1)) + ->method('insert') + ->with($this->equalTo($return[1][1])); + $this->itemMapper->expects($this->at(2)) + ->method('findByGuidHash') + ->with( + $this->equalTo($item1->getGuidHash()), + $this->equalTo($item1->getFeedId()), + $this->equalTo($this->user)); + + $feed = $this->feedService->create($url, $folderId, $this->user); + + $this->assertEquals($feed->getFolderId(), $folderId); + $this->assertEquals($feed->getUrl(), $url); + $this->assertEquals(1, $feed->getUnreadCount()); + } + + + public function testUpdateCreatesNewEntry(){ + $feed = new Feed(); + $feed->setId(3); + $feed->setArticlesPerUpdate(1); + $feed->setUrlHash('yo'); + + $item = new Item(); + $item->setGuidHash(md5('hi')); + $item->setFeedId(3); + $items = [$item]; + + $ex = new DoesNotExistException('hi'); + + $fetchReturn = [$feed, $items]; + + $this->feedMapper->expects($this->at(0)) + ->method('find') + ->with($this->equalTo($feed->getId()), + $this->equalTo($this->user)) + ->will($this->returnValue($feed)); + $this->fetcher->expects($this->once()) + ->method('fetch') + ->will($this->returnValue($fetchReturn)); + $this->itemMapper->expects($this->once()) + ->method('findByGuidHash') + ->with($this->equalTo($items[0]->getGuidHash()), + $this->equalTo($items[0]->getFeedId()), + $this->equalTo($this->user)) + ->will($this->throwException($ex)); + $this->enhancer->expects($this->at(0)) + ->method('enhance') + ->with($this->equalTo($items[0]), + $this->equalTo($feed->getUrl())) + ->will($this->returnValue($items[0])); + $this->purifier->expects($this->at(0)) + ->method('purify') + ->with($this->equalTo($items[0]->getBody())) + ->will($this->returnValue($items[0]->getBody())); + $this->itemMapper->expects($this->once()) + ->method('insert') + ->with($this->equalTo($items[0])); + + $this->feedMapper->expects($this->at(1)) + ->method('find') + ->with($feed->getId(), $this->user) + ->will($this->returnValue($feed)); + + $return = $this->feedService->update($feed->getId(), $this->user); + + $this->assertEquals($return, $feed); + } + + + public function testUpdateUpdatesArticlesPerFeedCount() { + $feed = new Feed(); + $feed->setId(3); + $feed->setUrlHash('yo'); + + $existingFeed = new Feed(); + $feed->setArticlesPerUpdate(2); + + $item = new Item(); + $item->setGuidHash(md5('hi')); + $item->setFeedId(3); + $items = [$item]; + + $this->feedMapper->expects($this->any()) + ->method('find') + ->will($this->returnValue($existingFeed)); + + $this->fetcher->expects($this->once()) + ->method('fetch') + ->will($this->returnValue([$feed, $items])); + + $this->feedMapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($existingFeed)); + + + $this->feedService->update($feed->getId(), $this->user); + } + + public function testUpdateFails(){ + $feed = new Feed(); + $feed->setId(3); + $ex = new FetcherException(''); + + $this->feedMapper->expects($this->at(0)) + ->method('find') + ->with($this->equalTo($feed->getId()), + $this->equalTo($this->user)) + ->will($this->returnValue($feed)); + $this->fetcher->expects($this->once()) + ->method('fetch') + ->will($this->throwException($ex)); + $this->logger->expects($this->any()) + ->method('debug'); + + $this->feedMapper->expects($this->at(1)) + ->method('find') + ->with($feed->getId(), $this->user) + ->will($this->returnValue($feed)); + + $return = $this->feedService->update($feed->getId(), $this->user); + + $this->assertEquals($return, $feed); + } + + + public function testUpdateDoesNotFindEntry() { + $feed = new Feed(); + $feed->setId(3); + + $ex = new DoesNotExistException(''); + + $this->feedMapper->expects($this->at(0)) + ->method('find') + ->with($this->equalTo($feed->getId()), + $this->equalTo($this->user)) + ->will($this->throwException($ex)); + + $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); + $this->feedService->update($feed->getId(), $this->user); + } + + + public function testUpdateDoesNotFindUpdatedEntry() { + $feed = new Feed(); + $feed->setId(3); + $feed->setArticlesPerUpdate(1); + + $item = new Item(); + $item->setGuidHash(md5('hi')); + $item->setPubDate(3333); + $item->setId(4); + $items = [$item]; + + $item2 = new Item(); + $item2->setPubDate(111); + + $fetchReturn = [$feed, $items]; + $ex = new DoesNotExistException(''); + + $this->feedMapper->expects($this->at(0)) + ->method('find') + ->with($this->equalTo($feed->getId()), + $this->equalTo($this->user)) + ->will($this->returnValue($feed)); + $this->fetcher->expects($this->once()) + ->method('fetch') + ->will($this->returnValue($fetchReturn)); + $this->itemMapper->expects($this->once()) + ->method('findByGuidHash') + ->with($this->equalTo($item->getGuidHash()), + $this->equalTo($feed->getId()), + $this->equalTo($this->user)) + ->will($this->returnValue($item2));; + + $this->feedMapper->expects($this->at(1)) + ->method('find') + ->with($this->equalTo($feed->getId()), + $this->equalTo($this->user)) + ->will($this->throwException($ex)); + + $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); + $this->feedService->update($feed->getId(), $this->user); + } + + + public function testUpdateDoesntUpdateIfFeedIsPrevented() { + $feedId = 3; + $feed = new Feed(); + $feed->setFolderId(16); + $feed->setId($feedId); + $feed->setPreventUpdate(true); + + $this->feedMapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($feedId), + $this->equalTo($this->user)) + ->will($this->returnValue($feed)); + $this->fetcher->expects($this->never()) + ->method('fetch'); + + $this->feedService->update($feedId, $this->user); + } + + + public function testMove(){ + $feedId = 3; + $folderId = 4; + $feed = new Feed(); + $feed->setFolderId(16); + $feed->setId($feedId); + + $this->feedMapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($feedId), $this->equalTo($this->user)) + ->will($this->returnValue($feed)); + + $this->feedMapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($feed)); + + $this->feedService->move($feedId, $folderId, $this->user); + + $this->assertEquals($folderId, $feed->getFolderId()); + } + + + public function testRenameFeed(){ + $feedId = 3; + $feedTitle = "New Feed Title"; + $feed = new Feed(); + $feed->setTitle("Feed Title"); + $feed->setId($feedId); + + $this->feedMapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($feedId), $this->equalTo($this->user)) + ->will($this->returnValue($feed)); + + $this->feedMapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($feed)); + + $this->feedService->rename($feedId, $feedTitle, $this->user); + + $this->assertEquals($feedTitle, $feed->getTitle()); + } + + + public function testImportArticles(){ + $url = 'http://owncloud/nofeed'; + + $feed = new Feed(); + $feed->setId(3); + $feed->setUserId($this->user); + $feed->setUrl($url); + $feed->setLink($url); + $feed->setTitle('Articles without feed'); + $feed->setAdded($this->time); + $feed->setFolderId(0); + $feed->setPreventUpdate(true); + + $feeds = [$feed]; + + $item = new Item(); + $item->setFeedId(3); + $item->setAuthor('john'); + $item->setGuid('s'); + $item->setTitle('hey'); + $item->setPubDate(333); + $item->setBody('come over'); + $item->setEnclosureMime('mime'); + $item->setEnclosureLink('lin'); + $item->setUnread(); + $item->setUnstarred(); + $item->setLastModified($this->time); + + $json = $item->toExport(['feed3' => $feed]); + + $items = [$json]; + + $this->feedMapper->expects($this->once()) + ->method('findAllFromUser') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + + $this->itemMapper->expects($this->once()) + ->method('findByGuidHash') + ->will($this->throwException(new DoesNotExistException('yo'))); + $this->itemMapper->expects($this->once()) + ->method('insert') + ->with($this->equalTo($item)); + + $this->purifier->expects($this->once()) + ->method('purify') + ->with($this->equalTo($item->getBody())) + ->will($this->returnValue($item->getBody())); + + $result = $this->feedService->importArticles($items, $this->user); + + $this->assertEquals(null, $result); + } + + + public function testImportArticlesCreatesOwnFeedWhenNotFound(){ + $url = 'http://owncloud/args'; + + $feed = new Feed(); + $feed->setId(3); + $feed->setUserId($this->user); + $feed->setUrl($url); + $feed->setLink($url); + $feed->setTitle('Articles without feed'); + $feed->setAdded($this->time); + $feed->setFolderId(0); + $feed->setPreventUpdate(true); + + $feeds = [$feed]; + + $item = new Item(); + $item->setFeedId(3); + $item->setAuthor('john'); + $item->setGuid('s'); + $item->setTitle('hey'); + $item->setPubDate(333); + $item->setBody('come over'); + $item->setEnclosureMime('mime'); + $item->setEnclosureLink('lin'); + $item->setUnread(); + $item->setUnstarred(); + $item->setLastModified($this->time); + + $json = $item->toExport(['feed3' => $feed]); + $json2 = $json; + $json2['feedLink'] = 'http://test.com'; // believe it or not this copies stuff :D + + $items = [$json, $json2]; + + $insertFeed = new Feed(); + $insertFeed->setLink('http://owncloud/nofeed'); + $insertFeed->setUrl('http://owncloud/nofeed'); + $insertFeed->setUserId($this->user); + $insertFeed->setTitle('Articles without feed'); + $insertFeed->setAdded($this->time); + $insertFeed->setPreventUpdate(true); + $insertFeed->setFolderId(0); + + $this->l10n->expects($this->once()) + ->method('t') + ->will($this->returnValue('Articles without feed')); + $this->feedMapper->expects($this->once()) + ->method('findAllFromUser') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + $this->feedMapper->expects($this->once()) + ->method('insert') + ->with($this->equalTo($insertFeed)) + ->will($this->returnValue($insertFeed)); + + + $this->itemMapper->expects($this->at(0)) + ->method('findByGuidHash') + ->will($this->throwException(new DoesNotExistException('yo'))); + $this->purifier->expects($this->once()) + ->method('purify') + ->with($this->equalTo($item->getBody())) + ->will($this->returnValue($item->getBody())); + $this->itemMapper->expects($this->at(1)) + ->method('insert') + ->with($this->equalTo($item)); + + $this->itemMapper->expects($this->at(2)) + ->method('findByGuidHash') + ->will($this->returnValue($item)); + $this->itemMapper->expects($this->at(3)) + ->method('update') + ->with($this->equalTo($item)); + + $this->feedMapper->expects($this->once()) + ->method('findByUrlHash') + ->will($this->returnValue($feed)); + + $result = $this->feedService->importArticles($items, $this->user); + + $this->assertEquals($feed, $result); + } + + + public function testMarkDeleted() { + $id = 3; + $feed = new Feed(); + $feed2 = new Feed(); + $feed2->setDeletedAt($this->time); + + $this->feedMapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($id), $this->equalTo($this->user)) + ->will($this->returnValue($feed)); + $this->feedMapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($feed2)); + + $this->feedService->markDeleted($id, $this->user); + } + + + public function testUnmarkDeleted() { + $id = 3; + $feed = new Feed(); + $feed2 = new Feed(); + $feed2->setDeletedAt(0); + + $this->feedMapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($id), $this->equalTo($this->user)) + ->will($this->returnValue($feed)); + $this->feedMapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($feed2)); + + $this->feedService->unmarkDeleted($id, $this->user); + } + + + public function testPurgeDeleted(){ + $feed1 = new Feed(); + $feed1->setId(3); + $feed2 = new Feed(); + $feed2->setId(5); + $feeds = [$feed1, $feed2]; + + $time = $this->time - $this->autoPurgeMinimumInterval; + $this->feedMapper->expects($this->once()) + ->method('getToDelete') + ->with($this->equalTo($time), $this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + $this->feedMapper->expects($this->at(1)) + ->method('delete') + ->with($this->equalTo($feed1)); + $this->feedMapper->expects($this->at(2)) + ->method('delete') + ->with($this->equalTo($feed2)); + + $this->feedService->purgeDeleted($this->user); + } + + + public function testPurgeDeletedWithoutInterval(){ + $feed1 = new Feed(); + $feed1->setId(3); + $feed2 = new Feed(); + $feed2->setId(5); + $feeds = [$feed1, $feed2]; + + $this->feedMapper->expects($this->once()) + ->method('getToDelete') + ->with($this->equalTo(null), $this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + $this->feedMapper->expects($this->at(1)) + ->method('delete') + ->with($this->equalTo($feed1)); + $this->feedMapper->expects($this->at(2)) + ->method('delete') + ->with($this->equalTo($feed2)); + + $this->feedService->purgeDeleted($this->user, false); + } + + + public function testfindAllFromAllUsers() { + $expected = 'hi'; + $this->feedMapper->expects($this->once()) + ->method('findAll') + ->will($this->returnValue($expected)); + $result = $this->feedService->findAllFromAllUsers(); + $this->assertEquals($expected, $result); + } + + + public function testDeleteUser() { + $this->feedMapper->expects($this->once()) + ->method('deleteUser') + ->will($this->returnValue($this->user)); + + $this->feedService->deleteUser($this->user); + } } diff --git a/tests/unit/service/FolderServiceTest.php b/tests/unit/service/FolderServiceTest.php index bbc89c99d..53fb737b7 100644 --- a/tests/unit/service/FolderServiceTest.php +++ b/tests/unit/service/FolderServiceTest.php @@ -18,255 +18,255 @@ use \OCA\News\Db\Folder; class FolderServiceTest extends \PHPUnit_Framework_TestCase { - private $folderMapper; - private $folderService; - private $time; - private $user; - private $autoPurgeMinimumInterval; - private $l10n; - - protected function setUp(){ - $this->l10n = $this->getMockBuilder('\OCP\IL10N') - ->disableOriginalConstructor() - ->getMock(); - $this->time = 222; - $timeFactory = $this->getMock('TimeFactory', ['getTime']); - $timeFactory->expects($this->any()) - ->method('getTime') - ->will($this->returnValue($this->time)); - $this->folderMapper = $this->getMockBuilder( - '\OCA\News\Db\FolderMapper') - ->disableOriginalConstructor() - ->getMock(); - $this->autoPurgeMinimumInterval = 10; - $config = $this->getMockBuilder( - '\OCA\News\Config\Config') - ->disableOriginalConstructor() - ->getMock(); - $config->expects($this->any()) - ->method('getAutoPurgeMinimumInterval') - ->will($this->returnValue($this->autoPurgeMinimumInterval)); - $this->folderService = new FolderService( - $this->folderMapper, $this->l10n, $timeFactory, $config); - $this->user = 'hi'; - } + private $folderMapper; + private $folderService; + private $time; + private $user; + private $autoPurgeMinimumInterval; + private $l10n; + + protected function setUp(){ + $this->l10n = $this->getMockBuilder('\OCP\IL10N') + ->disableOriginalConstructor() + ->getMock(); + $this->time = 222; + $timeFactory = $this->getMock('TimeFactory', ['getTime']); + $timeFactory->expects($this->any()) + ->method('getTime') + ->will($this->returnValue($this->time)); + $this->folderMapper = $this->getMockBuilder( + '\OCA\News\Db\FolderMapper') + ->disableOriginalConstructor() + ->getMock(); + $this->autoPurgeMinimumInterval = 10; + $config = $this->getMockBuilder( + '\OCA\News\Config\Config') + ->disableOriginalConstructor() + ->getMock(); + $config->expects($this->any()) + ->method('getAutoPurgeMinimumInterval') + ->will($this->returnValue($this->autoPurgeMinimumInterval)); + $this->folderService = new FolderService( + $this->folderMapper, $this->l10n, $timeFactory, $config); + $this->user = 'hi'; + } - function testFindAll(){ - $userId = 'jack'; - $return = 'hi'; - $this->folderMapper->expects($this->once()) - ->method('findAllFromUser') - ->with($this->equalTo($userId)) - ->will($this->returnValue($return)); - - $result = $this->folderService->findAll($userId); - - $this->assertEquals($return, $result); - } - - - public function testCreate(){ - $folder = new Folder(); - $folder->setName('hey'); - $folder->setParentId(5); - $folder->setUserId('john'); - $folder->setOpened(true); + function testFindAll(){ + $userId = 'jack'; + $return = 'hi'; + $this->folderMapper->expects($this->once()) + ->method('findAllFromUser') + ->with($this->equalTo($userId)) + ->will($this->returnValue($return)); + + $result = $this->folderService->findAll($userId); + + $this->assertEquals($return, $result); + } + + + public function testCreate(){ + $folder = new Folder(); + $folder->setName('hey'); + $folder->setParentId(5); + $folder->setUserId('john'); + $folder->setOpened(true); - $this->folderMapper->expects($this->once()) - ->method('insert') - ->with($this->equalTo($folder)) - ->will($this->returnValue($folder)); - - $result = $this->folderService->create('hey', 'john', 5); + $this->folderMapper->expects($this->once()) + ->method('insert') + ->with($this->equalTo($folder)) + ->will($this->returnValue($folder)); + + $result = $this->folderService->create('hey', 'john', 5); - $this->assertEquals($folder, $result); - } + $this->assertEquals($folder, $result); + } - public function testCreateThrowsExWhenFolderNameExists(){ - $folderName = 'hihi'; - $rows = [['id' => 1]]; + public function testCreateThrowsExWhenFolderNameExists(){ + $folderName = 'hihi'; + $rows = [['id' => 1]]; - $this->l10n->expects($this->once()) - ->method('t'); - $this->folderMapper->expects($this->once()) - ->method('findByName') - ->with($this->equalTo($folderName)) - ->will($this->returnValue($rows)); - - $this->setExpectedException('\OCA\News\Service\ServiceConflictException'); - $this->folderService->create($folderName, 'john', 3); - } + $this->l10n->expects($this->once()) + ->method('t'); + $this->folderMapper->expects($this->once()) + ->method('findByName') + ->with($this->equalTo($folderName)) + ->will($this->returnValue($rows)); + + $this->setExpectedException('\OCA\News\Service\ServiceConflictException'); + $this->folderService->create($folderName, 'john', 3); + } - public function testCreateThrowsExWhenFolderNameEmpty(){ - $folderName = ''; - - $this->folderMapper->expects($this->once()) - ->method('findByName') - ->with($this->equalTo($folderName)) - ->will($this->returnValue([])); - - $this->setExpectedException('\OCA\News\Service\ServiceValidationException'); - $this->folderService->create($folderName, 'john', 3); - } - - - public function testOpen(){ - $folder = new Folder(); - - $this->folderMapper->expects($this->once()) - ->method('find') - ->with($this->equalTo(3)) - ->will($this->returnValue($folder)); - - $this->folderMapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($folder)); - - $this->folderService->open(3, false, ''); - - $this->assertFalse($folder->getOpened()); - - } - - - public function testRename(){ - $folder = new Folder(); - $folder->setName('jooohn'); - - $this->folderMapper->expects($this->once()) - ->method('find') - ->with($this->equalTo(3)) - ->will($this->returnValue($folder)); + public function testCreateThrowsExWhenFolderNameEmpty(){ + $folderName = ''; + + $this->folderMapper->expects($this->once()) + ->method('findByName') + ->with($this->equalTo($folderName)) + ->will($this->returnValue([])); + + $this->setExpectedException('\OCA\News\Service\ServiceValidationException'); + $this->folderService->create($folderName, 'john', 3); + } + + + public function testOpen(){ + $folder = new Folder(); + + $this->folderMapper->expects($this->once()) + ->method('find') + ->with($this->equalTo(3)) + ->will($this->returnValue($folder)); + + $this->folderMapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($folder)); + + $this->folderService->open(3, false, ''); + + $this->assertFalse($folder->getOpened()); + + } + + + public function testRename(){ + $folder = new Folder(); + $folder->setName('jooohn'); + + $this->folderMapper->expects($this->once()) + ->method('find') + ->with($this->equalTo(3)) + ->will($this->returnValue($folder)); - $this->folderMapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($folder)); + $this->folderMapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($folder)); - $this->folderService->rename(3, 'bogus', ''); + $this->folderService->rename(3, 'bogus', ''); - $this->assertEquals('bogus', $folder->getName()); - } + $this->assertEquals('bogus', $folder->getName()); + } - public function testRenameThrowsExWhenFolderNameExists(){ - $folderName = 'hihi'; - $rows = [['id' => 1]]; + public function testRenameThrowsExWhenFolderNameExists(){ + $folderName = 'hihi'; + $rows = [['id' => 1]]; - $this->l10n->expects($this->once()) - ->method('t'); - $this->folderMapper->expects($this->once()) - ->method('findByName') - ->with($this->equalTo($folderName)) - ->will($this->returnValue($rows)); + $this->l10n->expects($this->once()) + ->method('t'); + $this->folderMapper->expects($this->once()) + ->method('findByName') + ->with($this->equalTo($folderName)) + ->will($this->returnValue($rows)); - $this->setExpectedException('\OCA\News\Service\ServiceConflictException'); - $this->folderService->rename(3, $folderName, 'john'); - } + $this->setExpectedException('\OCA\News\Service\ServiceConflictException'); + $this->folderService->rename(3, $folderName, 'john'); + } - public function testRenameThrowsExWhenFolderNameEmpty(){ - $folderName = ''; + public function testRenameThrowsExWhenFolderNameEmpty(){ + $folderName = ''; - $this->folderMapper->expects($this->once()) - ->method('findByName') - ->with($this->equalTo($folderName)) - ->will($this->returnValue([])); + $this->folderMapper->expects($this->once()) + ->method('findByName') + ->with($this->equalTo($folderName)) + ->will($this->returnValue([])); - $this->setExpectedException('\OCA\News\Service\ServiceValidationException'); - $this->folderService->rename(3, $folderName, 'john'); - } + $this->setExpectedException('\OCA\News\Service\ServiceValidationException'); + $this->folderService->rename(3, $folderName, 'john'); + } - public function testMarkDeleted() { - $id = 3; - $folder = new Folder(); - $folder2 = new Folder(); - $folder2->setDeletedAt($this->time); + public function testMarkDeleted() { + $id = 3; + $folder = new Folder(); + $folder2 = new Folder(); + $folder2->setDeletedAt($this->time); - $this->folderMapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($id), $this->equalTo($this->user)) - ->will($this->returnValue($folder)); - $this->folderMapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($folder2)); + $this->folderMapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($id), $this->equalTo($this->user)) + ->will($this->returnValue($folder)); + $this->folderMapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($folder2)); - $this->folderService->markDeleted($id, $this->user); - } + $this->folderService->markDeleted($id, $this->user); + } - public function testUnmarkDeleted() { - $id = 3; - $folder = new Folder(); - $folder2 = new Folder(); - $folder2->setDeletedAt(0); - - $this->folderMapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($id), $this->equalTo($this->user)) - ->will($this->returnValue($folder)); - $this->folderMapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($folder2)); + public function testUnmarkDeleted() { + $id = 3; + $folder = new Folder(); + $folder2 = new Folder(); + $folder2->setDeletedAt(0); + + $this->folderMapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($id), $this->equalTo($this->user)) + ->will($this->returnValue($folder)); + $this->folderMapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($folder2)); - $this->folderService->unmarkDeleted($id, $this->user); - } - - public function testPurgeDeleted(){ - $folder1 = new Folder(); - $folder1->setId(3); - $folder2 = new Folder(); - $folder2->setId(5); - $feeds = [$folder1, $folder2]; - - $time = $this->time - $this->autoPurgeMinimumInterval; - $this->folderMapper->expects($this->once()) - ->method('getToDelete') - ->with($this->equalTo($time), $this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - $this->folderMapper->expects($this->at(1)) - ->method('delete') - ->with($this->equalTo($folder1)); - $this->folderMapper->expects($this->at(2)) - ->method('delete') - ->with($this->equalTo($folder2)); - - $this->folderService->purgeDeleted($this->user); - } - - - public function testPurgeDeletedNoInterval(){ - $folder1 = new Folder(); - $folder1->setId(3); - $folder2 = new Folder(); - $folder2->setId(5); - $feeds = [$folder1, $folder2]; - - $this->folderMapper->expects($this->once()) - ->method('getToDelete') - ->with($this->equalTo(null), $this->equalTo($this->user)) - ->will($this->returnValue($feeds)); - $this->folderMapper->expects($this->at(1)) - ->method('delete') - ->with($this->equalTo($folder1)); - $this->folderMapper->expects($this->at(2)) - ->method('delete') - ->with($this->equalTo($folder2)); - - $this->folderService->purgeDeleted($this->user, false); - } - - - public function testDeleteUser() { - $this->folderMapper->expects($this->once()) - ->method('deleteUser') - ->will($this->returnValue($this->user)); - - $this->folderService->deleteUser($this->user); - } + $this->folderService->unmarkDeleted($id, $this->user); + } + + public function testPurgeDeleted(){ + $folder1 = new Folder(); + $folder1->setId(3); + $folder2 = new Folder(); + $folder2->setId(5); + $feeds = [$folder1, $folder2]; + + $time = $this->time - $this->autoPurgeMinimumInterval; + $this->folderMapper->expects($this->once()) + ->method('getToDelete') + ->with($this->equalTo($time), $this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + $this->folderMapper->expects($this->at(1)) + ->method('delete') + ->with($this->equalTo($folder1)); + $this->folderMapper->expects($this->at(2)) + ->method('delete') + ->with($this->equalTo($folder2)); + + $this->folderService->purgeDeleted($this->user); + } + + + public function testPurgeDeletedNoInterval(){ + $folder1 = new Folder(); + $folder1->setId(3); + $folder2 = new Folder(); + $folder2->setId(5); + $feeds = [$folder1, $folder2]; + + $this->folderMapper->expects($this->once()) + ->method('getToDelete') + ->with($this->equalTo(null), $this->equalTo($this->user)) + ->will($this->returnValue($feeds)); + $this->folderMapper->expects($this->at(1)) + ->method('delete') + ->with($this->equalTo($folder1)); + $this->folderMapper->expects($this->at(2)) + ->method('delete') + ->with($this->equalTo($folder2)); + + $this->folderService->purgeDeleted($this->user, false); + } + + + public function testDeleteUser() { + $this->folderMapper->expects($this->once()) + ->method('deleteUser') + ->will($this->returnValue($this->user)); + + $this->folderService->deleteUser($this->user); + } } diff --git a/tests/unit/service/ItemServiceTest.php b/tests/unit/service/ItemServiceTest.php index 03d644eb9..b9f23fee6 100644 --- a/tests/unit/service/ItemServiceTest.php +++ b/tests/unit/service/ItemServiceTest.php @@ -22,403 +22,403 @@ use \OCA\News\Db\FeedType; class ItemServiceTest extends \PHPUnit_Framework_TestCase { - private $mapper; - private $itemService; - private $user; - private $response; - private $status; - private $time; - private $newestItemId; - - - protected function setUp(){ - $this->time = 222; - $timeFactory = $this->getMock('TimeFactory', ['getTime']); - $timeFactory->expects($this->any()) - ->method('getTime') - ->will($this->returnValue($this->time)); - $this->mapper = $this->getMockBuilder('\OCA\News\Db\ItemMapper') - ->disableOriginalConstructor() - ->getMock(); - $statusFlag = $this->getMockBuilder('\OCA\News\Db\StatusFlag') - ->disableOriginalConstructor() - ->getMock(); - $this->status = StatusFlag::STARRED; - $statusFlag->expects($this->any()) - ->method('typeToStatus') - ->will($this->returnValue($this->status)); - $this->threshold = 2; - $config = $this->getMockBuilder( - '\OCA\News\Config\Config') - ->disableOriginalConstructor() - ->getMock(); - $config->expects($this->any()) - ->method('getAutoPurgeCount') - ->will($this->returnValue($this->threshold)); - $this->itemService = new ItemService($this->mapper, - $statusFlag, $timeFactory, $config); - $this->user = 'jack'; - $this->id = 3; - $this->updatedSince = 20333; - $this->showAll = true; - $this->offset = 5; - $this->limit = 20; - $this->newestItemId = 4; - } - - - public function testFindAllNewFeed(){ - $type = FeedType::FEED; - $this->mapper->expects($this->once()) - ->method('findAllNewFeed') - ->with($this->equalTo($this->id), - $this->equalTo($this->updatedSince), - $this->equalTo($this->status), - $this->equalTo($this->user)) - ->will($this->returnValue($this->response)); - - $result = $this->itemService->findAllNew( - $this->id, $type, $this->updatedSince, $this->showAll, - $this->user); - $this->assertEquals($this->response, $result); - } - - - public function testFindAllNewFolder(){ - $type = FeedType::FOLDER; - $this->mapper->expects($this->once()) - ->method('findAllNewFolder') - ->with($this->equalTo($this->id), - $this->equalTo($this->updatedSince), - $this->equalTo($this->status), - $this->equalTo($this->user)) - ->will($this->returnValue($this->response)); - - $result = $this->itemService->findAllNew( - $this->id, $type, $this->updatedSince, $this->showAll, - $this->user); - $this->assertEquals($this->response, $result); - } - - - public function testFindAllNew(){ - $type = FeedType::STARRED; - $this->mapper->expects($this->once()) - ->method('findAllNew') - ->with( $this->equalTo($this->updatedSince), - $this->equalTo($this->status), - $this->equalTo($this->user)) - ->will($this->returnValue($this->response)); - - $result = $this->itemService->findAllNew( - $this->id, $type, $this->updatedSince, $this->showAll, - $this->user); - $this->assertEquals($this->response, $result); - } - - - public function testFindAllFeed(){ - $type = FeedType::FEED; - $this->mapper->expects($this->once()) - ->method('findAllFeed') - ->with($this->equalTo($this->id), - $this->equalTo($this->limit), - $this->equalTo($this->offset), - $this->equalTo($this->status), - $this->equalTo(false), - $this->equalTo($this->user)) - ->will($this->returnValue($this->response)); - - $result = $this->itemService->findAll( - $this->id, $type, $this->limit, $this->offset, - $this->showAll, false, $this->user - ); - $this->assertEquals($this->response, $result); - } - - - public function testFindAllFolder(){ - $type = FeedType::FOLDER; - $this->mapper->expects($this->once()) - ->method('findAllFolder') - ->with($this->equalTo($this->id), - $this->equalTo($this->limit), - $this->equalTo($this->offset), - $this->equalTo($this->status), - $this->equalTo(true), - $this->equalTo($this->user)) - ->will($this->returnValue($this->response)); - - $result = $this->itemService->findAll( - $this->id, $type, $this->limit, $this->offset, - $this->showAll, true, $this->user - ); - $this->assertEquals($this->response, $result); - } - - - public function testFindAll(){ - $type = FeedType::STARRED; - $this->mapper->expects($this->once()) - ->method('findAll') - ->with( $this->equalTo($this->limit), - $this->equalTo($this->offset), - $this->equalTo($this->status), - $this->equalTo(true), - $this->equalTo($this->user)) - ->will($this->returnValue($this->response)); - - $result = $this->itemService->findAll( - $this->id, $type, $this->limit, $this->offset, - $this->showAll, true, $this->user - ); - $this->assertEquals($this->response, $result); - } - - - public function testStar(){ - $itemId = 3; - $feedId = 5; - $guidHash = md5('hihi'); - - $item = new Item(); - $item->setStatus(128); - $item->setId($itemId); - $item->setUnstarred(); - - $expectedItem = new Item(); - $expectedItem->setStatus(128); - $expectedItem->setStarred(); - $expectedItem->setId($itemId); - $expectedItem->setLastModified($this->time); - - $this->mapper->expects($this->once()) - ->method('findByGuidHash') - ->with( - $this->equalTo($guidHash), - $this->equalTo($feedId), - $this->equalTo($this->user)) - ->will($this->returnValue($item)); - - $this->mapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($expectedItem)); - - $this->itemService->star($feedId, $guidHash, true, $this->user); - - $this->assertTrue($item->isStarred()); - } - - - public function testUnstar(){ - $itemId = 3; - $feedId = 5; - $guidHash = md5('hihi'); - - $item = new Item(); - $item->setStatus(128); - $item->setId($itemId); - $item->setStarred(); - - $expectedItem = new Item(); - $expectedItem->setStatus(128); - $expectedItem->setUnstarred(); - $expectedItem->setId($itemId); - $expectedItem->setLastModified($this->time); - - $this->mapper->expects($this->once()) - ->method('findByGuidHash') - ->with( - $this->equalTo($guidHash), - $this->equalTo($feedId), - $this->equalTo($this->user)) - ->will($this->returnValue($item)); - - $this->mapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($expectedItem)); - - $this->itemService->star($feedId, $guidHash, false, $this->user); - - $this->assertTrue($item->isUnstarred()); - } - - public function testUnread(){ - $itemId = 3; - $item = new Item(); - $item->setStatus(128); - $item->setId($itemId); - $item->setRead(); - - $expectedItem = new Item(); - $expectedItem->setStatus(128); - $expectedItem->setUnread(); - $expectedItem->setId($itemId); - $expectedItem->setLastModified($this->time); + private $mapper; + private $itemService; + private $user; + private $response; + private $status; + private $time; + private $newestItemId; + + + protected function setUp(){ + $this->time = 222; + $timeFactory = $this->getMock('TimeFactory', ['getTime']); + $timeFactory->expects($this->any()) + ->method('getTime') + ->will($this->returnValue($this->time)); + $this->mapper = $this->getMockBuilder('\OCA\News\Db\ItemMapper') + ->disableOriginalConstructor() + ->getMock(); + $statusFlag = $this->getMockBuilder('\OCA\News\Db\StatusFlag') + ->disableOriginalConstructor() + ->getMock(); + $this->status = StatusFlag::STARRED; + $statusFlag->expects($this->any()) + ->method('typeToStatus') + ->will($this->returnValue($this->status)); + $this->threshold = 2; + $config = $this->getMockBuilder( + '\OCA\News\Config\Config') + ->disableOriginalConstructor() + ->getMock(); + $config->expects($this->any()) + ->method('getAutoPurgeCount') + ->will($this->returnValue($this->threshold)); + $this->itemService = new ItemService($this->mapper, + $statusFlag, $timeFactory, $config); + $this->user = 'jack'; + $this->id = 3; + $this->updatedSince = 20333; + $this->showAll = true; + $this->offset = 5; + $this->limit = 20; + $this->newestItemId = 4; + } + + + public function testFindAllNewFeed(){ + $type = FeedType::FEED; + $this->mapper->expects($this->once()) + ->method('findAllNewFeed') + ->with($this->equalTo($this->id), + $this->equalTo($this->updatedSince), + $this->equalTo($this->status), + $this->equalTo($this->user)) + ->will($this->returnValue($this->response)); + + $result = $this->itemService->findAllNew( + $this->id, $type, $this->updatedSince, $this->showAll, + $this->user); + $this->assertEquals($this->response, $result); + } + + + public function testFindAllNewFolder(){ + $type = FeedType::FOLDER; + $this->mapper->expects($this->once()) + ->method('findAllNewFolder') + ->with($this->equalTo($this->id), + $this->equalTo($this->updatedSince), + $this->equalTo($this->status), + $this->equalTo($this->user)) + ->will($this->returnValue($this->response)); + + $result = $this->itemService->findAllNew( + $this->id, $type, $this->updatedSince, $this->showAll, + $this->user); + $this->assertEquals($this->response, $result); + } + + + public function testFindAllNew(){ + $type = FeedType::STARRED; + $this->mapper->expects($this->once()) + ->method('findAllNew') + ->with( $this->equalTo($this->updatedSince), + $this->equalTo($this->status), + $this->equalTo($this->user)) + ->will($this->returnValue($this->response)); + + $result = $this->itemService->findAllNew( + $this->id, $type, $this->updatedSince, $this->showAll, + $this->user); + $this->assertEquals($this->response, $result); + } + + + public function testFindAllFeed(){ + $type = FeedType::FEED; + $this->mapper->expects($this->once()) + ->method('findAllFeed') + ->with($this->equalTo($this->id), + $this->equalTo($this->limit), + $this->equalTo($this->offset), + $this->equalTo($this->status), + $this->equalTo(false), + $this->equalTo($this->user)) + ->will($this->returnValue($this->response)); + + $result = $this->itemService->findAll( + $this->id, $type, $this->limit, $this->offset, + $this->showAll, false, $this->user + ); + $this->assertEquals($this->response, $result); + } + + + public function testFindAllFolder(){ + $type = FeedType::FOLDER; + $this->mapper->expects($this->once()) + ->method('findAllFolder') + ->with($this->equalTo($this->id), + $this->equalTo($this->limit), + $this->equalTo($this->offset), + $this->equalTo($this->status), + $this->equalTo(true), + $this->equalTo($this->user)) + ->will($this->returnValue($this->response)); + + $result = $this->itemService->findAll( + $this->id, $type, $this->limit, $this->offset, + $this->showAll, true, $this->user + ); + $this->assertEquals($this->response, $result); + } + + + public function testFindAll(){ + $type = FeedType::STARRED; + $this->mapper->expects($this->once()) + ->method('findAll') + ->with( $this->equalTo($this->limit), + $this->equalTo($this->offset), + $this->equalTo($this->status), + $this->equalTo(true), + $this->equalTo($this->user)) + ->will($this->returnValue($this->response)); + + $result = $this->itemService->findAll( + $this->id, $type, $this->limit, $this->offset, + $this->showAll, true, $this->user + ); + $this->assertEquals($this->response, $result); + } + + + public function testStar(){ + $itemId = 3; + $feedId = 5; + $guidHash = md5('hihi'); + + $item = new Item(); + $item->setStatus(128); + $item->setId($itemId); + $item->setUnstarred(); + + $expectedItem = new Item(); + $expectedItem->setStatus(128); + $expectedItem->setStarred(); + $expectedItem->setId($itemId); + $expectedItem->setLastModified($this->time); + + $this->mapper->expects($this->once()) + ->method('findByGuidHash') + ->with( + $this->equalTo($guidHash), + $this->equalTo($feedId), + $this->equalTo($this->user)) + ->will($this->returnValue($item)); + + $this->mapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($expectedItem)); + + $this->itemService->star($feedId, $guidHash, true, $this->user); + + $this->assertTrue($item->isStarred()); + } + + + public function testUnstar(){ + $itemId = 3; + $feedId = 5; + $guidHash = md5('hihi'); + + $item = new Item(); + $item->setStatus(128); + $item->setId($itemId); + $item->setStarred(); + + $expectedItem = new Item(); + $expectedItem->setStatus(128); + $expectedItem->setUnstarred(); + $expectedItem->setId($itemId); + $expectedItem->setLastModified($this->time); + + $this->mapper->expects($this->once()) + ->method('findByGuidHash') + ->with( + $this->equalTo($guidHash), + $this->equalTo($feedId), + $this->equalTo($this->user)) + ->will($this->returnValue($item)); + + $this->mapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($expectedItem)); + + $this->itemService->star($feedId, $guidHash, false, $this->user); + + $this->assertTrue($item->isUnstarred()); + } + + public function testUnread(){ + $itemId = 3; + $item = new Item(); + $item->setStatus(128); + $item->setId($itemId); + $item->setRead(); + + $expectedItem = new Item(); + $expectedItem->setStatus(128); + $expectedItem->setUnread(); + $expectedItem->setId($itemId); + $expectedItem->setLastModified($this->time); - $this->mapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($itemId), $this->equalTo($this->user)) - ->will($this->returnValue($item)); + $this->mapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($itemId), $this->equalTo($this->user)) + ->will($this->returnValue($item)); - $this->mapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($expectedItem)); + $this->mapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($expectedItem)); - $this->itemService->read($itemId, false, $this->user); + $this->itemService->read($itemId, false, $this->user); - $this->assertTrue($item->isUnread()); - } + $this->assertTrue($item->isUnread()); + } - public function testRead(){ - $itemId = 3; - $item = new Item(); - $item->setStatus(128); - $item->setId($itemId); - $item->setUnread(); + public function testRead(){ + $itemId = 3; + $item = new Item(); + $item->setStatus(128); + $item->setId($itemId); + $item->setUnread(); - $expectedItem = new Item(); - $expectedItem->setStatus(128); - $expectedItem->setRead(); - $expectedItem->setId($itemId); - $expectedItem->setLastModified($this->time); + $expectedItem = new Item(); + $expectedItem->setStatus(128); + $expectedItem->setRead(); + $expectedItem->setId($itemId); + $expectedItem->setLastModified($this->time); - $this->mapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($itemId), $this->equalTo($this->user)) - ->will($this->returnValue($item)); + $this->mapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($itemId), $this->equalTo($this->user)) + ->will($this->returnValue($item)); - $this->mapper->expects($this->once()) - ->method('update') - ->with($this->equalTo($expectedItem)); + $this->mapper->expects($this->once()) + ->method('update') + ->with($this->equalTo($expectedItem)); - $this->itemService->read($itemId, true, $this->user); + $this->itemService->read($itemId, true, $this->user); - $this->assertTrue($item->isRead()); - } + $this->assertTrue($item->isRead()); + } - public function testStarDoesNotExist(){ + public function testStarDoesNotExist(){ - $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); - $this->mapper->expects($this->once()) - ->method('findByGuidHash') - ->will($this->throwException(new DoesNotExistException(''))); + $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); + $this->mapper->expects($this->once()) + ->method('findByGuidHash') + ->will($this->throwException(new DoesNotExistException(''))); - $this->itemService->star(1, 'hash', true, $this->user); - } + $this->itemService->star(1, 'hash', true, $this->user); + } - public function testReadAll(){ - $highestItemId = 6; + public function testReadAll(){ + $highestItemId = 6; - $this->mapper->expects($this->once()) - ->method('readAll') - ->with($this->equalTo($highestItemId), - $this->equalTo($this->time), - $this->equalTo($this->user)); + $this->mapper->expects($this->once()) + ->method('readAll') + ->with($this->equalTo($highestItemId), + $this->equalTo($this->time), + $this->equalTo($this->user)); - $this->itemService->readAll($highestItemId, $this->user); - } + $this->itemService->readAll($highestItemId, $this->user); + } - public function testReadFolder(){ - $folderId = 3; - $highestItemId = 6; + public function testReadFolder(){ + $folderId = 3; + $highestItemId = 6; - $this->mapper->expects($this->once()) - ->method('readFolder') - ->with($this->equalTo($folderId), - $this->equalTo($highestItemId), - $this->equalTo($this->time), - $this->equalTo($this->user)); + $this->mapper->expects($this->once()) + ->method('readFolder') + ->with($this->equalTo($folderId), + $this->equalTo($highestItemId), + $this->equalTo($this->time), + $this->equalTo($this->user)); - $this->itemService->readFolder($folderId, $highestItemId, $this->user); - } + $this->itemService->readFolder($folderId, $highestItemId, $this->user); + } - public function testReadFeed(){ - $feedId = 3; - $highestItemId = 6; + public function testReadFeed(){ + $feedId = 3; + $highestItemId = 6; - $this->mapper->expects($this->once()) - ->method('readFeed') - ->with($this->equalTo($feedId), - $this->equalTo($highestItemId), - $this->equalTo($this->time), - $this->equalTo($this->user)); + $this->mapper->expects($this->once()) + ->method('readFeed') + ->with($this->equalTo($feedId), + $this->equalTo($highestItemId), + $this->equalTo($this->time), + $this->equalTo($this->user)); - $this->itemService->readFeed($feedId, $highestItemId, $this->user); - } + $this->itemService->readFeed($feedId, $highestItemId, $this->user); + } - public function testAutoPurgeOldWillPurgeOld(){ - $this->mapper->expects($this->once()) - ->method('deleteReadOlderThanThreshold') - ->with($this->equalTo($this->threshold)); + public function testAutoPurgeOldWillPurgeOld(){ + $this->mapper->expects($this->once()) + ->method('deleteReadOlderThanThreshold') + ->with($this->equalTo($this->threshold)); - $this->itemService->autoPurgeOld(); - } + $this->itemService->autoPurgeOld(); + } - public function testGetNewestItemId() { - $this->mapper->expects($this->once()) - ->method('getNewestItemId') - ->with($this->equalTo($this->user)) - ->will($this->returnValue(12)); + public function testGetNewestItemId() { + $this->mapper->expects($this->once()) + ->method('getNewestItemId') + ->with($this->equalTo($this->user)) + ->will($this->returnValue(12)); - $result = $this->itemService->getNewestItemId($this->user); - $this->assertEquals(12, $result); - } + $result = $this->itemService->getNewestItemId($this->user); + $this->assertEquals(12, $result); + } - public function testGetNewestItemIdDoesNotExist() { - $this->mapper->expects($this->once()) - ->method('getNewestItemId') - ->with($this->equalTo($this->user)) - ->will($this->throwException(new DoesNotExistException('There are no items'))); + public function testGetNewestItemIdDoesNotExist() { + $this->mapper->expects($this->once()) + ->method('getNewestItemId') + ->with($this->equalTo($this->user)) + ->will($this->throwException(new DoesNotExistException('There are no items'))); - $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); - $this->itemService->getNewestItemId($this->user); - } + $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); + $this->itemService->getNewestItemId($this->user); + } - public function testStarredCount(){ - $star = 18; + public function testStarredCount(){ + $star = 18; - $this->mapper->expects($this->once()) - ->method('starredCount') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($star)); + $this->mapper->expects($this->once()) + ->method('starredCount') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($star)); - $result = $this->itemService->starredCount($this->user); + $result = $this->itemService->starredCount($this->user); - $this->assertEquals($star, $result); - } + $this->assertEquals($star, $result); + } - public function testGetUnreadOrStarred(){ - $star = 18; + public function testGetUnreadOrStarred(){ + $star = 18; - $this->mapper->expects($this->once()) - ->method('findAllUnreadOrStarred') - ->with($this->equalTo($this->user)) - ->will($this->returnValue($star)); + $this->mapper->expects($this->once()) + ->method('findAllUnreadOrStarred') + ->with($this->equalTo($this->user)) + ->will($this->returnValue($star)); - $result = $this->itemService->getUnreadOrStarred($this->user); + $result = $this->itemService->getUnreadOrStarred($this->user); - $this->assertEquals($star, $result); - } + $this->assertEquals($star, $result); + } - public function testDeleteUser() { - $this->mapper->expects($this->once()) - ->method('deleteUser') - ->will($this->returnValue($this->user)); + public function testDeleteUser() { + $this->mapper->expects($this->once()) + ->method('deleteUser') + ->will($this->returnValue($this->user)); - $this->itemService->deleteUser($this->user); - } + $this->itemService->deleteUser($this->user); + } diff --git a/tests/unit/service/ServiceTest.php b/tests/unit/service/ServiceTest.php index 369962128..473141cd3 100644 --- a/tests/unit/service/ServiceTest.php +++ b/tests/unit/service/ServiceTest.php @@ -20,75 +20,75 @@ use \OCA\News\Db\Folder; class TestService extends Service { - public function __construct($mapper){ - parent::__construct($mapper); - } + public function __construct($mapper){ + parent::__construct($mapper); + } } class ServiceTest extends \PHPUnit_Framework_TestCase { - protected $mapper; - protected $newsService; + protected $mapper; + protected $newsService; - protected function setUp(){ - $this->mapper = $this->getMockBuilder('\OCA\News\Db\ItemMapper') - ->disableOriginalConstructor() - ->getMock(); - $this->newsService = new TestService($this->mapper); - } + protected function setUp(){ + $this->mapper = $this->getMockBuilder('\OCA\News\Db\ItemMapper') + ->disableOriginalConstructor() + ->getMock(); + $this->newsService = new TestService($this->mapper); + } - public function testDelete(){ - $id = 5; - $user = 'ken'; - $folder = new Folder(); - $folder->setId($id); + public function testDelete(){ + $id = 5; + $user = 'ken'; + $folder = new Folder(); + $folder->setId($id); - $this->mapper->expects($this->once()) - ->method('delete') - ->with($this->equalTo($folder)); - $this->mapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($id), $this->equalTo($user)) - ->will($this->returnValue($folder)); + $this->mapper->expects($this->once()) + ->method('delete') + ->with($this->equalTo($folder)); + $this->mapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($id), $this->equalTo($user)) + ->will($this->returnValue($folder)); - $this->newsService->delete($id, $user); - } + $this->newsService->delete($id, $user); + } - public function testFind(){ - $id = 3; - $user = 'ken'; + public function testFind(){ + $id = 3; + $user = 'ken'; - $this->mapper->expects($this->once()) - ->method('find') - ->with($this->equalTo($id), $this->equalTo($user)); + $this->mapper->expects($this->once()) + ->method('find') + ->with($this->equalTo($id), $this->equalTo($user)); - $this->newsService->find($id, $user); - } + $this->newsService->find($id, $user); + } - public function testFindDoesNotExist(){ - $ex = new DoesNotExistException('hi'); + public function testFindDoesNotExist(){ + $ex = new DoesNotExistException('hi'); - $this->mapper->expects($this->once()) - ->method('find') - ->will($this->throwException($ex)); + $this->mapper->expects($this->once()) + ->method('find') + ->will($this->throwException($ex)); - $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); - $this->newsService->find(1, ''); - } + $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); + $this->newsService->find(1, ''); + } - public function testFindMultiple(){ - $ex = new MultipleObjectsReturnedException('hi'); + public function testFindMultiple(){ + $ex = new MultipleObjectsReturnedException('hi'); - $this->mapper->expects($this->once()) - ->method('find') - ->will($this->throwException($ex)); + $this->mapper->expects($this->once()) + ->method('find') + ->will($this->throwException($ex)); - $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); - $this->newsService->find(1, ''); - } + $this->setExpectedException('\OCA\News\Service\ServiceNotFoundException'); + $this->newsService->find(1, ''); + } } diff --git a/tests/unit/service/StatusFlagTest.php b/tests/unit/service/StatusFlagTest.php index 372fdbd88..820560aa4 100644 --- a/tests/unit/service/StatusFlagTest.php +++ b/tests/unit/service/StatusFlagTest.php @@ -16,42 +16,42 @@ namespace OCA\News\Db; class StatusFlagTest extends \PHPUnit_Framework_TestCase { - private $statusFlag; + private $statusFlag; - protected function setUp(){ - $this->statusFlag = new StatusFlag(); - } + protected function setUp(){ + $this->statusFlag = new StatusFlag(); + } - public function testTypeToStatusUnreadStarred(){ - $expected = StatusFlag::STARRED; - $status = $this->statusFlag->typeToStatus(FeedType::STARRED, false); + public function testTypeToStatusUnreadStarred(){ + $expected = StatusFlag::STARRED; + $status = $this->statusFlag->typeToStatus(FeedType::STARRED, false); - $this->assertEquals($expected, $status); - } + $this->assertEquals($expected, $status); + } - public function testTypeToStatusUnread(){ - $expected = StatusFlag::UNREAD; - $status = $this->statusFlag->typeToStatus(FeedType::FEED, false); + public function testTypeToStatusUnread(){ + $expected = StatusFlag::UNREAD; + $status = $this->statusFlag->typeToStatus(FeedType::FEED, false); - $this->assertEquals($expected, $status); - } + $this->assertEquals($expected, $status); + } - public function testTypeToStatusReadStarred(){ - $expected = StatusFlag::STARRED; - $status = $this->statusFlag->typeToStatus(FeedType::STARRED, true); + public function testTypeToStatusReadStarred(){ + $expected = StatusFlag::STARRED; + $status = $this->statusFlag->typeToStatus(FeedType::STARRED, true); - $this->assertEquals($expected, $status); - } + $this->assertEquals($expected, $status); + } - public function testTypeToStatusRead(){ - $expected = (~StatusFlag::UNREAD) & 0; - $status = $this->statusFlag->typeToStatus(FeedType::FEED, true); + public function testTypeToStatusRead(){ + $expected = (~StatusFlag::UNREAD) & 0; + $status = $this->statusFlag->typeToStatus(FeedType::FEED, true); - $this->assertEquals($expected, $status); - } + $this->assertEquals($expected, $status); + } }
\ No newline at end of file diff --git a/tests/unit/utility/FaviconFetcherTest.php b/tests/unit/utility/FaviconFetcherTest.php index 3ed0d4dc8..e73510a13 100644 --- a/tests/unit/utility/FaviconFetcherTest.php +++ b/tests/unit/utility/FaviconFetcherTest.php @@ -17,183 +17,183 @@ namespace OCA\News\Utility; class FaviconFetcherTest extends \PHPUnit_Framework_TestCase { - private $fetcher; - private $fileFactory; - private $png; + private $fetcher; + private $fileFactory; + private $png; - protected function setUp(){ - $this->png = "\x89\x50\x4E\x47\x0D\x0A\x1A\x0A"; - $this->fileFactory = $this->getMockBuilder( - '\OCA\News\Utility\SimplePieAPIFactory') - ->disableOriginalConstructor() - ->getMock(); - $this->config = $this->getMockBuilder( - '\OCA\News\Utility\Config') - ->disableOriginalConstructor() - ->getMock(); - $this->fetcher = new FaviconFetcher($this->fileFactory); - } + protected function setUp(){ + $this->png = "\x89\x50\x4E\x47\x0D\x0A\x1A\x0A"; + $this->fileFactory = $this->getMockBuilder( + '\OCA\News\Utility\SimplePieAPIFactory') + ->disableOriginalConstructor() + ->getMock(); + $this->config = $this->getMockBuilder( + '\OCA\News\Utility\Config') + ->disableOriginalConstructor() + ->getMock(); + $this->fetcher = new FaviconFetcher($this->fileFactory); + } - protected function getFileMock($body='') { - $mock = $this->getMockBuilder('\SimplePie_File') - ->disableOriginalConstructor() - ->getMock(); - $mock->body = $body; - return $mock; - } + protected function getFileMock($body='') { + $mock = $this->getMockBuilder('\SimplePie_File') + ->disableOriginalConstructor() + ->getMock(); + $mock->body = $body; + return $mock; + } - protected function getFileMockCallback($onEqual, $returnMock) { - $defaultMock = $this->getFileMock(); + protected function getFileMockCallback($onEqual, $returnMock) { + $defaultMock = $this->getFileMock(); - return function($url) use ($onEqual, $returnMock, $defaultMock) { - if($url === $onEqual){ - return $returnMock; - } else { - return $defaultMock; - } - }; - } + return function($url) use ($onEqual, $returnMock, $defaultMock) { + if($url === $onEqual){ + return $returnMock; + } else { + return $defaultMock; + } + }; + } - public function testFetchNoResponseReturnsNull() { - $mock = $this->getFileMock(); + public function testFetchNoResponseReturnsNull() { + $mock = $this->getFileMock(); - $this->fileFactory->expects($this->any()) - ->method('getFile') - ->will($this->returnValue($mock)); + $this->fileFactory->expects($this->any()) + ->method('getFile') + ->will($this->returnValue($mock)); - $favicon = $this->fetcher->fetch('dfdf'); - $this->assertNull($favicon); - } + $favicon = $this->fetcher->fetch('dfdf'); + $this->assertNull($favicon); + } - public function testNoProxySettingsAreUsed() { - $faviconPath = "/owncloud/core/img/favicon.png"; - $html = $this->getFaviconHTML($faviconPath); + public function testNoProxySettingsAreUsed() { + $faviconPath = "/owncloud/core/img/favicon.png"; + $html = $this->getFaviconHTML($faviconPath); - $url = 'http://google.com'; - $pageMock = $this->getFileMock($html); - $pngMock = $this->getFileMock($this->png); + $url = 'http://google.com'; + $pageMock = $this->getFileMock($html); + $pngMock = $this->getFileMock($this->png); - $this->fileFactory->expects($this->at(0)) - ->method('getFile') - ->with($this->equalTo('http://google.com')) - ->will($this->returnValue($pageMock)); + $this->fileFactory->expects($this->at(0)) + ->method('getFile') + ->with($this->equalTo('http://google.com')) + ->will($this->returnValue($pageMock)); - $this->fileFactory->expects($this->at(1)) - ->method('getFile') - ->with($this->equalTo( - 'http://google.com/owncloud/core/img/favicon.png'), - $this->equalTo(10), - $this->equalTo(5), - $this->equalTo(null), - $this->equalTo('Mozilla/5.0 AppleWebKit')) - ->will($this->returnValue($pngMock)); + $this->fileFactory->expects($this->at(1)) + ->method('getFile') + ->with($this->equalTo( + 'http://google.com/owncloud/core/img/favicon.png'), + $this->equalTo(10), + $this->equalTo(5), + $this->equalTo(null), + $this->equalTo('Mozilla/5.0 AppleWebKit')) + ->will($this->returnValue($pngMock)); - $favicon = $this->fetcher->fetch($url); + $favicon = $this->fetcher->fetch($url); - $this->assertEquals('http://google.com/owncloud/core/img/favicon.png', $favicon); - } + $this->assertEquals('http://google.com/owncloud/core/img/favicon.png', $favicon); + } - public function testFetchFaviconFaviconDotIcoHttp(){ - $url = ' sub.google.com '; - $mock = $this->getFileMock($this->png); + public function testFetchFaviconFaviconDotIcoHttp(){ + $url = ' sub.google.com '; + $mock = $this->getFileMock($this->png); - $callback = $this->getFileMockCallback( - 'http://sub.google.com/favicon.ico', $mock); + $callback = $this->getFileMockCallback( + 'http://sub.google.com/favicon.ico', $mock); - $this->fileFactory->expects($this->any()) - ->method('getFile') - ->will($this->returnCallback($callback)); + $this->fileFactory->expects($this->any()) + ->method('getFile') + ->will($this->returnCallback($callback)); - $favicon = $this->fetcher->fetch($url); + $favicon = $this->fetcher->fetch($url); - $this->assertEquals('http://sub.google.com/favicon.ico', $favicon); - } + $this->assertEquals('http://sub.google.com/favicon.ico', $favicon); + } - public function testFetchFaviconFaviconDotIcoHttpBaseUrl(){ - $url = 'https://google.com/sometetst/dfladsf'; - $mock = $this->getFileMock($this->png); + public function testFetchFaviconFaviconDotIcoHttpBaseUrl(){ + $url = 'https://google.com/sometetst/dfladsf'; + $mock = $this->getFileMock($this->png); - $callback = $this->getFileMockCallback( - 'https://google.com/favicon.ico', $mock); + $callback = $this->getFileMockCallback( + 'https://google.com/favicon.ico', $mock); - $this->fileFactory->expects($this->any()) - ->method('getFile') - ->will($this->returnCallback($callback)); + $this->fileFactory->expects($this->any()) + ->method('getFile') + ->will($this->returnCallback($callback)); - $favicon = $this->fetcher->fetch($url); + $favicon = $this->fetcher->fetch($url); - $this->assertEquals('https://google.com/favicon.ico', $favicon); - } + $this->assertEquals('https://google.com/favicon.ico', $favicon); + } - private function getFaviconHTML($faviconPath) { - return "<html> - <head> - <link rel=\"shortcut icon\" href=\"$faviconPath\" /> - </head> - <body></body> - </html>"; - } + private function getFaviconHTML($faviconPath) { + return "<html> + <head> + <link rel=\"shortcut icon\" href=\"$faviconPath\" /> + </head> + <body></body> + </html>"; + } - public function testIconAbspathHTTP() { - $faviconPath = "/owncloud/core/img/favicon.png"; - $html = $this->getFaviconHTML($faviconPath); + public function testIconAbspathHTTP() { + $faviconPath = "/owncloud/core/img/favicon.png"; + $html = $this->getFaviconHTML($faviconPath); - $url = 'http://google.com'; - $pageMock = $this->getFileMock($html); - $pngMock = $this->getFileMock($this->png); + $url = 'http://google.com'; + $pageMock = $this->getFileMock($html); + $pngMock = $this->getFileMock($this->png); - $this->fileFactory->expects($this->at(0)) - ->method('getFile') - ->with($this->equalTo('http://google.com')) - ->will($this->returnValue($pageMock)); + $this->fileFactory->expects($this->at(0)) + ->method('getFile') + ->with($this->equalTo('http://google.com')) + ->will($this->returnValue($pageMock)); - $this->fileFactory->expects($this->at(1)) - ->method('getFile') - ->with($this->equalTo( - 'http://google.com/owncloud/core/img/favicon.png')) - ->will($this->returnValue($pngMock)); + $this->fileFactory->expects($this->at(1)) + ->method('getFile') + ->with($this->equalTo( + 'http://google.com/owncloud/core/img/favicon.png')) + ->will($this->returnValue($pngMock)); - $favicon = $this->fetcher->fetch($url); + $favicon = $this->fetcher->fetch($url); - $this->assertEquals('http://google.com/owncloud/core/img/favicon.png', $favicon); - } + $this->assertEquals('http://google.com/owncloud/core/img/favicon.png', $favicon); + } - public function testEmptyFilePathDoesNotOpenFile() { - $url = ''; + public function testEmptyFilePathDoesNotOpenFile() { + $url = ''; - $this->fileFactory->expects($this->never()) - ->method('getFile'); + $this->fileFactory->expects($this->never()) + ->method('getFile'); - $this->fetcher->fetch($url); - } + $this->fetcher->fetch($url); + } - public function testInvalidHostnameDoesNotOpenFile() { - $url = "a.b_c.de"; + public function testInvalidHostnameDoesNotOpenFile() { + $url = "a.b_c.de"; - $this->fileFactory->expects($this->never()) - ->method('getFile'); + $this->fileFactory->expects($this->never()) + ->method('getFile'); - $this->fetcher->fetch($url); - } + $this->fetcher->fetch($url); + } - public function testInvalidHostnameDoesNotOpenFileHttp() { - $url = "http://a.b_c.de"; + public function testInvalidHostnameDoesNotOpenFileHttp() { + $url = "http://a.b_c.de"; - $this->fileFactory->expects($this->never()) - ->method('getFile'); + $this->fileFactory->expects($this->never()) + ->method('getFile'); - $this->fetcher->fetch($url); - } + $this->fetcher->fetch($url); + } } diff --git a/tests/unit/utility/OPMLExporterTest.php b/tests/unit/utility/OPMLExporterTest.php index fe7b142e8..5d6f849fb 100644 --- a/tests/unit/utility/OPMLExporterTest.php +++ b/tests/unit/utility/OPMLExporterTest.php @@ -19,92 +19,92 @@ use \OCA\News\Db\Feed; class OPMLExporterTest extends \PHPUnit_Framework_TestCase { - private $exporter; - private $feed1; - private $feed2; - - protected function setUp() { - $this->exporter = new OPMLExporter(); - $this->folder1 = new Folder(); - $this->folder1->setId(3); - $this->folder1->setParentId(0); - $this->folder1->setName('Örgendwas'); - $this->folder2 = new Folder(); - $this->folder2->setId(1); - $this->folder2->setParentId(3); - $this->folder2->setName('a ergendwas'); - $this->feed1 = new Feed(); - $this->feed1->setUrl('url 1'); - $this->feed1->setTitle('tötel'); - $this->feed1->setFolderId(0); - $this->feed2 = new Feed(); - $this->feed2->setUrl('url'); - $this->feed2->setTitle('ttel df'); - $this->feed2->setLink('goooooogel'); - $this->feed2->setFolderId(1); - } - - - private function getAttribute($item, $name) { - // used to fix scrutinizer errors - if ($item instanceof \DOMElement) { - return $item->getAttribute($name); - } else { - return null; - } - } - - - public function testBuildEmpty(){ - $result = $this->exporter->build([], []); - $xpath = new \DOMXpath($result); - - $this->assertEquals(0, $xpath->query('//outline')->length); - } - - - public function testBuildReturnsFolders() { - $result = $this->exporter->build([$this->folder1, $this->folder2], []); - $xpath = new \DOMXpath($result); - $elems = $xpath->query('/opml/body/outline'); - - $this->assertEquals(2, $elems->length); - $this->assertEquals($this->folder1->getName(), $this->getAttribute($elems->item(0), 'title')); - $this->assertEquals($this->folder1->getName(), $this->getAttribute($elems->item(0), 'text')); - $this->assertEquals($this->folder2->getName(), $this->getAttribute($elems->item(1), 'title')); - $this->assertEquals($this->folder2->getName(), $this->getAttribute($elems->item(1), 'text')); - } - - - public function testBuildReturnsOnlyOneFeedIfParentFolderNotThere() { - $result = $this->exporter->build([], [$this->feed1, $this->feed2]); - $xpath = new \DOMXpath($result); - $elems = $xpath->query('//outline'); - - $this->assertEquals(1, $elems->length); - $this->assertEquals($this->feed1->getTitle(), $this->getAttribute($elems->item(0), 'title')); - $this->assertEquals($this->feed1->getTitle(), $this->getAttribute($elems->item(0), 'text')); - $this->assertEquals($this->feed1->getUrl(), $this->getAttribute($elems->item(0), 'xmlUrl')); - $this->assertEquals('', $this->getAttribute($elems->item(0), 'htmlUrl')); - } - - - public function testBuildReturnsFeedsAndFolders() { - $result = $this->exporter->build( - [$this->folder1, $this->folder2], - [$this->feed1, $this->feed2] - ); - $xpath = new \DOMXpath($result); - $elems = $xpath->query('/opml/body/outline'); - - $this->assertEquals(3, $elems->length); - - - $this->assertEquals($this->folder1->getName(), $this->getAttribute($elems->item(0), 'title')); - $this->assertEquals($this->folder2->getName(), $this->getAttribute($elems->item(1), 'text')); - $this->assertEquals($this->feed1->getUrl(), $this->getAttribute($elems->item(2), 'xmlUrl')); - $this->assertEquals($this->feed2->getLink(), $this->getAttribute($elems->item(1)->childNodes->item(0), 'htmlUrl')); - } + private $exporter; + private $feed1; + private $feed2; + + protected function setUp() { + $this->exporter = new OPMLExporter(); + $this->folder1 = new Folder(); + $this->folder1->setId(3); + $this->folder1->setParentId(0); + $this->folder1->setName('Örgendwas'); + $this->folder2 = new Folder(); + $this->folder2->setId(1); + $this->folder2->setParentId(3); + $this->folder2->setName('a ergendwas'); + $this->feed1 = new Feed(); + $this->feed1->setUrl('url 1'); + $this->feed1->setTitle('tötel'); + $this->feed1->setFolderId(0); + $this->feed2 = new Feed(); + $this->feed2->setUrl('url'); + $this->feed2->setTitle('ttel df'); + $this->feed2->setLink('goooooogel'); + $this->feed2->setFolderId(1); + } + + + private function getAttribute($item, $name) { + // used to fix scrutinizer errors + if ($item instanceof \DOMElement) { + return $item->getAttribute($name); + } else { + return null; + } + } + + + public function testBuildEmpty(){ + $result = $this->exporter->build([], []); + $xpath = new \DOMXpath($result); + + $this->assertEquals(0, $xpath->query('//outline')->length); + } + + + public function testBuildReturnsFolders() { + $result = $this->exporter->build([$this->folder1, $this->folder2], []); + $xpath = new \DOMXpath($result); + $elems = $xpath->query('/opml/body/outline'); + + $this->assertEquals(2, $elems->length); + $this->assertEquals($this->folder1->getName(), $this->getAttribute($elems->item(0), 'title')); + $this->assertEquals($this->folder1->getName(), $this->getAttribute($elems->item(0), 'text')); + $this->assertEquals($this->folder2->getName(), $this->getAttribute($elems->item(1), 'title')); + $this->assertEquals($this->folder2->getName(), $this->getAttribute($elems->item(1), 'text')); + } + + + public function testBuildReturnsOnlyOneFeedIfParentFolderNotThere() { + $result = $this->exporter->build([], [$this->feed1, $this->feed2]); + $xpath = new \DOMXpath($result); + $elems = $xpath->query('//outline'); + + $this->assertEquals(1, $elems->length); + $this->assertEquals($this->feed1->getTitle(), $this->getAttribute($elems->item(0), 'title')); + $this->assertEquals($this->feed1->getTitle(), $this->getAttribute($elems->item(0), 'text')); + $this->assertEquals($this->feed1->getUrl(), $this->getAttribute($elems->item(0), 'xmlUrl')); + $this->assertEquals('', $this->getAttribute($elems->item(0), 'htmlUrl')); + } + + + public function testBuildReturnsFeedsAndFolders() { + $result = $this->exporter->build( + [$this->folder1, $this->folder2], + [$this->feed1, $this->feed2] + ); + $xpath = new \DOMXpath($result); + $elems = $xpath->query('/opml/body/outline'); + + $this->assertEquals(3, $elems->length); + + + $this->assertEquals($this->folder1->getName(), $this->getAttribute($elems->item(0), 'title')); + $this->assertEquals($this->folder2->getName(), $this->getAttribute($elems->item(1), 'text')); + $this->assertEquals($this->feed1->getUrl(), $this->getAttribute($elems->item(2), 'xmlUrl')); + $this->assertEquals($this->feed2->getLink(), $this->getAttribute($elems->item(1)->childNodes->item(0), 'htmlUrl')); + } }
\ No newline at end of file diff --git a/tests/unit/utility/SimplePieAPIFactoryTest.php b/tests/unit/utility/SimplePieAPIFactoryTest.php index a7e7472a0..4f401a72e 100644 --- a/tests/unit/utility/SimplePieAPIFactoryTest.php +++ b/tests/unit/utility/SimplePieAPIFactoryTest.php @@ -17,18 +17,18 @@ namespace OCA\News\Utility; class SimplePieAPIFactoryTest extends \PHPUnit_Framework_TestCase { - public function testGetFile() { - $factory = new SimplePieAPIFactory(); - $file = $factory->getFile('php://input', 10, 5, $headers='headers', - $useragent='flashce', $force_fsockopen=true); - $this->assertTrue($file instanceof \SimplePie_File); - } - - - public function testGetCore() { - $factory = new SimplePieAPIFactory(); - $this->assertTrue($factory->getCore() instanceof \SimplePie); - } + public function testGetFile() { + $factory = new SimplePieAPIFactory(); + $file = $factory->getFile('php://input', 10, 5, $headers='headers', + $useragent='flashce', $force_fsockopen=true); + $this->assertTrue($file instanceof \SimplePie_File); + } + + + public function testGetCore() { + $factory = new SimplePieAPIFactory(); + $this->assertTrue($factory->getCore() instanceof \SimplePie); + } }
\ No newline at end of file diff --git a/tests/unit/utility/UpdaterTest.php b/tests/unit/utility/UpdaterTest.php index 1d61d65bb..edca29f67 100644 --- a/tests/unit/utility/UpdaterTest.php +++ b/tests/unit/utility/UpdaterTest.php @@ -16,47 +16,47 @@ namespace OCA\News\Utility; class UpdaterTest extends \PHPUnit_Framework_TestCase { - private $folderService; - private $feedService; - private $itemService; - private $updater; - - protected function setUp() { - $this->folderService = $this->getMockBuilder( - '\OCA\News\Service\FolderService') - ->disableOriginalConstructor() - ->getMock(); - $this->feedService = $this->getMockBuilder( - '\OCA\News\Service\FeedService') - ->disableOriginalConstructor() - ->getMock(); - $this->itemService = $this->getMockBuilder( - '\OCA\News\Service\ItemService') - ->disableOriginalConstructor() - ->getMock(); - $this->updater = new Updater($this->folderService, - $this->feedService, - $this->itemService); - } - - public function testBeforeUpdate() { - $this->folderService->expects($this->once()) - ->method('purgeDeleted'); - $this->feedService->expects($this->once()) - ->method('purgeDeleted'); - $this->updater->beforeUpdate(); - } - - - public function testAfterUpdate() { - $this->itemService->expects($this->once()) - ->method('autoPurgeOld'); - $this->updater->afterUpdate(); - } - - public function testUpdate() { - $this->feedService->expects($this->once()) - ->method('updateAll'); - $this->updater->update(); - } + private $folderService; + private $feedService; + private $itemService; + private $updater; + + protected function setUp() { + $this->folderService = $this->getMockBuilder( + '\OCA\News\Service\FolderService') + ->disableOriginalConstructor() + ->getMock(); + $this->feedService = $this->getMockBuilder( + '\OCA\News\Service\FeedService') + ->disableOriginalConstructor() + ->getMock(); + $this->itemService = $this->getMockBuilder( + '\OCA\News\Service\ItemService') + ->disableOriginalConstructor() + ->getMock(); + $this->updater = new Updater($this->folderService, + $this->feedService, + $this->itemService); + } + + public function testBeforeUpdate() { + $this->folderService->expects($this->once()) + ->method('purgeDeleted'); + $this->feedService->expects($this->once()) + ->method('purgeDeleted'); + $this->updater->beforeUpdate(); + } + + + public function testAfterUpdate() { + $this->itemService->expects($this->once()) + ->method('autoPurgeOld'); + $this->updater->afterUpdate(); + } + + public function testUpdate() { + $this->feedService->expects($this->once()) + ->method('updateAll'); + $this->updater->update(); + } }
\ No newline at end of file diff --git a/utility/faviconfetcher.php b/utility/faviconfetcher.php index 850a7f576..b837db91c 100644 --- a/utility/faviconfetcher.php +++ b/utility/faviconfetcher.php @@ -18,16 +18,16 @@ use \ZendXml\Security; class FaviconFetcher { - private $apiFactory; + private $apiFactory; - /** - * Inject a factory to build a simplepie file object. This is needed because - * the file object contains logic in its constructor which makes it - * impossible to inject and test - */ - public function __construct(SimplePieAPIFactory $apiFactory) { - $this->apiFactory = $apiFactory; - } + /** + * Inject a factory to build a simplepie file object. This is needed because + * the file object contains logic in its constructor which makes it + * impossible to inject and test + */ + public function __construct(SimplePieAPIFactory $apiFactory) { + $this->apiFactory = $apiFactory; + } /** @@ -36,129 +36,129 @@ class FaviconFetcher { * @param string|null $url the url where to fetch it from * @return null|string */ - public function fetch($url) { - try { - $url = $this->buildURL($url); - } catch (NoValidUrlException $e) { - return null; - } - - $faviconUrl = $this->extractFromPage($url); - - // check the url for a valid image - if($faviconUrl && $this->isImage($faviconUrl)) { - return $faviconUrl; - } elseif ($url) { - $base = new \Net_URL2($url); - $faviconUrl = (string) $base->resolve('/favicon.ico'); - - if($this->isImage($faviconUrl)) { - return $faviconUrl; - } - } - - return null; - } - - /** - * Get the attribute if its a DOMElement, otherwise return null - */ - private function getAttribute($item, $name) { - // used to fix scrutinizer errors - if ($item instanceof \DOMElement) { - return $item->getAttribute($name); - } else { - return null; - } - } - - - /** - * Tries to get a favicon from a page - * @param string $url the url to the page - * @return string the full url to the page - */ - protected function extractFromPage($url) { - if(!$url) { - return null; - } - - $file = $this->getFile($url); + public function fetch($url) { + try { + $url = $this->buildURL($url); + } catch (NoValidUrlException $e) { + return null; + } + + $faviconUrl = $this->extractFromPage($url); + + // check the url for a valid image + if($faviconUrl && $this->isImage($faviconUrl)) { + return $faviconUrl; + } elseif ($url) { + $base = new \Net_URL2($url); + $faviconUrl = (string) $base->resolve('/favicon.ico'); + + if($this->isImage($faviconUrl)) { + return $faviconUrl; + } + } + + return null; + } + + /** + * Get the attribute if its a DOMElement, otherwise return null + */ + private function getAttribute($item, $name) { + // used to fix scrutinizer errors + if ($item instanceof \DOMElement) { + return $item->getAttribute($name); + } else { + return null; + } + } + + + /** + * Tries to get a favicon from a page + * @param string $url the url to the page + * @return string the full url to the page + */ + protected function extractFromPage($url) { + if(!$url) { + return null; + } + + $file = $this->getFile($url); /** @noinspection PhpUndefinedFieldInspection */ if($file->body !== '') { - $dom = new \DOMDocument(); + $dom = new \DOMDocument(); - Security::scan($file->body, $dom, function ($xml, $dom) { - return @$dom->loadHTML($xml, LIBXML_NONET); - }); + Security::scan($file->body, $dom, function ($xml, $dom) { + return @$dom->loadHTML($xml, LIBXML_NONET); + }); - if($dom) { - $xpath = new \DOMXpath($dom); - $elements = $xpath->query("//link[contains(@rel, 'icon')]"); + if($dom) { + $xpath = new \DOMXpath($dom); + $elements = $xpath->query("//link[contains(@rel, 'icon')]"); - if ($elements->length > 0) { + if ($elements->length > 0) { /** @noinspection PhpUndefinedMethodInspection */ $iconPath = $this->getAttribute($elements->item(0), 'href'); $base = new \Net_URL2($url); - $absPath = (string) $base->resolve($iconPath, $url); - return $absPath; - } - } - } + $absPath = (string) $base->resolve($iconPath, $url); + return $absPath; + } + } + } return null; - } + } - private function getFile($url) { - return $this->apiFactory->getFile( - $url, 10, 5, null, 'Mozilla/5.0 AppleWebKit' - ); - } + private function getFile($url) { + return $this->apiFactory->getFile( + $url, 10, 5, null, 'Mozilla/5.0 AppleWebKit' + ); + } - /** - * Test if the file is an image - * @param string $url the url to the file - * @return bool true if image - */ - protected function isImage($url) { - // check for empty urls - if(!$url) { - return false; - } + /** + * Test if the file is an image + * @param string $url the url to the file + * @return bool true if image + */ + protected function isImage($url) { + // check for empty urls + if(!$url) { + return false; + } - $file = $this->getFile($url); + $file = $this->getFile($url); /** @noinspection PhpParamsInspection */ $sniffer = new \SimplePie_Content_Type_Sniffer($file); - return $sniffer->image() !== false; - } - - - /** - * Get HTTP or HTTPS addresses from an incomplete URL - * @param string $url the url that should be built - * @return string a string containing the http or https address - * @throws NoValidUrlException when no valid url can be returned - */ - protected function buildURL($url) { - // trim the right / from the url - $url = trim($url); - $url = rtrim($url, '/'); - - // check for http:// or https:// and validate URL - if (strpos($url, 'http://') === 0 || strpos($url, 'https://') === 0) { - if (filter_var($url, FILTER_VALIDATE_URL)) { - return $url; - } - } elseif (filter_var("http://" . $url, FILTER_VALIDATE_URL)) { - // maybe $url was something like www.example.com - return 'http://' . $url; - } - - // no valid URL was passed in or could be built from $url - throw new NoValidUrlException(); - } + return $sniffer->image() !== false; + } + + + /** + * Get HTTP or HTTPS addresses from an incomplete URL + * @param string $url the url that should be built + * @return string a string containing the http or https address + * @throws NoValidUrlException when no valid url can be returned + */ + protected function buildURL($url) { + // trim the right / from the url + $url = trim($url); + $url = rtrim($url, '/'); + + // check for http:// or https:// and validate URL + if (strpos($url, 'http://') === 0 || strpos($url, 'https://') === 0) { + if (filter_var($url, FILTER_VALIDATE_URL)) { + return $url; + } + } elseif (filter_var("http://" . $url, FILTER_VALIDATE_URL)) { + // maybe $url was something like www.example.com + return 'http://' . $url; + } + + // no valid URL was passed in or could be built from $url + throw new NoValidUrlException(); + } } diff --git a/utility/opmlexporter.php b/utility/opmlexporter.php index 0efaba9b8..d786c0c6f 100644 --- a/utility/opmlexporter.php +++ b/utility/opmlexporter.php @@ -25,66 +25,66 @@ class OPMLExporter { * @param \OCA\News\Db\Feed[] $feeds * @return \DomDocument the document */ - public function build($folders, $feeds){ - $document = new \DomDocument('1.0', 'UTF-8'); - $document->formatOutput = true; - - $root = $document->createElement('opml'); - $root->setAttribute('version', '2.0'); - - // head - $head = $document->createElement('head'); - - $title = $document->createElement('title', 'Subscriptions'); - $head->appendChild($title); - - $root->appendChild($head); - - // body - $body = $document->createElement('body'); - - // feeds with folders - foreach($folders as $folder) { - $folderOutline = $document->createElement('outline'); - $folderOutline->setAttribute('title', $folder->getName()); - $folderOutline->setAttribute('text', $folder->getName()); - - // feeds in folders - foreach ($feeds as $feed) { - if ($feed->getFolderId() === $folder->getId()) { - $feedOutline = $this->createFeedOutline($feed, $document); - $folderOutline->appendChild($feedOutline); - } - } - - $body->appendChild($folderOutline); - } - - // feeds without folders - foreach ($feeds as $feed) { - if ($feed->getFolderId() === 0) { - $feedOutline = $this->createFeedOutline($feed, $document); - $body->appendChild($feedOutline); - } - } - - $root->appendChild($body); - - $document->appendChild($root); - - return $document; - } - - - protected function createFeedOutline($feed, $document) { - $feedOutline = $document->createElement('outline'); - $feedOutline->setAttribute('title', $feed->getTitle()); - $feedOutline->setAttribute('text', $feed->getTitle()); - $feedOutline->setAttribute('type', 'rss'); - $feedOutline->setAttribute('xmlUrl', $feed->getUrl()); - $feedOutline->setAttribute('htmlUrl', $feed->getLink()); - return $feedOutline; - } + public function build($folders, $feeds){ + $document = new \DomDocument('1.0', 'UTF-8'); + $document->formatOutput = true; + + $root = $document->createElement('opml'); + $root->setAttribute('version', '2.0'); + + // head + $head = $document->createElement('head'); + + $title = $document->createElement('title', 'Subscriptions'); + $head->appendChild($title); + + $root->appendChild($head); + + // body + $body = $document->createElement('body'); + + // feeds with folders + foreach($folders as $folder) { + $folderOutline = $document->createElement('outline'); + $folderOutline->setAttribute('title', $folder->getName()); + $folderOutline->setAttribute('text', $folder->getName()); + + // feeds in folders + foreach ($feeds as $feed) { + if ($feed->getFolderId() === $folder->getId()) { + $feedOutline = $this->createFeedOutline($feed, $document); + $folderOutline->appendChild($feedOutline); + } + } + + $body->appendChild($folderOutline); + } + + // feeds without folders + foreach ($feeds as $feed) { + if ($feed->getFolderId() === 0) { + $feedOutline = $this->createFeedOutline($feed, $document); + $body->appendChild($feedOutline); + } + } + + $root->appendChild($body); + + $document->appendChild($root); + + return $document; + } + + + protected function createFeedOutline($feed, $document) { + $feedOutline = $document->createElement('outline'); + $feedOutline->setAttribute('title', $feed->getTitle()); + $feedOutline->setAttribute('text', $feed->getTitle()); + $feedOutline->setAttribute('type', 'rss'); + $feedOutline->setAttribute('xmlUrl', $feed->getUrl()); + $feedOutline->setAttribute('htmlUrl', $feed->getLink()); + return $feedOutline; + } } diff --git a/utility/simplepieapifactory.php b/utility/simplepieapifactory.php index 0e9326ba8..92cbe18f3 100644 --- a/utility/simplepieapifactory.php +++ b/utility/simplepieapifactory.php @@ -30,24 +30,24 @@ class SimplePieAPIFactory { * @param bool $force_fsockopen * @return \SimplePie_File a new object */ - public function getFile($url, $timeout=10, $redirects=5, $headers=null, - $useragent=null, $force_fsockopen=false) { - - return new \SimplePie_File($url, $timeout, $redirects, $headers, - $useragent, $force_fsockopen); - } - - - /** - * Returns a new instance of a SimplePie_Core() object. This is needed - * because the class relies on external dependencies which are not passed - * in via the constructor and thus making it nearly impossible to unit test - * code that uses this class - * @return \SimplePie_Core instance - */ - public function getCore() { - return new \SimplePie(); - } + public function getFile($url, $timeout=10, $redirects=5, $headers=null, + $useragent=null, $force_fsockopen=false) { + + return new \SimplePie_File($url, $timeout, $redirects, $headers, + $useragent, $force_fsockopen); + } + + + /** + * Returns a new instance of a SimplePie_Core() object. This is needed + * because the class relies on external dependencies which are not passed + * in via the constructor and thus making it nearly impossible to unit test + * code that uses this class + * @return \SimplePie_Core instance + */ + public function getCore() { + return new \SimplePie(); + } }
\ No newline at end of file diff --git a/utility/updater.php b/utility/updater.php index 6c4ceae9f..a6f8dc28a 100644 --- a/utility/updater.php +++ b/utility/updater.php @@ -22,33 +22,33 @@ use \OCA\News\Service\ItemService; class Updater { - private $folderService; - private $feedService; - private $itemService; + private $folderService; + private $feedService; + private $itemService; - public function __construct(FolderService $folderService, - FeedService $feedService, - ItemService $itemService) { - $this->folderService = $folderService; - $this->feedService = $feedService; - $this->itemService = $itemService; - } + public function __construct(FolderService $folderService, + FeedService $feedService, + ItemService $itemService) { + $this->folderService = $folderService; + $this->feedService = $feedService; + $this->itemService = $itemService; + } - public function beforeUpdate() { - $this->folderService->purgeDeleted(); - $this->feedService->purgeDeleted(); - } + public function beforeUpdate() { + $this->folderService->purgeDeleted(); + $this->feedService->purgeDeleted(); + } - public function update() { - $this->feedService->updateAll(); - } + public function update() { + $this->feedService->updateAll(); + } - public function afterUpdate() { - $this->itemService->autoPurgeOld(); - } + public function afterUpdate() { + $this->itemService->autoPurgeOld(); + } }
\ No newline at end of file |