In response to request from eivindkvedalen, one of the original author of the Spreadsheet workbench, I make this post for discussion of my current work on expression and spreadsheet. You may find a more user oriented overview at here. At the current stage, I consider it not matured enough to be considered for merging to master. And as you can see from the overview, there are some security concerns that need to be formally addressed first. In addition, it partially depends on my Link implementation, so it won't happen until Link is merged first.
Please build my LinkStage3 if you want to test it, as there are quite a few fixes since my last AppImage release.
Here is an overview from developer point of view. The expression syntax has been extended to mimic Python. I used a patched version of bison to generate the parser for performance reason. You can find the patch at my repo (ExpressionParser-bison-3.0.4.patch). I have replaced boost::any with a customized implementation at App/stx/any.hpp (forked from here, with some modification), also for performance reason. Specifically, boost::any does dynamic allocation for any value stored, even for bool type. Expression classes are heavily refactored. std::unique_ptr is used everywhere to eliminate most of the raw pointer usage.
I have unified all link type properties using a common parent class called PropertyLinkBase. I added several new link properties that support external link, which all have XLink in their names, implemented in PropertyLinks.cpp. In particular, there is a type called PropertyXLinkContainer, which is designed to contain multiple PropertyXLink inside. Another property, PropertyExpressionContainer is derived from PropertyXLinkContainer which offers interface for FreeCAD to batch set/get expressions. Both PropertyExpressionEngine and PropertySheet are changed to be derived from PropertyExpressionContainer, which adds a few new capabilities to these two,
* When a document contains external referencing expressions are opened, the referenced documents will be opened automatically.
* Document recomputation will auto include any external referenced object with correct ordering
* New commands are available to get/set all expressions from all objects in all documents, implemented in CommandDoc.cpp, class StdCmdExpression.
* Unified handling (like all other types of link property) of common link operations, such as auto link breaking, dependency walking, linked object label tracking, smart geometry reference based on my new topological naming, etc.
I have also just implemented user abortion during document restoring and recomputing, because of possible infinite loop in the expression.
Although I did have performance in mind when refactoring the expression, I haven't got time to do any serious benchmark or performance tuning yet. As for now, simple loop test shows that in release build, the expression evaluates about 25 times slower than Python equivalent (12 times slower if disallow user abortion). This is mostly due to excessive conversion back and forth among expression, App::any and Py::Object. I'll deal with that later.