[GNC-dev] Python-Bindings: issue when C expects GList argument

Matteo Lasagni laser820 at gmail.com
Tue May 10 17:23:01 EDT 2022


If I can find a good solution, yes, I will put it in a pull request.

I have tried to encapsulate Transaction* in a list, but of course it
doesn't work without touching swig definitions.
I am now trying to create a specific typemap for handling the double
pointer. I think this would be the cleanest solution.

Alternatively, a quick and dirty workaround is to add a C wrapper in
gncOwner.c that expects Transaction* and passes Transaction** to
gncOwnerCreatePaymentLotSecs:


GNCLot *
gncOwnerCreatePaymentLotSecsPyHelper (const GncOwner *owner, Transaction
*txn, Account *posted_acc, Account *xfer_acc, gnc_numeric amount,
gnc_numeric exch, time64 date, const char *memo, const char *num)
{
    return gncOwnerCreatePaymentLotSecs(owner, &txn, posted_acc, xfer_acc,
amount, exch, date, memo, num);
}


regards,
Matteo

On Tue, 10 May 2022 at 17:25, john <jralls at ceridwen.us> wrote:

>
>
> On May 10, 2022, at 1:53 AM, Matteo Lasagni <laser820 at gmail.com> wrote:
>
> Thank you, John!
>
> I fixed it by adding the following into base-typemaps.i:
>
> %typemap(in) GList * {
>     $1 = NULL;
>     /* Check if is a list */
>     if (PyList_Check($input)) {
>         int i;
>         int size = PyList_Size($input);
>         for (i = size-1; i >= 0; i--) {
>             PyObject *o = PyList_GetItem($input, i);
>             $1 = g_list_prepend($1, o);
>         }
>     } else {
>         PyErr_SetString(PyExc_TypeError, "not a list");
>         return NULL;
>     }
> }
>
> I had overlooked the swig definition in engine.i, where there is a typemap
> (in) for GList, but then it is cleared right afterwards...
> I am not (yet) very familiar with swig :-)
>
> I have also noticed that CreatePaymentLotSecs does not work out of the
> box, as it expects **Transaction while only *Transaction is type mapped.
>
> I will test these changes then I will figure out how to share them with
> the developers.
>
>
> Matteo
>
>
> On Tue, 10 May 2022 at 02:32, John Ralls <jralls at ceridwen.us> wrote:
>
>>
>>
>> > On May 9, 2022, at 2:17 PM, Matteo Lasagni <laser820 at gmail.com> wrote:
>> >
>> > Hi,
>> > I am writing a python script to automatically associate a set of
>> > invoices to a single transaction.
>> > To this end, I am trying to use the function AutoApplyPaymentsWithLots
>> > with no success:
>> >
>> >
>> > lots = [lot1, lot2, lotn, ..]
>> > owner.AutoApplyPaymentsWithLots(lots)
>> >
>> > This causes the following error:
>> >
>> > TypeError: in method 'gncOwnerAutoApplyPaymentsWithLots', argument 2 of
>> > type 'GList *'
>> >
>> > I have tried different solutions from passing different types of python
>> > objects, to updating the swig typemap and also to modifying the
>> > auto-generated gnucash_core.c...nothing worked out so far.
>> > I could write an additional c-wrapper, but I am sure there is a more
>> > general solution.
>>
>> The fundamental problem is that there's only a Python out typemap for
>> GList, that is one that converts from a GList* to a python list. Lacking an
>> in typemap the gncOwner.AutoApplyPaymentsWithLots python wrapper expects an
>> already constructed and Swig-wrapped GList*.
>>
>> Regards,
>> John Ralls
>>
>>
>
> Nice. Would you put that in a pull request?
>
> There are two typemap(in) GList* in engine.i, but they're both for Guile
> (Scheme), not Python. 'scm' is the giveaway.
>
> If there's a way to implement an output pointer parameter in Python I
> don't know about it. You can pass in a container object and put the output
> Transaction* in the container, but that's both a bit of a hack and doesn't
> have the same meaning as Transaction** nor is it very pythonic. Nor, for
> that matter, is gncOwnerCreatePaymentLotSecs a very good design as it mixes
> responsibilities. Unfortunately there's a lot of that in GnuCash because
> most of it is written with a very narrow focus, in this case providing for
> the payments dialog.
>
> Regards,
> John Ralls
>
>

-- 

-------------
Matteo Lasagni


*"You can't connect the dots looking forward,you can only connect them
looking backwards"* [Steve Jobs]


More information about the gnucash-devel mailing list