That's awesome, Nick! Looking forward to seeing how this works out.

On Fri, May 3, 2019 at 10:06 AM Nick Allen <n...@nickallen.org> wrote:

> I'm exploring the use of TestContainers right now as part of the HDP 3.1
> effort.  Still exploring feasibility, but it is looking promising.
>
> On Fri, May 3, 2019 at 10:46 AM Justin Leet <justinjl...@gmail.com> wrote:
>
> > I think everything Casey mentioned is a good call-out as things start to
> > build into specifics. I definitely agree it's a very nontrivial amount of
> > work, but that lowering the barrier of entry to a lot of PRs eases the
> > burden on both new and existing contributors by a substantial amount.
> >
> > @Mike,
> > As a heads up, I (super briefly) looked into the Docker stuff a bit, and
> > the extension idea may not work with the Docker stuff to the extent we
> want
> > (at least without us doing some additional work ourselves).  It seems
> like
> > at least what I linked earlier and some other stuff actually provide
> direct
> > annotations rather than plugging directly into the same extensions idea.
> >
> > Before we dive into it too much, it might be worth playing around with it
> > more and coming back to the group with a couple options. If you're
> > interested in looking into it, I *suspect* it'll boil down to a couple
> > options
> > * Use Docker with something like the above link or testcontainers
> > <https://www.testcontainers.org/>. It's possible the Docker stuff ends
> up
> > being lightweight / fast enough to use on at least a per class basis like
> > we do now, rather than trying to generalize across all tests immediately.
> > * Roll our own code to have more fine-grained control over the Docker
> > lifecycle and which components need to be spun up for extensions.
> > * Figure out how to make the prior options play nice
> > * Other
> >
> > I'll probably dig a bit on my own, but I'm not sure how much focused time
> > I'll be able to put into it in the absolute immediate term.  I can
> probably
> > whip up a quick demo of the extensions stuff over the next week or so in
> a
> > one-off project to give a bit of a demo and maybe help out with some of
> > experimentation. Feel free to reach out if there's anything in particular
> > that would be helpful to look into.
> >
> > The extensions stuff does have a lot of benefits, but I had less
> components
> > to work with and didn't have the same classpath worries that made real
> > instances (i.e. Docker) more attractive. It was sufficient for our
> > purposes, but there might have to be compromises here. We depend on a lot
> > more of the Hadoop stack.
> >
> > Migrating to JUnit 5 in general *should* be pretty easy. I don't think we
> > really use any of the stuff that migrated in odd ways, so it should
> mostly
> > just be updating annotations and imports (@Before to @BeforeEach, etc.).
> > I'm sure this glosses over at least a few gotchas, though.
> >
> > On Fri, May 3, 2019 at 10:09 AM Michael Miklavcic <
> > michael.miklav...@gmail.com> wrote:
> >
> > > I didn't get a chance to say so earlier, but Justin, I also like the
> > JUnit
> > > 5 extension suggestion. I've gone through some en-masse changes before,
> > > e.g. standardizing the log4j construction idiom, and it honestly wasn't
> > too
> > > bad. Just a thought, it might make sense to kick this off by upgrading
> > > overall JUnit 4 to 5 across the code base, and then diving into some of
> > the
> > > more 5-specific changes you're recommending as needed. I created this
> > Jira
> > > a bit ago - https://issues.apache.org/jira/browse/METRON-2037. That
> was
> > to
> > > upgrade to 4.13, but we might be able to kill 2 birds with one stone if
> > we
> > > go to JUnit 5. I'm volunteering to look into this and/or see the work
> > > through to completion. What do you think?
> > >
> > > > - debuggability (right now we run the tests in the same JVM and
> setting
> > >    breakpoints is trivial, even in the innards of Hadoop.  This is very
> > >    valuable for figuring out what's going wrong and we'll need SOME
> > > solution
> > >    for it)
> > >
> > > Yeah Casey, I remember this from the last time we discussed it. That's
> > the
> > > most import issue to be sure we have a handle on, imo. We'll need to
> > figure
> > > out remote debugging in Docker containers. Not to mention, the
> execution
> > > path becomes a bit more spread out when we're running multiple
> components
> > > as nature intended across multiple processes.
> > >
> > >
> > >
> > > On Fri, May 3, 2019 at 7:14 AM Casey Stella <ceste...@gmail.com>
> wrote:
> > >
> > > > I just want to chime in and say I'm STRONGLY in favor of a
> docker-based
> > > > approach to testing (I specifically like the JUnit 5 extensions
> > > > suggestion).  I think that forcing a full-dev evaluation for every
> > small
> > > PR
> > > > is a barrier to entry that I'd like to overcome.  I also think that
> > this
> > > is
> > > > going to not be trivial.
> > > >
> > > > There will be weirdness/drama with:
> > > >
> > > >    - cleanup
> > > >    - setup in situations where multi-components are used
> > > >    - debuggability (right now we run the tests in the same JVM and
> > > setting
> > > >    breakpoints is trivial, even in the innards of Hadoop.  This is
> very
> > > >    valuable for figuring out what's going wrong and we'll need SOME
> > > > solution
> > > >    for it)
> > > >    - possible resource limitations in travis for running tests with
> > > >    multiple components
> > > >
> > > > Even so, with ALL of that being said, I still think the value
> outweighs
> > > the
> > > > difficulty by a factor of 10.  Being able to be confident after a
> > travis
> > > > run that people aren't introducing subtle classpath or
> cross-component
> > > > interaction issues would open up 80% of the class of PRs that don't
> > > require
> > > > full-dev review.  That being said, I still don't think it's 100%.
> > > > Specifically, PRs which can credibly be argued that they touch
> > > installation
> > > > pathways would still need to be verified in full-dev as it's the only
> > > path
> > > > to validating that (otherwise we would be regressing in test
> coverage).
> > > >
> > > > On Wed, May 1, 2019 at 9:33 PM Justin Leet <justinjl...@gmail.com>
> > > wrote:
> > > >
> > > > > >
> > > > > > My impression is that this is already the status quo. But, if we
> > > think
> > > > we
> > > > > > need to be more clear on this, let's put up a vote to change the
> > > coding
> > > > > > guidelines and PR checklist. I've done this many times in the
> past,
> > > the
> > > > > > most obvious instances are when I've made doc changes or unit
> test
> > > > > > modifications because those will not impact full dev. I will own
> > this
> > > > > item.
> > > > > > I think it can probably get rolled in with my dev guideline
> changes
> > > for
> > > > > > architecture diagrams.
> > > > >
> > > > >
> > > > > For completeness in our PR checklist: "- [ ] Have you verified the
> > > basic
> > > > > functionality of the build by building and running locally with
> > Vagrant
> > > > > full-dev environment or the equivalent?"  In practice, you're
> right,
> > > but
> > > > > any newer contributors aren't necessarily going to know this.
> > > > >
> > > > > 1. I think we should create Jiras with the end deliverable being
> that
> > > our
> > > > > > private vs public API endpoints are clearly delineated. From
> there,
> > > we
> > > > > > create another round of javadoc - for the public APIs let the
> > > javadocs
> > > > > rain
> > > > > > from the heavens to your heart's content. It's for public
> > consumption
> > > > and
> > > > > > should assist end users. See Mockito, for example -
> > > > > >
> > > > > >
> > > > >
> > > >
> > >
> >
> https://static.javadoc.io/org.mockito/mockito-core/2.27.0/org/mockito/Mockito.html
> > > > > > .
> > > > > > For developer docs, I'm of the *extremely strong* opinion that
> this
> > > > > should
> > > > > > be limited. Emphasize module, package, class, and method naming
> > > > > conventions
> > > > > > over all else. If it doesn't make sense just reading the code,
> > take a
> > > > > > minute to summarize what you're doing and consider refactoring.
> For
> > > > > > legitimately more complex and necessary code passages, add a
> note.
> > > For
> > > > > > multi-class interactions that provide a larger story arc, add dev
> > > docs
> > > > to
> > > > > > the relevant READMEs. Our use of Zookeeper Curator and its
> > > interaction
> > > > > with
> > > > > > our topology config loading is a perfect example of a feature
> that
> > > > would
> > > > > > fit this need.
> > > > > >
> > > > > 2. I'm an immediate -1 on any documentation that looks like " /**
> > Open
> > > > the
> > > > > > car door **/ public void openCarDoor() {...}" :-). The code
> speaks
> > > for
> > > > > > itself.
> > > > > > 3. Publish javadocs for public APIs, not our internal dev APIs.
> Let
> > > > your
> > > > > > fav IDE fill in the gaps for devs.
> > > > >
> > > > >
> > > > > I'm +1 on delineating public vs private APIs like you've outlined
> > > > there.  I
> > > > > think our dev stuff is *better* than our general usage guides, but
> > > > there's
> > > > > room for improvement. I'm fairly agnostic on the dev docs because
> to
> > be
> > > > > honest, a ton of our older code is not at all self explanatory, and
> > to
> > > be
> > > > > blunt refactoring a lot of it is a substantial lift (as we've all
> > seen
> > > > > multiple times trying to refactor it).  If this were greenfield,
> I'd
> > be
> > > > in
> > > > > much stronger agreement with you, but I suspect in practice
> there's a
> > > lot
> > > > > of stuff nobody's going to refactor for awhile.
> > > > >
> > > > >
> > > > > > Full dev until we vote to replace the existing setup and can be
> > > > confident
> > > > > > that the new approach 1. is stable, 2. takes <= the amount of
> time
> > to
> > > > > > complete as full dev. I am +1 for migrating towards this approach
> > and
> > > > > think
> > > > > > we should do so when it's dialed in.
> > > > >
> > > > >
> > > > > Great, I look forward to that getting in.
> > > > >
> > > > > Justin, what are your thoughts on leveraging this approach along
> with
> > > > > > long-lived Docker containers?
> > > > > >
> > > > >
> > > > > Apparently, there's actually an extension for running Docker
> > > containers,
> > > > > see  https://faustxvi.github.io/junit5-docker/.  My main
> hesitation
> > > > there
> > > > > is more around how much effort to migrate it is. I think that's
> > almost
> > > > > certainly a cleaner long term solution, but I suspect the 80%
> > solution
> > > of
> > > > > migrating what we have *might* be easier.  There might also be ways
> > of
> > > > just
> > > > > leveraging this by moving stuff over to failsafe from surefire,
> but I
> > > > > really don't know enough about it.
> > > > >
> > > > >  Clean/reset component state after test method and/or test class
> > > > > >    completion
> > > > >
> > > > >
> > > > > Probably doable regardless of approach, but things can take
> > nontrivial
> > > > > amounts of time to clean up (e.g. topic deletion or clearing). I
> > > believe
> > > > we
> > > > > do this right now, so I'd expect to continue with that.
> > > > >
> > > > >
> > > > > On Wed, May 1, 2019 at 8:48 PM Michael Miklavcic <
> > > > > michael.miklav...@gmail.com> wrote:
> > > > >
> > > > > > Justin, what are your thoughts on leveraging this approach along
> > with
> > > > > > long-lived Docker containers? I think the lifecycle would look
> > like:
> > > > > >
> > > > > >    1. I need components A, B, C
> > > > > >    2. If not started, start A, B, C
> > > > > >    3. If started, clean/reset it
> > > > > >    4. Setup pre-test state
> > > > > >    5. Run test(s)
> > > > > >    6. Clean/reset component state after test method and/or test
> > class
> > > > > >    completion (we may consider nuking this step - I assisted in
> > > > designing
> > > > > > an
> > > > > >    acceptance testing framework in the past where we handled
> > cleanup
> > > on
> > > > > the
> > > > > >    front end. This meant that remediation for failed tests became
> > > > simpler
> > > > > >    because I still had the state from the failed test run)
> > > > > >
> > > > > > Stopping/removing the containers could be a manual process or
> just
> > a
> > > > > simple
> > > > > > script in the project root. We could also add a special module
> that
> > > > runs
> > > > > > last that handles shutting down containers, if desired.
> > > > > >
> > > > > > I know this has been a perennial thread for us. I can dig up the
> > > > original
> > > > > > discuss threads on this as well if folks think they're still
> > > pertinent,
> > > > > but
> > > > > > I think we're pretty far removed now from that original point in
> > time
> > > > and
> > > > > > should just move forward with fresh perspectives.
> > > > > >
> > > > > > On Wed, May 1, 2019 at 9:21 AM Justin Leet <
> justinjl...@gmail.com>
> > > > > wrote:
> > > > > >
> > > > > > > Re: the integration testing point above, a strategy I used
> > recently
> > > > to
> > > > > > > alleviate a similar problem was to exploit JUnit 5's
> > extensions.  I
> > > > > > haven't
> > > > > > > played with this at all in Metron's code, so 1) Take this with
> a
> > > > > several
> > > > > > > grains of salt and 2) Feel encouraged to point out anything
> > > > > > > wrong/problematic/ludicrous.  My use case was pretty tame and
> > easy
> > > to
> > > > > > > implement.
> > > > > > >
> > > > > > > Essentially, you can set up an extension backed by a singleton
> > > > cluster
> > > > > > (in
> > > > > > > the case I was doing, I had two extensions, one for a Kafka
> > cluster
> > > > and
> > > > > > one
> > > > > > > for MiniDfs).  The backing clusters expose some methods (i.e.
> > > create
> > > > > > topic,
> > > > > > > get brokers, get file system, etc.), which lets the tests
> classes
> > > > setup
> > > > > > > whatever they need. Classes that need them just use an
> annotation
> > > and
> > > > > can
> > > > > > > be setup under the hood to init only when tests in the current
> > run
> > > > > suite
> > > > > > > actually use them and spin down after all are done. This saved
> ~1
> > > min
> > > > > on
> > > > > > a
> > > > > > > 4 minute build.  It ends up being a pretty clean way to use
> them,
> > > > > > although
> > > > > > > we might need to be a bit more sophisticated, since my case was
> > > less
> > > > > > > complicated. The main messiness is that this necessarily
> invites
> > > > tests
> > > > > to
> > > > > > > interfere with each other (i.e. if multiple tests use the kafka
> > > topic
> > > > > > > "test", problems will be involved). We might be able to improve
> > on
> > > > > this.
> > > > > > >
> > > > > > > We could likely do something similar with our
> InMemoryComponents.
> > > > Right
> > > > > > now
> > > > > > > these are spun up on a per-test basis, rather than the overall
> > > suite.
> > > > > > This
> > > > > > > involves some setup in any class that wants them, just to be
> able
> > > to
> > > > > get
> > > > > > a
> > > > > > > cluster.  There's also some definition of spin up order and so
> > on,
> > > > > which
> > > > > > is
> > > > > > > already taken care of with the extensions (declaration order).
> > The
> > > > > other
> > > > > > > catch in our case is that we have way more code covered by
> JUnit
> > 4,
> > > > > which
> > > > > > > doesn't have the same capabilities.  That migration doesn't
> > > > necessarily
> > > > > > > have to be done all at once, but it is a potential substantial
> > pain
> > > > > > point.
> > > > > > >
> > > > > > > Basically, I'd hope to push management of our abstraction
> further
> > > > back
> > > > > > into
> > > > > > > actual JUnit so they're get more reuse across runs and it's
> > easily
> > > > > > > understood what a test needs and uses right up front.  In our
> > case,
> > > > the
> > > > > > > InMemoryComponents likely map to extensions.
> > > > > > >
> > > > > > > If we did something like this, it potentially solves a few
> > problems
> > > > > > > * Makes it easy to build an integration test that says "Give me
> > > these
> > > > > > > components".
> > > > > > > * Keeps it alive across any test that needs them
> > > > > > > * Only spins it up if there are tests running that do need
> them.
> > > Only
> > > > > > spins
> > > > > > > up the necessary components.
> > > > > > > * Lower our build times.
> > > > > > > * Interaction with components remains primarily through the
> same
> > > > > methods
> > > > > > > you'd normally interact (you can build producers/consumers, or
> > > > > whatever).
> > > > > > > * IMO, easier to explain and have people use.  I've had a
> couple
> > > > people
> > > > > > > pretty easily pick up on it.
> > > > > > >
> > > > > > > I can't share the code, but essentially it looks like (And I'm
> > sure
> > > > > email
> > > > > > > will butcher this, so I'm sorry in advance):
> > > > > > > @ExtendWith({<ExtensionOne.class, ExtensionTwo.class, ...})
> > > > > > > ...
> > > > > > > @BeforeAll
> > > > > > > public static void beforeAll() {
> > > > > > >    // Test specific setup, similar to before. But without the
> > > cluster
> > > > > > > creation work.
> > > > > > > }
> > > > > > >
> > > > > > > Everything else gets handled under the covers, with the caveat
> > that
> > > > > what
> > > > > > I
> > > > > > > needed to do was less involved than some of our tests, so there
> > may
> > > > be
> > > > > > some
> > > > > > > experimenting.
> > > > > > >
> > > > > > > On Wed, May 1, 2019 at 10:59 AM Justin Leet <
> > justinjl...@gmail.com
> > > >
> > > > > > wrote:
> > > > > > >
> > > > > > > > Hi all,
> > > > > > > >
> > > > > > > > I wanted to start a discussion on something near and dear to
> > all
> > > of
> > > > > our
> > > > > > > > hearts: The role of full-dev in our testing cycle.
> > > > > > > >
> > > > > > > > Right now, we require all PRs to have spun up the full-dev
> > > > > environment
> > > > > > > and
> > > > > > > > make sure that things flow through properly. In some cases,
> > this
> > > > is a
> > > > > > > > necessity, and in other cases, it's a fairly large burden on
> > > > current
> > > > > > and
> > > > > > > > potential contributors.
> > > > > > > >
> > > > > > > > So what do we need to do to reduce our dependence on full dev
> > and
> > > > > > > increase
> > > > > > > > our confidence in our CI process?
> > > > > > > >
> > > > > > > > My initial thoughts on this encompass a few things
> > > > > > > > * Increasing our ability to easily write automated tests. In
> > > > > > particular,
> > > > > > > I
> > > > > > > > think our integration testing is fairly hard and has some
> > > > structural
> > > > > > > issues
> > > > > > > > (e.g. our tests spin up components per Test class, not for
> the
> > > > > overall
> > > > > > > test
> > > > > > > > suite being run, which also increases build times, etc.). How
> > do
> > > we
> > > > > > make
> > > > > > > > this easier and have less boilerplate?  I have one potential
> > idea
> > > > > I'll
> > > > > > > > reply to this thread with.
> > > > > > > > * Unit tests in general. I'd argue that any area we thing
> need
> > > > > full-dev
> > > > > > > > spun up to be confident in needs more testing. Does anyone
> have
> > > any
> > > > > > > > opinions on which areas we have the least confidence in?
> Which
> > > > areas
> > > > > > of
> > > > > > > > code are people afraid to touch?
> > > > > > > > * Our general procedures. Should we not be requiring full-dev
> > on
> > > > all
> > > > > > PRs,
> > > > > > > > but maybe just asking for a justification why not (e.g. "I
> > don't
> > > > need
> > > > > > > > full-dev for this, because I added unit tests here and here
> and
> > > > > > > integration
> > > > > > > > tests for the these components?"). And then a reviewer can
> > > request
> > > > a
> > > > > > > > full-dev spin up if needed?  Could we stage this rollout
> (e.g.
> > > > > > > > metron-platform modules require it, but others don't, etc.?)
> > > > This'll
> > > > > > add
> > > > > > > > more pressure onto the release phase, so maybe that involves
> > > > fleshing
> > > > > > > out a
> > > > > > > > checklist of critical path items to check.
> > > > > > > > * Do we need to improve our docs? Publish Javadocs? After
> all,
> > if
> > > > > docs
> > > > > > > are
> > > > > > > > better, hopefully we'd see less issues introduced and be more
> > > > > confident
> > > > > > > in
> > > > > > > > changes coming in.
> > > > > > > > * What environment do we even want testing to occur in?
> > > > > > > > https://github.com/apache/metron/pull/1261 has seen a lot of
> > > work,
> > > > > and
> > > > > > > > getting it across the finish line may help make the dev
> > > environment
> > > > > > less
> > > > > > > > onerous, even if still needed.
> > > > > > > >
> > > > > > >
> > > > > >
> > > > >
> > > >
> > >
> >
>

Reply via email to