Welcome | Get started | Dive | Contribute | Topics | Reference | Changes | More

This is the 2019 change log for Developer Guide. General information about how to read and maintain this document in Documenting changes.



New plugin configuration parameter lino_xl.lib.cal.Plugin.demo_absences.


Release Lino 19.12.3 and XL 19.12.5 to PyPI.

XL 19.12.5 fixed one bug but introduced another: register_voucher() is now being called after state change, so the side effect of updating the fields of a VAT declaration was no longer saved. Fixed.

Released XL 19.12.6 to PyPI.

Discovered and fixed a bug in lino_xl.lib.eevat: a sales intracom invoice must not generate any movement with a VAT amount.


Fixed a bug in lino_xl.lib.vat that caused Lino to not compute correctly a DeclarationField with a condition on DeclarationField.vat_classes which mentioned only vat classes to be excluded (i.e. prefixed with an “!”). Same for DeclarationField.vat_columns and DeclarationField.vat_regimes.


Fixed a subtle bug that might have been the cause for #3178.


The lino_xl.lib.households now provides a usable HouseholdDetail when lino_xl.lib.addresses and lino_xl.lib.phones are also installed.

Bugfix #3429 TypeError: must be str, not __proxy__ (on a recurrent event with non-empty lino.modlib.system.RecurrenceSet.positions field and occurring on more than one weekday.


The new lino.core.model.Model.disable_create_choice attribute can be used to disable automatic creation from a learning foreign key field.

Released Lino 19.12.2 to PyPI because


The lino_xl.lib.contacts.Role.person field is now a learning foreign key field.

Released XL 19.12.3 to PyPI.


The lino_xl.lib.lists.MembersByList table has two new (virtual) columns “Address” and “Contact details”. lino_xl.lib.lists.MembersByPartner is now in summary display mode, and list memberships now have a detail window.

Released XL 19.12.1 to PyPI (immediately followed by 19.12.2 because 19.12.1 had an oops bug).


Bugfix : The Estonian VAT declaration (lino_xl.lib.eevat) didn’t yet handle Intracom purchases correctly.

New feature : national VAT implementations can now prefix observed fields of a VAT declaration field (lino_xl.lib.vat.DeclarationField.fieldnames) with a “-” to indicate that the field is “inverted”.


Released Lino 19.12.1 to PyPI.


Release to PyPI : version 19.12.0 of lino, lino-xl and lino-cosi.


More changes in lino_xl.lib.vat and the three national VAT plugins.


Two new tables PurchasesByDeclaration and SalesByDeclaration in lino_xl.lib.vat. These are included in the VatDeclaration detail view of lino_xl.lib.eevat (other national plugins will follow).



Fixed #2001 (When I have changed my password, Lino says OK, but then it says “Database problem” and I need to re-login)


Fixed #3333 (Unable to create comments with invalid @user or #ticket).


Release to PyPI : lino lino-xl lino-welfare lino-weleup lino-react lino-avanti


The title of insert windows is no longer e.g. “Insert into All Tickets” but simply “New Ticket”. Thanks to Amber who had the idea. #3327.


lino_xl.lib.addresses.AddressOwner.get_primary_address() now returns None if MultipleObjectsReturned (instead of raising a server error).


Added Lino.core.actions.Action.react_icon_name. Used first rather than icon_name.


We started to publish React front end as a package on PyPI. Version 19.11.1 might work, but we didn’t yet test it.


The BaseRequest.set_confirm_answer() is now being inherited to child requests.

The dashboard in React front end now issues separated Ajax requests for each dashboard item. New attribute lino.core.renderer.Renderer.hide_dashboard_items.


The server_status field in lino.modlib.about.About has been removed because it was showing just the number of pending dialog threads which no longer applies since 20191014 and now caused an error.

New feature in lino_xl.lib.trends: When the new checkbox TrendStage.subject_column is checked, Lino will add a virtual field to the Plugin.subject_model which shows the date of the first TrendEvent of this stage for this client. The columns are not visible by default but the end user can activate them.

Above change required a new minor feature in lino.core.fields: Virtual fields aren’t normally used as wildcard data elements. The new attribute VirtualField.wildcard_data_elem. makes it possible to define virtual fields that are used as wildcard data elements.


Database changes in lino_xl.lib.tickets.


Database changes for #3108 (Report when a ticket or user is mentioned in a comment) in lino.modlib.comments : new model lino.modlib.comments.Mention.


Some changes for #3284: The demo fixture of lino_xl.lib.groups now adds first names for every user because otherwise Lino complains when users.Users inherits from contacts.Person. In lino_xl.lib.groups the Membership.user field is now labeled “User” instead of “Author”, and the model now has a detail layout and an insert layout (e.g. MembersByGroup now has a insert button)


Fixed a failure in presto caused by changes in lino_xl.lib.beid.


Fixed a typo bug in lino_xl.lib.cal that caused NameError: name 'cls' is not defined e.g. when showing the detail of a cal.Guest.

lino.modlib.system.Lockable now uses a database field instead of an in-memory dict in order to be usable on a multi-process site (#3277).

Released Lino to PyPI


Fixed callbacks for lino_xl.lib.beid actions (#3269)

Released Lino and XL to PyPI


New setting simulate_eidreader_path for lino_xl.lib.beid. Used in lino_book.projects.avanti1 to reproduce #3269 without having a Belgian ID card.


Fixed a TypeError __str__ returned non-string (type __proxy__) occuring e.g. when showing the detail of a lino_xl.lib.excerpts.Excerpt.

The templates excerpts/base.weasy.html and weasyprint/base.weasy.html have been optimized. New bottomleft and bottomright blocks are expected to contain the content property for their respective element.

lino.core.requests.BaseRequest.get_printable_context() adds a new function activate_language() to set the language for the remaining part of the template.

New method lino_xl.lib.clients.KnownContactType.get_contacts (i.e. get them all, not just one) is now used instead of lino_xl.lib.clients.KnownContactType.get_contact.

Summary layout of lino_xl.lib.cv.HistoryByPerson was not very readable: added a colon behind each field label, and the field value is now bold. Fixed a bug in that same summary which inserted an empty bullet at the beginning of the list.

Released Lino, XL and Avanti to PyPI.


New approach for handling callbacks on nginx with multiple worker processes.


New plugin setting multiple_primary_coachings for lino_xl.lib.coachings. When this is set to True, the uniqueness of the primary coaching is no longer just per client but per client and coaching type. As a result you can have multiple primary coachings per client. #3137


New database field lino.modlib.system.RecurrenceSet.positions. Fixes #3225.


Fixed #3248 (NameError: name ‘force_text’ is not defined). A one-day bug caused by yesterday’s changes.

Fixed some issues in accounting: #3236 (‘PaymentOrder’ object has no attribute ‘your_ref’). Payment Orders were also suggesting negative payments. Added a new filter parameter ExpectedMovements.same_dc and use it in lino_xl.lib.finan.SuggestionsByPaymentOrder. #3215 (the quick search field in booking suggestions now works). The payment orders generated by the payments fixture were not cleared. Whether a payment order generates individual counter entries (one per partner) no longer depends on Account.needs_partner but on whether the journal has a partner or not (whether Journal.partner is empty or not).


Moved callback management into a separate module lino.core.callbacks. One benefit is that the code is organized in a better way. The main goal is to get callbacks also work when running under nginx with multiple threads (#3228).


Fixed a NameError: name 'unicode' is not defined in lino_xl.lib.outbox.

Released versions 19.10.0 of Lino and XL.


lino_xl.lib.polls.AnswersByResponsePrint no longer forgets to print entries that have only a remark.

lino.core.requests.BaseRequest.show() has a new optional keyword argument display_mode which can be used to ask a summary for a table that does not show as summary by default.

The three tables based on lino_xl.lib.cv.HistoryByPerson now have a new kind of summary view which displays them as a bullet list where each item includes the field names.


lino.modlib.users.UserPlan.create_user_plan() didn’t like it when it found more than one instances of a plan for a given user. Now it simply deletes all existing reports all in that case. In lino_book.projects.cosi_ee it said MultipleObjectsReturned: get() returned more than one Report -- it returned 2! (#3232).

Fixed a bug in lino_xl.lib.sheets : the allow_cascaded_delete of the report items weren’t set correctly. When you inadvertently try to delete a partner who is mentioned in an accounting report, you want Lino to refuse your action (not to remove the entry from the report).


#3212 (Summary view for RecentComments) : lino.modlib.comments.RecentComments now has a summary view that looks much better in the dashboard. And it no longer stops displaying comments modified in the future. This is useful when you modify a comment in a demo database.

This change caused a series of changes and optimizations:

  • Fixed a bug in lino.modlib.memo.Previewable which caused it to not use the default_ui when lino.modlib.memo.Plugin.front_end is None.

  • When a BaseRequest is spawned from a parent, it now inherits the request attribute (i.e. the incoming Django HTTP request that caused the action request). This is needed so that subrequests can decide whether to generate links using “javascript:” or not. When displaying links in a comment on the exts dashboard, we prefer them to remain under the same url.

  • The demo2 fixture for lino.modlib.comments generates a series of fictive comments. But until now they all had the real timestamp when the pm prep command was run. Now they have a fictive demo date and time.


  • Fixed #3225 (saving a locked row does not unlock it)

  • Action preprocessors (the optional function given by lino.core.actions.Action.preprocessor) can now optionally add an attribute timeout to the returned object to ask Lino to wait before sending the action’s AJAX call. This is used by lino_xl.lib.beid.BeIdReadCardAction and lino_xl.lib.beid.FindByBeIdAction to make sure (or rather probable) that eidreader has done its work before the action runs on the server. This is needed to fix #3225 which occurs when nginx is running with a single worker process.


Released Lino XL 19.9.6 and Lino 19.9.1 for the site upgrade of the Lino Avanti preview site.

The lino.core.site.Site.setup_logging() method now sets the level of Django’s django.utils.autoreload logger to INFO (to avoid the problem reported on Django ticket #30554).


A series of changes for Lino Avanti (#2274):

Changes in lino_xl.lib.cv: BiographyOwner.language_knowledge now also shows whether there is a certificate or not. The CefLevel choicelist now shows only the values (A0, A1, …) and no longer their textual descriptions. Changes in final_report.body.html.

Change in lino_xl.lib.polls: New table AnswersByResponsePrint is now shown in the detail of a response.


Fixed 'AnswersByQuestionRow' object has no attribute 'get_detail_action'.


Fixed #3210 (Amici removes participants of my meeting). Changed “Edit participants” to “Fill guests” (in EntryStates) Renamed EntryState.edit_guests to EntryState.fill_guests Changed the EntryState.fill_guests for EntryStates.took_place from True to False. Not sure whether this is good. To be observed. Maybe this is application specific. Changed the default value for EventType.fill_presences from True to False.

Fixed #3211 (‘DueMovement’ object has no attribute ‘get_detail_action’).

Released XL 19.9.5.

Fixed #3213 (DataChecker to check/update body_preview) : added a new PreviewableChecker.


lino.utils.diag.Analyzer.show_window_fields() no longer shows dummy fields.

Released Lino 19.9.4.


Fixed a bug in lino_xl.lib.phones which caused checkdata to fail when a same partner had multiple contact detail entries marked as primary (MultipleObjectsReturned). Now it creates a message “Multiple primary items for <type>”.

Released XL 19.9.4.


When using returnable VAT, the total_vat field is now always empty and the total_incl field does not include the VAT. This is valid per invoice item and per invoice. The total_incl field is labelled “Total to pay” also on items. The amount of retturnable VAT is computed only when the invoice is registered.

Released XL 19.9.3.


Fixed a bug in lino_xl.lib.cv.LanguageKnowledge which caused a TypeError '>' not supported between instances of 'NoneType' and 'str' when CEF Level was empty.

Released XL 19.9.2.


Released XL 19.9.1.

Fixed #3183 : When entering the vat_regime of a partner with empty vat_id, Lino did not show regimes having needs_vat_id set. This was irritating because users who didn’t know about this subtle rule had no chance to understand why. Lino now shows these regimes also when there is no VAT id, but complains Cannot use VAT regime X for partner without VAT id when you try to save a document for that regime and that partner.


Changes in several accounting modules (accounting, vat, eevat, bevat) to fix #3192 and #2847.


Some extensions for Lino Avanti (#2274)

  • New option lino_xl.lib.cv.Plugin.with_language_history. If this is True, Lino adds a field LanguageKnowledge.obervation_date and allows multiple entries per (person, language). This can be used to record a history of the evolution of a person’s language knowledge.

  • Renamed the demo project lino_book.projects.adg to lino_book.projects.avanti1.

  • Reviewed the avanti/Client/final_report.body.html template and started using it.

  • The few_languages demo fixture for lino.modlib.languages now also sets the lino.modlib.languages.Language.iso2 field.


Disabled tidy error checking in lino.utils.html2xhtml because Tidy 5.6 also reports warnings as errors.

Released The lino package version 19.9.0.


Fixed invalid HTML in the contacts/Person/TermsConditions.odt template (in lino_xl.lib.contacts). The curly quotes were corrected by older version of tidy, but Tidy 5.6.0 no longer cleans them up.

Released Lino Extensions Library version 19.9.0.


New feature #3175 : The lino.modlib.about.About dialog now shows the “complexity factors”, which now includes the number of active user accounts.


Bugfix #3171 lino_xl.lib.courses says “Course matching query does not exist” on enrolmenmt without course.


Two optimizations (#3159) in lino_xl.lib.accounting and lino_xl.lib.vat: User can now manually edit the VAT amount in account invoices. Added a new field lino_xl.lib.accounting.Account.vat_class.

migrate failed e.g. in Lino Welfare because e.g. the default value of a database field was a callable which accesses lino.core.site.Site.site_config. Fixed.

Released XL 19.8.1 and Lino 19.8.1 to PyPI.


use_linod did not yet automatically cause install to install the schedule package.

Released XL 19.8.0 and Lino 19.8.0 to PyPI.


Fixed a bug in lino_xl.lib.accounting : when the Account.common_account was updated via the web interface, Lino did not “realize” this until the server process was restarted.

Added a new method lino.core.diff.ChangeWatcher.get_old_value().

lino_xl.lib.vat.InvoicesByJournal did not display the right sorting order. It was using [‘-id’] instead of the order defined in lino_xl.lib.accounting.ByJournal. Fixed.

The custom values in lino.utils.quantities are now deconstructible.


Renamed admin command configure`to :manage:`install. The command now calls pip only once for all requirements.


New feature in lino_xl.lib.accounting : Internal clearings (#3106).

Fixed #3135 (RecentComments is empty).

Released XL 19.7.6 and Lino 19.7.5 to PyPI.


Released XL 19.7.5 and Lino 19.7.4 to PyPI.


Added wrapper action for daily calender view to allow for event inserting.


Maybe fixed #2986 (Automatic browser update fails when using a permalink) (delete p.lv)


Released version 19.7.4 of XL to PyPI. (needed for testing getlino).


Released version 19.7.3 of Lino and XL to PyPI.

Fixed: install failed when appy was needed but not yet installed.


Support creating multiple rows with a single POST after submitting an insert form (for #3122).

The install command didn’t show the output of the subcommands. Fixed.

The get_requirements of lino_xl.lib.mailbox and lino_xl.lib.appypod check whether the appy or django_mailbox package is already installed before requiring it. To support the use case when a developer has a clone of the appy or django_mailbox sources and uses this version. I


Added a new method lino.core.plugin.Plugin.get_requirements(). Added a new admin command configure (later renamed to install). Both to be used by getlino configure (#3036).


Lino now uses the BASE tag when sending notification emails.

The front_end setting of the lino.modlib.memo plugin is now ready for beta testing on a site with two web front ends.

Internal changes (to be changed in React front end) : The plugin attribute of lino.core.renderer.Renderer has been renamed to front_end. The get_detail_url() method has been moved from lino.core.renderer.Renderer to lino.core.plugin.Plugin. The MailRenderer class in lino.core.renderer has been removed because it was no longer needed. The lino.core.site.Site.mobile_server_url is no longer used and has been removed. Compare commit for details.


The new plugin lino.modlib.memo regroups functionality which until now was dispersed in lino.mixins.bleached, lino.utils.memo and lino.utils.soup. Instead of saying SITE.kernel.memo_parser you now say SITE.plugins.memo.parser.

The lino.mixins.bleached.BleachedPreviewBody model mixin has been replaced by lino.modlib.memo.Previewable.

In lino.modlib.comments, Comment needs a database migration because instead of a single field body_preview it now has two fields short_preview and full_preview. Simply delete the following line in the definition of the create_comments_comment() function of the restore.py file:


The lino_xl.lib.notes plugin also requires lino.modlib.memo, but the changes don’t need a data migration because it uses just the parser, not Previewable.


The duplicate action didn’t work on registered vouchers (Voucher). And the and the general behaviour after duplicating a voucher was irritating.

Now the number is set to the next available number and entry_date to today.

General changes for all duplicate actions: The lino.mixins.duplicable.Duplicate action now calls full_clean() on the newly created copy. And it is now readonly (e.g. also callable on a registered voucher).

In InvoicesByJournal the grid layout was still using voucher_date instead of entry_date. The default behaviour in Lino Così is to use only entry_date because this is what counts for accounting.

Added an UploadsByController panel to the detail layout of BankStatement.

The std fixture of lino_xl.lib.accounting now creates an upload type “source document”. Note that UPLOADTYPE_SOURCE_DOCUMENT is 4 in order to avoid duplicate keys in Lino Welfare (weleup).

Optimizations in lino.modlib.memo.parser: Fixed a error occuring when there were no suggesters defined. The parser now makes a pattern clickable without adding the full text and with setting a title for the link so that the text is shown when the mouse hovers over the link.

Released Lino 19.7.2 and XL 19.7.2 to PyPI.


Minor optimizations for #3101.

Released Lino 19.7.1 and XL 19.7.1 to PyPI.


In lino_xl.working we have a new model lino_xl.working.UserSummary. Similar to SiteSummary, but per user instead of per site and monthly instead of yearly.


Reviewed the “license” field of all projects to use “BSD-2-Clause” (an SPDX identifier).

Released Lino 19.7.0 and XL 19.7.0 to PyPI.

Optimized the columns layout of lino_xl.lib.accounting.Accounts.

Added a journal group “Miscellaneous transactions” to the default configuration (lino_xl.lib.accounting.JournalGroups).


New method lino.core.actors.Actor.get_navinfo().

lino_xl.lib.cal.CalendarView navigation now also works using the buttons in the toolbar.


Fixed #861. Lino now automatically rebuilds the JavaScript files (linoweb.js) when a lino_xl.lib.accounting.Journal has been modified using the web interface. This is needed so that changes become visible in the menu. Note that you still need to reload the browser page in order to actually refresh the menu.

Vouchers are now duplicable. (lino_xl.lib.accounting.Voucher inherits from lino.mixins.duplicable.Duplicable).


Some general optimizations for #3091: Layout of lino_xl.lib.cal.EntriesByProject and lino_xl.lib.orders.EnrolmentsByWorker. Some German translations and ui labels.

Lino now checks for a database field hiding a previously virtual field of same name and raises a ChangedAPI exception when this happens. Added a demo project and a documentation page which tests it: Overriding virtual fields.

The field lino_xl.lib.topics.Topic.description was an example of above pitfall and has been renamed to lino_xl.lib.topics.Topic.description_text. This change requires a database migration.

Changed the default value for lino.core.site.Site.textfield_bleached to True. Added <div> to the default value of lino.core.site.Site.bleach_allowed_tags.

Released Lino 19.6.3 and XL 19.6.1 to PyPI.

Added the notion of “suggesters” to the memo parser. See Lino Noi for examples. This will be used by the react front-end to configure auto-completion suggestions (#3041).


Added a new table lino_xl.lib.cal.EntriesByGuest for #3090.

New method lino.core.dbtables.Table.after_create_instance().

Lino now supports a slave table whose lino.core.actors.Actor.master_key is a remote field.

Released Lino 19.6.1 and XL 19.6.0 to PyPI.

Fixed a bug introduced by 19.6.1 which caused an exception: “Error while computing salesrule__invoice_recipient: ‘NoneType’ object has no attribute ‘full_value_from_object’ (<OneToOneRel: invoicing.salesrule> in [<OneToOneRel: invoicing.salesrule>, <django.db.models.fields.related.ForeignKey: invoice_recipient>])” when opening the detail of a client in presto.

Released Lino 19.6.2 to PyPI.

Fixed a bug in lino.core.model.Model which caused a failure of tst suites

Added a new data checker lino.modlib.system.BleachChecker.


When filtering the calendar view on lino_xl.lib.cal.Events.presence_guest, Lino now also shows holiday type entries (i.e. entries whose all_rooms is checked).

The lino_xl.lib.cal.Event.max_days field can now be 0 to say that you don’t want any check.

Multi-day events must be shown on every day of their date range. Lino didn’t yet handle them correctly

Added a field lino_xl.lib.cal.EventType.fill_presences because not all events should automatically fill their presences (lino_xl.lib.cal.Guest). When lino_xl.lib.cal.EntryState.fill_guests is True, Lino also removes unwanted guests each time you hit the save button. But for example in Lino Presto when registering a absence day or a worker, the list of suggested guests is usually empty (because the project is empty), and we don’t want Lino to remove any manually added guests.

The std fixture for lino_xl.lib.cal now adds a new entry type “Absence” with this configuration. The demo2 fixture adds some “absences for private reasons”, some of them several days.


Changed the API for using bleached text fields. See lino.core.site.Site.textfield_bleached and the bleached attribute of a lino.core.fields.RichTextField.


Added a new function lino.modlib.printing.weekdays() to the global default print context.

Released Lino 19.6.0 to PyPI.


Changed http_method of CreateRow to “POST”

Some subtle optimizations in XL: translations, permissions




Fixed #3010 (subclasses of Report are not shown in the dashboard).


Released Lino XL 19.5.4 to PyPI.

A new method Event.colored_calendar_fmt is used by the calender.This method could be overridden for new need.


Released Lino 19.5.1 to PyPI.

Released Lino XL 19.5.2 to PyPI.

Removed the customized __str__() method for EventType as it disturbs in Lino Presto.

Fixed a bug in calendar view: must call calendar_fmt() on instance, not on class.

Show full description when hovering over the truncated text

Released Lino XL 19.5.3 to PyPI.


New database field lino_xl.lib.cal.Room.display_color.



Optimization in lino_xl.lib.households: added a member type “Forster-child”.

lino_xl.lib.products.Product is now duplicable.


Released Lino 19.5.0 to PyPI. Released Lino XL 19.5.0 to PyPI.

Removed the changed handler for lino_xl.lib.cal.Event.end_time because it was irritating.

Released Lino XL 19.5.1 to PyPI.

Minor changes in lino_xl.lib.cal: The new calendar views are now visible for all applications (no longer only presto). The required_roles for the new calendar views were not yet set as it should. In general you must be lino_xl.lib.office.OfficeUser or lino_xl.lib.office.OfficeOperator (or both). Note that avanti overrides the required_roles of lino_xl.lib.cal.CalendarView because they have different rules: only users who may see client names may see the calendar. The default calendar view is now monthly instead of weekly. Restored Event.__str__() from previous version. Renamed some classes (e.g. “CalView” became “CalendarView”).


weasyprint now logs the template names when rendering a template.

cgi.escape is deprecated in Python 3

New field invoicing.Plan.min_date can be used to specify a start date.

lino_xl.lib.invoicing now injects two fields invoicing_min_date and invoicing_max_date to the voucher_model. These are set for every generated invoice to those specified in the invoicing plan. They can be printed on the invoice so the customer sees the invoiced period.

Fixed a bug in VoucherTypes.get_for_model which caused it to simply return the first possible candidate. But it is possible to have two voucher types which use the same model. It is now an error to call VoucherTypes.get_for_model (or VoucherTypes.get_for_table) with a model (or a table) for which we don’t have a unique voucher type.


Added lino.utils.Parametrizable.use_detail_param_panel which causes he params panel to be shown in the detail view.

The new calendar view seems ready for a first presentation. Congratulations to Tonis and Hamza who implemented this mostly without any assistance by Luc.

Quite some changes in the lino_xl.lib.healthcare plugin. This plugin is in proof-of-concept phase and not yet used in any production site.


Lino (lino.mixins.ref.StructuredReferrable) now handles topics with an empty reference more elegantly. Use case lino_xl.lib.topics.Topic with empty ref field.

Removed a hack which caused side effects when trying to sort a choicelist with lazy items). The lino.core.choicelists.ChoiceList.add_item_lazy() method now specifies weak=False for the receiver (as explained in the docs for Signal.connect) instead of storing the wrapper function itself.

Lino now handles topics with an empty reference more elegantly lino_xl.lib.topics.Topic with empty ref field.

Orders are now printable.


Changes in lino_xl.lib.invoicing: Added a new model Area to be configured by the site admin via Configure ‣ Sales ‣ Invoicing areas. New field Plan.area. Removed field Plan.journal (which is replaced by Area.journal). Removed the StartInvoicingForJournal action which anyway wasn’t used by anybody.

The detail_layout of lino_xl.lib.accounting.Journals is now specified as a string. Used by lino_presto.lib.accounting which overrides the class.


Undid the change on 2019-04-23 (#2975): Choicelists are sorted by their natural order of creation. To sort them by their value, you can now call lino.core.choicelists.Choicelist.sort(). This is done for lino_xl.lib.accounting.JournalGroups by lino_xl.lib.orders, and for lino_xl.lib.accounting.CommonAccounts by lino_xl.lib.accounting.


Add use_detail_params_value as a new attribute to the lino.core.dbtables.Table.


Choicelists are now always sorted by their value (#2975). For example lino_xl.lib.orders adds a journal group “Orders” to lino_xl.lib.accounting.JournalGroups with value “05” which means that we want it to comes before the “Sales” group. The ordering of journal groups influences the ordering of items of the main menu.


lino_xl.lib.orders no longer stores the room per order but expects a field room per journal. Order items and Workers of an order are now deleted in cascade with the order.


Fixed order of the lino_xl.lib.cal.Events table. (#2969) :

A few modifications for Lino Noi lino_xl.lib.tickets: Renamed state “Started” to “Working”. lino_xl.lib.tickets had ‘lino_noi.lib.noi’ in needed_plugins. Bullshit. Removed. Renamed TicketsNeedingFeedback to TicketsNeedingMyFeedback. And the labels of the two feedback tables are now more similar to the internal $


New method requests.BaseRequest.goto_pk(). This required a change in linoweb.js where I add a global Lino.goto_record_id() function.

Moved handle_uploaded_files from dbtables to actors because it is also possible on a virtual table like DailyView.

The new lino_xl.lib.cal.DailyView table shows a basic calendar navigator. Looks promising, though there is more to do. For example we also need a WeeklyView and a MonthlyView. They will share the same navigator. This change requires the newest version of Lino as well. The table is currently visible only in Lino Presto.


#2946 Fix calcul of person’s age.

New option lino.modlib.users.StartPlan.update_after_start


Override the visible text for the lino_xl.lib.vat.VatAccountInvoice.your_ref field for the purchase invoice. And add this field to the grid panel.

Released Lino 19.4.0 to PyPI. Released Lino XL 19.4.0 to PyPI.


Fixed a bug in lino.utils.quantities which caused 1*Duration("0:15") to print 0.250000000000000000 instead of 0:15.

The lino_xl.lib.orders.Order.room field is no longer nullable.

When adding the workers of an order as guests of a calendar entry, Lino no longer sorts them by name. This behaviour came from lino_xl.lib.courses where it is useful, but the workers of an order should remain in their natural order.


In lino.core.site.Site.setup_menu() we now differentiate between the “technical” plugin order and the order “visible to the end user”. The end user wants to see menu entries of explicitly installed plugins before those of automatically installed plugins.

Lino now supports choicelist items without a value. When no value is specified, the value (the sequence number) is set automatically when it is added to the choicelist. Such choices should not be stored to the database, otherwise they are like normal choicelists. lino_xl.lib.vat.VatRules is the first usage example.

Lino now supports unbound data checkers. If lino.modlib.checkdata.Checker.model is None, the checker is unbound, i.e. the problem messages will not be bound to a particular database object.

Fixed a bug in diag : the plugins were listed in a random arbitrary order.

lino.core.plugin.Plugin.needed_by is now the immediate parent, not the top-level parent. The loop to the top is now done only in lino.core.plugin.Plugin.get_menu_group().

New property lino_xl.lib.vat.VatRegime.needs_vat_id. The chooser for lino_xl.lib.contacts.Partner.vat_regime now also depends on whether the partner has a VAT id or not. The choicelist of the vat_regime field of a voucher wasn’t yet filtered. New function lino_xl.lib.vat.get_vat_regime_choices() used by both choosers. The lino_xl.lib.vat.VatRegimes table now shows all these properties.

Changes in lino_xl.lib.eevat : removed regime “Private person (reduced)”. The regime “Private person” can now be used for any area. Selling to private persons in other countries was not yet allowed.

In lino_xl.lib.vat I changed declaration_plugins to declaration_plugin because I realized that you can have only one declaration plugin.

New config setting eu_country_codes, and the list is now complete (at least at the moment of writing this).

lino_xl.lib.sepa.Payable now gives a more comprehensible warning “No trade type for {}” when the trade type for the voucher is undefined.

I reviewed the demo fixture of lino_xl.lib.contacts. It has become more readable. It no longer creates cities which don’t exist (and instead omits partners in these cities). I removed München and Kelmis because these are difficult to lookup because their name varies with the languages used on the site. Each contact now has at least a city.

The demo fixture for lino_xl.lib.vat now sets fictive VAT numbers for each company.

Minor changes in the ordering of menu commands.

New property lino_xl.lib.vat.VatColumn.common_account and a new data checker to verify that every VAT column has an account configured if it requires one.


Fixed #2937 (Cannot add Duration and time). Updated the documentation about the lino.utils.quantities module.

Invoice generators have a new attribute default_invoiceable_qty whose default value is 1 (as it was until now, but now we can change the hard-coded default value per application).

New field lino_xl.lib.cal.EventType.default_duration per calendar entry type. If a calendar entry has a type (event_type) and if that type has a default duration, Lino will change the end_time of an entry when the start_date is changed (and the start_time when the end_date)

New field lino_xl.lib.cal.EventType.default_duration. If a calendar entry has a type (event_type) and if that type has a default duration (EventTypedefault_duration), Lino will change the end_time of an entry when the start_date is changed.

The lino_xl.lib.products plugin adds one menu entry per product type (lino_xl.lib.products.ProductTypes). When doing this, until now, it used the label of the lino_xl.lib.products.ProductType.table_name, now it uses the lino_xl.lib.products.ProductType.text.

The (description) of an order item is now a single-line CharField (not a multi-line RichTextField)


lino.utils.choosers now accepts choosers on char fields without a display method. Lino catches edge case of bad extjs code generation. Ticket #2916


Added ar param for lino.modlib.notify.ChangeNotifier.get_change_observers(). After creating record add elem to ar.selected_rows.

It is now possible to define a choices method for a lino.core.choicelists.ChoiceListField.

Limit the choices of Partner.vat_regime depending on the Partner.country and the available lino_xl.lib.vat.VatRules. (#2924)

Changes in lino_xl.lib.orders and lino_xl.lib.cal for #2776:

  • lino_xl.lib.orders.Order.project and lino_xl.lib.orders.Order.invoice_recipient were missing in OrderDetail.

  • lino_xl.lib.orders.Order.update_all_guests caused a UNIQUE error because the workers were being suggested twice.

  • Optimized the layout of lino_xl.lib.cal.EventDetail

  • When a user manually creates an event on a controller (lino.modlib.gfks.Controllable), then Lino now also calls lino.modlib.system.RecurrenceSet.before_auto_event_save() and lino_xl.lib.cal.EventGenerator.auto_cal_event_type() (if the controller is an instance of these)

  • The Explorer menu now shows the lino_xl.lib.products.PriceFactors.

2019-03-27 (v19.3.3 and v19.3.4)

Minor changes in lino_xl.lib.eevat: VAT rate 20% (not 21%). Removed regime “Delay in collection”.

Released Lino XL 19.3.3 and 19.3.4 to PyPI. In 19.3.3 lino_xl.lib.eevat failed.


Added optional _ar keyword param to @dd.chooser methods, to be able to access current user and actor info. Used by the chooser for lino_noi.lib.tickets.Ticket.site


Fixed notification order on dashboard. Added .dashboard-item class to divs in the dashboard. Made mark_all_seen action of MyMessages render in dashboard, and not require post-run refresh.


Disabled force refresh on update feature when running Lino on Pycharm. Fixed minor bug when submitting new ticket from dashboard in extjs3

Restore DEL key on the grid.

Released Lino 19.3.1 to PyPI.

Released Lino XL 19.3.2 to PyPI.


Added two new methods lino.core.site.Site.get_plugin_configs() and lino.core.plugin.Plugin.get_required_plugins(). Feature used by lino_xl.lib.vat.

New config setting lino_xl.lib.vat.Plugin.declaration_plugins.


  • Added a new plugin lino_xl.lib.eevat. This is a quickly adapted copy of bevat where we just removed the regimes that make no sense in Estonia. The declaration itself will need more work.



Release Lino 19.3.0

lino_xl.lib.vat can now be used without also using any of lino_xl.lib.bevat or lino_xl.lib.bevats. It defines a VAT regime normal and a VAT rule which allows everything.

lino_xl.lib.accounting.MatchRule now has allow_cascaded_delete set to “journal” (when you delete a journal, related match rules should delete automatically)


Fixed file upload dialog not closing correctly.


Added ensure_csrf_cookie decorator to all entry point views in extjs.


Added mobile_server_url attr to SITE, for use in sending notification emails. Have MailRenderer generate urls using actor.model.get_default_table().__name__ rather than actor.model.__name__ Means that the url will always point to an actor rather than a model which need to be redirected to an actor.


Add a new method Actor.get_actions_hotkeys() to enable hotkeys binding to actions on table.This method should return a list of hotkeys.

2019-03-11 (v 19.3.1)

Moved read_card_data_from_file() out of load_card_data(). This is just an internal change used for writing test cases.

Released XL 19.3.1 to PyPI.


Added alert_eval_js responce option, which is a js string that is evaluated after the alert dialog is closed.

Added Version checking, so that the server alerts the browser when it’s running an old version of lino.

2019-03-07 (v 19.3.0)

Released XL 19.3.0 to PyPI.


Added CSS classnames to insert, detail, form and actionForm Panel for use in e2e testing. Also for classnames for confirmation dialogs and main-menu, and action panel ok + cancel buttons.


Make it possible to the actions_hotkeys of a panel to set the ‘shift’ options.

Add new action lino_xl.lib.accounting.Voucher.changing_state() to the lino_xl.lib.accounting.Voucher. This action changes the invoice between the two Registered and Draft states. This action can be trigger using the Ctrl+X keyboard shortcut. It is defined in the lino_xl.lib.accounting.ui.Vouchers.get_actions_hotkeys() .


Courses with a Course.max_date before today are now longer available as choices when creating a new enrolment. As it was already before for Course.enrolments_until


Fixed #2811 (UnicodeError when re-reading a beid card where the diff contained non-ascii chars).


Uploading files under Python 3 caused a server error Exception Value: a bytes-like object is required, not 'str' (#2845).

Released Lino 19.2.1.

Fixed a bug in which caused a UnicodeEncodeError in export_excel : Exporting to Excel on Travis and possibly in other situations as well.

Released Lino 19.2.2.


It is now possible to easily redefine the detail layout for lino_xl.lib.cal.Rooms by overriding lino_xl.lib.cal.RoomDetail


Have the renderer return a js string that when eval’d reloads the dashboard, rather than a hard-coded string.


Make the field’s label following FileField visible #2830.


lino_xl.lib.accounting.Voucher.get_wanted_movements() now has a default implementation which returns no movements.


Translations for #2834.

More changes in the lino_xl.lib.orders plugin which is still work in progress for Lino Presto.


Added a button “Close and save window” (#2816)


Released Lino 19.2.0 to PyPI.

Added two columns volume library_file in UploadsByController

Released Lino XL 19.2.0 to PyPI.


The lino.modlib.uploads plugin has been extended to support #2826. Until now an Upload could represent either an uploaded file (the original meaning) or just an entry representing some external document to be monitored by its author, without any uploaded file. With #2826 we add a third possibility a “library file”, i.e. a file that has been stored on some volume using some other method than uploading.


  • Added a new model Volume

  • Added two fields volume and library_file to the Upload model.

  • The insert_layout of UploadsByControler does not include the volume, but instead the controller (owner) decides which volume is to be used.

    IOW a new method UploadController.get_uploads_volume(). The field should be hidden or at least readonly when the owner says that there is no volume.

Changes in lino_xl.lib.vat and lino_xl.lib.accounting to use the new “volumes” feature (library uploads). For #2826.



Fixed #2822 (Cannot create new user ‘NoneType’ object has no attribute ‘full_value_from_object’)

Fixed ActionFormPanel logic to use action.html_method.

Changed sign_in action to use POST as html_method.


In lino_xl.lib.beid we moved some functionality from BeIdCardHolder into a separate new mixin SSIN which can be used also when the plugin is not installed. Existing applications don’t need to adapt. Converted docstrings to prosa docs.

More changes in the lino_xl.lib.orders plugin which is still work in progress.


Field values for actons with paramiers no long need to be an array with a key of ‘fv’. They now can be included in the root of the data object with the field name as the key.


In lino_xl.lib.products we now have a new model PriceRule and a new choicelist PriceFactors (taken from lino_tera.lib.courses). For Lino Tera this means a minor data migration: change “courses.PriceRule” to “products.PriceRule” in the restore.py field.

We have a new plugin lino_xl.lib.orders that is being developed for Lino Presto. Not yet stable.


We fixed the #2782 (Dashboard in Jane is slower than before). Store has a new attribute _disabled_fields_storefield.


Changed the verbose name for lino.modlib.printing.BuildMethods from “Build method” to “Print method”.

The field lino_xl.lib.contacts.Role.type had a verbose name “Role” which was useless and irritating because “Function” is clear enough and the same word as in Configure ‣ Contacts ‣ Functions.

Optimized the detail layout of lino_xl.lib.accounting.Journal and the library base class for partner details (lino_xl.lib.contacts.PartnerDetail).

Fixed #2813 (the summary of lino_xl.lib.blogs.LatestEntries inserted an additional line break when rendering links to database objects using a memo command. Also the German translation did not correctly show date and author of a blog entry in this summary.


lino.sphinxcontrib.help_text_extractor caused a Sphinx warning RemovedInSphinx20Warning: app.info() is now deprecated. Use sphinx.util.logging instead. (fixed)

Added intersphinx_urls, srcref_url and doc_trees settings to the main module so that other doctrees can link to the docs.

Fixed a little bug in lino_xl.lib.vat : when you created an invoice in a journal with edit_totals and leave the total field empty, Lino said “TypeError: unsupported operand type(s) for -: ‘NoneType’ and ‘Decimal’”

Added intersphinx_urls, srcref_url and doc_trees settings to the main module so that other doctrees can link to the docs.

Released version 19.1.1


The change notes for Lino Extensions Library are now separated from those of The lino package.

New plugin attribute lino_xl.lib.tim2lino.Plugin.timloader_kwargs to be used e.g. as follows:

def setup_plugins(self):
        languages='de fr',
    super(Site, self).setup_plugins()

This new feature is not tested because the reason was just a missing “u” prefix.


The categories (lino_xl.lib.products.Category) now have a field product_type (i.e. all applications that depend on it need to migrate). This is because I realized that categories are not useless. The difference between the “category” and the “type” of a product is that end-users can edit the former while the latter are to be provided by the application developer.

I fixed a subtle bug in the lino_xl.lib.accounting.Plugin.setup_main_menu() method: the Accounting menu came before the Sales menu because a menu for “accounting” was being created before looping over the journal groups. I removed an unused plugin attribute intrusive_menu (whether a journal group is “intrusive” or not now depends on its menu_group).


The ref_max_length for lino_xl.lib.accounting.Journal is now 5 instead of the default 40.

Printing invoices was broken (since we changed the default build method from appy to weasy). It said “No template found for sales/VatProductInvoice/default.weasy.html, excerpts/default.weasy.html”. We created a new template sales/VatProductInvoice/default.weasy.html (in the config directory of lino_xl.lib.trading).


I fixed #2785 (Django 2.1.5 under Py3 restore.py fails saying disable_constraint_checking). For the test lino.utils.djangotest.RestoreTestCase, we need to make sure that foreign_keys is set to OFF before we actually start the restore.


I fixed #2784 (Some actions are duplicated). The show action of lino_welfare.modlib.integ.ActivityReport was duplicated in lino.core.actors.Actor._actions_list. Actually nobody ever complained because it was not visible. But since I wrote a test case in Lino Welfare (integ specs) which verifies that the ticket is fixed, I must now do a release on PyPI to get the test suite on Travis CI passing again.


We released Lino 19.1.2

Immediately after the release we discovered a bug in Lino 19.1.2 which caused a missing insert button in a critical place in Tera. So we did a quick bugfix release 19.1.3.


We released Lino 19.1.0

New lino.core.fields.TableRow.

The message “Form fields may not be submitted with invalid values” says now “Please check all fields of this form before submitting.” (linoweb.js)

We released XL 19.1.0

The fields addr2 and prefix are now mostly hidden in forms. We consider them obsolete. lino_xl.lib.contacts.