diff --git a/app/Http/Controllers/ReportController.php b/app/Http/Controllers/ReportController.php index 9abe90b45cbc..a09ab46e9595 100644 --- a/app/Http/Controllers/ReportController.php +++ b/app/Http/Controllers/ReportController.php @@ -61,14 +61,6 @@ class ReportController extends BaseController $enableChart = true; } - $displayData = []; - $exportData = []; - $reportTotals = [ - 'amount' => [], - 'balance' => [], - 'paid' => [], - ]; - $dateTypes = [ 'DAYOFYEAR' => 'Daily', 'WEEK' => 'Weekly', @@ -183,7 +175,7 @@ class ReportController extends BaseController if ($entityType == ENTITY_INVOICE) { $labelFormat = $groupBy == 'DAYOFYEAR' ? 'j' : ($groupBy == 'WEEK' ? 'W' : 'F'); - $label = $d->format($labelFormat); + $label = $d->format($labelFormat); $labels[] = $label; } } @@ -256,6 +248,14 @@ class ReportController extends BaseController $lastInvoiceId = null; $sameAsLast = false; + $displayData = []; + + $exportData = []; + $reportTotals = [ + 'amount' => [], + 'balance' => [], + 'paid' => [], + ]; foreach ($data as $record) { $sameAsLast = ($lastInvoiceId == $record->invoice_public_id); diff --git a/readme.md b/readme.md index 20580dd77839..29abc1e737e6 100644 --- a/readme.md +++ b/readme.md @@ -18,7 +18,7 @@ If you'd like to use our code to sell your own invoicing app email us for detail ### Features * Built using Laravel 5 * Live PDF generation using [pdfmake](http://pdfmake.org/) -* Integrates with 30+ payment providers with [OmniPay](https://github.com/thephpleague/omnipay) +* Integrates with 50+ payment providers with [OmniPay](https://github.com/thephpleague/omnipay) * Recurring invoices with auto-billing * Tasks with time-tracking * Multi-user/multi-company support diff --git a/resources/lang/da/texts.php b/resources/lang/da/texts.php index 55af0a5ad7f5..6fa11cd5d2a6 100644 --- a/resources/lang/da/texts.php +++ b/resources/lang/da/texts.php @@ -909,5 +909,14 @@ 'archived' => 'Archived', 'untitled_account' => 'Untitled Company', + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', + ); diff --git a/resources/lang/de/texts.php b/resources/lang/de/texts.php index 26cea549d170..85c3a81c55b2 100644 --- a/resources/lang/de/texts.php +++ b/resources/lang/de/texts.php @@ -911,4 +911,13 @@ return array( 'archived' => 'Archived', 'untitled_account' => 'Untitled Company', + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', + ); diff --git a/resources/lang/es/texts.php b/resources/lang/es/texts.php index a9f91b1394b0..0fb7664d7d67 100644 --- a/resources/lang/es/texts.php +++ b/resources/lang/es/texts.php @@ -887,5 +887,14 @@ return array( 'archived' => 'Archived', 'untitled_account' => 'Untitled Company', + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', + ); diff --git a/resources/lang/es_ES/texts.php b/resources/lang/es_ES/texts.php index 74c16fb5e8ea..4a6214f10233 100644 --- a/resources/lang/es_ES/texts.php +++ b/resources/lang/es_ES/texts.php @@ -908,4 +908,13 @@ return array( 'archived' => 'Archived', 'untitled_account' => 'Untitled Company', + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', + ); diff --git a/resources/lang/fr/texts.php b/resources/lang/fr/texts.php index 6886d76d7a85..177a1091bd36 100644 --- a/resources/lang/fr/texts.php +++ b/resources/lang/fr/texts.php @@ -901,5 +901,14 @@ return array( 'restored_recurring_invoice' => 'Successfully restored recurring invoice', 'archived' => 'Archivé', 'untitled_account' => 'Société sans nom', + + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', ); diff --git a/resources/lang/fr_CA/texts.php b/resources/lang/fr_CA/texts.php index 0658ff11f552..13d3e367d999 100644 --- a/resources/lang/fr_CA/texts.php +++ b/resources/lang/fr_CA/texts.php @@ -902,4 +902,13 @@ return array( 'archived' => 'Archived', 'untitled_account' => 'Untitled Company', + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', + ); diff --git a/resources/lang/it/texts.php b/resources/lang/it/texts.php index 3f4d458f3412..a35a42cbb2ed 100644 --- a/resources/lang/it/texts.php +++ b/resources/lang/it/texts.php @@ -903,5 +903,14 @@ return array( 'restored_recurring_invoice' => 'Successfully restored recurring invoice', 'archived' => 'Archived', 'untitled_account' => 'Untitled Company', + + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', ); diff --git a/resources/lang/lt/texts.php b/resources/lang/lt/texts.php index 328a5058720c..9aee3cd86e2a 100644 --- a/resources/lang/lt/texts.php +++ b/resources/lang/lt/texts.php @@ -910,6 +910,15 @@ return array( 'restored_recurring_invoice' => 'Successfully restored recurring invoice', 'archived' => 'Archived', 'untitled_account' => 'Untitled Company', + + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', ); diff --git a/resources/lang/nb_NO/texts.php b/resources/lang/nb_NO/texts.php index 0db24adf37cd..3c50871fa650 100644 --- a/resources/lang/nb_NO/texts.php +++ b/resources/lang/nb_NO/texts.php @@ -908,5 +908,14 @@ return array( 'restored_recurring_invoice' => 'Suksessfullt gjenopprettet gjentakende faktura', 'archived' => 'Arkivert', 'untitled_account' => 'Selskap Uten Navn', + + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', ); diff --git a/resources/lang/nl/texts.php b/resources/lang/nl/texts.php index 6ab529243a44..7a14e15bce24 100644 --- a/resources/lang/nl/texts.php +++ b/resources/lang/nl/texts.php @@ -903,5 +903,14 @@ return array( 'restored_recurring_invoice' => 'Successfully restored recurring invoice', 'archived' => 'Archived', 'untitled_account' => 'Untitled Company', + + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', ); diff --git a/resources/lang/pt_BR/texts.php b/resources/lang/pt_BR/texts.php index 9c9ff0e3a5a5..7daba486a8d8 100644 --- a/resources/lang/pt_BR/texts.php +++ b/resources/lang/pt_BR/texts.php @@ -904,6 +904,14 @@ return array( 'archived' => 'Arquivado', 'untitled_account' => 'Empresa Sem Nome', - 'before' => 'Antes', + 'before' => 'Antes', 'after' => 'Depois', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', + + ); diff --git a/resources/lang/sv/texts.php b/resources/lang/sv/texts.php index 44bd13b1e030..7401020eb6d7 100644 --- a/resources/lang/sv/texts.php +++ b/resources/lang/sv/texts.php @@ -906,5 +906,14 @@ return array( 'restored_recurring_invoice' => 'Successfully restored recurring invoice', 'archived' => 'Archived', 'untitled_account' => 'Untitled Company', + + 'before' => 'Before', + 'after' => 'After', + 'reset_terms_help' => 'Reset to the default account terms', + 'reset_footer_help' => 'Reset to the default account footer', + 'export_data' => 'Export Data', + 'user' => 'User', + 'country' => 'Country', + 'include' => 'Include', ); diff --git a/resources/views/reports/chart_builder.blade.php b/resources/views/reports/chart_builder.blade.php index 0b4e7fad9f00..159b71b177bd 100644 --- a/resources/views/reports/chart_builder.blade.php +++ b/resources/views/reports/chart_builder.blade.php @@ -161,27 +161,31 @@ $('#action').val(''); } - var ctx = document.getElementById('monthly-reports').getContext('2d'); - var chart = { - labels: {!! json_encode($labels) !!}, - datasets: [ - @foreach ($datasets as $dataset) - { - data: {!! json_encode($dataset['totals']) !!}, - fillColor : "rgba({!! $dataset['colors'] !!},0.5)", - strokeColor : "rgba({!! $dataset['colors'] !!},1)", - }, - @endforeach - ] - } + @if ($enableChart) + var ctx = document.getElementById('monthly-reports').getContext('2d'); + var chart = { + labels: {!! json_encode($labels) !!}, + datasets: [ + @foreach ($datasets as $dataset) + { + data: {!! json_encode($dataset['totals']) !!}, + fillColor : "rgba({!! $dataset['colors'] !!},0.5)", + strokeColor : "rgba({!! $dataset['colors'] !!},1)", + }, + @endforeach + ] + } - var options = { - scaleOverride: true, - scaleSteps: 10, - scaleStepWidth: {!! $scaleStepWidth !!}, - scaleStartValue: 0, - scaleLabel : "<%=value%>", - }; + var options = { + scaleOverride: true, + scaleSteps: 10, + scaleStepWidth: {!! $scaleStepWidth !!}, + scaleStartValue: 0, + scaleLabel : "<%=value%>", + }; + + new Chart(ctx).{!! $chartType !!}(chart, options); + @endif $(function() { $('.start_date .input-group-addon').click(function() { @@ -192,7 +196,6 @@ }); }) - new Chart(ctx).{!! $chartType !!}(chart, options); diff --git a/tests/_support/_generated/AcceptanceTesterActions.php b/tests/_support/_generated/AcceptanceTesterActions.php index 2adc19ca2c5a..94bb9b320601 100644 --- a/tests/_support/_generated/AcceptanceTesterActions.php +++ b/tests/_support/_generated/AcceptanceTesterActions.php @@ -1,4 +1,4 @@ -getScenario()->runStep(new \Codeception\Step\Action('debugWebDriverLogs', func_get_args())); + } + + /** * [!] Method is generated. Documentation taken from corresponding module. * @@ -249,7 +260,6 @@ trait AcceptanceTesterActions * $I->amOnPage('/'); * // opens /register page * $I->amOnPage('/register'); - * ?> * ``` * * @param $page @@ -263,16 +273,31 @@ trait AcceptanceTesterActions /** * [!] Method is generated. Documentation taken from corresponding module. * - * Checks that the current page contains the given string. - * Specify a locator as the second parameter to match a specific region. + * Checks that the current page contains the given string (case insensitive). + * + * You can specify a specific HTML element (via CSS or XPath) as the second + * parameter to only search within that element. * * ``` php * see('Logout'); // I can suppose user is logged in - * $I->see('Sign Up','h1'); // I can suppose it's a signup page - * $I->see('Sign Up','//body/h1'); // with XPath - * ?> + * $I->see('Logout'); // I can suppose user is logged in + * $I->see('Sign Up', 'h1'); // I can suppose it's a signup page + * $I->see('Sign Up', '//body/h1'); // with XPath * ``` + * + * Note that the search is done after stripping all HTML tags from the body, + * so `$I->see('strong')` will return true for strings like: + * + * - `

I am Stronger than thou

` + * - `` + * + * But will *not* be true for strings like: + * + * - `Home` + * - `
Home` + * - `` + * + * For checking the raw source code, use `seeInSource()`. * * @param $text * @param null $selector @@ -285,16 +310,31 @@ trait AcceptanceTesterActions /** * [!] Method is generated. Documentation taken from corresponding module. * - * Checks that the current page contains the given string. - * Specify a locator as the second parameter to match a specific region. + * Checks that the current page contains the given string (case insensitive). + * + * You can specify a specific HTML element (via CSS or XPath) as the second + * parameter to only search within that element. * * ``` php * see('Logout'); // I can suppose user is logged in - * $I->see('Sign Up','h1'); // I can suppose it's a signup page - * $I->see('Sign Up','//body/h1'); // with XPath - * ?> + * $I->see('Logout'); // I can suppose user is logged in + * $I->see('Sign Up', 'h1'); // I can suppose it's a signup page + * $I->see('Sign Up', '//body/h1'); // with XPath * ``` + * + * Note that the search is done after stripping all HTML tags from the body, + * so `$I->see('strong')` will return true for strings like: + * + * - `

I am Stronger than thou

` + * - `` + * + * But will *not* be true for strings like: + * + * - `Home` + * - `
Home` + * - `` + * + * For checking the raw source code, use `seeInSource()`. * * @param $text * @param null $selector @@ -308,16 +348,29 @@ trait AcceptanceTesterActions /** * [!] Method is generated. Documentation taken from corresponding module. * - * Checks that the current page doesn't contain the text specified. + * Checks that the current page doesn't contain the text specified (case insensitive). * Give a locator as the second parameter to match a specific region. * * ```php * dontSee('Login'); // I can suppose user is already logged in - * $I->dontSee('Sign Up','h1'); // I can suppose it's not a signup page - * $I->dontSee('Sign Up','//body/h1'); // with XPath - * ?> + * $I->dontSee('Login'); // I can suppose user is already logged in + * $I->dontSee('Sign Up','h1'); // I can suppose it's not a signup page + * $I->dontSee('Sign Up','//body/h1'); // with XPath * ``` + * + * Note that the search is done after stripping all HTML tags from the body, + * so `$I->dontSee('strong')` will fail on strings like: + * + * - `

I am Stronger than thou

` + * - `` + * + * But will ignore strings like: + * + * - `Home` + * - `
Home` + * - `` + * + * For checking the raw source code, use `seeInSource()`. * * @param $text * @param null $selector @@ -330,16 +383,29 @@ trait AcceptanceTesterActions /** * [!] Method is generated. Documentation taken from corresponding module. * - * Checks that the current page doesn't contain the text specified. + * Checks that the current page doesn't contain the text specified (case insensitive). * Give a locator as the second parameter to match a specific region. * * ```php * dontSee('Login'); // I can suppose user is already logged in - * $I->dontSee('Sign Up','h1'); // I can suppose it's not a signup page - * $I->dontSee('Sign Up','//body/h1'); // with XPath - * ?> + * $I->dontSee('Login'); // I can suppose user is already logged in + * $I->dontSee('Sign Up','h1'); // I can suppose it's not a signup page + * $I->dontSee('Sign Up','//body/h1'); // with XPath * ``` + * + * Note that the search is done after stripping all HTML tags from the body, + * so `$I->dontSee('strong')` will fail on strings like: + * + * - `

I am Stronger than thou

` + * - `` + * + * But will ignore strings like: + * + * - `Home` + * - `
Home` + * - `` + * + * For checking the raw source code, use `seeInSource()`. * * @param $text * @param null $selector @@ -350,6 +416,80 @@ trait AcceptanceTesterActions } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Checks that the current page contains the given string in its + * raw source code. + * + * ``` php + * seeInSource('

Green eggs & ham

'); + * ``` + * + * @param $raw + * Conditional Assertion: Test won't be stopped on fail + * @see \Codeception\Module\WebDriver::seeInSource() + */ + public function canSeeInSource($raw) { + return $this->getScenario()->runStep(new \Codeception\Step\ConditionalAssertion('seeInSource', func_get_args())); + } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Checks that the current page contains the given string in its + * raw source code. + * + * ``` php + * seeInSource('

Green eggs & ham

'); + * ``` + * + * @param $raw + * @see \Codeception\Module\WebDriver::seeInSource() + */ + public function seeInSource($raw) { + return $this->getScenario()->runStep(new \Codeception\Step\Assertion('seeInSource', func_get_args())); + } + + + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Checks that the current page contains the given string in its + * raw source code. + * + * ```php + * dontSeeInSource('

Green eggs & ham

'); + * ``` + * + * @param $raw + * Conditional Assertion: Test won't be stopped on fail + * @see \Codeception\Module\WebDriver::dontSeeInSource() + */ + public function cantSeeInSource($raw) { + return $this->getScenario()->runStep(new \Codeception\Step\ConditionalAssertion('dontSeeInSource', func_get_args())); + } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Checks that the current page contains the given string in its + * raw source code. + * + * ```php + * dontSeeInSource('

Green eggs & ham

'); + * ``` + * + * @param $raw + * @see \Codeception\Module\WebDriver::dontSeeInSource() + */ + public function dontSeeInSource($raw) { + return $this->getScenario()->runStep(new \Codeception\Step\Assertion('dontSeeInSource', func_get_args())); + } + + /** * [!] Method is generated. Documentation taken from corresponding module. * @@ -1999,13 +2139,13 @@ trait AcceptanceTesterActions * ``` * Note that "2" will be the submitted value for the "plan" field, as it is * the selected option. - * + * * Also note that this differs from PhpBrowser, in that * ```'user' => [ 'login' => 'Davert' ]``` is not supported at the moment. * Named array keys *must* be included in the name as above. - * + * * Pair this with seeInFormFields for quick testing magic. - * + * * ``` php * submitForm('#my-form', [ * 'field[]' => 'value', * 'field[]' => 'another value', // 'field[]' is already a defined key * ]); * ``` - * + * * The solution is to pass an array value: - * + * * ```php * // this way both values are submitted * $I->submitForm('#my-form', [ @@ -2528,7 +2668,7 @@ trait AcceptanceTesterActions /** * [!] Method is generated. Documentation taken from corresponding module. * - * Inserts SQL record into database. This record will be erased after the test. + * Inserts an SQL record into a database. This record will be erased after the test. * * ``` php * seeInDatabase * - * Checks if there is no record with such column values in database. + * Asserts that there is no record with the given column values in a database. * Provide table name and column values. * * Example: @@ -2680,7 +2820,7 @@ trait AcceptanceTesterActions * * Effect is opposite to ->seeInDatabase * - * Checks if there is no record with such column values in database. + * Asserts that there is no record with the given column values in a database. * Provide table name and column values. * * Example: diff --git a/tests/_support/_generated/FunctionalTesterActions.php b/tests/_support/_generated/FunctionalTesterActions.php index cffb7b2e0c8b..a3980a806784 100644 --- a/tests/_support/_generated/FunctionalTesterActions.php +++ b/tests/_support/_generated/FunctionalTesterActions.php @@ -1,4 +1,4 @@ -amOnPage('/'); * // opens /register page * $I->amOnPage('/register'); - * ?> * ``` * * @param $page @@ -217,16 +216,31 @@ trait FunctionalTesterActions /** * [!] Method is generated. Documentation taken from corresponding module. * - * Checks that the current page contains the given string. - * Specify a locator as the second parameter to match a specific region. + * Checks that the current page contains the given string (case insensitive). + * + * You can specify a specific HTML element (via CSS or XPath) as the second + * parameter to only search within that element. * * ``` php * see('Logout'); // I can suppose user is logged in - * $I->see('Sign Up','h1'); // I can suppose it's a signup page - * $I->see('Sign Up','//body/h1'); // with XPath - * ?> + * $I->see('Logout'); // I can suppose user is logged in + * $I->see('Sign Up', 'h1'); // I can suppose it's a signup page + * $I->see('Sign Up', '//body/h1'); // with XPath * ``` + * + * Note that the search is done after stripping all HTML tags from the body, + * so `$I->see('strong')` will return true for strings like: + * + * - `

I am Stronger than thou

` + * - `` + * + * But will *not* be true for strings like: + * + * - `Home` + * - `
Home` + * - `` + * + * For checking the raw source code, use `seeInSource()`. * * @param $text * @param null $selector @@ -239,16 +253,31 @@ trait FunctionalTesterActions /** * [!] Method is generated. Documentation taken from corresponding module. * - * Checks that the current page contains the given string. - * Specify a locator as the second parameter to match a specific region. + * Checks that the current page contains the given string (case insensitive). + * + * You can specify a specific HTML element (via CSS or XPath) as the second + * parameter to only search within that element. * * ``` php * see('Logout'); // I can suppose user is logged in - * $I->see('Sign Up','h1'); // I can suppose it's a signup page - * $I->see('Sign Up','//body/h1'); // with XPath - * ?> + * $I->see('Logout'); // I can suppose user is logged in + * $I->see('Sign Up', 'h1'); // I can suppose it's a signup page + * $I->see('Sign Up', '//body/h1'); // with XPath * ``` + * + * Note that the search is done after stripping all HTML tags from the body, + * so `$I->see('strong')` will return true for strings like: + * + * - `

I am Stronger than thou

` + * - `` + * + * But will *not* be true for strings like: + * + * - `Home` + * - `
Home` + * - `` + * + * For checking the raw source code, use `seeInSource()`. * * @param $text * @param null $selector @@ -262,16 +291,29 @@ trait FunctionalTesterActions /** * [!] Method is generated. Documentation taken from corresponding module. * - * Checks that the current page doesn't contain the text specified. + * Checks that the current page doesn't contain the text specified (case insensitive). * Give a locator as the second parameter to match a specific region. * * ```php * dontSee('Login'); // I can suppose user is already logged in - * $I->dontSee('Sign Up','h1'); // I can suppose it's not a signup page - * $I->dontSee('Sign Up','//body/h1'); // with XPath - * ?> + * $I->dontSee('Login'); // I can suppose user is already logged in + * $I->dontSee('Sign Up','h1'); // I can suppose it's not a signup page + * $I->dontSee('Sign Up','//body/h1'); // with XPath * ``` + * + * Note that the search is done after stripping all HTML tags from the body, + * so `$I->dontSee('strong')` will fail on strings like: + * + * - `

I am Stronger than thou

` + * - `` + * + * But will ignore strings like: + * + * - `Home` + * - `
Home` + * - `` + * + * For checking the raw source code, use `seeInSource()`. * * @param $text * @param null $selector @@ -284,16 +326,29 @@ trait FunctionalTesterActions /** * [!] Method is generated. Documentation taken from corresponding module. * - * Checks that the current page doesn't contain the text specified. + * Checks that the current page doesn't contain the text specified (case insensitive). * Give a locator as the second parameter to match a specific region. * * ```php * dontSee('Login'); // I can suppose user is already logged in - * $I->dontSee('Sign Up','h1'); // I can suppose it's not a signup page - * $I->dontSee('Sign Up','//body/h1'); // with XPath - * ?> + * $I->dontSee('Login'); // I can suppose user is already logged in + * $I->dontSee('Sign Up','h1'); // I can suppose it's not a signup page + * $I->dontSee('Sign Up','//body/h1'); // with XPath * ``` + * + * Note that the search is done after stripping all HTML tags from the body, + * so `$I->dontSee('strong')` will fail on strings like: + * + * - `

I am Stronger than thou

` + * - `` + * + * But will ignore strings like: + * + * - `Home` + * - `
Home` + * - `` + * + * For checking the raw source code, use `seeInSource()`. * * @param $text * @param null $selector @@ -304,6 +359,80 @@ trait FunctionalTesterActions } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Checks that the current page contains the given string in its + * raw source code. + * + * ``` php + * seeInSource('

Green eggs & ham

'); + * ``` + * + * @param $raw + * Conditional Assertion: Test won't be stopped on fail + * @see \Codeception\Lib\InnerBrowser::seeInSource() + */ + public function canSeeInSource($raw) { + return $this->getScenario()->runStep(new \Codeception\Step\ConditionalAssertion('seeInSource', func_get_args())); + } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Checks that the current page contains the given string in its + * raw source code. + * + * ``` php + * seeInSource('

Green eggs & ham

'); + * ``` + * + * @param $raw + * @see \Codeception\Lib\InnerBrowser::seeInSource() + */ + public function seeInSource($raw) { + return $this->getScenario()->runStep(new \Codeception\Step\Assertion('seeInSource', func_get_args())); + } + + + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Checks that the current page contains the given string in its + * raw source code. + * + * ```php + * dontSeeInSource('

Green eggs & ham

'); + * ``` + * + * @param $raw + * Conditional Assertion: Test won't be stopped on fail + * @see \Codeception\Lib\InnerBrowser::dontSeeInSource() + */ + public function cantSeeInSource($raw) { + return $this->getScenario()->runStep(new \Codeception\Step\ConditionalAssertion('dontSeeInSource', func_get_args())); + } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Checks that the current page contains the given string in its + * raw source code. + * + * ```php + * dontSeeInSource('

Green eggs & ham

'); + * ``` + * + * @param $raw + * @see \Codeception\Lib\InnerBrowser::dontSeeInSource() + */ + public function dontSeeInSource($raw) { + return $this->getScenario()->runStep(new \Codeception\Step\Assertion('dontSeeInSource', func_get_args())); + } + + /** * [!] Method is generated. Documentation taken from corresponding module. * @@ -1076,13 +1205,25 @@ trait FunctionalTesterActions * Submits the given form on the page, optionally with the given form * values. Give the form fields values as an array. * - * Skipped fields will be filled by their values from the page. + * Although this function can be used as a short-hand version of + * `fillField()`, `selectOption()`, `click()` etc. it has some important + * differences: + * + * * Only field *names* may be used, not CSS/XPath selectors nor field labels + * * If a field is sent to this function that does *not* exist on the page, + * it will silently be added to the HTTP request. This is helpful for testing + * some types of forms, but be aware that you will *not* get an exception + * like you would if you called `fillField()` or `selectOption()` with + * a missing field. + * + * Fields that are not provided will be filled by their values from the page, + * or from any previous calls to `fillField()`, `selectOption()` etc. * You don't need to click the 'Submit' button afterwards. * This command itself triggers the request to form's action. * - * You can optionally specify what button's value to include - * in the request with the last parameter as an alternative to - * explicitly setting its value in the second parameter, as + * You can optionally specify which button's value to include + * in the request with the last parameter (as an alternative to + * explicitly setting its value in the second parameter), as * button values are not otherwise included in the request. * * Examples: @@ -1156,7 +1297,8 @@ trait FunctionalTesterActions * ); * ``` * - * Pair this with seeInFormFields for quick testing magic. + * This function works well when paired with `seeInFormFields()` + * for quickly testing CRUD interfaces and form validation logic. * * ``` php * true, * // ... * ]; - * $I->submitForm('//form[@id=my-form]', $form, 'submitButton'); + * $I->submitForm('#my-form', $form, 'submitButton'); * // $I->amOnPage('/path/to/form-page') may be needed - * $I->seeInFormFields('//form[@id=my-form]', $form); - * ?> + * $I->seeInFormFields('#my-form', $form); * ``` * * Parameter values can be set to arrays for multiple input fields * of the same name, or multi-select combo boxes. For checkboxes, - * either the string value can be used, or boolean values which will + * you can use either the string value or boolean `true`/`false` which will * be replaced by the checkbox's value in the DOM. * * ``` php @@ -1183,7 +1324,7 @@ trait FunctionalTesterActions * 'field1' => 'value', * 'checkbox' => [ * 'value of first checkbox', - * 'value of second checkbox, + * 'value of second checkbox', * ], * 'otherCheckboxes' => [ * true, @@ -1195,27 +1336,29 @@ trait FunctionalTesterActions * 'second option value' * ] * ]); - * ?> * ``` * * Mixing string and boolean values for a checkbox's value is not supported * and may produce unexpected results. * - * Field names ending in "[]" must be passed without the trailing square + * Field names ending in `[]` must be passed without the trailing square * bracket characters, and must contain an array for its value. This allows * submitting multiple values with the same name, consider: * * ```php + * submitForm('#my-form', [ * 'field[]' => 'value', - * 'field[]' => 'another value', // 'field[]' is already a defined key + * 'field[]' => 'another value', // 'field[]' is already a defined key * ]); * ``` * * The solution is to pass an array value: * * ```php - * // this way both values are submitted + * submitForm('#my-form', [ * 'field' => [ * 'value', @@ -2017,6 +2160,19 @@ trait FunctionalTesterActions } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Moves back in history. + * + * @param int $numberOfSteps (default value 1) + * @see \Codeception\Lib\InnerBrowser::moveBack() + */ + public function moveBack($numberOfSteps = null) { + return $this->getScenario()->runStep(new \Codeception\Step\Action('moveBack', func_get_args())); + } + + /** * [!] Method is generated. Documentation taken from corresponding module. * @@ -2116,16 +2272,78 @@ trait FunctionalTesterActions * * ``` php * expectEvents('App\MyEvent'); - * $I->expectEvents('App\MyEvent', 'App\MyOtherEvent'); - * $I->expectEvents(['App\MyEvent', 'App\MyOtherEvent']); + * $I->seeEventTriggered('App\MyEvent'); + * $I->seeEventTriggered(new App\Events\MyEvent()); + * $I->seeEventTriggered('App\MyEvent', 'App\MyOtherEvent'); + * $I->seeEventTriggered(['App\MyEvent', 'App\MyOtherEvent']); * ?> * ``` * @param $events - * @see \Codeception\Module\Laravel5::expectEvents() + * Conditional Assertion: Test won't be stopped on fail + * @see \Codeception\Module\Laravel5::seeEventTriggered() */ - public function expectEvents($events) { - return $this->getScenario()->runStep(new \Codeception\Step\Action('expectEvents', func_get_args())); + public function canSeeEventTriggered($events) { + return $this->getScenario()->runStep(new \Codeception\Step\ConditionalAssertion('seeEventTriggered', func_get_args())); + } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Make sure events fired during the test. + * + * ``` php + * seeEventTriggered('App\MyEvent'); + * $I->seeEventTriggered(new App\Events\MyEvent()); + * $I->seeEventTriggered('App\MyEvent', 'App\MyOtherEvent'); + * $I->seeEventTriggered(['App\MyEvent', 'App\MyOtherEvent']); + * ?> + * ``` + * @param $events + * @see \Codeception\Module\Laravel5::seeEventTriggered() + */ + public function seeEventTriggered($events) { + return $this->getScenario()->runStep(new \Codeception\Step\Assertion('seeEventTriggered', func_get_args())); + } + + + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Make sure events did not fire during the test. + * + * ``` php + * dontSeeEventTriggered('App\MyEvent'); + * $I->dontSeeEventTriggered(new App\Events\MyEvent()); + * $I->dontSeeEventTriggered('App\MyEvent', 'App\MyOtherEvent'); + * $I->dontSeeEventTriggered(['App\MyEvent', 'App\MyOtherEvent']); + * ?> + * ``` + * @param $events + * Conditional Assertion: Test won't be stopped on fail + * @see \Codeception\Module\Laravel5::dontSeeEventTriggered() + */ + public function cantSeeEventTriggered($events) { + return $this->getScenario()->runStep(new \Codeception\Step\ConditionalAssertion('dontSeeEventTriggered', func_get_args())); + } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Make sure events did not fire during the test. + * + * ``` php + * dontSeeEventTriggered('App\MyEvent'); + * $I->dontSeeEventTriggered(new App\Events\MyEvent()); + * $I->dontSeeEventTriggered('App\MyEvent', 'App\MyOtherEvent'); + * $I->dontSeeEventTriggered(['App\MyEvent', 'App\MyOtherEvent']); + * ?> + * ``` + * @param $events + * @see \Codeception\Module\Laravel5::dontSeeEventTriggered() + */ + public function dontSeeEventTriggered($events) { + return $this->getScenario()->runStep(new \Codeception\Step\Assertion('dontSeeEventTriggered', func_get_args())); } @@ -2149,6 +2367,41 @@ trait FunctionalTesterActions } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Checks that current url matches route + * + * ``` php + * seeCurrentRouteIs('posts.index'); + * ?> + * ``` + * @param $routeName + * Conditional Assertion: Test won't be stopped on fail + * @see \Codeception\Module\Laravel5::seeCurrentRouteIs() + */ + public function canSeeCurrentRouteIs($routeName) { + return $this->getScenario()->runStep(new \Codeception\Step\ConditionalAssertion('seeCurrentRouteIs', func_get_args())); + } + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Checks that current url matches route + * + * ``` php + * seeCurrentRouteIs('posts.index'); + * ?> + * ``` + * @param $routeName + * @see \Codeception\Module\Laravel5::seeCurrentRouteIs() + */ + public function seeCurrentRouteIs($routeName) { + return $this->getScenario()->runStep(new \Codeception\Step\Assertion('seeCurrentRouteIs', func_get_args())); + } + + /** * [!] Method is generated. Documentation taken from corresponding module. * @@ -2169,43 +2422,6 @@ trait FunctionalTesterActions } - /** - * [!] Method is generated. Documentation taken from corresponding module. - * - * Checks that current url matches route - * - * ``` php - * seeCurrentRouteIs('posts.index'); - * ?> - * ``` - * @param $route - * @param array $params - * Conditional Assertion: Test won't be stopped on fail - * @see \Codeception\Module\Laravel5::seeCurrentRouteIs() - */ - public function canSeeCurrentRouteIs($route, $params = null) { - return $this->getScenario()->runStep(new \Codeception\Step\ConditionalAssertion('seeCurrentRouteIs', func_get_args())); - } - /** - * [!] Method is generated. Documentation taken from corresponding module. - * - * Checks that current url matches route - * - * ``` php - * seeCurrentRouteIs('posts.index'); - * ?> - * ``` - * @param $route - * @param array $params - * @see \Codeception\Module\Laravel5::seeCurrentRouteIs() - */ - public function seeCurrentRouteIs($route, $params = null) { - return $this->getScenario()->runStep(new \Codeception\Step\Assertion('seeCurrentRouteIs', func_get_args())); - } - - /** * [!] Method is generated. Documentation taken from corresponding module. * @@ -2218,11 +2434,10 @@ trait FunctionalTesterActions * ``` * * @param $action - * @param array $params * Conditional Assertion: Test won't be stopped on fail * @see \Codeception\Module\Laravel5::seeCurrentActionIs() */ - public function canSeeCurrentActionIs($action, $params = null) { + public function canSeeCurrentActionIs($action) { return $this->getScenario()->runStep(new \Codeception\Step\ConditionalAssertion('seeCurrentActionIs', func_get_args())); } /** @@ -2237,10 +2452,9 @@ trait FunctionalTesterActions * ``` * * @param $action - * @param array $params * @see \Codeception\Module\Laravel5::seeCurrentActionIs() */ - public function seeCurrentActionIs($action, $params = null) { + public function seeCurrentActionIs($action) { return $this->getScenario()->runStep(new \Codeception\Step\Assertion('seeCurrentActionIs', func_get_args())); } @@ -2408,14 +2622,14 @@ trait FunctionalTesterActions * * Assert that specific form error messages are set in the view. * - * Useful for validation messages e.g. - * return `Redirect::to('register')->withErrors($validator);` - * - * Example of Usage + * This method calls `seeFormErrorMessage` for each entry in the `$bindings` array. * * ``` php * seeFormErrorMessages(array('username'=>'Invalid Username')); + * $I->seeFormErrorMessages([ + * 'username' => 'Invalid Username', + * 'password' => null, + * ]); * ?> * ``` * @param array $bindings @@ -2430,14 +2644,14 @@ trait FunctionalTesterActions * * Assert that specific form error messages are set in the view. * - * Useful for validation messages e.g. - * return `Redirect::to('register')->withErrors($validator);` - * - * Example of Usage + * This method calls `seeFormErrorMessage` for each entry in the `$bindings` array. * * ``` php * seeFormErrorMessages(array('username'=>'Invalid Username')); + * $I->seeFormErrorMessages([ + * 'username' => 'Invalid Username', + * 'password' => null, + * ]); * ?> * ``` * @param array $bindings @@ -2451,48 +2665,50 @@ trait FunctionalTesterActions /** * [!] Method is generated. Documentation taken from corresponding module. * - * Assert that specific form error message is set in the view. + * Assert that a specific form error message is set in the view. * - * Useful for validation messages and generally messages array - * e.g. - * return `Redirect::to('register')->withErrors($validator);` + * If you want to assert that there is a form error message for a specific key + * but don't care about the actual error message you can omit `$expectedErrorMessage`. * - * Example of Usage + * If you do pass `$expectedErrorMessage`, this method checks if the actual error message for a key + * contains `$expectedErrorMessage`. * * ``` php * seeFormErrorMessage('username'); * $I->seeFormErrorMessage('username', 'Invalid Username'); * ?> * ``` * @param string $key - * @param string $errorMessage + * @param string|null $expectedErrorMessage * Conditional Assertion: Test won't be stopped on fail * @see \Codeception\Module\Laravel5::seeFormErrorMessage() */ - public function canSeeFormErrorMessage($key, $errorMessage) { + public function canSeeFormErrorMessage($key, $expectedErrorMessage = null) { return $this->getScenario()->runStep(new \Codeception\Step\ConditionalAssertion('seeFormErrorMessage', func_get_args())); } /** * [!] Method is generated. Documentation taken from corresponding module. * - * Assert that specific form error message is set in the view. + * Assert that a specific form error message is set in the view. * - * Useful for validation messages and generally messages array - * e.g. - * return `Redirect::to('register')->withErrors($validator);` + * If you want to assert that there is a form error message for a specific key + * but don't care about the actual error message you can omit `$expectedErrorMessage`. * - * Example of Usage + * If you do pass `$expectedErrorMessage`, this method checks if the actual error message for a key + * contains `$expectedErrorMessage`. * * ``` php * seeFormErrorMessage('username'); * $I->seeFormErrorMessage('username', 'Invalid Username'); * ?> * ``` * @param string $key - * @param string $errorMessage + * @param string|null $expectedErrorMessage * @see \Codeception\Module\Laravel5::seeFormErrorMessage() */ - public function seeFormErrorMessage($key, $errorMessage) { + public function seeFormErrorMessage($key, $expectedErrorMessage = null) { return $this->getScenario()->runStep(new \Codeception\Step\Assertion('seeFormErrorMessage', func_get_args())); } @@ -2504,8 +2720,6 @@ trait FunctionalTesterActions * Takes either an object that implements the User interface or * an array of credentials. * - * Example of Usage - * * ``` php * getScenario()->runStep(new \Codeception\Step\Action('grabRecord', func_get_args())); } + + + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Use Laravel's model factory to create a model. + * Can only be used with Laravel 5.1 and later. + * + * ``` php + * haveModel('App\User'); + * $I->haveModel('App\User', ['name' => 'John Doe']); + * $I->haveModel('App\User', [], 'admin'); + * $I->haveModel('App\User', [], 'admin', 3); + * ?> + * ``` + * + * @see http://laravel.com/docs/5.1/testing#model-factories + * @param string $model + * @param array $attributes + * @param string $name + * @param int $times + * @return mixed + * @see \Codeception\Module\Laravel5::haveModel() + */ + public function haveModel($model, $attributes = null, $name = null, $times = null) { + return $this->getScenario()->runStep(new \Codeception\Step\Action('haveModel', func_get_args())); + } + + + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Use Laravel's model factory to create a model. + * Can only be used with Laravel 5.1 and later. + * + * ``` php + * createModel('App\User'); + * $I->createModel('App\User', ['name' => 'John Doe']); + * $I->createModel('App\User', [], 'admin'); + * $I->createModel('App\User', [], 'admin', 3); + * ?> + * ``` + * + * @see http://laravel.com/docs/5.1/testing#model-factories + * @param string $model + * @param array $attributes + * @param string $name + * @param int $times + * @return mixed + * @see \Codeception\Module\Laravel5::createModel() + */ + public function createModel($model, $attributes = null, $name = null, $times = null) { + return $this->getScenario()->runStep(new \Codeception\Step\Action('createModel', func_get_args())); + } + + + /** + * [!] Method is generated. Documentation taken from corresponding module. + * + * Use Laravel's model factory to make a model. + * Can only be used with Laravel 5.1 and later. + * + * ``` php + * makeModel('App\User'); + * $I->makeModel('App\User', ['name' => 'John Doe']); + * $I->makeModel('App\User', [], 'admin'); + * $I->makeModel('App\User', [], 'admin', 3); + * ?> + * ``` + * + * @see http://laravel.com/docs/5.1/testing#model-factories + * @param string $model + * @param array $attributes + * @param string $name + * @param int $times + * @return mixed + * @see \Codeception\Module\Laravel5::makeModel() + */ + public function makeModel($model, $attributes = null, $name = null, $times = null) { + return $this->getScenario()->runStep(new \Codeception\Step\Action('makeModel', func_get_args())); + } }