Frank Kleine, 1&1 Internet AG. vfsstream. A better approach for file system dependent tests



Similar documents
Unit and Functional Testing for the ios Platform. Christopher M. Judd

Dove User Guide Copyright Virgil Trasca

Safewhere*Identify 3.4. Release Notes

PHP Integration Kit. Version User Guide

Web development... the server side (of the force)

A Tour of Silex and Symfony Components. Robert

NSA-220. Support Notes. (Network Storage Appliance) ZyXEL Storage

Setting up the integration between Oracle Social Engagement & Monitoring Cloud Service and Oracle RightNow Cloud Service

mypro Installation and Handling Manual Version: 7

SQL Server 2008 R2 Express Edition Installation Guide

OpenLogin: PTA, SAML, and OAuth/OpenID

Automated Offsite Backup with rdiff-backup

Licensed for viewing only. Printing is prohibited. For hard copies, please purchase from

Hadoop Shell Commands

Hadoop Shell Commands

Magento Search Extension TECHNICAL DOCUMENTATION

How to print or upgrade using the FTP protocol.

X-POS GUIDE. v3.4 INSTALLATION SmartOSC and X-POS

CONFIGURING VIRTUAL TERMINAL: This is the screen you will see when you first open Virtual Terminal

IBM Redistribute Big SQL v4.x Storage Paths IBM. Redistribute Big SQL v4.x Storage Paths

Setting Up an AudioCodes MP-114

Setting Up the Mercent Marketplace Price Optimizer Extension

Troubleshooting PHP Issues with Zend Server Code Tracing

X644e, X646e. User s Guide. January 2006

New Relic & JMeter - Perfect Performance Testing

Everything you ever wanted to know about Drupal 8*

HP Universal Print Driver Series for Windows Active Directory Administrator Template White Paper

PHPUnit Manual. Sebastian Bergmann

IceWarp to IceWarp Server Migration

Cloud Services. Sharepoint. Admin Quick Start Guide

NAStorage. Administrator Guide. Security Policy Of NAStorage Under UNIX/LINUX Environment

Unit objectives IBM Power Systems

Here is a quick diagram of the ULV SSO/Sync Application. Number 3 is what we deal with in this document.

Hardened Plone. Making Your Plone Site Even More Secure. Presented by: Nathan Van Gheem

CSE331: Introduction to Networks and Security. Lecture 12 Fall 2006

Installing Magento Extensions

Setting up DCOM for Windows XP. Research

Getting Started with Zoom

Web Server using Apache. Heng Sovannarith

Installing an open source version of MateCat

Application Note: Cisco Integration with Onsight Connect

php-crypto-params Documentation

Using the Adventist Framework with your netadventist Site

Setting up the local FTP server

EXPOLeads Connect User Guide

A guide to https and Secure Sockets Layer in SharePoint Release 1.0

At the most basic level you need two things, namely: You need an IMAP account and you need an authorized source.

SERVICE MENU USER GUIDE

HTG XROADS NETWORKS. Network Appliance How To Guide: EdgeDNS. How To Guide

by

CEFNS Web Hosting a Guide for CS212

Customer Tips. Xerox Network Scanning HTTP/HTTPS Configuration using Microsoft IIS. for the user. Purpose. Background

Integrating SalesForce with SharePoint 2007 via the Business Data Catalog

Webapps Vulnerability Report

A. Hot-Standby mode and Active-Standby mode in High Availability

How to Upgrade the Firmware of a Brother Printer/Print Server

Introduction to PhPCollab

v Devolutions inc.

App Building Guidelines

Quick Guide #3G: Philips MRx Configuration and Operation with Rosetta- DS (Bluetooth Connection)

Installation and Running of RADR

Installing Booked scheduler on CentOS 6.5

The BackTrack Successor

1. Scope of Service. 1.1 About Boxcryptor Classic

DDNS Management System User Manual V1.0

WebSphere Commerce V7 Feature Pack 3

FioranoMQ 9. High Availability Guide

Google Apps and Open Directory. Randy Saeks

Basics Series-4004 Database Manager and Import Version 9.0

TESTING WITH JUNIT. Lab 3 : Testing

Package TSfame. February 15, 2013

INSTALLATION GUIDE VERSION

How do I Install and Configure MS Remote Desktop for the Haas Terminal Server on my Mac?

Jive Connects for Microsoft SharePoint: Troubleshooting Tips

ENABLING RPC OVER HTTPS CONNECTIONS TO M-FILES SERVER

Using Red Hat Enterprise Linux with Georgia Tech's RHN Satellite Server Installing Red Hat Enterprise Linux

XCloner Official User Manual

How To Set Up A Backupassist For An Raspberry Netbook With A Data Host On A Nsync Server On A Usb 2 (Qnap) On A Netbook (Qnet) On An Usb 2 On A Cdnap (

Intellicus Single Sign-on

List Service Customizing a List. Introduction. Adding an Owner or Moderator. Process Summary Introduction. Adding an Owner or Moderator

NetClient software user manual

Configuring -to-Feed in MangoApps

Project Online: Manage External Sharing

Log Blindspots: A review of cases where System Logs are insufficient

Bazaarvoice for Magento Extension Implementation Guide v6.3.4

Fermilab Central Web Service Site Owner User Manual. DocDB: CS-doc-5372

Introduction. Setting Up the Scanner. Performing Verification Sequence

Paper Airplanes & Scientific Methods

How do I Install and Configure MS Remote Desktop for the Haas Terminal Server on my Mac?

Kotlin for Android Developers

ivms-4200 Client Software Quick Start Guide

Transcription:

Frank Kleine, 1&1 Internet AG vfsstream A better approach for file system dependent tests

T-Shirt available at zazzle.de (no, I'm not paid for this)

(Obligatory Zen-Style image)

AND NOW FOR SOMETHING COMPLETELY DIFFERENT

Unit tests I assume you do unit tests Testing file system related functions/methods can be hard setup(), teardown(), and unusual scenarios

Basic example: a method to test class Example { public function construct($id) { $this->id = $id; public function setdirectory($dir) { $this->dir = $dir. '/'. $this->id; if (file_exists($this->dir) === false) { mkdir($this->dir, 0700, true);

Basic example: traditional test $DIR = dirname( FILE ); public function setup() { if (file_exists($dir. '/id')) { rmdir($dir. '/id'); public function teardown() { if (file_exists($dir. '/id')) { rmdir($dir. '/id'); public function testdirectoryiscreated() { $example = new Example('id'); $this->assertfalse(file_exists($dir. '/id')); $example->setdirectory($dir); $this->asserttrue(file_exists($dir. '/id'));

Basic example: vfsstream test public function setup() { vfsstreamwrapper::register(); $root = new vfsstreamdirectory('adir'); vfsstreamwrapper::setroot($root); public function testdirectoryiscreated() { $url = vfsstream::url('adir/id'); $example = new Example('id'); $this->assertfalse(file_exists($url)); $example->setdirectory(vfsstream::url('adir')); $this->asserttrue(file_exists($url));

Advantages Cleaner tests Nothing happens on disc, all operations are memory only More control over file system environment

How does this work? PHP stream wrapper Allows you to invent your own url protocol Whenever a vfs:// url is given to a file system function PHP calls back the registered stream implementation for this protocol Works well for most of file system functions

What does not work? File system functions working with pure file names only: realpath() touch() File system function without stream wrapper support: chmod() chown() chgrp() ext/zip does not support userland stream wrappers

Example with file mode class Example { public function construct($id, $mode = 0700) { $this->id = $id; $this->mode = $mode; public function setdirectory($dir) { $this->dir = $dir. '/'. $this->id; if (file_exists($this->dir) === false) { mkdir($this->directory, $this->mode, true);

Example with file mode, cont. $DIR = dirname( FILE ); public function testdirdefaultfilepermissions() { $example = new Example('id'); $example->setdirectory($dir); if (DIRECTORY_SEPARATOR === '\\') { $this->assertequals(40777, decoct(fileperms($dir. '/id'))); else { $this->assertequals(40700, decoct(fileperms($dir. '/id'))); public function testdirdifferentfilepermissions() { $example = new Example('id', 0755); $example->setdirectory($dir); if (DIRECTORY_SEPARATOR === '\\') { $this->assertequals(40777, decoct(fileperms($dir. '/id'))); else { $this->assertequals(40755, decoct(fileperms($dir. '/id')));

Example with file mode, cont. public function setup() { vfsstreamwrapper::register(); $this->root = new vfsstreamdirectory('adir'); vfsstreamwrapper::setroot($this->root); public function testdirdefaultfilepermissions() { $example = new Example('id'); $example->setdirectory(vfsstream::url('adir')); $this->assertequals(0700, $this->root->getchild('id')->getpermissions()); public function testdirdifferentfilepermissions() { $example = new Example('id', 0755); $example->setdirectory(vfsstream::url('adir')); $this->assertequals(0755, $this->root->getchild('id')->getpermissions());

Advantages Independent of operating system a test is running on Intentions of test cases become more clear Easier to understand

Different config files class RssFeedController { public function construct($configpath) { $feeds = Properties::fromFile($configPath. '/rss-feeds.ini') ->getsection('feeds', array()); if (count($feeds) === 0) { throw new ConfigurationException(); $this->routename = valuefromrequest(); if (null === $this->routename) { // no special feed requested, use first configured one reset($feeds); $this->routename = key($feeds);

Different config files, cont. public function setup() { vfsstreamwrapper::register(); $root = new vfsstreamdirectory('config'); vfsstreamwrapper::setroot($root); $this->configfile = vfsstream::newfile('rss-feeds.ini') ->at($root); /** * @test * @expectedexception FileNotFoundException **/ public function loadfeedsfailsiffeedconfigfiledoesnotexist() { $example = new RssFeedController(vfsStream::url('doesNotExist'));

Different config files, cont. 2 /** * @test * @expectedexception ConfigurationException **/ public function nofeedssectionconfiguredthrowsexception() { $this->configfile->setcontent(''); $example = new RssFeedController(vfsStream::url('config'));

Different config files, cont. 3 /** * @test * @expectedexception ConfigurationException **/ public function nofeedsconfiguredthrowsexception() { $this->configfile->setcontent('[feeds]'); $example = new RssFeedController(vfsStream::url('config'));

Different config files, cont. 4 /** * @test **/ public function selectsfirstfeedifnonegivenwithrequestvalue() { $this->configfile->setcontent('[feeds]\n default = "org::stubbles::test::xml::rss::defaultfeed"'); $example = new RssFeedController(vfsStream::url('config')); // assertions that the default feed was selected

Different config files, cont. 5 /** * @test **/ public function selectsotherfeedbasedonrequestvalue() { $this->configfile->setcontent("[feeds]\n default = \"org::stubbles::test::xml::rss::defaultfeed\"\n other = \"org::stubbles::test::xml::rss::otherfeed\"\n"); $example = new RssFeedController(vfsStream::url('config')); // assertions that the other feed was selected

Advantages Concentrate on the test, not on config files Everything is in the test, no test related information in external files Simple to set up Create different test scenarios on the fly

vfsstream 0.7.0 Considers file permissions correctly Allows to write tests to check how your application responds to incorrect file permissions To be released in the next days Probably buggy :->

File permissions class Example { public function writeconfig($config, $configfile) { file_put_contents($configfile, serialize($config));

File permissions, the tests /** * @test */ public function normaltest() { vfsstreamwrapper::setroot(vfsstream::newdirectory('exampledir')); $example = new FilePermissionsExample(); $example->writeconfig(array('foo' => 'bar'), vfsstream::url('exampledir/writable.ini') ); // assertions here

File permissions, another test /** * @test */ public function directorynotwritable() { vfsstreamwrapper::setroot( vfsstream::newdirectory('exampledir', 0444) ); $example = new FilePermissionsExample(); $example->writeconfig(array('foo' => 'bar'), vfsstream::url('exampledir/config.ini') );

Advantages Allows simple tests you would not do otherwise because they are too hard to do Helps to find probably buggy code or code which behaves not user friendly Makes your application more failsafe

Ressources http://vfs.bovigo.org/ http://php.net/class.streamwrapper Twitter @bovigo @mikey179