Continue writing thesis
This commit is contained in:
parent
2f728dc353
commit
137fde57ca
@ -128,3 +128,12 @@
|
||||
year={2017},
|
||||
month=dec,
|
||||
}
|
||||
|
||||
@online{SemancatVersioning,
|
||||
title={Semancat versioning},
|
||||
url={https://blog.avatao.com/semancat-versioning/},
|
||||
language={english},
|
||||
author={Kristóf Tóth},
|
||||
year={2018},
|
||||
month=sep,
|
||||
}
|
||||
|
@ -4,3 +4,27 @@
|
||||
This creation of this framework would not have been possible alone.
|
||||
In this chapter I would like to express my gratitude towards great people who have
|
||||
helped me in some way or an other along the way.
|
||||
|
||||
First of all I would like to thank Bálint Bokros, my good friend and colleauge for
|
||||
his awesome work during the initial phases of development and for always
|
||||
being open to provide useful input.
|
||||
He has also earned my gratitude by always being there to lift my spirits, be that
|
||||
with beer or general friendship things.
|
||||
|
||||
I'd also like to thank Gábor Pék and Márk Félegyházi,
|
||||
for letting us make this project possible by always setting reasonable goals,
|
||||
being there to provide feedback and encouraging us along the way.
|
||||
Gábor Pék also contributed to this in several ways, for which we always will be
|
||||
grateful.
|
||||
|
||||
I can't thank my consultant, Levente Buttyán enough for enduring my general
|
||||
inability to deal with deadlines and administration.
|
||||
|
||||
I also appreciate the company my colleagues have provided in the office,
|
||||
by always being there be that for work or fun. They also have my gratitude
|
||||
for general contributions to the framework, be that with ideas, assistance,
|
||||
or actual code.
|
||||
|
||||
Finally I'd like to thank all the developers for using the framework and creating
|
||||
great tutorials with it. They always provide useful feedback, bug reports, and
|
||||
have great feature requests or even contributions.
|
||||
|
@ -149,7 +149,8 @@ a related task.
|
||||
This teacher scenario would allow you to take the helm sometimes and try applying
|
||||
your newfound skills in action immediately.
|
||||
|
||||
For example a chatbot would show you how to encrypt a file using GnuGP,
|
||||
For example a chatbot would show you how to encrypt a file using GnuGP%
|
||||
\footnote{\href{https://www.gnupg.org}{https://www.gnupg.org}},
|
||||
then it would ask you to encrypt an other file similarly.
|
||||
After this the bot could teach you how to a configure a database server and then
|
||||
ask you to write a configuration file yourself and then encrypt it because it might
|
||||
|
@ -3,4 +3,86 @@
|
||||
In this chapter I am going to evaluate the state of the project and set future goals for
|
||||
the framework.
|
||||
I'll also try and reflect on some of the most important things I have learned during
|
||||
working on this project in case it might be useful for someone in the future.
|
||||
working on this it, in case I've experienced something that might be useful for
|
||||
someone else reading this in the future.
|
||||
|
||||
\section{Project Evaluation}
|
||||
|
||||
How do we define if a project is a success or not?
|
||||
Instead of trying to do so, in this section I am going to express
|
||||
my personal feelings and opinions about the Tutorial Framework.
|
||||
To get unbiased opinions I'd recommend asking someone who hasn't been maintaining
|
||||
this project for so long.
|
||||
I could promise to be as objective as possible, but I think that it is just better
|
||||
to admit that I have a sweet spot for this project.
|
||||
|
||||
Currently a total of 63 tutorials based on the framework are running in production,
|
||||
with new ones being released on a weekly basis.
|
||||
These exercises have been solved several hunders of times.
|
||||
User feedback is getting better and better as the project moves forward.
|
||||
As a maintainer currently I know about a single unfixed bug in the framework, which
|
||||
is getting reported by users as well.
|
||||
There are more, of course, the world is never going to run out of bugs to fix,
|
||||
but I sleep well knowing that things aren't breaking on a constant basis.
|
||||
Considering that this is a one year old project including initial development,
|
||||
I'd consider this a solid success.
|
||||
|
||||
We were able to achieve most of the goals we have envisioned on the beginning of
|
||||
this journey, and considering some of the things we have planned for the future
|
||||
we are just getting started.
|
||||
|
||||
\section{I Have a Plan!}
|
||||
|
||||
In this section I'd like to set some goals regarding the future of the framework
|
||||
apart from implementing new features (new features will always come in as we go).
|
||||
|
||||
First of all I think that we need to put more focus on developing TFW, as currently
|
||||
other projects are often being priorized over it.
|
||||
While some of these are understandable, the framework is a very promising project
|
||||
with great potential and deserves more attantion from us.
|
||||
The fact that it is stable does not validate neglecting it.
|
||||
|
||||
I'd also like to concentrate on stabilizing the API of the framework.
|
||||
Currently each major release lasts for a few months before I am forced to break something
|
||||
to accomodate new features.
|
||||
While the communication of these breakages is fine --- we use mailing lists for this purpose
|
||||
and our versioning scheme seems solid so far, this forces developers
|
||||
to constantly update older tutorials to comply new API.
|
||||
To make this better I'd need to consider planning ahead more, so that the newest API is flexible
|
||||
enough to support new features on the roadmap and not get distracted as much by
|
||||
other features emerging on the horizon.
|
||||
|
||||
An other thing is that I often feel like that there are some things in using the framework
|
||||
that could be made a lot easier. As a maintainer sometimes I find it hard to
|
||||
tell what these things are, as I know TFW inside out, having written most
|
||||
of the codebase myself.
|
||||
I'd like to set some time aside to create tutorials using the framework myself
|
||||
so I can better narrow these potential difficulities down.
|
||||
|
||||
Currently the framework is proprietary software.
|
||||
While it is not feasible to go open source today or tomorrow for various reasons,
|
||||
we all believe that software which is free as in freedom \emph{is} the future.
|
||||
As such, at some point I'd like to open source the whole thing if the circumstances will allow
|
||||
us to do so.
|
||||
|
||||
\section{Things That I Have Learned}
|
||||
|
||||
I've spent a long time working on and maintaining this project.
|
||||
While the list of technical things I've learned is long and exciting, I also feel like
|
||||
I've learned a lot about supporting other developers, project management and communication.
|
||||
|
||||
A thing that I will always remember as a software engineer and I've learned during this period
|
||||
is to never, ever lower my expectations regarding code quality.
|
||||
No matter what anybody tells you about ``but we have to finish until'' and stuff like that,
|
||||
in the long run it is always like shooting yourself in the foot.
|
||||
We as professionals must always thrive for excellence, and must always express our
|
||||
deepest respect towards our craft.
|
||||
The only way we can do this is by creating quality software as craftsmen.
|
||||
Many developers fail to understand that no matter how insignificant the code you write
|
||||
today may seem, software is art, and art is something worth pursuing just for the sake
|
||||
of doing art itself.
|
||||
\emph{If} that art has some purpose --- and usually the code we write has ---
|
||||
that is a good thing, but not something that we always have to keep in mind.
|
||||
More often than not will you find, that while creating that funky little piece of
|
||||
code with no purpose back in the day, it is you who have learned something new and
|
||||
valuable.
|
||||
|
@ -212,6 +212,25 @@ The use of this directory is not mandatory, only a good practice, as developers
|
||||
are free to implement the non-TFW parts of their exercises as they see fit
|
||||
(the copying of these files into image layers are their resposibility).
|
||||
|
||||
\section{Configuring Built-in Components}
|
||||
|
||||
The configuration of built-ins is generally done in two different ways.
|
||||
For the frontend (Angular) side, developers can edit a \code{config.ts} file,
|
||||
which is full of key-value pairs of configurable frontend functionality.
|
||||
These pairs are generally pretty self-documenting:
|
||||
\lstinputlisting[
|
||||
caption={Example of the frontend \code{config.ts} file (shortened to save space)},
|
||||
captionpos=b
|
||||
]{listings/config.ts}
|
||||
Configuring built-in event handlers is possible by editing the Python file they are
|
||||
initialized in, which exposes several communicative options through the
|
||||
\code{__init__()} methods of these event handlers:
|
||||
\lstinputlisting[
|
||||
language=python,
|
||||
caption={Example of inicializing some event handlers},
|
||||
captionpos=b
|
||||
]{listings/event_handler_main.py}
|
||||
|
||||
\section{Impelenting a Finite State Machine}
|
||||
|
||||
The Tutorial Framework allows developers to define state machines in two ways,
|
||||
@ -255,23 +274,31 @@ programming language is usable to implement said callbacks.
|
||||
The advantage of the Python version is that since the framework is being developed in
|
||||
Python as well, it is going to be easier to interface with library code.
|
||||
|
||||
\section{Configuring Components}
|
||||
\section{Implementing Event Handlers}
|
||||
|
||||
The configuration of built-ins is generally done in two different ways.
|
||||
For the frontend (Angular) side, developers can edit a \code{config.ts} file,
|
||||
which is full of key-value pairs of configurable frontend functionality.
|
||||
These pairs are generally pretty self-documenting:
|
||||
\lstinputlisting[
|
||||
caption={Example of the frontend \code{config.ts} file (stripped down to save space)},
|
||||
captionpos=b
|
||||
]{listings/config.ts}
|
||||
Configuring built-in event handlers is possible by editing the Python file they are
|
||||
initialized in, which exposes several communicative options:
|
||||
In this section I am going to showcase how implementing event handlers is possible
|
||||
when using the framework.
|
||||
I am going to use the Python programming language, but it isn't hard
|
||||
to create event handlers in other languages, because the only thing
|
||||
they have to be capable of is communicating with the TFW server using
|
||||
ZeroMQ sockets, as previously discussed.
|
||||
The library provided by the framework abstracts low level socket logic
|
||||
away by implementing easy to use base classes.
|
||||
Creating such base classes in a given language shouldn't take longer
|
||||
than a few hours for an experienced developer.
|
||||
Our challenge creators have already implemented similar libraries for
|
||||
Java, JavaScript and C++ as well.
|
||||
\lstinputlisting[
|
||||
language=python,
|
||||
caption={Example of inicializing some event handlers},
|
||||
caption={A very simple event hander implemented in Python},
|
||||
captionpos=b
|
||||
]{listings/event_handler_main.py}
|
||||
]{listings/event_handler_example.py}
|
||||
This simple event handler subscribes to the \code{fsm_update} messages,
|
||||
then the only thing it does is writing the
|
||||
messages received to the messages component on the frontend.
|
||||
When using the TFW library in Python, all classes inheriting from
|
||||
\code{EventHandlerBase} must implement the \code{handle_event()}
|
||||
abstract method, which is used to, well, handle events.
|
||||
|
||||
\section{Setting Up a Developer Environment}\label{devenv}
|
||||
|
||||
@ -429,3 +456,33 @@ is present or not, and only deal with the frontend if this argument is not defin
|
||||
The \code{|| :} notation in bash basically means ``or true'', which is required
|
||||
to avoid aborting the build due to the non-zero return code produced
|
||||
by the \code{test} command if the build arg is defined.
|
||||
|
||||
\section{Versioning and Releases}
|
||||
|
||||
Currently I use git tags%
|
||||
\footnote{\href{https://git-scm.com/docs/git-tag}{https://git-scm.com/docs/git-tag}}
|
||||
to manage releases of the TFW baseimage.
|
||||
Each new release is a tag digitally signed by me using GnuPG so that
|
||||
everyone is able to verify that the release is authentic.
|
||||
The tags are named according to the versioning scheme I have adopted for the project.
|
||||
I explain this versioning system extensively in a blog post\cite{SemancatVersioning}.
|
||||
|
||||
The short version is that we use a solution that is a mix between
|
||||
semantic versioning%
|
||||
\footnote{\href{https://semver.org}{https://semver.org}}
|
||||
and calendar versioning%
|
||||
\footnote{\href{https://calver.org}{https://calver.org}}.
|
||||
Our release tags look similar to this one: \code{mainecoon-20180712}
|
||||
(this was the actual tag of an older release).
|
||||
The part before the ``\code{-}'' is the major version, which is always named after a breed
|
||||
of cat, for the additional fun factor, and because we love cats.
|
||||
The part after that is a timestamp of the day the release was made on.
|
||||
I only change major versions when I introduce backwards incompatible changes in the
|
||||
API of the framework, this way developers can trust that releases
|
||||
with the same majors are compatible with eachother in regards to client code.
|
||||
|
||||
The \code{master} branches of the frontend-TFW and test-TFW repositories are always
|
||||
kept compatible with the newest release tag of the baseimage.
|
||||
This is one of the ways the bootstrap script can operate safely: when cloning the three
|
||||
repositories, it checks out the newest tag of the baseimage before building it,
|
||||
ensuring that the newest released version is used for the newly created dev environment.
|
||||
|
18
listings/event_handler_example.py
Normal file
18
listings/event_handler_example.py
Normal file
@ -0,0 +1,18 @@
|
||||
from tfw import EventHandlerBase
|
||||
|
||||
class MyFirstEventHandler(EventHandlerBase):
|
||||
def __init__(self):
|
||||
super().__init__(self, key='fsm_update')
|
||||
|
||||
def handle_event(self, message):
|
||||
print('I have received a message! Yaaay!')
|
||||
|
||||
# the return value of this method is automatically
|
||||
# sent back to the TFW server
|
||||
return {
|
||||
'key': 'message',
|
||||
'data': {
|
||||
'originator': 'My first event handler',
|
||||
'message': f'I have received this message: {message}'
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user