Wesley Leggette schrieb:
Since it is impossible to conviently store report setups
(except by manually backing them up) without keeping them open, I like
to keep them open. (...)

Of course, I suppose just adding the ability to save reports, and even
better groups of reports, would go a long way. To elaborate, you could
export or bookmark or whatever your custom configurations for reports.
You could then also group them together and open the whole group at
once. Very neat.

This is one of the features most regularly asked for. Although a clean implementation of that would require additional GUI components and probably quite some code and time, I nevertheless came up with an idea that might do already:


The options of an opened report are stored in ~/.gnucash/books/my_book_name as scheme code. The report is restored by running this scheme code and calling gnc:report-restore (in src/reports/report-system/report.scm) afterwards. How difficult would it be to turn these two steps from restoring a report into a new call of the gnc:define-report function, hence offering a new report? It would be well sufficient to have a manual procedure involving text file manipulation, but fully outside gnucash. A step-by-step instruction to create your own report would read as follows:

1. In gnucash, open the report. Change the options so that it shows what you want. Close gnucash while leaving that report window opened.
2. Open the file ~/.gnucash/books/<your_book_name> with your favorite text editor.
3. Find the section entitled ";; options for report <your_report_name>". For each of your still-opened reports, there is one such section. If you have multiple reports based on the same template, you need to figure out which one you want by looking closely at each report's options.
4. Copy the section with the report options into a new text file, e.g. "my-report.scm". The section starts with the command "(let ((options ..." and it ends with the closing parentheses that closes the opening parentheses before the "let" command.
5. In "my-report.scm", replace ??? (FIXME: see below) inside your pasted section by ???.
7. Save "my-report.scm" in your gnucash scheme directory. If your gnucash installation was installed with the prefix /usr, then this is in /usr/share/guile-modules/gnucash/reports/ (FIXME: is this correct?)
8. In the file "report-system.scm" that can be found in that very same directory (FIXME: is this correct?), append the line


(load-from-path "my-report.scm")

at the very end of that file. This makes gnucash aware of your new report file. If your new file contains any errors that gnucash complains about, you can always remove this load-from-path command from this file and gnucash will load normally again. Watch out: Each time you install a new version of gnucash, the file report-system.scm will be overwritten and you will have to insert this line again. But all other steps are not affected by a new installation of gnucash.

As for the code that needs to be added: For sure, the normal report definition has to be done as usual:

(gnc:define-report
  'version 1
  'name "My personalized report about my Income"
  'options-generator ???
  'renderer ???)

The renderer should probably be the very same function that is already used in the original report definition file, e.g. accsum-renderer from account-summary.scm for the account summary report. It might be necessary to add an additional (export accsum-renderer) in that files, but I'm not too sure about this. OTOH the options-generator is probably the key to implement this customizing of the report:

Usually, the options-generator is a function that returns the appropriate options object. In the scheme code from the user's file with the saved options, we actually already have that options object available. The saved options code ends with the command

  (gnc:restore-report report-id report-type options)

where "options" is precisely the options object as returned by the original options-generator, but now changed into our customized settings. So all that we need to do is to replace the gnc:restore-report command by a gnc:define-report command, where the options-generator now is a lambda that directly returns this very customized options object. How about this (with a customized account summary as an example):

  (gnc:define-report
   'version 1
   'name "My customized account summary"
   'options-generator (lambda() options)
   'renderer accsum-renderer)

To summarize: The full options command before the manual change would read like this:

;; options for report "My customized summary"
(let ((options (gnc:report-template-new-options/name "Account Summary")))
(let ((option (gnc:lookup-option options "General" "Name")))
((lambda (option) (if option ((gnc:option-setter option) "My customized summary"))) option))
;; ... more options ...
(gnc:restore-report 1234 "Account Summary" options))


After the manual change, the command would read like this:

;; options for report "My customized summary"
(let ((options (gnc:report-template-new-options/name "Account Summary")))
(let ((option (gnc:lookup-option options "General" "Name")))
((lambda (option) (if option ((gnc:option-setter option) "My customized summary"))) option))
;; ... more options ...
(gnc:define-report
'version 1
'name "My customized summary"
'options-generator (lambda() options)
'renderer accsum-renderer))


One very last quirk: When defining a new report, the "Report Name" and "Stylesheet" options are *always* added by the report system (in gnc:report-template-new-options), not by the original options-generator. In our case this means that the options object with the customized settings already contains these options, although gnc:define-report is going to register them again. What is the behaviour of (hash-set! section-hash name new-option), if the section-hash already contains an element with the key "name"? Does it silently overwrite the existing object, does it fail, or does it create a second entry? Pretty much all three cases are not what we want. The simplest solution would be to register these two options in gnc:report-template-new-options (in report.scm) only if they don't exist yet, i.e. change

        (let ((options (generator)))
          (gnc:register-option options stylesheet)
          (gnc:register-option options namer)
          options)

into

(define (lookup-existing-option options option)
(if option
(gnc:lookup-options options (gnc:option-section option) (gnc:option-name option))
#f))
(let ((options (generator)))
(if (not (lookup-existing-option options stylesheet))
(gnc:register-option options stylesheet))
(if (not (lookup-existing-option options namer))
(gnc:register-option options namer))
options)





_______________________________________________ gnucash-devel mailing list [EMAIL PROTECTED] https://lists.gnucash.org/mailman/listinfo/gnucash-devel

Reply via email to