Re: Imports and dot-notation

2023-08-09 Thread Cameron Simpson via Python-list

On 09Aug2023 12:30, Oliver Schinagl  wrote:
Looking at a python projects code and repository layout, we see the 
following directory structure.



/project/core
/project/components/module1
...
/project/components/moduleN
/projects/util

(this is far from complete, but enough to help paint a picture.

Some modules import other modules, and I see (at the very least) two 
(kind of three?) different ways of doing so.


`from project.components.module1 import function1, function2 as func, 
CONST1, CONST2 as CONST`


or maybe even (which has as an advantage that it becomes clear which 
namespace something belongs to


`from project.components.module1 import function1, function2 as 
module1_function2, CONST1, CONST2 as MODULE1_CONST2`


but then it really just becomes personal preference, as the number of 
characters saved on typing is almost negative (due to having a more 
complex import).



but also the dot notation being used

`from project.components import module1`

where obviously the functions are invoked as `module1.function1` etc

I hope the above is clear enough from an example.


Simply put, which of the two would be considered cleaner and more pythonic?


This is almost entirely a programmer preference thing.

The Zen, as usual, offers guideance but not dictates.

As you say, the module1.func form is very clear and has its beauty.  
Personally I lean towards the single name flavour, sometimes with a 
rename. FOr example, with os.path I often go:


from os.path import join as joinpath

and likewise for several other names from there, because the bare names 
are very generic (eg "join"). I see to be alone here. Many other people 
use:


import os.path

and use the full os.path.join in their code, which I find jarring and 
visually noisy.


Now for a bit more thought, looking at PEP8, we notes about imports, 
but sadly PEP8 does not state which method is better/preferred. While 
obviously in the end, it's always the maintainers choice in what they 
prefer, so are tabs vs spaces and PEP8 is opinionated about that too 
(in a good way, even though I'm not a fan :p).


PEP8 is for the stdlib source code; that said it is also the basis for 
most Python coding styles in the wild.


For me, the Zen's "readability counts" is the most important guideline; 
and to this end, your "module1.function" is an entirely reasonable 
response, particularly if you've got a lot of imports. But it does make 
for more verbose code, and that works against readability to a degree.


This is why it's all subjective.

Particular workplaces may mandate particular styles, but in your 
personal code? Do what seem best, and experience will cause that to 
evolve over time.


Also, the style can depend on the code you're working on. For a small 
module with few imports the:


from module1 import funcname

can be a win because the code is short, and this short form of funcname 
is both clear and readable. But in a very long piece of code with many 
imports you might go for module1.funcname for clarity, particularly if 
funcname is generic or overlaps with another similar imported name.


Cheers,
Cameron Simpson 
--
https://mail.python.org/mailman/listinfo/python-list


Re: Imports and dot-notation

2023-08-09 Thread dn via Python-list

On 09/08/2023 22.30, Oliver Schinagl via Python-list wrote:
...> Looking at a python projects code and repository layout, we see the

following directory structure.

/project/core
/project/components/module1
...
/project/components/moduleN
/projects/util

...> Some modules import other modules, and I see (at the very least) two

(kind of three?) different ways of doing so.

`from project.components.module1 import function1, function2 as func, 
CONST1, CONST2 as CONST`


or maybe even (which has as an advantage that it becomes clear which 
namespace something belongs to


`from project.components.module1 import function1, function2 as 
module1_function2, CONST1, CONST2 as MODULE1_CONST2`


but then it really just becomes personal preference, as the number of 
characters saved on typing is almost negative (due to having a more 
complex import).


but also the dot notation being used

`from project.components import module1`

where obviously the functions are invoked as `module1.function1` etc


Firstly, the path followed will depend upon the starting position!

Keep reading and you should come across a reference to 'hobgoblin of 
little minds'.


What should we be concentrating on/about? If 'naming' is a great (?the 
greatest) challenge of programming, surely remembering the names of 
classes, methods, functions, modules, etc; follows...
(and by implication, as you've illustrated, perhaps where they 
come-from), ie code is read more often than it is written, so think 
about comprehension rather than typing!



If one (one's team!) frequently uses a module, then a jargon may 
develop. For example:


import numpy as np
...
a = np.arange(6)

In which case, those au-fait with the jargon know that the "np." prefix 
tells them where "arange()" can be found - conversely, that if the IDE 
doesn't alert, that np/numpy must be (first) import-ed.


However, there is a cognitive-load to 'translate' "np" into "numpy". Not 
much, but then over-load is not a single thought but the combination of 
'everything'.


The second option (OP) is very (laboriously) clear in mapping the source 
of each function or constant. By way of comparison then, the code may 
now appear cluttered, because there's so much text to read. There would 
be less if an abbreviation were used.


The dev.tool in-use may also influence this decision. If hovering-over 
an identifier reveals source-information, what value the extra code? 
Intelligent completion also reduces relevance of 'number of characters 
saved on typing'.


Accordingly, give frequently-used functions/modules the abbreviation 
treatment -but only if YOU feel it right. Otherwise, use a longer-form 
to improve readability/comprehension.


THE answer will thus vary by library/package/module, by application, and 
by coder (jargon works best if 'all' use it/understand same).


Side note: Using "...import identifier, ..." does not save storage-space 
over "import module" (the whole module is imported regardless, IIRC), 
however it does form an "interface" and thus recommend leaning into the 
"Interface Segregation Principle", or as our InfoSec brethren would say 
'the principle of least privilege'. Accordingly, prefer "from ... import 
... as ...".


--
Regards,
=dn
--
https://mail.python.org/mailman/listinfo/python-list


Re: Planning a Python / PyData conference

2023-08-09 Thread Fulian Wang via Python-list
I recommend Sichuan ,Taiwan , or  Thailand

Get Outlook for iOS

From: Python-list  on 
behalf of dn via Python-list 
Sent: Wednesday, August 9, 2023 00:10
To: python-list@python.org 
Subject: Re: Planning a Python / PyData conference

Hi Wilber,


On 09/08/2023 14.28, Wilber H via Python-list wrote:
> Hi,
>
> I would like to plan a Python / PyData conference in the country of the
> Dominican Republic, and would like your feedback on how to best plan
> for the conference.

Recommend making your request of the folks who organise EuroPython
and/or PyConUS - and then same for smaller gatherings.

(would suggest to ours, but those folk are already over-loaded to be
ready in a few weeks' time)

--
Regards,
=dn
--
https://mail.python.org/mailman/listinfo/python-list
-- 
https://mail.python.org/mailman/listinfo/python-list


Imports and dot-notation

2023-08-09 Thread Oliver Schinagl via Python-list

Dear list,


First a disclaimer, I am a python novice ;) so apologies beforehand for 
any incorrect terms and use thereof :)


I have a question about the preferred/pythonic way dealing with imports. 
But let me start by giving a little bit of an example (which lead me to 
this question).


Looking at a python projects code and repository layout, we see the 
following directory structure.



/project/core
/project/components/module1
...
/project/components/moduleN
/projects/util

(this is far from complete, but enough to help paint a picture.

Some modules import other modules, and I see (at the very least) two 
(kind of three?) different ways of doing so.


`from project.components.module1 import function1, function2 as func, 
CONST1, CONST2 as CONST`


or maybe even (which has as an advantage that it becomes clear which 
namespace something belongs to


`from project.components.module1 import function1, function2 as 
module1_function2, CONST1, CONST2 as MODULE1_CONST2`


but then it really just becomes personal preference, as the number of 
characters saved on typing is almost negative (due to having a more 
complex import).



but also the dot notation being used

`from project.components import module1`

where obviously the functions are invoked as `module1.function1` etc

I hope the above is clear enough from an example.


Simply put, which of the two would be considered cleaner and more pythonic?

Now for a bit more thought, looking at PEP8, we notes about imports, but 
sadly PEP8 does not state which method is better/preferred. While 
obviously in the end, it's always the maintainers choice in what they 
prefer, so are tabs vs spaces and PEP8 is opinionated about that too (in 
a good way, even though I'm not a fan :p).


Likewise, if we look at PEP20, there's quite a few 'guidelines' that 
suggest the dot-notation. To name a few (opinionated) examples (but note 
I am just using PEP20 as a helper to give some arguments, I know some 
people feel strongly against pep20 :p):


* Beautiful is better than ugly.
  - Personally, I think the dot notation is more beautiful, but I 
understand that some people find the short notation more beautiful and 
less of an eye sore ;)


* Explicit is better than implicit.
  - To me, this is a strong point. Being more explicit is always 
better, using the dot notation (if though it's not doing the WHOLE path) 
is a nice balance in being explicit enough. Code readability comes from 
being more explicit (without being to terse of course).


* Simple is better than complex.
* Flat is better than nested.
  -  I think having more flat and simple imports, and (while more 
characters to potentially type in the invocation) more readable 
invocations would be better?


* Readability counts.
  - The dot notation seems to help in readability. For those unfamiliar 
(or less familiar) with a code base, it becomes incredibly clear where a 
something comes from (WITHOUT having to rely on IDE's; sure you can 
hover over something and see that the IDE has hopefully worked out where 
something came from, but this doesn't work when just reading a page of 
code, you aren't going to hover over everything and remember all that 
context).


* In the face of ambiguity, refuse the temptation to guess.
  - I'd argue this is almost self-explanatory, not using dot-notation 
makes it more ambiguous where something is coming from.


* There should be one-- and preferably only one --obvious way to do it.
  - This is where my confusion/question obviously comes from, as 
there's multiple ways of doing it, so maybe PEP8 (or a new one) should 
more strongly favor one?


* Namespaces are one honking great idea -- let's do more of those!
  - Basically, this question/proposal would 'force/nudge' you into 
writing more with namespaces by using the namespace as prefix.



So what IS the preferred/more pythonic/recommended way to deal with imports?

Why was this not mentioned in PEP8?

Is it worth while to introduce a new PEP or amend PEP8?


For what it's worth, hallucinating chatgpt/google bard both say the same 
about this topic, that within the python community, it is generally 
preferred and a good idea to use dot-notation. But how correct are they lol.



Thank you for reading,

Olliver



--
https://mail.python.org/mailman/listinfo/python-list


[Python-announce] SQLObject 3.10.2

2023-08-09 Thread Oleg Broytman
Hello!

I'm pleased to announce version 3.10.2, a minor feature release
and the second bugfix release of branch 3.10 of SQLObject.


What's new in SQLObject
===

The contributor for this release is Igor Yudytskiy. Thanks!

Minor features
--

* Class ``Alias`` grows a method ``.select()`` to match ``SQLObject.select()``.

Bug fixes
-

* Fixed a bug in ``SQLRelatedJoin`` in the case where the table joins with
  itself; in the resulting SQL two instances of the table must use different
  aliases. Thanks to Igor Yudytskiy for providing an elaborated bug report.

For a more complete list, please see the news:
http://sqlobject.org/News.html


What is SQLObject
=

SQLObject is a free and open-source (LGPL) Python object-relational
mapper.  Your database tables are described as classes, and rows are
instances of those classes.  SQLObject is meant to be easy to use and
quick to get started with.

SQLObject supports a number of backends: MySQL/MariaDB (with a number of
DB API drivers: ``MySQLdb``, ``mysqlclient``, ``mysql-connector``,
``PyMySQL``, ``mariadb``), PostgreSQL (``psycopg2``, ``PyGreSQL``,
partially ``pg8000`` and ``py-postgresql``), SQLite (builtin ``sqlite``,
``pysqlite``, partially ``supersqlite``); connections to other backends
- Firebird, Sybase, MSSQL and MaxDB (also known as SAPDB) - are less
debugged).

Python 2.7 or 3.4+ is required.


Where is SQLObject
==

Site:
http://sqlobject.org

Download:
https://pypi.org/project/SQLObject/3.10.2a0.dev20221222/

News and changes:
http://sqlobject.org/News.html

StackOverflow:
https://stackoverflow.com/questions/tagged/sqlobject

Mailing lists:
https://sourceforge.net/p/sqlobject/mailman/

Development:
http://sqlobject.org/devel/

Developer Guide:
http://sqlobject.org/DeveloperGuide.html


Example
===

Install::

  $ pip install sqlobject

Create a simple class that wraps a table::

  >>> from sqlobject import *
  >>>
  >>> sqlhub.processConnection = connectionForURI('sqlite:/:memory:')
  >>>
  >>> class Person(SQLObject):
  ... fname = StringCol()
  ... mi = StringCol(length=1, default=None)
  ... lname = StringCol()
  ...
  >>> Person.createTable()

Use the object::

  >>> p = Person(fname="John", lname="Doe")
  >>> p
  
  >>> p.fname
  'John'
  >>> p.mi = 'Q'
  >>> p2 = Person.get(1)
  >>> p2
  
  >>> p is p2
  True

Queries::

  >>> p3 = Person.selectBy(lname="Doe")[0]
  >>> p3
  
  >>> pc = Person.select(Person.q.lname=="Doe").count()
  >>> pc
  1

Oleg.
-- 
Oleg Broytmanhttps://phdru.name/p...@phdru.name
   Programmers don't die, they just GOSUB without RETURN.
___
Python-announce-list mailing list -- python-announce-list@python.org
To unsubscribe send an email to python-announce-list-le...@python.org
https://mail.python.org/mailman3/lists/python-announce-list.python.org/
Member address: arch...@mail-archive.com


SQLObject 3.10.2

2023-08-09 Thread Oleg Broytman via Python-list
Hello!

I'm pleased to announce version 3.10.2, a minor feature release
and the second bugfix release of branch 3.10 of SQLObject.


What's new in SQLObject
===

The contributor for this release is Igor Yudytskiy. Thanks!

Minor features
--

* Class ``Alias`` grows a method ``.select()`` to match ``SQLObject.select()``.

Bug fixes
-

* Fixed a bug in ``SQLRelatedJoin`` in the case where the table joins with
  itself; in the resulting SQL two instances of the table must use different
  aliases. Thanks to Igor Yudytskiy for providing an elaborated bug report.

For a more complete list, please see the news:
http://sqlobject.org/News.html


What is SQLObject
=

SQLObject is a free and open-source (LGPL) Python object-relational
mapper.  Your database tables are described as classes, and rows are
instances of those classes.  SQLObject is meant to be easy to use and
quick to get started with.

SQLObject supports a number of backends: MySQL/MariaDB (with a number of
DB API drivers: ``MySQLdb``, ``mysqlclient``, ``mysql-connector``,
``PyMySQL``, ``mariadb``), PostgreSQL (``psycopg2``, ``PyGreSQL``,
partially ``pg8000`` and ``py-postgresql``), SQLite (builtin ``sqlite``,
``pysqlite``, partially ``supersqlite``); connections to other backends
- Firebird, Sybase, MSSQL and MaxDB (also known as SAPDB) - are less
debugged).

Python 2.7 or 3.4+ is required.


Where is SQLObject
==

Site:
http://sqlobject.org

Download:
https://pypi.org/project/SQLObject/3.10.2a0.dev20221222/

News and changes:
http://sqlobject.org/News.html

StackOverflow:
https://stackoverflow.com/questions/tagged/sqlobject

Mailing lists:
https://sourceforge.net/p/sqlobject/mailman/

Development:
http://sqlobject.org/devel/

Developer Guide:
http://sqlobject.org/DeveloperGuide.html


Example
===

Install::

  $ pip install sqlobject

Create a simple class that wraps a table::

  >>> from sqlobject import *
  >>>
  >>> sqlhub.processConnection = connectionForURI('sqlite:/:memory:')
  >>>
  >>> class Person(SQLObject):
  ... fname = StringCol()
  ... mi = StringCol(length=1, default=None)
  ... lname = StringCol()
  ...
  >>> Person.createTable()

Use the object::

  >>> p = Person(fname="John", lname="Doe")
  >>> p
  
  >>> p.fname
  'John'
  >>> p.mi = 'Q'
  >>> p2 = Person.get(1)
  >>> p2
  
  >>> p is p2
  True

Queries::

  >>> p3 = Person.selectBy(lname="Doe")[0]
  >>> p3
  
  >>> pc = Person.select(Person.q.lname=="Doe").count()
  >>> pc
  1

Oleg.
-- 
Oleg Broytmanhttps://phdru.name/p...@phdru.name
   Programmers don't die, they just GOSUB without RETURN.
-- 
https://mail.python.org/mailman/listinfo/python-list


zoneinfo and tzdata

2023-08-09 Thread Mike Dewhirst via Python-list
The zoneinfo module does not work on Windows unless you have installed 
tzdata.


On Ubuntu that data seems to exist already. Not sure how or why but it 
obviously isn't there in a Windows virtualenv unless deliberately installed.


I just spent a bit of time trying to switch from pytz to zoneinfo in 
Django without luck. I then asked and greatly embarrassed ChatGPT which 
kept apologizing when I fed back all the zoneinfo errors its advice caused.


It wasn't until I read the docs that I saw zoneinfo would get timezone 
data from tzdata if the real info wasn't where it first looked.


As soon as I installed tzdata, ChatGPT's advice started to work. When I 
reported this, it was very grateful and assured me my generosity in 
bothering to correct it would be very beneficial for other users having 
similar problems.


Might I suggest that if zoneinfo comes up empty-handed it should raise 
an error saying no timezone information was found?


Currently, it just nominates the timezone key you attempt to use. Behind 
the scenes it surely knows there are no such keys. In that case it might 
suggest installing tzdata.


Cheers

Mike
--
https://mail.python.org/mailman/listinfo/python-list