[GRASS-dev] move everything from /lib/init/grass.py to /lib/python/init

Vaclav Petras wenzeslaus at gmail.com
Wed Jul 19 07:00:15 PDT 2017


On Wed, Jul 19, 2017 at 1:42 AM, Pietro <peter.zamb at gmail.com> wrote:

> On Mon, Jul 17, 2017 at 5:36 PM, Vaclav Petras <wenzeslaus at gmail.com>
> wrote:
>
>>
>> On Mon, Jul 17, 2017 at 12:36 AM, Pietro <peter.zamb at gmail.com> wrote:
>>
>>>
>>> On Fri, Jul 14, 2017 at 6:00 PM, Vaclav Petras <wenzeslaus at gmail.com>
>>> wrote:
>>>
>>>> This is exactly what I had in my mind when doing the last major changes
>>>> in the grass.py file.
>>>>
>>> I generally like the layout you suggested. It seems to me that choosing
>>>> a good name for the whole module will be a bit tricky.
>>>>
>>>
>>> This is intended as a proof of concept to see the feasibility.
>>> I've try to found a better name but didn't come up to my mind...
>>> Perhaps: session instead of init?
>>>
>>> My final objective is to be able to do something like:
>>>
>>
>> That makes sense. In fact, that's very similar to a file I drafted some
>> time ago splitting the data initialization and runtime in
>> grass.script.setup and adding Session (see the attached file). Another
>> example, for a different case, is here:
>>
>> https://github.com/wenzeslaus/g.remote/blob/master/grasssession.py
>>
>
> Nice module, I was not aware of it!
> However I think that the purpose is slightly different. The grassession
> aims is to generate the session remotely, here I would like to setup a
> local session. It is true that I should be able to just connect through ssh
> to the localhost... but it seems to me not the right way.
>

Sure, the code is for use remote session on another computer, although by
switching the backend you can use the API for local session (without any
ssh to localhost):

https://github.com/wenzeslaus/g.remote/blob/master/localsession.py

What I'm bring up here is the idea of a Session API which works the same
for local session, remote session, or multiple sessions (in one script).


> So I've sketch a possible implementation just to see how it could work,
> see:
>
> https://git.osgeo.org/gogs/zarch/grass/commit/
> b9cb69a1d7381924b0c2229ba43f21b1b7473c72
>
>
Looks nice and clean. The difference to the above is that it does not
contain API for actually executing anything which removes the dependency
problems I mentioned earlier. This is probably much more fitting to the
current session as opposed to the remote (or generally "other") session as
used in g.remote. In other words, we have two different concepts for a
Session object (API): SessionA which sets the global state and thus sets up
a current session and SessionB which sets up a session which is remote or
local (but does touch the global state, i.e. the current session). SessionA
does not have any extra functions and all is executed through standard
(current) APIs while SessionB needs to provide all (or at least some)
functions for execution of modules or code (e.g. g.remote executes scripts).

Besides the fact that SessionA and SessionB have very different APIs and
behavior, my concern is that I think we should consider (and possibly
cover) the use case of parallel processing in different mapsets or parallel
rendering. SessionA is not good for this. SessionB is.

Another concern is the usage of context manager. It makes sense. It is a
resource, you connect, you open. But the state which is changes is global.
Is that expected from context manager? I don't know, I need to read the PEP.


> from grass.init import Session
>>>
>>> # with statement
>>> with Session('mygisdbase/location/mapset') as session:
>>>     # do my stuff here
>>> ```
>>>
>>>
>>
>> Unfortunately, here is where the trouble begins. The above leads to the
>> following:
>>
>> with Session as session:
>>     session.run_command(...)
>>
>> which fits with API which already exists for Ruby:
>>
>> https://github.com/jgoizueta/grassgis/
>>
>> GrassGis.session configuration do+
>>     r.info 'slope'
>>     g.region '-p'
>> end
>> The trouble is that session (at least in Python) needs to depend on the
>> rest of the library because it is the interface for the rest (on demand
>> imports may help here).
>>
>
> Sorry I'm not sure that I get your point here, what do you mean?
> The following code is running at the moment on my machine:
>
> ```python
> import os
> import sys
>
> MAPSET = '/home/pietro/docdat/gis/nc_basic_spm_grass7/user1/'
> GISBASE = '/home/pietro/docdat/src/gis/ggrass/dist.x86_64-pc-linux-gnu/'
>
> # set the path
> sys.path.append(os.path.join(os.environ.get('GISBASE', GISBASE),
>                              'etc', 'python'))
>
> # import the python GRASS libraries
> from grass.script.core import run_command
> from session import Session
>
>
> with Session(MAPSET) as session:
>     run_command('r.slope.aspect', elevation='elevation',
>                 slope='slope', aspect='aspect',
>                 overwrite=True)
> ```
>
>
My concern is just another concern about the context manager. Is is OK that
it is actually not used in the with block? Again, that's something PEP
hopefully answers.

Whatever would be the default usage, I can see how it could be used. Here
is an example for the use case when we are currently passing the env
parameter (like the parallel processing mentioned above):

```
with Session(MAPSET) as session:
    run_command('r.slope.aspect', elevation='elevation',
                slope='slope', aspect='aspect',
                overwrite=True, env=session.env)
```


>
> So perhaps having grass.init or grass.setup with the low level functions
>> and then a separate grass.session with a nice interface which may depend on
>> all other modules may be a better way. (Although having each function from
>> the library as a method of Session calls for more thinking about
>> grass.session.Session.
>>
>
> I was thinking to add this Session class definition inside init/session.py
> to then try to refactor the main function in parser.py:
>
> https://git.osgeo.org/gogs/zarch/grass/src/grass_session/
> lib/python/init/parser.py#L189
>
> to start a session and then execute all the rest of the functions to
> start/use the grass shell/gui.
>
>

I'm not sure what are the changes you plan. What I can say now is that I
suggest to not use the name parser.py as it means something very specific
in GRASS. I'm also not sure if main() of lib/init/grass.py should be part
of the library (it seems to me actually impossible as it should be on the
executable path rather than a library path).
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.osgeo.org/pipermail/grass-dev/attachments/20170719/d232c8f3/attachment.html>


More information about the grass-dev mailing list