Commit Graph

30 Commits

Author SHA1 Message Date
MarkBaker 441ae741d7 Update Excel function samples for Date/Time and Engineering functions 2022-09-14 14:16:32 +02:00
Mark Baker a911e9bb7b
Calculation engine empty arguments (#2143)
* Initia work on differentiating between empty arguments and null arguments passed to Excel functions

Previously we always passed a null value for an empty argument (i.e. where there was an argument separator in the function call without an argument.... PHP doesn't support empty arguments, so we needed to provide some value but then it wasn't possible to differentiate between a genuine null argument (either a literal null, or a null cell value) and the null that we were passing to represent an empty argument value.

This change evaluates empty arguments within the calculation engine, and instead of passing a null, it reads the signature of the required Excel function, and passes the default value for that argument; so now a null argument really does mean a null value argument.

* If the Excel function implementation doesn't accept any arguments; or once we reach a variadic argument, or try to pass more arguments than the method supports in its signature, then there's no point in checking for defaults, and to do so will lead to PHP errors, so break out of the default replacement loop
2021-06-10 08:49:53 +02:00
oleibman 9beacd21be
Complete Breakup Of Calculation/DateTime Functions (#1937)
* Complete Breakup Of Calculation/DateTime Functions

In conjunction with parallel breakups happening in other areas of Calculation, this change breaks up all the DateTime functions into their own classes. All methods remaining in DateTime itself have a doc block deprecation notice, and consist only of stub code to call the replacement methods. Coverage of DateTime itself and all the replacement methods is 100%.

There is only one substantive change to the code (see next paragraph). Among the non-substantive changes, it now adopts the same parsing technique (throwing and catching exceptions) already in use in Engineering and MathTrig. Boolean parameters are allowed in lieu of numbers when Excel allows them. Most of the code changes involve refactoring due to the need to avoid Scrutinizer "complexity" failures in what it will consider to be new methods.

Issue #1936 was opened just as I was staging this. It is now fixed. One existing WORKDAY test was wrong (noted in a comment in the test data file), and a bunch of new tests are added.

I found it confusing to use DateTime as a node of the the class name since most of the methods invoke native DateTime methods. So, everything is moved to directory DateTimeExcel, and that is what is used in the class names.

There are several follow-up activities that I am planning to undertake if this PR is merged.

- ODS supports dates well before 1900. There are exactly 2 assertions for this functionality. More are needed (and some functions might have to change to accept this).
- WEEKDAY has some poorly documented extra options for "style" which are not yet implemented.
- Most tests have been changed to use a formula as entered on a spreadsheet rather than a direct call to the method which implements the formula. There are 3 exceptions at this time. WORKDAY and NETWORKDAYS, which include arrays as part of their parameters, are more complicated than most. YEARFRAC was just too large to deal with now.
- There are direct calls to the now-deprecated methods in both source code and tests, mostly in Financial code, but possibly in others as well. These need to be changed.
- Some constants, none "officially" documented, remain in the original class. These should be either deleted or marked deprecated. I wasn't sure if deprecation was even possible (or desirable), and did not want that to be something which would cause Scrutinizer to fail the change.

* Deprecate Now-unused Constants, Fix Yearfrac bug, Change 3 Tests

Add new DateTime/Constants class, initially populated with constants used in Weeknum.

MS has another inconsistency with how it handles null cells in Yearfrac. Change PhpSpreadsheet to behave compatibly with this bug.

I have modified YearFrac, WorkDay, and NetworkDays tests to be more to my liking. Many tests added to YearFrac because of the bug above. Only minor modifications to the existing tests for the others.
2021-03-21 09:12:05 +01:00
oleibman 80a20fc991
100% Coverage for Calculation/DateTime (#1870)
* 100% Coverage for Calculation/DateTime

The code in DateTime is now completely covered.
Along the way, some errors were discovered and corrected.
- The tests which have had to be changed at the start of every year are
replaced by more robust equivalents which do not require annual changes.
- Several places in the code where Gnumeric and OpenOffice were thought to differ
from Excel do not appear to have had any justification.
I have left a comment where such code has been removed.
- Use DateTime when possible rather than date, time, or strftime functions to avoid
potential Y2038 problems.
- Some impossible code has been removed, replaced by an explanatory comment.
- NETWORKDAYS had a bug when the start date was Sunday. There had been no tests
of this condition.
- Some functions allow boolean and null arguments where a number is expected.
This is more complicated than the equivalent situations in MathTrig because
the initial date for these calculations can be Day 1 rather than Day 0.
- More testing for dates from 1900-01-01 through the fictitious
everywhere-but-Excel 1900-01-29.
    - This showed that there is an additional Excel bug - Excel evaluates
WEEKNUM(emptycell) as 0, which is not a valid result for
WEEKNUM without a second argument.
PhpSpreadsheet now duplicates this bug.
    - There is a similar and even worse bug for 1904-01-01 in 1904 calculations.
Weeknum returns 0 for this,
but returns the correct value for arguments of 0 or null.
    - DATEVALUE should accept 1900-02-29 (sigh) and relatives.
PhpSpreadsheet now duplicates this bug.
- Testing bootstrap sets default timezone. This appears to be a relic from
the releases of PHP where the unwise decision, subsequenly reversed,
was made to issue messages for
"no default timezone is set" rather than just use a sensible default.
This was a disruptive setting for some of the tests I added.
There is only one test in the entire suite which is default-timezone-dependent.
Setting and resetting of default timezone is moved to that test
(Reader/ODS/ODSTest), and out of bootstrap.
- There had been no testing of NOW() function.
- DATEVALUE test had no tests for 1904 calendar and needs some.
- DATE test changed 1900/1904 calendar in use without restoring it.
- WEEKDAY test had no tests for 1904 calendar and needs some.
    - Which revealed a bug in Shared/Date (excelToDateTimeObject was not
recognizing 1904-01-01 as valid when 1904 calendar is in use).
    - And an additional bug in that legal 1904-calendar values in the 0.0-1.0
range yielded the same "wrong" answers as 1900-calendar (see "One note" below).
Also the comment for one of the calendar-1904 tests was wrong in attempting
to identify what time of day the fraction represented.

I had wanted to break this up into a set of smaller modules, a process already
started for Engineering and MathTrig.
However the number of source code changes was sufficient that I wanted
a clean delta for this request.
If it is merged, I will work on breaking it up afterwards.

One note - Shared/Date/excelToDateTimeObject, when calendar-1900 is in use,
returns an unexpected result if its argument is between 0 and 1,
which is nominally invalid for that calendar.
It uses a base-1970 calendar in that instance. That check is not justifiable
for calendar-1904, where values in that range are legal,
so I made the check specific to calendar-1900,
and adjusted 3 1904 unit test results accordingly. However, I have to admit that
I don't understand why that check should be made even for calendar-1900.
It certainly doesn't match anything that Excel does.
I would recommend scrapping that code altogether.
If agreed, I would do this as part of the break-up into smaller modules.

Another note -
more controversially, it is clear that PhpSpreadsheet needs to support
the Excel and PHP date formats. Although it requires further study,
I am not convinced that it needs to support Unix timestamp format.
Since that is a potential source of Y2038 problems on 32-bit systems,
I would like to open a PR to deprecate the use of that format.
Please let me know if you are aware of a valid reason to continue to support it.
2021-02-27 20:43:22 +01:00
Martins Sipenko d2edab2827
Fix date tests withut specified year for current year 2021 (#1774) 2021-01-07 11:41:46 +01:00
Alban Duval 7ed96e0be1
Calcualtion - DATEDIF - fix result for Y & YM units (#1466)
Bugfix for negative results and too small results

2000-02-02 => 2001-02-01
 > DATEDIF with Y unit: 0 year (returned -1 before fix)
 > DATEDIF with YM unit: 11 months (returned -1 before fix)
2020-05-25 21:33:48 +02:00
Adrien Crivelli fcd9f10663
Update PHP-CS-Fixer rules 2020-05-18 13:49:57 +09:00
oleibman cb18163a1d
Changes to WEEKNUM and YEARFRAC (#1316)
* Changes to WEEKNUM and YEARFRAC

The optional second parameter for WEEKNUM can take any of 10 values
(1, 2, 11-17, and 21), but currently only 1 and 2 are supported.
This change adds support for the other 8 possibilities.

YEARFRAC in Excel does not require that end date be before start date,
but PhpSpreadsheet was returning an error in that situation.

YEARFRAC third parameter (method) of 1 was not correctly implemented.
I was able to find a description of the algorithm, and documented
that location in the code, and implemented according to that spec.
PHPExcel had a (failing) test to assert the result of
YEARFRAC("1960-12-19", "2008-06-28", 1). This test had been dropped
from PhpSpreadsheet, and is now restored; several new tests have
been added, and verified against Excel.

* Add YEARFRAC Tests

Scrutinizer reported a very mysterious failure with no details.
project.metric_change("scrutinizer.test_coverage", < 0),
without even a link to explain what it is reporting.
It is possible that it was a complaint about code coverage.
If so, I have added some tests which will, I hope, eliminate the problem.

* Make Array Constant

Responding to review from Mark Baker.

* Merge with PR 1362 Bugfix 1161

Travis CI reported problem with Calculation.php (which is not part
  of this change).
That was changed in master a few days ago
(delete some unused code).
Perhaps the lack of that change is the problem here.
Merging it manually.
2020-02-19 20:22:31 +01:00
Mark Baker 0417c8cc2b
Fix date tests withut specified year for current year 2020 (#1302) 2020-01-03 23:24:45 +01:00
MarkBaker 7219e665a0 As always, falling foul of codesniffer 2019-07-30 19:07:24 +02:00
MarkBaker 4c9d51c11b Add Associative indexing to dataprovider for DATE 2019-07-30 19:00:00 +02:00
MarkBaker aa35a2f85f More refactoring Excel of Calculation Function Unit Tests 2019-07-30 18:54:37 +02:00
Mark Baker aaf996a165
Refactor engineering tests (#1106)
* Merge branch 'master' of C:\Projects\PHPOffice\PHPSpreadsheet\develop with conflicts.

* Bessels, and set some date tests to defined/named arguments

* Fix test class naming

* Names arguments for math/trig tests

* Docblock updates

* More engineering function unit test refactorings

* More engineering function unit test refactorings. This time, moving on to the Complex engineering functions

* Fix ImConjugate test

* Fix parseComplex test

* Fix parseComplex test

* More of the complex number function unit tests refactored

* Finish refactoring of the complex number function unit tests

* Newer phpunit assertions

* Add parsecomplex unit test back until we're ready to drop the deprecated function; but as it doesn't use the specified data provider at all, drop reference to that
2019-07-25 21:02:41 +02:00
Mark Baker 342ffb629b
Refactoring of math trig tests (#1102)
* Merge branch 'master' of C:\Projects\PHPOffice\PHPSpreadsheet\develop with conflicts.

* First pass at moving MathTrig tests into individual test files

* Appeasement to the great goddess PHPCS

* Appeasement to the great goddess PHPCS

* Minor scrutinizer issue resolved

* More refactoring of tests into individual test files fr each math/trig function

* More work on the math/trig test refactoring, plus a bit of tidyup of date/time tests as well

* Fix test

* Fix docblock in test

* Finish refactoring Math/Trig tests into separate files

* Fix SubTotal Test

* Import additional classes for SubTotal test
2019-07-23 00:50:30 +02:00
Mark Baker 9ad6de620e
Refactoring of date time tests (#1101)
* Merge branch 'master' of C:\Projects\PHPOffice\PHPSpreadsheet\develop with conflicts.

* Separate out date/time tests into individual tests

* Need to update the version of phpunit at some point to deal with the new assertions and deprecated assertions

* Appease the CS Gods

* More refactoring of Date/Time tests

* Replace self assertions with instance assertions (looking forward to upgrading phpunit)

* Finish refactoring of date/time tests as individual tests

* Test for DateTimeInterface rather than for DateTime

* A few strict comparisons

* Fix to test names
2019-07-21 20:55:41 +02:00
Adrien Crivelli e8c25c33cd
Fix unit tests for 2019 2019-01-01 17:48:07 +11:00
Biser Antonov 2c981e47a1
Added the DAYS() function
https://support.office.com/en-us/article/days-function-57740535-d549-4395-8728-0f07bff0b9df
2018-10-21 15:26:46 +11:00
Mark Baker 9b44cf3418
Add further new Functions introduced in MS Excel 2013 and 2016 (#608)
- Fix ISFORMULA() function to work with a cell reference to another worksheet
 - Added calculation engine support for the new functions that were added in MS Excel 2013 and MS Excel 2016
   - Text Functions
     - CONCAT()     Synonym for CONCATENATE()
     - NUMBERVALUE()  Converts text to a number, in a locale-independent way
     - UNICHAR()    Synonym for CHAR() in PHPSpreadsheet, which has always used UTF-8 internally
     - UNIORD()     Synonym for ORD() in PHPSpreadsheet, which has always used UTF-8 internally
     - TEXTJOIN()   Joins together two or more text strings, separated by a delimiter
   - Logical Functions
     - XOR()        Returns a logical Exclusive Or of all arguments
   - Date/Time Functions
     - ISOWEEKNUM()  Returns the ISO 8601 week number of the year for a given date
   - Lookup and Reference Functions
     - FORMULATEXT()  Returns a formula as a string
   - Engineering Functions
     - ERF.PRECISE()   Returns the error function integrated between 0 and a supplied limit
     - ERFC.PRECISE()  Synonym for ERFC
   - Math and Trig Functions
     - SEC()          Returns the secant of an angle
     - SECH()         Returns the hyperbolic secant of an angle
     - CSC()          Returns the cosecant of an angle
     - CSCH()         Returns the hyperbolic cosecant of an angle
     - COT()          Returns the cotangent of an angle
     - COTH()         Returns the hyperbolic cotangent of an angle
     - ACOT()         Returns the cotangent of an angle
     - ACOTH()        Returns the hyperbolic cotangent of an angle
  - Financial Functions
    - PDURATION()    Calculates the number of periods required for an investment to reach a specified value
    - RRI()          Calculates the interest rate required for an investment to grow to a specified future value
2018-07-22 19:17:04 +01:00
Adrien Crivelli 36441da330
Fix unit tests for 2018
Closes #311
2018-01-02 00:39:38 +09:00
Maxim 088a76737e Fix DAY() function with 0<x<1 input (#230)
Also bring support for OpenOffice DATE() calculation method
2017-10-04 12:57:01 +09:00
Adrien Crivelli 8dddf56c2e
Use proper syntax for variadic functions
This simplify code, increase readability and improve the function
signature for API users.
2017-01-23 15:01:20 +09:00
Adrien Crivelli f0445366d2
Fix date related unit tests for 2017 2017-01-04 17:37:23 +09:00
mattkibbler 62345ef4da
Allow start and end date of DATEDIF function to be the same 2016-12-04 19:04:10 +09:00
Adrien Crivelli ae1b85f961
Fix code style 2016-10-02 15:21:52 +09:00
Adrien Crivelli 431a1799fb
Fix unit tests for YEARFRAC() 2016-10-02 15:17:52 +09:00
Adrien Crivelli 8c4c11346b
Fix unit tests for DATEDIF()
Leap years where not properly taken into consideration
2016-10-02 14:46:11 +09:00
Adrien Crivelli 60533a4f59
Fix unit tests for WEEKDAY()
In Excel the expected value was incorrect (but it would be different
for LibreOffice)
2016-10-02 09:28:00 +09:00
Adrien Crivelli 23fbc845dd
Fix unit tests for WEEKNUM() 2016-10-01 22:33:12 +09:00
Adrien Crivelli 539a89a918
Rename namespace `PHPExcel` to `PhpSpreadsheet`
This also fix a few bugs that were introduced when migrating to
namespace. Some non-namespaces classes were leftover

FIX #15
2016-08-16 23:24:47 +09:00
Adrien Crivelli e1f81f0fe0
Refactor tests data from custom format to PHP
FIX #14
2016-08-16 21:00:19 +09:00