Skip to content

Commandline <> Lib communication using generators #37

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 16 commits into from
Aug 31, 2017

Conversation

gronke
Copy link
Member

@gronke gronke commented Aug 27, 2017

implements #16

Specific class methods will allow to set a yields=True argument that will turn it into a Python generator. This generator will push status updates in form of libiocage.lib.events.*

Demo Snippets

This are some demos that demonstrate generators. They don't aim to be the exact output we will provide to the users.

Fetch: https://asciinema.org/a/CSpa7Nw9KMXrD4MAUo9TItNlI
List: https://asciinema.org/a/Azzsm7RBOdRCunwzQpcFcio3v
Bulk-Set: https://asciinema.org/a/8bUcbXAk3MPwfcOkq7RNoNNyG

Copy link
Collaborator

@igalic igalic left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

first look

except Exception:
raise
exit(1)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

i don't think raise and exit will do much taken together

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm sorry, but this is necessary to see python stacktraces, so I have this enabled until I prepare the branch for the merge. The errors that get swallowed from exit(1) are structural ones, not feature failures, so they are useful for development only. Already told @skarekrow that I'll find a better solution for this, because it lead to quite some confusion. For example this one #35 (comment)

:trollface:

@gronke gronke force-pushed the chore/cli-generators branch 5 times, most recently from a51e1bd to 2da2fe6 Compare August 29, 2017 00:27
@@ -332,7 +376,7 @@ def fetch_updates(self):
"Components"
))
f.truncate()
f.close()
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why are you removing this? I don't see it being used anywhere, this will result in leaking fd's

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

with is already taking care of that. See http://effbot.org/zone/python-with-statement.htm

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I know how with works ;) I commented on that in a different ticket. I just forgot to click that little expand thing.

if isinstance(event, libiocage.lib.events.IocageEvent):
yield event
else:
# the only non-IocageEvent is out return value
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

s/out/our/


self.log(message, level="spam", jail=jail, indent=indent)
# ToDo: Handle redrawig of multiline entries with different line count
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

s/redrawig/redrawing/ Sorry, OCD!

f"\033[{delta}F", # CPL - Cursor Previous Line
"\r", # CR - Carriage Return
self._indent(log_entry.message, log_entry.indent),
"\033[K", # EL - Erease in Line
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

s/Erease/Erase/

# ToDo: Handle redrawig of multiline entries with different line count

output = "".join([
#"\033[s", # SCP - Save Cursor Position
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If this is used (assuming you left a comment on it because it was useful), why is it commented out then?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was playing with various techniques to alter already printed output. Didn't get it to work as expected, but it was the most promising solution when it comes to multi-line editing

self._indent(log_entry.message, log_entry.indent),
"\033[K", # EL - Erease in Line
"\n" * delta
#"\033[s" # RCP - Restore Cursor Position
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same here

])

sys.stdout.write(output)
#print(log_entry.message)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Debug print

indent=0):
def screen(self, message, indent=0, **kwargs):
"""
Screen does never get printed to log files
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You can drop does for that sentence, then add a s to get

@@ -511,7 +552,7 @@ def _launch_jail(self):

def _start_vimage_network(self):

self.logger.log("Starting VNET/VIMAGE", jail=self)
self.logger.debug("Starting VNET/VIMAGE", jail=self)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why debug and not info?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The library is not supposed to print. Info/Log gets printed by default and we want all stdout to be generated from the event responses.

# "values: basic, digest")
# @click.option("--verify/--noverify", "-V/-NV", default=True,
# help="Enable or disable verifying SSL cert for HTTP fetching.")
# def cli(url, files, release, update):
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why are we removing current CLI flags?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because they were not implemented yet, so I removed it to clean up the file. Most probably #43 will cause need to re-apply and use this option. I've updated the CLI criteria for signature checking, so that it's not forgotten.

@gronke gronke force-pushed the chore/cli-generators branch 6 times, most recently from 87306eb to 21b6a29 Compare August 30, 2017 18:07
Copy link
Contributor

@skarekrow skarekrow left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Another quick review :)

output += event.get_state_string(
done="OK",
error="failed",
skipped="skipped",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

They should all be capitalized to keep with legacy's style. SKIPPED, FAILED.

@click.command(cls=IOCageCLI)
@click.version_option(version="0.9.10 07/30/2017", prog_name="iocage",
@click.version_option(version="0.2.11 08/29/2017", prog_name="ioc",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Where are you getting this versioning scheme from? Besides our placeholder release, we haven't discussed versioning much.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I started with 0.0.1 and everytime it will introduce new features I'd love to bump the minor version. For breaking changes (after 1.0.0) the major version number will increase. We should discuss and document the versioning system!

import libiocage.lib.Logger

supported_output_formats = ['table', 'csv', 'list']
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

JSON soon? :D

Copy link
Member Author

@gronke gronke Aug 30, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe now. That's super easy. But csv and list come with some nice optimizations - they stream their output. For JSON that would be useless :) But I will add it because it's a low hanging fruit!

Update: What about yaml?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

yaml is even lower hanging fruit! It should also buy us XML iirc

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

no no no double no

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@igalic I can understand that you want XML so badly, but we can't just disable all other list options just for that! :trollface: @skarekrow would be very disappointed if we drop the table output!


def _lookup_jail_value(jail, key):
if key in libiocage.lib.Jails.Jails.JAIL_KEYS:
# ToDo: Move this into lib/Jails ?
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This I think better belongs in helpers

except Exception:
failed_jails.append(jail)
continue
exit(1)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

exit after continue?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No exit! Was a left-over from the previous implementation. Will be cleaned with the next commit!

@@ -0,0 +1,275 @@
from timeit import default_timer as timer
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Missing iocage license

@@ -1,9 +1,38 @@
import os
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Missing iocage license

@@ -1,12 +1,13 @@
import re
from typing import Generator, Union, Iterable
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Missing iocage license


import libzfs

import libiocage.lib.Jail
import libiocage.lib.JailFilter
import libiocage.lib.helpers
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Are you running isort like CONTRIBUTING says? These look out of order, I'm seeing that around the files here in general

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Didn't care about the order yet. Let's put in a static analyzer rule in addition to the contribution guidelines.

I suggest to tackle those kind of changes in a separate PR, so that we concentrate on a specific feature in a PR. Too often features have implications to other parts of libiocage as well. But I'm pretty sure this will change in the near future after the interfaces are well tested.

#47 is the ticket for that

return jails
self._filters = None
self.filters = filters
list.__init__(self, [])
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Debug?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nope. Line 31 makes the _filters property available, the line below calls the filters property setter.

@gronke
Copy link
Member Author

gronke commented Aug 31, 2017

@skarekrow we can work on the license issue in a different PR :)

@gronke gronke force-pushed the chore/cli-generators branch 2 times, most recently from d5d02f0 to 150f500 Compare August 31, 2017 15:40
@gronke gronke force-pushed the chore/cli-generators branch from a87ce12 to 37e016f Compare August 31, 2017 17:15
skarekrow
skarekrow previously approved these changes Aug 31, 2017
skarekrow
skarekrow previously approved these changes Aug 31, 2017
@@ -661,22 +711,21 @@ def _teardown_mounts(self):
)

def _resolve_name(self, text):

if (text is None) or (len(text)==0):
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I know, you know I hate parenthesis, but I think this is a good example. It makes de-compacting that hard on my eyes. Instead of if test is None or len(text) == 0, it's easier to see those elements to me. I won't mark as needs changes, because it's your personal style ;)

But just felt I had to say it atleast! :D

@@ -85,7 +85,7 @@ def __init__(self, print_level=None, log_directory="/var/log/iocage"):

@property
def default_print_level(self):
return "spam"
return "info"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

info now? You told me that printed, does it not now?

@@ -213,7 +213,7 @@ def _set_name(self, name, **kwargs):
self["id"] = name
else:
try:
self["id"] = str(uuid.UUID(name)) # legacy support
self["id"] = str(uuid.UUID(name)) # legacy support
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since this is for legacy support, I think uuid would be a better indicator of what the id is. As id can be a bit ambiguous

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The ID brings together all the concepts of name and uuid :) It's the only true identifier of a jail.

@gronke gronke merged commit dcfc41e into master Aug 31, 2017
@gronke gronke deleted the chore/cli-generators branch August 31, 2017 23:59
Copy link
Collaborator

@igalic igalic left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

finally understood one of the errors that mypy is throwing at me

if self._validate_name_filter_string(filter_value) is False:
raise libiocage.lib.errors.JailFilterInvalidName(
filter_value,
logger=self.logger
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The class Term has no attribute logger, if it needs one, we should extend its __init__

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

there's now a patch for this #62

import libiocage.lib.Logger

supported_output_formats = ['table', 'csv', 'list', 'json']
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yay json!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants