I'm not a fan of this idea for two (related) reasons:

1) This seems like something that's a relatively niche case to *want* to do
rather than doing unintentionally.
2) This vastly increases the chance of silent bugs in code.

With regards to #1, the main examples I've seen posited in this thread are
unpacking of unstructured object formats (e.g. JSON) and applying subsets
of key-values from a configuration file [which is basically another
unstructured object format). This seems like the level of functionality
that I'd expect a helper function to be the right choice for - it can be
part of the overall library handling the objects, or coded as a one-off for
smaller projects.

Regarding #2, passing unknown bags of values to functions is an easy way to
run into both logic and security errors - see for example the problems that
the Ruby on Rails ORM ran into with its batch-setter functionality when
developers didn't properly limit what values in objects could be updated
and forgot to sanitize inputs. Similarly, for keyword args with default
values, adding this functionality would make it easy for a typo to result
in a parameter that a user expects to be getting passed in not actually
getting passed, because the function got {foobra=1} instead of {foobar=1}
and silently discarded foobra=1 in favor of the default value for foobar.

There may be cases where passing an unknown bag is what you want to do, but
it's probably worth requiring that to be more explicit and intentional
rather than an easily-missed extra asterisk.

On Fri, Apr 12, 2019 at 4:09 PM Greg Ewing <greg.ew...@canterbury.ac.nz>
wrote:

> Bruce Leban wrote:
> > I think this is a real problem given the frequent convention that you
> > can freely add fields to json objects with the additional fields to be
> > ignored.
>
> Unpacking json objects isn't something one does every day, so I
> don't think it would be worth adding syntax just for this.
>
> Rather than new syntax, how about a helper function such as:
>
> def call_with_kwds_from(func, kwds):
>      code = func.__code__
>      names = code.co_varnames[:code.co_argcount]
>      func(**{name : kwds[name] for name in names})
>
> Usage example:
>
> def f(a, b):
>      print("a =", a, "b =", b)
>
> d = {"a": "a_value", "b": "b_value", "c": "something extra"}
>
> call_with_kwds_from(f, d)
>
> --
> Greg
> _______________________________________________
> Python-ideas mailing list
> Python-ideas@python.org
> https://mail.python.org/mailman/listinfo/python-ideas
> Code of Conduct: http://python.org/psf/codeofconduct/
>
_______________________________________________
Python-ideas mailing list
Python-ideas@python.org
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/

Reply via email to